LyoKICogRE9TIFZpcnR1YWwgTWFjaGluZQogKgogKiBDb3B5cmlnaHQgMTk5OCBPdmUgS+V2ZW4KICoKICogVGhpcyBjb2RlIGhhc24ndCBiZWVuIGNvbXBsZXRlbHkgY2xlYW5lZCB1cCB5ZXQuCiAqLwoKI2luY2x1ZGUgImNvbmZpZy5oIgoKI2luY2x1ZGUgPHN0ZGlvLmg+CiNpbmNsdWRlIDxzdGRsaWIuaD4KI2luY2x1ZGUgPHN0cmluZy5oPgojaW5jbHVkZSA8ZXJybm8uaD4KI2luY2x1ZGUgPGZjbnRsLmg+CiNpbmNsdWRlIDxzaWduYWwuaD4KI2luY2x1ZGUgPHVuaXN0ZC5oPgojaW5jbHVkZSA8c3lzL3RpbWUuaD4KI2luY2x1ZGUgPHN5cy90eXBlcy5oPgojaW5jbHVkZSA8c3lzL3N0YXQuaD4KCiNpbmNsdWRlICJ3aW5lL3dpbmJhc2UxNi5oIgojaW5jbHVkZSAid2luZS9leGNlcHRpb24uaCIKI2luY2x1ZGUgIndpbmRlZi5oIgojaW5jbHVkZSAid2luYmFzZS5oIgojaW5jbHVkZSAid2luZ2RpLmgiCiNpbmNsdWRlICJ3aW51c2VyLmgiCiNpbmNsdWRlICJ3aW5udC5oIgojaW5jbHVkZSAid2luY29uLmgiCgojaW5jbHVkZSAiY2FsbGJhY2suaCIKI2luY2x1ZGUgIm1zZG9zLmgiCiNpbmNsdWRlICJmaWxlLmgiCiNpbmNsdWRlICJtaXNjZW11LmgiCiNpbmNsdWRlICJkb3NleGUuaCIKI2luY2x1ZGUgImRvc21vZC5oIgojaW5jbHVkZSAic3RhY2tmcmFtZS5oIgojaW5jbHVkZSAiZGVidWd0b29scy5oIgoKREVDTEFSRV9ERUJVR19DSEFOTkVMKGludCkKREVDTEFSRV9ERUJVR19DSEFOTkVMKG1vZHVsZSkKREVDTEFSRV9ERUJVR19DSEFOTkVMKHJlbGF5KQoKI2lmZGVmIE1aX1NVUFBPUlRFRAoKI2lmZGVmIEhBVkVfU1lTX1ZNODZfSAojIGluY2x1ZGUgPHN5cy92bTg2Lmg+CiNlbmRpZgojaWZkZWYgSEFWRV9TWVNfTU1BTl9ICiMgaW5jbHVkZSA8c3lzL21tYW4uaD4KI2VuZGlmCgojZGVmaW5lIElGX0NMUihjdHgpIEVGTF9yZWcoY3R4KSAmPSB+VklGX01BU0sKI2RlZmluZSBJRl9FTkFCTEVEKGN0eCkgKEVGTF9yZWcoY3R4KSAmIFZJRl9NQVNLKQojZGVmaW5lIFNFVF9QRU5EKGN0eCkgRUZMX3JlZyhjdHgpIHw9IFZJUF9NQVNLCiNkZWZpbmUgQ0xSX1BFTkQoY3R4KSBFRkxfcmVnKGN0eCkgJj0gflZJUF9NQVNLCiNkZWZpbmUgSVNfUEVORChjdHgpIChFRkxfcmVnKGN0eCkgJiBWSVBfTUFTSykKCiN1bmRlZiBUUllfUElDUkVUVVJOCgpzdGF0aWMgdm9pZCBkb19leGNlcHRpb24oIGludCBzaWduYWwsIENPTlRFWFQ4NiAqY29udGV4dCApCnsKICAgIEVYQ0VQVElPTl9SRUNPUkQgcmVjOwogICAgaWYgKChzaWduYWwgPT0gU0lHVFJBUCkgfHwgKHNpZ25hbCA9PSBTSUdIVVApKQogICAgewogICAgICAgIHJlYy5FeGNlcHRpb25Db2RlICA9IEVYQ0VQVElPTl9CUkVBS1BPSU5UOwogICAgICAgIHJlYy5FeGNlcHRpb25GbGFncyA9IEVYQ0VQVElPTl9DT05USU5VQUJMRTsKICAgIH0KICAgIGVsc2UKICAgIHsKICAgICAgICByZWMuRXhjZXB0aW9uQ29kZSAgPSBFWENFUFRJT05fSUxMRUdBTF9JTlNUUlVDVElPTjsgIC8qIGdlbmVyaWMgZXJyb3IgKi8KICAgICAgICByZWMuRXhjZXB0aW9uRmxhZ3MgPSBFSF9OT05DT05USU5VQUJMRTsKICAgIH0KICAgIHJlYy5FeGNlcHRpb25SZWNvcmQgID0gTlVMTDsKICAgIHJlYy5FeGNlcHRpb25BZGRyZXNzID0gKExQVk9JRClFSVBfcmVnKGNvbnRleHQpOwogICAgcmVjLk51bWJlclBhcmFtZXRlcnMgPSAwOwogICAgRVhDX1J0bFJhaXNlRXhjZXB0aW9uKCAmcmVjLCBjb250ZXh0ICk7Cn0KCnN0YXRpYyB2b2lkIERPU1ZNX0R1bXAoIExQRE9TVEFTSyBscERvc1Rhc2ssIGludCBmbiwgaW50IHNpZywKICAgICAgICAgICAgICAgICAgICAgICAgc3RydWN0IHZtODZwbHVzX3N0cnVjdCpWTTg2ICkKewogdW5zaWduZWQgaW9mczsKIEJZVEUqaW5zdDsKIGludCB4OwoKIHN3aXRjaCAoVk04Nl9UWVBFKGZuKSkgewogIGNhc2UgVk04Nl9TSUdOQUw6CiAgIHByaW50ZigiVHJhcHBlZCBzaWduYWwgJWRcbiIsc2lnKTsgYnJlYWs7CiAgY2FzZSBWTTg2X1VOS05PV046CiAgIHByaW50ZigiVHJhcHBlZCB1bmhhbmRsZWQgR1BGXG4iKTsgYnJlYWs7CiAgY2FzZSBWTTg2X0lOVHg6CiAgIHByaW50ZigiVHJhcHBlZCBJTlQgJTAyeFxuIixWTTg2X0FSRyhmbikpOyBicmVhazsKICBjYXNlIFZNODZfU1RJOgogICBwcmludGYoIlRyYXBwZWQgU1RJXG4iKTsgYnJlYWs7CiAgY2FzZSBWTTg2X1BJQ1JFVFVSTjoKICAgcHJpbnRmKCJUcmFwcGVkIGR1ZSB0byBwZW5kaW5nIFBJQyByZXF1ZXN0XG4iKTsgYnJlYWs7CiAgY2FzZSBWTTg2X1RSQVA6CiAgIHByaW50ZigiVHJhcHBlZCBkZWJ1ZyByZXF1ZXN0XG4iKTsgYnJlYWs7CiAgZGVmYXVsdDoKICAgcHJpbnRmKCJUcmFwcGVkIHVua25vd24gVk04NiB0eXBlICVkIGFyZyAlZFxuIixWTTg2X1RZUEUoZm4pLFZNODZfQVJHKGZuKSk7IGJyZWFrOwogfQojZGVmaW5lIFJFR1MgVk04Ni0+cmVncwogZnByaW50ZihzdGRlcnIsIkFYPSUwNGxYIENYPSUwNGxYIERYPSUwNGxYIEJYPSUwNGxYXG4iLFJFR1MuZWF4LFJFR1MuZWN4LFJFR1MuZWR4LFJFR1MuZWJ4KTsKIGZwcmludGYoc3RkZXJyLCJTST0lMDRsWCBEST0lMDRsWCBTUD0lMDRsWCBCUD0lMDRsWFxuIixSRUdTLmVzaSxSRUdTLmVkaSxSRUdTLmVzcCxSRUdTLmVicCk7CiBmcHJpbnRmKHN0ZGVyciwiQ1M9JTA0WCBEUz0lMDRYIEVTPSUwNFggU1M9JTA0WFxuIixSRUdTLmNzLFJFR1MuZHMsUkVHUy5lcyxSRUdTLnNzKTsKIGZwcmludGYoc3RkZXJyLCJJUD0lMDRsWCBFRkxBR1M9JTA4bFhcbiIsUkVHUy5laXAsUkVHUy5lZmxhZ3MpOwoKIGlvZnM9KChEV09SRClSRUdTLmNzPDw0KStSRUdTLmVpcDsKI3VuZGVmIFJFR1MKIGluc3Q9KEJZVEUqKWxwRG9zVGFzay0+aW1nK2lvZnM7CiBwcmludGYoIk9wY29kZXM6Iik7CiBmb3IgKHg9MDsgeDw4OyB4KyspIHByaW50ZigiICUwMngiLGluc3RbeF0pOwogcHJpbnRmKCJcbiIpOwp9CgpzdGF0aWMgaW50IERPU1ZNX0ludCggaW50IHZlY3QsIENPTlRFWFQ4NiAqY29udGV4dCwgTFBET1NUQVNLIGxwRG9zVGFzayApCnsKIGV4dGVybiBVSU5UMTYgRFBNSV93cmFwX3NlZzsKCiBpZiAodmVjdD09MHgzMSkgewogIGlmIChDU19yZWcoY29udGV4dCk9PURQTUlfd3JhcF9zZWcpIHsKICAgLyogZXhpdCBmcm9tIHJlYWwtbW9kZSB3cmFwcGVyICovCiAgIHJldHVybiAtMTsKICB9CiAgLyogd2UgY291bGQgcHJvYmFibHkgbW92ZSBzb21lIG90aGVyIGRvZGd5IHN0dWZmIGhlcmUgdG9vIGZyb20gZHBtaS5jICovCiB9CiBJTlRfUmVhbE1vZGVJbnRlcnJ1cHQodmVjdCxjb250ZXh0KTsKIHJldHVybiAwOwp9CgpzdGF0aWMgdm9pZCBET1NWTV9TaW11bGF0ZUludCggaW50IHZlY3QsIENPTlRFWFQ4NiAqY29udGV4dCwgTFBET1NUQVNLIGxwRG9zVGFzayApCnsKICBGQVJQUk9DMTYgaGFuZGxlcj1JTlRfR2V0Uk1IYW5kbGVyKHZlY3QpOwoKICBpZiAoU0VMRUNUT1JPRihoYW5kbGVyKT09MHhmMDAwKSB7CiAgICAvKiBpZiBpbnRlcm5hbCBpbnRlcnJ1cHQsIGNhbGwgaXQgZGlyZWN0bHkgKi8KICAgIElOVF9SZWFsTW9kZUludGVycnVwdCh2ZWN0LGNvbnRleHQpOwogIH0gZWxzZSB7CiAgICBXT1JEKnN0YWNrPShXT1JEKikoVjg2QkFTRShjb250ZXh0KSsoKChEV09SRClTU19yZWcoY29udGV4dCkpPDw0KStMT1dPUkQoRVNQX3JlZyhjb250ZXh0KSkpOwogICAgV09SRCBmbGFnPUxPV09SRChFRkxfcmVnKGNvbnRleHQpKTsKCiAgICBpZiAoSUZfRU5BQkxFRChjb250ZXh0KSkgZmxhZ3w9SUZfTUFTSzsKICAgIGVsc2UgZmxhZyY9fklGX01BU0s7CgogICAgKigtLXN0YWNrKT1mbGFnOwogICAgKigtLXN0YWNrKT1DU19yZWcoY29udGV4dCk7CiAgICAqKC0tc3RhY2spPUxPV09SRChFSVBfcmVnKGNvbnRleHQpKTsKICAgIEVTUF9yZWcoY29udGV4dCktPTY7CiAgICBDU19yZWcoY29udGV4dCk9U0VMRUNUT1JPRihoYW5kbGVyKTsKICAgIEVJUF9yZWcoY29udGV4dCk9T0ZGU0VUT0YoaGFuZGxlcik7CiAgICBJRl9DTFIoY29udGV4dCk7CiAgfQp9CgojZGVmaW5lIFNIT1VMRF9QRU5EKHgpIFwKICAoeCAmJiAoKCFscERvc1Rhc2stPmN1cnJlbnQpIHx8ICh4LT5wcmlvcml0eSA8IGxwRG9zVGFzay0+Y3VycmVudC0+cHJpb3JpdHkpKSkKCnN0YXRpYyB2b2lkIERPU1ZNX1NlbmRRdWV1ZWRFdmVudChDT05URVhUODYgKmNvbnRleHQsIExQRE9TVEFTSyBscERvc1Rhc2spCnsKICBMUERPU0VWRU5UIGV2ZW50ID0gbHBEb3NUYXNrLT5wZW5kaW5nOwoKICBpZiAoU0hPVUxEX1BFTkQoZXZlbnQpKSB7CiAgICAvKiByZW1vdmUgZnJvbSAicGVuZGluZyIgbGlzdCAqLwogICAgbHBEb3NUYXNrLT5wZW5kaW5nID0gZXZlbnQtPm5leHQ7CiAgICAvKiBwcm9jZXNzIGV2ZW50ICovCiAgICBpZiAoZXZlbnQtPmlycT49MCkgewogICAgICAvKiBpdCdzIGFuIElSUSwgbW92ZSBpdCB0byAiY3VycmVudCIgbGlzdCAqLwogICAgICBldmVudC0+bmV4dCA9IGxwRG9zVGFzay0+Y3VycmVudDsKICAgICAgbHBEb3NUYXNrLT5jdXJyZW50ID0gZXZlbnQ7CiAgICAgIFRSQUNFXyhpbnQpKCJkaXNwYXRjaGluZyBJUlEgJWRcbiIsZXZlbnQtPmlycSk7CiAgICAgIC8qIG5vdGUgdGhhdCBpZiBET1NWTV9TaW11bGF0ZUludCBjYWxscyBhbiBpbnRlcm5hbCBpbnRlcnJ1cHQgZGlyZWN0bHksCiAgICAgICAqIGxwRG9zVGFzay0+Y3VycmVudCBtaWdodCBiZSBjbGVhcmVkIChhbmQgZXZlbnQgZnJlZWQpIGluIHRoaXMgdmVyeSBjYWxsISAqLwogICAgICBET1NWTV9TaW11bGF0ZUludCgoZXZlbnQtPmlycTw4KT8oZXZlbnQtPmlycSs4KTooZXZlbnQtPmlycS04KzB4NzApLGNvbnRleHQsbHBEb3NUYXNrKTsKICAgIH0gZWxzZSB7CiAgICAgIC8qIGNhbGxiYWNrIGV2ZW50ICovCiAgICAgIFRSQUNFXyhpbnQpKCJkaXNwYXRjaGluZyBjYWxsYmFjayBldmVudFxuIik7CiAgICAgICgqZXZlbnQtPnJlbGF5KShscERvc1Rhc2ssY29udGV4dCxldmVudC0+ZGF0YSk7CiAgICAgIGZyZWUoZXZlbnQpOwogICAgfQogIH0KICBpZiAoIVNIT1VMRF9QRU5EKGxwRG9zVGFzay0+cGVuZGluZykpIHsKICAgIFRSQUNFXyhpbnQpKCJjbGVhcmluZyBQZW5kaW5nIGZsYWdcbiIpOwogICAgQ0xSX1BFTkQoY29udGV4dCk7CiAgfQp9CgpzdGF0aWMgdm9pZCBET1NWTV9TZW5kUXVldWVkRXZlbnRzKENPTlRFWFQ4NiAqY29udGV4dCwgTFBET1NUQVNLIGxwRG9zVGFzaykKewogIC8qIHdlIHdpbGwgc2VuZCBhbGwgcXVldWVkIGV2ZW50cyBhcyBsb25nIGFzIGludGVycnVwdHMgYXJlIGVuYWJsZWQsCiAgICogYnV0IElSUSBldmVudHMgd2lsbCBkaXNhYmxlIGludGVycnVwdHMgYWdhaW4gKi8KICB3aGlsZSAoSVNfUEVORChjb250ZXh0KSAmJiBJRl9FTkFCTEVEKGNvbnRleHQpKQogICAgRE9TVk1fU2VuZFF1ZXVlZEV2ZW50KGNvbnRleHQsbHBEb3NUYXNrKTsKfQoKdm9pZCBET1NWTV9RdWV1ZUV2ZW50KCBpbnQgaXJxLCBpbnQgcHJpb3JpdHksIHZvaWQgKCpyZWxheSkoTFBET1NUQVNLLENPTlRFWFQ4Niosdm9pZCopLCB2b2lkICpkYXRhKQp7CiAgTFBET1NUQVNLIGxwRG9zVGFzayA9IE1aX0N1cnJlbnQoKTsKICBMUERPU0VWRU5UIGV2ZW50LCBjdXIsIHByZXY7CgogIGlmIChscERvc1Rhc2sgJiYgbHBEb3NUYXNrLT5lbnRlcmVkKSB7CiAgICBldmVudCA9IG1hbGxvYyhzaXplb2YoRE9TRVZFTlQpKTsKICAgIGlmICghZXZlbnQpIHsKICAgICAgRVJSXyhpbnQpKCJvdXQgb2YgbWVtb3J5IGFsbG9jYXRpbmcgZXZlbnQgZW50cnlcbiIpOwogICAgICByZXR1cm47CiAgICB9CiAgICBldmVudC0+aXJxID0gaXJxOyBldmVudC0+cHJpb3JpdHkgPSBwcmlvcml0eTsKICAgIGV2ZW50LT5yZWxheSA9IHJlbGF5OyBldmVudC0+ZGF0YSA9IGRhdGE7CgogICAgLyogaW5zZXJ0IGV2ZW50IGludG8gbGlua2VkIGxpc3QsIGluIG9yZGVyICphZnRlcioKICAgICAqIGFsbCBlYXJsaWVyIGV2ZW50cyBvZiBoaWdoZXIgb3IgZXF1YWwgcHJpb3JpdHkgKi8KICAgIGN1ciA9IGxwRG9zVGFzay0+cGVuZGluZzsgcHJldiA9IE5VTEw7CiAgICB3aGlsZSAoY3VyICYmIGN1ci0+cHJpb3JpdHk8PXByaW9yaXR5KSB7CiAgICAgIHByZXYgPSBjdXI7CiAgICAgIGN1ciA9IGN1ci0+bmV4dDsKICAgIH0KICAgIGV2ZW50LT5uZXh0ID0gY3VyOwogICAgaWYgKHByZXYpIHByZXYtPm5leHQgPSBldmVudDsKICAgIGVsc2UgbHBEb3NUYXNrLT5wZW5kaW5nID0gZXZlbnQ7CiAgICAKICAgIC8qIGdldCBkb3Ntb2QncyBhdHRlbnRpb24gdG8gdGhlIG5ldyBldmVudCwgaWYgbmVjZXNzYXJ5ICovCiAgICBpZiAoIWxwRG9zVGFzay0+c2lnX3NlbnQpIHsKICAgICAgVFJBQ0VfKGludCkoIm5ldyBldmVudCBxdWV1ZWQsIHNpZ25hbGxpbmcgZG9zbW9kXG4iKTsKICAgICAga2lsbChscERvc1Rhc2stPnRhc2ssU0lHVVNSMik7CiAgICAgIGxwRG9zVGFzay0+c2lnX3NlbnQrKzsKICAgIH0gZWxzZSB7CiAgICAgIFRSQUNFXyhpbnQpKCJuZXcgZXZlbnQgcXVldWVkXG4iKTsKICAgIH0KICB9IGVsc2UgewogICAgLyogRE9TIHN1YnN5c3RlbSBub3QgcnVubmluZyAqLwogICAgLyogKHRoaXMgcHJvYmFibHkgbWVhbnMgdGhhdCB3ZSdyZSBydW5uaW5nIGEgd2luMTYgYXBwCiAgICAgKiAgd2hpY2ggdXNlcyBEUE1JIHRvIHRodW5rIGRvd24gdG8gRE9TIHNlcnZpY2VzKSAqLwogICAgaWYgKGlycTwwKSB7CiAgICAgIC8qIGNhbGxiYWNrIGV2ZW50LCBwZXJmb3JtIGl0IHdpdGggZHVtbXkgY29udGV4dCAqLwogICAgICBDT05URVhUODYgY29udGV4dDsKICAgICAgbWVtc2V0KCZjb250ZXh0LDAsc2l6ZW9mKGNvbnRleHQpKTsKICAgICAgKCpyZWxheSkobHBEb3NUYXNrLCZjb250ZXh0LGRhdGEpOwogICAgfSBlbHNlIHsKICAgICAgRVJSXyhpbnQpKCJJUlEgd2l0aG91dCBET1MgdGFzazogc2hvdWxkIG5vdCBoYXBwZW4iKTsKICAgIH0KICB9Cn0KCiNkZWZpbmUgQ1YgQ1AoZWF4LEVBWCk7IENQKGVjeCxFQ1gpOyBDUChlZHgsRURYKTsgQ1AoZWJ4LEVCWCk7IFwKICAgICAgICAgICBDUChlc2ksRVNJKTsgQ1AoZWRpLEVESSk7IENQKGVzcCxFU1ApOyBDUChlYnAsRUJQKTsgXAogICAgICAgICAgIENQKGNzLENTKTsgQ1AoZHMsRFMpOyBDUChlcyxFUyk7IFwKICAgICAgICAgICBDUChzcyxTUyk7IENQKGZzLEZTKTsgQ1AoZ3MsR1MpOyBcCiAgICAgICAgICAgQ1AoZWlwLEVJUCk7IENQKGVmbGFncyxFRkwpCgpzdGF0aWMgaW50IERPU1ZNX1Byb2Nlc3MoIExQRE9TVEFTSyBscERvc1Rhc2ssIGludCBmbiwgaW50IHNpZywKICAgICAgICAgICAgICAgICAgICAgICAgICBzdHJ1Y3Qgdm04NnBsdXNfc3RydWN0KlZNODYgKQp7CiBDT05URVhUODYgY29udGV4dDsKIGludCByZXQ9MDsKCiNkZWZpbmUgQ1AoeCx5KSB5IyNfcmVnKCZjb250ZXh0KSA9IFZNODYtPnJlZ3MueAogIENWOwojdW5kZWYgQ1AKIGlmIChWTTg2X1RZUEUoZm4pPT1WTTg2X1VOS05PV04pIHsKICByZXQ9SU5TVFJfRW11bGF0ZUluc3RydWN0aW9uKCZjb250ZXh0KTsKI2RlZmluZSBDUCh4LHkpIFZNODYtPnJlZ3MueCA9IHkjI19yZWcoJmNvbnRleHQpCiAgQ1Y7CiN1bmRlZiBDUAogIGlmIChyZXQpIHJldHVybiAwOwogIHJldD0wOwogfQojaWZkZWYgVFJZX1BJQ1JFVFVSTgogaWYgKFZNODYtPnZtODZwbHVzLmZvcmNlX3JldHVybl9mb3JfcGljKSB7CiAgIFNFVF9QRU5EKCZjb250ZXh0KTsKIH0KI2Vsc2UKIC8qIGxpbnV4IGRvZXNuJ3QgcHJlc2VydmUgcGVuZGluZyBmbGFnIG9uIHJldHVybiAqLwogaWYgKFNIT1VMRF9QRU5EKGxwRG9zVGFzay0+cGVuZGluZykpIHsKICAgU0VUX1BFTkQoJmNvbnRleHQpOwogfQojZW5kaWYKCiBzd2l0Y2ggKFZNODZfVFlQRShmbikpIHsKICBjYXNlIFZNODZfU0lHTkFMOgogICBUUkFDRV8oaW50KSgiRE9TIG1vZHVsZSBjYXVnaHQgc2lnbmFsICVkXG4iLHNpZyk7CiAgIGlmICgoc2lnPT1TSUdBTFJNKSB8fCAoc2lnPT1TSUdVU1IyKSkgewogICAgIGlmIChzaWc9PVNJR0FMUk0pIHsKICAgICAgIGxwRG9zVGFzay0+c2lnX3NlbnQrKzsKICAgICAgIERPU1ZNX1F1ZXVlRXZlbnQoMCxET1NfUFJJT1JJVFlfUkVBTFRJTUUsTlVMTCxOVUxMKTsKICAgICB9CiAgICAgaWYgKGxwRG9zVGFzay0+cGVuZGluZykgewogICAgICAgVFJBQ0VfKGludCkoInNldHRpbmcgUGVuZGluZyBmbGFnLCBpbnRlcnJ1cHRzIGFyZSBjdXJyZW50bHkgJXNcbiIsCiAgICAgICAgICAgICAgICAgSUZfRU5BQkxFRCgmY29udGV4dCkgPyAiZW5hYmxlZCIgOiAiZGlzYWJsZWQiKTsKICAgICAgIFNFVF9QRU5EKCZjb250ZXh0KTsKICAgICAgIERPU1ZNX1NlbmRRdWV1ZWRFdmVudHMoJmNvbnRleHQsbHBEb3NUYXNrKTsKICAgICB9IGVsc2UgewogICAgICAgVFJBQ0VfKGludCkoIm5vIGV2ZW50cyBhcmUgcGVuZGluZywgY2xlYXJpbmcgUGVuZGluZyBmbGFnXG4iKTsKICAgICAgIENMUl9QRU5EKCZjb250ZXh0KTsKICAgICB9CiAgICAgbHBEb3NUYXNrLT5zaWdfc2VudC0tOwogICB9CiAgIGVsc2UgaWYgKChzaWc9PVNJR0hVUCkgfHwgKHNpZz09U0lHSUxMKSB8fCAoc2lnPT1TSUdTRUdWKSkgewogICAgICAgZG9fZXhjZXB0aW9uKCBzaWcsICZjb250ZXh0ICk7CiAgIH0gZWxzZSB7CiAgICBET1NWTV9EdW1wKGxwRG9zVGFzayxmbixzaWcsVk04Nik7CiAgICByZXQ9LTE7CiAgIH0KICAgYnJlYWs7CiAgY2FzZSBWTTg2X1VOS05PV046IC8qIHVuaGFuZGxlZCBHUEYgKi8KICAgRE9TVk1fRHVtcChscERvc1Rhc2ssZm4sc2lnLFZNODYpOwogICBkb19leGNlcHRpb24oIFNJR1NFR1YsICZjb250ZXh0ICk7CiAgIGJyZWFrOwogIGNhc2UgVk04Nl9JTlR4OgogICBpZiAoVFJBQ0VfT04ocmVsYXkpKQogICAgRFBSSU5URigiQ2FsbCBET1MgaW50IDB4JTAyeCAoRUFYPSUwOGx4KSByZXQ9JTA0bHg6JTA0bHhcbiIsVk04Nl9BUkcoZm4pLGNvbnRleHQuRWF4LGNvbnRleHQuU2VnQ3MsY29udGV4dC5FaXApOwogICByZXQ9RE9TVk1fSW50KFZNODZfQVJHKGZuKSwmY29udGV4dCxscERvc1Rhc2spOwogICBpZiAoVFJBQ0VfT04ocmVsYXkpKQogICAgRFBSSU5URigiUmV0ICBET1MgaW50IDB4JTAyeCAoRUFYPSUwOGx4KSByZXQ9JTA0bHg6JTA0bHhcbiIsVk04Nl9BUkcoZm4pLGNvbnRleHQuRWF4LGNvbnRleHQuU2VnQ3MsY29udGV4dC5FaXApOwogICBicmVhazsKICBjYXNlIFZNODZfU1RJOgogIGNhc2UgVk04Nl9QSUNSRVRVUk46CiAgICBUUkFDRV8oaW50KSgiRE9TIHRhc2sgZW5hYmxlZCBpbnRlcnJ1cHRzIHdpdGggZXZlbnRzIHBlbmRpbmcsIHNlbmRpbmcgZXZlbnRzXG4iKTsKICAgIERPU1ZNX1NlbmRRdWV1ZWRFdmVudHMoJmNvbnRleHQsbHBEb3NUYXNrKTsKICAgIGJyZWFrOwogIGNhc2UgVk04Nl9UUkFQOgogICBkb19leGNlcHRpb24oIFNJR1RSQVAsICZjb250ZXh0ICk7CiAgIGJyZWFrOwogIGRlZmF1bHQ6CiAgIERPU1ZNX0R1bXAobHBEb3NUYXNrLGZuLHNpZyxWTTg2KTsKICAgcmV0PS0xOwogfQoKI2RlZmluZSBDUCh4LHkpIFZNODYtPnJlZ3MueCA9IHkjI19yZWcoJmNvbnRleHQpCiBDVjsKI3VuZGVmIENQCiNpZmRlZiBUUllfUElDUkVUVVJOCiBWTTg2LT52bTg2cGx1cy5mb3JjZV9yZXR1cm5fZm9yX3BpYyA9IElTX1BFTkQoJmNvbnRleHQpID8gMSA6IDA7CiBDTFJfUEVORCgmY29udGV4dCk7CiNlbmRpZgogcmV0dXJuIHJldDsKfQoKc3RhdGljIHZvaWQgRE9TVk1fUHJvY2Vzc0NvbnNvbGUoTFBET1NUQVNLIGxwRG9zVGFzaykKewogIElOUFVUX1JFQ09SRCBtc2c7CiAgRFdPUkQgcmVzOwogIEJZVEUgc2NhbjsKCiAgaWYgKFJlYWRDb25zb2xlSW5wdXRBKEdldFN0ZEhhbmRsZShTVERfSU5QVVRfSEFORExFKSwmbXNnLDEsJnJlcykpIHsKICAgIHN3aXRjaCAobXNnLkV2ZW50VHlwZSkgewogICAgY2FzZSBLRVlfRVZFTlQ6CiAgICAgIHNjYW4gPSBtc2cuRXZlbnQuS2V5RXZlbnQud1ZpcnR1YWxTY2FuQ29kZTsKICAgICAgaWYgKCFtc2cuRXZlbnQuS2V5RXZlbnQuYktleURvd24pIHNjYW4gfD0gMHg4MDsKCiAgICAgIC8qIGNoZWNrIHdoZXRoZXIgZXh0ZW5kZWQgYml0IGlzIHNldCwKICAgICAgICogYW5kIGlmIHNvLCBxdWV1ZSB0aGUgZXh0ZW5zaW9uIHByZWZpeCAqLwogICAgICBpZiAobXNnLkV2ZW50LktleUV2ZW50LmR3Q29udHJvbEtleVN0YXRlICYgRU5IQU5DRURfS0VZKSB7CiAgICAgICAgSU5UX0ludDA5U2VuZFNjYW4oMHhFMCwwKTsKICAgICAgfQogICAgICBJTlRfSW50MDlTZW5kU2NhbihzY2FuLG1zZy5FdmVudC5LZXlFdmVudC51Q2hhci5Bc2NpaUNoYXIpOwogICAgICBicmVhazsKICAgIGRlZmF1bHQ6CiAgICAgIEZJWE1FXyhpbnQpKCJ1bmhhbmRsZWQgY29uc29sZSBldmVudDogJWRcbiIsIG1zZy5FdmVudFR5cGUpOwogICAgfQogIH0KfQoKc3RhdGljIHZvaWQgRE9TVk1fUHJvY2Vzc01lc3NhZ2UoTFBET1NUQVNLIGxwRG9zVGFzayxNU0cgKm1zZykKewogIEJZVEUgc2NhbiA9IDA7CgogIFRSQUNFXyhpbnQpKCJnb3QgbWVzc2FnZSAlMDR4LCB3cGFyYW09JTA4eCwgbHBhcmFtPSUwOGx4XG4iLG1zZy0+bWVzc2FnZSxtc2ctPndQYXJhbSxtc2ctPmxQYXJhbSk7CiAgaWYgKChtc2ctPm1lc3NhZ2U+PVdNX01PVVNFRklSU1QpJiYKICAgICAgKG1zZy0+bWVzc2FnZTw9V01fTU9VU0VMQVNUKSkgewogICAgSU5UX0ludDMzTWVzc2FnZShtc2ctPm1lc3NhZ2UsbXNnLT53UGFyYW0sbXNnLT5sUGFyYW0pOwogIH0gZWxzZSB7CiAgICBzd2l0Y2ggKG1zZy0+bWVzc2FnZSkgewogICAgY2FzZSBXTV9LRVlVUDoKICAgICAgc2NhbiA9IDB4ODA7CiAgICBjYXNlIFdNX0tFWURPV046CiAgICAgIHNjYW4gfD0gKG1zZy0+bFBhcmFtID4+IDE2KSAmIDB4N2Y7CgogICAgICAvKiBjaGVjayB3aGV0aGVyIGV4dGVuZGVkIGJpdCBpcyBzZXQsCiAgICAgICAqIGFuZCBpZiBzbywgcXVldWUgdGhlIGV4dGVuc2lvbiBwcmVmaXggKi8KICAgICAgaWYgKG1zZy0+bFBhcmFtICYgMHgxMDAwMDAwKSB7CgkvKiBGSVhNRTogc29tZSBrZXlzIChmdW5jdGlvbiBrZXlzKSBoYXZlCgkgKiBleHRlbmRlZCBiaXQgc2V0IGV2ZW4gd2hlbiB0aGV5IHNob3VsZG4ndCwKCSAqIHNob3VsZCBjaGVjayBmb3IgdGhlbSAqLwoJSU5UX0ludDA5U2VuZFNjYW4oMHhFMCwwKTsKICAgICAgfQogICAgICBJTlRfSW50MDlTZW5kU2NhbihzY2FuLDApOwogICAgICBicmVhazsKICAgIH0KICB9Cn0KCnZvaWQgRE9TVk1fV2FpdCggaW50IHJlYWRfcGlwZSwgSEFORExFIGhPYmplY3QgKQp7CiAgTFBET1NUQVNLIGxwRG9zVGFzayA9IE1aX0N1cnJlbnQoKTsKICBNU0cgbXNnOwogIERXT1JEIHdhaXRyZXQ7CiAgSEFORExFIG9ianNbMl07CiAgaW50IG9iamM7CiAgQk9PTCBnb3RfbXNnID0gRkFMU0U7CgogIG9ianNbMF09bHBEb3NUYXNrLT5oQ29uSW5wdXQ7CiAgb2Jqc1sxXT1oT2JqZWN0OwogIG9iamM9aE9iamVjdD8yOjE7CiAgZG8gewogICAgLyogY2hlY2sgZm9yIG1lc3NhZ2VzICh3YXN0ZSB0aW1lIGJlZm9yZSB0aGUgcmVzcG9uc2UgY2hlY2sgYmVsb3cpICovCiAgICB3aGlsZSAoQ2FsbG91dC5QZWVrTWVzc2FnZUEoJm1zZywwLDAsMCxQTV9SRU1PVkV8UE1fTk9ZSUVMRCkpIHsKICAgICAgLyogZ290IGEgbWVzc2FnZSAqLwogICAgICBET1NWTV9Qcm9jZXNzTWVzc2FnZShscERvc1Rhc2ssJm1zZyk7CiAgICAgIC8qIHdlIGRvbid0IG5lZWQgYSBUcmFuc2xhdGVNZXNzYWdlIGhlcmUgKi8KICAgICAgQ2FsbG91dC5EaXNwYXRjaE1lc3NhZ2VBKCZtc2cpOwogICAgICBnb3RfbXNnID0gVFJVRTsKICAgIH0KICAgIGlmICghZ290X21zZykgewogICAgICAvKiBjaGVjayBmb3IgY29uc29sZSBpbnB1dCAqLwogICAgICBJTlBVVF9SRUNPUkQgbXNnOwogICAgICBEV09SRCBudW07CiAgICAgIGlmIChQZWVrQ29uc29sZUlucHV0QShvYmpzWzBdLCZtc2csMSwmbnVtKSAmJiBudW0pIHsKICAgICAgICBET1NWTV9Qcm9jZXNzQ29uc29sZShscERvc1Rhc2spOwogICAgICAgIGdvdF9tc2cgPSBUUlVFOwogICAgICB9CiAgICB9CiAgICBpZiAocmVhZF9waXBlID09IC0xKSB7CiAgICAgIGlmIChnb3RfbXNnKSBicmVhazsKICAgIH0gZWxzZSB7CiAgICAgIGZkX3NldCByZWFkZmRzOwogICAgICBzdHJ1Y3QgdGltZXZhbCB0aW1lb3V0PXswLDB9OwogICAgICAvKiBxdWljayBjaGVjayBmb3IgcmVzcG9uc2UgZnJvbSBkb3Ntb2QKICAgICAgICogKGZhc3RlciB0aGFuIGRvaW5nIHRoZSBmdWxsIGJsb2NraW5nIHdhaXQsIGlmIGRhdGEgYWxyZWFkeSBhdmFpbGFibGUpICovCiAgICAgIEZEX1pFUk8oJnJlYWRmZHMpOyBGRF9TRVQocmVhZF9waXBlLCZyZWFkZmRzKTsKICAgICAgaWYgKHNlbGVjdChyZWFkX3BpcGUrMSwmcmVhZGZkcyxOVUxMLE5VTEwsJnRpbWVvdXQpPjApCglicmVhazsKICAgIH0KICAgIC8qIG5vdGhpbmcgeWV0LCBibG9jayB3aGlsZSB3YWl0aW5nIGZvciBzb21ldGhpbmcgdG8gZG8gKi8KICAgIHdhaXRyZXQ9Q2FsbG91dC5Nc2dXYWl0Rm9yTXVsdGlwbGVPYmplY3RzKG9iamMsb2JqcyxGQUxTRSxJTkZJTklURSxRU19BTExJTlBVVCk7CiAgICBpZiAod2FpdHJldD09KERXT1JEKS0xKSB7CiAgICAgIEVSUl8obW9kdWxlKSgiZG9zdm0gd2FpdCBlcnJvcj0lbGRcbiIsR2V0TGFzdEVycm9yKCkpOwogICAgfQogICAgaWYgKChyZWFkX3BpcGUgIT0gLTEpICYmIGhPYmplY3QpIHsKICAgICAgaWYgKHdhaXRyZXQ9PShXQUlUX09CSkVDVF8wKzEpKSBicmVhazsKICAgIH0KICAgIGlmICh3YWl0cmV0PT1XQUlUX09CSkVDVF8wKSB7CiAgICAgIERPU1ZNX1Byb2Nlc3NDb25zb2xlKGxwRG9zVGFzayk7CiAgICB9CiAgfSB3aGlsZSAoVFJVRSk7Cn0KCmludCBET1NWTV9FbnRlciggQ09OVEVYVDg2ICpjb250ZXh0ICkKewogTFBET1NUQVNLIGxwRG9zVGFzayA9IE1aX0N1cnJlbnQoKTsKIHN0cnVjdCB2bTg2cGx1c19zdHJ1Y3QgVk04NjsKIGludCBzdGF0LGxlbixzaWc7CgogaWYgKCFscERvc1Rhc2spIHsKICAvKiBNWl9DcmVhdGVQcm9jZXNzIG9yIE1aX0FsbG9jRFBNSVRhc2sgc2hvdWxkIGhhdmUgYmVlbiBjYWxsZWQgZmlyc3QgKi8KICBFUlJfKG1vZHVsZSkoImRvc21vZCBoYXMgbm90IGJlZW4gaW5pdGlhbGl6ZWQhIik7CiAgcmV0dXJuIC0xOwogfQoKIGlmIChjb250ZXh0KSB7CiNkZWZpbmUgQ1AoeCx5KSBWTTg2LnJlZ3MueCA9IHkjI19yZWcoY29udGV4dCkKICBDVjsKI3VuZGVmIENQCiAgaWYgKFZNODYucmVncy5lZmxhZ3MgJiBJRl9NQVNLKQogICAgVk04Ni5yZWdzLmVmbGFncyB8PSBWSUZfTUFTSzsKIH0gZWxzZSB7Ci8qIGluaXRpYWwgc2V0dXAgKi8KICAvKiByZWdpc3RlcnMgKi8KICBtZW1zZXQoJlZNODYsMCxzaXplb2YoVk04NikpOwogIFZNODYucmVncy5jcz1scERvc1Rhc2stPmluaXRfY3M7CiAgVk04Ni5yZWdzLmVpcD1scERvc1Rhc2stPmluaXRfaXA7CiAgVk04Ni5yZWdzLnNzPWxwRG9zVGFzay0+aW5pdF9zczsKICBWTTg2LnJlZ3MuZXNwPWxwRG9zVGFzay0+aW5pdF9zcDsKICBWTTg2LnJlZ3MuZHM9bHBEb3NUYXNrLT5wc3Bfc2VnOwogIFZNODYucmVncy5lcz1scERvc1Rhc2stPnBzcF9zZWc7CiAgVk04Ni5yZWdzLmVmbGFncz1WSUZfTUFTSzsKICAvKiBobW0sIHdoYXQgZWxzZSBkbyB3ZSBuZWVkPyAqLwogfQoKIC8qIG1haW4gZXhjaGFuZ2UgbG9vcCAqLwogbHBEb3NUYXNrLT5lbnRlcmVkKys7CiBkbyB7CiAgVFJBQ0VfKG1vZHVsZSkoInRocmVhZCBpczogJWx4XG4iLEdldEN1cnJlbnRUaHJlYWRJZCgpKTsKICBzdGF0ID0gVk04Nl9FTlRFUjsKICBlcnJubyA9IDA7CiAgLyogdHJhbnNtaXQgVk04NiBzdHJ1Y3R1cmUgdG8gZG9zbW9kIHRhc2sgKi8KICBpZiAod3JpdGUobHBEb3NUYXNrLT53cml0ZV9waXBlLCZzdGF0LHNpemVvZihzdGF0KSkhPXNpemVvZihzdGF0KSkgewogICBFUlJfKG1vZHVsZSkoImRvc21vZCBzeW5jIGxvc3QsIGVycm5vPSVkLCBmZD0lZCwgcGlkPSVkXG4iLGVycm5vLGxwRG9zVGFzay0+d3JpdGVfcGlwZSxnZXRwaWQoKSk7CiAgIHJldHVybiAtMTsKICB9CiAgaWYgKHdyaXRlKGxwRG9zVGFzay0+d3JpdGVfcGlwZSwmVk04NixzaXplb2YoVk04NikpIT1zaXplb2YoVk04NikpIHsKICAgRVJSXyhtb2R1bGUpKCJkb3Ntb2Qgc3luYyBsb3N0LCBlcnJubz0lZFxuIixlcnJubyk7CiAgIHJldHVybiAtMTsKICB9CiAgLyogd2FpdCBmb3IgcmVzcG9uc2UsIGRvaW5nIG90aGVyIHRoaW5ncyBpbiB0aGUgbWVhbnRpbWUgKi8KICBET1NWTV9XYWl0KGxwRG9zVGFzay0+cmVhZF9waXBlLCBscERvc1Rhc2stPmhSZWFkUGlwZSk7CiAgLyogcmVhZCByZXNwb25zZSAqLwogIHdoaWxlICgxKSB7CiAgICBpZiAoKGxlbj1yZWFkKGxwRG9zVGFzay0+cmVhZF9waXBlLCZzdGF0LHNpemVvZihzdGF0KSkpPT1zaXplb2Yoc3RhdCkpIGJyZWFrOwogICAgaWYgKCgoZXJybm89PUVJTlRSKXx8KGVycm5vPT1FQUdBSU4pKSYmKGxlbjw9MCkpIHsKICAgICBXQVJOXyhtb2R1bGUpKCJyZXJlYWRpbmcgZG9zbW9kIHJldHVybiBjb2RlIGR1ZSB0byBlcnJubz0lZCwgcmVzdWx0PSVkXG4iLGVycm5vLGxlbik7CiAgICAgY29udGludWU7CiAgICB9CiAgICBFUlJfKG1vZHVsZSkoImRvc21vZCBzeW5jIGxvc3QgcmVhZGluZyByZXR1cm4gY29kZSwgZXJybm89JWQsIHJlc3VsdD0lZFxuIixlcnJubyxsZW4pOwogICAgcmV0dXJuIC0xOwogIH0KICBUUkFDRV8obW9kdWxlKSgiZG9zbW9kIHJldHVybiBjb2RlPSVkXG4iLHN0YXQpOwogIGlmIChzdGF0PT1ET1NNT0RfTEVGVElETEUpIHsKICAgIGxwRG9zVGFzay0+aWRsaW5nLS07CiAgICBjb250aW51ZTsKICB9CiAgd2hpbGUgKDEpIHsKICAgIGlmICgobGVuPXJlYWQobHBEb3NUYXNrLT5yZWFkX3BpcGUsJlZNODYsc2l6ZW9mKFZNODYpKSk9PXNpemVvZihWTTg2KSkgYnJlYWs7CiAgICBpZiAoKChlcnJubz09RUlOVFIpfHwoZXJybm89PUVBR0FJTikpJiYobGVuPD0wKSkgewogICAgIFdBUk5fKG1vZHVsZSkoInJlcmVhZGluZyBkb3Ntb2QgVk04NiBzdHJ1Y3R1cmUgZHVlIHRvIGVycm5vPSVkLCByZXN1bHQ9JWRcbiIsZXJybm8sbGVuKTsKICAgICBjb250aW51ZTsKICAgIH0KICAgIEVSUl8obW9kdWxlKSgiZG9zbW9kIHN5bmMgbG9zdCByZWFkaW5nIFZNODYgc3RydWN0dXJlLCBlcnJubz0lZCwgcmVzdWx0PSVkXG4iLGVycm5vLGxlbik7CiAgICByZXR1cm4gLTE7CiAgfQogIGlmICgoc3RhdCYweGZmKT09RE9TTU9EX1NJR05BTCkgewogICAgd2hpbGUgKDEpIHsKICAgICAgaWYgKChsZW49cmVhZChscERvc1Rhc2stPnJlYWRfcGlwZSwmc2lnLHNpemVvZihzaWcpKSk9PXNpemVvZihzaWcpKSBicmVhazsKICAgICAgaWYgKCgoZXJybm89PUVJTlRSKXx8KGVycm5vPT1FQUdBSU4pKSYmKGxlbjw9MCkpIHsKCVdBUk5fKG1vZHVsZSkoInJlcmVhZGluZyBkb3Ntb2Qgc2lnbmFsIGR1ZSB0byBlcnJubz0lZCwgcmVzdWx0PSVkXG4iLGVycm5vLGxlbik7Cgljb250aW51ZTsKICAgICAgfQogICAgICBFUlJfKG1vZHVsZSkoImRvc21vZCBzeW5jIGxvc3QgcmVhZGluZyBzaWduYWwsIGVycm5vPSVkLCByZXN1bHQ9JWRcbiIsZXJybm8sbGVuKTsKICAgICAgcmV0dXJuIC0xOwogICAgfSB3aGlsZSAoMCk7CiAgfSBlbHNlIHNpZz0wOwogIC8qIGdvdCByZXNwb25zZSAqLwogfSB3aGlsZSAoRE9TVk1fUHJvY2VzcyhscERvc1Rhc2ssc3RhdCxzaWcsJlZNODYpPj0wKTsKIGxwRG9zVGFzay0+ZW50ZXJlZC0tOwoKIGlmIChjb250ZXh0KSB7CiNkZWZpbmUgQ1AoeCx5KSB5IyNfcmVnKGNvbnRleHQpID0gVk04Ni5yZWdzLngKICBDVjsKI3VuZGVmIENQCiB9CiByZXR1cm4gMDsKfQoKdm9pZCBET1NWTV9QSUNfaW9wb3J0X291dCggV09SRCBwb3J0LCBCWVRFIHZhbCkKewogIExQRE9TVEFTSyBscERvc1Rhc2sgPSBNWl9DdXJyZW50KCk7CiAgTFBET1NFVkVOVCBldmVudDsKCiAgaWYgKGxwRG9zVGFzaykgewogICAgaWYgKChwb3J0PT0weDIwKSAmJiAodmFsPT0weDIwKSkgewogICAgICBpZiAobHBEb3NUYXNrLT5jdXJyZW50KSB7CgkvKiBFT0kgKEVuZCBPZiBJbnRlcnJ1cHQpICovCglUUkFDRV8oaW50KSgicmVjZWl2ZWQgRU9JIGZvciBjdXJyZW50IElSUSwgY2xlYXJpbmdcbiIpOwoJZXZlbnQgPSBscERvc1Rhc2stPmN1cnJlbnQ7CglscERvc1Rhc2stPmN1cnJlbnQgPSBldmVudC0+bmV4dDsKCWlmIChldmVudC0+cmVsYXkpCgkoKmV2ZW50LT5yZWxheSkobHBEb3NUYXNrLE5VTEwsZXZlbnQtPmRhdGEpOwoJZnJlZShldmVudCk7CgoJaWYgKGxwRG9zVGFzay0+cGVuZGluZyAmJgoJICAgICFscERvc1Rhc2stPnNpZ19zZW50KSB7CgkgIC8qIGFub3RoZXIgZXZlbnQgaXMgcGVuZGluZywgd2hpY2ggd2Ugc2hvdWxkIHByb2JhYmx5CgkgICAqIGJlIGFibGUgdG8gcHJvY2VzcyBub3csIHNvIHRlbGwgZG9zbW9kIGFib3V0IGl0ICovCgkgIFRSQUNFXyhpbnQpKCJhbm90aGVyIGV2ZW50IHBlbmRpbmcsIHNpZ25hbGxpbmcgZG9zbW9kXG4iKTsKCSAga2lsbChscERvc1Rhc2stPnRhc2ssU0lHVVNSMik7CgkgIGxwRG9zVGFzay0+c2lnX3NlbnQrKzsKCX0KICAgICAgfSBlbHNlIHsKCVdBUk5fKGludCkoIkVPSSB3aXRob3V0IGFjdGl2ZSBJUlFcbiIpOwogICAgICB9CiAgICB9IGVsc2UgewogICAgICBGSVhNRV8oaW50KSgidW5yZWNvZ25pemVkIFBJQyBjb21tYW5kICUwMnhcbiIsdmFsKTsKICAgIH0KICB9Cn0KCnZvaWQgRE9TVk1fU2V0VGltZXIoIHVuc2lnbmVkIHRpY2tzICkKewogIExQRE9TVEFTSyBscERvc1Rhc2sgPSBNWl9DdXJyZW50KCk7CiAgaW50IHN0YXQ9RE9TTU9EX1NFVF9USU1FUjsKICBzdHJ1Y3QgdGltZXZhbCB0aW07CgogIGlmIChscERvc1Rhc2spIHsKICAgIC8qIHRoZSBQQyBjbG9ja3MgdGlja3MgYXQgMTE5MzE4MCBIeiAqLwogICAgdGltLnR2X3NlYz0wOwogICAgdGltLnR2X3VzZWM9KCh1bnNpZ25lZCBsb25nIGxvbmcpdGlja3MqMTAwMDAwMCkvMTE5MzE4MDsKICAgIC8qIHNhbml0eSBjaGVjayAqLwogICAgaWYgKCF0aW0udHZfdXNlYykgdGltLnR2X3VzZWM9MTsKCiAgICBpZiAod3JpdGUobHBEb3NUYXNrLT53cml0ZV9waXBlLCZzdGF0LHNpemVvZihzdGF0KSkhPXNpemVvZihzdGF0KSkgewogICAgICBFUlJfKG1vZHVsZSkoImRvc21vZCBzeW5jIGxvc3QsIGVycm5vPSVkXG4iLGVycm5vKTsKICAgICAgcmV0dXJuOwogICAgfQogICAgaWYgKHdyaXRlKGxwRG9zVGFzay0+d3JpdGVfcGlwZSwmdGltLHNpemVvZih0aW0pKSE9c2l6ZW9mKHRpbSkpIHsKICAgICAgRVJSXyhtb2R1bGUpKCJkb3Ntb2Qgc3luYyBsb3N0LCBlcnJubz0lZFxuIixlcnJubyk7CiAgICAgIHJldHVybjsKICAgIH0KICAgIC8qIHRoZXJlJ3Mgbm8gcmV0dXJuICovCiAgfQp9Cgp1bnNpZ25lZCBET1NWTV9HZXRUaW1lciggdm9pZCApCnsKICBMUERPU1RBU0sgbHBEb3NUYXNrID0gTVpfQ3VycmVudCgpOwogIGludCBzdGF0PURPU01PRF9HRVRfVElNRVI7CiAgc3RydWN0IHRpbWV2YWwgdGltOwoKICBpZiAobHBEb3NUYXNrKSB7CiAgICBpZiAod3JpdGUobHBEb3NUYXNrLT53cml0ZV9waXBlLCZzdGF0LHNpemVvZihzdGF0KSkhPXNpemVvZihzdGF0KSkgewogICAgICBFUlJfKG1vZHVsZSkoImRvc21vZCBzeW5jIGxvc3QsIGVycm5vPSVkXG4iLGVycm5vKTsKICAgICAgcmV0dXJuIDA7CiAgICB9CiAgICAvKiByZWFkIHJlc3BvbnNlICovCiAgICB3aGlsZSAoMSkgewogICAgICBpZiAocmVhZChscERvc1Rhc2stPnJlYWRfcGlwZSwmdGltLHNpemVvZih0aW0pKT09c2l6ZW9mKHRpbSkpIGJyZWFrOwogICAgICBpZiAoKGVycm5vPT1FSU5UUil8fChlcnJubz09RUFHQUlOKSkgY29udGludWU7CiAgICAgIEVSUl8obW9kdWxlKSgiZG9zbW9kIHN5bmMgbG9zdCwgZXJybm89JWRcbiIsZXJybm8pOwogICAgICByZXR1cm4gMDsKICAgIH0KICAgIHJldHVybiAoKHVuc2lnbmVkIGxvbmcgbG9uZyl0aW0udHZfdXNlYyoxMTkzMTgwKS8xMDAwMDAwOwogIH0KICByZXR1cm4gMDsKfQoKdm9pZCBET1NWTV9TZXRTeXN0ZW1EYXRhKCBpbnQgaWQsIHZvaWQgKmRhdGEgKQp7CiAgTFBET1NUQVNLIGxwRG9zVGFzayA9IE1aX0N1cnJlbnQoKTsKICBET1NTWVNURU0gKnN5cywgKnByZXY7CgogIGlmIChscERvc1Rhc2spIHsKICAgIHN5cyA9IGxwRG9zVGFzay0+c3lzOwogICAgcHJldiA9IE5VTEw7CiAgICB3aGlsZSAoc3lzICYmIChzeXMtPmlkICE9IGlkKSkgewogICAgICBwcmV2ID0gc3lzOwogICAgICBzeXMgPSBzeXMtPm5leHQ7CiAgICB9CiAgICBpZiAoc3lzKSB7CiAgICAgIGZyZWUoc3lzLT5kYXRhKTsKICAgICAgc3lzLT5kYXRhID0gZGF0YTsKICAgIH0gZWxzZSB7CiAgICAgIHN5cyA9IG1hbGxvYyhzaXplb2YoRE9TU1lTVEVNKSk7CiAgICAgIHN5cy0+aWQgPSBpZDsKICAgICAgc3lzLT5kYXRhID0gZGF0YTsKICAgICAgc3lzLT5uZXh0ID0gTlVMTDsKICAgICAgaWYgKHByZXYpIHByZXYtPm5leHQgPSBzeXM7CiAgICAgIGVsc2UgbHBEb3NUYXNrLT5zeXMgPSBzeXM7CiAgICB9CiAgfSBlbHNlIGZyZWUoZGF0YSk7Cn0KCnZvaWQqIERPU1ZNX0dldFN5c3RlbURhdGEoIGludCBpZCApCnsKICBMUERPU1RBU0sgbHBEb3NUYXNrID0gTVpfQ3VycmVudCgpOwogIERPU1NZU1RFTSAqc3lzOwoKICBpZiAobHBEb3NUYXNrKSB7CiAgICBzeXMgPSBscERvc1Rhc2stPnN5czsKICAgIHdoaWxlIChzeXMgJiYgKHN5cy0+aWQgIT0gaWQpKQogICAgICBzeXMgPSBzeXMtPm5leHQ7CiAgICBpZiAoc3lzKQogICAgICByZXR1cm4gc3lzLT5kYXRhOwogIH0KICByZXR1cm4gTlVMTDsKfQoKI2Vsc2UgLyogIU1aX1NVUFBPUlRFRCAqLwoKaW50IERPU1ZNX0VudGVyKCBDT05URVhUODYgKmNvbnRleHQgKQp7CiBFUlJfKG1vZHVsZSkoIkRPUyByZWFsbW9kZSBub3Qgc3VwcG9ydGVkIG9uIHRoaXMgYXJjaGl0ZWN0dXJlIVxuIik7CiByZXR1cm4gLTE7Cn0KCnZvaWQgRE9TVk1fV2FpdCggaW50IHJlYWRfcGlwZSwgSEFORExFIGhPYmplY3QpIHt9CnZvaWQgRE9TVk1fUElDX2lvcG9ydF9vdXQoIFdPUkQgcG9ydCwgQllURSB2YWwpIHt9CnZvaWQgRE9TVk1fU2V0VGltZXIoIHVuc2lnbmVkIHRpY2tzICkge30KdW5zaWduZWQgRE9TVk1fR2V0VGltZXIoIHZvaWQgKSB7IHJldHVybiAwOyB9CnZvaWQgRE9TVk1fU2V0U3lzdGVtRGF0YSggaW50IGlkLCB2b2lkICpkYXRhICkgeyBmcmVlKGRhdGEpOyB9CnZvaWQqIERPU1ZNX0dldFN5c3RlbURhdGEoIGludCBpZCApIHsgcmV0dXJuIE5VTEw7IH0Kdm9pZCBET1NWTV9RdWV1ZUV2ZW50KCBpbnQgaXJxLCBpbnQgcHJpb3JpdHksIHZvaWQgKCpyZWxheSkoTFBET1NUQVNLLENPTlRFWFQ4Niosdm9pZCopLCB2b2lkICpkYXRhKQp7CiAgaWYgKGlycTwwKSB7CiAgICAvKiBjYWxsYmFjayBldmVudCwgcGVyZm9ybSBpdCB3aXRoIGR1bW15IGNvbnRleHQgKi8KICAgIENPTlRFWFQ4NiBjb250ZXh0OwogICAgbWVtc2V0KCZjb250ZXh0LDAsc2l6ZW9mKGNvbnRleHQpKTsKICAgICgqcmVsYXkpKE5VTEwsJmNvbnRleHQsZGF0YSk7CiAgfSBlbHNlIHsKICAgIEVSUl8oaW50KSgiSVJRIHdpdGhvdXQgRE9TIHRhc2s6IHNob3VsZCBub3QgaGFwcGVuIik7CiAgfQp9CgojZW5kaWYK