LyoKICogY2kxM3h4eF91ZGMuYyAtIE1JUFMgVVNCIElQIGNvcmUgZmFtaWx5IGRldmljZSBjb250cm9sbGVyCiAqCiAqIENvcHlyaWdodCAoQykgMjAwOCBDaGlwaWRlYSAtIE1JUFMgVGVjaG5vbG9naWVzLCBJbmMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAqCiAqIEF1dGhvcjogRGF2aWQgTG9wbwogKgogKiBUaGlzIHByb2dyYW0gaXMgZnJlZSBzb2Z0d2FyZTsgeW91IGNhbiByZWRpc3RyaWJ1dGUgaXQgYW5kL29yIG1vZGlmeQogKiBpdCB1bmRlciB0aGUgdGVybXMgb2YgdGhlIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlIHZlcnNpb24gMiBhcwogKiBwdWJsaXNoZWQgYnkgdGhlIEZyZWUgU29mdHdhcmUgRm91bmRhdGlvbi4KICovCgovKgogKiBEZXNjcmlwdGlvbjogTUlQUyBVU0IgSVAgY29yZSBmYW1pbHkgZGV2aWNlIGNvbnRyb2xsZXIKICogICAgICAgICAgICAgIEN1cnJlbnRseSBpdCBvbmx5IHN1cHBvcnRzIElQIHBhcnQgbnVtYmVyIENJMTM0MTIKICoKICogVGhpcyBkcml2ZXIgaXMgY29tcG9zZWQgb2Ygc2V2ZXJhbCBibG9ja3M6CiAqIC0gSFc6ICAgICBoYXJkd2FyZSBpbnRlcmZhY2UKICogLSBEQkc6ICAgIGRlYnVnIGZhY2lsaXRpZXMgKG9wdGlvbmFsKQogKiAtIFVUSUw6ICAgdXRpbGl0aWVzCiAqIC0gSVNSOiAgICBpbnRlcnJ1cHRzIGhhbmRsaW5nCiAqIC0gRU5EUFQ6ICBlbmRwb2ludCBvcGVyYXRpb25zIChHYWRnZXQgQVBJKQogKiAtIEdBREdFVDogZ2FkZ2V0IG9wZXJhdGlvbnMgKEdhZGdldCBBUEkpCiAqIC0gQlVTOiAgICBidXMgZ2x1ZSBjb2RlLCBidXMgYWJzdHJhY3Rpb24gbGF5ZXIKICogLSBQQ0k6ICAgIFBDSSBjb3JlIGludGVyZmFjZSBhbmQgUENJIHJlc291cmNlcyAoaW50ZXJydXB0cywgbWVtb3J5Li4uKQogKgogKiBDb21waWxlIE9wdGlvbnMKICogLSBDT05GSUdfVVNCX0dBREdFVF9ERUJVR19GSUxFUzogZW5hYmxlIGRlYnVnIGZhY2lsaXRpZXMKICogLSBTVEFMTF9JTjogIG5vbi1lbXB0eSBidWxrLWluIHBpcGVzIGNhbm5vdCBiZSBoYWx0ZWQKICogICAgICAgICAgICAgIGlmIGRlZmluZWQgbWFzcyBzdG9yYWdlIGNvbXBsaWFuY2Ugc3VjY2VlZHMgYnV0IHdpdGggd2FybmluZ3MKICogICAgICAgICAgICAgID0+IGNhc2UgNDogSGkgPiAgRG4KICogICAgICAgICAgICAgID0+IGNhc2UgNTogSGkgPiAgRGkKICogICAgICAgICAgICAgID0+IGNhc2UgODogSGkgPD4gRG8KICogICAgICAgICAgICAgIGlmIHVuZGVmaW5lZCB1c2J0ZXN0IDEzIGZhaWxzCiAqIC0gVFJBQ0U6ICAgICBlbmFibGUgZnVuY3Rpb24gdHJhY2luZyAoZGVwZW5kcyBvbiBERUJVRykKICoKICogTWFpbiBGZWF0dXJlcwogKiAtIENoYXB0ZXIgOSAmIE1hc3MgU3RvcmFnZSBDb21wbGlhbmNlIHdpdGggR2FkZ2V0IEZpbGUgU3RvcmFnZQogKiAtIENoYXB0ZXIgOSBDb21wbGlhbmNlIHdpdGggR2FkZ2V0IFplcm8gKFNUQUxMX0lOIHVuZGVmaW5lZCkKICogLSBOb3JtYWwgJiBMUE0gc3VwcG9ydAogKgogKiBVU0JURVNUIFJlcG9ydAogKiAtIE9LOiAwLTEyLCAxMyAoU1RBTExfSU4gZGVmaW5lZCkgJiAxNAogKiAtIE5vdCBTdXBwb3J0ZWQ6IDE1ICYgMTYgKElTTykKICoKICogVE9ETyBMaXN0CiAqIC0gT1RHCiAqIC0gSXNvY2hyb25vdXMgJiBJbnRlcnJ1cHQgVHJhZmZpYwogKiAtIEhhbmRsZSByZXF1ZXN0cyB3aGljaCBzcGF3bnMgaW50byBzZXZlcmFsIFREcwogKiAtIEdFVF9TVEFUVVMoZGV2aWNlKSAtIGFsd2F5cyByZXBvcnRzIDAKICogLSBHYWRnZXQgQVBJIChtYWpvcml0eSBvZiBvcHRpb25hbCBmZWF0dXJlcykKICogLSBTdXNwZW5kICYgUmVtb3RlIFdha2V1cAogKi8KI2luY2x1ZGUgPGxpbnV4L2RldmljZS5oPgojaW5jbHVkZSA8bGludXgvZG1hcG9vbC5oPgojaW5jbHVkZSA8bGludXgvZG1hLW1hcHBpbmcuaD4KI2luY2x1ZGUgPGxpbnV4L2luaXQuaD4KI2luY2x1ZGUgPGxpbnV4L2ludGVycnVwdC5oPgojaW5jbHVkZSA8bGludXgvaW50ZXJydXB0Lmg+CiNpbmNsdWRlIDxsaW51eC9pby5oPgojaW5jbHVkZSA8bGludXgvaXJxLmg+CiNpbmNsdWRlIDxsaW51eC9rZXJuZWwuaD4KI2luY2x1ZGUgPGxpbnV4L21vZHVsZS5oPgojaW5jbHVkZSA8bGludXgvcGNpLmg+CiNpbmNsdWRlIDxsaW51eC91c2IvY2g5Lmg+CiNpbmNsdWRlIDxsaW51eC91c2IvZ2FkZ2V0Lmg+CgojaW5jbHVkZSAiY2kxM3h4eF91ZGMuaCIKCgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIERFRklORQogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCi8qIGN0cmwgcmVnaXN0ZXIgYmFuayBhY2Nlc3MgKi8Kc3RhdGljIERFRklORV9TUElOTE9DSyh1ZGNfbG9jayk7CgovKiBkcml2ZXIgbmFtZSAqLwojZGVmaW5lIFVEQ19EUklWRVJfTkFNRSAgICJjaTEzeHh4X3VkYyIKCi8qIGNvbnRyb2wgZW5kcG9pbnQgZGVzY3JpcHRpb24gKi8Kc3RhdGljIGNvbnN0IHN0cnVjdCB1c2JfZW5kcG9pbnRfZGVzY3JpcHRvcgpjdHJsX2VuZHB0X2Rlc2MgPSB7CgkuYkxlbmd0aCAgICAgICAgID0gVVNCX0RUX0VORFBPSU5UX1NJWkUsCgkuYkRlc2NyaXB0b3JUeXBlID0gVVNCX0RUX0VORFBPSU5ULAoKCS5ibUF0dHJpYnV0ZXMgICAgPSBVU0JfRU5EUE9JTlRfWEZFUl9DT05UUk9MLAoJLndNYXhQYWNrZXRTaXplICA9IGNwdV90b19sZTE2KENUUkxfUEFZTE9BRF9NQVgpLAp9OwoKLyogVURDIGRlc2NyaXB0b3IgKi8Kc3RhdGljIHN0cnVjdCBjaTEzeHh4ICpfdWRjOwoKLyogSW50ZXJydXB0IHN0YXRpc3RpY3MgKi8KI2RlZmluZSBJU1JfTUFTSyAgIDB4MUYKc3RhdGljIHN0cnVjdCB7Cgl1MzIgdGVzdDsKCXUzMiB1aTsKCXUzMiB1ZWk7Cgl1MzIgcGNpOwoJdTMyIHVyaTsKCXUzMiBzbGk7Cgl1MzIgbm9uZTsKCXN0cnVjdCB7CgkJdTMyIGNudDsKCQl1MzIgYnVmW0lTUl9NQVNLKzFdOwoJCXUzMiBpZHg7Cgl9IGhuZGw7Cn0gaXNyX3N0YXRpc3RpY3M7CgovKioKICogZmZzX25yOiBmaW5kIGZpcnN0IChsZWFzdCBzaWduaWZpY2FudCkgYml0IHNldAogKiBAeDogdGhlIHdvcmQgdG8gc2VhcmNoCiAqCiAqIFRoaXMgZnVuY3Rpb24gcmV0dXJucyBiaXQgbnVtYmVyIChpbnN0ZWFkIG9mIHBvc2l0aW9uKQogKi8Kc3RhdGljIGludCBmZnNfbnIodTMyIHgpCnsKCWludCBuID0gZmZzKHgpOwoKCXJldHVybiBuID8gbi0xIDogMzI7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSFcgYmxvY2sKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwovKiByZWdpc3RlciBiYW5rIGRlc2NyaXB0b3IgKi8Kc3RhdGljIHN0cnVjdCB7Cgl1bnNpZ25lZCAgICAgIGxwbTsgICAgLyogaXMgTFBNPyAqLwoJdm9pZCBfX2lvbWVtICphYnM7ICAgIC8qIGJ1cyBtYXAgb2Zmc2V0ICovCgl2b2lkIF9faW9tZW0gKmNhcDsgICAgLyogYnVzIG1hcCBvZmZzZXQgKyBDQVAgb2Zmc2V0ICsgQ0FQIGRhdGEgKi8KCXNpemVfdCAgICAgICAgc2l6ZTsgICAvKiBiYW5rIHNpemUgKi8KfSBod19iYW5rOwoKLyogVURDIHJlZ2lzdGVyIG1hcCAqLwojZGVmaW5lIEFCU19DQVBMRU5HVEggICAgICAgKDB4MTAwVUwpCiNkZWZpbmUgQUJTX0hDQ1BBUkFNUyAgICAgICAoMHgxMDhVTCkKI2RlZmluZSBBQlNfRENDUEFSQU1TICAgICAgICgweDEyNFVMKQojZGVmaW5lIEFCU19URVNUTU9ERSAgICAgICAgKGh3X2JhbmsubHBtID8gMHgwRkNVTCA6IDB4MTM4VUwpCi8qIG9mZnNldCB0byBDQVBMRU5UR0ggKGFkZHIgKyBkYXRhKSAqLwojZGVmaW5lIENBUF9VU0JDTUQgICAgICAgICAgKDB4MDAwVUwpCiNkZWZpbmUgQ0FQX1VTQlNUUyAgICAgICAgICAoMHgwMDRVTCkKI2RlZmluZSBDQVBfVVNCSU5UUiAgICAgICAgICgweDAwOFVMKQojZGVmaW5lIENBUF9ERVZJQ0VBRERSICAgICAgKDB4MDE0VUwpCiNkZWZpbmUgQ0FQX0VORFBUTElTVEFERFIgICAoMHgwMThVTCkKI2RlZmluZSBDQVBfUE9SVFNDICAgICAgICAgICgweDA0NFVMKQojZGVmaW5lIENBUF9ERVZMQyAgICAgICAgICAgKDB4MEI0VUwpCiNkZWZpbmUgQ0FQX1VTQk1PREUgICAgICAgICAoaHdfYmFuay5scG0gPyAweDBDOFVMIDogMHgwNjhVTCkKI2RlZmluZSBDQVBfRU5EUFRTRVRVUFNUQVQgIChod19iYW5rLmxwbSA/IDB4MEQ4VUwgOiAweDA2Q1VMKQojZGVmaW5lIENBUF9FTkRQVFBSSU1FICAgICAgKGh3X2JhbmsubHBtID8gMHgwRENVTCA6IDB4MDcwVUwpCiNkZWZpbmUgQ0FQX0VORFBURkxVU0ggICAgICAoaHdfYmFuay5scG0gPyAweDBFMFVMIDogMHgwNzRVTCkKI2RlZmluZSBDQVBfRU5EUFRTVEFUICAgICAgIChod19iYW5rLmxwbSA/IDB4MEU0VUwgOiAweDA3OFVMKQojZGVmaW5lIENBUF9FTkRQVENPTVBMRVRFICAgKGh3X2JhbmsubHBtID8gMHgwRThVTCA6IDB4MDdDVUwpCiNkZWZpbmUgQ0FQX0VORFBUQ1RSTCAgICAgICAoaHdfYmFuay5scG0gPyAweDBFQ1VMIDogMHgwODBVTCkKI2RlZmluZSBDQVBfTEFTVCAgICAgICAgICAgIChod19iYW5rLmxwbSA/IDB4MTJDVUwgOiAweDBDMFVMKQoKLyogbWF4aW11bSBudW1iZXIgb2YgZW5wb2ludHM6IHZhbGlkIG9ubHkgYWZ0ZXIgaHdfZGV2aWNlX3Jlc2V0KCkgKi8Kc3RhdGljIHVuc2lnbmVkIGh3X2VwX21heDsKCi8qKgogKiBod19lcF9iaXQ6IGNhbGN1bGF0ZXMgdGhlIGJpdCBudW1iZXIKICogQG51bTogZW5kcG9pbnQgbnVtYmVyCiAqIEBkaXI6IGVuZHBvaW50IGRpcmVjdGlvbgogKgogKiBUaGlzIGZ1bmN0aW9uIHJldHVybnMgYml0IG51bWJlcgogKi8Kc3RhdGljIGlubGluZSBpbnQgaHdfZXBfYml0KGludCBudW0sIGludCBkaXIpCnsKCXJldHVybiBudW0gKyAoZGlyID8gMTYgOiAwKTsKfQoKLyoqCiAqIGh3X2FyZWFkOiByZWFkcyBmcm9tIHJlZ2lzdGVyIGJpdGZpZWxkCiAqIEBhZGRyOiBhZGRyZXNzIHJlbGF0aXZlIHRvIGJ1cyBtYXAKICogQG1hc2s6IGJpdGZpZWxkIG1hc2sKICoKICogVGhpcyBmdW5jdGlvbiByZXR1cm5zIHJlZ2lzdGVyIGJpdGZpZWxkIGRhdGEKICovCnN0YXRpYyB1MzIgaHdfYXJlYWQodTMyIGFkZHIsIHUzMiBtYXNrKQp7CglyZXR1cm4gaW9yZWFkMzIoYWRkciArIGh3X2JhbmsuYWJzKSAmIG1hc2s7Cn0KCi8qKgogKiBod19hd3JpdGU6IHdyaXRlcyB0byByZWdpc3RlciBiaXRmaWVsZAogKiBAYWRkcjogYWRkcmVzcyByZWxhdGl2ZSB0byBidXMgbWFwCiAqIEBtYXNrOiBiaXRmaWVsZCBtYXNrCiAqIEBkYXRhOiBuZXcgZGF0YQogKi8Kc3RhdGljIHZvaWQgaHdfYXdyaXRlKHUzMiBhZGRyLCB1MzIgbWFzaywgdTMyIGRhdGEpCnsKCWlvd3JpdGUzMihod19hcmVhZChhZGRyLCB+bWFzaykgfCAoZGF0YSAmIG1hc2spLAoJCSAgYWRkciArIGh3X2JhbmsuYWJzKTsKfQoKLyoqCiAqIGh3X2NyZWFkOiByZWFkcyBmcm9tIHJlZ2lzdGVyIGJpdGZpZWxkCiAqIEBhZGRyOiBhZGRyZXNzIHJlbGF0aXZlIHRvIENBUCBvZmZzZXQgcGx1cyBjb250ZW50CiAqIEBtYXNrOiBiaXRmaWVsZCBtYXNrCiAqCiAqIFRoaXMgZnVuY3Rpb24gcmV0dXJucyByZWdpc3RlciBiaXRmaWVsZCBkYXRhCiAqLwpzdGF0aWMgdTMyIGh3X2NyZWFkKHUzMiBhZGRyLCB1MzIgbWFzaykKewoJcmV0dXJuIGlvcmVhZDMyKGFkZHIgKyBod19iYW5rLmNhcCkgJiBtYXNrOwp9CgovKioKICogaHdfY3dyaXRlOiB3cml0ZXMgdG8gcmVnaXN0ZXIgYml0ZmllbGQKICogQGFkZHI6IGFkZHJlc3MgcmVsYXRpdmUgdG8gQ0FQIG9mZnNldCBwbHVzIGNvbnRlbnQKICogQG1hc2s6IGJpdGZpZWxkIG1hc2sKICogQGRhdGE6IG5ldyBkYXRhCiAqLwpzdGF0aWMgdm9pZCBod19jd3JpdGUodTMyIGFkZHIsIHUzMiBtYXNrLCB1MzIgZGF0YSkKewoJaW93cml0ZTMyKGh3X2NyZWFkKGFkZHIsIH5tYXNrKSB8IChkYXRhICYgbWFzayksCgkJICBhZGRyICsgaHdfYmFuay5jYXApOwp9CgovKioKICogaHdfY3Rlc3RfYW5kX2NsZWFyOiB0ZXN0cyAmIGNsZWFycyByZWdpc3RlciBiaXRmaWVsZAogKiBAYWRkcjogYWRkcmVzcyByZWxhdGl2ZSB0byBDQVAgb2Zmc2V0IHBsdXMgY29udGVudAogKiBAbWFzazogYml0ZmllbGQgbWFzawogKgogKiBUaGlzIGZ1bmN0aW9uIHJldHVybnMgcmVnaXN0ZXIgYml0ZmllbGQgZGF0YQogKi8Kc3RhdGljIHUzMiBod19jdGVzdF9hbmRfY2xlYXIodTMyIGFkZHIsIHUzMiBtYXNrKQp7Cgl1MzIgcmVnID0gaHdfY3JlYWQoYWRkciwgbWFzayk7CgoJaW93cml0ZTMyKHJlZywgYWRkciArIGh3X2JhbmsuY2FwKTsKCXJldHVybiByZWc7Cn0KCi8qKgogKiBod19jdGVzdF9hbmRfd3JpdGU6IHRlc3RzICYgd3JpdGVzIHJlZ2lzdGVyIGJpdGZpZWxkCiAqIEBhZGRyOiBhZGRyZXNzIHJlbGF0aXZlIHRvIENBUCBvZmZzZXQgcGx1cyBjb250ZW50CiAqIEBtYXNrOiBiaXRmaWVsZCBtYXNrCiAqIEBkYXRhOiBuZXcgZGF0YQogKgogKiBUaGlzIGZ1bmN0aW9uIHJldHVybnMgcmVnaXN0ZXIgYml0ZmllbGQgZGF0YQogKi8Kc3RhdGljIHUzMiBod19jdGVzdF9hbmRfd3JpdGUodTMyIGFkZHIsIHUzMiBtYXNrLCB1MzIgZGF0YSkKewoJdTMyIHJlZyA9IGh3X2NyZWFkKGFkZHIsIH4wKTsKCglpb3dyaXRlMzIoKHJlZyAmIH5tYXNrKSB8IChkYXRhICYgbWFzayksIGFkZHIgKyBod19iYW5rLmNhcCk7CglyZXR1cm4gKHJlZyAmIG1hc2spID4+IGZmc19ucihtYXNrKTsKfQoKLyoqCiAqIGh3X2RldmljZV9yZXNldDogcmVzZXRzIGNoaXAgKGV4ZWN1dGUgd2l0aG91dCBpbnRlcnJ1cHRpb24pCiAqIEBiYXNlOiByZWdpc3RlciBiYXNlIGFkZHJlc3MKICoKICogVGhpcyBmdW5jdGlvbiByZXR1cm5zIGFuIGVycm9yIGNvZGUKICovCnN0YXRpYyBpbnQgaHdfZGV2aWNlX3Jlc2V0KHZvaWQgX19pb21lbSAqYmFzZSkKewoJdTMyIHJlZzsKCgkvKiBiYW5rIGlzIGEgbW9kdWxlIHZhcmlhYmxlICovCglod19iYW5rLmFicyA9IGJhc2U7CgoJaHdfYmFuay5jYXAgPSBod19iYW5rLmFiczsKCWh3X2JhbmsuY2FwICs9IEFCU19DQVBMRU5HVEg7Cglod19iYW5rLmNhcCArPSBpb3JlYWQ4KGh3X2JhbmsuY2FwKTsKCglyZWcgPSBod19hcmVhZChBQlNfSENDUEFSQU1TLCBIQ0NQQVJBTVNfTEVOKSA+PiBmZnNfbnIoSENDUEFSQU1TX0xFTik7Cglod19iYW5rLmxwbSAgPSByZWc7Cglod19iYW5rLnNpemUgPSBod19iYW5rLmNhcCAtIGh3X2JhbmsuYWJzOwoJaHdfYmFuay5zaXplICs9IENBUF9MQVNUOwoJaHdfYmFuay5zaXplIC89IHNpemVvZih1MzIpOwoKCS8qIHNob3VsZCBmbHVzaCAmIHN0b3AgYmVmb3JlIHJlc2V0ICovCglod19jd3JpdGUoQ0FQX0VORFBURkxVU0gsIH4wLCB+MCk7Cglod19jd3JpdGUoQ0FQX1VTQkNNRCwgVVNCQ01EX1JTLCAwKTsKCglod19jd3JpdGUoQ0FQX1VTQkNNRCwgVVNCQ01EX1JTVCwgVVNCQ01EX1JTVCk7Cgl3aGlsZSAoaHdfY3JlYWQoQ0FQX1VTQkNNRCwgVVNCQ01EX1JTVCkpCgkJdWRlbGF5KDEwKTsgICAgICAgICAgICAgLyogbm90IFJUT1MgZnJpZW5kbHkgKi8KCgkvKiBVU0JNT0RFIHNob3VsZCBiZSBjb25maWd1cmVkIHN0ZXAgYnkgc3RlcCAqLwoJaHdfY3dyaXRlKENBUF9VU0JNT0RFLCBVU0JNT0RFX0NNLCBVU0JNT0RFX0NNX0lETEUpOwoJaHdfY3dyaXRlKENBUF9VU0JNT0RFLCBVU0JNT0RFX0NNLCBVU0JNT0RFX0NNX0RFVklDRSk7Cglod19jd3JpdGUoQ0FQX1VTQk1PREUsIFVTQk1PREVfU0xPTSwgVVNCTU9ERV9TTE9NKTsgIC8qIEhXID49IDIuMyAqLwoKCWlmIChod19jcmVhZChDQVBfVVNCTU9ERSwgVVNCTU9ERV9DTSkgIT0gVVNCTU9ERV9DTV9ERVZJQ0UpIHsKCQlwcl9lcnIoImNhbm5vdCBlbnRlciBpbiBkZXZpY2UgbW9kZSIpOwoJCXByX2VycigibHBtID0gJWkiLCBod19iYW5rLmxwbSk7CgkJcmV0dXJuIC1FTk9ERVY7Cgl9CgoJcmVnID0gaHdfYXJlYWQoQUJTX0RDQ1BBUkFNUywgRENDUEFSQU1TX0RFTikgPj4gZmZzX25yKERDQ1BBUkFNU19ERU4pOwoJaWYgKHJlZyA9PSAwIHx8IHJlZyA+IEVORFBUX01BWCkKCQlyZXR1cm4gLUVOT0RFVjsKCglod19lcF9tYXggPSByZWc7ICAgLyogY2FjaGUgaHcgRU5EUFRfTUFYICovCgoJLyogc2V0dXAgbG9jayBtb2RlID8gKi8KCgkvKiBFTkRQVFNFVFVQU1RBVCBpcyAnMCcgYnkgZGVmYXVsdCAqLwoKCS8qIEhDU1BBUkFNUy5iZi5wcGMgU0hPVUxEIEJFIHplcm8gZm9yIGRldmljZSAqLwoKCXJldHVybiAwOwp9CgovKioKICogaHdfZGV2aWNlX3N0YXRlOiBlbmFibGVzL2Rpc2FibGVzIGludGVycnVwdHMgJiBzdGFydHMvc3RvcHMgZGV2aWNlIChleGVjdXRlCiAqICAgICAgICAgICAgICAgICAgd2l0aG91dCBpbnRlcnJ1cHRpb24pCiAqIEBkbWE6IDAgPT4gZGlzYWJsZSwgITAgPT4gZW5hYmxlIGFuZCBzZXQgZG1hIGVuZ2luZQogKgogKiBUaGlzIGZ1bmN0aW9uIHJldHVybnMgYW4gZXJyb3IgY29kZQogKi8Kc3RhdGljIGludCBod19kZXZpY2Vfc3RhdGUodTMyIGRtYSkKewoJaWYgKGRtYSkgewoJCWh3X2N3cml0ZShDQVBfRU5EUFRMSVNUQUREUiwgfjAsIGRtYSk7CgkJLyogaW50ZXJydXB0LCBlcnJvciwgcG9ydCBjaGFuZ2UsIHJlc2V0LCBzbGVlcC9zdXNwZW5kICovCgkJaHdfY3dyaXRlKENBUF9VU0JJTlRSLCB+MCwKCQkJICAgICBVU0JpX1VJfFVTQmlfVUVJfFVTQmlfUENJfFVTQmlfVVJJfFVTQmlfU0xJKTsKCQlod19jd3JpdGUoQ0FQX1VTQkNNRCwgVVNCQ01EX1JTLCBVU0JDTURfUlMpOwoJfSBlbHNlIHsKCQlod19jd3JpdGUoQ0FQX1VTQkNNRCwgVVNCQ01EX1JTLCAwKTsKCQlod19jd3JpdGUoQ0FQX1VTQklOVFIsIH4wLCAwKTsKCX0KCXJldHVybiAwOwp9CgovKioKICogaHdfZXBfZmx1c2g6IGZsdXNoIGVuZHBvaW50IGZpZm8gKGV4ZWN1dGUgd2l0aG91dCBpbnRlcnJ1cHRpb24pCiAqIEBudW06IGVuZHBvaW50IG51bWJlcgogKiBAZGlyOiBlbmRwb2ludCBkaXJlY3Rpb24KICoKICogVGhpcyBmdW5jdGlvbiByZXR1cm5zIGFuIGVycm9yIGNvZGUKICovCnN0YXRpYyBpbnQgaHdfZXBfZmx1c2goaW50IG51bSwgaW50IGRpcikKewoJaW50IG4gPSBod19lcF9iaXQobnVtLCBkaXIpOwoKCWRvIHsKCQkvKiBmbHVzaCBhbnkgcGVuZGluZyB0cmFuc2ZlciAqLwoJCWh3X2N3cml0ZShDQVBfRU5EUFRGTFVTSCwgQklUKG4pLCBCSVQobikpOwoJCXdoaWxlIChod19jcmVhZChDQVBfRU5EUFRGTFVTSCwgQklUKG4pKSkKCQkJY3B1X3JlbGF4KCk7Cgl9IHdoaWxlIChod19jcmVhZChDQVBfRU5EUFRTVEFULCBCSVQobikpKTsKCglyZXR1cm4gMDsKfQoKLyoqCiAqIGh3X2VwX2Rpc2FibGU6IGRpc2FibGVzIGVuZHBvaW50IChleGVjdXRlIHdpdGhvdXQgaW50ZXJydXB0aW9uKQogKiBAbnVtOiBlbmRwb2ludCBudW1iZXIKICogQGRpcjogZW5kcG9pbnQgZGlyZWN0aW9uCiAqCiAqIFRoaXMgZnVuY3Rpb24gcmV0dXJucyBhbiBlcnJvciBjb2RlCiAqLwpzdGF0aWMgaW50IGh3X2VwX2Rpc2FibGUoaW50IG51bSwgaW50IGRpcikKewoJaHdfZXBfZmx1c2gobnVtLCBkaXIpOwoJaHdfY3dyaXRlKENBUF9FTkRQVENUUkwgKyBudW0gKiBzaXplb2YodTMyKSwKCQkgIGRpciA/IEVORFBUQ1RSTF9UWEUgOiBFTkRQVENUUkxfUlhFLCAwKTsKCXJldHVybiAwOwp9CgovKioKICogaHdfZXBfZW5hYmxlOiBlbmFibGVzIGVuZHBvaW50IChleGVjdXRlIHdpdGhvdXQgaW50ZXJydXB0aW9uKQogKiBAbnVtOiAgZW5kcG9pbnQgbnVtYmVyCiAqIEBkaXI6ICBlbmRwb2ludCBkaXJlY3Rpb24KICogQHR5cGU6IGVuZHBvaW50IHR5cGUKICoKICogVGhpcyBmdW5jdGlvbiByZXR1cm5zIGFuIGVycm9yIGNvZGUKICovCnN0YXRpYyBpbnQgaHdfZXBfZW5hYmxlKGludCBudW0sIGludCBkaXIsIGludCB0eXBlKQp7Cgl1MzIgbWFzaywgZGF0YTsKCglpZiAoZGlyKSB7CgkJbWFzayAgPSBFTkRQVENUUkxfVFhUOyAgLyogdHlwZSAgICAqLwoJCWRhdGEgID0gdHlwZSA8PCBmZnNfbnIobWFzayk7CgoJCW1hc2sgfD0gRU5EUFRDVFJMX1RYUzsgIC8qIHVuc3RhbGwgKi8KCQltYXNrIHw9IEVORFBUQ1RSTF9UWFI7ICAvKiByZXNldCBkYXRhIHRvZ2dsZSAqLwoJCWRhdGEgfD0gRU5EUFRDVFJMX1RYUjsKCQltYXNrIHw9IEVORFBUQ1RSTF9UWEU7ICAvKiBlbmFibGUgICovCgkJZGF0YSB8PSBFTkRQVENUUkxfVFhFOwoJfSBlbHNlIHsKCQltYXNrICA9IEVORFBUQ1RSTF9SWFQ7ICAvKiB0eXBlICAgICovCgkJZGF0YSAgPSB0eXBlIDw8IGZmc19ucihtYXNrKTsKCgkJbWFzayB8PSBFTkRQVENUUkxfUlhTOyAgLyogdW5zdGFsbCAqLwoJCW1hc2sgfD0gRU5EUFRDVFJMX1JYUjsgIC8qIHJlc2V0IGRhdGEgdG9nZ2xlICovCgkJZGF0YSB8PSBFTkRQVENUUkxfUlhSOwoJCW1hc2sgfD0gRU5EUFRDVFJMX1JYRTsgIC8qIGVuYWJsZSAgKi8KCQlkYXRhIHw9IEVORFBUQ1RSTF9SWEU7Cgl9Cglod19jd3JpdGUoQ0FQX0VORFBUQ1RSTCArIG51bSAqIHNpemVvZih1MzIpLCBtYXNrLCBkYXRhKTsKCXJldHVybiAwOwp9CgovKioKICogaHdfZXBfZ2V0X2hhbHQ6IHJldHVybiBlbmRwb2ludCBoYWx0IHN0YXR1cwogKiBAbnVtOiBlbmRwb2ludCBudW1iZXIKICogQGRpcjogZW5kcG9pbnQgZGlyZWN0aW9uCiAqCiAqIFRoaXMgZnVuY3Rpb24gcmV0dXJucyAxIGlmIGVuZHBvaW50IGhhbHRlZAogKi8Kc3RhdGljIGludCBod19lcF9nZXRfaGFsdChpbnQgbnVtLCBpbnQgZGlyKQp7Cgl1MzIgbWFzayA9IGRpciA/IEVORFBUQ1RSTF9UWFMgOiBFTkRQVENUUkxfUlhTOwoKCXJldHVybiBod19jcmVhZChDQVBfRU5EUFRDVFJMICsgbnVtICogc2l6ZW9mKHUzMiksIG1hc2spID8gMSA6IDA7Cn0KCi8qKgogKiBod19lcF9pc19wcmltZWQ6IHRlc3QgaWYgZW5kcG9pbnQgaXMgcHJpbWVkIChleGVjdXRlIHdpdGhvdXQgaW50ZXJydXB0aW9uKQogKiBAbnVtOiAgIGVuZHBvaW50IG51bWJlcgogKiBAZGlyOiAgIGVuZHBvaW50IGRpcmVjdGlvbgogKgogKiBUaGlzIGZ1bmN0aW9uIHJldHVybnMgdHJ1ZSBpZiBlbmRwb2ludCBwcmltZWQKICovCnN0YXRpYyBpbnQgaHdfZXBfaXNfcHJpbWVkKGludCBudW0sIGludCBkaXIpCnsKCXUzMiByZWcgPSBod19jcmVhZChDQVBfRU5EUFRQUklNRSwgfjApIHwgaHdfY3JlYWQoQ0FQX0VORFBUU1RBVCwgfjApOwoKCXJldHVybiB0ZXN0X2JpdChod19lcF9iaXQobnVtLCBkaXIpLCAodm9pZCAqKSZyZWcpOwp9CgovKioKICogaHdfdGVzdF9hbmRfY2xlYXJfc2V0dXBfc3RhdHVzOiB0ZXN0ICYgY2xlYXIgc2V0dXAgc3RhdHVzIChleGVjdXRlIHdpdGhvdXQKICogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBpbnRlcnJ1cHRpb24pCiAqIEBuOiBiaXQgbnVtYmVyIChlbmRwb2ludCkKICoKICogVGhpcyBmdW5jdGlvbiByZXR1cm5zIHNldHVwIHN0YXR1cwogKi8Kc3RhdGljIGludCBod190ZXN0X2FuZF9jbGVhcl9zZXR1cF9zdGF0dXMoaW50IG4pCnsKCXJldHVybiBod19jdGVzdF9hbmRfY2xlYXIoQ0FQX0VORFBUU0VUVVBTVEFULCBCSVQobikpOwp9CgovKioKICogaHdfZXBfcHJpbWU6IHByaW1lcyBlbmRwb2ludCAoZXhlY3V0ZSB3aXRob3V0IGludGVycnVwdGlvbikKICogQG51bTogICAgIGVuZHBvaW50IG51bWJlcgogKiBAZGlyOiAgICAgZW5kcG9pbnQgZGlyZWN0aW9uCiAqIEBpc19jdHJsOiB0cnVlIGlmIGNvbnRyb2wgZW5kcG9pbnQKICoKICogVGhpcyBmdW5jdGlvbiByZXR1cm5zIGFuIGVycm9yIGNvZGUKICovCnN0YXRpYyBpbnQgaHdfZXBfcHJpbWUoaW50IG51bSwgaW50IGRpciwgaW50IGlzX2N0cmwpCnsKCWludCBuID0gaHdfZXBfYml0KG51bSwgZGlyKTsKCgkvKiB0aGUgY2FsbGVyIHNob3VsZCBmbHVzaCBmaXJzdCAqLwoJaWYgKGh3X2VwX2lzX3ByaW1lZChudW0sIGRpcikpCgkJcmV0dXJuIC1FQlVTWTsKCglpZiAoaXNfY3RybCAmJiBkaXIgPT0gUlggJiYgaHdfY3JlYWQoQ0FQX0VORFBUU0VUVVBTVEFULCBCSVQobnVtKSkpCgkJcmV0dXJuIC1FQUdBSU47CgoJaHdfY3dyaXRlKENBUF9FTkRQVFBSSU1FLCBCSVQobiksIEJJVChuKSk7CgoJd2hpbGUgKGh3X2NyZWFkKENBUF9FTkRQVFBSSU1FLCBCSVQobikpKQoJCWNwdV9yZWxheCgpOwoJaWYgKGlzX2N0cmwgJiYgZGlyID09IFJYICAmJiBod19jcmVhZChDQVBfRU5EUFRTRVRVUFNUQVQsIEJJVChudW0pKSkKCQlyZXR1cm4gLUVBR0FJTjsKCgkvKiBzdGF0dXMgc2hvdWx0IGJlIHRlc3RlZCBhY2NvcmRpbmcgd2l0aCBtYW51YWwgYnV0IGl0IGRvZXNuJ3Qgd29yayAqLwoJcmV0dXJuIDA7Cn0KCi8qKgogKiBod19lcF9zZXRfaGFsdDogY29uZmlndXJlcyBlcCBoYWx0ICYgcmVzZXRzIGRhdGEgdG9nZ2xlIGFmdGVyIGNsZWFyIChleGVjdXRlCiAqICAgICAgICAgICAgICAgICB3aXRob3V0IGludGVycnVwdGlvbikKICogQG51bTogICBlbmRwb2ludCBudW1iZXIKICogQGRpcjogICBlbmRwb2ludCBkaXJlY3Rpb24KICogQHZhbHVlOiB0cnVlID0+IHN0YWxsLCBmYWxzZSA9PiB1bnN0YWxsCiAqCiAqIFRoaXMgZnVuY3Rpb24gcmV0dXJucyBhbiBlcnJvciBjb2RlCiAqLwpzdGF0aWMgaW50IGh3X2VwX3NldF9oYWx0KGludCBudW0sIGludCBkaXIsIGludCB2YWx1ZSkKewoJaWYgKHZhbHVlICE9IDAgJiYgdmFsdWUgIT0gMSkKCQlyZXR1cm4gLUVJTlZBTDsKCglkbyB7CgkJdTMyIGFkZHIgPSBDQVBfRU5EUFRDVFJMICsgbnVtICogc2l6ZW9mKHUzMik7CgkJdTMyIG1hc2tfeHMgPSBkaXIgPyBFTkRQVENUUkxfVFhTIDogRU5EUFRDVFJMX1JYUzsKCQl1MzIgbWFza194ciA9IGRpciA/IEVORFBUQ1RSTF9UWFIgOiBFTkRQVENUUkxfUlhSOwoKCQkvKiBkYXRhIHRvZ2dsZSAtIHJlc2VydmVkIGZvciBFUDAgYnV0IGl0J3MgaW4gRVNTICovCgkJaHdfY3dyaXRlKGFkZHIsIG1hc2tfeHN8bWFza194ciwgdmFsdWUgPyBtYXNrX3hzIDogbWFza194cik7CgoJfSB3aGlsZSAodmFsdWUgIT0gaHdfZXBfZ2V0X2hhbHQobnVtLCBkaXIpKTsKCglyZXR1cm4gMDsKfQoKLyoqCiAqIGh3X2ludHJfY2xlYXI6IGRpc2FibGVzIGludGVycnVwdCAmIGNsZWFycyBpbnRlcnJ1cHQgc3RhdHVzIChleGVjdXRlIHdpdGhvdXQKICogICAgICAgICAgICAgICAgaW50ZXJydXB0aW9uKQogKiBAbjogaW50ZXJydXB0IGJpdAogKgogKiBUaGlzIGZ1bmN0aW9uIHJldHVybnMgYW4gZXJyb3IgY29kZQogKi8Kc3RhdGljIGludCBod19pbnRyX2NsZWFyKGludCBuKQp7CglpZiAobiA+PSBSRUdfQklUUykKCQlyZXR1cm4gLUVJTlZBTDsKCglod19jd3JpdGUoQ0FQX1VTQklOVFIsIEJJVChuKSwgMCk7Cglod19jd3JpdGUoQ0FQX1VTQlNUUywgIEJJVChuKSwgQklUKG4pKTsKCXJldHVybiAwOwp9CgovKioKICogaHdfaW50cl9mb3JjZTogZW5hYmxlcyBpbnRlcnJ1cHQgJiBmb3JjZXMgaW50ZXJydXB0IHN0YXR1cyAoZXhlY3V0ZSB3aXRob3V0CiAqICAgICAgICAgICAgICAgIGludGVycnVwdGlvbikKICogQG46IGludGVycnVwdCBiaXQKICoKICogVGhpcyBmdW5jdGlvbiByZXR1cm5zIGFuIGVycm9yIGNvZGUKICovCnN0YXRpYyBpbnQgaHdfaW50cl9mb3JjZShpbnQgbikKewoJaWYgKG4gPj0gUkVHX0JJVFMpCgkJcmV0dXJuIC1FSU5WQUw7CgoJaHdfYXdyaXRlKEFCU19URVNUTU9ERSwgVEVTVE1PREVfRk9SQ0UsIFRFU1RNT0RFX0ZPUkNFKTsKCWh3X2N3cml0ZShDQVBfVVNCSU5UUiwgIEJJVChuKSwgQklUKG4pKTsKCWh3X2N3cml0ZShDQVBfVVNCU1RTLCAgIEJJVChuKSwgQklUKG4pKTsKCWh3X2F3cml0ZShBQlNfVEVTVE1PREUsIFRFU1RNT0RFX0ZPUkNFLCAwKTsKCXJldHVybiAwOwp9CgovKioKICogaHdfaXNfcG9ydF9oaWdoX3NwZWVkOiB0ZXN0IGlmIHBvcnQgaXMgaGlnaCBzcGVlZAogKgogKiBUaGlzIGZ1bmN0aW9uIHJldHVybnMgdHJ1ZSBpZiBoaWdoIHNwZWVkIHBvcnQKICovCnN0YXRpYyBpbnQgaHdfcG9ydF9pc19oaWdoX3NwZWVkKHZvaWQpCnsKCXJldHVybiBod19iYW5rLmxwbSA/IGh3X2NyZWFkKENBUF9ERVZMQywgREVWTENfUFNQRCkgOgoJCWh3X2NyZWFkKENBUF9QT1JUU0MsIFBPUlRTQ19IU1ApOwp9CgovKioKICogaHdfcG9ydF90ZXN0X2dldDogcmVhZHMgcG9ydCB0ZXN0IG1vZGUgdmFsdWUKICoKICogVGhpcyBmdW5jdGlvbiByZXR1cm5zIHBvcnQgdGVzdCBtb2RlIHZhbHVlCiAqLwpzdGF0aWMgdTggaHdfcG9ydF90ZXN0X2dldCh2b2lkKQp7CglyZXR1cm4gaHdfY3JlYWQoQ0FQX1BPUlRTQywgUE9SVFNDX1BUQykgPj4gZmZzX25yKFBPUlRTQ19QVEMpOwp9CgovKioKICogaHdfcG9ydF90ZXN0X3NldDogd3JpdGVzIHBvcnQgdGVzdCBtb2RlIChleGVjdXRlIHdpdGhvdXQgaW50ZXJydXB0aW9uKQogKiBAbW9kZTogbmV3IHZhbHVlCiAqCiAqIFRoaXMgZnVuY3Rpb24gcmV0dXJucyBhbiBlcnJvciBjb2RlCiAqLwpzdGF0aWMgaW50IGh3X3BvcnRfdGVzdF9zZXQodTggbW9kZSkKewoJY29uc3QgdTggVEVTVF9NT0RFX01BWCA9IDc7CgoJaWYgKG1vZGUgPiBURVNUX01PREVfTUFYKQoJCXJldHVybiAtRUlOVkFMOwoKCWh3X2N3cml0ZShDQVBfUE9SVFNDLCBQT1JUU0NfUFRDLCBtb2RlIDw8IGZmc19ucihQT1JUU0NfUFRDKSk7CglyZXR1cm4gMDsKfQoKLyoqCiAqIGh3X3JlYWRfaW50cl9lbmFibGU6IHJldHVybnMgaW50ZXJydXB0IGVuYWJsZSByZWdpc3RlcgogKgogKiBUaGlzIGZ1bmN0aW9uIHJldHVybnMgcmVnaXN0ZXIgZGF0YQogKi8Kc3RhdGljIHUzMiBod19yZWFkX2ludHJfZW5hYmxlKHZvaWQpCnsKCXJldHVybiBod19jcmVhZChDQVBfVVNCSU5UUiwgfjApOwp9CgovKioKICogaHdfcmVhZF9pbnRyX3N0YXR1czogcmV0dXJucyBpbnRlcnJ1cHQgc3RhdHVzIHJlZ2lzdGVyCiAqCiAqIFRoaXMgZnVuY3Rpb24gcmV0dXJucyByZWdpc3RlciBkYXRhCiAqLwpzdGF0aWMgdTMyIGh3X3JlYWRfaW50cl9zdGF0dXModm9pZCkKewoJcmV0dXJuIGh3X2NyZWFkKENBUF9VU0JTVFMsIH4wKTsKfQoKLyoqCiAqIGh3X3JlZ2lzdGVyX3JlYWQ6IHJlYWRzIGFsbCBkZXZpY2UgcmVnaXN0ZXJzIChleGVjdXRlIHdpdGhvdXQgaW50ZXJydXB0aW9uKQogKiBAYnVmOiAgZGVzdGluYXRpb24gYnVmZmVyCiAqIEBzaXplOiBidWZmZXIgc2l6ZQogKgogKiBUaGlzIGZ1bmN0aW9uIHJldHVybnMgbnVtYmVyIG9mIHJlZ2lzdGVycyByZWFkCiAqLwpzdGF0aWMgc2l6ZV90IGh3X3JlZ2lzdGVyX3JlYWQodTMyICpidWYsIHNpemVfdCBzaXplKQp7Cgl1bnNpZ25lZCBpOwoKCWlmIChzaXplID4gaHdfYmFuay5zaXplKQoJCXNpemUgPSBod19iYW5rLnNpemU7CgoJZm9yIChpID0gMDsgaSA8IHNpemU7IGkrKykKCQlidWZbaV0gPSBod19hcmVhZChpICogc2l6ZW9mKHUzMiksIH4wKTsKCglyZXR1cm4gc2l6ZTsKfQoKLyoqCiAqIGh3X3JlZ2lzdGVyX3dyaXRlOiB3cml0ZXMgdG8gcmVnaXN0ZXIKICogQGFkZHI6IHJlZ2lzdGVyIGFkZHJlc3MKICogQGRhdGE6IHJlZ2lzdGVyIHZhbHVlCiAqCiAqIFRoaXMgZnVuY3Rpb24gcmV0dXJucyBhbiBlcnJvciBjb2RlCiAqLwpzdGF0aWMgaW50IGh3X3JlZ2lzdGVyX3dyaXRlKHUxNiBhZGRyLCB1MzIgZGF0YSkKewoJLyogYWxpZ24gKi8KCWFkZHIgLz0gc2l6ZW9mKHUzMik7CgoJaWYgKGFkZHIgPj0gaHdfYmFuay5zaXplKQoJCXJldHVybiAtRUlOVkFMOwoKCS8qIGFsaWduICovCglhZGRyICo9IHNpemVvZih1MzIpOwoKCWh3X2F3cml0ZShhZGRyLCB+MCwgZGF0YSk7CglyZXR1cm4gMDsKfQoKLyoqCiAqIGh3X3Rlc3RfYW5kX2NsZWFyX2NvbXBsZXRlOiB0ZXN0ICYgY2xlYXIgY29tcGxldGUgc3RhdHVzIChleGVjdXRlIHdpdGhvdXQKICogICAgICAgICAgICAgICAgICAgICAgICAgICAgIGludGVycnVwdGlvbikKICogQG46IGJpdCBudW1iZXIgKGVuZHBvaW50KQogKgogKiBUaGlzIGZ1bmN0aW9uIHJldHVybnMgY29tcGxldGUgc3RhdHVzCiAqLwpzdGF0aWMgaW50IGh3X3Rlc3RfYW5kX2NsZWFyX2NvbXBsZXRlKGludCBuKQp7CglyZXR1cm4gaHdfY3Rlc3RfYW5kX2NsZWFyKENBUF9FTkRQVENPTVBMRVRFLCBCSVQobikpOwp9CgovKioKICogaHdfdGVzdF9hbmRfY2xlYXJfaW50cl9hY3RpdmU6IHRlc3QgJiBjbGVhciBhY3RpdmUgaW50ZXJydXB0cyAoZXhlY3V0ZQogKiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgd2l0aG91dCBpbnRlcnJ1cHRpb24pCiAqCiAqIFRoaXMgZnVuY3Rpb24gcmV0dXJucyBhY3RpdmUgaW50ZXJydXRwcwogKi8Kc3RhdGljIHUzMiBod190ZXN0X2FuZF9jbGVhcl9pbnRyX2FjdGl2ZSh2b2lkKQp7Cgl1MzIgcmVnID0gaHdfcmVhZF9pbnRyX3N0YXR1cygpICYgaHdfcmVhZF9pbnRyX2VuYWJsZSgpOwoKCWh3X2N3cml0ZShDQVBfVVNCU1RTLCB+MCwgcmVnKTsKCXJldHVybiByZWc7Cn0KCi8qKgogKiBod190ZXN0X2FuZF9jbGVhcl9zZXR1cF9ndWFyZDogdGVzdCAmIGNsZWFyIHNldHVwIGd1YXJkIChleGVjdXRlIHdpdGhvdXQKICogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGludGVycnVwdGlvbikKICoKICogVGhpcyBmdW5jdGlvbiByZXR1cm5zIGd1YXJkIHZhbHVlCiAqLwpzdGF0aWMgaW50IGh3X3Rlc3RfYW5kX2NsZWFyX3NldHVwX2d1YXJkKHZvaWQpCnsKCXJldHVybiBod19jdGVzdF9hbmRfd3JpdGUoQ0FQX1VTQkNNRCwgVVNCQ01EX1NVVFcsIDApOwp9CgovKioKICogaHdfdGVzdF9hbmRfc2V0X3NldHVwX2d1YXJkOiB0ZXN0ICYgc2V0IHNldHVwIGd1YXJkIChleGVjdXRlIHdpdGhvdXQKICogICAgICAgICAgICAgICAgICAgICAgICAgICAgICBpbnRlcnJ1cHRpb24pCiAqCiAqIFRoaXMgZnVuY3Rpb24gcmV0dXJucyBndWFyZCB2YWx1ZQogKi8Kc3RhdGljIGludCBod190ZXN0X2FuZF9zZXRfc2V0dXBfZ3VhcmQodm9pZCkKewoJcmV0dXJuIGh3X2N0ZXN0X2FuZF93cml0ZShDQVBfVVNCQ01ELCBVU0JDTURfU1VUVywgVVNCQ01EX1NVVFcpOwp9CgovKioKICogaHdfdXNiX3NldF9hZGRyZXNzOiBjb25maWd1cmVzIFVTQiBhZGRyZXNzIChleGVjdXRlIHdpdGhvdXQgaW50ZXJydXB0aW9uKQogKiBAdmFsdWU6IG5ldyBVU0IgYWRkcmVzcwogKgogKiBUaGlzIGZ1bmN0aW9uIHJldHVybnMgYW4gZXJyb3IgY29kZQogKi8Kc3RhdGljIGludCBod191c2Jfc2V0X2FkZHJlc3ModTggdmFsdWUpCnsKCS8qIGFkdmFuY2UgKi8KCWh3X2N3cml0ZShDQVBfREVWSUNFQUREUiwgREVWSUNFQUREUl9VU0JBRFIgfCBERVZJQ0VBRERSX1VTQkFEUkEsCgkJICB2YWx1ZSA8PCBmZnNfbnIoREVWSUNFQUREUl9VU0JBRFIpIHwgREVWSUNFQUREUl9VU0JBRFJBKTsKCXJldHVybiAwOwp9CgovKioKICogaHdfdXNiX3Jlc2V0OiByZXN0YXJ0IGRldmljZSBhZnRlciBhIGJ1cyByZXNldCAoZXhlY3V0ZSB3aXRob3V0CiAqICAgICAgICAgICAgICAgaW50ZXJydXB0aW9uKQogKgogKiBUaGlzIGZ1bmN0aW9uIHJldHVybnMgYW4gZXJyb3IgY29kZQogKi8Kc3RhdGljIGludCBod191c2JfcmVzZXQodm9pZCkKewoJaHdfdXNiX3NldF9hZGRyZXNzKDApOwoKCS8qIEVTUyBmbHVzaGVzIG9ubHkgYXQgZW5kPyE/ICovCglod19jd3JpdGUoQ0FQX0VORFBURkxVU0gsICAgIH4wLCB+MCk7ICAgLyogZmx1c2ggYWxsIEVQcyAqLwoKCS8qIGNsZWFyIHNldHVwIHRva2VuIHNlbWFwaG9yZXMgKi8KCWh3X2N3cml0ZShDQVBfRU5EUFRTRVRVUFNUQVQsIDAsICAwKTsgICAvKiB3cml0ZXMgaXRzIGNvbnRlbnQgKi8KCgkvKiBjbGVhciBjb21wbGV0ZSBzdGF0dXMgKi8KCWh3X2N3cml0ZShDQVBfRU5EUFRDT01QTEVURSwgIDAsICAwKTsgICAvKiB3cml0ZXMgaXRzIGNvbnRlbnQgKi8KCgkvKiB3YWl0IHVudGlsIGFsbCBiaXRzIGNsZWFyZWQgKi8KCXdoaWxlIChod19jcmVhZChDQVBfRU5EUFRQUklNRSwgfjApKQoJCXVkZWxheSgxMCk7ICAgICAgICAgICAgIC8qIG5vdCBSVE9TIGZyaWVuZGx5ICovCgoJLyogcmVzZXQgYWxsIGVuZHBvaW50cyA/ICovCgoJLyogcmVzZXQgaW50ZXJuYWwgc3RhdHVzIGFuZCB3YWl0IGZvciBmdXJ0aGVyIGluc3RydWN0aW9ucwoJICAgbm8gbmVlZCB0byB2ZXJpZnkgdGhlIHBvcnQgcmVzZXQgc3RhdHVzIChFU1MgZG9lcyBpdCkgKi8KCglyZXR1cm4gMDsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBEQkcgYmxvY2sKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwovKioKICogc2hvd19kZXZpY2U6IHByaW50cyBpbmZvcm1hdGlvbiBhYm91dCBkZXZpY2UgY2FwYWJpbGl0aWVzIGFuZCBzdGF0dXMKICoKICogQ2hlY2sgImRldmljZS5oIiBmb3IgZGV0YWlscwogKi8Kc3RhdGljIHNzaXplX3Qgc2hvd19kZXZpY2Uoc3RydWN0IGRldmljZSAqZGV2LCBzdHJ1Y3QgZGV2aWNlX2F0dHJpYnV0ZSAqYXR0ciwKCQkJICAgY2hhciAqYnVmKQp7CglzdHJ1Y3QgY2kxM3h4eCAqdWRjID0gY29udGFpbmVyX29mKGRldiwgc3RydWN0IGNpMTN4eHgsIGdhZGdldC5kZXYpOwoJc3RydWN0IHVzYl9nYWRnZXQgKmdhZGdldCA9ICZ1ZGMtPmdhZGdldDsKCWludCBuID0gMDsKCglkYmdfdHJhY2UoIlslc10gJXBcbiIsIF9fZnVuY19fLCBidWYpOwoJaWYgKGF0dHIgPT0gTlVMTCB8fCBidWYgPT0gTlVMTCkgewoJCWRldl9lcnIoZGV2LCAiWyVzXSBFSU5WQUxcbiIsIF9fZnVuY19fKTsKCQlyZXR1cm4gMDsKCX0KCgluICs9IHNjbnByaW50ZihidWYgKyBuLCBQQUdFX1NJWkUgLSBuLCAic3BlZWQgICAgICAgICAgICAgPSAlZFxuIiwKCQkgICAgICAgZ2FkZ2V0LT5zcGVlZCk7CgluICs9IHNjbnByaW50ZihidWYgKyBuLCBQQUdFX1NJWkUgLSBuLCAiaXNfZHVhbHNwZWVkICAgICAgPSAlZFxuIiwKCQkgICAgICAgZ2FkZ2V0LT5pc19kdWFsc3BlZWQpOwoJbiArPSBzY25wcmludGYoYnVmICsgbiwgUEFHRV9TSVpFIC0gbiwgImlzX290ZyAgICAgICAgICAgID0gJWRcbiIsCgkJICAgICAgIGdhZGdldC0+aXNfb3RnKTsKCW4gKz0gc2NucHJpbnRmKGJ1ZiArIG4sIFBBR0VfU0laRSAtIG4sICJpc19hX3BlcmlwaGVyYWwgICA9ICVkXG4iLAoJCSAgICAgICBnYWRnZXQtPmlzX2FfcGVyaXBoZXJhbCk7CgluICs9IHNjbnByaW50ZihidWYgKyBuLCBQQUdFX1NJWkUgLSBuLCAiYl9obnBfZW5hYmxlICAgICAgPSAlZFxuIiwKCQkgICAgICAgZ2FkZ2V0LT5iX2hucF9lbmFibGUpOwoJbiArPSBzY25wcmludGYoYnVmICsgbiwgUEFHRV9TSVpFIC0gbiwgImFfaG5wX3N1cHBvcnQgICAgID0gJWRcbiIsCgkJICAgICAgIGdhZGdldC0+YV9obnBfc3VwcG9ydCk7CgluICs9IHNjbnByaW50ZihidWYgKyBuLCBQQUdFX1NJWkUgLSBuLCAiYV9hbHRfaG5wX3N1cHBvcnQgPSAlZFxuIiwKCQkgICAgICAgZ2FkZ2V0LT5hX2FsdF9obnBfc3VwcG9ydCk7CgluICs9IHNjbnByaW50ZihidWYgKyBuLCBQQUdFX1NJWkUgLSBuLCAibmFtZSAgICAgICAgICAgICAgPSAlc1xuIiwKCQkgICAgICAgKGdhZGdldC0+bmFtZSA/IGdhZGdldC0+bmFtZSA6ICIiKSk7CgoJcmV0dXJuIG47Cn0Kc3RhdGljIERFVklDRV9BVFRSKGRldmljZSwgU19JUlVTUiwgc2hvd19kZXZpY2UsIE5VTEwpOwoKLyoqCiAqIHNob3dfZHJpdmVyOiBwcmludHMgaW5mb3JtYXRpb24gYWJvdXQgYXR0YWNoZWQgZ2FkZ2V0IChpZiBhbnkpCiAqCiAqIENoZWNrICJkZXZpY2UuaCIgZm9yIGRldGFpbHMKICovCnN0YXRpYyBzc2l6ZV90IHNob3dfZHJpdmVyKHN0cnVjdCBkZXZpY2UgKmRldiwgc3RydWN0IGRldmljZV9hdHRyaWJ1dGUgKmF0dHIsCgkJCSAgIGNoYXIgKmJ1ZikKewoJc3RydWN0IGNpMTN4eHggKnVkYyA9IGNvbnRhaW5lcl9vZihkZXYsIHN0cnVjdCBjaTEzeHh4LCBnYWRnZXQuZGV2KTsKCXN0cnVjdCB1c2JfZ2FkZ2V0X2RyaXZlciAqZHJpdmVyID0gdWRjLT5kcml2ZXI7CglpbnQgbiA9IDA7CgoJZGJnX3RyYWNlKCJbJXNdICVwXG4iLCBfX2Z1bmNfXywgYnVmKTsKCWlmIChhdHRyID09IE5VTEwgfHwgYnVmID09IE5VTEwpIHsKCQlkZXZfZXJyKGRldiwgIlslc10gRUlOVkFMXG4iLCBfX2Z1bmNfXyk7CgkJcmV0dXJuIDA7Cgl9CgoJaWYgKGRyaXZlciA9PSBOVUxMKQoJCXJldHVybiBzY25wcmludGYoYnVmLCBQQUdFX1NJWkUsCgkJCQkgIlRoZXJlIGlzIG5vIGdhZGdldCBhdHRhY2hlZCFcbiIpOwoKCW4gKz0gc2NucHJpbnRmKGJ1ZiArIG4sIFBBR0VfU0laRSAtIG4sICJmdW5jdGlvbiAgPSAlc1xuIiwKCQkgICAgICAgKGRyaXZlci0+ZnVuY3Rpb24gPyBkcml2ZXItPmZ1bmN0aW9uIDogIiIpKTsKCW4gKz0gc2NucHJpbnRmKGJ1ZiArIG4sIFBBR0VfU0laRSAtIG4sICJtYXggc3BlZWQgPSAlZFxuIiwKCQkgICAgICAgZHJpdmVyLT5zcGVlZCk7CgoJcmV0dXJuIG47Cn0Kc3RhdGljIERFVklDRV9BVFRSKGRyaXZlciwgU19JUlVTUiwgc2hvd19kcml2ZXIsIE5VTEwpOwoKLyogTWF4aW11bSBldmVudCBtZXNzYWdlIGxlbmd0aCAqLwojZGVmaW5lIERCR19EQVRBX01TRyAgIDY0VUwKCi8qIE1heGltdW0gZXZlbnQgbWVzc2FnZXMgKi8KI2RlZmluZSBEQkdfREFUQV9NQVggICAxMjhVTAoKLyogRXZlbnQgYnVmZmVyIGRlc2NyaXB0b3IgKi8Kc3RhdGljIHN0cnVjdCB7CgljaGFyICAgICAoYnVmW0RCR19EQVRBX01BWF0pW0RCR19EQVRBX01TR107ICAgLyogYnVmZmVyICovCgl1bnNpZ25lZCBpZHg7ICAgLyogaW5kZXggKi8KCXVuc2lnbmVkIHR0eTsgICAvKiBwcmludCB0byBjb25zb2xlPyAqLwoJcndsb2NrX3QgbGNrOyAgIC8qIGxvY2sgKi8KfSBkYmdfZGF0YSA9IHsKCS5pZHggPSAwLAoJLnR0eSA9IDAsCgkubGNrID0gX19SV19MT0NLX1VOTE9DS0VEKGxjaykKfTsKCi8qKgogKiBkYmdfZGVjOiBkZWNyZW1lbnRzIGRlYnVnIGV2ZW50IGluZGV4CiAqIEBpZHg6IGJ1ZmZlciBpbmRleAogKi8Kc3RhdGljIHZvaWQgZGJnX2RlYyh1bnNpZ25lZCAqaWR4KQp7CgkqaWR4ID0gKCppZHggLSAxKSAmIChEQkdfREFUQV9NQVgtMSk7Cn0KCi8qKgogKiBkYmdfaW5jOiBpbmNyZW1lbnRzIGRlYnVnIGV2ZW50IGluZGV4CiAqIEBpZHg6IGJ1ZmZlciBpbmRleAogKi8Kc3RhdGljIHZvaWQgZGJnX2luYyh1bnNpZ25lZCAqaWR4KQp7CgkqaWR4ID0gKCppZHggKyAxKSAmIChEQkdfREFUQV9NQVgtMSk7Cn0KCi8qKgogKiBkYmdfcHJpbnQ6ICBwcmludHMgdGhlIGNvbW1vbiBwYXJ0IG9mIHRoZSBldmVudAogKiBAYWRkcjogICBlbmRwb2ludCBhZGRyZXNzCiAqIEBuYW1lOiAgIGV2ZW50IG5hbWUKICogQHN0YXR1czogc3RhdHVzCiAqIEBleHRyYTogIGV4dHJhIGluZm9ybWF0aW9uCiAqLwpzdGF0aWMgdm9pZCBkYmdfcHJpbnQodTggYWRkciwgY29uc3QgY2hhciAqbmFtZSwgaW50IHN0YXR1cywgY29uc3QgY2hhciAqZXh0cmEpCnsKCXN0cnVjdCB0aW1ldmFsIHR2YWw7Cgl1bnNpZ25lZCBpbnQgc3RhbXA7Cgl1bnNpZ25lZCBsb25nIGZsYWdzOwoKCXdyaXRlX2xvY2tfaXJxc2F2ZSgmZGJnX2RhdGEubGNrLCBmbGFncyk7CgoJZG9fZ2V0dGltZW9mZGF5KCZ0dmFsKTsKCXN0YW1wID0gdHZhbC50dl9zZWMgJiAweEZGRkY7CS8qIDJeMzIgPSA0Mjk0OTY3Mjk2LiBMaW1pdCB0byA0MDk2cyAqLwoJc3RhbXAgPSBzdGFtcCAqIDEwMDAwMDAgKyB0dmFsLnR2X3VzZWM7CgoJc2NucHJpbnRmKGRiZ19kYXRhLmJ1ZltkYmdfZGF0YS5pZHhdLCBEQkdfREFUQV9NU0csCgkJICAiJTA0WFx0uyAlMDJYICUtNy43cyAlNGkgq1x0JXNcbiIsCgkJICBzdGFtcCwgYWRkciwgbmFtZSwgc3RhdHVzLCBleHRyYSk7CgoJZGJnX2luYygmZGJnX2RhdGEuaWR4KTsKCgl3cml0ZV91bmxvY2tfaXJxcmVzdG9yZSgmZGJnX2RhdGEubGNrLCBmbGFncyk7CgoJaWYgKGRiZ19kYXRhLnR0eSAhPSAwKQoJCXByX25vdGljZSgiJTA0WFx0uyAlMDJYICUtNy43cyAlNGkgq1x0JXNcbiIsCgkJCSAgc3RhbXAsIGFkZHIsIG5hbWUsIHN0YXR1cywgZXh0cmEpOwp9CgovKioKICogZGJnX2RvbmU6IHByaW50cyBhIERPTkUgZXZlbnQKICogQGFkZHI6ICAgZW5kcG9pbnQgYWRkcmVzcwogKiBAdGQ6ICAgICB0cmFuc2ZlciBkZXNjcmlwdG9yCiAqIEBzdGF0dXM6IHN0YXR1cwogKi8Kc3RhdGljIHZvaWQgZGJnX2RvbmUodTggYWRkciwgY29uc3QgdTMyIHRva2VuLCBpbnQgc3RhdHVzKQp7CgljaGFyIG1zZ1tEQkdfREFUQV9NU0ddOwoKCXNjbnByaW50Zihtc2csIHNpemVvZihtc2cpLCAiJWQgJTAyWCIsCgkJICAoaW50KSh0b2tlbiAmIFREX1RPVEFMX0JZVEVTKSA+PiBmZnNfbnIoVERfVE9UQUxfQllURVMpLAoJCSAgKGludCkodG9rZW4gJiBURF9TVEFUVVMpICAgICAgPj4gZmZzX25yKFREX1NUQVRVUykpOwoJZGJnX3ByaW50KGFkZHIsICJET05FIiwgc3RhdHVzLCBtc2cpOwp9CgovKioKICogZGJnX2V2ZW50OiBwcmludHMgYSBnZW5lcmljIGV2ZW50CiAqIEBhZGRyOiAgIGVuZHBvaW50IGFkZHJlc3MKICogQG5hbWU6ICAgZXZlbnQgbmFtZQogKiBAc3RhdHVzOiBzdGF0dXMKICovCnN0YXRpYyB2b2lkIGRiZ19ldmVudCh1OCBhZGRyLCBjb25zdCBjaGFyICpuYW1lLCBpbnQgc3RhdHVzKQp7CglpZiAobmFtZSAhPSBOVUxMKQoJCWRiZ19wcmludChhZGRyLCBuYW1lLCBzdGF0dXMsICIiKTsKfQoKLyoKICogZGJnX3F1ZXVlOiBwcmludHMgYSBRVUVVRSBldmVudAogKiBAYWRkcjogICBlbmRwb2ludCBhZGRyZXNzCiAqIEByZXE6ICAgIFVTQiByZXF1ZXN0CiAqIEBzdGF0dXM6IHN0YXR1cwogKi8Kc3RhdGljIHZvaWQgZGJnX3F1ZXVlKHU4IGFkZHIsIGNvbnN0IHN0cnVjdCB1c2JfcmVxdWVzdCAqcmVxLCBpbnQgc3RhdHVzKQp7CgljaGFyIG1zZ1tEQkdfREFUQV9NU0ddOwoKCWlmIChyZXEgIT0gTlVMTCkgewoJCXNjbnByaW50Zihtc2csIHNpemVvZihtc2cpLAoJCQkgICIlZCAlZCIsICFyZXEtPm5vX2ludGVycnVwdCwgcmVxLT5sZW5ndGgpOwoJCWRiZ19wcmludChhZGRyLCAiUVVFVUUiLCBzdGF0dXMsIG1zZyk7Cgl9Cn0KCi8qKgogKiBkYmdfc2V0dXA6IHByaW50cyBhIFNFVFVQIGV2ZW50CiAqIEBhZGRyOiBlbmRwb2ludCBhZGRyZXNzCiAqIEByZXE6ICBzZXR1cCByZXF1ZXN0CiAqLwpzdGF0aWMgdm9pZCBkYmdfc2V0dXAodTggYWRkciwgY29uc3Qgc3RydWN0IHVzYl9jdHJscmVxdWVzdCAqcmVxKQp7CgljaGFyIG1zZ1tEQkdfREFUQV9NU0ddOwoKCWlmIChyZXEgIT0gTlVMTCkgewoJCXNjbnByaW50Zihtc2csIHNpemVvZihtc2cpLAoJCQkgICIlMDJYICUwMlggJTA0WCAlMDRYICVkIiwgcmVxLT5iUmVxdWVzdFR5cGUsCgkJCSAgcmVxLT5iUmVxdWVzdCwgbGUxNl90b19jcHUocmVxLT53VmFsdWUpLAoJCQkgIGxlMTZfdG9fY3B1KHJlcS0+d0luZGV4KSwgbGUxNl90b19jcHUocmVxLT53TGVuZ3RoKSk7CgkJZGJnX3ByaW50KGFkZHIsICJTRVRVUCIsIDAsIG1zZyk7Cgl9Cn0KCi8qKgogKiBzaG93X2V2ZW50czogZGlzcGxheXMgdGhlIGV2ZW50IGJ1ZmZlcgogKgogKiBDaGVjayAiZGV2aWNlLmgiIGZvciBkZXRhaWxzCiAqLwpzdGF0aWMgc3NpemVfdCBzaG93X2V2ZW50cyhzdHJ1Y3QgZGV2aWNlICpkZXYsIHN0cnVjdCBkZXZpY2VfYXR0cmlidXRlICphdHRyLAoJCQkgICBjaGFyICpidWYpCnsKCXVuc2lnbmVkIGxvbmcgZmxhZ3M7Cgl1bnNpZ25lZCBpLCBqLCBuID0gMDsKCglkYmdfdHJhY2UoIlslc10gJXBcbiIsIF9fZnVuY19fLCBidWYpOwoJaWYgKGF0dHIgPT0gTlVMTCB8fCBidWYgPT0gTlVMTCkgewoJCWRldl9lcnIoZGV2LCAiWyVzXSBFSU5WQUxcbiIsIF9fZnVuY19fKTsKCQlyZXR1cm4gMDsKCX0KCglyZWFkX2xvY2tfaXJxc2F2ZSgmZGJnX2RhdGEubGNrLCBmbGFncyk7CgoJaSA9IGRiZ19kYXRhLmlkeDsKCWZvciAoZGJnX2RlYygmaSk7IGkgIT0gZGJnX2RhdGEuaWR4OyBkYmdfZGVjKCZpKSkgewoJCW4gKz0gc3RybGVuKGRiZ19kYXRhLmJ1ZltpXSk7CgkJaWYgKG4gPj0gUEFHRV9TSVpFKSB7CgkJCW4gLT0gc3RybGVuKGRiZ19kYXRhLmJ1ZltpXSk7CgkJCWJyZWFrOwoJCX0KCX0KCWZvciAoaiA9IDAsIGRiZ19pbmMoJmkpOyBqIDwgbjsgZGJnX2luYygmaSkpCgkJaiArPSBzY25wcmludGYoYnVmICsgaiwgUEFHRV9TSVpFIC0gaiwKCQkJICAgICAgICIlcyIsIGRiZ19kYXRhLmJ1ZltpXSk7CgoJcmVhZF91bmxvY2tfaXJxcmVzdG9yZSgmZGJnX2RhdGEubGNrLCBmbGFncyk7CgoJcmV0dXJuIG47Cn0KCi8qKgogKiBzdG9yZV9ldmVudHM6IGNvbmZpZ3VyZSBpZiBldmVudHMgYXJlIGdvaW5nIHRvIGJlIGFsc28gcHJpbnRlZCB0byBjb25zb2xlCiAqCiAqIENoZWNrICJkZXZpY2UuaCIgZm9yIGRldGFpbHMKICovCnN0YXRpYyBzc2l6ZV90IHN0b3JlX2V2ZW50cyhzdHJ1Y3QgZGV2aWNlICpkZXYsIHN0cnVjdCBkZXZpY2VfYXR0cmlidXRlICphdHRyLAoJCQkgICAgY29uc3QgY2hhciAqYnVmLCBzaXplX3QgY291bnQpCnsKCXVuc2lnbmVkIHR0eTsKCglkYmdfdHJhY2UoIlslc10gJXAsICVkXG4iLCBfX2Z1bmNfXywgYnVmLCBjb3VudCk7CglpZiAoYXR0ciA9PSBOVUxMIHx8IGJ1ZiA9PSBOVUxMKSB7CgkJZGV2X2VycihkZXYsICJbJXNdIEVJTlZBTFxuIiwgX19mdW5jX18pOwoJCWdvdG8gZG9uZTsKCX0KCglpZiAoc3NjYW5mKGJ1ZiwgIiV1IiwgJnR0eSkgIT0gMSB8fCB0dHkgPiAxKSB7CgkJZGV2X2VycihkZXYsICI8MXwwPjogZW5hYmxlfGRpc2FibGUgY29uc29sZSBsb2dcbiIpOwoJCWdvdG8gZG9uZTsKCX0KCglkYmdfZGF0YS50dHkgPSB0dHk7CglkZXZfaW5mbyhkZXYsICJ0dHkgPSAldSIsIGRiZ19kYXRhLnR0eSk7CgogZG9uZToKCXJldHVybiBjb3VudDsKfQpzdGF0aWMgREVWSUNFX0FUVFIoZXZlbnRzLCBTX0lSVVNSIHwgU19JV1VTUiwgc2hvd19ldmVudHMsIHN0b3JlX2V2ZW50cyk7CgovKioKICogc2hvd19pbnRlcnM6IGludGVycnVwdCBzdGF0dXMsIGVuYWJsZSBzdGF0dXMgYW5kIGhpc3RvcmljCiAqCiAqIENoZWNrICJkZXZpY2UuaCIgZm9yIGRldGFpbHMKICovCnN0YXRpYyBzc2l6ZV90IHNob3dfaW50ZXJzKHN0cnVjdCBkZXZpY2UgKmRldiwgc3RydWN0IGRldmljZV9hdHRyaWJ1dGUgKmF0dHIsCgkJCSAgIGNoYXIgKmJ1ZikKewoJc3RydWN0IGNpMTN4eHggKnVkYyA9IGNvbnRhaW5lcl9vZihkZXYsIHN0cnVjdCBjaTEzeHh4LCBnYWRnZXQuZGV2KTsKCXVuc2lnbmVkIGxvbmcgZmxhZ3M7Cgl1MzIgaW50cjsKCXVuc2lnbmVkIGksIGosIG4gPSAwOwoKCWRiZ190cmFjZSgiWyVzXSAlcFxuIiwgX19mdW5jX18sIGJ1Zik7CglpZiAoYXR0ciA9PSBOVUxMIHx8IGJ1ZiA9PSBOVUxMKSB7CgkJZGV2X2VycihkZXYsICJbJXNdIEVJTlZBTFxuIiwgX19mdW5jX18pOwoJCXJldHVybiAwOwoJfQoKCXNwaW5fbG9ja19pcnFzYXZlKHVkYy0+bG9jaywgZmxhZ3MpOwoKCW4gKz0gc2NucHJpbnRmKGJ1ZiArIG4sIFBBR0VfU0laRSAtIG4sCgkJICAgICAgICJzdGF0dXMgPSAlMDh4XG4iLCBod19yZWFkX2ludHJfc3RhdHVzKCkpOwoJbiArPSBzY25wcmludGYoYnVmICsgbiwgUEFHRV9TSVpFIC0gbiwKCQkgICAgICAgImVuYWJsZSA9ICUwOHhcbiIsIGh3X3JlYWRfaW50cl9lbmFibGUoKSk7CgoJbiArPSBzY25wcmludGYoYnVmICsgbiwgUEFHRV9TSVpFIC0gbiwgIip0ZXN0ID0gJWRcbiIsCgkJICAgICAgIGlzcl9zdGF0aXN0aWNzLnRlc3QpOwoJbiArPSBzY25wcmludGYoYnVmICsgbiwgUEFHRV9TSVpFIC0gbiwgIrsgdWkgID0gJWRcbiIsCgkJICAgICAgIGlzcl9zdGF0aXN0aWNzLnVpKTsKCW4gKz0gc2NucHJpbnRmKGJ1ZiArIG4sIFBBR0VfU0laRSAtIG4sICK7IHVlaSA9ICVkXG4iLAoJCSAgICAgICBpc3Jfc3RhdGlzdGljcy51ZWkpOwoJbiArPSBzY25wcmludGYoYnVmICsgbiwgUEFHRV9TSVpFIC0gbiwgIrsgcGNpID0gJWRcbiIsCgkJICAgICAgIGlzcl9zdGF0aXN0aWNzLnBjaSk7CgluICs9IHNjbnByaW50ZihidWYgKyBuLCBQQUdFX1NJWkUgLSBuLCAiuyB1cmkgPSAlZFxuIiwKCQkgICAgICAgaXNyX3N0YXRpc3RpY3MudXJpKTsKCW4gKz0gc2NucHJpbnRmKGJ1ZiArIG4sIFBBR0VfU0laRSAtIG4sICK7IHNsaSA9ICVkXG4iLAoJCSAgICAgICBpc3Jfc3RhdGlzdGljcy5zbGkpOwoJbiArPSBzY25wcmludGYoYnVmICsgbiwgUEFHRV9TSVpFIC0gbiwgIipub25lID0gJWRcbiIsCgkJICAgICAgIGlzcl9zdGF0aXN0aWNzLm5vbmUpOwoJbiArPSBzY25wcmludGYoYnVmICsgbiwgUEFHRV9TSVpFIC0gbiwgIipobmRsID0gJWRcbiIsCgkJICAgICAgIGlzcl9zdGF0aXN0aWNzLmhuZGwuY250KTsKCglmb3IgKGkgPSBpc3Jfc3RhdGlzdGljcy5obmRsLmlkeCwgaiA9IDA7IGogPD0gSVNSX01BU0s7IGorKywgaSsrKSB7CgkJaSAgICY9IElTUl9NQVNLOwoJCWludHIgPSBpc3Jfc3RhdGlzdGljcy5obmRsLmJ1ZltpXTsKCgkJaWYgKFVTQmlfVUkgICYgaW50cikKCQkJbiArPSBzY25wcmludGYoYnVmICsgbiwgUEFHRV9TSVpFIC0gbiwgInVpICAiKTsKCQlpbnRyICY9IH5VU0JpX1VJOwoJCWlmIChVU0JpX1VFSSAmIGludHIpCgkJCW4gKz0gc2NucHJpbnRmKGJ1ZiArIG4sIFBBR0VfU0laRSAtIG4sICJ1ZWkgIik7CgkJaW50ciAmPSB+VVNCaV9VRUk7CgkJaWYgKFVTQmlfUENJICYgaW50cikKCQkJbiArPSBzY25wcmludGYoYnVmICsgbiwgUEFHRV9TSVpFIC0gbiwgInBjaSAiKTsKCQlpbnRyICY9IH5VU0JpX1BDSTsKCQlpZiAoVVNCaV9VUkkgJiBpbnRyKQoJCQluICs9IHNjbnByaW50ZihidWYgKyBuLCBQQUdFX1NJWkUgLSBuLCAidXJpICIpOwoJCWludHIgJj0gflVTQmlfVVJJOwoJCWlmIChVU0JpX1NMSSAmIGludHIpCgkJCW4gKz0gc2NucHJpbnRmKGJ1ZiArIG4sIFBBR0VfU0laRSAtIG4sICJzbGkgIik7CgkJaW50ciAmPSB+VVNCaV9TTEk7CgkJaWYgKGludHIpCgkJCW4gKz0gc2NucHJpbnRmKGJ1ZiArIG4sIFBBR0VfU0laRSAtIG4sICI/Pz8gIik7CgkJaWYgKGlzcl9zdGF0aXN0aWNzLmhuZGwuYnVmW2ldKQoJCQluICs9IHNjbnByaW50ZihidWYgKyBuLCBQQUdFX1NJWkUgLSBuLCAiXG4iKTsKCX0KCglzcGluX3VubG9ja19pcnFyZXN0b3JlKHVkYy0+bG9jaywgZmxhZ3MpOwoKCXJldHVybiBuOwp9CgovKioKICogc3RvcmVfaW50ZXJzOiBlbmFibGUgJiBmb3JjZSBvciBkaXNhYmxlIGFuIGluZGl2aWR1YWwgaW50ZXJydXRwcwogKiAgICAgICAgICAgICAgICAgICAodG8gYmUgdXNlZCBmb3IgdGVzdCBwdXJwb3NlcyBvbmx5KQogKgogKiBDaGVjayAiZGV2aWNlLmgiIGZvciBkZXRhaWxzCiAqLwpzdGF0aWMgc3NpemVfdCBzdG9yZV9pbnRlcnMoc3RydWN0IGRldmljZSAqZGV2LCBzdHJ1Y3QgZGV2aWNlX2F0dHJpYnV0ZSAqYXR0ciwKCQkJICAgIGNvbnN0IGNoYXIgKmJ1Ziwgc2l6ZV90IGNvdW50KQp7CglzdHJ1Y3QgY2kxM3h4eCAqdWRjID0gY29udGFpbmVyX29mKGRldiwgc3RydWN0IGNpMTN4eHgsIGdhZGdldC5kZXYpOwoJdW5zaWduZWQgbG9uZyBmbGFnczsKCXVuc2lnbmVkIGVuLCBiaXQ7CgoJZGJnX3RyYWNlKCJbJXNdICVwLCAlZFxuIiwgX19mdW5jX18sIGJ1ZiwgY291bnQpOwoJaWYgKGF0dHIgPT0gTlVMTCB8fCBidWYgPT0gTlVMTCkgewoJCWRldl9lcnIoZGV2LCAiWyVzXSBFSU5WQUxcbiIsIF9fZnVuY19fKTsKCQlnb3RvIGRvbmU7Cgl9CgoJaWYgKHNzY2FuZihidWYsICIldSAldSIsICZlbiwgJmJpdCkgIT0gMiB8fCBlbiA+IDEpIHsKCQlkZXZfZXJyKGRldiwgIjwxfDA+IDxiaXQ+OiBlbmFibGV8ZGlzYWJsZSBpbnRlcnJ1cHQiKTsKCQlnb3RvIGRvbmU7Cgl9CgoJc3Bpbl9sb2NrX2lycXNhdmUodWRjLT5sb2NrLCBmbGFncyk7CglpZiAoZW4pIHsKCQlpZiAoaHdfaW50cl9mb3JjZShiaXQpKQoJCQlkZXZfZXJyKGRldiwgImludmFsaWQgYml0IG51bWJlclxuIik7CgkJZWxzZQoJCQlpc3Jfc3RhdGlzdGljcy50ZXN0Kys7Cgl9IGVsc2UgewoJCWlmIChod19pbnRyX2NsZWFyKGJpdCkpCgkJCWRldl9lcnIoZGV2LCAiaW52YWxpZCBiaXQgbnVtYmVyXG4iKTsKCX0KCXNwaW5fdW5sb2NrX2lycXJlc3RvcmUodWRjLT5sb2NrLCBmbGFncyk7CgogZG9uZToKCXJldHVybiBjb3VudDsKfQpzdGF0aWMgREVWSUNFX0FUVFIoaW50ZXJzLCBTX0lSVVNSIHwgU19JV1VTUiwgc2hvd19pbnRlcnMsIHN0b3JlX2ludGVycyk7CgovKioKICogc2hvd19wb3J0X3Rlc3Q6IHJlYWRzIHBvcnQgdGVzdCBtb2RlCiAqCiAqIENoZWNrICJkZXZpY2UuaCIgZm9yIGRldGFpbHMKICovCnN0YXRpYyBzc2l6ZV90IHNob3dfcG9ydF90ZXN0KHN0cnVjdCBkZXZpY2UgKmRldiwKCQkJICAgICAgc3RydWN0IGRldmljZV9hdHRyaWJ1dGUgKmF0dHIsIGNoYXIgKmJ1ZikKewoJc3RydWN0IGNpMTN4eHggKnVkYyA9IGNvbnRhaW5lcl9vZihkZXYsIHN0cnVjdCBjaTEzeHh4LCBnYWRnZXQuZGV2KTsKCXVuc2lnbmVkIGxvbmcgZmxhZ3M7Cgl1bnNpZ25lZCBtb2RlOwoKCWRiZ190cmFjZSgiWyVzXSAlcFxuIiwgX19mdW5jX18sIGJ1Zik7CglpZiAoYXR0ciA9PSBOVUxMIHx8IGJ1ZiA9PSBOVUxMKSB7CgkJZGV2X2VycihkZXYsICJbJXNdIEVJTlZBTFxuIiwgX19mdW5jX18pOwoJCXJldHVybiAwOwoJfQoKCXNwaW5fbG9ja19pcnFzYXZlKHVkYy0+bG9jaywgZmxhZ3MpOwoJbW9kZSA9IGh3X3BvcnRfdGVzdF9nZXQoKTsKCXNwaW5fdW5sb2NrX2lycXJlc3RvcmUodWRjLT5sb2NrLCBmbGFncyk7CgoJcmV0dXJuIHNjbnByaW50ZihidWYsIFBBR0VfU0laRSwgIm1vZGUgPSAldVxuIiwgbW9kZSk7Cn0KCi8qKgogKiBzdG9yZV9wb3J0X3Rlc3Q6IHdyaXRlcyBwb3J0IHRlc3QgbW9kZQogKgogKiBDaGVjayAiZGV2aWNlLmgiIGZvciBkZXRhaWxzCiAqLwpzdGF0aWMgc3NpemVfdCBzdG9yZV9wb3J0X3Rlc3Qoc3RydWN0IGRldmljZSAqZGV2LAoJCQkgICAgICAgc3RydWN0IGRldmljZV9hdHRyaWJ1dGUgKmF0dHIsCgkJCSAgICAgICBjb25zdCBjaGFyICpidWYsIHNpemVfdCBjb3VudCkKewoJc3RydWN0IGNpMTN4eHggKnVkYyA9IGNvbnRhaW5lcl9vZihkZXYsIHN0cnVjdCBjaTEzeHh4LCBnYWRnZXQuZGV2KTsKCXVuc2lnbmVkIGxvbmcgZmxhZ3M7Cgl1bnNpZ25lZCBtb2RlOwoKCWRiZ190cmFjZSgiWyVzXSAlcCwgJWRcbiIsIF9fZnVuY19fLCBidWYsIGNvdW50KTsKCWlmIChhdHRyID09IE5VTEwgfHwgYnVmID09IE5VTEwpIHsKCQlkZXZfZXJyKGRldiwgIlslc10gRUlOVkFMXG4iLCBfX2Z1bmNfXyk7CgkJZ290byBkb25lOwoJfQoKCWlmIChzc2NhbmYoYnVmLCAiJXUiLCAmbW9kZSkgIT0gMSkgewoJCWRldl9lcnIoZGV2LCAiPG1vZGU+OiBzZXQgcG9ydCB0ZXN0IG1vZGUiKTsKCQlnb3RvIGRvbmU7Cgl9CgoJc3Bpbl9sb2NrX2lycXNhdmUodWRjLT5sb2NrLCBmbGFncyk7CglpZiAoaHdfcG9ydF90ZXN0X3NldChtb2RlKSkKCQlkZXZfZXJyKGRldiwgImludmFsaWQgbW9kZVxuIik7CglzcGluX3VubG9ja19pcnFyZXN0b3JlKHVkYy0+bG9jaywgZmxhZ3MpOwoKIGRvbmU6CglyZXR1cm4gY291bnQ7Cn0Kc3RhdGljIERFVklDRV9BVFRSKHBvcnRfdGVzdCwgU19JUlVTUiB8IFNfSVdVU1IsCgkJICAgc2hvd19wb3J0X3Rlc3QsIHN0b3JlX3BvcnRfdGVzdCk7CgovKioKICogc2hvd19xaGVhZHM6IERNQSBjb250ZW50cyBvZiBhbGwgcXVldWUgaGVhZHMKICoKICogQ2hlY2sgImRldmljZS5oIiBmb3IgZGV0YWlscwogKi8Kc3RhdGljIHNzaXplX3Qgc2hvd19xaGVhZHMoc3RydWN0IGRldmljZSAqZGV2LCBzdHJ1Y3QgZGV2aWNlX2F0dHJpYnV0ZSAqYXR0ciwKCQkJICAgY2hhciAqYnVmKQp7CglzdHJ1Y3QgY2kxM3h4eCAqdWRjID0gY29udGFpbmVyX29mKGRldiwgc3RydWN0IGNpMTN4eHgsIGdhZGdldC5kZXYpOwoJdW5zaWduZWQgbG9uZyBmbGFnczsKCXVuc2lnbmVkIGksIGosIG4gPSAwOwoKCWRiZ190cmFjZSgiWyVzXSAlcFxuIiwgX19mdW5jX18sIGJ1Zik7CglpZiAoYXR0ciA9PSBOVUxMIHx8IGJ1ZiA9PSBOVUxMKSB7CgkJZGV2X2VycihkZXYsICJbJXNdIEVJTlZBTFxuIiwgX19mdW5jX18pOwoJCXJldHVybiAwOwoJfQoKCXNwaW5fbG9ja19pcnFzYXZlKHVkYy0+bG9jaywgZmxhZ3MpOwoJZm9yIChpID0gMDsgaSA8IGh3X2VwX21heDsgaSsrKSB7CgkJc3RydWN0IGNpMTN4eHhfZXAgKm1FcCA9ICZ1ZGMtPmNpMTN4eHhfZXBbaV07CgkJbiArPSBzY25wcmludGYoYnVmICsgbiwgUEFHRV9TSVpFIC0gbiwKCQkJICAgICAgICJFUD0lMDJpOiBSWD0lMDhYIFRYPSUwOFhcbiIsCgkJCSAgICAgICBpLCAodTMyKW1FcC0+cWhbUlhdLmRtYSwgKHUzMiltRXAtPnFoW1RYXS5kbWEpOwoJCWZvciAoaiA9IDA7IGogPCAoc2l6ZW9mKHN0cnVjdCBjaTEzeHh4X3FoKS9zaXplb2YodTMyKSk7IGorKykgewoJCQluICs9IHNjbnByaW50ZihidWYgKyBuLCBQQUdFX1NJWkUgLSBuLAoJCQkJICAgICAgICIgJTA0WDogICAgJTA4WCAgICAlMDhYXG4iLCBqLAoJCQkJICAgICAgICooKHUzMiAqKW1FcC0+cWhbUlhdLnB0ciArIGopLAoJCQkJICAgICAgICooKHUzMiAqKW1FcC0+cWhbVFhdLnB0ciArIGopKTsKCQl9Cgl9CglzcGluX3VubG9ja19pcnFyZXN0b3JlKHVkYy0+bG9jaywgZmxhZ3MpOwoKCXJldHVybiBuOwp9CnN0YXRpYyBERVZJQ0VfQVRUUihxaGVhZHMsIFNfSVJVU1IsIHNob3dfcWhlYWRzLCBOVUxMKTsKCi8qKgogKiBzaG93X3JlZ2lzdGVyczogZHVtcHMgYWxsIHJlZ2lzdGVycwogKgogKiBDaGVjayAiZGV2aWNlLmgiIGZvciBkZXRhaWxzCiAqLwpzdGF0aWMgc3NpemVfdCBzaG93X3JlZ2lzdGVycyhzdHJ1Y3QgZGV2aWNlICpkZXYsCgkJCSAgICAgIHN0cnVjdCBkZXZpY2VfYXR0cmlidXRlICphdHRyLCBjaGFyICpidWYpCnsKCXN0cnVjdCBjaTEzeHh4ICp1ZGMgPSBjb250YWluZXJfb2YoZGV2LCBzdHJ1Y3QgY2kxM3h4eCwgZ2FkZ2V0LmRldik7Cgl1bnNpZ25lZCBsb25nIGZsYWdzOwoJdTMyIGR1bXBbNTEyXTsKCXVuc2lnbmVkIGksIGssIG4gPSAwOwoKCWRiZ190cmFjZSgiWyVzXSAlcFxuIiwgX19mdW5jX18sIGJ1Zik7CglpZiAoYXR0ciA9PSBOVUxMIHx8IGJ1ZiA9PSBOVUxMKSB7CgkJZGV2X2VycihkZXYsICJbJXNdIEVJTlZBTFxuIiwgX19mdW5jX18pOwoJCXJldHVybiAwOwoJfQoKCXNwaW5fbG9ja19pcnFzYXZlKHVkYy0+bG9jaywgZmxhZ3MpOwoJayA9IGh3X3JlZ2lzdGVyX3JlYWQoZHVtcCwgc2l6ZW9mKGR1bXApL3NpemVvZih1MzIpKTsKCXNwaW5fdW5sb2NrX2lycXJlc3RvcmUodWRjLT5sb2NrLCBmbGFncyk7CgoJZm9yIChpID0gMDsgaSA8IGs7IGkrKykgewoJCW4gKz0gc2NucHJpbnRmKGJ1ZiArIG4sIFBBR0VfU0laRSAtIG4sCgkJCSAgICAgICAicmVnWzB4JTA0WF0gPSAweCUwOFhcbiIsCgkJCSAgICAgICBpICogKHVuc2lnbmVkKXNpemVvZih1MzIpLCBkdW1wW2ldKTsKCX0KCglyZXR1cm4gbjsKfQoKLyoqCiAqIHN0b3JlX3JlZ2lzdGVyczogd3JpdGVzIHZhbHVlIHRvIHJlZ2lzdGVyIGFkZHJlc3MKICoKICogQ2hlY2sgImRldmljZS5oIiBmb3IgZGV0YWlscwogKi8Kc3RhdGljIHNzaXplX3Qgc3RvcmVfcmVnaXN0ZXJzKHN0cnVjdCBkZXZpY2UgKmRldiwKCQkJICAgICAgIHN0cnVjdCBkZXZpY2VfYXR0cmlidXRlICphdHRyLAoJCQkgICAgICAgY29uc3QgY2hhciAqYnVmLCBzaXplX3QgY291bnQpCnsKCXN0cnVjdCBjaTEzeHh4ICp1ZGMgPSBjb250YWluZXJfb2YoZGV2LCBzdHJ1Y3QgY2kxM3h4eCwgZ2FkZ2V0LmRldik7Cgl1bnNpZ25lZCBsb25nIGFkZHIsIGRhdGEsIGZsYWdzOwoKCWRiZ190cmFjZSgiWyVzXSAlcCwgJWRcbiIsIF9fZnVuY19fLCBidWYsIGNvdW50KTsKCWlmIChhdHRyID09IE5VTEwgfHwgYnVmID09IE5VTEwpIHsKCQlkZXZfZXJyKGRldiwgIlslc10gRUlOVkFMXG4iLCBfX2Z1bmNfXyk7CgkJZ290byBkb25lOwoJfQoKCWlmIChzc2NhbmYoYnVmLCAiJWxpICVsaSIsICZhZGRyLCAmZGF0YSkgIT0gMikgewoJCWRldl9lcnIoZGV2LCAiPGFkZHI+IDxkYXRhPjogd3JpdGUgZGF0YSB0byByZWdpc3RlciBhZGRyZXNzIik7CgkJZ290byBkb25lOwoJfQoKCXNwaW5fbG9ja19pcnFzYXZlKHVkYy0+bG9jaywgZmxhZ3MpOwoJaWYgKGh3X3JlZ2lzdGVyX3dyaXRlKGFkZHIsIGRhdGEpKQoJCWRldl9lcnIoZGV2LCAiaW52YWxpZCBhZGRyZXNzIHJhbmdlXG4iKTsKCXNwaW5fdW5sb2NrX2lycXJlc3RvcmUodWRjLT5sb2NrLCBmbGFncyk7CgogZG9uZToKCXJldHVybiBjb3VudDsKfQpzdGF0aWMgREVWSUNFX0FUVFIocmVnaXN0ZXJzLCBTX0lSVVNSIHwgU19JV1VTUiwKCQkgICBzaG93X3JlZ2lzdGVycywgc3RvcmVfcmVnaXN0ZXJzKTsKCi8qKgogKiBzaG93X3JlcXVlc3RzOiBETUEgY29udGVudHMgb2YgYWxsIHJlcXVlc3RzIGN1cnJlbnRseSBxdWV1ZWQgKGFsbCBlbmRwdHMpCiAqCiAqIENoZWNrICJkZXZpY2UuaCIgZm9yIGRldGFpbHMKICovCnN0YXRpYyBzc2l6ZV90IHNob3dfcmVxdWVzdHMoc3RydWN0IGRldmljZSAqZGV2LCBzdHJ1Y3QgZGV2aWNlX2F0dHJpYnV0ZSAqYXR0ciwKCQkJICAgICBjaGFyICpidWYpCnsKCXN0cnVjdCBjaTEzeHh4ICp1ZGMgPSBjb250YWluZXJfb2YoZGV2LCBzdHJ1Y3QgY2kxM3h4eCwgZ2FkZ2V0LmRldik7Cgl1bnNpZ25lZCBsb25nIGZsYWdzOwoJc3RydWN0IGxpc3RfaGVhZCAgICpwdHIgPSBOVUxMOwoJc3RydWN0IGNpMTN4eHhfcmVxICpyZXEgPSBOVUxMOwoJdW5zaWduZWQgaSwgaiwgaywgbiA9IDAsIHFTaXplID0gc2l6ZW9mKHN0cnVjdCBjaTEzeHh4X3RkKS9zaXplb2YodTMyKTsKCglkYmdfdHJhY2UoIlslc10gJXBcbiIsIF9fZnVuY19fLCBidWYpOwoJaWYgKGF0dHIgPT0gTlVMTCB8fCBidWYgPT0gTlVMTCkgewoJCWRldl9lcnIoZGV2LCAiWyVzXSBFSU5WQUxcbiIsIF9fZnVuY19fKTsKCQlyZXR1cm4gMDsKCX0KCglzcGluX2xvY2tfaXJxc2F2ZSh1ZGMtPmxvY2ssIGZsYWdzKTsKCWZvciAoaSA9IDA7IGkgPCBod19lcF9tYXg7IGkrKykKCQlmb3IgKGsgPSBSWDsgayA8PSBUWDsgaysrKQoJCQlsaXN0X2Zvcl9lYWNoKHB0ciwgJnVkYy0+Y2kxM3h4eF9lcFtpXS5xaFtrXS5xdWV1ZSkKCQkJewoJCQkJcmVxID0gbGlzdF9lbnRyeShwdHIsCgkJCQkJCSBzdHJ1Y3QgY2kxM3h4eF9yZXEsIHF1ZXVlKTsKCgkJCQluICs9IHNjbnByaW50ZihidWYgKyBuLCBQQUdFX1NJWkUgLSBuLAoJCQkJCSAgICAgICAiRVA9JTAyaTogVEQ9JTA4WCAlc1xuIiwKCQkJCQkgICAgICAgaSwgKHUzMilyZXEtPmRtYSwKCQkJCQkgICAgICAgKChrID09IFJYKSA/ICJSWCIgOiAiVFgiKSk7CgoJCQkJZm9yIChqID0gMDsgaiA8IHFTaXplOyBqKyspCgkJCQkJbiArPSBzY25wcmludGYoYnVmICsgbiwgUEFHRV9TSVpFIC0gbiwKCQkJCQkJICAgICAgICIgJTA0WDogICAgJTA4WFxuIiwgaiwKCQkJCQkJICAgICAgICooKHUzMiAqKXJlcS0+cHRyICsgaikpOwoJCQl9CglzcGluX3VubG9ja19pcnFyZXN0b3JlKHVkYy0+bG9jaywgZmxhZ3MpOwoKCXJldHVybiBuOwp9CnN0YXRpYyBERVZJQ0VfQVRUUihyZXF1ZXN0cywgU19JUlVTUiwgc2hvd19yZXF1ZXN0cywgTlVMTCk7CgovKioKICogZGJnX2NyZWF0ZV9maWxlczogaW5pdGlhbGl6ZXMgdGhlIGF0dHJpYnV0ZSBpbnRlcmZhY2UKICogQGRldjogZGV2aWNlCiAqCiAqIFRoaXMgZnVuY3Rpb24gcmV0dXJucyBhbiBlcnJvciBjb2RlCiAqLwpfX21heWJlX3VudXNlZCBzdGF0aWMgaW50IGRiZ19jcmVhdGVfZmlsZXMoc3RydWN0IGRldmljZSAqZGV2KQp7CglpbnQgcmV0dmFsID0gMDsKCglpZiAoZGV2ID09IE5VTEwpCgkJcmV0dXJuIC1FSU5WQUw7CglyZXR2YWwgPSBkZXZpY2VfY3JlYXRlX2ZpbGUoZGV2LCAmZGV2X2F0dHJfZGV2aWNlKTsKCWlmIChyZXR2YWwpCgkJZ290byBkb25lOwoJcmV0dmFsID0gZGV2aWNlX2NyZWF0ZV9maWxlKGRldiwgJmRldl9hdHRyX2RyaXZlcik7CglpZiAocmV0dmFsKQoJCWdvdG8gcm1fZGV2aWNlOwoJcmV0dmFsID0gZGV2aWNlX2NyZWF0ZV9maWxlKGRldiwgJmRldl9hdHRyX2V2ZW50cyk7CglpZiAocmV0dmFsKQoJCWdvdG8gcm1fZHJpdmVyOwoJcmV0dmFsID0gZGV2aWNlX2NyZWF0ZV9maWxlKGRldiwgJmRldl9hdHRyX2ludGVycyk7CglpZiAocmV0dmFsKQoJCWdvdG8gcm1fZXZlbnRzOwoJcmV0dmFsID0gZGV2aWNlX2NyZWF0ZV9maWxlKGRldiwgJmRldl9hdHRyX3BvcnRfdGVzdCk7CglpZiAocmV0dmFsKQoJCWdvdG8gcm1faW50ZXJzOwoJcmV0dmFsID0gZGV2aWNlX2NyZWF0ZV9maWxlKGRldiwgJmRldl9hdHRyX3FoZWFkcyk7CglpZiAocmV0dmFsKQoJCWdvdG8gcm1fcG9ydF90ZXN0OwoJcmV0dmFsID0gZGV2aWNlX2NyZWF0ZV9maWxlKGRldiwgJmRldl9hdHRyX3JlZ2lzdGVycyk7CglpZiAocmV0dmFsKQoJCWdvdG8gcm1fcWhlYWRzOwoJcmV0dmFsID0gZGV2aWNlX2NyZWF0ZV9maWxlKGRldiwgJmRldl9hdHRyX3JlcXVlc3RzKTsKCWlmIChyZXR2YWwpCgkJZ290byBybV9yZWdpc3RlcnM7CglyZXR1cm4gMDsKCiBybV9yZWdpc3RlcnM6CglkZXZpY2VfcmVtb3ZlX2ZpbGUoZGV2LCAmZGV2X2F0dHJfcmVnaXN0ZXJzKTsKIHJtX3FoZWFkczoKCWRldmljZV9yZW1vdmVfZmlsZShkZXYsICZkZXZfYXR0cl9xaGVhZHMpOwogcm1fcG9ydF90ZXN0OgoJZGV2aWNlX3JlbW92ZV9maWxlKGRldiwgJmRldl9hdHRyX3BvcnRfdGVzdCk7CiBybV9pbnRlcnM6CglkZXZpY2VfcmVtb3ZlX2ZpbGUoZGV2LCAmZGV2X2F0dHJfaW50ZXJzKTsKIHJtX2V2ZW50czoKCWRldmljZV9yZW1vdmVfZmlsZShkZXYsICZkZXZfYXR0cl9ldmVudHMpOwogcm1fZHJpdmVyOgoJZGV2aWNlX3JlbW92ZV9maWxlKGRldiwgJmRldl9hdHRyX2RyaXZlcik7CiBybV9kZXZpY2U6CglkZXZpY2VfcmVtb3ZlX2ZpbGUoZGV2LCAmZGV2X2F0dHJfZGV2aWNlKTsKIGRvbmU6CglyZXR1cm4gcmV0dmFsOwp9CgovKioKICogZGJnX3JlbW92ZV9maWxlczogZGVzdHJveXMgdGhlIGF0dHJpYnV0ZSBpbnRlcmZhY2UKICogQGRldjogZGV2aWNlCiAqCiAqIFRoaXMgZnVuY3Rpb24gcmV0dXJucyBhbiBlcnJvciBjb2RlCiAqLwpfX21heWJlX3VudXNlZCBzdGF0aWMgaW50IGRiZ19yZW1vdmVfZmlsZXMoc3RydWN0IGRldmljZSAqZGV2KQp7CglpZiAoZGV2ID09IE5VTEwpCgkJcmV0dXJuIC1FSU5WQUw7CglkZXZpY2VfcmVtb3ZlX2ZpbGUoZGV2LCAmZGV2X2F0dHJfcmVxdWVzdHMpOwoJZGV2aWNlX3JlbW92ZV9maWxlKGRldiwgJmRldl9hdHRyX3JlZ2lzdGVycyk7CglkZXZpY2VfcmVtb3ZlX2ZpbGUoZGV2LCAmZGV2X2F0dHJfcWhlYWRzKTsKCWRldmljZV9yZW1vdmVfZmlsZShkZXYsICZkZXZfYXR0cl9wb3J0X3Rlc3QpOwoJZGV2aWNlX3JlbW92ZV9maWxlKGRldiwgJmRldl9hdHRyX2ludGVycyk7CglkZXZpY2VfcmVtb3ZlX2ZpbGUoZGV2LCAmZGV2X2F0dHJfZXZlbnRzKTsKCWRldmljZV9yZW1vdmVfZmlsZShkZXYsICZkZXZfYXR0cl9kcml2ZXIpOwoJZGV2aWNlX3JlbW92ZV9maWxlKGRldiwgJmRldl9hdHRyX2RldmljZSk7CglyZXR1cm4gMDsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBVVElMIGJsb2NrCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8KLyoqCiAqIF91c2JfYWRkcjogY2FsY3VsYXRlcyBlbmRwb2ludCBhZGRyZXNzIGZyb20gZGlyZWN0aW9uICYgbnVtYmVyCiAqIEBlcDogIGVuZHBvaW50CiAqLwpzdGF0aWMgaW5saW5lIHU4IF91c2JfYWRkcihzdHJ1Y3QgY2kxM3h4eF9lcCAqZXApCnsKCXJldHVybiAoKGVwLT5kaXIgPT0gVFgpID8gVVNCX0VORFBPSU5UX0RJUl9NQVNLIDogMCkgfCBlcC0+bnVtOwp9CgovKioKICogX2hhcmR3YXJlX3F1ZXVlOiBjb25maWd1cmVzIGEgcmVxdWVzdCBhdCBoYXJkd2FyZSBsZXZlbAogKiBAZ2FkZ2V0OiBnYWRnZXQKICogQG1FcDogICAgZW5kcG9pbnQKICoKICogVGhpcyBmdW5jdGlvbiByZXR1cm5zIGFuIGVycm9yIGNvZGUKICovCnN0YXRpYyBpbnQgX2hhcmR3YXJlX2VucXVldWUoc3RydWN0IGNpMTN4eHhfZXAgKm1FcCwgc3RydWN0IGNpMTN4eHhfcmVxICptUmVxKQp7Cgl1bnNpZ25lZCBpOwoKCXRyYWNlKCIlcCwgJXAiLCBtRXAsIG1SZXEpOwoKCS8qIGRvbid0IHF1ZXVlIHR3aWNlICovCglpZiAobVJlcS0+cmVxLnN0YXR1cyA9PSAtRUFMUkVBRFkpCgkJcmV0dXJuIC1FQUxSRUFEWTsKCglpZiAoaHdfZXBfaXNfcHJpbWVkKG1FcC0+bnVtLCBtRXAtPmRpcikpCgkJcmV0dXJuIC1FQlVTWTsKCgltUmVxLT5yZXEuc3RhdHVzID0gLUVBTFJFQURZOwoKCWlmIChtUmVxLT5yZXEubGVuZ3RoICYmICFtUmVxLT5yZXEuZG1hKSB7CgkJbVJlcS0+cmVxLmRtYSA9IFwKCQkJZG1hX21hcF9zaW5nbGUobUVwLT5kZXZpY2UsIG1SZXEtPnJlcS5idWYsCgkJCQkgICAgICAgbVJlcS0+cmVxLmxlbmd0aCwgbUVwLT5kaXIgPwoJCQkJICAgICAgIERNQV9UT19ERVZJQ0UgOiBETUFfRlJPTV9ERVZJQ0UpOwoJCWlmIChtUmVxLT5yZXEuZG1hID09IDApCgkJCXJldHVybiAtRU5PTUVNOwoKCQltUmVxLT5tYXAgPSAxOwoJfQoKCS8qCgkgKiBURCBjb25maWd1cmF0aW9uCgkgKiBUT0RPIC0gaGFuZGxlIHJlcXVlc3RzIHdoaWNoIHNwYXducyBpbnRvIHNldmVyYWwgVERzCgkgKi8KCW1lbXNldChtUmVxLT5wdHIsIDAsIHNpemVvZigqbVJlcS0+cHRyKSk7CgltUmVxLT5wdHItPm5leHQgICAgfD0gVERfVEVSTUlOQVRFOwoJbVJlcS0+cHRyLT50b2tlbiAgICA9IG1SZXEtPnJlcS5sZW5ndGggPDwgZmZzX25yKFREX1RPVEFMX0JZVEVTKTsKCW1SZXEtPnB0ci0+dG9rZW4gICAmPSBURF9UT1RBTF9CWVRFUzsKCW1SZXEtPnB0ci0+dG9rZW4gICB8PSBURF9JT0M7CgltUmVxLT5wdHItPnRva2VuICAgfD0gVERfU1RBVFVTX0FDVElWRTsKCW1SZXEtPnB0ci0+cGFnZVswXSAgPSBtUmVxLT5yZXEuZG1hOwoJZm9yIChpID0gMTsgaSA8IDU7IGkrKykKCQltUmVxLT5wdHItPnBhZ2VbaV0gPQoJCQkobVJlcS0+cmVxLmRtYSArIGkgKiBQQUdFX1NJWkUpICYgflREX1JFU0VSVkVEX01BU0s7CgoJLyoKCSAqICBRSCBjb25maWd1cmF0aW9uCgkgKiAgQXQgdGhpcyBwb2ludCBpdCdzIGd1YXJhbnRlZWQgZXhjbHVzaXZlIGFjY2VzcyB0byBxaGVhZAoJICogIChlbmRwdCBpcyBub3QgcHJpbWVkKSBzbyBpdCdzIG5vIG5lZWQgdG8gdXNlIHRyaXB3aXJlCgkgKi8KCW1FcC0+cWhbbUVwLT5kaXJdLnB0ci0+dGQubmV4dCAgID0gbVJlcS0+ZG1hOyAgICAvKiBURVJNSU5BVEUgPSAwICovCgltRXAtPnFoW21FcC0+ZGlyXS5wdHItPnRkLnRva2VuICY9IH5URF9TVEFUVVM7ICAgLyogY2xlYXIgc3RhdHVzICovCglpZiAobVJlcS0+cmVxLnplcm8gPT0gMCkKCQltRXAtPnFoW21FcC0+ZGlyXS5wdHItPmNhcCB8PSAgUUhfWkxUOwoJZWxzZQoJCW1FcC0+cWhbbUVwLT5kaXJdLnB0ci0+Y2FwICY9IH5RSF9aTFQ7CgoJd21iKCk7ICAgLyogc3luY2hyb25pemUgYmVmb3JlIGVwIHByaW1lICovCgoJcmV0dXJuIGh3X2VwX3ByaW1lKG1FcC0+bnVtLCBtRXAtPmRpciwKCQkJICAgbUVwLT50eXBlID09IFVTQl9FTkRQT0lOVF9YRkVSX0NPTlRST0wpOwp9CgovKioKICogX2hhcmR3YXJlX2RlcXVldWU6IGhhbmRsZXMgYSByZXF1ZXN0IGF0IGhhcmR3YXJlIGxldmVsCiAqIEBnYWRnZXQ6IGdhZGdldAogKiBAbUVwOiAgICBlbmRwb2ludAogKgogKiBUaGlzIGZ1bmN0aW9uIHJldHVybnMgYW4gZXJyb3IgY29kZQogKi8Kc3RhdGljIGludCBfaGFyZHdhcmVfZGVxdWV1ZShzdHJ1Y3QgY2kxM3h4eF9lcCAqbUVwLCBzdHJ1Y3QgY2kxM3h4eF9yZXEgKm1SZXEpCnsKCXRyYWNlKCIlcCwgJXAiLCBtRXAsIG1SZXEpOwoKCWlmIChtUmVxLT5yZXEuc3RhdHVzICE9IC1FQUxSRUFEWSkKCQlyZXR1cm4gLUVJTlZBTDsKCglpZiAoaHdfZXBfaXNfcHJpbWVkKG1FcC0+bnVtLCBtRXAtPmRpcikpCgkJaHdfZXBfZmx1c2gobUVwLT5udW0sIG1FcC0+ZGlyKTsKCgltUmVxLT5yZXEuc3RhdHVzID0gMDsKCglpZiAobVJlcS0+bWFwKSB7CgkJZG1hX3VubWFwX3NpbmdsZShtRXAtPmRldmljZSwgbVJlcS0+cmVxLmRtYSwgbVJlcS0+cmVxLmxlbmd0aCwKCQkJCSBtRXAtPmRpciA/IERNQV9UT19ERVZJQ0UgOiBETUFfRlJPTV9ERVZJQ0UpOwoJCW1SZXEtPnJlcS5kbWEgPSAwOwoJCW1SZXEtPm1hcCAgICAgPSAwOwoJfQoKCW1SZXEtPnJlcS5zdGF0dXMgPSBtUmVxLT5wdHItPnRva2VuICYgVERfU1RBVFVTOwoJaWYgICAgICAoKFREX1NUQVRVU19BQ1RJVkUgJiBtUmVxLT5yZXEuc3RhdHVzKSAhPSAwKQoJCW1SZXEtPnJlcS5zdGF0dXMgPSAtRUNPTk5SRVNFVDsKCWVsc2UgaWYgKChURF9TVEFUVVNfSEFMVEVEICYgbVJlcS0+cmVxLnN0YXR1cykgIT0gMCkKCQltUmVxLT5yZXEuc3RhdHVzID0gLTE7CgllbHNlIGlmICgoVERfU1RBVFVTX0RUX0VSUiAmIG1SZXEtPnJlcS5zdGF0dXMpICE9IDApCgkJbVJlcS0+cmVxLnN0YXR1cyA9IC0xOwoJZWxzZSBpZiAoKFREX1NUQVRVU19UUl9FUlIgJiBtUmVxLT5yZXEuc3RhdHVzKSAhPSAwKQoJCW1SZXEtPnJlcS5zdGF0dXMgPSAtMTsKCgltUmVxLT5yZXEuYWN0dWFsICAgPSBtUmVxLT5wdHItPnRva2VuICYgVERfVE9UQUxfQllURVM7CgltUmVxLT5yZXEuYWN0dWFsID4+PSBmZnNfbnIoVERfVE9UQUxfQllURVMpOwoJbVJlcS0+cmVxLmFjdHVhbCAgID0gbVJlcS0+cmVxLmxlbmd0aCAtIG1SZXEtPnJlcS5hY3R1YWw7CgltUmVxLT5yZXEuYWN0dWFsICAgPSBtUmVxLT5yZXEuc3RhdHVzID8gMCA6IG1SZXEtPnJlcS5hY3R1YWw7CgoJcmV0dXJuIG1SZXEtPnJlcS5hY3R1YWw7Cn0KCi8qKgogKiBfZXBfbnVrZTogZGVxdWV1ZXMgYWxsIGVuZHBvaW50IHJlcXVlc3RzCiAqIEBtRXA6IGVuZHBvaW50CiAqCiAqIFRoaXMgZnVuY3Rpb24gcmV0dXJucyBhbiBlcnJvciBjb2RlCiAqIENhbGxlciBtdXN0IGhvbGQgbG9jawogKi8Kc3RhdGljIGludCBfZXBfbnVrZShzdHJ1Y3QgY2kxM3h4eF9lcCAqbUVwKQpfX3JlbGVhc2VzKG1FcC0+bG9jaykKX19hY3F1aXJlcyhtRXAtPmxvY2spCnsKCXRyYWNlKCIlcCIsIG1FcCk7CgoJaWYgKG1FcCA9PSBOVUxMKQoJCXJldHVybiAtRUlOVkFMOwoKCWh3X2VwX2ZsdXNoKG1FcC0+bnVtLCBtRXAtPmRpcik7CgoJd2hpbGUgKCFsaXN0X2VtcHR5KCZtRXAtPnFoW21FcC0+ZGlyXS5xdWV1ZSkpIHsKCgkJLyogcG9wIG9sZGVzdCByZXF1ZXN0ICovCgkJc3RydWN0IGNpMTN4eHhfcmVxICptUmVxID0gXAoJCQlsaXN0X2VudHJ5KG1FcC0+cWhbbUVwLT5kaXJdLnF1ZXVlLm5leHQsCgkJCQkgICBzdHJ1Y3QgY2kxM3h4eF9yZXEsIHF1ZXVlKTsKCQlsaXN0X2RlbF9pbml0KCZtUmVxLT5xdWV1ZSk7CgkJbVJlcS0+cmVxLnN0YXR1cyA9IC1FU0hVVERPV047CgoJCWlmICghbVJlcS0+cmVxLm5vX2ludGVycnVwdCAmJiBtUmVxLT5yZXEuY29tcGxldGUgIT0gTlVMTCkgewoJCQlzcGluX3VubG9jayhtRXAtPmxvY2spOwoJCQltUmVxLT5yZXEuY29tcGxldGUoJm1FcC0+ZXAsICZtUmVxLT5yZXEpOwoJCQlzcGluX2xvY2sobUVwLT5sb2NrKTsKCQl9Cgl9CglyZXR1cm4gMDsKfQoKLyoqCiAqIF9nYWRnZXRfc3RvcF9hY3Rpdml0eTogc3RvcHMgYWxsIFVTQiBhY3Rpdml0eSwgZmx1c2hlcyAmIGRpc2FibGVzIGFsbCBlbmRwdHMKICogQGdhZGdldDogZ2FkZ2V0CiAqCiAqIFRoaXMgZnVuY3Rpb24gcmV0dXJucyBhbiBlcnJvciBjb2RlCiAqIENhbGxlciBtdXN0IGhvbGQgbG9jawogKi8Kc3RhdGljIGludCBfZ2FkZ2V0X3N0b3BfYWN0aXZpdHkoc3RydWN0IHVzYl9nYWRnZXQgKmdhZGdldCkKX19yZWxlYXNlcyh1ZGMtPmxvY2spCl9fYWNxdWlyZXModWRjLT5sb2NrKQp7CglzdHJ1Y3QgdXNiX2VwICplcDsKCXN0cnVjdCBjaTEzeHh4ICAgICp1ZGMgPSBjb250YWluZXJfb2YoZ2FkZ2V0LCBzdHJ1Y3QgY2kxM3h4eCwgZ2FkZ2V0KTsKCXN0cnVjdCBjaTEzeHh4X2VwICptRXAgPSBjb250YWluZXJfb2YoZ2FkZ2V0LT5lcDAsCgkJCQkJICAgICAgc3RydWN0IGNpMTN4eHhfZXAsIGVwKTsKCgl0cmFjZSgiJXAiLCBnYWRnZXQpOwoKCWlmIChnYWRnZXQgPT0gTlVMTCkKCQlyZXR1cm4gLUVJTlZBTDsKCglzcGluX3VubG9jayh1ZGMtPmxvY2spOwoKCS8qIGZsdXNoIGFsbCBlbmRwb2ludHMgKi8KCWdhZGdldF9mb3JfZWFjaF9lcChlcCwgZ2FkZ2V0KSB7CgkJdXNiX2VwX2ZpZm9fZmx1c2goZXApOwoJfQoJdXNiX2VwX2ZpZm9fZmx1c2goZ2FkZ2V0LT5lcDApOwoKCXVkYy0+ZHJpdmVyLT5kaXNjb25uZWN0KGdhZGdldCk7CgoJLyogbWFrZSBzdXJlIHRvIGRpc2FibGUgYWxsIGVuZHBvaW50cyAqLwoJZ2FkZ2V0X2Zvcl9lYWNoX2VwKGVwLCBnYWRnZXQpIHsKCQl1c2JfZXBfZGlzYWJsZShlcCk7Cgl9Cgl1c2JfZXBfZGlzYWJsZShnYWRnZXQtPmVwMCk7CgoJaWYgKG1FcC0+c3RhdHVzICE9IE5VTEwpIHsKCQl1c2JfZXBfZnJlZV9yZXF1ZXN0KGdhZGdldC0+ZXAwLCBtRXAtPnN0YXR1cyk7CgkJbUVwLT5zdGF0dXMgPSBOVUxMOwoJfQoKCXNwaW5fbG9jayh1ZGMtPmxvY2spOwoKCXJldHVybiAwOwp9CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElTUiBibG9jawogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCi8qKgogKiBpc3JfcmVzZXRfaGFuZGxlcjogVVNCIHJlc2V0IGludGVycnVwdCBoYW5kbGVyCiAqIEB1ZGM6IFVEQyBkZXZpY2UKICoKICogVGhpcyBmdW5jdGlvbiByZXNldHMgVVNCIGVuZ2luZSBhZnRlciBhIGJ1cyByZXNldCBvY2N1cnJlZAogKi8Kc3RhdGljIHZvaWQgaXNyX3Jlc2V0X2hhbmRsZXIoc3RydWN0IGNpMTN4eHggKnVkYykKX19yZWxlYXNlcyh1ZGMtPmxvY2spCl9fYWNxdWlyZXModWRjLT5sb2NrKQp7CglzdHJ1Y3QgY2kxM3h4eF9lcCAqbUVwID0gJnVkYy0+Y2kxM3h4eF9lcFswXTsKCWludCByZXR2YWw7CgoJdHJhY2UoIiVwIiwgdWRjKTsKCglpZiAodWRjID09IE5VTEwpIHsKCQllcnIoIkVJTlZBTCIpOwoJCXJldHVybjsKCX0KCglkYmdfZXZlbnQoMHhGRiwgIkJVUyBSU1QiLCAwKTsKCglyZXR2YWwgPSBfZ2FkZ2V0X3N0b3BfYWN0aXZpdHkoJnVkYy0+Z2FkZ2V0KTsKCWlmIChyZXR2YWwpCgkJZ290byBkb25lOwoKCXJldHZhbCA9IGh3X3VzYl9yZXNldCgpOwoJaWYgKHJldHZhbCkKCQlnb3RvIGRvbmU7CgoJc3Bpbl91bmxvY2sodWRjLT5sb2NrKTsKCXJldHZhbCA9IHVzYl9lcF9lbmFibGUoJm1FcC0+ZXAsICZjdHJsX2VuZHB0X2Rlc2MpOwoJaWYgKCFyZXR2YWwpIHsKCQltRXAtPnN0YXR1cyA9IHVzYl9lcF9hbGxvY19yZXF1ZXN0KCZtRXAtPmVwLCBHRlBfS0VSTkVMKTsKCQlpZiAobUVwLT5zdGF0dXMgPT0gTlVMTCkgewoJCQl1c2JfZXBfZGlzYWJsZSgmbUVwLT5lcCk7CgkJCXJldHZhbCA9IC1FTk9NRU07CgkJfQoJfQoJc3Bpbl9sb2NrKHVkYy0+bG9jayk7CgogZG9uZToKCWlmIChyZXR2YWwpCgkJZXJyKCJlcnJvcjogJWkiLCByZXR2YWwpOwp9CgovKioKICogaXNyX2dldF9zdGF0dXNfY29tcGxldGU6IGdldF9zdGF0dXMgcmVxdWVzdCBjb21wbGV0ZSBmdW5jdGlvbgogKiBAZXA6ICBlbmRwb2ludAogKiBAcmVxOiByZXF1ZXN0IGhhbmRsZWQKICoKICogQ2FsbGVyIG11c3QgcmVsZWFzZSBsb2NrCiAqLwpzdGF0aWMgdm9pZCBpc3JfZ2V0X3N0YXR1c19jb21wbGV0ZShzdHJ1Y3QgdXNiX2VwICplcCwgc3RydWN0IHVzYl9yZXF1ZXN0ICpyZXEpCnsKCXRyYWNlKCIlcCwgJXAiLCBlcCwgcmVxKTsKCglpZiAoZXAgPT0gTlVMTCB8fCByZXEgPT0gTlVMTCkgewoJCWVycigiRUlOVkFMIik7CgkJcmV0dXJuOwoJfQoKCWtmcmVlKHJlcS0+YnVmKTsKCXVzYl9lcF9mcmVlX3JlcXVlc3QoZXAsIHJlcSk7Cn0KCi8qKgogKiBpc3JfZ2V0X3N0YXR1c19yZXNwb25zZTogZ2V0X3N0YXR1cyByZXF1ZXN0IHJlc3BvbnNlCiAqIEBlcDogICAgZW5kcG9pbnQKICogQHNldHVwOiBzZXR1cCByZXF1ZXN0IHBhY2tldAogKgogKiBUaGlzIGZ1bmN0aW9uIHJldHVybnMgYW4gZXJyb3IgY29kZQogKi8Kc3RhdGljIGludCBpc3JfZ2V0X3N0YXR1c19yZXNwb25zZShzdHJ1Y3QgY2kxM3h4eF9lcCAqbUVwLAoJCQkJICAgc3RydWN0IHVzYl9jdHJscmVxdWVzdCAqc2V0dXApCl9fcmVsZWFzZXMobUVwLT5sb2NrKQpfX2FjcXVpcmVzKG1FcC0+bG9jaykKewoJc3RydWN0IHVzYl9yZXF1ZXN0ICpyZXEgPSBOVUxMOwoJZ2ZwX3QgZ2ZwX2ZsYWdzID0gR0ZQX0FUT01JQzsKCWludCBkaXIsIG51bSwgcmV0dmFsOwoKCXRyYWNlKCIlcCwgJXAiLCBtRXAsIHNldHVwKTsKCglpZiAobUVwID09IE5VTEwgfHwgc2V0dXAgPT0gTlVMTCkKCQlyZXR1cm4gLUVJTlZBTDsKCglzcGluX3VubG9jayhtRXAtPmxvY2spOwoJcmVxID0gdXNiX2VwX2FsbG9jX3JlcXVlc3QoJm1FcC0+ZXAsIGdmcF9mbGFncyk7CglzcGluX2xvY2sobUVwLT5sb2NrKTsKCWlmIChyZXEgPT0gTlVMTCkKCQlyZXR1cm4gLUVOT01FTTsKCglyZXEtPmNvbXBsZXRlID0gaXNyX2dldF9zdGF0dXNfY29tcGxldGU7CglyZXEtPmxlbmd0aCAgID0gMjsKCXJlcS0+YnVmICAgICAgPSBremFsbG9jKHJlcS0+bGVuZ3RoLCBnZnBfZmxhZ3MpOwoJaWYgKHJlcS0+YnVmID09IE5VTEwpIHsKCQlyZXR2YWwgPSAtRU5PTUVNOwoJCWdvdG8gZXJyX2ZyZWVfcmVxOwoJfQoKCWlmICgoc2V0dXAtPmJSZXF1ZXN0VHlwZSAmIFVTQl9SRUNJUF9NQVNLKSA9PSBVU0JfUkVDSVBfREVWSUNFKSB7CgkJLyogVE9ETzogRDEgLSBSZW1vdGUgV2FrZXVwOyBEMCAtIFNlbGYgUG93ZXJlZCAqLwoJCXJldHZhbCA9IDA7Cgl9IGVsc2UgaWYgKChzZXR1cC0+YlJlcXVlc3RUeXBlICYgVVNCX1JFQ0lQX01BU0spIFwKCQkgICA9PSBVU0JfUkVDSVBfRU5EUE9JTlQpIHsKCQlkaXIgPSAobGUxNl90b19jcHUoc2V0dXAtPndJbmRleCkgJiBVU0JfRU5EUE9JTlRfRElSX01BU0spID8KCQkJVFggOiBSWDsKCQludW0gPSAgbGUxNl90b19jcHUoc2V0dXAtPndJbmRleCkgJiBVU0JfRU5EUE9JTlRfTlVNQkVSX01BU0s7CgkJKigodTE2ICopcmVxLT5idWYpID0gaHdfZXBfZ2V0X2hhbHQobnVtLCBkaXIpOwoJfQoJLyogZWxzZSBkbyBub3RoaW5nOyByZXNlcnZlZCBmb3IgZnV0dXJlIHVzZSAqLwoKCXNwaW5fdW5sb2NrKG1FcC0+bG9jayk7CglyZXR2YWwgPSB1c2JfZXBfcXVldWUoJm1FcC0+ZXAsIHJlcSwgZ2ZwX2ZsYWdzKTsKCXNwaW5fbG9jayhtRXAtPmxvY2spOwoJaWYgKHJldHZhbCkKCQlnb3RvIGVycl9mcmVlX2J1ZjsKCglyZXR1cm4gMDsKCiBlcnJfZnJlZV9idWY6CglrZnJlZShyZXEtPmJ1Zik7CiBlcnJfZnJlZV9yZXE6CglzcGluX3VubG9jayhtRXAtPmxvY2spOwoJdXNiX2VwX2ZyZWVfcmVxdWVzdCgmbUVwLT5lcCwgcmVxKTsKCXNwaW5fbG9jayhtRXAtPmxvY2spOwoJcmV0dXJuIHJldHZhbDsKfQoKLyoqCiAqIGlzcl9zZXR1cF9zdGF0dXNfcGhhc2U6IHF1ZXVlcyB0aGUgc3RhdHVzIHBoYXNlIG9mIGEgc2V0dXAgdHJhbnNhdGlvbgogKiBAbUVwOiBlbmRwb2ludAogKgogKiBUaGlzIGZ1bmN0aW9uIHJldHVybnMgYW4gZXJyb3IgY29kZQogKi8Kc3RhdGljIGludCBpc3Jfc2V0dXBfc3RhdHVzX3BoYXNlKHN0cnVjdCBjaTEzeHh4X2VwICptRXApCl9fcmVsZWFzZXMobUVwLT5sb2NrKQpfX2FjcXVpcmVzKG1FcC0+bG9jaykKewoJaW50IHJldHZhbDsKCgl0cmFjZSgiJXAiLCBtRXApOwoKCS8qIG1FcCBpcyBhbHdheXMgdmFsaWQgJiBjb25maWd1cmVkICovCgoJaWYgKG1FcC0+dHlwZSA9PSBVU0JfRU5EUE9JTlRfWEZFUl9DT05UUk9MKQoJCW1FcC0+ZGlyID0gKG1FcC0+ZGlyID09IFRYKSA/IFJYIDogVFg7CgoJbUVwLT5zdGF0dXMtPm5vX2ludGVycnVwdCA9IDE7CgoJc3Bpbl91bmxvY2sobUVwLT5sb2NrKTsKCXJldHZhbCA9IHVzYl9lcF9xdWV1ZSgmbUVwLT5lcCwgbUVwLT5zdGF0dXMsIEdGUF9BVE9NSUMpOwoJc3Bpbl9sb2NrKG1FcC0+bG9jayk7CgoJcmV0dXJuIHJldHZhbDsKfQoKLyoqCiAqIGlzcl90cl9jb21wbGV0ZV9sb3c6IHRyYW5zYWN0aW9uIGNvbXBsZXRlIGxvdyBsZXZlbCBoYW5kbGVyCiAqIEBtRXA6IGVuZHBvaW50CiAqCiAqIFRoaXMgZnVuY3Rpb24gcmV0dXJucyBhbiBlcnJvciBjb2RlCiAqIENhbGxlciBtdXN0IGhvbGQgbG9jawogKi8Kc3RhdGljIGludCBpc3JfdHJfY29tcGxldGVfbG93KHN0cnVjdCBjaTEzeHh4X2VwICptRXApCl9fcmVsZWFzZXMobUVwLT5sb2NrKQpfX2FjcXVpcmVzKG1FcC0+bG9jaykKewoJc3RydWN0IGNpMTN4eHhfcmVxICptUmVxOwoJaW50IHJldHZhbDsKCgl0cmFjZSgiJXAiLCBtRXApOwoKCWlmIChsaXN0X2VtcHR5KCZtRXAtPnFoW21FcC0+ZGlyXS5xdWV1ZSkpCgkJcmV0dXJuIC1FSU5WQUw7CgoJLyogcG9wIG9sZGVzdCByZXF1ZXN0ICovCgltUmVxID0gbGlzdF9lbnRyeShtRXAtPnFoW21FcC0+ZGlyXS5xdWV1ZS5uZXh0LAoJCQkgIHN0cnVjdCBjaTEzeHh4X3JlcSwgcXVldWUpOwoJbGlzdF9kZWxfaW5pdCgmbVJlcS0+cXVldWUpOwoKCXJldHZhbCA9IF9oYXJkd2FyZV9kZXF1ZXVlKG1FcCwgbVJlcSk7CglpZiAocmV0dmFsIDwgMCkgewoJCWRiZ19ldmVudChfdXNiX2FkZHIobUVwKSwgIkRPTkUiLCByZXR2YWwpOwoJCWdvdG8gZG9uZTsKCX0KCglkYmdfZG9uZShfdXNiX2FkZHIobUVwKSwgbVJlcS0+cHRyLT50b2tlbiwgcmV0dmFsKTsKCglpZiAoIW1SZXEtPnJlcS5ub19pbnRlcnJ1cHQgJiYgbVJlcS0+cmVxLmNvbXBsZXRlICE9IE5VTEwpIHsKCQlzcGluX3VubG9jayhtRXAtPmxvY2spOwoJCW1SZXEtPnJlcS5jb21wbGV0ZSgmbUVwLT5lcCwgJm1SZXEtPnJlcSk7CgkJc3Bpbl9sb2NrKG1FcC0+bG9jayk7Cgl9CgoJaWYgKCFsaXN0X2VtcHR5KCZtRXAtPnFoW21FcC0+ZGlyXS5xdWV1ZSkpIHsKCQltUmVxID0gbGlzdF9lbnRyeShtRXAtPnFoW21FcC0+ZGlyXS5xdWV1ZS5uZXh0LAoJCQkJICBzdHJ1Y3QgY2kxM3h4eF9yZXEsIHF1ZXVlKTsKCQlfaGFyZHdhcmVfZW5xdWV1ZShtRXAsIG1SZXEpOwoJfQoKIGRvbmU6CglyZXR1cm4gcmV0dmFsOwp9CgovKioKICogaXNyX3RyX2NvbXBsZXRlX2hhbmRsZXI6IHRyYW5zYWN0aW9uIGNvbXBsZXRlIGludGVycnVwdCBoYW5kbGVyCiAqIEB1ZGM6IFVEQyBkZXNjcmlwdG9yCiAqCiAqIFRoaXMgZnVuY3Rpb24gaGFuZGxlcyB0cmFmZmljIGV2ZW50cwogKi8Kc3RhdGljIHZvaWQgaXNyX3RyX2NvbXBsZXRlX2hhbmRsZXIoc3RydWN0IGNpMTN4eHggKnVkYykKX19yZWxlYXNlcyh1ZGMtPmxvY2spCl9fYWNxdWlyZXModWRjLT5sb2NrKQp7Cgl1bnNpZ25lZCBpOwoKCXRyYWNlKCIlcCIsIHVkYyk7CgoJaWYgKHVkYyA9PSBOVUxMKSB7CgkJZXJyKCJFSU5WQUwiKTsKCQlyZXR1cm47Cgl9CgoJZm9yIChpID0gMDsgaSA8IGh3X2VwX21heDsgaSsrKSB7CgkJc3RydWN0IGNpMTN4eHhfZXAgKm1FcCAgPSAmdWRjLT5jaTEzeHh4X2VwW2ldOwoJCWludCB0eXBlLCBudW0sIGVyciA9IC1FSU5WQUw7CgkJc3RydWN0IHVzYl9jdHJscmVxdWVzdCByZXE7CgoKCQlpZiAobUVwLT5kZXNjID09IE5VTEwpCgkJCWNvbnRpbnVlOyAgIC8qIG5vdCBjb25maWd1cmVkICovCgoJCWlmICgobUVwLT5kaXIgPT0gUlggJiYgaHdfdGVzdF9hbmRfY2xlYXJfY29tcGxldGUoaSkpIHx8CgkJICAgIChtRXAtPmRpciA9PSBUWCAmJiBod190ZXN0X2FuZF9jbGVhcl9jb21wbGV0ZShpICsgMTYpKSkgewoJCQllcnIgPSBpc3JfdHJfY29tcGxldGVfbG93KG1FcCk7CgkJCWlmIChtRXAtPnR5cGUgPT0gVVNCX0VORFBPSU5UX1hGRVJfQ09OVFJPTCkgewoJCQkJaWYgKGVyciA+IDApICAgLyogbmVlZHMgc3RhdHVzIHBoYXNlICovCgkJCQkJZXJyID0gaXNyX3NldHVwX3N0YXR1c19waGFzZShtRXApOwoJCQkJaWYgKGVyciA8IDApIHsKCQkJCQlkYmdfZXZlbnQoX3VzYl9hZGRyKG1FcCksCgkJCQkJCSAgIkVSUk9SIiwgZXJyKTsKCQkJCQlzcGluX3VubG9jayh1ZGMtPmxvY2spOwoJCQkJCWlmICh1c2JfZXBfc2V0X2hhbHQoJm1FcC0+ZXApKQoJCQkJCQllcnIoImVycm9yOiBlcF9zZXRfaGFsdCIpOwoJCQkJCXNwaW5fbG9jayh1ZGMtPmxvY2spOwoJCQkJfQoJCQl9CgkJfQoKCQlpZiAobUVwLT50eXBlICE9IFVTQl9FTkRQT0lOVF9YRkVSX0NPTlRST0wgfHwKCQkgICAgIWh3X3Rlc3RfYW5kX2NsZWFyX3NldHVwX3N0YXR1cyhpKSkKCQkJY29udGludWU7CgoJCWlmIChpICE9IDApIHsKCQkJd2FybigiY3RybCB0cmFmZmljIHJlY2VpdmVkIGF0IGVuZHBvaW50Iik7CgkJCWNvbnRpbnVlOwoJCX0KCgkJLyogcmVhZF9zZXR1cF9wYWNrZXQgKi8KCQlkbyB7CgkJCWh3X3Rlc3RfYW5kX3NldF9zZXR1cF9ndWFyZCgpOwoJCQltZW1jcHkoJnJlcSwgJm1FcC0+cWhbUlhdLnB0ci0+c2V0dXAsIHNpemVvZihyZXEpKTsKCQl9IHdoaWxlICghaHdfdGVzdF9hbmRfY2xlYXJfc2V0dXBfZ3VhcmQoKSk7CgoJCXR5cGUgPSByZXEuYlJlcXVlc3RUeXBlOwoKCQltRXAtPmRpciA9ICh0eXBlICYgVVNCX0RJUl9JTikgPyBUWCA6IFJYOwoKCQlkYmdfc2V0dXAoX3VzYl9hZGRyKG1FcCksICZyZXEpOwoKCQlzd2l0Y2ggKHJlcS5iUmVxdWVzdCkgewoJCWNhc2UgVVNCX1JFUV9DTEVBUl9GRUFUVVJFOgoJCQlpZiAodHlwZSAhPSAoVVNCX0RJUl9PVVR8VVNCX1JFQ0lQX0VORFBPSU5UKSAmJgoJCQkgICAgbGUxNl90b19jcHUocmVxLndWYWx1ZSkgIT0gVVNCX0VORFBPSU5UX0hBTFQpCgkJCQlnb3RvIGRlbGVnYXRlOwoJCQlpZiAocmVxLndMZW5ndGggIT0gMCkKCQkJCWJyZWFrOwoJCQludW0gID0gbGUxNl90b19jcHUocmVxLndJbmRleCk7CgkJCW51bSAmPSBVU0JfRU5EUE9JTlRfTlVNQkVSX01BU0s7CgkJCWlmICghdWRjLT5jaTEzeHh4X2VwW251bV0ud2VkZ2UpIHsKCQkJCXNwaW5fdW5sb2NrKHVkYy0+bG9jayk7CgkJCQllcnIgPSB1c2JfZXBfY2xlYXJfaGFsdCgKCQkJCQkmdWRjLT5jaTEzeHh4X2VwW251bV0uZXApOwoJCQkJc3Bpbl9sb2NrKHVkYy0+bG9jayk7CgkJCQlpZiAoZXJyKQoJCQkJCWJyZWFrOwoJCQl9CgkJCWVyciA9IGlzcl9zZXR1cF9zdGF0dXNfcGhhc2UobUVwKTsKCQkJYnJlYWs7CgkJY2FzZSBVU0JfUkVRX0dFVF9TVEFUVVM6CgkJCWlmICh0eXBlICE9IChVU0JfRElSX0lOfFVTQl9SRUNJUF9ERVZJQ0UpICAgJiYKCQkJICAgIHR5cGUgIT0gKFVTQl9ESVJfSU58VVNCX1JFQ0lQX0VORFBPSU5UKSAmJgoJCQkgICAgdHlwZSAhPSAoVVNCX0RJUl9JTnxVU0JfUkVDSVBfSU5URVJGQUNFKSkKCQkJCWdvdG8gZGVsZWdhdGU7CgkJCWlmIChsZTE2X3RvX2NwdShyZXEud0xlbmd0aCkgIT0gMiB8fAoJCQkgICAgbGUxNl90b19jcHUocmVxLndWYWx1ZSkgICE9IDApCgkJCQlicmVhazsKCQkJZXJyID0gaXNyX2dldF9zdGF0dXNfcmVzcG9uc2UobUVwLCAmcmVxKTsKCQkJYnJlYWs7CgkJY2FzZSBVU0JfUkVRX1NFVF9BRERSRVNTOgoJCQlpZiAodHlwZSAhPSAoVVNCX0RJUl9PVVR8VVNCX1JFQ0lQX0RFVklDRSkpCgkJCQlnb3RvIGRlbGVnYXRlOwoJCQlpZiAobGUxNl90b19jcHUocmVxLndMZW5ndGgpICE9IDAgfHwKCQkJICAgIGxlMTZfdG9fY3B1KHJlcS53SW5kZXgpICAhPSAwKQoJCQkJYnJlYWs7CgkJCWVyciA9IGh3X3VzYl9zZXRfYWRkcmVzcygodTgpbGUxNl90b19jcHUocmVxLndWYWx1ZSkpOwoJCQlpZiAoZXJyKQoJCQkJYnJlYWs7CgkJCWVyciA9IGlzcl9zZXR1cF9zdGF0dXNfcGhhc2UobUVwKTsKCQkJYnJlYWs7CgkJY2FzZSBVU0JfUkVRX1NFVF9GRUFUVVJFOgoJCQlpZiAodHlwZSAhPSAoVVNCX0RJUl9PVVR8VVNCX1JFQ0lQX0VORFBPSU5UKSAmJgoJCQkgICAgbGUxNl90b19jcHUocmVxLndWYWx1ZSkgIT0gVVNCX0VORFBPSU5UX0hBTFQpCgkJCQlnb3RvIGRlbGVnYXRlOwoJCQlpZiAocmVxLndMZW5ndGggIT0gMCkKCQkJCWJyZWFrOwoJCQludW0gID0gbGUxNl90b19jcHUocmVxLndJbmRleCk7CgkJCW51bSAmPSBVU0JfRU5EUE9JTlRfTlVNQkVSX01BU0s7CgoJCQlzcGluX3VubG9jayh1ZGMtPmxvY2spOwoJCQllcnIgPSB1c2JfZXBfc2V0X2hhbHQoJnVkYy0+Y2kxM3h4eF9lcFtudW1dLmVwKTsKCQkJc3Bpbl9sb2NrKHVkYy0+bG9jayk7CgkJCWlmIChlcnIpCgkJCQlicmVhazsKCQkJZXJyID0gaXNyX3NldHVwX3N0YXR1c19waGFzZShtRXApOwoJCQlicmVhazsKCQlkZWZhdWx0OgpkZWxlZ2F0ZToKCQkJaWYgKHJlcS53TGVuZ3RoID09IDApICAgLyogbm8gZGF0YSBwaGFzZSAqLwoJCQkJbUVwLT5kaXIgPSBUWDsKCgkJCXNwaW5fdW5sb2NrKHVkYy0+bG9jayk7CgkJCWVyciA9IHVkYy0+ZHJpdmVyLT5zZXR1cCgmdWRjLT5nYWRnZXQsICZyZXEpOwoJCQlzcGluX2xvY2sodWRjLT5sb2NrKTsKCQkJYnJlYWs7CgkJfQoKCQlpZiAoZXJyIDwgMCkgewoJCQlkYmdfZXZlbnQoX3VzYl9hZGRyKG1FcCksICJFUlJPUiIsIGVycik7CgoJCQlzcGluX3VubG9jayh1ZGMtPmxvY2spOwoJCQlpZiAodXNiX2VwX3NldF9oYWx0KCZtRXAtPmVwKSkKCQkJCWVycigiZXJyb3I6IGVwX3NldF9oYWx0Iik7CgkJCXNwaW5fbG9jayh1ZGMtPmxvY2spOwoJCX0KCX0KfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBFTkRQVCBibG9jawogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCi8qKgogKiBlcF9lbmFibGU6IGNvbmZpZ3VyZSBlbmRwb2ludCwgbWFraW5nIGl0IHVzYWJsZQogKgogKiBDaGVjayB1c2JfZXBfZW5hYmxlKCkgYXQgInVzYl9nYWRnZXQuaCIgZm9yIGRldGFpbHMKICovCnN0YXRpYyBpbnQgZXBfZW5hYmxlKHN0cnVjdCB1c2JfZXAgKmVwLAoJCSAgICAgY29uc3Qgc3RydWN0IHVzYl9lbmRwb2ludF9kZXNjcmlwdG9yICpkZXNjKQp7CglzdHJ1Y3QgY2kxM3h4eF9lcCAqbUVwID0gY29udGFpbmVyX29mKGVwLCBzdHJ1Y3QgY2kxM3h4eF9lcCwgZXApOwoJaW50IGRpcmVjdGlvbiwgcmV0dmFsID0gMDsKCXVuc2lnbmVkIGxvbmcgZmxhZ3M7CgoJdHJhY2UoIiVwLCAlcCIsIGVwLCBkZXNjKTsKCglpZiAoZXAgPT0gTlVMTCB8fCBkZXNjID09IE5VTEwpCgkJcmV0dXJuIC1FSU5WQUw7CgoJc3Bpbl9sb2NrX2lycXNhdmUobUVwLT5sb2NrLCBmbGFncyk7CgoJLyogb25seSBpbnRlcm5hbCBTVyBzaG91bGQgZW5hYmxlIGN0cmwgZW5kcHRzICovCgoJbUVwLT5kZXNjID0gZGVzYzsKCglpZiAoIWxpc3RfZW1wdHkoJm1FcC0+cWhbbUVwLT5kaXJdLnF1ZXVlKSkKCQl3YXJuKCJlbmFibGluZyBhIG5vbi1lbXB0eSBlbmRwb2ludCEiKTsKCgltRXAtPmRpciAgPSAoZGVzYy0+YkVuZHBvaW50QWRkcmVzcyAmIFVTQl9FTkRQT0lOVF9ESVJfTUFTSykgPyBUWCA6IFJYOwoJbUVwLT5udW0gID0gIGRlc2MtPmJFbmRwb2ludEFkZHJlc3MgJiBVU0JfRU5EUE9JTlRfTlVNQkVSX01BU0s7CgltRXAtPnR5cGUgPSAgZGVzYy0+Ym1BdHRyaWJ1dGVzICYgVVNCX0VORFBPSU5UX1hGRVJUWVBFX01BU0s7CgoJbUVwLT5lcC5tYXhwYWNrZXQgPSBfX2NvbnN0YW50X2xlMTZfdG9fY3B1KGRlc2MtPndNYXhQYWNrZXRTaXplKTsKCglkaXJlY3Rpb24gPSBtRXAtPmRpcjsKCWRvIHsKCQlkYmdfZXZlbnQoX3VzYl9hZGRyKG1FcCksICJFTkFCTEUiLCAwKTsKCgkJaWYgKG1FcC0+dHlwZSA9PSBVU0JfRU5EUE9JTlRfWEZFUl9DT05UUk9MKQoJCQltRXAtPnFoW21FcC0+ZGlyXS5wdHItPmNhcCB8PSAgUUhfSU9TOwoJCWVsc2UgaWYgKG1FcC0+dHlwZSA9PSBVU0JfRU5EUE9JTlRfWEZFUl9JU09DKQoJCQltRXAtPnFoW21FcC0+ZGlyXS5wdHItPmNhcCAmPSB+UUhfTVVMVDsKCQllbHNlCgkJCW1FcC0+cWhbbUVwLT5kaXJdLnB0ci0+Y2FwICY9IH5RSF9aTFQ7CgoJCW1FcC0+cWhbbUVwLT5kaXJdLnB0ci0+Y2FwIHw9CgkJCShtRXAtPmVwLm1heHBhY2tldCA8PCBmZnNfbnIoUUhfTUFYX1BLVCkpICYgUUhfTUFYX1BLVDsKCQltRXAtPnFoW21FcC0+ZGlyXS5wdHItPnRkLm5leHQgfD0gVERfVEVSTUlOQVRFOyAgIC8qIG5lZWRlZD8gKi8KCgkJcmV0dmFsIHw9IGh3X2VwX2VuYWJsZShtRXAtPm51bSwgbUVwLT5kaXIsIG1FcC0+dHlwZSk7CgoJCWlmIChtRXAtPnR5cGUgPT0gVVNCX0VORFBPSU5UX1hGRVJfQ09OVFJPTCkKCQkJbUVwLT5kaXIgPSAobUVwLT5kaXIgPT0gVFgpID8gUlggOiBUWDsKCgl9IHdoaWxlIChtRXAtPmRpciAhPSBkaXJlY3Rpb24pOwoKCXNwaW5fdW5sb2NrX2lycXJlc3RvcmUobUVwLT5sb2NrLCBmbGFncyk7CglyZXR1cm4gcmV0dmFsOwp9CgovKioKICogZXBfZGlzYWJsZTogZW5kcG9pbnQgaXMgbm8gbG9uZ2VyIHVzYWJsZQogKgogKiBDaGVjayB1c2JfZXBfZGlzYWJsZSgpIGF0ICJ1c2JfZ2FkZ2V0LmgiIGZvciBkZXRhaWxzCiAqLwpzdGF0aWMgaW50IGVwX2Rpc2FibGUoc3RydWN0IHVzYl9lcCAqZXApCnsKCXN0cnVjdCBjaTEzeHh4X2VwICptRXAgPSBjb250YWluZXJfb2YoZXAsIHN0cnVjdCBjaTEzeHh4X2VwLCBlcCk7CglpbnQgZGlyZWN0aW9uLCByZXR2YWwgPSAwOwoJdW5zaWduZWQgbG9uZyBmbGFnczsKCgl0cmFjZSgiJXAiLCBlcCk7CgoJaWYgKGVwID09IE5VTEwpCgkJcmV0dXJuIC1FSU5WQUw7CgllbHNlIGlmIChtRXAtPmRlc2MgPT0gTlVMTCkKCQlyZXR1cm4gLUVCVVNZOwoKCXNwaW5fbG9ja19pcnFzYXZlKG1FcC0+bG9jaywgZmxhZ3MpOwoKCS8qIG9ubHkgaW50ZXJuYWwgU1cgc2hvdWxkIGRpc2FibGUgY3RybCBlbmRwdHMgKi8KCglkaXJlY3Rpb24gPSBtRXAtPmRpcjsKCWRvIHsKCQlkYmdfZXZlbnQoX3VzYl9hZGRyKG1FcCksICJESVNBQkxFIiwgMCk7CgoJCXJldHZhbCB8PSBfZXBfbnVrZShtRXApOwoJCXJldHZhbCB8PSBod19lcF9kaXNhYmxlKG1FcC0+bnVtLCBtRXAtPmRpcik7CgoJCWlmIChtRXAtPnR5cGUgPT0gVVNCX0VORFBPSU5UX1hGRVJfQ09OVFJPTCkKCQkJbUVwLT5kaXIgPSAobUVwLT5kaXIgPT0gVFgpID8gUlggOiBUWDsKCgl9IHdoaWxlIChtRXAtPmRpciAhPSBkaXJlY3Rpb24pOwoKCW1FcC0+ZGVzYyA9IE5VTEw7CgoJc3Bpbl91bmxvY2tfaXJxcmVzdG9yZShtRXAtPmxvY2ssIGZsYWdzKTsKCXJldHVybiByZXR2YWw7Cn0KCi8qKgogKiBlcF9hbGxvY19yZXF1ZXN0OiBhbGxvY2F0ZSBhIHJlcXVlc3Qgb2JqZWN0IHRvIHVzZSB3aXRoIHRoaXMgZW5kcG9pbnQKICoKICogQ2hlY2sgdXNiX2VwX2FsbG9jX3JlcXVlc3QoKSBhdCAidXNiX2dhZGdldC5oIiBmb3IgZGV0YWlscwogKi8Kc3RhdGljIHN0cnVjdCB1c2JfcmVxdWVzdCAqZXBfYWxsb2NfcmVxdWVzdChzdHJ1Y3QgdXNiX2VwICplcCwgZ2ZwX3QgZ2ZwX2ZsYWdzKQp7CglzdHJ1Y3QgY2kxM3h4eF9lcCAgKm1FcCAgPSBjb250YWluZXJfb2YoZXAsIHN0cnVjdCBjaTEzeHh4X2VwLCBlcCk7CglzdHJ1Y3QgY2kxM3h4eF9yZXEgKm1SZXEgPSBOVUxMOwoJdW5zaWduZWQgbG9uZyBmbGFnczsKCgl0cmFjZSgiJXAsICVpIiwgZXAsIGdmcF9mbGFncyk7CgoJaWYgKGVwID09IE5VTEwpIHsKCQllcnIoIkVJTlZBTCIpOwoJCXJldHVybiBOVUxMOwoJfQoKCXNwaW5fbG9ja19pcnFzYXZlKG1FcC0+bG9jaywgZmxhZ3MpOwoKCW1SZXEgPSBremFsbG9jKHNpemVvZihzdHJ1Y3QgY2kxM3h4eF9yZXEpLCBnZnBfZmxhZ3MpOwoJaWYgKG1SZXEgIT0gTlVMTCkgewoJCUlOSVRfTElTVF9IRUFEKCZtUmVxLT5xdWV1ZSk7CgoJCW1SZXEtPnB0ciA9IGRtYV9wb29sX2FsbG9jKG1FcC0+dGRfcG9vbCwgZ2ZwX2ZsYWdzLAoJCQkJCSAgICZtUmVxLT5kbWEpOwoJCWlmIChtUmVxLT5wdHIgPT0gTlVMTCkgewoJCQlrZnJlZShtUmVxKTsKCQkJbVJlcSA9IE5VTEw7CgkJfQoJfQoKCWRiZ19ldmVudChfdXNiX2FkZHIobUVwKSwgIkFMTE9DIiwgbVJlcSA9PSBOVUxMKTsKCglzcGluX3VubG9ja19pcnFyZXN0b3JlKG1FcC0+bG9jaywgZmxhZ3MpOwoKCXJldHVybiAobVJlcSA9PSBOVUxMKSA/IE5VTEwgOiAmbVJlcS0+cmVxOwp9CgovKioKICogZXBfZnJlZV9yZXF1ZXN0OiBmcmVlcyBhIHJlcXVlc3Qgb2JqZWN0CiAqCiAqIENoZWNrIHVzYl9lcF9mcmVlX3JlcXVlc3QoKSBhdCAidXNiX2dhZGdldC5oIiBmb3IgZGV0YWlscwogKi8Kc3RhdGljIHZvaWQgZXBfZnJlZV9yZXF1ZXN0KHN0cnVjdCB1c2JfZXAgKmVwLCBzdHJ1Y3QgdXNiX3JlcXVlc3QgKnJlcSkKewoJc3RydWN0IGNpMTN4eHhfZXAgICptRXAgID0gY29udGFpbmVyX29mKGVwLCAgc3RydWN0IGNpMTN4eHhfZXAsIGVwKTsKCXN0cnVjdCBjaTEzeHh4X3JlcSAqbVJlcSA9IGNvbnRhaW5lcl9vZihyZXEsIHN0cnVjdCBjaTEzeHh4X3JlcSwgcmVxKTsKCXVuc2lnbmVkIGxvbmcgZmxhZ3M7CgoJdHJhY2UoIiVwLCAlcCIsIGVwLCByZXEpOwoKCWlmIChlcCA9PSBOVUxMIHx8IHJlcSA9PSBOVUxMKSB7CgkJZXJyKCJFSU5WQUwiKTsKCQlyZXR1cm47Cgl9IGVsc2UgaWYgKCFsaXN0X2VtcHR5KCZtUmVxLT5xdWV1ZSkpIHsKCQllcnIoIkVCVVNZIik7CgkJcmV0dXJuOwoJfQoKCXNwaW5fbG9ja19pcnFzYXZlKG1FcC0+bG9jaywgZmxhZ3MpOwoKCWlmIChtUmVxLT5wdHIpCgkJZG1hX3Bvb2xfZnJlZShtRXAtPnRkX3Bvb2wsIG1SZXEtPnB0ciwgbVJlcS0+ZG1hKTsKCWtmcmVlKG1SZXEpOwoKCWRiZ19ldmVudChfdXNiX2FkZHIobUVwKSwgIkZSRUUiLCAwKTsKCglzcGluX3VubG9ja19pcnFyZXN0b3JlKG1FcC0+bG9jaywgZmxhZ3MpOwp9CgovKioKICogZXBfcXVldWU6IHF1ZXVlcyAoc3VibWl0cykgYW4gSS9PIHJlcXVlc3QgdG8gYW4gZW5kcG9pbnQKICoKICogQ2hlY2sgdXNiX2VwX3F1ZXVlKCkqIGF0IHVzYl9nYWRnZXQuaCIgZm9yIGRldGFpbHMKICovCnN0YXRpYyBpbnQgZXBfcXVldWUoc3RydWN0IHVzYl9lcCAqZXAsIHN0cnVjdCB1c2JfcmVxdWVzdCAqcmVxLAoJCSAgICBnZnBfdCBfX21heWJlX3VudXNlZCBnZnBfZmxhZ3MpCnsKCXN0cnVjdCBjaTEzeHh4X2VwICAqbUVwICA9IGNvbnRhaW5lcl9vZihlcCwgIHN0cnVjdCBjaTEzeHh4X2VwLCBlcCk7CglzdHJ1Y3QgY2kxM3h4eF9yZXEgKm1SZXEgPSBjb250YWluZXJfb2YocmVxLCBzdHJ1Y3QgY2kxM3h4eF9yZXEsIHJlcSk7CglpbnQgcmV0dmFsID0gMDsKCXVuc2lnbmVkIGxvbmcgZmxhZ3M7CgoJdHJhY2UoIiVwLCAlcCwgJVgiLCBlcCwgcmVxLCBnZnBfZmxhZ3MpOwoKCWlmIChlcCA9PSBOVUxMIHx8IHJlcSA9PSBOVUxMIHx8IG1FcC0+ZGVzYyA9PSBOVUxMKQoJCXJldHVybiAtRUlOVkFMOwoKCXNwaW5fbG9ja19pcnFzYXZlKG1FcC0+bG9jaywgZmxhZ3MpOwoKCWlmIChtRXAtPnR5cGUgPT0gVVNCX0VORFBPSU5UX1hGRVJfQ09OVFJPTCAmJgoJICAgICFsaXN0X2VtcHR5KCZtRXAtPnFoW21FcC0+ZGlyXS5xdWV1ZSkpIHsKCQlfZXBfbnVrZShtRXApOwoJCXJldHZhbCA9IC1FT1ZFUkZMT1c7CgkJd2FybigiZW5kcG9pbnQgY3RybCAlWCBudWtlZCIsIF91c2JfYWRkcihtRXApKTsKCX0KCgkvKiBmaXJzdCBudWtlIHRoZW4gdGVzdCBsaW5rLCBlLmcuIHByZXZpb3VzIHN0YXR1cyBoYXMgbm90IHNlbnQgKi8KCWlmICghbGlzdF9lbXB0eSgmbVJlcS0+cXVldWUpKSB7CgkJcmV0dmFsID0gLUVCVVNZOwoJCWVycigicmVxdWVzdCBhbHJlYWR5IGluIHF1ZXVlIik7CgkJZ290byBkb25lOwoJfQoKCWlmIChyZXEtPmxlbmd0aCA+ICg0ICogUEFHRV9TSVpFKSkgewoJCXJlcS0+bGVuZ3RoID0gKDQgKiBQQUdFX1NJWkUpOwoJCXJldHZhbCA9IC1FTVNHU0laRTsKCQl3YXJuKCJyZXF1ZXN0IGxlbmd0aCB0cnVuY2F0ZWQiKTsKCX0KCglkYmdfcXVldWUoX3VzYl9hZGRyKG1FcCksIHJlcSwgcmV0dmFsKTsKCgkvKiBwdXNoIHJlcXVlc3QgKi8KCW1SZXEtPnJlcS5zdGF0dXMgPSAtRUlOUFJPR1JFU1M7CgltUmVxLT5yZXEuYWN0dWFsID0gMDsKCWxpc3RfYWRkX3RhaWwoJm1SZXEtPnF1ZXVlLCAmbUVwLT5xaFttRXAtPmRpcl0ucXVldWUpOwoKCXJldHZhbCA9IF9oYXJkd2FyZV9lbnF1ZXVlKG1FcCwgbVJlcSk7CglpZiAocmV0dmFsID09IC1FQUxSRUFEWSB8fCByZXR2YWwgPT0gLUVCVVNZKSB7CgkJZGJnX2V2ZW50KF91c2JfYWRkcihtRXApLCAiUVVFVUUiLCByZXR2YWwpOwoJCXJldHZhbCA9IDA7Cgl9CgogZG9uZToKCXNwaW5fdW5sb2NrX2lycXJlc3RvcmUobUVwLT5sb2NrLCBmbGFncyk7CglyZXR1cm4gcmV0dmFsOwp9CgovKioKICogZXBfZGVxdWV1ZTogZGVxdWV1ZXMgKGNhbmNlbHMsIHVubGlua3MpIGFuIEkvTyByZXF1ZXN0IGZyb20gYW4gZW5kcG9pbnQKICoKICogQ2hlY2sgdXNiX2VwX2RlcXVldWUoKSBhdCAidXNiX2dhZGdldC5oIiBmb3IgZGV0YWlscwogKi8Kc3RhdGljIGludCBlcF9kZXF1ZXVlKHN0cnVjdCB1c2JfZXAgKmVwLCBzdHJ1Y3QgdXNiX3JlcXVlc3QgKnJlcSkKewoJc3RydWN0IGNpMTN4eHhfZXAgICptRXAgID0gY29udGFpbmVyX29mKGVwLCAgc3RydWN0IGNpMTN4eHhfZXAsIGVwKTsKCXN0cnVjdCBjaTEzeHh4X3JlcSAqbVJlcSA9IGNvbnRhaW5lcl9vZihyZXEsIHN0cnVjdCBjaTEzeHh4X3JlcSwgcmVxKTsKCXVuc2lnbmVkIGxvbmcgZmxhZ3M7CgoJdHJhY2UoIiVwLCAlcCIsIGVwLCByZXEpOwoKCWlmIChlcCA9PSBOVUxMIHx8IHJlcSA9PSBOVUxMIHx8IG1FcC0+ZGVzYyA9PSBOVUxMIHx8CgkgICAgbGlzdF9lbXB0eSgmbVJlcS0+cXVldWUpICB8fCBsaXN0X2VtcHR5KCZtRXAtPnFoW21FcC0+ZGlyXS5xdWV1ZSkpCgkJcmV0dXJuIC1FSU5WQUw7CgoJc3Bpbl9sb2NrX2lycXNhdmUobUVwLT5sb2NrLCBmbGFncyk7CgoJZGJnX2V2ZW50KF91c2JfYWRkcihtRXApLCAiREVRVUVVRSIsIDApOwoKCWlmIChtUmVxLT5yZXEuc3RhdHVzID09IC1FQUxSRUFEWSkKCQlfaGFyZHdhcmVfZGVxdWV1ZShtRXAsIG1SZXEpOwoKCS8qIHBvcCByZXF1ZXN0ICovCglsaXN0X2RlbF9pbml0KCZtUmVxLT5xdWV1ZSk7CglyZXEtPnN0YXR1cyA9IC1FQ09OTlJFU0VUOwoKCWlmICghbVJlcS0+cmVxLm5vX2ludGVycnVwdCAmJiBtUmVxLT5yZXEuY29tcGxldGUgIT0gTlVMTCkgewoJCXNwaW5fdW5sb2NrKG1FcC0+bG9jayk7CgkJbVJlcS0+cmVxLmNvbXBsZXRlKCZtRXAtPmVwLCAmbVJlcS0+cmVxKTsKCQlzcGluX2xvY2sobUVwLT5sb2NrKTsKCX0KCglzcGluX3VubG9ja19pcnFyZXN0b3JlKG1FcC0+bG9jaywgZmxhZ3MpOwoJcmV0dXJuIDA7Cn0KCi8qKgogKiBlcF9zZXRfaGFsdDogc2V0cyB0aGUgZW5kcG9pbnQgaGFsdCBmZWF0dXJlCiAqCiAqIENoZWNrIHVzYl9lcF9zZXRfaGFsdCgpIGF0ICJ1c2JfZ2FkZ2V0LmgiIGZvciBkZXRhaWxzCiAqLwpzdGF0aWMgaW50IGVwX3NldF9oYWx0KHN0cnVjdCB1c2JfZXAgKmVwLCBpbnQgdmFsdWUpCnsKCXN0cnVjdCBjaTEzeHh4X2VwICptRXAgPSBjb250YWluZXJfb2YoZXAsIHN0cnVjdCBjaTEzeHh4X2VwLCBlcCk7CglpbnQgZGlyZWN0aW9uLCByZXR2YWwgPSAwOwoJdW5zaWduZWQgbG9uZyBmbGFnczsKCgl0cmFjZSgiJXAsICVpIiwgZXAsIHZhbHVlKTsKCglpZiAoZXAgPT0gTlVMTCB8fCBtRXAtPmRlc2MgPT0gTlVMTCkKCQlyZXR1cm4gLUVJTlZBTDsKCglzcGluX2xvY2tfaXJxc2F2ZShtRXAtPmxvY2ssIGZsYWdzKTsKCiNpZm5kZWYgU1RBTExfSU4KCS8qIGdfZmlsZV9zdG9yYWdlIE1TIGNvbXBsaWFudCBidXQgZ196ZXJvIGZhaWxzIGNoYXB0ZXIgOSBjb21wbGlhbmNlICovCglpZiAodmFsdWUgJiYgbUVwLT50eXBlID09IFVTQl9FTkRQT0lOVF9YRkVSX0JVTEsgJiYgbUVwLT5kaXIgPT0gVFggJiYKCSAgICAhbGlzdF9lbXB0eSgmbUVwLT5xaFttRXAtPmRpcl0ucXVldWUpKSB7CgkJc3Bpbl91bmxvY2tfaXJxcmVzdG9yZShtRXAtPmxvY2ssIGZsYWdzKTsKCQlyZXR1cm4gLUVBR0FJTjsKCX0KI2VuZGlmCgoJZGlyZWN0aW9uID0gbUVwLT5kaXI7CglkbyB7CgkJZGJnX2V2ZW50KF91c2JfYWRkcihtRXApLCAiSEFMVCIsIHZhbHVlKTsKCQlyZXR2YWwgfD0gaHdfZXBfc2V0X2hhbHQobUVwLT5udW0sIG1FcC0+ZGlyLCB2YWx1ZSk7CgoJCWlmICghdmFsdWUpCgkJCW1FcC0+d2VkZ2UgPSAwOwoKCQlpZiAobUVwLT50eXBlID09IFVTQl9FTkRQT0lOVF9YRkVSX0NPTlRST0wpCgkJCW1FcC0+ZGlyID0gKG1FcC0+ZGlyID09IFRYKSA/IFJYIDogVFg7CgoJfSB3aGlsZSAobUVwLT5kaXIgIT0gZGlyZWN0aW9uKTsKCglzcGluX3VubG9ja19pcnFyZXN0b3JlKG1FcC0+bG9jaywgZmxhZ3MpOwoJcmV0dXJuIHJldHZhbDsKfQoKLyoqCiAqIGVwX3NldF93ZWRnZTogc2V0cyB0aGUgaGFsdCBmZWF0dXJlIGFuZCBpZ25vcmVzIGNsZWFyIHJlcXVlc3RzCiAqCiAqIENoZWNrIHVzYl9lcF9zZXRfd2VkZ2UoKSBhdCAidXNiX2dhZGdldC5oIiBmb3IgZGV0YWlscwogKi8Kc3RhdGljIGludCBlcF9zZXRfd2VkZ2Uoc3RydWN0IHVzYl9lcCAqZXApCnsKCXN0cnVjdCBjaTEzeHh4X2VwICptRXAgPSBjb250YWluZXJfb2YoZXAsIHN0cnVjdCBjaTEzeHh4X2VwLCBlcCk7Cgl1bnNpZ25lZCBsb25nIGZsYWdzOwoKCXRyYWNlKCIlcCIsIGVwKTsKCglpZiAoZXAgPT0gTlVMTCB8fCBtRXAtPmRlc2MgPT0gTlVMTCkKCQlyZXR1cm4gLUVJTlZBTDsKCglzcGluX2xvY2tfaXJxc2F2ZShtRXAtPmxvY2ssIGZsYWdzKTsKCglkYmdfZXZlbnQoX3VzYl9hZGRyKG1FcCksICJXRURHRSIsIDApOwoJbUVwLT53ZWRnZSA9IDE7CgoJc3Bpbl91bmxvY2tfaXJxcmVzdG9yZShtRXAtPmxvY2ssIGZsYWdzKTsKCglyZXR1cm4gdXNiX2VwX3NldF9oYWx0KGVwKTsKfQoKLyoqCiAqIGVwX2ZpZm9fZmx1c2g6IGZsdXNoZXMgY29udGVudHMgb2YgYSBmaWZvCiAqCiAqIENoZWNrIHVzYl9lcF9maWZvX2ZsdXNoKCkgYXQgInVzYl9nYWRnZXQuaCIgZm9yIGRldGFpbHMKICovCnN0YXRpYyB2b2lkIGVwX2ZpZm9fZmx1c2goc3RydWN0IHVzYl9lcCAqZXApCnsKCXN0cnVjdCBjaTEzeHh4X2VwICptRXAgPSBjb250YWluZXJfb2YoZXAsIHN0cnVjdCBjaTEzeHh4X2VwLCBlcCk7Cgl1bnNpZ25lZCBsb25nIGZsYWdzOwoKCXRyYWNlKCIlcCIsIGVwKTsKCglpZiAoZXAgPT0gTlVMTCkgewoJCWVycigiJTAyWDogLUVJTlZBTCIsIF91c2JfYWRkcihtRXApKTsKCQlyZXR1cm47Cgl9CgoJc3Bpbl9sb2NrX2lycXNhdmUobUVwLT5sb2NrLCBmbGFncyk7CgoJZGJnX2V2ZW50KF91c2JfYWRkcihtRXApLCAiRkZMVVNIIiwgMCk7Cglod19lcF9mbHVzaChtRXAtPm51bSwgbUVwLT5kaXIpOwoKCXNwaW5fdW5sb2NrX2lycXJlc3RvcmUobUVwLT5sb2NrLCBmbGFncyk7Cn0KCi8qKgogKiBFbmRwb2ludC1zcGVjaWZpYyBwYXJ0IG9mIHRoZSBBUEkgdG8gdGhlIFVTQiBjb250cm9sbGVyIGhhcmR3YXJlCiAqIENoZWNrICJ1c2JfZ2FkZ2V0LmgiIGZvciBkZXRhaWxzCiAqLwpzdGF0aWMgY29uc3Qgc3RydWN0IHVzYl9lcF9vcHMgdXNiX2VwX29wcyA9IHsKCS5lbmFibGUJICAgICAgID0gZXBfZW5hYmxlLAoJLmRpc2FibGUgICAgICAgPSBlcF9kaXNhYmxlLAoJLmFsbG9jX3JlcXVlc3QgPSBlcF9hbGxvY19yZXF1ZXN0LAoJLmZyZWVfcmVxdWVzdCAgPSBlcF9mcmVlX3JlcXVlc3QsCgkucXVldWUJICAgICAgID0gZXBfcXVldWUsCgkuZGVxdWV1ZSAgICAgICA9IGVwX2RlcXVldWUsCgkuc2V0X2hhbHQgICAgICA9IGVwX3NldF9oYWx0LAoJLnNldF93ZWRnZSAgICAgPSBlcF9zZXRfd2VkZ2UsCgkuZmlmb19mbHVzaCAgICA9IGVwX2ZpZm9fZmx1c2gsCn07CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIEdBREdFVCBibG9jawogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCi8qKgogKiBEZXZpY2Ugb3BlcmF0aW9ucyBwYXJ0IG9mIHRoZSBBUEkgdG8gdGhlIFVTQiBjb250cm9sbGVyIGhhcmR3YXJlLAogKiB3aGljaCBkb24ndCBpbnZvbHZlIGVuZHBvaW50cyAob3IgaS9vKQogKiBDaGVjayAgInVzYl9nYWRnZXQuaCIgZm9yIGRldGFpbHMKICovCnN0YXRpYyBjb25zdCBzdHJ1Y3QgdXNiX2dhZGdldF9vcHMgdXNiX2dhZGdldF9vcHM7CgovKioKICogdXNiX2dhZGdldF9yZWdpc3Rlcl9kcml2ZXI6IHJlZ2lzdGVyIGEgZ2FkZ2V0IGRyaXZlcgogKgogKiBDaGVjayB1c2JfZ2FkZ2V0X3JlZ2lzdGVyX2RyaXZlcigpIGF0ICJ1c2JfZ2FkZ2V0LmgiIGZvciBkZXRhaWxzCiAqIEludGVycnVwdHMgYXJlIGVuYWJsZWQgaGVyZQogKi8KaW50IHVzYl9nYWRnZXRfcmVnaXN0ZXJfZHJpdmVyKHN0cnVjdCB1c2JfZ2FkZ2V0X2RyaXZlciAqZHJpdmVyKQp7CglzdHJ1Y3QgY2kxM3h4eCAqdWRjID0gX3VkYzsKCXVuc2lnbmVkIGxvbmcgaSwgaywgZmxhZ3M7CglpbnQgcmV0dmFsID0gLUVOT01FTTsKCgl0cmFjZSgiJXAiLCBkcml2ZXIpOwoKCWlmIChkcml2ZXIgICAgICAgICAgICAgPT0gTlVMTCB8fAoJICAgIGRyaXZlci0+YmluZCAgICAgICA9PSBOVUxMIHx8CgkgICAgZHJpdmVyLT51bmJpbmQgICAgID09IE5VTEwgfHwKCSAgICBkcml2ZXItPnNldHVwICAgICAgPT0gTlVMTCB8fAoJICAgIGRyaXZlci0+ZGlzY29ubmVjdCA9PSBOVUxMIHx8CgkgICAgZHJpdmVyLT5zdXNwZW5kICAgID09IE5VTEwgfHwKCSAgICBkcml2ZXItPnJlc3VtZSAgICAgPT0gTlVMTCkKCQlyZXR1cm4gLUVJTlZBTDsKCWVsc2UgaWYgKHVkYyAgICAgICAgID09IE5VTEwpCgkJcmV0dXJuIC1FTk9ERVY7CgllbHNlIGlmICh1ZGMtPmRyaXZlciAhPSBOVUxMKQoJCXJldHVybiAtRUJVU1k7CgoJLyogYWxsb2MgcmVzb3VyY2VzICovCgl1ZGMtPnFoX3Bvb2wgPSBkbWFfcG9vbF9jcmVhdGUoImNpMTN4eHhfcWgiLCAmdWRjLT5nYWRnZXQuZGV2LAoJCQkJICAgICAgIHNpemVvZihzdHJ1Y3QgY2kxM3h4eF9xaCksCgkJCQkgICAgICAgNjQsIFBBR0VfU0laRSk7CglpZiAodWRjLT5xaF9wb29sID09IE5VTEwpCgkJcmV0dXJuIC1FTk9NRU07CgoJdWRjLT50ZF9wb29sID0gZG1hX3Bvb2xfY3JlYXRlKCJjaTEzeHh4X3RkIiwgJnVkYy0+Z2FkZ2V0LmRldiwKCQkJCSAgICAgICBzaXplb2Yoc3RydWN0IGNpMTN4eHhfdGQpLAoJCQkJICAgICAgIDY0LCBQQUdFX1NJWkUpOwoJaWYgKHVkYy0+dGRfcG9vbCA9PSBOVUxMKSB7CgkJZG1hX3Bvb2xfZGVzdHJveSh1ZGMtPnFoX3Bvb2wpOwoJCXVkYy0+cWhfcG9vbCA9IE5VTEw7CgkJcmV0dXJuIC1FTk9NRU07Cgl9CgoJc3Bpbl9sb2NrX2lycXNhdmUodWRjLT5sb2NrLCBmbGFncyk7CgoJaW5mbygiaHdfZXBfbWF4ID0gJWQiLCBod19lcF9tYXgpOwoKCXVkYy0+ZHJpdmVyID0gZHJpdmVyOwoJdWRjLT5nYWRnZXQub3BzICAgICAgICA9IE5VTEw7Cgl1ZGMtPmdhZGdldC5kZXYuZHJpdmVyID0gTlVMTDsKCglyZXR2YWwgPSAwOwoJZm9yIChpID0gMDsgaSA8IGh3X2VwX21heDsgaSsrKSB7CgkJc3RydWN0IGNpMTN4eHhfZXAgKm1FcCA9ICZ1ZGMtPmNpMTN4eHhfZXBbaV07CgoJCXNjbnByaW50ZihtRXAtPm5hbWUsIHNpemVvZihtRXAtPm5hbWUpLCAiZXAlaSIsIChpbnQpaSk7CgoJCW1FcC0+bG9jayAgICAgICAgID0gdWRjLT5sb2NrOwoJCW1FcC0+ZGV2aWNlICAgICAgID0gJnVkYy0+Z2FkZ2V0LmRldjsKCQltRXAtPnRkX3Bvb2wgICAgICA9IHVkYy0+dGRfcG9vbDsKCgkJbUVwLT5lcC5uYW1lICAgICAgPSBtRXAtPm5hbWU7CgkJbUVwLT5lcC5vcHMgICAgICAgPSAmdXNiX2VwX29wczsKCQltRXAtPmVwLm1heHBhY2tldCA9IENUUkxfUEFZTE9BRF9NQVg7CgoJCS8qIHRoaXMgYWxsb2NhdGlvbiBjYW5ub3QgYmUgcmFuZG9tICovCgkJZm9yIChrID0gUlg7IGsgPD0gVFg7IGsrKykgewoJCQlJTklUX0xJU1RfSEVBRCgmbUVwLT5xaFtrXS5xdWV1ZSk7CgkJCW1FcC0+cWhba10ucHRyID0gZG1hX3Bvb2xfYWxsb2ModWRjLT5xaF9wb29sLAoJCQkJCQkJR0ZQX0tFUk5FTCwKCQkJCQkJCSZtRXAtPnFoW2tdLmRtYSk7CgkJCWlmIChtRXAtPnFoW2tdLnB0ciA9PSBOVUxMKQoJCQkJcmV0dmFsID0gLUVOT01FTTsKCQkJZWxzZQoJCQkJbWVtc2V0KG1FcC0+cWhba10ucHRyLCAwLAoJCQkJICAgICAgIHNpemVvZigqbUVwLT5xaFtrXS5wdHIpKTsKCQl9CgkJaWYgKGkgPT0gMCkKCQkJdWRjLT5nYWRnZXQuZXAwID0gJm1FcC0+ZXA7CgkJZWxzZQoJCQlsaXN0X2FkZF90YWlsKCZtRXAtPmVwLmVwX2xpc3QsICZ1ZGMtPmdhZGdldC5lcF9saXN0KTsKCX0KCWlmIChyZXR2YWwpCgkJZ290byBkb25lOwoKCS8qIGJpbmQgZ2FkZ2V0ICovCglkcml2ZXItPmRyaXZlci5idXMgICAgID0gTlVMTDsKCXVkYy0+Z2FkZ2V0Lm9wcyAgICAgICAgPSAmdXNiX2dhZGdldF9vcHM7Cgl1ZGMtPmdhZGdldC5kZXYuZHJpdmVyID0gJmRyaXZlci0+ZHJpdmVyOwoKCXNwaW5fdW5sb2NrX2lycXJlc3RvcmUodWRjLT5sb2NrLCBmbGFncyk7CglyZXR2YWwgPSBkcml2ZXItPmJpbmQoJnVkYy0+Z2FkZ2V0KTsgICAgICAgICAgICAgICAgLyogTUFZIFNMRUVQICovCglzcGluX2xvY2tfaXJxc2F2ZSh1ZGMtPmxvY2ssIGZsYWdzKTsKCglpZiAocmV0dmFsKSB7CgkJdWRjLT5nYWRnZXQub3BzICAgICAgICA9IE5VTEw7CgkJdWRjLT5nYWRnZXQuZGV2LmRyaXZlciA9IE5VTEw7CgkJZ290byBkb25lOwoJfQoKCXJldHZhbCA9IGh3X2RldmljZV9zdGF0ZSh1ZGMtPmNpMTN4eHhfZXBbMF0ucWhbUlhdLmRtYSk7CgogZG9uZToKCXNwaW5fdW5sb2NrX2lycXJlc3RvcmUodWRjLT5sb2NrLCBmbGFncyk7CglpZiAocmV0dmFsKQoJCXVzYl9nYWRnZXRfdW5yZWdpc3Rlcl9kcml2ZXIoZHJpdmVyKTsKCXJldHVybiByZXR2YWw7Cn0KRVhQT1JUX1NZTUJPTCh1c2JfZ2FkZ2V0X3JlZ2lzdGVyX2RyaXZlcik7CgovKioKICogdXNiX2dhZGdldF91bnJlZ2lzdGVyX2RyaXZlcjogdW5yZWdpc3RlciBhIGdhZGdldCBkcml2ZXIKICoKICogQ2hlY2sgdXNiX2dhZGdldF91bnJlZ2lzdGVyX2RyaXZlcigpIGF0ICJ1c2JfZ2FkZ2V0LmgiIGZvciBkZXRhaWxzCiAqLwppbnQgdXNiX2dhZGdldF91bnJlZ2lzdGVyX2RyaXZlcihzdHJ1Y3QgdXNiX2dhZGdldF9kcml2ZXIgKmRyaXZlcikKewoJc3RydWN0IGNpMTN4eHggKnVkYyA9IF91ZGM7Cgl1bnNpZ25lZCBsb25nIGksIGssIGZsYWdzOwoKCXRyYWNlKCIlcCIsIGRyaXZlcik7CgoJaWYgKGRyaXZlciAgICAgICAgICAgICA9PSBOVUxMIHx8CgkgICAgZHJpdmVyLT5iaW5kICAgICAgID09IE5VTEwgfHwKCSAgICBkcml2ZXItPnVuYmluZCAgICAgPT0gTlVMTCB8fAoJICAgIGRyaXZlci0+c2V0dXAgICAgICA9PSBOVUxMIHx8CgkgICAgZHJpdmVyLT5kaXNjb25uZWN0ID09IE5VTEwgfHwKCSAgICBkcml2ZXItPnN1c3BlbmQgICAgPT0gTlVMTCB8fAoJICAgIGRyaXZlci0+cmVzdW1lICAgICA9PSBOVUxMIHx8CgkgICAgZHJpdmVyICAgICAgICAgICAgICE9IHVkYy0+ZHJpdmVyKQoJCXJldHVybiAtRUlOVkFMOwoKCXNwaW5fbG9ja19pcnFzYXZlKHVkYy0+bG9jaywgZmxhZ3MpOwoKCWh3X2RldmljZV9zdGF0ZSgwKTsKCgkvKiB1bmJpbmQgZ2FkZ2V0ICovCglpZiAodWRjLT5nYWRnZXQub3BzICE9IE5VTEwpIHsKCQlfZ2FkZ2V0X3N0b3BfYWN0aXZpdHkoJnVkYy0+Z2FkZ2V0KTsKCgkJc3Bpbl91bmxvY2tfaXJxcmVzdG9yZSh1ZGMtPmxvY2ssIGZsYWdzKTsKCQlkcml2ZXItPnVuYmluZCgmdWRjLT5nYWRnZXQpOyAgICAgICAgICAgICAgIC8qIE1BWSBTTEVFUCAqLwoJCXNwaW5fbG9ja19pcnFzYXZlKHVkYy0+bG9jaywgZmxhZ3MpOwoKCQl1ZGMtPmdhZGdldC5vcHMgICAgICAgID0gTlVMTDsKCQl1ZGMtPmdhZGdldC5kZXYuZHJpdmVyID0gTlVMTDsKCX0KCgkvKiBmcmVlIHJlc291cmNlcyAqLwoJZm9yIChpID0gMDsgaSA8IGh3X2VwX21heDsgaSsrKSB7CgkJc3RydWN0IGNpMTN4eHhfZXAgKm1FcCA9ICZ1ZGMtPmNpMTN4eHhfZXBbaV07CgoJCWlmIChpID09IDApCgkJCXVkYy0+Z2FkZ2V0LmVwMCA9IE5VTEw7CgkJZWxzZSBpZiAoIWxpc3RfZW1wdHkoJm1FcC0+ZXAuZXBfbGlzdCkpCgkJCWxpc3RfZGVsX2luaXQoJm1FcC0+ZXAuZXBfbGlzdCk7CgoJCWZvciAoayA9IFJYOyBrIDw9IFRYOyBrKyspCgkJCWlmIChtRXAtPnFoW2tdLnB0ciAhPSBOVUxMKQoJCQkJZG1hX3Bvb2xfZnJlZSh1ZGMtPnFoX3Bvb2wsCgkJCQkJICAgICAgbUVwLT5xaFtrXS5wdHIsIG1FcC0+cWhba10uZG1hKTsKCX0KCgl1ZGMtPmRyaXZlciA9IE5VTEw7CgoJc3Bpbl91bmxvY2tfaXJxcmVzdG9yZSh1ZGMtPmxvY2ssIGZsYWdzKTsKCglpZiAodWRjLT50ZF9wb29sICE9IE5VTEwpIHsKCQlkbWFfcG9vbF9kZXN0cm95KHVkYy0+dGRfcG9vbCk7CgkJdWRjLT50ZF9wb29sID0gTlVMTDsKCX0KCWlmICh1ZGMtPnFoX3Bvb2wgIT0gTlVMTCkgewoJCWRtYV9wb29sX2Rlc3Ryb3kodWRjLT5xaF9wb29sKTsKCQl1ZGMtPnFoX3Bvb2wgPSBOVUxMOwoJfQoKCXJldHVybiAwOwp9CkVYUE9SVF9TWU1CT0wodXNiX2dhZGdldF91bnJlZ2lzdGVyX2RyaXZlcik7CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIEJVUyBibG9jawogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCi8qKgogKiB1ZGNfaXJxOiBnbG9iYWwgaW50ZXJydXB0IGhhbmRsZXIKICoKICogVGhpcyBmdW5jdGlvbiByZXR1cm5zIElSUV9IQU5ETEVEIGlmIHRoZSBJUlEgaGFzIGJlZW4gaGFuZGxlZAogKiBJdCBsb2NrcyBhY2Nlc3MgdG8gcmVnaXN0ZXJzCiAqLwpzdGF0aWMgaXJxcmV0dXJuX3QgdWRjX2lycSh2b2lkKQp7CglzdHJ1Y3QgY2kxM3h4eCAqdWRjID0gX3VkYzsKCWlycXJldHVybl90IHJldHZhbDsKCXUzMiBpbnRyOwoKCXRyYWNlKCk7CgoJaWYgKHVkYyA9PSBOVUxMKSB7CgkJZXJyKCJFTk9ERVYiKTsKCQlyZXR1cm4gSVJRX0hBTkRMRUQ7Cgl9CgoJc3Bpbl9sb2NrKHVkYy0+bG9jayk7CglpbnRyID0gaHdfdGVzdF9hbmRfY2xlYXJfaW50cl9hY3RpdmUoKTsKCWlmIChpbnRyKSB7CgkJaXNyX3N0YXRpc3RpY3MuaG5kbC5idWZbaXNyX3N0YXRpc3RpY3MuaG5kbC5pZHgrK10gPSBpbnRyOwoJCWlzcl9zdGF0aXN0aWNzLmhuZGwuaWR4ICY9IElTUl9NQVNLOwoJCWlzcl9zdGF0aXN0aWNzLmhuZGwuY250Kys7CgoJCS8qIG9yZGVyIGRlZmluZXMgcHJpb3JpdHkgLSBkbyBOT1QgY2hhbmdlIGl0ICovCgkJaWYgKFVTQmlfVVJJICYgaW50cikgewoJCQlpc3Jfc3RhdGlzdGljcy51cmkrKzsKCQkJaXNyX3Jlc2V0X2hhbmRsZXIodWRjKTsKCQl9CgkJaWYgKFVTQmlfUENJICYgaW50cikgewoJCQlpc3Jfc3RhdGlzdGljcy5wY2krKzsKCQkJdWRjLT5nYWRnZXQuc3BlZWQgPSBod19wb3J0X2lzX2hpZ2hfc3BlZWQoKSA/CgkJCQlVU0JfU1BFRURfSElHSCA6IFVTQl9TUEVFRF9GVUxMOwoJCX0KCQlpZiAoVVNCaV9VRUkgJiBpbnRyKQoJCQlpc3Jfc3RhdGlzdGljcy51ZWkrKzsKCQlpZiAoVVNCaV9VSSAgJiBpbnRyKSB7CgkJCWlzcl9zdGF0aXN0aWNzLnVpKys7CgkJCWlzcl90cl9jb21wbGV0ZV9oYW5kbGVyKHVkYyk7CgkJfQoJCWlmIChVU0JpX1NMSSAmIGludHIpCgkJCWlzcl9zdGF0aXN0aWNzLnNsaSsrOwoJCXJldHZhbCA9IElSUV9IQU5ETEVEOwoJfSBlbHNlIHsKCQlpc3Jfc3RhdGlzdGljcy5ub25lKys7CgkJcmV0dmFsID0gSVJRX05PTkU7Cgl9CglzcGluX3VubG9jayh1ZGMtPmxvY2spOwoKCXJldHVybiByZXR2YWw7Cn0KCi8qKgogKiB1ZGNfcmVsZWFzZTogZHJpdmVyIHJlbGVhc2UgZnVuY3Rpb24KICogQGRldjogZGV2aWNlCiAqCiAqIEN1cnJlbnRseSBkb2VzIG5vdGhpbmcKICovCnN0YXRpYyB2b2lkIHVkY19yZWxlYXNlKHN0cnVjdCBkZXZpY2UgKmRldikKewoJdHJhY2UoIiVwIiwgZGV2KTsKCglpZiAoZGV2ID09IE5VTEwpCgkJZXJyKCJFSU5WQUwiKTsKfQoKLyoqCiAqIHVkY19wcm9iZTogcGFyZW50IHByb2JlIG11c3QgY2FsbCB0aGlzIHRvIGluaXRpYWxpemUgVURDCiAqIEBkZXY6ICBwYXJlbnQgZGV2aWNlCiAqIEByZWdzOiByZWdpc3RlcnMgYmFzZSBhZGRyZXNzCiAqIEBuYW1lOiBkcml2ZXIgbmFtZQogKgogKiBUaGlzIGZ1bmN0aW9uIHJldHVybnMgYW4gZXJyb3IgY29kZQogKiBObyBpbnRlcnJ1cHRzIGFjdGl2ZSwgdGhlIElSUSBoYXMgbm90IGJlZW4gcmVxdWVzdGVkIHlldAogKiBLZXJuZWwgYXNzdW1lcyAzMi1iaXQgRE1BIG9wZXJhdGlvbnMgYnkgZGVmYXVsdCwgbm8gbmVlZCB0byBkbWFfc2V0X21hc2sKICovCnN0YXRpYyBpbnQgdWRjX3Byb2JlKHN0cnVjdCBkZXZpY2UgKmRldiwgdm9pZCBfX2lvbWVtICpyZWdzLCBjb25zdCBjaGFyICpuYW1lKQp7CglzdHJ1Y3QgY2kxM3h4eCAqdWRjOwoJaW50IHJldHZhbCA9IDA7CgoJdHJhY2UoIiVwLCAlcCwgJXAiLCBkZXYsIHJlZ3MsIG5hbWUpOwoKCWlmIChkZXYgPT0gTlVMTCB8fCByZWdzID09IE5VTEwgfHwgbmFtZSA9PSBOVUxMKQoJCXJldHVybiAtRUlOVkFMOwoKCXVkYyA9IGt6YWxsb2Moc2l6ZW9mKHN0cnVjdCBjaTEzeHh4KSwgR0ZQX0tFUk5FTCk7CglpZiAodWRjID09IE5VTEwpCgkJcmV0dXJuIC1FTk9NRU07CgoJdWRjLT5sb2NrID0gJnVkY19sb2NrOwoKCXJldHZhbCA9IGh3X2RldmljZV9yZXNldChyZWdzKTsKCWlmIChyZXR2YWwpCgkJZ290byBkb25lOwoKCXVkYy0+Z2FkZ2V0Lm9wcyAgICAgICAgICA9IE5VTEw7Cgl1ZGMtPmdhZGdldC5zcGVlZCAgICAgICAgPSBVU0JfU1BFRURfVU5LTk9XTjsKCXVkYy0+Z2FkZ2V0LmlzX2R1YWxzcGVlZCA9IDE7Cgl1ZGMtPmdhZGdldC5pc19vdGcgICAgICAgPSAwOwoJdWRjLT5nYWRnZXQubmFtZSAgICAgICAgID0gbmFtZTsKCglJTklUX0xJU1RfSEVBRCgmdWRjLT5nYWRnZXQuZXBfbGlzdCk7Cgl1ZGMtPmdhZGdldC5lcDAgPSBOVUxMOwoKCXN0cmNweSh1ZGMtPmdhZGdldC5kZXYuYnVzX2lkLCAiZ2FkZ2V0Iik7Cgl1ZGMtPmdhZGdldC5kZXYuZG1hX21hc2sgPSBkZXYtPmRtYV9tYXNrOwoJdWRjLT5nYWRnZXQuZGV2LnBhcmVudCAgID0gZGV2OwoJdWRjLT5nYWRnZXQuZGV2LnJlbGVhc2UgID0gdWRjX3JlbGVhc2U7CgoJcmV0dmFsID0gZGV2aWNlX3JlZ2lzdGVyKCZ1ZGMtPmdhZGdldC5kZXYpOwoJaWYgKHJldHZhbCkKCQlnb3RvIGRvbmU7CgojaWZkZWYgQ09ORklHX1VTQl9HQURHRVRfREVCVUdfRklMRVMKCXJldHZhbCA9IGRiZ19jcmVhdGVfZmlsZXMoJnVkYy0+Z2FkZ2V0LmRldik7CiNlbmRpZgoJaWYgKHJldHZhbCkgewoJCWRldmljZV91bnJlZ2lzdGVyKCZ1ZGMtPmdhZGdldC5kZXYpOwoJCWdvdG8gZG9uZTsKCX0KCglfdWRjID0gdWRjOwoJcmV0dXJuIHJldHZhbDsKCiBkb25lOgoJZXJyKCJlcnJvciA9ICVpIiwgcmV0dmFsKTsKCWtmcmVlKHVkYyk7CglfdWRjID0gTlVMTDsKCXJldHVybiByZXR2YWw7Cn0KCi8qKgogKiB1ZGNfcmVtb3ZlOiBwYXJlbnQgcmVtb3ZlIG11c3QgY2FsbCB0aGlzIHRvIHJlbW92ZSBVREMKICoKICogTm8gaW50ZXJydXB0cyBhY3RpdmUsIHRoZSBJUlEgaGFzIGJlZW4gcmVsZWFzZWQKICovCnN0YXRpYyB2b2lkIHVkY19yZW1vdmUodm9pZCkKewoJc3RydWN0IGNpMTN4eHggKnVkYyA9IF91ZGM7CgoJaWYgKHVkYyA9PSBOVUxMKSB7CgkJZXJyKCJFSU5WQUwiKTsKCQlyZXR1cm47Cgl9CgojaWZkZWYgQ09ORklHX1VTQl9HQURHRVRfREVCVUdfRklMRVMKCWRiZ19yZW1vdmVfZmlsZXMoJnVkYy0+Z2FkZ2V0LmRldik7CiNlbmRpZgoJZGV2aWNlX3VucmVnaXN0ZXIoJnVkYy0+Z2FkZ2V0LmRldik7CgoJa2ZyZWUodWRjKTsKCV91ZGMgPSBOVUxMOwp9CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIFBDSSBibG9jawogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCi8qKgogKiBjaTEzeHh4X3BjaV9pcnE6IGludGVycnV0IGhhbmRsZXIKICogQGlycTogIGlycSBudW1iZXIKICogQHBkZXY6IFVTQiBEZXZpY2UgQ29udHJvbGxlciBpbnRlcnJ1cHQgc291cmNlCiAqCiAqIFRoaXMgZnVuY3Rpb24gcmV0dXJucyBJUlFfSEFORExFRCBpZiB0aGUgSVJRIGhhcyBiZWVuIGhhbmRsZWQKICogVGhpcyBpcyBhbiBJU1IgZG9uJ3QgdHJhY2UsIHVzZSBhdHRyaWJ1dGUgaW50ZXJmYWNlIGluc3RlYWQKICovCnN0YXRpYyBpcnFyZXR1cm5fdCBjaTEzeHh4X3BjaV9pcnEoaW50IGlycSwgdm9pZCAqcGRldikKewoJaWYgKGlycSA9PSAwKSB7CgkJZGV2X2VycigmKChzdHJ1Y3QgcGNpX2RldiAqKXBkZXYpLT5kZXYsICJJbnZhbGlkIElSUTAgdXNhZ2UhIik7CgkJcmV0dXJuIElSUV9IQU5ETEVEOwoJfQoJcmV0dXJuIHVkY19pcnEoKTsKfQoKLyoqCiAqIGNpMTN4eHhfcGNpX3Byb2JlOiBQQ0kgcHJvYmUKICogQHBkZXY6IFVTQiBkZXZpY2UgY29udHJvbGxlciBiZWluZyBwcm9iZWQKICogQGlkOiAgIFBDSSBob3RwbHVnIElEIGNvbm5lY3RpbmcgY29udHJvbGxlciB0byBVREMgZnJhbWV3b3JrCiAqCiAqIFRoaXMgZnVuY3Rpb24gcmV0dXJucyBhbiBlcnJvciBjb2RlCiAqIEFsbG9jYXRlcyBiYXNpYyBQQ0kgcmVzb3VyY2VzIGZvciB0aGlzIFVTQiBkZXZpY2UgY29udHJvbGxlciwgYW5kIHRoZW4KICogaW52b2tlcyB0aGUgdWRjX3Byb2JlKCkgbWV0aG9kIHRvIHN0YXJ0IHRoZSBVREMgYXNzb2NpYXRlZCB3aXRoIGl0CiAqLwpzdGF0aWMgaW50IF9fZGV2aW5pdCBjaTEzeHh4X3BjaV9wcm9iZShzdHJ1Y3QgcGNpX2RldiAqcGRldiwKCQkJCSAgICAgICBjb25zdCBzdHJ1Y3QgcGNpX2RldmljZV9pZCAqaWQpCnsKCXZvaWQgX19pb21lbSAqcmVncyA9IE5VTEw7CglpbnQgcmV0dmFsID0gMDsKCglpZiAoaWQgPT0gTlVMTCkKCQlyZXR1cm4gLUVJTlZBTDsKCglyZXR2YWwgPSBwY2lfZW5hYmxlX2RldmljZShwZGV2KTsKCWlmIChyZXR2YWwpCgkJZ290byBkb25lOwoKCWlmICghcGRldi0+aXJxKSB7CgkJZGV2X2VycigmcGRldi0+ZGV2LCAiTm8gSVJRLCBjaGVjayBCSU9TL1BDSSBzZXR1cCEiKTsKCQlyZXR2YWwgPSAtRU5PREVWOwoJCWdvdG8gZGlzYWJsZV9kZXZpY2U7Cgl9CgoJcmV0dmFsID0gcGNpX3JlcXVlc3RfcmVnaW9ucyhwZGV2LCBVRENfRFJJVkVSX05BTUUpOwoJaWYgKHJldHZhbCkKCQlnb3RvIGRpc2FibGVfZGV2aWNlOwoKCS8qIEJBUiAwIGhvbGRzIGFsbCB0aGUgcmVnaXN0ZXJzICovCglyZWdzID0gcGNpX2lvbWFwKHBkZXYsIDAsIDApOwoJaWYgKCFyZWdzKSB7CgkJZGV2X2VycigmcGRldi0+ZGV2LCAiRXJyb3IgbWFwcGluZyBtZW1vcnkhIik7CgkJcmV0dmFsID0gLUVGQVVMVDsKCQlnb3RvIHJlbGVhc2VfcmVnaW9uczsKCX0KCXBjaV9zZXRfZHJ2ZGF0YShwZGV2LCAoX19mb3JjZSB2b2lkICopcmVncyk7CgoJcGNpX3NldF9tYXN0ZXIocGRldik7CglwY2lfdHJ5X3NldF9td2kocGRldik7CgoJcmV0dmFsID0gdWRjX3Byb2JlKCZwZGV2LT5kZXYsIHJlZ3MsIFVEQ19EUklWRVJfTkFNRSk7CglpZiAocmV0dmFsKQoJCWdvdG8gaW91bm1hcDsKCgkvKiBvdXIgZGV2aWNlIGRvZXMgbm90IGhhdmUgTVNJIGNhcGFiaWxpdHkgKi8KCglyZXR2YWwgPSByZXF1ZXN0X2lycShwZGV2LT5pcnEsIGNpMTN4eHhfcGNpX2lycSwgSVJRRl9TSEFSRUQsCgkJCSAgICAgVURDX0RSSVZFUl9OQU1FLCBwZGV2KTsKCWlmIChyZXR2YWwpCgkJZ290byBnYWRnZXRfcmVtb3ZlOwoKCXJldHVybiAwOwoKIGdhZGdldF9yZW1vdmU6Cgl1ZGNfcmVtb3ZlKCk7CiBpb3VubWFwOgoJcGNpX2lvdW5tYXAocGRldiwgcmVncyk7CiByZWxlYXNlX3JlZ2lvbnM6CglwY2lfcmVsZWFzZV9yZWdpb25zKHBkZXYpOwogZGlzYWJsZV9kZXZpY2U6CglwY2lfZGlzYWJsZV9kZXZpY2UocGRldik7CiBkb25lOgoJcmV0dXJuIHJldHZhbDsKfQoKLyoqCiAqIGNpMTN4eHhfcGNpX3JlbW92ZTogUENJIHJlbW92ZQogKiBAcGRldjogVVNCIERldmljZSBDb250cm9sbGVyIGJlaW5nIHJlbW92ZWQKICoKICogUmV2ZXJzZXMgdGhlIGVmZmVjdCBvZiBjaTEzeHh4X3BjaV9wcm9iZSgpLAogKiBmaXJzdCBpbnZva2luZyB0aGUgdWRjX3JlbW92ZSgpIGFuZCB0aGVuIHJlbGVhc2VzCiAqIGFsbCBQQ0kgcmVzb3VyY2VzIGFsbG9jYXRlZCBmb3IgdGhpcyBVU0IgZGV2aWNlIGNvbnRyb2xsZXIKICovCnN0YXRpYyB2b2lkIF9fZGV2ZXhpdCBjaTEzeHh4X3BjaV9yZW1vdmUoc3RydWN0IHBjaV9kZXYgKnBkZXYpCnsKCWZyZWVfaXJxKHBkZXYtPmlycSwgcGRldik7Cgl1ZGNfcmVtb3ZlKCk7CglwY2lfaW91bm1hcChwZGV2LCAoX19mb3JjZSB2b2lkIF9faW9tZW0gKilwY2lfZ2V0X2RydmRhdGEocGRldikpOwoJcGNpX3JlbGVhc2VfcmVnaW9ucyhwZGV2KTsKCXBjaV9kaXNhYmxlX2RldmljZShwZGV2KTsKfQoKLyoqCiAqIFBDSSBkZXZpY2UgdGFibGUKICogUENJIGRldmljZSBzdHJ1Y3R1cmUKICoKICogQ2hlY2sgInBjaS5oIiBmb3IgZGV0YWlscwogKi8Kc3RhdGljIERFRklORV9QQ0lfREVWSUNFX1RBQkxFKGNpMTN4eHhfcGNpX2lkX3RhYmxlKSA9IHsKCXsgUENJX0RFVklDRSgweDE1M0YsIDB4MTAwNCkgfSwKCXsgUENJX0RFVklDRSgweDE1M0YsIDB4MTAwNikgfSwKCXsgMCwgMCwgMCwgMCwgMCwgMCwgMCAvKiBlbmQ6IGFsbCB6ZXJvZXMgKi8gfQp9OwpNT0RVTEVfREVWSUNFX1RBQkxFKHBjaSwgY2kxM3h4eF9wY2lfaWRfdGFibGUpOwoKc3RhdGljIHN0cnVjdCBwY2lfZHJpdmVyIGNpMTN4eHhfcGNpX2RyaXZlciA9IHsKCS5uYW1lICAgICAgICAgPQlVRENfRFJJVkVSX05BTUUsCgkuaWRfdGFibGUgICAgID0JY2kxM3h4eF9wY2lfaWRfdGFibGUsCgkucHJvYmUgICAgICAgID0JY2kxM3h4eF9wY2lfcHJvYmUsCgkucmVtb3ZlICAgICAgID0JX19kZXZleGl0X3AoY2kxM3h4eF9wY2lfcmVtb3ZlKSwKfTsKCi8qKgogKiBjaTEzeHh4X3BjaV9pbml0OiBtb2R1bGUgaW5pdAogKgogKiBEcml2ZXIgbG9hZAogKi8Kc3RhdGljIGludCBfX2luaXQgY2kxM3h4eF9wY2lfaW5pdCh2b2lkKQp7CglyZXR1cm4gcGNpX3JlZ2lzdGVyX2RyaXZlcigmY2kxM3h4eF9wY2lfZHJpdmVyKTsKfQptb2R1bGVfaW5pdChjaTEzeHh4X3BjaV9pbml0KTsKCi8qKgogKiBjaTEzeHh4X3BjaV9leGl0OiBtb2R1bGUgZXhpdAogKgogKiBEcml2ZXIgdW5sb2FkCiAqLwpzdGF0aWMgdm9pZCBfX2V4aXQgY2kxM3h4eF9wY2lfZXhpdCh2b2lkKQp7CglwY2lfdW5yZWdpc3Rlcl9kcml2ZXIoJmNpMTN4eHhfcGNpX2RyaXZlcik7Cn0KbW9kdWxlX2V4aXQoY2kxM3h4eF9wY2lfZXhpdCk7CgpNT0RVTEVfQVVUSE9SKCJNSVBTIC0gRGF2aWQgTG9wbyA8ZGxvcG9AY2hpcGlkZWEubWlwcy5jb20+Iik7Ck1PRFVMRV9ERVNDUklQVElPTigiTUlQUyBDSTEzWFhYIFVTQiBQZXJpcGhlcmFsIENvbnRyb2xsZXIiKTsKTU9EVUxFX0xJQ0VOU0UoIkdQTCIpOwpNT0RVTEVfVkVSU0lPTigiSnVuZSAyMDA4Iik7Cg==