LyoKICoKICogKEMpIENvcHlyaWdodCAyMDAyCiAqIERhbmllbCBFbmdzdHL2bSwgT21pY3JvbiBDZXRpIEFCIDxkYW5pZWxAb21pY3Jvbi5zZT4uCiAqCiAqIFNlZSBmaWxlIENSRURJVFMgZm9yIGxpc3Qgb2YgcGVvcGxlIHdobyBjb250cmlidXRlZCB0byB0aGlzCiAqIHByb2plY3QuCiAqCiAqIFRoaXMgcHJvZ3JhbSBpcyBmcmVlIHNvZnR3YXJlOyB5b3UgY2FuIHJlZGlzdHJpYnV0ZSBpdCBhbmQvb3IKICogbW9kaWZ5IGl0IHVuZGVyIHRoZSB0ZXJtcyBvZiB0aGUgR05VIEdlbmVyYWwgUHVibGljIExpY2Vuc2UgYXMKICogcHVibGlzaGVkIGJ5IHRoZSBGcmVlIFNvZnR3YXJlIEZvdW5kYXRpb247IGVpdGhlciB2ZXJzaW9uIDIgb2YKICogdGhlIExpY2Vuc2UsIG9yIChhdCB5b3VyIG9wdGlvbikgYW55IGxhdGVyIHZlcnNpb24uCiAqCiAqIFRoaXMgcHJvZ3JhbSBpcyBkaXN0cmlidXRlZCBpbiB0aGUgaG9wZSB0aGF0IGl0IHdpbGwgYmUgdXNlZnVsLAogKiBidXQgV0lUSE9VVCBBTlkgV0FSUkFOVFk7IHdpdGhvdXQgZXZlbiB0aGUgaW1wbGllZCB3YXJyYW50eSBvZgogKiBNRVJDSEFOVEFCSUxJVFkgb3IgRklUTkVTUyBGT1IgQSBQQVJUSUNVTEFSIFBVUlBPU0UuICBTZWUgdGhlCiAqIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlIGZvciBtb3JlIGRldGFpbHMuCiAqCiAqIFlvdSBzaG91bGQgaGF2ZSByZWNlaXZlZCBhIGNvcHkgb2YgdGhlIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlCiAqIGFsb25nIHdpdGggdGhpcyBwcm9ncmFtOyBpZiBub3QsIHdyaXRlIHRvIHRoZSBGcmVlIFNvZnR3YXJlCiAqIEZvdW5kYXRpb24sIEluYy4sIDU5IFRlbXBsZSBQbGFjZSwgU3VpdGUgMzMwLCBCb3N0b24sCiAqIE1BIDAyMTExLTEzMDcgVVNBCiAqLwoKI2luY2x1ZGUgPGNvbW1vbi5oPgojaW5jbHVkZSA8cGNpLmg+CiNpbmNsdWRlIDxzc2kuaD4KI2luY2x1ZGUgPGFzbS9pby5oPgojaW5jbHVkZSA8YXNtL3BjaS5oPgojaW5jbHVkZSA8YXNtL2ljL3NjNTIwLmg+CgpERUNMQVJFX0dMT0JBTF9EQVRBX1BUUjsKCi8qCiAqIFRoZW9yeToKICogV2UgZmlyc3Qgc2V0IHVwIGFsbCBJUlFzIHRvIGJlIG5vbi1wY2ksIGVkZ2UgdHJpZ2dlcmVkLAogKiB3aGVuIHdlIGxhdGVyIGVudW1lcmF0ZSB0aGUgcGNpIGJ1cyBhbmQgcGNpX3NjNTIwX2ZpeHVwX2lycSgpIGdldHMKICogY2FsbGVkIHdlIHJlYWxsb2NhdGUgaXJxcyB0byB0aGUgcGNpIGJ1cyB3aXRoIHNjNTIwX3BjaV9zZXRfaXJxKCkKICogYXMgbmVlZGVkLiBXaGUgY2hvb3NlIHRoZSBpcnFzIHRvIGdyYW0gZnJvbSBhIGNvbmZpZ3VyYWJsZSBsaXN0CiAqIGluc2lkZSBwY2lfc2M1MjBfZml4dXBfaXJxKCkgKElmIHRoaXMgbGlzdCBjb250YWlucyBzdHVwaWQgaXJxJ3MKICogc3VjaCBhcyAwIHRobmdhcyB3aWxsIG5vdCB3b3JrKQogKi8KCnN0YXRpYyB2b2lkIGlycV9pbml0KHZvaWQpCnsKCS8qIGRpc2FibGUgZ2xvYmFsIGludGVycnVwdCBtb2RlICovCgl3cml0ZV9tbWNyX2J5dGUoU0M1MjBfUElDSUNSLCAweDQwKTsKCgkvKiBzZXQgYWxsIGlycXMgdG8gZWRnZSAqLwoJd3JpdGVfbW1jcl9ieXRlKFNDNTIwX01QSUNNT0RFLCAweDAwKTsKCXdyaXRlX21tY3JfYnl0ZShTQzUyMF9TTDFQSUNNT0RFLCAweDAwKTsKCXdyaXRlX21tY3JfYnl0ZShTQzUyMF9TTDJQSUNNT0RFLCAweDAwKTsKCgkvKiBhY3RpdmUgbG93IHBvbGFyaXR5IG9uIFBJQyBpbnRlcnJ1cHQgcGlucywKCSAqICBhY3RpdmUgaGlnaCBwb2xhcml0eSBvbiBhbGwgb3RoZXIgaXJxIHBpbnMgKi8KCXdyaXRlX21tY3Jfd29yZChTQzUyMF9JTlRQSU5QT0wsIDB4MDAwMCk7CgoJLyogc2V0IGlycSBudW1iZXIgbWFwcGluZyAqLwoJd3JpdGVfbW1jcl9ieXRlKFNDNTIwX0dQVE1SME1BUCwgU0M1MjBfSVJRX0RJU0FCTEVEKTsgICAvKiBkaXNhYmxlIEdQIHRpbWVyIDAgSU5UICovCgl3cml0ZV9tbWNyX2J5dGUoU0M1MjBfR1BUTVIxTUFQLCBTQzUyMF9JUlFfRElTQUJMRUQpOyAgIC8qIGRpc2FibGUgR1AgdGltZXIgMSBJTlQgKi8KCXdyaXRlX21tY3JfYnl0ZShTQzUyMF9HUFRNUjJNQVAsIFNDNTIwX0lSUV9ESVNBQkxFRCk7ICAgLyogZGlzYWJsZSBHUCB0aW1lciAyIElOVCAqLwoJd3JpdGVfbW1jcl9ieXRlKFNDNTIwX1BJVDBNQVAsIFNDNTIwX0lSUTApOyAgICAgICAgICAgICAvKiBTZXQgUElUIHRpbWVyIDAgSU5UIHRvIElSUTAgKi8KCXdyaXRlX21tY3JfYnl0ZShTQzUyMF9QSVQxTUFQLCBTQzUyMF9JUlFfRElTQUJMRUQpOyAgICAgLyogZGlzYWJsZSBQSVQgdGltZXIgMSBJTlQgKi8KCXdyaXRlX21tY3JfYnl0ZShTQzUyMF9QSVQyTUFQLCBTQzUyMF9JUlFfRElTQUJMRUQpOyAgICAgLyogZGlzYWJsZSBQSVQgdGltZXIgMiBJTlQgKi8KCXdyaXRlX21tY3JfYnl0ZShTQzUyMF9QQ0lJTlRBTUFQLCBTQzUyMF9JUlFfRElTQUJMRUQpOyAgLyogZGlzYWJsZSBQQ0kgSU5UIEEgKi8KCXdyaXRlX21tY3JfYnl0ZShTQzUyMF9QQ0lJTlRCTUFQLCBTQzUyMF9JUlFfRElTQUJMRUQpOyAgLyogZGlzYWJsZSBQQ0kgSU5UIEIgKi8KCXdyaXRlX21tY3JfYnl0ZShTQzUyMF9QQ0lJTlRDTUFQLCBTQzUyMF9JUlFfRElTQUJMRUQpOyAgLyogZGlzYWJsZSBQQ0kgSU5UIEMgKi8KCXdyaXRlX21tY3JfYnl0ZShTQzUyMF9QQ0lJTlRETUFQLCBTQzUyMF9JUlFfRElTQUJMRUQpOyAgLyogZGlzYWJsZSBQQ0kgSU5UIEQgKi8KCXdyaXRlX21tY3JfYnl0ZShTQzUyMF9ETUFCQ0lOVE1BUCwgU0M1MjBfSVJRX0RJU0FCTEVEKTsgLyogZGlzYWJsZSBETUEgSU5UICovCgl3cml0ZV9tbWNyX2J5dGUoU0M1MjBfU1NJTUFQLCBTQzUyMF9JUlE2KTsgICAgICAgICAgICAgIC8qIFNldCBTeW5jaHJvbml1cyBzZXJpYWwgSU5UIHRvIElSUTYqLwoJd3JpdGVfbW1jcl9ieXRlKFNDNTIwX1dEVE1BUCwgU0M1MjBfSVJRX0RJU0FCTEVEKTsgICAgICAvKiBkaXNhYmxlIFdhdGNoZG9nIElOVCAqLwoJd3JpdGVfbW1jcl9ieXRlKFNDNTIwX1JUQ01BUCwgU0M1MjBfSVJROCk7ICAgICAgICAgICAgICAvKiBTZXQgUlRDIGludCB0byA4ICovCgl3cml0ZV9tbWNyX2J5dGUoU0M1MjBfV1BWTUFQLCBTQzUyMF9JUlFfRElTQUJMRUQpOyAgICAgIC8qIGRpc2FibGUgd3JpdGUgcHJvdGVjdCBJTlQgKi8KCXdyaXRlX21tY3JfYnl0ZShTQzUyMF9JQ0VNQVAsIFNDNTIwX0lSUTEpOyAgICAgICAgICAgICAgLyogU2V0IElDRSBEZWJ1ZyBTZXJpZWxwb3J0IElOVCB0byBJUlExICovCgl3cml0ZV9tbWNyX2J5dGUoU0M1MjBfRkVSUk1BUCxTQzUyMF9JUlExMyk7ICAgICAgICAgICAgIC8qIFNldCBGUCBlcnJvciBJTlQgdG8gSVJRMTMgKi8KCgl3cml0ZV9tbWNyX2J5dGUoU0M1MjBfVUFSVDFNQVAsIFNDNTIwX0lSUTQpOyAgICAgICAgICAgIC8qIFNldCBpbnRlcm5hbCBVQVJUMiBJTlQgdG8gSVJRNCAqLwoJd3JpdGVfbW1jcl9ieXRlKFNDNTIwX1VBUlQyTUFQLCBTQzUyMF9JUlEzKTsgICAgICAgICAgICAvKiBTZXQgaW50ZXJuYWwgVUFSVDIgSU5UIHRvIElSUTMgKi8KCgl3cml0ZV9tbWNyX2J5dGUoU0M1MjBfR1AwSU1BUCwgU0M1MjBfSVJRNyk7ICAgICAgICAgICAgIC8qIFNldCBHUElSUTAgKFBDLUNhcmQgQVVYIElSUSkgdG8gSVJRNyAqLwoJd3JpdGVfbW1jcl9ieXRlKFNDNTIwX0dQMUlNQVAsIFNDNTIwX0lSUTE0KTsgICAgICAgICAgICAvKiBTZXQgR1BJUlExIChDRiBJUlEpIHRvIElSUTE0ICovCgl3cml0ZV9tbWNyX2J5dGUoU0M1MjBfR1AzSU1BUCwgU0M1MjBfSVJRNSk7ICAgICAgICAgICAgIC8qIFNldCBHUElSUTMgKCBDQU4gSVJRICkgdGkgSVJRNSAqLwoJd3JpdGVfbW1jcl9ieXRlKFNDNTIwX0dQNElNQVAsIFNDNTIwX0lSUV9ESVNBQkxFRCk7ICAgICAvKiBkaXNiYWxlIEdJUlE0ICggSVJSIElSUSApICovCgl3cml0ZV9tbWNyX2J5dGUoU0M1MjBfR1A1SU1BUCwgU0M1MjBfSVJRX0RJU0FCTEVEKTsgICAgIC8qIGRpc2FibGUgR1BJUlE1ICovCgl3cml0ZV9tbWNyX2J5dGUoU0M1MjBfR1A2SU1BUCwgU0M1MjBfSVJRX0RJU0FCTEVEKTsgICAgIC8qIGRpc2FibGUgR1BJUlE2ICovCgl3cml0ZV9tbWNyX2J5dGUoU0M1MjBfR1A3SU1BUCwgU0M1MjBfSVJRX0RJU0FCTEVEKTsgICAgIC8qIGRpc2FibGUgR1BJUlE3ICovCgl3cml0ZV9tbWNyX2J5dGUoU0M1MjBfR1A4SU1BUCwgU0M1MjBfSVJRX0RJU0FCTEVEKTsgICAgIC8qIGRpc2FibGUgR1BJUlE4ICovCgl3cml0ZV9tbWNyX2J5dGUoU0M1MjBfR1A5SU1BUCwgU0M1MjBfSVJRX0RJU0FCTEVEKTsgICAgIC8qIGRpc2FibGUgR1BJUlE5ICovCgl3cml0ZV9tbWNyX2J5dGUoU0M1MjBfR1AySU1BUCwgU0M1MjBfSVJRX0RJU0FCTEVEKTsgICAgIC8qIGRpc2FibGUgR1BJUlEyICovCgl3cml0ZV9tbWNyX2J5dGUoU0M1MjBfR1AxMElNQVAsU0M1MjBfSVJRX0RJU0FCTEVEKTsgICAgIC8qIGRpc2FibGUgR1BJUlExMCAqLwoKCXdyaXRlX21tY3Jfd29yZChTQzUyMF9QQ0lIT1NUTUFQLCAweDExZik7ICAgICAgICAgICAgICAgLyogTWFwIFBDSSBob3N0YnJpZGdlIElOVCB0byBOTUkgKi8KCXdyaXRlX21tY3Jfd29yZChTQzUyMF9FQ0NNQVAsIDB4MTAwKTsgICAgICAgICAgICAgICAgICAgLyogTWFwIFNEUkFNIEVDQyBmYWlsdXJlIElOVCB0byBOTUkgKi8KCn0KCgovKiBQQ0kgc3R1ZmYgKi8Kc3RhdGljIHZvaWQgcGNpX3NjNTIwX3NwdW5rX2ZpeHVwX2lycShzdHJ1Y3QgcGNpX2NvbnRyb2xsZXIgKmhvc2UsIHBjaV9kZXZfdCBkZXYpCnsKCWludCB2ZXJzaW9uID0gcmVhZF9tbWNyX2J5dGUoU0M1MjBfU1lTSU5GTyk7CgoJLyogYSBjb25maWd1cmFibGUgbGlzdHMgb2YgaXJxcyB0byBzdGVhbAoJICogd2hlbiB3ZSBuZWVkIG9uZSAoYSBib2FyZCB3aXRoIG1vcmUgcGNpIGludGVycnVwdCBwaW5zCgkgKiB3b3VsZCB1c2UgYSBsYXJnZXIgdGFibGUgKi8KCXN0YXRpYyBpbnQgaXJxX2xpc3RbXSA9IHsKCQlDRkdfRklSU1RfUENJX0lSUSwKCQlDRkdfU0VDT05EX1BDSV9JUlEsCgkJQ0ZHX1RISVJEX1BDSV9JUlEsCgkJQ0ZHX0ZPUlRIX1BDSV9JUlEKCX07CglzdGF0aWMgaW50IG5leHRfaXJxX2luZGV4PTA7CgoJY2hhciB0bXBfcGluOwoJaW50IHBpbjsKCglwY2lfaG9zZV9yZWFkX2NvbmZpZ19ieXRlKGhvc2UsIGRldiwgUENJX0lOVEVSUlVQVF9QSU4sICZ0bXBfcGluKTsKCXBpbiA9IHRtcF9waW47CgoJcGluLT0xOyAvKiBwY2kgY29uZmlnIHNwYWNlIHVzZSAxLWJhc2VkIG51bWJlcmluZyAqLwoJaWYgKC0xID09IHBpbikgewoJCXJldHVybjsgLyogZGV2aWNlIHVzZSBubyBpcnEgKi8KCX0KCgoJLyogbWFwIGRldmljZSBudW1iZXIgKyAgcGluIHRvIGEgcGluIG9uIHRoZSBzYzUyMCAqLwoJc3dpdGNoIChQQ0lfREVWKGRldikpIHsKCWNhc2UgNjogIC8qIEVUSDAgKi8KCQlwaW4rPVNDNTIwX1BDSV9JTlRBOwoJCWJyZWFrOwoKCWNhc2UgNzogIC8qIEVUSDEgKi8KCQlwaW4rPVNDNTIwX1BDSV9JTlRCOwoJCWJyZWFrOwoKCWNhc2UgODogIC8qIENyeXB0byAqLwoJCXBpbis9U0M1MjBfUENJX0lOVEM7CgkJYnJlYWs7CgoJY2FzZSA5OiAvKiBQTUMgc2xvdCAqLwoJCXBpbis9U0M1MjBfUENJX0lOVEQ7CgkJYnJlYWs7CgoJY2FzZSAxMDogLyogUEMtQ2FyZCAqLwoKCQlpZiAodmVyc2lvbiA8IDEwKSB7CgkJCXBpbis9U0M1MjBfUENJX0lOVEQ7CgkJfSBlbHNlIHsKCQkJcGluKz1TQzUyMF9QQ0lfSU5UQzsKCQl9CgkJYnJlYWs7CgoJZGVmYXVsdDoKCQlyZXR1cm47Cgl9CgoJcGluJj0zOyAvKiB3cmFwIGFyb3VuZCAqLwoKCWlmIChzYzUyMF9wY2lfaW50c1twaW5dID09IC0xKSB7CgkJLyogcmUtcm91dGUgb25lIGludGVycnVwdCBmb3IgdXMgKi8KCQlpZiAobmV4dF9pcnFfaW5kZXggPiAzKSB7CgkJCXJldHVybjsKCQl9CgkJaWYgKHBjaV9zYzUyMF9zZXRfaXJxKHBpbiwgaXJxX2xpc3RbbmV4dF9pcnFfaW5kZXhdKSkgewoJCQlyZXR1cm47CgkJfQoJCW5leHRfaXJxX2luZGV4Kys7Cgl9CgoKCWlmICgtMSAhPSBzYzUyMF9wY2lfaW50c1twaW5dKSB7CgkJcGNpX2hvc2Vfd3JpdGVfY29uZmlnX2J5dGUoaG9zZSwgZGV2LCBQQ0lfSU5URVJSVVBUX0xJTkUsCgkJCQkJICAgc2M1MjBfcGNpX2ludHNbcGluXSk7Cgl9CiNpZiAwCglwcmludGYoImZpeHVwX2lycTogZGV2aWNlICVkIHBpbiAlYyBpcnEgJWRcbiIsCgkgICAgICAgUENJX0RFVihkZXYpLCAnQScgKyBwaW4sIHNjNTIwX3BjaV9pbnRzW3Bpbl0pOwojZW5kaWYKfQoKCnN0YXRpYyB2b2lkIHBjaV9zYzUyMF9zcHVua19jb25maWd1cmVfY2FyZGJ1cyhzdHJ1Y3QgcGNpX2NvbnRyb2xsZXIgKmhvc2UsCgkJCQkJICAgICAgcGNpX2Rldl90IGRldiwgc3RydWN0IHBjaV9jb25maWdfdGFibGUgKnRlKQp7Cgl1MzIgaW9fYmFzZTsKCXUzMiB0ZW1wOwoKCXBjaWF1dG9fY29uZmlnX2RldmljZShob3NlLCBkZXYpOwoKCXBjaV9ob3NlX3dyaXRlX2NvbmZpZ193b3JkKGhvc2UsIGRldiwgUENJX0NPTU1BTkQsIDB4MDcpOyAgLyogZW5hYmxlIGRldmljZSAqLwoJcGNpX2hvc2Vfd3JpdGVfY29uZmlnX2J5dGUoaG9zZSwgZGV2LCAweDBjLCAweDEwKTsgICAgICAgICAvKiBjYWNoZWxpbmUgc2l6ZSAqLwoJcGNpX2hvc2Vfd3JpdGVfY29uZmlnX2J5dGUoaG9zZSwgZGV2LCAweDBkLCAweDQwKTsgICAgICAgICAvKiBsYXRlbmN5IHRpbWVyICovCglwY2lfaG9zZV93cml0ZV9jb25maWdfYnl0ZShob3NlLCBkZXYsIDB4MWIsIDB4NDApOyAgICAgICAgIC8qIGNhcmRidXMgbGF0ZW5jeSB0aW1lciAqLwoJcGNpX2hvc2Vfd3JpdGVfY29uZmlnX3dvcmQoaG9zZSwgZGV2LCBQQ0lfQlJJREdFX0NPTlRST0wsIDB4MDA0MCk7ICAvKiByZXNldCBjYXJkYnVzICovCglwY2lfaG9zZV93cml0ZV9jb25maWdfd29yZChob3NlLCBkZXYsIFBDSV9CUklER0VfQ09OVFJPTCwgMHgwMDgwKTsgIC8qIHJvdXRlIGludGVycnVwdHMgdGhvdWdoIEV4Q0EgKi8KCXBjaV9ob3NlX3dyaXRlX2NvbmZpZ193b3JkKGhvc2UsIGRldiwgIDB4NDQsIDB4M2UwKTsgLyogbWFwIGxlZ2FjeSBJL08gcG9ydCB0byAweDNlMCAqLwoKCXBjaV9ob3NlX3JlYWRfY29uZmlnX2R3b3JkKGhvc2UsIGRldiwgIDB4ODAsICZ0ZW1wKTsgLyogU3lzdGVtIGNvbnRyb2wgKi8KCXBjaV9ob3NlX3dyaXRlX2NvbmZpZ19kd29yZChob3NlLCBkZXYsICAweDgwLCB0ZW1wIHwgMHg2MCk7IC8qIFN5c3RlbSBjb250cm9sOiBkaXNhYmxlIGNsb2NrcnVuICovCgkvKiByb3V0ZSBNRjAgdG8gfklOVCBhbmQgTUYzIHRvIElSUTcKCSAqIHJlc2VydmUgYWxsIG90aGVycyAqLwoJcGNpX2hvc2Vfd3JpdGVfY29uZmlnX2R3b3JkKGhvc2UsIGRldiwgMHg4YywgMHgwMDAwNzAwMik7CglwY2lfaG9zZV93cml0ZV9jb25maWdfYnl0ZShob3NlLCBkZXYsIDB4OTEsIDB4MDApOyAgICAvKiBjYXJkIGNvbnRyb2wgKi8KCXBjaV9ob3NlX3dyaXRlX2NvbmZpZ19ieXRlKGhvc2UsIGRldiwgMHg5MiwgMHg2Mik7ICAgIC8qIGRldmljZSBjb250cm9sICovCgoJaWYgKHRlLT5kZXZpY2UgIT0gMHhhYzU2KSB7CgkJcGNpX2hvc2Vfd3JpdGVfY29uZmlnX2J5dGUoaG9zZSwgZGV2LCAweDkzLCAweDIxKTsgICAgLyogYXN5bmMgaW50ZXJydXB0IGVuYWJsZSAqLwoJCXBjaV9ob3NlX3dyaXRlX2NvbmZpZ193b3JkKGhvc2UsIGRldiwgMHhhOCwgMHgwMDAwKTsgIC8qIHJlc2V0IEdQSU8gKi8KCQlwY2lfaG9zZV93cml0ZV9jb25maWdfd29yZChob3NlLCBkZXYsIDB4YWMsIDB4MDAwMCk7ICAvKiByZXNldCBHUElPICovCgkJcGNpX2hvc2Vfd3JpdGVfY29uZmlnX3dvcmQoaG9zZSwgZGV2LCAweGFhLCAweDAwMDApOyAgLyogcmVzZXQgR1BJTyAqLwoJCXBjaV9ob3NlX3dyaXRlX2NvbmZpZ193b3JkKGhvc2UsIGRldiwgMHhhZSwgMHgwMDAwKTsgIC8qIHJlc2V0IEdQSU8gKi8KCX0gZWxzZSB7CgkJcGNpX2hvc2Vfd3JpdGVfY29uZmlnX2J5dGUoaG9zZSwgZGV2LCAweDkzLCAweDIwKTsgICAgLyogICovCgl9CglwY2lfaG9zZV93cml0ZV9jb25maWdfd29yZChob3NlLCBkZXYsIDB4YTQsIDB4ODAwMCk7ICAvKiByZXNldCBwb3dlciBtYW5hZ2VtZW50ICovCgoKCXBjaV9ob3NlX3JlYWRfY29uZmlnX2R3b3JkKGhvc2UsIGRldiwgUENJX0JBU0VfQUREUkVTU18wLCAmaW9fYmFzZSk7Cglpb19iYXNlICY9IH4weGZMOwoKCXdyaXRlYigweDA3LCBpb19iYXNlKzB4ODAzKTsgLyogcm91dGUgQ1NDIGlycSB0aG91Z2ggRXhDQSBhbmQgZW5hYmxlIElSUTcgKi8KCXdyaXRlbCgwLCBpb19iYXNlKzB4MTApOyAgICAgLyogQ0xLUlVOIGRlZmF1bHQgKi8KCXdyaXRlbCgwLCBpb19iYXNlKzB4MjApOyAgICAgLyogQ0xLUlVOIGRlZmF1bHQgKi8KCn0KCgpzdGF0aWMgc3RydWN0IHBjaV9jb25maWdfdGFibGUgcGNpX3NjNTIwX3NwdW5rX2NvbmZpZ190YWJsZVtdID0gewoJeyAweDEwNGMsIDB4YWM1MCwgUENJX0FOWV9JRCwgMCwgMHgwYSwgMCwgcGNpX3NjNTIwX3NwdW5rX2NvbmZpZ3VyZV9jYXJkYnVzLCB7IDAsIDAsIDB9IH0sCgl7IDB4MTA0YywgMHhhYzU2LCBQQ0lfQU5ZX0lELCAwLCAweDBhLCAwLCBwY2lfc2M1MjBfc3B1bmtfY29uZmlndXJlX2NhcmRidXMsIHsgMCwgMCwgMH0gfSwKCXsgMCwgMCwgMCwgMCwgMCwgMCwgTlVMTCwgezAsMCwwfX0KfTsKCnN0YXRpYyBzdHJ1Y3QgcGNpX2NvbnRyb2xsZXIgc2M1MjBfc3B1bmtfaG9zZSA9IHsKCWZpeHVwX2lycTogcGNpX3NjNTIwX3NwdW5rX2ZpeHVwX2lycSwKCWNvbmZpZ190YWJsZTogcGNpX3NjNTIwX3NwdW5rX2NvbmZpZ190YWJsZSwKCWZpcnN0X2J1c25vOiAweDAwLAoJbGFzdF9idXNubzogMHhmZiwKfTsKCnZvaWQgcGNpX2luaXRfYm9hcmQodm9pZCkKewoJcGNpX3NjNTIwX2luaXQoJnNjNTIwX3NwdW5rX2hvc2UpOwp9CgoKLyogc2V0IHVwIHRoZSBJU0EgYnVzIHRpbWluZyBhbmQgc3lzdGVtIGFkZHJlc3MgbWFwcGluZ3MgKi8Kc3RhdGljIHZvaWQgYnVzX2luaXQodm9pZCkKewoJLyogdmVyc2lvbnMKCSAqIDAgICBIeWdsbyB2ZXJzaW9ucyAwLjk1IGFuZCAwLjk2IChsYXJnZSBiYW9yZHMpCgkgKiA/PyAgSHlnbG8gdmVyc2lvbiAwLjk3IChzbWFsbCBib2FyZCkKCSAqIDEwICBTcHVuayBib2FyZAoJICovCglpbnQgdmVyc2lvbiA9IHJlYWRfbW1jcl9ieXRlKFNDNTIwX1NZU0lORk8pOwoKCWlmICh2ZXJzaW9uKSB7CgkJLyogc2V0IHVwIHRoZSBHUCBJTyBwaW5zIChmb3IgdGhlIFNwdW5rIGJvYXJkKSAqLwoJCXdyaXRlX21tY3Jfd29yZChTQzUyMF9QSU9QRlMzMV8xNiwgMHhmZmYwKTsgCS8qIHNldCB0aGUgR1BJTyBwaW4gZnVuY3Rpb24gMzEtMTYgcmVnICovCgkJd3JpdGVfbW1jcl93b3JkKFNDNTIwX1BJT1BGUzE1XzAsICAweDAwMGYpOyAgCS8qIHNldCB0aGUgR1BJTyBwaW4gZnVuY3Rpb24gMTUtMCByZWcgKi8KCQl3cml0ZV9tbWNyX3dvcmQoU0M1MjBfUElPRElSMzFfMTYsIDB4MDAwZik7IAkvKiBzZXQgdGhlIEdQSU8gZGlyZWN0aW9uIDMxLTE2IHJlZyAqLwoJCXdyaXRlX21tY3Jfd29yZChTQzUyMF9QSU9ESVIxNV8wLCAgMHgxZmYwKTsgIAkvKiBzZXQgdGhlIEdQSU8gZGlyZWN0aW9uIDE1LTAgcmVnICovCgkJd3JpdGVfbW1jcl9ieXRlKFNDNTIwX0NTUEZTLCAweGMwKTsgIAkJLyogc2V0IHRoZSBDUyBwaW4gZnVuY3Rpb24gcmVnICovCgkJd3JpdGVfbW1jcl9ieXRlKFNDNTIwX0NMS1NFTCwgMHg3MCk7CgoJCXdyaXRlX21tY3Jfd29yZChTQzUyMF9QSU9DTFIzMV8xNiwgMHgwMDAzKTsgICAgIC8qIHJlc2V0IFNTSSBjaGlwLXNlbGVjdHMgKi8KCQl3cml0ZV9tbWNyX3dvcmQoU0M1MjBfUElPU0VUMzFfMTYsIDB4MDAwYyk7CgoJfSBlbHNlIHsKCQkvKiBzZXQgdXAgdGhlIEdQIElPIHBpbnMgKGZvciB0aGUgSHlnbG8gYm9hcmQpICovCgkJd3JpdGVfbW1jcl93b3JkKFNDNTIwX1BJT1BGUzMxXzE2LCAweGZmYzApOyAJLyogc2V0IHRoZSBHUElPIHBpbiBmdW5jdGlvbiAzMS0xNiByZWcgKi8KCQl3cml0ZV9tbWNyX3dvcmQoU0M1MjBfUElPUEZTMTVfMCwgMHgxZTdmKTsgIAkvKiBzZXQgdGhlIEdQSU8gcGluIGZ1bmN0aW9uIDE1LTAgcmVnICovCgkJd3JpdGVfbW1jcl93b3JkKFNDNTIwX1BJT0RJUjMxXzE2LCAweDAwM2YpOyAJLyogc2V0IHRoZSBHUElPIGRpcmVjdGlvbiAzMS0xNiByZWcgKi8KCQl3cml0ZV9tbWNyX3dvcmQoU0M1MjBfUElPRElSMTVfMCwgMHhlMTgwKTsgIAkvKiBzZXQgdGhlIEdQSU8gZGlyZWN0aW9uIDE1LTAgcmVnICovCgkJd3JpdGVfbW1jcl9ieXRlKFNDNTIwX0NTUEZTLCAweDAwKTsgIAkJLyogc2V0IHRoZSBDUyBwaW4gZnVuY3Rpb24gcmVnICovCgkJd3JpdGVfbW1jcl9ieXRlKFNDNTIwX0NMS1NFTCwgMHg3MCk7CgoJCXdyaXRlX21tY3Jfd29yZChTQzUyMF9QSU9DTFIxNV8wLCAweDAxODApOyAgICAgIC8qIHJlc2V0IFNTSSBjaGlwLXNlbGVjdHMgKi8KCX0KCgl3cml0ZV9tbWNyX2J5dGUoU0M1MjBfR1BDU1JULCAxKTsgICAvKiBzZXQgdGhlIEdQIENTIG9mZnNldCAqLwoJd3JpdGVfbW1jcl9ieXRlKFNDNTIwX0dQQ1NQVywgMyk7ICAgLyogc2V0IHRoZSBHUCBDUyBwdWxzZSB3aWR0aCAqLwoJd3JpdGVfbW1jcl9ieXRlKFNDNTIwX0dQQ1NPRkYsIDEpOyAgLyogc2V0IHRoZSBHUCBDUyBvZmZzZXQgKi8KCXdyaXRlX21tY3JfYnl0ZShTQzUyMF9HUFJEVywgMyk7ICAgIC8qIHNldCB0aGUgUkQgcHVsc2Ugd2lkdGggKi8KCXdyaXRlX21tY3JfYnl0ZShTQzUyMF9HUFJET0ZGLCAxKTsgIC8qIHNldCB0aGUgR1AgUkQgb2Zmc2V0ICovCgl3cml0ZV9tbWNyX2J5dGUoU0M1MjBfR1BXUlcsIDMpOyAgICAvKiBzZXQgdGhlIEdQIFdSIHB1bHNlIHdpZHRoICovCgl3cml0ZV9tbWNyX2J5dGUoU0M1MjBfR1BXUk9GRiwgMSk7ICAvKiBzZXQgdGhlIEdQIFdSIG9mZnNldCAqLwoKCXdyaXRlX21tY3Jfd29yZChTQzUyMF9CT09UQ1NDVEwsIDB4MDQwNyk7CQkvKiBzZXQgdXAgdGltaW5nIG9mIEJPT1RDUyAqLwoKCS8qIGFkanVzdCB0aGUgbWVtb3J5IG1hcDoKCSAqIGJ5IGRlZmF1bHQgdGhlIGZpcnN0IDI1Nk1CICgweDAwMDAwMDAwIC0gMHgwZmZmZmZmZikgaXMgbWFwcGVkIHRvIFNEUkFNCgkgKiBhbmQgMjU2TUIgdG8gMUctMTI4ayAgKDB4MTAwMDAwMCAtIDB4MzdmZmZmZmYpIGlzIG1hcHBlZCB0byBQQ0kgbW1pbwoJICogd2UgbmVlZCB0byBtYXAgMUctMTI4ayAtIDFHICgweDM4MDAwMDAwIC0gMHgzZmZmZmZmZikgdG8gQ1MxICovCgoKCS8qIGJvb3RjcyAqLwoJd3JpdGVfbW1jcl9sb25nKFNDNTIwX1BBUjEyLCAweDhiZmZlODAwKTsKCgkvKiBJREUwID0gR1BDUzYgMWYwLTFmNyAqLwoJd3JpdGVfbW1jcl9sb25nKFNDNTIwX1BBUjMsICAweDM4MDgwMWYwKTsKCgkvKiBJREUxID0gR1BDUzcgM2Y2ICovCgl3cml0ZV9tbWNyX2xvbmcoU0M1MjBfUEFSNCwgIDB4M2MwMDAzZjYpOwoKCWFzbSAoIndiaW52ZFxuIik7IC8qIEZsdXNoIGNhY2hlLCByZXEuIGFmdGVyIHNldHRpbmcgdGhlIHVuY2hhY2hlZCBhdHRyaWJ1dGUgb25hIFBBUiAqLwoKCXdyaXRlX21tY3JfYnl0ZShTQzUyMF9BRERERUNDVEwsIHJlYWRfbW1jcl9ieXRlKFNDNTIwX0FERERFQ0NUTCkgJiB+KFVBUlQyX0RJU3xVQVJUMV9ESVMpKTsKCn0KCgovKiBwYXIgdXNhZ2U6CiAqIFBBUjAgICAobGVnYWN5X3ZpZGVvKQogKiBQQVIxICAgKFBDSSBST00gbWFwcGluZykKICogUEFSMgogKiBQQVIzICAgSURFCiAqIFBBUjQgICBJREUKICogUEFSNSAgIChsZWdhY3lfdmlkZW8pCiAqIFBBUjYKICogUEFSNyAgIChsZWdhY3lfdmlkZW8pCiAqIFBBUjggICAobGVnYWN5X3ZpZGVvKQogKiBQQVI5ICAgKGxlZ2FjeV92aWRlbykKICogUEFSMTAKICogUEFSMTEgIChJU0FST00pCiAqIFBBUjEyICBCT09UQ1MKICogUEFSMTMKICogUEFSMTQKICogUEFSMTUKICovCgovKgogKiBUaGlzIGZ1bmN0aW9uIHNob3VsZCBtYXAgYSBjaHVuayBvZiBzaXplIGJ5dGVzCiAqIG9mIHRoZSBzeXN0ZW0gYWRkcmVzcyBzcGFjZSB0byB0aGUgSVNBIGJ1cwogKgogKiBUaGUgZnVuY3Rpb24gd2lsbCByZXR1cm4gdGhlIG1lbW9yeSBhZGRyZXNzCiAqIGFzIHNlZW4gYnkgdGhlIGhvc3QgKHdoaWNoIG1heSB2ZXJ5IHdpbGwgYmUgdGhlCiAqIHNhbWUgYXMgdGhlIGJ1cyBhZGRyZXNzKQogKi8KdTMyIGlzYV9tYXBfcm9tKHUzMiBidXNfYWRkciwgaW50IHNpemUpCnsKCXUzMiBwYXI7CgoJcHJpbnRmKCJpc2FfbWFwX3JvbSBhc2tlZCB0byBtYXAgJWQgYnl0ZXMgYXQgJXhcbiIsCgkgICAgICAgc2l6ZSwgYnVzX2FkZHIpOwoKCXBhciA9IHNpemU7CglpZiAocGFyIDwgMHg4MDAwMCkgewoJCXBhciA9IDB4ODAwMDA7Cgl9CglwYXIgPj49IDEyOwoJcGFyLS07CglwYXImPTB4N2Y7CglwYXIgPDw9IDE4OwoJcGFyIHw9IChidXNfYWRkcj4+MTIpOwoJcGFyIHw9IDB4NTAwMDAwMDA7CgoJcHJpbnRmICgic2V0dGluZyBQQVIxMSB0byAleFxuIiwgcGFyKTsKCgkvKiBNYXAgcm9tIDB4MTAwMDAgd2l0aCBQQVIxICovCgl3cml0ZV9tbWNyX2xvbmcoU0M1MjBfUEFSMTEsICBwYXIpOwoKCXJldHVybiBidXNfYWRkcjsKfQoKLyoKICogdGhpcyBmdW5jdGlvbiByZW1vdmVkIGFueSBtYXBwaW5nIGNyZWF0ZWQKICogd2l0aCBwY2lfZ2V0X3JvbV93aW5kb3coKQogKi8Kdm9pZCBpc2FfdW5tYXBfcm9tKHUzMiBhZGRyKQp7CglwcmludGYoImlzYV91bm1hcF9yb20gYXNrZWQgdG8gdW5tYXAgJXgiLCBhZGRyKTsKCWlmICgoYWRkcj4+MTIpID09IChyZWFkX21tY3JfbG9uZyhTQzUyMF9QQVIxMSkmMHgzZmZmZikpIHsKCQl3cml0ZV9tbWNyX2xvbmcoU0M1MjBfUEFSMTEsIDApOwoJCXByaW50ZigiIGRvbmVcbiIpOwoJCXJldHVybjsKCX0KCXByaW50ZigiIG5vdCBvdXJzXG4iKTsKfQoKI2lmZGVmIENPTkZJR19QQ0kKI2RlZmluZSBQQ0lfUk9NX1RFTVBfU1BBQ0UgMHgxMDAwMAovKgogKiBUaGlzIGZ1bmN0aW9uIHNob3VsZCBtYXAgYSBjaHVuayBvZiBzaXplIGJ5dGVzCiAqIG9mIHRoZSBzeXN0ZW0gYWRkcmVzcyBzcGFjZSB0byB0aGUgUENJIGJ1cywKICogc3VpdGFibGUgdG8gbWFwIFBDSSBST01TIChidXMgYWRkcmVzcyA8IDE2TSkKICogdGhlIGZ1bmN0aW9uIHdpbGwgcmV0dXJuIHRoZSBob3N0IG1lbW9yeSBhZGRyZXNzCiAqIHdoaWNoIHNob3VsZCBiZSBjb252ZXJ0ZWQgaW50byBhIGJ1cyBhZGRyZXNzCiAqIGJlZm9yZSB1c2VkIHRvIGNvbmZpZ3VyZSB0aGUgUENJIHJvbSBhZGRyZXNzCiAqIGRlY29kZXIKICovCnUzMiBwY2lfZ2V0X3JvbV93aW5kb3coc3RydWN0IHBjaV9jb250cm9sbGVyICpob3NlLCBpbnQgc2l6ZSkKewoJdTMyIHBhcjsKCglwYXIgPSBzaXplOwoJaWYgKHBhciA8IDB4ODAwMDApIHsKCQlwYXIgPSAweDgwMDAwOwoJfQoJcGFyID4+PSAxNjsKCXBhci0tOwoJcGFyJj0weDdmZjsKCXBhciA8PD0gMTQ7CglwYXIgfD0gKFBDSV9ST01fVEVNUF9TUEFDRT4+MTYpOwoJcGFyIHw9IDB4NzIwMDAwMDA7CgoJcHJpbnRmICgic2V0dGluZyBQQVIxIHRvICV4XG4iLCBwYXIpOwoKCS8qIE1hcCByb20gMHgxMDAwMCB3aXRoIFBBUjEgKi8KCXdyaXRlX21tY3JfbG9uZyhTQzUyMF9QQVIxLCAgcGFyKTsKCglyZXR1cm4gUENJX1JPTV9URU1QX1NQQUNFOwp9CgovKgogKiB0aGlzIGZ1bmN0aW9uIHJlbW92ZWQgYW55IG1hcHBpbmcgY3JlYXRlZAogKiB3aXRoIHBjaV9nZXRfcm9tX3dpbmRvdygpCiAqLwp2b2lkIHBjaV9yZW1vdmVfcm9tX3dpbmRvdyhzdHJ1Y3QgcGNpX2NvbnRyb2xsZXIgKmhvc2UsIHUzMiBhZGRyKQp7CglwcmludGYoInBjaV9yZW1vdmVfcm9tX3dpbmRvdzogJXgiLCBhZGRyKTsKCWlmIChhZGRyID09IFBDSV9ST01fVEVNUF9TUEFDRSkgewoJCXdyaXRlX21tY3JfbG9uZyhTQzUyMF9QQVIxLCAwKTsKCQlwcmludGYoIiBkb25lXG4iKTsKCQlyZXR1cm47Cgl9CglwcmludGYoIiBub3Qgb3Vyc1xuIik7Cgp9CgovKgogKiBUaGlzIGZ1bmN0aW9uIGlzIGNhbGxlZCBpbiBvcmRlciB0byBwcm92aWRlIGFjY2VzIHRvIHRoZQogKiBsZWdhY3kgdmlkZW8gSS9PIHBvcnRzIG9uIHRoZSBQQ0kgYnVzLgogKiBBZnRlciB0aGlzIGZ1bmN0aW9uIGFjY2Vzc2VzIHRvIEkvTyBwb3J0cyAweDNiMC0weDNiYiBhbmQKICogMHgzYzAtMHgzZGYgc2h1bGQgcmVzdWx0IGluIHRyYW5zYWN0aW9ucyBvbiB0aGUgUENJIGJ1cy4KICoKICovCmludCBwY2lfZW5hYmxlX2xlZ2FjeV92aWRlb19wb3J0cyhzdHJ1Y3QgcGNpX2NvbnRyb2xsZXIgKmhvc2UpCnsKCS8qIE1hcCB2aWRlbyBtZW1vcnkgdG8gMHhhMDAwMCovCgl3cml0ZV9tbWNyX2xvbmcoU0M1MjBfUEFSMCwgIDB4NzIwMDQwMGEpOwoKCS8qIGZvcndhcmQgYWxsIEkvTyBhY2Nlc3NlcyB0byBQQ0kgKi8KCXdyaXRlX21tY3JfYnl0ZShTQzUyMF9BRERERUNDVEwsCgkJCXJlYWRfbW1jcl9ieXRlKFNDNTIwX0FERERFQ0NUTCkgfCBJT19IT0xFX0RFU1RfUENJKTsKCgoJLyogc28gd2UgbWFwIGF3YXkgYWxsIGlvIHBvcnRzIHRvIHBjaSAob25seSB3YXkgdG8gYWNjZXNzIHBjaSBpbwoJICogYmVsb3cgMHg0MDAuIEJ1dCB0aGVuIHdlIGhhdmUgdG8gbWFwIGJhY2sgdGhlIHBvcnRpb25zIHRoYXQgd2UgZG9udAoJICogdXNlIHNvIHRoYXQgdGhlIGdlbmVyYXRlIGN5Y2xlcyBvbiB0aGUgR1BJTyBidXMgd2hlcmUgdGhlIHNpbyBhbmQKCSAqIElTQSBzbG90cyBhcmUgY29ubmVjdGVkLCB0aGlzIHJlcXVyZSB0aGUgdXNlIG9mIHNldmVyYWwgUEFSIHJlZ2lzdGVycwoJICovCgoJLyogYnJpbmcgMHgxMDAgLSAweDJmNyBiYWNrIHRvIElTQSB1c2luZyBQQVI1ICovCgl3cml0ZV9tbWNyX2xvbmcoU0M1MjBfUEFSNSwgMHgzMWY3MDEwMCk7CgoJLyogY29tMiB1c2UgMmY4LTJmZiAqLwoKCS8qIGJyaW5nIDB4MzAwIC0gMHgzYWYgYmFjayB0byBJU0EgdXNpbmcgUEFSNyAqLwoJd3JpdGVfbW1jcl9sb25nKFNDNTIwX1BBUjcsIDB4MzBhZjAzMDApOwoKCS8qIHZnYSB1c2UgM2IwLTNiYiAqLwoKCS8qIGJyaW5nIDB4M2JjIC0gMHgzYmYgYmFjayB0byBJU0EgdXNpbmcgUEFSOCAqLwoJd3JpdGVfbW1jcl9sb25nKFNDNTIwX1BBUjgsIDB4MzAwMzAzYmMpOwoKCS8qIHZnYSB1c2UgM2MwLTNkZiAqLwoKCS8qIGJyaW5nIDB4M2UwIC0gMHgzZjcgYmFjayB0byBJU0EgdXNpbmcgUEFSOSAqLwoJd3JpdGVfbW1jcl9sb25nKFNDNTIwX1BBUjksIDB4MzAxNzAzZTApOwoKCS8qIGNvbTEgdXNlIDNmOC0zZmYgKi8KCglyZXR1cm4gMDsKfQojZW5kaWYKCi8qCiAqIE1pc2NlbGFuZW91cyBwbGF0Zm9ybSBkZXBlbmRlbnQgaW5pdGlhbGlzYXRpb25zCiAqLwoKaW50IGJvYXJkX2luaXQodm9pZCkKewoJaW5pdF9zYzUyMCgpOwoJYnVzX2luaXQoKTsKCWlycV9pbml0KCk7CgoJLyogbWF4IGRyaXZlIGN1cnJlbnQgb24gU0RSQU0gKi8KCXdyaXRlX21tY3Jfd29yZChTQzUyMF9EU0NUTCwgMHgwMTAwKTsKCgkvKiBlbnRlciBkZWJ1ZyBtb2RlIGFmdGVyIG5leHQgcmVzZXQgKG9ubHkgaWYganVtcGVyIGlzIGFsc28gc2V0KSAqLwoJd3JpdGVfbW1jcl9ieXRlKFNDNTIwX1JFU0NGRywgMHgwOCk7CgkvKiBjb25maWd1cmUgdGhlIHNvZnR3YXJlIHRpbWVyIHRvIDMzLjAwME1IeiAqLwoJd3JpdGVfbW1jcl9ieXRlKFNDNTIwX1NXVE1SQ0ZHLCAxKTsKCWdkLT5idXNfY2xrID0gMzMwMDAwMDA7CgoJcmV0dXJuIDA7Cn0KCmludCBkcmFtX2luaXQodm9pZCkKewoJaW5pdF9zYzUyMF9kcmFtKCk7CglyZXR1cm4gMDsKfQoKdm9pZCBzaG93X2Jvb3RfcHJvZ3Jlc3MoaW50IHZhbCkKewoJaW50IHZlcnNpb24gPSByZWFkX21tY3JfYnl0ZShTQzUyMF9TWVNJTkZPKTsKCglpZiAodmVyc2lvbiA9PSAwKSB7CgkJLyogUElPMzEtUElPMTYgRGF0YSAqLwoJCXdyaXRlX21tY3Jfd29yZChTQzUyMF9QSU9EQVRBMzFfMTYsCgkJCQkocmVhZF9tbWNyX3dvcmQoU0M1MjBfUElPREFUQTMxXzE2KSAmIDB4ZmZjMCl8ICgodmFsJjB4N2UpPj4xKSk7IC8qIDB4MWY4ID4+IDMgKi8KCgkJLyogUElPMC1QSU8xNSBEYXRhICovCgkJd3JpdGVfbW1jcl93b3JkKFNDNTIwX1BJT0RBVEExNV8wLAoJCQkJKHJlYWRfbW1jcl93b3JkKFNDNTIwX1BJT0RBVEExNV8wKSAmIDB4MWZmZil8ICgodmFsJjB4Nyk8PDEzKSk7Cgl9IGVsc2UgewoJCS8qIG5ld2VyIGJvYXJkcyB1c2UgUElPNC1QSU8xMiAqLwoJCS8qIFBJTzAtUElPMTUgRGF0YSAqLwojaWYgMAoJCXZhbCA9ICh2YWwgJiAweDAwNykgfCAoKHZhbCAmIDB4MDM4KSA8PCAzKSB8ICgodmFsICYgMHgxYzApID4+IDMpOwojZWxzZQoJCXZhbCA9ICh2YWwgJiAweDAwNykgfCAoKHZhbCAmIDB4MDdlKSA8PCAyKTsKI2VuZGlmCgkJd3JpdGVfbW1jcl93b3JkKFNDNTIwX1BJT0RBVEExNV8wLAoJCQkJKHJlYWRfbW1jcl93b3JkKFNDNTIwX1BJT0RBVEExNV8wKSAmIDB4ZTAwZikgfCAoKHZhbCYweDAxZmYpPDw0KSk7Cgl9Cn0KCgppbnQgbGFzdF9zdGFnZV9pbml0KHZvaWQpCnsKCglpbnQgdmVyc2lvbiA9IHJlYWRfbW1jcl9ieXRlKFNDNTIwX1NZU0lORk8pOwoKCXByaW50ZigiT21pY3JvbiBDZXRpIFNDNTIwIFNwdW5rIHJldmlzaW9uICV4XG4iLCB2ZXJzaW9uKTsKCiNpZiAwCglpZiAodmVyc2lvbikgewoJCWludCB4LCB5OwoKCQlwcmludGYoImVlcHJvbSBwcm9iZSAlZFxuIiwgc3BpX2VlcHJvbV9wcm9iZSgxKSk7CgoJCXNwaV9lZXByb21fcmVhZCgxLCAwLCAodTgqKSZ4LCAyKTsKCQlzcGlfZWVwcm9tX3JlYWQoMSwgMSwgKHU4KikmeSwgMik7CgkJcHJpbnRmKCJlZXByb20gYnl0ZXMgJTA0eCUwNHhcbiIsIHgsIHkpOwoJCXggXj0gMHhmZmZmOwoJCXkgXj0gMHhmZmZmOwoJCXNwaV9lZXByb21fd3JpdGUoMSwgMCwgKHU4KikmeCwgMik7CgkJc3BpX2VlcHJvbV93cml0ZSgxLCAxLCAodTgqKSZ5LCAyKTsKCgkJc3BpX2VlcHJvbV9yZWFkKDEsIDAsICh1OCopJngsIDIpOwoJCXNwaV9lZXByb21fcmVhZCgxLCAxLCAodTgqKSZ5LCAyKTsKCQlwcmludGYoImVlcHJvbSBieXRlcyAlMDR4JTA0eFxuIiwgeCwgeSk7CgoJfSBlbHNlIHsKCQlpbnQgeCwgeTsKCgkJcHJpbnRmKCJlZXByb20gcHJvYmUgJWRcbiIsIG13X2VlcHJvbV9wcm9iZSgxKSk7CgoJCW13X2VlcHJvbV9yZWFkKDEsIDAsICh1OCopJngsIDIpOwoJCW13X2VlcHJvbV9yZWFkKDEsIDEsICh1OCopJnksIDIpOwoJCXByaW50ZigiZWVwcm9tIGJ5dGVzICUwNHglMDR4XG4iLCB4LCB5KTsKCgkJeCBePSAweGZmZmY7CgkJeSBePSAweGZmZmY7CgkJbXdfZWVwcm9tX3dyaXRlKDEsIDAsICh1OCopJngsIDIpOwoJCW13X2VlcHJvbV93cml0ZSgxLCAxLCAodTgqKSZ5LCAyKTsKCgkJbXdfZWVwcm9tX3JlYWQoMSwgMCwgKHU4KikmeCwgMik7CgkJbXdfZWVwcm9tX3JlYWQoMSwgMSwgKHU4KikmeSwgMik7CgkJcHJpbnRmKCJlZXByb20gYnl0ZXMgJTA0eCUwNHhcbiIsIHgsIHkpOwoKCgl9CiNlbmRpZgoKCWRzMTcyMl9wcm9iZSgyKTsKCglyZXR1cm4gMDsKfQoKdm9pZCBzc2lfY2hpcF9zZWxlY3QoaW50IGRldikKewoJaW50IHZlcnNpb24gPSByZWFkX21tY3JfYnl0ZShTQzUyMF9TWVNJTkZPKTsKCglpZiAodmVyc2lvbikgewoJCS8qIFNwdW5rIGJvYXJkOiBFRVBST00gYW5kIENBTiBhcmUgYWN0b3ZlLWxvdywgVEVNUCBhbmQgQVVYIGFyZSBhY3RpdmUgaGlnaCAqLwoJCXN3aXRjaCAoZGV2KSB7CgkJY2FzZSAxOiAvKiBFRVBST00gKi8KCQkJd3JpdGVfbW1jcl93b3JkKFNDNTIwX1BJT0NMUjMxXzE2LCAweDAwMDQpOwoJCQlicmVhazsKCgkJY2FzZSAyOiAvKiBUZW1wIFByb2JlICovCgkJCXdyaXRlX21tY3Jfd29yZChTQzUyMF9QSU9TRVQzMV8xNiwgMHgwMDAyKTsKCQkJYnJlYWs7CgoJCWNhc2UgMzogLyogQ0FOICovCgkJCXdyaXRlX21tY3Jfd29yZChTQzUyMF9QSU9DTFIzMV8xNiwgMHgwMDA4KTsKCQkJYnJlYWs7CgoJCWNhc2UgNDogLyogQVVYICovCgkJCXdyaXRlX21tY3Jfd29yZChTQzUyMF9QSU9TRVQzMV8xNiwgMHgwMDAxKTsKCQkJYnJlYWs7CgoJCWNhc2UgMDoKCQkJd3JpdGVfbW1jcl93b3JkKFNDNTIwX1BJT0NMUjMxXzE2LCAweDAwMDMpOwoJCQl3cml0ZV9tbWNyX3dvcmQoU0M1MjBfUElPU0VUMzFfMTYsIDB4MDAwYyk7CgkJCWJyZWFrOwoKCQlkZWZhdWx0OgoJCQlwcmludGYoIklsbGVnYWwgU1NJIGRldmljZSByZXF1ZXN0ZWQ6ICVkXG4iLCBkZXYpOwoJCX0KCX0gZWxzZSB7CgoJCS8qIEdsb2JveCBib2FyZDogQm90aCBFRVBST00gYW5kIFRFTVAgYXJlIGFjdGl2ZS1oaWdoICovCgoJCXN3aXRjaCAoZGV2KSB7CgkJY2FzZSAxOiAvKiBFRVBST00gKi8KCQkJd3JpdGVfbW1jcl93b3JkKFNDNTIwX1BJT1NFVDE1XzAsIDB4MDEwMCk7CgkJCWJyZWFrOwoKCQljYXNlIDI6IC8qIFRlbXAgUHJvYmUgKi8KCQkJd3JpdGVfbW1jcl93b3JkKFNDNTIwX1BJT1NFVDE1XzAsIDB4MDA4MCk7CgkJCWJyZWFrOwoKCQljYXNlIDA6CgkJCXdyaXRlX21tY3Jfd29yZChTQzUyMF9QSU9DTFIxNV8wLCAweDAxODApOwoJCQlicmVhazsKCgkJZGVmYXVsdDoKCQkJcHJpbnRmKCJJbGxlZ2FsIFNTSSBkZXZpY2UgcmVxdWVzdGVkOiAlZFxuIiwgZGV2KTsKCQl9Cgl9Cn0KCgp2b2lkIHNwaV9pbml0X2Yodm9pZCkKewoJcmVhZF9tbWNyX2J5dGUoU0M1MjBfU1lTSU5GTykgPwoJCXNwaV9lZXByb21fcHJvYmUoMSkgOgoJbXdfZWVwcm9tX3Byb2JlKDEpOwoKfQoKc3NpemVfdCBzcGlfcmVhZCh1Y2hhciAqYWRkciwgaW50IGFsZW4sIHVjaGFyICpidWZmZXIsIGludCBsZW4pCnsKCWludCBvZmZzZXQ7CglpbnQgaTsKCglvZmZzZXQgPSAwOwoJZm9yIChpPTA7aTxhbGVuO2krKykgewoJCW9mZnNldCA8PD0gODsKCQlvZmZzZXQgfD0gYWRkcltpXTsKCX0KCglyZXR1cm4gCXJlYWRfbW1jcl9ieXRlKFNDNTIwX1NZU0lORk8pID8KCQlzcGlfZWVwcm9tX3JlYWQoMSwgb2Zmc2V0LCBidWZmZXIsIGxlbikgOgoJbXdfZWVwcm9tX3JlYWQoMSwgb2Zmc2V0LCBidWZmZXIsIGxlbik7Cn0KCnNzaXplX3Qgc3BpX3dyaXRlKHVjaGFyICphZGRyLCBpbnQgYWxlbiwgdWNoYXIgKmJ1ZmZlciwgaW50IGxlbikKewoJaW50IG9mZnNldDsKCWludCBpOwoKCW9mZnNldCA9IDA7Cglmb3IgKGk9MDtpPGFsZW47aSsrKSB7CgkJb2Zmc2V0IDw8PSA4OwoJCW9mZnNldCB8PSBhZGRyW2ldOwoJfQoKCXJldHVybiAJcmVhZF9tbWNyX2J5dGUoU0M1MjBfU1lTSU5GTykgPwoJCXNwaV9lZXByb21fd3JpdGUoMSwgb2Zmc2V0LCBidWZmZXIsIGxlbikgOgoJbXdfZWVwcm9tX3dyaXRlKDEsIG9mZnNldCwgYnVmZmVyLCBsZW4pOwp9Cg==