LyogLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLSAqLwovKiBpMmMtaW9wM3h4LmMgaTJjIGRyaXZlciBhbGdvcml0aG1zIGZvciBJbnRlbCBYU2NhbGUgSU9QM3h4ICYgSVhQNDZ4ICAgICAgICovCi8qIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0gKi8KLyogQ29weXJpZ2h0IChDKSAyMDAzIFBldGVyIE1pbG5lLCBELVRBQ1EgU29sdXRpb25zIEx0ZAogKiAgICAgICAgICAgICAgICAgICAgPFBldGVyIGRvdCBNaWxuZSBhdCBEIGh5cGhlbiBUQUNRIGRvdCBjb20+CiAqCiAqIFdpdGggYWNrbm93bGVkZ2VtZW50cyB0byBpMmMtYWxnby1pYm1fb2NwLmMgYnkgCiAqIElhbiBEYVNpbHZhLCBNb250YVZpc3RhIFNvZnR3YXJlLCBJbmMuIGlkYXNpbHZhQG12aXN0YS5jb20KICoKICogQW5kIGkyYy1hbGdvLXBjZi5jLCB3aGljaCB3YXMgY3JlYXRlZCBieSBTaW1vbiBHLiBWb2dsIGFuZCBIYW5zIEJlcmdsdW5kOgogKgogKiBDb3B5cmlnaHQgKEMpIDE5OTUtMTk5NyBTaW1vbiBHLiBWb2dsLCAxOTk4LTIwMDAgSGFucyBCZXJnbHVuZAogKiAgCiAqIEFuZCB3aGljaCBhY2tub3dsZWRnZWQgS3n2c3RpIE3kbGtraSA8a21hbGtraUBjYy5odXQuZmk+LAogKiBGcm9kbyBMb29pamFhcmQgPGZyb2RvbEBkZHMubmw+LCBNYXJ0aW4gQmFpbGV5PG1iYWlsZXlAbGl0dGxlZmVldC1pbmMuY29tPgogKgogKiBNYWpvciBjbGVhbnVwIGJ5IERlZXBhayBTYXhlbmEgPGRzYXhlbmFAcGxleGl0eS5uZXQ+LCAwMS8yMDA1OgogKgogKiAtIFVzZSBkcml2ZXIgbW9kZWwgdG8gcGFzcyBwZXItY2hpcCBpbmZvIGluc3RlYWQgb2YgaGFyZGNvZGluZyBhbmQgI2lmZGVmcwogKiAtIFVzZSBpb3JlbWFwL19fcmF3X3JlYWRsL19fcmF3X3dyaXRlbCBpbnN0ZWFkIG9mIGRpcmVjdCBkZXJlZmVyZW5jZQogKiAtIE1ha2UgaXQgd29yayB3aXRoIElYUDQ2eCBjaGlwcwogKiAtIENsZWFudXAgZnVuY3Rpb24gbmFtZXMsIGNvZGluZyBzdHlsZSwgZXRjCiAqCiAqIFRoaXMgcHJvZ3JhbSBpcyBmcmVlIHNvZnR3YXJlOyB5b3UgY2FuIHJlZGlzdHJpYnV0ZSBpdCBhbmQvb3IgbW9kaWZ5CiAqIGl0IHVuZGVyIHRoZSB0ZXJtcyBvZiB0aGUgR05VIEdlbmVyYWwgUHVibGljIExpY2Vuc2UgYXMgcHVibGlzaGVkIGJ5CiAqIHRoZSBGcmVlIFNvZnR3YXJlIEZvdW5kYXRpb24sIHZlcnNpb24gMi4KICovCgojaW5jbHVkZSA8bGludXgvY29uZmlnLmg+CiNpbmNsdWRlIDxsaW51eC9pbnRlcnJ1cHQuaD4KI2luY2x1ZGUgPGxpbnV4L2tlcm5lbC5oPgojaW5jbHVkZSA8bGludXgvbW9kdWxlLmg+CiNpbmNsdWRlIDxsaW51eC9kZWxheS5oPgojaW5jbHVkZSA8bGludXgvc2xhYi5oPgojaW5jbHVkZSA8bGludXgvaW5pdC5oPgojaW5jbHVkZSA8bGludXgvZXJybm8uaD4KI2luY2x1ZGUgPGxpbnV4L3NjaGVkLmg+CiNpbmNsdWRlIDxsaW51eC9kZXZpY2UuaD4KI2luY2x1ZGUgPGxpbnV4L2kyYy5oPgoKI2luY2x1ZGUgPGFzbS9pby5oPgoKI2luY2x1ZGUgImkyYy1pb3AzeHguaCIKCi8qIGdsb2JhbCB1bml0IGNvdW50ZXIgKi8Kc3RhdGljIGludCBpMmNfaWQgPSAwOwoKc3RhdGljIGlubGluZSB1bnNpZ25lZCBjaGFyIAppaWNfY29va19hZGRyKHN0cnVjdCBpMmNfbXNnICptc2cpIAp7Cgl1bnNpZ25lZCBjaGFyIGFkZHI7CgoJYWRkciA9IChtc2ctPmFkZHIgPDwgMSk7CgoJaWYgKG1zZy0+ZmxhZ3MgJiBJMkNfTV9SRCkKCQlhZGRyIHw9IDE7CgoJLyoKCSAqIFJlYWQgb3IgV3JpdGU/CgkgKi8KCWlmIChtc2ctPmZsYWdzICYgSTJDX01fUkVWX0RJUl9BRERSKQoJCWFkZHIgXj0gMTsKCglyZXR1cm4gYWRkcjsgICAKfQoKc3RhdGljIHZvaWQgCmlvcDN4eF9pMmNfcmVzZXQoc3RydWN0IGkyY19hbGdvX2lvcDN4eF9kYXRhICppb3AzeHhfYWRhcCkKewoJLyogRm9sbG93cyBkZXZtYW4gOS4zICovCglfX3Jhd193cml0ZWwoSU9QM1hYX0lDUl9VTklUX1JFU0VULCBpb3AzeHhfYWRhcC0+aW9hZGRyICsgQ1JfT0ZGU0VUKTsKCV9fcmF3X3dyaXRlbChJT1AzWFhfSVNSX0NMRUFSQklUUywgaW9wM3h4X2FkYXAtPmlvYWRkciArIFNSX09GRlNFVCk7CglfX3Jhd193cml0ZWwoMCwgaW9wM3h4X2FkYXAtPmlvYWRkciArIENSX09GRlNFVCk7Cn0gCgpzdGF0aWMgdm9pZCAKaW9wM3h4X2kyY19zZXRfc2xhdmVfYWRkcihzdHJ1Y3QgaTJjX2FsZ29faW9wM3h4X2RhdGEgKmlvcDN4eF9hZGFwKQp7CglfX3Jhd193cml0ZWwoTVlTQVIsIGlvcDN4eF9hZGFwLT5pb2FkZHIgKyBTQVJfT0ZGU0VUKTsKfQoKc3RhdGljIHZvaWQgCmlvcDN4eF9pMmNfZW5hYmxlKHN0cnVjdCBpMmNfYWxnb19pb3AzeHhfZGF0YSAqaW9wM3h4X2FkYXApCnsKCXUzMiBjciA9IElPUDNYWF9JQ1JfR0NEIHwgSU9QM1hYX0lDUl9TQ0xFTiB8IElPUDNYWF9JQ1JfVUU7CgoJLyogCgkgKiBFdmVyeXRpbWUgdW5pdCBlbmFibGUgaXMgYXNzZXJ0ZWQsIEdQT0QgbmVlZHMgdG8gYmUgY2xlYXJlZAoJICogb24gSU9QMzIxIHRvIGF2b2lkIGRhdGEgY29ycnVwdGlvbiBvbiB0aGUgYnVzLgoJICovCiNpZmRlZiBDT05GSUdfQVJDSF9JT1AzMjEKI2RlZmluZSBJT1AzMjFfR1BPRF9JMkMwICAgIDB4MDBjMCAgLyogY2xlYXIgdGhlc2UgYml0cyB0byBlbmFibGUgY2gwICovCiNkZWZpbmUgSU9QMzIxX0dQT0RfSTJDMSAgICAweDAwMzAgIC8qIGNsZWFyIHRoZXNlIGJpdHMgdG8gZW5hYmxlIGNoMSAqLwoKCSpJT1AzMjFfR1BPRCAmPSAoaW9wM3h4X2FkYXAtPmlkID09IDApID8gfklPUDMyMV9HUE9EX0kyQzAgOiAKCQl+SU9QMzIxX0dQT0RfSTJDMTsKI2VuZGlmCgkvKiBOQiBTUiBiaXRzIG5vdCBzYW1lIHBvc2l0aW9uIGFzIENSIElFIGJpdHMgOi0oICovCglpb3AzeHhfYWRhcC0+U1JfZW5hYmxlZCA9IAoJCUlPUDNYWF9JU1JfQUxEIHwgSU9QM1hYX0lTUl9CRVJSRCB8CgkJSU9QM1hYX0lTUl9SWEZVTEwgfCBJT1AzWFhfSVNSX1RYRU1QVFk7CgoJY3IgfD0gSU9QM1hYX0lDUl9BTERfSUUgfCBJT1AzWFhfSUNSX0JFUlJfSUUgfAoJCUlPUDNYWF9JQ1JfUlhGVUxMX0lFIHwgSU9QM1hYX0lDUl9UWEVNUFRZX0lFOwoKCV9fcmF3X3dyaXRlbChjciwgaW9wM3h4X2FkYXAtPmlvYWRkciArIENSX09GRlNFVCk7Cn0KCnN0YXRpYyB2b2lkIAppb3AzeHhfaTJjX3RyYW5zYWN0aW9uX2NsZWFudXAoc3RydWN0IGkyY19hbGdvX2lvcDN4eF9kYXRhICppb3AzeHhfYWRhcCkKewoJdW5zaWduZWQgbG9uZyBjciA9IF9fcmF3X3JlYWRsKGlvcDN4eF9hZGFwLT5pb2FkZHIgKyBDUl9PRkZTRVQpOwoJCgljciAmPSB+KElPUDNYWF9JQ1JfTVNUQVJUIHwgSU9QM1hYX0lDUl9UQllURSB8IAoJCUlPUDNYWF9JQ1JfTVNUT1AgfCBJT1AzWFhfSUNSX1NDTEVOKTsKCglfX3Jhd193cml0ZWwoY3IsIGlvcDN4eF9hZGFwLT5pb2FkZHIgKyBDUl9PRkZTRVQpOwp9CgovKiAKICogTkI6IHRoZSBoYW5kbGVyIGhhcyB0byBjbGVhciB0aGUgc291cmNlIG9mIHRoZSBpbnRlcnJ1cHQhIAogKiBUaGVuIGl0IHBhc3NlcyB0aGUgU1IgZmxhZ3Mgb2YgaW50ZXJlc3QgdG8gQkggdmlhIGFkYXAgZGF0YQogKi8Kc3RhdGljIGlycXJldHVybl90IAppb3AzeHhfaTJjX2lycV9oYW5kbGVyKGludCB0aGlzX2lycSwgdm9pZCAqZGV2X2lkLCBzdHJ1Y3QgcHRfcmVncyAqcmVncykgCnsKCXN0cnVjdCBpMmNfYWxnb19pb3AzeHhfZGF0YSAqaW9wM3h4X2FkYXAgPSBkZXZfaWQ7Cgl1MzIgc3IgPSBfX3Jhd19yZWFkbChpb3AzeHhfYWRhcC0+aW9hZGRyICsgU1JfT0ZGU0VUKTsKCglpZiAoKHNyICY9IGlvcDN4eF9hZGFwLT5TUl9lbmFibGVkKSkgewoJCV9fcmF3X3dyaXRlbChzciwgaW9wM3h4X2FkYXAtPmlvYWRkciArIFNSX09GRlNFVCk7CgkJaW9wM3h4X2FkYXAtPlNSX3JlY2VpdmVkIHw9IHNyOwoJCXdha2VfdXBfaW50ZXJydXB0aWJsZSgmaW9wM3h4X2FkYXAtPndhaXRxKTsKCX0KCXJldHVybiBJUlFfSEFORExFRDsKfQoKLyogY2hlY2sgYWxsIGVycm9yIGNvbmRpdGlvbnMsIGNsZWFyIHRoZW0gLCByZXBvcnQgbW9zdCBpbXBvcnRhbnQgKi8Kc3RhdGljIGludCAKaW9wM3h4X2kyY19lcnJvcih1MzIgc3IpCnsKCWludCByYyA9IDA7CgoJaWYgKChzciAmIElPUDNYWF9JU1JfQkVSUkQpKSB7CgkJaWYgKCAhcmMgKSByYyA9IC1JMkNfRVJSX0JFUlI7Cgl9CglpZiAoKHNyICYgSU9QM1hYX0lTUl9BTEQpKSB7CgkJaWYgKCAhcmMgKSByYyA9IC1JMkNfRVJSX0FMRDsJCQoJfQoJcmV0dXJuIHJjOwkKfQoKc3RhdGljIGlubGluZSB1MzIgCmlvcDN4eF9pMmNfZ2V0X3Nyc3RhdChzdHJ1Y3QgaTJjX2FsZ29faW9wM3h4X2RhdGEgKmlvcDN4eF9hZGFwKQp7Cgl1bnNpZ25lZCBsb25nIGZsYWdzOwoJdTMyIHNyOwoKCXNwaW5fbG9ja19pcnFzYXZlKCZpb3AzeHhfYWRhcC0+bG9jaywgZmxhZ3MpOwoJc3IgPSBpb3AzeHhfYWRhcC0+U1JfcmVjZWl2ZWQ7Cglpb3AzeHhfYWRhcC0+U1JfcmVjZWl2ZWQgPSAwOwoJc3Bpbl91bmxvY2tfaXJxcmVzdG9yZSgmaW9wM3h4X2FkYXAtPmxvY2ssIGZsYWdzKTsKCglyZXR1cm4gc3I7Cn0KCi8qCiAqIHNsZWVwIHVudGlsIGludGVycnVwdGVkLCB0aGVuIHJlY292ZXIgYW5kIGFuYWx5c2UgdGhlIFNSCiAqIHNhdmVkIGJ5IGhhbmRsZXIKICovCnR5cGVkZWYgaW50ICgqIGNvbXBhcmVfZnVuYykodW5zaWduZWQgdGVzdCwgdW5zaWduZWQgbWFzayk7Ci8qIHJldHVybnMgMSBvbiBjb3JyZWN0IGNvbXBhcmlzb24gKi8KCnN0YXRpYyBpbnQgCmlvcDN4eF9pMmNfd2FpdF9ldmVudChzdHJ1Y3QgaTJjX2FsZ29faW9wM3h4X2RhdGEgKmlvcDN4eF9hZGFwLCAKCQkJICB1bnNpZ25lZCBmbGFncywgdW5zaWduZWQqIHN0YXR1cywKCQkJICBjb21wYXJlX2Z1bmMgY29tcGFyZSkKewoJdW5zaWduZWQgc3IgPSAwOwoJaW50IGludGVycnVwdGVkOwoJaW50IGRvbmU7CglpbnQgcmMgPSAwOwoKCWRvIHsKCQlpbnRlcnJ1cHRlZCA9IHdhaXRfZXZlbnRfaW50ZXJydXB0aWJsZV90aW1lb3V0ICgKCQkJaW9wM3h4X2FkYXAtPndhaXRxLAoJCQkoZG9uZSA9IGNvbXBhcmUoIHNyID0gaW9wM3h4X2kyY19nZXRfc3JzdGF0KGlvcDN4eF9hZGFwKQkJCQkJLGZsYWdzICkpLAoJCQkxICogSFo7CgkJCSk7CgkJaWYgKChyYyA9IGlvcDN4eF9pMmNfZXJyb3Ioc3IpKSA8IDApIHsKCQkJKnN0YXR1cyA9IHNyOwoJCQlyZXR1cm4gcmM7CgkJfSBlbHNlIGlmICghaW50ZXJydXB0ZWQpIHsKCQkJKnN0YXR1cyA9IHNyOwoJCQlyZXR1cm4gLUVUSU1FRE9VVDsKCQl9Cgl9IHdoaWxlKCFkb25lKTsKCgkqc3RhdHVzID0gc3I7CgoJcmV0dXJuIDA7Cn0KCi8qCiAqIENvbmNyZXRlIGNvbXBhcmVfZnVuY3MgCiAqLwpzdGF0aWMgaW50IAphbGxfYml0c19jbGVhcih1bnNpZ25lZCB0ZXN0LCB1bnNpZ25lZCBtYXNrKQp7CglyZXR1cm4gKHRlc3QgJiBtYXNrKSA9PSAwOwp9CgpzdGF0aWMgaW50IAphbnlfYml0c19zZXQodW5zaWduZWQgdGVzdCwgdW5zaWduZWQgbWFzaykKewoJcmV0dXJuICh0ZXN0ICYgbWFzaykgIT0gMDsKfQoKc3RhdGljIGludCAKaW9wM3h4X2kyY193YWl0X3R4X2RvbmUoc3RydWN0IGkyY19hbGdvX2lvcDN4eF9kYXRhICppb3AzeHhfYWRhcCwgaW50ICpzdGF0dXMpCnsKCXJldHVybiBpb3AzeHhfaTJjX3dhaXRfZXZlbnQoIAoJCWlvcDN4eF9hZGFwLCAKCSAgICAgICAgSU9QM1hYX0lTUl9UWEVNUFRZIHwgSU9QM1hYX0lTUl9BTEQgfCBJT1AzWFhfSVNSX0JFUlJELAoJCXN0YXR1cywgYW55X2JpdHNfc2V0KTsKfQoKc3RhdGljIGludCAKaW9wM3h4X2kyY193YWl0X3J4X2RvbmUoc3RydWN0IGkyY19hbGdvX2lvcDN4eF9kYXRhICppb3AzeHhfYWRhcCwgaW50ICpzdGF0dXMpCnsKCXJldHVybiBpb3AzeHhfaTJjX3dhaXRfZXZlbnQoIAoJCWlvcDN4eF9hZGFwLCAKCQlJT1AzWFhfSVNSX1JYRlVMTCB8IElPUDNYWF9JU1JfQUxEIHwgSU9QM1hYX0lTUl9CRVJSRCwKCQlzdGF0dXMsCWFueV9iaXRzX3NldCk7Cn0KCnN0YXRpYyBpbnQgCmlvcDN4eF9pMmNfd2FpdF9pZGxlKHN0cnVjdCBpMmNfYWxnb19pb3AzeHhfZGF0YSAqaW9wM3h4X2FkYXAsIGludCAqc3RhdHVzKQp7CglyZXR1cm4gaW9wM3h4X2kyY193YWl0X2V2ZW50KCAKCQlpb3AzeHhfYWRhcCwgSU9QM1hYX0lTUl9VTklUQlVTWSwgc3RhdHVzLCBhbGxfYml0c19jbGVhcik7Cn0KCnN0YXRpYyBpbnQgCmlvcDN4eF9pMmNfc2VuZF90YXJnZXRfYWRkcihzdHJ1Y3QgaTJjX2FsZ29faW9wM3h4X2RhdGEgKmlvcDN4eF9hZGFwLCAKCQkJCXN0cnVjdCBpMmNfbXNnKiBtc2cpCnsKCXVuc2lnbmVkIGxvbmcgY3IgPSBfX3Jhd19yZWFkbChpb3AzeHhfYWRhcC0+aW9hZGRyICsgQ1JfT0ZGU0VUKTsKCWludCBzdGF0dXM7CglpbnQgcmM7CgoJX19yYXdfd3JpdGVsKGlpY19jb29rX2FkZHIobXNnKSwgaW9wM3h4X2FkYXAtPmlvYWRkciArIERCUl9PRkZTRVQpOwoJCgljciAmPSB+KElPUDNYWF9JQ1JfTVNUT1AgfCBJT1AzWFhfSUNSX05BQ0spOwoJY3IgfD0gSU9QM1hYX0lDUl9NU1RBUlQgfCBJT1AzWFhfSUNSX1RCWVRFOwoKCV9fcmF3X3dyaXRlbChjciwgaW9wM3h4X2FkYXAtPmlvYWRkciArIENSX09GRlNFVCk7CglyYyA9IGlvcDN4eF9pMmNfd2FpdF90eF9kb25lKGlvcDN4eF9hZGFwLCAmc3RhdHVzKTsKCglyZXR1cm4gcmM7Cn0KCnN0YXRpYyBpbnQgCmlvcDN4eF9pMmNfd3JpdGVfYnl0ZShzdHJ1Y3QgaTJjX2FsZ29faW9wM3h4X2RhdGEgKmlvcDN4eF9hZGFwLCBjaGFyIGJ5dGUsIAoJCQkJaW50IHN0b3ApCnsKCXVuc2lnbmVkIGxvbmcgY3IgPSBfX3Jhd19yZWFkbChpb3AzeHhfYWRhcC0+aW9hZGRyICsgQ1JfT0ZGU0VUKTsKCWludCBzdGF0dXM7CglpbnQgcmMgPSAwOwoKCV9fcmF3X3dyaXRlbChieXRlLCBpb3AzeHhfYWRhcC0+aW9hZGRyICsgREJSX09GRlNFVCk7CgljciAmPSB+SU9QM1hYX0lDUl9NU1RBUlQ7CglpZiAoc3RvcCkgewoJCWNyIHw9IElPUDNYWF9JQ1JfTVNUT1A7Cgl9IGVsc2UgewoJCWNyICY9IH5JT1AzWFhfSUNSX01TVE9QOwoJfQoJY3IgfD0gSU9QM1hYX0lDUl9UQllURTsKCV9fcmF3X3dyaXRlbChjciwgaW9wM3h4X2FkYXAtPmlvYWRkciArIENSX09GRlNFVCk7CglyYyA9IGlvcDN4eF9pMmNfd2FpdF90eF9kb25lKGlvcDN4eF9hZGFwLCAmc3RhdHVzKTsKCglyZXR1cm4gcmM7Cn0gCgpzdGF0aWMgaW50IAppb3AzeHhfaTJjX3JlYWRfYnl0ZShzdHJ1Y3QgaTJjX2FsZ29faW9wM3h4X2RhdGEgKmlvcDN4eF9hZGFwLCBjaGFyKiBieXRlLCAKCQkJCWludCBzdG9wKQp7Cgl1bnNpZ25lZCBsb25nIGNyID0gX19yYXdfcmVhZGwoaW9wM3h4X2FkYXAtPmlvYWRkciArIENSX09GRlNFVCk7CglpbnQgc3RhdHVzOwoJaW50IHJjID0gMDsKCgljciAmPSB+SU9QM1hYX0lDUl9NU1RBUlQ7CgoJaWYgKHN0b3ApIHsKCQljciB8PSBJT1AzWFhfSUNSX01TVE9QIHwgSU9QM1hYX0lDUl9OQUNLOwoJfSBlbHNlIHsKCQljciAmPSB+KElPUDNYWF9JQ1JfTVNUT1AgfCBJT1AzWFhfSUNSX05BQ0spOwoJfQoJY3IgfD0gSU9QM1hYX0lDUl9UQllURTsKCV9fcmF3X3dyaXRlbChjciwgaW9wM3h4X2FkYXAtPmlvYWRkciArIENSX09GRlNFVCk7CgoJcmMgPSBpb3AzeHhfaTJjX3dhaXRfcnhfZG9uZShpb3AzeHhfYWRhcCwgJnN0YXR1cyk7CgoJKmJ5dGUgPSBfX3Jhd19yZWFkbChpb3AzeHhfYWRhcC0+aW9hZGRyICsgREJSX09GRlNFVCk7CgoJcmV0dXJuIHJjOwp9CgpzdGF0aWMgaW50IAppb3AzeHhfaTJjX3dyaXRlYnl0ZXMoc3RydWN0IGkyY19hZGFwdGVyICppMmNfYWRhcCwgY29uc3QgY2hhciAqYnVmLCBpbnQgY291bnQpCnsKCXN0cnVjdCBpMmNfYWxnb19pb3AzeHhfZGF0YSAqaW9wM3h4X2FkYXAgPSBpMmNfYWRhcC0+YWxnb19kYXRhOwoJaW50IGlpOwoJaW50IHJjID0gMDsKCglmb3IgKGlpID0gMDsgcmMgPT0gMCAmJiBpaSAhPSBjb3VudDsgKytpaSkgCgkJcmMgPSBpb3AzeHhfaTJjX3dyaXRlX2J5dGUoaW9wM3h4X2FkYXAsIGJ1ZltpaV0sIGlpPT1jb3VudC0xKTsKCXJldHVybiByYzsKfQoKc3RhdGljIGludCAKaW9wM3h4X2kyY19yZWFkYnl0ZXMoc3RydWN0IGkyY19hZGFwdGVyICppMmNfYWRhcCwgY2hhciAqYnVmLCBpbnQgY291bnQpCnsKCXN0cnVjdCBpMmNfYWxnb19pb3AzeHhfZGF0YSAqaW9wM3h4X2FkYXAgPSBpMmNfYWRhcC0+YWxnb19kYXRhOwoJaW50IGlpOwoJaW50IHJjID0gMDsKCglmb3IgKGlpID0gMDsgcmMgPT0gMCAmJiBpaSAhPSBjb3VudDsgKytpaSkKCQlyYyA9IGlvcDN4eF9pMmNfcmVhZF9ieXRlKGlvcDN4eF9hZGFwLCAmYnVmW2lpXSwgaWk9PWNvdW50LTEpOwoJCglyZXR1cm4gcmM7Cn0KCi8qCiAqIERlc2NyaXB0aW9uOiAgVGhpcyBmdW5jdGlvbiBpbXBsZW1lbnRzIGNvbWJpbmVkIHRyYW5zYWN0aW9ucy4gIENvbWJpbmVkCiAqIHRyYW5zYWN0aW9ucyBjb25zaXN0IG9mIGNvbWJpbmF0aW9ucyBvZiByZWFkaW5nIGFuZCB3cml0aW5nIGJsb2NrcyBvZiBkYXRhLgogKiBGUk9NIFRIRSBTQU1FIEFERFJFU1MKICogRWFjaCB0cmFuc2ZlciAoaS5lLiBhIHJlYWQgb3IgYSB3cml0ZSkgaXMgc2VwYXJhdGVkIGJ5IGEgcmVwZWF0ZWQgc3RhcnQKICogY29uZGl0aW9uLgogKi8Kc3RhdGljIGludCAKaW9wM3h4X2kyY19oYW5kbGVfbXNnKHN0cnVjdCBpMmNfYWRhcHRlciAqaTJjX2FkYXAsIHN0cnVjdCBpMmNfbXNnKiBwbXNnKSAKewoJc3RydWN0IGkyY19hbGdvX2lvcDN4eF9kYXRhICppb3AzeHhfYWRhcCA9IGkyY19hZGFwLT5hbGdvX2RhdGE7CglpbnQgcmM7CgoJcmMgPSBpb3AzeHhfaTJjX3NlbmRfdGFyZ2V0X2FkZHIoaW9wM3h4X2FkYXAsIHBtc2cpOwoJaWYgKHJjIDwgMCkgewoJCXJldHVybiByYzsKCX0KCglpZiAoKHBtc2ctPmZsYWdzJkkyQ19NX1JEKSkgewoJCXJldHVybiBpb3AzeHhfaTJjX3JlYWRieXRlcyhpMmNfYWRhcCwgcG1zZy0+YnVmLCBwbXNnLT5sZW4pOwoJfSBlbHNlIHsKCQlyZXR1cm4gaW9wM3h4X2kyY193cml0ZWJ5dGVzKGkyY19hZGFwLCBwbXNnLT5idWYsIHBtc2ctPmxlbik7Cgl9Cn0KCi8qCiAqIG1hc3Rlcl94ZmVyKCkgLSBtYWluIHJlYWQvd3JpdGUgZW50cnkKICovCnN0YXRpYyBpbnQgCmlvcDN4eF9pMmNfbWFzdGVyX3hmZXIoc3RydWN0IGkyY19hZGFwdGVyICppMmNfYWRhcCwgc3RydWN0IGkyY19tc2cgKm1zZ3MsIAoJCQkJaW50IG51bSkKewoJc3RydWN0IGkyY19hbGdvX2lvcDN4eF9kYXRhICppb3AzeHhfYWRhcCA9IGkyY19hZGFwLT5hbGdvX2RhdGE7CglpbnQgaW0gPSAwOwoJaW50IHJldCA9IDA7CglpbnQgc3RhdHVzOwoKCWlvcDN4eF9pMmNfd2FpdF9pZGxlKGlvcDN4eF9hZGFwLCAmc3RhdHVzKTsKCWlvcDN4eF9pMmNfcmVzZXQoaW9wM3h4X2FkYXApOwoJaW9wM3h4X2kyY19lbmFibGUoaW9wM3h4X2FkYXApOwoKCWZvciAoaW0gPSAwOyByZXQgPT0gMCAmJiBpbSAhPSBudW07IGltKyspIHsKCQlyZXQgPSBpb3AzeHhfaTJjX2hhbmRsZV9tc2coaTJjX2FkYXAsICZtc2dzW2ltXSk7Cgl9CgoJaW9wM3h4X2kyY190cmFuc2FjdGlvbl9jbGVhbnVwKGlvcDN4eF9hZGFwKTsKCQoJaWYocmV0KQoJCXJldHVybiByZXQ7CgoJcmV0dXJuIGltOyAgIAp9CgpzdGF0aWMgaW50IAppb3AzeHhfaTJjX2FsZ29fY29udHJvbChzdHJ1Y3QgaTJjX2FkYXB0ZXIgKmFkYXB0ZXIsIHVuc2lnbmVkIGludCBjbWQsCgkJCXVuc2lnbmVkIGxvbmcgYXJnKQp7CglyZXR1cm4gMDsKfQoKc3RhdGljIHUzMiAKaW9wM3h4X2kyY19mdW5jKHN0cnVjdCBpMmNfYWRhcHRlciAqYWRhcCkKewoJcmV0dXJuIEkyQ19GVU5DX0kyQyB8IEkyQ19GVU5DX1NNQlVTX0VNVUw7Cn0KCnN0YXRpYyBzdHJ1Y3QgaTJjX2FsZ29yaXRobSBpb3AzeHhfaTJjX2FsZ28gPSB7CgkubmFtZQkJPSAiSU9QM3h4IEkyQyBhbGdvcml0aG0iLAoJLmlkCQk9IEkyQ19BTEdPX0lPUDNYWCwKCS5tYXN0ZXJfeGZlcgk9IGlvcDN4eF9pMmNfbWFzdGVyX3hmZXIsCgkuYWxnb19jb250cm9sCT0gaW9wM3h4X2kyY19hbGdvX2NvbnRyb2wsCgkuZnVuY3Rpb25hbGl0eQk9IGlvcDN4eF9pMmNfZnVuYywKfTsKCnN0YXRpYyBpbnQgCmlvcDN4eF9pMmNfcmVtb3ZlKHN0cnVjdCBkZXZpY2UgKmRldmljZSkKewoJc3RydWN0IHBsYXRmb3JtX2RldmljZSAqcGRldiA9IHRvX3BsYXRmb3JtX2RldmljZShkZXZpY2UpOwoJc3RydWN0IGkyY19hZGFwdGVyICpwYWRhcHRlciA9IGRldl9nZXRfZHJ2ZGF0YSgmcGRldi0+ZGV2KTsKCXN0cnVjdCBpMmNfYWxnb19pb3AzeHhfZGF0YSAqYWRhcHRlcl9kYXRhID0gCgkJKHN0cnVjdCBpMmNfYWxnb19pb3AzeHhfZGF0YSAqKXBhZGFwdGVyLT5hbGdvX2RhdGE7CglzdHJ1Y3QgcmVzb3VyY2UgKnJlcyA9IHBsYXRmb3JtX2dldF9yZXNvdXJjZShwZGV2LCBJT1JFU09VUkNFX01FTSwgMCk7Cgl1bnNpZ25lZCBsb25nIGNyID0gX19yYXdfcmVhZGwoYWRhcHRlcl9kYXRhLT5pb2FkZHIgKyBDUl9PRkZTRVQpOwoKCS8qCgkgKiBEaXNhYmxlIHRoZSBhY3R1YWwgSFcgdW5pdAoJICovCgljciAmPSB+KElPUDNYWF9JQ1JfQUxEX0lFIHwgSU9QM1hYX0lDUl9CRVJSX0lFIHwKCQlJT1AzWFhfSUNSX1JYRlVMTF9JRSB8IElPUDNYWF9JQ1JfVFhFTVBUWV9JRSk7CglfX3Jhd193cml0ZWwoY3IsIGFkYXB0ZXJfZGF0YS0+aW9hZGRyICsgQ1JfT0ZGU0VUKTsKCglpb3VubWFwKCh2b2lkIF9faW9tZW0qKWFkYXB0ZXJfZGF0YS0+aW9hZGRyKTsKCXJlbGVhc2VfbWVtX3JlZ2lvbihyZXMtPnN0YXJ0LCBJT1AzWFhfSTJDX0lPX1NJWkUpOwoJa2ZyZWUoYWRhcHRlcl9kYXRhKTsKCWtmcmVlKHBhZGFwdGVyKTsKCglkZXZfc2V0X2RydmRhdGEoJnBkZXYtPmRldiwgTlVMTCk7CgoJcmV0dXJuIDA7Cn0KCnN0YXRpYyBpbnQgCmlvcDN4eF9pMmNfcHJvYmUoc3RydWN0IGRldmljZSAqZGV2KQp7CglzdHJ1Y3QgcGxhdGZvcm1fZGV2aWNlICpwZGV2ID0gdG9fcGxhdGZvcm1fZGV2aWNlKGRldik7CglzdHJ1Y3QgcmVzb3VyY2UgKnJlczsKCWludCByZXQ7CglzdHJ1Y3QgaTJjX2FkYXB0ZXIgKm5ld19hZGFwdGVyOwoJc3RydWN0IGkyY19hbGdvX2lvcDN4eF9kYXRhICphZGFwdGVyX2RhdGE7CgoJbmV3X2FkYXB0ZXIgPSBrbWFsbG9jKHNpemVvZihzdHJ1Y3QgaTJjX2FkYXB0ZXIpLCBHRlBfS0VSTkVMKTsKCWlmICghbmV3X2FkYXB0ZXIpIHsKCQlyZXQgPSAtRU5PTUVNOwoJCWdvdG8gb3V0OwoJfQoJbWVtc2V0KCh2b2lkKiluZXdfYWRhcHRlciwgMCwgc2l6ZW9mKCpuZXdfYWRhcHRlcikpOwoKCWFkYXB0ZXJfZGF0YSA9IGttYWxsb2Moc2l6ZW9mKHN0cnVjdCBpMmNfYWxnb19pb3AzeHhfZGF0YSksIEdGUF9LRVJORUwpOwoJaWYgKCFhZGFwdGVyX2RhdGEpIHsKCQlyZXQgPSAtRU5PTUVNOwoJCWdvdG8gZnJlZV9hZGFwdGVyOwoJfQoJbWVtc2V0KCh2b2lkKilhZGFwdGVyX2RhdGEsIDAsIHNpemVvZigqYWRhcHRlcl9kYXRhKSk7CgoJcmVzID0gcGxhdGZvcm1fZ2V0X3Jlc291cmNlKHBkZXYsIElPUkVTT1VSQ0VfTUVNLCAwKTsKCWlmICghcmVzKSB7CgkJcmV0ID0gLUVOT0RFVjsKCQlnb3RvIGZyZWVfYm90aDsKCX0KCglpZiAoIXJlcXVlc3RfbWVtX3JlZ2lvbihyZXMtPnN0YXJ0LCBJT1AzWFhfSTJDX0lPX1NJWkUsIHBkZXYtPm5hbWUpKSB7CgkJcmV0ID0gLUVCVVNZOwoJCWdvdG8gZnJlZV9ib3RoOwoJfQoKCS8qIHNldCB0aGUgYWRhcHRlciBlbnVtZXJhdGlvbiAjICovCglhZGFwdGVyX2RhdGEtPmlkID0gaTJjX2lkKys7CgoJYWRhcHRlcl9kYXRhLT5pb2FkZHIgPSAodTMyKWlvcmVtYXAocmVzLT5zdGFydCwgSU9QM1hYX0kyQ19JT19TSVpFKTsKCWlmICghYWRhcHRlcl9kYXRhLT5pb2FkZHIpIHsKCQlyZXQgPSAtRU5PTUVNOwoJCWdvdG8gcmVsZWFzZV9yZWdpb247Cgl9CgoJcmVzID0gcmVxdWVzdF9pcnEocGxhdGZvcm1fZ2V0X2lycShwZGV2LCAwKSwgaW9wM3h4X2kyY19pcnFfaGFuZGxlciwgMCwgCgkJCQlwZGV2LT5uYW1lLCBhZGFwdGVyX2RhdGEpOwoJaWYgKHJlcykgewoJCXJldCA9IC1FSU87CgkJZ290byB1bm1hcDsKCX0KCgltZW1jcHkobmV3X2FkYXB0ZXItPm5hbWUsIHBkZXYtPm5hbWUsIHN0cmxlbihwZGV2LT5uYW1lKSk7CgluZXdfYWRhcHRlci0+aWQgPSBJMkNfSFdfSU9QM1hYOwoJbmV3X2FkYXB0ZXItPm93bmVyID0gVEhJU19NT0RVTEU7CgluZXdfYWRhcHRlci0+ZGV2LnBhcmVudCA9ICZwZGV2LT5kZXY7CgoJLyoKCSAqIERlZmF1bHQgdmFsdWVzLi4uc2hvdWxkIHRoZXNlIGNvbWUgaW4gZnJvbSBib2FyZCBjb2RlPwoJICovCgluZXdfYWRhcHRlci0+dGltZW91dCA9IDEwMDsJCgluZXdfYWRhcHRlci0+cmV0cmllcyA9IDM7CgluZXdfYWRhcHRlci0+YWxnbyA9ICZpb3AzeHhfaTJjX2FsZ287CgoJaW5pdF93YWl0cXVldWVfaGVhZCgmYWRhcHRlcl9kYXRhLT53YWl0cSk7CglzcGluX2xvY2tfaW5pdCgmYWRhcHRlcl9kYXRhLT5sb2NrKTsKCglpb3AzeHhfaTJjX3Jlc2V0KGFkYXB0ZXJfZGF0YSk7Cglpb3AzeHhfaTJjX3NldF9zbGF2ZV9hZGRyKGFkYXB0ZXJfZGF0YSk7Cglpb3AzeHhfaTJjX2VuYWJsZShhZGFwdGVyX2RhdGEpOwoKCWRldl9zZXRfZHJ2ZGF0YSgmcGRldi0+ZGV2LCBuZXdfYWRhcHRlcik7CgluZXdfYWRhcHRlci0+YWxnb19kYXRhID0gYWRhcHRlcl9kYXRhOwoKCWkyY19hZGRfYWRhcHRlcihuZXdfYWRhcHRlcik7CgoJcmV0dXJuIDA7Cgp1bm1hcDoKCWlvdW5tYXAoKHZvaWQgX19pb21lbSopYWRhcHRlcl9kYXRhLT5pb2FkZHIpOwoKcmVsZWFzZV9yZWdpb246CglyZWxlYXNlX21lbV9yZWdpb24ocmVzLT5zdGFydCwgSU9QM1hYX0kyQ19JT19TSVpFKTsKCmZyZWVfYm90aDoKCWtmcmVlKGFkYXB0ZXJfZGF0YSk7CgpmcmVlX2FkYXB0ZXI6CglrZnJlZShuZXdfYWRhcHRlcik7CgpvdXQ6CglyZXR1cm4gcmV0Owp9CgoKc3RhdGljIHN0cnVjdCBkZXZpY2VfZHJpdmVyIGlvcDN4eF9pMmNfZHJpdmVyID0gewoJLm5hbWUJCT0gIklPUDN4eC1JMkMiLAoJLmJ1cwkJPSAmcGxhdGZvcm1fYnVzX3R5cGUsCgkucHJvYmUJCT0gaW9wM3h4X2kyY19wcm9iZSwKCS5yZW1vdmUJCT0gaW9wM3h4X2kyY19yZW1vdmUKfTsKCnN0YXRpYyBpbnQgX19pbml0IAppMmNfaW9wM3h4X2luaXQgKHZvaWQpCnsKCXJldHVybiBkcml2ZXJfcmVnaXN0ZXIoJmlvcDN4eF9pMmNfZHJpdmVyKTsKfQoKc3RhdGljIHZvaWQgX19leGl0IAppMmNfaW9wM3h4X2V4aXQgKHZvaWQpCnsKCWRyaXZlcl91bnJlZ2lzdGVyKCZpb3AzeHhfaTJjX2RyaXZlcik7CglyZXR1cm47Cn0KCm1vZHVsZV9pbml0IChpMmNfaW9wM3h4X2luaXQpOwptb2R1bGVfZXhpdCAoaTJjX2lvcDN4eF9leGl0KTsKCk1PRFVMRV9BVVRIT1IoIkQtVEFDUSBTb2x1dGlvbnMgTHRkIDx3d3cuZC10YWNxLmNvbT4iKTsKTU9EVUxFX0RFU0NSSVBUSU9OKCJJT1AzeHggaWljIGFsZ29yaXRobSBhbmQgZHJpdmVyIik7Ck1PRFVMRV9MSUNFTlNFKCJHUEwiKTsK