LyoKICAgIGkyYy12aWFwcm8uYyAtIFBhcnQgb2YgbG1fc2Vuc29ycywgTGludXgga2VybmVsIG1vZHVsZXMgZm9yIGhhcmR3YXJlCiAgICAgICAgICAgICAgbW9uaXRvcmluZwogICAgQ29weXJpZ2h0IChjKSAxOTk4IC0gMjAwMiAgRnJvZG8gTG9vaWphYXJkIDxmcm9kb2xAZGRzLm5sPiwKICAgIFBoaWxpcCBFZGVsYnJvY2sgPHBoaWxAbmV0cm9lZGdlLmNvbT4sIEt59nN0aSBN5Gxra2kgPGttYWxra2lAY2MuaHV0LmZpPiwKICAgIE1hcmsgRC4gU3R1ZGViYWtlciA8bWRzeHl6MTIzQHlhaG9vLmNvbT4KICAgIENvcHlyaWdodCAoQykgMjAwNSAtIDIwMDcgIEplYW4gRGVsdmFyZSA8a2hhbGlAbGludXgtZnIub3JnPgoKICAgIFRoaXMgcHJvZ3JhbSBpcyBmcmVlIHNvZnR3YXJlOyB5b3UgY2FuIHJlZGlzdHJpYnV0ZSBpdCBhbmQvb3IgbW9kaWZ5CiAgICBpdCB1bmRlciB0aGUgdGVybXMgb2YgdGhlIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlIGFzIHB1Ymxpc2hlZCBieQogICAgdGhlIEZyZWUgU29mdHdhcmUgRm91bmRhdGlvbjsgZWl0aGVyIHZlcnNpb24gMiBvZiB0aGUgTGljZW5zZSwgb3IKICAgIChhdCB5b3VyIG9wdGlvbikgYW55IGxhdGVyIHZlcnNpb24uCgogICAgVGhpcyBwcm9ncmFtIGlzIGRpc3RyaWJ1dGVkIGluIHRoZSBob3BlIHRoYXQgaXQgd2lsbCBiZSB1c2VmdWwsCiAgICBidXQgV0lUSE9VVCBBTlkgV0FSUkFOVFk7IHdpdGhvdXQgZXZlbiB0aGUgaW1wbGllZCB3YXJyYW50eSBvZgogICAgTUVSQ0hBTlRBQklMSVRZIG9yIEZJVE5FU1MgRk9SIEEgUEFSVElDVUxBUiBQVVJQT1NFLiAgU2VlIHRoZQogICAgR05VIEdlbmVyYWwgUHVibGljIExpY2Vuc2UgZm9yIG1vcmUgZGV0YWlscy4KCiAgICBZb3Ugc2hvdWxkIGhhdmUgcmVjZWl2ZWQgYSBjb3B5IG9mIHRoZSBHTlUgR2VuZXJhbCBQdWJsaWMgTGljZW5zZQogICAgYWxvbmcgd2l0aCB0aGlzIHByb2dyYW07IGlmIG5vdCwgd3JpdGUgdG8gdGhlIEZyZWUgU29mdHdhcmUKICAgIEZvdW5kYXRpb24sIEluYy4sIDY3NSBNYXNzIEF2ZSwgQ2FtYnJpZGdlLCBNQSAwMjEzOSwgVVNBLgoqLwoKLyoKICAgU3VwcG9ydHMgdGhlIGZvbGxvd2luZyBWSUEgc291dGggYnJpZGdlczoKCiAgIENoaXAgbmFtZSAgICAgICAgICBQQ0kgSUQgIFJFViAgICAgSTJDIGJsb2NrCiAgIFZUODJDNTk2QSAgICAgICAgICAweDMwNTAgICAgICAgICAgICAgbm8KICAgVlQ4MkM1OTZCICAgICAgICAgIDB4MzA1MSAgICAgICAgICAgICBubwogICBWVDgyQzY4NkEgICAgICAgICAgMHgzMDU3ICAweDMwICAgICAgIG5vCiAgIFZUODJDNjg2QiAgICAgICAgICAweDMwNTcgIDB4NDAgICAgICAgeWVzCiAgIFZUODIzMSAgICAgICAgICAgICAweDgyMzUgICAgICAgICAgICAgbm8/CiAgIFZUODIzMyAgICAgICAgICAgICAweDMwNzQgICAgICAgICAgICAgeWVzCiAgIFZUODIzM0EgICAgICAgICAgICAweDMxNDcgICAgICAgICAgICAgeWVzPwogICBWVDgyMzUgICAgICAgICAgICAgMHgzMTc3ICAgICAgICAgICAgIHllcwogICBWVDgyMzdSICAgICAgICAgICAgMHgzMjI3ICAgICAgICAgICAgIHllcwogICBWVDgyMzdBICAgICAgICAgICAgMHgzMzM3ICAgICAgICAgICAgIHllcwogICBWVDgyNTEgICAgICAgICAgICAgMHgzMjg3ICAgICAgICAgICAgIHllcwogICBDWDcwMCAgICAgICAgICAgICAgMHg4MzI0ICAgICAgICAgICAgIHllcwoKICAgTm90ZTogd2UgYXNzdW1lIHRoZXJlIGNhbiBvbmx5IGJlIG9uZSBkZXZpY2UsIHdpdGggb25lIFNNQnVzIGludGVyZmFjZS4KKi8KCiNpbmNsdWRlIDxsaW51eC9tb2R1bGUuaD4KI2luY2x1ZGUgPGxpbnV4L2RlbGF5Lmg+CiNpbmNsdWRlIDxsaW51eC9wY2kuaD4KI2luY2x1ZGUgPGxpbnV4L2tlcm5lbC5oPgojaW5jbHVkZSA8bGludXgvc3RkZGVmLmg+CiNpbmNsdWRlIDxsaW51eC9pb3BvcnQuaD4KI2luY2x1ZGUgPGxpbnV4L2kyYy5oPgojaW5jbHVkZSA8bGludXgvaW5pdC5oPgojaW5jbHVkZSA8YXNtL2lvLmg+CgpzdGF0aWMgc3RydWN0IHBjaV9kZXYgKnZ0NTk2X3BkZXY7CgojZGVmaW5lIFNNQkJBMQkJMHg5MAojZGVmaW5lIFNNQkJBMgkJMHg4MAojZGVmaW5lIFNNQkJBMwkJMHhEMAoKLyogU01CdXMgYWRkcmVzcyBvZmZzZXRzICovCnN0YXRpYyB1bnNpZ25lZCBzaG9ydCB2dDU5Nl9zbWJhOwojZGVmaW5lIFNNQkhTVFNUUwkodnQ1OTZfc21iYSArIDApCiNkZWZpbmUgU01CSFNUQ05UCSh2dDU5Nl9zbWJhICsgMikKI2RlZmluZSBTTUJIU1RDTUQJKHZ0NTk2X3NtYmEgKyAzKQojZGVmaW5lIFNNQkhTVEFERAkodnQ1OTZfc21iYSArIDQpCiNkZWZpbmUgU01CSFNUREFUMAkodnQ1OTZfc21iYSArIDUpCiNkZWZpbmUgU01CSFNUREFUMQkodnQ1OTZfc21iYSArIDYpCiNkZWZpbmUgU01CQkxLREFUCSh2dDU5Nl9zbWJhICsgNykKCi8qIFBDSSBBZGRyZXNzIENvbnN0YW50cyAqLwoKLyogU01CdXMgZGF0YSBpbiBjb25maWd1cmF0aW9uIHNwYWNlIGNhbiBiZSBmb3VuZCBpbiB0d28gcGxhY2VzLAogICBXZSB0cnkgdG8gc2VsZWN0IHRoZSBiZXR0ZXIgb25lICovCgpzdGF0aWMgdW5zaWduZWQgc2hvcnQgU01CSFNUQ0ZHID0gMHhEMjsKCi8qIE90aGVyIHNldHRpbmdzICovCiNkZWZpbmUgTUFYX1RJTUVPVVQJNTAwCgovKiBWVDgyQzU5NiBjb25zdGFudHMgKi8KI2RlZmluZSBWVDU5Nl9RVUlDSwkJMHgwMAojZGVmaW5lIFZUNTk2X0JZVEUJCTB4MDQKI2RlZmluZSBWVDU5Nl9CWVRFX0RBVEEJCTB4MDgKI2RlZmluZSBWVDU5Nl9XT1JEX0RBVEEJCTB4MEMKI2RlZmluZSBWVDU5Nl9CTE9DS19EQVRBCTB4MTQKI2RlZmluZSBWVDU5Nl9JMkNfQkxPQ0tfREFUQQkweDM0CgoKLyogSWYgZm9yY2UgaXMgc2V0IHRvIGFueXRoaW5nIGRpZmZlcmVudCBmcm9tIDAsIHdlIGZvcmNpYmx5IGVuYWJsZSB0aGUKICAgVlQ1OTYuIERBTkdFUk9VUyEgKi8Kc3RhdGljIGludCBmb3JjZTsKbW9kdWxlX3BhcmFtKGZvcmNlLCBib29sLCAwKTsKTU9EVUxFX1BBUk1fREVTQyhmb3JjZSwgIkZvcmNpYmx5IGVuYWJsZSB0aGUgU01CdXMuIERBTkdFUk9VUyEiKTsKCi8qIElmIGZvcmNlX2FkZHIgaXMgc2V0IHRvIGFueXRoaW5nIGRpZmZlcmVudCBmcm9tIDAsIHdlIGZvcmNpYmx5IGVuYWJsZQogICB0aGUgVlQ1OTYgYXQgdGhlIGdpdmVuIGFkZHJlc3MuIFZFUlkgREFOR0VST1VTISAqLwpzdGF0aWMgdTE2IGZvcmNlX2FkZHI7Cm1vZHVsZV9wYXJhbShmb3JjZV9hZGRyLCB1c2hvcnQsIDApOwpNT0RVTEVfUEFSTV9ERVNDKGZvcmNlX2FkZHIsCgkJICJGb3JjaWJseSBlbmFibGUgdGhlIFNNQnVzIGF0IHRoZSBnaXZlbiBhZGRyZXNzLiAiCgkJICJFWFRSRU1FTFkgREFOR0VST1VTISIpOwoKCnN0YXRpYyBzdHJ1Y3QgcGNpX2RyaXZlciB2dDU5Nl9kcml2ZXI7CnN0YXRpYyBzdHJ1Y3QgaTJjX2FkYXB0ZXIgdnQ1OTZfYWRhcHRlcjsKCiNkZWZpbmUgRkVBVFVSRV9JMkNCTE9DSwkoMTw8MCkKc3RhdGljIHVuc2lnbmVkIGludCB2dDU5Nl9mZWF0dXJlczsKCiNpZmRlZiBERUJVRwpzdGF0aWMgdm9pZCB2dDU5Nl9kdW1wX3JlZ3MoY29uc3QgY2hhciAqbXNnLCB1OCBzaXplKQp7CglkZXZfZGJnKCZ2dDU5Nl9hZGFwdGVyLmRldiwgIiVzOiBTVFM9JTAyeCBDTlQ9JTAyeCBDTUQ9JTAyeCBBREQ9JTAyeCAiCgkJIkRBVD0lMDJ4LCUwMnhcbiIsIG1zZywgaW5iX3AoU01CSFNUU1RTKSwgaW5iX3AoU01CSFNUQ05UKSwKCQlpbmJfcChTTUJIU1RDTUQpLCBpbmJfcChTTUJIU1RBREQpLCBpbmJfcChTTUJIU1REQVQwKSwKCQlpbmJfcChTTUJIU1REQVQxKSk7CgoJaWYgKHNpemUgPT0gVlQ1OTZfQkxPQ0tfREFUQQoJIHx8IHNpemUgPT0gVlQ1OTZfSTJDX0JMT0NLX0RBVEEpIHsKCQlpbnQgaTsKCgkJZGV2X2RiZygmdnQ1OTZfYWRhcHRlci5kZXYsICJCTEs9Iik7CgkJZm9yIChpID0gMDsgaSA8IEkyQ19TTUJVU19CTE9DS19NQVggLyAyOyBpKyspCgkJCXByaW50aygiJTAyeCwiLCBpbmJfcChTTUJCTEtEQVQpKTsKCQlwcmludGsoIlxuIik7CgkJZGV2X2RiZygmdnQ1OTZfYWRhcHRlci5kZXYsICIgICAgIik7CgkJZm9yICg7IGkgPCBJMkNfU01CVVNfQkxPQ0tfTUFYIC0gMTsgaSsrKQoJCQlwcmludGsoIiUwMngsIiwgaW5iX3AoU01CQkxLREFUKSk7CgkJcHJpbnRrKCIlMDJ4XG4iLCBpbmJfcChTTUJCTEtEQVQpKTsKCX0KfQojZWxzZQpzdGF0aWMgaW5saW5lIHZvaWQgdnQ1OTZfZHVtcF9yZWdzKGNvbnN0IGNoYXIgKm1zZywgdTggc2l6ZSkgeyB9CiNlbmRpZgoKLyogUmV0dXJuIC0xIG9uIGVycm9yLCAwIG9uIHN1Y2Nlc3MgKi8Kc3RhdGljIGludCB2dDU5Nl90cmFuc2FjdGlvbih1OCBzaXplKQp7CglpbnQgdGVtcDsKCWludCByZXN1bHQgPSAwOwoJaW50IHRpbWVvdXQgPSAwOwoKCXZ0NTk2X2R1bXBfcmVncygiVHJhbnNhY3Rpb24gKHByZSkiLCBzaXplKTsKCgkvKiBNYWtlIHN1cmUgdGhlIFNNQnVzIGhvc3QgaXMgcmVhZHkgdG8gc3RhcnQgdHJhbnNtaXR0aW5nICovCglpZiAoKHRlbXAgPSBpbmJfcChTTUJIU1RTVFMpKSAmIDB4MUYpIHsKCQlkZXZfZGJnKCZ2dDU5Nl9hZGFwdGVyLmRldiwgIlNNQnVzIGJ1c3kgKDB4JTAyeCkuICIKCQkJIlJlc2V0dGluZy4uLlxuIiwgdGVtcCk7CgoJCW91dGJfcCh0ZW1wLCBTTUJIU1RTVFMpOwoJCWlmICgodGVtcCA9IGluYl9wKFNNQkhTVFNUUykpICYgMHgxRikgewoJCQlkZXZfZXJyKCZ2dDU5Nl9hZGFwdGVyLmRldiwgIlNNQnVzIHJlc2V0IGZhaWxlZCEgIgoJCQkJIigweCUwMngpXG4iLCB0ZW1wKTsKCQkJcmV0dXJuIC0xOwoJCX0KCX0KCgkvKiBTdGFydCB0aGUgdHJhbnNhY3Rpb24gYnkgc2V0dGluZyBiaXQgNiAqLwoJb3V0Yl9wKDB4NDAgfCBzaXplLCBTTUJIU1RDTlQpOwoKCS8qIFdlIHdpbGwgYWx3YXlzIHdhaXQgZm9yIGEgZnJhY3Rpb24gb2YgYSBzZWNvbmQgKi8KCWRvIHsKCQltc2xlZXAoMSk7CgkJdGVtcCA9IGluYl9wKFNNQkhTVFNUUyk7Cgl9IHdoaWxlICgodGVtcCAmIDB4MDEpICYmICh0aW1lb3V0KysgPCBNQVhfVElNRU9VVCkpOwoKCS8qIElmIHRoZSBTTUJ1cyBpcyBzdGlsbCBidXN5LCB3ZSBnaXZlIHVwICovCglpZiAodGltZW91dCA+PSBNQVhfVElNRU9VVCkgewoJCXJlc3VsdCA9IC0xOwoJCWRldl9lcnIoJnZ0NTk2X2FkYXB0ZXIuZGV2LCAiU01CdXMgdGltZW91dCFcbiIpOwoJfQoKCWlmICh0ZW1wICYgMHgxMCkgewoJCXJlc3VsdCA9IC0xOwoJCWRldl9lcnIoJnZ0NTk2X2FkYXB0ZXIuZGV2LCAiVHJhbnNhY3Rpb24gZmFpbGVkICgweCUwMngpXG4iLAoJCQlzaXplKTsKCX0KCglpZiAodGVtcCAmIDB4MDgpIHsKCQlyZXN1bHQgPSAtMTsKCQlkZXZfZXJyKCZ2dDU5Nl9hZGFwdGVyLmRldiwgIlNNQnVzIGNvbGxpc2lvbiFcbiIpOwoJfQoKCWlmICh0ZW1wICYgMHgwNCkgewoJCWludCByZWFkID0gaW5iX3AoU01CSFNUQUREKSAmIDB4MDE7CgkJcmVzdWx0ID0gLTE7CgkJLyogVGhlIHF1aWNrIGFuZCByZWNlaXZlIGJ5dGUgY29tbWFuZHMgYXJlIHVzZWQgdG8gcHJvYmUKCQkgICBmb3IgY2hpcHMsIHNvIGVycm9ycyBhcmUgZXhwZWN0ZWQsIGFuZCB3ZSBkb24ndCB3YW50CgkJICAgdG8gZnJpZ2h0ZW4gdGhlIHVzZXIuICovCgkJaWYgKCEoKHNpemUgPT0gVlQ1OTZfUVVJQ0sgJiYgIXJlYWQpIHx8CgkJICAgICAgKHNpemUgPT0gVlQ1OTZfQllURSAmJiByZWFkKSkpCgkJCWRldl9lcnIoJnZ0NTk2X2FkYXB0ZXIuZGV2LCAiVHJhbnNhY3Rpb24gZXJyb3IhXG4iKTsKCX0KCgkvKiBSZXNldHRpbmcgc3RhdHVzIHJlZ2lzdGVyICovCglpZiAodGVtcCAmIDB4MUYpCgkJb3V0Yl9wKHRlbXAsIFNNQkhTVFNUUyk7CgoJdnQ1OTZfZHVtcF9yZWdzKCJUcmFuc2FjdGlvbiAocG9zdCkiLCBzaXplKTsKCglyZXR1cm4gcmVzdWx0Owp9CgovKiBSZXR1cm4gLTEgb24gZXJyb3IsIDAgb24gc3VjY2VzcyAqLwpzdGF0aWMgczMyIHZ0NTk2X2FjY2VzcyhzdHJ1Y3QgaTJjX2FkYXB0ZXIgKmFkYXAsIHUxNiBhZGRyLAoJCXVuc2lnbmVkIHNob3J0IGZsYWdzLCBjaGFyIHJlYWRfd3JpdGUsIHU4IGNvbW1hbmQsCgkJaW50IHNpemUsIHVuaW9uIGkyY19zbWJ1c19kYXRhICpkYXRhKQp7CglpbnQgaTsKCglzd2l0Y2ggKHNpemUpIHsKCWNhc2UgSTJDX1NNQlVTX1FVSUNLOgoJCXNpemUgPSBWVDU5Nl9RVUlDSzsKCQlicmVhazsKCWNhc2UgSTJDX1NNQlVTX0JZVEU6CgkJaWYgKHJlYWRfd3JpdGUgPT0gSTJDX1NNQlVTX1dSSVRFKQoJCQlvdXRiX3AoY29tbWFuZCwgU01CSFNUQ01EKTsKCQlzaXplID0gVlQ1OTZfQllURTsKCQlicmVhazsKCWNhc2UgSTJDX1NNQlVTX0JZVEVfREFUQToKCQlvdXRiX3AoY29tbWFuZCwgU01CSFNUQ01EKTsKCQlpZiAocmVhZF93cml0ZSA9PSBJMkNfU01CVVNfV1JJVEUpCgkJCW91dGJfcChkYXRhLT5ieXRlLCBTTUJIU1REQVQwKTsKCQlzaXplID0gVlQ1OTZfQllURV9EQVRBOwoJCWJyZWFrOwoJY2FzZSBJMkNfU01CVVNfV09SRF9EQVRBOgoJCW91dGJfcChjb21tYW5kLCBTTUJIU1RDTUQpOwoJCWlmIChyZWFkX3dyaXRlID09IEkyQ19TTUJVU19XUklURSkgewoJCQlvdXRiX3AoZGF0YS0+d29yZCAmIDB4ZmYsIFNNQkhTVERBVDApOwoJCQlvdXRiX3AoKGRhdGEtPndvcmQgJiAweGZmMDApID4+IDgsIFNNQkhTVERBVDEpOwoJCX0KCQlzaXplID0gVlQ1OTZfV09SRF9EQVRBOwoJCWJyZWFrOwoJY2FzZSBJMkNfU01CVVNfSTJDX0JMT0NLX0RBVEE6CgkJaWYgKCEodnQ1OTZfZmVhdHVyZXMgJiBGRUFUVVJFX0kyQ0JMT0NLKSkKCQkJZ290byBleGl0X3Vuc3VwcG9ydGVkOwoJCWlmIChyZWFkX3dyaXRlID09IEkyQ19TTUJVU19SRUFEKQoJCQlvdXRiX3AoSTJDX1NNQlVTX0JMT0NLX01BWCwgU01CSFNUREFUMCk7CgkJLyogRmFsbCB0aHJvdWdoICovCgljYXNlIEkyQ19TTUJVU19CTE9DS19EQVRBOgoJCW91dGJfcChjb21tYW5kLCBTTUJIU1RDTUQpOwoJCWlmIChyZWFkX3dyaXRlID09IEkyQ19TTUJVU19XUklURSkgewoJCQl1OCBsZW4gPSBkYXRhLT5ibG9ja1swXTsKCQkJaWYgKGxlbiA+IEkyQ19TTUJVU19CTE9DS19NQVgpCgkJCQlsZW4gPSBJMkNfU01CVVNfQkxPQ0tfTUFYOwoJCQlvdXRiX3AobGVuLCBTTUJIU1REQVQwKTsKCQkJaW5iX3AoU01CSFNUQ05UKTsJLyogUmVzZXQgU01CQkxLREFUICovCgkJCWZvciAoaSA9IDE7IGkgPD0gbGVuOyBpKyspCgkJCQlvdXRiX3AoZGF0YS0+YmxvY2tbaV0sIFNNQkJMS0RBVCk7CgkJfQoJCXNpemUgPSAoc2l6ZSA9PSBJMkNfU01CVVNfSTJDX0JMT0NLX0RBVEEpID8KCQkgICAgICAgVlQ1OTZfSTJDX0JMT0NLX0RBVEEgOiBWVDU5Nl9CTE9DS19EQVRBOwoJCWJyZWFrOwoJZGVmYXVsdDoKCQlnb3RvIGV4aXRfdW5zdXBwb3J0ZWQ7Cgl9CgoJb3V0Yl9wKCgoYWRkciAmIDB4N2YpIDw8IDEpIHwgcmVhZF93cml0ZSwgU01CSFNUQUREKTsKCglpZiAodnQ1OTZfdHJhbnNhY3Rpb24oc2l6ZSkpIC8qIEVycm9yIGluIHRyYW5zYWN0aW9uICovCgkJcmV0dXJuIC0xOwoKCWlmICgocmVhZF93cml0ZSA9PSBJMkNfU01CVVNfV1JJVEUpIHx8IChzaXplID09IFZUNTk2X1FVSUNLKSkKCQlyZXR1cm4gMDsKCglzd2l0Y2ggKHNpemUpIHsKCWNhc2UgVlQ1OTZfQllURToKCWNhc2UgVlQ1OTZfQllURV9EQVRBOgoJCWRhdGEtPmJ5dGUgPSBpbmJfcChTTUJIU1REQVQwKTsKCQlicmVhazsKCWNhc2UgVlQ1OTZfV09SRF9EQVRBOgoJCWRhdGEtPndvcmQgPSBpbmJfcChTTUJIU1REQVQwKSArIChpbmJfcChTTUJIU1REQVQxKSA8PCA4KTsKCQlicmVhazsKCWNhc2UgVlQ1OTZfSTJDX0JMT0NLX0RBVEE6CgljYXNlIFZUNTk2X0JMT0NLX0RBVEE6CgkJZGF0YS0+YmxvY2tbMF0gPSBpbmJfcChTTUJIU1REQVQwKTsKCQlpZiAoZGF0YS0+YmxvY2tbMF0gPiBJMkNfU01CVVNfQkxPQ0tfTUFYKQoJCQlkYXRhLT5ibG9ja1swXSA9IEkyQ19TTUJVU19CTE9DS19NQVg7CgkJaW5iX3AoU01CSFNUQ05UKTsJLyogUmVzZXQgU01CQkxLREFUICovCgkJZm9yIChpID0gMTsgaSA8PSBkYXRhLT5ibG9ja1swXTsgaSsrKQoJCQlkYXRhLT5ibG9ja1tpXSA9IGluYl9wKFNNQkJMS0RBVCk7CgkJYnJlYWs7Cgl9CglyZXR1cm4gMDsKCmV4aXRfdW5zdXBwb3J0ZWQ6CglkZXZfd2FybigmdnQ1OTZfYWRhcHRlci5kZXYsICJVbnN1cHBvcnRlZCBjb21tYW5kIGludm9rZWQhICgweCUwMngpXG4iLAoJCSBzaXplKTsKCXJldHVybiAtMTsKfQoKc3RhdGljIHUzMiB2dDU5Nl9mdW5jKHN0cnVjdCBpMmNfYWRhcHRlciAqYWRhcHRlcikKewoJdTMyIGZ1bmMgPSBJMkNfRlVOQ19TTUJVU19RVUlDSyB8IEkyQ19GVU5DX1NNQlVTX0JZVEUgfAoJICAgIEkyQ19GVU5DX1NNQlVTX0JZVEVfREFUQSB8IEkyQ19GVU5DX1NNQlVTX1dPUkRfREFUQSB8CgkgICAgSTJDX0ZVTkNfU01CVVNfQkxPQ0tfREFUQTsKCglpZiAodnQ1OTZfZmVhdHVyZXMgJiBGRUFUVVJFX0kyQ0JMT0NLKQoJCWZ1bmMgfD0gSTJDX0ZVTkNfU01CVVNfSTJDX0JMT0NLOwoJcmV0dXJuIGZ1bmM7Cn0KCnN0YXRpYyBjb25zdCBzdHJ1Y3QgaTJjX2FsZ29yaXRobSBzbWJ1c19hbGdvcml0aG0gPSB7Cgkuc21idXNfeGZlcgk9IHZ0NTk2X2FjY2VzcywKCS5mdW5jdGlvbmFsaXR5CT0gdnQ1OTZfZnVuYywKfTsKCnN0YXRpYyBzdHJ1Y3QgaTJjX2FkYXB0ZXIgdnQ1OTZfYWRhcHRlciA9IHsKCS5vd25lcgkJPSBUSElTX01PRFVMRSwKCS5pZAkJPSBJMkNfSFdfU01CVVNfVklBMiwKCS5jbGFzcwkJPSBJMkNfQ0xBU1NfSFdNT04sCgkuYWxnbwkJPSAmc21idXNfYWxnb3JpdGhtLAp9OwoKc3RhdGljIGludCBfX2RldmluaXQgdnQ1OTZfcHJvYmUoc3RydWN0IHBjaV9kZXYgKnBkZXYsCgkJCQkgY29uc3Qgc3RydWN0IHBjaV9kZXZpY2VfaWQgKmlkKQp7Cgl1bnNpZ25lZCBjaGFyIHRlbXA7CglpbnQgZXJyb3IgPSAtRU5PREVWOwoKCS8qIERldGVybWluZSB0aGUgYWRkcmVzcyBvZiB0aGUgU01CdXMgYXJlYXMgKi8KCWlmIChmb3JjZV9hZGRyKSB7CgkJdnQ1OTZfc21iYSA9IGZvcmNlX2FkZHIgJiAweGZmZjA7CgkJZm9yY2UgPSAwOwoJCWdvdG8gZm91bmQ7Cgl9CgoJaWYgKChwY2lfcmVhZF9jb25maWdfd29yZChwZGV2LCBpZC0+ZHJpdmVyX2RhdGEsICZ2dDU5Nl9zbWJhKSkgfHwKCSAgICAhKHZ0NTk2X3NtYmEgJiAweDAwMDEpKSB7CgkJLyogdHJ5IDJuZCBhZGRyZXNzIGFuZCBjb25maWcgcmVnLiBmb3IgNTk2ICovCgkJaWYgKGlkLT5kZXZpY2UgPT0gUENJX0RFVklDRV9JRF9WSUFfODJDNTk2XzMgJiYKCQkgICAgIXBjaV9yZWFkX2NvbmZpZ193b3JkKHBkZXYsIFNNQkJBMiwgJnZ0NTk2X3NtYmEpICYmCgkJICAgICh2dDU5Nl9zbWJhICYgMHgwMDAxKSkgewoJCQlTTUJIU1RDRkcgPSAweDg0OwoJCX0gZWxzZSB7CgkJCS8qIG5vIG1hdGNoZXMgYXQgYWxsICovCgkJCWRldl9lcnIoJnBkZXYtPmRldiwgIkNhbm5vdCBjb25maWd1cmUgIgoJCQkJIlNNQnVzIEkvTyBCYXNlIGFkZHJlc3NcbiIpOwoJCQlyZXR1cm4gLUVOT0RFVjsKCQl9Cgl9CgoJdnQ1OTZfc21iYSAmPSAweGZmZjA7CglpZiAodnQ1OTZfc21iYSA9PSAwKSB7CgkJZGV2X2VycigmcGRldi0+ZGV2LCAiU01CdXMgYmFzZSBhZGRyZXNzICIKCQkJInVuaW5pdGlhbGl6ZWQgLSB1cGdyYWRlIEJJT1Mgb3IgdXNlICIKCQkJImZvcmNlX2FkZHI9MHhhZGRyXG4iKTsKCQlyZXR1cm4gLUVOT0RFVjsKCX0KCmZvdW5kOgoJaWYgKCFyZXF1ZXN0X3JlZ2lvbih2dDU5Nl9zbWJhLCA4LCB2dDU5Nl9kcml2ZXIubmFtZSkpIHsKCQlkZXZfZXJyKCZwZGV2LT5kZXYsICJTTUJ1cyByZWdpb24gMHgleCBhbHJlYWR5IGluIHVzZSFcbiIsCgkJCXZ0NTk2X3NtYmEpOwoJCXJldHVybiAtRU5PREVWOwoJfQoKCXBjaV9yZWFkX2NvbmZpZ19ieXRlKHBkZXYsIFNNQkhTVENGRywgJnRlbXApOwoJLyogSWYgZm9yY2VfYWRkciBpcyBzZXQsIHdlIHByb2dyYW0gdGhlIG5ldyBhZGRyZXNzIGhlcmUuIEp1c3QgdG8gbWFrZQoJICAgc3VyZSwgd2UgZGlzYWJsZSB0aGUgVlQ1OTYgZmlyc3QuICovCglpZiAoZm9yY2VfYWRkcikgewoJCXBjaV93cml0ZV9jb25maWdfYnl0ZShwZGV2LCBTTUJIU1RDRkcsIHRlbXAgJiAweGZlKTsKCQlwY2lfd3JpdGVfY29uZmlnX3dvcmQocGRldiwgaWQtPmRyaXZlcl9kYXRhLCB2dDU5Nl9zbWJhKTsKCQlwY2lfd3JpdGVfY29uZmlnX2J5dGUocGRldiwgU01CSFNUQ0ZHLCB0ZW1wIHwgMHgwMSk7CgkJZGV2X3dhcm4oJnBkZXYtPmRldiwgIldBUk5JTkc6IFNNQnVzIGludGVyZmFjZSBzZXQgdG8gbmV3ICIKCQkJICJhZGRyZXNzIDB4JTA0eCFcbiIsIHZ0NTk2X3NtYmEpOwoJfSBlbHNlIGlmICghKHRlbXAgJiAweDAxKSkgewoJCWlmIChmb3JjZSkgewoJCQkvKiBOT1RFOiBUaGlzIGFzc3VtZXMgSS9PIHNwYWNlIGFuZCBvdGhlciBhbGxvY2F0aW9ucwoJCQkgKiBXRVJFIGRvbmUgYnkgdGhlIEJpb3MhICBEb24ndCBjb21wbGFpbiBpZiB5b3VyCgkJCSAqIGhhcmR3YXJlIGRvZXMgd2VpcmQgdGhpbmdzIGFmdGVyIGVuYWJsaW5nIHRoaXMuCgkJCSAqIDonKSBDaGVjayBmb3IgQmlvcyB1cGRhdGVzIGJlZm9yZSByZXNvcnRpbmcgdG8KCQkJICogdGhpcy4KCQkJICovCgkJCXBjaV93cml0ZV9jb25maWdfYnl0ZShwZGV2LCBTTUJIU1RDRkcsIHRlbXAgfCAweDAxKTsKCQkJZGV2X2luZm8oJnBkZXYtPmRldiwgIkVuYWJsaW5nIFNNQnVzIGRldmljZVxuIik7CgkJfSBlbHNlIHsKCQkJZGV2X2VycigmcGRldi0+ZGV2LCAiU01CVVM6IEVycm9yOiBIb3N0IFNNQnVzICIKCQkJCSJjb250cm9sbGVyIG5vdCBlbmFibGVkISAtIHVwZ3JhZGUgQklPUyBvciAiCgkJCQkidXNlIGZvcmNlPTFcbiIpOwoJCQlnb3RvIHJlbGVhc2VfcmVnaW9uOwoJCX0KCX0KCglkZXZfZGJnKCZwZGV2LT5kZXYsICJWVDU5Nl9zbWJhID0gMHglWFxuIiwgdnQ1OTZfc21iYSk7CgoJc3dpdGNoIChwZGV2LT5kZXZpY2UpIHsKCWNhc2UgUENJX0RFVklDRV9JRF9WSUFfQ1g3MDA6CgljYXNlIFBDSV9ERVZJQ0VfSURfVklBXzgyNTE6CgljYXNlIFBDSV9ERVZJQ0VfSURfVklBXzgyMzc6CgljYXNlIFBDSV9ERVZJQ0VfSURfVklBXzgyMzdBOgoJY2FzZSBQQ0lfREVWSUNFX0lEX1ZJQV84MjM1OgoJY2FzZSBQQ0lfREVWSUNFX0lEX1ZJQV84MjMzQToKCWNhc2UgUENJX0RFVklDRV9JRF9WSUFfODIzM18wOgoJCXZ0NTk2X2ZlYXR1cmVzIHw9IEZFQVRVUkVfSTJDQkxPQ0s7CgkJYnJlYWs7CgljYXNlIFBDSV9ERVZJQ0VfSURfVklBXzgyQzY4Nl80OgoJCS8qIFRoZSBWVDgyQzY4NkIgKHJldiAweDQwKSBkb2VzIHN1cHBvcnQgSTJDIGJsb2NrCgkJICAgdHJhbnNhY3Rpb25zLCBidXQgdGhlIFZUODJDNjg2QSAocmV2IDB4MzApIGRvZXNuJ3QgKi8KCQlpZiAoIXBjaV9yZWFkX2NvbmZpZ19ieXRlKHBkZXYsIFBDSV9SRVZJU0lPTl9JRCwgJnRlbXApCgkJICYmIHRlbXAgPj0gMHg0MCkKCQkJdnQ1OTZfZmVhdHVyZXMgfD0gRkVBVFVSRV9JMkNCTE9DSzsKCQlicmVhazsKCX0KCgl2dDU5Nl9hZGFwdGVyLmRldi5wYXJlbnQgPSAmcGRldi0+ZGV2OwoJc25wcmludGYodnQ1OTZfYWRhcHRlci5uYW1lLCBJMkNfTkFNRV9TSVpFLAoJCSAiU01CdXMgVmlhIFBybyBhZGFwdGVyIGF0ICUwNHgiLCB2dDU5Nl9zbWJhKTsKCgl2dDU5Nl9wZGV2ID0gcGNpX2Rldl9nZXQocGRldik7CglpZiAoaTJjX2FkZF9hZGFwdGVyKCZ2dDU5Nl9hZGFwdGVyKSkgewoJCXBjaV9kZXZfcHV0KHZ0NTk2X3BkZXYpOwoJCXZ0NTk2X3BkZXYgPSBOVUxMOwoJfQoKCS8qIEFsd2F5cyByZXR1cm4gZmFpbHVyZSBoZXJlLiAgVGhpcyBpcyB0byBhbGxvdyBvdGhlciBkcml2ZXJzIHRvIGJpbmQKCSAqIHRvIHRoaXMgcGNpIGRldmljZS4gIFdlIGRvbid0IHJlYWxseSB3YW50IHRvIGhhdmUgY29udHJvbCBvdmVyIHRoZQoJICogcGNpIGRldmljZSwgd2Ugb25seSB3YW50ZWQgdG8gcmVhZCBhcyBmZXcgcmVnaXN0ZXIgdmFsdWVzIGZyb20gaXQuCgkgKi8KCXJldHVybiAtRU5PREVWOwoKcmVsZWFzZV9yZWdpb246CglyZWxlYXNlX3JlZ2lvbih2dDU5Nl9zbWJhLCA4KTsKCXJldHVybiBlcnJvcjsKfQoKc3RhdGljIHN0cnVjdCBwY2lfZGV2aWNlX2lkIHZ0NTk2X2lkc1tdID0gewoJeyBQQ0lfREVWSUNFKFBDSV9WRU5ET1JfSURfVklBLCBQQ0lfREVWSUNFX0lEX1ZJQV84MkM1OTZfMyksCgkgIC5kcml2ZXJfZGF0YSA9IFNNQkJBMSB9LAoJeyBQQ0lfREVWSUNFKFBDSV9WRU5ET1JfSURfVklBLCBQQ0lfREVWSUNFX0lEX1ZJQV84MkM1OTZCXzMpLAoJICAuZHJpdmVyX2RhdGEgPSBTTUJCQTEgfSwKCXsgUENJX0RFVklDRShQQ0lfVkVORE9SX0lEX1ZJQSwgUENJX0RFVklDRV9JRF9WSUFfODJDNjg2XzQpLAoJICAuZHJpdmVyX2RhdGEgPSBTTUJCQTEgfSwKCXsgUENJX0RFVklDRShQQ0lfVkVORE9SX0lEX1ZJQSwgUENJX0RFVklDRV9JRF9WSUFfODIzM18wKSwKCSAgLmRyaXZlcl9kYXRhID0gU01CQkEzIH0sCgl7IFBDSV9ERVZJQ0UoUENJX1ZFTkRPUl9JRF9WSUEsIFBDSV9ERVZJQ0VfSURfVklBXzgyMzNBKSwKCSAgLmRyaXZlcl9kYXRhID0gU01CQkEzIH0sCgl7IFBDSV9ERVZJQ0UoUENJX1ZFTkRPUl9JRF9WSUEsIFBDSV9ERVZJQ0VfSURfVklBXzgyMzUpLAoJICAuZHJpdmVyX2RhdGEgPSBTTUJCQTMgfSwKCXsgUENJX0RFVklDRShQQ0lfVkVORE9SX0lEX1ZJQSwgUENJX0RFVklDRV9JRF9WSUFfODIzNyksCgkgIC5kcml2ZXJfZGF0YSA9IFNNQkJBMyB9LAoJeyBQQ0lfREVWSUNFKFBDSV9WRU5ET1JfSURfVklBLCBQQ0lfREVWSUNFX0lEX1ZJQV84MjM3QSksCgkgIC5kcml2ZXJfZGF0YSA9IFNNQkJBMyB9LAoJeyBQQ0lfREVWSUNFKFBDSV9WRU5ET1JfSURfVklBLCBQQ0lfREVWSUNFX0lEX1ZJQV84MjMxXzQpLAoJICAuZHJpdmVyX2RhdGEgPSBTTUJCQTEgfSwKCXsgUENJX0RFVklDRShQQ0lfVkVORE9SX0lEX1ZJQSwgUENJX0RFVklDRV9JRF9WSUFfODI1MSksCgkgIC5kcml2ZXJfZGF0YSA9IFNNQkJBMyB9LAoJeyBQQ0lfREVWSUNFKFBDSV9WRU5ET1JfSURfVklBLCBQQ0lfREVWSUNFX0lEX1ZJQV9DWDcwMCksCgkgIC5kcml2ZXJfZGF0YSA9IFNNQkJBMyB9LAoJeyAwLCB9Cn07CgpNT0RVTEVfREVWSUNFX1RBQkxFKHBjaSwgdnQ1OTZfaWRzKTsKCnN0YXRpYyBzdHJ1Y3QgcGNpX2RyaXZlciB2dDU5Nl9kcml2ZXIgPSB7CgkubmFtZQkJPSAidnQ1OTZfc21idXMiLAoJLmlkX3RhYmxlCT0gdnQ1OTZfaWRzLAoJLnByb2JlCQk9IHZ0NTk2X3Byb2JlLAp9OwoKc3RhdGljIGludCBfX2luaXQgaTJjX3Z0NTk2X2luaXQodm9pZCkKewoJcmV0dXJuIHBjaV9yZWdpc3Rlcl9kcml2ZXIoJnZ0NTk2X2RyaXZlcik7Cn0KCgpzdGF0aWMgdm9pZCBfX2V4aXQgaTJjX3Z0NTk2X2V4aXQodm9pZCkKewoJcGNpX3VucmVnaXN0ZXJfZHJpdmVyKCZ2dDU5Nl9kcml2ZXIpOwoJaWYgKHZ0NTk2X3BkZXYgIT0gTlVMTCkgewoJCWkyY19kZWxfYWRhcHRlcigmdnQ1OTZfYWRhcHRlcik7CgkJcmVsZWFzZV9yZWdpb24odnQ1OTZfc21iYSwgOCk7CgkJcGNpX2Rldl9wdXQodnQ1OTZfcGRldik7CgkJdnQ1OTZfcGRldiA9IE5VTEw7Cgl9Cn0KCk1PRFVMRV9BVVRIT1IoIkt5b3N0aSBNYWxra2kgPGttYWxra2lAY2MuaHV0LmZpPiwgIgoJICAgICAgIk1hcmsgRC4gU3R1ZGViYWtlciA8bWRzeHl6MTIzQHlhaG9vLmNvbT4gYW5kICIKCSAgICAgICJKZWFuIERlbHZhcmUgPGtoYWxpQGxpbnV4LWZyLm9yZz4iKTsKTU9EVUxFX0RFU0NSSVBUSU9OKCJ2dDgyYzU5NiBTTUJ1cyBkcml2ZXIiKTsKTU9EVUxFX0xJQ0VOU0UoIkdQTCIpOwoKbW9kdWxlX2luaXQoaTJjX3Z0NTk2X2luaXQpOwptb2R1bGVfZXhpdChpMmNfdnQ1OTZfZXhpdCk7Cg==