LyogLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLSAqLwovKiBpMmMtYWxnby1zaWJ5dGUuYyBpMmMgZHJpdmVyIGFsZ29yaXRobXMgZm9yIGJpdC1zaGlmdCBhZGFwdGVycwkJICAgICAqLwovKiAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tICovCi8qICAgQ29weXJpZ2h0IChDKSAyMDAxLDIwMDIsMjAwMyBCcm9hZGNvbSBDb3Jwb3JhdGlvbgogICAgIENvcHlyaWdodCAoQykgMTk5NS0yMDAwIFNpbW9uIEcuIFZvZ2wKCiAgICBUaGlzIHByb2dyYW0gaXMgZnJlZSBzb2Z0d2FyZTsgeW91IGNhbiByZWRpc3RyaWJ1dGUgaXQgYW5kL29yIG1vZGlmeQogICAgaXQgdW5kZXIgdGhlIHRlcm1zIG9mIHRoZSBHTlUgR2VuZXJhbCBQdWJsaWMgTGljZW5zZSBhcyBwdWJsaXNoZWQgYnkKICAgIHRoZSBGcmVlIFNvZnR3YXJlIEZvdW5kYXRpb247IGVpdGhlciB2ZXJzaW9uIDIgb2YgdGhlIExpY2Vuc2UsIG9yCiAgICAoYXQgeW91ciBvcHRpb24pIGFueSBsYXRlciB2ZXJzaW9uLgoKICAgIFRoaXMgcHJvZ3JhbSBpcyBkaXN0cmlidXRlZCBpbiB0aGUgaG9wZSB0aGF0IGl0IHdpbGwgYmUgdXNlZnVsLAogICAgYnV0IFdJVEhPVVQgQU5ZIFdBUlJBTlRZOyB3aXRob3V0IGV2ZW4gdGhlIGltcGxpZWQgd2FycmFudHkgb2YKICAgIE1FUkNIQU5UQUJJTElUWSBvciBGSVRORVNTIEZPUiBBIFBBUlRJQ1VMQVIgUFVSUE9TRS4gIFNlZSB0aGUKICAgIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlIGZvciBtb3JlIGRldGFpbHMuCgogICAgWW91IHNob3VsZCBoYXZlIHJlY2VpdmVkIGEgY29weSBvZiB0aGUgR05VIEdlbmVyYWwgUHVibGljIExpY2Vuc2UKICAgIGFsb25nIHdpdGggdGhpcyBwcm9ncmFtOyBpZiBub3QsIHdyaXRlIHRvIHRoZSBGcmVlIFNvZnR3YXJlCiAgICBGb3VuZGF0aW9uLCBJbmMuLCA2NzUgTWFzcyBBdmUsIENhbWJyaWRnZSwgTUEgMDIxMzksIFVTQS4JCSAgICAgKi8KLyogLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLSAqLwoKLyogV2l0aCBzb21lIGNoYW5nZXMgZnJvbSBLefZzdGkgTeRsa2tpIDxrbWFsa2tpQGNjLmh1dC5maT4gYW5kIGV2ZW4KICAgRnJvZG8gTG9vaWphYXJkIDxmcm9kb2xAZGRzLm5sPi4gICovCgovKiBQb3J0ZWQgZm9yIFNpQnl0ZSBTT0NzIGJ5IEJyb2FkY29tIENvcnBvcmF0aW9uLiAgKi8KCiNpbmNsdWRlIDxsaW51eC9jb25maWcuaD4KI2luY2x1ZGUgPGxpbnV4L2tlcm5lbC5oPgojaW5jbHVkZSA8bGludXgvbW9kdWxlLmg+CiNpbmNsdWRlIDxsaW51eC9pbml0Lmg+CgojaW5jbHVkZSA8YXNtL2lvLmg+CiNpbmNsdWRlIDxhc20vc2lieXRlL3NiMTI1MF9yZWdzLmg+CiNpbmNsdWRlIDxhc20vc2lieXRlL3NiMTI1MF9zbWJ1cy5oPgoKI2luY2x1ZGUgPGxpbnV4L2kyYy5oPgojaW5jbHVkZSA8bGludXgvaTJjLWFsZ28tc2lieXRlLmg+CgovKiAtLS0tLSBnbG9iYWwgZGVmaW5lcyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLSAqLwojZGVmaW5lIFNNQl9DU1IoYSxyKSAoKGxvbmcpKGEtPnJlZ19iYXNlICsgcikpCgovKiAtLS0tLSBnbG9iYWwgdmFyaWFibGVzIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQkqLwoKLyogbW9kdWxlIHBhcmFtZXRlcnM6CiAqLwpzdGF0aWMgaW50IGJpdF9zY2FuPTA7CS8qIGhhdmUgYSBsb29rIGF0IHdoYXQncyBoYW5naW5nICdyb3VuZAkJKi8KCgpzdGF0aWMgaW50IHNtYnVzX3hmZXIoc3RydWN0IGkyY19hZGFwdGVyICppMmNfYWRhcCwgdTE2IGFkZHIsIAogICAgICAgICAgICAgICAgICAgICAgdW5zaWduZWQgc2hvcnQgZmxhZ3MsIGNoYXIgcmVhZF93cml0ZSwKICAgICAgICAgICAgICAgICAgICAgIHU4IGNvbW1hbmQsIGludCBzaXplLCB1bmlvbiBpMmNfc21idXNfZGF0YSAqIGRhdGEpCnsKCXN0cnVjdCBpMmNfYWxnb19zaWJ5dGVfZGF0YSAqYWRhcCA9IGkyY19hZGFwLT5hbGdvX2RhdGE7CiAgICAgICAgaW50IGRhdGFfYnl0ZXMgPSAwOwogICAgICAgIGludCBlcnJvcjsKCiAgICAgICAgd2hpbGUgKGNzcl9pbjMyKFNNQl9DU1IoYWRhcCwgUl9TTUJfU1RBVFVTKSkgJiBNX1NNQl9CVVNZKQogICAgICAgICAgICAgICAgOwoKICAgICAgICBzd2l0Y2ggKHNpemUpIHsKICAgICAgICBjYXNlIEkyQ19TTUJVU19RVUlDSzoKICAgICAgICAgICAgICAgIGNzcl9vdXQzMigoVl9TTUJfQUREUihhZGRyKSB8IChyZWFkX3dyaXRlID09IEkyQ19TTUJVU19SRUFEID8gTV9TTUJfUURBVEEgOiAwKSB8CgkJCSAgIFZfU01CX1RUX1FVSUNLQ01EKSwgU01CX0NTUihhZGFwLCBSX1NNQl9TVEFSVCkpOwogICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgY2FzZSBJMkNfU01CVVNfQllURToKICAgICAgICAgICAgICAgIGlmIChyZWFkX3dyaXRlID09IEkyQ19TTUJVU19SRUFEKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGNzcl9vdXQzMigoVl9TTUJfQUREUihhZGRyKSB8IFZfU01CX1RUX1JEMUJZVEUpLAoJCQkJICBTTUJfQ1NSKGFkYXAsIFJfU01CX1NUQVJUKSk7CiAgICAgICAgICAgICAgICAgICAgICAgIGRhdGFfYnl0ZXMgPSAxOwogICAgICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgICAgICAgICAgY3NyX291dDMyKFZfU01CX0NNRChjb21tYW5kKSwgU01CX0NTUihhZGFwLCBSX1NNQl9DTUQpKTsKICAgICAgICAgICAgICAgICAgICAgICAgY3NyX291dDMyKChWX1NNQl9BRERSKGFkZHIpIHwgVl9TTUJfVFRfV1IxQllURSksCgkJCQkgIFNNQl9DU1IoYWRhcCwgUl9TTUJfU1RBUlQpKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgIGNhc2UgSTJDX1NNQlVTX0JZVEVfREFUQToKICAgICAgICAgICAgICAgIGNzcl9vdXQzMihWX1NNQl9DTUQoY29tbWFuZCksIFNNQl9DU1IoYWRhcCwgUl9TTUJfQ01EKSk7CiAgICAgICAgICAgICAgICBpZiAocmVhZF93cml0ZSA9PSBJMkNfU01CVVNfUkVBRCkgewogICAgICAgICAgICAgICAgICAgICAgICBjc3Jfb3V0MzIoKFZfU01CX0FERFIoYWRkcikgfCBWX1NNQl9UVF9DTURfUkQxQllURSksCgkJCQkgIFNNQl9DU1IoYWRhcCwgUl9TTUJfU1RBUlQpKTsKICAgICAgICAgICAgICAgICAgICAgICAgZGF0YV9ieXRlcyA9IDE7CiAgICAgICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgICAgICAgICAgICBjc3Jfb3V0MzIoVl9TTUJfTEIoZGF0YS0+Ynl0ZSksIFNNQl9DU1IoYWRhcCwgUl9TTUJfREFUQSkpOwogICAgICAgICAgICAgICAgICAgICAgICBjc3Jfb3V0MzIoKFZfU01CX0FERFIoYWRkcikgfCBWX1NNQl9UVF9XUjJCWVRFKSwKCQkJCSAgU01CX0NTUihhZGFwLCBSX1NNQl9TVEFSVCkpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgY2FzZSBJMkNfU01CVVNfV09SRF9EQVRBOgogICAgICAgICAgICAgICAgY3NyX291dDMyKFZfU01CX0NNRChjb21tYW5kKSwgU01CX0NTUihhZGFwLCBSX1NNQl9DTUQpKTsKICAgICAgICAgICAgICAgIGlmIChyZWFkX3dyaXRlID09IEkyQ19TTUJVU19SRUFEKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGNzcl9vdXQzMigoVl9TTUJfQUREUihhZGRyKSB8IFZfU01CX1RUX0NNRF9SRDJCWVRFKSwKCQkJCSAgU01CX0NTUihhZGFwLCBSX1NNQl9TVEFSVCkpOwogICAgICAgICAgICAgICAgICAgICAgICBkYXRhX2J5dGVzID0gMjsKICAgICAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGNzcl9vdXQzMihWX1NNQl9MQihkYXRhLT53b3JkICYgMHhmZiksIFNNQl9DU1IoYWRhcCwgUl9TTUJfREFUQSkpOwogICAgICAgICAgICAgICAgICAgICAgICBjc3Jfb3V0MzIoVl9TTUJfTUIoZGF0YS0+d29yZCA+PiA4KSwgU01CX0NTUihhZGFwLCBSX1NNQl9EQVRBKSk7CiAgICAgICAgICAgICAgICAgICAgICAgIGNzcl9vdXQzMigoVl9TTUJfQUREUihhZGRyKSB8IFZfU01CX1RUX1dSMkJZVEUpLAoJCQkJICBTTUJfQ1NSKGFkYXAsIFJfU01CX1NUQVJUKSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICBkZWZhdWx0OgogICAgICAgICAgICAgICAgcmV0dXJuIC0xOyAgICAgIC8qIFhYWEtXIGJldHRlciBlcnJvciBjb2RlPyAqLwogICAgICAgIH0KCiAgICAgICAgd2hpbGUgKGNzcl9pbjMyKFNNQl9DU1IoYWRhcCwgUl9TTUJfU1RBVFVTKSkgJiBNX1NNQl9CVVNZKQogICAgICAgICAgICAgICAgOwoKICAgICAgICBlcnJvciA9IGNzcl9pbjMyKFNNQl9DU1IoYWRhcCwgUl9TTUJfU1RBVFVTKSk7CiAgICAgICAgaWYgKGVycm9yICYgTV9TTUJfRVJST1IpIHsKICAgICAgICAgICAgICAgIC8qIENsZWFyIGVycm9yIGJpdCBieSB3cml0aW5nIGEgMSAqLwogICAgICAgICAgICAgICAgY3NyX291dDMyKE1fU01CX0VSUk9SLCBTTUJfQ1NSKGFkYXAsIFJfU01CX1NUQVRVUykpOwogICAgICAgICAgICAgICAgcmV0dXJuIC0xOyAgICAgIC8qIFhYWEtXIGJldHRlciBlcnJvciBjb2RlPyAqLwogICAgICAgIH0KCiAgICAgICAgaWYgKGRhdGFfYnl0ZXMgPT0gMSkKICAgICAgICAgICAgICAgIGRhdGEtPmJ5dGUgPSBjc3JfaW4zMihTTUJfQ1NSKGFkYXAsIFJfU01CX0RBVEEpKSAmIDB4ZmY7CiAgICAgICAgaWYgKGRhdGFfYnl0ZXMgPT0gMikKICAgICAgICAgICAgICAgIGRhdGEtPndvcmQgPSBjc3JfaW4zMihTTUJfQ1NSKGFkYXAsIFJfU01CX0RBVEEpKSAmIDB4ZmZmZjsKCiAgICAgICAgcmV0dXJuIDA7Cn0KCnN0YXRpYyBpbnQgYWxnb19jb250cm9sKHN0cnVjdCBpMmNfYWRhcHRlciAqYWRhcHRlciwgCgl1bnNpZ25lZCBpbnQgY21kLCB1bnNpZ25lZCBsb25nIGFyZykKewoJcmV0dXJuIDA7Cn0KCnN0YXRpYyB1MzIgYml0X2Z1bmMoc3RydWN0IGkyY19hZGFwdGVyICphZGFwKQp7CglyZXR1cm4gKEkyQ19GVU5DX1NNQlVTX1FVSUNLIHwgSTJDX0ZVTkNfU01CVVNfQllURSB8CiAgICAgICAgICAgICAgICBJMkNfRlVOQ19TTUJVU19CWVRFX0RBVEEgfCBJMkNfRlVOQ19TTUJVU19XT1JEX0RBVEEpOwp9CgoKLyogLS0tLS1leHBvcnRlZCBhbGdvcml0aG0gZGF0YTogLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQkqLwoKc3RhdGljIHN0cnVjdCBpMmNfYWxnb3JpdGhtIGkyY19zaWJ5dGVfYWxnbyA9IHsKCS5uYW1lCQk9ICJTaUJ5dGUgYWxnb3JpdGhtIiwKCS5pZAkJPSBJMkNfQUxHT19TSUJZVEUsCgkuc21idXNfeGZlcgk9IHNtYnVzX3hmZXIsCgkuYWxnb19jb250cm9sCT0gYWxnb19jb250cm9sLCAvKiBpb2N0bCAqLwoJLmZ1bmN0aW9uYWxpdHkJPSBiaXRfZnVuYywKfTsKCi8qIAogKiByZWdpc3RlcmluZyBmdW5jdGlvbnMgdG8gbG9hZCBhbGdvcml0aG1zIGF0IHJ1bnRpbWUgCiAqLwppbnQgaTJjX3NpYnl0ZV9hZGRfYnVzKHN0cnVjdCBpMmNfYWRhcHRlciAqaTJjX2FkYXAsIGludCBzcGVlZCkKewoJaW50IGk7CglzdHJ1Y3QgaTJjX2FsZ29fc2lieXRlX2RhdGEgKmFkYXAgPSBpMmNfYWRhcC0+YWxnb19kYXRhOwoKCS8qIHJlZ2lzdGVyIG5ldyBhZGFwdGVyIHRvIGkyYyBtb2R1bGUuLi4gKi8KCglpMmNfYWRhcC0+aWQgfD0gaTJjX3NpYnl0ZV9hbGdvLmlkOwoJaTJjX2FkYXAtPmFsZ28gPSAmaTJjX3NpYnl0ZV9hbGdvOwogICAgICAgIAogICAgICAgIC8qIFNldCB0aGUgZnJlcXVlbmN5IHRvIDEwMCBrSHogKi8KICAgICAgICBjc3Jfb3V0MzIoc3BlZWQsIFNNQl9DU1IoYWRhcCxSX1NNQl9GUkVRKSk7CiAgICAgICAgY3NyX291dDMyKDAsIFNNQl9DU1IoYWRhcCxSX1NNQl9DT05UUk9MKSk7CgoJLyogc2NhbiBidXMgKi8KCWlmIChiaXRfc2NhbikgewogICAgICAgICAgICAgICAgdW5pb24gaTJjX3NtYnVzX2RhdGEgZGF0YTsKICAgICAgICAgICAgICAgIGludCByYzsKCQlwcmludGsoS0VSTl9JTkZPICIgaTJjLWFsZ28tc2lieXRlLm86IHNjYW5uaW5nIGJ1cyAlcy5cbiIsCgkJICAgICAgIGkyY19hZGFwLT5uYW1lKTsKCQlmb3IgKGkgPSAweDAwOyBpIDwgMHg3ZjsgaSsrKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIC8qIFhYWEtXIGlzIHRoaXMgYSByZWFsaXN0aWMgcHJvYmU/ICovCiAgICAgICAgICAgICAgICAgICAgICAgIHJjID0gc21idXNfeGZlcihpMmNfYWRhcCwgaSwgMCwgSTJDX1NNQlVTX1JFQUQsIDAsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBJMkNfU01CVVNfQllURV9EQVRBLCAmZGF0YSk7CgkJCWlmICghcmMpIHsKCQkJCXByaW50aygiKCUwMngpIixpKTsgCgkJCX0gZWxzZSAKCQkJCXByaW50aygiLiIpOyAKCQl9CgkJcHJpbnRrKCJcbiIpOwoJfQoKCWkyY19hZGRfYWRhcHRlcihpMmNfYWRhcCk7CgoJcmV0dXJuIDA7Cn0KCgppbnQgaTJjX3NpYnl0ZV9kZWxfYnVzKHN0cnVjdCBpMmNfYWRhcHRlciAqYWRhcCkKewoJaW50IHJlczsKCglpZiAoKHJlcyA9IGkyY19kZWxfYWRhcHRlcihhZGFwKSkgPCAwKQoJCXJldHVybiByZXM7CgoJcmV0dXJuIDA7Cn0KCmludCBfX2luaXQgaTJjX2FsZ29fc2lieXRlX2luaXQgKHZvaWQpCnsKCXByaW50aygiaTJjLWFsZ28tc2lieXRlLm86IGkyYyBTaUJ5dGUgYWxnb3JpdGhtIG1vZHVsZVxuIik7CglyZXR1cm4gMDsKfQoKCkVYUE9SVF9TWU1CT0woaTJjX3NpYnl0ZV9hZGRfYnVzKTsKRVhQT1JUX1NZTUJPTChpMmNfc2lieXRlX2RlbF9idXMpOwoKI2lmZGVmIE1PRFVMRQpNT0RVTEVfQVVUSE9SKCJLaXAgV2Fsa2VyLCBCcm9hZGNvbSBDb3JwLiIpOwpNT0RVTEVfREVTQ1JJUFRJT04oIlNpQnl0ZSBJMkMtQnVzIGFsZ29yaXRobSIpOwpNT0RVTEVfUEFSTShiaXRfc2NhbiwgImkiKTsKTU9EVUxFX1BBUk1fREVTQyhiaXRfc2NhbiwgIlNjYW4gZm9yIGFjdGl2ZSBjaGlwcyBvbiB0aGUgYnVzIik7Ck1PRFVMRV9MSUNFTlNFKCJHUEwiKTsKCmludCBpbml0X21vZHVsZSh2b2lkKSAKewoJcmV0dXJuIGkyY19hbGdvX3NpYnl0ZV9pbml0KCk7Cn0KCnZvaWQgY2xlYW51cF9tb2R1bGUodm9pZCkgCnsKfQojZW5kaWYK