LyogaTJjLWNvcmUuYyAtIGEgZGV2aWNlIGRyaXZlciBmb3IgdGhlIGlpYy1idXMgaW50ZXJmYWNlCQkgICAgICovCi8qIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0gKi8KLyogICBDb3B5cmlnaHQgKEMpIDE5OTUtOTkgU2ltb24gRy4gVm9nbAoKICAgIFRoaXMgcHJvZ3JhbSBpcyBmcmVlIHNvZnR3YXJlOyB5b3UgY2FuIHJlZGlzdHJpYnV0ZSBpdCBhbmQvb3IgbW9kaWZ5CiAgICBpdCB1bmRlciB0aGUgdGVybXMgb2YgdGhlIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlIGFzIHB1Ymxpc2hlZCBieQogICAgdGhlIEZyZWUgU29mdHdhcmUgRm91bmRhdGlvbjsgZWl0aGVyIHZlcnNpb24gMiBvZiB0aGUgTGljZW5zZSwgb3IKICAgIChhdCB5b3VyIG9wdGlvbikgYW55IGxhdGVyIHZlcnNpb24uCgogICAgVGhpcyBwcm9ncmFtIGlzIGRpc3RyaWJ1dGVkIGluIHRoZSBob3BlIHRoYXQgaXQgd2lsbCBiZSB1c2VmdWwsCiAgICBidXQgV0lUSE9VVCBBTlkgV0FSUkFOVFk7IHdpdGhvdXQgZXZlbiB0aGUgaW1wbGllZCB3YXJyYW50eSBvZgogICAgTUVSQ0hBTlRBQklMSVRZIG9yIEZJVE5FU1MgRk9SIEEgUEFSVElDVUxBUiBQVVJQT1NFLiAgU2VlIHRoZQogICAgR05VIEdlbmVyYWwgUHVibGljIExpY2Vuc2UgZm9yIG1vcmUgZGV0YWlscy4KCiAgICBZb3Ugc2hvdWxkIGhhdmUgcmVjZWl2ZWQgYSBjb3B5IG9mIHRoZSBHTlUgR2VuZXJhbCBQdWJsaWMgTGljZW5zZQogICAgYWxvbmcgd2l0aCB0aGlzIHByb2dyYW07IGlmIG5vdCwgd3JpdGUgdG8gdGhlIEZyZWUgU29mdHdhcmUKICAgIEZvdW5kYXRpb24sIEluYy4sIDY3NSBNYXNzIEF2ZSwgQ2FtYnJpZGdlLCBNQSAwMjEzOSwgVVNBLgkJICAgICAqLwovKiAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tICovCgovKiBXaXRoIHNvbWUgY2hhbmdlcyBmcm9tIEt59nN0aSBN5Gxra2kgPGttYWxra2lAY2MuaHV0LmZpPi4KICAgQWxsIFNNQnVzLXJlbGF0ZWQgdGhpbmdzIGFyZSB3cml0dGVuIGJ5IEZyb2RvIExvb2lqYWFyZCA8ZnJvZG9sQGRkcy5ubD4KICAgU01CdXMgMi4wIHN1cHBvcnQgYnkgTWFyayBTdHVkZWJha2VyIDxtZHN4eXoxMjNAeWFob28uY29tPiBhbmQKICAgSmVhbiBEZWx2YXJlIDxraGFsaUBsaW51eC1mci5vcmc+ICovCgojaW5jbHVkZSA8bGludXgvbW9kdWxlLmg+CiNpbmNsdWRlIDxsaW51eC9rZXJuZWwuaD4KI2luY2x1ZGUgPGxpbnV4L2Vycm5vLmg+CiNpbmNsdWRlIDxsaW51eC9zbGFiLmg+CiNpbmNsdWRlIDxsaW51eC9pMmMuaD4KI2luY2x1ZGUgPGxpbnV4L2luaXQuaD4KI2luY2x1ZGUgPGxpbnV4L2lkci5oPgojaW5jbHVkZSA8bGludXgvc2VxX2ZpbGUuaD4KI2luY2x1ZGUgPGxpbnV4L3BsYXRmb3JtX2RldmljZS5oPgojaW5jbHVkZSA8bGludXgvbXV0ZXguaD4KI2luY2x1ZGUgPGFzbS91YWNjZXNzLmg+CgoKc3RhdGljIExJU1RfSEVBRChhZGFwdGVycyk7CnN0YXRpYyBMSVNUX0hFQUQoZHJpdmVycyk7CnN0YXRpYyBERUZJTkVfTVVURVgoY29yZV9saXN0cyk7CnN0YXRpYyBERUZJTkVfSURSKGkyY19hZGFwdGVyX2lkcik7CgovKiBtYXRjaCBhbHdheXMgc3VjY2VlZHMsIGFzIHdlIHdhbnQgdGhlIHByb2JlKCkgdG8gdGVsbCBpZiB3ZSByZWFsbHkgYWNjZXB0IHRoaXMgbWF0Y2ggKi8Kc3RhdGljIGludCBpMmNfZGV2aWNlX21hdGNoKHN0cnVjdCBkZXZpY2UgKmRldiwgc3RydWN0IGRldmljZV9kcml2ZXIgKmRydikKewoJcmV0dXJuIDE7Cn0KCnN0YXRpYyBpbnQgaTJjX2J1c19zdXNwZW5kKHN0cnVjdCBkZXZpY2UgKiBkZXYsIHBtX21lc3NhZ2VfdCBzdGF0ZSkKewoJaW50IHJjID0gMDsKCglpZiAoZGV2LT5kcml2ZXIgJiYgZGV2LT5kcml2ZXItPnN1c3BlbmQpCgkJcmMgPSBkZXYtPmRyaXZlci0+c3VzcGVuZChkZXYsIHN0YXRlKTsKCXJldHVybiByYzsKfQoKc3RhdGljIGludCBpMmNfYnVzX3Jlc3VtZShzdHJ1Y3QgZGV2aWNlICogZGV2KQp7CglpbnQgcmMgPSAwOwoJCglpZiAoZGV2LT5kcml2ZXIgJiYgZGV2LT5kcml2ZXItPnJlc3VtZSkKCQlyYyA9IGRldi0+ZHJpdmVyLT5yZXN1bWUoZGV2KTsKCXJldHVybiByYzsKfQoKc3RhdGljIGludCBpMmNfZGV2aWNlX3Byb2JlKHN0cnVjdCBkZXZpY2UgKmRldikKewoJcmV0dXJuIC1FTk9ERVY7Cn0KCnN0YXRpYyBpbnQgaTJjX2RldmljZV9yZW1vdmUoc3RydWN0IGRldmljZSAqZGV2KQp7CglyZXR1cm4gMDsKfQoKc3RydWN0IGJ1c190eXBlIGkyY19idXNfdHlwZSA9IHsKCS5uYW1lID0JCSJpMmMiLAoJLm1hdGNoID0JaTJjX2RldmljZV9tYXRjaCwKCS5wcm9iZSA9CWkyY19kZXZpY2VfcHJvYmUsCgkucmVtb3ZlID0JaTJjX2RldmljZV9yZW1vdmUsCgkuc3VzcGVuZCA9ICAgICAgaTJjX2J1c19zdXNwZW5kLAoJLnJlc3VtZSA9ICAgICAgIGkyY19idXNfcmVzdW1lLAp9OwoKdm9pZCBpMmNfYWRhcHRlcl9kZXZfcmVsZWFzZShzdHJ1Y3QgZGV2aWNlICpkZXYpCnsKCXN0cnVjdCBpMmNfYWRhcHRlciAqYWRhcCA9IGRldl90b19pMmNfYWRhcHRlcihkZXYpOwoJY29tcGxldGUoJmFkYXAtPmRldl9yZWxlYXNlZCk7Cn0KCnN0cnVjdCBkZXZpY2VfZHJpdmVyIGkyY19hZGFwdGVyX2RyaXZlciA9IHsKCS5vd25lciA9IFRISVNfTU9EVUxFLAoJLm5hbWUgPQkiaTJjX2FkYXB0ZXIiLAoJLmJ1cyA9ICZpMmNfYnVzX3R5cGUsCn07CgpzdGF0aWMgdm9pZCBpMmNfYWRhcHRlcl9jbGFzc19kZXZfcmVsZWFzZShzdHJ1Y3QgY2xhc3NfZGV2aWNlICpkZXYpCnsKCXN0cnVjdCBpMmNfYWRhcHRlciAqYWRhcCA9IGNsYXNzX2Rldl90b19pMmNfYWRhcHRlcihkZXYpOwoJY29tcGxldGUoJmFkYXAtPmNsYXNzX2Rldl9yZWxlYXNlZCk7Cn0KCnN0cnVjdCBjbGFzcyBpMmNfYWRhcHRlcl9jbGFzcyA9IHsKCS5vd25lciA9CVRISVNfTU9EVUxFLAoJLm5hbWUgPQkJImkyYy1hZGFwdGVyIiwKCS5yZWxlYXNlID0JJmkyY19hZGFwdGVyX2NsYXNzX2Rldl9yZWxlYXNlLAp9OwoKc3RhdGljIHNzaXplX3Qgc2hvd19hZGFwdGVyX25hbWUoc3RydWN0IGRldmljZSAqZGV2LCBzdHJ1Y3QgZGV2aWNlX2F0dHJpYnV0ZSAqYXR0ciwgY2hhciAqYnVmKQp7CglzdHJ1Y3QgaTJjX2FkYXB0ZXIgKmFkYXAgPSBkZXZfdG9faTJjX2FkYXB0ZXIoZGV2KTsKCXJldHVybiBzcHJpbnRmKGJ1ZiwgIiVzXG4iLCBhZGFwLT5uYW1lKTsKfQpzdGF0aWMgREVWSUNFX0FUVFIobmFtZSwgU19JUlVHTywgc2hvd19hZGFwdGVyX25hbWUsIE5VTEwpOwoKCnN0YXRpYyB2b2lkIGkyY19jbGllbnRfcmVsZWFzZShzdHJ1Y3QgZGV2aWNlICpkZXYpCnsKCXN0cnVjdCBpMmNfY2xpZW50ICpjbGllbnQgPSB0b19pMmNfY2xpZW50KGRldik7Cgljb21wbGV0ZSgmY2xpZW50LT5yZWxlYXNlZCk7Cn0KCnN0YXRpYyBzc2l6ZV90IHNob3dfY2xpZW50X25hbWUoc3RydWN0IGRldmljZSAqZGV2LCBzdHJ1Y3QgZGV2aWNlX2F0dHJpYnV0ZSAqYXR0ciwgY2hhciAqYnVmKQp7CglzdHJ1Y3QgaTJjX2NsaWVudCAqY2xpZW50ID0gdG9faTJjX2NsaWVudChkZXYpOwoJcmV0dXJuIHNwcmludGYoYnVmLCAiJXNcbiIsIGNsaWVudC0+bmFtZSk7Cn0KCi8qIAogKiBXZSBjYW4ndCB1c2UgdGhlIERFVklDRV9BVFRSKCkgbWFjcm8gaGVyZSBhcyB3ZSB3YW50IHRoZSBzYW1lIGZpbGVuYW1lIGZvciBhCiAqIGRpZmZlcmVudCB0eXBlIG9mIGEgZGV2aWNlLiAgU28gYmV3YXJlIGlmIHRoZSBERVZJQ0VfQVRUUigpIG1hY3JvIGV2ZXIKICogY2hhbmdlcywgdGhpcyBkZWZpbml0aW9uIHdpbGwgYWxzbyBoYXZlIHRvIGNoYW5nZS4KICovCnN0YXRpYyBzdHJ1Y3QgZGV2aWNlX2F0dHJpYnV0ZSBkZXZfYXR0cl9jbGllbnRfbmFtZSA9IHsKCS5hdHRyCT0gey5uYW1lID0gIm5hbWUiLCAubW9kZSA9IFNfSVJVR08sIC5vd25lciA9IFRISVNfTU9EVUxFIH0sCgkuc2hvdwk9ICZzaG93X2NsaWVudF9uYW1lLAp9OwoKCi8qIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQogKiByZWdpc3RlcmluZyBmdW5jdGlvbnMgCiAqIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLSAKICovCgovKiAtLS0tLQogKiBpMmNfYWRkX2FkYXB0ZXIgaXMgY2FsbGVkIGZyb20gd2l0aGluIHRoZSBhbGdvcml0aG0gbGF5ZXIsCiAqIHdoZW4gYSBuZXcgaHcgYWRhcHRlciByZWdpc3RlcnMuIEEgbmV3IGRldmljZSBpcyByZWdpc3RlciB0byBiZQogKiBhdmFpbGFibGUgZm9yIGNsaWVudHMuCiAqLwppbnQgaTJjX2FkZF9hZGFwdGVyKHN0cnVjdCBpMmNfYWRhcHRlciAqYWRhcCkKewoJaW50IGlkLCByZXMgPSAwOwoJc3RydWN0IGxpc3RfaGVhZCAgICppdGVtOwoJc3RydWN0IGkyY19kcml2ZXIgICpkcml2ZXI7CgoJbXV0ZXhfbG9jaygmY29yZV9saXN0cyk7CgoJaWYgKGlkcl9wcmVfZ2V0KCZpMmNfYWRhcHRlcl9pZHIsIEdGUF9LRVJORUwpID09IDApIHsKCQlyZXMgPSAtRU5PTUVNOwoJCWdvdG8gb3V0X3VubG9jazsKCX0KCglyZXMgPSBpZHJfZ2V0X25ldygmaTJjX2FkYXB0ZXJfaWRyLCBhZGFwLCAmaWQpOwoJaWYgKHJlcyA8IDApIHsKCQlpZiAocmVzID09IC1FQUdBSU4pCgkJCXJlcyA9IC1FTk9NRU07CgkJZ290byBvdXRfdW5sb2NrOwoJfQoKCWFkYXAtPm5yID0gIGlkICYgTUFYX0lEX01BU0s7CgltdXRleF9pbml0KCZhZGFwLT5idXNfbG9jayk7CgltdXRleF9pbml0KCZhZGFwLT5jbGlzdF9sb2NrKTsKCWxpc3RfYWRkX3RhaWwoJmFkYXAtPmxpc3QsJmFkYXB0ZXJzKTsKCUlOSVRfTElTVF9IRUFEKCZhZGFwLT5jbGllbnRzKTsKCgkvKiBBZGQgdGhlIGFkYXB0ZXIgdG8gdGhlIGRyaXZlciBjb3JlLgoJICogSWYgdGhlIHBhcmVudCBwb2ludGVyIGlzIG5vdCBzZXQgdXAsCgkgKiB3ZSBhZGQgdGhpcyBhZGFwdGVyIHRvIHRoZSBob3N0IGJ1cy4KCSAqLwoJaWYgKGFkYXAtPmRldi5wYXJlbnQgPT0gTlVMTCkKCQlhZGFwLT5kZXYucGFyZW50ID0gJnBsYXRmb3JtX2J1czsKCXNwcmludGYoYWRhcC0+ZGV2LmJ1c19pZCwgImkyYy0lZCIsIGFkYXAtPm5yKTsKCWFkYXAtPmRldi5kcml2ZXIgPSAmaTJjX2FkYXB0ZXJfZHJpdmVyOwoJYWRhcC0+ZGV2LnJlbGVhc2UgPSAmaTJjX2FkYXB0ZXJfZGV2X3JlbGVhc2U7CglyZXMgPSBkZXZpY2VfcmVnaXN0ZXIoJmFkYXAtPmRldik7CglpZiAocmVzKQoJCWdvdG8gb3V0X2xpc3Q7CglyZXMgPSBkZXZpY2VfY3JlYXRlX2ZpbGUoJmFkYXAtPmRldiwgJmRldl9hdHRyX25hbWUpOwoJaWYgKHJlcykKCQlnb3RvIG91dF91bnJlZ2lzdGVyOwoKCS8qIEFkZCB0aGlzIGFkYXB0ZXIgdG8gdGhlIGkyY19hZGFwdGVyIGNsYXNzICovCgltZW1zZXQoJmFkYXAtPmNsYXNzX2RldiwgMHgwMCwgc2l6ZW9mKHN0cnVjdCBjbGFzc19kZXZpY2UpKTsKCWFkYXAtPmNsYXNzX2Rldi5kZXYgPSAmYWRhcC0+ZGV2OwoJYWRhcC0+Y2xhc3NfZGV2LmNsYXNzID0gJmkyY19hZGFwdGVyX2NsYXNzOwoJc3RybGNweShhZGFwLT5jbGFzc19kZXYuY2xhc3NfaWQsIGFkYXAtPmRldi5idXNfaWQsIEJVU19JRF9TSVpFKTsKCXJlcyA9IGNsYXNzX2RldmljZV9yZWdpc3RlcigmYWRhcC0+Y2xhc3NfZGV2KTsKCWlmIChyZXMpCgkJZ290byBvdXRfcmVtb3ZlX25hbWU7CgoJZGV2X2RiZygmYWRhcC0+ZGV2LCAiYWRhcHRlciBbJXNdIHJlZ2lzdGVyZWRcbiIsIGFkYXAtPm5hbWUpOwoKCS8qIGluZm9ybSBkcml2ZXJzIG9mIG5ldyBhZGFwdGVycyAqLwoJbGlzdF9mb3JfZWFjaChpdGVtLCZkcml2ZXJzKSB7CgkJZHJpdmVyID0gbGlzdF9lbnRyeShpdGVtLCBzdHJ1Y3QgaTJjX2RyaXZlciwgbGlzdCk7CgkJaWYgKGRyaXZlci0+YXR0YWNoX2FkYXB0ZXIpCgkJCS8qIFdlIGlnbm9yZSB0aGUgcmV0dXJuIGNvZGU7IGlmIGl0IGZhaWxzLCB0b28gYmFkICovCgkJCWRyaXZlci0+YXR0YWNoX2FkYXB0ZXIoYWRhcCk7Cgl9CgpvdXRfdW5sb2NrOgoJbXV0ZXhfdW5sb2NrKCZjb3JlX2xpc3RzKTsKCXJldHVybiByZXM7CgpvdXRfcmVtb3ZlX25hbWU6CglkZXZpY2VfcmVtb3ZlX2ZpbGUoJmFkYXAtPmRldiwgJmRldl9hdHRyX25hbWUpOwpvdXRfdW5yZWdpc3RlcjoKCWluaXRfY29tcGxldGlvbigmYWRhcC0+ZGV2X3JlbGVhc2VkKTsgLyogTmVlZGVkPyAqLwoJZGV2aWNlX3VucmVnaXN0ZXIoJmFkYXAtPmRldik7Cgl3YWl0X2Zvcl9jb21wbGV0aW9uKCZhZGFwLT5kZXZfcmVsZWFzZWQpOwpvdXRfbGlzdDoKCWxpc3RfZGVsKCZhZGFwLT5saXN0KTsKCWlkcl9yZW1vdmUoJmkyY19hZGFwdGVyX2lkciwgYWRhcC0+bnIpOwoJZ290byBvdXRfdW5sb2NrOwp9CgoKaW50IGkyY19kZWxfYWRhcHRlcihzdHJ1Y3QgaTJjX2FkYXB0ZXIgKmFkYXApCnsKCXN0cnVjdCBsaXN0X2hlYWQgICppdGVtLCAqX247CglzdHJ1Y3QgaTJjX2FkYXB0ZXIgKmFkYXBfZnJvbV9saXN0OwoJc3RydWN0IGkyY19kcml2ZXIgKmRyaXZlcjsKCXN0cnVjdCBpMmNfY2xpZW50ICpjbGllbnQ7CglpbnQgcmVzID0gMDsKCgltdXRleF9sb2NrKCZjb3JlX2xpc3RzKTsKCgkvKiBGaXJzdCBtYWtlIHN1cmUgdGhhdCB0aGlzIGFkYXB0ZXIgd2FzIGV2ZXIgYWRkZWQgKi8KCWxpc3RfZm9yX2VhY2hfZW50cnkoYWRhcF9mcm9tX2xpc3QsICZhZGFwdGVycywgbGlzdCkgewoJCWlmIChhZGFwX2Zyb21fbGlzdCA9PSBhZGFwKQoJCQlicmVhazsKCX0KCWlmIChhZGFwX2Zyb21fbGlzdCAhPSBhZGFwKSB7CgkJcHJfZGVidWcoImkyYy1jb3JlOiBhdHRlbXB0aW5nIHRvIGRlbGV0ZSB1bnJlZ2lzdGVyZWQgIgoJCQkgImFkYXB0ZXIgWyVzXVxuIiwgYWRhcC0+bmFtZSk7CgkJcmVzID0gLUVJTlZBTDsKCQlnb3RvIG91dF91bmxvY2s7Cgl9CgoJbGlzdF9mb3JfZWFjaChpdGVtLCZkcml2ZXJzKSB7CgkJZHJpdmVyID0gbGlzdF9lbnRyeShpdGVtLCBzdHJ1Y3QgaTJjX2RyaXZlciwgbGlzdCk7CgkJaWYgKGRyaXZlci0+ZGV0YWNoX2FkYXB0ZXIpCgkJCWlmICgocmVzID0gZHJpdmVyLT5kZXRhY2hfYWRhcHRlcihhZGFwKSkpIHsKCQkJCWRldl9lcnIoJmFkYXAtPmRldiwgImRldGFjaF9hZGFwdGVyIGZhaWxlZCAiCgkJCQkJImZvciBkcml2ZXIgWyVzXVxuIiwKCQkJCQlkcml2ZXItPmRyaXZlci5uYW1lKTsKCQkJCWdvdG8gb3V0X3VubG9jazsKCQkJfQoJfQoKCS8qIGRldGFjaCBhbnkgYWN0aXZlIGNsaWVudHMuIFRoaXMgbXVzdCBiZSBkb25lIGZpcnN0LCBiZWNhdXNlCgkgKiBpdCBjYW4gZmFpbDsgaW4gd2hpY2ggY2FzZSB3ZSBnaXZlIHVwLiAqLwoJbGlzdF9mb3JfZWFjaF9zYWZlKGl0ZW0sIF9uLCAmYWRhcC0+Y2xpZW50cykgewoJCWNsaWVudCA9IGxpc3RfZW50cnkoaXRlbSwgc3RydWN0IGkyY19jbGllbnQsIGxpc3QpOwoKCQlpZiAoKHJlcz1jbGllbnQtPmRyaXZlci0+ZGV0YWNoX2NsaWVudChjbGllbnQpKSkgewoJCQlkZXZfZXJyKCZhZGFwLT5kZXYsICJkZXRhY2hfY2xpZW50IGZhaWxlZCBmb3IgY2xpZW50ICIKCQkJCSJbJXNdIGF0IGFkZHJlc3MgMHglMDJ4XG4iLCBjbGllbnQtPm5hbWUsCgkJCQljbGllbnQtPmFkZHIpOwoJCQlnb3RvIG91dF91bmxvY2s7CgkJfQoJfQoKCS8qIGNsZWFuIHVwIHRoZSBzeXNmcyByZXByZXNlbnRhdGlvbiAqLwoJaW5pdF9jb21wbGV0aW9uKCZhZGFwLT5kZXZfcmVsZWFzZWQpOwoJaW5pdF9jb21wbGV0aW9uKCZhZGFwLT5jbGFzc19kZXZfcmVsZWFzZWQpOwoJY2xhc3NfZGV2aWNlX3VucmVnaXN0ZXIoJmFkYXAtPmNsYXNzX2Rldik7CglkZXZpY2VfcmVtb3ZlX2ZpbGUoJmFkYXAtPmRldiwgJmRldl9hdHRyX25hbWUpOwoJZGV2aWNlX3VucmVnaXN0ZXIoJmFkYXAtPmRldik7CglsaXN0X2RlbCgmYWRhcC0+bGlzdCk7CgoJLyogd2FpdCBmb3Igc3lzZnMgdG8gZHJvcCBhbGwgcmVmZXJlbmNlcyAqLwoJd2FpdF9mb3JfY29tcGxldGlvbigmYWRhcC0+ZGV2X3JlbGVhc2VkKTsKCXdhaXRfZm9yX2NvbXBsZXRpb24oJmFkYXAtPmNsYXNzX2Rldl9yZWxlYXNlZCk7CgoJLyogZnJlZSBkeW5hbWljYWxseSBhbGxvY2F0ZWQgYnVzIGlkICovCglpZHJfcmVtb3ZlKCZpMmNfYWRhcHRlcl9pZHIsIGFkYXAtPm5yKTsKCglkZXZfZGJnKCZhZGFwLT5kZXYsICJhZGFwdGVyIFslc10gdW5yZWdpc3RlcmVkXG4iLCBhZGFwLT5uYW1lKTsKCiBvdXRfdW5sb2NrOgoJbXV0ZXhfdW5sb2NrKCZjb3JlX2xpc3RzKTsKCXJldHVybiByZXM7Cn0KCgovKiAtLS0tLQogKiBXaGF0IGZvbGxvd3MgaXMgdGhlICJ1cHdhcmRzIiBpbnRlcmZhY2U6IGNvbW1hbmRzIGZvciB0YWxraW5nIHRvIGNsaWVudHMsCiAqIHdoaWNoIGltcGxlbWVudCB0aGUgZnVuY3Rpb25zIHRvIGFjY2VzcyB0aGUgcGh5c2ljYWwgaW5mb3JtYXRpb24gb2YgdGhlCiAqIGNoaXBzLgogKi8KCmludCBpMmNfcmVnaXN0ZXJfZHJpdmVyKHN0cnVjdCBtb2R1bGUgKm93bmVyLCBzdHJ1Y3QgaTJjX2RyaXZlciAqZHJpdmVyKQp7CglzdHJ1Y3QgbGlzdF9oZWFkICAgKml0ZW07CglzdHJ1Y3QgaTJjX2FkYXB0ZXIgKmFkYXB0ZXI7CglpbnQgcmVzOwoKCS8qIGFkZCB0aGUgZHJpdmVyIHRvIHRoZSBsaXN0IG9mIGkyYyBkcml2ZXJzIGluIHRoZSBkcml2ZXIgY29yZSAqLwoJZHJpdmVyLT5kcml2ZXIub3duZXIgPSBvd25lcjsKCWRyaXZlci0+ZHJpdmVyLmJ1cyA9ICZpMmNfYnVzX3R5cGU7CgoJcmVzID0gZHJpdmVyX3JlZ2lzdGVyKCZkcml2ZXItPmRyaXZlcik7CglpZiAocmVzKQoJCXJldHVybiByZXM7CgkKCW11dGV4X2xvY2soJmNvcmVfbGlzdHMpOwoKCWxpc3RfYWRkX3RhaWwoJmRyaXZlci0+bGlzdCwmZHJpdmVycyk7Cglwcl9kZWJ1ZygiaTJjLWNvcmU6IGRyaXZlciBbJXNdIHJlZ2lzdGVyZWRcbiIsIGRyaXZlci0+ZHJpdmVyLm5hbWUpOwoKCS8qIG5vdyBsb29rIGZvciBpbnN0YW5jZXMgb2YgZHJpdmVyIG9uIG91ciBhZGFwdGVycyAqLwoJaWYgKGRyaXZlci0+YXR0YWNoX2FkYXB0ZXIpIHsKCQlsaXN0X2Zvcl9lYWNoKGl0ZW0sJmFkYXB0ZXJzKSB7CgkJCWFkYXB0ZXIgPSBsaXN0X2VudHJ5KGl0ZW0sIHN0cnVjdCBpMmNfYWRhcHRlciwgbGlzdCk7CgkJCWRyaXZlci0+YXR0YWNoX2FkYXB0ZXIoYWRhcHRlcik7CgkJfQoJfQoKCW11dGV4X3VubG9jaygmY29yZV9saXN0cyk7CglyZXR1cm4gMDsKfQpFWFBPUlRfU1lNQk9MKGkyY19yZWdpc3Rlcl9kcml2ZXIpOwoKaW50IGkyY19kZWxfZHJpdmVyKHN0cnVjdCBpMmNfZHJpdmVyICpkcml2ZXIpCnsKCXN0cnVjdCBsaXN0X2hlYWQgICAqaXRlbTEsICppdGVtMiwgKl9uOwoJc3RydWN0IGkyY19jbGllbnQgICpjbGllbnQ7CglzdHJ1Y3QgaTJjX2FkYXB0ZXIgKmFkYXA7CgkKCWludCByZXMgPSAwOwoKCW11dGV4X2xvY2soJmNvcmVfbGlzdHMpOwoKCS8qIEhhdmUgYSBsb29rIGF0IGVhY2ggYWRhcHRlciwgaWYgY2xpZW50cyBvZiB0aGlzIGRyaXZlciBhcmUgc3RpbGwKCSAqIGF0dGFjaGVkLiBJZiBzbywgZGV0YWNoIHRoZW0gdG8gYmUgYWJsZSB0byBraWxsIHRoZSBkcml2ZXIgCgkgKiBhZnRlcndhcmRzLgoJICovCglsaXN0X2Zvcl9lYWNoKGl0ZW0xLCZhZGFwdGVycykgewoJCWFkYXAgPSBsaXN0X2VudHJ5KGl0ZW0xLCBzdHJ1Y3QgaTJjX2FkYXB0ZXIsIGxpc3QpOwoJCWlmIChkcml2ZXItPmRldGFjaF9hZGFwdGVyKSB7CgkJCWlmICgocmVzID0gZHJpdmVyLT5kZXRhY2hfYWRhcHRlcihhZGFwKSkpIHsKCQkJCWRldl9lcnIoJmFkYXAtPmRldiwgImRldGFjaF9hZGFwdGVyIGZhaWxlZCAiCgkJCQkJImZvciBkcml2ZXIgWyVzXVxuIiwKCQkJCQlkcml2ZXItPmRyaXZlci5uYW1lKTsKCQkJCWdvdG8gb3V0X3VubG9jazsKCQkJfQoJCX0gZWxzZSB7CgkJCWxpc3RfZm9yX2VhY2hfc2FmZShpdGVtMiwgX24sICZhZGFwLT5jbGllbnRzKSB7CgkJCQljbGllbnQgPSBsaXN0X2VudHJ5KGl0ZW0yLCBzdHJ1Y3QgaTJjX2NsaWVudCwgbGlzdCk7CgkJCQlpZiAoY2xpZW50LT5kcml2ZXIgIT0gZHJpdmVyKQoJCQkJCWNvbnRpbnVlOwoJCQkJZGV2X2RiZygmYWRhcC0+ZGV2LCAiZGV0YWNoaW5nIGNsaWVudCBbJXNdICIKCQkJCQkiYXQgMHglMDJ4XG4iLCBjbGllbnQtPm5hbWUsCgkJCQkJY2xpZW50LT5hZGRyKTsKCQkJCWlmICgocmVzID0gZHJpdmVyLT5kZXRhY2hfY2xpZW50KGNsaWVudCkpKSB7CgkJCQkJZGV2X2VycigmYWRhcC0+ZGV2LCAiZGV0YWNoX2NsaWVudCAiCgkJCQkJCSJmYWlsZWQgZm9yIGNsaWVudCBbJXNdIGF0ICIKCQkJCQkJIjB4JTAyeFxuIiwgY2xpZW50LT5uYW1lLAoJCQkJCQljbGllbnQtPmFkZHIpOwoJCQkJCWdvdG8gb3V0X3VubG9jazsKCQkJCX0KCQkJfQoJCX0KCX0KCglkcml2ZXJfdW5yZWdpc3RlcigmZHJpdmVyLT5kcml2ZXIpOwoJbGlzdF9kZWwoJmRyaXZlci0+bGlzdCk7Cglwcl9kZWJ1ZygiaTJjLWNvcmU6IGRyaXZlciBbJXNdIHVucmVnaXN0ZXJlZFxuIiwgZHJpdmVyLT5kcml2ZXIubmFtZSk7Cgogb3V0X3VubG9jazoKCW11dGV4X3VubG9jaygmY29yZV9saXN0cyk7CglyZXR1cm4gMDsKfQoKc3RhdGljIGludCBfX2kyY19jaGVja19hZGRyKHN0cnVjdCBpMmNfYWRhcHRlciAqYWRhcHRlciwgdW5zaWduZWQgaW50IGFkZHIpCnsKCXN0cnVjdCBsaXN0X2hlYWQgICAqaXRlbTsKCXN0cnVjdCBpMmNfY2xpZW50ICAqY2xpZW50OwoKCWxpc3RfZm9yX2VhY2goaXRlbSwmYWRhcHRlci0+Y2xpZW50cykgewoJCWNsaWVudCA9IGxpc3RfZW50cnkoaXRlbSwgc3RydWN0IGkyY19jbGllbnQsIGxpc3QpOwoJCWlmIChjbGllbnQtPmFkZHIgPT0gYWRkcikKCQkJcmV0dXJuIC1FQlVTWTsKCX0KCXJldHVybiAwOwp9CgppbnQgaTJjX2NoZWNrX2FkZHIoc3RydWN0IGkyY19hZGFwdGVyICphZGFwdGVyLCBpbnQgYWRkcikKewoJaW50IHJ2YWw7CgoJbXV0ZXhfbG9jaygmYWRhcHRlci0+Y2xpc3RfbG9jayk7CglydmFsID0gX19pMmNfY2hlY2tfYWRkcihhZGFwdGVyLCBhZGRyKTsKCW11dGV4X3VubG9jaygmYWRhcHRlci0+Y2xpc3RfbG9jayk7CgoJcmV0dXJuIHJ2YWw7Cn0KCmludCBpMmNfYXR0YWNoX2NsaWVudChzdHJ1Y3QgaTJjX2NsaWVudCAqY2xpZW50KQp7CglzdHJ1Y3QgaTJjX2FkYXB0ZXIgKmFkYXB0ZXIgPSBjbGllbnQtPmFkYXB0ZXI7CglpbnQgcmVzID0gMDsKCgltdXRleF9sb2NrKCZhZGFwdGVyLT5jbGlzdF9sb2NrKTsKCWlmIChfX2kyY19jaGVja19hZGRyKGNsaWVudC0+YWRhcHRlciwgY2xpZW50LT5hZGRyKSkgewoJCXJlcyA9IC1FQlVTWTsKCQlnb3RvIG91dF91bmxvY2s7Cgl9CglsaXN0X2FkZF90YWlsKCZjbGllbnQtPmxpc3QsJmFkYXB0ZXItPmNsaWVudHMpOwoJCgljbGllbnQtPnVzYWdlX2NvdW50ID0gMDsKCgljbGllbnQtPmRldi5wYXJlbnQgPSAmY2xpZW50LT5hZGFwdGVyLT5kZXY7CgljbGllbnQtPmRldi5kcml2ZXIgPSAmY2xpZW50LT5kcml2ZXItPmRyaXZlcjsKCWNsaWVudC0+ZGV2LmJ1cyA9ICZpMmNfYnVzX3R5cGU7CgljbGllbnQtPmRldi5yZWxlYXNlID0gJmkyY19jbGllbnRfcmVsZWFzZTsKCQoJc25wcmludGYoJmNsaWVudC0+ZGV2LmJ1c19pZFswXSwgc2l6ZW9mKGNsaWVudC0+ZGV2LmJ1c19pZCksCgkJIiVkLSUwNHgiLCBpMmNfYWRhcHRlcl9pZChhZGFwdGVyKSwgY2xpZW50LT5hZGRyKTsKCWRldl9kYmcoJmFkYXB0ZXItPmRldiwgImNsaWVudCBbJXNdIHJlZ2lzdGVyZWQgd2l0aCBidXMgaWQgJXNcbiIsCgkJY2xpZW50LT5uYW1lLCBjbGllbnQtPmRldi5idXNfaWQpOwoJcmVzID0gZGV2aWNlX3JlZ2lzdGVyKCZjbGllbnQtPmRldik7CglpZiAocmVzKQoJCWdvdG8gb3V0X2xpc3Q7CglyZXMgPSBkZXZpY2VfY3JlYXRlX2ZpbGUoJmNsaWVudC0+ZGV2LCAmZGV2X2F0dHJfY2xpZW50X25hbWUpOwoJaWYgKHJlcykKCQlnb3RvIG91dF91bnJlZ2lzdGVyOwoJbXV0ZXhfdW5sb2NrKCZhZGFwdGVyLT5jbGlzdF9sb2NrKTsKCglpZiAoYWRhcHRlci0+Y2xpZW50X3JlZ2lzdGVyKSAgewoJCWlmIChhZGFwdGVyLT5jbGllbnRfcmVnaXN0ZXIoY2xpZW50KSkgewoJCQlkZXZfZGJnKCZhZGFwdGVyLT5kZXYsICJjbGllbnRfcmVnaXN0ZXIgIgoJCQkJImZhaWxlZCBmb3IgY2xpZW50IFslc10gYXQgMHglMDJ4XG4iLAoJCQkJY2xpZW50LT5uYW1lLCBjbGllbnQtPmFkZHIpOwoJCX0KCX0KCglyZXR1cm4gMDsKCm91dF91bnJlZ2lzdGVyOgoJaW5pdF9jb21wbGV0aW9uKCZjbGllbnQtPnJlbGVhc2VkKTsgLyogTmVlZGVkPyAqLwoJZGV2aWNlX3VucmVnaXN0ZXIoJmNsaWVudC0+ZGV2KTsKCXdhaXRfZm9yX2NvbXBsZXRpb24oJmNsaWVudC0+cmVsZWFzZWQpOwpvdXRfbGlzdDoKCWxpc3RfZGVsKCZjbGllbnQtPmxpc3QpOwoJZGV2X2VycigmYWRhcHRlci0+ZGV2LCAiRmFpbGVkIHRvIGF0dGFjaCBpMmMgY2xpZW50ICVzIGF0IDB4JTAyeCAiCgkJIiglZClcbiIsIGNsaWVudC0+bmFtZSwgY2xpZW50LT5hZGRyLCByZXMpOwpvdXRfdW5sb2NrOgoJbXV0ZXhfdW5sb2NrKCZhZGFwdGVyLT5jbGlzdF9sb2NrKTsKCXJldHVybiByZXM7Cn0KCgppbnQgaTJjX2RldGFjaF9jbGllbnQoc3RydWN0IGkyY19jbGllbnQgKmNsaWVudCkKewoJc3RydWN0IGkyY19hZGFwdGVyICphZGFwdGVyID0gY2xpZW50LT5hZGFwdGVyOwoJaW50IHJlcyA9IDA7CgkKCWlmIChjbGllbnQtPnVzYWdlX2NvdW50ID4gMCkgewoJCWRldl93YXJuKCZjbGllbnQtPmRldiwgIkNsaWVudCBbJXNdIHN0aWxsIGJ1c3ksICIKCQkJICJjYW4ndCBkZXRhY2hcbiIsIGNsaWVudC0+bmFtZSk7CgkJcmV0dXJuIC1FQlVTWTsKCX0KCglpZiAoYWRhcHRlci0+Y2xpZW50X3VucmVnaXN0ZXIpICB7CgkJcmVzID0gYWRhcHRlci0+Y2xpZW50X3VucmVnaXN0ZXIoY2xpZW50KTsKCQlpZiAocmVzKSB7CgkJCWRldl9lcnIoJmNsaWVudC0+ZGV2LAoJCQkJImNsaWVudF91bnJlZ2lzdGVyIFslc10gZmFpbGVkLCAiCgkJCQkiY2xpZW50IG5vdCBkZXRhY2hlZFxuIiwgY2xpZW50LT5uYW1lKTsKCQkJZ290byBvdXQ7CgkJfQoJfQoKCW11dGV4X2xvY2soJmFkYXB0ZXItPmNsaXN0X2xvY2spOwoJbGlzdF9kZWwoJmNsaWVudC0+bGlzdCk7Cglpbml0X2NvbXBsZXRpb24oJmNsaWVudC0+cmVsZWFzZWQpOwoJZGV2aWNlX3JlbW92ZV9maWxlKCZjbGllbnQtPmRldiwgJmRldl9hdHRyX2NsaWVudF9uYW1lKTsKCWRldmljZV91bnJlZ2lzdGVyKCZjbGllbnQtPmRldik7CgltdXRleF91bmxvY2soJmFkYXB0ZXItPmNsaXN0X2xvY2spOwoJd2FpdF9mb3JfY29tcGxldGlvbigmY2xpZW50LT5yZWxlYXNlZCk7Cgogb3V0OgoJcmV0dXJuIHJlczsKfQoKc3RhdGljIGludCBpMmNfaW5jX3VzZV9jbGllbnQoc3RydWN0IGkyY19jbGllbnQgKmNsaWVudCkKewoKCWlmICghdHJ5X21vZHVsZV9nZXQoY2xpZW50LT5kcml2ZXItPmRyaXZlci5vd25lcikpCgkJcmV0dXJuIC1FTk9ERVY7CglpZiAoIXRyeV9tb2R1bGVfZ2V0KGNsaWVudC0+YWRhcHRlci0+b3duZXIpKSB7CgkJbW9kdWxlX3B1dChjbGllbnQtPmRyaXZlci0+ZHJpdmVyLm93bmVyKTsKCQlyZXR1cm4gLUVOT0RFVjsKCX0KCglyZXR1cm4gMDsKfQoKc3RhdGljIHZvaWQgaTJjX2RlY191c2VfY2xpZW50KHN0cnVjdCBpMmNfY2xpZW50ICpjbGllbnQpCnsKCW1vZHVsZV9wdXQoY2xpZW50LT5kcml2ZXItPmRyaXZlci5vd25lcik7Cgltb2R1bGVfcHV0KGNsaWVudC0+YWRhcHRlci0+b3duZXIpOwp9CgppbnQgaTJjX3VzZV9jbGllbnQoc3RydWN0IGkyY19jbGllbnQgKmNsaWVudCkKewoJaW50IHJldDsKCglyZXQgPSBpMmNfaW5jX3VzZV9jbGllbnQoY2xpZW50KTsKCWlmIChyZXQpCgkJcmV0dXJuIHJldDsKCgljbGllbnQtPnVzYWdlX2NvdW50Kys7CgoJcmV0dXJuIDA7Cn0KCmludCBpMmNfcmVsZWFzZV9jbGllbnQoc3RydWN0IGkyY19jbGllbnQgKmNsaWVudCkKewoJaWYgKCFjbGllbnQtPnVzYWdlX2NvdW50KSB7CgkJcHJfZGVidWcoImkyYy1jb3JlOiAlcyB1c2VkIG9uZSB0b28gbWFueSB0aW1lc1xuIiwKCQkJIF9fRlVOQ1RJT05fXyk7CgkJcmV0dXJuIC1FUEVSTTsKCX0KCQoJY2xpZW50LT51c2FnZV9jb3VudC0tOwoJaTJjX2RlY191c2VfY2xpZW50KGNsaWVudCk7CgkKCXJldHVybiAwOwp9Cgp2b2lkIGkyY19jbGllbnRzX2NvbW1hbmQoc3RydWN0IGkyY19hZGFwdGVyICphZGFwLCB1bnNpZ25lZCBpbnQgY21kLCB2b2lkICphcmcpCnsKCXN0cnVjdCBsaXN0X2hlYWQgICppdGVtOwoJc3RydWN0IGkyY19jbGllbnQgKmNsaWVudDsKCgltdXRleF9sb2NrKCZhZGFwLT5jbGlzdF9sb2NrKTsKCWxpc3RfZm9yX2VhY2goaXRlbSwmYWRhcC0+Y2xpZW50cykgewoJCWNsaWVudCA9IGxpc3RfZW50cnkoaXRlbSwgc3RydWN0IGkyY19jbGllbnQsIGxpc3QpOwoJCWlmICghdHJ5X21vZHVsZV9nZXQoY2xpZW50LT5kcml2ZXItPmRyaXZlci5vd25lcikpCgkJCWNvbnRpbnVlOwoJCWlmIChOVUxMICE9IGNsaWVudC0+ZHJpdmVyLT5jb21tYW5kKSB7CgkJCW11dGV4X3VubG9jaygmYWRhcC0+Y2xpc3RfbG9jayk7CgkJCWNsaWVudC0+ZHJpdmVyLT5jb21tYW5kKGNsaWVudCxjbWQsYXJnKTsKCQkJbXV0ZXhfbG9jaygmYWRhcC0+Y2xpc3RfbG9jayk7CgkJfQoJCW1vZHVsZV9wdXQoY2xpZW50LT5kcml2ZXItPmRyaXZlci5vd25lcik7CiAgICAgICB9CiAgICAgICBtdXRleF91bmxvY2soJmFkYXAtPmNsaXN0X2xvY2spOwp9CgpzdGF0aWMgaW50IF9faW5pdCBpMmNfaW5pdCh2b2lkKQp7CglpbnQgcmV0dmFsOwoKCXJldHZhbCA9IGJ1c19yZWdpc3RlcigmaTJjX2J1c190eXBlKTsKCWlmIChyZXR2YWwpCgkJcmV0dXJuIHJldHZhbDsKCXJldHZhbCA9IGRyaXZlcl9yZWdpc3RlcigmaTJjX2FkYXB0ZXJfZHJpdmVyKTsKCWlmIChyZXR2YWwpCgkJcmV0dXJuIHJldHZhbDsKCXJldHVybiBjbGFzc19yZWdpc3RlcigmaTJjX2FkYXB0ZXJfY2xhc3MpOwp9CgpzdGF0aWMgdm9pZCBfX2V4aXQgaTJjX2V4aXQodm9pZCkKewoJY2xhc3NfdW5yZWdpc3RlcigmaTJjX2FkYXB0ZXJfY2xhc3MpOwoJZHJpdmVyX3VucmVnaXN0ZXIoJmkyY19hZGFwdGVyX2RyaXZlcik7CglidXNfdW5yZWdpc3RlcigmaTJjX2J1c190eXBlKTsKfQoKc3Vic3lzX2luaXRjYWxsKGkyY19pbml0KTsKbW9kdWxlX2V4aXQoaTJjX2V4aXQpOwoKLyogLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQogKiB0aGUgZnVuY3Rpb25hbCBpbnRlcmZhY2UgdG8gdGhlIGkyYyBidXNzZXMuCiAqIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KICovCgppbnQgaTJjX3RyYW5zZmVyKHN0cnVjdCBpMmNfYWRhcHRlciAqIGFkYXAsIHN0cnVjdCBpMmNfbXNnICptc2dzLCBpbnQgbnVtKQp7CglpbnQgcmV0OwoKCWlmIChhZGFwLT5hbGdvLT5tYXN0ZXJfeGZlcikgewojaWZkZWYgREVCVUcKCQlmb3IgKHJldCA9IDA7IHJldCA8IG51bTsgcmV0KyspIHsKCQkJZGV2X2RiZygmYWRhcC0+ZGV2LCAibWFzdGVyX3hmZXJbJWRdICVjLCBhZGRyPTB4JTAyeCwgIgoJCQkJImxlbj0lZFxuIiwgcmV0LCBtc2dzW3JldF0uZmxhZ3MgJiBJMkNfTV9SRCA/CgkJCQknUicgOiAnVycsIG1zZ3NbcmV0XS5hZGRyLCBtc2dzW3JldF0ubGVuKTsKCQl9CiNlbmRpZgoKCQltdXRleF9sb2NrKCZhZGFwLT5idXNfbG9jayk7CgkJcmV0ID0gYWRhcC0+YWxnby0+bWFzdGVyX3hmZXIoYWRhcCxtc2dzLG51bSk7CgkJbXV0ZXhfdW5sb2NrKCZhZGFwLT5idXNfbG9jayk7CgoJCXJldHVybiByZXQ7Cgl9IGVsc2UgewoJCWRldl9kYmcoJmFkYXAtPmRldiwgIkkyQyBsZXZlbCB0cmFuc2ZlcnMgbm90IHN1cHBvcnRlZFxuIik7CgkJcmV0dXJuIC1FTk9TWVM7Cgl9Cn0KCmludCBpMmNfbWFzdGVyX3NlbmQoc3RydWN0IGkyY19jbGllbnQgKmNsaWVudCxjb25zdCBjaGFyICpidWYgLGludCBjb3VudCkKewoJaW50IHJldDsKCXN0cnVjdCBpMmNfYWRhcHRlciAqYWRhcD1jbGllbnQtPmFkYXB0ZXI7CglzdHJ1Y3QgaTJjX21zZyBtc2c7CgoJbXNnLmFkZHIgPSBjbGllbnQtPmFkZHI7Cgltc2cuZmxhZ3MgPSBjbGllbnQtPmZsYWdzICYgSTJDX01fVEVOOwoJbXNnLmxlbiA9IGNvdW50OwoJbXNnLmJ1ZiA9IChjaGFyICopYnVmOwoJCglyZXQgPSBpMmNfdHJhbnNmZXIoYWRhcCwgJm1zZywgMSk7CgoJLyogSWYgZXZlcnl0aGluZyB3ZW50IG9rIChpLmUuIDEgbXNnIHRyYW5zbWl0dGVkKSwgcmV0dXJuICNieXRlcwoJICAgdHJhbnNtaXR0ZWQsIGVsc2UgZXJyb3IgY29kZS4gKi8KCXJldHVybiAocmV0ID09IDEpID8gY291bnQgOiByZXQ7Cn0KCmludCBpMmNfbWFzdGVyX3JlY3Yoc3RydWN0IGkyY19jbGllbnQgKmNsaWVudCwgY2hhciAqYnVmICxpbnQgY291bnQpCnsKCXN0cnVjdCBpMmNfYWRhcHRlciAqYWRhcD1jbGllbnQtPmFkYXB0ZXI7CglzdHJ1Y3QgaTJjX21zZyBtc2c7CglpbnQgcmV0OwoKCW1zZy5hZGRyID0gY2xpZW50LT5hZGRyOwoJbXNnLmZsYWdzID0gY2xpZW50LT5mbGFncyAmIEkyQ19NX1RFTjsKCW1zZy5mbGFncyB8PSBJMkNfTV9SRDsKCW1zZy5sZW4gPSBjb3VudDsKCW1zZy5idWYgPSBidWY7CgoJcmV0ID0gaTJjX3RyYW5zZmVyKGFkYXAsICZtc2csIDEpOwoKCS8qIElmIGV2ZXJ5dGhpbmcgd2VudCBvayAoaS5lLiAxIG1zZyB0cmFuc21pdHRlZCksIHJldHVybiAjYnl0ZXMKCSAgIHRyYW5zbWl0dGVkLCBlbHNlIGVycm9yIGNvZGUuICovCglyZXR1cm4gKHJldCA9PSAxKSA/IGNvdW50IDogcmV0Owp9CgoKaW50IGkyY19jb250cm9sKHN0cnVjdCBpMmNfY2xpZW50ICpjbGllbnQsCgl1bnNpZ25lZCBpbnQgY21kLCB1bnNpZ25lZCBsb25nIGFyZykKewoJaW50IHJldCA9IDA7CglzdHJ1Y3QgaTJjX2FkYXB0ZXIgKmFkYXAgPSBjbGllbnQtPmFkYXB0ZXI7CgoJZGV2X2RiZygmY2xpZW50LT5hZGFwdGVyLT5kZXYsICJpMmMgaW9jdGwsIGNtZDogMHgleCwgYXJnOiAlI2x4XG4iLCBjbWQsIGFyZyk7Cglzd2l0Y2ggKGNtZCkgewoJCWNhc2UgSTJDX1JFVFJJRVM6CgkJCWFkYXAtPnJldHJpZXMgPSBhcmc7CgkJCWJyZWFrOwoJCWNhc2UgSTJDX1RJTUVPVVQ6CgkJCWFkYXAtPnRpbWVvdXQgPSBhcmc7CgkJCWJyZWFrOwoJCWRlZmF1bHQ6CgkJCWlmIChhZGFwLT5hbGdvLT5hbGdvX2NvbnRyb2whPU5VTEwpCgkJCQlyZXQgPSBhZGFwLT5hbGdvLT5hbGdvX2NvbnRyb2woYWRhcCxjbWQsYXJnKTsKCX0KCXJldHVybiByZXQ7Cn0KCi8qIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KICogdGhlIGkyYyBhZGRyZXNzIHNjYW5uaW5nIGZ1bmN0aW9uCiAqIFdpbGwgbm90IHdvcmsgZm9yIDEwLWJpdCBhZGRyZXNzZXMhCiAqIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KICovCnN0YXRpYyBpbnQgaTJjX3Byb2JlX2FkZHJlc3Moc3RydWN0IGkyY19hZGFwdGVyICphZGFwdGVyLCBpbnQgYWRkciwgaW50IGtpbmQsCgkJCSAgICAgaW50ICgqZm91bmRfcHJvYykgKHN0cnVjdCBpMmNfYWRhcHRlciAqLCBpbnQsIGludCkpCnsKCWludCBlcnI7CgoJLyogTWFrZSBzdXJlIHRoZSBhZGRyZXNzIGlzIHZhbGlkICovCglpZiAoYWRkciA8IDB4MDMgfHwgYWRkciA+IDB4NzcpIHsKCQlkZXZfd2FybigmYWRhcHRlci0+ZGV2LCAiSW52YWxpZCBwcm9iZSBhZGRyZXNzIDB4JTAyeFxuIiwKCQkJIGFkZHIpOwoJCXJldHVybiAtRUlOVkFMOwoJfQoKCS8qIFNraXAgaWYgYWxyZWFkeSBpbiB1c2UgKi8KCWlmIChpMmNfY2hlY2tfYWRkcihhZGFwdGVyLCBhZGRyKSkKCQlyZXR1cm4gMDsKCgkvKiBNYWtlIHN1cmUgdGhlcmUgaXMgc29tZXRoaW5nIGF0IHRoaXMgYWRkcmVzcywgdW5sZXNzIGZvcmNlZCAqLwoJaWYgKGtpbmQgPCAwKSB7CgkJaWYgKGkyY19zbWJ1c194ZmVyKGFkYXB0ZXIsIGFkZHIsIDAsIDAsIDAsCgkJCQkgICBJMkNfU01CVVNfUVVJQ0ssIE5VTEwpIDwgMCkKCQkJcmV0dXJuIDA7CgoJCS8qIHByZXZlbnQgMjRSRjA4IGNvcnJ1cHRpb24gKi8KCQlpZiAoKGFkZHIgJiB+MHgwZikgPT0gMHg1MCkKCQkJaTJjX3NtYnVzX3hmZXIoYWRhcHRlciwgYWRkciwgMCwgMCwgMCwKCQkJCSAgICAgICBJMkNfU01CVVNfUVVJQ0ssIE5VTEwpOwoJfQoKCS8qIEZpbmFsbHkgY2FsbCB0aGUgY3VzdG9tIGRldGVjdGlvbiBmdW5jdGlvbiAqLwoJZXJyID0gZm91bmRfcHJvYyhhZGFwdGVyLCBhZGRyLCBraW5kKTsKCS8qIC1FTk9ERVYgY2FuIGJlIHJldHVybmVkIGlmIHRoZXJlIGlzIGEgY2hpcCBhdCB0aGUgZ2l2ZW4gYWRkcmVzcwoJICAgYnV0IGl0IGlzbid0IHN1cHBvcnRlZCBieSB0aGlzIGNoaXAgZHJpdmVyLiBXZSBjYXRjaCBpdCBoZXJlIGFzCgkgICB0aGlzIGlzbid0IGFuIGVycm9yLiAqLwoJaWYgKGVyciA9PSAtRU5PREVWKQoJCWVyciA9IDA7CgoJaWYgKGVycikKCQlkZXZfd2FybigmYWRhcHRlci0+ZGV2LCAiQ2xpZW50IGNyZWF0aW9uIGZhaWxlZCBhdCAweCV4ICglZClcbiIsCgkJCSBhZGRyLCBlcnIpOwoJcmV0dXJuIGVycjsKfQoKaW50IGkyY19wcm9iZShzdHJ1Y3QgaTJjX2FkYXB0ZXIgKmFkYXB0ZXIsCgkgICAgICBzdHJ1Y3QgaTJjX2NsaWVudF9hZGRyZXNzX2RhdGEgKmFkZHJlc3NfZGF0YSwKCSAgICAgIGludCAoKmZvdW5kX3Byb2MpIChzdHJ1Y3QgaTJjX2FkYXB0ZXIgKiwgaW50LCBpbnQpKQp7CglpbnQgaSwgZXJyOwoJaW50IGFkYXBfaWQgPSBpMmNfYWRhcHRlcl9pZChhZGFwdGVyKTsKCgkvKiBGb3JjZSBlbnRyaWVzIGFyZSBkb25lIGZpcnN0LCBhbmQgYXJlIG5vdCBhZmZlY3RlZCBieSBpZ25vcmUKCSAgIGVudHJpZXMgKi8KCWlmIChhZGRyZXNzX2RhdGEtPmZvcmNlcykgewoJCXVuc2lnbmVkIHNob3J0ICoqZm9yY2VzID0gYWRkcmVzc19kYXRhLT5mb3JjZXM7CgkJaW50IGtpbmQ7CgoJCWZvciAoa2luZCA9IDA7IGZvcmNlc1traW5kXTsga2luZCsrKSB7CgkJCWZvciAoaSA9IDA7IGZvcmNlc1traW5kXVtpXSAhPSBJMkNfQ0xJRU5UX0VORDsKCQkJICAgICBpICs9IDIpIHsKCQkJCWlmIChmb3JjZXNba2luZF1baV0gPT0gYWRhcF9pZAoJCQkJIHx8IGZvcmNlc1traW5kXVtpXSA9PSBBTllfSTJDX0JVUykgewoJCQkJCWRldl9kYmcoJmFkYXB0ZXItPmRldiwgImZvdW5kIGZvcmNlICIKCQkJCQkJInBhcmFtZXRlciBmb3IgYWRhcHRlciAlZCwgIgoJCQkJCQkiYWRkciAweCUwMngsIGtpbmQgJWRcbiIsCgkJCQkJCWFkYXBfaWQsIGZvcmNlc1traW5kXVtpICsgMV0sCgkJCQkJCWtpbmQpOwoJCQkJCWVyciA9IGkyY19wcm9iZV9hZGRyZXNzKGFkYXB0ZXIsCgkJCQkJCWZvcmNlc1traW5kXVtpICsgMV0sCgkJCQkJCWtpbmQsIGZvdW5kX3Byb2MpOwoJCQkJCWlmIChlcnIpCgkJCQkJCXJldHVybiBlcnI7CgkJCQl9CgkJCX0KCQl9Cgl9CgoJLyogU3RvcCBoZXJlIGlmIHdlIGNhbid0IHVzZSBTTUJVU19RVUlDSyAqLwoJaWYgKCFpMmNfY2hlY2tfZnVuY3Rpb25hbGl0eShhZGFwdGVyLCBJMkNfRlVOQ19TTUJVU19RVUlDSykpIHsKCQlpZiAoYWRkcmVzc19kYXRhLT5wcm9iZVswXSA9PSBJMkNfQ0xJRU5UX0VORAoJCSAmJiBhZGRyZXNzX2RhdGEtPm5vcm1hbF9pMmNbMF0gPT0gSTJDX0NMSUVOVF9FTkQpCgkJIAlyZXR1cm4gMDsKCgkJZGV2X3dhcm4oJmFkYXB0ZXItPmRldiwgIlNNQnVzIFF1aWNrIGNvbW1hbmQgbm90IHN1cHBvcnRlZCwgIgoJCQkgImNhbid0IHByb2JlIGZvciBjaGlwc1xuIik7CgkJcmV0dXJuIC0xOwoJfQoKCS8qIFByb2JlIGVudHJpZXMgYXJlIGRvbmUgc2Vjb25kLCBhbmQgYXJlIG5vdCBhZmZlY3RlZCBieSBpZ25vcmUKCSAgIGVudHJpZXMgZWl0aGVyICovCglmb3IgKGkgPSAwOyBhZGRyZXNzX2RhdGEtPnByb2JlW2ldICE9IEkyQ19DTElFTlRfRU5EOyBpICs9IDIpIHsKCQlpZiAoYWRkcmVzc19kYXRhLT5wcm9iZVtpXSA9PSBhZGFwX2lkCgkJIHx8IGFkZHJlc3NfZGF0YS0+cHJvYmVbaV0gPT0gQU5ZX0kyQ19CVVMpIHsKCQkJZGV2X2RiZygmYWRhcHRlci0+ZGV2LCAiZm91bmQgcHJvYmUgcGFyYW1ldGVyIGZvciAiCgkJCQkiYWRhcHRlciAlZCwgYWRkciAweCUwMnhcbiIsIGFkYXBfaWQsCgkJCQlhZGRyZXNzX2RhdGEtPnByb2JlW2kgKyAxXSk7CgkJCWVyciA9IGkyY19wcm9iZV9hZGRyZXNzKGFkYXB0ZXIsCgkJCQkJCWFkZHJlc3NfZGF0YS0+cHJvYmVbaSArIDFdLAoJCQkJCQktMSwgZm91bmRfcHJvYyk7CgkJCWlmIChlcnIpCgkJCQlyZXR1cm4gZXJyOwoJCX0KCX0KCgkvKiBOb3JtYWwgZW50cmllcyBhcmUgZG9uZSBsYXN0LCB1bmxlc3Mgc2hhZG93ZWQgYnkgYW4gaWdub3JlIGVudHJ5ICovCglmb3IgKGkgPSAwOyBhZGRyZXNzX2RhdGEtPm5vcm1hbF9pMmNbaV0gIT0gSTJDX0NMSUVOVF9FTkQ7IGkgKz0gMSkgewoJCWludCBqLCBpZ25vcmU7CgoJCWlnbm9yZSA9IDA7CgkJZm9yIChqID0gMDsgYWRkcmVzc19kYXRhLT5pZ25vcmVbal0gIT0gSTJDX0NMSUVOVF9FTkQ7CgkJICAgICBqICs9IDIpIHsKCQkJaWYgKChhZGRyZXNzX2RhdGEtPmlnbm9yZVtqXSA9PSBhZGFwX2lkIHx8CgkJCSAgICAgYWRkcmVzc19kYXRhLT5pZ25vcmVbal0gPT0gQU5ZX0kyQ19CVVMpCgkJCSAmJiBhZGRyZXNzX2RhdGEtPmlnbm9yZVtqICsgMV0KCQkJICAgID09IGFkZHJlc3NfZGF0YS0+bm9ybWFsX2kyY1tpXSkgewoJCQkJZGV2X2RiZygmYWRhcHRlci0+ZGV2LCAiZm91bmQgaWdub3JlICIKCQkJCQkicGFyYW1ldGVyIGZvciBhZGFwdGVyICVkLCAiCgkJCQkJImFkZHIgMHglMDJ4XG4iLCBhZGFwX2lkLAoJCQkJCWFkZHJlc3NfZGF0YS0+aWdub3JlW2ogKyAxXSk7CgkJCQlpZ25vcmUgPSAxOwoJCQkJYnJlYWs7CgkJCX0KCQl9CgkJaWYgKGlnbm9yZSkKCQkJY29udGludWU7CgoJCWRldl9kYmcoJmFkYXB0ZXItPmRldiwgImZvdW5kIG5vcm1hbCBlbnRyeSBmb3IgYWRhcHRlciAlZCwgIgoJCQkiYWRkciAweCUwMnhcbiIsIGFkYXBfaWQsCgkJCWFkZHJlc3NfZGF0YS0+bm9ybWFsX2kyY1tpXSk7CgkJZXJyID0gaTJjX3Byb2JlX2FkZHJlc3MoYWRhcHRlciwgYWRkcmVzc19kYXRhLT5ub3JtYWxfaTJjW2ldLAoJCQkJCS0xLCBmb3VuZF9wcm9jKTsKCQlpZiAoZXJyKQoJCQlyZXR1cm4gZXJyOwoJfQoKCXJldHVybiAwOwp9CgpzdHJ1Y3QgaTJjX2FkYXB0ZXIqIGkyY19nZXRfYWRhcHRlcihpbnQgaWQpCnsKCXN0cnVjdCBpMmNfYWRhcHRlciAqYWRhcHRlcjsKCQoJbXV0ZXhfbG9jaygmY29yZV9saXN0cyk7CglhZGFwdGVyID0gKHN0cnVjdCBpMmNfYWRhcHRlciAqKWlkcl9maW5kKCZpMmNfYWRhcHRlcl9pZHIsIGlkKTsKCWlmIChhZGFwdGVyICYmICF0cnlfbW9kdWxlX2dldChhZGFwdGVyLT5vd25lcikpCgkJYWRhcHRlciA9IE5VTEw7CgoJbXV0ZXhfdW5sb2NrKCZjb3JlX2xpc3RzKTsKCXJldHVybiBhZGFwdGVyOwp9Cgp2b2lkIGkyY19wdXRfYWRhcHRlcihzdHJ1Y3QgaTJjX2FkYXB0ZXIgKmFkYXApCnsKCW1vZHVsZV9wdXQoYWRhcC0+b3duZXIpOwp9CgovKiBUaGUgU01CdXMgcGFydHMgKi8KCiNkZWZpbmUgUE9MWSAgICAoMHgxMDcwVSA8PCAzKSAKc3RhdGljIHU4CmNyYzgodTE2IGRhdGEpCnsKCWludCBpOwogIAoJZm9yKGkgPSAwOyBpIDwgODsgaSsrKSB7CgkJaWYgKGRhdGEgJiAweDgwMDApIAoJCQlkYXRhID0gZGF0YSBeIFBPTFk7CgkJZGF0YSA9IGRhdGEgPDwgMTsKCX0KCXJldHVybiAodTgpKGRhdGEgPj4gOCk7Cn0KCi8qIEluY3JlbWVudGFsIENSQzggb3ZlciBjb3VudCBieXRlcyBpbiB0aGUgYXJyYXkgcG9pbnRlZCB0byBieSBwICovCnN0YXRpYyB1OCBpMmNfc21idXNfcGVjKHU4IGNyYywgdTggKnAsIHNpemVfdCBjb3VudCkKewoJaW50IGk7CgoJZm9yKGkgPSAwOyBpIDwgY291bnQ7IGkrKykKCQljcmMgPSBjcmM4KChjcmMgXiBwW2ldKSA8PCA4KTsKCXJldHVybiBjcmM7Cn0KCi8qIEFzc3VtZSBhIDctYml0IGFkZHJlc3MsIHdoaWNoIGlzIHJlYXNvbmFibGUgZm9yIFNNQnVzICovCnN0YXRpYyB1OCBpMmNfc21idXNfbXNnX3BlYyh1OCBwZWMsIHN0cnVjdCBpMmNfbXNnICptc2cpCnsKCS8qIFRoZSBhZGRyZXNzIHdpbGwgYmUgc2VudCBmaXJzdCAqLwoJdTggYWRkciA9IChtc2ctPmFkZHIgPDwgMSkgfCAhIShtc2ctPmZsYWdzICYgSTJDX01fUkQpOwoJcGVjID0gaTJjX3NtYnVzX3BlYyhwZWMsICZhZGRyLCAxKTsKCgkvKiBUaGUgZGF0YSBidWZmZXIgZm9sbG93cyAqLwoJcmV0dXJuIGkyY19zbWJ1c19wZWMocGVjLCBtc2ctPmJ1ZiwgbXNnLT5sZW4pOwp9CgovKiBVc2VkIGZvciB3cml0ZSBvbmx5IHRyYW5zYWN0aW9ucyAqLwpzdGF0aWMgaW5saW5lIHZvaWQgaTJjX3NtYnVzX2FkZF9wZWMoc3RydWN0IGkyY19tc2cgKm1zZykKewoJbXNnLT5idWZbbXNnLT5sZW5dID0gaTJjX3NtYnVzX21zZ19wZWMoMCwgbXNnKTsKCW1zZy0+bGVuKys7Cn0KCi8qIFJldHVybiA8MCBvbiBDUkMgZXJyb3IKICAgSWYgdGhlcmUgd2FzIGEgd3JpdGUgYmVmb3JlIHRoaXMgcmVhZCAobW9zdCBjYXNlcykgd2UgbmVlZCB0byB0YWtlIHRoZQogICBwYXJ0aWFsIENSQyBmcm9tIHRoZSB3cml0ZSBwYXJ0IGludG8gYWNjb3VudC4KICAgTm90ZSB0aGF0IHRoaXMgZnVuY3Rpb24gZG9lcyBtb2RpZnkgdGhlIG1lc3NhZ2UgKHdlIG5lZWQgdG8gZGVjcmVhc2UgdGhlCiAgIG1lc3NhZ2UgbGVuZ3RoIHRvIGhpZGUgdGhlIENSQyBieXRlIGZyb20gdGhlIGNhbGxlcikuICovCnN0YXRpYyBpbnQgaTJjX3NtYnVzX2NoZWNrX3BlYyh1OCBjcGVjLCBzdHJ1Y3QgaTJjX21zZyAqbXNnKQp7Cgl1OCBycGVjID0gbXNnLT5idWZbLS1tc2ctPmxlbl07CgljcGVjID0gaTJjX3NtYnVzX21zZ19wZWMoY3BlYywgbXNnKTsKCglpZiAocnBlYyAhPSBjcGVjKSB7CgkJcHJfZGVidWcoImkyYy1jb3JlOiBCYWQgUEVDIDB4JTAyeCB2cy4gMHglMDJ4XG4iLAoJCQlycGVjLCBjcGVjKTsKCQlyZXR1cm4gLTE7Cgl9CglyZXR1cm4gMDsJCn0KCnMzMiBpMmNfc21idXNfd3JpdGVfcXVpY2soc3RydWN0IGkyY19jbGllbnQgKmNsaWVudCwgdTggdmFsdWUpCnsKCXJldHVybiBpMmNfc21idXNfeGZlcihjbGllbnQtPmFkYXB0ZXIsY2xpZW50LT5hZGRyLGNsaWVudC0+ZmxhZ3MsCiAJICAgICAgICAgICAgICAgICAgICAgIHZhbHVlLDAsSTJDX1NNQlVTX1FVSUNLLE5VTEwpOwp9CgpzMzIgaTJjX3NtYnVzX3JlYWRfYnl0ZShzdHJ1Y3QgaTJjX2NsaWVudCAqY2xpZW50KQp7Cgl1bmlvbiBpMmNfc21idXNfZGF0YSBkYXRhOwoJaWYgKGkyY19zbWJ1c194ZmVyKGNsaWVudC0+YWRhcHRlcixjbGllbnQtPmFkZHIsY2xpZW50LT5mbGFncywKCSAgICAgICAgICAgICAgICAgICBJMkNfU01CVVNfUkVBRCwwLEkyQ19TTUJVU19CWVRFLCAmZGF0YSkpCgkJcmV0dXJuIC0xOwoJZWxzZQoJCXJldHVybiBkYXRhLmJ5dGU7Cn0KCnMzMiBpMmNfc21idXNfd3JpdGVfYnl0ZShzdHJ1Y3QgaTJjX2NsaWVudCAqY2xpZW50LCB1OCB2YWx1ZSkKewoJcmV0dXJuIGkyY19zbWJ1c194ZmVyKGNsaWVudC0+YWRhcHRlcixjbGllbnQtPmFkZHIsY2xpZW50LT5mbGFncywKCSAgICAgICAgICAgICAgICAgICAgICBJMkNfU01CVVNfV1JJVEUsIHZhbHVlLCBJMkNfU01CVVNfQllURSwgTlVMTCk7Cn0KCnMzMiBpMmNfc21idXNfcmVhZF9ieXRlX2RhdGEoc3RydWN0IGkyY19jbGllbnQgKmNsaWVudCwgdTggY29tbWFuZCkKewoJdW5pb24gaTJjX3NtYnVzX2RhdGEgZGF0YTsKCWlmIChpMmNfc21idXNfeGZlcihjbGllbnQtPmFkYXB0ZXIsY2xpZW50LT5hZGRyLGNsaWVudC0+ZmxhZ3MsCgkgICAgICAgICAgICAgICAgICAgSTJDX1NNQlVTX1JFQUQsY29tbWFuZCwgSTJDX1NNQlVTX0JZVEVfREFUQSwmZGF0YSkpCgkJcmV0dXJuIC0xOwoJZWxzZQoJCXJldHVybiBkYXRhLmJ5dGU7Cn0KCnMzMiBpMmNfc21idXNfd3JpdGVfYnl0ZV9kYXRhKHN0cnVjdCBpMmNfY2xpZW50ICpjbGllbnQsIHU4IGNvbW1hbmQsIHU4IHZhbHVlKQp7Cgl1bmlvbiBpMmNfc21idXNfZGF0YSBkYXRhOwoJZGF0YS5ieXRlID0gdmFsdWU7CglyZXR1cm4gaTJjX3NtYnVzX3hmZXIoY2xpZW50LT5hZGFwdGVyLGNsaWVudC0+YWRkcixjbGllbnQtPmZsYWdzLAoJICAgICAgICAgICAgICAgICAgICAgIEkyQ19TTUJVU19XUklURSxjb21tYW5kLAoJICAgICAgICAgICAgICAgICAgICAgIEkyQ19TTUJVU19CWVRFX0RBVEEsJmRhdGEpOwp9CgpzMzIgaTJjX3NtYnVzX3JlYWRfd29yZF9kYXRhKHN0cnVjdCBpMmNfY2xpZW50ICpjbGllbnQsIHU4IGNvbW1hbmQpCnsKCXVuaW9uIGkyY19zbWJ1c19kYXRhIGRhdGE7CglpZiAoaTJjX3NtYnVzX3hmZXIoY2xpZW50LT5hZGFwdGVyLGNsaWVudC0+YWRkcixjbGllbnQtPmZsYWdzLAoJICAgICAgICAgICAgICAgICAgIEkyQ19TTUJVU19SRUFELGNvbW1hbmQsIEkyQ19TTUJVU19XT1JEX0RBVEEsICZkYXRhKSkKCQlyZXR1cm4gLTE7CgllbHNlCgkJcmV0dXJuIGRhdGEud29yZDsKfQoKczMyIGkyY19zbWJ1c193cml0ZV93b3JkX2RhdGEoc3RydWN0IGkyY19jbGllbnQgKmNsaWVudCwgdTggY29tbWFuZCwgdTE2IHZhbHVlKQp7Cgl1bmlvbiBpMmNfc21idXNfZGF0YSBkYXRhOwoJZGF0YS53b3JkID0gdmFsdWU7CglyZXR1cm4gaTJjX3NtYnVzX3hmZXIoY2xpZW50LT5hZGFwdGVyLGNsaWVudC0+YWRkcixjbGllbnQtPmZsYWdzLAoJICAgICAgICAgICAgICAgICAgICAgIEkyQ19TTUJVU19XUklURSxjb21tYW5kLAoJICAgICAgICAgICAgICAgICAgICAgIEkyQ19TTUJVU19XT1JEX0RBVEEsJmRhdGEpOwp9CgpzMzIgaTJjX3NtYnVzX3dyaXRlX2Jsb2NrX2RhdGEoc3RydWN0IGkyY19jbGllbnQgKmNsaWVudCwgdTggY29tbWFuZCwKCQkJICAgICAgIHU4IGxlbmd0aCwgY29uc3QgdTggKnZhbHVlcykKewoJdW5pb24gaTJjX3NtYnVzX2RhdGEgZGF0YTsKCglpZiAobGVuZ3RoID4gSTJDX1NNQlVTX0JMT0NLX01BWCkKCQlsZW5ndGggPSBJMkNfU01CVVNfQkxPQ0tfTUFYOwoJZGF0YS5ibG9ja1swXSA9IGxlbmd0aDsKCW1lbWNweSgmZGF0YS5ibG9ja1sxXSwgdmFsdWVzLCBsZW5ndGgpOwoJcmV0dXJuIGkyY19zbWJ1c194ZmVyKGNsaWVudC0+YWRhcHRlcixjbGllbnQtPmFkZHIsY2xpZW50LT5mbGFncywKCQkJICAgICAgSTJDX1NNQlVTX1dSSVRFLGNvbW1hbmQsCgkJCSAgICAgIEkyQ19TTUJVU19CTE9DS19EQVRBLCZkYXRhKTsKfQoKLyogUmV0dXJucyB0aGUgbnVtYmVyIG9mIHJlYWQgYnl0ZXMgKi8KczMyIGkyY19zbWJ1c19yZWFkX2kyY19ibG9ja19kYXRhKHN0cnVjdCBpMmNfY2xpZW50ICpjbGllbnQsIHU4IGNvbW1hbmQsIHU4ICp2YWx1ZXMpCnsKCXVuaW9uIGkyY19zbWJ1c19kYXRhIGRhdGE7CgoJaWYgKGkyY19zbWJ1c194ZmVyKGNsaWVudC0+YWRhcHRlcixjbGllbnQtPmFkZHIsY2xpZW50LT5mbGFncywKCSAgICAgICAgICAgICAgICAgICAgICBJMkNfU01CVVNfUkVBRCxjb21tYW5kLAoJICAgICAgICAgICAgICAgICAgICAgIEkyQ19TTUJVU19JMkNfQkxPQ0tfREFUQSwmZGF0YSkpCgkJcmV0dXJuIC0xOwoKCW1lbWNweSh2YWx1ZXMsICZkYXRhLmJsb2NrWzFdLCBkYXRhLmJsb2NrWzBdKTsKCXJldHVybiBkYXRhLmJsb2NrWzBdOwp9CgpzMzIgaTJjX3NtYnVzX3dyaXRlX2kyY19ibG9ja19kYXRhKHN0cnVjdCBpMmNfY2xpZW50ICpjbGllbnQsIHU4IGNvbW1hbmQsCgkJCQkgICB1OCBsZW5ndGgsIGNvbnN0IHU4ICp2YWx1ZXMpCnsKCXVuaW9uIGkyY19zbWJ1c19kYXRhIGRhdGE7CgoJaWYgKGxlbmd0aCA+IEkyQ19TTUJVU19CTE9DS19NQVgpCgkJbGVuZ3RoID0gSTJDX1NNQlVTX0JMT0NLX01BWDsKCWRhdGEuYmxvY2tbMF0gPSBsZW5ndGg7CgltZW1jcHkoZGF0YS5ibG9jayArIDEsIHZhbHVlcywgbGVuZ3RoKTsKCXJldHVybiBpMmNfc21idXNfeGZlcihjbGllbnQtPmFkYXB0ZXIsIGNsaWVudC0+YWRkciwgY2xpZW50LT5mbGFncywKCQkJICAgICAgSTJDX1NNQlVTX1dSSVRFLCBjb21tYW5kLAoJCQkgICAgICBJMkNfU01CVVNfSTJDX0JMT0NLX0RBVEEsICZkYXRhKTsKfQoKLyogU2ltdWxhdGUgYSBTTUJ1cyBjb21tYW5kIHVzaW5nIHRoZSBpMmMgcHJvdG9jb2wgCiAgIE5vIGNoZWNraW5nIG9mIHBhcmFtZXRlcnMgaXMgZG9uZSEgICovCnN0YXRpYyBzMzIgaTJjX3NtYnVzX3hmZXJfZW11bGF0ZWQoc3RydWN0IGkyY19hZGFwdGVyICogYWRhcHRlciwgdTE2IGFkZHIsIAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHVuc2lnbmVkIHNob3J0IGZsYWdzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNoYXIgcmVhZF93cml0ZSwgdTggY29tbWFuZCwgaW50IHNpemUsIAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHVuaW9uIGkyY19zbWJ1c19kYXRhICogZGF0YSkKewoJLyogU28gd2UgbmVlZCB0byBnZW5lcmF0ZSBhIHNlcmllcyBvZiBtc2dzLiBJbiB0aGUgY2FzZSBvZiB3cml0aW5nLCB3ZQoJICBuZWVkIHRvIHVzZSBvbmx5IG9uZSBtZXNzYWdlOyB3aGVuIHJlYWRpbmcsIHdlIG5lZWQgdHdvLiBXZSBpbml0aWFsaXplCgkgIG1vc3QgdGhpbmdzIHdpdGggc2FuZSBkZWZhdWx0cywgdG8ga2VlcCB0aGUgY29kZSBiZWxvdyBzb21ld2hhdAoJICBzaW1wbGVyLiAqLwoJdW5zaWduZWQgY2hhciBtc2didWYwW0kyQ19TTUJVU19CTE9DS19NQVgrM107Cgl1bnNpZ25lZCBjaGFyIG1zZ2J1ZjFbSTJDX1NNQlVTX0JMT0NLX01BWCsyXTsKCWludCBudW0gPSByZWFkX3dyaXRlID09IEkyQ19TTUJVU19SRUFEPzI6MTsKCXN0cnVjdCBpMmNfbXNnIG1zZ1syXSA9IHsgeyBhZGRyLCBmbGFncywgMSwgbXNnYnVmMCB9LCAKCSAgICAgICAgICAgICAgICAgICAgICAgICAgeyBhZGRyLCBmbGFncyB8IEkyQ19NX1JELCAwLCBtc2didWYxIH0KCSAgICAgICAgICAgICAgICAgICAgICAgIH07CglpbnQgaTsKCXU4IHBhcnRpYWxfcGVjID0gMDsKCgltc2didWYwWzBdID0gY29tbWFuZDsKCXN3aXRjaChzaXplKSB7CgljYXNlIEkyQ19TTUJVU19RVUlDSzoKCQltc2dbMF0ubGVuID0gMDsKCQkvKiBTcGVjaWFsIGNhc2U6IFRoZSByZWFkL3dyaXRlIGZpZWxkIGlzIHVzZWQgYXMgZGF0YSAqLwoJCW1zZ1swXS5mbGFncyA9IGZsYWdzIHwgKHJlYWRfd3JpdGU9PUkyQ19TTUJVU19SRUFEKT9JMkNfTV9SRDowOwoJCW51bSA9IDE7CgkJYnJlYWs7CgljYXNlIEkyQ19TTUJVU19CWVRFOgoJCWlmIChyZWFkX3dyaXRlID09IEkyQ19TTUJVU19SRUFEKSB7CgkJCS8qIFNwZWNpYWwgY2FzZTogb25seSBhIHJlYWQhICovCgkJCW1zZ1swXS5mbGFncyA9IEkyQ19NX1JEIHwgZmxhZ3M7CgkJCW51bSA9IDE7CgkJfQoJCWJyZWFrOwoJY2FzZSBJMkNfU01CVVNfQllURV9EQVRBOgoJCWlmIChyZWFkX3dyaXRlID09IEkyQ19TTUJVU19SRUFEKQoJCQltc2dbMV0ubGVuID0gMTsKCQllbHNlIHsKCQkJbXNnWzBdLmxlbiA9IDI7CgkJCW1zZ2J1ZjBbMV0gPSBkYXRhLT5ieXRlOwoJCX0KCQlicmVhazsKCWNhc2UgSTJDX1NNQlVTX1dPUkRfREFUQToKCQlpZiAocmVhZF93cml0ZSA9PSBJMkNfU01CVVNfUkVBRCkKCQkJbXNnWzFdLmxlbiA9IDI7CgkJZWxzZSB7CgkJCW1zZ1swXS5sZW49MzsKCQkJbXNnYnVmMFsxXSA9IGRhdGEtPndvcmQgJiAweGZmOwoJCQltc2didWYwWzJdID0gZGF0YS0+d29yZCA+PiA4OwoJCX0KCQlicmVhazsKCWNhc2UgSTJDX1NNQlVTX1BST0NfQ0FMTDoKCQludW0gPSAyOyAvKiBTcGVjaWFsIGNhc2UgKi8KCQlyZWFkX3dyaXRlID0gSTJDX1NNQlVTX1JFQUQ7CgkJbXNnWzBdLmxlbiA9IDM7CgkJbXNnWzFdLmxlbiA9IDI7CgkJbXNnYnVmMFsxXSA9IGRhdGEtPndvcmQgJiAweGZmOwoJCW1zZ2J1ZjBbMl0gPSBkYXRhLT53b3JkID4+IDg7CgkJYnJlYWs7CgljYXNlIEkyQ19TTUJVU19CTE9DS19EQVRBOgoJCWlmIChyZWFkX3dyaXRlID09IEkyQ19TTUJVU19SRUFEKSB7CgkJCWRldl9lcnIoJmFkYXB0ZXItPmRldiwgIkJsb2NrIHJlYWQgbm90IHN1cHBvcnRlZCAiCgkJCSAgICAgICAidW5kZXIgSTJDIGVtdWxhdGlvbiFcbiIpOwoJCQlyZXR1cm4gLTE7CgkJfSBlbHNlIHsKCQkJbXNnWzBdLmxlbiA9IGRhdGEtPmJsb2NrWzBdICsgMjsKCQkJaWYgKG1zZ1swXS5sZW4gPiBJMkNfU01CVVNfQkxPQ0tfTUFYICsgMikgewoJCQkJZGV2X2VycigmYWRhcHRlci0+ZGV2LCAic21idXNfYWNjZXNzIGNhbGxlZCB3aXRoICIKCQkJCSAgICAgICAiaW52YWxpZCBibG9jayB3cml0ZSBzaXplICglZClcbiIsCgkJCQkgICAgICAgZGF0YS0+YmxvY2tbMF0pOwoJCQkJcmV0dXJuIC0xOwoJCQl9CgkJCWZvciAoaSA9IDE7IGkgPCBtc2dbMF0ubGVuOyBpKyspCgkJCQltc2didWYwW2ldID0gZGF0YS0+YmxvY2tbaS0xXTsKCQl9CgkJYnJlYWs7CgljYXNlIEkyQ19TTUJVU19CTE9DS19QUk9DX0NBTEw6CgkJZGV2X2RiZygmYWRhcHRlci0+ZGV2LCAiQmxvY2sgcHJvY2VzcyBjYWxsIG5vdCBzdXBwb3J0ZWQgIgoJCSAgICAgICAidW5kZXIgSTJDIGVtdWxhdGlvbiFcbiIpOwoJCXJldHVybiAtMTsKCWNhc2UgSTJDX1NNQlVTX0kyQ19CTE9DS19EQVRBOgoJCWlmIChyZWFkX3dyaXRlID09IEkyQ19TTUJVU19SRUFEKSB7CgkJCW1zZ1sxXS5sZW4gPSBJMkNfU01CVVNfQkxPQ0tfTUFYOwoJCX0gZWxzZSB7CgkJCW1zZ1swXS5sZW4gPSBkYXRhLT5ibG9ja1swXSArIDE7CgkJCWlmIChtc2dbMF0ubGVuID4gSTJDX1NNQlVTX0JMT0NLX01BWCArIDEpIHsKCQkJCWRldl9lcnIoJmFkYXB0ZXItPmRldiwgImkyY19zbWJ1c194ZmVyX2VtdWxhdGVkIGNhbGxlZCB3aXRoICIKCQkJCSAgICAgICAiaW52YWxpZCBibG9jayB3cml0ZSBzaXplICglZClcbiIsCgkJCQkgICAgICAgZGF0YS0+YmxvY2tbMF0pOwoJCQkJcmV0dXJuIC0xOwoJCQl9CgkJCWZvciAoaSA9IDE7IGkgPD0gZGF0YS0+YmxvY2tbMF07IGkrKykKCQkJCW1zZ2J1ZjBbaV0gPSBkYXRhLT5ibG9ja1tpXTsKCQl9CgkJYnJlYWs7CglkZWZhdWx0OgoJCWRldl9lcnIoJmFkYXB0ZXItPmRldiwgInNtYnVzX2FjY2VzcyBjYWxsZWQgd2l0aCBpbnZhbGlkIHNpemUgKCVkKVxuIiwKCQkgICAgICAgc2l6ZSk7CgkJcmV0dXJuIC0xOwoJfQoKCWkgPSAoKGZsYWdzICYgSTJDX0NMSUVOVF9QRUMpICYmIHNpemUgIT0gSTJDX1NNQlVTX1FVSUNLCgkJCQkgICAgICAmJiBzaXplICE9IEkyQ19TTUJVU19JMkNfQkxPQ0tfREFUQSk7CglpZiAoaSkgewoJCS8qIENvbXB1dGUgUEVDIGlmIGZpcnN0IG1lc3NhZ2UgaXMgYSB3cml0ZSAqLwoJCWlmICghKG1zZ1swXS5mbGFncyAmIEkyQ19NX1JEKSkgewoJCSAJaWYgKG51bSA9PSAxKSAvKiBXcml0ZSBvbmx5ICovCgkJCQlpMmNfc21idXNfYWRkX3BlYygmbXNnWzBdKTsKCQkJZWxzZSAvKiBXcml0ZSBmb2xsb3dlZCBieSByZWFkICovCgkJCQlwYXJ0aWFsX3BlYyA9IGkyY19zbWJ1c19tc2dfcGVjKDAsICZtc2dbMF0pOwoJCX0KCQkvKiBBc2sgZm9yIFBFQyBpZiBsYXN0IG1lc3NhZ2UgaXMgYSByZWFkICovCgkJaWYgKG1zZ1tudW0tMV0uZmxhZ3MgJiBJMkNfTV9SRCkKCQkgCW1zZ1tudW0tMV0ubGVuKys7Cgl9CgoJaWYgKGkyY190cmFuc2ZlcihhZGFwdGVyLCBtc2csIG51bSkgPCAwKQoJCXJldHVybiAtMTsKCgkvKiBDaGVjayBQRUMgaWYgbGFzdCBtZXNzYWdlIGlzIGEgcmVhZCAqLwoJaWYgKGkgJiYgKG1zZ1tudW0tMV0uZmxhZ3MgJiBJMkNfTV9SRCkpIHsKCQlpZiAoaTJjX3NtYnVzX2NoZWNrX3BlYyhwYXJ0aWFsX3BlYywgJm1zZ1tudW0tMV0pIDwgMCkKCQkJcmV0dXJuIC0xOwoJfQoKCWlmIChyZWFkX3dyaXRlID09IEkyQ19TTUJVU19SRUFEKQoJCXN3aXRjaChzaXplKSB7CgkJCWNhc2UgSTJDX1NNQlVTX0JZVEU6CgkJCQlkYXRhLT5ieXRlID0gbXNnYnVmMFswXTsKCQkJCWJyZWFrOwoJCQljYXNlIEkyQ19TTUJVU19CWVRFX0RBVEE6CgkJCQlkYXRhLT5ieXRlID0gbXNnYnVmMVswXTsKCQkJCWJyZWFrOwoJCQljYXNlIEkyQ19TTUJVU19XT1JEX0RBVEE6IAoJCQljYXNlIEkyQ19TTUJVU19QUk9DX0NBTEw6CgkJCQlkYXRhLT53b3JkID0gbXNnYnVmMVswXSB8IChtc2didWYxWzFdIDw8IDgpOwoJCQkJYnJlYWs7CgkJCWNhc2UgSTJDX1NNQlVTX0kyQ19CTE9DS19EQVRBOgoJCQkJLyogZml4ZWQgYXQgMzIgZm9yIG5vdyAqLwoJCQkJZGF0YS0+YmxvY2tbMF0gPSBJMkNfU01CVVNfQkxPQ0tfTUFYOwoJCQkJZm9yIChpID0gMDsgaSA8IEkyQ19TTUJVU19CTE9DS19NQVg7IGkrKykKCQkJCQlkYXRhLT5ibG9ja1tpKzFdID0gbXNnYnVmMVtpXTsKCQkJCWJyZWFrOwoJCX0KCXJldHVybiAwOwp9CgoKczMyIGkyY19zbWJ1c194ZmVyKHN0cnVjdCBpMmNfYWRhcHRlciAqIGFkYXB0ZXIsIHUxNiBhZGRyLCB1bnNpZ25lZCBzaG9ydCBmbGFncywKICAgICAgICAgICAgICAgICAgIGNoYXIgcmVhZF93cml0ZSwgdTggY29tbWFuZCwgaW50IHNpemUsIAogICAgICAgICAgICAgICAgICAgdW5pb24gaTJjX3NtYnVzX2RhdGEgKiBkYXRhKQp7CglzMzIgcmVzOwoKCWZsYWdzICY9IEkyQ19NX1RFTiB8IEkyQ19DTElFTlRfUEVDOwoKCWlmIChhZGFwdGVyLT5hbGdvLT5zbWJ1c194ZmVyKSB7CgkJbXV0ZXhfbG9jaygmYWRhcHRlci0+YnVzX2xvY2spOwoJCXJlcyA9IGFkYXB0ZXItPmFsZ28tPnNtYnVzX3hmZXIoYWRhcHRlcixhZGRyLGZsYWdzLHJlYWRfd3JpdGUsCgkJICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBjb21tYW5kLHNpemUsZGF0YSk7CgkJbXV0ZXhfdW5sb2NrKCZhZGFwdGVyLT5idXNfbG9jayk7Cgl9IGVsc2UKCQlyZXMgPSBpMmNfc21idXNfeGZlcl9lbXVsYXRlZChhZGFwdGVyLGFkZHIsZmxhZ3MscmVhZF93cml0ZSwKCSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY29tbWFuZCxzaXplLGRhdGEpOwoKCXJldHVybiByZXM7Cn0KCgovKiBOZXh0IGZvdXIgYXJlIG5lZWRlZCBieSBpMmMtaXNhICovCkVYUE9SVF9TWU1CT0xfR1BMKGkyY19hZGFwdGVyX2Rldl9yZWxlYXNlKTsKRVhQT1JUX1NZTUJPTF9HUEwoaTJjX2FkYXB0ZXJfZHJpdmVyKTsKRVhQT1JUX1NZTUJPTF9HUEwoaTJjX2FkYXB0ZXJfY2xhc3MpOwpFWFBPUlRfU1lNQk9MX0dQTChpMmNfYnVzX3R5cGUpOwoKRVhQT1JUX1NZTUJPTChpMmNfYWRkX2FkYXB0ZXIpOwpFWFBPUlRfU1lNQk9MKGkyY19kZWxfYWRhcHRlcik7CkVYUE9SVF9TWU1CT0woaTJjX2RlbF9kcml2ZXIpOwpFWFBPUlRfU1lNQk9MKGkyY19hdHRhY2hfY2xpZW50KTsKRVhQT1JUX1NZTUJPTChpMmNfZGV0YWNoX2NsaWVudCk7CkVYUE9SVF9TWU1CT0woaTJjX3VzZV9jbGllbnQpOwpFWFBPUlRfU1lNQk9MKGkyY19yZWxlYXNlX2NsaWVudCk7CkVYUE9SVF9TWU1CT0woaTJjX2NsaWVudHNfY29tbWFuZCk7CkVYUE9SVF9TWU1CT0woaTJjX2NoZWNrX2FkZHIpOwoKRVhQT1JUX1NZTUJPTChpMmNfbWFzdGVyX3NlbmQpOwpFWFBPUlRfU1lNQk9MKGkyY19tYXN0ZXJfcmVjdik7CkVYUE9SVF9TWU1CT0woaTJjX2NvbnRyb2wpOwpFWFBPUlRfU1lNQk9MKGkyY190cmFuc2Zlcik7CkVYUE9SVF9TWU1CT0woaTJjX2dldF9hZGFwdGVyKTsKRVhQT1JUX1NZTUJPTChpMmNfcHV0X2FkYXB0ZXIpOwpFWFBPUlRfU1lNQk9MKGkyY19wcm9iZSk7CgpFWFBPUlRfU1lNQk9MKGkyY19zbWJ1c194ZmVyKTsKRVhQT1JUX1NZTUJPTChpMmNfc21idXNfd3JpdGVfcXVpY2spOwpFWFBPUlRfU1lNQk9MKGkyY19zbWJ1c19yZWFkX2J5dGUpOwpFWFBPUlRfU1lNQk9MKGkyY19zbWJ1c193cml0ZV9ieXRlKTsKRVhQT1JUX1NZTUJPTChpMmNfc21idXNfcmVhZF9ieXRlX2RhdGEpOwpFWFBPUlRfU1lNQk9MKGkyY19zbWJ1c193cml0ZV9ieXRlX2RhdGEpOwpFWFBPUlRfU1lNQk9MKGkyY19zbWJ1c19yZWFkX3dvcmRfZGF0YSk7CkVYUE9SVF9TWU1CT0woaTJjX3NtYnVzX3dyaXRlX3dvcmRfZGF0YSk7CkVYUE9SVF9TWU1CT0woaTJjX3NtYnVzX3dyaXRlX2Jsb2NrX2RhdGEpOwpFWFBPUlRfU1lNQk9MKGkyY19zbWJ1c19yZWFkX2kyY19ibG9ja19kYXRhKTsKRVhQT1JUX1NZTUJPTChpMmNfc21idXNfd3JpdGVfaTJjX2Jsb2NrX2RhdGEpOwoKTU9EVUxFX0FVVEhPUigiU2ltb24gRy4gVm9nbCA8c2ltb25AdGsudW5pLWxpbnouYWMuYXQ+Iik7Ck1PRFVMRV9ERVNDUklQVElPTigiSTJDLUJ1cyBtYWluIG1vZHVsZSIpOwpNT0RVTEVfTElDRU5TRSgiR1BMIik7Cg==