LyogUG9ydGlvbnMgb2YgdGhpcyBmaWxlIGFyZSBzdWJqZWN0IHRvIHRoZSBmb2xsb3dpbmcgY29weXJpZ2h0KHMpLiAgU2VlCiAqIHRoZSBOZXQtU05NUCdzIENPUFlJTkcgZmlsZSBmb3IgbW9yZSBkZXRhaWxzIGFuZCBvdGhlciBjb3B5cmlnaHRzCiAqIHRoYXQgbWF5IGFwcGx5OgogKi8KLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgoJQ29weXJpZ2h0IDE5ODksIDE5OTEsIDE5OTIgYnkgQ2FybmVnaWUgTWVsbG9uIFVuaXZlcnNpdHkKCiAgICAgICAgICAgICAgICAgICAgICBBbGwgUmlnaHRzIFJlc2VydmVkCgpQZXJtaXNzaW9uIHRvIHVzZSwgY29weSwgbW9kaWZ5LCBhbmQgZGlzdHJpYnV0ZSB0aGlzIHNvZnR3YXJlIGFuZCBpdHMKZG9jdW1lbnRhdGlvbiBmb3IgYW55IHB1cnBvc2UgYW5kIHdpdGhvdXQgZmVlIGlzIGhlcmVieSBncmFudGVkLApwcm92aWRlZCB0aGF0IHRoZSBhYm92ZSBjb3B5cmlnaHQgbm90aWNlIGFwcGVhciBpbiBhbGwgY29waWVzIGFuZCB0aGF0CmJvdGggdGhhdCBjb3B5cmlnaHQgbm90aWNlIGFuZCB0aGlzIHBlcm1pc3Npb24gbm90aWNlIGFwcGVhciBpbgpzdXBwb3J0aW5nIGRvY3VtZW50YXRpb24sIGFuZCB0aGF0IHRoZSBuYW1lIG9mIENNVSBub3QgYmUKdXNlZCBpbiBhZHZlcnRpc2luZyBvciBwdWJsaWNpdHkgcGVydGFpbmluZyB0byBkaXN0cmlidXRpb24gb2YgdGhlCnNvZnR3YXJlIHdpdGhvdXQgc3BlY2lmaWMsIHdyaXR0ZW4gcHJpb3IgcGVybWlzc2lvbi4KCkNNVSBESVNDTEFJTVMgQUxMIFdBUlJBTlRJRVMgV0lUSCBSRUdBUkQgVE8gVEhJUyBTT0ZUV0FSRSwgSU5DTFVESU5HCkFMTCBJTVBMSUVEIFdBUlJBTlRJRVMgT0YgTUVSQ0hBTlRBQklMSVRZIEFORCBGSVRORVNTLCBJTiBOTyBFVkVOVCBTSEFMTApDTVUgQkUgTElBQkxFIEZPUiBBTlkgU1BFQ0lBTCwgSU5ESVJFQ1QgT1IgQ09OU0VRVUVOVElBTCBEQU1BR0VTIE9SCkFOWSBEQU1BR0VTIFdIQVRTT0VWRVIgUkVTVUxUSU5HIEZST00gTE9TUyBPRiBVU0UsIERBVEEgT1IgUFJPRklUUywKV0hFVEhFUiBJTiBBTiBBQ1RJT04gT0YgQ09OVFJBQ1QsIE5FR0xJR0VOQ0UgT1IgT1RIRVIgVE9SVElPVVMgQUNUSU9OLApBUklTSU5HIE9VVCBPRiBPUiBJTiBDT05ORUNUSU9OIFdJVEggVEhFIFVTRSBPUiBQRVJGT1JNQU5DRSBPRiBUSElTClNPRlRXQVJFLgoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCi8qCiAqIFBvcnRpb25zIG9mIHRoaXMgZmlsZSBhcmUgY29weXJpZ2h0ZWQgYnk6CiAqIENvcHlyaWdodCBDb3B5cmlnaHQgMjAwMyBTdW4gTWljcm9zeXN0ZW1zLCBJbmMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAqIFVzZSBpcyBzdWJqZWN0IHRvIGxpY2Vuc2UgdGVybXMgc3BlY2lmaWVkIGluIHRoZSBDT1BZSU5HIGZpbGUKICogZGlzdHJpYnV0ZWQgd2l0aCB0aGUgTmV0LVNOTVAgcGFja2FnZS4KICovCgovKiogQGRlZmdyb3VwIGxpYnJhcnkgVGhlIE5ldC1TTk1QIGxpYnJhcnkKICogIEB7CiAqLwovKgogKiBzbm1wX2FwaS5jIC0gQVBJIGZvciBhY2Nlc3MgdG8gc25tcC4KICovCiNpbmNsdWRlIDxuZXQtc25tcC9uZXQtc25tcC1jb25maWcuaD4KCiNpbmNsdWRlIDxzdGRpby5oPgojaW5jbHVkZSA8Y3R5cGUuaD4KI2lmIEhBVkVfU1RETElCX0gKI2luY2x1ZGUgPHN0ZGxpYi5oPgojZW5kaWYKI2lmIEhBVkVfU1RSSU5HX0gKI2luY2x1ZGUgPHN0cmluZy5oPgojZWxzZQojaW5jbHVkZSA8c3RyaW5ncy5oPgojZW5kaWYKI2lmIEhBVkVfVU5JU1REX0gKI2luY2x1ZGUgPHVuaXN0ZC5oPgojZW5kaWYKI2luY2x1ZGUgPHN5cy90eXBlcy5oPgojaWYgSEFWRV9TWVNfUEFSQU1fSAojaW5jbHVkZSA8c3lzL3BhcmFtLmg+CiNlbmRpZgojaWYgVElNRV9XSVRIX1NZU19USU1FCiMgaWZkZWYgV0lOMzIKIyAgaW5jbHVkZSA8c3lzL3RpbWViLmg+CiMgZWxzZQojICBpbmNsdWRlIDxzeXMvdGltZS5oPgojIGVuZGlmCiMgaW5jbHVkZSA8dGltZS5oPgojZWxzZQojIGlmIEhBVkVfU1lTX1RJTUVfSAojICBpbmNsdWRlIDxzeXMvdGltZS5oPgojIGVsc2UKIyAgaW5jbHVkZSA8dGltZS5oPgojIGVuZGlmCiNlbmRpZgojaWYgSEFWRV9ORVRJTkVUX0lOX0gKI2luY2x1ZGUgPG5ldGluZXQvaW4uaD4KI2VuZGlmCiNpZiBIQVZFX0FSUEFfSU5FVF9ICiNpbmNsdWRlIDxhcnBhL2luZXQuaD4KI2VuZGlmCiNpZiBIQVZFX1NZU19TRUxFQ1RfSAojaW5jbHVkZSA8c3lzL3NlbGVjdC5oPgojZW5kaWYKI2lmIEhBVkVfSU9fSAojaW5jbHVkZSA8aW8uaD4KI2VuZGlmCiNpZiBIQVZFX1dJTlNPQ0tfSAojaW5jbHVkZSA8d2luc29jay5oPgojZW5kaWYKI2lmIEhBVkVfU1lTX1NPQ0tFVF9ICiNpbmNsdWRlIDxzeXMvc29ja2V0Lmg+CiNlbmRpZgojaWYgSEFWRV9TWVNfVU5fSAojaW5jbHVkZSA8c3lzL3VuLmg+CiNlbmRpZgojaWYgSEFWRV9ORVREQl9ICiNpbmNsdWRlIDxuZXRkYi5oPgojZW5kaWYKI2lmIEhBVkVfTkVUX0lGX0RMX0gKI2lmbmRlZiBkeW5peAojaW5jbHVkZSA8bmV0L2lmX2RsLmg+CiNlbHNlCiNpbmNsdWRlIDxzeXMvbmV0L2lmX2RsLmg+CiNlbmRpZgojZW5kaWYKI2luY2x1ZGUgPGVycm5vLmg+CgojaWYgSEFWRV9MT0NBTEVfSAojaW5jbHVkZSA8bG9jYWxlLmg+CiNlbmRpZgoKI2lmIEhBVkVfRE1BTExPQ19ICiNpbmNsdWRlIDxkbWFsbG9jLmg+CiNlbmRpZgoKI2RlZmluZSBTTk1QX05FRURfUkVRVUVTVF9MSVNUCiNpbmNsdWRlIDxuZXQtc25tcC90eXBlcy5oPgojaW5jbHVkZSA8bmV0LXNubXAvb3V0cHV0X2FwaS5oPgojaW5jbHVkZSA8bmV0LXNubXAvY29uZmlnX2FwaS5oPgojaW5jbHVkZSA8bmV0LXNubXAvdXRpbGl0aWVzLmg+CgojaW5jbHVkZSA8bmV0LXNubXAvbGlicmFyeS9hc24xLmg+CiNpbmNsdWRlIDxuZXQtc25tcC9saWJyYXJ5L3NubXAuaD4gICAgICAvKiBmb3IgeGR1bXAgJiB7YnVpbGQscGFyc2V9X3Zhcl9vcCAqLwojaW5jbHVkZSA8bmV0LXNubXAvbGlicmFyeS9zbm1wX2FwaS5oPgojaW5jbHVkZSA8bmV0LXNubXAvbGlicmFyeS9zbm1wX2NsaWVudC5oPgojaW5jbHVkZSA8bmV0LXNubXAvbGlicmFyeS9wYXJzZS5oPgojaW5jbHVkZSA8bmV0LXNubXAvbGlicmFyeS9taWIuaD4KI2luY2x1ZGUgPG5ldC1zbm1wL2xpYnJhcnkvaW50NjQuaD4KI2luY2x1ZGUgPG5ldC1zbm1wL2xpYnJhcnkvc25tcHYzLmg+CiNpbmNsdWRlIDxuZXQtc25tcC9saWJyYXJ5L2NhbGxiYWNrLmg+CiNpbmNsdWRlIDxuZXQtc25tcC9saWJyYXJ5L2NvbnRhaW5lci5oPgojaW5jbHVkZSA8bmV0LXNubXAvbGlicmFyeS9zbm1wX3NlY21vZC5oPgojaWZkZWYgTkVUU05NUF9TRUNNT0RfVVNNCiNpbmNsdWRlIDxuZXQtc25tcC9saWJyYXJ5L3NubXB1c20uaD4KI2VuZGlmCiNpZmRlZiBORVRTTk1QX1NFQ01PRF9LU00KI2luY2x1ZGUgPG5ldC1zbm1wL2xpYnJhcnkvc25tcGtzbS5oPgojZW5kaWYKI2luY2x1ZGUgPG5ldC1zbm1wL2xpYnJhcnkva2V5dG9vbHMuaD4KI2luY2x1ZGUgPG5ldC1zbm1wL2xpYnJhcnkvbGNkX3RpbWUuaD4KI2luY2x1ZGUgPG5ldC1zbm1wL2xpYnJhcnkvc25tcF9hbGFybS5oPgojaW5jbHVkZSA8bmV0LXNubXAvbGlicmFyeS9zbm1wX3RyYW5zcG9ydC5oPgojaW5jbHVkZSA8bmV0LXNubXAvbGlicmFyeS9zbm1wX3NlcnZpY2UuaD4KI2luY2x1ZGUgPG5ldC1zbm1wL2xpYnJhcnkvdmFjbS5oPgoKc3RhdGljIHZvaWQgICAgIF9pbml0X3NubXAodm9pZCk7CgojaW5jbHVkZSAiLi4vYWdlbnQvbWliZ3JvdXAvYWdlbnR4L3Byb3RvY29sLmgiCiNpbmNsdWRlIDxuZXQtc25tcC9saWJyYXJ5L3RyYW5zZm9ybV9vaWRzLmg+CiNpZm5kZWYgdGltZXJjbXAKI2RlZmluZQl0aW1lcmNtcCh0dnAsIHV2cCwgY21wKSBcCgkvKiBDU1RZTEVEICovIFwKCSgodHZwKS0+dHZfc2VjIGNtcCAodXZwKS0+dHZfc2VjIHx8IFwKCSgodHZwKS0+dHZfc2VjID09ICh1dnApLT50dl9zZWMgJiYgXAoJLyogQ1NUWUxFRCAqLyBcCgkodHZwKS0+dHZfdXNlYyBjbXAgKHV2cCktPnR2X3VzZWMpKQojZW5kaWYKI2lmbmRlZiB0aW1lcmNsZWFyCiNkZWZpbmUJdGltZXJjbGVhcih0dnApCQkodHZwKS0+dHZfc2VjID0gKHR2cCktPnR2X3VzZWMgPSAwCiNlbmRpZgoKLyoKICogR2xvYmFscy4KICovCiNkZWZpbmUgTUFYX1BBQ0tFVF9MRU5HVEgJKDB4N2ZmZmZmZmYpCiNpZm5kZWYgTkVUU05NUF9TVFJFQU1fUVVFVUVfTEVOCiNkZWZpbmUgTkVUU05NUF9TVFJFQU1fUVVFVUVfTEVOICA1CiNlbmRpZgoKI2lmbmRlZiBCU0Q0XzMKI2RlZmluZSBCU0Q0XzIKI2VuZGlmCgojaWZuZGVmIEZEX1NFVAoKdHlwZWRlZiBsb25nICAgIGZkX21hc2s7CiNkZWZpbmUgTkZEQklUUwkoc2l6ZW9mKGZkX21hc2spICogTkJCWSkgICAgICAgIC8qIGJpdHMgcGVyIG1hc2sgKi8KCiNkZWZpbmUJRkRfU0VUKG4sIHApCSgocCktPmZkc19iaXRzWyhuKS9ORkRCSVRTXSB8PSAoMSA8PCAoKG4pICUgTkZEQklUUykpKQojZGVmaW5lCUZEX0NMUihuLCBwKQkoKHApLT5mZHNfYml0c1sobikvTkZEQklUU10gJj0gfigxIDw8ICgobikgJSBORkRCSVRTKSkpCiNkZWZpbmUJRkRfSVNTRVQobiwgcCkJKChwKS0+ZmRzX2JpdHNbKG4pL05GREJJVFNdICYgKDEgPDwgKChuKSAlIE5GREJJVFMpKSkKI2RlZmluZSBGRF9aRVJPKHApCW1lbXNldCgocCksIDAsIHNpemVvZigqKHApKSkKI2VuZGlmCgpzdGF0aWMgb2lkICAgICAgZGVmYXVsdF9lbnRlcnByaXNlW10gPSB7IDEsIDMsIDYsIDEsIDQsIDEsIDMsIDEsIDEgfTsKLyoKICogZW50ZXJwcmlzZXMuY211LnN5c3RlbXMuY211U05NUCAKICovCgojZGVmaW5lIERFRkFVTFRfQ09NTVVOSVRZICAgInB1YmxpYyIKI2RlZmluZSBERUZBVUxUX1JFVFJJRVMJICAgIDUKI2RlZmluZSBERUZBVUxUX1RJTUVPVVQJICAgIDEwMDAwMDBMCiNkZWZpbmUgREVGQVVMVF9SRU1QT1JUCSAgICBTTk1QX1BPUlQKI2RlZmluZSBERUZBVUxUX0VOVEVSUFJJU0UgIGRlZmF1bHRfZW50ZXJwcmlzZQojZGVmaW5lIERFRkFVTFRfVElNRQkgICAgMAoKLyoKICogZG9uJ3Qgc2V0IGhpZ2hlciB0aGFuIDB4N2ZmZmZmZmYsIGFuZCBJIGRvdWJ0IGl0IHNob3VsZCBiZSB0aGF0IGhpZ2gKICogKiA9IDQgZ2lnIHNubXAgbWVzc2FnZXMgbWF4IAogKi8KI2RlZmluZSBNQVhJTVVNX1BBQ0tFVF9TSVpFIDB4N2ZmZmZmZmYKCi8qCiAqIEludGVybmFsIGluZm9ybWF0aW9uIGFib3V0IHRoZSBzdGF0ZSBvZiB0aGUgc25tcCBzZXNzaW9uLgogKi8Kc3RydWN0IHNubXBfaW50ZXJuYWxfc2Vzc2lvbiB7CiAgICBuZXRzbm1wX3JlcXVlc3RfbGlzdCAqcmVxdWVzdHM7ICAgICAvKiBJbmZvIGFib3V0IG91dHN0YW5kaW5nIHJlcXVlc3RzICovCiAgICBuZXRzbm1wX3JlcXVlc3RfbGlzdCAqcmVxdWVzdHNFbmQ7ICAvKiBwdHIgdG8gZW5kIG9mIGxpc3QgKi8KICAgIGludCAgICAgICAgICAgICAoKmhvb2tfcHJlKSAobmV0c25tcF9zZXNzaW9uICosIG5ldHNubXBfdHJhbnNwb3J0ICosCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHZvaWQgKiwgaW50KTsKICAgIGludCAgICAgICAgICAgICAoKmhvb2tfcGFyc2UpIChuZXRzbm1wX3Nlc3Npb24gKiwgbmV0c25tcF9wZHUgKiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB1X2NoYXIgKiwgc2l6ZV90KTsKICAgIGludCAgICAgICAgICAgICAoKmhvb2tfcG9zdCkgKG5ldHNubXBfc2Vzc2lvbiAqLCBuZXRzbm1wX3BkdSAqLCBpbnQpOwogICAgaW50ICAgICAgICAgICAgICgqaG9va19idWlsZCkgKG5ldHNubXBfc2Vzc2lvbiAqLCBuZXRzbm1wX3BkdSAqLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHVfY2hhciAqLCBzaXplX3QgKik7CiAgICBpbnQgICAgICAgICAgICAgKCpob29rX3JlYWxsb2NfYnVpbGQpIChuZXRzbm1wX3Nlc3Npb24gKiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIG5ldHNubXBfcGR1ICosIHVfY2hhciAqKiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNpemVfdCAqLCBzaXplX3QgKik7CiAgICBpbnQgICAgICAgICAgICAgKCpjaGVja19wYWNrZXQpICh1X2NoYXIgKiwgc2l6ZV90KTsKICAgIG5ldHNubXBfcGR1ICAgICooKmhvb2tfY3JlYXRlX3BkdSkgKG5ldHNubXBfdHJhbnNwb3J0ICosCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2b2lkICosIHNpemVfdCk7CgogICAgdV9jaGFyICAgICAgICAgKnBhY2tldDsKICAgIHNpemVfdCAgICAgICAgICBwYWNrZXRfbGVuLCBwYWNrZXRfc2l6ZTsKfTsKCi8qCiAqIFRoZSBsaXN0IG9mIGFjdGl2ZS9vcGVuIHNlc3Npb25zLgogKi8Kc3RydWN0IHNlc3Npb25fbGlzdCB7CiAgICBzdHJ1Y3Qgc2Vzc2lvbl9saXN0ICpuZXh0OwogICAgbmV0c25tcF9zZXNzaW9uICpzZXNzaW9uOwogICAgbmV0c25tcF90cmFuc3BvcnQgKnRyYW5zcG9ydDsKICAgIHN0cnVjdCBzbm1wX2ludGVybmFsX3Nlc3Npb24gKmludGVybmFsOwp9OwoKCgpzdGF0aWMgY29uc3QgY2hhciAqYXBpX2Vycm9yc1stU05NUEVSUl9NQVggKyAxXSA9IHsKICAgICJObyBlcnJvciIsICAgICAgICAgICAgICAgICAvKiBTTk1QRVJSX1NVQ0NFU1MgKi8KICAgICJHZW5lcmljIGVycm9yIiwgICAgICAgICAgICAvKiBTTk1QRVJSX0dFTkVSUiAqLwogICAgIkludmFsaWQgbG9jYWwgcG9ydCIsICAgICAgIC8qIFNOTVBFUlJfQkFEX0xPQ1BPUlQgKi8KICAgICJVbmtub3duIGhvc3QiLCAgICAgICAgICAgICAvKiBTTk1QRVJSX0JBRF9BRERSRVNTICovCiAgICAiVW5rbm93biBzZXNzaW9uIiwgICAgICAgICAgLyogU05NUEVSUl9CQURfU0VTU0lPTiAqLwogICAgIlRvbyBsb25nIiwgICAgICAgICAgICAgICAgIC8qIFNOTVBFUlJfVE9PX0xPTkcgKi8KICAgICJObyBzb2NrZXQiLCAgICAgICAgICAgICAgICAvKiBTTk1QRVJSX05PX1NPQ0tFVCAqLwogICAgIkNhbm5vdCBzZW5kIFYyIFBEVSBvbiBWMSBzZXNzaW9uIiwgLyogU05NUEVSUl9WMl9JTl9WMSAqLwogICAgIkNhbm5vdCBzZW5kIFYxIFBEVSBvbiBWMiBzZXNzaW9uIiwgLyogU05NUEVSUl9WMV9JTl9WMiAqLwogICAgIkJhZCB2YWx1ZSBmb3Igbm9uLXJlcGVhdGVycyIsICAgICAgLyogU05NUEVSUl9CQURfUkVQRUFURVJTICovCiAgICAiQmFkIHZhbHVlIGZvciBtYXgtcmVwZXRpdGlvbnMiLCAgICAvKiBTTk1QRVJSX0JBRF9SRVBFVElUSU9OUyAqLwogICAgIkVycm9yIGJ1aWxkaW5nIEFTTi4xIHJlcHJlc2VudGF0aW9uIiwgICAgICAvKiBTTk1QRVJSX0JBRF9BU04xX0JVSUxEICovCiAgICAiRmFpbHVyZSBpbiBzZW5kdG8iLCAgICAgICAgLyogU05NUEVSUl9CQURfU0VORFRPICovCiAgICAiQmFkIHBhcnNlIG9mIEFTTi4xIHR5cGUiLCAgLyogU05NUEVSUl9CQURfUEFSU0UgKi8KICAgICJCYWQgdmVyc2lvbiBzcGVjaWZpZWQiLCAgICAvKiBTTk1QRVJSX0JBRF9WRVJTSU9OICovCiAgICAiQmFkIHNvdXJjZSBwYXJ0eSBzcGVjaWZpZWQiLCAgICAgICAvKiBTTk1QRVJSX0JBRF9TUkNfUEFSVFkgKi8KICAgICJCYWQgZGVzdGluYXRpb24gcGFydHkgc3BlY2lmaWVkIiwgIC8qIFNOTVBFUlJfQkFEX0RTVF9QQVJUWSAqLwogICAgIkJhZCBjb250ZXh0IHNwZWNpZmllZCIsICAgIC8qIFNOTVBFUlJfQkFEX0NPTlRFWFQgKi8KICAgICJCYWQgY29tbXVuaXR5IHNwZWNpZmllZCIsICAvKiBTTk1QRVJSX0JBRF9DT01NVU5JVFkgKi8KICAgICJDYW5ub3Qgc2VuZCBub0F1dGgvUHJpdiIsICAgICAgIC8qIFNOTVBFUlJfTk9BVVRIX0RFU1BSSVYgKi8KICAgICJCYWQgQUNMIGRlZmluaXRpb24iLCAgICAgICAvKiBTTk1QRVJSX0JBRF9BQ0wgKi8KICAgICJCYWQgUGFydHkgZGVmaW5pdGlvbiIsICAgICAvKiBTTk1QRVJSX0JBRF9QQVJUWSAqLwogICAgIlNlc3Npb24gYWJvcnQgZmFpbHVyZSIsICAgIC8qIFNOTVBFUlJfQUJPUlQgKi8KICAgICJVbmtub3duIFBEVSB0eXBlIiwgICAgICAgICAvKiBTTk1QRVJSX1VOS05PV05fUERVICovCiAgICAiVGltZW91dCIsICAgICAgICAgICAgICAgICAgLyogU05NUEVSUl9USU1FT1VUICovCiAgICAiRmFpbHVyZSBpbiByZWN2ZnJvbSIsICAgICAgLyogU05NUEVSUl9CQURfUkVDVkZST00gKi8KICAgICJVbmFibGUgdG8gZGV0ZXJtaW5lIGNvbnRleHRFbmdpbmVJRCIsICAgICAgLyogU05NUEVSUl9CQURfRU5HX0lEICovCiAgICAiTm8gc2VjdXJpdHlOYW1lIHNwZWNpZmllZCIsICAgICAgICAvKiBTTk1QRVJSX0JBRF9TRUNfTkFNRSAqLwogICAgIlVuYWJsZSB0byBkZXRlcm1pbmUgc2VjdXJpdHlMZXZlbCIsICAgICAgICAvKiBTTk1QRVJSX0JBRF9TRUNfTEVWRUwgICovCiAgICAiQVNOLjEgcGFyc2UgZXJyb3IgaW4gbWVzc2FnZSIsICAgICAvKiBTTk1QRVJSX0FTTl9QQVJTRV9FUlIgKi8KICAgICJVbmtub3duIHNlY3VyaXR5IG1vZGVsIGluIG1lc3NhZ2UiLCAgICAgICAgLyogU05NUEVSUl9VTktOT1dOX1NFQ19NT0RFTCAqLwogICAgIkludmFsaWQgbWVzc2FnZSAoZS5nLiBtc2dGbGFncykiLCAgLyogU05NUEVSUl9JTlZBTElEX01TRyAqLwogICAgIlVua25vd24gZW5naW5lIElEIiwgICAgICAgIC8qIFNOTVBFUlJfVU5LTk9XTl9FTkdfSUQgKi8KICAgICJVbmtub3duIHVzZXIgbmFtZSIsICAgICAgICAvKiBTTk1QRVJSX1VOS05PV05fVVNFUl9OQU1FICovCiAgICAiVW5zdXBwb3J0ZWQgc2VjdXJpdHkgbGV2ZWwiLCAgICAgICAvKiBTTk1QRVJSX1VOU1VQUE9SVEVEX1NFQ19MRVZFTCAqLwogICAgIkF1dGhlbnRpY2F0aW9uIGZhaWx1cmUgKGluY29ycmVjdCBwYXNzd29yZCwgY29tbXVuaXR5IG9yIGtleSkiLCAgICAvKiBTTk1QRVJSX0FVVEhFTlRJQ0FUSU9OX0ZBSUxVUkUgKi8KICAgICJOb3QgaW4gdGltZSB3aW5kb3ciLCAgICAgICAvKiBTTk1QRVJSX05PVF9JTl9USU1FX1dJTkRPVyAqLwogICAgIkRlY3J5cHRpb24gZXJyb3IiLCAgICAgICAgIC8qIFNOTVBFUlJfREVDUllQVElPTl9FUlIgKi8KICAgICJTQ0FQSSBnZW5lcmFsIGZhaWx1cmUiLCAgICAvKiBTTk1QRVJSX1NDX0dFTkVSQUxfRkFJTFVSRSAqLwogICAgIlNDQVBJIHN1Yi1zeXN0ZW0gbm90IGNvbmZpZ3VyZWQiLCAgLyogU05NUEVSUl9TQ19OT1RfQ09ORklHVVJFRCAqLwogICAgIktleSB0b29scyBub3QgYXZhaWxhYmxlIiwgIC8qIFNOTVBFUlJfS1RfTk9UX0FWQUlMQUJMRSAqLwogICAgIlVua25vd24gUmVwb3J0IG1lc3NhZ2UiLCAgIC8qIFNOTVBFUlJfVU5LTk9XTl9SRVBPUlQgKi8KICAgICJVU00gZ2VuZXJpYyBlcnJvciIsICAgICAgICAvKiBTTk1QRVJSX1VTTV9HRU5FUklDRVJST1IgKi8KICAgICJVU00gdW5rbm93biBzZWN1cml0eSBuYW1lIChubyBzdWNoIHVzZXIgZXhpc3RzKSIsICAvKiBTTk1QRVJSX1VTTV9VTktOT1dOU0VDVVJJVFlOQU1FICovCiAgICAiVVNNIHVuc3VwcG9ydGVkIHNlY3VyaXR5IGxldmVsICh0aGlzIHVzZXIgaGFzIG5vdCBiZWVuIGNvbmZpZ3VyZWQgZm9yIHRoYXQgbGV2ZWwgb2Ygc2VjdXJpdHkpIiwgICAgLyogU05NUEVSUl9VU01fVU5TVVBQT1JURURTRUNVUklUWUxFVkVMICovCiAgICAiVVNNIGVuY3J5cHRpb24gZXJyb3IiLCAgICAgLyogU05NUEVSUl9VU01fRU5DUllQVElPTkVSUk9SICovCiAgICAiVVNNIGF1dGhlbnRpY2F0aW9uIGZhaWx1cmUgKGluY29ycmVjdCBwYXNzd29yZCBvciBrZXkpIiwgICAvKiBTTk1QRVJSX1VTTV9BVVRIRU5USUNBVElPTkZBSUxVUkUgKi8KICAgICJVU00gcGFyc2UgZXJyb3IiLCAgICAgICAgICAvKiBTTk1QRVJSX1VTTV9QQVJTRUVSUk9SICovCiAgICAiVVNNIHVua25vd24gZW5naW5lSUQiLCAgICAgLyogU05NUEVSUl9VU01fVU5LTk9XTkVOR0lORUlEICovCiAgICAiVVNNIG5vdCBpbiB0aW1lIHdpbmRvdyIsICAgLyogU05NUEVSUl9VU01fTk9USU5USU1FV0lORE9XICovCiAgICAiVVNNIGRlY3J5cHRpb24gZXJyb3IiLCAgICAgLyogU05NUEVSUl9VU01fREVDUllQVElPTkVSUk9SICovCiAgICAiTUlCIG5vdCBpbml0aWFsaXplZCIsICAgICAgLyogU05NUEVSUl9OT01JQiAqLwogICAgIlZhbHVlIG91dCBvZiByYW5nZSIsICAgICAgIC8qIFNOTVBFUlJfUkFOR0UgKi8KICAgICJTdWItaWQgb3V0IG9mIHJhbmdlIiwgICAgICAvKiBTTk1QRVJSX01BWF9TVUJJRCAqLwogICAgIkJhZCBzdWItaWQgaW4gb2JqZWN0IGlkZW50aWZpZXIiLCAgLyogU05NUEVSUl9CQURfU1VCSUQgKi8KICAgICJPYmplY3QgaWRlbnRpZmllciB0b28gbG9uZyIsICAgICAgIC8qIFNOTVBFUlJfTE9OR19PSUQgKi8KICAgICJCYWQgdmFsdWUgbmFtZSIsICAgICAgICAgICAvKiBTTk1QRVJSX0JBRF9OQU1FICovCiAgICAiQmFkIHZhbHVlIG5vdGF0aW9uIiwgICAgICAgLyogU05NUEVSUl9WQUxVRSAqLwogICAgIlVua25vd24gT2JqZWN0IElkZW50aWZpZXIiLCAgICAgICAgLyogU05NUEVSUl9VTktOT1dOX09CSklEICovCiAgICAiTm8gUERVIGluIHNubXBfc2VuZCIsICAgICAgLyogU05NUEVSUl9OVUxMX1BEVSAqLwogICAgIk1pc3NpbmcgdmFyaWFibGVzIGluIFBEVSIsIC8qIFNOTVBFUlJfTk9fVkFSUyAqLwogICAgIkJhZCB2YXJpYWJsZSB0eXBlIiwgICAgICAgIC8qIFNOTVBFUlJfVkFSX1RZUEUgKi8KICAgICJPdXQgb2YgbWVtb3J5IChtYWxsb2MgZmFpbHVyZSkiLCAgIC8qIFNOTVBFUlJfTUFMTE9DICovCiAgICAiS2VyYmVyb3MgcmVsYXRlZCBlcnJvciIsICAgLyogU05NUEVSUl9LUkI1ICovCiAgICAiUHJvdG9jb2wgZXJyb3IiLAkJLyogU05NUEVSUl9QUk9UT0NPTCAqLwogICAgIk9JRCBub3QgaW5jcmVhc2luZyIsICAgICAgIC8qIFNOTVBFUlJfT0lEX05PTklOQ1JFQVNJTkcgKi8KfTsKCnN0YXRpYyBjb25zdCBjaGFyICpzZWNMZXZlbE5hbWVbXSA9IHsKICAgICJCQURfU0VDX0xFVkVMIiwKICAgICJub0F1dGhOb1ByaXYiLAogICAgImF1dGhOb1ByaXYiLAogICAgImF1dGhQcml2Igp9OwoKLyoKICogTXVsdGlwbGUgdGhyZWFkcyBtYXkgY2hhbmdlcyB0aGVzZSB2YXJpYWJsZXMuCiAqIFN1Z2dlc3QgdXNpbmcgdGhlIFNpbmdsZSBBUEksIHdoaWNoIGRvZXMgbm90IHVzZSBTZXNzaW9ucy4KICoKICogUmVxaWQgbWF5IG5lZWQgdG8gYmUgcHJvdGVjdGVkLiBUaW1lIHdpbGwgdGVsbC4uLgogKgogKi8KLyoKICogTVRDUklUSUNBTF9SRVNPVVJDRQogKi8KLyoKICogdXNlIHRva2VuIGluIGNvbW1lbnRzIHRvIGluZGl2aWR1YWxseSBwcm90ZWN0IHRoZXNlIHJlc291cmNlcyAKICovCnN0cnVjdCBzZXNzaW9uX2xpc3QgKlNlc3Npb25zID0gTlVMTDsgICAvKiBNVF9MSUJfU0VTU0lPTiAqLwpzdGF0aWMgbG9uZyAgICAgUmVxaWQgPSAwOyAgICAgIC8qIE1UX0xJQl9SRVFVRVNUSUQgKi8Kc3RhdGljIGxvbmcgICAgIE1zZ2lkID0gMDsgICAgICAvKiBNVF9MSUJfTUVTU0FHRUlEICovCnN0YXRpYyBsb25nICAgICBTZXNzaWQgPSAwOyAgICAgLyogTVRfTElCX1NFU1NJT05JRCAqLwpzdGF0aWMgbG9uZyAgICAgVHJhbnNpZCA9IDA7ICAgIC8qIE1UX0xJQl9UUkFOU0lEICovCmludCAgICAgICAgICAgICBzbm1wX2Vycm5vID0gMDsKLyoKICogRU5EIE1UQ1JJVElDQUxfUkVTT1VSQ0UKICovCgovKgogKiBnbG9iYWwgZXJyb3IgZGV0YWlsIHN0b3JhZ2UKICovCnN0YXRpYyBjaGFyICAgICBzbm1wX2RldGFpbFsxOTJdOwpzdGF0aWMgaW50ICAgICAgc25tcF9kZXRhaWxfZiA9IDA7CgovKgogKiBQcm90b3R5cGVzLgogKi8KaW50ICAgICAgICAgICAgIHNubXBfYnVpbGQodV9jaGFyICoqIHBrdCwgc2l6ZV90ICogcGt0X2xlbiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgc2l6ZV90ICogb2Zmc2V0LCBuZXRzbm1wX3Nlc3Npb24gKiBwc3MsCiAgICAgICAgICAgICAgICAgICAgICAgICAgIG5ldHNubXBfcGR1ICpwZHUpOwpzdGF0aWMgaW50ICAgICAgc25tcF9wYXJzZSh2b2lkICosIG5ldHNubXBfc2Vzc2lvbiAqLCBuZXRzbm1wX3BkdSAqLAogICAgICAgICAgICAgICAgICAgICAgICAgICB1X2NoYXIgKiwgc2l6ZV90KTsKCnN0YXRpYyB2b2lkICAgICBzbm1wdjNfY2FsY19tc2dfZmxhZ3MoaW50LCBpbnQsIHVfY2hhciAqKTsKc3RhdGljIGludCAgICAgIHNubXB2M192ZXJpZnlfbXNnKG5ldHNubXBfcmVxdWVzdF9saXN0ICosIG5ldHNubXBfcGR1ICopOwpzdGF0aWMgaW50ICAgICAgc25tcHYzX2J1aWxkX3Byb2JlX3BkdShuZXRzbm1wX3BkdSAqKik7CnN0YXRpYyBpbnQgICAgICBzbm1wdjNfYnVpbGQodV9jaGFyICoqIHBrdCwgc2l6ZV90ICogcGt0X2xlbiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzaXplX3QgKiBvZmZzZXQsIG5ldHNubXBfc2Vzc2lvbiAqIHNlc3Npb24sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgbmV0c25tcF9wZHUgKnBkdSk7CnN0YXRpYyBpbnQgICAgICBzbm1wX3BhcnNlX3ZlcnNpb24odV9jaGFyICosIHNpemVfdCk7CnN0YXRpYyBpbnQgICAgICBzbm1wX3Jlc2VuZF9yZXF1ZXN0KHN0cnVjdCBzZXNzaW9uX2xpc3QgKnNscCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgbmV0c25tcF9yZXF1ZXN0X2xpc3QgKnJwLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBpbnQgaW5jcl9yZXRyaWVzKTsKc3RhdGljIHZvaWQgICAgIHJlZ2lzdGVyX2RlZmF1bHRfaGFuZGxlcnModm9pZCk7CnN0YXRpYyBzdHJ1Y3Qgc2Vzc2lvbl9saXN0ICpzbm1wX3Nlc3NfY29weShuZXRzbm1wX3Nlc3Npb24gKiBwc3MpOwppbnQgICAgICAgICAgICAgc25tcF9nZXRfZXJybm8odm9pZCk7CnZvaWQgICAgICAgICAgICBzbm1wX3N5bmNoX3Jlc2V0KG5ldHNubXBfc2Vzc2lvbiAqIG5vdHVzZWQpOwp2b2lkICAgICAgICAgICAgc25tcF9zeW5jaF9zZXR1cChuZXRzbm1wX3Nlc3Npb24gKiBub3R1c2VkKTsKCiNpZm5kZWYgSEFWRV9TVFJFUlJPUgpjb25zdCBjaGFyICAgICAqCnN0cmVycm9yKGludCBlcnIpCnsKICAgIGV4dGVybiBjb25zdCBjaGFyICpzeXNfZXJybGlzdFtdOwogICAgZXh0ZXJuIGludCAgICAgIHN5c19uZXJyOwoKICAgIGlmIChlcnIgPCAwIHx8IGVyciA+PSBzeXNfbmVycikKICAgICAgICByZXR1cm4gIlVua25vd24gZXJyb3IiOwogICAgcmV0dXJuIHN5c19lcnJsaXN0W2Vycl07Cn0KI2VuZGlmCgpjb25zdCBjaGFyICoKc25tcF9wZHVfdHlwZShpbnQgdHlwZSkKewogICAgc3RhdGljIGNoYXIgdW5rbm93blsyMF07CiAgICBzd2l0Y2godHlwZSkgewogICAgY2FzZSBTTk1QX01TR19HRVQ6CiAgICAgICAgcmV0dXJuICJHRVQiOwogICAgY2FzZSBTTk1QX01TR19HRVRORVhUOgogICAgICAgIHJldHVybiAiR0VUTkVYVCI7CiAgICBjYXNlIFNOTVBfTVNHX1JFU1BPTlNFOgogICAgICAgIHJldHVybiAiUkVTUE9OU0UiOwogICAgY2FzZSBTTk1QX01TR19TRVQ6CiAgICAgICAgcmV0dXJuICJTRVQiOwogICAgY2FzZSBTTk1QX01TR19HRVRCVUxLOgogICAgICAgIHJldHVybiAiR0VUQlVMSyI7CiAgICBjYXNlIFNOTVBfTVNHX0lORk9STToKICAgICAgICByZXR1cm4gIklORk9STSI7CiAgICBjYXNlIFNOTVBfTVNHX1RSQVAyOgogICAgICAgIHJldHVybiAiVFJBUDIiOwogICAgY2FzZSBTTk1QX01TR19SRVBPUlQ6CiAgICAgICAgcmV0dXJuICJSRVBPUlQiOwogICAgZGVmYXVsdDoKICAgICAgICBzbnByaW50Zih1bmtub3duLCBzaXplb2YodW5rbm93biksICI/MHglMlg/IiwgdHlwZSk7CglyZXR1cm4gdW5rbm93bjsKICAgIH0KfQoKI2RlZmluZSBERUJVR1BSSU5UUERVVFlQRSh0b2tlbiwgdHlwZSkgXAogICAgREVCVUdEVU1QU0VDVElPTih0b2tlbiwgc25tcF9wZHVfdHlwZSh0eXBlKSkKCmxvbmcKc25tcF9nZXRfbmV4dF9yZXFpZCh2b2lkKQp7CiAgICBsb25nICAgICAgICAgICAgcmV0VmFsOwogICAgc25tcF9yZXNfbG9jayhNVF9MSUJSQVJZX0lELCBNVF9MSUJfUkVRVUVTVElEKTsKICAgIHJldFZhbCA9IDEgKyBSZXFpZDsgICAgICAgICAvKk1UQ1JJVElDQUxfUkVTT1VSQ0UgKi8KICAgIGlmICghcmV0VmFsKQogICAgICAgIHJldFZhbCA9IDI7CiAgICBSZXFpZCA9IHJldFZhbDsKICAgIGlmIChuZXRzbm1wX2RzX2dldF9ib29sZWFuKE5FVFNOTVBfRFNfTElCUkFSWV9JRCwgTkVUU05NUF9EU19MSUJfMTZCSVRfSURTKSkKICAgICAgICByZXRWYWwgJj0gMHg3ZmZmOwkvKiBtYXNrIHRvIDE1IGJpdHMgKi8KICAgIGVsc2UKICAgICAgICByZXRWYWwgJj0gMHg3ZmZmZmZmZjsJLyogbWFzayB0byAzMSBiaXRzICovCgogICAgaWYgKCFyZXRWYWwpIHsKICAgICAgICBSZXFpZCA9IHJldFZhbCA9IDI7CiAgICB9CiAgICBzbm1wX3Jlc191bmxvY2soTVRfTElCUkFSWV9JRCwgTVRfTElCX1JFUVVFU1RJRCk7CiAgICByZXR1cm4gcmV0VmFsOwp9Cgpsb25nCnNubXBfZ2V0X25leHRfbXNnaWQodm9pZCkKewogICAgbG9uZyAgICAgICAgICAgIHJldFZhbDsKICAgIHNubXBfcmVzX2xvY2soTVRfTElCUkFSWV9JRCwgTVRfTElCX01FU1NBR0VJRCk7CiAgICByZXRWYWwgPSAxICsgTXNnaWQ7ICAgICAgICAgLypNVENSSVRJQ0FMX1JFU09VUkNFICovCiAgICBpZiAoIXJldFZhbCkKICAgICAgICByZXRWYWwgPSAyOwogICAgTXNnaWQgPSByZXRWYWw7CiAgICBpZiAobmV0c25tcF9kc19nZXRfYm9vbGVhbihORVRTTk1QX0RTX0xJQlJBUllfSUQsIE5FVFNOTVBfRFNfTElCXzE2QklUX0lEUykpCiAgICAgICAgcmV0VmFsICY9IDB4N2ZmZjsJLyogbWFzayB0byAxNSBiaXRzICovCiAgICBlbHNlCiAgICAgICAgcmV0VmFsICY9IDB4N2ZmZmZmZmY7CS8qIG1hc2sgdG8gMzEgYml0cyAqLwoKICAgIGlmICghcmV0VmFsKSB7CiAgICAgICAgTXNnaWQgPSByZXRWYWwgPSAyOwogICAgfQogICAgc25tcF9yZXNfdW5sb2NrKE1UX0xJQlJBUllfSUQsIE1UX0xJQl9NRVNTQUdFSUQpOwogICAgcmV0dXJuIHJldFZhbDsKfQoKbG9uZwpzbm1wX2dldF9uZXh0X3Nlc3NpZCh2b2lkKQp7CiAgICBsb25nICAgICAgICAgICAgcmV0VmFsOwogICAgc25tcF9yZXNfbG9jayhNVF9MSUJSQVJZX0lELCBNVF9MSUJfU0VTU0lPTklEKTsKICAgIHJldFZhbCA9IDEgKyBTZXNzaWQ7ICAgICAgICAvKk1UQ1JJVElDQUxfUkVTT1VSQ0UgKi8KICAgIGlmICghcmV0VmFsKQogICAgICAgIHJldFZhbCA9IDI7CiAgICBTZXNzaWQgPSByZXRWYWw7CiAgICBpZiAobmV0c25tcF9kc19nZXRfYm9vbGVhbihORVRTTk1QX0RTX0xJQlJBUllfSUQsIE5FVFNOTVBfRFNfTElCXzE2QklUX0lEUykpCiAgICAgICAgcmV0VmFsICY9IDB4N2ZmZjsJLyogbWFzayB0byAxNSBiaXRzICovCiAgICBlbHNlCiAgICAgICAgcmV0VmFsICY9IDB4N2ZmZmZmZmY7CS8qIG1hc2sgdG8gMzEgYml0cyAqLwoKICAgIGlmICghcmV0VmFsKSB7CiAgICAgICAgU2Vzc2lkID0gcmV0VmFsID0gMjsKICAgIH0KICAgIHNubXBfcmVzX3VubG9jayhNVF9MSUJSQVJZX0lELCBNVF9MSUJfU0VTU0lPTklEKTsKICAgIHJldHVybiByZXRWYWw7Cn0KCmxvbmcKc25tcF9nZXRfbmV4dF90cmFuc2lkKHZvaWQpCnsKICAgIGxvbmcgICAgICAgICAgICByZXRWYWw7CiAgICBzbm1wX3Jlc19sb2NrKE1UX0xJQlJBUllfSUQsIE1UX0xJQl9UUkFOU0lEKTsKICAgIHJldFZhbCA9IDEgKyBUcmFuc2lkOyAgICAgICAvKk1UQ1JJVElDQUxfUkVTT1VSQ0UgKi8KICAgIGlmICghcmV0VmFsKQogICAgICAgIHJldFZhbCA9IDI7CiAgICBUcmFuc2lkID0gcmV0VmFsOwogICAgaWYgKG5ldHNubXBfZHNfZ2V0X2Jvb2xlYW4oTkVUU05NUF9EU19MSUJSQVJZX0lELCBORVRTTk1QX0RTX0xJQl8xNkJJVF9JRFMpKQogICAgICAgIHJldFZhbCAmPSAweDdmZmY7CS8qIG1hc2sgdG8gMTUgYml0cyAqLwogICAgZWxzZQogICAgICAgIHJldFZhbCAmPSAweDdmZmZmZmZmOwkvKiBtYXNrIHRvIDMxIGJpdHMgKi8KCiAgICBpZiAoIXJldFZhbCkgewogICAgICAgIFRyYW5zaWQgPSByZXRWYWwgPSAyOwogICAgfQogICAgc25tcF9yZXNfdW5sb2NrKE1UX0xJQlJBUllfSUQsIE1UX0xJQl9UUkFOU0lEKTsKICAgIHJldHVybiByZXRWYWw7Cn0KCnZvaWQKc25tcF9wZXJyb3IoY29uc3QgY2hhciAqcHJvZ19zdHJpbmcpCnsKICAgIGNvbnN0IGNoYXIgICAgICpzdHI7CiAgICBpbnQgICAgICAgICAgICAgeGVycjsKICAgIHhlcnIgPSBzbm1wX2Vycm5vOyAgICAgICAgICAvKk1UQ1JJVElDQUxfUkVTT1VSQ0UgKi8KICAgIHN0ciA9IHNubXBfYXBpX2VycnN0cmluZyh4ZXJyKTsKICAgIHNubXBfbG9nKExPR19FUlIsICIlczogJXNcbiIsIHByb2dfc3RyaW5nLCBzdHIpOwp9Cgp2b2lkCnNubXBfc2V0X2RldGFpbChjb25zdCBjaGFyICpkZXRhaWxfc3RyaW5nKQp7CiAgICBpZiAoZGV0YWlsX3N0cmluZyAhPSBOVUxMKSB7CiAgICAgICAgc3RybGNweSgoY2hhciAqKSBzbm1wX2RldGFpbCwgZGV0YWlsX3N0cmluZywgc2l6ZW9mKHNubXBfZGV0YWlsKSk7CiAgICAgICAgc25tcF9kZXRhaWxfZiA9IDE7CiAgICB9Cn0KCi8qCiAqIHJldHVybnMgcG9pbnRlciB0byBzdGF0aWMgZGF0YSAKICovCi8qCiAqIHJlc3VsdHMgbm90IGd1YXJhbnRlZWQgaW4gbXVsdGktdGhyZWFkZWQgdXNlIAogKi8KY29uc3QgY2hhciAgICAgKgpzbm1wX2FwaV9lcnJzdHJpbmcoaW50IHNubXBfZXJybnVtYmVyKQp7CiAgICBjb25zdCBjaGFyICAgICAqbXNnID0gIiI7CiAgICBzdGF0aWMgY2hhciAgICAgbXNnX2J1ZltTUFJJTlRfTUFYX0xFTl07CgogICAgaWYgKHNubXBfZXJybnVtYmVyID49IFNOTVBFUlJfTUFYICYmIHNubXBfZXJybnVtYmVyIDw9IFNOTVBFUlJfR0VORVJSKSB7CiAgICAgICAgbXNnID0gYXBpX2Vycm9yc1stc25tcF9lcnJudW1iZXJdOwogICAgfSBlbHNlIGlmIChzbm1wX2Vycm51bWJlciAhPSBTTk1QRVJSX1NVQ0NFU1MpIHsKICAgICAgICBtc2cgPSBOVUxMOwogICAgfQogICAgaWYgKCFtc2cpIHsKCXNucHJpbnRmKG1zZ19idWYsIHNpemVvZihtc2dfYnVmKSwgIlVua25vd24gZXJyb3I6ICVkIiwgc25tcF9lcnJudW1iZXIpOwogICAgICAgIG1zZ19idWZbc2l6ZW9mKG1zZ19idWYpLTFdID0gJ1wwJzsKICAgIH0gZWxzZSBpZiAoc25tcF9kZXRhaWxfZikgewogICAgICAgIHNucHJpbnRmKG1zZ19idWYsIHNpemVvZihtc2dfYnVmKSwgIiVzICglcykiLCBtc2csIHNubXBfZGV0YWlsKTsKICAgICAgICBtc2dfYnVmW3NpemVvZihtc2dfYnVmKS0xXSA9ICdcMCc7CiAgICAgICAgc25tcF9kZXRhaWxfZiA9IDA7CiAgICB9IGVsc2UgewogICAgICAgIHN0cmxjcHkobXNnX2J1ZiwgbXNnLCBzaXplb2YobXNnX2J1ZikpOwogICAgfQoKICAgIHJldHVybiAobXNnX2J1Zik7Cn0KCi8qCiAqIHNubXBfZXJyb3IgLSByZXR1cm4gZXJyb3IgZGF0YQogKiBJbnB1dHMgOiAgYWRkcmVzcyBvZiBlcnJubywgYWRkcmVzcyBvZiBzbm1wX2Vycm5vLCBhZGRyZXNzIG9mIHN0cmluZwogKiBDYWxsZXIgbXVzdCBmcmVlIHRoZSBzdHJpbmcgcmV0dXJuZWQgYWZ0ZXIgdXNlLgogKi8Kdm9pZApzbm1wX2Vycm9yKG5ldHNubXBfc2Vzc2lvbiAqIHBzZXNzLAogICAgICAgICAgIGludCAqcF9lcnJubywgaW50ICpwX3NubXBfZXJybm8sIGNoYXIgKipwX3N0cikKewogICAgY2hhciAgICAgICAgICAgIGJ1ZltTUFJJTlRfTUFYX0xFTl07CiAgICBpbnQgICAgICAgICAgICAgc25tcF9lcnJudW1iZXI7CgogICAgaWYgKHBfZXJybm8pCiAgICAgICAgKnBfZXJybm8gPSBwc2Vzcy0+c19lcnJubzsKICAgIGlmIChwX3NubXBfZXJybm8pCiAgICAgICAgKnBfc25tcF9lcnJubyA9IHBzZXNzLT5zX3NubXBfZXJybm87CiAgICBpZiAocF9zdHIgPT0gTlVMTCkKICAgICAgICByZXR1cm47CgogICAgc3RyY3B5KGJ1ZiwgIiIpOwogICAgc25tcF9lcnJudW1iZXIgPSBwc2Vzcy0+c19zbm1wX2Vycm5vOwogICAgaWYgKHNubXBfZXJybnVtYmVyID49IFNOTVBFUlJfTUFYICYmIHNubXBfZXJybnVtYmVyIDw9IFNOTVBFUlJfR0VORVJSKSB7CglpZiAoc25tcF9kZXRhaWxfZikgewogICAgICAgICAgICBzbnByaW50ZihidWYsIHNpemVvZihidWYpLCAiJXMgKCVzKSIsIGFwaV9lcnJvcnNbLXNubXBfZXJybnVtYmVyXSwKCQkgICAgc25tcF9kZXRhaWwpOwogICAgICAgICAgICBidWZbc2l6ZW9mKGJ1ZiktMV0gPSAnXDAnOwoJICAgIHNubXBfZGV0YWlsX2YgPSAwOwoJfQoJZWxzZQoJICAgIHN0cmxjcHkoYnVmLCBhcGlfZXJyb3JzWy1zbm1wX2Vycm51bWJlcl0sIHNpemVvZihidWYpKTsKICAgIH0gZWxzZSB7CiAgICAgICAgaWYgKHNubXBfZXJybnVtYmVyKSB7CiAgICAgICAgICAgIHNucHJpbnRmKGJ1Ziwgc2l6ZW9mKGJ1ZiksICJVbmtub3duIEVycm9yICVkIiwgc25tcF9lcnJudW1iZXIpOwogICAgICAgICAgICBidWZbc2l6ZW9mKGJ1ZiktMV0gPSAnXDAnOwogICAgICAgIH0KICAgIH0KCiAgICAvKgogICAgICogYXBwZW5kIGEgdXNlZnVsIHN5c3RlbSBlcnJubyBpbnRlcnByZXRhdGlvbi4gCiAgICAgKi8KICAgIGlmIChwc2Vzcy0+c19lcnJubykgewogICAgICAgIGNvbnN0IGNoYXIqIGVycm9yID0gc3RyZXJyb3IocHNlc3MtPnNfZXJybm8pOwogICAgICAgIGlmKGVycm9yID09IE5VTEwpCiAgICAgICAgICAgIGVycm9yID0gIlVua25vd24gRXJyb3IiOwogICAgICAgIHNucHJpbnRmICgmYnVmW3N0cmxlbihidWYpXSwgc2l6ZW9mKGJ1Ziktc3RybGVuKGJ1ZiksCiAgICAgICAgICAgICAgICAgIiAoJXMpIiwgZXJyb3IpOwogICAgfQogICAgYnVmW3NpemVvZihidWYpLTFdID0gJ1wwJzsKICAgICpwX3N0ciA9IHN0cmR1cChidWYpOwp9CgovKgogKiBzbm1wX3Nlc3NfZXJyb3IgLSBzYW1lIGFzIHNubXBfZXJyb3IgZm9yIHNpbmdsZSBzZXNzaW9uIEFQSSB1c2UuCiAqLwp2b2lkCnNubXBfc2Vzc19lcnJvcih2b2lkICpzZXNzcCwgaW50ICpwX2Vycm5vLCBpbnQgKnBfc25tcF9lcnJubywgY2hhciAqKnBfc3RyKQp7CiAgICBzdHJ1Y3Qgc2Vzc2lvbl9saXN0ICpzbHAgPSAoc3RydWN0IHNlc3Npb25fbGlzdCAqKSBzZXNzcDsKCiAgICBpZiAoKHNscCkgJiYgKHNscC0+c2Vzc2lvbikpCiAgICAgICAgc25tcF9lcnJvcihzbHAtPnNlc3Npb24sIHBfZXJybm8sIHBfc25tcF9lcnJubywgcF9zdHIpOwp9CgovKgogKiBuZXRzbm1wX3Nlc3NfbG9nX2Vycm9yKCk6IHByaW50IGEgZXJyb3Igc3RvcmVkIGluIGEgc2Vzc2lvbiBwb2ludGVyIAogKi8Kdm9pZApuZXRzbm1wX3Nlc3NfbG9nX2Vycm9yKGludCBwcmlvcml0eSwKICAgICAgICAgICAgICAgICAgICAgICBjb25zdCBjaGFyICpwcm9nX3N0cmluZywgbmV0c25tcF9zZXNzaW9uICogc3MpCnsKICAgIGNoYXIgICAgICAgICAgICplcnI7CiAgICBzbm1wX2Vycm9yKHNzLCBOVUxMLCBOVUxMLCAmZXJyKTsKICAgIHNubXBfbG9nKHByaW9yaXR5LCAiJXM6ICVzXG4iLCBwcm9nX3N0cmluZywgZXJyKTsKICAgIFNOTVBfRlJFRShlcnIpOwp9CgovKgogKiBzbm1wX3Nlc3NfcGVycm9yKCk6IHByaW50IGEgZXJyb3Igc3RvcmVkIGluIGEgc2Vzc2lvbiBwb2ludGVyIAogKi8Kdm9pZApzbm1wX3Nlc3NfcGVycm9yKGNvbnN0IGNoYXIgKnByb2dfc3RyaW5nLCBuZXRzbm1wX3Nlc3Npb24gKiBzcykKewogICAgbmV0c25tcF9zZXNzX2xvZ19lcnJvcihMT0dfRVJSLCBwcm9nX3N0cmluZywgc3MpOwp9CgoKCi8qCiAqIFByaW1vcmRpYWwgU05NUCBsaWJyYXJ5IGluaXRpYWxpemF0aW9uLgogKiBJbml0aWFsaXplcyBtdXRleCBsb2Nrcy4KICogSW52b2tlcyBtaW5pbXVtIHJlcXVpcmVkIGluaXRpYWxpemF0aW9uIGZvciBkaXNwbGF5aW5nIE1JQiBvYmplY3RzLgogKiBHZXRzIGluaXRpYWwgcmVxdWVzdCBJRCBmb3IgYWxsIHRyYW5zYWN0aW9ucywKICogYW5kIGZpbmRzIHdoaWNoIHBvcnQgU05NUCBvdmVyIFVEUCB1c2VzLgogKiBTTk1QIG92ZXIgQXBwbGVUYWxrIGlzIG5vdCBjdXJyZW50bHkgc3VwcG9ydGVkLgogKgogKiBXYXJuaW5nOiBubyBkZWJ1ZyBtZXNzYWdlcyBoZXJlLgogKi8Kc3RhdGljIGNoYXIgX2luaXRfc25tcF9pbml0X2RvbmUgPSAwOwpzdGF0aWMgdm9pZApfaW5pdF9zbm1wKHZvaWQpCnsKCiAgICBzdHJ1Y3QgdGltZXZhbCAgdHY7CiAgICBsb25nICAgICAgICAgICAgdG1wUmVxaWQsIHRtcE1zZ2lkOwoKICAgIGlmIChfaW5pdF9zbm1wX2luaXRfZG9uZSkKICAgICAgICByZXR1cm47CiAgICBfaW5pdF9zbm1wX2luaXRfZG9uZSA9IDE7CiAgICBSZXFpZCA9IDE7CgogICAgc25tcF9yZXNfaW5pdCgpOyAgICAgICAgICAgIC8qIGluaXRpYWxpemUgdGhlIG10IGxvY2tpbmcgc3RydWN0dXJlcyAqLwojaWZuZGVmIE5FVFNOTVBfRElTQUJMRV9NSUJfTE9BRElORwogICAgbmV0c25tcF9pbml0X21pYl9pbnRlcm5hbHMoKTsKI2VuZGlmIC8qIE5FVFNOTVBfRElTQUJMRV9NSUJfTE9BRElORyAqLwogICAgbmV0c25tcF90ZG9tYWluX2luaXQoKTsKCiAgICBnZXR0aW1lb2ZkYXkoJnR2LCAoc3RydWN0IHRpbWV6b25lICopIDApOwogICAgLyoKICAgICAqIE5vdyA9IHR2OwogICAgICovCgogICAgLyoKICAgICAqIGdldCBwc2V1ZG8tcmFuZG9tIHZhbHVlcyBmb3IgcmVxdWVzdCBJRCBhbmQgbWVzc2FnZSBJRCAKICAgICAqLwogICAgLyoKICAgICAqIGRvbid0IGFsbG93IHplcm8gdmFsdWUgdG8gcmVwZWF0IGluaXQgCiAgICAgKi8KI2lmZGVmIFNWUjQKICAgIHNyYW5kNDgodHYudHZfc2VjIF4gdHYudHZfdXNlYyk7CiAgICB0bXBSZXFpZCA9IGxyYW5kNDgoKTsKICAgIHRtcE1zZ2lkID0gbHJhbmQ0OCgpOwojZWxzZQogICAgc3JhbmRvbSh0di50dl9zZWMgXiB0di50dl91c2VjKTsKICAgIHRtcFJlcWlkID0gcmFuZG9tKCk7CiAgICB0bXBNc2dpZCA9IHJhbmRvbSgpOwojZW5kaWYKCiAgICBpZiAodG1wUmVxaWQgPT0gMCkKICAgICAgICB0bXBSZXFpZCA9IDE7CiAgICBpZiAodG1wTXNnaWQgPT0gMCkKICAgICAgICB0bXBNc2dpZCA9IDE7CiAgICBSZXFpZCA9IHRtcFJlcWlkOwogICAgTXNnaWQgPSB0bXBNc2dpZDsKCiAgICBuZXRzbm1wX3JlZ2lzdGVyX2RlZmF1bHRfZG9tYWluKCJzbm1wIiwgInVkcCB1ZHA2Iik7CiAgICBuZXRzbm1wX3JlZ2lzdGVyX2RlZmF1bHRfZG9tYWluKCJzbm1wdHJhcCIsICJ1ZHAgdWRwNiIpOwoKICAgIG5ldHNubXBfcmVnaXN0ZXJfZGVmYXVsdF90YXJnZXQoInNubXAiLCAidWRwIiwgIjoxNjEiKTsKICAgIG5ldHNubXBfcmVnaXN0ZXJfZGVmYXVsdF90YXJnZXQoInNubXAiLCAidGNwIiwgIjoxNjEiKTsKICAgIG5ldHNubXBfcmVnaXN0ZXJfZGVmYXVsdF90YXJnZXQoInNubXAiLCAidWRwNiIsICI6MTYxIik7CiAgICBuZXRzbm1wX3JlZ2lzdGVyX2RlZmF1bHRfdGFyZ2V0KCJzbm1wIiwgInRjcDYiLCAiOjE2MSIpOwogICAgbmV0c25tcF9yZWdpc3Rlcl9kZWZhdWx0X3RhcmdldCgic25tcCIsICJpcHgiLCAiLzM2ODc5Iik7CiAgICBuZXRzbm1wX3JlZ2lzdGVyX2RlZmF1bHRfdGFyZ2V0KCJzbm1wdHJhcCIsICJ1ZHAiLCAiOjE2MiIpOwogICAgbmV0c25tcF9yZWdpc3Rlcl9kZWZhdWx0X3RhcmdldCgic25tcHRyYXAiLCAidGNwIiwgIjoxNjIiKTsKICAgIG5ldHNubXBfcmVnaXN0ZXJfZGVmYXVsdF90YXJnZXQoInNubXB0cmFwIiwgInVkcDYiLCAiOjE2MiIpOwogICAgbmV0c25tcF9yZWdpc3Rlcl9kZWZhdWx0X3RhcmdldCgic25tcHRyYXAiLCAidGNwNiIsICI6MTYyIik7CiAgICBuZXRzbm1wX3JlZ2lzdGVyX2RlZmF1bHRfdGFyZ2V0KCJzbm1wdHJhcCIsICJpcHgiLCAiLzM2ODgwIik7CgogICAgbmV0c25tcF9kc19zZXRfaW50KE5FVFNOTVBfRFNfTElCUkFSWV9JRCwgCiAgICAgICAgICAgICAgICAgICAgICAgTkVUU05NUF9EU19MSUJfSEVYX09VVFBVVF9MRU5HVEgsIDE2KTsKCiNpZmRlZiBORVRTTk1QX1VTRV9SRVZFUlNFX0FTTkVOQ09ESU5HCiAgICBuZXRzbm1wX2RzX3NldF9ib29sZWFuKE5FVFNOTVBfRFNfTElCUkFSWV9JRCwgCgkJCSAgIE5FVFNOTVBfRFNfTElCX1JFVkVSU0VfRU5DT0RFLAoJCQkgICBORVRTTk1QX0RFRkFVTFRfQVNORU5DT0RJTkdfRElSRUNUSU9OKTsKI2VuZGlmCn0KCi8qCiAqIEluaXRpYWxpemVzIHRoZSBzZXNzaW9uIHN0cnVjdHVyZS4KICogTWF5IHBlcmZvcm0gb25lIHRpbWUgbWluaW1hbCBsaWJyYXJ5IGluaXRpYWxpemF0aW9uLgogKiBObyBNSUIgZmlsZSBwcm9jZXNzaW5nIGlzIGRvbmUgdmlhIHRoaXMgY2FsbC4KICovCnZvaWQKc25tcF9zZXNzX2luaXQobmV0c25tcF9zZXNzaW9uICogc2Vzc2lvbikKewogICAgX2luaXRfc25tcCgpOwoKICAgIC8qCiAgICAgKiBpbml0aWFsaXplIHNlc3Npb24gdG8gZGVmYXVsdCB2YWx1ZXMgCiAgICAgKi8KCiAgICBtZW1zZXQoc2Vzc2lvbiwgMCwgc2l6ZW9mKG5ldHNubXBfc2Vzc2lvbikpOwogICAgc2Vzc2lvbi0+cmVtb3RlX3BvcnQgPSBTTk1QX0RFRkFVTFRfUkVNUE9SVDsKICAgIHNlc3Npb24tPnRpbWVvdXQgPSBTTk1QX0RFRkFVTFRfVElNRU9VVDsKICAgIHNlc3Npb24tPnJldHJpZXMgPSBTTk1QX0RFRkFVTFRfUkVUUklFUzsKICAgIHNlc3Npb24tPnZlcnNpb24gPSBTTk1QX0RFRkFVTFRfVkVSU0lPTjsKICAgIHNlc3Npb24tPnNlY3VyaXR5TW9kZWwgPSBTTk1QX0RFRkFVTFRfU0VDTU9ERUw7CiAgICBzZXNzaW9uLT5yY3ZNc2dNYXhTaXplID0gU05NUF9NQVhfTVNHX1NJWkU7CiAgICBzZXNzaW9uLT5mbGFncyB8PSBTTk1QX0ZMQUdTX0RPTlRfUFJPQkU7Cn0KCgpzdGF0aWMgdm9pZApyZWdpc3Rlcl9kZWZhdWx0X2hhbmRsZXJzKHZvaWQpCnsKICAgIG5ldHNubXBfZHNfcmVnaXN0ZXJfY29uZmlnKEFTTl9CT09MRUFOLCAic25tcCIsICJkdW1wUGFja2V0IiwKCQkgICAgICBORVRTTk1QX0RTX0xJQlJBUllfSUQsIE5FVFNOTVBfRFNfTElCX0RVTVBfUEFDS0VUKTsKICAgIG5ldHNubXBfZHNfcmVnaXN0ZXJfY29uZmlnKEFTTl9CT09MRUFOLCAic25tcCIsICJyZXZlcnNlRW5jb2RlQkVSIiwKCQkgICAgICBORVRTTk1QX0RTX0xJQlJBUllfSUQsIE5FVFNOTVBfRFNfTElCX1JFVkVSU0VfRU5DT0RFKTsKICAgIG5ldHNubXBfZHNfcmVnaXN0ZXJfY29uZmlnKEFTTl9JTlRFR0VSLCAic25tcCIsICJkZWZhdWx0UG9ydCIsCgkJICAgICAgTkVUU05NUF9EU19MSUJSQVJZX0lELCBORVRTTk1QX0RTX0xJQl9ERUZBVUxUX1BPUlQpOwojaWYgIWRlZmluZWQoTkVUU05NUF9ESVNBQkxFX1NOTVBWMSkgfHwgIWRlZmluZWQoTkVUU05NUF9ESVNBQkxFX1NOTVBWMkMpCiAgICBuZXRzbm1wX2RzX3JlZ2lzdGVyX2NvbmZpZyhBU05fT0NURVRfU1RSLCAic25tcCIsICJkZWZDb21tdW5pdHkiLAogICAgICAgICAgICAgICAgICAgICAgTkVUU05NUF9EU19MSUJSQVJZX0lELCBORVRTTk1QX0RTX0xJQl9DT01NVU5JVFkpOwojZW5kaWYKICAgIG5ldHNubXBfZHNfcmVnaXN0ZXJfcHJlbWliKEFTTl9CT09MRUFOLCAic25tcCIsICJub1Rva2VuV2FybmluZ3MiLAogICAgICAgICAgICAgICAgICAgICAgTkVUU05NUF9EU19MSUJSQVJZX0lELCBORVRTTk1QX0RTX0xJQl9OT19UT0tFTl9XQVJOSU5HUyk7CiAgICBuZXRzbm1wX2RzX3JlZ2lzdGVyX2NvbmZpZyhBU05fQk9PTEVBTiwgInNubXAiLCAibm9SYW5nZUNoZWNrIiwKCQkgICAgICBORVRTTk1QX0RTX0xJQlJBUllfSUQsIE5FVFNOTVBfRFNfTElCX0RPTlRfQ0hFQ0tfUkFOR0UpOwogICAgbmV0c25tcF9kc19yZWdpc3Rlcl9wcmVtaWIoQVNOX09DVEVUX1NUUiwgInNubXAiLCAicGVyc2lzdGVudERpciIsCgkgICAgICAgICAgICAgIE5FVFNOTVBfRFNfTElCUkFSWV9JRCwgTkVUU05NUF9EU19MSUJfUEVSU0lTVEVOVF9ESVIpOwogICAgbmV0c25tcF9kc19yZWdpc3Rlcl9jb25maWcoQVNOX09DVEVUX1NUUiwgInNubXAiLCAidGVtcEZpbGVQYXR0ZXJuIiwKCSAgICAgICAgICAgICAgTkVUU05NUF9EU19MSUJSQVJZX0lELCBORVRTTk1QX0RTX0xJQl9URU1QX0ZJTEVfUEFUVEVSTik7CiAgICBuZXRzbm1wX2RzX3JlZ2lzdGVyX2NvbmZpZyhBU05fQk9PTEVBTiwgInNubXAiLCAibm9EaXNwbGF5SGludCIsCgkgICAgICAgICAgICAgIE5FVFNOTVBfRFNfTElCUkFSWV9JRCwgTkVUU05NUF9EU19MSUJfTk9fRElTUExBWV9ISU5UKTsKICAgIG5ldHNubXBfZHNfcmVnaXN0ZXJfY29uZmlnKEFTTl9CT09MRUFOLCAic25tcCIsICIxNmJpdElEcyIsCgkgICAgICAgICAgICAgIE5FVFNOTVBfRFNfTElCUkFSWV9JRCwgTkVUU05NUF9EU19MSUJfMTZCSVRfSURTKTsKICAgIG5ldHNubXBfZHNfcmVnaXN0ZXJfcHJlbWliKEFTTl9PQ1RFVF9TVFIsICJzbm1wIiwgImNsaWVudGFkZHIiLAogICAgICAgICAgICAgICAgICAgICAgTkVUU05NUF9EU19MSUJSQVJZX0lELCBORVRTTk1QX0RTX0xJQl9DTElFTlRfQUREUik7CiAgICBuZXRzbm1wX2RzX3JlZ2lzdGVyX2NvbmZpZyhBU05fSU5URUdFUiwgInNubXAiLCAic2VydmVyU2VuZEJ1ZiIsCgkJICAgICAgTkVUU05NUF9EU19MSUJSQVJZX0lELCBORVRTTk1QX0RTX0xJQl9TRVJWRVJTRU5EQlVGKTsKICAgIG5ldHNubXBfZHNfcmVnaXN0ZXJfY29uZmlnKEFTTl9JTlRFR0VSLCAic25tcCIsICJzZXJ2ZXJSZWN2QnVmIiwKCQkgICAgICBORVRTTk1QX0RTX0xJQlJBUllfSUQsIE5FVFNOTVBfRFNfTElCX1NFUlZFUlJFQ1ZCVUYpOwogICAgbmV0c25tcF9kc19yZWdpc3Rlcl9jb25maWcoQVNOX0lOVEVHRVIsICJzbm1wIiwgImNsaWVudFNlbmRCdWYiLAoJCSAgICAgIE5FVFNOTVBfRFNfTElCUkFSWV9JRCwgTkVUU05NUF9EU19MSUJfQ0xJRU5UU0VOREJVRik7CiAgICBuZXRzbm1wX2RzX3JlZ2lzdGVyX2NvbmZpZyhBU05fSU5URUdFUiwgInNubXAiLCAiY2xpZW50UmVjdkJ1ZiIsCgkJICAgICAgTkVUU05NUF9EU19MSUJSQVJZX0lELCBORVRTTk1QX0RTX0xJQl9DTElFTlRSRUNWQlVGKTsKICAgIG5ldHNubXBfZHNfcmVnaXN0ZXJfY29uZmlnKEFTTl9CT09MRUFOLCAic25tcCIsICJub1BlcnNpc3RlbnRMb2FkIiwKCQkgICAgICBORVRTTk1QX0RTX0xJQlJBUllfSUQsIE5FVFNOTVBfRFNfTElCX0RJU0FCTEVfUEVSU0lTVEVOVF9MT0FEKTsKICAgIG5ldHNubXBfZHNfcmVnaXN0ZXJfY29uZmlnKEFTTl9CT09MRUFOLCAic25tcCIsICJub1BlcnNpc3RlbnRTYXZlIiwKCQkgICAgICBORVRTTk1QX0RTX0xJQlJBUllfSUQsIE5FVFNOTVBfRFNfTElCX0RJU0FCTEVfUEVSU0lTVEVOVF9TQVZFKTsKICAgIG5ldHNubXBfcmVnaXN0ZXJfc2VydmljZV9oYW5kbGVycygpOwp9CgpzdGF0aWMgaW50IGluaXRfc25tcF9pbml0X2RvbmUgPSAwOyAvKiBUbyBwcmV2ZW50IGRvdWJsZSBpbml0J3MuICovCi8qKgogKiBDYWxscyB0aGUgZnVuY3Rpb25zIHRvIGRvIGNvbmZpZyBmaWxlIGxvYWRpbmcgYW5kICBtaWIgbW9kdWxlIHBhcnNpbmcKICogaW4gdGhlIGNvcnJlY3Qgb3JkZXIuCiAqCiAqIEBwYXJhbSB0eXBlIGxhYmVsIGZvciB0aGUgY29uZmlnIGZpbGUgInR5cGUiCiAqCiAqIEByZXR1cm4gdm9pZAogKgogKiBAc2VlIGluaXRfYWdlbnQKICovCnZvaWQKaW5pdF9zbm1wKGNvbnN0IGNoYXIgKnR5cGUpCnsKICAgIGlmIChpbml0X3NubXBfaW5pdF9kb25lKSB7CiAgICAgICAgcmV0dXJuOwogICAgfQoKICAgIGluaXRfc25tcF9pbml0X2RvbmUgPSAxOwoKICAgIC8qCiAgICAgKiBtYWtlIHRoZSB0eXBlIGF2YWlsYWJsZSBldmVyeXdoZXJlIGVsc2UgCiAgICAgKi8KICAgIGlmICh0eXBlICYmICFuZXRzbm1wX2RzX2dldF9zdHJpbmcoTkVUU05NUF9EU19MSUJSQVJZX0lELCAKCQkJCSAgICAgICBORVRTTk1QX0RTX0xJQl9BUFBUWVBFKSkgewogICAgICAgIG5ldHNubXBfZHNfc2V0X3N0cmluZyhORVRTTk1QX0RTX0xJQlJBUllfSUQsIAoJCQkgICAgICBORVRTTk1QX0RTX0xJQl9BUFBUWVBFLCB0eXBlKTsKICAgIH0KCiAgICBfaW5pdF9zbm1wKCk7CgogICAgLyoKICAgICAqIHNldCBvdXIgY3VycmVudCBsb2NhbGUgcHJvcGVybHkgdG8gaW5pdGlhbGl6ZSBpc3ByaW50KCkgdHlwZSBmdW5jdGlvbnMgCiAgICAgKi8KI2lmZGVmIEhBVkVfU0VUTE9DQUxFCiAgICBzZXRsb2NhbGUoTENfQ1RZUEUsICIiKTsKI2VuZGlmCgogICAgc25tcF9kZWJ1Z19pbml0KCk7ICAgIC8qIHNob3VsZCBiZSBkb25lIGZpcnN0LCB0byB0dXJuIG9uIGRlYnVnZ2luZyBBU0FQICovCiAgICBuZXRzbm1wX2NvbnRhaW5lcl9pbml0X2xpc3QoKTsKICAgIGluaXRfY2FsbGJhY2tzKCk7CiAgICBpbml0X3NubXBfbG9nZ2luZygpOwogICAgc25tcF9pbml0X3N0YXRpc3RpY3MoKTsKICAgIHJlZ2lzdGVyX21pYl9oYW5kbGVycygpOwogICAgcmVnaXN0ZXJfZGVmYXVsdF9oYW5kbGVycygpOwogICAgaW5pdF9zbm1wdjModHlwZSk7CiAgICBpbml0X3NubXBfYWxhcm0oKTsKICAgIGluaXRfc25tcF9lbnVtKHR5cGUpOwogICAgaW5pdF92YWNtKCk7CgogICAgcmVhZF9wcmVtaWJfY29uZmlncygpOwojaWZuZGVmIE5FVFNOTVBfRElTQUJMRV9NSUJfTE9BRElORwogICAgbmV0c25tcF9pbml0X21pYigpOwojZW5kaWYgLyogTkVUU05NUF9ESVNBQkxFX01JQl9MT0FESU5HICovCgogICAgcmVhZF9jb25maWdzKCk7Cgp9ICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8qIGVuZCBpbml0X3NubXAoKSAqLwoKdm9pZApzbm1wX3N0b3JlKGNvbnN0IGNoYXIgKnR5cGUpCnsKICAgIERFQlVHTVNHVEwoKCJzbm1wX3N0b3JlIiwgInN0b3Jpbmcgc3R1ZmYuLi5cbiIpKTsKICAgIHNubXBfc2F2ZV9wZXJzaXN0ZW50KHR5cGUpOwogICAgc25tcF9jYWxsX2NhbGxiYWNrcyhTTk1QX0NBTExCQUNLX0xJQlJBUlksIFNOTVBfQ0FMTEJBQ0tfU1RPUkVfREFUQSwgTlVMTCk7CiAgICBzbm1wX2NsZWFuX3BlcnNpc3RlbnQodHlwZSk7Cn0KCgovKioKICogU2h1dHMgZG93biB0aGUgYXBwbGljYXRpb24sIHNhdmluZyBhbnkgbmVlZGVkIHBlcnNpc3RlbnQgc3RvcmFnZSwKICogYW5kIGFwcHJvcHJpYXRlIGNsZWFuIHVwLgogKiAKICogQHBhcmFtIHR5cGUgTGFiZWwgZm9yIHRoZSBjb25maWcgZmlsZSAidHlwZSIgdXNlZAogKgogKiBAcmV0dXJuIHZvaWQKICovCnZvaWQKc25tcF9zaHV0ZG93bihjb25zdCBjaGFyICp0eXBlKQp7CiAgICBzbm1wX3N0b3JlKHR5cGUpOwogICAgc25tcF9jYWxsX2NhbGxiYWNrcyhTTk1QX0NBTExCQUNLX0xJQlJBUlksIFNOTVBfQ0FMTEJBQ0tfU0hVVERPV04sIE5VTEwpOwogICAgc2h1dGRvd25fc25tcF9sb2dnaW5nKCk7CiAgICBzbm1wX2FsYXJtX3VucmVnaXN0ZXJfYWxsKCk7CiAgICBzbm1wX2Nsb3NlX3Nlc3Npb25zKCk7CiNpZm5kZWYgTkVUU05NUF9ESVNBQkxFX01JQl9MT0FESU5HCiAgICBzaHV0ZG93bl9taWIoKTsKI2VuZGlmIC8qIE5FVFNOTVBfRElTQUJMRV9NSUJfTE9BRElORyAqLwogICAgdW5yZWdpc3Rlcl9hbGxfY29uZmlnX2hhbmRsZXJzKCk7CiAgICBuZXRzbm1wX2NvbnRhaW5lcl9mcmVlX2xpc3QoKTsKICAgIGNsZWFyX3NlY19tb2QoKTsKICAgIGNsZWFyX3NubXBfZW51bSgpOwogICAgbmV0c25tcF9jbGVhcl90ZG9tYWluX2xpc3QoKTsKICAgIGNsZWFyX2NhbGxiYWNrKCk7CiAgICBuZXRzbm1wX2RzX3NodXRkb3duKCk7CiAgICBjbGVhcl91c2VyX2xpc3QoKTsKICAgIG5ldHNubXBfY2xlYXJfZGVmYXVsdF90YXJnZXQoKTsKICAgIG5ldHNubXBfY2xlYXJfZGVmYXVsdF9kb21haW4oKTsKICAgIGZyZWVfZXRpbWVsaXN0KCk7CgogICAgaW5pdF9zbm1wX2luaXRfZG9uZSAgPSAwOwogICAgX2luaXRfc25tcF9pbml0X2RvbmUgPSAwOwp9CgoKLyoKICogU2V0cyB1cCB0aGUgc2Vzc2lvbiB3aXRoIHRoZSBzbm1wX3Nlc3Npb24gaW5mb3JtYXRpb24gcHJvdmlkZWQgYnkgdGhlIHVzZXIuCiAqIFRoZW4gb3BlbnMgYW5kIGJpbmRzIHRoZSBuZWNlc3NhcnkgbG93LWxldmVsIHRyYW5zcG9ydC4gIEEgaGFuZGxlIHRvIHRoZQogKiBjcmVhdGVkIHNlc3Npb24gaXMgcmV0dXJuZWQgKHRoaXMgaXMgTk9UIHRoZSBzYW1lIGFzIHRoZSBwb2ludGVyIHBhc3NlZCB0bwogKiBzbm1wX29wZW4oKSkuICBPbiBhbnkgZXJyb3IsIE5VTEwgaXMgcmV0dXJuZWQgYW5kIHNubXBfZXJybm8gaXMgc2V0IHRvIHRoZQogKiBhcHByb3ByaWF0ZSBlcnJvciBjb2RlLgogKi8KbmV0c25tcF9zZXNzaW9uICoKc25tcF9vcGVuKG5ldHNubXBfc2Vzc2lvbiAqc2Vzc2lvbikKewogICAgc3RydWN0IHNlc3Npb25fbGlzdCAqc2xwOwogICAgc2xwID0gKHN0cnVjdCBzZXNzaW9uX2xpc3QgKikgc25tcF9zZXNzX29wZW4oc2Vzc2lvbik7CiAgICBpZiAoIXNscCkgewogICAgICAgIHJldHVybiBOVUxMOwogICAgfQoKICAgIHNubXBfcmVzX2xvY2soTVRfTElCUkFSWV9JRCwgTVRfTElCX1NFU1NJT04pOwogICAgc2xwLT5uZXh0ID0gU2Vzc2lvbnM7CiAgICBTZXNzaW9ucyA9IHNscDsKICAgIHNubXBfcmVzX3VubG9jayhNVF9MSUJSQVJZX0lELCBNVF9MSUJfU0VTU0lPTik7CgogICAgcmV0dXJuIChzbHAtPnNlc3Npb24pOwp9CgovKgogKiBleHRlbmRlZCBvcGVuIAogKi8KbmV0c25tcF9zZXNzaW9uICoKc25tcF9vcGVuX2V4KG5ldHNubXBfc2Vzc2lvbiAqc2Vzc2lvbiwKICAgICAgICAgICAgIGludCAoKmZwcmVfcGFyc2UpCShuZXRzbm1wX3Nlc3Npb24gKiwgbmV0c25tcF90cmFuc3BvcnQgKiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2b2lkICosIGludCksCiAgICAgICAgICAgICBpbnQgKCpmcGFyc2UpCShuZXRzbm1wX3Nlc3Npb24gKiwgbmV0c25tcF9wZHUgKiwgdV9jaGFyICosCgkJCQkgc2l6ZV90KSwKCSAgICAgaW50ICgqZnBvc3RfcGFyc2UpCShuZXRzbm1wX3Nlc3Npb24gKiwgbmV0c25tcF9wZHUgKiwgaW50KSwKCiAgICAgICAgICAgICBpbnQgKCpmYnVpbGQpCShuZXRzbm1wX3Nlc3Npb24gKiwgbmV0c25tcF9wZHUgKiwgdV9jaGFyICosCgkJCQkgc2l6ZV90ICopLAoJICAgICBpbnQgKCpmcmJ1aWxkKQkobmV0c25tcF9zZXNzaW9uICosIG5ldHNubXBfcGR1ICosCgkJCQkgdV9jaGFyICoqLCBzaXplX3QgKiwgc2l6ZV90ICopLAogICAgICAgICAgICAgaW50ICgqZmNoZWNrKQkodV9jaGFyICosIHNpemVfdCkKCSAgICAgKQp7CiAgICBzdHJ1Y3Qgc2Vzc2lvbl9saXN0ICpzbHA7CiAgICBzbHAgPSAoc3RydWN0IHNlc3Npb25fbGlzdCAqKSBzbm1wX3Nlc3Nfb3BlbihzZXNzaW9uKTsKICAgIGlmICghc2xwKSB7CiAgICAgICAgcmV0dXJuIE5VTEw7CiAgICB9CiAgICBzbHAtPmludGVybmFsLT5ob29rX3ByZSA9IGZwcmVfcGFyc2U7CiAgICBzbHAtPmludGVybmFsLT5ob29rX3BhcnNlID0gZnBhcnNlOwogICAgc2xwLT5pbnRlcm5hbC0+aG9va19wb3N0ID0gZnBvc3RfcGFyc2U7CiAgICBzbHAtPmludGVybmFsLT5ob29rX2J1aWxkID0gZmJ1aWxkOwogICAgc2xwLT5pbnRlcm5hbC0+aG9va19yZWFsbG9jX2J1aWxkID0gZnJidWlsZDsKICAgIHNscC0+aW50ZXJuYWwtPmNoZWNrX3BhY2tldCA9IGZjaGVjazsKCiAgICBzbm1wX3Jlc19sb2NrKE1UX0xJQlJBUllfSUQsIE1UX0xJQl9TRVNTSU9OKTsKICAgIHNscC0+bmV4dCA9IFNlc3Npb25zOwogICAgU2Vzc2lvbnMgPSBzbHA7CiAgICBzbm1wX3Jlc191bmxvY2soTVRfTElCUkFSWV9JRCwgTVRfTElCX1NFU1NJT04pOwoKICAgIHJldHVybiAoc2xwLT5zZXNzaW9uKTsKfQoKc3RhdGljIHN0cnVjdCBzZXNzaW9uX2xpc3QgKgpfc2Vzc19jb3B5KG5ldHNubXBfc2Vzc2lvbiAqIGluX3Nlc3Npb24pCnsKICAgIHN0cnVjdCBzZXNzaW9uX2xpc3QgKnNscDsKICAgIHN0cnVjdCBzbm1wX2ludGVybmFsX3Nlc3Npb24gKmlzcDsKICAgIG5ldHNubXBfc2Vzc2lvbiAqc2Vzc2lvbjsKICAgIHN0cnVjdCBzbm1wX3NlY21vZF9kZWYgKnNwdHI7CiAgICBjaGFyICAgICAgICAgICAqY3A7CiAgICB1X2NoYXIgICAgICAgICAqdWNwOwogICAgc2l6ZV90ICAgICAgICAgIGk7CgogICAgaW5fc2Vzc2lvbi0+c19zbm1wX2Vycm5vID0gMDsKICAgIGluX3Nlc3Npb24tPnNfZXJybm8gPSAwOwoKICAgIC8qCiAgICAgKiBDb3B5IHNlc3Npb24gc3RydWN0dXJlIGFuZCBsaW5rIGludG8gbGlzdCAKICAgICAqLwogICAgc2xwID0gKHN0cnVjdCBzZXNzaW9uX2xpc3QgKikgY2FsbG9jKDEsIHNpemVvZihzdHJ1Y3Qgc2Vzc2lvbl9saXN0KSk7CiAgICBpZiAoc2xwID09IE5VTEwpIHsKICAgICAgICBpbl9zZXNzaW9uLT5zX3NubXBfZXJybm8gPSBTTk1QRVJSX01BTExPQzsKICAgICAgICByZXR1cm4gKE5VTEwpOwogICAgfQoKICAgIHNscC0+dHJhbnNwb3J0ID0gTlVMTDsKCiAgICBpc3AgPSAoc3RydWN0IHNubXBfaW50ZXJuYWxfc2Vzc2lvbiAqKWNhbGxvYygxLCBzaXplb2Yoc3RydWN0IHNubXBfaW50ZXJuYWxfc2Vzc2lvbikpOwoKICAgIGlmIChpc3AgPT0gTlVMTCkgewogICAgICAgIHNubXBfc2Vzc19jbG9zZShzbHApOwogICAgICAgIGluX3Nlc3Npb24tPnNfc25tcF9lcnJubyA9IFNOTVBFUlJfTUFMTE9DOwogICAgICAgIHJldHVybiAoTlVMTCk7CiAgICB9CgogICAgc2xwLT5pbnRlcm5hbCA9IGlzcDsKICAgIHNscC0+c2Vzc2lvbiA9IChuZXRzbm1wX3Nlc3Npb24gKiltYWxsb2Moc2l6ZW9mKG5ldHNubXBfc2Vzc2lvbikpOwogICAgaWYgKHNscC0+c2Vzc2lvbiA9PSBOVUxMKSB7CiAgICAgICAgc25tcF9zZXNzX2Nsb3NlKHNscCk7CiAgICAgICAgaW5fc2Vzc2lvbi0+c19zbm1wX2Vycm5vID0gU05NUEVSUl9NQUxMT0M7CiAgICAgICAgcmV0dXJuIChOVUxMKTsKICAgIH0KICAgIG1lbW1vdmUoc2xwLT5zZXNzaW9uLCBpbl9zZXNzaW9uLCBzaXplb2YobmV0c25tcF9zZXNzaW9uKSk7CiAgICBzZXNzaW9uID0gc2xwLT5zZXNzaW9uOwoKICAgIC8qCiAgICAgKiB6ZXJvIG91dCBwb2ludGVycyBzbyBpZiB3ZSBoYXZlIHRvIGZyZWUgdGhlIHNlc3Npb24gd2Ugd29udCBmcmVlIG1lbQogICAgICogb3duZWQgYnkgaW5fc2Vzc2lvbiAKICAgICAqLwogICAgc2Vzc2lvbi0+bG9jYWxuYW1lID0gTlVMTDsKICAgIHNlc3Npb24tPnBlZXJuYW1lID0gTlVMTDsKICAgIHNlc3Npb24tPmNvbW11bml0eSA9IE5VTEw7CiAgICBzZXNzaW9uLT5jb250ZXh0RW5naW5lSUQgPSBOVUxMOwogICAgc2Vzc2lvbi0+Y29udGV4dE5hbWUgPSBOVUxMOwogICAgc2Vzc2lvbi0+c2VjdXJpdHlFbmdpbmVJRCA9IE5VTEw7CiAgICBzZXNzaW9uLT5zZWN1cml0eU5hbWUgPSBOVUxMOwogICAgc2Vzc2lvbi0+c2VjdXJpdHlBdXRoUHJvdG8gPSBOVUxMOwogICAgc2Vzc2lvbi0+c2VjdXJpdHlQcml2UHJvdG8gPSBOVUxMOwogICAgLyoKICAgICAqIHNlc3Npb24gbm93IHBvaW50cyB0byB0aGUgbmV3IHN0cnVjdHVyZSB0aGF0IHN0aWxsIGNvbnRhaW5zIHBvaW50ZXJzIHRvCiAgICAgKiBkYXRhIGFsbG9jYXRlZCBlbHNld2hlcmUuICBTb21lIG9mIHRoaXMgZGF0YSBpcyBjb3BpZWQgdG8gc3BhY2UgbWFsbG9jJ2QKICAgICAqIGhlcmUsIGFuZCB0aGUgcG9pbnRlciByZXBsYWNlZCB3aXRoIHRoZSBuZXcgb25lLgogICAgICovCgogICAgaWYgKGluX3Nlc3Npb24tPnBlZXJuYW1lICE9IE5VTEwpIHsKICAgICAgICBzZXNzaW9uLT5wZWVybmFtZSA9IChjaGFyICopbWFsbG9jKHN0cmxlbihpbl9zZXNzaW9uLT5wZWVybmFtZSkgKyAxKTsKICAgICAgICBpZiAoc2Vzc2lvbi0+cGVlcm5hbWUgPT0gTlVMTCkgewogICAgICAgICAgICBzbm1wX3Nlc3NfY2xvc2Uoc2xwKTsKICAgICAgICAgICAgaW5fc2Vzc2lvbi0+c19zbm1wX2Vycm5vID0gU05NUEVSUl9NQUxMT0M7CiAgICAgICAgICAgIHJldHVybiAoTlVMTCk7CiAgICAgICAgfQogICAgICAgIHN0cmNweShzZXNzaW9uLT5wZWVybmFtZSwgaW5fc2Vzc2lvbi0+cGVlcm5hbWUpOwogICAgfQoKICAgIC8qCiAgICAgKiBGaWxsIGluIGRlZmF1bHRzIGlmIG5lY2Vzc2FyeSAKICAgICAqLwojaWYgIWRlZmluZWQoTkVUU05NUF9ESVNBQkxFX1NOTVBWMSkgfHwgIWRlZmluZWQoTkVUU05NUF9ESVNBQkxFX1NOTVBWMkMpCiAgICBpZiAoaW5fc2Vzc2lvbi0+Y29tbXVuaXR5X2xlbiAhPSBTTk1QX0RFRkFVTFRfQ09NTVVOSVRZX0xFTikgewogICAgICAgIHVjcCA9ICh1X2NoYXIgKikgbWFsbG9jKGluX3Nlc3Npb24tPmNvbW11bml0eV9sZW4pOwogICAgICAgIGlmICh1Y3AgIT0gTlVMTCkKICAgICAgICAgICAgbWVtbW92ZSh1Y3AsIGluX3Nlc3Npb24tPmNvbW11bml0eSwgaW5fc2Vzc2lvbi0+Y29tbXVuaXR5X2xlbik7CiAgICB9IGVsc2UgewogICAgICAgIGlmICgoY3AgPSBuZXRzbm1wX2RzX2dldF9zdHJpbmcoTkVUU05NUF9EU19MSUJSQVJZX0lELCAKCQkJCQlORVRTTk1QX0RTX0xJQl9DT01NVU5JVFkpKSAhPSBOVUxMKSB7CiAgICAgICAgICAgIHNlc3Npb24tPmNvbW11bml0eV9sZW4gPSBzdHJsZW4oY3ApOwogICAgICAgICAgICB1Y3AgPSAodV9jaGFyICopIG1hbGxvYyhzZXNzaW9uLT5jb21tdW5pdHlfbGVuKTsKICAgICAgICAgICAgaWYgKHVjcCkKICAgICAgICAgICAgICAgIG1lbW1vdmUodWNwLCBjcCwgc2Vzc2lvbi0+Y29tbXVuaXR5X2xlbik7CiAgICAgICAgfSBlbHNlIHsKI2lmZGVmIE5FVFNOTVBfTk9fWkVST0xFTkdUSF9DT01NVU5JVFkKICAgICAgICAgICAgc2Vzc2lvbi0+Y29tbXVuaXR5X2xlbiA9IHN0cmxlbihERUZBVUxUX0NPTU1VTklUWSk7CiAgICAgICAgICAgIHVjcCA9ICh1X2NoYXIgKikgbWFsbG9jKHNlc3Npb24tPmNvbW11bml0eV9sZW4pOwogICAgICAgICAgICBpZiAodWNwKQogICAgICAgICAgICAgICAgbWVtbW92ZSh1Y3AsIERFRkFVTFRfQ09NTVVOSVRZLCBzZXNzaW9uLT5jb21tdW5pdHlfbGVuKTsKI2Vsc2UKICAgICAgICAgICAgdWNwID0gKHVfY2hhciAqKSBzdHJkdXAoIiIpOwojZW5kaWYKICAgICAgICB9CiAgICB9CgogICAgaWYgKHVjcCA9PSBOVUxMKSB7CiAgICAgICAgc25tcF9zZXNzX2Nsb3NlKHNscCk7CiAgICAgICAgaW5fc2Vzc2lvbi0+c19zbm1wX2Vycm5vID0gU05NUEVSUl9NQUxMT0M7CiAgICAgICAgcmV0dXJuIChOVUxMKTsKICAgIH0KICAgIHNlc3Npb24tPmNvbW11bml0eSA9IHVjcDsgICAvKiByZXBsYWNlIHBvaW50ZXIgd2l0aCBwb2ludGVyIHRvIG5ldyBkYXRhICovCiNlbmRpZgoKICAgIGlmIChzZXNzaW9uLT5zZWN1cml0eUxldmVsIDw9IDApIHsKICAgICAgICBzZXNzaW9uLT5zZWN1cml0eUxldmVsID0KICAgICAgICAgICAgbmV0c25tcF9kc19nZXRfaW50KE5FVFNOTVBfRFNfTElCUkFSWV9JRCwgTkVUU05NUF9EU19MSUJfU0VDTEVWRUwpOwogICAgfQoKICAgIGlmIChzZXNzaW9uLT5zZWN1cml0eUxldmVsID09IDApCiAgICAgICAgc2Vzc2lvbi0+c2VjdXJpdHlMZXZlbCA9IFNOTVBfU0VDX0xFVkVMX05PQVVUSDsKCiAgICBpZiAoaW5fc2Vzc2lvbi0+c2VjdXJpdHlBdXRoUHJvdG9MZW4gPiAwKSB7CiAgICAgICAgc2Vzc2lvbi0+c2VjdXJpdHlBdXRoUHJvdG8gPQogICAgICAgICAgICBzbm1wX2R1cGxpY2F0ZV9vYmppZChpbl9zZXNzaW9uLT5zZWN1cml0eUF1dGhQcm90bywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaW5fc2Vzc2lvbi0+c2VjdXJpdHlBdXRoUHJvdG9MZW4pOwogICAgICAgIGlmIChzZXNzaW9uLT5zZWN1cml0eUF1dGhQcm90byA9PSBOVUxMKSB7CiAgICAgICAgICAgIHNubXBfc2Vzc19jbG9zZShzbHApOwogICAgICAgICAgICBpbl9zZXNzaW9uLT5zX3NubXBfZXJybm8gPSBTTk1QRVJSX01BTExPQzsKICAgICAgICAgICAgcmV0dXJuIChOVUxMKTsKICAgICAgICB9CiAgICB9IGVsc2UgaWYgKGdldF9kZWZhdWx0X2F1dGh0eXBlKCZpKSAhPSBOVUxMKSB7CiAgICAgICAgc2Vzc2lvbi0+c2VjdXJpdHlBdXRoUHJvdG8gPQogICAgICAgICAgICBzbm1wX2R1cGxpY2F0ZV9vYmppZChnZXRfZGVmYXVsdF9hdXRodHlwZShOVUxMKSwgaSk7CiAgICAgICAgc2Vzc2lvbi0+c2VjdXJpdHlBdXRoUHJvdG9MZW4gPSBpOwogICAgfQoKICAgIGlmIChpbl9zZXNzaW9uLT5zZWN1cml0eVByaXZQcm90b0xlbiA+IDApIHsKICAgICAgICBzZXNzaW9uLT5zZWN1cml0eVByaXZQcm90byA9CiAgICAgICAgICAgIHNubXBfZHVwbGljYXRlX29iamlkKGluX3Nlc3Npb24tPnNlY3VyaXR5UHJpdlByb3RvLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBpbl9zZXNzaW9uLT5zZWN1cml0eVByaXZQcm90b0xlbik7CiAgICAgICAgaWYgKHNlc3Npb24tPnNlY3VyaXR5UHJpdlByb3RvID09IE5VTEwpIHsKICAgICAgICAgICAgc25tcF9zZXNzX2Nsb3NlKHNscCk7CiAgICAgICAgICAgIGluX3Nlc3Npb24tPnNfc25tcF9lcnJubyA9IFNOTVBFUlJfTUFMTE9DOwogICAgICAgICAgICByZXR1cm4gKE5VTEwpOwogICAgICAgIH0KICAgIH0gZWxzZSBpZiAoZ2V0X2RlZmF1bHRfcHJpdnR5cGUoJmkpICE9IE5VTEwpIHsKICAgICAgICBzZXNzaW9uLT5zZWN1cml0eVByaXZQcm90byA9CiAgICAgICAgICAgIHNubXBfZHVwbGljYXRlX29iamlkKGdldF9kZWZhdWx0X3ByaXZ0eXBlKE5VTEwpLCBpKTsKICAgICAgICBzZXNzaW9uLT5zZWN1cml0eVByaXZQcm90b0xlbiA9IGk7CiAgICB9CgogICAgaWYgKGluX3Nlc3Npb24tPnNlY3VyaXR5RW5naW5lSURMZW4gPiAwKSB7CiAgICAgICAgdWNwID0gKHVfY2hhciAqKSBtYWxsb2MoaW5fc2Vzc2lvbi0+c2VjdXJpdHlFbmdpbmVJRExlbik7CiAgICAgICAgaWYgKHVjcCA9PSBOVUxMKSB7CiAgICAgICAgICAgIHNubXBfc2Vzc19jbG9zZShzbHApOwogICAgICAgICAgICBpbl9zZXNzaW9uLT5zX3NubXBfZXJybm8gPSBTTk1QRVJSX01BTExPQzsKICAgICAgICAgICAgcmV0dXJuIChOVUxMKTsKICAgICAgICB9CiAgICAgICAgbWVtbW92ZSh1Y3AsIGluX3Nlc3Npb24tPnNlY3VyaXR5RW5naW5lSUQsCiAgICAgICAgICAgICAgICBpbl9zZXNzaW9uLT5zZWN1cml0eUVuZ2luZUlETGVuKTsKICAgICAgICBzZXNzaW9uLT5zZWN1cml0eUVuZ2luZUlEID0gdWNwOwoKICAgIH0KCiAgICBpZiAoaW5fc2Vzc2lvbi0+Y29udGV4dEVuZ2luZUlETGVuID4gMCkgewogICAgICAgIHVjcCA9ICh1X2NoYXIgKikgbWFsbG9jKGluX3Nlc3Npb24tPmNvbnRleHRFbmdpbmVJRExlbik7CiAgICAgICAgaWYgKHVjcCA9PSBOVUxMKSB7CiAgICAgICAgICAgIHNubXBfc2Vzc19jbG9zZShzbHApOwogICAgICAgICAgICBpbl9zZXNzaW9uLT5zX3NubXBfZXJybm8gPSBTTk1QRVJSX01BTExPQzsKICAgICAgICAgICAgcmV0dXJuIChOVUxMKTsKICAgICAgICB9CiAgICAgICAgbWVtbW92ZSh1Y3AsIGluX3Nlc3Npb24tPmNvbnRleHRFbmdpbmVJRCwKICAgICAgICAgICAgICAgIGluX3Nlc3Npb24tPmNvbnRleHRFbmdpbmVJRExlbik7CiAgICAgICAgc2Vzc2lvbi0+Y29udGV4dEVuZ2luZUlEID0gdWNwOwogICAgfSBlbHNlIGlmIChpbl9zZXNzaW9uLT5zZWN1cml0eUVuZ2luZUlETGVuID4gMCkgewogICAgICAgIC8qCiAgICAgICAgICogZGVmYXVsdCBjb250ZXh0RW5naW5lSUQgdG8gc2VjdXJpdHlFbmdpbmVJRExlbiBpZiBkZWZpbmVkIAogICAgICAgICAqLwogICAgICAgIHVjcCA9ICh1X2NoYXIgKikgbWFsbG9jKGluX3Nlc3Npb24tPnNlY3VyaXR5RW5naW5lSURMZW4pOwogICAgICAgIGlmICh1Y3AgPT0gTlVMTCkgewogICAgICAgICAgICBzbm1wX3Nlc3NfY2xvc2Uoc2xwKTsKICAgICAgICAgICAgaW5fc2Vzc2lvbi0+c19zbm1wX2Vycm5vID0gU05NUEVSUl9NQUxMT0M7CiAgICAgICAgICAgIHJldHVybiAoTlVMTCk7CiAgICAgICAgfQogICAgICAgIG1lbW1vdmUodWNwLCBpbl9zZXNzaW9uLT5zZWN1cml0eUVuZ2luZUlELAogICAgICAgICAgICAgICAgaW5fc2Vzc2lvbi0+c2VjdXJpdHlFbmdpbmVJRExlbik7CiAgICAgICAgc2Vzc2lvbi0+Y29udGV4dEVuZ2luZUlEID0gdWNwOwogICAgICAgIHNlc3Npb24tPmNvbnRleHRFbmdpbmVJRExlbiA9IGluX3Nlc3Npb24tPnNlY3VyaXR5RW5naW5lSURMZW47CiAgICB9CgogICAgaWYgKGluX3Nlc3Npb24tPmNvbnRleHROYW1lKSB7CiAgICAgICAgc2Vzc2lvbi0+Y29udGV4dE5hbWUgPSBzdHJkdXAoaW5fc2Vzc2lvbi0+Y29udGV4dE5hbWUpOwogICAgICAgIGlmIChzZXNzaW9uLT5jb250ZXh0TmFtZSA9PSBOVUxMKSB7CiAgICAgICAgICAgIHNubXBfc2Vzc19jbG9zZShzbHApOwogICAgICAgICAgICByZXR1cm4gKE5VTEwpOwogICAgICAgIH0KICAgICAgICBzZXNzaW9uLT5jb250ZXh0TmFtZUxlbiA9IGluX3Nlc3Npb24tPmNvbnRleHROYW1lTGVuOwogICAgfSBlbHNlIHsKICAgICAgICBpZiAoKGNwID0gbmV0c25tcF9kc19nZXRfc3RyaW5nKE5FVFNOTVBfRFNfTElCUkFSWV9JRCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIE5FVFNOTVBfRFNfTElCX0NPTlRFWFQpKSAhPSBOVUxMKQogICAgICAgICAgICBjcCA9IHN0cmR1cChjcCk7CiAgICAgICAgZWxzZQogICAgICAgICAgICBjcCA9IHN0cmR1cChTTk1QX0RFRkFVTFRfQ09OVEVYVCk7CiAgICAgICAgaWYgKGNwID09IE5VTEwpIHsKICAgICAgICAgICAgc25tcF9zZXNzX2Nsb3NlKHNscCk7CiAgICAgICAgICAgIHJldHVybiAoTlVMTCk7CiAgICAgICAgfQogICAgICAgIHNlc3Npb24tPmNvbnRleHROYW1lID0gY3A7CiAgICAgICAgc2Vzc2lvbi0+Y29udGV4dE5hbWVMZW4gPSBzdHJsZW4oY3ApOwogICAgfQoKICAgIGlmIChpbl9zZXNzaW9uLT5zZWN1cml0eU5hbWUpIHsKICAgICAgICBzZXNzaW9uLT5zZWN1cml0eU5hbWUgPSBzdHJkdXAoaW5fc2Vzc2lvbi0+c2VjdXJpdHlOYW1lKTsKICAgICAgICBpZiAoc2Vzc2lvbi0+c2VjdXJpdHlOYW1lID09IE5VTEwpIHsKICAgICAgICAgICAgc25tcF9zZXNzX2Nsb3NlKHNscCk7CiAgICAgICAgICAgIHJldHVybiAoTlVMTCk7CiAgICAgICAgfQogICAgfSBlbHNlIGlmICgoY3AgPSBuZXRzbm1wX2RzX2dldF9zdHJpbmcoTkVUU05NUF9EU19MSUJSQVJZX0lELCAKCQkJCQkgICBORVRTTk1QX0RTX0xJQl9TRUNOQU1FKSkgIT0gTlVMTCkgewogICAgICAgIGNwID0gc3RyZHVwKGNwKTsKICAgICAgICBpZiAoY3AgPT0gTlVMTCkgewogICAgICAgICAgICBzbm1wX3Nlc3NfY2xvc2Uoc2xwKTsKICAgICAgICAgICAgcmV0dXJuIChOVUxMKTsKICAgICAgICB9CiAgICAgICAgc2Vzc2lvbi0+c2VjdXJpdHlOYW1lID0gY3A7CiAgICAgICAgc2Vzc2lvbi0+c2VjdXJpdHlOYW1lTGVuID0gc3RybGVuKGNwKTsKICAgIH0KCiAgICBpZiAoKGluX3Nlc3Npb24tPnNlY3VyaXR5QXV0aEtleUxlbiA8PSAwKSAmJgogICAgICAgICgoY3AgPSBuZXRzbm1wX2RzX2dldF9zdHJpbmcoTkVUU05NUF9EU19MSUJSQVJZX0lELCAKCQkJCSAgICAgTkVUU05NUF9EU19MSUJfQVVUSE1BU1RFUktFWSkpKSkgewogICAgICAgIHNpemVfdCBidWZsZW4gPSBzaXplb2Yoc2Vzc2lvbi0+c2VjdXJpdHlBdXRoS2V5KTsKICAgICAgICB1X2NoYXIgKnRtcHAgPSBzZXNzaW9uLT5zZWN1cml0eUF1dGhLZXk7CiAgICAgICAgc2Vzc2lvbi0+c2VjdXJpdHlBdXRoS2V5TGVuID0gMDsKICAgICAgICAvKiBpdCB3aWxsIGJlIGEgaGV4IHN0cmluZyAqLwogICAgICAgIGlmICghc25tcF9oZXhfdG9fYmluYXJ5KCZ0bXBwLCAmYnVmbGVuLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICZzZXNzaW9uLT5zZWN1cml0eUF1dGhLZXlMZW4sIDAsIGNwKSkgewogICAgICAgICAgICBzbm1wX3NldF9kZXRhaWwoImVycm9yIHBhcnNpbmcgYXV0aGVudGljYXRpb24gbWFzdGVyIGtleSIpOwogICAgICAgICAgICBzbm1wX3Nlc3NfY2xvc2Uoc2xwKTsKICAgICAgICAgICAgcmV0dXJuIE5VTEw7CiAgICAgICAgfQogICAgfSBlbHNlIGlmICgoaW5fc2Vzc2lvbi0+c2VjdXJpdHlBdXRoS2V5TGVuIDw9IDApICYmCiAgICAgICAgKChjcCA9IG5ldHNubXBfZHNfZ2V0X3N0cmluZyhORVRTTk1QX0RTX0xJQlJBUllfSUQsIAoJCQkJICAgICBORVRTTk1QX0RTX0xJQl9BVVRIUEFTU1BIUkFTRSkpIHx8CiAgICAgICAgIChjcCA9IG5ldHNubXBfZHNfZ2V0X3N0cmluZyhORVRTTk1QX0RTX0xJQlJBUllfSUQsIAoJCQkJICAgICBORVRTTk1QX0RTX0xJQl9QQVNTUEhSQVNFKSkpKSB7CiAgICAgICAgc2Vzc2lvbi0+c2VjdXJpdHlBdXRoS2V5TGVuID0gVVNNX0FVVEhfS1VfTEVOOwogICAgICAgIGlmIChnZW5lcmF0ZV9LdShzZXNzaW9uLT5zZWN1cml0eUF1dGhQcm90bywKICAgICAgICAgICAgICAgICAgICAgICAgc2Vzc2lvbi0+c2VjdXJpdHlBdXRoUHJvdG9MZW4sCiAgICAgICAgICAgICAgICAgICAgICAgICh1X2NoYXIgKikgY3AsIHN0cmxlbihjcCksCiAgICAgICAgICAgICAgICAgICAgICAgIHNlc3Npb24tPnNlY3VyaXR5QXV0aEtleSwKICAgICAgICAgICAgICAgICAgICAgICAgJnNlc3Npb24tPnNlY3VyaXR5QXV0aEtleUxlbikgIT0gU05NUEVSUl9TVUNDRVNTKSB7CiAgICAgICAgICAgIHNubXBfc2V0X2RldGFpbAogICAgICAgICAgICAgICAgKCJFcnJvciBnZW5lcmF0aW5nIGEga2V5IChLdSkgZnJvbSB0aGUgc3VwcGxpZWQgYXV0aGVudGljYXRpb24gcGFzcyBwaHJhc2UuIik7CiAgICAgICAgICAgIHNubXBfc2Vzc19jbG9zZShzbHApOwogICAgICAgICAgICByZXR1cm4gTlVMTDsKICAgICAgICB9CiAgICB9CgogICAgCiAgICBpZiAoKGluX3Nlc3Npb24tPnNlY3VyaXR5UHJpdktleUxlbiA8PSAwKSAmJgogICAgICAgICgoY3AgPSBuZXRzbm1wX2RzX2dldF9zdHJpbmcoTkVUU05NUF9EU19MSUJSQVJZX0lELCAKCQkJCSAgICAgTkVUU05NUF9EU19MSUJfUFJJVk1BU1RFUktFWSkpKSkgewogICAgICAgIHNpemVfdCBidWZsZW4gPSBzaXplb2Yoc2Vzc2lvbi0+c2VjdXJpdHlQcml2S2V5KTsKICAgICAgICB1X2NoYXIgKnRtcHAgPSBzZXNzaW9uLT5zZWN1cml0eVByaXZLZXk7CiAgICAgICAgc2Vzc2lvbi0+c2VjdXJpdHlQcml2S2V5TGVuID0gMDsKICAgICAgICAvKiBpdCB3aWxsIGJlIGEgaGV4IHN0cmluZyAqLwogICAgICAgIGlmICghc25tcF9oZXhfdG9fYmluYXJ5KCZ0bXBwLCAmYnVmbGVuLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICZzZXNzaW9uLT5zZWN1cml0eVByaXZLZXlMZW4sIDAsIGNwKSkgewogICAgICAgICAgICBzbm1wX3NldF9kZXRhaWwoImVycm9yIHBhcnNpbmcgZW5jcnlwdGlvbiBtYXN0ZXIga2V5Iik7CiAgICAgICAgICAgIHNubXBfc2Vzc19jbG9zZShzbHApOwogICAgICAgICAgICByZXR1cm4gTlVMTDsKICAgICAgICB9CiAgICB9IGVsc2UgaWYgKChpbl9zZXNzaW9uLT5zZWN1cml0eVByaXZLZXlMZW4gPD0gMCkgJiYKICAgICAgICAoKGNwID0gbmV0c25tcF9kc19nZXRfc3RyaW5nKE5FVFNOTVBfRFNfTElCUkFSWV9JRCwgCgkJCQkgICAgIE5FVFNOTVBfRFNfTElCX1BSSVZQQVNTUEhSQVNFKSkgfHwKICAgICAgICAgKGNwID0gbmV0c25tcF9kc19nZXRfc3RyaW5nKE5FVFNOTVBfRFNfTElCUkFSWV9JRCwgCgkJCQkgICAgIE5FVFNOTVBfRFNfTElCX1BBU1NQSFJBU0UpKSkpIHsKICAgICAgICBzZXNzaW9uLT5zZWN1cml0eVByaXZLZXlMZW4gPSBVU01fUFJJVl9LVV9MRU47CiAgICAgICAgaWYgKGdlbmVyYXRlX0t1KHNlc3Npb24tPnNlY3VyaXR5QXV0aFByb3RvLAogICAgICAgICAgICAgICAgICAgICAgICBzZXNzaW9uLT5zZWN1cml0eUF1dGhQcm90b0xlbiwKICAgICAgICAgICAgICAgICAgICAgICAgKHVfY2hhciAqKSBjcCwgc3RybGVuKGNwKSwKICAgICAgICAgICAgICAgICAgICAgICAgc2Vzc2lvbi0+c2VjdXJpdHlQcml2S2V5LAogICAgICAgICAgICAgICAgICAgICAgICAmc2Vzc2lvbi0+c2VjdXJpdHlQcml2S2V5TGVuKSAhPSBTTk1QRVJSX1NVQ0NFU1MpIHsKICAgICAgICAgICAgc25tcF9zZXRfZGV0YWlsCiAgICAgICAgICAgICAgICAoIkVycm9yIGdlbmVyYXRpbmcgYSBrZXkgKEt1KSBmcm9tIHRoZSBzdXBwbGllZCBwcml2YWN5IHBhc3MgcGhyYXNlLiIpOwogICAgICAgICAgICBzbm1wX3Nlc3NfY2xvc2Uoc2xwKTsKICAgICAgICAgICAgcmV0dXJuIE5VTEw7CiAgICAgICAgfQogICAgfQoKICAgIGlmIChzZXNzaW9uLT5yZXRyaWVzID09IFNOTVBfREVGQVVMVF9SRVRSSUVTKQogICAgICAgIHNlc3Npb24tPnJldHJpZXMgPSBERUZBVUxUX1JFVFJJRVM7CiAgICBpZiAoc2Vzc2lvbi0+dGltZW91dCA9PSBTTk1QX0RFRkFVTFRfVElNRU9VVCkKICAgICAgICBzZXNzaW9uLT50aW1lb3V0ID0gREVGQVVMVF9USU1FT1VUOwogICAgc2Vzc2lvbi0+c2Vzc2lkID0gc25tcF9nZXRfbmV4dF9zZXNzaWQoKTsKCiAgICBzbm1wX2NhbGxfY2FsbGJhY2tzKFNOTVBfQ0FMTEJBQ0tfTElCUkFSWSwgU05NUF9DQUxMQkFDS19TRVNTSU9OX0lOSVQsCiAgICAgICAgICAgICAgICAgICAgICAgIHNlc3Npb24pOwoKICAgIGlmICgoc3B0ciA9IGZpbmRfc2VjX21vZChzZXNzaW9uLT5zZWN1cml0eU1vZGVsKSkgIT0gTlVMTCAmJgogICAgICAgIHNwdHItPnNlc3Npb25fb3BlbiAhPSBOVUxMKSB7CiAgICAgICAgLyoKICAgICAgICAgKiBzZWN1cml0eSBtb2R1bGUgc3BlY2lmaWMgaW5pYWxpemF0aW9uIAogICAgICAgICAqLwogICAgICAgICgqc3B0ci0+c2Vzc2lvbl9vcGVuKSAoc2Vzc2lvbik7CiAgICB9CgogICAgcmV0dXJuIChzbHApOwp9CgpzdGF0aWMgc3RydWN0IHNlc3Npb25fbGlzdCAqCnNubXBfc2Vzc19jb3B5KG5ldHNubXBfc2Vzc2lvbiAqIHBzcykKewogICAgc3RydWN0IHNlc3Npb25fbGlzdCAqcHNsOwogICAgcHNsID0gX3Nlc3NfY29weShwc3MpOwogICAgaWYgKCFwc2wpIHsKICAgICAgICBpZiAoIXBzcy0+c19zbm1wX2Vycm5vKSB7CiAgICAgICAgICAgIHBzcy0+c19zbm1wX2Vycm5vID0gU05NUEVSUl9HRU5FUlI7CiAgICAgICAgfQogICAgICAgIFNFVF9TTk1QX0VSUk9SKHBzcy0+c19zbm1wX2Vycm5vKTsKICAgIH0KICAgIHJldHVybiBwc2w7Cn0KCi8qKgogKiBwcm9iZSBmb3IgcGVlciBlbmdpbmVJRAogKgogKiBAcGFyYW0gc2xwICAgICAgICAgc2Vzc2lvbiBsaXN0IHBvaW50ZXIuCiAqIEBwYXJhbSBpbl9zZXNzaW9uICBzZXNzaW9uIGZvciBlcnJvcnMKICoKICogQG5vdGUKICogIC0gY2FsbGVkIGJ5IF9zZXNzX29wZW4oKSwgc25tcF9zZXNzX2FkZF9leCgpCiAqICAtIGluX3Nlc3Npb24gaXMgdGhlIHVzZXIgc3VwcGxpZWQgc2Vzc2lvbiBwcm92aWRlZCB0byB0aG9zZSBmdW5jdGlvbnMuCiAqICAtIHRoZSBmaXJzdCBzZXNzaW9uIGluIHNscCBzaG91bGQgdGhlIGludGVybmFsIGFsbG9jYXRlZCBjb3B5IG9mIGluX3Nlc3Npb24KICoKICogQHJldHVybiAwIDogZXJyb3IKICogQHJldHVybiAxIDogb2sKICoKICovCmludApzbm1wdjNfZW5naW5lSURfcHJvYmUoc3RydWN0IHNlc3Npb25fbGlzdCAqc2xwLAogICAgICAgICAgICAgICAgICAgICAgbmV0c25tcF9zZXNzaW9uICogaW5fc2Vzc2lvbikKewogICAgbmV0c25tcF9wZHUgICAgKnBkdSA9IE5VTEwsICpyZXNwb25zZSA9IE5VTEw7CiAgICBuZXRzbm1wX3Nlc3Npb24gKnNlc3Npb247CiAgICB1bnNpZ25lZCBpbnQgICAgaTsKICAgIGludCAgICAgICAgICAgICBzdGF0dXM7CgogICAgaWYgKHNscCA9PSBOVUxMIHx8IHNscC0+c2Vzc2lvbiA9PSBOVUxMKSB7CiAgICAgICAgcmV0dXJuIDA7CiAgICB9CgogICAgc2Vzc2lvbiA9IHNscC0+c2Vzc2lvbjsKCiAgICAvKgogICAgICogSWYgd2UgYXJlIG9wZW5pbmcgYSBWMyBzZXNzaW9uIGFuZCB3ZSBkb24ndCBrbm93IGVuZ2luZUlEIHdlIG11c3QgcHJvYmUKICAgICAqIGl0IC0tIHRoaXMgbXVzdCBiZSBkb25lIGFmdGVyIHRoZSBzZXNzaW9uIGlzIGNyZWF0ZWQgYW5kIGluc2VydGVkIGluIHRoZQogICAgICogbGlzdCBzbyB0aGF0IHRoZSByZXNwb25zZSBjYW4gaGFuZGxlZCBjb3JyZWN0bHkuIAogICAgICovCgogICAgaWYgKChzZXNzaW9uLT5mbGFncyAmIFNOTVBfRkxBR1NfRE9OVF9QUk9CRSkgPT0gU05NUF9GTEFHU19ET05UX1BST0JFKQogICAgICAgIHJldHVybiAxOwoKICAgIGlmIChzZXNzaW9uLT52ZXJzaW9uID09IFNOTVBfVkVSU0lPTl8zKSB7CiAgICAgICAgaWYgKHNlc3Npb24tPnNlY3VyaXR5RW5naW5lSURMZW4gPT0gMCkgewogICAgICAgICAgICBpZiAoc25tcHYzX2J1aWxkX3Byb2JlX3BkdSgmcGR1KSAhPSAwKSB7CiAgICAgICAgICAgICAgICBERUJVR01TR1RMKCgic25tcF9hcGkiLCAidW5hYmxlIHRvIGNyZWF0ZSBwcm9iZSBQRFVcbiIpKTsKICAgICAgICAgICAgICAgIHJldHVybiAwOwogICAgICAgICAgICB9CiAgICAgICAgICAgIERFQlVHTVNHVEwoKCJzbm1wX2FwaSIsICJwcm9iaW5nIGZvciBlbmdpbmVJRC4uLlxuIikpOwogICAgICAgICAgICBzZXNzaW9uLT5mbGFncyB8PSBTTk1QX0ZMQUdTX0RPTlRfUFJPQkU7IC8qIHByZXZlbnQgcmVjdXJzaW9uICovCiAgICAgICAgICAgIHN0YXR1cyA9IHNubXBfc2Vzc19zeW5jaF9yZXNwb25zZShzbHAsIHBkdSwgJnJlc3BvbnNlKTsKCiAgICAgICAgICAgIGlmICgocmVzcG9uc2UgPT0gTlVMTCkgJiYgKHN0YXR1cyA9PSBTVEFUX1NVQ0NFU1MpKSB7CiAgICAgICAgICAgICAgICBzdGF0dXMgPSBTVEFUX0VSUk9SOwogICAgICAgICAgICB9CgogICAgICAgICAgICBzd2l0Y2ggKHN0YXR1cykgewogICAgICAgICAgICBjYXNlIFNUQVRfU1VDQ0VTUzoKICAgICAgICAgICAgICAgIGluX3Nlc3Npb24tPnNfc25tcF9lcnJubyA9IFNOTVBFUlJfSU5WQUxJRF9NU0c7IC8qIFhYPz8gKi8KICAgICAgICAgICAgICAgIERFQlVHTVNHVEwoKCJzbm1wX3Nlc3Nfb3BlbiIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAiZXJyb3I6IGV4cGVjdGVkIFJlcG9ydCBhcyByZXNwb25zZSB0byBwcm9iZTogJXMgKCVkKVxuIiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNubXBfZXJyc3RyaW5nKHJlc3BvbnNlLT5lcnJzdGF0KSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJlc3BvbnNlLT5lcnJzdGF0KSk7CiAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgY2FzZSBTVEFUX0VSUk9SOiAgIC8qIHRoaXMgaXMgd2hhdCB3ZSBleHBlY3RlZCAtPiBSZXBvcnQgPT0gU1RBVF9FUlJPUiAqLwogICAgICAgICAgICAgICAgaW5fc2Vzc2lvbi0+c19zbm1wX2Vycm5vID0gU05NUEVSUl9VTktOT1dOX0VOR19JRDsKICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICBjYXNlIFNUQVRfVElNRU9VVDoKICAgICAgICAgICAgICAgIGluX3Nlc3Npb24tPnNfc25tcF9lcnJubyA9IFNOTVBFUlJfVElNRU9VVDsKICAgICAgICAgICAgZGVmYXVsdDoKICAgICAgICAgICAgICAgIERFQlVHTVNHVEwoKCJzbm1wX3Nlc3Nfb3BlbiIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAidW5hYmxlIHRvIGNvbm5lY3Qgd2l0aCByZW1vdGUgZW5naW5lOiAlcyAoJWQpXG4iLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgc25tcF9hcGlfZXJyc3RyaW5nKHNlc3Npb24tPnNfc25tcF9lcnJubyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBzZXNzaW9uLT5zX3NubXBfZXJybm8pKTsKICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICB9CgogICAgICAgICAgICBpZiAoc2xwLT5zZXNzaW9uLT5zZWN1cml0eUVuZ2luZUlETGVuID09IDApIHsKICAgICAgICAgICAgICAgIERFQlVHTVNHVEwoKCJzbm1wX2FwaSIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAidW5hYmxlIHRvIGRldGVybWluZSByZW1vdGUgZW5naW5lIElEXG4iKSk7CiAgICAgICAgICAgICAgICAvKiBjbGVhciB0aGUgZmxhZyBzbyB0aGF0IHByb2JlIG9jY3VycyBvbiBuZXh0IGluZm9ybSAqLwogICAgICAgICAgICAgICAgc2Vzc2lvbi0+ZmxhZ3MgJj0gflNOTVBfRkxBR1NfRE9OVF9QUk9CRTsKICAgICAgICAgICAgICAgIHJldHVybiAwOwogICAgICAgICAgICB9CgogICAgICAgICAgICBpbl9zZXNzaW9uLT5zX3NubXBfZXJybm8gPSBTTk1QRVJSX1NVQ0NFU1M7CiAgICAgICAgICAgIGlmIChzbm1wX2dldF9kb19kZWJ1Z2dpbmcoKSkgewogICAgICAgICAgICAgICAgREVCVUdNU0dUTCgoInNubXBfc2Vzc19vcGVuIiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICIgIHByb2JlIGZvdW5kIGVuZ2luZUlEOiAgIikpOwogICAgICAgICAgICAgICAgZm9yIChpID0gMDsgaSA8IHNscC0+c2Vzc2lvbi0+c2VjdXJpdHlFbmdpbmVJRExlbjsgaSsrKQogICAgICAgICAgICAgICAgICAgIERFQlVHTVNHKCgic25tcF9zZXNzX29wZW4iLCAiJTAyeCIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNscC0+c2Vzc2lvbi0+c2VjdXJpdHlFbmdpbmVJRFtpXSkpOwogICAgICAgICAgICAgICAgREVCVUdNU0coKCJzbm1wX3Nlc3Nfb3BlbiIsICJcbiIpKTsKICAgICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLyoKICAgICAgICAgKiBpZiBib290L3RpbWUgc3VwcGxpZWQgc2V0IGl0IGZvciB0aGlzIGVuZ2luZUlEIAogICAgICAgICAqLwogICAgICAgIGlmIChzZXNzaW9uLT5lbmdpbmVCb290cyB8fCBzZXNzaW9uLT5lbmdpbmVUaW1lKSB7CiAgICAgICAgICAgIHNldF9lbmdpbmV0aW1lKHNlc3Npb24tPnNlY3VyaXR5RW5naW5lSUQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgIHNlc3Npb24tPnNlY3VyaXR5RW5naW5lSURMZW4sCiAgICAgICAgICAgICAgICAgICAgICAgICAgIHNlc3Npb24tPmVuZ2luZUJvb3RzLCBzZXNzaW9uLT5lbmdpbmVUaW1lLAogICAgICAgICAgICAgICAgICAgICAgICAgICBUUlVFKTsKICAgICAgICB9CgogICAgICAgIGlmIChjcmVhdGVfdXNlcl9mcm9tX3Nlc3Npb24oc2xwLT5zZXNzaW9uKSAhPSBTTk1QRVJSX1NVQ0NFU1MpIHsKICAgICAgICAgICAgaW5fc2Vzc2lvbi0+c19zbm1wX2Vycm5vID0gU05NUEVSUl9VTktOT1dOX1VTRVJfTkFNRTsgICAgICAgLyogWFg/PyAqLwogICAgICAgICAgICBERUJVR01TR1RMKCgic25tcF9hcGkiLAogICAgICAgICAgICAgICAgICAgICAgICAic25tcHYzX2VuZ2luZV9wcm9iZSgpOiBmYWlsZWQoMikgdG8gY3JlYXRlIGEgbmV3IHVzZXIgZnJvbSBzZXNzaW9uXG4iKSk7CiAgICAgICAgICAgIHJldHVybiAwOwogICAgICAgIH0KICAgIH0KCiAgICByZXR1cm4gMTsKfQoKCgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi1vLSoqKioqKgogKiBzbm1wX3Nlc3Nfb3BlbgogKgogKiBQYXJhbWV0ZXJzOgogKgkqaW5fc2Vzc2lvbgogKgogKiBSZXR1cm5zOgogKiAgICAgIFBvaW50ZXIgdG8gYSBzZXNzaW9uIGluIHRoZSBzZXNzaW9uIGxpc3QgICAtT1ItCQlGSVggLS0gcmlnaHQ/CiAqCU5VTEwgb24gZmFpbHVyZS4KICoKICogVGhlICJzcGluLWZyZWUiIHZlcnNpb24gb2Ygc25tcF9vcGVuLgogKi8Kc3RhdGljIHZvaWQgICAgKgpfc2Vzc19vcGVuKG5ldHNubXBfc2Vzc2lvbiAqIGluX3Nlc3Npb24pCnsKICAgIHN0cnVjdCBzZXNzaW9uX2xpc3QgKnNscDsKICAgIG5ldHNubXBfc2Vzc2lvbiAqc2Vzc2lvbjsKICAgIGNoYXIgICAgICAgICAgICAqY2xpZW50YWRkcl9zYXZlID0gTlVMTDsKCiAgICBpbl9zZXNzaW9uLT5zX3NubXBfZXJybm8gPSAwOwogICAgaW5fc2Vzc2lvbi0+c19lcnJubyA9IDA7CgogICAgX2luaXRfc25tcCgpOwoKICAgIGlmICgoc2xwID0gc25tcF9zZXNzX2NvcHkoaW5fc2Vzc2lvbikpID09IE5VTEwpIHsKICAgICAgICByZXR1cm4gKE5VTEwpOwogICAgfQogICAgc2Vzc2lvbiA9IHNscC0+c2Vzc2lvbjsKICAgIHNscC0+dHJhbnNwb3J0ID0gTlVMTDsKCiAgICBpZiAoTlVMTCAhPSBzZXNzaW9uLT5sb2NhbG5hbWUpIHsKICAgICAgICBjbGllbnRhZGRyX3NhdmUgPSBuZXRzbm1wX2RzX2dldF9zdHJpbmcoTkVUU05NUF9EU19MSUJSQVJZX0lELAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBORVRTTk1QX0RTX0xJQl9DTElFTlRfQUREUik7CiAgICAgICAgbmV0c25tcF9kc19zZXRfc3RyaW5nKE5FVFNOTVBfRFNfTElCUkFSWV9JRCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgTkVUU05NUF9EU19MSUJfQ0xJRU5UX0FERFIsIHNlc3Npb24tPmxvY2FsbmFtZSk7CiAgICB9CgogICAgaWYgKHNlc3Npb24tPmZsYWdzICYgU05NUF9GTEFHU19TVFJFQU1fU09DS0VUKSB7CiAgICAgICAgc2xwLT50cmFuc3BvcnQgPQoJICBuZXRzbm1wX3Rkb21haW5fdHJhbnNwb3J0X2Z1bGwoInNubXAiLCBzZXNzaW9uLT5wZWVybmFtZSwKCQkJCQkgc2Vzc2lvbi0+bG9jYWxfcG9ydCwgInRjcCIsIE5VTEwpOwogICAgfSBlbHNlIHsKICAgICAgICBzbHAtPnRyYW5zcG9ydCA9CgkgIG5ldHNubXBfdGRvbWFpbl90cmFuc3BvcnRfZnVsbCgic25tcCIsIHNlc3Npb24tPnBlZXJuYW1lLAoJCQkJCSBzZXNzaW9uLT5sb2NhbF9wb3J0LCAidWRwIiwgTlVMTCk7CiAgICB9CgogICAgaWYgKE5VTEwgIT0gc2Vzc2lvbi0+bG9jYWxuYW1lKQogICAgICAgIG5ldHNubXBfZHNfc2V0X3N0cmluZyhORVRTTk1QX0RTX0xJQlJBUllfSUQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIE5FVFNOTVBfRFNfTElCX0NMSUVOVF9BRERSLCBjbGllbnRhZGRyX3NhdmUpOwoKICAgIGlmIChzbHAtPnRyYW5zcG9ydCA9PSBOVUxMKSB7CiAgICAgICAgREVCVUdNU0dUTCgoIl9zZXNzX29wZW4iLCAiY291bGRuJ3QgaW50ZXJwcmV0IHBlZXJuYW1lXG4iKSk7CiAgICAgICAgaW5fc2Vzc2lvbi0+c19zbm1wX2Vycm5vID0gU05NUEVSUl9CQURfQUREUkVTUzsKICAgICAgICBpbl9zZXNzaW9uLT5zX2Vycm5vID0gZXJybm87CiAgICAgICAgc25tcF9zZXRfZGV0YWlsKHNlc3Npb24tPnBlZXJuYW1lKTsKICAgICAgICBzbm1wX3Nlc3NfY2xvc2Uoc2xwKTsKICAgICAgICByZXR1cm4gTlVMTDsKICAgIH0KCiAgICBzZXNzaW9uLT5yY3ZNc2dNYXhTaXplID0gc2xwLT50cmFuc3BvcnQtPm1zZ01heFNpemU7CgogICAgaWYgKCFzbm1wdjNfZW5naW5lSURfcHJvYmUoc2xwLCBpbl9zZXNzaW9uKSkgewogICAgICAgIHNubXBfc2Vzc19jbG9zZShzbHApOwogICAgICAgIHJldHVybiBOVUxMOwogICAgfQogICAgaWYgKGNyZWF0ZV91c2VyX2Zyb21fc2Vzc2lvbihzbHAtPnNlc3Npb24pICE9IFNOTVBFUlJfU1VDQ0VTUykgewogICAgICAgIGluX3Nlc3Npb24tPnNfc25tcF9lcnJubyA9IFNOTVBFUlJfVU5LTk9XTl9VU0VSX05BTUU7ICAgICAgIC8qIFhYPz8gKi8KICAgICAgICBERUJVR01TR1RMKCgic25tcF9hcGkiLAogICAgICAgICAgICAgICAgICAgICJfc2Vzc19vcGVuKCk6IGZhaWxlZCgyKSB0byBjcmVhdGUgYSBuZXcgdXNlciBmcm9tIHNlc3Npb25cbiIpKTsKICAgICAgICBzbm1wX3Nlc3NfY2xvc2Uoc2xwKTsKICAgICAgICByZXR1cm4gTlVMTDsKICAgIH0KICAgIAogICAgc2Vzc2lvbi0+ZmxhZ3MgJj0gflNOTVBfRkxBR1NfRE9OVF9QUk9CRTsKCgogICAgcmV0dXJuICh2b2lkICopIHNscDsKfSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAvKiBlbmQgc25tcF9zZXNzX29wZW4oKSAqLwoKCgovKgogKiBFWFRFTkRFRCBTRVNTSU9OIEFQSSAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0gCiAqIAogKiBzbm1wX3Nlc3NfYWRkX2V4LCBzbm1wX3Nlc3NfYWRkLCBzbm1wX2FkZCAKICogCiAqIEFuYWxvZ291cyB0byBzbm1wX29wZW4gZmFtaWx5IG9mIGZ1bmN0aW9ucywgYnV0IHRha2luZyBhIG5ldHNubXBfdHJhbnNwb3J0CiAqIHBvaW50ZXIgYXMgYW4gZXh0cmEgYXJndW1lbnQuICBVbmxpa2Ugc25tcF9vcGVuIGV0IGFsLiBpdCBkb2Vzbid0IGF0dGVtcHQKICogdG8gaW50ZXJwcmV0IHRoZSBpbl9zZXNzaW9uLT5wZWVybmFtZSBhcyBhIHRyYW5zcG9ydCBlbmRwb2ludCBzcGVjaWZpZXIsCiAqIGJ1dCBpbnN0ZWFkIHVzZXMgdGhlIHN1cHBsaWVkIHRyYW5zcG9ydC4gIEpCUE4KICogCiAqLwoKbmV0c25tcF9zZXNzaW9uICoKc25tcF9hZGQobmV0c25tcF9zZXNzaW9uICogaW5fc2Vzc2lvbiwKICAgICAgICAgbmV0c25tcF90cmFuc3BvcnQgKnRyYW5zcG9ydCwKICAgICAgICAgaW50ICgqZnByZV9wYXJzZSkgKG5ldHNubXBfc2Vzc2lvbiAqLCBuZXRzbm1wX3RyYW5zcG9ydCAqLCB2b2lkICosCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBpbnQpLCBpbnQgKCpmcG9zdF9wYXJzZSkgKG5ldHNubXBfc2Vzc2lvbiAqLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBuZXRzbm1wX3BkdSAqLCBpbnQpKQp7CiAgICBzdHJ1Y3Qgc2Vzc2lvbl9saXN0ICpzbHA7CiAgICBzbHAgPSAoc3RydWN0IHNlc3Npb25fbGlzdCAqKSBzbm1wX3Nlc3NfYWRkX2V4KGluX3Nlc3Npb24sIHRyYW5zcG9ydCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZnByZV9wYXJzZSwgTlVMTCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZnBvc3RfcGFyc2UsIE5VTEwsIE5VTEwsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIE5VTEwsIE5VTEwpOwogICAgaWYgKHNscCA9PSBOVUxMKSB7CiAgICAgICAgcmV0dXJuIE5VTEw7CiAgICB9CgogICAgc25tcF9yZXNfbG9jayhNVF9MSUJSQVJZX0lELCBNVF9MSUJfU0VTU0lPTik7CiAgICBzbHAtPm5leHQgPSBTZXNzaW9uczsKICAgIFNlc3Npb25zID0gc2xwOwogICAgc25tcF9yZXNfdW5sb2NrKE1UX0xJQlJBUllfSUQsIE1UX0xJQl9TRVNTSU9OKTsKCiAgICByZXR1cm4gKHNscC0+c2Vzc2lvbik7Cn0KCm5ldHNubXBfc2Vzc2lvbiAqCnNubXBfYWRkX2Z1bGwobmV0c25tcF9zZXNzaW9uICogaW5fc2Vzc2lvbiwKICAgICAgICAgICAgICBuZXRzbm1wX3RyYW5zcG9ydCAqdHJhbnNwb3J0LAogICAgICAgICAgICAgIGludCAoKmZwcmVfcGFyc2UpIChuZXRzbm1wX3Nlc3Npb24gKiwgbmV0c25tcF90cmFuc3BvcnQgKiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdm9pZCAqLCBpbnQpLAogICAgICAgICAgICAgIGludCAoKmZwYXJzZSkgKG5ldHNubXBfc2Vzc2lvbiAqLCBuZXRzbm1wX3BkdSAqLCB1X2NoYXIgKiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzaXplX3QpLAogICAgICAgICAgICAgIGludCAoKmZwb3N0X3BhcnNlKSAobmV0c25tcF9zZXNzaW9uICosIG5ldHNubXBfcGR1ICosIGludCksCiAgICAgICAgICAgICAgaW50ICgqZmJ1aWxkKSAobmV0c25tcF9zZXNzaW9uICosIG5ldHNubXBfcGR1ICosIHVfY2hhciAqLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNpemVfdCAqKSwgaW50ICgqZnJidWlsZCkgKG5ldHNubXBfc2Vzc2lvbiAqLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIG5ldHNubXBfcGR1ICosCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdV9jaGFyICoqLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNpemVfdCAqLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNpemVfdCAqKSwKICAgICAgICAgICAgICBpbnQgKCpmY2hlY2spICh1X2NoYXIgKiwgc2l6ZV90KSwKICAgICAgICAgICAgICBuZXRzbm1wX3BkdSAqKCpmY3JlYXRlX3BkdSkgKG5ldHNubXBfdHJhbnNwb3J0ICosIHZvaWQgKiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNpemVfdCkpCnsKICAgIHN0cnVjdCBzZXNzaW9uX2xpc3QgKnNscDsKICAgIHNscCA9IChzdHJ1Y3Qgc2Vzc2lvbl9saXN0ICopIHNubXBfc2Vzc19hZGRfZXgoaW5fc2Vzc2lvbiwgdHJhbnNwb3J0LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBmcHJlX3BhcnNlLCBmcGFyc2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGZwb3N0X3BhcnNlLCBmYnVpbGQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGZyYnVpbGQsIGZjaGVjaywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZmNyZWF0ZV9wZHUpOwogICAgaWYgKHNscCA9PSBOVUxMKSB7CiAgICAgICAgcmV0dXJuIE5VTEw7CiAgICB9CgogICAgc25tcF9yZXNfbG9jayhNVF9MSUJSQVJZX0lELCBNVF9MSUJfU0VTU0lPTik7CiAgICBzbHAtPm5leHQgPSBTZXNzaW9uczsKICAgIFNlc3Npb25zID0gc2xwOwogICAgc25tcF9yZXNfdW5sb2NrKE1UX0xJQlJBUllfSUQsIE1UX0xJQl9TRVNTSU9OKTsKCiAgICByZXR1cm4gKHNscC0+c2Vzc2lvbik7Cn0KCgoKdm9pZCAgICAgICAgICAgKgpzbm1wX3Nlc3NfYWRkX2V4KG5ldHNubXBfc2Vzc2lvbiAqIGluX3Nlc3Npb24sCiAgICAgICAgICAgICAgICAgbmV0c25tcF90cmFuc3BvcnQgKnRyYW5zcG9ydCwKICAgICAgICAgICAgICAgICBpbnQgKCpmcHJlX3BhcnNlKSAobmV0c25tcF9zZXNzaW9uICosIG5ldHNubXBfdHJhbnNwb3J0ICosCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHZvaWQgKiwgaW50KSwKICAgICAgICAgICAgICAgICBpbnQgKCpmcGFyc2UpIChuZXRzbm1wX3Nlc3Npb24gKiwgbmV0c25tcF9wZHUgKiwgdV9jaGFyICosCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2l6ZV90KSwKICAgICAgICAgICAgICAgICBpbnQgKCpmcG9zdF9wYXJzZSkgKG5ldHNubXBfc2Vzc2lvbiAqLCBuZXRzbm1wX3BkdSAqLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaW50KSwKICAgICAgICAgICAgICAgICBpbnQgKCpmYnVpbGQpIChuZXRzbm1wX3Nlc3Npb24gKiwgbmV0c25tcF9wZHUgKiwgdV9jaGFyICosCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2l6ZV90ICopLAogICAgICAgICAgICAgICAgIGludCAoKmZyYnVpbGQpIChuZXRzbm1wX3Nlc3Npb24gKiwgbmV0c25tcF9wZHUgKiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdV9jaGFyICoqLCBzaXplX3QgKiwgc2l6ZV90ICopLAogICAgICAgICAgICAgICAgIGludCAoKmZjaGVjaykgKHVfY2hhciAqLCBzaXplX3QpLAogICAgICAgICAgICAgICAgIG5ldHNubXBfcGR1ICooKmZjcmVhdGVfcGR1KSAobmV0c25tcF90cmFuc3BvcnQgKiwgdm9pZCAqLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2l6ZV90KSkKewogICAgc3RydWN0IHNlc3Npb25fbGlzdCAqc2xwOwoKICAgIF9pbml0X3NubXAoKTsKCiAgICBpZiAodHJhbnNwb3J0ID09IE5VTEwpCiAgICAgICAgcmV0dXJuIE5VTEw7CgogICAgaWYgKGluX3Nlc3Npb24gPT0gTlVMTCkgewogICAgICAgIHRyYW5zcG9ydC0+Zl9jbG9zZSh0cmFuc3BvcnQpOwogICAgICAgIG5ldHNubXBfdHJhbnNwb3J0X2ZyZWUodHJhbnNwb3J0KTsKICAgICAgICByZXR1cm4gTlVMTDsKICAgIH0KCiAgICBERUJVR01TR1RMKCgic25tcF9zZXNzX2FkZCIsICJmZCAlZFxuIiwgdHJhbnNwb3J0LT5zb2NrKSk7CgogICAgaWYgKChzbHAgPSBzbm1wX3Nlc3NfY29weShpbl9zZXNzaW9uKSkgPT0gTlVMTCkgewogICAgICAgIHRyYW5zcG9ydC0+Zl9jbG9zZSh0cmFuc3BvcnQpOwogICAgICAgIG5ldHNubXBfdHJhbnNwb3J0X2ZyZWUodHJhbnNwb3J0KTsKICAgICAgICByZXR1cm4gKE5VTEwpOwogICAgfQoKICAgIHNscC0+dHJhbnNwb3J0ID0gdHJhbnNwb3J0OwogICAgc2xwLT5pbnRlcm5hbC0+aG9va19wcmUgPSBmcHJlX3BhcnNlOwogICAgc2xwLT5pbnRlcm5hbC0+aG9va19wYXJzZSA9IGZwYXJzZTsKICAgIHNscC0+aW50ZXJuYWwtPmhvb2tfcG9zdCA9IGZwb3N0X3BhcnNlOwogICAgc2xwLT5pbnRlcm5hbC0+aG9va19idWlsZCA9IGZidWlsZDsKICAgIHNscC0+aW50ZXJuYWwtPmhvb2tfcmVhbGxvY19idWlsZCA9IGZyYnVpbGQ7CiAgICBzbHAtPmludGVybmFsLT5jaGVja19wYWNrZXQgPSBmY2hlY2s7CiAgICBzbHAtPmludGVybmFsLT5ob29rX2NyZWF0ZV9wZHUgPSBmY3JlYXRlX3BkdTsKCiAgICBzbHAtPnNlc3Npb24tPnJjdk1zZ01heFNpemUgPSB0cmFuc3BvcnQtPm1zZ01heFNpemU7CgogICAgaWYgKHNscC0+c2Vzc2lvbi0+dmVyc2lvbiA9PSBTTk1QX1ZFUlNJT05fMykgewogICAgICAgIERFQlVHTVNHVEwoKCJzbm1wX3Nlc3NfYWRkIiwKICAgICAgICAgICAgICAgICAgICAiYWRkaW5nIHYzIHNlc3Npb24gLS0gZW5naW5lSUQgcHJvYmUgbm93XG4iKSk7CiAgICAgICAgaWYgKCFzbm1wdjNfZW5naW5lSURfcHJvYmUoc2xwLCBpbl9zZXNzaW9uKSkgewogICAgICAgICAgICBERUJVR01TR1RMKCgic25tcF9zZXNzX2FkZCIsICJlbmdpbmUgSUQgcHJvYmUgZmFpbGVkXG4iKSk7CiAgICAgICAgICAgIHNubXBfc2Vzc19jbG9zZShzbHApOwogICAgICAgICAgICByZXR1cm4gTlVMTDsKICAgICAgICB9CiAgICAgICAgaWYgKGNyZWF0ZV91c2VyX2Zyb21fc2Vzc2lvbihzbHAtPnNlc3Npb24pICE9IFNOTVBFUlJfU1VDQ0VTUykgewogICAgICAgICAgICBpbl9zZXNzaW9uLT5zX3NubXBfZXJybm8gPSBTTk1QRVJSX1VOS05PV05fVVNFUl9OQU1FOwogICAgICAgICAgICBERUJVR01TR1RMKCgic25tcF9hcGkiLAogICAgICAgICAgICAgICAgICAgICAgICAic25tcF9zZXNzX2FkZCgpOiBmYWlsZWQoMikgdG8gY3JlYXRlIGEgbmV3IHVzZXIgZnJvbSBzZXNzaW9uXG4iKSk7CiAgICAgICAgICAgIHNubXBfc2Vzc19jbG9zZShzbHApOwogICAgICAgICAgICByZXR1cm4gTlVMTDsKICAgICAgICB9CiAgICB9CgogICAgc2xwLT5zZXNzaW9uLT5mbGFncyAmPSB+U05NUF9GTEFHU19ET05UX1BST0JFOwoKICAgIHJldHVybiAodm9pZCAqKSBzbHA7Cn0gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgLyogIGVuZCBzbm1wX3Nlc3NfYWRkX2V4KCkgICovCgoKCnZvaWQgICAgICAgICAgICoKc25tcF9zZXNzX2FkZChuZXRzbm1wX3Nlc3Npb24gKiBpbl9zZXNzaW9uLAogICAgICAgICAgICAgIG5ldHNubXBfdHJhbnNwb3J0ICp0cmFuc3BvcnQsCiAgICAgICAgICAgICAgaW50ICgqZnByZV9wYXJzZSkgKG5ldHNubXBfc2Vzc2lvbiAqLCBuZXRzbm1wX3RyYW5zcG9ydCAqLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2b2lkICosIGludCksCiAgICAgICAgICAgICAgaW50ICgqZnBvc3RfcGFyc2UpIChuZXRzbm1wX3Nlc3Npb24gKiwgbmV0c25tcF9wZHUgKiwgaW50KSkKewogICAgcmV0dXJuIHNubXBfc2Vzc19hZGRfZXgoaW5fc2Vzc2lvbiwgdHJhbnNwb3J0LCBmcHJlX3BhcnNlLCBOVUxMLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgZnBvc3RfcGFyc2UsIE5VTEwsIE5VTEwsIE5VTEwsIE5VTEwpOwp9CgoKCnZvaWQgICAgICAgICAgICoKc25tcF9zZXNzX29wZW4obmV0c25tcF9zZXNzaW9uICogcHNzKQp7CiAgICB2b2lkICAgICAgICAgICAqcHZvaWQ7CiAgICBwdm9pZCA9IF9zZXNzX29wZW4ocHNzKTsKICAgIGlmICghcHZvaWQpIHsKICAgICAgICBTRVRfU05NUF9FUlJPUihwc3MtPnNfc25tcF9lcnJubyk7CiAgICB9CiAgICByZXR1cm4gcHZvaWQ7Cn0KCgoKLyoKICogY3JlYXRlX3VzZXJfZnJvbV9zZXNzaW9uKG5ldHNubXBfc2Vzc2lvbiAqc2Vzc2lvbik6CiAqIAogKiBjcmVhdGVzIGEgdXNlciBpbiB0aGUgdXNtIHRhYmxlIGZyb20gdGhlIGluZm9ybWF0aW9uIGluIGEgc2Vzc2lvbi4KICogSWYgdGhlIHVzZXIgYWxyZWFkeSBleGlzdHMsIGl0IGlzIHVwZGF0ZWQgd2l0aCB0aGUgY3VycmVudAogKiBpbmZvcm1hdGlvbiBmcm9tIHRoZSBzZXNzaW9uCiAqIAogKiBQYXJhbWV0ZXJzOgogKiBzZXNzaW9uIC0tIElOOiBwb2ludGVyIHRvIHRoZSBzZXNzaW9uIHRvIHVzZSB3aGVuIGNyZWF0aW5nIHRoZSB1c2VyLgogKiAKICogUmV0dXJuczoKICogU05NUEVSUl9TVUNDRVNTCiAqIFNOTVBFUlJfR0VORVJSIAogKi8KaW50CmNyZWF0ZV91c2VyX2Zyb21fc2Vzc2lvbihuZXRzbm1wX3Nlc3Npb24gKiBzZXNzaW9uKQp7CiAgICBzdHJ1Y3QgdXNtVXNlciAqdXNlcjsKICAgIGludCAgICAgICAgICAgICB1c2VyX2p1c3RfY3JlYXRlZCA9IDA7CiAgICBjaGFyICpjcDsKCiAgICAvKgogICAgICogLSBkb24ndCBjcmVhdGUtYW5vdGhlci9jb3B5LWludG8gdXNlciBmb3IgdGhpcyBzZXNzaW9uIGJ5IGRlZmF1bHQKICAgICAqIC0gYmFpbCBub3cgKG5vIGVycm9yKSBpZiB3ZSBkb24ndCBoYXZlIGFuIGVuZ2luZUlECiAgICAgKi8KICAgIGlmIChTTk1QX0ZMQUdTX1VTRVJfQ1JFQVRFRCA9PSAoc2Vzc2lvbi0+ZmxhZ3MgJiBTTk1QX0ZMQUdTX1VTRVJfQ1JFQVRFRCkgfHwKICAgICAgICBzZXNzaW9uLT5zZWN1cml0eU1vZGVsICE9IFNOTVBfU0VDX01PREVMX1VTTSB8fAogICAgICAgIHNlc3Npb24tPnZlcnNpb24gIT0gU05NUF9WRVJTSU9OXzMgfHwKICAgICAgICBzZXNzaW9uLT5zZWN1cml0eU5hbWVMZW4gPT0gMCB8fAogICAgICAgIHNlc3Npb24tPnNlY3VyaXR5RW5naW5lSURMZW4gPT0gMCkKICAgICAgICByZXR1cm4gU05NUEVSUl9TVUNDRVNTOwoKICAgIHNlc3Npb24tPmZsYWdzIHw9IFNOTVBfRkxBR1NfVVNFUl9DUkVBVEVEOwoKICAgIC8qCiAgICAgKiBub3cgdGhhdCB3ZSBoYXZlIHRoZSBlbmdpbmVJRCwgY3JlYXRlIGFuIGVudHJ5IGluIHRoZSBVU00gbGlzdAogICAgICogZm9yIHRoaXMgdXNlciB1c2luZyB0aGUgaW5mb3JtYXRpb24gaW4gdGhlIHNlc3Npb24gCiAgICAgKi8KICAgIHVzZXIgPSB1c21fZ2V0X3VzZXJfZnJvbV9saXN0KHNlc3Npb24tPnNlY3VyaXR5RW5naW5lSUQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzZXNzaW9uLT5zZWN1cml0eUVuZ2luZUlETGVuLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2Vzc2lvbi0+c2VjdXJpdHlOYW1lLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdXNtX2dldF91c2VyTGlzdCgpLCAwKTsKICAgIGlmICh1c2VyID09IE5VTEwpIHsKICAgICAgICBERUJVR01TR1RMKCgic25tcF9hcGkiLCAiQnVpbGRpbmcgdXNlciAlcy4uLlxuIiwKICAgICAgICAgICAgICAgICAgICBzZXNzaW9uLT5zZWN1cml0eU5hbWUpKTsKICAgICAgICAvKgogICAgICAgICAqIHVzZXIgZG9lc24ndCBleGlzdCBzbyB3ZSBjcmVhdGUgYW5kIGFkZCBpdCAKICAgICAgICAgKi8KICAgICAgICB1c2VyID0gKHN0cnVjdCB1c21Vc2VyICopIGNhbGxvYygxLCBzaXplb2Yoc3RydWN0IHVzbVVzZXIpKTsKICAgICAgICBpZiAodXNlciA9PSBOVUxMKQogICAgICAgICAgICByZXR1cm4gU05NUEVSUl9HRU5FUlI7CgogICAgICAgIC8qCiAgICAgICAgICogY29weSBpbiB0aGUgc2VjdXJpdHlOYW1lIAogICAgICAgICAqLwogICAgICAgIGlmIChzZXNzaW9uLT5zZWN1cml0eU5hbWUpIHsKICAgICAgICAgICAgdXNlci0+bmFtZSA9IHN0cmR1cChzZXNzaW9uLT5zZWN1cml0eU5hbWUpOwogICAgICAgICAgICB1c2VyLT5zZWNOYW1lID0gc3RyZHVwKHNlc3Npb24tPnNlY3VyaXR5TmFtZSk7CiAgICAgICAgICAgIGlmICh1c2VyLT5uYW1lID09IE5VTEwgfHwgdXNlci0+c2VjTmFtZSA9PSBOVUxMKSB7CiAgICAgICAgICAgICAgICB1c21fZnJlZV91c2VyKHVzZXIpOwogICAgICAgICAgICAgICAgcmV0dXJuIFNOTVBFUlJfR0VORVJSOwogICAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvKgogICAgICAgICAqIGNvcHkgaW4gdGhlIGVuZ2luZUlEIAogICAgICAgICAqLwogICAgICAgIHVzZXItPmVuZ2luZUlEID0gbmV0c25tcF9tZW1kdXAoc2Vzc2lvbi0+c2VjdXJpdHlFbmdpbmVJRCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNlc3Npb24tPnNlY3VyaXR5RW5naW5lSURMZW4pOwogICAgICAgIGlmICghdXNlci0+ZW5naW5lSUQpIHsKICAgICAgICAgICAgdXNtX2ZyZWVfdXNlcih1c2VyKTsKICAgICAgICAgICAgcmV0dXJuIFNOTVBFUlJfR0VORVJSOwogICAgICAgIH0KICAgICAgICB1c2VyLT5lbmdpbmVJRExlbiA9IHNlc3Npb24tPnNlY3VyaXR5RW5naW5lSURMZW47CgogICAgICAgIHVzZXJfanVzdF9jcmVhdGVkID0gMTsKICAgIH0KCiAgICAvKgogICAgICogY29weSB0aGUgYXV0aCBwcm90b2NvbCAKICAgICAqLwogICAgaWYgKHVzZXItPmF1dGhQcm90b2NvbCA9PSBOVUxMICYmIHNlc3Npb24tPnNlY3VyaXR5QXV0aFByb3RvICE9IE5VTEwpIHsKICAgICAgICBTTk1QX0ZSRUUodXNlci0+YXV0aFByb3RvY29sKTsKICAgICAgICB1c2VyLT5hdXRoUHJvdG9jb2wgPQogICAgICAgICAgICBzbm1wX2R1cGxpY2F0ZV9vYmppZChzZXNzaW9uLT5zZWN1cml0eUF1dGhQcm90bywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2Vzc2lvbi0+c2VjdXJpdHlBdXRoUHJvdG9MZW4pOwogICAgICAgIGlmICh1c2VyLT5hdXRoUHJvdG9jb2wgPT0gTlVMTCkgewogICAgICAgICAgICB1c21fZnJlZV91c2VyKHVzZXIpOwogICAgICAgICAgICByZXR1cm4gU05NUEVSUl9HRU5FUlI7CiAgICAgICAgfQogICAgICAgIHVzZXItPmF1dGhQcm90b2NvbExlbiA9IHNlc3Npb24tPnNlY3VyaXR5QXV0aFByb3RvTGVuOwogICAgfQoKICAgIC8qCiAgICAgKiBjb3B5IHRoZSBwcml2IHByb3RvY29sIAogICAgICovCiAgICBpZiAodXNlci0+cHJpdlByb3RvY29sID09IE5VTEwgJiYgc2Vzc2lvbi0+c2VjdXJpdHlQcml2UHJvdG8gIT0gTlVMTCkgewogICAgICAgIFNOTVBfRlJFRSh1c2VyLT5wcml2UHJvdG9jb2wpOwogICAgICAgIHVzZXItPnByaXZQcm90b2NvbCA9CiAgICAgICAgICAgIHNubXBfZHVwbGljYXRlX29iamlkKHNlc3Npb24tPnNlY3VyaXR5UHJpdlByb3RvLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzZXNzaW9uLT5zZWN1cml0eVByaXZQcm90b0xlbik7CiAgICAgICAgaWYgKHVzZXItPnByaXZQcm90b2NvbCA9PSBOVUxMKSB7CiAgICAgICAgICAgIHVzbV9mcmVlX3VzZXIodXNlcik7CiAgICAgICAgICAgIHJldHVybiBTTk1QRVJSX0dFTkVSUjsKICAgICAgICB9CiAgICAgICAgdXNlci0+cHJpdlByb3RvY29sTGVuID0gc2Vzc2lvbi0+c2VjdXJpdHlQcml2UHJvdG9MZW47CiAgICB9CgogICAgLyoKICAgICAqIGNvcHkgaW4gdGhlIGF1dGhlbnRpY2F0aW9uIEtleS4gIElmIG5vdCBsb2NhbGl6ZWQsIGxvY2FsaXplIGl0IAogICAgICovCiAgICBpZiAodXNlci0+YXV0aEtleSA9PSBOVUxMKSB7CiAgICAgICAgaWYgKHNlc3Npb24tPnNlY3VyaXR5QXV0aExvY2FsS2V5ICE9IE5VTEwKICAgICAgICAgICAgJiYgc2Vzc2lvbi0+c2VjdXJpdHlBdXRoTG9jYWxLZXlMZW4gIT0gMCkgewogICAgICAgICAgICAvKiBhbHJlYWR5IGxvY2FsaXplZCBrZXkgcGFzc2VkIGluLiAgdXNlIGl0ICovCiAgICAgICAgICAgIFNOTVBfRlJFRSh1c2VyLT5hdXRoS2V5KTsKICAgICAgICAgICAgdXNlci0+YXV0aEtleSA9IG5ldHNubXBfbWVtZHVwKHNlc3Npb24tPnNlY3VyaXR5QXV0aExvY2FsS2V5LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2Vzc2lvbi0+c2VjdXJpdHlBdXRoTG9jYWxLZXlMZW4pOwogICAgICAgICAgICBpZiAoIXVzZXItPmF1dGhLZXkpIHsKICAgICAgICAgICAgICAgIHVzbV9mcmVlX3VzZXIodXNlcik7CiAgICAgICAgICAgICAgICByZXR1cm4gU05NUEVSUl9HRU5FUlI7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdXNlci0+YXV0aEtleUxlbiA9IHNlc3Npb24tPnNlY3VyaXR5QXV0aExvY2FsS2V5TGVuOwogICAgICAgIH0gZWxzZSBpZiAoc2Vzc2lvbi0+c2VjdXJpdHlBdXRoS2V5ICE9IE5VTEwKICAgICAgICAgICAgICAgICAgICYmIHNlc3Npb24tPnNlY3VyaXR5QXV0aEtleUxlbiAhPSAwKSB7CiAgICAgICAgICAgIFNOTVBfRlJFRSh1c2VyLT5hdXRoS2V5KTsKICAgICAgICAgICAgdXNlci0+YXV0aEtleSA9ICh1X2NoYXIgKikgY2FsbG9jKDEsIFVTTV9MRU5HVEhfS1VfSEFTSEJMT0NLKTsKICAgICAgICAgICAgaWYgKHVzZXItPmF1dGhLZXkgPT0gTlVMTCkgewogICAgICAgICAgICAgICAgdXNtX2ZyZWVfdXNlcih1c2VyKTsKICAgICAgICAgICAgICAgIHJldHVybiBTTk1QRVJSX0dFTkVSUjsKICAgICAgICAgICAgfQogICAgICAgICAgICB1c2VyLT5hdXRoS2V5TGVuID0gVVNNX0xFTkdUSF9LVV9IQVNIQkxPQ0s7CiAgICAgICAgICAgIGlmIChnZW5lcmF0ZV9rdWwodXNlci0+YXV0aFByb3RvY29sLCB1c2VyLT5hdXRoUHJvdG9jb2xMZW4sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2Vzc2lvbi0+c2VjdXJpdHlFbmdpbmVJRCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzZXNzaW9uLT5zZWN1cml0eUVuZ2luZUlETGVuLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNlc3Npb24tPnNlY3VyaXR5QXV0aEtleSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzZXNzaW9uLT5zZWN1cml0eUF1dGhLZXlMZW4sIHVzZXItPmF1dGhLZXksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJnVzZXItPmF1dGhLZXlMZW4pICE9IFNOTVBFUlJfU1VDQ0VTUykgewogICAgICAgICAgICAgICAgdXNtX2ZyZWVfdXNlcih1c2VyKTsKICAgICAgICAgICAgICAgIHJldHVybiBTTk1QRVJSX0dFTkVSUjsKICAgICAgICAgICAgfQogICAgICAgIH0gZWxzZSBpZiAoKGNwID0gbmV0c25tcF9kc19nZXRfc3RyaW5nKE5FVFNOTVBfRFNfTElCUkFSWV9JRCwgCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgTkVUU05NUF9EU19MSUJfQVVUSExPQ0FMSVpFREtFWSkpKSB7CiAgICAgICAgICAgIHNpemVfdCBidWZsZW4gPSBVU01fQVVUSF9LVV9MRU47CiAgICAgICAgICAgIFNOTVBfRlJFRSh1c2VyLT5hdXRoS2V5KTsKICAgICAgICAgICAgdXNlci0+YXV0aEtleSA9ICh1X2NoYXIgKiltYWxsb2MoYnVmbGVuKTsgLyogbWF4IGxlbmd0aCBuZWVkZWQgKi8KICAgICAgICAgICAgdXNlci0+YXV0aEtleUxlbiA9IDA7CiAgICAgICAgICAgIC8qIGl0IHdpbGwgYmUgYSBoZXggc3RyaW5nICovCiAgICAgICAgICAgIGlmICghc25tcF9oZXhfdG9fYmluYXJ5KCZ1c2VyLT5hdXRoS2V5LCAmYnVmbGVuLCAmdXNlci0+YXV0aEtleUxlbiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgMCwgY3ApKSB7CiAgICAgICAgICAgICAgICB1c21fZnJlZV91c2VyKHVzZXIpOwogICAgICAgICAgICAgICAgcmV0dXJuIFNOTVBFUlJfR0VORVJSOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgfQoKICAgIC8qCiAgICAgKiBjb3B5IGluIHRoZSBwcml2YWN5IEtleS4gIElmIG5vdCBsb2NhbGl6ZWQsIGxvY2FsaXplIGl0IAogICAgICovCiAgICBpZiAodXNlci0+cHJpdktleSA9PSBOVUxMKSB7CiAgICAgICAgaWYgKHNlc3Npb24tPnNlY3VyaXR5UHJpdkxvY2FsS2V5ICE9IE5VTEwKICAgICAgICAgICAgJiYgc2Vzc2lvbi0+c2VjdXJpdHlQcml2TG9jYWxLZXlMZW4gIT0gMCkgewogICAgICAgICAgICAvKiBhbHJlYWR5IGxvY2FsaXplZCBrZXkgcGFzc2VkIGluLiAgdXNlIGl0ICovCiAgICAgICAgICAgIFNOTVBfRlJFRSh1c2VyLT5wcml2S2V5KTsKICAgICAgICAgICAgdXNlci0+cHJpdktleSA9IG5ldHNubXBfbWVtZHVwKHNlc3Npb24tPnNlY3VyaXR5UHJpdkxvY2FsS2V5LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2Vzc2lvbi0+c2VjdXJpdHlQcml2TG9jYWxLZXlMZW4pOwogICAgICAgICAgICBpZiAoIXVzZXItPnByaXZLZXkpIHsKICAgICAgICAgICAgICAgIHVzbV9mcmVlX3VzZXIodXNlcik7CiAgICAgICAgICAgICAgICByZXR1cm4gU05NUEVSUl9HRU5FUlI7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdXNlci0+cHJpdktleUxlbiA9IHNlc3Npb24tPnNlY3VyaXR5UHJpdkxvY2FsS2V5TGVuOwogICAgICAgIH0gZWxzZSBpZiAoc2Vzc2lvbi0+c2VjdXJpdHlQcml2S2V5ICE9IE5VTEwKICAgICAgICAgICAgICAgICAgICYmIHNlc3Npb24tPnNlY3VyaXR5UHJpdktleUxlbiAhPSAwKSB7CiAgICAgICAgICAgIFNOTVBfRlJFRSh1c2VyLT5wcml2S2V5KTsKICAgICAgICAgICAgdXNlci0+cHJpdktleSA9ICh1X2NoYXIgKikgY2FsbG9jKDEsIFVTTV9MRU5HVEhfS1VfSEFTSEJMT0NLKTsKICAgICAgICAgICAgaWYgKHVzZXItPnByaXZLZXkgPT0gTlVMTCkgewogICAgICAgICAgICAgICAgdXNtX2ZyZWVfdXNlcih1c2VyKTsKICAgICAgICAgICAgICAgIHJldHVybiBTTk1QRVJSX0dFTkVSUjsKICAgICAgICAgICAgfQogICAgICAgICAgICB1c2VyLT5wcml2S2V5TGVuID0gVVNNX0xFTkdUSF9LVV9IQVNIQkxPQ0s7CiAgICAgICAgICAgIGlmIChnZW5lcmF0ZV9rdWwodXNlci0+YXV0aFByb3RvY29sLCB1c2VyLT5hdXRoUHJvdG9jb2xMZW4sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2Vzc2lvbi0+c2VjdXJpdHlFbmdpbmVJRCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzZXNzaW9uLT5zZWN1cml0eUVuZ2luZUlETGVuLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNlc3Npb24tPnNlY3VyaXR5UHJpdktleSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzZXNzaW9uLT5zZWN1cml0eVByaXZLZXlMZW4sIHVzZXItPnByaXZLZXksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJnVzZXItPnByaXZLZXlMZW4pICE9IFNOTVBFUlJfU1VDQ0VTUykgewogICAgICAgICAgICAgICAgdXNtX2ZyZWVfdXNlcih1c2VyKTsKICAgICAgICAgICAgICAgIHJldHVybiBTTk1QRVJSX0dFTkVSUjsKICAgICAgICAgICAgfQogICAgICAgIH0gZWxzZSBpZiAoKGNwID0gbmV0c25tcF9kc19nZXRfc3RyaW5nKE5FVFNOTVBfRFNfTElCUkFSWV9JRCwgCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgTkVUU05NUF9EU19MSUJfUFJJVkxPQ0FMSVpFREtFWSkpKSB7CiAgICAgICAgICAgIHNpemVfdCBidWZsZW4gPSBVU01fUFJJVl9LVV9MRU47CiAgICAgICAgICAgIFNOTVBfRlJFRSh1c2VyLT5wcml2S2V5KTsKICAgICAgICAgICAgdXNlci0+cHJpdktleSA9ICh1X2NoYXIgKiltYWxsb2MoYnVmbGVuKTsgLyogbWF4IGxlbmd0aCBuZWVkZWQgKi8KICAgICAgICAgICAgdXNlci0+cHJpdktleUxlbiA9IDA7CiAgICAgICAgICAgIC8qIGl0IHdpbGwgYmUgYSBoZXggc3RyaW5nICovCiAgICAgICAgICAgIGlmICghc25tcF9oZXhfdG9fYmluYXJ5KCZ1c2VyLT5wcml2S2V5LCAmYnVmbGVuLCAmdXNlci0+cHJpdktleUxlbiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgMCwgY3ApKSB7CiAgICAgICAgICAgICAgICB1c21fZnJlZV91c2VyKHVzZXIpOwogICAgICAgICAgICAgICAgcmV0dXJuIFNOTVBFUlJfR0VORVJSOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgfQoKICAgIGlmICh1c2VyX2p1c3RfY3JlYXRlZCkgewogICAgICAgIC8qCiAgICAgICAgICogYWRkIHRoZSB1c2VyIGludG8gdGhlIGRhdGFiYXNlIAogICAgICAgICAqLwogICAgICAgIHVzZXItPnVzZXJTdGF0dXMgPSBSU19BQ1RJVkU7CiAgICAgICAgdXNlci0+dXNlclN0b3JhZ2VUeXBlID0gU1RfUkVBRE9OTFk7CiAgICAgICAgdXNtX2FkZF91c2VyKHVzZXIpOwogICAgfQoKICAgIHJldHVybiBTTk1QRVJSX1NVQ0NFU1M7CgoKfSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAvKiBlbmQgY3JlYXRlX3VzZXJfZnJvbV9zZXNzaW9uKCkgKi8KCi8qCiAqICBEbyBhICJkZWVwIGZyZWUoKSIgb2YgYSBuZXRzbm1wX3Nlc3Npb24uCiAqCiAqICBDQVVUSU9OOiAgU0hPVUxEIE9OTFkgQkUgVVNFRCBGUk9NIHNubXBfc2Vzc19jbG9zZSgpIE9SIFNJTUlMQVIuCiAqICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKGhlbmNlIGl0IGlzIHN0YXRpYykKICovCgpzdGF0aWMgdm9pZApzbm1wX2ZyZWVfc2Vzc2lvbihuZXRzbm1wX3Nlc3Npb24gKiBzKQp7CiAgICBpZiAocykgewogICAgICAgIFNOTVBfRlJFRShzLT5sb2NhbG5hbWUpOwogICAgICAgIFNOTVBfRlJFRShzLT5wZWVybmFtZSk7CiAgICAgICAgU05NUF9GUkVFKHMtPmNvbW11bml0eSk7CiAgICAgICAgU05NUF9GUkVFKHMtPmNvbnRleHRFbmdpbmVJRCk7CiAgICAgICAgU05NUF9GUkVFKHMtPmNvbnRleHROYW1lKTsKICAgICAgICBTTk1QX0ZSRUUocy0+c2VjdXJpdHlFbmdpbmVJRCk7CiAgICAgICAgU05NUF9GUkVFKHMtPnNlY3VyaXR5TmFtZSk7CiAgICAgICAgU05NUF9GUkVFKHMtPnNlY3VyaXR5QXV0aFByb3RvKTsKICAgICAgICBTTk1QX0ZSRUUocy0+c2VjdXJpdHlQcml2UHJvdG8pOwogICAgICAgIFNOTVBfRlJFRShzLT5wYXJhbU5hbWUpOwoKICAgICAgICAvKgogICAgICAgICAqIGNsZWFyIHNlc3Npb24gZnJvbSBhbnkgY2FsbGJhY2tzCiAgICAgICAgICovCiAgICAgICAgbmV0c25tcF9jYWxsYmFja19jbGVhcl9jbGllbnRfYXJnKHMsIDAsIDApOwoKICAgICAgICBmcmVlKChjaGFyICopIHMpOwogICAgfQp9CgovKgogKiBDbG9zZSB0aGUgaW5wdXQgc2Vzc2lvbi4gIEZyZWVzIGFsbCBkYXRhIGFsbG9jYXRlZCBmb3IgdGhlIHNlc3Npb24sCiAqIGRlcXVldWVzIGFueSBwZW5kaW5nIHJlcXVlc3RzLCBhbmQgY2xvc2VzIGFueSBzb2NrZXRzIGFsbG9jYXRlZCBmb3IKICogdGhlIHNlc3Npb24uICBSZXR1cm5zIDAgb24gZXJyb3IsIDEgb3RoZXJ3aXNlLgogKi8KaW50CnNubXBfc2Vzc19jbG9zZSh2b2lkICpzZXNzcCkKewogICAgc3RydWN0IHNlc3Npb25fbGlzdCAqc2xwID0gKHN0cnVjdCBzZXNzaW9uX2xpc3QgKikgc2Vzc3A7CiAgICBuZXRzbm1wX3RyYW5zcG9ydCAqdHJhbnNwb3J0OwogICAgc3RydWN0IHNubXBfaW50ZXJuYWxfc2Vzc2lvbiAqaXNwOwogICAgbmV0c25tcF9zZXNzaW9uICpzZXNwID0gTlVMTDsKICAgIHN0cnVjdCBzbm1wX3NlY21vZF9kZWYgKnNwdHI7CgogICAgaWYgKHNscCA9PSBOVUxMKSB7CiAgICAgICAgcmV0dXJuIDA7CiAgICB9CgogICAgaWYgKHNscC0+c2Vzc2lvbiAhPSBOVUxMICYmCiAgICAgICAgKHNwdHIgPSBmaW5kX3NlY19tb2Qoc2xwLT5zZXNzaW9uLT5zZWN1cml0eU1vZGVsKSkgIT0gTlVMTCAmJgogICAgICAgIHNwdHItPnNlc3Npb25fY2xvc2UgIT0gTlVMTCkgewogICAgICAgICgqc3B0ci0+c2Vzc2lvbl9jbG9zZSkgKHNscC0+c2Vzc2lvbik7CiAgICB9CgogICAgaXNwID0gc2xwLT5pbnRlcm5hbDsKICAgIHNscC0+aW50ZXJuYWwgPSAwOwoKICAgIGlmIChpc3ApIHsKICAgICAgICBuZXRzbm1wX3JlcXVlc3RfbGlzdCAqcnAsICpvcnA7CgogICAgICAgIFNOTVBfRlJFRShpc3AtPnBhY2tldCk7CgogICAgICAgIC8qCiAgICAgICAgICogRnJlZSBlYWNoIGVsZW1lbnQgaW4gdGhlIGlucHV0IHJlcXVlc3QgbGlzdC4gIAogICAgICAgICAqLwogICAgICAgIHJwID0gaXNwLT5yZXF1ZXN0czsKICAgICAgICB3aGlsZSAocnApIHsKICAgICAgICAgICAgb3JwID0gcnA7CiAgICAgICAgICAgIHJwID0gcnAtPm5leHRfcmVxdWVzdDsKICAgICAgICAgICAgaWYgKG9ycC0+Y2FsbGJhY2spIHsKICAgICAgICAgICAgICAgIG9ycC0+Y2FsbGJhY2soTkVUU05NUF9DQUxMQkFDS19PUF9USU1FRF9PVVQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNscC0+c2Vzc2lvbiwgb3JwLT5wZHUtPnJlcWlkLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICBvcnAtPnBkdSwgb3JwLT5jYl9kYXRhKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBzbm1wX2ZyZWVfcGR1KG9ycC0+cGR1KTsKICAgICAgICAgICAgZnJlZSgoY2hhciAqKSBvcnApOwogICAgICAgIH0KCiAgICAgICAgZnJlZSgoY2hhciAqKSBpc3ApOwogICAgfQoKICAgIHRyYW5zcG9ydCA9IHNscC0+dHJhbnNwb3J0OwogICAgc2xwLT50cmFuc3BvcnQgPSAwOwoKICAgIGlmICh0cmFuc3BvcnQpIHsKICAgICAgICB0cmFuc3BvcnQtPmZfY2xvc2UodHJhbnNwb3J0KTsKICAgICAgICBuZXRzbm1wX3RyYW5zcG9ydF9mcmVlKHRyYW5zcG9ydCk7CiAgICB9CgogICAgc2VzcCA9IHNscC0+c2Vzc2lvbjsKICAgIHNscC0+c2Vzc2lvbiA9IDA7CgogICAgLyoKICAgICAqIFRoZSBmb2xsb3dpbmcgaXMgbmVjZXNzYXJ5IHRvIGF2b2lkIG1lbW9yeSBsZWFrYWdlIHdoZW4gY2xvc2luZyBBZ2VudFggCiAgICAgKiBzZXNzaW9ucyB0aGF0IG1heSBoYXZlIG11bHRpcGxlIHN1YnNlc3Npb25zLiAgVGhlc2UgaGFuZyBvZmYgdGhlIG1haW4KICAgICAqIHNlc3Npb24gYXQgLT5zdWJzZXNzaW9uLCBhbmQgY2hhaW4gdGhyb3VnaCAtPm5leHQuICAKICAgICAqLwoKICAgIGlmIChzZXNwICE9IE5VTEwgJiYgc2VzcC0+c3Vic2Vzc2lvbiAhPSBOVUxMKSB7CiAgICAgICAgbmV0c25tcF9zZXNzaW9uICpzdWJzZXNzaW9uID0gc2VzcC0+c3Vic2Vzc2lvbiwgKnRtcHN1YjsKCiAgICAgICAgd2hpbGUgKHN1YnNlc3Npb24gIT0gTlVMTCkgewogICAgICAgICAgICBERUJVR01TR1RMKCgic25tcF9zZXNzX2Nsb3NlIiwKICAgICAgICAgICAgICAgICAgICAgICAgImNsb3Npbmcgc2Vzc2lvbiAlcCwgc3Vic2Vzc2lvbiAlcFxuIiwgc2VzcCwKICAgICAgICAgICAgICAgICAgICAgICAgc3Vic2Vzc2lvbikpOwogICAgICAgICAgICB0bXBzdWIgPSBzdWJzZXNzaW9uLT5uZXh0OwogICAgICAgICAgICBzbm1wX2ZyZWVfc2Vzc2lvbihzdWJzZXNzaW9uKTsKICAgICAgICAgICAgc3Vic2Vzc2lvbiA9IHRtcHN1YjsKICAgICAgICB9CiAgICB9CgogICAgc25tcF9mcmVlX3Nlc3Npb24oc2VzcCk7CiAgICBmcmVlKChjaGFyICopIHNscCk7CiAgICByZXR1cm4gMTsKfQoKaW50CnNubXBfY2xvc2UobmV0c25tcF9zZXNzaW9uICogc2Vzc2lvbikKewogICAgc3RydWN0IHNlc3Npb25fbGlzdCAqc2xwID0gTlVMTCwgKm9zbHAgPSBOVUxMOwoKICAgIHsgICAgICAgICAgICAgICAgICAgICAgICAgICAvKk1UQ1JJVElDQUxfUkVTT1VSQ0UgKi8KICAgICAgICBzbm1wX3Jlc19sb2NrKE1UX0xJQlJBUllfSUQsIE1UX0xJQl9TRVNTSU9OKTsKICAgICAgICBpZiAoU2Vzc2lvbnMgJiYgU2Vzc2lvbnMtPnNlc3Npb24gPT0gc2Vzc2lvbikgeyAvKiBJZiBmaXJzdCBlbnRyeSAqLwogICAgICAgICAgICBzbHAgPSBTZXNzaW9uczsKICAgICAgICAgICAgU2Vzc2lvbnMgPSBzbHAtPm5leHQ7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgZm9yIChzbHAgPSBTZXNzaW9uczsgc2xwOyBzbHAgPSBzbHAtPm5leHQpIHsKICAgICAgICAgICAgICAgIGlmIChzbHAtPnNlc3Npb24gPT0gc2Vzc2lvbikgewogICAgICAgICAgICAgICAgICAgIGlmIChvc2xwKSAgIC8qIGlmIHdlIGZvdW5kIGVudHJ5IHRoYXQgcG9pbnRzIGhlcmUgKi8KICAgICAgICAgICAgICAgICAgICAgICAgb3NscC0+bmV4dCA9IHNscC0+bmV4dDsgLyogbGluayBhcm91bmQgdGhpcyBlbnRyeSAqLwogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgb3NscCA9IHNscDsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBzbm1wX3Jlc191bmxvY2soTVRfTElCUkFSWV9JRCwgTVRfTElCX1NFU1NJT04pOwogICAgfSAgICAgICAgICAgICAgICAgICAgICAgICAgIC8qRU5EIE1UQ1JJVElDQUxfUkVTT1VSQ0UgKi8KICAgIGlmIChzbHAgPT0gTlVMTCkgewogICAgICAgIHJldHVybiAwOwogICAgfQogICAgcmV0dXJuIHNubXBfc2Vzc19jbG9zZSgodm9pZCAqKSBzbHApOwp9CgppbnQKc25tcF9jbG9zZV9zZXNzaW9ucyh2b2lkKQp7CiAgICBzdHJ1Y3Qgc2Vzc2lvbl9saXN0ICpzbHA7CgogICAgc25tcF9yZXNfbG9jayhNVF9MSUJSQVJZX0lELCBNVF9MSUJfU0VTU0lPTik7CiAgICB3aGlsZSAoU2Vzc2lvbnMpIHsKICAgICAgICBzbHAgPSBTZXNzaW9uczsKICAgICAgICBTZXNzaW9ucyA9IFNlc3Npb25zLT5uZXh0OwogICAgICAgIHNubXBfc2Vzc19jbG9zZSgodm9pZCAqKSBzbHApOwogICAgfQogICAgc25tcF9yZXNfdW5sb2NrKE1UX0xJQlJBUllfSUQsIE1UX0xJQl9TRVNTSU9OKTsKICAgIHJldHVybiAxOwp9CgpzdGF0aWMgaW50CnNubXB2M19idWlsZF9wcm9iZV9wZHUobmV0c25tcF9wZHUgKipwZHUpCnsKICAgIHN0cnVjdCB1c21Vc2VyICp1c2VyOwoKICAgIC8qCiAgICAgKiBjcmVhdGUgdGhlIHBkdSAKICAgICAqLwogICAgaWYgKCFwZHUpCiAgICAgICAgcmV0dXJuIC0xOwogICAgKnBkdSA9IHNubXBfcGR1X2NyZWF0ZShTTk1QX01TR19HRVQpOwogICAgaWYgKCEoKnBkdSkpCiAgICAgICAgcmV0dXJuIC0xOwogICAgKCpwZHUpLT52ZXJzaW9uID0gU05NUF9WRVJTSU9OXzM7CiAgICAoKnBkdSktPnNlY3VyaXR5TmFtZSA9IHN0cmR1cCgiIik7CiAgICAoKnBkdSktPnNlY3VyaXR5TmFtZUxlbiA9IHN0cmxlbigoKnBkdSktPnNlY3VyaXR5TmFtZSk7CiAgICAoKnBkdSktPnNlY3VyaXR5TGV2ZWwgPSBTTk1QX1NFQ19MRVZFTF9OT0FVVEg7CiAgICAoKnBkdSktPnNlY3VyaXR5TW9kZWwgPSBTTk1QX1NFQ19NT0RFTF9VU007CgogICAgLyoKICAgICAqIGNyZWF0ZSB0aGUgZW1wdHkgdXNlciAKICAgICAqLwogICAgdXNlciA9IHVzbV9nZXRfdXNlcihOVUxMLCAwLCAoKnBkdSktPnNlY3VyaXR5TmFtZSk7CiAgICBpZiAodXNlciA9PSBOVUxMKSB7CiAgICAgICAgdXNlciA9IChzdHJ1Y3QgdXNtVXNlciAqKSBjYWxsb2MoMSwgc2l6ZW9mKHN0cnVjdCB1c21Vc2VyKSk7CiAgICAgICAgaWYgKHVzZXIgPT0gTlVMTCkgewogICAgICAgICAgICBzbm1wX2ZyZWVfcGR1KCpwZHUpOwogICAgICAgICAgICAqcGR1ID0gKG5ldHNubXBfcGR1ICopIE5VTEw7CiAgICAgICAgICAgIHJldHVybiAtMTsKICAgICAgICB9CiAgICAgICAgdXNlci0+bmFtZSA9IHN0cmR1cCgoKnBkdSktPnNlY3VyaXR5TmFtZSk7CiAgICAgICAgdXNlci0+c2VjTmFtZSA9IHN0cmR1cCgoKnBkdSktPnNlY3VyaXR5TmFtZSk7CiAgICAgICAgdXNlci0+YXV0aFByb3RvY29sTGVuID0gc2l6ZW9mKHVzbU5vQXV0aFByb3RvY29sKSAvIHNpemVvZihvaWQpOwogICAgICAgIHVzZXItPmF1dGhQcm90b2NvbCA9CiAgICAgICAgICAgIHNubXBfZHVwbGljYXRlX29iamlkKHVzbU5vQXV0aFByb3RvY29sLCB1c2VyLT5hdXRoUHJvdG9jb2xMZW4pOwogICAgICAgIHVzZXItPnByaXZQcm90b2NvbExlbiA9IHNpemVvZih1c21Ob1ByaXZQcm90b2NvbCkgLyBzaXplb2Yob2lkKTsKICAgICAgICB1c2VyLT5wcml2UHJvdG9jb2wgPQogICAgICAgICAgICBzbm1wX2R1cGxpY2F0ZV9vYmppZCh1c21Ob1ByaXZQcm90b2NvbCwgdXNlci0+cHJpdlByb3RvY29sTGVuKTsKICAgICAgICB1c21fYWRkX3VzZXIodXNlcik7CiAgICB9CiAgICByZXR1cm4gMDsKfQoKc3RhdGljIHZvaWQKc25tcHYzX2NhbGNfbXNnX2ZsYWdzKGludCBzZWNfbGV2ZWwsIGludCBtc2dfY29tbWFuZCwgdV9jaGFyICogZmxhZ3MpCnsKICAgICpmbGFncyA9IDA7CiAgICBpZiAoc2VjX2xldmVsID09IFNOTVBfU0VDX0xFVkVMX0FVVEhOT1BSSVYpCiAgICAgICAgKmZsYWdzID0gU05NUF9NU0dfRkxBR19BVVRIX0JJVDsKICAgIGVsc2UgaWYgKHNlY19sZXZlbCA9PSBTTk1QX1NFQ19MRVZFTF9BVVRIUFJJVikKICAgICAgICAqZmxhZ3MgPSBTTk1QX01TR19GTEFHX0FVVEhfQklUIHwgU05NUF9NU0dfRkxBR19QUklWX0JJVDsKCiAgICBpZiAoU05NUF9DTURfQ09ORklSTUVEKG1zZ19jb21tYW5kKSkKICAgICAgICAqZmxhZ3MgfD0gU05NUF9NU0dfRkxBR19SUFJUX0JJVDsKCiAgICByZXR1cm47Cn0KCnN0YXRpYyBpbnQKc25tcHYzX3ZlcmlmeV9tc2cobmV0c25tcF9yZXF1ZXN0X2xpc3QgKnJwLCBuZXRzbm1wX3BkdSAqcGR1KQp7CiAgICBuZXRzbm1wX3BkdSAgICAqcnBkdTsKCiAgICBpZiAoIXJwIHx8ICFycC0+cGR1IHx8ICFwZHUpCiAgICAgICAgcmV0dXJuIDA7CiAgICAvKgogICAgICogUmVwb3J0cyBkb24ndCBoYXZlIHRvIG1hdGNoIGFueXRoaW5nIGFjY29yZGluZyB0byB0aGUgc3BlYyAKICAgICAqLwogICAgaWYgKHBkdS0+Y29tbWFuZCA9PSBTTk1QX01TR19SRVBPUlQpCiAgICAgICAgcmV0dXJuIDE7CiAgICBycGR1ID0gcnAtPnBkdTsKICAgIGlmIChycC0+cmVxdWVzdF9pZCAhPSBwZHUtPnJlcWlkIHx8IHJwZHUtPnJlcWlkICE9IHBkdS0+cmVxaWQpCiAgICAgICAgcmV0dXJuIDA7CiAgICBpZiAocnBkdS0+dmVyc2lvbiAhPSBwZHUtPnZlcnNpb24pCiAgICAgICAgcmV0dXJuIDA7CiAgICBpZiAocnBkdS0+c2VjdXJpdHlNb2RlbCAhPSBwZHUtPnNlY3VyaXR5TW9kZWwpCiAgICAgICAgcmV0dXJuIDA7CiAgICBpZiAocnBkdS0+c2VjdXJpdHlMZXZlbCAhPSBwZHUtPnNlY3VyaXR5TGV2ZWwpCiAgICAgICAgcmV0dXJuIDA7CgogICAgaWYgKHJwZHUtPmNvbnRleHRFbmdpbmVJRExlbiAhPSBwZHUtPmNvbnRleHRFbmdpbmVJRExlbiB8fAogICAgICAgIG1lbWNtcChycGR1LT5jb250ZXh0RW5naW5lSUQsIHBkdS0+Y29udGV4dEVuZ2luZUlELAogICAgICAgICAgICAgICBwZHUtPmNvbnRleHRFbmdpbmVJRExlbikpCiAgICAgICAgcmV0dXJuIDA7CiAgICBpZiAocnBkdS0+Y29udGV4dE5hbWVMZW4gIT0gcGR1LT5jb250ZXh0TmFtZUxlbiB8fAogICAgICAgIG1lbWNtcChycGR1LT5jb250ZXh0TmFtZSwgcGR1LT5jb250ZXh0TmFtZSwgcGR1LT5jb250ZXh0TmFtZUxlbikpCiAgICAgICAgcmV0dXJuIDA7CiAgICBpZiAocnBkdS0+c2VjdXJpdHlFbmdpbmVJRExlbiAhPSBwZHUtPnNlY3VyaXR5RW5naW5lSURMZW4gfHwKICAgICAgICBtZW1jbXAocnBkdS0+c2VjdXJpdHlFbmdpbmVJRCwgcGR1LT5zZWN1cml0eUVuZ2luZUlELAogICAgICAgICAgICAgICBwZHUtPnNlY3VyaXR5RW5naW5lSURMZW4pKQogICAgICAgIHJldHVybiAwOwogICAgaWYgKHJwZHUtPnNlY3VyaXR5TmFtZUxlbiAhPSBwZHUtPnNlY3VyaXR5TmFtZUxlbiB8fAogICAgICAgIG1lbWNtcChycGR1LT5zZWN1cml0eU5hbWUsIHBkdS0+c2VjdXJpdHlOYW1lLAogICAgICAgICAgICAgICBwZHUtPnNlY3VyaXR5TmFtZUxlbikpCiAgICAgICAgcmV0dXJuIDA7CiAgICByZXR1cm4gMTsKfQoKCi8qCiAqIFNOTVB2MwogKiAqIFRha2VzIGEgc2Vzc2lvbiBhbmQgYSBwZHUgYW5kIHNlcmlhbGl6ZXMgdGhlIEFTTiBQRFUgaW50byB0aGUgYXJlYQogKiAqIHBvaW50ZWQgdG8gYnkgcGFja2V0LiAgb3V0X2xlbmd0aCBpcyB0aGUgc2l6ZSBvZiB0aGUgZGF0YSBhcmVhIGF2YWlsYWJsZS4KICogKiBSZXR1cm5zIHRoZSBsZW5ndGggb2YgdGhlIGNvbXBsZXRlZCBwYWNrZXQgaW4gb3V0X2xlbmd0aC4gIElmIGFueSBlcnJvcnMKICogKiBvY2N1ciwgLTEgaXMgcmV0dXJuZWQuICBJZiBhbGwgZ29lcyB3ZWxsLCAwIGlzIHJldHVybmVkLgogKi8Kc3RhdGljIGludApzbm1wdjNfYnVpbGQodV9jaGFyICoqIHBrdCwgc2l6ZV90ICogcGt0X2xlbiwgc2l6ZV90ICogb2Zmc2V0LAogICAgICAgICAgICAgbmV0c25tcF9zZXNzaW9uICogc2Vzc2lvbiwgbmV0c25tcF9wZHUgKnBkdSkKewogICAgaW50ICAgICAgICAgICAgIHJldDsKCiAgICBzZXNzaW9uLT5zX3NubXBfZXJybm8gPSAwOwogICAgc2Vzc2lvbi0+c19lcnJubyA9IDA7CgogICAgLyoKICAgICAqIGRvIHZhbGlkYXRpb24gZm9yIFBEVSB0eXBlcyAKICAgICAqLwogICAgc3dpdGNoIChwZHUtPmNvbW1hbmQpIHsKICAgIGNhc2UgU05NUF9NU0dfUkVTUE9OU0U6CiAgICBjYXNlIFNOTVBfTVNHX1RSQVAyOgogICAgY2FzZSBTTk1QX01TR19SRVBPUlQ6CiAgICAgICAgbmV0c25tcF9hc3NlcnQoMCA9PSAocGR1LT5mbGFncyAmIFVDRF9NU0dfRkxBR19FWFBFQ1RfUkVTUE9OU0UpKTsKICAgICAgICAvKgogICAgICAgICAqIEZhbGx0aHJvdWdoIAogICAgICAgICAqLwogICAgY2FzZSBTTk1QX01TR19HRVQ6CiAgICBjYXNlIFNOTVBfTVNHX0dFVE5FWFQ6CiAgICBjYXNlIFNOTVBfTVNHX1NFVDoKICAgIGNhc2UgU05NUF9NU0dfSU5GT1JNOgogICAgICAgIGlmIChwZHUtPmVycnN0YXQgPT0gU05NUF9ERUZBVUxUX0VSUlNUQVQpCiAgICAgICAgICAgIHBkdS0+ZXJyc3RhdCA9IDA7CiAgICAgICAgaWYgKHBkdS0+ZXJyaW5kZXggPT0gU05NUF9ERUZBVUxUX0VSUklOREVYKQogICAgICAgICAgICBwZHUtPmVycmluZGV4ID0gMDsKICAgICAgICBicmVhazsKCiAgICBjYXNlIFNOTVBfTVNHX0dFVEJVTEs6CiAgICAgICAgaWYgKHBkdS0+bWF4X3JlcGV0aXRpb25zIDwgMCkgewogICAgICAgICAgICBzZXNzaW9uLT5zX3NubXBfZXJybm8gPSBTTk1QRVJSX0JBRF9SRVBFVElUSU9OUzsKICAgICAgICAgICAgcmV0dXJuIC0xOwogICAgICAgIH0KICAgICAgICBpZiAocGR1LT5ub25fcmVwZWF0ZXJzIDwgMCkgewogICAgICAgICAgICBzZXNzaW9uLT5zX3NubXBfZXJybm8gPSBTTk1QRVJSX0JBRF9SRVBFQVRFUlM7CiAgICAgICAgICAgIHJldHVybiAtMTsKICAgICAgICB9CiAgICAgICAgYnJlYWs7CgogICAgY2FzZSBTTk1QX01TR19UUkFQOgogICAgICAgIHNlc3Npb24tPnNfc25tcF9lcnJubyA9IFNOTVBFUlJfVjFfSU5fVjI7CiAgICAgICAgcmV0dXJuIC0xOwoKICAgIGRlZmF1bHQ6CiAgICAgICAgc2Vzc2lvbi0+c19zbm1wX2Vycm5vID0gU05NUEVSUl9VTktOT1dOX1BEVTsKICAgICAgICByZXR1cm4gLTE7CiAgICB9CgogICAgLyogRG8gd2UgbmVlZCB0byBzZXQgdGhlIHNlc3Npb24gc2VjdXJpdHkgZW5naW5laWQ/ICovCiAgICBpZiAocGR1LT5zZWN1cml0eUVuZ2luZUlETGVuID09IDApIHsKICAgICAgICBpZiAoc2Vzc2lvbi0+c2VjdXJpdHlFbmdpbmVJRExlbikgewogICAgICAgICAgICBzbm1wdjNfY2xvbmVfZW5naW5lSUQoJnBkdS0+c2VjdXJpdHlFbmdpbmVJRCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICZwZHUtPnNlY3VyaXR5RW5naW5lSURMZW4sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzZXNzaW9uLT5zZWN1cml0eUVuZ2luZUlELAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2Vzc2lvbi0+c2VjdXJpdHlFbmdpbmVJRExlbik7CiAgICAgICAgfQogICAgfQogICAgCiAgICAvKiBEbyB3ZSBuZWVkIHRvIHNldCB0aGUgc2Vzc2lvbiBjb250ZXh0IGVuZ2luZWlkPyAqLwogICAgaWYgKHBkdS0+Y29udGV4dEVuZ2luZUlETGVuID09IDApIHsKICAgICAgICBpZiAoc2Vzc2lvbi0+Y29udGV4dEVuZ2luZUlETGVuKSB7CiAgICAgICAgICAgIHNubXB2M19jbG9uZV9lbmdpbmVJRCgmcGR1LT5jb250ZXh0RW5naW5lSUQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmcGR1LT5jb250ZXh0RW5naW5lSURMZW4sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzZXNzaW9uLT5jb250ZXh0RW5naW5lSUQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzZXNzaW9uLT5jb250ZXh0RW5naW5lSURMZW4pOwogICAgICAgIH0gZWxzZSBpZiAocGR1LT5zZWN1cml0eUVuZ2luZUlETGVuKSB7CiAgICAgICAgICAgIHNubXB2M19jbG9uZV9lbmdpbmVJRCgmcGR1LT5jb250ZXh0RW5naW5lSUQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmcGR1LT5jb250ZXh0RW5naW5lSURMZW4sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBwZHUtPnNlY3VyaXR5RW5naW5lSUQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBwZHUtPnNlY3VyaXR5RW5naW5lSURMZW4pOwogICAgICAgIH0KICAgIH0KCiAgICBpZiAocGR1LT5jb250ZXh0TmFtZSA9PSBOVUxMKSB7CiAgICAgICAgaWYgKCFzZXNzaW9uLT5jb250ZXh0TmFtZSkgewogICAgICAgICAgICBzZXNzaW9uLT5zX3NubXBfZXJybm8gPSBTTk1QRVJSX0JBRF9DT05URVhUOwogICAgICAgICAgICByZXR1cm4gLTE7CiAgICAgICAgfQogICAgICAgIHBkdS0+Y29udGV4dE5hbWUgPSBzdHJkdXAoc2Vzc2lvbi0+Y29udGV4dE5hbWUpOwogICAgICAgIGlmIChwZHUtPmNvbnRleHROYW1lID09IE5VTEwpIHsKICAgICAgICAgICAgc2Vzc2lvbi0+c19zbm1wX2Vycm5vID0gU05NUEVSUl9HRU5FUlI7CiAgICAgICAgICAgIHJldHVybiAtMTsKICAgICAgICB9CiAgICAgICAgcGR1LT5jb250ZXh0TmFtZUxlbiA9IHNlc3Npb24tPmNvbnRleHROYW1lTGVuOwogICAgfQogICAgaWYgKHBkdS0+c2VjdXJpdHlNb2RlbCA9PSBTTk1QX0RFRkFVTFRfU0VDTU9ERUwpIHsKICAgICAgICBwZHUtPnNlY3VyaXR5TW9kZWwgPSBzZXNzaW9uLT5zZWN1cml0eU1vZGVsOwogICAgICAgIGlmIChwZHUtPnNlY3VyaXR5TW9kZWwgPT0gU05NUF9ERUZBVUxUX1NFQ01PREVMKSB7CiAgICAgICAgICAgIHBkdS0+c2VjdXJpdHlNb2RlbCA9IFNOTVBfU0VDX01PREVMX1VTTTsKICAgICAgICB9CiAgICB9CiAgICBpZiAocGR1LT5zZWN1cml0eU5hbWVMZW4gPT0gMCAmJiBwZHUtPnNlY3VyaXR5TmFtZSA9PSAwKSB7CiAgICAgICAgaWYgKHNlc3Npb24tPnNlY3VyaXR5TmFtZUxlbiA9PSAwKSB7CiAgICAgICAgICAgIHNlc3Npb24tPnNfc25tcF9lcnJubyA9IFNOTVBFUlJfQkFEX1NFQ19OQU1FOwogICAgICAgICAgICByZXR1cm4gLTE7CiAgICAgICAgfQogICAgICAgIHBkdS0+c2VjdXJpdHlOYW1lID0gc3RyZHVwKHNlc3Npb24tPnNlY3VyaXR5TmFtZSk7CiAgICAgICAgaWYgKHBkdS0+c2VjdXJpdHlOYW1lID09IE5VTEwpIHsKICAgICAgICAgICAgc2Vzc2lvbi0+c19zbm1wX2Vycm5vID0gU05NUEVSUl9HRU5FUlI7CiAgICAgICAgICAgIHJldHVybiAtMTsKICAgICAgICB9CiAgICAgICAgcGR1LT5zZWN1cml0eU5hbWVMZW4gPSBzZXNzaW9uLT5zZWN1cml0eU5hbWVMZW47CiAgICB9CiAgICBpZiAocGR1LT5zZWN1cml0eUxldmVsID09IDApIHsKICAgICAgICBpZiAoc2Vzc2lvbi0+c2VjdXJpdHlMZXZlbCA9PSAwKSB7CiAgICAgICAgICAgIHNlc3Npb24tPnNfc25tcF9lcnJubyA9IFNOTVBFUlJfQkFEX1NFQ19MRVZFTDsKICAgICAgICAgICAgcmV0dXJuIC0xOwogICAgICAgIH0KICAgICAgICBwZHUtPnNlY3VyaXR5TGV2ZWwgPSBzZXNzaW9uLT5zZWN1cml0eUxldmVsOwogICAgfQogICAgREVCVUdNU0dUTCgoInNubXBfYnVpbGQiLAogICAgICAgICAgICAgICAgIkJ1aWxkaW5nIFNOTVB2MyBtZXNzYWdlIChzZWNOYW1lOlwiJXNcIiwgc2VjTGV2ZWw6JXMpLi4uXG4iLAogICAgICAgICAgICAgICAgKChzZXNzaW9uLT5zZWN1cml0eU5hbWUpID8gKGNoYXIgKikgc2Vzc2lvbi0+c2VjdXJpdHlOYW1lIDoKICAgICAgICAgICAgICAgICAoKHBkdS0+c2VjdXJpdHlOYW1lKSA/IChjaGFyICopIHBkdS0+c2VjdXJpdHlOYW1lIDoKICAgICAgICAgICAgICAgICAgIkVSUk9SOiB1bmRlZmluZWQiKSksIHNlY0xldmVsTmFtZVtwZHUtPnNlY3VyaXR5TGV2ZWxdKSk7CgogICAgREVCVUdEVU1QU0VDVElPTigic2VuZCIsICJTTk1QdjMgTWVzc2FnZSIpOwojaWZkZWYgTkVUU05NUF9VU0VfUkVWRVJTRV9BU05FTkNPRElORwogICAgaWYgKG5ldHNubXBfZHNfZ2V0X2Jvb2xlYW4oTkVUU05NUF9EU19MSUJSQVJZX0lELCBORVRTTk1QX0RTX0xJQl9SRVZFUlNFX0VOQ09ERSkpIHsKICAgICAgICByZXQgPSBzbm1wdjNfcGFja2V0X3JlYWxsb2NfcmJ1aWxkKHBrdCwgcGt0X2xlbiwgb2Zmc2V0LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2Vzc2lvbiwgcGR1LCBOVUxMLCAwKTsKICAgIH0gZWxzZSB7CiNlbmRpZgogICAgICAgIHJldCA9IHNubXB2M19wYWNrZXRfYnVpbGQoc2Vzc2lvbiwgcGR1LCAqcGt0LCBwa3RfbGVuLCBOVUxMLCAwKTsKI2lmZGVmIE5FVFNOTVBfVVNFX1JFVkVSU0VfQVNORU5DT0RJTkcKICAgIH0KI2VuZGlmCiAgICBERUJVR0lOREVOVExFU1MoKTsKICAgIGlmICgtMSAhPSByZXQpIHsKICAgICAgICBzZXNzaW9uLT5zX3NubXBfZXJybm8gPSByZXQ7CiAgICB9CgogICAgcmV0dXJuIHJldDsKCn0gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgLyogZW5kIHNubXB2M19idWlsZCgpICovCgoKCgpzdGF0aWMgdV9jaGFyICAqCnNubXB2M19oZWFkZXJfYnVpbGQobmV0c25tcF9zZXNzaW9uICogc2Vzc2lvbiwgbmV0c25tcF9wZHUgKnBkdSwKICAgICAgICAgICAgICAgICAgICB1X2NoYXIgKiBwYWNrZXQsIHNpemVfdCAqIG91dF9sZW5ndGgsCiAgICAgICAgICAgICAgICAgICAgc2l6ZV90IGxlbmd0aCwgdV9jaGFyICoqIG1zZ19oZHJfZSkKewogICAgdV9jaGFyICAgICAgICAgKmdsb2JhbF9oZHIsICpnbG9iYWxfaGRyX2U7CiAgICB1X2NoYXIgICAgICAgICAqY3A7CiAgICB1X2NoYXIgICAgICAgICAgbXNnX2ZsYWdzOwogICAgbG9uZyAgICAgICAgICAgIG1heF9zaXplOwogICAgbG9uZyAgICAgICAgICAgIHNlY19tb2RlbDsKICAgIHVfY2hhciAgICAgICAgICpwYiwgKnBiMGU7CgogICAgLyoKICAgICAqIFNhdmUgY3VycmVudCBsb2NhdGlvbiBhbmQgYnVpbGQgU0VRVUVOQ0UgdGFnIGFuZCBsZW5ndGggcGxhY2Vob2xkZXIKICAgICAqICogZm9yIFNOTVAgbWVzc2FnZSBzZXF1ZW5jZSAoYWN0dWFsIGxlbmd0aCBpbnNlcnRlZCBsYXRlcikKICAgICAqLwogICAgY3AgPSBhc25fYnVpbGRfc2VxdWVuY2UocGFja2V0LCBvdXRfbGVuZ3RoLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgKHVfY2hhcikgKEFTTl9TRVFVRU5DRSB8IEFTTl9DT05TVFJVQ1RPUiksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBsZW5ndGgpOwogICAgaWYgKGNwID09IE5VTEwpCiAgICAgICAgcmV0dXJuIE5VTEw7CiAgICBpZiAobXNnX2hkcl9lICE9IE5VTEwpCiAgICAgICAgKm1zZ19oZHJfZSA9IGNwOwogICAgcGIwZSA9IGNwOwoKCiAgICAvKgogICAgICogc3RvcmUgdGhlIHZlcnNpb24gZmllbGQgLSBtc2dWZXJzaW9uCiAgICAgKi8KICAgIERFQlVHRFVNUEhFQURFUigic2VuZCIsICJTTk1QIFZlcnNpb24gTnVtYmVyIik7CiAgICBjcCA9IGFzbl9idWlsZF9pbnQoY3AsIG91dF9sZW5ndGgsCiAgICAgICAgICAgICAgICAgICAgICAgKHVfY2hhcikgKEFTTl9VTklWRVJTQUwgfCBBU05fUFJJTUlUSVZFIHwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgQVNOX0lOVEVHRVIpLCAobG9uZyAqKSAmcGR1LT52ZXJzaW9uLAogICAgICAgICAgICAgICAgICAgICAgIHNpemVvZihwZHUtPnZlcnNpb24pKTsKICAgIERFQlVHSU5ERU5UTEVTUygpOwogICAgaWYgKGNwID09IE5VTEwpCiAgICAgICAgcmV0dXJuIE5VTEw7CgogICAgZ2xvYmFsX2hkciA9IGNwOwogICAgLyoKICAgICAqIG1zZ0dsb2JhbERhdGEgSGVhZGVyRGF0YSAKICAgICAqLwogICAgREVCVUdEVU1QU0VDVElPTigic2VuZCIsICJtc2dHbG9iYWxEYXRhIik7CiAgICBjcCA9IGFzbl9idWlsZF9zZXF1ZW5jZShjcCwgb3V0X2xlbmd0aCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICh1X2NoYXIpIChBU05fU0VRVUVOQ0UgfCBBU05fQ09OU1RSVUNUT1IpLCAwKTsKICAgIGlmIChjcCA9PSBOVUxMKQogICAgICAgIHJldHVybiBOVUxMOwogICAgZ2xvYmFsX2hkcl9lID0gY3A7CgoKICAgIC8qCiAgICAgKiBtc2dJRCAKICAgICAqLwogICAgREVCVUdEVU1QSEVBREVSKCJzZW5kIiwgIm1zZ0lEIik7CiAgICBjcCA9IGFzbl9idWlsZF9pbnQoY3AsIG91dF9sZW5ndGgsCiAgICAgICAgICAgICAgICAgICAgICAgKHVfY2hhcikgKEFTTl9VTklWRVJTQUwgfCBBU05fUFJJTUlUSVZFIHwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgQVNOX0lOVEVHRVIpLCAmcGR1LT5tc2dpZCwKICAgICAgICAgICAgICAgICAgICAgICBzaXplb2YocGR1LT5tc2dpZCkpOwogICAgREVCVUdJTkRFTlRMRVNTKCk7CiAgICBpZiAoY3AgPT0gTlVMTCkKICAgICAgICByZXR1cm4gTlVMTDsKCiAgICAvKgogICAgICogbXNnTWF4U2l6ZSAKICAgICAqLwogICAgbWF4X3NpemUgPSBzZXNzaW9uLT5yY3ZNc2dNYXhTaXplOwogICAgREVCVUdEVU1QSEVBREVSKCJzZW5kIiwgIm1zZ01heFNpemUiKTsKICAgIGNwID0gYXNuX2J1aWxkX2ludChjcCwgb3V0X2xlbmd0aCwKICAgICAgICAgICAgICAgICAgICAgICAodV9jaGFyKSAoQVNOX1VOSVZFUlNBTCB8IEFTTl9QUklNSVRJVkUgfAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBBU05fSU5URUdFUiksICZtYXhfc2l6ZSwKICAgICAgICAgICAgICAgICAgICAgICBzaXplb2YobWF4X3NpemUpKTsKICAgIERFQlVHSU5ERU5UTEVTUygpOwogICAgaWYgKGNwID09IE5VTEwpCiAgICAgICAgcmV0dXJuIE5VTEw7CgogICAgLyoKICAgICAqIG1zZ0ZsYWdzIAogICAgICovCiAgICBzbm1wdjNfY2FsY19tc2dfZmxhZ3MocGR1LT5zZWN1cml0eUxldmVsLCBwZHUtPmNvbW1hbmQsICZtc2dfZmxhZ3MpOwogICAgREVCVUdEVU1QSEVBREVSKCJzZW5kIiwgIm1zZ0ZsYWdzIik7CiAgICBjcCA9IGFzbl9idWlsZF9zdHJpbmcoY3AsIG91dF9sZW5ndGgsCiAgICAgICAgICAgICAgICAgICAgICAgICAgKHVfY2hhcikgKEFTTl9VTklWRVJTQUwgfCBBU05fUFJJTUlUSVZFIHwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgQVNOX09DVEVUX1NUUiksICZtc2dfZmxhZ3MsCiAgICAgICAgICAgICAgICAgICAgICAgICAgc2l6ZW9mKG1zZ19mbGFncykpOwogICAgREVCVUdJTkRFTlRMRVNTKCk7CiAgICBpZiAoY3AgPT0gTlVMTCkKICAgICAgICByZXR1cm4gTlVMTDsKCiAgICAvKgogICAgICogbXNnU2VjdXJpdHlNb2RlbCAKICAgICAqLwogICAgc2VjX21vZGVsID0gcGR1LT5zZWN1cml0eU1vZGVsOwogICAgREVCVUdEVU1QSEVBREVSKCJzZW5kIiwgIm1zZ1NlY3VyaXR5TW9kZWwiKTsKICAgIGNwID0gYXNuX2J1aWxkX2ludChjcCwgb3V0X2xlbmd0aCwKICAgICAgICAgICAgICAgICAgICAgICAodV9jaGFyKSAoQVNOX1VOSVZFUlNBTCB8IEFTTl9QUklNSVRJVkUgfAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBBU05fSU5URUdFUiksICZzZWNfbW9kZWwsCiAgICAgICAgICAgICAgICAgICAgICAgc2l6ZW9mKHNlY19tb2RlbCkpOwogICAgREVCVUdJTkRFTlRBREQoLTQpOyAgICAgICAgIC8qIHJldHVybiBmcm9tIGdsb2JhbCBkYXRhIGluZGVudCAqLwogICAgaWYgKGNwID09IE5VTEwpCiAgICAgICAgcmV0dXJuIE5VTEw7CgoKICAgIC8qCiAgICAgKiBpbnNlcnQgYWN0dWFsIGxlbmd0aCBvZiBnbG9iYWxEYXRhCiAgICAgKi8KICAgIHBiID0gYXNuX2J1aWxkX3NlcXVlbmNlKGdsb2JhbF9oZHIsIG91dF9sZW5ndGgsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAodV9jaGFyKSAoQVNOX1NFUVVFTkNFIHwgQVNOX0NPTlNUUlVDVE9SKSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNwIC0gZ2xvYmFsX2hkcl9lKTsKICAgIGlmIChwYiA9PSBOVUxMKQogICAgICAgIHJldHVybiBOVUxMOwoKCiAgICAvKgogICAgICogaW5zZXJ0IHRoZSBhY3R1YWwgbGVuZ3RoIG9mIHRoZSBlbnRpcmUgcGFja2V0CiAgICAgKi8KICAgIHBiID0gYXNuX2J1aWxkX3NlcXVlbmNlKHBhY2tldCwgb3V0X2xlbmd0aCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICh1X2NoYXIpIChBU05fU0VRVUVOQ0UgfCBBU05fQ09OU1RSVUNUT1IpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgbGVuZ3RoICsgKGNwIC0gcGIwZSkpOwogICAgaWYgKHBiID09IE5VTEwpCiAgICAgICAgcmV0dXJuIE5VTEw7CgogICAgcmV0dXJuIGNwOwoKfSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAvKiBlbmQgc25tcHYzX2hlYWRlcl9idWlsZCgpICovCgojaWZkZWYgTkVUU05NUF9VU0VfUkVWRVJTRV9BU05FTkNPRElORwoKaW50CnNubXB2M19oZWFkZXJfcmVhbGxvY19yYnVpbGQodV9jaGFyICoqIHBrdCwgc2l6ZV90ICogcGt0X2xlbiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzaXplX3QgKiBvZmZzZXQsIG5ldHNubXBfc2Vzc2lvbiAqIHNlc3Npb24sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgbmV0c25tcF9wZHUgKnBkdSkKewogICAgc2l6ZV90ICAgICAgICAgIHN0YXJ0X29mZnNldCA9ICpvZmZzZXQ7CiAgICB1X2NoYXIgICAgICAgICAgbXNnX2ZsYWdzOwogICAgbG9uZyAgICAgICAgICAgIG1heF9zaXplLCBzZWNfbW9kZWw7CiAgICBpbnQgICAgICAgICAgICAgcmMgPSAwOwoKICAgIC8qCiAgICAgKiBtc2dTZWN1cml0eU1vZGVsLiAgCiAgICAgKi8KICAgIHNlY19tb2RlbCA9IHBkdS0+c2VjdXJpdHlNb2RlbDsKICAgIERFQlVHRFVNUEhFQURFUigic2VuZCIsICJtc2dTZWN1cml0eU1vZGVsIik7CiAgICByYyA9IGFzbl9yZWFsbG9jX3JidWlsZF9pbnQocGt0LCBwa3RfbGVuLCBvZmZzZXQsIDEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKHVfY2hhcikgKEFTTl9VTklWRVJTQUwgfCBBU05fUFJJTUlUSVZFIHwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgQVNOX0lOVEVHRVIpLCAmc2VjX21vZGVsLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNpemVvZihzZWNfbW9kZWwpKTsKICAgIERFQlVHSU5ERU5UTEVTUygpOwogICAgaWYgKHJjID09IDApIHsKICAgICAgICByZXR1cm4gMDsKICAgIH0KCiAgICAvKgogICAgICogbXNnRmxhZ3MuICAKICAgICAqLwogICAgc25tcHYzX2NhbGNfbXNnX2ZsYWdzKHBkdS0+c2VjdXJpdHlMZXZlbCwgcGR1LT5jb21tYW5kLCAmbXNnX2ZsYWdzKTsKICAgIERFQlVHRFVNUEhFQURFUigic2VuZCIsICJtc2dGbGFncyIpOwogICAgcmMgPSBhc25fcmVhbGxvY19yYnVpbGRfc3RyaW5nKHBrdCwgcGt0X2xlbiwgb2Zmc2V0LCAxLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICh1X2NoYXIpIChBU05fVU5JVkVSU0FMIHwgQVNOX1BSSU1JVElWRQogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB8IEFTTl9PQ1RFVF9TVFIpLCAmbXNnX2ZsYWdzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNpemVvZihtc2dfZmxhZ3MpKTsKICAgIERFQlVHSU5ERU5UTEVTUygpOwogICAgaWYgKHJjID09IDApIHsKICAgICAgICByZXR1cm4gMDsKICAgIH0KCiAgICAvKgogICAgICogbXNnTWF4U2l6ZS4gIAogICAgICovCiAgICBtYXhfc2l6ZSA9IHNlc3Npb24tPnJjdk1zZ01heFNpemU7CiAgICBERUJVR0RVTVBIRUFERVIoInNlbmQiLCAibXNnTWF4U2l6ZSIpOwogICAgcmMgPSBhc25fcmVhbGxvY19yYnVpbGRfaW50KHBrdCwgcGt0X2xlbiwgb2Zmc2V0LCAxLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICh1X2NoYXIpIChBU05fVU5JVkVSU0FMIHwgQVNOX1BSSU1JVElWRSB8CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEFTTl9JTlRFR0VSKSwgJm1heF9zaXplLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNpemVvZihtYXhfc2l6ZSkpOwogICAgREVCVUdJTkRFTlRMRVNTKCk7CiAgICBpZiAocmMgPT0gMCkgewogICAgICAgIHJldHVybiAwOwogICAgfQoKICAgIC8qCiAgICAgKiBtc2dJRC4gIAogICAgICovCiAgICBERUJVR0RVTVBIRUFERVIoInNlbmQiLCAibXNnSUQiKTsKICAgIHJjID0gYXNuX3JlYWxsb2NfcmJ1aWxkX2ludChwa3QsIHBrdF9sZW4sIG9mZnNldCwgMSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAodV9jaGFyKSAoQVNOX1VOSVZFUlNBTCB8IEFTTl9QUklNSVRJVkUgfAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBBU05fSU5URUdFUiksICZwZHUtPm1zZ2lkLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNpemVvZihwZHUtPm1zZ2lkKSk7CiAgICBERUJVR0lOREVOVExFU1MoKTsKICAgIGlmIChyYyA9PSAwKSB7CiAgICAgICAgcmV0dXJuIDA7CiAgICB9CgogICAgLyoKICAgICAqIEdsb2JhbCBkYXRhIHNlcXVlbmNlLiAgCiAgICAgKi8KICAgIHJjID0gYXNuX3JlYWxsb2NfcmJ1aWxkX3NlcXVlbmNlKHBrdCwgcGt0X2xlbiwgb2Zmc2V0LCAxLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKHVfY2hhcikgKEFTTl9TRVFVRU5DRSB8CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgQVNOX0NPTlNUUlVDVE9SKSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICpvZmZzZXQgLSBzdGFydF9vZmZzZXQpOwogICAgaWYgKHJjID09IDApIHsKICAgICAgICByZXR1cm4gMDsKICAgIH0KCiAgICAvKgogICAgICogU3RvcmUgdGhlIHZlcnNpb24gZmllbGQgLSBtc2dWZXJzaW9uLiAgCiAgICAgKi8KICAgIERFQlVHRFVNUEhFQURFUigic2VuZCIsICJTTk1QIFZlcnNpb24gTnVtYmVyIik7CiAgICByYyA9IGFzbl9yZWFsbG9jX3JidWlsZF9pbnQocGt0LCBwa3RfbGVuLCBvZmZzZXQsIDEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKHVfY2hhcikgKEFTTl9VTklWRVJTQUwgfCBBU05fUFJJTUlUSVZFIHwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgQVNOX0lOVEVHRVIpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIChsb25nICopICZwZHUtPnZlcnNpb24sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2l6ZW9mKHBkdS0+dmVyc2lvbikpOwogICAgREVCVUdJTkRFTlRMRVNTKCk7CiAgICByZXR1cm4gcmM7Cn0gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgLyogZW5kIHNubXB2M19oZWFkZXJfcmVhbGxvY19yYnVpbGQoKSAqLwojZW5kaWYgICAgICAgICAgICAgICAgICAgICAgICAgIC8qIE5FVFNOTVBfVVNFX1JFVkVSU0VfQVNORU5DT0RJTkcgKi8KCnN0YXRpYyB1X2NoYXIgICoKc25tcHYzX3Njb3BlZFBEVV9oZWFkZXJfYnVpbGQobmV0c25tcF9wZHUgKnBkdSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdV9jaGFyICogcGFja2V0LCBzaXplX3QgKiBvdXRfbGVuZ3RoLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICB1X2NoYXIgKiogc3BkdV9lKQp7CiAgICB1X2NoYXIgICAgICAgICAqc2NvcGVkUGR1LCAqcGI7CgogICAgcGIgPSBzY29wZWRQZHUgPSBwYWNrZXQ7CiAgICBwYiA9IGFzbl9idWlsZF9zZXF1ZW5jZShwYiwgb3V0X2xlbmd0aCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICh1X2NoYXIpIChBU05fU0VRVUVOQ0UgfCBBU05fQ09OU1RSVUNUT1IpLCAwKTsKICAgIGlmIChwYiA9PSBOVUxMKQogICAgICAgIHJldHVybiBOVUxMOwogICAgaWYgKHNwZHVfZSkKICAgICAgICAqc3BkdV9lID0gcGI7CgogICAgREVCVUdEVU1QSEVBREVSKCJzZW5kIiwgImNvbnRleHRFbmdpbmVJRCIpOwogICAgcGIgPSBhc25fYnVpbGRfc3RyaW5nKHBiLCBvdXRfbGVuZ3RoLAogICAgICAgICAgICAgICAgICAgICAgICAgIChBU05fVU5JVkVSU0FMIHwgQVNOX1BSSU1JVElWRSB8IEFTTl9PQ1RFVF9TVFIpLAogICAgICAgICAgICAgICAgICAgICAgICAgIHBkdS0+Y29udGV4dEVuZ2luZUlELCBwZHUtPmNvbnRleHRFbmdpbmVJRExlbik7CiAgICBERUJVR0lOREVOVExFU1MoKTsKICAgIGlmIChwYiA9PSBOVUxMKQogICAgICAgIHJldHVybiBOVUxMOwoKICAgIERFQlVHRFVNUEhFQURFUigic2VuZCIsICJjb250ZXh0TmFtZSIpOwogICAgcGIgPSBhc25fYnVpbGRfc3RyaW5nKHBiLCBvdXRfbGVuZ3RoLAogICAgICAgICAgICAgICAgICAgICAgICAgIChBU05fVU5JVkVSU0FMIHwgQVNOX1BSSU1JVElWRSB8IEFTTl9PQ1RFVF9TVFIpLAogICAgICAgICAgICAgICAgICAgICAgICAgICh1X2NoYXIgKikgcGR1LT5jb250ZXh0TmFtZSwKICAgICAgICAgICAgICAgICAgICAgICAgICBwZHUtPmNvbnRleHROYW1lTGVuKTsKICAgIERFQlVHSU5ERU5UTEVTUygpOwogICAgaWYgKHBiID09IE5VTEwpCiAgICAgICAgcmV0dXJuIE5VTEw7CgogICAgcmV0dXJuIHBiOwoKfSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAvKiBlbmQgc25tcHYzX3Njb3BlZFBEVV9oZWFkZXJfYnVpbGQoKSAqLwoKCiNpZmRlZiBORVRTTk1QX1VTRV9SRVZFUlNFX0FTTkVOQ09ESU5HCmludApzbm1wdjNfc2NvcGVkUERVX2hlYWRlcl9yZWFsbG9jX3JidWlsZCh1X2NoYXIgKiogcGt0LCBzaXplX3QgKiBwa3RfbGVuLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzaXplX3QgKiBvZmZzZXQsIG5ldHNubXBfcGR1ICpwZHUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNpemVfdCBib2R5X2xlbikKewogICAgc2l6ZV90ICAgICAgICAgIHN0YXJ0X29mZnNldCA9ICpvZmZzZXQ7CiAgICBpbnQgICAgICAgICAgICAgcmMgPSAwOwoKICAgIC8qCiAgICAgKiBjb250ZXh0TmFtZS4gIAogICAgICovCiAgICBERUJVR0RVTVBIRUFERVIoInNlbmQiLCAiY29udGV4dE5hbWUiKTsKICAgIHJjID0gYXNuX3JlYWxsb2NfcmJ1aWxkX3N0cmluZyhwa3QsIHBrdF9sZW4sIG9mZnNldCwgMSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAodV9jaGFyKSAoQVNOX1VOSVZFUlNBTCB8IEFTTl9QUklNSVRJVkUKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgfCBBU05fT0NURVRfU1RSKSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAodV9jaGFyICopIHBkdS0+Y29udGV4dE5hbWUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcGR1LT5jb250ZXh0TmFtZUxlbik7CiAgICBERUJVR0lOREVOVExFU1MoKTsKICAgIGlmIChyYyA9PSAwKSB7CiAgICAgICAgcmV0dXJuIDA7CiAgICB9CgogICAgLyoKICAgICAqIGNvbnRleHRFbmdpbmVJRC4gIAogICAgICovCiAgICBERUJVR0RVTVBIRUFERVIoInNlbmQiLCAiY29udGV4dEVuZ2luZUlEIik7CiAgICByYyA9IGFzbl9yZWFsbG9jX3JidWlsZF9zdHJpbmcocGt0LCBwa3RfbGVuLCBvZmZzZXQsIDEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKHVfY2hhcikgKEFTTl9VTklWRVJTQUwgfCBBU05fUFJJTUlUSVZFCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHwgQVNOX09DVEVUX1NUUiksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcGR1LT5jb250ZXh0RW5naW5lSUQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcGR1LT5jb250ZXh0RW5naW5lSURMZW4pOwogICAgREVCVUdJTkRFTlRMRVNTKCk7CiAgICBpZiAocmMgPT0gMCkgewogICAgICAgIHJldHVybiAwOwogICAgfQoKICAgIHJjID0gYXNuX3JlYWxsb2NfcmJ1aWxkX3NlcXVlbmNlKHBrdCwgcGt0X2xlbiwgb2Zmc2V0LCAxLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKHVfY2hhcikgKEFTTl9TRVFVRU5DRSB8CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgQVNOX0NPTlNUUlVDVE9SKSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICpvZmZzZXQgLSBzdGFydF9vZmZzZXQgKyBib2R5X2xlbik7CgogICAgcmV0dXJuIHJjOwp9ICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8qIGVuZCBzbm1wdjNfc2NvcGVkUERVX2hlYWRlcl9yZWFsbG9jX3JidWlsZCgpICovCiNlbmRpZiAgICAgICAgICAgICAgICAgICAgICAgICAgLyogTkVUU05NUF9VU0VfUkVWRVJTRV9BU05FTkNPRElORyAqLwoKI2lmZGVmIE5FVFNOTVBfVVNFX1JFVkVSU0VfQVNORU5DT0RJTkcKLyoKICogcmV0dXJucyAwIGlmIHN1Y2Nlc3MsIC0xIGlmIGZhaWwsIG5vdCAwIGlmIFNNIGJ1aWxkIGZhaWx1cmUgCiAqLwppbnQKc25tcHYzX3BhY2tldF9yZWFsbG9jX3JidWlsZCh1X2NoYXIgKiogcGt0LCBzaXplX3QgKiBwa3RfbGVuLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNpemVfdCAqIG9mZnNldCwgbmV0c25tcF9zZXNzaW9uICogc2Vzc2lvbiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICBuZXRzbm1wX3BkdSAqcGR1LCB1X2NoYXIgKiBwZHVfZGF0YSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzaXplX3QgcGR1X2RhdGFfbGVuKQp7CiAgICB1X2NoYXIgICAgICAgICAqc2NvcGVkX3BkdSwgKmhkcmJ1ZiA9IE5VTEwsICpoZHIgPSBOVUxMOwogICAgc2l6ZV90ICAgICAgICAgIGhkcmJ1Zl9sZW4gPSBTTk1QX01BWF9NU0dfVjNfSERSUywgaGRyX29mZnNldCA9CiAgICAgICAgMCwgc3BkdV9vZmZzZXQgPSAwOwogICAgc2l6ZV90ICAgICAgICAgIGJvZHlfZW5kX29mZnNldCA9ICpvZmZzZXQsIGJvZHlfbGVuID0gMDsKICAgIHN0cnVjdCBzbm1wX3NlY21vZF9kZWYgKnNwdHIgPSBOVUxMOwogICAgaW50ICAgICAgICAgICAgIHJjID0gMDsKCiAgICAvKgogICAgICogQnVpbGQgYSBzY29wZWRQRFUgc3RydWN0dXJlIGludG8gdGhlIHBhY2tldCBidWZmZXIuICAKICAgICAqLwogICAgREVCVUdQUklOVFBEVVRZUEUoInNlbmQiLCBwZHUtPmNvbW1hbmQpOwogICAgaWYgKHBkdV9kYXRhKSB7CiAgICAgICAgd2hpbGUgKCgqcGt0X2xlbiAtICpvZmZzZXQpIDwgcGR1X2RhdGFfbGVuKSB7CiAgICAgICAgICAgIGlmICghYXNuX3JlYWxsb2MocGt0LCBwa3RfbGVuKSkgewogICAgICAgICAgICAgICAgcmV0dXJuIC0xOwogICAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAqb2Zmc2V0ICs9IHBkdV9kYXRhX2xlbjsKICAgICAgICBtZW1jcHkoKnBrdCArICpwa3RfbGVuIC0gKm9mZnNldCwgcGR1X2RhdGEsIHBkdV9kYXRhX2xlbik7CiAgICB9IGVsc2UgewogICAgICAgIHJjID0gc25tcF9wZHVfcmVhbGxvY19yYnVpbGQocGt0LCBwa3RfbGVuLCBvZmZzZXQsIHBkdSk7CiAgICAgICAgaWYgKHJjID09IDApIHsKICAgICAgICAgICAgcmV0dXJuIC0xOwogICAgICAgIH0KICAgIH0KICAgIGJvZHlfbGVuID0gKm9mZnNldCAtIGJvZHlfZW5kX29mZnNldDsKCiAgICBERUJVR0RVTVBTRUNUSU9OKCJzZW5kIiwgIlNjb3BlZFBkdSIpOwogICAgcmMgPSBzbm1wdjNfc2NvcGVkUERVX2hlYWRlcl9yZWFsbG9jX3JidWlsZChwa3QsIHBrdF9sZW4sIG9mZnNldCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcGR1LCBib2R5X2xlbik7CiAgICBpZiAocmMgPT0gMCkgewogICAgICAgIHJldHVybiAtMTsKICAgIH0KICAgIHNwZHVfb2Zmc2V0ID0gKm9mZnNldDsKICAgIERFQlVHSU5ERU5UQUREKC00KTsgICAgICAgICAvKiAgUmV0dXJuIGZyb20gU2NvcGVkIFBEVS4gICovCgogICAgaWYgKChoZHJidWYgPSAodV9jaGFyICopIG1hbGxvYyhoZHJidWZfbGVuKSkgPT0gTlVMTCkgewogICAgICAgIHJldHVybiAtMTsKICAgIH0KCiAgICByYyA9IHNubXB2M19oZWFkZXJfcmVhbGxvY19yYnVpbGQoJmhkcmJ1ZiwgJmhkcmJ1Zl9sZW4sICZoZHJfb2Zmc2V0LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNlc3Npb24sIHBkdSk7CiAgICBpZiAocmMgPT0gMCkgewogICAgICAgIFNOTVBfRlJFRShoZHJidWYpOwogICAgICAgIHJldHVybiAtMTsKICAgIH0KICAgIGhkciA9IGhkcmJ1ZiArIGhkcmJ1Zl9sZW4gLSBoZHJfb2Zmc2V0OwogICAgc2NvcGVkX3BkdSA9ICpwa3QgKyAqcGt0X2xlbiAtIHNwZHVfb2Zmc2V0OwoKICAgIC8qCiAgICAgKiBDYWxsIHRoZSBzZWN1cml0eSBtb2R1bGUgdG8gcG9zc2libHkgZW5jcnlwdCBhbmQgYXV0aGVudGljYXRlIHRoZQogICAgICogbWVzc2FnZS0tLXRoZSBlbnRpcmUgbWVzc2FnZSB0byB0cmFuc21pdHRlZCBvbiB0aGUgd2lyZSBpcyByZXR1cm5lZC4gIAogICAgICovCgogICAgc3B0ciA9IGZpbmRfc2VjX21vZChwZHUtPnNlY3VyaXR5TW9kZWwpOwogICAgREVCVUdEVU1QU0VDVElPTigic2VuZCIsICJTTSBtc2dTZWN1cml0eVBhcmFtZXRlcnMiKTsKICAgIGlmIChzcHRyICYmIHNwdHItPmVuY29kZV9yZXZlcnNlKSB7CiAgICAgICAgc3RydWN0IHNubXBfc2VjbW9kX291dGdvaW5nX3BhcmFtcyBwYXJtczsKCiAgICAgICAgcGFybXMubXNnUHJvY01vZGVsID0gcGR1LT5tc2dQYXJzZU1vZGVsOwogICAgICAgIHBhcm1zLmdsb2JhbERhdGEgPSBoZHI7CiAgICAgICAgcGFybXMuZ2xvYmFsRGF0YUxlbiA9IGhkcl9vZmZzZXQ7CiAgICAgICAgcGFybXMubWF4TXNnU2l6ZSA9IFNOTVBfTUFYX01TR19TSVpFOwogICAgICAgIHBhcm1zLnNlY01vZGVsID0gcGR1LT5zZWN1cml0eU1vZGVsOwogICAgICAgIHBhcm1zLnNlY0VuZ2luZUlEID0gcGR1LT5zZWN1cml0eUVuZ2luZUlEOwogICAgICAgIHBhcm1zLnNlY0VuZ2luZUlETGVuID0gcGR1LT5zZWN1cml0eUVuZ2luZUlETGVuOwogICAgICAgIHBhcm1zLnNlY05hbWUgPSBwZHUtPnNlY3VyaXR5TmFtZTsKICAgICAgICBwYXJtcy5zZWNOYW1lTGVuID0gcGR1LT5zZWN1cml0eU5hbWVMZW47CiAgICAgICAgcGFybXMuc2VjTGV2ZWwgPSBwZHUtPnNlY3VyaXR5TGV2ZWw7CiAgICAgICAgcGFybXMuc2NvcGVkUGR1ID0gc2NvcGVkX3BkdTsKICAgICAgICBwYXJtcy5zY29wZWRQZHVMZW4gPSBzcGR1X29mZnNldDsKICAgICAgICBwYXJtcy5zZWNTdGF0ZVJlZiA9IHBkdS0+c2VjdXJpdHlTdGF0ZVJlZjsKICAgICAgICBwYXJtcy53aG9sZU1zZyA9IHBrdDsKICAgICAgICBwYXJtcy53aG9sZU1zZ0xlbiA9IHBrdF9sZW47CiAgICAgICAgcGFybXMud2hvbGVNc2dPZmZzZXQgPSBvZmZzZXQ7CiAgICAgICAgcGFybXMuc2Vzc2lvbiA9IHNlc3Npb247CiAgICAgICAgcGFybXMucGR1ID0gcGR1OwoKICAgICAgICByYyA9ICgqc3B0ci0+ZW5jb2RlX3JldmVyc2UpICgmcGFybXMpOwogICAgfSBlbHNlIHsKICAgICAgICBpZiAoIXNwdHIpIHsKICAgICAgICAgICAgc25tcF9sb2coTE9HX0VSUiwKICAgICAgICAgICAgICAgICAgICAgIm5vIHN1Y2ggc2VjdXJpdHkgc2VydmljZSBhdmFpbGFibGU6ICVkXG4iLAogICAgICAgICAgICAgICAgICAgICBwZHUtPnNlY3VyaXR5TW9kZWwpOwogICAgICAgIH0gZWxzZSBpZiAoIXNwdHItPmVuY29kZV9yZXZlcnNlKSB7CiAgICAgICAgICAgIHNubXBfbG9nKExPR19FUlIsCiAgICAgICAgICAgICAgICAgICAgICJzZWN1cml0eSBzZXJ2aWNlICVkIGRvZXNuJ3Qgc3VwcG9ydCByZXZlcnNlIGVuY29kaW5nLlxuIiwKICAgICAgICAgICAgICAgICAgICAgcGR1LT5zZWN1cml0eU1vZGVsKTsKICAgICAgICB9CiAgICAgICAgcmMgPSAtMTsKICAgIH0KCiAgICBERUJVR0lOREVOVExFU1MoKTsKICAgIFNOTVBfRlJFRShoZHJidWYpOwogICAgcmV0dXJuIHJjOwp9ICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8qIGVuZCBzbm1wdjNfcGFja2V0X3JlYWxsb2NfcmJ1aWxkKCkgKi8KI2VuZGlmICAgICAgICAgICAgICAgICAgICAgICAgICAvKiBORVRTTk1QX1VTRV9SRVZFUlNFX0FTTkVOQ09ESU5HICovCgovKgogKiByZXR1cm5zIDAgaWYgc3VjY2VzcywgLTEgaWYgZmFpbCwgbm90IDAgaWYgU00gYnVpbGQgZmFpbHVyZSAKICovCmludApzbm1wdjNfcGFja2V0X2J1aWxkKG5ldHNubXBfc2Vzc2lvbiAqIHNlc3Npb24sIG5ldHNubXBfcGR1ICpwZHUsCiAgICAgICAgICAgICAgICAgICAgdV9jaGFyICogcGFja2V0LCBzaXplX3QgKiBvdXRfbGVuZ3RoLAogICAgICAgICAgICAgICAgICAgIHVfY2hhciAqIHBkdV9kYXRhLCBzaXplX3QgcGR1X2RhdGFfbGVuKQp7CiAgICB1X2NoYXIgICAgICAgICAqZ2xvYmFsX2RhdGEsICpzZWNfcGFyYW1zLCAqc3BkdV9oZHJfZTsKICAgIHNpemVfdCAgICAgICAgICBnbG9iYWxfZGF0YV9sZW4sIHNlY19wYXJhbXNfbGVuOwogICAgdV9jaGFyICAgICAgICAgIHNwZHVfYnVmW1NOTVBfTUFYX01TR19TSVpFXTsKICAgIHNpemVfdCAgICAgICAgICBzcGR1X2J1Zl9sZW4sIHNwZHVfbGVuOwogICAgdV9jaGFyICAgICAgICAgKmNwOwogICAgaW50ICAgICAgICAgICAgIHJlc3VsdDsKICAgIHN0cnVjdCBzbm1wX3NlY21vZF9kZWYgKnNwdHI7CgogICAgZ2xvYmFsX2RhdGEgPSBwYWNrZXQ7CgogICAgLyoKICAgICAqIGJ1aWxkIHRoZSBoZWFkZXJzIGZvciB0aGUgcGFja2V0LCByZXR1cm5lZCBhZGRyID0gc3RhcnQgb2Ygc2VjUGFyYW1zCiAgICAgKi8KICAgIHNlY19wYXJhbXMgPSBzbm1wdjNfaGVhZGVyX2J1aWxkKHNlc3Npb24sIHBkdSwgZ2xvYmFsX2RhdGEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBvdXRfbGVuZ3RoLCAwLCBOVUxMKTsKICAgIGlmIChzZWNfcGFyYW1zID09IE5VTEwpCiAgICAgICAgcmV0dXJuIC0xOwogICAgZ2xvYmFsX2RhdGFfbGVuID0gc2VjX3BhcmFtcyAtIGdsb2JhbF9kYXRhOwogICAgc2VjX3BhcmFtc19sZW4gPSAqb3V0X2xlbmd0aDsgICAgICAgLyogbGVuZ3RoIGxlZnQgaW4gcGFja2V0IGJ1ZiBmb3Igc2VjX3BhcmFtcyAqLwoKCiAgICAvKgogICAgICogYnVpbGQgYSBzY29wZWRQRFUgc3RydWN0dXJlIGludG8gc3BkdV9idWYKICAgICAqLwogICAgc3BkdV9idWZfbGVuID0gU05NUF9NQVhfTVNHX1NJWkU7CiAgICBERUJVR0RVTVBTRUNUSU9OKCJzZW5kIiwgIlNjb3BlZFBkdSIpOwogICAgY3AgPSBzbm1wdjNfc2NvcGVkUERVX2hlYWRlcl9idWlsZChwZHUsIHNwZHVfYnVmLCAmc3BkdV9idWZfbGVuLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmc3BkdV9oZHJfZSk7CiAgICBpZiAoY3AgPT0gTlVMTCkKICAgICAgICByZXR1cm4gLTE7CgogICAgLyoKICAgICAqIGJ1aWxkIHRoZSBQRFUgc3RydWN0dXJlIG9udG8gdGhlIGVuZCBvZiBzcGR1X2J1ZiAKICAgICAqLwogICAgREVCVUdQUklOVFBEVVRZUEUoInNlbmQiLCAoKHBkdV9kYXRhKSA/ICpwZHVfZGF0YSA6IDB4MDApKTsKICAgIGlmIChwZHVfZGF0YSkgewogICAgICAgIG1lbWNweShjcCwgcGR1X2RhdGEsIHBkdV9kYXRhX2xlbik7CiAgICAgICAgY3AgKz0gcGR1X2RhdGFfbGVuOwogICAgfSBlbHNlIHsKICAgICAgICBjcCA9IHNubXBfcGR1X2J1aWxkKHBkdSwgY3AsICZzcGR1X2J1Zl9sZW4pOwogICAgICAgIGlmIChjcCA9PSBOVUxMKQogICAgICAgICAgICByZXR1cm4gLTE7CiAgICB9CiAgICBERUJVR0lOREVOVEFERCgtNCk7ICAgICAgICAgLyogcmV0dXJuIGZyb20gU2NvcGVkIFBEVSAqLwoKICAgIC8qCiAgICAgKiByZS1lbmNvZGUgdGhlIGFjdHVhbCBBU04uMSBsZW5ndGggb2YgdGhlIHNjb3BlZFBkdQogICAgICovCiAgICBzcGR1X2xlbiA9IGNwIC0gc3BkdV9oZHJfZTsgLyogbGVuZ3RoIG9mIHNjb3BlZFBkdSBtaW51cyBBU04uMSBoZWFkZXJzICovCiAgICBzcGR1X2J1Zl9sZW4gPSBTTk1QX01BWF9NU0dfU0laRTsKICAgIGlmIChhc25fYnVpbGRfc2VxdWVuY2Uoc3BkdV9idWYsICZzcGR1X2J1Zl9sZW4sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICh1X2NoYXIpIChBU05fU0VRVUVOQ0UgfCBBU05fQ09OU1RSVUNUT1IpLAogICAgICAgICAgICAgICAgICAgICAgICAgICBzcGR1X2xlbikgPT0gTlVMTCkKICAgICAgICByZXR1cm4gLTE7CiAgICBzcGR1X2xlbiA9IGNwIC0gc3BkdV9idWY7ICAgLyogdGhlIGxlbmd0aCBvZiB0aGUgZW50aXJlIHNjb3BlZFBkdSAqLwoKCiAgICAvKgogICAgICogY2FsbCB0aGUgc2VjdXJpdHkgbW9kdWxlIHRvIHBvc3NpYmx5IGVuY3J5cHQgYW5kIGF1dGhlbnRpY2F0ZSB0aGUKICAgICAqIG1lc3NhZ2UgLSB0aGUgZW50aXJlIG1lc3NhZ2UgdG8gdHJhbnNtaXR0ZWQgb24gdGhlIHdpcmUgaXMgcmV0dXJuZWQKICAgICAqLwogICAgY3AgPSBOVUxMOwogICAgKm91dF9sZW5ndGggPSBTTk1QX01BWF9NU0dfU0laRTsKICAgIERFQlVHRFVNUFNFQ1RJT04oInNlbmQiLCAiU00gbXNnU2VjdXJpdHlQYXJhbWV0ZXJzIik7CiAgICBzcHRyID0gZmluZF9zZWNfbW9kKHBkdS0+c2VjdXJpdHlNb2RlbCk7CiAgICBpZiAoc3B0ciAmJiBzcHRyLT5lbmNvZGVfZm9yd2FyZCkgewogICAgICAgIHN0cnVjdCBzbm1wX3NlY21vZF9vdXRnb2luZ19wYXJhbXMgcGFybXM7CiAgICAgICAgcGFybXMubXNnUHJvY01vZGVsID0gcGR1LT5tc2dQYXJzZU1vZGVsOwogICAgICAgIHBhcm1zLmdsb2JhbERhdGEgPSBnbG9iYWxfZGF0YTsKICAgICAgICBwYXJtcy5nbG9iYWxEYXRhTGVuID0gZ2xvYmFsX2RhdGFfbGVuOwogICAgICAgIHBhcm1zLm1heE1zZ1NpemUgPSBTTk1QX01BWF9NU0dfU0laRTsKICAgICAgICBwYXJtcy5zZWNNb2RlbCA9IHBkdS0+c2VjdXJpdHlNb2RlbDsKICAgICAgICBwYXJtcy5zZWNFbmdpbmVJRCA9IHBkdS0+c2VjdXJpdHlFbmdpbmVJRDsKICAgICAgICBwYXJtcy5zZWNFbmdpbmVJRExlbiA9IHBkdS0+c2VjdXJpdHlFbmdpbmVJRExlbjsKICAgICAgICBwYXJtcy5zZWNOYW1lID0gcGR1LT5zZWN1cml0eU5hbWU7CiAgICAgICAgcGFybXMuc2VjTmFtZUxlbiA9IHBkdS0+c2VjdXJpdHlOYW1lTGVuOwogICAgICAgIHBhcm1zLnNlY0xldmVsID0gcGR1LT5zZWN1cml0eUxldmVsOwogICAgICAgIHBhcm1zLnNjb3BlZFBkdSA9IHNwZHVfYnVmOwogICAgICAgIHBhcm1zLnNjb3BlZFBkdUxlbiA9IHNwZHVfbGVuOwogICAgICAgIHBhcm1zLnNlY1N0YXRlUmVmID0gcGR1LT5zZWN1cml0eVN0YXRlUmVmOwogICAgICAgIHBhcm1zLnNlY1BhcmFtcyA9IHNlY19wYXJhbXM7CiAgICAgICAgcGFybXMuc2VjUGFyYW1zTGVuID0gJnNlY19wYXJhbXNfbGVuOwogICAgICAgIHBhcm1zLndob2xlTXNnID0gJmNwOwogICAgICAgIHBhcm1zLndob2xlTXNnTGVuID0gb3V0X2xlbmd0aDsKICAgICAgICBwYXJtcy5zZXNzaW9uID0gc2Vzc2lvbjsKICAgICAgICBwYXJtcy5wZHUgPSBwZHU7CiAgICAgICAgcmVzdWx0ID0gKCpzcHRyLT5lbmNvZGVfZm9yd2FyZCkgKCZwYXJtcyk7CiAgICB9IGVsc2UgewogICAgICAgIGlmICghc3B0cikgewogICAgICAgICAgICBzbm1wX2xvZyhMT0dfRVJSLCAibm8gc3VjaCBzZWN1cml0eSBzZXJ2aWNlIGF2YWlsYWJsZTogJWRcbiIsCiAgICAgICAgICAgICAgICAgICAgIHBkdS0+c2VjdXJpdHlNb2RlbCk7CiAgICAgICAgfSBlbHNlIGlmICghc3B0ci0+ZW5jb2RlX2ZvcndhcmQpIHsKICAgICAgICAgICAgc25tcF9sb2coTE9HX0VSUiwKICAgICAgICAgICAgICAgICAgICAgInNlY3VyaXR5IHNlcnZpY2UgJWQgZG9lc24ndCBzdXBwb3J0IGZvcndhcmQgb3V0IGVuY29kaW5nLlxuIiwKICAgICAgICAgICAgICAgICAgICAgcGR1LT5zZWN1cml0eU1vZGVsKTsKICAgICAgICB9CiAgICAgICAgcmVzdWx0ID0gLTE7CiAgICB9CiAgICBERUJVR0lOREVOVExFU1MoKTsKICAgIHJldHVybiByZXN1bHQ7Cgp9ICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8qIGVuZCBzbm1wdjNfcGFja2V0X2J1aWxkKCkgKi8KCgovKgogKiBUYWtlcyBhIHNlc3Npb24gYW5kIGEgcGR1IGFuZCBzZXJpYWxpemVzIHRoZSBBU04gUERVIGludG8gdGhlIGFyZWEKICogcG9pbnRlZCB0byBieSAqcGt0LiAgKnBrdF9sZW4gaXMgdGhlIHNpemUgb2YgdGhlIGRhdGEgYXJlYSBhdmFpbGFibGUuCiAqIFJldHVybnMgdGhlIGxlbmd0aCBvZiB0aGUgY29tcGxldGVkIHBhY2tldCBpbiAqb2Zmc2V0LiAgSWYgYW55IGVycm9ycwogKiBvY2N1ciwgLTEgaXMgcmV0dXJuZWQuICBJZiBhbGwgZ29lcyB3ZWxsLCAwIGlzIHJldHVybmVkLgogKi8KCnN0YXRpYyBpbnQKX3NubXBfYnVpbGQodV9jaGFyICoqIHBrdCwgc2l6ZV90ICogcGt0X2xlbiwgc2l6ZV90ICogb2Zmc2V0LAogICAgICAgICAgICBuZXRzbm1wX3Nlc3Npb24gKiBzZXNzaW9uLCBuZXRzbm1wX3BkdSAqcGR1KQp7CiNpZiAhZGVmaW5lZChORVRTTk1QX0RJU0FCTEVfU05NUFYxKSB8fCAhZGVmaW5lZChORVRTTk1QX0RJU0FCTEVfU05NUFYyQykKICAgIHVfY2hhciAgICAgICAgICpoMGUgPSAwOwogICAgc2l6ZV90ICAgICAgICAgIHN0YXJ0X29mZnNldCA9ICpvZmZzZXQ7CiAgICBsb25nICAgICAgICAgICAgdmVyc2lvbjsKICAgIGludCAgICAgICAgICAgICByYyA9IDA7CiNlbmRpZiAvKiBzdXBwb3J0IGZvciBjb21tdW5pdHkgYmFzZWQgU05NUCAqLwogICAgCiAgICB1X2NoYXIgICAgICAgICAqY3A7CiAgICBzaXplX3QgICAgICAgICAgbGVuZ3RoOwoKICAgIHNlc3Npb24tPnNfc25tcF9lcnJubyA9IDA7CiAgICBzZXNzaW9uLT5zX2Vycm5vID0gMDsKCiAgICBpZiAocGR1LT52ZXJzaW9uID09IFNOTVBfVkVSU0lPTl8zKSB7CiAgICAgICAgcmV0dXJuIHNubXB2M19idWlsZChwa3QsIHBrdF9sZW4sIG9mZnNldCwgc2Vzc2lvbiwgcGR1KTsKICAgIH0KCiAgICBzd2l0Y2ggKHBkdS0+Y29tbWFuZCkgewogICAgY2FzZSBTTk1QX01TR19SRVNQT05TRToKICAgICAgICBuZXRzbm1wX2Fzc2VydCgwID09IChwZHUtPmZsYWdzICYgVUNEX01TR19GTEFHX0VYUEVDVF9SRVNQT05TRSkpOwogICAgICAgIC8qCiAgICAgICAgICogRmFsbHRocm91Z2ggCiAgICAgICAgICovCiAgICBjYXNlIFNOTVBfTVNHX0dFVDoKICAgIGNhc2UgU05NUF9NU0dfR0VUTkVYVDoKICAgIGNhc2UgU05NUF9NU0dfU0VUOgogICAgICAgIC8qCiAgICAgICAgICogYWxsIHZlcnNpb25zIHN1cHBvcnQgdGhlc2UgUERVIHR5cGVzIAogICAgICAgICAqLwogICAgICAgIC8qCiAgICAgICAgICogaW5pdGlhbGl6ZSBkZWZhdWx0ZWQgUERVIGZpZWxkcyAKICAgICAgICAgKi8KCiAgICAgICAgaWYgKHBkdS0+ZXJyc3RhdCA9PSBTTk1QX0RFRkFVTFRfRVJSU1RBVCkKICAgICAgICAgICAgcGR1LT5lcnJzdGF0ID0gMDsKICAgICAgICBpZiAocGR1LT5lcnJpbmRleCA9PSBTTk1QX0RFRkFVTFRfRVJSSU5ERVgpCiAgICAgICAgICAgIHBkdS0+ZXJyaW5kZXggPSAwOwogICAgICAgIGJyZWFrOwoKICAgIGNhc2UgU05NUF9NU0dfVFJBUDI6CiAgICAgICAgbmV0c25tcF9hc3NlcnQoMCA9PSAocGR1LT5mbGFncyAmIFVDRF9NU0dfRkxBR19FWFBFQ1RfUkVTUE9OU0UpKTsKICAgICAgICAvKgogICAgICAgICAqIEZhbGx0aHJvdWdoIAogICAgICAgICAqLwogICAgY2FzZSBTTk1QX01TR19JTkZPUk06CiNpZm5kZWYgTkVUU05NUF9ESVNBQkxFX1NOTVBWMQogICAgICAgIC8qCiAgICAgICAgICogbm90IHN1cHBvcnRlZCBpbiBTTk1QdjEgYW5kIFNOTVBzZWMgCiAgICAgICAgICovCiAgICAgICAgaWYgKHBkdS0+dmVyc2lvbiA9PSBTTk1QX1ZFUlNJT05fMSkgewogICAgICAgICAgICBzZXNzaW9uLT5zX3NubXBfZXJybm8gPSBTTk1QRVJSX1YyX0lOX1YxOwogICAgICAgICAgICByZXR1cm4gLTE7CiAgICAgICAgfQojZW5kaWYKICAgICAgICBpZiAocGR1LT5lcnJzdGF0ID09IFNOTVBfREVGQVVMVF9FUlJTVEFUKQogICAgICAgICAgICBwZHUtPmVycnN0YXQgPSAwOwogICAgICAgIGlmIChwZHUtPmVycmluZGV4ID09IFNOTVBfREVGQVVMVF9FUlJJTkRFWCkKICAgICAgICAgICAgcGR1LT5lcnJpbmRleCA9IDA7CiAgICAgICAgYnJlYWs7CgogICAgY2FzZSBTTk1QX01TR19HRVRCVUxLOgogICAgICAgIC8qCiAgICAgICAgICogbm90IHN1cHBvcnRlZCBpbiBTTk1QdjEgYW5kIFNOTVBzZWMgCiAgICAgICAgICovCiNpZm5kZWYgTkVUU05NUF9ESVNBQkxFX1NOTVBWMQogICAgICAgIGlmIChwZHUtPnZlcnNpb24gPT0gU05NUF9WRVJTSU9OXzEpIHsKICAgICAgICAgICAgc2Vzc2lvbi0+c19zbm1wX2Vycm5vID0gU05NUEVSUl9WMl9JTl9WMTsKICAgICAgICAgICAgcmV0dXJuIC0xOwogICAgICAgIH0KI2VuZGlmCiAgICAgICAgaWYgKHBkdS0+bWF4X3JlcGV0aXRpb25zIDwgMCkgewogICAgICAgICAgICBzZXNzaW9uLT5zX3NubXBfZXJybm8gPSBTTk1QRVJSX0JBRF9SRVBFVElUSU9OUzsKICAgICAgICAgICAgcmV0dXJuIC0xOwogICAgICAgIH0KICAgICAgICBpZiAocGR1LT5ub25fcmVwZWF0ZXJzIDwgMCkgewogICAgICAgICAgICBzZXNzaW9uLT5zX3NubXBfZXJybm8gPSBTTk1QRVJSX0JBRF9SRVBFQVRFUlM7CiAgICAgICAgICAgIHJldHVybiAtMTsKICAgICAgICB9CiAgICAgICAgYnJlYWs7CgogICAgY2FzZSBTTk1QX01TR19UUkFQOgogICAgICAgIC8qCiAgICAgICAgICogKm9ubHkqIHN1cHBvcnRlZCBpbiBTTk1QdjEgYW5kIFNOTVBzZWMgCiAgICAgICAgICovCiNpZm5kZWYgTkVUU05NUF9ESVNBQkxFX1NOTVBWMQogICAgICAgIGlmIChwZHUtPnZlcnNpb24gIT0gU05NUF9WRVJTSU9OXzEpIHsKICAgICAgICAgICAgc2Vzc2lvbi0+c19zbm1wX2Vycm5vID0gU05NUEVSUl9WMV9JTl9WMjsKICAgICAgICAgICAgcmV0dXJuIC0xOwogICAgICAgIH0KI2VuZGlmCiAgICAgICAgLyoKICAgICAgICAgKiBpbml0aWFsaXplIGRlZmF1bHRlZCBUcmFwIFBEVSBmaWVsZHMgCiAgICAgICAgICovCiAgICAgICAgcGR1LT5yZXFpZCA9IDE7ICAgICAgICAgLyogZ2l2ZSBhIGJvZ3VzIG5vbi1lcnJvciByZXFpZCBmb3IgdHJhcHMgKi8KICAgICAgICBpZiAocGR1LT5lbnRlcnByaXNlX2xlbmd0aCA9PSBTTk1QX0RFRkFVTFRfRU5URVJQUklTRV9MRU5HVEgpIHsKICAgICAgICAgICAgcGR1LT5lbnRlcnByaXNlID0gKG9pZCAqKSBtYWxsb2Moc2l6ZW9mKERFRkFVTFRfRU5URVJQUklTRSkpOwogICAgICAgICAgICBpZiAocGR1LT5lbnRlcnByaXNlID09IE5VTEwpIHsKICAgICAgICAgICAgICAgIHNlc3Npb24tPnNfc25tcF9lcnJubyA9IFNOTVBFUlJfTUFMTE9DOwogICAgICAgICAgICAgICAgcmV0dXJuIC0xOwogICAgICAgICAgICB9CiAgICAgICAgICAgIG1lbW1vdmUocGR1LT5lbnRlcnByaXNlLCBERUZBVUxUX0VOVEVSUFJJU0UsCiAgICAgICAgICAgICAgICAgICAgc2l6ZW9mKERFRkFVTFRfRU5URVJQUklTRSkpOwogICAgICAgICAgICBwZHUtPmVudGVycHJpc2VfbGVuZ3RoID0KICAgICAgICAgICAgICAgIHNpemVvZihERUZBVUxUX0VOVEVSUFJJU0UpIC8gc2l6ZW9mKG9pZCk7CiAgICAgICAgfQogICAgICAgIGlmIChwZHUtPnRpbWUgPT0gU05NUF9ERUZBVUxUX1RJTUUpCiAgICAgICAgICAgIHBkdS0+dGltZSA9IERFRkFVTFRfVElNRTsKICAgICAgICAvKgogICAgICAgICAqIGRvbid0IGV4cGVjdCBhIHJlc3BvbnNlIAogICAgICAgICAqLwogICAgICAgIHBkdS0+ZmxhZ3MgJj0gKH5VQ0RfTVNHX0ZMQUdfRVhQRUNUX1JFU1BPTlNFKTsKICAgICAgICBicmVhazsKCiAgICBjYXNlIFNOTVBfTVNHX1JFUE9SVDogICAgICAvKiBTTk1QdjMgb25seSAqLwogICAgZGVmYXVsdDoKICAgICAgICBzZXNzaW9uLT5zX3NubXBfZXJybm8gPSBTTk1QRVJSX1VOS05PV05fUERVOwogICAgICAgIHJldHVybiAtMTsKICAgIH0KCiAgICAvKgogICAgICogc2F2ZSBsZW5ndGggCiAgICAgKi8KICAgIGxlbmd0aCA9ICpwa3RfbGVuOwoKICAgIC8qCiAgICAgKiBzZXR1cCBhZG1pbmlzdHJhdGl2ZSBmaWVsZHMgYmFzZWQgb24gdmVyc2lvbiAKICAgICAqLwogICAgLyoKICAgICAqIGJ1aWxkIHRoZSBtZXNzYWdlIHdyYXBwZXIgYW5kIGFsbCB0aGUgYWRtaW5pc3RyYXRpdmUgZmllbGRzCiAgICAgKiB1cHRvIHRoZSBQRFUgc2VxdWVuY2UKICAgICAqIChub3RlIHRoYXQgYWN0dWFsIGxlbmd0aCBvZiBtZXNzYWdlIHdpbGwgYmUgaW5zZXJ0ZWQgbGF0ZXIpIAogICAgICovCiAgICBzd2l0Y2ggKHBkdS0+dmVyc2lvbikgewojaWZuZGVmIE5FVFNOTVBfRElTQUJMRV9TTk1QVjEKICAgIGNhc2UgU05NUF9WRVJTSU9OXzE6CiNlbmRpZgojaWZuZGVmIE5FVFNOTVBfRElTQUJMRV9TTk1QVjJDCiAgICBjYXNlIFNOTVBfVkVSU0lPTl8yYzoKI2VuZGlmCiNpZiAhZGVmaW5lZChORVRTTk1QX0RJU0FCTEVfU05NUFYxKSB8fCAhZGVmaW5lZChORVRTTk1QX0RJU0FCTEVfU05NUFYyQykKI2lmZGVmIE5FVFNOTVBfTk9fWkVST0xFTkdUSF9DT01NVU5JVFkKICAgICAgICBpZiAocGR1LT5jb21tdW5pdHlfbGVuID09IDApIHsKICAgICAgICAgICAgaWYgKHNlc3Npb24tPmNvbW11bml0eV9sZW4gPT0gMCkgewogICAgICAgICAgICAgICAgc2Vzc2lvbi0+c19zbm1wX2Vycm5vID0gU05NUEVSUl9CQURfQ09NTVVOSVRZOwogICAgICAgICAgICAgICAgcmV0dXJuIC0xOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHBkdS0+Y29tbXVuaXR5ID0gKHVfY2hhciAqKSBtYWxsb2Moc2Vzc2lvbi0+Y29tbXVuaXR5X2xlbik7CiAgICAgICAgICAgIGlmIChwZHUtPmNvbW11bml0eSA9PSBOVUxMKSB7CiAgICAgICAgICAgICAgICBzZXNzaW9uLT5zX3NubXBfZXJybm8gPSBTTk1QRVJSX01BTExPQzsKICAgICAgICAgICAgICAgIHJldHVybiAtMTsKICAgICAgICAgICAgfQogICAgICAgICAgICBtZW1tb3ZlKHBkdS0+Y29tbXVuaXR5LAogICAgICAgICAgICAgICAgICAgIHNlc3Npb24tPmNvbW11bml0eSwgc2Vzc2lvbi0+Y29tbXVuaXR5X2xlbik7CiAgICAgICAgICAgIHBkdS0+Y29tbXVuaXR5X2xlbiA9IHNlc3Npb24tPmNvbW11bml0eV9sZW47CiAgICAgICAgfQojZWxzZSAgICAgICAgICAgICAgICAgICAgICAgICAgIC8qICFORVRTTk1QX05PX1pFUk9MRU5HVEhfQ09NTVVOSVRZICovCiAgICAgICAgaWYgKHBkdS0+Y29tbXVuaXR5X2xlbiA9PSAwICYmIHBkdS0+Y29tbWFuZCAhPSBTTk1QX01TR19SRVNQT05TRSkgewogICAgICAgICAgICAvKgogICAgICAgICAgICAgKiBjb3B5IHNlc3Npb24gY29tbXVuaXR5IGV4YWN0bHkgdG8gcGR1IGNvbW11bml0eSAKICAgICAgICAgICAgICovCiAgICAgICAgICAgIGlmICgwID09IHNlc3Npb24tPmNvbW11bml0eV9sZW4pIHsKICAgICAgICAgICAgICAgIFNOTVBfRlJFRShwZHUtPmNvbW11bml0eSk7CiAgICAgICAgICAgICAgICBwZHUtPmNvbW11bml0eSA9IE5VTEw7CiAgICAgICAgICAgIH0gZWxzZSBpZiAocGR1LT5jb21tdW5pdHlfbGVuID09IHNlc3Npb24tPmNvbW11bml0eV9sZW4pIHsKICAgICAgICAgICAgICAgIG1lbW1vdmUocGR1LT5jb21tdW5pdHksCiAgICAgICAgICAgICAgICAgICAgICAgIHNlc3Npb24tPmNvbW11bml0eSwgc2Vzc2lvbi0+Y29tbXVuaXR5X2xlbik7CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICBTTk1QX0ZSRUUocGR1LT5jb21tdW5pdHkpOwogICAgICAgICAgICAgICAgcGR1LT5jb21tdW5pdHkgPSAodV9jaGFyICopIG1hbGxvYyhzZXNzaW9uLT5jb21tdW5pdHlfbGVuKTsKICAgICAgICAgICAgICAgIGlmIChwZHUtPmNvbW11bml0eSA9PSBOVUxMKSB7CiAgICAgICAgICAgICAgICAgICAgc2Vzc2lvbi0+c19zbm1wX2Vycm5vID0gU05NUEVSUl9NQUxMT0M7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIC0xOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgbWVtbW92ZShwZHUtPmNvbW11bml0eSwKICAgICAgICAgICAgICAgICAgICAgICAgc2Vzc2lvbi0+Y29tbXVuaXR5LCBzZXNzaW9uLT5jb21tdW5pdHlfbGVuKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBwZHUtPmNvbW11bml0eV9sZW4gPSBzZXNzaW9uLT5jb21tdW5pdHlfbGVuOwogICAgICAgIH0KI2VuZGlmICAgICAgICAgICAgICAgICAgICAgICAgICAvKiAhTkVUU05NUF9OT19aRVJPTEVOR1RIX0NPTU1VTklUWSAqLwoKICAgICAgICBERUJVR01TR1RMKCgic25tcF9zZW5kIiwgIkJ1aWxkaW5nIFNOTVB2JWQgbWVzc2FnZS4uLlxuIiwKICAgICAgICAgICAgICAgICAgICAoMSArIHBkdS0+dmVyc2lvbikpKTsKI2lmZGVmIE5FVFNOTVBfVVNFX1JFVkVSU0VfQVNORU5DT0RJTkcKICAgICAgICBpZiAobmV0c25tcF9kc19nZXRfYm9vbGVhbihORVRTTk1QX0RTX0xJQlJBUllfSUQsIE5FVFNOTVBfRFNfTElCX1JFVkVSU0VfRU5DT0RFKSkgewogICAgICAgICAgICBERUJVR1BSSU5UUERVVFlQRSgic2VuZCIsIHBkdS0+Y29tbWFuZCk7CiAgICAgICAgICAgIHJjID0gc25tcF9wZHVfcmVhbGxvY19yYnVpbGQocGt0LCBwa3RfbGVuLCBvZmZzZXQsIHBkdSk7CiAgICAgICAgICAgIGlmIChyYyA9PSAwKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gLTE7CiAgICAgICAgICAgIH0KCiAgICAgICAgICAgIERFQlVHRFVNUEhFQURFUigic2VuZCIsICJDb21tdW5pdHkgU3RyaW5nIik7CiAgICAgICAgICAgIHJjID0gYXNuX3JlYWxsb2NfcmJ1aWxkX3N0cmluZyhwa3QsIHBrdF9sZW4sIG9mZnNldCwgMSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICh1X2NoYXIpIChBU05fVU5JVkVSU0FMIHwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBBU05fUFJJTUlUSVZFIHwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBBU05fT0NURVRfU1RSKSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHBkdS0+Y29tbXVuaXR5LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcGR1LT5jb21tdW5pdHlfbGVuKTsKICAgICAgICAgICAgREVCVUdJTkRFTlRMRVNTKCk7CiAgICAgICAgICAgIGlmIChyYyA9PSAwKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gLTE7CiAgICAgICAgICAgIH0KCgogICAgICAgICAgICAvKgogICAgICAgICAgICAgKiBTdG9yZSB0aGUgdmVyc2lvbiBmaWVsZC4gIAogICAgICAgICAgICAgKi8KICAgICAgICAgICAgREVCVUdEVU1QSEVBREVSKCJzZW5kIiwgIlNOTVAgVmVyc2lvbiBOdW1iZXIiKTsKCiAgICAgICAgICAgIHZlcnNpb24gPSBwZHUtPnZlcnNpb247CiAgICAgICAgICAgIHJjID0gYXNuX3JlYWxsb2NfcmJ1aWxkX2ludChwa3QsIHBrdF9sZW4sIG9mZnNldCwgMSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICh1X2NoYXIpIChBU05fVU5JVkVSU0FMIHwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBBU05fUFJJTUlUSVZFIHwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBBU05fSU5URUdFUiksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAobG9uZyAqKSAmdmVyc2lvbiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNpemVvZih2ZXJzaW9uKSk7CiAgICAgICAgICAgIERFQlVHSU5ERU5UTEVTUygpOwogICAgICAgICAgICBpZiAocmMgPT0gMCkgewogICAgICAgICAgICAgICAgcmV0dXJuIC0xOwogICAgICAgICAgICB9CgogICAgICAgICAgICAvKgogICAgICAgICAgICAgKiBCdWlsZCB0aGUgZmluYWwgc2VxdWVuY2UuICAKICAgICAgICAgICAgICovCiNpZm5kZWYgTkVUU05NUF9ESVNBQkxFX1NOTVBWMQogICAgICAgICAgICBpZiAocGR1LT52ZXJzaW9uID09IFNOTVBfVkVSU0lPTl8xKSB7CiAgICAgICAgICAgICAgICBERUJVR0RVTVBTRUNUSU9OKCJzZW5kIiwgIlNOTVB2MSBNZXNzYWdlIik7CiAgICAgICAgICAgIH0gZWxzZSB7CiNlbmRpZgogICAgICAgICAgICAgICAgREVCVUdEVU1QU0VDVElPTigic2VuZCIsICJTTk1QdjJjIE1lc3NhZ2UiKTsKI2lmbmRlZiBORVRTTk1QX0RJU0FCTEVfU05NUFYxCiAgICAgICAgICAgIH0KI2VuZGlmCiAgICAgICAgICAgIHJjID0gYXNuX3JlYWxsb2NfcmJ1aWxkX3NlcXVlbmNlKHBrdCwgcGt0X2xlbiwgb2Zmc2V0LCAxLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAodV9jaGFyKSAoQVNOX1NFUVVFTkNFIHwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEFTTl9DT05TVFJVQ1RPUiksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICpvZmZzZXQgLSBzdGFydF9vZmZzZXQpOwogICAgICAgICAgICBERUJVR0lOREVOVExFU1MoKTsKCiAgICAgICAgICAgIGlmIChyYyA9PSAwKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gLTE7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIDA7CiAgICAgICAgfSBlbHNlIHsKCiNlbmRpZiAgICAgICAgICAgICAgICAgICAgICAgICAgLyogTkVUU05NUF9VU0VfUkVWRVJTRV9BU05FTkNPRElORyAqLwogICAgICAgICAgICAvKgogICAgICAgICAgICAgKiBTYXZlIGN1cnJlbnQgbG9jYXRpb24gYW5kIGJ1aWxkIFNFUVVFTkNFIHRhZyBhbmQgbGVuZ3RoCiAgICAgICAgICAgICAqIHBsYWNlaG9sZGVyIGZvciBTTk1QIG1lc3NhZ2Ugc2VxdWVuY2UKICAgICAgICAgICAgICogKGFjdHVhbCBsZW5ndGggd2lsbCBiZSBpbnNlcnRlZCBsYXRlcikgCiAgICAgICAgICAgICAqLwogICAgICAgICAgICBjcCA9IGFzbl9idWlsZF9zZXF1ZW5jZSgqcGt0LCBwa3RfbGVuLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAodV9jaGFyKSAoQVNOX1NFUVVFTkNFIHwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEFTTl9DT05TVFJVQ1RPUiksIDApOwogICAgICAgICAgICBpZiAoY3AgPT0gTlVMTCkgewogICAgICAgICAgICAgICAgcmV0dXJuIC0xOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGgwZSA9IGNwOwoKI2lmbmRlZiBORVRTTk1QX0RJU0FCTEVfU05NUFYxCiAgICAgICAgICAgIGlmIChwZHUtPnZlcnNpb24gPT0gU05NUF9WRVJTSU9OXzEpIHsKICAgICAgICAgICAgICAgIERFQlVHRFVNUFNFQ1RJT04oInNlbmQiLCAiU05NUHYxIE1lc3NhZ2UiKTsKICAgICAgICAgICAgfSBlbHNlIHsKI2VuZGlmCiAgICAgICAgICAgICAgICBERUJVR0RVTVBTRUNUSU9OKCJzZW5kIiwgIlNOTVB2MmMgTWVzc2FnZSIpOwojaWZuZGVmIE5FVFNOTVBfRElTQUJMRV9TTk1QVjEKICAgICAgICAgICAgfQojZW5kaWYKCiAgICAgICAgICAgIC8qCiAgICAgICAgICAgICAqIHN0b3JlIHRoZSB2ZXJzaW9uIGZpZWxkIAogICAgICAgICAgICAgKi8KICAgICAgICAgICAgREVCVUdEVU1QSEVBREVSKCJzZW5kIiwgIlNOTVAgVmVyc2lvbiBOdW1iZXIiKTsKCiAgICAgICAgICAgIHZlcnNpb24gPSBwZHUtPnZlcnNpb247CiAgICAgICAgICAgIGNwID0gYXNuX2J1aWxkX2ludChjcCwgcGt0X2xlbiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICh1X2NoYXIpIChBU05fVU5JVkVSU0FMIHwgQVNOX1BSSU1JVElWRSB8CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgQVNOX0lOVEVHRVIpLCAobG9uZyAqKSAmdmVyc2lvbiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNpemVvZih2ZXJzaW9uKSk7CiAgICAgICAgICAgIERFQlVHSU5ERU5UTEVTUygpOwogICAgICAgICAgICBpZiAoY3AgPT0gTlVMTCkKICAgICAgICAgICAgICAgIHJldHVybiAtMTsKCiAgICAgICAgICAgIC8qCiAgICAgICAgICAgICAqIHN0b3JlIHRoZSBjb21tdW5pdHkgc3RyaW5nIAogICAgICAgICAgICAgKi8KICAgICAgICAgICAgREVCVUdEVU1QSEVBREVSKCJzZW5kIiwgIkNvbW11bml0eSBTdHJpbmciKTsKICAgICAgICAgICAgY3AgPSBhc25fYnVpbGRfc3RyaW5nKGNwLCBwa3RfbGVuLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKHVfY2hhcikgKEFTTl9VTklWRVJTQUwgfCBBU05fUFJJTUlUSVZFIHwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBBU05fT0NURVRfU1RSKSwgcGR1LT5jb21tdW5pdHksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBwZHUtPmNvbW11bml0eV9sZW4pOwogICAgICAgICAgICBERUJVR0lOREVOVExFU1MoKTsKICAgICAgICAgICAgaWYgKGNwID09IE5VTEwpCiAgICAgICAgICAgICAgICByZXR1cm4gLTE7CiAgICAgICAgICAgIGJyZWFrOwoKI2lmZGVmIE5FVFNOTVBfVVNFX1JFVkVSU0VfQVNORU5DT0RJTkcKICAgICAgICB9CiNlbmRpZiAgICAgICAgICAgICAgICAgICAgICAgICAgLyogTkVUU05NUF9VU0VfUkVWRVJTRV9BU05FTkNPRElORyAqLwogICAgICAgIGJyZWFrOwojZW5kaWYgLyogc3VwcG9ydCBmb3IgY29tbXVuaXR5IGJhc2VkIFNOTVAgKi8KICAgIGNhc2UgU05NUF9WRVJTSU9OXzJwOgogICAgY2FzZSBTTk1QX1ZFUlNJT05fc2VjOgogICAgY2FzZSBTTk1QX1ZFUlNJT05fMnU6CiAgICBjYXNlIFNOTVBfVkVSU0lPTl8yc3RhcjoKICAgIGRlZmF1bHQ6CiAgICAgICAgc2Vzc2lvbi0+c19zbm1wX2Vycm5vID0gU05NUEVSUl9CQURfVkVSU0lPTjsKICAgICAgICByZXR1cm4gLTE7CiAgICB9CgogICAgREVCVUdQUklOVFBEVVRZUEUoInNlbmQiLCBwZHUtPmNvbW1hbmQpOwogICAgY3AgPSBzbm1wX3BkdV9idWlsZChwZHUsIGNwLCBwa3RfbGVuKTsKICAgIERFQlVHSU5ERU5UQUREKC00KTsgICAgICAgICAvKiByZXR1cm4gZnJvbSBlbnRpcmUgdjEvdjJjIG1lc3NhZ2UgKi8KICAgIGlmIChjcCA9PSBOVUxMKQogICAgICAgIHJldHVybiAtMTsKCiAgICAvKgogICAgICogaW5zZXJ0IHRoZSBhY3R1YWwgbGVuZ3RoIG9mIHRoZSBtZXNzYWdlIHNlcXVlbmNlIAogICAgICovCiAgICBzd2l0Y2ggKHBkdS0+dmVyc2lvbikgewojaWZuZGVmIE5FVFNOTVBfRElTQUJMRV9TTk1QVjEKICAgIGNhc2UgU05NUF9WRVJTSU9OXzE6CiNlbmRpZgojaWZuZGVmIE5FVFNOTVBfRElTQUJMRV9TTk1QVjJDCiAgICBjYXNlIFNOTVBfVkVSU0lPTl8yYzoKI2VuZGlmCiNpZiAhZGVmaW5lZChORVRTTk1QX0RJU0FCTEVfU05NUFYxKSB8fCAhZGVmaW5lZChORVRTTk1QX0RJU0FCTEVfU05NUFYyQykKICAgICAgICBhc25fYnVpbGRfc2VxdWVuY2UoKnBrdCwgJmxlbmd0aCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgKHVfY2hhcikgKEFTTl9TRVFVRU5DRSB8IEFTTl9DT05TVFJVQ1RPUiksCiAgICAgICAgICAgICAgICAgICAgICAgICAgIGNwIC0gaDBlKTsKICAgICAgICBicmVhazsKI2VuZGlmIC8qIHN1cHBvcnQgZm9yIGNvbW11bml0eSBiYXNlZCBTTk1QICovCgogICAgY2FzZSBTTk1QX1ZFUlNJT05fMnA6CiAgICBjYXNlIFNOTVBfVkVSU0lPTl9zZWM6CiAgICBjYXNlIFNOTVBfVkVSU0lPTl8ydToKICAgIGNhc2UgU05NUF9WRVJTSU9OXzJzdGFyOgogICAgZGVmYXVsdDoKICAgICAgICBzZXNzaW9uLT5zX3NubXBfZXJybm8gPSBTTk1QRVJSX0JBRF9WRVJTSU9OOwogICAgICAgIHJldHVybiAtMTsKICAgIH0KICAgICpwa3RfbGVuID0gY3AgLSAqcGt0OwogICAgcmV0dXJuIDA7Cn0KCmludApzbm1wX2J1aWxkKHVfY2hhciAqKiBwa3QsIHNpemVfdCAqIHBrdF9sZW4sIHNpemVfdCAqIG9mZnNldCwKICAgICAgICAgICBuZXRzbm1wX3Nlc3Npb24gKiBwc3MsIG5ldHNubXBfcGR1ICpwZHUpCnsKICAgIGludCAgICAgICAgICAgICByYzsKICAgIHJjID0gX3NubXBfYnVpbGQocGt0LCBwa3RfbGVuLCBvZmZzZXQsIHBzcywgcGR1KTsKICAgIGlmIChyYykgewogICAgICAgIGlmICghcHNzLT5zX3NubXBfZXJybm8pIHsKICAgICAgICAgICAgc25tcF9sb2coTE9HX0VSUiwgInNubXBfYnVpbGQ6IHVua25vd24gZmFpbHVyZVxuIik7CiAgICAgICAgICAgIHBzcy0+c19zbm1wX2Vycm5vID0gU05NUEVSUl9CQURfQVNOMV9CVUlMRDsKICAgICAgICB9CiAgICAgICAgU0VUX1NOTVBfRVJST1IocHNzLT5zX3NubXBfZXJybm8pOwogICAgICAgIHJjID0gLTE7CiAgICB9CiAgICByZXR1cm4gcmM7Cn0KCi8qCiAqIG9uIGVycm9yLCByZXR1cm5zIE5VTEwgKGxpa2VseSBhbiBlbmNvZGluZyBwcm9ibGVtKS4gCiAqLwp1X2NoYXIgICAgICAgICAqCnNubXBfcGR1X2J1aWxkKG5ldHNubXBfcGR1ICpwZHUsIHVfY2hhciAqIGNwLCBzaXplX3QgKiBvdXRfbGVuZ3RoKQp7CiAgICB1X2NoYXIgICAgICAgICAqaDEsICpoMWUsICpoMiwgKmgyZTsKICAgIG5ldHNubXBfdmFyaWFibGVfbGlzdCAqdnA7CiAgICBzaXplX3QgICAgICAgICAgbGVuZ3RoOwoKICAgIGxlbmd0aCA9ICpvdXRfbGVuZ3RoOwogICAgLyoKICAgICAqIFNhdmUgY3VycmVudCBsb2NhdGlvbiBhbmQgYnVpbGQgUERVIHRhZyBhbmQgbGVuZ3RoIHBsYWNlaG9sZGVyCiAgICAgKiAoYWN0dWFsIGxlbmd0aCB3aWxsIGJlIGluc2VydGVkIGxhdGVyKSAKICAgICAqLwogICAgaDEgPSBjcDsKICAgIGNwID0gYXNuX2J1aWxkX3NlcXVlbmNlKGNwLCBvdXRfbGVuZ3RoLCAodV9jaGFyKSBwZHUtPmNvbW1hbmQsIDApOwogICAgaWYgKGNwID09IE5VTEwpCiAgICAgICAgcmV0dXJuIE5VTEw7CiAgICBoMWUgPSBjcDsKCiAgICAvKgogICAgICogc3RvcmUgZmllbGRzIGluIHRoZSBQRFUgcHJlY2VlZGluZyB0aGUgdmFyaWFibGUtYmluZGluZ3Mgc2VxdWVuY2UgCiAgICAgKi8KICAgIGlmIChwZHUtPmNvbW1hbmQgIT0gU05NUF9NU0dfVFJBUCkgewogICAgICAgIC8qCiAgICAgICAgICogUERVIGlzIG5vdCBhbiBTTk1QdjEgdHJhcCAKICAgICAgICAgKi8KCiAgICAgICAgREVCVUdEVU1QSEVBREVSKCJzZW5kIiwgInJlcXVlc3RfaWQiKTsKICAgICAgICAvKgogICAgICAgICAqIHJlcXVlc3QgaWQgCiAgICAgICAgICovCiAgICAgICAgY3AgPSBhc25fYnVpbGRfaW50KGNwLCBvdXRfbGVuZ3RoLAogICAgICAgICAgICAgICAgICAgICAgICAgICAodV9jaGFyKSAoQVNOX1VOSVZFUlNBTCB8IEFTTl9QUklNSVRJVkUgfAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgQVNOX0lOVEVHRVIpLCAmcGR1LT5yZXFpZCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgc2l6ZW9mKHBkdS0+cmVxaWQpKTsKICAgICAgICBERUJVR0lOREVOVExFU1MoKTsKICAgICAgICBpZiAoY3AgPT0gTlVMTCkKICAgICAgICAgICAgcmV0dXJuIE5VTEw7CgogICAgICAgIC8qCiAgICAgICAgICogZXJyb3Igc3RhdHVzIChnZXRidWxrIG5vbi1yZXBlYXRlcnMpIAogICAgICAgICAqLwogICAgICAgIERFQlVHRFVNUEhFQURFUigic2VuZCIsICJlcnJvciBzdGF0dXMiKTsKICAgICAgICBjcCA9IGFzbl9idWlsZF9pbnQoY3AsIG91dF9sZW5ndGgsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICh1X2NoYXIpIChBU05fVU5JVkVSU0FMIHwgQVNOX1BSSU1JVElWRSB8CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBBU05fSU5URUdFUiksICZwZHUtPmVycnN0YXQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgIHNpemVvZihwZHUtPmVycnN0YXQpKTsKICAgICAgICBERUJVR0lOREVOVExFU1MoKTsKICAgICAgICBpZiAoY3AgPT0gTlVMTCkKICAgICAgICAgICAgcmV0dXJuIE5VTEw7CgogICAgICAgIC8qCiAgICAgICAgICogZXJyb3IgaW5kZXggKGdldGJ1bGsgbWF4LXJlcGV0aXRpb25zKSAKICAgICAgICAgKi8KICAgICAgICBERUJVR0RVTVBIRUFERVIoInNlbmQiLCAiZXJyb3IgaW5kZXgiKTsKICAgICAgICBjcCA9IGFzbl9idWlsZF9pbnQoY3AsIG91dF9sZW5ndGgsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICh1X2NoYXIpIChBU05fVU5JVkVSU0FMIHwgQVNOX1BSSU1JVElWRSB8CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBBU05fSU5URUdFUiksICZwZHUtPmVycmluZGV4LAogICAgICAgICAgICAgICAgICAgICAgICAgICBzaXplb2YocGR1LT5lcnJpbmRleCkpOwogICAgICAgIERFQlVHSU5ERU5UTEVTUygpOwogICAgICAgIGlmIChjcCA9PSBOVUxMKQogICAgICAgICAgICByZXR1cm4gTlVMTDsKICAgIH0gZWxzZSB7CiAgICAgICAgLyoKICAgICAgICAgKiBhbiBTTk1QdjEgdHJhcCBQRFUgCiAgICAgICAgICovCgogICAgICAgIC8qCiAgICAgICAgICogZW50ZXJwcmlzZSAKICAgICAgICAgKi8KICAgICAgICBERUJVR0RVTVBIRUFERVIoInNlbmQiLCAiZW50ZXJwcmlzZSBPQkpJRCIpOwogICAgICAgIGNwID0gYXNuX2J1aWxkX29iamlkKGNwLCBvdXRfbGVuZ3RoLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICh1X2NoYXIpIChBU05fVU5JVkVSU0FMIHwgQVNOX1BSSU1JVElWRSB8CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEFTTl9PQkpFQ1RfSUQpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgIChvaWQgKikgcGR1LT5lbnRlcnByaXNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgIHBkdS0+ZW50ZXJwcmlzZV9sZW5ndGgpOwogICAgICAgIERFQlVHSU5ERU5UTEVTUygpOwogICAgICAgIGlmIChjcCA9PSBOVUxMKQogICAgICAgICAgICByZXR1cm4gTlVMTDsKCiAgICAgICAgLyoKICAgICAgICAgKiBhZ2VudC1hZGRyIAogICAgICAgICAqLwogICAgICAgIERFQlVHRFVNUEhFQURFUigic2VuZCIsICJhZ2VudCBBZGRyZXNzIik7CiAgICAgICAgY3AgPSBhc25fYnVpbGRfc3RyaW5nKGNwLCBvdXRfbGVuZ3RoLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAodV9jaGFyKSAoQVNOX0lQQUREUkVTUyB8IEFTTl9QUklNSVRJVkUpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAodV9jaGFyICopIHBkdS0+YWdlbnRfYWRkciwgNCk7CiAgICAgICAgREVCVUdJTkRFTlRMRVNTKCk7CiAgICAgICAgaWYgKGNwID09IE5VTEwpCiAgICAgICAgICAgIHJldHVybiBOVUxMOwoKICAgICAgICAvKgogICAgICAgICAqIGdlbmVyaWMgdHJhcCAKICAgICAgICAgKi8KICAgICAgICBERUJVR0RVTVBIRUFERVIoInNlbmQiLCAiZ2VuZXJpYyB0cmFwIG51bWJlciIpOwogICAgICAgIGNwID0gYXNuX2J1aWxkX2ludChjcCwgb3V0X2xlbmd0aCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgKHVfY2hhcikgKEFTTl9VTklWRVJTQUwgfCBBU05fUFJJTUlUSVZFIHwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEFTTl9JTlRFR0VSKSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgKGxvbmcgKikgJnBkdS0+dHJhcF90eXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICBzaXplb2YocGR1LT50cmFwX3R5cGUpKTsKICAgICAgICBERUJVR0lOREVOVExFU1MoKTsKICAgICAgICBpZiAoY3AgPT0gTlVMTCkKICAgICAgICAgICAgcmV0dXJuIE5VTEw7CgogICAgICAgIC8qCiAgICAgICAgICogc3BlY2lmaWMgdHJhcCAKICAgICAgICAgKi8KICAgICAgICBERUJVR0RVTVBIRUFERVIoInNlbmQiLCAic3BlY2lmaWMgdHJhcCBudW1iZXIiKTsKICAgICAgICBjcCA9IGFzbl9idWlsZF9pbnQoY3AsIG91dF9sZW5ndGgsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICh1X2NoYXIpIChBU05fVU5JVkVSU0FMIHwgQVNOX1BSSU1JVElWRSB8CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBBU05fSU5URUdFUiksCiAgICAgICAgICAgICAgICAgICAgICAgICAgIChsb25nICopICZwZHUtPnNwZWNpZmljX3R5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgIHNpemVvZihwZHUtPnNwZWNpZmljX3R5cGUpKTsKICAgICAgICBERUJVR0lOREVOVExFU1MoKTsKICAgICAgICBpZiAoY3AgPT0gTlVMTCkKICAgICAgICAgICAgcmV0dXJuIE5VTEw7CgogICAgICAgIC8qCiAgICAgICAgICogdGltZXN0YW1wICAKICAgICAgICAgKi8KICAgICAgICBERUJVR0RVTVBIRUFERVIoInNlbmQiLCAidGltZXN0YW1wIik7CiAgICAgICAgY3AgPSBhc25fYnVpbGRfdW5zaWduZWRfaW50KGNwLCBvdXRfbGVuZ3RoLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAodV9jaGFyKSAoQVNOX1RJTUVUSUNLUyB8CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBBU05fUFJJTUlUSVZFKSwgJnBkdS0+dGltZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2l6ZW9mKHBkdS0+dGltZSkpOwogICAgICAgIERFQlVHSU5ERU5UTEVTUygpOwogICAgICAgIGlmIChjcCA9PSBOVUxMKQogICAgICAgICAgICByZXR1cm4gTlVMTDsKICAgIH0KCiAgICAvKgogICAgICogU2F2ZSBjdXJyZW50IGxvY2F0aW9uIGFuZCBidWlsZCBTRVFVRU5DRSB0YWcgYW5kIGxlbmd0aCBwbGFjZWhvbGRlcgogICAgICogZm9yIHZhcmlhYmxlLWJpbmRpbmdzIHNlcXVlbmNlCiAgICAgKiAoYWN0dWFsIGxlbmd0aCB3aWxsIGJlIGluc2VydGVkIGxhdGVyKSAKICAgICAqLwogICAgaDIgPSBjcDsKICAgIGNwID0gYXNuX2J1aWxkX3NlcXVlbmNlKGNwLCBvdXRfbGVuZ3RoLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgKHVfY2hhcikgKEFTTl9TRVFVRU5DRSB8IEFTTl9DT05TVFJVQ1RPUiksIDApOwogICAgaWYgKGNwID09IE5VTEwpCiAgICAgICAgcmV0dXJuIE5VTEw7CiAgICBoMmUgPSBjcDsKCiAgICAvKgogICAgICogU3RvcmUgdmFyaWFibGUtYmluZGluZ3MgCiAgICAgKi8KICAgIERFQlVHRFVNUFNFQ1RJT04oInNlbmQiLCAiVmFyQmluZExpc3QiKTsKICAgIGZvciAodnAgPSBwZHUtPnZhcmlhYmxlczsgdnA7IHZwID0gdnAtPm5leHRfdmFyaWFibGUpIHsKICAgICAgICBERUJVR0RVTVBTRUNUSU9OKCJzZW5kIiwgIlZhckJpbmQiKTsKICAgICAgICBjcCA9IHNubXBfYnVpbGRfdmFyX29wKGNwLCB2cC0+bmFtZSwgJnZwLT5uYW1lX2xlbmd0aCwgdnAtPnR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2cC0+dmFsX2xlbiwgKHVfY2hhciAqKSB2cC0+dmFsLnN0cmluZywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIG91dF9sZW5ndGgpOwogICAgICAgIERFQlVHSU5ERU5UTEVTUygpOwogICAgICAgIGlmIChjcCA9PSBOVUxMKQogICAgICAgICAgICByZXR1cm4gTlVMTDsKICAgIH0KICAgIERFQlVHSU5ERU5UTEVTUygpOwoKICAgIC8qCiAgICAgKiBpbnNlcnQgYWN0dWFsIGxlbmd0aCBvZiB2YXJpYWJsZS1iaW5kaW5ncyBzZXF1ZW5jZSAKICAgICAqLwogICAgYXNuX2J1aWxkX3NlcXVlbmNlKGgyLCAmbGVuZ3RoLAogICAgICAgICAgICAgICAgICAgICAgICh1X2NoYXIpIChBU05fU0VRVUVOQ0UgfCBBU05fQ09OU1RSVUNUT1IpLAogICAgICAgICAgICAgICAgICAgICAgIGNwIC0gaDJlKTsKCiAgICAvKgogICAgICogaW5zZXJ0IGFjdHVhbCBsZW5ndGggb2YgUERVIHNlcXVlbmNlIAogICAgICovCiAgICBhc25fYnVpbGRfc2VxdWVuY2UoaDEsICZsZW5ndGgsICh1X2NoYXIpIHBkdS0+Y29tbWFuZCwgY3AgLSBoMWUpOwoKICAgIHJldHVybiBjcDsKfQoKI2lmZGVmIE5FVFNOTVBfVVNFX1JFVkVSU0VfQVNORU5DT0RJTkcKLyoKICogT24gZXJyb3IsIHJldHVybnMgMCAobGlrZWx5IGFuIGVuY29kaW5nIHByb2JsZW0pLiAgCiAqLwppbnQKc25tcF9wZHVfcmVhbGxvY19yYnVpbGQodV9jaGFyICoqIHBrdCwgc2l6ZV90ICogcGt0X2xlbiwgc2l6ZV90ICogb2Zmc2V0LAogICAgICAgICAgICAgICAgICAgICAgICBuZXRzbm1wX3BkdSAqcGR1KQp7CiNpZm5kZWYgVlBDQUNIRV9TSVpFCiNkZWZpbmUgVlBDQUNIRV9TSVpFIDUwCiNlbmRpZgogICAgbmV0c25tcF92YXJpYWJsZV9saXN0ICp2cGNhY2hlW1ZQQ0FDSEVfU0laRV07CiAgICBuZXRzbm1wX3ZhcmlhYmxlX2xpc3QgKnZwLCAqdG1wdnA7CiAgICBzaXplX3QgICAgICAgICAgc3RhcnRfb2Zmc2V0ID0gKm9mZnNldDsKICAgIGludCAgICAgICAgICAgICBpLCB3cmFwcGVkID0gMCwgbm90ZG9uZSwgZmluYWwsIHJjID0gMDsKCiAgICBERUJVR01TR1RMKCgic25tcF9wZHVfcmVhbGxvY19yYnVpbGQiLCAic3RhcnRpbmdcbiIpKTsKICAgIGZvciAodnAgPSBwZHUtPnZhcmlhYmxlcywgaSA9IFZQQ0FDSEVfU0laRSAtIDE7IHZwOwogICAgICAgICB2cCA9IHZwLT5uZXh0X3ZhcmlhYmxlLCBpLS0pIHsKICAgICAgICBpZiAoaSA8IDApIHsKICAgICAgICAgICAgd3JhcHBlZCA9IG5vdGRvbmUgPSAxOwogICAgICAgICAgICBpID0gVlBDQUNIRV9TSVpFIC0gMTsKICAgICAgICAgICAgREVCVUdNU0dUTCgoInNubXBfcGR1X3JlYWxsb2NfcmJ1aWxkIiwgIndyYXBwZWRcbiIpKTsKICAgICAgICB9CiAgICAgICAgdnBjYWNoZVtpXSA9IHZwOwogICAgfQogICAgZmluYWwgPSBpICsgMTsKCiAgICBkbyB7CiAgICAgICAgZm9yIChpID0gZmluYWw7IGkgPCBWUENBQ0hFX1NJWkU7IGkrKykgewogICAgICAgICAgICB2cCA9IHZwY2FjaGVbaV07CiAgICAgICAgICAgIERFQlVHRFVNUFNFQ1RJT04oInNlbmQiLCAiVmFyQmluZCIpOwogICAgICAgICAgICByYyA9IHNubXBfcmVhbGxvY19yYnVpbGRfdmFyX29wKHBrdCwgcGt0X2xlbiwgb2Zmc2V0LCAxLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHZwLT5uYW1lLCAmdnAtPm5hbWVfbGVuZ3RoLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHZwLT50eXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICh1X2NoYXIgKikgdnAtPnZhbC5zdHJpbmcsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdnAtPnZhbF9sZW4pOwogICAgICAgICAgICBERUJVR0lOREVOVExFU1MoKTsKICAgICAgICAgICAgaWYgKHJjID09IDApIHsKICAgICAgICAgICAgICAgIHJldHVybiAwOwogICAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICBERUJVR0lOREVOVExFU1MoKTsKICAgICAgICBpZiAod3JhcHBlZCkgewogICAgICAgICAgICBub3Rkb25lID0gMTsKICAgICAgICAgICAgZm9yIChpID0gMDsgaSA8IGZpbmFsOyBpKyspIHsKICAgICAgICAgICAgICAgIHZwID0gdnBjYWNoZVtpXTsKICAgICAgICAgICAgICAgIERFQlVHRFVNUFNFQ1RJT04oInNlbmQiLCAiVmFyQmluZCIpOwogICAgICAgICAgICAgICAgcmMgPSBzbm1wX3JlYWxsb2NfcmJ1aWxkX3Zhcl9vcChwa3QsIHBrdF9sZW4sIG9mZnNldCwgMSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdnAtPm5hbWUsICZ2cC0+bmFtZV9sZW5ndGgsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHZwLT50eXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAodV9jaGFyICopIHZwLT52YWwuc3RyaW5nLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2cC0+dmFsX2xlbik7CiAgICAgICAgICAgICAgICBERUJVR0lOREVOVExFU1MoKTsKICAgICAgICAgICAgICAgIGlmIChyYyA9PSAwKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIDA7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KCiAgICAgICAgICAgIGlmIChmaW5hbCA9PSAwKSB7CiAgICAgICAgICAgICAgICB0bXB2cCA9IHZwY2FjaGVbVlBDQUNIRV9TSVpFIC0gMV07CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICB0bXB2cCA9IHZwY2FjaGVbZmluYWwgLSAxXTsKICAgICAgICAgICAgfQogICAgICAgICAgICB3cmFwcGVkID0gMDsKCiAgICAgICAgICAgIGZvciAodnAgPSBwZHUtPnZhcmlhYmxlcywgaSA9IFZQQ0FDSEVfU0laRSAtIDE7CiAgICAgICAgICAgICAgICAgdnAgJiYgdnAgIT0gdG1wdnA7IHZwID0gdnAtPm5leHRfdmFyaWFibGUsIGktLSkgewogICAgICAgICAgICAgICAgaWYgKGkgPCAwKSB7CiAgICAgICAgICAgICAgICAgICAgd3JhcHBlZCA9IDE7CiAgICAgICAgICAgICAgICAgICAgaSA9IFZQQ0FDSEVfU0laRSAtIDE7CiAgICAgICAgICAgICAgICAgICAgREVCVUdNU0dUTCgoInNubXBfcGR1X3JlYWxsb2NfcmJ1aWxkIiwgIndyYXBwZWRcbiIpKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHZwY2FjaGVbaV0gPSB2cDsKICAgICAgICAgICAgfQogICAgICAgICAgICBmaW5hbCA9IGkgKyAxOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIG5vdGRvbmUgPSAwOwogICAgICAgIH0KICAgIH0gd2hpbGUgKG5vdGRvbmUpOwoKICAgIC8qCiAgICAgKiBTYXZlIGN1cnJlbnQgbG9jYXRpb24gYW5kIGJ1aWxkIFNFUVVFTkNFIHRhZyBhbmQgbGVuZ3RoIHBsYWNlaG9sZGVyIGZvcgogICAgICogdmFyaWFibGUtYmluZGluZ3Mgc2VxdWVuY2UgKGFjdHVhbCBsZW5ndGggd2lsbCBiZSBpbnNlcnRlZCBsYXRlcikuICAKICAgICAqLwoKICAgIHJjID0gYXNuX3JlYWxsb2NfcmJ1aWxkX3NlcXVlbmNlKHBrdCwgcGt0X2xlbiwgb2Zmc2V0LCAxLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKHVfY2hhcikgKEFTTl9TRVFVRU5DRSB8CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgQVNOX0NPTlNUUlVDVE9SKSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICpvZmZzZXQgLSBzdGFydF9vZmZzZXQpOwoKICAgIC8qCiAgICAgKiBTdG9yZSBmaWVsZHMgaW4gdGhlIFBEVSBwcmVjZWVkaW5nIHRoZSB2YXJpYWJsZS1iaW5kaW5ncyBzZXF1ZW5jZS4gIAogICAgICovCiAgICBpZiAocGR1LT5jb21tYW5kICE9IFNOTVBfTVNHX1RSQVApIHsKICAgICAgICAvKgogICAgICAgICAqIEVycm9yIGluZGV4IChnZXRidWxrIG1heC1yZXBldGl0aW9ucykuICAKICAgICAgICAgKi8KICAgICAgICBERUJVR0RVTVBIRUFERVIoInNlbmQiLCAiZXJyb3IgaW5kZXgiKTsKICAgICAgICByYyA9IGFzbl9yZWFsbG9jX3JidWlsZF9pbnQocGt0LCBwa3RfbGVuLCBvZmZzZXQsIDEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICh1X2NoYXIpIChBU05fVU5JVkVSU0FMIHwgQVNOX1BSSU1JVElWRQogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgfCBBU05fSU5URUdFUiksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICZwZHUtPmVycmluZGV4LCBzaXplb2YocGR1LT5lcnJpbmRleCkpOwogICAgICAgIERFQlVHSU5ERU5UTEVTUygpOwogICAgICAgIGlmIChyYyA9PSAwKSB7CiAgICAgICAgICAgIHJldHVybiAwOwogICAgICAgIH0KCiAgICAgICAgLyoKICAgICAgICAgKiBFcnJvciBzdGF0dXMgKGdldGJ1bGsgbm9uLXJlcGVhdGVycykuICAKICAgICAgICAgKi8KICAgICAgICBERUJVR0RVTVBIRUFERVIoInNlbmQiLCAiZXJyb3Igc3RhdHVzIik7CiAgICAgICAgcmMgPSBhc25fcmVhbGxvY19yYnVpbGRfaW50KHBrdCwgcGt0X2xlbiwgb2Zmc2V0LCAxLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAodV9jaGFyKSAoQVNOX1VOSVZFUlNBTCB8IEFTTl9QUklNSVRJVkUKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHwgQVNOX0lOVEVHRVIpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmcGR1LT5lcnJzdGF0LCBzaXplb2YocGR1LT5lcnJzdGF0KSk7CiAgICAgICAgREVCVUdJTkRFTlRMRVNTKCk7CiAgICAgICAgaWYgKHJjID09IDApIHsKICAgICAgICAgICAgcmV0dXJuIDA7CiAgICAgICAgfQoKICAgICAgICAvKgogICAgICAgICAqIFJlcXVlc3QgSUQuICAKICAgICAgICAgKi8KICAgICAgICBERUJVR0RVTVBIRUFERVIoInNlbmQiLCAicmVxdWVzdF9pZCIpOwogICAgICAgIHJjID0gYXNuX3JlYWxsb2NfcmJ1aWxkX2ludChwa3QsIHBrdF9sZW4sIG9mZnNldCwgMSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKHVfY2hhcikgKEFTTl9VTklWRVJTQUwgfCBBU05fUFJJTUlUSVZFCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB8IEFTTl9JTlRFR0VSKSwgJnBkdS0+cmVxaWQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNpemVvZihwZHUtPnJlcWlkKSk7CiAgICAgICAgREVCVUdJTkRFTlRMRVNTKCk7CiAgICAgICAgaWYgKHJjID09IDApIHsKICAgICAgICAgICAgcmV0dXJuIDA7CiAgICAgICAgfQogICAgfSBlbHNlIHsKICAgICAgICAvKgogICAgICAgICAqIEFuIFNOTVB2MSB0cmFwIFBEVS4gIAogICAgICAgICAqLwoKICAgICAgICAvKgogICAgICAgICAqIFRpbWVzdGFtcC4gIAogICAgICAgICAqLwogICAgICAgIERFQlVHRFVNUEhFQURFUigic2VuZCIsICJ0aW1lc3RhbXAiKTsKICAgICAgICByYyA9IGFzbl9yZWFsbG9jX3JidWlsZF91bnNpZ25lZF9pbnQocGt0LCBwa3RfbGVuLCBvZmZzZXQsIDEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICh1X2NoYXIpIChBU05fVElNRVRJQ0tTIHwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEFTTl9QUklNSVRJVkUpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmcGR1LT50aW1lLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzaXplb2YocGR1LT50aW1lKSk7CiAgICAgICAgREVCVUdJTkRFTlRMRVNTKCk7CiAgICAgICAgaWYgKHJjID09IDApIHsKICAgICAgICAgICAgcmV0dXJuIDA7CiAgICAgICAgfQoKICAgICAgICAvKgogICAgICAgICAqIFNwZWNpZmljIHRyYXAuICAKICAgICAgICAgKi8KICAgICAgICBERUJVR0RVTVBIRUFERVIoInNlbmQiLCAic3BlY2lmaWMgdHJhcCBudW1iZXIiKTsKICAgICAgICByYyA9IGFzbl9yZWFsbG9jX3JidWlsZF9pbnQocGt0LCBwa3RfbGVuLCBvZmZzZXQsIDEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICh1X2NoYXIpIChBU05fVU5JVkVSU0FMIHwgQVNOX1BSSU1JVElWRQogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgfCBBU05fSU5URUdFUiksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIChsb25nICopICZwZHUtPnNwZWNpZmljX3R5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNpemVvZihwZHUtPnNwZWNpZmljX3R5cGUpKTsKICAgICAgICBERUJVR0lOREVOVExFU1MoKTsKICAgICAgICBpZiAocmMgPT0gMCkgewogICAgICAgICAgICByZXR1cm4gMDsKICAgICAgICB9CgogICAgICAgIC8qCiAgICAgICAgICogR2VuZXJpYyB0cmFwLiAgCiAgICAgICAgICovCiAgICAgICAgREVCVUdEVU1QSEVBREVSKCJzZW5kIiwgImdlbmVyaWMgdHJhcCBudW1iZXIiKTsKICAgICAgICByYyA9IGFzbl9yZWFsbG9jX3JidWlsZF9pbnQocGt0LCBwa3RfbGVuLCBvZmZzZXQsIDEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICh1X2NoYXIpIChBU05fVU5JVkVSU0FMIHwgQVNOX1BSSU1JVElWRQogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgfCBBU05fSU5URUdFUiksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIChsb25nICopICZwZHUtPnRyYXBfdHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2l6ZW9mKHBkdS0+dHJhcF90eXBlKSk7CiAgICAgICAgREVCVUdJTkRFTlRMRVNTKCk7CiAgICAgICAgaWYgKHJjID09IDApIHsKICAgICAgICAgICAgcmV0dXJuIDA7CiAgICAgICAgfQoKICAgICAgICAvKgogICAgICAgICAqIEFnZW50LWFkZHIuICAKICAgICAgICAgKi8KICAgICAgICBERUJVR0RVTVBIRUFERVIoInNlbmQiLCAiYWdlbnQgQWRkcmVzcyIpOwogICAgICAgIHJjID0gYXNuX3JlYWxsb2NfcmJ1aWxkX3N0cmluZyhwa3QsIHBrdF9sZW4sIG9mZnNldCwgMSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKHVfY2hhcikgKEFTTl9JUEFERFJFU1MgfAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgQVNOX1BSSU1JVElWRSksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICh1X2NoYXIgKikgcGR1LT5hZ2VudF9hZGRyLCA0KTsKICAgICAgICBERUJVR0lOREVOVExFU1MoKTsKICAgICAgICBpZiAocmMgPT0gMCkgewogICAgICAgICAgICByZXR1cm4gMDsKICAgICAgICB9CgogICAgICAgIC8qCiAgICAgICAgICogRW50ZXJwcmlzZS4gIAogICAgICAgICAqLwogICAgICAgIERFQlVHRFVNUEhFQURFUigic2VuZCIsICJlbnRlcnByaXNlIE9CSklEIik7CiAgICAgICAgcmMgPSBhc25fcmVhbGxvY19yYnVpbGRfb2JqaWQocGt0LCBwa3RfbGVuLCBvZmZzZXQsIDEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKHVfY2hhcikgKEFTTl9VTklWRVJTQUwgfAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBBU05fUFJJTUlUSVZFIHwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgQVNOX09CSkVDVF9JRCksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKG9pZCAqKSBwZHUtPmVudGVycHJpc2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcGR1LT5lbnRlcnByaXNlX2xlbmd0aCk7CiAgICAgICAgREVCVUdJTkRFTlRMRVNTKCk7CiAgICAgICAgaWYgKHJjID09IDApIHsKICAgICAgICAgICAgcmV0dXJuIDA7CiAgICAgICAgfQogICAgfQoKICAgIC8qCiAgICAgKiBCdWlsZCB0aGUgUERVIHNlcXVlbmNlLiAgCiAgICAgKi8KICAgIHJjID0gYXNuX3JlYWxsb2NfcmJ1aWxkX3NlcXVlbmNlKHBrdCwgcGt0X2xlbiwgb2Zmc2V0LCAxLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKHVfY2hhcikgcGR1LT5jb21tYW5kLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKm9mZnNldCAtIHN0YXJ0X29mZnNldCk7CiAgICByZXR1cm4gcmM7Cn0KI2VuZGlmICAgICAgICAgICAgICAgICAgICAgICAgICAvKiBORVRTTk1QX1VTRV9SRVZFUlNFX0FTTkVOQ09ESU5HICovCgovKgogKiBQYXJzZXMgdGhlIHBhY2tldCByZWNlaXZlZCB0byBkZXRlcm1pbmUgdmVyc2lvbiwgZWl0aGVyIGRpcmVjdGx5CiAqIGZyb20gcGFja2V0cyB2ZXJzaW9uIGZpZWxkIG9yIGluZmVycmVkIGZyb20gQVNOLjEgY29uc3RydWN0LgogKi8Kc3RhdGljIGludApzbm1wX3BhcnNlX3ZlcnNpb24odV9jaGFyICogZGF0YSwgc2l6ZV90IGxlbmd0aCkKewogICAgdV9jaGFyICAgICAgICAgIHR5cGU7CiAgICBsb25nICAgICAgICAgICAgdmVyc2lvbiA9IFNOTVBFUlJfQkFEX1ZFUlNJT047CgogICAgZGF0YSA9IGFzbl9wYXJzZV9zZXF1ZW5jZShkYXRhLCAmbGVuZ3RoLCAmdHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKEFTTl9TRVFVRU5DRSB8IEFTTl9DT05TVFJVQ1RPUiksICJ2ZXJzaW9uIik7CiAgICBpZiAoZGF0YSkgewogICAgICAgIGRhdGEgPQogICAgICAgICAgICBhc25fcGFyc2VfaW50KGRhdGEsICZsZW5ndGgsICZ0eXBlLCAmdmVyc2lvbiwgc2l6ZW9mKHZlcnNpb24pKTsKICAgICAgICBpZiAoIWRhdGEgfHwgdHlwZSAhPSBBU05fSU5URUdFUikgewogICAgICAgICAgICByZXR1cm4gU05NUEVSUl9CQURfVkVSU0lPTjsKICAgICAgICB9CiAgICB9CiAgICByZXR1cm4gdmVyc2lvbjsKfQoKCmludApzbm1wdjNfcGFyc2UobmV0c25tcF9wZHUgKnBkdSwKICAgICAgICAgICAgIHVfY2hhciAqIGRhdGEsCiAgICAgICAgICAgICBzaXplX3QgKiBsZW5ndGgsCiAgICAgICAgICAgICB1X2NoYXIgKiogYWZ0ZXJfaGVhZGVyLCBuZXRzbm1wX3Nlc3Npb24gKiBzZXNzKQp7CiAgICB1X2NoYXIgICAgICAgICAgdHlwZSwgbXNnX2ZsYWdzOwogICAgbG9uZyAgICAgICAgICAgIHZlciwgbXNnX21heF9zaXplLCBtc2dfc2VjX21vZGVsOwogICAgc2l6ZV90ICAgICAgICAgIG1heF9zaXplX3Jlc3BvbnNlOwogICAgdV9jaGFyICAgICAgICAgIHRtcF9idWZbU05NUF9NQVhfTVNHX1NJWkVdOwogICAgc2l6ZV90ICAgICAgICAgIHRtcF9idWZfbGVuOwogICAgdV9jaGFyICAgICAgICAgIHBkdV9idWZbU05NUF9NQVhfTVNHX1NJWkVdOwogICAgdV9jaGFyICAgICAgICAgKm1hbGxvY2J1ZiA9IE5VTEw7CiAgICBzaXplX3QgICAgICAgICAgcGR1X2J1Zl9sZW4gPSBTTk1QX01BWF9NU0dfU0laRTsKICAgIHVfY2hhciAgICAgICAgICpzZWNfcGFyYW1zOwogICAgdV9jaGFyICAgICAgICAgKm1zZ19kYXRhOwogICAgdV9jaGFyICAgICAgICAgKmNwOwogICAgc2l6ZV90ICAgICAgICAgIGFzbl9sZW4sIG1zZ19sZW47CiAgICBpbnQgICAgICAgICAgICAgcmV0LCByZXRfdmFsOwogICAgc3RydWN0IHNubXBfc2VjbW9kX2RlZiAqc3B0cjsKCgogICAgbXNnX2RhdGEgPSBkYXRhOwogICAgbXNnX2xlbiA9ICpsZW5ndGg7CgoKICAgIC8qCiAgICAgKiBtZXNzYWdlIGlzIGFuIEFTTi4xIFNFUVVFTkNFICAKICAgICAqLwogICAgREVCVUdEVU1QU0VDVElPTigicmVjdiIsICJTTk1QdjMgTWVzc2FnZSIpOwogICAgZGF0YSA9IGFzbl9wYXJzZV9zZXF1ZW5jZShkYXRhLCBsZW5ndGgsICZ0eXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAoQVNOX1NFUVVFTkNFIHwgQVNOX0NPTlNUUlVDVE9SKSwgIm1lc3NhZ2UiKTsKICAgIGlmIChkYXRhID09IE5VTEwpIHsKICAgICAgICAvKgogICAgICAgICAqIGVycm9yIG1zZyBkZXRhaWwgaXMgc2V0IAogICAgICAgICAqLwogICAgICAgIHNubXBfaW5jcmVtZW50X3N0YXRpc3RpYyhTVEFUX1NOTVBJTkFTTlBBUlNFRVJSUyk7CiAgICAgICAgREVCVUdJTkRFTlRMRVNTKCk7CiAgICAgICAgcmV0dXJuIFNOTVBFUlJfQVNOX1BBUlNFX0VSUjsKICAgIH0KCiAgICAvKgogICAgICogcGFyc2UgbXNnVmVyc2lvbiAgCiAgICAgKi8KICAgIERFQlVHRFVNUEhFQURFUigicmVjdiIsICJTTk1QIFZlcnNpb24gTnVtYmVyIik7CiAgICBkYXRhID0gYXNuX3BhcnNlX2ludChkYXRhLCBsZW5ndGgsICZ0eXBlLCAmdmVyLCBzaXplb2YodmVyKSk7CiAgICBERUJVR0lOREVOVExFU1MoKTsKICAgIGlmIChkYXRhID09IE5VTEwpIHsKICAgICAgICBFUlJPUl9NU0coImJhZCBwYXJzZSBvZiB2ZXJzaW9uIik7CiAgICAgICAgc25tcF9pbmNyZW1lbnRfc3RhdGlzdGljKFNUQVRfU05NUElOQVNOUEFSU0VFUlJTKTsKICAgICAgICBERUJVR0lOREVOVExFU1MoKTsKICAgICAgICByZXR1cm4gU05NUEVSUl9BU05fUEFSU0VfRVJSOwogICAgfQogICAgcGR1LT52ZXJzaW9uID0gdmVyOwoKICAgIC8qCiAgICAgKiBwYXJzZSBtc2dHbG9iYWxEYXRhIHNlcXVlbmNlICAKICAgICAqLwogICAgY3AgPSBkYXRhOwogICAgYXNuX2xlbiA9ICpsZW5ndGg7CiAgICBERUJVR0RVTVBTRUNUSU9OKCJyZWN2IiwgIm1zZ0dsb2JhbERhdGEiKTsKICAgIGRhdGEgPSBhc25fcGFyc2Vfc2VxdWVuY2UoZGF0YSwgJmFzbl9sZW4sICZ0eXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAoQVNOX1NFUVVFTkNFIHwgQVNOX0NPTlNUUlVDVE9SKSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIm1zZ0dsb2JhbERhdGEiKTsKICAgIGlmIChkYXRhID09IE5VTEwpIHsKICAgICAgICAvKgogICAgICAgICAqIGVycm9yIG1zZyBkZXRhaWwgaXMgc2V0IAogICAgICAgICAqLwogICAgICAgIHNubXBfaW5jcmVtZW50X3N0YXRpc3RpYyhTVEFUX1NOTVBJTkFTTlBBUlNFRVJSUyk7CiAgICAgICAgREVCVUdJTkRFTlRBREQoLTQpOwogICAgICAgIHJldHVybiBTTk1QRVJSX0FTTl9QQVJTRV9FUlI7CiAgICB9CiAgICAqbGVuZ3RoIC09IGRhdGEgLSBjcDsgICAgICAgLyogc3VidHJhY3Qgb2ZmIHRoZSBsZW5ndGggb2YgdGhlIGhlYWRlciAqLwoKICAgIC8qCiAgICAgKiBtc2dJRCAKICAgICAqLwogICAgREVCVUdEVU1QSEVBREVSKCJyZWN2IiwgIm1zZ0lEIik7CiAgICBkYXRhID0KICAgICAgICBhc25fcGFyc2VfaW50KGRhdGEsIGxlbmd0aCwgJnR5cGUsICZwZHUtPm1zZ2lkLAogICAgICAgICAgICAgICAgICAgICAgc2l6ZW9mKHBkdS0+bXNnaWQpKTsKICAgIERFQlVHSU5ERU5UTEVTUygpOwogICAgaWYgKGRhdGEgPT0gTlVMTCB8fCB0eXBlICE9IEFTTl9JTlRFR0VSKSB7CiAgICAgICAgRVJST1JfTVNHKCJlcnJvciBwYXJzaW5nIG1zZ0lEIik7CiAgICAgICAgREVCVUdJTkRFTlRBREQoLTQpOwogICAgICAgIHNubXBfaW5jcmVtZW50X3N0YXRpc3RpYyhTVEFUX1NOTVBJTkFTTlBBUlNFRVJSUyk7CiAgICAgICAgcmV0dXJuIFNOTVBFUlJfQVNOX1BBUlNFX0VSUjsKICAgIH0KCiAgICAvKgogICAgICogQ2hlY2sgdGhlIG1zZ0lEIHdlIHJlY2VpdmVkIGlzIGEgbGVnYWwgdmFsdWUuICBJZiBub3QsIHRoZW4gaW5jcmVtZW50CiAgICAgKiBzbm1wSW5BU05QYXJzZUVycnMgYW5kIHJldHVybiB0aGUgYXBwcm9wcmlhdGUgZXJyb3IgKHNlZSBSRkMgMjU3MiwKICAgICAqIHBhcmEuIDcuMiwgc2VjdGlvbiAyIC0tIG5vdGUgdGhhdCBhIGJhZCBtc2dJRCBtZWFucyB0aGF0IHRoZSByZWNlaXZlZAogICAgICogbWVzc2FnZSBpcyBOT1QgYSBzZXJpYWxpaXphdGlvbiBvZiBhbiBTTk1QdjNNZXNzYWdlLCBzaW5jZSB0aGUgbXNnSUQKICAgICAqIGZpZWxkIGlzIG91dCBvZiBib3VuZHMpLiAgCiAgICAgKi8KCiAgICBpZiAocGR1LT5tc2dpZCA8IDAgfHwgcGR1LT5tc2dpZCA+IDB4N2ZmZmZmZmYpIHsKICAgICAgICBzbm1wX2xvZyhMT0dfRVJSLCAiUmVjZWl2ZWQgYmFkIG1zZ0lEICglbGQgJXMgJXMpLlxuIiwgcGR1LT5tc2dpZCwKICAgICAgICAgICAgICAgICAocGR1LT5tc2dpZCA8IDApID8gIjwiIDogIj4iLAogICAgICAgICAgICAgICAgIChwZHUtPm1zZ2lkIDwgMCkgPyAiMCIgOiAiMl4zMSAtIDEiKTsKICAgICAgICBzbm1wX2luY3JlbWVudF9zdGF0aXN0aWMoU1RBVF9TTk1QSU5BU05QQVJTRUVSUlMpOwogICAgICAgIERFQlVHSU5ERU5UQUREKC00KTsKICAgICAgICByZXR1cm4gU05NUEVSUl9BU05fUEFSU0VfRVJSOwogICAgfQoKICAgIC8qCiAgICAgKiBtc2dNYXhTaXplIAogICAgICovCiAgICBERUJVR0RVTVBIRUFERVIoInJlY3YiLCAibXNnTWF4U2l6ZSIpOwogICAgZGF0YSA9IGFzbl9wYXJzZV9pbnQoZGF0YSwgbGVuZ3RoLCAmdHlwZSwgJm1zZ19tYXhfc2l6ZSwKICAgICAgICAgICAgICAgICAgICAgICAgIHNpemVvZihtc2dfbWF4X3NpemUpKTsKICAgIERFQlVHSU5ERU5UTEVTUygpOwogICAgaWYgKGRhdGEgPT0gTlVMTCB8fCB0eXBlICE9IEFTTl9JTlRFR0VSKSB7CiAgICAgICAgRVJST1JfTVNHKCJlcnJvciBwYXJzaW5nIG1zZ01heFNpemUiKTsKICAgICAgICBzbm1wX2luY3JlbWVudF9zdGF0aXN0aWMoU1RBVF9TTk1QSU5BU05QQVJTRUVSUlMpOwogICAgICAgIERFQlVHSU5ERU5UQUREKC00KTsKICAgICAgICByZXR1cm4gU05NUEVSUl9BU05fUEFSU0VfRVJSOwogICAgfQoKICAgIC8qCiAgICAgKiBDaGVjayB0aGUgbXNnTWF4U2l6ZSB3ZSByZWNlaXZlZCBpcyBhIGxlZ2FsIHZhbHVlLiAgSWYgbm90LCB0aGVuCiAgICAgKiBpbmNyZW1lbnQgc25tcEluQVNOUGFyc2VFcnJzIGFuZCByZXR1cm4gdGhlIGFwcHJvcHJpYXRlIGVycm9yIChzZWUgUkZDCiAgICAgKiAyNTcyLCBwYXJhLiA3LjIsIHNlY3Rpb24gMiAtLSBub3RlIHRoYXQgYSBiYWQgbXNnTWF4U2l6ZSBtZWFucyB0aGF0IHRoZQogICAgICogcmVjZWl2ZWQgbWVzc2FnZSBpcyBOT1QgYSBzZXJpYWxpaXphdGlvbiBvZiBhbiBTTk1QdjNNZXNzYWdlLCBzaW5jZSB0aGUKICAgICAqIG1zZ01heFNpemUgZmllbGQgaXMgb3V0IG9mIGJvdW5kcykuCiAgICAgKiAKICAgICAqIE5vdGUgd2Ugc3RvcmUgdGhlIG1zZ01heFNpemUgb24gYSBwZXItc2Vzc2lvbiBiYXNpcyB3aGljaCBhbHNvIHNlZW1zCiAgICAgKiByZWFzb25hYmxlOyBpdCBjb3VsZCB2YXJ5IGZyb20gUERVIHRvIFBEVSBidXQgdGhhdCB3b3VsZCBiZSBzdHJhbmdlCiAgICAgKiAoYWxzbyBzaW5jZSB3ZSBkZWFsIHdpdGggYSBQRFUgYXQgYSB0aW1lLCBpdCB3b3VsZG4ndCBtYWtlIGFueQogICAgICogZGlmZmVyZW5jZSB0byBvdXIgcmVzcG9uc2VzLCBpZiBhbnkpLiAgCiAgICAgKi8KCiAgICBpZiAobXNnX21heF9zaXplIDwgNDg0KSB7CiAgICAgICAgc25tcF9sb2coTE9HX0VSUiwgIlJlY2VpdmVkIGJhZCBtc2dNYXhTaXplICglbHUgPCA0ODQpLlxuIiwKICAgICAgICAgICAgICAgICBtc2dfbWF4X3NpemUpOwogICAgICAgIHNubXBfaW5jcmVtZW50X3N0YXRpc3RpYyhTVEFUX1NOTVBJTkFTTlBBUlNFRVJSUyk7CiAgICAgICAgREVCVUdJTkRFTlRBREQoLTQpOwogICAgICAgIHJldHVybiBTTk1QRVJSX0FTTl9QQVJTRV9FUlI7CiAgICB9IGVsc2UgaWYgKG1zZ19tYXhfc2l6ZSA+IDB4N2ZmZmZmZmYpIHsKICAgICAgICBzbm1wX2xvZyhMT0dfRVJSLCAiUmVjZWl2ZWQgYmFkIG1zZ01heFNpemUgKCVsdSA+IDJeMzEgLSAxKS5cbiIsCiAgICAgICAgICAgICAgICAgbXNnX21heF9zaXplKTsKICAgICAgICBzbm1wX2luY3JlbWVudF9zdGF0aXN0aWMoU1RBVF9TTk1QSU5BU05QQVJTRUVSUlMpOwogICAgICAgIERFQlVHSU5ERU5UQUREKC00KTsKICAgICAgICByZXR1cm4gU05NUEVSUl9BU05fUEFSU0VfRVJSOwogICAgfSBlbHNlIHsKICAgICAgICBERUJVR01TR1RMKCgic25tcHYzX3BhcnNlIiwgIm1zZ01heFNpemUgJWx1IHJlY2VpdmVkXG4iLAogICAgICAgICAgICAgICAgICAgIG1zZ19tYXhfc2l6ZSkpOwogICAgICAgIHNlc3MtPnNuZE1zZ01heFNpemUgPSBtc2dfbWF4X3NpemU7CiAgICB9CgogICAgLyoKICAgICAqIG1zZ0ZsYWdzIAogICAgICovCiAgICB0bXBfYnVmX2xlbiA9IFNOTVBfTUFYX01TR19TSVpFOwogICAgREVCVUdEVU1QSEVBREVSKCJyZWN2IiwgIm1zZ0ZsYWdzIik7CiAgICBkYXRhID0gYXNuX3BhcnNlX3N0cmluZyhkYXRhLCBsZW5ndGgsICZ0eXBlLCB0bXBfYnVmLCAmdG1wX2J1Zl9sZW4pOwogICAgREVCVUdJTkRFTlRMRVNTKCk7CiAgICBpZiAoZGF0YSA9PSBOVUxMIHx8IHR5cGUgIT0gQVNOX09DVEVUX1NUUiB8fCB0bXBfYnVmX2xlbiAhPSAxKSB7CiAgICAgICAgRVJST1JfTVNHKCJlcnJvciBwYXJzaW5nIG1zZ0ZsYWdzIik7CiAgICAgICAgc25tcF9pbmNyZW1lbnRfc3RhdGlzdGljKFNUQVRfU05NUElOQVNOUEFSU0VFUlJTKTsKICAgICAgICBERUJVR0lOREVOVEFERCgtNCk7CiAgICAgICAgcmV0dXJuIFNOTVBFUlJfQVNOX1BBUlNFX0VSUjsKICAgIH0KICAgIG1zZ19mbGFncyA9ICp0bXBfYnVmOwogICAgaWYgKG1zZ19mbGFncyAmIFNOTVBfTVNHX0ZMQUdfUlBSVF9CSVQpCiAgICAgICAgcGR1LT5mbGFncyB8PSBTTk1QX01TR19GTEFHX1JQUlRfQklUOwogICAgZWxzZQogICAgICAgIHBkdS0+ZmxhZ3MgJj0gKH5TTk1QX01TR19GTEFHX1JQUlRfQklUKTsKCiAgICAvKgogICAgICogbXNnU2VjdXJpdHlNb2RlbCAKICAgICAqLwogICAgREVCVUdEVU1QSEVBREVSKCJyZWN2IiwgIm1zZ1NlY3VyaXR5TW9kZWwiKTsKICAgIGRhdGEgPSBhc25fcGFyc2VfaW50KGRhdGEsIGxlbmd0aCwgJnR5cGUsICZtc2dfc2VjX21vZGVsLAogICAgICAgICAgICAgICAgICAgICAgICAgc2l6ZW9mKG1zZ19zZWNfbW9kZWwpKTsKICAgIERFQlVHSU5ERU5UQUREKC00KTsgICAgICAgICAvKiByZXR1cm4gZnJvbSBnbG9iYWwgZGF0YSBpbmRlbnQgKi8KICAgIGlmIChkYXRhID09IE5VTEwgfHwgdHlwZSAhPSBBU05fSU5URUdFUiB8fAogICAgICAgIG1zZ19zZWNfbW9kZWwgPCAxIHx8IG1zZ19zZWNfbW9kZWwgPiAweDdmZmZmZmZmKSB7CiAgICAgICAgRVJST1JfTVNHKCJlcnJvciBwYXJzaW5nIG1zZ1NlY3VyaXR5TW9kZWwiKTsKICAgICAgICBzbm1wX2luY3JlbWVudF9zdGF0aXN0aWMoU1RBVF9TTk1QSU5BU05QQVJTRUVSUlMpOwogICAgICAgIERFQlVHSU5ERU5UTEVTUygpOwogICAgICAgIHJldHVybiBTTk1QRVJSX0FTTl9QQVJTRV9FUlI7CiAgICB9CiAgICBzcHRyID0gZmluZF9zZWNfbW9kKG1zZ19zZWNfbW9kZWwpOwogICAgaWYgKCFzcHRyKSB7CiAgICAgICAgc25tcF9sb2coTE9HX1dBUk5JTkcsICJ1bmtub3duIHNlY3VyaXR5IG1vZGVsOiAlbGRcbiIsCiAgICAgICAgICAgICAgICAgbXNnX3NlY19tb2RlbCk7CiAgICAgICAgc25tcF9pbmNyZW1lbnRfc3RhdGlzdGljKFNUQVRfU05NUFVOS05PV05TRUNVUklUWU1PREVMUyk7CiAgICAgICAgREVCVUdJTkRFTlRMRVNTKCk7CiAgICAgICAgcmV0dXJuIFNOTVBFUlJfVU5LTk9XTl9TRUNfTU9ERUw7CiAgICB9CiAgICBwZHUtPnNlY3VyaXR5TW9kZWwgPSBtc2dfc2VjX21vZGVsOwoKICAgIGlmIChtc2dfZmxhZ3MgJiBTTk1QX01TR19GTEFHX1BSSVZfQklUICYmCiAgICAgICAgIShtc2dfZmxhZ3MgJiBTTk1QX01TR19GTEFHX0FVVEhfQklUKSkgewogICAgICAgIEVSUk9SX01TRygiaW52YWxpZCBtZXNzYWdlLCBpbGxlZ2FsIG1zZ0ZsYWdzIik7CiAgICAgICAgc25tcF9pbmNyZW1lbnRfc3RhdGlzdGljKFNUQVRfU05NUElOVkFMSURNU0dTKTsKICAgICAgICBERUJVR0lOREVOVExFU1MoKTsKICAgICAgICByZXR1cm4gU05NUEVSUl9JTlZBTElEX01TRzsKICAgIH0KICAgIHBkdS0+c2VjdXJpdHlMZXZlbCA9ICgobXNnX2ZsYWdzICYgU05NUF9NU0dfRkxBR19BVVRIX0JJVCkKICAgICAgICAgICAgICAgICAgICAgICAgICA/ICgobXNnX2ZsYWdzICYgU05NUF9NU0dfRkxBR19QUklWX0JJVCkKICAgICAgICAgICAgICAgICAgICAgICAgICAgICA/IFNOTVBfU0VDX0xFVkVMX0FVVEhQUklWCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgOiBTTk1QX1NFQ19MRVZFTF9BVVRITk9QUklWKQogICAgICAgICAgICAgICAgICAgICAgICAgIDogU05NUF9TRUNfTEVWRUxfTk9BVVRIKTsKICAgIC8qCiAgICAgKiBlbmQgb2YgbXNnR2xvYmFsRGF0YSAKICAgICAqLwoKICAgIC8qCiAgICAgKiBzZWN1cnRpdHlQYXJhbWV0ZXJzIE9DVEVUIFNUUklORyBiZWdpbnMgYWZ0ZXIgbXNnR2xvYmFsRGF0YSAKICAgICAqLwogICAgc2VjX3BhcmFtcyA9IGRhdGE7CiAgICBwZHUtPmNvbnRleHRFbmdpbmVJRCA9ICh1X2NoYXIgKikgY2FsbG9jKDEsIFNOTVBfTUFYX0VOR19TSVpFKTsKICAgIHBkdS0+Y29udGV4dEVuZ2luZUlETGVuID0gU05NUF9NQVhfRU5HX1NJWkU7CgogICAgLyoKICAgICAqIE5vdGU6IHRoZXJlIGlzIG5vIGxlbmd0aCBsaW1pdCBvbiB0aGUgbXNnQXV0aG9yaXRhdGl2ZUVuZ2luZUlEIGZpZWxkLAogICAgICogYWx0aG91Z2ggd2Ugd291bGQgRVhQRUNUIGl0IHRvIGJlIGxpbWl0ZWQgdG8gMzIgKHRoZSBTbm1wRW5naW5lSUQgVEMKICAgICAqIGxpbWl0KS4gIFdlJ2xsIHVzZSBkb3VibGUgdGhhdCBoZXJlIHRvIGJlIG9uIHRoZSBzYWZlIHNpZGUuICAKICAgICAqLwoKICAgIHBkdS0+c2VjdXJpdHlFbmdpbmVJRCA9ICh1X2NoYXIgKikgY2FsbG9jKDEsIFNOTVBfTUFYX0VOR19TSVpFICogMik7CiAgICBwZHUtPnNlY3VyaXR5RW5naW5lSURMZW4gPSBTTk1QX01BWF9FTkdfU0laRSAqIDI7CiAgICBwZHUtPnNlY3VyaXR5TmFtZSA9IChjaGFyICopIGNhbGxvYygxLCBTTk1QX01BWF9TRUNfTkFNRV9TSVpFKTsKICAgIHBkdS0+c2VjdXJpdHlOYW1lTGVuID0gU05NUF9NQVhfU0VDX05BTUVfU0laRTsKCiAgICBpZiAoKHBkdS0+c2VjdXJpdHlOYW1lID09IE5VTEwpIHx8CiAgICAgICAgKHBkdS0+c2VjdXJpdHlFbmdpbmVJRCA9PSBOVUxMKSB8fAogICAgICAgIChwZHUtPmNvbnRleHRFbmdpbmVJRCA9PSBOVUxMKSkgewogICAgICAgIHJldHVybiBTTk1QRVJSX01BTExPQzsKICAgIH0KCiAgICBpZiAocGR1X2J1Zl9sZW4gPCBtc2dfbGVuCiAgICAgICAgJiYgcGR1LT5zZWN1cml0eUxldmVsID09IFNOTVBfU0VDX0xFVkVMX0FVVEhQUklWKSB7CiAgICAgICAgLyoKICAgICAgICAgKiBzcGFjZSBuZWVkZWQgaXMgbGFyZ2VyIHRoYW4gd2UgaGF2ZSBpbiB0aGUgZGVmYXVsdCBidWZmZXIgCiAgICAgICAgICovCiAgICAgICAgbWFsbG9jYnVmID0gKHVfY2hhciAqKSBjYWxsb2MoMSwgbXNnX2xlbik7CiAgICAgICAgcGR1X2J1Zl9sZW4gPSBtc2dfbGVuOwogICAgICAgIGNwID0gbWFsbG9jYnVmOwogICAgfSBlbHNlIHsKICAgICAgICBtZW1zZXQocGR1X2J1ZiwgMCwgcGR1X2J1Zl9sZW4pOwogICAgICAgIGNwID0gcGR1X2J1ZjsKICAgIH0KCiAgICBERUJVR0RVTVBTRUNUSU9OKCJyZWN2IiwgIlNNIG1zZ1NlY3VyaXR5UGFyYW1ldGVycyIpOwogICAgaWYgKHNwdHItPmRlY29kZSkgewogICAgICAgIHN0cnVjdCBzbm1wX3NlY21vZF9pbmNvbWluZ19wYXJhbXMgcGFybXM7CiAgICAgICAgcGFybXMubXNnUHJvY01vZGVsID0gcGR1LT5tc2dQYXJzZU1vZGVsOwogICAgICAgIHBhcm1zLm1heE1zZ1NpemUgPSBtc2dfbWF4X3NpemU7CiAgICAgICAgcGFybXMuc2VjUGFyYW1zID0gc2VjX3BhcmFtczsKICAgICAgICBwYXJtcy5zZWNNb2RlbCA9IG1zZ19zZWNfbW9kZWw7CiAgICAgICAgcGFybXMuc2VjTGV2ZWwgPSBwZHUtPnNlY3VyaXR5TGV2ZWw7CiAgICAgICAgcGFybXMud2hvbGVNc2cgPSBtc2dfZGF0YTsKICAgICAgICBwYXJtcy53aG9sZU1zZ0xlbiA9IG1zZ19sZW47CiAgICAgICAgcGFybXMuc2VjRW5naW5lSUQgPSBwZHUtPnNlY3VyaXR5RW5naW5lSUQ7CiAgICAgICAgcGFybXMuc2VjRW5naW5lSURMZW4gPSAmcGR1LT5zZWN1cml0eUVuZ2luZUlETGVuOwogICAgICAgIHBhcm1zLnNlY05hbWUgPSBwZHUtPnNlY3VyaXR5TmFtZTsKICAgICAgICBwYXJtcy5zZWNOYW1lTGVuID0gJnBkdS0+c2VjdXJpdHlOYW1lTGVuOwogICAgICAgIHBhcm1zLnNjb3BlZFBkdSA9ICZjcDsKICAgICAgICBwYXJtcy5zY29wZWRQZHVMZW4gPSAmcGR1X2J1Zl9sZW47CiAgICAgICAgcGFybXMubWF4U2l6ZVJlc3BvbnNlID0gJm1heF9zaXplX3Jlc3BvbnNlOwogICAgICAgIHBhcm1zLnNlY1N0YXRlUmVmID0gJnBkdS0+c2VjdXJpdHlTdGF0ZVJlZjsKICAgICAgICBwYXJtcy5zZXNzID0gc2VzczsKICAgICAgICBwYXJtcy5wZHUgPSBwZHU7CiAgICAgICAgcGFybXMubXNnX2ZsYWdzID0gbXNnX2ZsYWdzOwogICAgICAgIHJldF92YWwgPSAoKnNwdHItPmRlY29kZSkgKCZwYXJtcyk7CiAgICB9IGVsc2UgewogICAgICAgIFNOTVBfRlJFRShtYWxsb2NidWYpOwogICAgICAgIERFQlVHSU5ERU5UTEVTUygpOwogICAgICAgIHNubXBfbG9nKExPR19XQVJOSU5HLCAic2VjdXJpdHkgc2VydmljZSAlbGQgY2FuJ3QgZGVjb2RlIHBhY2tldHNcbiIsCiAgICAgICAgICAgICAgICAgbXNnX3NlY19tb2RlbCk7CiAgICAgICAgcmV0dXJuICgtMSk7CiAgICB9CgogICAgaWYgKHJldF92YWwgIT0gU05NUEVSUl9TVUNDRVNTKSB7CiAgICAgICAgREVCVUdEVU1QU0VDVElPTigicmVjdiIsICJTY29wZWRQRFUiKTsKICAgICAgICAvKgogICAgICAgICAqIFBhcnNlIGFzIG11Y2ggYXMgcG9zc2libGUgLS0gdGhvdWdoIEkgZG9uJ3Qgc2VlIHRoZSBwb2ludD8gW2picG5dLiAgCiAgICAgICAgICovCiAgICAgICAgaWYgKGNwKSB7CiAgICAgICAgICAgIGNwID0gc25tcHYzX3Njb3BlZFBEVV9wYXJzZShwZHUsIGNwLCAmcGR1X2J1Zl9sZW4pOwogICAgICAgIH0KICAgICAgICBpZiAoY3ApIHsKICAgICAgICAgICAgREVCVUdQUklOVFBEVVRZUEUoInJlY3YiLCAqY3ApOwogICAgICAgICAgICBzbm1wX3BkdV9wYXJzZShwZHUsIGNwLCAmcGR1X2J1Zl9sZW4pOwogICAgICAgICAgICBERUJVR0lOREVOVEFERCgtOCk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgREVCVUdJTkRFTlRBREQoLTQpOwogICAgICAgIH0KCiAgICAgICAgaWYgKG1hbGxvY2J1ZikgewogICAgICAgICAgICBTTk1QX0ZSRUUobWFsbG9jYnVmKTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIHJldF92YWw7CiAgICB9CgogICAgLyoKICAgICAqIHBhcnNlIHBsYWludGV4dCBTY29wZWRQRFUgc2VxdWVuY2UgCiAgICAgKi8KICAgICpsZW5ndGggPSBwZHVfYnVmX2xlbjsKICAgIERFQlVHRFVNUFNFQ1RJT04oInJlY3YiLCAiU2NvcGVkUERVIik7CiAgICBkYXRhID0gc25tcHYzX3Njb3BlZFBEVV9wYXJzZShwZHUsIGNwLCBsZW5ndGgpOwogICAgaWYgKGRhdGEgPT0gTlVMTCkgewogICAgICAgIHNubXBfaW5jcmVtZW50X3N0YXRpc3RpYyhTVEFUX1NOTVBJTkFTTlBBUlNFRVJSUyk7CiAgICAgICAgREVCVUdJTkRFTlRBREQoLTQpOwogICAgICAgIGlmIChtYWxsb2NidWYpIHsKICAgICAgICAgICAgU05NUF9GUkVFKG1hbGxvY2J1Zik7CiAgICAgICAgfQogICAgICAgIHJldHVybiBTTk1QRVJSX0FTTl9QQVJTRV9FUlI7CiAgICB9CgogICAgLyoKICAgICAqIHBhcnNlIHRoZSBQRFUuICAKICAgICAqLwogICAgaWYgKGFmdGVyX2hlYWRlciAhPSBOVUxMKSB7CiAgICAgICAgKmFmdGVyX2hlYWRlciA9IGRhdGE7CiAgICAgICAgdG1wX2J1Zl9sZW4gPSAqbGVuZ3RoOwogICAgfQoKICAgIERFQlVHUFJJTlRQRFVUWVBFKCJyZWN2IiwgKmRhdGEpOwogICAgcmV0ID0gc25tcF9wZHVfcGFyc2UocGR1LCBkYXRhLCBsZW5ndGgpOwogICAgREVCVUdJTkRFTlRBREQoLTgpOwoKICAgIGlmIChhZnRlcl9oZWFkZXIgIT0gTlVMTCkgewogICAgICAgICpsZW5ndGggPSB0bXBfYnVmX2xlbjsKICAgIH0KCiAgICBpZiAocmV0ICE9IFNOTVBFUlJfU1VDQ0VTUykgewogICAgICAgIEVSUk9SX01TRygiZXJyb3IgcGFyc2luZyBQRFUiKTsKICAgICAgICBzbm1wX2luY3JlbWVudF9zdGF0aXN0aWMoU1RBVF9TTk1QSU5BU05QQVJTRUVSUlMpOwogICAgICAgIGlmIChtYWxsb2NidWYpIHsKICAgICAgICAgICAgU05NUF9GUkVFKG1hbGxvY2J1Zik7CiAgICAgICAgfQogICAgICAgIHJldHVybiBTTk1QRVJSX0FTTl9QQVJTRV9FUlI7CiAgICB9CgogICAgaWYgKG1hbGxvY2J1ZikgewogICAgICAgIFNOTVBfRlJFRShtYWxsb2NidWYpOwogICAgfQogICAgcmV0dXJuIFNOTVBFUlJfU1VDQ0VTUzsKfSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAvKiBlbmQgc25tcHYzX3BhcnNlKCkgKi8KCiNkZWZpbmUgRVJST1JfU1RBVF9MRU5HVEggMTEKCmludApzbm1wdjNfbWFrZV9yZXBvcnQobmV0c25tcF9wZHUgKnBkdSwgaW50IGVycm9yKQp7CgogICAgbG9uZyAgICAgICAgICAgIGx0bXA7CiAgICBzdGF0aWMgb2lkICAgICAgdW5rbm93blNlY3VyaXR5TGV2ZWxbXSA9CiAgICAgICAgeyAxLCAzLCA2LCAxLCA2LCAzLCAxNSwgMSwgMSwgMSwgMCB9OwogICAgc3RhdGljIG9pZCAgICAgIG5vdEluVGltZVdpbmRvd1tdID0KICAgICAgICB7IDEsIDMsIDYsIDEsIDYsIDMsIDE1LCAxLCAxLCAyLCAwIH07CiAgICBzdGF0aWMgb2lkICAgICAgdW5rbm93blVzZXJOYW1lW10gPQogICAgICAgIHsgMSwgMywgNiwgMSwgNiwgMywgMTUsIDEsIDEsIDMsIDAgfTsKICAgIHN0YXRpYyBvaWQgICAgICB1bmtub3duRW5naW5lSURbXSA9CiAgICAgICAgeyAxLCAzLCA2LCAxLCA2LCAzLCAxNSwgMSwgMSwgNCwgMCB9OwogICAgc3RhdGljIG9pZCAgICAgIHdyb25nRGlnZXN0W10gPSB7IDEsIDMsIDYsIDEsIDYsIDMsIDE1LCAxLCAxLCA1LCAwIH07CiAgICBzdGF0aWMgb2lkICAgICAgZGVjcnlwdGlvbkVycm9yW10gPQogICAgICAgIHsgMSwgMywgNiwgMSwgNiwgMywgMTUsIDEsIDEsIDYsIDAgfTsKICAgIG9pZCAgICAgICAgICAgICplcnJfdmFyOwogICAgaW50ICAgICAgICAgICAgIGVycl92YXJfbGVuOwogICAgaW50ICAgICAgICAgICAgIHN0YXRfaW5kOwogICAgc3RydWN0IHNubXBfc2VjbW9kX2RlZiAqc3B0cjsKCiAgICBzd2l0Y2ggKGVycm9yKSB7CiAgICBjYXNlIFNOTVBFUlJfVVNNX1VOS05PV05FTkdJTkVJRDoKICAgICAgICBzdGF0X2luZCA9IFNUQVRfVVNNU1RBVFNVTktOT1dORU5HSU5FSURTOwogICAgICAgIGVycl92YXIgPSB1bmtub3duRW5naW5lSUQ7CiAgICAgICAgZXJyX3Zhcl9sZW4gPSBFUlJPUl9TVEFUX0xFTkdUSDsKICAgICAgICBicmVhazsKICAgIGNhc2UgU05NUEVSUl9VU01fVU5LTk9XTlNFQ1VSSVRZTkFNRToKICAgICAgICBzdGF0X2luZCA9IFNUQVRfVVNNU1RBVFNVTktOT1dOVVNFUk5BTUVTOwogICAgICAgIGVycl92YXIgPSB1bmtub3duVXNlck5hbWU7CiAgICAgICAgZXJyX3Zhcl9sZW4gPSBFUlJPUl9TVEFUX0xFTkdUSDsKICAgICAgICBicmVhazsKICAgIGNhc2UgU05NUEVSUl9VU01fVU5TVVBQT1JURURTRUNVUklUWUxFVkVMOgogICAgICAgIHN0YXRfaW5kID0gU1RBVF9VU01TVEFUU1VOU1VQUE9SVEVEU0VDTEVWRUxTOwogICAgICAgIGVycl92YXIgPSB1bmtub3duU2VjdXJpdHlMZXZlbDsKICAgICAgICBlcnJfdmFyX2xlbiA9IEVSUk9SX1NUQVRfTEVOR1RIOwogICAgICAgIGJyZWFrOwogICAgY2FzZSBTTk1QRVJSX1VTTV9BVVRIRU5USUNBVElPTkZBSUxVUkU6CiAgICAgICAgc3RhdF9pbmQgPSBTVEFUX1VTTVNUQVRTV1JPTkdESUdFU1RTOwogICAgICAgIGVycl92YXIgPSB3cm9uZ0RpZ2VzdDsKICAgICAgICBlcnJfdmFyX2xlbiA9IEVSUk9SX1NUQVRfTEVOR1RIOwogICAgICAgIGJyZWFrOwogICAgY2FzZSBTTk1QRVJSX1VTTV9OT1RJTlRJTUVXSU5ET1c6CiAgICAgICAgc3RhdF9pbmQgPSBTVEFUX1VTTVNUQVRTTk9USU5USU1FV0lORE9XUzsKICAgICAgICBlcnJfdmFyID0gbm90SW5UaW1lV2luZG93OwogICAgICAgIGVycl92YXJfbGVuID0gRVJST1JfU1RBVF9MRU5HVEg7CiAgICAgICAgYnJlYWs7CiAgICBjYXNlIFNOTVBFUlJfVVNNX0RFQ1JZUFRJT05FUlJPUjoKICAgICAgICBzdGF0X2luZCA9IFNUQVRfVVNNU1RBVFNERUNSWVBUSU9ORVJST1JTOwogICAgICAgIGVycl92YXIgPSBkZWNyeXB0aW9uRXJyb3I7CiAgICAgICAgZXJyX3Zhcl9sZW4gPSBFUlJPUl9TVEFUX0xFTkdUSDsKICAgICAgICBicmVhazsKICAgIGRlZmF1bHQ6CiAgICAgICAgcmV0dXJuIFNOTVBFUlJfR0VORVJSOwogICAgfQoKICAgIHNubXBfZnJlZV92YXJiaW5kKHBkdS0+dmFyaWFibGVzKTsgIC8qIGZyZWUgdGhlIGN1cnJlbnQgdmFyYmluZCAqLwoKICAgIHBkdS0+dmFyaWFibGVzID0gTlVMTDsKICAgIFNOTVBfRlJFRShwZHUtPnNlY3VyaXR5RW5naW5lSUQpOwogICAgcGR1LT5zZWN1cml0eUVuZ2luZUlEID0KICAgICAgICBzbm1wdjNfZ2VuZXJhdGVfZW5naW5lSUQoJnBkdS0+c2VjdXJpdHlFbmdpbmVJRExlbik7CiAgICBTTk1QX0ZSRUUocGR1LT5jb250ZXh0RW5naW5lSUQpOwogICAgcGR1LT5jb250ZXh0RW5naW5lSUQgPQogICAgICAgIHNubXB2M19nZW5lcmF0ZV9lbmdpbmVJRCgmcGR1LT5jb250ZXh0RW5naW5lSURMZW4pOwogICAgcGR1LT5jb21tYW5kID0gU05NUF9NU0dfUkVQT1JUOwogICAgcGR1LT5lcnJzdGF0ID0gMDsKICAgIHBkdS0+ZXJyaW5kZXggPSAwOwogICAgU05NUF9GUkVFKHBkdS0+Y29udGV4dE5hbWUpOwogICAgcGR1LT5jb250ZXh0TmFtZSA9IHN0cmR1cCgiIik7CiAgICBwZHUtPmNvbnRleHROYW1lTGVuID0gc3RybGVuKHBkdS0+Y29udGV4dE5hbWUpOwoKICAgIC8qCiAgICAgKiByZXBvcnRzIHNob3VsZG4ndCBjYWNoZSBwcmV2aW91cyBkYXRhLiAKICAgICAqLwogICAgLyoKICAgICAqIEZJWCAtIHllcyB0aGV5IHNob3VsZCBidXQgVVNNIG5lZWRzIHRvIGZvbGxvdyBuZXcgRW9QIHRvIGRldGVybWluZQogICAgICogd2hpY2ggY2FjaGVkIHZhbHVlcyB0byB1c2UgCiAgICAgKi8KICAgIGlmIChwZHUtPnNlY3VyaXR5U3RhdGVSZWYpIHsKICAgICAgICBzcHRyID0gZmluZF9zZWNfbW9kKHBkdS0+c2VjdXJpdHlNb2RlbCk7CiAgICAgICAgaWYgKHNwdHIpIHsKICAgICAgICAgICAgaWYgKHNwdHItPnBkdV9mcmVlX3N0YXRlX3JlZikgewogICAgICAgICAgICAgICAgKCpzcHRyLT5wZHVfZnJlZV9zdGF0ZV9yZWYpIChwZHUtPnNlY3VyaXR5U3RhdGVSZWYpOwogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgICAgc25tcF9sb2coTE9HX0VSUiwKICAgICAgICAgICAgICAgICAgICAgICAgICJTZWN1cml0eSBNb2RlbCAlZCBjYW4ndCBmcmVlIHN0YXRlIHJlZmVyZW5jZXNcbiIsCiAgICAgICAgICAgICAgICAgICAgICAgICBwZHUtPnNlY3VyaXR5TW9kZWwpOwogICAgICAgICAgICB9CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgc25tcF9sb2coTE9HX0VSUiwKICAgICAgICAgICAgICAgICAgICAgIkNhbid0IGZpbmQgc2VjdXJpdHkgbW9kZWwgdG8gZnJlZSBwdHI6ICVkXG4iLAogICAgICAgICAgICAgICAgICAgICBwZHUtPnNlY3VyaXR5TW9kZWwpOwogICAgICAgIH0KICAgICAgICBwZHUtPnNlY3VyaXR5U3RhdGVSZWYgPSBOVUxMOwogICAgfQoKICAgIGlmIChlcnJvciA9PSBTTk1QRVJSX1VTTV9OT1RJTlRJTUVXSU5ET1cpIHsKICAgICAgICBwZHUtPnNlY3VyaXR5TGV2ZWwgPSBTTk1QX1NFQ19MRVZFTF9BVVRITk9QUklWOwogICAgfSBlbHNlIHsKICAgICAgICBwZHUtPnNlY3VyaXR5TGV2ZWwgPSBTTk1QX1NFQ19MRVZFTF9OT0FVVEg7CiAgICB9CgogICAgLyoKICAgICAqIGZpbmQgdGhlIGFwcHJvcHJpYXRlIGVycm9yIGNvdW50ZXIgIAogICAgICovCiAgICBsdG1wID0gc25tcF9nZXRfc3RhdGlzdGljKHN0YXRfaW5kKTsKCiAgICAvKgogICAgICogcmV0dXJuIHRoZSBhcHByb3ByaWF0ZSBlcnJvciBjb3VudGVyICAKICAgICAqLwogICAgc25tcF9wZHVfYWRkX3ZhcmlhYmxlKHBkdSwgZXJyX3ZhciwgZXJyX3Zhcl9sZW4sCiAgICAgICAgICAgICAgICAgICAgICAgICAgQVNOX0NPVU5URVIsICh1X2NoYXIgKikgJiBsdG1wLCBzaXplb2YobHRtcCkpOwoKICAgIHJldHVybiBTTk1QRVJSX1NVQ0NFU1M7Cn0gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgLyogZW5kIHNubXB2M19tYWtlX3JlcG9ydCgpICovCgoKaW50CnNubXB2M19nZXRfcmVwb3J0X3R5cGUobmV0c25tcF9wZHUgKnBkdSkKewogICAgc3RhdGljIG9pZCAgICAgIHNubXBNUERTdGF0c1tdID0geyAxLCAzLCA2LCAxLCA2LCAzLCAxMSwgMiwgMSB9OwogICAgc3RhdGljIG9pZCAgICAgIHRhcmdldFN0YXRzW10gID0geyAxLCAzLCA2LCAxLCA2LCAzLCAxMiwgMSAgICB9OwogICAgc3RhdGljIG9pZCAgICAgIHVzbVN0YXRzW10gICAgID0geyAxLCAzLCA2LCAxLCA2LCAzLCAxNSwgMSwgMSB9OwogICAgbmV0c25tcF92YXJpYWJsZV9saXN0ICp2cDsKICAgIGludCAgICAgICAgICAgICBycHRfdHlwZSA9IFNOTVBFUlJfVU5LTk9XTl9SRVBPUlQ7CgogICAgaWYgKHBkdSA9PSBOVUxMIHx8IHBkdS0+dmFyaWFibGVzID09IE5VTEwpCiAgICAgICAgcmV0dXJuIHJwdF90eXBlOwogICAgdnAgPSBwZHUtPnZhcmlhYmxlczsKICAgIC8qIE1QRCBvciBVU00gYmFzZWQgcmVwb3J0IHN0YXRpc3RpY3Mgb2JqZWN0cyBoYXZlIHRoZSBzYW1lIGxlbmd0aCBwcmVmaXgKICAgICAqICAgc28gdGhlIGFjdHVhbCBzdGF0aXN0aWNzIE9JRCB3aWxsIGhhdmUgdGhpcyBsZW5ndGgsCiAgICAgKiAgIHBsdXMgb25lIHN1YmlkZW50aWZpZXIgZm9yIHRoZSBzY2FsYXIgTUlCIG9iamVjdCBpdHNlbGYsCiAgICAgKiAgIGFuZCBvbmUgZm9yIHRoZSBpbnN0YW5jZSBzdWJpZGVudGlmaWVyCiAgICAgKi8KICAgIGlmICh2cC0+bmFtZV9sZW5ndGggPT0gUkVQT1JUX1NUQVRTX0xFTiArIDIpIHsKICAgICAgICBpZiAobWVtY21wKHNubXBNUERTdGF0cywgdnAtPm5hbWUsIFJFUE9SVF9TVEFUU19MRU4gKiBzaXplb2Yob2lkKSkgPT0gMCkgewogICAgICAgICAgICBzd2l0Y2ggKHZwLT5uYW1lW1JFUE9SVF9TVEFUU19MRU5dKSB7CiAgICAgICAgICAgIGNhc2UgUkVQT1JUX3NubXBVbmtub3duU2VjdXJpdHlNb2RlbHNfTlVNOgogICAgICAgICAgICAgICAgcnB0X3R5cGUgPSBTTk1QRVJSX1VOS05PV05fU0VDX01PREVMOwogICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIGNhc2UgUkVQT1JUX3NubXBJbnZhbGlkTXNnc19OVU06CiAgICAgICAgICAgICAgICBycHRfdHlwZSA9IFNOTVBFUlJfSU5WQUxJRF9NU0c7CiAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgY2FzZSBSRVBPUlRfc25tcFVua25vd25QRFVIYW5kbGVyc19OVU06CiAgICAgICAgICAgICAgICBycHRfdHlwZSA9IFNOTVBFUlJfQkFEX1ZFUlNJT047CiAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgIH0gZWxzZSBpZiAobWVtY21wKHVzbVN0YXRzLCB2cC0+bmFtZSwgUkVQT1JUX1NUQVRTX0xFTiAqIHNpemVvZihvaWQpKSA9PSAwKSB7CiAgICAgICAgICAgIHN3aXRjaCAodnAtPm5hbWVbUkVQT1JUX1NUQVRTX0xFTl0pIHsKICAgICAgICAgICAgY2FzZSBSRVBPUlRfdXNtU3RhdHNVbnN1cHBvcnRlZFNlY0xldmVsc19OVU06CiAgICAgICAgICAgICAgICBycHRfdHlwZSA9IFNOTVBFUlJfVU5TVVBQT1JURURfU0VDX0xFVkVMOwogICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIGNhc2UgUkVQT1JUX3VzbVN0YXRzTm90SW5UaW1lV2luZG93c19OVU06CiAgICAgICAgICAgICAgICBycHRfdHlwZSA9IFNOTVBFUlJfTk9UX0lOX1RJTUVfV0lORE9XOwogICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIGNhc2UgUkVQT1JUX3VzbVN0YXRzVW5rbm93blVzZXJOYW1lc19OVU06CiAgICAgICAgICAgICAgICBycHRfdHlwZSA9IFNOTVBFUlJfVU5LTk9XTl9VU0VSX05BTUU7CiAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgY2FzZSBSRVBPUlRfdXNtU3RhdHNVbmtub3duRW5naW5lSURzX05VTToKICAgICAgICAgICAgICAgIHJwdF90eXBlID0gU05NUEVSUl9VTktOT1dOX0VOR19JRDsKICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICBjYXNlIFJFUE9SVF91c21TdGF0c1dyb25nRGlnZXN0c19OVU06CiAgICAgICAgICAgICAgICBycHRfdHlwZSA9IFNOTVBFUlJfQVVUSEVOVElDQVRJT05fRkFJTFVSRTsKICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICBjYXNlIFJFUE9SVF91c21TdGF0c0RlY3J5cHRpb25FcnJvcnNfTlVNOgogICAgICAgICAgICAgICAgcnB0X3R5cGUgPSBTTk1QRVJSX0RFQ1JZUFRJT05fRVJSOwogICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICB9CiAgICAvKiBDb250ZXh0LWJhc2VkIHJlcG9ydCBzdGF0aXN0aWNzIGZyb20gdGhlIFRhcmdldCBNSUIgYXJlIHNpbWlsYXIKICAgICAqICAgYnV0IHRoZSBPSUQgcHJlZml4IGhhcyBhIGRpZmZlcmVudCBsZW5ndGgKICAgICAqLwogICAgaWYgKHZwLT5uYW1lX2xlbmd0aCA9PSBSRVBPUlRfU1RBVFNfTEVOMiArIDIpIHsKICAgICAgICBpZiAobWVtY21wKHRhcmdldFN0YXRzLCB2cC0+bmFtZSwgUkVQT1JUX1NUQVRTX0xFTjIgKiBzaXplb2Yob2lkKSkgPT0gMCkgewogICAgICAgICAgICBzd2l0Y2ggKHZwLT5uYW1lW1JFUE9SVF9TVEFUU19MRU4yXSkgewogICAgICAgICAgICBjYXNlIFJFUE9SVF9zbm1wVW5hdmFpbGFibGVDb250ZXh0c19OVU06CiAgICAgICAgICAgICAgICBycHRfdHlwZSA9IFNOTVBFUlJfQkFEX0NPTlRFWFQ7CiAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgY2FzZSBSRVBPUlRfc25tcFVua25vd25Db250ZXh0c19OVU06CiAgICAgICAgICAgICAgICBycHRfdHlwZSA9IFNOTVBFUlJfQkFEX0NPTlRFWFQ7CiAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgIH0KICAgIERFQlVHTVNHVEwoKCJyZXBvcnQiLCAiUmVwb3J0IHR5cGU6ICVkXG4iLCBycHRfdHlwZSkpOwogICAgcmV0dXJuIHJwdF90eXBlOwp9CgovKgogKiBQYXJzZXMgdGhlIHBhY2tldCByZWNlaXZlZCBvbiB0aGUgaW5wdXQgc2Vzc2lvbiwgYW5kIHBsYWNlcyB0aGUgZGF0YSBpbnRvCiAqIHRoZSBpbnB1dCBwZHUuICBsZW5ndGggaXMgdGhlIGxlbmd0aCBvZiB0aGUgaW5wdXQgcGFja2V0LgogKiBJZiBhbnkgZXJyb3JzIGFyZSBlbmNvdW50ZXJlZCwgLTEgb3IgVVNNIGVycm9yIGlzIHJldHVybmVkLgogKiBPdGhlcndpc2UsIGEgMCBpcyByZXR1cm5lZC4KICovCnN0YXRpYyBpbnQKX3NubXBfcGFyc2Uodm9pZCAqc2Vzc3AsCiAgICAgICAgICAgIG5ldHNubXBfc2Vzc2lvbiAqIHNlc3Npb24sCiAgICAgICAgICAgIG5ldHNubXBfcGR1ICpwZHUsIHVfY2hhciAqIGRhdGEsIHNpemVfdCBsZW5ndGgpCnsKI2lmICFkZWZpbmVkKE5FVFNOTVBfRElTQUJMRV9TTk1QVjEpIHx8ICFkZWZpbmVkKE5FVFNOTVBfRElTQUJMRV9TTk1QVjJDKQogICAgdV9jaGFyICAgICAgICAgIGNvbW11bml0eVtDT01NVU5JVFlfTUFYX0xFTl07CiAgICBzaXplX3QgICAgICAgICAgY29tbXVuaXR5X2xlbmd0aCA9IENPTU1VTklUWV9NQVhfTEVOOwojZW5kaWYKICAgIGludCAgICAgICAgICAgICByZXN1bHQgPSAtMTsKCiAgICBzZXNzaW9uLT5zX3NubXBfZXJybm8gPSAwOwogICAgc2Vzc2lvbi0+c19lcnJubyA9IDA7CgogICAgLyoKICAgICAqIEVuc3VyZSBhbGwgaW5jb21pbmcgUERVcyBoYXZlIGEgdW5pcXVlIG1lYW5zIG9mIGlkZW50aWZpY2F0aW9uIAogICAgICogKFRoaXMgaXMgbm90IHJlc3RyaWN0ZWQgdG8gQWdlbnRYIGhhbmRsaW5nLAogICAgICogdGhvdWdoIHRoYXQgaXMgd2hlcmUgdGhlIG5lZWQgYmVjb21lcyB2aXNpYmxlKSAgIAogICAgICovCiAgICBwZHUtPnRyYW5zaWQgPSBzbm1wX2dldF9uZXh0X3RyYW5zaWQoKTsKCiAgICBpZiAoc2Vzc2lvbi0+dmVyc2lvbiAhPSBTTk1QX0RFRkFVTFRfVkVSU0lPTikgewogICAgICAgIHBkdS0+dmVyc2lvbiA9IHNlc3Npb24tPnZlcnNpb247CiAgICB9IGVsc2UgewogICAgICAgIHBkdS0+dmVyc2lvbiA9IHNubXBfcGFyc2VfdmVyc2lvbihkYXRhLCBsZW5ndGgpOwogICAgfQoKICAgIHN3aXRjaCAocGR1LT52ZXJzaW9uKSB7CiNpZm5kZWYgTkVUU05NUF9ESVNBQkxFX1NOTVBWMQogICAgY2FzZSBTTk1QX1ZFUlNJT05fMToKI2VuZGlmCiNpZm5kZWYgTkVUU05NUF9ESVNBQkxFX1NOTVBWMkMKICAgIGNhc2UgU05NUF9WRVJTSU9OXzJjOgojZW5kaWYKI2lmICFkZWZpbmVkKE5FVFNOTVBfRElTQUJMRV9TTk1QVjEpIHx8ICFkZWZpbmVkKE5FVFNOTVBfRElTQUJMRV9TTk1QVjJDKQogICAgICAgIERFQlVHTVNHVEwoKCJzbm1wX2FwaSIsICJQYXJzaW5nIFNOTVB2JWQgbWVzc2FnZS4uLlxuIiwKICAgICAgICAgICAgICAgICAgICAoMSArIHBkdS0+dmVyc2lvbikpKTsKCiAgICAgICAgLyoKICAgICAgICAgKiBhdXRoZW50aWNhdGVzIG1lc3NhZ2UgYW5kIHJldHVybnMgbGVuZ3RoIGlmIHZhbGlkIAogICAgICAgICAqLwojaWZuZGVmIE5FVFNOTVBfRElTQUJMRV9TTk1QVjEKICAgICAgICBpZiAocGR1LT52ZXJzaW9uID09IFNOTVBfVkVSU0lPTl8xKSB7CiAgICAgICAgICAgIERFQlVHRFVNUFNFQ1RJT04oInJlY3YiLCAiU05NUHYxIG1lc3NhZ2VcbiIpOwogICAgICAgIH0gZWxzZSB7CiNlbmRpZgogICAgICAgICAgICBERUJVR0RVTVBTRUNUSU9OKCJyZWN2IiwgIlNOTVB2MmMgbWVzc2FnZVxuIik7CiNpZm5kZWYgTkVUU05NUF9ESVNBQkxFX1NOTVBWMQogICAgICAgIH0KI2VuZGlmCiAgICAgICAgZGF0YSA9IHNubXBfY29tc3RyX3BhcnNlKGRhdGEsICZsZW5ndGgsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNvbW11bml0eSwgJmNvbW11bml0eV9sZW5ndGgsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICZwZHUtPnZlcnNpb24pOwogICAgICAgIGlmIChkYXRhID09IE5VTEwpCiAgICAgICAgICAgIHJldHVybiAtMTsKCiAgICAgICAgaWYgKHBkdS0+dmVyc2lvbiAhPSBzZXNzaW9uLT52ZXJzaW9uICYmCiAgICAgICAgICAgIHNlc3Npb24tPnZlcnNpb24gIT0gU05NUF9ERUZBVUxUX1ZFUlNJT04pIHsKICAgICAgICAgICAgc2Vzc2lvbi0+c19zbm1wX2Vycm5vID0gU05NUEVSUl9CQURfVkVSU0lPTjsKICAgICAgICAgICAgcmV0dXJuIC0xOwogICAgICAgIH0KCiAgICAgICAgLyoKICAgICAgICAgKiBtYXliZSBnZXQgdGhlIGNvbW11bml0eSBzdHJpbmcuIAogICAgICAgICAqLwogICAgICAgIHBkdS0+c2VjdXJpdHlMZXZlbCA9IFNOTVBfU0VDX0xFVkVMX05PQVVUSDsKICAgICAgICBwZHUtPnNlY3VyaXR5TW9kZWwgPSAKI2lmbmRlZiBORVRTTk1QX0RJU0FCTEVfU05NUFYxCiAgICAgICAgICAgIChwZHUtPnZlcnNpb24gPT0gU05NUF9WRVJTSU9OXzEpID8gU05NUF9TRUNfTU9ERUxfU05NUHYxIDogCiNlbmRpZgogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFNOTVBfU0VDX01PREVMX1NOTVB2MmM7CiAgICAgICAgU05NUF9GUkVFKHBkdS0+Y29tbXVuaXR5KTsKICAgICAgICBwZHUtPmNvbW11bml0eV9sZW4gPSAwOwogICAgICAgIHBkdS0+Y29tbXVuaXR5ID0gKHVfY2hhciAqKSAwOwogICAgICAgIGlmIChjb21tdW5pdHlfbGVuZ3RoKSB7CiAgICAgICAgICAgIHBkdS0+Y29tbXVuaXR5X2xlbiA9IGNvbW11bml0eV9sZW5ndGg7CiAgICAgICAgICAgIHBkdS0+Y29tbXVuaXR5ID0gKHVfY2hhciAqKSBtYWxsb2MoY29tbXVuaXR5X2xlbmd0aCk7CiAgICAgICAgICAgIGlmIChwZHUtPmNvbW11bml0eSA9PSBOVUxMKSB7CiAgICAgICAgICAgICAgICBzZXNzaW9uLT5zX3NubXBfZXJybm8gPSBTTk1QRVJSX01BTExPQzsKICAgICAgICAgICAgICAgIHJldHVybiAtMTsKICAgICAgICAgICAgfQogICAgICAgICAgICBtZW1tb3ZlKHBkdS0+Y29tbXVuaXR5LCBjb21tdW5pdHksIGNvbW11bml0eV9sZW5ndGgpOwogICAgICAgIH0KICAgICAgICBpZiAoc2Vzc2lvbi0+YXV0aGVudGljYXRvcikgewogICAgICAgICAgICBkYXRhID0gc2Vzc2lvbi0+YXV0aGVudGljYXRvcihkYXRhLCAmbGVuZ3RoLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBjb21tdW5pdHksIGNvbW11bml0eV9sZW5ndGgpOwogICAgICAgICAgICBpZiAoZGF0YSA9PSBOVUxMKSB7CiAgICAgICAgICAgICAgICBzZXNzaW9uLT5zX3NubXBfZXJybm8gPSBTTk1QRVJSX0FVVEhFTlRJQ0FUSU9OX0ZBSUxVUkU7CiAgICAgICAgICAgICAgICByZXR1cm4gLTE7CiAgICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIERFQlVHRFVNUFNFQ1RJT04oInJlY3YiLCAiUERVIik7CiAgICAgICAgcmVzdWx0ID0gc25tcF9wZHVfcGFyc2UocGR1LCBkYXRhLCAmbGVuZ3RoKTsKICAgICAgICBpZiAocmVzdWx0IDwgMCkgewogICAgICAgICAgICAvKgogICAgICAgICAgICAgKiBUaGlzIGluZGljYXRlcyBhIHBhcnNlIGVycm9yLiAgCiAgICAgICAgICAgICAqLwogICAgICAgICAgICBzbm1wX2luY3JlbWVudF9zdGF0aXN0aWMoU1RBVF9TTk1QSU5BU05QQVJTRUVSUlMpOwogICAgICAgIH0KICAgICAgICBERUJVR0lOREVOVEFERCgtNik7CiAgICAgICAgYnJlYWs7CiNlbmRpZiAvKiBzdXBwb3J0IGZvciBjb21tdW5pdHkgYmFzZWQgU05NUCAqLwoKICAgIGNhc2UgU05NUF9WRVJTSU9OXzM6CiAgICAgICAgcmVzdWx0ID0gc25tcHYzX3BhcnNlKHBkdSwgZGF0YSwgJmxlbmd0aCwgTlVMTCwgc2Vzc2lvbik7CiAgICAgICAgREVCVUdNU0dUTCgoInNubXBfcGFyc2UiLAogICAgICAgICAgICAgICAgICAgICJQYXJzZWQgU05NUHYzIG1lc3NhZ2UgKHNlY05hbWU6JXMsIHNlY0xldmVsOiVzKTogJXNcbiIsCiAgICAgICAgICAgICAgICAgICAgcGR1LT5zZWN1cml0eU5hbWUsIHNlY0xldmVsTmFtZVtwZHUtPnNlY3VyaXR5TGV2ZWxdLAogICAgICAgICAgICAgICAgICAgIHNubXBfYXBpX2VycnN0cmluZyhyZXN1bHQpKSk7CgogICAgICAgIGlmIChyZXN1bHQpIHsKICAgICAgICAgICAgc3RydWN0IHNubXBfc2VjbW9kX2RlZiAqc2VjbW9kID0KICAgICAgICAgICAgICAgIGZpbmRfc2VjX21vZChwZHUtPnNlY3VyaXR5TW9kZWwpOwogICAgICAgICAgICBpZiAoIXNlc3NwKSB7CiAgICAgICAgICAgICAgICBzZXNzaW9uLT5zX3NubXBfZXJybm8gPSByZXN1bHQ7CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICAvKgogICAgICAgICAgICAgICAgICogQ2FsbCB0aGUgc2VjdXJpdHkgbW9kZWwgdG8gc3BlY2lhbCBoYW5kbGUgYW55IGVycm9ycwogICAgICAgICAgICAgICAgICovCgogICAgICAgICAgICAgICAgaWYgKHNlY21vZCAmJiBzZWNtb2QtPmhhbmRsZV9yZXBvcnQpIHsKICAgICAgICAgICAgICAgICAgICBzdHJ1Y3Qgc2Vzc2lvbl9saXN0ICpzbHAgPSAoc3RydWN0IHNlc3Npb25fbGlzdCAqKSBzZXNzcDsKICAgICAgICAgICAgICAgICAgICAoKnNlY21vZC0+aGFuZGxlX3JlcG9ydCkoc2Vzc3AsIHNscC0+dHJhbnNwb3J0LCBzZXNzaW9uLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICByZXN1bHQsIHBkdSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHBkdS0+c2VjdXJpdHlTdGF0ZVJlZiAhPSBOVUxMKSB7CiAgICAgICAgICAgICAgICBpZiAoc2VjbW9kICYmIHNlY21vZC0+cGR1X2ZyZWVfc3RhdGVfcmVmKSB7CiAgICAgICAgICAgICAgICAgICAgc2VjbW9kLT5wZHVfZnJlZV9zdGF0ZV9yZWYocGR1LT5zZWN1cml0eVN0YXRlUmVmKTsKICAgICAgICAgICAgICAgICAgICBwZHUtPnNlY3VyaXR5U3RhdGVSZWYgPSBOVUxMOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIGJyZWFrOwogICAgY2FzZSBTTk1QRVJSX0JBRF9WRVJTSU9OOgogICAgICAgIEVSUk9SX01TRygiZXJyb3IgcGFyc2luZyBzbm1wIG1lc3NhZ2UgdmVyc2lvbiIpOwogICAgICAgIHNubXBfaW5jcmVtZW50X3N0YXRpc3RpYyhTVEFUX1NOTVBJTkFTTlBBUlNFRVJSUyk7CiAgICAgICAgc2Vzc2lvbi0+c19zbm1wX2Vycm5vID0gU05NUEVSUl9CQURfVkVSU0lPTjsKICAgICAgICBicmVhazsKICAgIGNhc2UgU05NUF9WRVJTSU9OX3NlYzoKICAgIGNhc2UgU05NUF9WRVJTSU9OXzJ1OgogICAgY2FzZSBTTk1QX1ZFUlNJT05fMnN0YXI6CiAgICBjYXNlIFNOTVBfVkVSU0lPTl8ycDoKICAgIGRlZmF1bHQ6CiAgICAgICAgRVJST1JfTVNHKCJ1bnN1cHBvcnRlZCBzbm1wIG1lc3NhZ2UgdmVyc2lvbiIpOwogICAgICAgIHNubXBfaW5jcmVtZW50X3N0YXRpc3RpYyhTVEFUX1NOTVBJTkJBRFZFUlNJT05TKTsKCiAgICAgICAgLyoKICAgICAgICAgKiBuZWVkIGJldHRlciB3YXkgdG8gZGV0ZXJtaW5lIE9TIGluZGVwZW5kZW50CiAgICAgICAgICogSU5UMzJfTUFYIHZhbHVlLCBmb3Igbm93IGhhcmRjb2RlCiAgICAgICAgICovCiAgICAgICAgaWYgKHBkdS0+dmVyc2lvbiA8IDAgfHwgcGR1LT52ZXJzaW9uID4gMjE0NzQ4MzY0NykgewogICAgICAgICAgICBzbm1wX2luY3JlbWVudF9zdGF0aXN0aWMoU1RBVF9TTk1QSU5BU05QQVJTRUVSUlMpOwogICAgICAgIH0KICAgICAgICBzZXNzaW9uLT5zX3NubXBfZXJybm8gPSBTTk1QRVJSX0JBRF9WRVJTSU9OOwogICAgICAgIGJyZWFrOwogICAgfQoKICAgIHJldHVybiByZXN1bHQ7Cn0KCnN0YXRpYyBpbnQKc25tcF9wYXJzZSh2b2lkICpzZXNzcCwKICAgICAgICAgICBuZXRzbm1wX3Nlc3Npb24gKiBwc3MsCiAgICAgICAgICAgbmV0c25tcF9wZHUgKnBkdSwgdV9jaGFyICogZGF0YSwgc2l6ZV90IGxlbmd0aCkKewogICAgaW50ICAgICAgICAgICAgIHJjOwoKICAgIHJjID0gX3NubXBfcGFyc2Uoc2Vzc3AsIHBzcywgcGR1LCBkYXRhLCBsZW5ndGgpOwogICAgaWYgKHJjKSB7CiAgICAgICAgaWYgKCFwc3MtPnNfc25tcF9lcnJubykgewogICAgICAgICAgICBwc3MtPnNfc25tcF9lcnJubyA9IFNOTVBFUlJfQkFEX1BBUlNFOwogICAgICAgIH0KICAgICAgICBTRVRfU05NUF9FUlJPUihwc3MtPnNfc25tcF9lcnJubyk7CiAgICB9CgogICAgcmV0dXJuIHJjOwp9CgppbnQKc25tcF9wZHVfcGFyc2UobmV0c25tcF9wZHUgKnBkdSwgdV9jaGFyICogZGF0YSwgc2l6ZV90ICogbGVuZ3RoKQp7CiAgICB1X2NoYXIgICAgICAgICAgdHlwZTsKICAgIHVfY2hhciAgICAgICAgICBtc2dfdHlwZTsKICAgIHVfY2hhciAgICAgICAgICp2YXJfdmFsOwogICAgaW50ICAgICAgICAgICAgIGJhZHR5cGUgPSAwOwogICAgc2l6ZV90ICAgICAgICAgIGxlbjsKICAgIHNpemVfdCAgICAgICAgICBmb3VyOwogICAgbmV0c25tcF92YXJpYWJsZV9saXN0ICp2cCA9IE5VTEw7CiAgICBvaWQgICAgICAgICAgICAgb2JqaWRbTUFYX09JRF9MRU5dOwoKICAgIC8qCiAgICAgKiBHZXQgdGhlIFBEVSB0eXBlIAogICAgICovCiAgICBkYXRhID0gYXNuX3BhcnNlX2hlYWRlcihkYXRhLCBsZW5ndGgsICZtc2dfdHlwZSk7CiAgICBpZiAoZGF0YSA9PSBOVUxMKQogICAgICAgIHJldHVybiAtMTsKICAgIERFQlVHTVNHVEwoKCJkdW1wdl9yZWN2IiwiICAgIENvbW1hbmQgJXNcbiIsIHNubXBfcGR1X3R5cGUobXNnX3R5cGUpKSk7CiAgICBwZHUtPmNvbW1hbmQgPSBtc2dfdHlwZTsKICAgIHBkdS0+ZmxhZ3MgJj0gKH5VQ0RfTVNHX0ZMQUdfUkVTUE9OU0VfUERVKTsKCiAgICAvKgogICAgICogZ2V0IHRoZSBmaWVsZHMgaW4gdGhlIFBEVSBwcmVjZWVkaW5nIHRoZSB2YXJpYWJsZS1iaW5kaW5ncyBzZXF1ZW5jZSAKICAgICAqLwogICAgc3dpdGNoIChwZHUtPmNvbW1hbmQpIHsKICAgIGNhc2UgU05NUF9NU0dfVFJBUDoKICAgICAgICAvKgogICAgICAgICAqIGVudGVycHJpc2UgCiAgICAgICAgICovCiAgICAgICAgcGR1LT5lbnRlcnByaXNlX2xlbmd0aCA9IE1BWF9PSURfTEVOOwogICAgICAgIGRhdGEgPSBhc25fcGFyc2Vfb2JqaWQoZGF0YSwgbGVuZ3RoLCAmdHlwZSwgb2JqaWQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmcGR1LT5lbnRlcnByaXNlX2xlbmd0aCk7CiAgICAgICAgaWYgKGRhdGEgPT0gTlVMTCkKICAgICAgICAgICAgcmV0dXJuIC0xOwogICAgICAgIHBkdS0+ZW50ZXJwcmlzZSA9CiAgICAgICAgICAgIChvaWQgKikgbWFsbG9jKHBkdS0+ZW50ZXJwcmlzZV9sZW5ndGggKiBzaXplb2Yob2lkKSk7CiAgICAgICAgaWYgKHBkdS0+ZW50ZXJwcmlzZSA9PSBOVUxMKSB7CiAgICAgICAgICAgIHJldHVybiAtMTsKICAgICAgICB9CiAgICAgICAgbWVtbW92ZShwZHUtPmVudGVycHJpc2UsIG9iamlkLAogICAgICAgICAgICAgICAgcGR1LT5lbnRlcnByaXNlX2xlbmd0aCAqIHNpemVvZihvaWQpKTsKCiAgICAgICAgLyoKICAgICAgICAgKiBhZ2VudC1hZGRyIAogICAgICAgICAqLwogICAgICAgIGZvdXIgPSA0OwogICAgICAgIGRhdGEgPSBhc25fcGFyc2Vfc3RyaW5nKGRhdGEsIGxlbmd0aCwgJnR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKHVfY2hhciAqKSBwZHUtPmFnZW50X2FkZHIsICZmb3VyKTsKICAgICAgICBpZiAoZGF0YSA9PSBOVUxMKQogICAgICAgICAgICByZXR1cm4gLTE7CgogICAgICAgIC8qCiAgICAgICAgICogZ2VuZXJpYyB0cmFwIAogICAgICAgICAqLwogICAgICAgIGRhdGEgPSBhc25fcGFyc2VfaW50KGRhdGEsIGxlbmd0aCwgJnR5cGUsIChsb25nICopICZwZHUtPnRyYXBfdHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzaXplb2YocGR1LT50cmFwX3R5cGUpKTsKICAgICAgICBpZiAoZGF0YSA9PSBOVUxMKQogICAgICAgICAgICByZXR1cm4gLTE7CiAgICAgICAgLyoKICAgICAgICAgKiBzcGVjaWZpYyB0cmFwIAogICAgICAgICAqLwogICAgICAgIGRhdGEgPQogICAgICAgICAgICBhc25fcGFyc2VfaW50KGRhdGEsIGxlbmd0aCwgJnR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgKGxvbmcgKikgJnBkdS0+c3BlY2lmaWNfdHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICBzaXplb2YocGR1LT5zcGVjaWZpY190eXBlKSk7CiAgICAgICAgaWYgKGRhdGEgPT0gTlVMTCkKICAgICAgICAgICAgcmV0dXJuIC0xOwoKICAgICAgICAvKgogICAgICAgICAqIHRpbWVzdGFtcCAgCiAgICAgICAgICovCiAgICAgICAgZGF0YSA9IGFzbl9wYXJzZV91bnNpZ25lZF9pbnQoZGF0YSwgbGVuZ3RoLCAmdHlwZSwgJnBkdS0+dGltZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzaXplb2YocGR1LT50aW1lKSk7CiAgICAgICAgaWYgKGRhdGEgPT0gTlVMTCkKICAgICAgICAgICAgcmV0dXJuIC0xOwoKICAgICAgICBicmVhazsKCiAgICBjYXNlIFNOTVBfTVNHX1JFU1BPTlNFOgogICAgY2FzZSBTTk1QX01TR19SRVBPUlQ6CiAgICAgICAgcGR1LT5mbGFncyB8PSBVQ0RfTVNHX0ZMQUdfUkVTUE9OU0VfUERVOwogICAgICAgIC8qCiAgICAgICAgICogZmFsbHRocm91Z2ggCiAgICAgICAgICovCgogICAgY2FzZSBTTk1QX01TR19HRVQ6CiAgICBjYXNlIFNOTVBfTVNHX0dFVE5FWFQ6CiAgICBjYXNlIFNOTVBfTVNHX0dFVEJVTEs6CiAgICBjYXNlIFNOTVBfTVNHX1RSQVAyOgogICAgY2FzZSBTTk1QX01TR19JTkZPUk06CiAgICBjYXNlIFNOTVBfTVNHX1NFVDoKICAgICAgICAvKgogICAgICAgICAqIFBEVSBpcyBub3QgYW4gU05NUHYxIFRSQVAgCiAgICAgICAgICovCgogICAgICAgIC8qCiAgICAgICAgICogcmVxdWVzdCBpZCAKICAgICAgICAgKi8KICAgICAgICBERUJVR0RVTVBIRUFERVIoInJlY3YiLCAicmVxdWVzdF9pZCIpOwogICAgICAgIGRhdGEgPSBhc25fcGFyc2VfaW50KGRhdGEsIGxlbmd0aCwgJnR5cGUsICZwZHUtPnJlcWlkLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNpemVvZihwZHUtPnJlcWlkKSk7CiAgICAgICAgREVCVUdJTkRFTlRMRVNTKCk7CiAgICAgICAgaWYgKGRhdGEgPT0gTlVMTCkgewogICAgICAgICAgICByZXR1cm4gLTE7CiAgICAgICAgfQoKICAgICAgICAvKgogICAgICAgICAqIGVycm9yIHN0YXR1cyAoZ2V0YnVsayBub24tcmVwZWF0ZXJzKSAKICAgICAgICAgKi8KICAgICAgICBERUJVR0RVTVBIRUFERVIoInJlY3YiLCAiZXJyb3Igc3RhdHVzIik7CiAgICAgICAgZGF0YSA9IGFzbl9wYXJzZV9pbnQoZGF0YSwgbGVuZ3RoLCAmdHlwZSwgJnBkdS0+ZXJyc3RhdCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzaXplb2YocGR1LT5lcnJzdGF0KSk7CiAgICAgICAgREVCVUdJTkRFTlRMRVNTKCk7CiAgICAgICAgaWYgKGRhdGEgPT0gTlVMTCkgewogICAgICAgICAgICByZXR1cm4gLTE7CiAgICAgICAgfQoKICAgICAgICAvKgogICAgICAgICAqIGVycm9yIGluZGV4IChnZXRidWxrIG1heC1yZXBldGl0aW9ucykgCiAgICAgICAgICovCiAgICAgICAgREVCVUdEVU1QSEVBREVSKCJyZWN2IiwgImVycm9yIGluZGV4Iik7CiAgICAgICAgZGF0YSA9IGFzbl9wYXJzZV9pbnQoZGF0YSwgbGVuZ3RoLCAmdHlwZSwgJnBkdS0+ZXJyaW5kZXgsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2l6ZW9mKHBkdS0+ZXJyaW5kZXgpKTsKICAgICAgICBERUJVR0lOREVOVExFU1MoKTsKICAgICAgICBpZiAoZGF0YSA9PSBOVUxMKSB7CiAgICAgICAgICAgIHJldHVybiAtMTsKICAgICAgICB9CglicmVhazsKCiAgICBkZWZhdWx0OgogICAgICAgIHNubXBfbG9nKExPR19FUlIsICJCYWQgUERVIHR5cGUgcmVjZWl2ZWQ6IDB4JS4yeFxuIiwgcGR1LT5jb21tYW5kKTsKICAgICAgICBzbm1wX2luY3JlbWVudF9zdGF0aXN0aWMoU1RBVF9TTk1QSU5BU05QQVJTRUVSUlMpOwogICAgICAgIHJldHVybiAtMTsKICAgIH0KCiAgICAvKgogICAgICogZ2V0IGhlYWRlciBmb3IgdmFyaWFibGUtYmluZGluZ3Mgc2VxdWVuY2UgCiAgICAgKi8KICAgIERFQlVHRFVNUFNFQ1RJT04oInJlY3YiLCAiVmFyQmluZExpc3QiKTsKICAgIGRhdGEgPSBhc25fcGFyc2Vfc2VxdWVuY2UoZGF0YSwgbGVuZ3RoLCAmdHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKEFTTl9TRVFVRU5DRSB8IEFTTl9DT05TVFJVQ1RPUiksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICJ2YXJiaW5kcyIpOwogICAgaWYgKGRhdGEgPT0gTlVMTCkKICAgICAgICByZXR1cm4gLTE7CgogICAgLyoKICAgICAqIGdldCBlYWNoIHZhckJpbmQgc2VxdWVuY2UgCiAgICAgKi8KICAgIHdoaWxlICgoaW50KSAqbGVuZ3RoID4gMCkgewogICAgICAgIG5ldHNubXBfdmFyaWFibGVfbGlzdCAqdnB0ZW1wOwogICAgICAgIHZwdGVtcCA9IChuZXRzbm1wX3ZhcmlhYmxlX2xpc3QgKikgbWFsbG9jKHNpemVvZigqdnB0ZW1wKSk7CiAgICAgICAgaWYgKDAgPT0gdnB0ZW1wKSB7CiAgICAgICAgICAgIHJldHVybiAtMTsKICAgICAgICB9CiAgICAgICAgaWYgKDAgPT0gdnApIHsKICAgICAgICAgICAgcGR1LT52YXJpYWJsZXMgPSB2cHRlbXA7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgdnAtPm5leHRfdmFyaWFibGUgPSB2cHRlbXA7CiAgICAgICAgfQogICAgICAgIHZwID0gdnB0ZW1wOwoKICAgICAgICB2cC0+bmV4dF92YXJpYWJsZSA9IE5VTEw7CiAgICAgICAgdnAtPnZhbC5zdHJpbmcgPSBOVUxMOwogICAgICAgIHZwLT5uYW1lX2xlbmd0aCA9IE1BWF9PSURfTEVOOwogICAgICAgIHZwLT5uYW1lID0gMDsKICAgICAgICB2cC0+aW5kZXggPSAwOwogICAgICAgIHZwLT5kYXRhID0gMDsKICAgICAgICB2cC0+ZGF0YUZyZWVIb29rID0gMDsKICAgICAgICBERUJVR0RVTVBTRUNUSU9OKCJyZWN2IiwgIlZhckJpbmQiKTsKICAgICAgICBkYXRhID0gc25tcF9wYXJzZV92YXJfb3AoZGF0YSwgb2JqaWQsICZ2cC0+bmFtZV9sZW5ndGgsICZ2cC0+dHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJnZwLT52YWxfbGVuLCAmdmFyX3ZhbCwgbGVuZ3RoKTsKICAgICAgICBpZiAoZGF0YSA9PSBOVUxMKQogICAgICAgICAgICByZXR1cm4gLTE7CiAgICAgICAgaWYgKHNubXBfc2V0X3Zhcl9vYmppZCh2cCwgb2JqaWQsIHZwLT5uYW1lX2xlbmd0aCkpCiAgICAgICAgICAgIHJldHVybiAtMTsKCiAgICAgICAgbGVuID0gTUFYX1BBQ0tFVF9MRU5HVEg7CiAgICAgICAgREVCVUdEVU1QSEVBREVSKCJyZWN2IiwgIlZhbHVlIik7CiAgICAgICAgc3dpdGNoICgoc2hvcnQpIHZwLT50eXBlKSB7CiAgICAgICAgY2FzZSBBU05fSU5URUdFUjoKICAgICAgICAgICAgdnAtPnZhbC5pbnRlZ2VyID0gKGxvbmcgKikgdnAtPmJ1ZjsKICAgICAgICAgICAgdnAtPnZhbF9sZW4gPSBzaXplb2YobG9uZyk7CiAgICAgICAgICAgIGFzbl9wYXJzZV9pbnQodmFyX3ZhbCwgJmxlbiwgJnZwLT50eXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgIChsb25nICopIHZwLT52YWwuaW50ZWdlciwKICAgICAgICAgICAgICAgICAgICAgICAgICBzaXplb2YoKnZwLT52YWwuaW50ZWdlcikpOwogICAgICAgICAgICBicmVhazsKICAgICAgICBjYXNlIEFTTl9DT1VOVEVSOgogICAgICAgIGNhc2UgQVNOX0dBVUdFOgogICAgICAgIGNhc2UgQVNOX1RJTUVUSUNLUzoKICAgICAgICBjYXNlIEFTTl9VSU5URUdFUjoKICAgICAgICAgICAgdnAtPnZhbC5pbnRlZ2VyID0gKGxvbmcgKikgdnAtPmJ1ZjsKICAgICAgICAgICAgdnAtPnZhbF9sZW4gPSBzaXplb2YodV9sb25nKTsKICAgICAgICAgICAgYXNuX3BhcnNlX3Vuc2lnbmVkX2ludCh2YXJfdmFsLCAmbGVuLCAmdnAtPnR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKHVfbG9uZyAqKSB2cC0+dmFsLmludGVnZXIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdnAtPnZhbF9sZW4pOwogICAgICAgICAgICBicmVhazsKI2lmZGVmIE5FVFNOTVBfV0lUSF9PUEFRVUVfU1BFQ0lBTF9UWVBFUwogICAgICAgIGNhc2UgQVNOX09QQVFVRV9DT1VOVEVSNjQ6CiAgICAgICAgY2FzZSBBU05fT1BBUVVFX1U2NDoKI2VuZGlmICAgICAgICAgICAgICAgICAgICAgICAgICAvKiBORVRTTk1QX1dJVEhfT1BBUVVFX1NQRUNJQUxfVFlQRVMgKi8KICAgICAgICBjYXNlIEFTTl9DT1VOVEVSNjQ6CiAgICAgICAgICAgIHZwLT52YWwuY291bnRlcjY0ID0gKHN0cnVjdCBjb3VudGVyNjQgKikgdnAtPmJ1ZjsKICAgICAgICAgICAgdnAtPnZhbF9sZW4gPSBzaXplb2Yoc3RydWN0IGNvdW50ZXI2NCk7CiAgICAgICAgICAgIGFzbl9wYXJzZV91bnNpZ25lZF9pbnQ2NCh2YXJfdmFsLCAmbGVuLCAmdnAtPnR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAoc3RydWN0IGNvdW50ZXI2NCAqKSB2cC0+dmFsLgogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY291bnRlcjY0LCB2cC0+dmFsX2xlbik7CiAgICAgICAgICAgIGJyZWFrOwojaWZkZWYgTkVUU05NUF9XSVRIX09QQVFVRV9TUEVDSUFMX1RZUEVTCiAgICAgICAgY2FzZSBBU05fT1BBUVVFX0ZMT0FUOgogICAgICAgICAgICB2cC0+dmFsLmZsb2F0VmFsID0gKGZsb2F0ICopIHZwLT5idWY7CiAgICAgICAgICAgIHZwLT52YWxfbGVuID0gc2l6ZW9mKGZsb2F0KTsKICAgICAgICAgICAgYXNuX3BhcnNlX2Zsb2F0KHZhcl92YWwsICZsZW4sICZ2cC0+dHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHZwLT52YWwuZmxvYXRWYWwsIHZwLT52YWxfbGVuKTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgY2FzZSBBU05fT1BBUVVFX0RPVUJMRToKICAgICAgICAgICAgdnAtPnZhbC5kb3VibGVWYWwgPSAoZG91YmxlICopIHZwLT5idWY7CiAgICAgICAgICAgIHZwLT52YWxfbGVuID0gc2l6ZW9mKGRvdWJsZSk7CiAgICAgICAgICAgIGFzbl9wYXJzZV9kb3VibGUodmFyX3ZhbCwgJmxlbiwgJnZwLT50eXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgIHZwLT52YWwuZG91YmxlVmFsLCB2cC0+dmFsX2xlbik7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgIGNhc2UgQVNOX09QQVFVRV9JNjQ6CiAgICAgICAgICAgIHZwLT52YWwuY291bnRlcjY0ID0gKHN0cnVjdCBjb3VudGVyNjQgKikgdnAtPmJ1ZjsKICAgICAgICAgICAgdnAtPnZhbF9sZW4gPSBzaXplb2Yoc3RydWN0IGNvdW50ZXI2NCk7CiAgICAgICAgICAgIGFzbl9wYXJzZV9zaWduZWRfaW50NjQodmFyX3ZhbCwgJmxlbiwgJnZwLT50eXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIChzdHJ1Y3QgY291bnRlcjY0ICopIHZwLT52YWwuY291bnRlcjY0LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNpemVvZigqdnAtPnZhbC5jb3VudGVyNjQpKTsKCiAgICAgICAgICAgIGJyZWFrOwojZW5kaWYgICAgICAgICAgICAgICAgICAgICAgICAgIC8qIE5FVFNOTVBfV0lUSF9PUEFRVUVfU1BFQ0lBTF9UWVBFUyAqLwogICAgICAgIGNhc2UgQVNOX09DVEVUX1NUUjoKICAgICAgICBjYXNlIEFTTl9JUEFERFJFU1M6CiAgICAgICAgY2FzZSBBU05fT1BBUVVFOgogICAgICAgIGNhc2UgQVNOX05TQVA6CiAgICAgICAgICAgIGlmICh2cC0+dmFsX2xlbiA8IHNpemVvZih2cC0+YnVmKSkgewogICAgICAgICAgICAgICAgdnAtPnZhbC5zdHJpbmcgPSAodV9jaGFyICopIHZwLT5idWY7CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICB2cC0+dmFsLnN0cmluZyA9ICh1X2NoYXIgKikgbWFsbG9jKHZwLT52YWxfbGVuKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodnAtPnZhbC5zdHJpbmcgPT0gTlVMTCkgewogICAgICAgICAgICAgICAgcmV0dXJuIC0xOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGFzbl9wYXJzZV9zdHJpbmcodmFyX3ZhbCwgJmxlbiwgJnZwLT50eXBlLCB2cC0+dmFsLnN0cmluZywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmdnAtPnZhbF9sZW4pOwogICAgICAgICAgICBicmVhazsKICAgICAgICBjYXNlIEFTTl9PQkpFQ1RfSUQ6CiAgICAgICAgICAgIHZwLT52YWxfbGVuID0gTUFYX09JRF9MRU47CiAgICAgICAgICAgIGFzbl9wYXJzZV9vYmppZCh2YXJfdmFsLCAmbGVuLCAmdnAtPnR5cGUsIG9iamlkLCAmdnAtPnZhbF9sZW4pOwogICAgICAgICAgICB2cC0+dmFsX2xlbiAqPSBzaXplb2Yob2lkKTsKICAgICAgICAgICAgdnAtPnZhbC5vYmppZCA9IChvaWQgKikgbWFsbG9jKHZwLT52YWxfbGVuKTsKICAgICAgICAgICAgaWYgKHZwLT52YWwub2JqaWQgPT0gTlVMTCkgewogICAgICAgICAgICAgICAgcmV0dXJuIC0xOwogICAgICAgICAgICB9CiAgICAgICAgICAgIG1lbW1vdmUodnAtPnZhbC5vYmppZCwgb2JqaWQsIHZwLT52YWxfbGVuKTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgY2FzZSBTTk1QX05PU1VDSE9CSkVDVDoKICAgICAgICBjYXNlIFNOTVBfTk9TVUNISU5TVEFOQ0U6CiAgICAgICAgY2FzZSBTTk1QX0VORE9GTUlCVklFVzoKICAgICAgICBjYXNlIEFTTl9OVUxMOgogICAgICAgICAgICBicmVhazsKICAgICAgICBjYXNlIEFTTl9CSVRfU1RSOgogICAgICAgICAgICB2cC0+dmFsLmJpdHN0cmluZyA9ICh1X2NoYXIgKikgbWFsbG9jKHZwLT52YWxfbGVuKTsKICAgICAgICAgICAgaWYgKHZwLT52YWwuYml0c3RyaW5nID09IE5VTEwpIHsKICAgICAgICAgICAgICAgIHJldHVybiAtMTsKICAgICAgICAgICAgfQogICAgICAgICAgICBhc25fcGFyc2VfYml0c3RyaW5nKHZhcl92YWwsICZsZW4sICZ2cC0+dHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2cC0+dmFsLmJpdHN0cmluZywgJnZwLT52YWxfbGVuKTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgZGVmYXVsdDoKICAgICAgICAgICAgc25tcF9sb2coTE9HX0VSUiwgImJhZCB0eXBlIHJldHVybmVkICgleClcbiIsIHZwLT50eXBlKTsKICAgICAgICAgICAgYmFkdHlwZSA9IC0xOwogICAgICAgICAgICBicmVhazsKICAgICAgICB9CiAgICAgICAgREVCVUdJTkRFTlRBREQoLTQpOwogICAgfQogICAgcmV0dXJuIGJhZHR5cGU7Cn0KCi8qCiAqIHNubXAgdjMgdXRpbGl0eSBmdW5jdGlvbiB0byBwYXJzZSBpbnRvIHRoZSBzY29wZWRQZHUuIHN0b3JlcyBjb250ZXh0TmFtZQogKiBhbmQgY29udGV4dEVuZ2luZUlEIGluIHBkdSBzdHJ1Y3QuIEFsc28gc3RvcmVzIHBkdS0+Y29tbWFuZCAoaGFuZHkgZm9yIAogKiBSZXBvcnQgZ2VuZXJhdGlvbikuCiAqIAogKiByZXR1cm5zIHBvaW50ZXIgdG8gYmVnaW5pbmcgb2YgUERVIG9yIE5VTEwgb24gZXJyb3IuCiAqLwp1X2NoYXIgICAgICAgICAqCnNubXB2M19zY29wZWRQRFVfcGFyc2UobmV0c25tcF9wZHUgKnBkdSwgdV9jaGFyICogY3AsIHNpemVfdCAqIGxlbmd0aCkKewogICAgdV9jaGFyICAgICAgICAgIHRtcF9idWZbU05NUF9NQVhfTVNHX1NJWkVdOwogICAgc2l6ZV90ICAgICAgICAgIHRtcF9idWZfbGVuOwogICAgdV9jaGFyICAgICAgICAgIHR5cGU7CiAgICBzaXplX3QgICAgICAgICAgYXNuX2xlbjsKICAgIHVfY2hhciAgICAgICAgICpkYXRhOwoKICAgIHBkdS0+Y29tbWFuZCA9IDA7ICAgICAgICAgICAvKiBpbml0aWFsaXplIHNvIHdlIGtub3cgaWYgaXQgZ290IHBhcnNlZCAqLwogICAgYXNuX2xlbiA9ICpsZW5ndGg7CiAgICBkYXRhID0gYXNuX3BhcnNlX3NlcXVlbmNlKGNwLCAmYXNuX2xlbiwgJnR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIChBU05fU0VRVUVOQ0UgfCBBU05fQ09OU1RSVUNUT1IpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAicGxhaW50ZXh0IHNjb3BlZFBEVSIpOwogICAgaWYgKGRhdGEgPT0gTlVMTCkgewogICAgICAgIHJldHVybiBOVUxMOwogICAgfQogICAgKmxlbmd0aCAtPSBkYXRhIC0gY3A7CgogICAgLyoKICAgICAqIGNvbnRleHRFbmdpbmVJRCBmcm9tIHNjb3BlZFBkdSAgCiAgICAgKi8KICAgIERFQlVHRFVNUEhFQURFUigicmVjdiIsICJjb250ZXh0RW5naW5lSUQiKTsKICAgIGRhdGEgPSBhc25fcGFyc2Vfc3RyaW5nKGRhdGEsIGxlbmd0aCwgJnR5cGUsIHBkdS0+Y29udGV4dEVuZ2luZUlELAogICAgICAgICAgICAgICAgICAgICAgICAgICAgJnBkdS0+Y29udGV4dEVuZ2luZUlETGVuKTsKICAgIERFQlVHSU5ERU5UTEVTUygpOwogICAgaWYgKGRhdGEgPT0gTlVMTCkgewogICAgICAgIEVSUk9SX01TRygiZXJyb3IgcGFyc2luZyBjb250ZXh0RW5naW5lSUQgZnJvbSBzY29wZWRQZHUiKTsKICAgICAgICByZXR1cm4gTlVMTDsKICAgIH0KCiAgICAvKgogICAgICogY2hlY2sgdGhhdCBpdCBhZ3JlZXMgd2l0aCBlbmdpbmVJRCByZXR1cm5lZCBmcm9tIFVTTSBhYm92ZQogICAgICogKiBvbmx5IGEgd2FybmluZyBiZWNhdXNlIHRoaXMgY291bGQgYmUgbGVnYWwgaWYgd2UgYXJlIGEgcHJveHkKICAgICAqLwogICAgaWYgKHBkdS0+c2VjdXJpdHlFbmdpbmVJRExlbiAhPSBwZHUtPmNvbnRleHRFbmdpbmVJRExlbiB8fAogICAgICAgIG1lbWNtcChwZHUtPnNlY3VyaXR5RW5naW5lSUQsIHBkdS0+Y29udGV4dEVuZ2luZUlELAogICAgICAgICAgICAgICBwZHUtPnNlY3VyaXR5RW5naW5lSURMZW4pICE9IDApIHsKICAgICAgICBERUJVR01TR1RMKCgic2NvcGVkUERVX3BhcnNlIiwKICAgICAgICAgICAgICAgICAgICAiaW5jb25zaXN0ZW50IGVuZ2luZUlEIGluZm9ybWF0aW9uIGluIG1lc3NhZ2VcbiIpKTsKICAgIH0KCiAgICAvKgogICAgICogcGFyc2UgY29udGV4dE5hbWUgZnJvbSBzY29wZWRQZHUKICAgICAqLwogICAgdG1wX2J1Zl9sZW4gPSBTTk1QX01BWF9DT05URVhUX1NJWkU7CiAgICBERUJVR0RVTVBIRUFERVIoInJlY3YiLCAiY29udGV4dE5hbWUiKTsKICAgIGRhdGEgPSBhc25fcGFyc2Vfc3RyaW5nKGRhdGEsIGxlbmd0aCwgJnR5cGUsIHRtcF9idWYsICZ0bXBfYnVmX2xlbik7CiAgICBERUJVR0lOREVOVExFU1MoKTsKICAgIGlmIChkYXRhID09IE5VTEwpIHsKICAgICAgICBFUlJPUl9NU0coImVycm9yIHBhcnNpbmcgY29udGV4dE5hbWUgZnJvbSBzY29wZWRQZHUiKTsKICAgICAgICByZXR1cm4gTlVMTDsKICAgIH0KCiAgICBpZiAodG1wX2J1Zl9sZW4pIHsKICAgICAgICBwZHUtPmNvbnRleHROYW1lID0gKGNoYXIgKikgbWFsbG9jKHRtcF9idWZfbGVuKTsKICAgICAgICBtZW1tb3ZlKHBkdS0+Y29udGV4dE5hbWUsIHRtcF9idWYsIHRtcF9idWZfbGVuKTsKICAgICAgICBwZHUtPmNvbnRleHROYW1lTGVuID0gdG1wX2J1Zl9sZW47CiAgICB9IGVsc2UgewogICAgICAgIHBkdS0+Y29udGV4dE5hbWUgPSBzdHJkdXAoIiIpOwogICAgICAgIHBkdS0+Y29udGV4dE5hbWVMZW4gPSAwOwogICAgfQogICAgaWYgKHBkdS0+Y29udGV4dE5hbWUgPT0gTlVMTCkgewogICAgICAgIEVSUk9SX01TRygiZXJyb3IgY29weWluZyBjb250ZXh0TmFtZSBmcm9tIHNjb3BlZFBkdSIpOwogICAgICAgIHJldHVybiBOVUxMOwogICAgfQoKICAgIC8qCiAgICAgKiBHZXQgdGhlIFBEVSB0eXBlIAogICAgICovCiAgICBhc25fbGVuID0gKmxlbmd0aDsKICAgIGNwID0gYXNuX3BhcnNlX2hlYWRlcihkYXRhLCAmYXNuX2xlbiwgJnR5cGUpOwogICAgaWYgKGNwID09IE5VTEwpCiAgICAgICAgcmV0dXJuIE5VTEw7CgogICAgcGR1LT5jb21tYW5kID0gdHlwZTsKCiAgICByZXR1cm4gZGF0YTsKfQoKLyoKICogVGhlc2UgZnVuY3Rpb25zIHNlbmQgUERVcyB1c2luZyBhbiBhY3RpdmUgc2Vzc2lvbjoKICogc25tcF9zZW5kICAgICAgICAgICAgIC0gdHJhZGl0aW9uYWwgQVBJLCBubyBjYWxsYmFjawogKiBzbm1wX2FzeW5jX3NlbmQgICAgICAgLSB0cmFkaXRpb25hbCBBUEksIHdpdGggY2FsbGJhY2sKICogc25tcF9zZXNzX3NlbmQgICAgICAgIC0gc2luZ2xlIHNlc3Npb24gQVBJLCBubyBjYWxsYmFjawogKiBzbm1wX3Nlc3NfYXN5bmNfc2VuZCAgLSBzaW5nbGUgc2Vzc2lvbiBBUEksIHdpdGggY2FsbGJhY2sKICoKICogQ2FsbCBzbm1wX2J1aWxkIHRvIGNyZWF0ZSBhIHNlcmlhbGl6ZWQgcGFja2V0ICh0aGUgcGR1KS4KICogSWYgbmVjZXNzYXJ5LCBzZXQgc29tZSBvZiB0aGUgcGR1IGRhdGEgZnJvbSB0aGUKICogc2Vzc2lvbiBkZWZhdWx0cy4KICogSWYgdGhlcmUgaXMgYW4gZXhwZWN0ZWQgcmVzcG9uc2UgZm9yIHRoaXMgUERVLAogKiBxdWV1ZSBhIGNvcnJlc3BvbmRpbmcgcmVxdWVzdCBvbiB0aGUgbGlzdAogKiBvZiBvdXRzdGFuZGluZyByZXF1ZXN0cyBmb3IgdGhpcyBzZXNzaW9uLAogKiBhbmQgc3RvcmUgdGhlIGNhbGxiYWNrIHZlY3RvcnMgaW4gdGhlIHJlcXVlc3QuCiAqCiAqIFNlbmQgdGhlIHBkdSB0byB0aGUgdGFyZ2V0IGlkZW50aWZpZWQgYnkgdGhpcyBzZXNzaW9uLgogKiBSZXR1cm4gb24gc3VjY2VzczoKICogICBUaGUgcmVxdWVzdCBpZCBvZiB0aGUgcGR1IGlzIHJldHVybmVkLCBhbmQgdGhlIHBkdSBpcyBmcmVlZC4KICogUmV0dXJuIG9uIGZhaWx1cmU6CiAqICAgWmVybyAoMCkgaXMgcmV0dXJuZWQuCiAqICAgVGhlIGNhbGxlciBtdXN0IGNhbGwgc25tcF9mcmVlX3BkdSBpZiAwIGlzIHJldHVybmVkLgogKi8KaW50CnNubXBfc2VuZChuZXRzbm1wX3Nlc3Npb24gKiBzZXNzaW9uLCBuZXRzbm1wX3BkdSAqcGR1KQp7CiAgICByZXR1cm4gc25tcF9hc3luY19zZW5kKHNlc3Npb24sIHBkdSwgTlVMTCwgTlVMTCk7Cn0KCmludApzbm1wX3Nlc3Nfc2VuZCh2b2lkICpzZXNzcCwgbmV0c25tcF9wZHUgKnBkdSkKewogICAgcmV0dXJuIHNubXBfc2Vzc19hc3luY19zZW5kKHNlc3NwLCBwZHUsIE5VTEwsIE5VTEwpOwp9CgppbnQKc25tcF9hc3luY19zZW5kKG5ldHNubXBfc2Vzc2lvbiAqIHNlc3Npb24sCiAgICAgICAgICAgICAgICBuZXRzbm1wX3BkdSAqcGR1LCBzbm1wX2NhbGxiYWNrIGNhbGxiYWNrLCB2b2lkICpjYl9kYXRhKQp7CiAgICB2b2lkICAgICAgICAgICAqc2Vzc3AgPSBzbm1wX3Nlc3NfcG9pbnRlcihzZXNzaW9uKTsKICAgIHJldHVybiBzbm1wX3Nlc3NfYXN5bmNfc2VuZChzZXNzcCwgcGR1LCBjYWxsYmFjaywgY2JfZGF0YSk7Cn0KCnN0YXRpYyBpbnQKX3Nlc3NfYXN5bmNfc2VuZCh2b2lkICpzZXNzcCwKICAgICAgICAgICAgICAgICBuZXRzbm1wX3BkdSAqcGR1LCBzbm1wX2NhbGxiYWNrIGNhbGxiYWNrLCB2b2lkICpjYl9kYXRhKQp7CiAgICBzdHJ1Y3Qgc2Vzc2lvbl9saXN0ICpzbHAgPSAoc3RydWN0IHNlc3Npb25fbGlzdCAqKSBzZXNzcDsKICAgIG5ldHNubXBfc2Vzc2lvbiAqc2Vzc2lvbjsKICAgIHN0cnVjdCBzbm1wX2ludGVybmFsX3Nlc3Npb24gKmlzcDsKICAgIG5ldHNubXBfdHJhbnNwb3J0ICp0cmFuc3BvcnQgPSBOVUxMOwogICAgdV9jaGFyICAgICAgICAgKnBrdGJ1ZiA9IE5VTEwsICpwYWNrZXQgPSBOVUxMOwogICAgc2l6ZV90ICAgICAgICAgIHBrdGJ1Zl9sZW4gPSAwLCBvZmZzZXQgPSAwLCBsZW5ndGggPSAwOwogICAgaW50ICAgICAgICAgICAgIHJlc3VsdDsKICAgIGxvbmcgICAgICAgICAgICByZXFpZDsKCiAgICBpZiAoc2xwID09IE5VTEwpIHsKICAgICAgICByZXR1cm4gMDsKICAgIH0gZWxzZSB7CiAgICAgICAgc2Vzc2lvbiA9IHNscC0+c2Vzc2lvbjsKICAgICAgICBpc3AgPSBzbHAtPmludGVybmFsOwogICAgICAgIHRyYW5zcG9ydCA9IHNscC0+dHJhbnNwb3J0OwogICAgICAgIGlmICghc2Vzc2lvbiB8fCAhaXNwIHx8ICF0cmFuc3BvcnQpIHsKICAgICAgICAgICAgREVCVUdNU0dUTCgoInNlc3NfYXN5bmNfc2VuZCIsICJzZW5kIGZhaWw6IGNsb3NpbmcuLi5cbiIpKTsKICAgICAgICAgICAgcmV0dXJuIDA7CiAgICAgICAgfQogICAgfQoKICAgIGlmIChwZHUgPT0gTlVMTCkgewogICAgICAgIHNlc3Npb24tPnNfc25tcF9lcnJubyA9IFNOTVBFUlJfTlVMTF9QRFU7CiAgICAgICAgcmV0dXJuIDA7CiAgICB9CgogICAgc2Vzc2lvbi0+c19zbm1wX2Vycm5vID0gMDsKICAgIHNlc3Npb24tPnNfZXJybm8gPSAwOwoKICAgIC8qCiAgICAgKiBDaGVjay9zZXR1cCB0aGUgdmVyc2lvbi4gIAogICAgICovCiAgICBpZiAocGR1LT52ZXJzaW9uID09IFNOTVBfREVGQVVMVF9WRVJTSU9OKSB7CiAgICAgICAgaWYgKHNlc3Npb24tPnZlcnNpb24gPT0gU05NUF9ERUZBVUxUX1ZFUlNJT04pIHsKICAgICAgICAgICAgc2Vzc2lvbi0+c19zbm1wX2Vycm5vID0gU05NUEVSUl9CQURfVkVSU0lPTjsKICAgICAgICAgICAgcmV0dXJuIDA7CiAgICAgICAgfQogICAgICAgIHBkdS0+dmVyc2lvbiA9IHNlc3Npb24tPnZlcnNpb247CiAgICB9IGVsc2UgaWYgKHNlc3Npb24tPnZlcnNpb24gPT0gU05NUF9ERUZBVUxUX1ZFUlNJT04pIHsKICAgICAgICAvKgogICAgICAgICAqIEl0J3MgT0sgIAogICAgICAgICAqLwogICAgfSBlbHNlIGlmIChwZHUtPnZlcnNpb24gIT0gc2Vzc2lvbi0+dmVyc2lvbikgewogICAgICAgIC8qCiAgICAgICAgICogRU5IQU5DRTogd2Ugc2hvdWxkIHN1cHBvcnQgbXVsdGktbGluZ3VhbCBzZXNzaW9ucyAgCiAgICAgICAgICovCiAgICAgICAgc2Vzc2lvbi0+c19zbm1wX2Vycm5vID0gU05NUEVSUl9CQURfVkVSU0lPTjsKICAgICAgICByZXR1cm4gMDsKICAgIH0KCiAgICAvKgogICAgICogZG8gd2UgZXhwZWN0IGEgcmVzcG9uc2U/CiAgICAgKi8KICAgIHN3aXRjaCAocGR1LT5jb21tYW5kKSB7CgogICAgICAgIGNhc2UgU05NUF9NU0dfUkVTUE9OU0U6CiAgICAgICAgY2FzZSBTTk1QX01TR19UUkFQOgogICAgICAgIGNhc2UgU05NUF9NU0dfVFJBUDI6CiAgICAgICAgY2FzZSBTTk1QX01TR19SRVBPUlQ6CiAgICAgICAgY2FzZSBBR0VOVFhfTVNHX0NMRUFOVVBTRVQ6CiAgICAgICAgY2FzZSBBR0VOVFhfTVNHX1JFU1BPTlNFOgogICAgICAgICAgICBwZHUtPmZsYWdzICY9IH5VQ0RfTVNHX0ZMQUdfRVhQRUNUX1JFU1BPTlNFOwogICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgCiAgICAgICAgZGVmYXVsdDoKICAgICAgICAgICAgcGR1LT5mbGFncyB8PSBVQ0RfTVNHX0ZMQUdfRVhQRUNUX1JFU1BPTlNFOwogICAgICAgICAgICBicmVhazsKICAgIH0KCiAgICAvKgogICAgICogY2hlY2sgdG8gc2VlIGlmIHdlIG5lZWQgYSB2MyBlbmdpbmVJRCBwcm9iZQogICAgICovCiAgICBpZiAoKHBkdS0+dmVyc2lvbiA9PSBTTk1QX1ZFUlNJT05fMykgJiYKICAgICAgICAocGR1LT5mbGFncyAmIFVDRF9NU0dfRkxBR19FWFBFQ1RfUkVTUE9OU0UpICYmCiAgICAgICAgKHNlc3Npb24tPnNlY3VyaXR5RW5naW5lSURMZW4gPT0gMCkgJiYKICAgICAgICAoMCA9PSAoc2Vzc2lvbi0+ZmxhZ3MgJiBTTk1QX0ZMQUdTX0RPTlRfUFJPQkUpKSkgewogICAgICAgIGludCByYzsKICAgICAgICBERUJVR01TR1RMKCgic25tcHYzX2J1aWxkIiwgImRlbGF5ZWQgcHJvYmUgZm9yIGVuZ2luZUlEXG4iKSk7CiAgICAgICAgcmMgPSBzbm1wdjNfZW5naW5lSURfcHJvYmUoc2xwLCBzZXNzaW9uKTsKICAgICAgICBpZiAocmMgPT0gMCkKICAgICAgICAgICAgcmV0dXJuIDA7IC8qIHNfc25tcF9lcnJubyBhbHJlYWR5IHNldCAqLwogICAgfQoKICAgIC8qCiAgICAgKiBjaGVjayB0byBzZWUgaWYgd2UgbmVlZCB0byBjcmVhdGUgYSB2MyB1c2VyIGZyb20gdGhlIHNlc3Npb24gaW5mbwogICAgICovCiAgICBpZiAoY3JlYXRlX3VzZXJfZnJvbV9zZXNzaW9uKHNlc3Npb24pICE9IFNOTVBFUlJfU1VDQ0VTUykgewogICAgICAgIHNlc3Npb24tPnNfc25tcF9lcnJubyA9IFNOTVBFUlJfVU5LTk9XTl9VU0VSX05BTUU7ICAvKiBYWD8/ICovCiAgICAgICAgREVCVUdNU0dUTCgoInNubXBfYXBpIiwKICAgICAgICAgICAgICAgICAgICAic25tcF9zZW5kKCk6IGZhaWxlZCgyKSB0byBjcmVhdGUgYSBuZXcgdXNlciBmcm9tIHNlc3Npb25cbiIpKTsKICAgICAgICByZXR1cm4gMDsKICAgIH0KCiAgICBpZiAoKHBrdGJ1ZiA9ICh1X2NoYXIgKiltYWxsb2MoMjA0OCkpID09IE5VTEwpIHsKICAgICAgICBERUJVR01TR1RMKCgic2Vzc19hc3luY19zZW5kIiwKICAgICAgICAgICAgICAgICAgICAiY291bGRuJ3QgbWFsbG9jIGluaXRpYWwgcGFja2V0IGJ1ZmZlclxuIikpOwogICAgICAgIHNlc3Npb24tPnNfc25tcF9lcnJubyA9IFNOTVBFUlJfTUFMTE9DOwogICAgICAgIHJldHVybiAwOwogICAgfSBlbHNlIHsKICAgICAgICBwa3RidWZfbGVuID0gMjA0ODsKICAgIH0KCiNpZiBURU1QT1JBUklMWV9ESVNBQkxFRAogICAgLyoKICAgICAqICBOVUxMIHZhcmlhYmxlIGFyZSBhbGxvd2VkIGluIGNlcnRhaW4gUERVIHR5cGVzLgogICAgICogIEluIHBhcnRpY3VsYXIsIFNOTVB2MyBlbmdpbmVJRCBwcm9iZXMgYXJlIG9mIHRoaXMgZm9ybS4KICAgICAqICBUaGVyZSBpcyBhbiBpbnRlcm5hbCBQRFUgZmxhZyB0byBpbmRpY2F0ZSB0aGF0IHRoaXMKICAgICAqICAgIGlzIGFjY2VwdGFibGUsIGJ1dCB1bnRpbCB0aGUgY29uc3RydWN0aW9uIG9mIGVuZ2luZUlECiAgICAgKiAgICBwcm9iZXMgY2FuIGJlIGFtZW5kZWQgdG8gc2V0IHRoaXMgZmxhZywgd2UnbGwgc2ltcGx5CiAgICAgKiAgICBza2lwIHRoaXMgdGVzdCBhbHRvZ2V0aGVyLgogICAgICovCiAgICBpZiAocGR1LT52YXJpYWJsZXMgPT0gTlVMTCkgewogICAgICAgIHN3aXRjaCAocGR1LT5jb21tYW5kKSB7CiAgICAgICAgY2FzZSBTTk1QX01TR19HRVQ6CiAgICAgICAgY2FzZSBTTk1QX01TR19TRVQ6CiAgICAgICAgY2FzZSBTTk1QX01TR19HRVRORVhUOgogICAgICAgIGNhc2UgU05NUF9NU0dfR0VUQlVMSzoKICAgICAgICBjYXNlIFNOTVBfTVNHX1JFU1BPTlNFOgogICAgICAgIGNhc2UgU05NUF9NU0dfVFJBUDI6CiAgICAgICAgY2FzZSBTTk1QX01TR19SRVBPUlQ6CiAgICAgICAgY2FzZSBTTk1QX01TR19JTkZPUk06CiAgICAgICAgICAgIHNlc3Npb24tPnNfc25tcF9lcnJubyA9IHNubXBfZXJybm8gPSBTTk1QRVJSX05PX1ZBUlM7CiAgICAgICAgICAgIHJldHVybiAwOwogICAgICAgIGNhc2UgU05NUF9NU0dfVFJBUDoKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgfQogICAgfQojZW5kaWYKCgogICAgLyoKICAgICAqIEJ1aWxkIHRoZSBtZXNzYWdlIHRvIHNlbmQuICAKICAgICAqLwogICAgaWYgKGlzcC0+aG9va19yZWFsbG9jX2J1aWxkKSB7CiAgICAgICAgcmVzdWx0ID0gaXNwLT5ob29rX3JlYWxsb2NfYnVpbGQoc2Vzc2lvbiwgcGR1LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICZwa3RidWYsICZwa3RidWZfbGVuLCAmb2Zmc2V0KTsKICAgICAgICBwYWNrZXQgPSBwa3RidWY7CiAgICAgICAgbGVuZ3RoID0gb2Zmc2V0OwogICAgfSBlbHNlIGlmIChpc3AtPmhvb2tfYnVpbGQpIHsKICAgICAgICBwYWNrZXQgPSBwa3RidWY7CiAgICAgICAgbGVuZ3RoID0gcGt0YnVmX2xlbjsKICAgICAgICByZXN1bHQgPSBpc3AtPmhvb2tfYnVpbGQoc2Vzc2lvbiwgcGR1LCBwa3RidWYsICZsZW5ndGgpOwogICAgfSBlbHNlIHsKI2lmZGVmIE5FVFNOTVBfVVNFX1JFVkVSU0VfQVNORU5DT0RJTkcKICAgICAgICBpZiAobmV0c25tcF9kc19nZXRfYm9vbGVhbihORVRTTk1QX0RTX0xJQlJBUllfSUQsIE5FVFNOTVBfRFNfTElCX1JFVkVSU0VfRU5DT0RFKSkgewogICAgICAgICAgICByZXN1bHQgPQogICAgICAgICAgICAgICAgc25tcF9idWlsZCgmcGt0YnVmLCAmcGt0YnVmX2xlbiwgJm9mZnNldCwgc2Vzc2lvbiwgcGR1KTsKICAgICAgICAgICAgcGFja2V0ID0gcGt0YnVmICsgcGt0YnVmX2xlbiAtIG9mZnNldDsKICAgICAgICAgICAgbGVuZ3RoID0gb2Zmc2V0OwogICAgICAgIH0gZWxzZSB7CiNlbmRpZgogICAgICAgICAgICBwYWNrZXQgPSBwa3RidWY7CiAgICAgICAgICAgIGxlbmd0aCA9IHBrdGJ1Zl9sZW47CiAgICAgICAgICAgIHJlc3VsdCA9IHNubXBfYnVpbGQoJnBrdGJ1ZiwgJmxlbmd0aCwgJm9mZnNldCwgc2Vzc2lvbiwgcGR1KTsKI2lmZGVmIE5FVFNOTVBfVVNFX1JFVkVSU0VfQVNORU5DT0RJTkcKICAgICAgICB9CiNlbmRpZgogICAgfQoKICAgIGlmIChyZXN1bHQgPCAwKSB7CiAgICAgICAgREVCVUdNU0dUTCgoInNlc3NfYXN5bmNfc2VuZCIsICJlbmNvZGluZyBmYWlsdXJlXG4iKSk7CiAgICAgICAgU05NUF9GUkVFKHBrdGJ1Zik7CiAgICAgICAgcmV0dXJuIDA7CiAgICB9CgogICAgLyoKICAgICAqIE1ha2Ugc3VyZSB3ZSBkb24ndCBzZW5kIHNvbWV0aGluZyB0aGF0IGlzIGJpZ2dlciB0aGFuIHRoZSBtc2dNYXhTaXplCiAgICAgKiBzcGVjaWZpZWQgaW4gdGhlIHJlY2VpdmVkIFBEVS4gIAogICAgICovCgogICAgaWYgKHBkdS0+dmVyc2lvbiA9PSBTTk1QX1ZFUlNJT05fMyAmJiBzZXNzaW9uLT5zbmRNc2dNYXhTaXplICE9IDAgJiYgbGVuZ3RoID4gc2Vzc2lvbi0+c25kTXNnTWF4U2l6ZSkgewogICAgICAgIERFQlVHTVNHVEwoKCJzZXNzX2FzeW5jX3NlbmQiLAogICAgICAgICAgICAgICAgICAgICJsZW5ndGggb2YgcGFja2V0ICglbHUpIGV4Y2VlZHMgc2Vzc2lvbiBtYXhpbXVtICglbHUpXG4iLAogICAgICAgICAgICAgICAgICAgIGxlbmd0aCwgc2Vzc2lvbi0+c25kTXNnTWF4U2l6ZSkpOwogICAgICAgIHNlc3Npb24tPnNfc25tcF9lcnJubyA9IFNOTVBFUlJfVE9PX0xPTkc7CiAgICAgICAgU05NUF9GUkVFKHBrdGJ1Zik7CiAgICAgICAgcmV0dXJuIDA7CiAgICB9CgogICAgLyoKICAgICAqIENoZWNrIHRoYXQgdGhlIHVuZGVybHlpbmcgdHJhbnNwb3J0IGlzIGNhcGFibGUgb2Ygc2VuZGluZyBhIHBhY2tldCBhcwogICAgICogbGFyZ2UgYXMgbGVuZ3RoLiAgCiAgICAgKi8KCiAgICBpZiAodHJhbnNwb3J0LT5tc2dNYXhTaXplICE9IDAgJiYgbGVuZ3RoID4gdHJhbnNwb3J0LT5tc2dNYXhTaXplKSB7CiAgICAgICAgREVCVUdNU0dUTCgoInNlc3NfYXN5bmNfc2VuZCIsCiAgICAgICAgICAgICAgICAgICAgImxlbmd0aCBvZiBwYWNrZXQgKCVsdSkgZXhjZWVkcyB0cmFuc3BvcnQgbWF4aW11bSAoJWx1KVxuIiwKICAgICAgICAgICAgICAgICAgICBsZW5ndGgsIHRyYW5zcG9ydC0+bXNnTWF4U2l6ZSkpOwogICAgICAgIHNlc3Npb24tPnNfc25tcF9lcnJubyA9IFNOTVBFUlJfVE9PX0xPTkc7CiAgICAgICAgU05NUF9GUkVFKHBrdGJ1Zik7CiAgICAgICAgcmV0dXJuIDA7CiAgICB9CgogICAgaWYgKG5ldHNubXBfZHNfZ2V0X2Jvb2xlYW4oTkVUU05NUF9EU19MSUJSQVJZX0lELCBORVRTTk1QX0RTX0xJQl9EVU1QX1BBQ0tFVCkpIHsKICAgICAgICBpZiAodHJhbnNwb3J0LT5mX2ZtdGFkZHIgIT0gTlVMTCkgewogICAgICAgICAgICBjaGFyICAgICAgICAgICAqZGVzdF90eHQgPQogICAgICAgICAgICAgICAgdHJhbnNwb3J0LT5mX2ZtdGFkZHIodHJhbnNwb3J0LCBwZHUtPnRyYW5zcG9ydF9kYXRhLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcGR1LT50cmFuc3BvcnRfZGF0YV9sZW5ndGgpOwogICAgICAgICAgICBpZiAoZGVzdF90eHQgIT0gTlVMTCkgewogICAgICAgICAgICAgICAgc25tcF9sb2coTE9HX0RFQlVHLCAiXG5TZW5kaW5nICVsdSBieXRlcyB0byAlc1xuIiwgKHVuc2lnbmVkIGxvbmcpbGVuZ3RoLAogICAgICAgICAgICAgICAgICAgICAgICAgZGVzdF90eHQpOwogICAgICAgICAgICAgICAgU05NUF9GUkVFKGRlc3RfdHh0KTsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgIHNubXBfbG9nKExPR19ERUJVRywgIlxuU2VuZGluZyAlbHUgYnl0ZXMgdG8gPFVOS05PV04+XG4iLAogICAgICAgICAgICAgICAgICAgICAgICAgKHVuc2lnbmVkIGxvbmcpbGVuZ3RoKTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICB4ZHVtcChwYWNrZXQsIGxlbmd0aCwgIiIpOwogICAgfQoKICAgIC8qCiAgICAgKiBTZW5kIHRoZSBtZXNzYWdlLiAgCiAgICAgKi8KCiAgICByZXN1bHQgPSB0cmFuc3BvcnQtPmZfc2VuZCh0cmFuc3BvcnQsIHBhY2tldCwgbGVuZ3RoLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJihwZHUtPnRyYW5zcG9ydF9kYXRhKSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICYocGR1LT50cmFuc3BvcnRfZGF0YV9sZW5ndGgpKTsKCiAgICBTTk1QX0ZSRUUocGt0YnVmKTsKCiAgICBpZiAocmVzdWx0IDwgMCkgewogICAgICAgIHNlc3Npb24tPnNfc25tcF9lcnJubyA9IFNOTVBFUlJfQkFEX1NFTkRUTzsKICAgICAgICBzZXNzaW9uLT5zX2Vycm5vID0gZXJybm87CiAgICAgICAgcmV0dXJuIDA7CiAgICB9CgogICAgcmVxaWQgPSBwZHUtPnJlcWlkOwoKICAgIC8qCiAgICAgKiBBZGQgdG8gcGVuZGluZyByZXF1ZXN0cyBsaXN0IGlmIHdlIGV4cGVjdCBhIHJlc3BvbnNlLiAgCiAgICAgKi8KICAgIGlmIChwZHUtPmZsYWdzICYgVUNEX01TR19GTEFHX0VYUEVDVF9SRVNQT05TRSkgewogICAgICAgIG5ldHNubXBfcmVxdWVzdF9saXN0ICpycDsKICAgICAgICBzdHJ1Y3QgdGltZXZhbCAgdHY7CgogICAgICAgIHJwID0gKG5ldHNubXBfcmVxdWVzdF9saXN0ICopIGNhbGxvYygxLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzaXplb2YobmV0c25tcF9yZXF1ZXN0X2xpc3QpKTsKICAgICAgICBpZiAocnAgPT0gTlVMTCkgewogICAgICAgICAgICBzZXNzaW9uLT5zX3NubXBfZXJybm8gPSBTTk1QRVJSX0dFTkVSUjsKICAgICAgICAgICAgcmV0dXJuIDA7CiAgICAgICAgfQoKICAgICAgICBnZXR0aW1lb2ZkYXkoJnR2LCAoc3RydWN0IHRpbWV6b25lICopIDApOwogICAgICAgIHJwLT5wZHUgPSBwZHU7CiAgICAgICAgcnAtPnJlcXVlc3RfaWQgPSBwZHUtPnJlcWlkOwogICAgICAgIHJwLT5tZXNzYWdlX2lkID0gcGR1LT5tc2dpZDsKICAgICAgICBycC0+Y2FsbGJhY2sgPSBjYWxsYmFjazsKICAgICAgICBycC0+Y2JfZGF0YSA9IGNiX2RhdGE7CiAgICAgICAgcnAtPnJldHJpZXMgPSAwOwogICAgICAgIGlmIChwZHUtPmZsYWdzICYgVUNEX01TR19GTEFHX1BEVV9USU1FT1VUKSB7CiAgICAgICAgICAgIHJwLT50aW1lb3V0ID0gcGR1LT50aW1lICogMTAwMDAwMEw7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgcnAtPnRpbWVvdXQgPSBzZXNzaW9uLT50aW1lb3V0OwogICAgICAgIH0KICAgICAgICBycC0+dGltZSA9IHR2OwogICAgICAgIHR2LnR2X3VzZWMgKz0gcnAtPnRpbWVvdXQ7CiAgICAgICAgdHYudHZfc2VjICs9IHR2LnR2X3VzZWMgLyAxMDAwMDAwTDsKICAgICAgICB0di50dl91c2VjICU9IDEwMDAwMDBMOwogICAgICAgIHJwLT5leHBpcmUgPSB0djsKCiAgICAgICAgLyoKICAgICAgICAgKiBYWCBsb2NrIHNob3VsZCBiZSBwZXIgc2Vzc2lvbiAhIAogICAgICAgICAqLwogICAgICAgIHNubXBfcmVzX2xvY2soTVRfTElCUkFSWV9JRCwgTVRfTElCX1NFU1NJT04pOwogICAgICAgIGlmIChpc3AtPnJlcXVlc3RzRW5kKSB7CiAgICAgICAgICAgIHJwLT5uZXh0X3JlcXVlc3QgPSBpc3AtPnJlcXVlc3RzRW5kLT5uZXh0X3JlcXVlc3Q7CiAgICAgICAgICAgIGlzcC0+cmVxdWVzdHNFbmQtPm5leHRfcmVxdWVzdCA9IHJwOwogICAgICAgICAgICBpc3AtPnJlcXVlc3RzRW5kID0gcnA7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgcnAtPm5leHRfcmVxdWVzdCA9IGlzcC0+cmVxdWVzdHM7CiAgICAgICAgICAgIGlzcC0+cmVxdWVzdHMgPSBycDsKICAgICAgICAgICAgaXNwLT5yZXF1ZXN0c0VuZCA9IHJwOwogICAgICAgIH0KICAgICAgICBzbm1wX3Jlc191bmxvY2soTVRfTElCUkFSWV9JRCwgTVRfTElCX1NFU1NJT04pOwogICAgfSBlbHNlIHsKICAgICAgICAvKgogICAgICAgICAqIE5vIHJlc3BvbnNlIGV4cGVjdGVkLi4uICAKICAgICAgICAgKi8KICAgICAgICBpZiAocmVxaWQpIHsKICAgICAgICAgICAgLyoKICAgICAgICAgICAgICogRnJlZSB2MSBvciB2MiBUUkFQIFBEVSBpZmYgbm8gZXJyb3IgIAogICAgICAgICAgICAgKi8KICAgICAgICAgICAgc25tcF9mcmVlX3BkdShwZHUpOwogICAgICAgIH0KICAgIH0KCiAgICByZXR1cm4gcmVxaWQ7Cn0KCmludApzbm1wX3Nlc3NfYXN5bmNfc2VuZCh2b2lkICpzZXNzcCwKICAgICAgICAgICAgICAgICAgICAgbmV0c25tcF9wZHUgKnBkdSwKICAgICAgICAgICAgICAgICAgICAgc25tcF9jYWxsYmFjayBjYWxsYmFjaywgdm9pZCAqY2JfZGF0YSkKewogICAgaW50ICAgICAgICAgICAgIHJjOwoKICAgIGlmIChzZXNzcCA9PSBOVUxMKSB7CiAgICAgICAgc25tcF9lcnJubyA9IFNOTVBFUlJfQkFEX1NFU1NJT047ICAgICAgIC8qTVRDUklUSUNBTF9SRVNPVVJDRSAqLwogICAgICAgIHJldHVybiAoMCk7CiAgICB9CiAgICAvKgogICAgICogc2VuZCBwZHUKICAgICAqLwogICAgcmMgPSBfc2Vzc19hc3luY19zZW5kKHNlc3NwLCBwZHUsIGNhbGxiYWNrLCBjYl9kYXRhKTsKICAgIGlmIChyYyA9PSAwKSB7CiAgICAgICAgc3RydWN0IHNlc3Npb25fbGlzdCAqcHNsOwogICAgICAgIG5ldHNubXBfc2Vzc2lvbiAqcHNzOwogICAgICAgIHBzbCA9IChzdHJ1Y3Qgc2Vzc2lvbl9saXN0ICopIHNlc3NwOwogICAgICAgIHBzcyA9IHBzbC0+c2Vzc2lvbjsKICAgICAgICBTRVRfU05NUF9FUlJPUihwc3MtPnNfc25tcF9lcnJubyk7CiAgICB9CiAgICByZXR1cm4gcmM7Cn0KCgovKgogKiBGcmVlcyB0aGUgdmFyaWFibGUgYW5kIGFueSBtYWxsb2MnZCBkYXRhIGFzc29jaWF0ZWQgd2l0aCBpdC4KICovCnZvaWQKc25tcF9mcmVlX3ZhcihuZXRzbm1wX3ZhcmlhYmxlX2xpc3QgKiB2YXIpCnsKICAgIGlmICghdmFyKQogICAgICAgIHJldHVybjsKCiAgICBpZiAodmFyLT5uYW1lICE9IHZhci0+bmFtZV9sb2MpCiAgICAgICAgU05NUF9GUkVFKHZhci0+bmFtZSk7CiAgICBpZiAodmFyLT52YWwuc3RyaW5nICE9IHZhci0+YnVmKQogICAgICAgIFNOTVBfRlJFRSh2YXItPnZhbC5zdHJpbmcpOwogICAgaWYgKHZhci0+ZGF0YSkgewogICAgICAgIGlmICh2YXItPmRhdGFGcmVlSG9vaykgewogICAgICAgICAgICB2YXItPmRhdGFGcmVlSG9vayh2YXItPmRhdGEpOwogICAgICAgICAgICB2YXItPmRhdGEgPSBOVUxMOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIFNOTVBfRlJFRSh2YXItPmRhdGEpOwogICAgICAgIH0KICAgIH0KCiAgICBmcmVlKChjaGFyICopIHZhcik7Cn0KCnZvaWQKc25tcF9mcmVlX3ZhcmJpbmQobmV0c25tcF92YXJpYWJsZV9saXN0ICogdmFyKQp7CiAgICBuZXRzbm1wX3ZhcmlhYmxlX2xpc3QgKnB0cjsKICAgIHdoaWxlICh2YXIpIHsKICAgICAgICBwdHIgPSB2YXItPm5leHRfdmFyaWFibGU7CiAgICAgICAgc25tcF9mcmVlX3Zhcih2YXIpOwogICAgICAgIHZhciA9IHB0cjsKICAgIH0KfQoKLyoKICogRnJlZXMgdGhlIHBkdSBhbmQgYW55IG1hbGxvYydkIGRhdGEgYXNzb2NpYXRlZCB3aXRoIGl0LgogKi8Kdm9pZApzbm1wX2ZyZWVfcGR1KG5ldHNubXBfcGR1ICpwZHUpCnsKICAgIHN0cnVjdCBzbm1wX3NlY21vZF9kZWYgKnNwdHI7CgogICAgaWYgKCFwZHUpCiAgICAgICAgcmV0dXJuOwoKICAgIC8qCiAgICAgKiBJZiB0aGUgY29tbWFuZCBmaWVsZCBpcyBlbXB0eSwgdGhhdCBwcm9iYWJseSBpbmRpY2F0ZXMKICAgICAqICAgdGhhdCB0aGlzIFBEVSBzdHJ1Y3R1cmUgaGFzIGFscmVhZHkgYmVlbiBmcmVlZC4KICAgICAqICAgTG9nIGEgd2FybmluZyBhbmQgcmV0dXJuIChyYXRoZXIgdGhhbiBmcmVlaW5nIHRoaW5ncyBhZ2FpbikKICAgICAqCiAgICAgKiBOb3RlIHRoYXQgdGhpcyBkb2VzIG5vdCBwaWNrIHVwIGR1YWwtZnJlZXMgd2hlcmUgdGhlCiAgICAgKiAgIG1lbW9yeSBpcyBzZXQgdG8gcmFuZG9tIGp1bmssIHdoaWNoIGlzIHByb2JhYmx5IG1vcmUgc2VyaW91cy4KICAgICAqCiAgICAgKiBya3M6IHdoaWxlIHRoaXMgaXMgYSBnb29kIGlkZWEsIHRoZXJlIGFyZSB0d28gcHJvYmxlbXMuCiAgICAgKiAgICAgICAgIDEpIGFnZW50eCBzZXRzIGNvbW1hbmQgdG8gMCBpbiBzb21lIGNhc2VzCiAgICAgKiAgICAgICAgIDIpIGFjY29yZGluZyB0byBXZXMsIGEgYmFkIGRlY29kZSBvZiBhIHYzIG1lc3NhZ2UgY291bGQKICAgICAqICAgICAgICAgICAgcmVzdWx0IGluIGEgMCBhdCB0aGlzIG9mZnNldC4KICAgICAqICAgICAgc28gSSdtIGNvbW1lbnRpbmcgaXQgb3V0IHVudGlsIGEgYmV0dGVyIHNvbHV0aW9uIGlzIGZvdW5kLgogICAgICogICAgICBub3RlIHRoYXQgSSdtIGxlYXZpbmcgdGhlIG1lbXNldCwgYmVsb3cuLi4uCiAgICAgKgogICAgaWYgKHBkdS0+Y29tbWFuZCA9PSAwKSB7CiAgICAgICAgc25tcF9sb2coTE9HX1dBUk5JTkcsICJzbm1wX2ZyZWVfcGR1IHByb2JhYmx5IGNhbGxlZCB0d2ljZVxuIik7CiAgICAgICAgcmV0dXJuOwogICAgfQogICAgICovCiAgICBpZiAoKHNwdHIgPSBmaW5kX3NlY19tb2QocGR1LT5zZWN1cml0eU1vZGVsKSkgIT0gTlVMTCAmJgogICAgICAgIHNwdHItPnBkdV9mcmVlICE9IE5VTEwpIHsKICAgICAgICAoKnNwdHItPnBkdV9mcmVlKSAocGR1KTsKICAgIH0KICAgIHNubXBfZnJlZV92YXJiaW5kKHBkdS0+dmFyaWFibGVzKTsKICAgIFNOTVBfRlJFRShwZHUtPmVudGVycHJpc2UpOwogICAgU05NUF9GUkVFKHBkdS0+Y29tbXVuaXR5KTsKICAgIFNOTVBfRlJFRShwZHUtPmNvbnRleHRFbmdpbmVJRCk7CiAgICBTTk1QX0ZSRUUocGR1LT5zZWN1cml0eUVuZ2luZUlEKTsKICAgIFNOTVBfRlJFRShwZHUtPmNvbnRleHROYW1lKTsKICAgIFNOTVBfRlJFRShwZHUtPnNlY3VyaXR5TmFtZSk7CiAgICBTTk1QX0ZSRUUocGR1LT50cmFuc3BvcnRfZGF0YSk7CiAgICBtZW1zZXQocGR1LCAwLCBzaXplb2YobmV0c25tcF9wZHUpKTsKICAgIGZyZWUoKGNoYXIgKikgcGR1KTsKfQoKbmV0c25tcF9wZHUgICAgKgpzbm1wX2NyZWF0ZV9zZXNzX3BkdShuZXRzbm1wX3RyYW5zcG9ydCAqdHJhbnNwb3J0LCB2b2lkICpvcGFxdWUsCiAgICAgICAgICAgICAgICAgICAgIHNpemVfdCBvbGVuZ3RoKQp7CiAgICBuZXRzbm1wX3BkdSAqcGR1ID0gKG5ldHNubXBfcGR1ICopY2FsbG9jKDEsIHNpemVvZihuZXRzbm1wX3BkdSkpOwogICAgaWYgKHBkdSA9PSBOVUxMKSB7CiAgICAgICAgREVCVUdNU0dUTCgoInNlc3NfcHJvY2Vzc19wYWNrZXQiLCAiY2FuJ3QgbWFsbG9jIHNwYWNlIGZvciBQRFVcbiIpKTsKICAgICAgICByZXR1cm4gTlVMTDsKICAgIH0KCiAgICAvKgogICAgICogU2F2ZSB0aGUgdHJhbnNwb3J0LWxldmVsIGRhdGEgc3BlY2lmaWMgdG8gdGhpcyByZWNlcHRpb24gKGUuZy4gVURQCiAgICAgKiBzb3VyY2UgYWRkcmVzcykuICAKICAgICAqLwoKICAgIHBkdS0+dHJhbnNwb3J0X2RhdGEgPSBvcGFxdWU7CiAgICBwZHUtPnRyYW5zcG9ydF9kYXRhX2xlbmd0aCA9IG9sZW5ndGg7CiAgICBwZHUtPnREb21haW4gPSB0cmFuc3BvcnQtPmRvbWFpbjsKICAgIHBkdS0+dERvbWFpbkxlbiA9IHRyYW5zcG9ydC0+ZG9tYWluX2xlbmd0aDsKICAgIHJldHVybiBwZHU7Cn0KCgovKgogKiBUaGlzIGZ1bmN0aW9uIHByb2Nlc3NlcyBhIGNvbXBsZXRlIChhY2NvcmRpbmcgdG8gYXNuX2NoZWNrX3BhY2tldCBvciB0aGUKICogQWdlbnRYIGVxdWl2YWxlbnQpIHBhY2tldCwgcGFyc2luZyBpdCBpbnRvIGEgUERVIGFuZCBjYWxsaW5nIHRoZSByZWxldmFudAogKiBjYWxsYmFja3MuICBPbiBlbnRyeSwgcGFja2V0cHRyIHBvaW50cyBhdCB0aGUgcGFja2V0IGluIHRoZSBzZXNzaW9uJ3MKICogYnVmZmVyIGFuZCBsZW5ndGggaXMgdGhlIGxlbmd0aCBvZiB0aGUgcGFja2V0LiAgCiAqLwoKc3RhdGljIGludApfc2Vzc19wcm9jZXNzX3BhY2tldCh2b2lkICpzZXNzcCwgbmV0c25tcF9zZXNzaW9uICogc3AsCiAgICAgICAgICAgICAgICAgICAgIHN0cnVjdCBzbm1wX2ludGVybmFsX3Nlc3Npb24gKmlzcCwKICAgICAgICAgICAgICAgICAgICAgbmV0c25tcF90cmFuc3BvcnQgKnRyYW5zcG9ydCwKICAgICAgICAgICAgICAgICAgICAgdm9pZCAqb3BhcXVlLCBpbnQgb2xlbmd0aCwKICAgICAgICAgICAgICAgICAgICAgdV9jaGFyICogcGFja2V0cHRyLCBpbnQgbGVuZ3RoKQp7CiAgc3RydWN0IHNlc3Npb25fbGlzdCAqc2xwID0gKHN0cnVjdCBzZXNzaW9uX2xpc3QgKikgc2Vzc3A7CiAgbmV0c25tcF9wZHUgICAgKnBkdTsKICBuZXRzbm1wX3JlcXVlc3RfbGlzdCAqcnAsICpvcnAgPSBOVUxMOwogIHN0cnVjdCBzbm1wX3NlY21vZF9kZWYgKnNwdHI7CiAgaW50ICAgICAgICAgICAgIHJldCA9IDAsIGhhbmRsZWQgPSAwOwoKICBERUJVR01TR1RMKCgic2Vzc19wcm9jZXNzX3BhY2tldCIsCgkgICAgICAic2Vzc2lvbiAlcCBmZCAlZCBwa3QgJXAgbGVuZ3RoICVkXG4iLCBzZXNzcCwKCSAgICAgIHRyYW5zcG9ydC0+c29jaywgcGFja2V0cHRyLCBsZW5ndGgpKTsKCiAgaWYgKG5ldHNubXBfZHNfZ2V0X2Jvb2xlYW4oTkVUU05NUF9EU19MSUJSQVJZX0lELCAKCQkJICAgICBORVRTTk1QX0RTX0xJQl9EVU1QX1BBQ0tFVCkpIHsKICAgIGlmICh0cmFuc3BvcnQtPmZfZm10YWRkciAhPSBOVUxMKSB7CiAgICAgIGNoYXIgKmFkZHJ0eHQgPSB0cmFuc3BvcnQtPmZfZm10YWRkcih0cmFuc3BvcnQsIG9wYXF1ZSwgb2xlbmd0aCk7CiAgICAgIGlmIChhZGRydHh0ICE9IE5VTEwpIHsKCXNubXBfbG9nKExPR19ERUJVRywgIlxuUmVjZWl2ZWQgJWQgYnl0ZXMgZnJvbSAlc1xuIiwKCQkgbGVuZ3RoLCBhZGRydHh0KTsKCVNOTVBfRlJFRShhZGRydHh0KTsKICAgICAgfSBlbHNlIHsKCXNubXBfbG9nKExPR19ERUJVRywgIlxuUmVjZWl2ZWQgJWQgYnl0ZXMgZnJvbSA8VU5LTk9XTj5cbiIsCgkJIGxlbmd0aCk7CiAgICAgIH0KICAgIH0KICAgIHhkdW1wKHBhY2tldHB0ciwgbGVuZ3RoLCAiIik7CiAgfQoKICAvKgogICAqIERvIHRyYW5zcG9ydC1sZXZlbCBmaWx0ZXJpbmcgKGUuZy4gSVAtYWRkcmVzcyBiYXNlZCBhbGxvdy9kZW55KS4gIAogICAqLwoKICBpZiAoaXNwLT5ob29rX3ByZSkgewogICAgaWYgKGlzcC0+aG9va19wcmUoc3AsIHRyYW5zcG9ydCwgb3BhcXVlLCBvbGVuZ3RoKSA9PSAwKSB7CiAgICAgIERFQlVHTVNHVEwoKCJzZXNzX3Byb2Nlc3NfcGFja2V0IiwgInByZS1wYXJzZSBmYWlsXG4iKSk7CiAgICAgIGlmIChvcGFxdWUgIT0gTlVMTCkgewoJU05NUF9GUkVFKG9wYXF1ZSk7CiAgICAgIH0KICAgICAgcmV0dXJuIC0xOwogICAgfQogIH0KCiAgaWYgKGlzcC0+aG9va19jcmVhdGVfcGR1KSB7CiAgICBwZHUgPSBpc3AtPmhvb2tfY3JlYXRlX3BkdSh0cmFuc3BvcnQsIG9wYXF1ZSwgb2xlbmd0aCk7CiAgfSBlbHNlIHsKICAgIHBkdSA9IHNubXBfY3JlYXRlX3Nlc3NfcGR1KHRyYW5zcG9ydCwgb3BhcXVlLCBvbGVuZ3RoKTsKICB9CiAgaWYgKHBkdSA9PSBOVUxMKSB7CiAgICBzbm1wX2xvZyhMT0dfRVJSLCAicGR1IGZhaWxlZCB0byBiZSBjcmVhdGVkXG4iKTsKICAgIGlmIChvcGFxdWUgIT0gTlVMTCkgewogICAgICBTTk1QX0ZSRUUob3BhcXVlKTsKICAgIH0KICAgIHJldHVybiAtMTsKICB9CgogIGlmIChpc3AtPmhvb2tfcGFyc2UpIHsKICAgIHJldCA9IGlzcC0+aG9va19wYXJzZShzcCwgcGR1LCBwYWNrZXRwdHIsIGxlbmd0aCk7CiAgfSBlbHNlIHsKICAgIHJldCA9IHNubXBfcGFyc2Uoc2Vzc3AsIHNwLCBwZHUsIHBhY2tldHB0ciwgbGVuZ3RoKTsKICB9CgogIGlmIChyZXQgIT0gU05NUF9FUlJfTk9FUlJPUikgewogICAgREVCVUdNU0dUTCgoInNlc3NfcHJvY2Vzc19wYWNrZXQiLCAicGFyc2UgZmFpbFxuIikpOwogIH0KCiAgaWYgKGlzcC0+aG9va19wb3N0KSB7CiAgICBpZiAoaXNwLT5ob29rX3Bvc3Qoc3AsIHBkdSwgcmV0KSA9PSAwKSB7CiAgICAgIERFQlVHTVNHVEwoKCJzZXNzX3Byb2Nlc3NfcGFja2V0IiwgInBvc3QtcGFyc2UgZmFpbFxuIikpOwogICAgICByZXQgPSBTTk1QRVJSX0FTTl9QQVJTRV9FUlI7CiAgICB9CiAgfQoKICBpZiAocmV0ICE9IFNOTVBfRVJSX05PRVJST1IpIHsKICAgIC8qCiAgICAgKiBDYWxsIHRoZSBzZWN1cml0eSBtb2RlbCB0byBmcmVlIGFueSBzZWN1cml0eVN0YXRlUmVmIHN1cHBsaWVkIHcvIG1zZy4gIAogICAgICovCiAgICBpZiAocGR1LT5zZWN1cml0eVN0YXRlUmVmICE9IE5VTEwpIHsKICAgICAgc3B0ciA9IGZpbmRfc2VjX21vZChwZHUtPnNlY3VyaXR5TW9kZWwpOwogICAgICBpZiAoc3B0ciAhPSBOVUxMKSB7CglpZiAoc3B0ci0+cGR1X2ZyZWVfc3RhdGVfcmVmICE9IE5VTEwpIHsKCSAgKCpzcHRyLT5wZHVfZnJlZV9zdGF0ZV9yZWYpIChwZHUtPnNlY3VyaXR5U3RhdGVSZWYpOwoJfSBlbHNlIHsKCSAgc25tcF9sb2coTE9HX0VSUiwKCQkgICAiU2VjdXJpdHkgTW9kZWwgJWQgY2FuJ3QgZnJlZSBzdGF0ZSByZWZlcmVuY2VzXG4iLAoJCSAgIHBkdS0+c2VjdXJpdHlNb2RlbCk7Cgl9CiAgICAgIH0gZWxzZSB7Cglzbm1wX2xvZyhMT0dfRVJSLAoJCSAiQ2FuJ3QgZmluZCBzZWN1cml0eSBtb2RlbCB0byBmcmVlIHB0cjogJWRcbiIsCgkJIHBkdS0+c2VjdXJpdHlNb2RlbCk7CiAgICAgIH0KICAgICAgcGR1LT5zZWN1cml0eVN0YXRlUmVmID0gTlVMTDsKICAgIH0KICAgIHNubXBfZnJlZV9wZHUocGR1KTsKICAgIHJldHVybiAtMTsKICB9CgogIGlmIChwZHUtPmZsYWdzICYgVUNEX01TR19GTEFHX1JFU1BPTlNFX1BEVSkgewogICAgLyoKICAgICAqIENhbGwgVVNNIHRvIGZyZWUgYW55IHNlY3VyaXR5U3RhdGVSZWYgc3VwcGxpZWQgd2l0aCB0aGUgbWVzc2FnZS4gIAogICAgICovCiAgICBpZiAocGR1LT5zZWN1cml0eVN0YXRlUmVmKSB7CiAgICAgIHNwdHIgPSBmaW5kX3NlY19tb2QocGR1LT5zZWN1cml0eU1vZGVsKTsKICAgICAgaWYgKHNwdHIpIHsKCWlmIChzcHRyLT5wZHVfZnJlZV9zdGF0ZV9yZWYpIHsKCSAgKCpzcHRyLT5wZHVfZnJlZV9zdGF0ZV9yZWYpIChwZHUtPnNlY3VyaXR5U3RhdGVSZWYpOwoJfSBlbHNlIHsKCSAgc25tcF9sb2coTE9HX0VSUiwKCQkgICAiU2VjdXJpdHkgTW9kZWwgJWQgY2FuJ3QgZnJlZSBzdGF0ZSByZWZlcmVuY2VzXG4iLAoJCSAgIHBkdS0+c2VjdXJpdHlNb2RlbCk7Cgl9CiAgICAgIH0gZWxzZSB7Cglzbm1wX2xvZyhMT0dfRVJSLAoJCSAiQ2FuJ3QgZmluZCBzZWN1cml0eSBtb2RlbCB0byBmcmVlIHB0cjogJWRcbiIsCgkJIHBkdS0+c2VjdXJpdHlNb2RlbCk7CiAgICAgIH0KICAgICAgcGR1LT5zZWN1cml0eVN0YXRlUmVmID0gTlVMTDsKICAgIH0KCiAgICBmb3IgKHJwID0gaXNwLT5yZXF1ZXN0czsgcnA7IG9ycCA9IHJwLCBycCA9IHJwLT5uZXh0X3JlcXVlc3QpIHsKICAgICAgc25tcF9jYWxsYmFjayAgIGNhbGxiYWNrOwogICAgICB2b2lkICAgICAgICAgICAqbWFnaWM7CgogICAgICBpZiAocGR1LT52ZXJzaW9uID09IFNOTVBfVkVSU0lPTl8zKSB7CgkvKgoJICogbXNnSWQgbXVzdCBtYXRjaCBmb3IgdjMgbWVzc2FnZXMuICAKCSAqLwoJaWYgKHJwLT5tZXNzYWdlX2lkICE9IHBkdS0+bXNnaWQpIHsKCSAgY29udGludWU7Cgl9CgoJLyoKCSAqIENoZWNrIHRoYXQgbWVzc2FnZSBmaWVsZHMgbWF0Y2ggb3JpZ2luYWwsIGlmIG5vdCwgbm8gZnVydGhlcgoJICogcHJvY2Vzc2luZy4gIAoJICovCglpZiAoIXNubXB2M192ZXJpZnlfbXNnKHJwLCBwZHUpKSB7CgkgIGJyZWFrOwoJfQogICAgICB9IGVsc2UgewoJaWYgKHJwLT5yZXF1ZXN0X2lkICE9IHBkdS0+cmVxaWQpIHsKCSAgY29udGludWU7Cgl9CiAgICAgIH0KCiAgICAgIGlmIChycC0+Y2FsbGJhY2spIHsKCWNhbGxiYWNrID0gcnAtPmNhbGxiYWNrOwoJbWFnaWMgPSBycC0+Y2JfZGF0YTsKICAgICAgfSBlbHNlIHsKCWNhbGxiYWNrID0gc3AtPmNhbGxiYWNrOwoJbWFnaWMgPSBzcC0+Y2FsbGJhY2tfbWFnaWM7CiAgICAgIH0KICAgICAgaGFuZGxlZCA9IDE7CgogICAgICAvKgogICAgICAgKiBNVFIgc25tcF9yZXNfbG9jayhNVF9MSUJSQVJZX0lELCBNVF9MSUJfU0VTU0lPTik7ICA/KiBYWCBsb2NrCiAgICAgICAqIHNob3VsZCBiZSBwZXIgc2Vzc2lvbiAhIAogICAgICAgKi8KCiAgICAgIGlmIChjYWxsYmFjayA9PSBOVUxMCgkgIHx8IGNhbGxiYWNrKE5FVFNOTVBfQ0FMTEJBQ0tfT1BfUkVDRUlWRURfTUVTU0FHRSwgc3AsCgkJICAgICAgcGR1LT5yZXFpZCwgcGR1LCBtYWdpYykgPT0gMSkgewoJaWYgKHBkdS0+Y29tbWFuZCA9PSBTTk1QX01TR19SRVBPUlQpIHsKCSAgaWYgKHNwLT5zX3NubXBfZXJybm8gPT0gU05NUEVSUl9OT1RfSU5fVElNRV9XSU5ET1cgfHwKCSAgICAgIHNubXB2M19nZXRfcmVwb3J0X3R5cGUocGR1KSA9PQoJICAgICAgU05NUEVSUl9OT1RfSU5fVElNRV9XSU5ET1cpIHsKCSAgICAvKgoJICAgICAqIHRyaWdnZXIgaW1tZWRpYXRlIHJldHJ5IG9uIHJlY292ZXJhYmxlIFJlcG9ydHMgCgkgICAgICogKiAobm90SW5UaW1lV2luZG93KSwgaW5jcl9yZXRyaWVzID09IFRSVUUgdG8gcHJldmVudAoJICAgICAqICogaW5pZmluaXRlIHJlc2VuZCAgICAgICAgICAgICAgICAgICAgICAKCSAgICAgKi8KCSAgICBpZiAocnAtPnJldHJpZXMgPD0gc3AtPnJldHJpZXMpIHsKCSAgICAgIHNubXBfcmVzZW5kX3JlcXVlc3Qoc2xwLCBycCwgVFJVRSk7CgkgICAgICBicmVhazsKCSAgICB9IGVsc2UgewoJICAgICAgLyogV2UncmUgZG9uZSB3aXRoIHJldHJpZXMsIHNvIG5vIGxvbmdlciB3YWl0aW5nIGZvciBhIHJlc3BvbnNlICovCgkgICAgICBpZiAobWFnaWMpIHsKCQkoKHN0cnVjdCBzeW5jaF9zdGF0ZSopbWFnaWMpLT53YWl0aW5nID0gMDsKCSAgICAgIH0KCSAgICB9CgkgIH0gZWxzZSB7CgkgICAgaWYgKFNOTVBWM19JR05PUkVfVU5BVVRIX1JFUE9SVFMpIHsKCSAgICAgIGJyZWFrOwoJICAgIH0gZWxzZSB7IC8qIFNldCB0aGUgc3RhdGUgdG8gbm8gbG9uZ2VyIGJlIHdhaXRpbmcsIHNpbmNlIHdlJ3JlIGRvbmUgd2l0aCByZXRyaWVzICovCgkgICAgICBpZiAobWFnaWMpIHsKCQkoKHN0cnVjdCBzeW5jaF9zdGF0ZSopbWFnaWMpLT53YWl0aW5nID0gMDsKCSAgICAgIH0KCSAgICB9CgkgIH0KCgkgIC8qCgkgICAqIEhhbmRsZSBlbmdpbmVJRCBkaXNjb3ZlcnkuICAKCSAgICovCgkgIGlmICghc3AtPnNlY3VyaXR5RW5naW5lSURMZW4gJiYgcGR1LT5zZWN1cml0eUVuZ2luZUlETGVuKSB7CgkgICAgc3AtPnNlY3VyaXR5RW5naW5lSUQgPQoJICAgICAgKHVfY2hhciAqKSBtYWxsb2MocGR1LT5zZWN1cml0eUVuZ2luZUlETGVuKTsKCSAgICBpZiAoc3AtPnNlY3VyaXR5RW5naW5lSUQgPT0gTlVMTCkgewoJICAgICAgLyoKCSAgICAgICAqIFRPRE8gRklYOiByZWNvdmVyIGFmdGVyIG1lc3NhZ2UgY2FsbGJhY2sgKj8KICAgICAgICAgICAgICAgKi8KCSAgICAgIHJldHVybiAtMTsKCSAgICB9CgkgICAgbWVtY3B5KHNwLT5zZWN1cml0eUVuZ2luZUlELCBwZHUtPnNlY3VyaXR5RW5naW5lSUQsCgkJICAgcGR1LT5zZWN1cml0eUVuZ2luZUlETGVuKTsKCSAgICBzcC0+c2VjdXJpdHlFbmdpbmVJRExlbiA9IHBkdS0+c2VjdXJpdHlFbmdpbmVJRExlbjsKCSAgICBpZiAoIXNwLT5jb250ZXh0RW5naW5lSURMZW4pIHsKCSAgICAgIHNwLT5jb250ZXh0RW5naW5lSUQgPQoJCSh1X2NoYXIgKikgbWFsbG9jKHBkdS0+CgkJCQkgIHNlY3VyaXR5RW5naW5lSURMZW4pOwoJICAgICAgaWYgKHNwLT5jb250ZXh0RW5naW5lSUQgPT0gTlVMTCkgewoJCS8qCgkJICogVE9ETyBGSVg6IHJlY292ZXIgYWZ0ZXIgbWVzc2FnZSBjYWxsYmFjayAqPwoJCSAqLwogICAgICAgICAgICAgICAgcmV0dXJuIC0xOwoJICAgICAgfQoJICAgICAgbWVtY3B5KHNwLT5jb250ZXh0RW5naW5lSUQsCgkJICAgICBwZHUtPnNlY3VyaXR5RW5naW5lSUQsCgkJICAgICBwZHUtPnNlY3VyaXR5RW5naW5lSURMZW4pOwoJICAgICAgc3AtPmNvbnRleHRFbmdpbmVJRExlbiA9CgkJcGR1LT5zZWN1cml0eUVuZ2luZUlETGVuOwoJICAgIH0KCSAgfQoJfQoKCS8qCgkgKiBTdWNjZXNzZnVsLCBzbyBkZWxldGUgcmVxdWVzdC4gIAoJICovCglpZiAoaXNwLT5yZXF1ZXN0cyA9PSBycCkgewoJICBpc3AtPnJlcXVlc3RzID0gcnAtPm5leHRfcmVxdWVzdDsKCSAgaWYgKGlzcC0+cmVxdWVzdHNFbmQgPT0gcnApIHsKCSAgICBpc3AtPnJlcXVlc3RzRW5kID0gTlVMTDsKCSAgfQoJfSBlbHNlIHsKCSAgb3JwLT5uZXh0X3JlcXVlc3QgPSBycC0+bmV4dF9yZXF1ZXN0OwoJICBpZiAoaXNwLT5yZXF1ZXN0c0VuZCA9PSBycCkgewoJICAgIGlzcC0+cmVxdWVzdHNFbmQgPSBvcnA7CgkgIH0KCX0KCXNubXBfZnJlZV9wZHUocnAtPnBkdSk7CglmcmVlKChjaGFyICopIHJwKTsKCS8qCgkgKiBUaGVyZSBzaG91bGRuJ3QgYmUgYW55IG1vcmUgcmVxdWVzdHMgd2l0aCB0aGUgc2FtZSByZXFpZC4gIAoJICovCglicmVhazsKICAgICAgfQogICAgICAvKgogICAgICAgKiBNVFIgc25tcF9yZXNfdW5sb2NrKE1UX0xJQlJBUllfSUQsIE1UX0xJQl9TRVNTSU9OKTsgID8qIFhYIGxvY2sgc2hvdWxkIGJlIHBlciBzZXNzaW9uICEgCiAgICAgICAqLwogICAgfQogIH0gZWxzZSB7CiAgICBpZiAoc3AtPmNhbGxiYWNrKSB7CiAgICAgIC8qCiAgICAgICAqIE1UUiBzbm1wX3Jlc19sb2NrKE1UX0xJQlJBUllfSUQsIE1UX0xJQl9TRVNTSU9OKTsgCiAgICAgICAqLwogICAgICBoYW5kbGVkID0gMTsKICAgICAgc3AtPmNhbGxiYWNrKE5FVFNOTVBfQ0FMTEJBQ0tfT1BfUkVDRUlWRURfTUVTU0FHRSwKCQkgICBzcCwgcGR1LT5yZXFpZCwgcGR1LCBzcC0+Y2FsbGJhY2tfbWFnaWMpOwogICAgICAvKgogICAgICAgKiBNVFIgc25tcF9yZXNfdW5sb2NrKE1UX0xJQlJBUllfSUQsIE1UX0xJQl9TRVNTSU9OKTsgCiAgICAgICAqLwogICAgfQogIH0KCiAgLyoKICAgKiBDYWxsIFVTTSB0byBmcmVlIGFueSBzZWN1cml0eVN0YXRlUmVmIHN1cHBsaWVkIHdpdGggdGhlIG1lc3NhZ2UuICAKICAgKi8KICBpZiAocGR1ICE9IE5VTEwgJiYgcGR1LT5zZWN1cml0eVN0YXRlUmVmICYmCiAgICAgIHBkdS0+Y29tbWFuZCA9PSBTTk1QX01TR19UUkFQMikgewogICAgc3B0ciA9IGZpbmRfc2VjX21vZChwZHUtPnNlY3VyaXR5TW9kZWwpOwogICAgaWYgKHNwdHIpIHsKICAgICAgaWYgKHNwdHItPnBkdV9mcmVlX3N0YXRlX3JlZikgewoJKCpzcHRyLT5wZHVfZnJlZV9zdGF0ZV9yZWYpIChwZHUtPnNlY3VyaXR5U3RhdGVSZWYpOwogICAgICB9IGVsc2UgewoJc25tcF9sb2coTE9HX0VSUiwKCQkgIlNlY3VyaXR5IE1vZGVsICVkIGNhbid0IGZyZWUgc3RhdGUgcmVmZXJlbmNlc1xuIiwKCQkgcGR1LT5zZWN1cml0eU1vZGVsKTsKICAgICAgfQogICAgfSBlbHNlIHsKICAgICAgc25tcF9sb2coTE9HX0VSUiwKCSAgICAgICAiQ2FuJ3QgZmluZCBzZWN1cml0eSBtb2RlbCB0byBmcmVlIHB0cjogJWRcbiIsCgkgICAgICAgcGR1LT5zZWN1cml0eU1vZGVsKTsKICAgIH0KICAgIHBkdS0+c2VjdXJpdHlTdGF0ZVJlZiA9IE5VTEw7CiAgfQoKICBpZiAoIWhhbmRsZWQpIHsKICAgIHNubXBfaW5jcmVtZW50X3N0YXRpc3RpYyhTVEFUX1NOTVBVTktOT1dOUERVSEFORExFUlMpOwogICAgREVCVUdNU0dUTCgoInNlc3NfcHJvY2Vzc19wYWNrZXQiLCAidW5oYW5kbGVkIFBEVVxuIikpOwogIH0KCiAgc25tcF9mcmVlX3BkdShwZHUpOwogIHJldHVybiAwOwp9CgovKgogKiBDaGVja3MgdG8gc2VlIGlmIGFueSBvZiB0aGUgZmQncyBzZXQgaW4gdGhlIGZkc2V0IGJlbG9uZyB0bwogKiBzbm1wLiAgRWFjaCBzb2NrZXQgd2l0aCBpdCdzIGZkIHNldCBoYXMgYSBwYWNrZXQgcmVhZCBmcm9tIGl0CiAqIGFuZCBzbm1wX3BhcnNlIGlzIGNhbGxlZCBvbiB0aGUgcGFja2V0IHJlY2VpdmVkLiAgVGhlIHJlc3VsdGluZyBwZHUKICogaXMgcGFzc2VkIHRvIHRoZSBjYWxsYmFjayByb3V0aW5lIGZvciB0aGF0IHNlc3Npb24uICBJZiB0aGUgY2FsbGJhY2sKICogcm91dGluZSByZXR1cm5zIHN1Y2Nlc3NmdWxseSwgdGhlIHBkdSBhbmQgaXQncyByZXF1ZXN0IGFyZSBkZWxldGVkLgogKi8Kdm9pZApzbm1wX3JlYWQoZmRfc2V0ICogZmRzZXQpCnsKICAgIHN0cnVjdCBzZXNzaW9uX2xpc3QgKnNscDsKICAgIHNubXBfcmVzX2xvY2soTVRfTElCUkFSWV9JRCwgTVRfTElCX1NFU1NJT04pOwogICAgZm9yIChzbHAgPSBTZXNzaW9uczsgc2xwOyBzbHAgPSBzbHAtPm5leHQpIHsKICAgICAgICBzbm1wX3Nlc3NfcmVhZCgodm9pZCAqKSBzbHAsIGZkc2V0KTsKICAgIH0KICAgIHNubXBfcmVzX3VubG9jayhNVF9MSUJSQVJZX0lELCBNVF9MSUJfU0VTU0lPTik7Cn0KCi8qCiAqIFNhbWUgYXMgc25tcF9yZWFkLCBidXQgd29ya3MganVzdCBvbmUgc2Vzc2lvbi4gCiAqIHJldHVybnMgMCBpZiBzdWNjZXNzLCAtMSBpZiBmYWlsIAogKiBNVFI6IGNhbid0IGxvY2sgaGVyZSBhbmQgYXQgc25tcF9yZWFkIAogKiBCZXdhcmUgcmVjdXJzaXZlIHNlbmQgbWF5YmUgaW5zaWRlIHNubXBfcmVhZCBjYWxsYmFjayBmdW5jdGlvbi4gCiAqLwppbnQKX3Nlc3NfcmVhZCh2b2lkICpzZXNzcCwgZmRfc2V0ICogZmRzZXQpCnsKICAgIHN0cnVjdCBzZXNzaW9uX2xpc3QgKnNscCA9IChzdHJ1Y3Qgc2Vzc2lvbl9saXN0ICopIHNlc3NwOwogICAgbmV0c25tcF9zZXNzaW9uICpzcCA9IHNscCA/IHNscC0+c2Vzc2lvbiA6IE5VTEw7CiAgICBzdHJ1Y3Qgc25tcF9pbnRlcm5hbF9zZXNzaW9uICppc3AgPSBzbHAgPyBzbHAtPmludGVybmFsIDogTlVMTDsKICAgIG5ldHNubXBfdHJhbnNwb3J0ICp0cmFuc3BvcnQgPSBzbHAgPyBzbHAtPnRyYW5zcG9ydCA6IE5VTEw7CiAgICBzaXplX3QgICAgICAgICAgcGR1bGVuID0gMCwgcnhidWZfbGVuID0gNjU1MzY7CiAgICB1X2NoYXIgICAgICAgICAqcnhidWYgPSBOVUxMOwogICAgaW50ICAgICAgICAgICAgIGxlbmd0aCA9IDAsIG9sZW5ndGggPSAwLCByYyA9IDA7CiAgICB2b2lkICAgICAgICAgICAqb3BhcXVlID0gTlVMTDsKCiAgICBpZiAoIXNwIHx8ICFpc3AgfHwgIXRyYW5zcG9ydCkgewogICAgICAgIERFQlVHTVNHVEwoKCJzZXNzX3JlYWQiLCAicmVhZCBmYWlsOiBjbG9zaW5nLi4uXG4iKSk7CiAgICAgICAgcmV0dXJuIDA7CiAgICB9CgogICAgLyogdG8gYXZvaWQgc3ViYWdlbnQgY3Jhc2ggKi8gCiAgICBpZiAodHJhbnNwb3J0LT5zb2NrIDwgMCkgeyAKICAgICAgICBzbm1wX2xvZyAoTE9HX0lORk8sICJ0cmFuc3BvcnQtPnNvY2sgZ290IG5lZ2F0aXZlIGZkIHZhbHVlICVkXG4iLCB0cmFuc3BvcnQtPnNvY2spOwogICAgICAgIHJldHVybiAwOyAKICAgIH0KCiAgICBpZiAoIWZkc2V0IHx8ICEoRkRfSVNTRVQodHJhbnNwb3J0LT5zb2NrLCBmZHNldCkpKSB7CiAgICAgICAgREVCVUdNU0dUTCgoInNlc3NfcmVhZCIsICJub3QgcmVhZGluZyAlZCAoZmRzZXQgJXAgc2V0ICVkKVxuIiwKICAgICAgICAgICAgICAgICAgICB0cmFuc3BvcnQtPnNvY2ssIGZkc2V0LAogICAgICAgICAgICAgICAgICAgIGZkc2V0ID8gRkRfSVNTRVQodHJhbnNwb3J0LT5zb2NrLCBmZHNldCkgOiAtOSkpOwogICAgICAgIHJldHVybiAwOwogICAgfQoKICAgIHNwLT5zX3NubXBfZXJybm8gPSAwOwogICAgc3AtPnNfZXJybm8gPSAwOwoKICAgIGlmICh0cmFuc3BvcnQtPmZsYWdzICYgTkVUU05NUF9UUkFOU1BPUlRfRkxBR19MSVNURU4pIHsKICAgICAgICBpbnQgICAgICAgICAgICAgZGF0YV9zb2NrID0gdHJhbnNwb3J0LT5mX2FjY2VwdCh0cmFuc3BvcnQpOwoKICAgICAgICBpZiAoZGF0YV9zb2NrID49IDApIHsKICAgICAgICAgICAgLyoKICAgICAgICAgICAgICogV2UndmUgc3VjY2Vzc2Z1bGx5IGFjY2VwdGVkIGEgbmV3IHN0cmVhbS1iYXNlZCBjb25uZWN0aW9uLgogICAgICAgICAgICAgKiBJdCdzIG5vdCB0b28gY2xlYXIgd2hhdCBzaG91bGQgaGFwcGVuIGhlcmUgaWYgd2UgYXJlIHVzaW5nIHRoZQogICAgICAgICAgICAgKiBzaW5nbGUtc2Vzc2lvbiBBUEkgYXQgdGhpcyBwb2ludC4gIEJhc2ljYWxseSBhICJzZXNzaW9uCiAgICAgICAgICAgICAqIGFjY2VwdGVkIiBjYWxsYmFjayBpcyBwcm9iYWJseSBuZWVkZWQgdG8gaGFuZCB0aGUgbmV3IHNlc3Npb24KICAgICAgICAgICAgICogb3ZlciB0byB0aGUgYXBwbGljYXRpb24uCiAgICAgICAgICAgICAqIAogICAgICAgICAgICAgKiBIb3dldmVyLCBmb3Igbm93LCBhcyBpbiB0aGUgb3JpZ2luYWwgc25tcF9hcGksIHdlIHdpbGwgQVNTVU1FCiAgICAgICAgICAgICAqIHRoYXQgd2UncmUgdXNpbmcgdGhlIHRyYWRpdGlvbmFsIEFQSSwgYW5kIHNpbXBseSBhZGQgdGhlIG5ldwogICAgICAgICAgICAgKiBzZXNzaW9uIHRvIHRoZSBsaXN0LiAgTm90ZSB3ZSBkb24ndCBoYXZlIHRvIGdldCB0aGUgU2Vzc2lvbgogICAgICAgICAgICAgKiBsaXN0IGxvY2sgaGVyZSwgYmVjYXVzZSB1bmRlciB0aGF0IGFzc3VtcHRpb24gd2UgYWxyZWFkeSBob2xkCiAgICAgICAgICAgICAqIGl0ICh0aGlzIGlzIGFsc28gd2h5IHdlIGRvbid0IGp1c3QgdXNlIHNubXBfYWRkKS4KICAgICAgICAgICAgICogCiAgICAgICAgICAgICAqIFRoZSBtb3JhbCBvZiB0aGUgc3RvcnkgaXM6IGRvbid0IHVzZSBsaXN0ZW5pbmcgc3RyZWFtLWJhc2VkCiAgICAgICAgICAgICAqIHRyYW5zcG9ydHMgaW4gYSBtdWx0aS10aHJlYWRlZCBlbnZpcm9ubWVudCBiZWNhdXNlIHNvbWV0aGluZwogICAgICAgICAgICAgKiB3aWxsIGdvIEhPUlJJQkxZIHdyb25nIChhbmQgYWxzbyB0aGF0IFNOTVAvVENQIGlzIG5vdCB0cml2aWFsKS4KICAgICAgICAgICAgICogCiAgICAgICAgICAgICAqIEFub3RoZXIgb3BlbiBpc3N1ZTogd2hhdCBzaG91bGQgaGFwcGVuIHRvIHNvY2tldHMgdGhhdCBoYXZlCiAgICAgICAgICAgICAqIGJlZW4gYWNjZXB0KCllZCBmcm9tIGEgbGlzdGVuaW5nIHNvY2tldCB3aGVuIHRoYXQgb3JpZ2luYWwKICAgICAgICAgICAgICogc29ja2V0IGlzIGNsb3NlZD8gIElmIHRoZXkgYXJlIGxlZnQgb3BlbiwgdGhlbiBhdHRlbXB0aW5nIHRvCiAgICAgICAgICAgICAqIHJlLW9wZW4gdGhlIGxpc3RlbmluZyBzb2NrZXQgd2lsbCBmYWlsLCB3aGljaCBpcyBzZW1hbnRpY2FsbHkKICAgICAgICAgICAgICogY29uZnVzaW5nLiAgUGVyaGFwcyB0aGVyZSBzaG91bGQgYmUgc29tZSBraW5kIG9mIGNoYWluaW5nIGluCiAgICAgICAgICAgICAqIHRoZSB0cmFuc3BvcnQgc3RydWN0dXJlIHNvIHRoYXQgdGhleSBjYW4gYWxsIGJlIGNsb3NlZC4KICAgICAgICAgICAgICogRGlzY3Vzcy4gIDstKQogICAgICAgICAgICAgKi8KCgkgICAgbmV0c25tcF90cmFuc3BvcnQgKm5ld190cmFuc3BvcnQ9bmV0c25tcF90cmFuc3BvcnRfY29weSh0cmFuc3BvcnQpOwogICAgICAgICAgICBpZiAobmV3X3RyYW5zcG9ydCAhPSBOVUxMKSB7CiAgICAgICAgICAgICAgICBzdHJ1Y3Qgc2Vzc2lvbl9saXN0ICpuc2xwID0gTlVMTDsKCiAgICAgICAgICAgICAgICBuZXdfdHJhbnNwb3J0LT5zb2NrID0gZGF0YV9zb2NrOwogICAgICAgICAgICAgICAgbmV3X3RyYW5zcG9ydC0+ZmxhZ3MgJj0gfk5FVFNOTVBfVFJBTlNQT1JUX0ZMQUdfTElTVEVOOwoKICAgICAgICAgICAgICAgIG5zbHAgPSAoc3RydWN0IHNlc3Npb25fbGlzdCAqKXNubXBfc2Vzc19hZGRfZXgoc3AsCgkJCSAgbmV3X3RyYW5zcG9ydCwgaXNwLT5ob29rX3ByZSwgaXNwLT5ob29rX3BhcnNlLAoJCQkgIGlzcC0+aG9va19wb3N0LCBpc3AtPmhvb2tfYnVpbGQsCgkJCSAgaXNwLT5ob29rX3JlYWxsb2NfYnVpbGQsIGlzcC0+Y2hlY2tfcGFja2V0LAoJCQkgIGlzcC0+aG9va19jcmVhdGVfcGR1KTsKCiAgICAgICAgICAgICAgICBpZiAobnNscCAhPSBOVUxMKSB7CiAgICAgICAgICAgICAgICAgICAgbnNscC0+bmV4dCA9IFNlc3Npb25zOwogICAgICAgICAgICAgICAgICAgIFNlc3Npb25zID0gbnNscDsKICAgICAgICAgICAgICAgICAgICAvKgogICAgICAgICAgICAgICAgICAgICAqIFRlbGwgdGhlIG5ldyBzZXNzaW9uIGFib3V0IGl0cyBleGlzdGFuY2UgaWYgcG9zc2libGUuCiAgICAgICAgICAgICAgICAgICAgICovCiAgICAgICAgICAgICAgICAgICAgREVCVUdNU0dUTCgoInNlc3NfcmVhZCIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgInBlcmZvcm0gY2FsbGJhY2sgd2l0aCBvcD1DT05ORUNUXG4iKSk7CiAgICAgICAgICAgICAgICAgICAgKHZvaWQpbnNscC0+c2Vzc2lvbi0+Y2FsbGJhY2soTkVUU05NUF9DQUxMQkFDS19PUF9DT05ORUNULAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIG5zbHAtPnNlc3Npb24sIDAsIE5VTEwsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc3AtPmNhbGxiYWNrX21hZ2ljKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHJldHVybiAwOwogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgICAgc3AtPnNfc25tcF9lcnJubyA9IFNOTVBFUlJfTUFMTE9DOwogICAgICAgICAgICAgICAgc3AtPnNfZXJybm8gPSBlcnJubzsKICAgICAgICAgICAgICAgIHNubXBfc2V0X2RldGFpbChzdHJlcnJvcihlcnJubykpOwogICAgICAgICAgICAgICAgcmV0dXJuIC0xOwogICAgICAgICAgICB9CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgc3AtPnNfc25tcF9lcnJubyA9IFNOTVBFUlJfQkFEX1JFQ1ZGUk9NOwogICAgICAgICAgICBzcC0+c19lcnJubyA9IGVycm5vOwogICAgICAgICAgICBzbm1wX3NldF9kZXRhaWwoc3RyZXJyb3IoZXJybm8pKTsKICAgICAgICAgICAgcmV0dXJuIC0xOwogICAgICAgIH0KICAgIH0KCiAgICAvKgogICAgICogV29yayBvdXQgd2hlcmUgdG8gcmVjZWl2ZSB0aGUgZGF0YSB0by4gIAogICAgICovCgogICAgaWYgKHRyYW5zcG9ydC0+ZmxhZ3MgJiBORVRTTk1QX1RSQU5TUE9SVF9GTEFHX1NUUkVBTSkgewogICAgICAgIGlmIChpc3AtPnBhY2tldCA9PSBOVUxMKSB7CiAgICAgICAgICAgIC8qCiAgICAgICAgICAgICAqIFdlIGhhdmUgbm8gc2F2ZWQgcGFja2V0LiAgQWxsb2NhdGUgb25lLiAgCiAgICAgICAgICAgICAqLwogICAgICAgICAgICBpZiAoKGlzcC0+cGFja2V0ID0gKHVfY2hhciAqKSBtYWxsb2MocnhidWZfbGVuKSkgPT0gTlVMTCkgewogICAgICAgICAgICAgICAgREVCVUdNU0dUTCgoInNlc3NfcmVhZCIsICJjYW4ndCBtYWxsb2MgJWQgYnl0ZXMgZm9yIHJ4YnVmXG4iLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgcnhidWZfbGVuKSk7CiAgICAgICAgICAgICAgICByZXR1cm4gMDsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgIHJ4YnVmID0gaXNwLT5wYWNrZXQ7CiAgICAgICAgICAgICAgICBpc3AtPnBhY2tldF9zaXplID0gcnhidWZfbGVuOwogICAgICAgICAgICAgICAgaXNwLT5wYWNrZXRfbGVuID0gMDsKICAgICAgICAgICAgfQogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIC8qCiAgICAgICAgICAgICAqIFdlIGhhdmUgc2F2ZWQgYSBwYXJ0aWFsIHBhY2tldCBmcm9tIGxhc3QgdGltZS4gIEV4dGVuZCB0aGF0LCBpZgogICAgICAgICAgICAgKiBuZWNlc3NhcnksIGFuZCByZWNlaXZlIG5ldyBkYXRhIGFmdGVyIHRoZSBvbGQgZGF0YS4gIAogICAgICAgICAgICAgKi8KICAgICAgICAgICAgdV9jaGFyICAgICAgICAgKm5ld2J1ZjsKCiAgICAgICAgICAgIGlmIChpc3AtPnBhY2tldF9zaXplIDwgaXNwLT5wYWNrZXRfbGVuICsgcnhidWZfbGVuKSB7CiAgICAgICAgICAgICAgICBuZXdidWYgPQogICAgICAgICAgICAgICAgICAgICh1X2NoYXIgKikgcmVhbGxvYyhpc3AtPnBhY2tldCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaXNwLT5wYWNrZXRfbGVuICsgcnhidWZfbGVuKTsKICAgICAgICAgICAgICAgIGlmIChuZXdidWYgPT0gTlVMTCkgewogICAgICAgICAgICAgICAgICAgIERFQlVHTVNHVEwoKCJzZXNzX3JlYWQiLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICJjYW4ndCBtYWxsb2MgJWQgbW9yZSBmb3IgcnhidWYgKCVkIHRvdClcbiIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcnhidWZfbGVuLCBpc3AtPnBhY2tldF9sZW4gKyByeGJ1Zl9sZW4pKTsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gMDsKICAgICAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgaXNwLT5wYWNrZXQgPSBuZXdidWY7CiAgICAgICAgICAgICAgICAgICAgaXNwLT5wYWNrZXRfc2l6ZSA9IGlzcC0+cGFja2V0X2xlbiArIHJ4YnVmX2xlbjsKICAgICAgICAgICAgICAgICAgICByeGJ1ZiA9IGlzcC0+cGFja2V0ICsgaXNwLT5wYWNrZXRfbGVuOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgICAgcnhidWYgPSBpc3AtPnBhY2tldCArIGlzcC0+cGFja2V0X2xlbjsKICAgICAgICAgICAgICAgIHJ4YnVmX2xlbiA9IGlzcC0+cGFja2V0X3NpemUgLSBpc3AtPnBhY2tldF9sZW47CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICB9IGVsc2UgewogICAgICAgIGlmICgocnhidWYgPSAodV9jaGFyICopIG1hbGxvYyhyeGJ1Zl9sZW4pKSA9PSBOVUxMKSB7CiAgICAgICAgICAgIERFQlVHTVNHVEwoKCJzZXNzX3JlYWQiLCAiY2FuJ3QgbWFsbG9jICVkIGJ5dGVzIGZvciByeGJ1ZlxuIiwKICAgICAgICAgICAgICAgICAgICAgICAgcnhidWZfbGVuKSk7CiAgICAgICAgICAgIHJldHVybiAwOwogICAgICAgIH0KICAgIH0KCiAgICBsZW5ndGggPSB0cmFuc3BvcnQtPmZfcmVjdih0cmFuc3BvcnQsIHJ4YnVmLCByeGJ1Zl9sZW4sICZvcGFxdWUsICZvbGVuZ3RoKTsKCiAgICBpZiAobGVuZ3RoID09IC0xICYmICEodHJhbnNwb3J0LT5mbGFncyAmIE5FVFNOTVBfVFJBTlNQT1JUX0ZMQUdfU1RSRUFNKSkgewogICAgICAgIHNwLT5zX3NubXBfZXJybm8gPSBTTk1QRVJSX0JBRF9SRUNWRlJPTTsKICAgICAgICBzcC0+c19lcnJubyA9IGVycm5vOwogICAgICAgIHNubXBfc2V0X2RldGFpbChzdHJlcnJvcihlcnJubykpOwogICAgICAgIFNOTVBfRlJFRShyeGJ1Zik7CiAgICAgICAgaWYgKG9wYXF1ZSAhPSBOVUxMKSB7CiAgICAgICAgICAgIFNOTVBfRlJFRShvcGFxdWUpOwogICAgICAgIH0KICAgICAgICByZXR1cm4gLTE7CiAgICB9CgogICAgLyoKICAgICAqIFJlbW90ZSBlbmQgY2xvc2VkIGNvbm5lY3Rpb24uICAKICAgICAqLwoKICAgIGlmIChsZW5ndGggPD0gMCAmJiB0cmFuc3BvcnQtPmZsYWdzICYgTkVUU05NUF9UUkFOU1BPUlRfRkxBR19TVFJFQU0pIHsKICAgICAgICAvKgogICAgICAgICAqIEFsZXJ0IHRoZSBhcHBsaWNhdGlvbiBpZiBwb3NzaWJsZS4gIAogICAgICAgICAqLwogICAgICAgIGlmIChzcC0+Y2FsbGJhY2sgIT0gTlVMTCkgewogICAgICAgICAgICBERUJVR01TR1RMKCgic2Vzc19yZWFkIiwgInBlcmZvcm0gY2FsbGJhY2sgd2l0aCBvcD1ESVNDT05ORUNUXG4iKSk7CiAgICAgICAgICAgICh2b2lkKSBzcC0+Y2FsbGJhY2soTkVUU05NUF9DQUxMQkFDS19PUF9ESVNDT05ORUNULCBzcCwgMCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBOVUxMLCBzcC0+Y2FsbGJhY2tfbWFnaWMpOwogICAgICAgIH0KICAgICAgICAvKgogICAgICAgICAqIENsb3NlIHNvY2tldCBhbmQgbWFyayBzZXNzaW9uIGZvciBkZWxldGlvbi4gIAogICAgICAgICAqLwogICAgICAgIERFQlVHTVNHVEwoKCJzZXNzX3JlYWQiLCAiZmQgJWQgY2xvc2VkXG4iLCB0cmFuc3BvcnQtPnNvY2spKTsKICAgICAgICB0cmFuc3BvcnQtPmZfY2xvc2UodHJhbnNwb3J0KTsKICAgICAgICBTTk1QX0ZSRUUoaXNwLT5wYWNrZXQpOwogICAgICAgIGlmIChvcGFxdWUgIT0gTlVMTCkgewogICAgICAgICAgICBTTk1QX0ZSRUUob3BhcXVlKTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIC0xOwogICAgfQoKICAgIGlmICh0cmFuc3BvcnQtPmZsYWdzICYgTkVUU05NUF9UUkFOU1BPUlRfRkxBR19TVFJFQU0pIHsKICAgICAgICB1X2NoYXIgKnBwdHIgPSBpc3AtPnBhY2tldDsKCXZvaWQgKm9jb3B5ID0gTlVMTDsKCiAgICAgICAgaXNwLT5wYWNrZXRfbGVuICs9IGxlbmd0aDsKCiAgICAgICAgd2hpbGUgKGlzcC0+cGFja2V0X2xlbiA+IDApIHsKCiAgICAgICAgICAgIC8qCiAgICAgICAgICAgICAqIEdldCB0aGUgdG90YWwgZGF0YSBsZW5ndGggd2UncmUgZXhwZWN0aW5nIChhbmQgbmVlZCB0byB3YWl0CiAgICAgICAgICAgICAqIGZvcikuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICBpZiAoaXNwLT5jaGVja19wYWNrZXQpIHsKICAgICAgICAgICAgICAgIHBkdWxlbiA9IGlzcC0+Y2hlY2tfcGFja2V0KHBwdHIsIGlzcC0+cGFja2V0X2xlbik7CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICBwZHVsZW4gPSBhc25fY2hlY2tfcGFja2V0KHBwdHIsIGlzcC0+cGFja2V0X2xlbik7CiAgICAgICAgICAgIH0KCiAgICAgICAgICAgIERFQlVHTVNHVEwoKCJzZXNzX3JlYWQiLCAiICBsb29wIHBhY2tldF9sZW4gJWQsIFBEVSBsZW5ndGggJWRcbiIsCiAgICAgICAgICAgICAgICAgICAgICAgIGlzcC0+cGFja2V0X2xlbiwgcGR1bGVuKSk7CiAgICAgICAgICAgICAKICAgICAgICAgICAgaWYgKChwZHVsZW4gPiBNQVhfUEFDS0VUX0xFTkdUSCkgfHwgKHBkdWxlbiA8IDApKSB7CiAgICAgICAgICAgICAgICAvKgogICAgICAgICAgICAgICAgICogSWxsZWdhbCBsZW5ndGgsIGRyb3AgdGhlIGNvbm5lY3Rpb24uICAKICAgICAgICAgICAgICAgICAqLwogICAgICAgICAgICAgICAgc25tcF9sb2coTE9HX0VSUiwgCgkJCSAiUmVjZWl2ZWQgYnJva2VuIHBhY2tldC4gQ2xvc2luZyBzZXNzaW9uLlxuIik7CgkJaWYgKHNwLT5jYWxsYmFjayAhPSBOVUxMKSB7CgkJICBERUJVR01TR1RMKCgic2Vzc19yZWFkIiwKCQkJICAgICAgInBlcmZvcm0gY2FsbGJhY2sgd2l0aCBvcD1ESVNDT05ORUNUXG4iKSk7CgkJICAodm9pZClzcC0+Y2FsbGJhY2soTkVUU05NUF9DQUxMQkFDS19PUF9ESVNDT05ORUNULAoJCQkJICAgICBzcCwgMCwgTlVMTCwgc3AtPmNhbGxiYWNrX21hZ2ljKTsKCQl9CgkJREVCVUdNU0dUTCgoInNlc3NfcmVhZCIsICJmZCAlZCBjbG9zZWRcbiIsIHRyYW5zcG9ydC0+c29jaykpOwogICAgICAgICAgICAgICAgdHJhbnNwb3J0LT5mX2Nsb3NlKHRyYW5zcG9ydCk7CiAgICAgICAgICAgICAgICBpZiAob3BhcXVlICE9IE5VTEwpIHsKICAgICAgICAgICAgICAgICAgICBTTk1QX0ZSRUUob3BhcXVlKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIC8qKiBYWFgtcmtzOiB3aHkgbm8gU05NUF9GUkVFKGlzcC0+cGFja2V0KTsgPz8gKi8KICAgICAgICAgICAgICAgIHJldHVybiAtMTsKICAgICAgICAgICAgfQoKICAgICAgICAgICAgaWYgKHBkdWxlbiA+IGlzcC0+cGFja2V0X2xlbiB8fCBwZHVsZW4gPT0gMCkgewogICAgICAgICAgICAgICAgLyoKICAgICAgICAgICAgICAgICAqIFdlIGRvbid0IGhhdmUgYSBjb21wbGV0ZSBwYWNrZXQgeWV0LiAgSWYgd2UndmUgYWxyZWFkeQogICAgICAgICAgICAgICAgICogcHJvY2Vzc2VkIGEgcGFja2V0LCBicmVhayBvdXQgc28gd2UnbGwgc2hpZnQgdGhpcyBwYWNrZXQKICAgICAgICAgICAgICAgICAqIHRvIHRoZSBzdGFydCBvZiB0aGUgYnVmZmVyLiBJZiB3ZSdyZSBhbHJlYWR5IGF0IHRoZQogICAgICAgICAgICAgICAgICogc3RhcnQsIHNpbXBseSByZXR1cm4gYW5kIHdhaXQgZm9yIG1vcmUgZGF0YSB0byBhcnJpdmUuCiAgICAgICAgICAgICAgICAgKi8KICAgICAgICAgICAgICAgIERFQlVHTVNHVEwoKCJzZXNzX3JlYWQiLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgInBrdCBub3QgY29tcGxldGUgKG5lZWQgJWQgZ290ICVkIHNvIGZhcilcbiIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBwZHVsZW4sIGlzcC0+cGFja2V0X2xlbikpOwoKICAgICAgICAgICAgICAgIGlmIChwcHRyICE9IGlzcC0+cGFja2V0KQogICAgICAgICAgICAgICAgICAgIGJyZWFrOyAvKiBvcGFxdWUgZnJlZWQgZm9yIHVzIG91dHNpZGUgb2YgbG9vcC4gKi8KCiAgICAgICAgICAgICAgICBpZiAob3BhcXVlICE9IE5VTEwpIHsKICAgICAgICAgICAgICAgICAgICBTTk1QX0ZSRUUob3BhcXVlKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHJldHVybiAwOwogICAgICAgICAgICB9CgogICAgICAgICAgICAvKiAgV2UgaGF2ZSAqYXQgbGVhc3QqIG9uZSBjb21wbGV0ZSBwYWNrZXQgaW4gdGhlIGJ1ZmZlciBub3cuICBJZgoJCXdlIGhhdmUgcG9zc2libHkgbW9yZSB0aGFuIG9uZSBwYWNrZXQsIHdlIG11c3QgY29weSB0aGUgb3BhcXVlCgkJcG9pbnRlciBiZWNhdXNlIHdlIG1heSBuZWVkIHRvIHJldXNlIGl0IGZvciBhIGxhdGVyIHBhY2tldC4gICovCgoJICAgIGlmIChwZHVsZW4gPCBpc3AtPnBhY2tldF9sZW4pIHsKCQlpZiAob2xlbmd0aCA+IDAgJiYgb3BhcXVlICE9IE5VTEwpIHsKCQkgICAgb2NvcHkgPSBtYWxsb2Mob2xlbmd0aCk7CgkJICAgIGlmIChvY29weSAhPSBOVUxMKSB7CgkJCW1lbWNweShvY29weSwgb3BhcXVlLCBvbGVuZ3RoKTsKCQkgICAgfQoJCX0KCSAgICB9IGVsc2UgaWYgKHBkdWxlbiA9PSBpc3AtPnBhY2tldF9sZW4pIHsKCQkvKiAgQ29tbW9uIGNhc2UgLS0gZXhhY3RseSBvbmUgcGFja2V0LiAgTm8gbmVlZCB0byBjb3B5IHRoZQoJCSAgICBvcGFxdWUgcG9pbnRlci4gICovCgkJb2NvcHkgPSBvcGFxdWU7CgkJb3BhcXVlID0gTlVMTDsKCSAgICB9CgogICAgICAgICAgICBpZiAoKHJjID0gX3Nlc3NfcHJvY2Vzc19wYWNrZXQoc2Vzc3AsIHNwLCBpc3AsIHRyYW5zcG9ydCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIG9jb3B5LCBvY29weT9vbGVuZ3RoOjAsIHBwdHIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBwZHVsZW4pKSkgewogICAgICAgICAgICAgICAgLyoKICAgICAgICAgICAgICAgICAqIFNvbWV0aGluZyB3ZW50IHdyb25nIHdoaWxlIHByb2Nlc3NpbmcgdGhpcyBwYWNrZXQgLS0gc2V0IHRoZQogICAgICAgICAgICAgICAgICogZXJybm8uICAKICAgICAgICAgICAgICAgICAqLwogICAgICAgICAgICAgICAgaWYgKHNwLT5zX3NubXBfZXJybm8gIT0gMCkgewogICAgICAgICAgICAgICAgICAgIFNFVF9TTk1QX0VSUk9SKHNwLT5zX3NubXBfZXJybm8pOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CgoJICAgIC8qICBvY29weSBoYXMgYmVlbiBmcmVlKClkIGJ5IF9zZXNzX3Byb2Nlc3NfcGFja2V0IGJ5IHRoaXMgcG9pbnQsCgkJc28gc2V0IGl0IHRvIE5VTEwuICAqLwoKCSAgICBvY29weSA9IE5VTEw7CgoJICAgIC8qICBTdGVwIHBhc3QgdGhlIHBhY2tldCB3ZSd2ZSBqdXN0IGRlYWx0IHdpdGguICAqLwoKICAgICAgICAgICAgcHB0ciArPSBwZHVsZW47CiAgICAgICAgICAgIGlzcC0+cGFja2V0X2xlbiAtPSBwZHVsZW47CiAgICAgICAgfQoKCS8qICBJZiB3ZSBoYWQgbW9yZSB0aGFuIG9uZSBwYWNrZXQsIHRoZW4gd2Ugd2VyZSB3b3JraW5nIHdpdGggY29waWVzCgkgICAgb2YgdGhlIG9wYXF1ZSBwb2ludGVyLCBzbyB3ZSBzdGlsbCBuZWVkIHRvIGZyZWUoKSB0aGUgb3BhcXVlCgkgICAgcG9pbnRlciBpdHNlbGYuICAqLwoKCWlmIChvcGFxdWUgIT0gTlVMTCkgewoJICAgIFNOTVBfRlJFRShvcGFxdWUpOwoJfQoKICAgICAgICBpZiAoaXNwLT5wYWNrZXRfbGVuID49IE1BWElNVU1fUEFDS0VUX1NJWkUpIHsKICAgICAgICAgICAgLyoKICAgICAgICAgICAgICogT2J2aW91c2x5IHRoaXMgc2hvdWxkIG5ldmVyIGhhcHBlbiEgIAogICAgICAgICAgICAgKi8KICAgICAgICAgICAgc25tcF9sb2coTE9HX0VSUiwKICAgICAgICAgICAgICAgICAgICAgInRvbyBsYXJnZSBwYWNrZXRfbGVuID0gJWx1LCBkcm9wcGluZyBjb25uZWN0aW9uICVkXG4iLAogICAgICAgICAgICAgICAgICAgICAodW5zaWduZWQgbG9uZykoaXNwLT5wYWNrZXRfbGVuKSwgdHJhbnNwb3J0LT5zb2NrKTsKICAgICAgICAgICAgdHJhbnNwb3J0LT5mX2Nsb3NlKHRyYW5zcG9ydCk7CiAgICAgICAgICAgIC8qKiBYWFgtcmtzOiB3aHkgbm8gU05NUF9GUkVFKGlzcC0+cGFja2V0KTsgPz8gKi8KICAgICAgICAgICAgcmV0dXJuIC0xOwogICAgICAgIH0gZWxzZSBpZiAoaXNwLT5wYWNrZXRfbGVuID09IDApIHsKICAgICAgICAgICAgLyoKICAgICAgICAgICAgICogVGhpcyBpcyBnb29kOiBpdCBtZWFucyB0aGUgcGFja2V0IGJ1ZmZlciBjb250YWluZWQgYW4gaW50ZWdyYWwKICAgICAgICAgICAgICogbnVtYmVyIG9mIFBEVXMsIHNvIHdlIGRvbid0IGhhdmUgdG8gc2F2ZSBhbnkgZGF0YSBmb3IgbmV4dAogICAgICAgICAgICAgKiB0aW1lLiAgV2UgY2FuIGZyZWUoKSB0aGUgYnVmZmVyIG5vdyB0byBrZWVwIHRoZSBtZW1vcnkKICAgICAgICAgICAgICogZm9vdHByaW50IGRvd24uCiAgICAgICAgICAgICAqLwogICAgICAgICAgICBTTk1QX0ZSRUUoaXNwLT5wYWNrZXQpOwogICAgICAgICAgICBpc3AtPnBhY2tldCA9IE5VTEw7CiAgICAgICAgICAgIGlzcC0+cGFja2V0X3NpemUgPSAwOwogICAgICAgICAgICBpc3AtPnBhY2tldF9sZW4gPSAwOwogICAgICAgICAgICByZXR1cm4gcmM7CiAgICAgICAgfQoKICAgICAgICAvKgogICAgICAgICAqIElmIHdlIGdldCBoZXJlLCB0aGVuIHRoZXJlIGlzIGEgcGFydGlhbCBwYWNrZXQgb2YgbGVuZ3RoCiAgICAgICAgICogaXNwLT5wYWNrZXRfbGVuIGJ5dGVzIHN0YXJ0aW5nIGF0IHBwdHIgbGVmdCBvdmVyLiAgTW92ZSB0aGF0IHRvIHRoZQogICAgICAgICAqIHN0YXJ0IG9mIHRoZSBidWZmZXIsIGFuZCB0aGVuIHJlYWxsb2MoKSB0aGUgYnVmZmVyIGRvd24gdG8gc2l6ZSB0bwogICAgICAgICAqIHJlZHVjZSB0aGUgbWVtb3J5IGZvb3RwcmludC4gIAogICAgICAgICAqLwoKICAgICAgICBtZW1tb3ZlKGlzcC0+cGFja2V0LCBwcHRyLCBpc3AtPnBhY2tldF9sZW4pOwogICAgICAgIERFQlVHTVNHVEwoKCJzZXNzX3JlYWQiLCAiZW5kOiBtZW1tb3ZlKCVwLCAlcCwgJWQpOyByZWFsbG9jKCVwLCAlZClcbiIsCiAgICAgICAgICAgICAgICAgICAgaXNwLT5wYWNrZXQsIHBwdHIsIGlzcC0+cGFja2V0X2xlbiwgaXNwLT5wYWNrZXQsCiAgICAgICAgICAgICAgICAgICAgaXNwLT5wYWNrZXRfbGVuKSk7CgogICAgICAgIGlmICgocnhidWYgPSAodV9jaGFyICopcmVhbGxvYyhpc3AtPnBhY2tldCwgaXNwLT5wYWNrZXRfbGVuKSkgPT0gTlVMTCkgewogICAgICAgICAgICAvKgogICAgICAgICAgICAgKiBJIGRvbid0IHNlZSB3aHkgdGhpcyBzaG91bGQgZXZlciBmYWlsLCBidXQgaXQncyBub3QgYSBiaWcgZGVhbC4KICAgICAgICAgICAgICovCiAgICAgICAgICAgIERFQlVHTVNHVEwoKCJzZXNzX3JlYWQiLCAicmVhbGxvYygpIGZhaWxlZFxuIikpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIERFQlVHTVNHVEwoKCJzZXNzX3JlYWQiLCAicmVhbGxvYygpIG9rYXksIG9sZCBidWZmZXIgJXAsIG5ldyAlcFxuIiwKICAgICAgICAgICAgICAgICAgICAgICAgaXNwLT5wYWNrZXQsIHJ4YnVmKSk7CiAgICAgICAgICAgIGlzcC0+cGFja2V0ID0gcnhidWY7CiAgICAgICAgICAgIGlzcC0+cGFja2V0X3NpemUgPSBpc3AtPnBhY2tldF9sZW47CiAgICAgICAgfQogICAgICAgIHJldHVybiByYzsKICAgIH0gZWxzZSB7CiAgICAgICAgcmMgPSBfc2Vzc19wcm9jZXNzX3BhY2tldChzZXNzcCwgc3AsIGlzcCwgdHJhbnNwb3J0LCBvcGFxdWUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBvbGVuZ3RoLCByeGJ1ZiwgbGVuZ3RoKTsKICAgICAgICBTTk1QX0ZSRUUocnhidWYpOwogICAgICAgIHJldHVybiByYzsKICAgIH0KfQoKCgovKgogKiByZXR1cm5zIDAgaWYgc3VjY2VzcywgLTEgaWYgZmFpbCAKICovCmludApzbm1wX3Nlc3NfcmVhZCh2b2lkICpzZXNzcCwgZmRfc2V0ICogZmRzZXQpCnsKICAgIHN0cnVjdCBzZXNzaW9uX2xpc3QgKnBzbDsKICAgIG5ldHNubXBfc2Vzc2lvbiAqcHNzOwogICAgaW50ICAgICAgICAgICAgIHJjOwoKICAgIHJjID0gX3Nlc3NfcmVhZChzZXNzcCwgZmRzZXQpOwogICAgcHNsID0gKHN0cnVjdCBzZXNzaW9uX2xpc3QgKikgc2Vzc3A7CiAgICBwc3MgPSBwc2wtPnNlc3Npb247CiAgICBpZiAocmMgJiYgcHNzLT5zX3NubXBfZXJybm8pIHsKICAgICAgICBTRVRfU05NUF9FUlJPUihwc3MtPnNfc25tcF9lcnJubyk7CiAgICB9CiAgICByZXR1cm4gcmM7Cn0KCgovKgogKiBSZXR1cm5zIGluZm8gYWJvdXQgd2hhdCBzbm1wIHJlcXVpcmVzIGZyb20gYSBzZWxlY3Qgc3RhdGVtZW50LgogKiBudW1mZHMgaXMgdGhlIG51bWJlciBvZiBmZHMgaW4gdGhlIGxpc3QgdGhhdCBhcmUgc2lnbmlmaWNhbnQuCiAqIEFsbCBmaWxlIGRlc2NyaXB0b3JzIG9wZW5lZCBmb3IgU05NUCBhcmUgT1InZCBpbnRvIHRoZSBmZHNldC4KICogSWYgYWN0aXZpdHkgb2NjdXJzIG9uIGFueSBvZiB0aGVzZSBmaWxlIGRlc2NyaXB0b3JzLCBzbm1wX3JlYWQKICogc2hvdWxkIGJlIGNhbGxlZCB3aXRoIHRoYXQgZmlsZSBkZXNjcmlwdG9yIHNldAogKgogKiBUaGUgdGltZW91dCBpcyB0aGUgbGF0ZXN0IHRpbWUgdGhhdCBTTk1QIGNhbiB3YWl0IGZvciBhIHRpbWVvdXQuICBUaGUKICogc2VsZWN0IHNob3VsZCBiZSBkb25lIHdpdGggdGhlIG1pbmltdW0gdGltZSBiZXR3ZWVuIHRpbWVvdXQgYW5kIGFueSBvdGhlcgogKiB0aW1lb3V0cyBuZWNlc3NhcnkuICBUaGlzIHNob3VsZCBiZSBjaGVja2VkIHVwb24gZWFjaCBpbnZvY2F0aW9uIG9mIHNlbGVjdC4KICogSWYgYSB0aW1lb3V0IGlzIHJlY2VpdmVkLCBzbm1wX3RpbWVvdXQgc2hvdWxkIGJlIGNhbGxlZCB0byBjaGVjayBpZiB0aGUKICogdGltZW91dCB3YXMgZm9yIFNOTVAuICAoc25tcF90aW1lb3V0IGlzIGlkZW1wb3RlbnQpCiAqCiAqIFRoZSB2YWx1ZSBvZiBibG9jayBpbmRpY2F0ZXMgaG93IHRoZSB0aW1lb3V0IHZhbHVlIGlzIGludGVycHJldGVkLgogKiBJZiBibG9jayBpcyB0cnVlIG9uIGlucHV0LCB0aGUgdGltZW91dCB2YWx1ZSB3aWxsIGJlIHRyZWF0ZWQgYXMgdW5kZWZpbmVkLAogKiBidXQgaXQgbXVzdCBiZSBhdmFpbGFibGUgZm9yIHNldHRpbmcgaW4gc25tcF9zZWxlY3RfaW5mby4gIE9uIHJldHVybiwKICogYmxvY2sgaXMgc2V0IHRvIHRydWUgaWYgdGhlIHZhbHVlIHJldHVybmVkIGZvciB0aW1lb3V0IGlzIHVuZGVmaW5lZDsKICogd2hlbiBibG9jayBpcyBzZXQgdG8gZmFsc2UsIHRpbWVvdXQgbWF5IGJlIHVzZWQgYXMgYSBwYXJtZXRlciB0byAnc2VsZWN0Jy4KICoKICogc25tcF9zZWxlY3RfaW5mbyByZXR1cm5zIHRoZSBudW1iZXIgb2Ygb3BlbiBzb2NrZXRzLiAgKGkuZS4gVGhlIG51bWJlciBvZgogKiBzZXNzaW9ucyBvcGVuKQogKi8KCmludApzbm1wX3NlbGVjdF9pbmZvKGludCAqbnVtZmRzLAogICAgICAgICAgICAgICAgIGZkX3NldCAqIGZkc2V0LCBzdHJ1Y3QgdGltZXZhbCAqdGltZW91dCwgaW50ICpibG9jaykKICAgIC8qCiAgICAgKiBpbnB1dDogIHNldCB0byAxIGlmIGlucHV0IHRpbWVvdXQgdmFsdWUgaXMgdW5kZWZpbmVkICAKICAgICAqIHNldCB0byAwIGlmIGlucHV0IHRpbWVvdXQgdmFsdWUgaXMgZGVmaW5lZCAgICAKICAgICAqIG91dHB1dDogc2V0IHRvIDEgaWYgb3V0cHV0IHRpbWVvdXQgdmFsdWUgaXMgdW5kZWZpbmVkIAogICAgICogc2V0IHRvIDAgaWYgb3V0cHV0IHJpbWVvdXQgdmxhdWUgaWQgZGVmaW5lZCAgIAogICAgICovCnsKICAgIHJldHVybiBzbm1wX3Nlc3Nfc2VsZWN0X2luZm8oKHZvaWQgKikgMCwgbnVtZmRzLCBmZHNldCwgdGltZW91dCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgYmxvY2spOwp9CgovKgogKiBTYW1lIGFzIHNubXBfc2VsZWN0X2luZm8sIGJ1dCB3b3JrcyBqdXN0IG9uZSBzZXNzaW9uLiAKICovCmludApzbm1wX3Nlc3Nfc2VsZWN0X2luZm8odm9pZCAqc2Vzc3AsCiAgICAgICAgICAgICAgICAgICAgICBpbnQgKm51bWZkcywKICAgICAgICAgICAgICAgICAgICAgIGZkX3NldCAqIGZkc2V0LCBzdHJ1Y3QgdGltZXZhbCAqdGltZW91dCwgaW50ICpibG9jaykKewogICAgc3RydWN0IHNlc3Npb25fbGlzdCAqc2xwdGVzdCA9IChzdHJ1Y3Qgc2Vzc2lvbl9saXN0ICopIHNlc3NwOwogICAgc3RydWN0IHNlc3Npb25fbGlzdCAqc2xwLCAqbmV4dCA9IE5VTEw7CiAgICBuZXRzbm1wX3JlcXVlc3RfbGlzdCAqcnA7CiAgICBzdHJ1Y3QgdGltZXZhbCAgbm93LCBlYXJsaWVzdCwgZGVsdGE7CiAgICBpbnQgICAgICAgICAgICAgYWN0aXZlID0gMCwgcmVxdWVzdHMgPSAwOwogICAgaW50ICAgICAgICAgICAgIG5leHRfYWxhcm0gPSAwOwoKICAgIHRpbWVyY2xlYXIoJmVhcmxpZXN0KTsKCiAgICAvKgogICAgICogRm9yIGVhY2ggcmVxdWVzdCBvdXRzdGFuZGluZywgYWRkIGl0cyBzb2NrZXQgdG8gdGhlIGZkc2V0LAogICAgICogYW5kIGlmIGl0IGlzIHRoZSBlYXJsaWVzdCB0aW1lb3V0IHRvIGV4cGlyZSwgbWFyayBpdCBhcyBsb3dlc3QuCiAgICAgKiBJZiBhIHNpbmdsZSBzZXNzaW9uIGlzIHNwZWNpZmllZCwgZG8ganVzdCBmb3IgdGhhdCBzZXNzaW9uLgogICAgICovCgogICAgaWYgKHNlc3NwKSB7CiAgICAgICAgc2xwID0gc2xwdGVzdDsKICAgIH0gZWxzZSB7CiAgICAgICAgc2xwID0gU2Vzc2lvbnM7CiAgICB9CgogICAgREVCVUdNU0dUTCgoInNlc3Nfc2VsZWN0IiwgImZvciAlcyBzZXNzaW9uJXM6ICIsCiAgICAgICAgICAgICAgICBzZXNzcCA/ICJzaW5nbGUiIDogImFsbCIsIHNlc3NwID8gIiIgOiAicyIpKTsKCiAgICBmb3IgKDsgc2xwOyBzbHAgPSBuZXh0KSB7CiAgICAgICAgbmV4dCA9IHNscC0+bmV4dDsKCiAgICAgICAgaWYgKHNscC0+dHJhbnNwb3J0ID09IE5VTEwpIHsKICAgICAgICAgICAgLyoKICAgICAgICAgICAgICogQ2xvc2UgaW4gcHJvZ3Jlc3MgLS0gc2tpcCB0aGlzIG9uZS4gIAogICAgICAgICAgICAgKi8KICAgICAgICAgICAgREVCVUdNU0coKCJzZXNzX3NlbGVjdCIsICJza2lwICIpKTsKICAgICAgICAgICAgY29udGludWU7CiAgICAgICAgfQoKICAgICAgICBpZiAoc2xwLT50cmFuc3BvcnQtPnNvY2sgPT0gLTEpIHsKICAgICAgICAgICAgLyoKICAgICAgICAgICAgICogVGhpcyBzZXNzaW9uIHdhcyBtYXJrZWQgZm9yIGRlbGV0aW9uLiAgCiAgICAgICAgICAgICAqLwogICAgICAgICAgICBERUJVR01TRygoInNlc3Nfc2VsZWN0IiwgImRlbGV0ZVxuIikpOwogICAgICAgICAgICBpZiAoc2Vzc3AgPT0gTlVMTCkgewogICAgICAgICAgICAgICAgc25tcF9jbG9zZShzbHAtPnNlc3Npb24pOwogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgICAgc25tcF9zZXNzX2Nsb3NlKHNscCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgREVCVUdNU0dUTCgoInNlc3Nfc2VsZWN0IiwgImZvciAlcyBzZXNzaW9uJXM6ICIsCiAgICAgICAgICAgICAgICAgICAgICAgIHNlc3NwID8gInNpbmdsZSIgOiAiYWxsIiwgc2Vzc3AgPyAiIiA6ICJzIikpOwogICAgICAgICAgICBjb250aW51ZTsKICAgICAgICB9CgogICAgICAgIERFQlVHTVNHKCgic2Vzc19zZWxlY3QiLCAiJWQgIiwgc2xwLT50cmFuc3BvcnQtPnNvY2spKTsKICAgICAgICBpZiAoKHNscC0+dHJhbnNwb3J0LT5zb2NrICsgMSkgPiAqbnVtZmRzKSB7CiAgICAgICAgICAgICpudW1mZHMgPSAoc2xwLT50cmFuc3BvcnQtPnNvY2sgKyAxKTsKICAgICAgICB9CgogICAgICAgIEZEX1NFVChzbHAtPnRyYW5zcG9ydC0+c29jaywgZmRzZXQpOwogICAgICAgIGlmIChzbHAtPmludGVybmFsICE9IE5VTEwgJiYgc2xwLT5pbnRlcm5hbC0+cmVxdWVzdHMpIHsKICAgICAgICAgICAgLyoKICAgICAgICAgICAgICogRm91bmQgYW5vdGhlciBzZXNzaW9uIHdpdGggb3V0c3RhbmRpbmcgcmVxdWVzdHMuICAKICAgICAgICAgICAgICovCiAgICAgICAgICAgIHJlcXVlc3RzKys7CiAgICAgICAgICAgIGZvciAocnAgPSBzbHAtPmludGVybmFsLT5yZXF1ZXN0czsgcnA7IHJwID0gcnAtPm5leHRfcmVxdWVzdCkgewogICAgICAgICAgICAgICAgaWYgKCghdGltZXJpc3NldCgmZWFybGllc3QpCiAgICAgICAgICAgICAgICAgICAgIHx8ICh0aW1lcmNtcCgmcnAtPmV4cGlyZSwgJmVhcmxpZXN0LCA8KSkpKSB7CiAgICAgICAgICAgICAgICAgICAgZWFybGllc3QgPSBycC0+ZXhwaXJlOwogICAgICAgICAgICAgICAgICAgIERFQlVHTVNHKCgidmVyYm9zZTpzZXNzX3NlbGVjdCIsIih0byBpbiAlZC4lZCBzZWMpICIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBlYXJsaWVzdC50dl9zZWMsIGVhcmxpZXN0LnR2X3VzZWMpKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgYWN0aXZlKys7CiAgICAgICAgaWYgKHNlc3NwKSB7CiAgICAgICAgICAgIC8qCiAgICAgICAgICAgICAqIFNpbmdsZSBzZXNzaW9uIHByb2Nlc3NpbmcuICAKICAgICAgICAgICAgICovCiAgICAgICAgICAgIGJyZWFrOwogICAgICAgIH0KICAgIH0KICAgIERFQlVHTVNHKCgic2Vzc19zZWxlY3QiLCAiXG4iKSk7CgogICAgaWYgKG5ldHNubXBfZHNfZ2V0X2Jvb2xlYW4oTkVUU05NUF9EU19MSUJSQVJZX0lELCBORVRTTk1QX0RTX0xJQl9BTEFSTV9ET05UX1VTRV9TSUcpKSB7CiAgICAgICAgbmV4dF9hbGFybSA9IGdldF9uZXh0X2FsYXJtX2RlbGF5X3RpbWUoJmRlbHRhKTsKICAgICAgICBERUJVR01TR1QoKCJzZXNzX3NlbGVjdCIsIm5leHQgYWxhcm0gJWQuJWQgc2VjXG4iLAogICAgICAgICAgICAgICAgICAgZGVsdGEudHZfc2VjLCBkZWx0YS50dl91c2VjKSk7CiAgICB9CiAgICBpZiAobmV4dF9hbGFybSA9PSAwICYmIHJlcXVlc3RzID09IDApIHsKICAgICAgICAvKgogICAgICAgICAqIElmIG5vbmUgYXJlIGFjdGl2ZSwgc2tpcCBhcml0aG1ldGljLiAgCiAgICAgICAgICovCiAgICAgICAgREVCVUdNU0dUKCgic2Vzc19zZWxlY3QiLCJibG9ja2luZzpubyBzZXNzaW9uIHJlcXVlc3RzIG9yIGFsYXJtcy5cbiIpKTsKICAgICAgICAqYmxvY2sgPSAxOyAvKiBjYW4gYmxvY2sgLSB0aW1lb3V0IHZhbHVlIGlzIHVuZGVmaW5lZCBpZiBubyByZXF1ZXN0cyAqLwogICAgICAgIHJldHVybiBhY3RpdmU7CiAgICB9CgogICAgLyoKICAgICAqICogTm93IGZpbmQgb3V0IGhvdyBtdWNoIHRpbWUgdW50aWwgdGhlIGVhcmxpZXN0IHRpbWVvdXQuICBUaGlzCiAgICAgKiAqIHRyYW5zZm9ybXMgZWFybGllc3QgZnJvbSBhbiBhYnNvbHV0ZSB0aW1lIGludG8gYSBkZWx0YSB0aW1lLCB0aGUKICAgICAqICogdGltZSBsZWZ0IHVudGlsIHRoZSBzZWxlY3Qgc2hvdWxkIHRpbWVvdXQuCiAgICAgKi8KICAgIGdldHRpbWVvZmRheSgmbm93LCAoc3RydWN0IHRpbWV6b25lICopIDApOwogICAgLyoKICAgICAqIE5vdyA9IG5vdzsKICAgICAqLwoKICAgIGlmIChuZXh0X2FsYXJtKSB7CiAgICAgICAgZGVsdGEudHZfc2VjICs9IG5vdy50dl9zZWM7CiAgICAgICAgZGVsdGEudHZfdXNlYyArPSBub3cudHZfdXNlYzsKICAgICAgICB3aGlsZSAoZGVsdGEudHZfdXNlYyA+PSAxMDAwMDAwKSB7CiAgICAgICAgICAgIGRlbHRhLnR2X3VzZWMgLT0gMTAwMDAwMDsKICAgICAgICAgICAgZGVsdGEudHZfc2VjICs9IDE7CiAgICAgICAgfQogICAgICAgIGlmICghdGltZXJpc3NldCgmZWFybGllc3QpIHx8CiAgICAgICAgICAgICgoZWFybGllc3QudHZfc2VjID4gZGVsdGEudHZfc2VjKSB8fAogICAgICAgICAgICAgKChlYXJsaWVzdC50dl9zZWMgPT0gZGVsdGEudHZfc2VjKSAmJgogICAgICAgICAgICAgIChlYXJsaWVzdC50dl91c2VjID4gZGVsdGEudHZfdXNlYykpKSkgewogICAgICAgICAgICBlYXJsaWVzdC50dl9zZWMgPSBkZWx0YS50dl9zZWM7CiAgICAgICAgICAgIGVhcmxpZXN0LnR2X3VzZWMgPSBkZWx0YS50dl91c2VjOwogICAgICAgIH0KICAgIH0KCiAgICBpZiAoZWFybGllc3QudHZfc2VjIDwgbm93LnR2X3NlYykgewogICAgICAgIERFQlVHTVNHVCgoInZlcmJvc2U6c2Vzc19zZWxlY3QiLCJ0aW1lciBvdmVyZHVlXG4iKSk7CiAgICAgICAgZWFybGllc3QudHZfc2VjID0gMDsKICAgICAgICBlYXJsaWVzdC50dl91c2VjID0gMDsKICAgIH0gZWxzZSBpZiAoZWFybGllc3QudHZfc2VjID09IG5vdy50dl9zZWMpIHsKICAgICAgICBlYXJsaWVzdC50dl9zZWMgPSAwOwogICAgICAgIGVhcmxpZXN0LnR2X3VzZWMgPSAoZWFybGllc3QudHZfdXNlYyAtIG5vdy50dl91c2VjKTsKICAgICAgICBpZiAoZWFybGllc3QudHZfdXNlYyA8IDApIHsKICAgICAgICAgICAgZWFybGllc3QudHZfdXNlYyA9IDEwMDsKICAgICAgICB9CiAgICAgICAgREVCVUdNU0dUKCgidmVyYm9zZTpzZXNzX3NlbGVjdCIsInRpbWVyIGR1ZSAqcmVhbCogc29vbi4gJWQgdXNlY1xuIiwKICAgICAgICAgICAgICAgICAgIGVhcmxpZXN0LnR2X3VzZWMpKTsKICAgIH0gZWxzZSB7CiAgICAgICAgZWFybGllc3QudHZfc2VjID0gKGVhcmxpZXN0LnR2X3NlYyAtIG5vdy50dl9zZWMpOwogICAgICAgIGVhcmxpZXN0LnR2X3VzZWMgPSAoZWFybGllc3QudHZfdXNlYyAtIG5vdy50dl91c2VjKTsKICAgICAgICBpZiAoZWFybGllc3QudHZfdXNlYyA8IDApIHsKICAgICAgICAgICAgZWFybGllc3QudHZfc2VjLS07CiAgICAgICAgICAgIGVhcmxpZXN0LnR2X3VzZWMgPSAoMTAwMDAwMEwgKyBlYXJsaWVzdC50dl91c2VjKTsKICAgICAgICB9CiAgICAgICAgREVCVUdNU0dUKCgidmVyYm9zZTpzZXNzX3NlbGVjdCIsInRpbWVyIGR1ZSBpbiAlZC4lZCBzZWNcbiIsCiAgICAgICAgICAgICAgICAgICBlYXJsaWVzdC50dl9zZWMsIGVhcmxpZXN0LnR2X3VzZWMpKTsKICAgIH0KCiAgICAvKgogICAgICogaWYgaXQgd2FzIGJsb2NraW5nIGJlZm9yZSBvciBvdXIgZGVsdGEgdGltZSBpcyBsZXNzLCByZXNldCB0aW1lb3V0IAogICAgICovCiAgICBpZiAoKCpibG9jayB8fCAodGltZXJjbXAoJmVhcmxpZXN0LCB0aW1lb3V0LCA8KSkpKSB7CiAgICAgICAgREVCVUdNU0dUKCgidmVyYm9zZTpzZXNzX3NlbGVjdCIsCiAgICAgICAgICAgICAgICAgICAic2V0dGluZyB0aW1lciB0byAlZC4lZCBzZWMsIGNsZWFyIGJsb2NrICh3YXMgJWQpXG4iLAogICAgICAgICAgICAgICAgICAgZWFybGllc3QudHZfc2VjLCBlYXJsaWVzdC50dl91c2VjLCAqYmxvY2spKTsKICAgICAgICAqdGltZW91dCA9IGVhcmxpZXN0OwogICAgICAgICpibG9jayA9IDA7CiAgICB9CiAgICByZXR1cm4gYWN0aXZlOwp9CgovKgogKiBzbm1wX3RpbWVvdXQgc2hvdWxkIGJlIGNhbGxlZCB3aGVuZXZlciB0aGUgdGltZW91dCBmcm9tIHNubXBfc2VsZWN0X2luZm8KICogZXhwaXJlcywgYnV0IGl0IGlzIGlkZW1wb3RlbnQsIHNvIHNubXBfdGltZW91dCBjYW4gYmUgcG9sbGVkIChwcm9iYWJseSBhCiAqIGNwdSBleHBlbnNpdmUgcHJvcG9zaXRpb24pLiAgc25tcF90aW1lb3V0IGNoZWNrcyB0byBzZWUgaWYgYW55IG9mIHRoZQogKiBzZXNzaW9ucyBoYXZlIGFuIG91dHN0YW5kaW5nIHJlcXVlc3QgdGhhdCBoYXMgdGltZWQgb3V0LiAgSWYgaXQgZmluZHMgb25lCiAqIChvciBtb3JlKSwgYW5kIHRoYXQgcGR1IGhhcyBtb3JlIHJldHJpZXMgYXZhaWxhYmxlLCBhIG5ldyBwYWNrZXQgaXMgZm9ybWVkCiAqIGZyb20gdGhlIHBkdSBhbmQgaXMgcmVzZW50LiAgSWYgdGhlcmUgYXJlIG5vIG1vcmUgcmV0cmllcyBhdmFpbGFibGUsIHRoZQogKiAgY2FsbGJhY2sgZm9yIHRoZSBzZXNzaW9uIGlzIHVzZWQgdG8gYWxlcnQgdGhlIHVzZXIgb2YgdGhlIHRpbWVvdXQuCiAqLwp2b2lkCnNubXBfdGltZW91dCh2b2lkKQp7CiAgICBzdHJ1Y3Qgc2Vzc2lvbl9saXN0ICpzbHA7CiAgICBzbm1wX3Jlc19sb2NrKE1UX0xJQlJBUllfSUQsIE1UX0xJQl9TRVNTSU9OKTsKICAgIGZvciAoc2xwID0gU2Vzc2lvbnM7IHNscDsgc2xwID0gc2xwLT5uZXh0KSB7CiAgICAgICAgc25tcF9zZXNzX3RpbWVvdXQoKHZvaWQgKikgc2xwKTsKICAgIH0KICAgIHNubXBfcmVzX3VubG9jayhNVF9MSUJSQVJZX0lELCBNVF9MSUJfU0VTU0lPTik7Cn0KCnN0YXRpYyBpbnQKc25tcF9yZXNlbmRfcmVxdWVzdChzdHJ1Y3Qgc2Vzc2lvbl9saXN0ICpzbHAsIG5ldHNubXBfcmVxdWVzdF9saXN0ICpycCwKICAgICAgICAgICAgICAgICAgICBpbnQgaW5jcl9yZXRyaWVzKQp7CiAgICBzdHJ1Y3Qgc25tcF9pbnRlcm5hbF9zZXNzaW9uICppc3A7CiAgICBuZXRzbm1wX3Nlc3Npb24gKnNwOwogICAgbmV0c25tcF90cmFuc3BvcnQgKnRyYW5zcG9ydDsKICAgIHVfY2hhciAgICAgICAgICpwa3RidWYgPSBOVUxMLCAqcGFja2V0ID0gTlVMTDsKICAgIHNpemVfdCAgICAgICAgICBwa3RidWZfbGVuID0gMCwgb2Zmc2V0ID0gMCwgbGVuZ3RoID0gMDsKICAgIHN0cnVjdCB0aW1ldmFsICB0diwgbm93OwogICAgaW50ICAgICAgICAgICAgIHJlc3VsdCA9IDA7CgogICAgc3AgPSBzbHAtPnNlc3Npb247CiAgICBpc3AgPSBzbHAtPmludGVybmFsOwogICAgdHJhbnNwb3J0ID0gc2xwLT50cmFuc3BvcnQ7CiAgICBpZiAoIXNwIHx8ICFpc3AgfHwgIXRyYW5zcG9ydCkgewogICAgICAgIERFQlVHTVNHVEwoKCJzZXNzX3JlYWQiLCAicmVzZW5kIGZhaWw6IGNsb3NpbmcuLi5cbiIpKTsKICAgICAgICByZXR1cm4gMDsKICAgIH0KCiAgICBpZiAoKHBrdGJ1ZiA9ICh1X2NoYXIgKiltYWxsb2MoMjA0OCkpID09IE5VTEwpIHsKICAgICAgICBERUJVR01TR1RMKCgic2Vzc19yZXNlbmQiLAogICAgICAgICAgICAgICAgICAgICJjb3VsZG4ndCBtYWxsb2MgaW5pdGlhbCBwYWNrZXQgYnVmZmVyXG4iKSk7CiAgICAgICAgcmV0dXJuIDA7CiAgICB9IGVsc2UgewogICAgICAgIHBrdGJ1Zl9sZW4gPSAyMDQ4OwogICAgfQoKICAgIGlmIChpbmNyX3JldHJpZXMpIHsKICAgICAgICBycC0+cmV0cmllcysrOwogICAgfQoKICAgIC8qCiAgICAgKiBBbHdheXMgaW5jcmVtZW50IG1zZ0lkIGZvciByZXNlbnQgbWVzc2FnZXMuICAKICAgICAqLwogICAgcnAtPnBkdS0+bXNnaWQgPSBycC0+bWVzc2FnZV9pZCA9IHNubXBfZ2V0X25leHRfbXNnaWQoKTsKCiAgICBpZiAoaXNwLT5ob29rX3JlYWxsb2NfYnVpbGQpIHsKICAgICAgICByZXN1bHQgPSBpc3AtPmhvb2tfcmVhbGxvY19idWlsZChzcCwgcnAtPnBkdSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmcGt0YnVmLCAmcGt0YnVmX2xlbiwgJm9mZnNldCk7CgogICAgICAgIHBhY2tldCA9IHBrdGJ1ZjsKICAgICAgICBsZW5ndGggPSBvZmZzZXQ7CiAgICB9IGVsc2UgaWYgKGlzcC0+aG9va19idWlsZCkgewogICAgICAgIHBhY2tldCA9IHBrdGJ1ZjsKICAgICAgICBsZW5ndGggPSBwa3RidWZfbGVuOwogICAgICAgIHJlc3VsdCA9IGlzcC0+aG9va19idWlsZChzcCwgcnAtPnBkdSwgcGt0YnVmLCAmbGVuZ3RoKTsKICAgIH0gZWxzZSB7CiNpZmRlZiBORVRTTk1QX1VTRV9SRVZFUlNFX0FTTkVOQ09ESU5HCiAgICAgICAgaWYgKG5ldHNubXBfZHNfZ2V0X2Jvb2xlYW4oTkVUU05NUF9EU19MSUJSQVJZX0lELCBORVRTTk1QX0RTX0xJQl9SRVZFUlNFX0VOQ09ERSkpIHsKICAgICAgICAgICAgcmVzdWx0ID0KICAgICAgICAgICAgICAgIHNubXBfYnVpbGQoJnBrdGJ1ZiwgJnBrdGJ1Zl9sZW4sICZvZmZzZXQsIHNwLCBycC0+cGR1KTsKICAgICAgICAgICAgcGFja2V0ID0gcGt0YnVmICsgcGt0YnVmX2xlbiAtIG9mZnNldDsKICAgICAgICAgICAgbGVuZ3RoID0gb2Zmc2V0OwogICAgICAgIH0gZWxzZSB7CiNlbmRpZgogICAgICAgICAgICBwYWNrZXQgPSBwa3RidWY7CiAgICAgICAgICAgIGxlbmd0aCA9IHBrdGJ1Zl9sZW47CiAgICAgICAgICAgIHJlc3VsdCA9IHNubXBfYnVpbGQoJnBrdGJ1ZiwgJmxlbmd0aCwgJm9mZnNldCwgc3AsIHJwLT5wZHUpOwojaWZkZWYgTkVUU05NUF9VU0VfUkVWRVJTRV9BU05FTkNPRElORwogICAgICAgIH0KI2VuZGlmCiAgICB9CgogICAgaWYgKHJlc3VsdCA8IDApIHsKICAgICAgICAvKgogICAgICAgICAqIFRoaXMgc2hvdWxkIG5ldmVyIGhhcHBlbi4gIAogICAgICAgICAqLwogICAgICAgIERFQlVHTVNHVEwoKCJzZXNzX3Jlc2VuZCIsICJlbmNvZGluZyBmYWlsdXJlXG4iKSk7CiAgICAgICAgaWYgKHBrdGJ1ZiAhPSBOVUxMKSB7CiAgICAgICAgICAgIFNOTVBfRlJFRShwa3RidWYpOwogICAgICAgIH0KICAgICAgICByZXR1cm4gLTE7CiAgICB9CgogICAgaWYgKG5ldHNubXBfZHNfZ2V0X2Jvb2xlYW4oTkVUU05NUF9EU19MSUJSQVJZX0lELCBORVRTTk1QX0RTX0xJQl9EVU1QX1BBQ0tFVCkpIHsKICAgICAgICBpZiAodHJhbnNwb3J0LT5mX2ZtdGFkZHIgIT0gTlVMTCkgewogICAgICAgICAgICBjaGFyICAgICAgICAgICAqc3RyID0gTlVMTDsKICAgICAgICAgICAgc3RyID0gdHJhbnNwb3J0LT5mX2ZtdGFkZHIodHJhbnNwb3J0LCBycC0+cGR1LT50cmFuc3BvcnRfZGF0YSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcnAtPnBkdS0+dHJhbnNwb3J0X2RhdGFfbGVuZ3RoKTsKICAgICAgICAgICAgaWYgKHN0ciAhPSBOVUxMKSB7CiAgICAgICAgICAgICAgICBzbm1wX2xvZyhMT0dfREVCVUcsICJcblJlc2VuZGluZyAlbHUgYnl0ZXMgdG8gJXNcbiIsIAogICAgICAgICAgICAgICAgICAgICAgICAgKHVuc2lnbmVkIGxvbmcpbGVuZ3RoLCBzdHIpOwogICAgICAgICAgICAgICAgU05NUF9GUkVFKHN0cik7CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICBzbm1wX2xvZyhMT0dfREVCVUcsICJcblJlc2VuZGluZyAlbHUgYnl0ZXMgdG8gPFVOS05PV04+XG4iLAogICAgICAgICAgICAgICAgICAgICAgICAgKHVuc2lnbmVkIGxvbmcpbGVuZ3RoKTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICB4ZHVtcChwYWNrZXQsIGxlbmd0aCwgIiIpOwogICAgfQoKICAgIHJlc3VsdCA9IHRyYW5zcG9ydC0+Zl9zZW5kKHRyYW5zcG9ydCwgcGFja2V0LCBsZW5ndGgsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmKHJwLT5wZHUtPnRyYW5zcG9ydF9kYXRhKSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICYocnAtPnBkdS0+dHJhbnNwb3J0X2RhdGFfbGVuZ3RoKSk7CgogICAgLyoKICAgICAqIFdlIGFyZSBmaW5pc2hlZCB3aXRoIHRoZSBsb2NhbCBwYWNrZXQgYnVmZmVyLCBpZiB3ZSBhbGxvY2F0ZWQgb25lIChkdWUKICAgICAqIHRvIHRoZXJlIGJlaW5nIG5vIHNhdmVkIHBhY2tldCkuICAKICAgICAqLwoKICAgIGlmIChwa3RidWYgIT0gTlVMTCkgewogICAgICAgIFNOTVBfRlJFRShwa3RidWYpOwogICAgICAgIHBrdGJ1ZiA9IHBhY2tldCA9IE5VTEw7CiAgICB9CgogICAgaWYgKHJlc3VsdCA8IDApIHsKICAgICAgICBzcC0+c19zbm1wX2Vycm5vID0gU05NUEVSUl9CQURfU0VORFRPOwogICAgICAgIHNwLT5zX2Vycm5vID0gZXJybm87CiAgICAgICAgc25tcF9zZXRfZGV0YWlsKHN0cmVycm9yKGVycm5vKSk7CiAgICAgICAgcmV0dXJuIC0xOwogICAgfSBlbHNlIHsKICAgICAgICBnZXR0aW1lb2ZkYXkoJm5vdywgKHN0cnVjdCB0aW1lem9uZSAqKSAwKTsKICAgICAgICB0diA9IG5vdzsKICAgICAgICBycC0+dGltZSA9IHR2OwogICAgICAgIHR2LnR2X3VzZWMgKz0gcnAtPnRpbWVvdXQ7CiAgICAgICAgdHYudHZfc2VjICs9IHR2LnR2X3VzZWMgLyAxMDAwMDAwTDsKICAgICAgICB0di50dl91c2VjICU9IDEwMDAwMDBMOwogICAgICAgIHJwLT5leHBpcmUgPSB0djsKICAgIH0KICAgIHJldHVybiAwOwp9CgoKCnZvaWQKc25tcF9zZXNzX3RpbWVvdXQodm9pZCAqc2Vzc3ApCnsKICAgIHN0cnVjdCBzZXNzaW9uX2xpc3QgKnNscCA9IChzdHJ1Y3Qgc2Vzc2lvbl9saXN0ICopIHNlc3NwOwogICAgbmV0c25tcF9zZXNzaW9uICpzcDsKICAgIHN0cnVjdCBzbm1wX2ludGVybmFsX3Nlc3Npb24gKmlzcDsKICAgIG5ldHNubXBfcmVxdWVzdF9saXN0ICpycCwgKm9ycCA9IE5VTEwsICpmcmVlbWUgPSBOVUxMOwogICAgc3RydWN0IHRpbWV2YWwgIG5vdzsKICAgIHNubXBfY2FsbGJhY2sgICBjYWxsYmFjazsKICAgIHZvaWQgICAgICAgICAgICptYWdpYzsKICAgIHN0cnVjdCBzbm1wX3NlY21vZF9kZWYgKnNwdHI7CgogICAgc3AgPSBzbHAtPnNlc3Npb247CiAgICBpc3AgPSBzbHAtPmludGVybmFsOwogICAgaWYgKCFzcCB8fCAhaXNwKSB7CiAgICAgICAgREVCVUdNU0dUTCgoInNlc3NfcmVhZCIsICJ0aW1lb3V0IGZhaWw6IGNsb3NpbmcuLi5cbiIpKTsKICAgICAgICByZXR1cm47CiAgICB9CgogICAgZ2V0dGltZW9mZGF5KCZub3csIChzdHJ1Y3QgdGltZXpvbmUgKikgMCk7CgogICAgLyoKICAgICAqIEZvciBlYWNoIHJlcXVlc3Qgb3V0c3RhbmRpbmcsIGNoZWNrIHRvIHNlZSBpZiBpdCBoYXMgZXhwaXJlZC4KICAgICAqLwogICAgZm9yIChycCA9IGlzcC0+cmVxdWVzdHM7IHJwOyBycCA9IHJwLT5uZXh0X3JlcXVlc3QpIHsKICAgICAgICBpZiAoZnJlZW1lICE9IE5VTEwpIHsKICAgICAgICAgICAgLyoKICAgICAgICAgICAgICogZnJlZXMgcnAncyBhZnRlciB0aGUgZm9yIGxvb3AgZ29lcyBvbiB0byB0aGUgbmV4dF9yZXF1ZXN0IAogICAgICAgICAgICAgKi8KICAgICAgICAgICAgZnJlZSgoY2hhciAqKSBmcmVlbWUpOwogICAgICAgICAgICBmcmVlbWUgPSBOVUxMOwogICAgICAgIH0KCiAgICAgICAgaWYgKCh0aW1lcmNtcCgmcnAtPmV4cGlyZSwgJm5vdywgPCkpKSB7CiAgICAgICAgICAgIGlmICgoc3B0ciA9IGZpbmRfc2VjX21vZChycC0+cGR1LT5zZWN1cml0eU1vZGVsKSkgIT0gTlVMTCAmJgogICAgICAgICAgICAgICAgc3B0ci0+cGR1X3RpbWVvdXQgIT0gTlVMTCkgewogICAgICAgICAgICAgICAgLyoKICAgICAgICAgICAgICAgICAqIGNhbGwgc2VjdXJpdHkgbW9kZWwgaWYgaXQgbmVlZHMgdG8ga25vdyBhYm91dCB0aGlzIAogICAgICAgICAgICAgICAgICovCiAgICAgICAgICAgICAgICAoKnNwdHItPnBkdV90aW1lb3V0KSAocnAtPnBkdSk7CiAgICAgICAgICAgIH0KCiAgICAgICAgICAgIC8qCiAgICAgICAgICAgICAqIHRoaXMgdGltZXIgaGFzIGV4cGlyZWQgCiAgICAgICAgICAgICAqLwogICAgICAgICAgICBpZiAocnAtPnJldHJpZXMgPj0gc3AtPnJldHJpZXMpIHsKICAgICAgICAgICAgICAgIGlmIChycC0+Y2FsbGJhY2spIHsKICAgICAgICAgICAgICAgICAgICBjYWxsYmFjayA9IHJwLT5jYWxsYmFjazsKICAgICAgICAgICAgICAgICAgICBtYWdpYyA9IHJwLT5jYl9kYXRhOwogICAgICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgICAgICBjYWxsYmFjayA9IHNwLT5jYWxsYmFjazsKICAgICAgICAgICAgICAgICAgICBtYWdpYyA9IHNwLT5jYWxsYmFja19tYWdpYzsKICAgICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgICAvKgogICAgICAgICAgICAgICAgICogTm8gbW9yZSBjaGFuY2VzLCBkZWxldGUgdGhpcyBlbnRyeSAKICAgICAgICAgICAgICAgICAqLwogICAgICAgICAgICAgICAgaWYgKGNhbGxiYWNrKSB7CiAgICAgICAgICAgICAgICAgICAgY2FsbGJhY2soTkVUU05NUF9DQUxMQkFDS19PUF9USU1FRF9PVVQsIHNwLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJwLT5wZHUtPnJlcWlkLCBycC0+cGR1LCBtYWdpYyk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBpZiAoaXNwLT5yZXF1ZXN0cyA9PSBycCkgewogICAgICAgICAgICAgICAgICAgIGlzcC0+cmVxdWVzdHMgPSBycC0+bmV4dF9yZXF1ZXN0OwogICAgICAgICAgICAgICAgICAgIGlmIChpc3AtPnJlcXVlc3RzRW5kID09IHJwKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGlzcC0+cmVxdWVzdHNFbmQgPSBOVUxMOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgb3JwLT5uZXh0X3JlcXVlc3QgPSBycC0+bmV4dF9yZXF1ZXN0OwogICAgICAgICAgICAgICAgICAgIGlmIChpc3AtPnJlcXVlc3RzRW5kID09IHJwKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGlzcC0+cmVxdWVzdHNFbmQgPSBvcnA7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgc25tcF9mcmVlX3BkdShycC0+cGR1KTsgLyogRklYICBycCBpcyBhbHJlYWR5IGZyZWUnZCEgKi8KICAgICAgICAgICAgICAgIGZyZWVtZSA9IHJwOwogICAgICAgICAgICAgICAgY29udGludWU7ICAgICAgIC8qIGRvbid0IHVwZGF0ZSBvcnAgYmVsb3cgKi8KICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgIGlmIChzbm1wX3Jlc2VuZF9yZXF1ZXN0KHNscCwgcnAsIFRSVUUpKSB7CiAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgb3JwID0gcnA7CiAgICB9CgogICAgaWYgKGZyZWVtZSAhPSBOVUxMKSB7CiAgICAgICAgZnJlZSgoY2hhciAqKSBmcmVlbWUpOwogICAgICAgIGZyZWVtZSA9IE5VTEw7CiAgICB9Cn0KCi8qCiAqIGxleGljb2dyYXBoaWNhbCBjb21wYXJlIHR3byBvYmplY3QgaWRlbnRpZmllcnMuCiAqICogUmV0dXJucyAtMSBpZiBuYW1lMSA8IG5hbWUyLAogKiAqICAgICAgICAgIDAgaWYgbmFtZTEgPSBuYW1lMiwKICogKiAgICAgICAgICAxIGlmIG5hbWUxID4gbmFtZTIKICogKgogKiAqIENhdXRpb246IHRoaXMgbWV0aG9kIGlzIGNhbGxlZCBvZnRlbiBieQogKiAqICAgICAgICAgIGNvbW1hbmQgcmVzcG9uZGVyIGFwcGxpY2F0aW9ucyAoaWUsIGFnZW50KS4KICovCmludApzbm1wX29pZF9uY29tcGFyZShjb25zdCBvaWQgKiBpbl9uYW1lMSwKICAgICAgICAgICAgICAgICAgc2l6ZV90IGxlbjEsCiAgICAgICAgICAgICAgICAgIGNvbnN0IG9pZCAqIGluX25hbWUyLCBzaXplX3QgbGVuMiwgc2l6ZV90IG1heF9sZW4pCnsKICAgIHJlZ2lzdGVyIGludCAgICBsZW47CiAgICByZWdpc3RlciBjb25zdCBvaWQgKm5hbWUxID0gaW5fbmFtZTE7CiAgICByZWdpc3RlciBjb25zdCBvaWQgKm5hbWUyID0gaW5fbmFtZTI7CiAgICBzaXplX3QgICAgICAgICAgbWluX2xlbjsKCiAgICAvKgogICAgICogbGVuID0gbWluaW11bSBvZiBsZW4xIGFuZCBsZW4yIAogICAgICovCiAgICBpZiAobGVuMSA8IGxlbjIpCiAgICAgICAgbWluX2xlbiA9IGxlbjE7CiAgICBlbHNlCiAgICAgICAgbWluX2xlbiA9IGxlbjI7CgogICAgaWYgKG1pbl9sZW4gPiBtYXhfbGVuKQogICAgICAgIG1pbl9sZW4gPSBtYXhfbGVuOwoKICAgIGxlbiA9IG1pbl9sZW47CgogICAgLyoKICAgICAqIGZpbmQgZmlyc3Qgbm9uLW1hdGNoaW5nIE9JRCAKICAgICAqLwogICAgd2hpbGUgKGxlbi0tID4gMCkgewogICAgICAgIC8qCiAgICAgICAgICogdGhlc2UgbXVzdCBiZSBkb25lIGluIHNlcGVyYXRlIGNvbXBhcmlzb25zLCBzaW5jZQogICAgICAgICAqIHN1YnRyYWN0aW5nIHRoZW0gYW5kIHVzaW5nIHRoYXQgcmVzdWx0IGhhcyBwcm9ibGVtcyB3aXRoCiAgICAgICAgICogc3ViaWRzID4gMl4zMS4gCiAgICAgICAgICovCiAgICAgICAgaWYgKCoobmFtZTEpICE9ICoobmFtZTIpKSB7CiAgICAgICAgICAgIGlmICgqKG5hbWUxKSA8ICoobmFtZTIpKQogICAgICAgICAgICAgICAgcmV0dXJuIC0xOwogICAgICAgICAgICByZXR1cm4gMTsKICAgICAgICB9CiAgICAgICAgbmFtZTErKzsKICAgICAgICBuYW1lMisrOwogICAgfQoKICAgIGlmIChtaW5fbGVuICE9IG1heF9sZW4pIHsKICAgICAgICAvKgogICAgICAgICAqIGJvdGggT0lEcyBlcXVhbCB1cCB0byBsZW5ndGggb2Ygc2hvcnRlciBPSUQgCiAgICAgICAgICovCiAgICAgICAgaWYgKGxlbjEgPCBsZW4yKQogICAgICAgICAgICByZXR1cm4gLTE7CiAgICAgICAgaWYgKGxlbjIgPCBsZW4xKQogICAgICAgICAgICByZXR1cm4gMTsKICAgIH0KCiAgICByZXR1cm4gMDsKfQoKLyoqIGxleGljb2dyYXBoaWNhbCBjb21wYXJlIHR3byBvYmplY3QgaWRlbnRpZmllcnMuCiAqIAogKiBDYXV0aW9uOiB0aGlzIG1ldGhvZCBpcyBjYWxsZWQgb2Z0ZW4gYnkKICogICAgICAgICAgY29tbWFuZCByZXNwb25kZXIgYXBwbGljYXRpb25zIChpZSwgYWdlbnQpLgogKgogKiBAcmV0dXJuIC0xIGlmIG5hbWUxIDwgbmFtZTIsIDAgaWYgbmFtZTEgPSBuYW1lMiwgMSBpZiBuYW1lMSA+IG5hbWUyCiAqLwppbnQKc25tcF9vaWRfY29tcGFyZShjb25zdCBvaWQgKiBpbl9uYW1lMSwKICAgICAgICAgICAgICAgICBzaXplX3QgbGVuMSwgY29uc3Qgb2lkICogaW5fbmFtZTIsIHNpemVfdCBsZW4yKQp7CiAgICByZWdpc3RlciBpbnQgICAgbGVuOwogICAgcmVnaXN0ZXIgY29uc3Qgb2lkICpuYW1lMSA9IGluX25hbWUxOwogICAgcmVnaXN0ZXIgY29uc3Qgb2lkICpuYW1lMiA9IGluX25hbWUyOwoKICAgIC8qCiAgICAgKiBsZW4gPSBtaW5pbXVtIG9mIGxlbjEgYW5kIGxlbjIgCiAgICAgKi8KICAgIGlmIChsZW4xIDwgbGVuMikKICAgICAgICBsZW4gPSBsZW4xOwogICAgZWxzZQogICAgICAgIGxlbiA9IGxlbjI7CiAgICAvKgogICAgICogZmluZCBmaXJzdCBub24tbWF0Y2hpbmcgT0lEIAogICAgICovCiAgICB3aGlsZSAobGVuLS0gPiAwKSB7CiAgICAgICAgLyoKICAgICAgICAgKiB0aGVzZSBtdXN0IGJlIGRvbmUgaW4gc2VwZXJhdGUgY29tcGFyaXNvbnMsIHNpbmNlCiAgICAgICAgICogc3VidHJhY3RpbmcgdGhlbSBhbmQgdXNpbmcgdGhhdCByZXN1bHQgaGFzIHByb2JsZW1zIHdpdGgKICAgICAgICAgKiBzdWJpZHMgPiAyXjMxLiAKICAgICAgICAgKi8KICAgICAgICBpZiAoKihuYW1lMSkgIT0gKihuYW1lMikpIHsKICAgICAgICAgICAgaWYgKCoobmFtZTEpIDwgKihuYW1lMikpCiAgICAgICAgICAgICAgICByZXR1cm4gLTE7CiAgICAgICAgICAgIHJldHVybiAxOwogICAgICAgIH0KICAgICAgICBuYW1lMSsrOwogICAgICAgIG5hbWUyKys7CiAgICB9CiAgICAvKgogICAgICogYm90aCBPSURzIGVxdWFsIHVwIHRvIGxlbmd0aCBvZiBzaG9ydGVyIE9JRCAKICAgICAqLwogICAgaWYgKGxlbjEgPCBsZW4yKQogICAgICAgIHJldHVybiAtMTsKICAgIGlmIChsZW4yIDwgbGVuMSkKICAgICAgICByZXR1cm4gMTsKICAgIHJldHVybiAwOwp9CgovKiogbGV4aWNvZ3JhcGhpY2FsIGNvbXBhcmUgdHdvIG9iamVjdCBpZGVudGlmaWVycyBhbmQgcmV0dXJuIHRoZSBwb2ludCB3aGVyZSB0aGV5IGRpZmZlcgogKiAKICogQ2F1dGlvbjogdGhpcyBtZXRob2QgaXMgY2FsbGVkIG9mdGVuIGJ5CiAqICAgICAgICAgIGNvbW1hbmQgcmVzcG9uZGVyIGFwcGxpY2F0aW9ucyAoaWUsIGFnZW50KS4KICoKICogQHJldHVybiAtMSBpZiBuYW1lMSA8IG5hbWUyLCAwIGlmIG5hbWUxID0gbmFtZTIsIDEgaWYgbmFtZTEgPiBuYW1lMiBhbmQgb2ZmcHQgPSBsZW4gd2hlcmUgbmFtZTEgIT0gbmFtZTIKICovCmludApuZXRzbm1wX29pZF9jb21wYXJlX2xsKGNvbnN0IG9pZCAqIGluX25hbWUxLAogICAgICAgICAgICAgICAgICAgICAgIHNpemVfdCBsZW4xLCBjb25zdCBvaWQgKiBpbl9uYW1lMiwgc2l6ZV90IGxlbjIsCiAgICAgICAgICAgICAgICAgICAgICAgc2l6ZV90ICpvZmZwdCkKewogICAgcmVnaXN0ZXIgaW50ICAgIGxlbjsKICAgIHJlZ2lzdGVyIGNvbnN0IG9pZCAqbmFtZTEgPSBpbl9uYW1lMTsKICAgIHJlZ2lzdGVyIGNvbnN0IG9pZCAqbmFtZTIgPSBpbl9uYW1lMjsKICAgIGludCBpbml0bGVuOwoKICAgIC8qCiAgICAgKiBsZW4gPSBtaW5pbXVtIG9mIGxlbjEgYW5kIGxlbjIgCiAgICAgKi8KICAgIGlmIChsZW4xIDwgbGVuMikKICAgICAgICBpbml0bGVuID0gbGVuID0gbGVuMTsKICAgIGVsc2UKICAgICAgICBpbml0bGVuID0gbGVuID0gbGVuMjsKICAgIC8qCiAgICAgKiBmaW5kIGZpcnN0IG5vbi1tYXRjaGluZyBPSUQgCiAgICAgKi8KICAgIHdoaWxlIChsZW4tLSA+IDApIHsKICAgICAgICAvKgogICAgICAgICAqIHRoZXNlIG11c3QgYmUgZG9uZSBpbiBzZXBlcmF0ZSBjb21wYXJpc29ucywgc2luY2UKICAgICAgICAgKiBzdWJ0cmFjdGluZyB0aGVtIGFuZCB1c2luZyB0aGF0IHJlc3VsdCBoYXMgcHJvYmxlbXMgd2l0aAogICAgICAgICAqIHN1YmlkcyA+IDJeMzEuIAogICAgICAgICAqLwogICAgICAgIGlmICgqKG5hbWUxKSAhPSAqKG5hbWUyKSkgewogICAgICAgICAgICAqb2ZmcHQgPSBpbml0bGVuIC0gbGVuOwogICAgICAgICAgICBpZiAoKihuYW1lMSkgPCAqKG5hbWUyKSkKICAgICAgICAgICAgICAgIHJldHVybiAtMTsKICAgICAgICAgICAgcmV0dXJuIDE7CiAgICAgICAgfQogICAgICAgIG5hbWUxKys7CiAgICAgICAgbmFtZTIrKzsKICAgIH0KICAgIC8qCiAgICAgKiBib3RoIE9JRHMgZXF1YWwgdXAgdG8gbGVuZ3RoIG9mIHNob3J0ZXIgT0lEIAogICAgICovCiAgICAqb2ZmcHQgPSBpbml0bGVuIC0gbGVuOwogICAgaWYgKGxlbjEgPCBsZW4yKQogICAgICAgIHJldHVybiAtMTsKICAgIGlmIChsZW4yIDwgbGVuMSkKICAgICAgICByZXR1cm4gMTsKICAgIHJldHVybiAwOwp9CgovKiogQ29tcGFyZXMgMiBPSURzIHRvIGRldGVybWluZSBpZiB0aGV5IGFyZSBlcXVhbCB1cCB1bnRpbCB0aGUgc2hvcnRlc3QgbGVuZ3RoLgogKiBAcGFyYW0gaW5fbmFtZTEgQSBwb2ludGVyIHRvIHRoZSBmaXJzdCBvaWQuCiAqIEBwYXJhbSBsZW4xICAgICBsZW5ndGggb2YgdGhlIGZpcnN0IE9JRCAoaW4gc2VnbWVudHMsIG5vdCBieXRlcykKICogQHBhcmFtIGluX25hbWUyIEEgcG9pbnRlciB0byB0aGUgc2Vjb25kIG9pZC4KICogQHBhcmFtIGxlbjIgICAgIGxlbmd0aCBvZiB0aGUgc2Vjb25kIE9JRCAoaW4gc2VnbWVudHMsIG5vdCBieXRlcykKICogQHJldHVybiAwIGlmIHRoZXkgYXJlIGVxdWFsLCAxIGlmIGluX25hbWUxIGlzID4gaW5fbmFtZTIsIG9yIC0xIGlmIDwuCiAqLyAKaW50CnNubXBfb2lkdHJlZV9jb21wYXJlKGNvbnN0IG9pZCAqIGluX25hbWUxLAogICAgICAgICAgICAgICAgICAgICBzaXplX3QgbGVuMSwgY29uc3Qgb2lkICogaW5fbmFtZTIsIHNpemVfdCBsZW4yKQp7CiAgICBpbnQgICAgICAgICAgICAgbGVuID0gKChsZW4xIDwgbGVuMikgPyBsZW4xIDogbGVuMik7CgogICAgcmV0dXJuIChzbm1wX29pZF9jb21wYXJlKGluX25hbWUxLCBsZW4sIGluX25hbWUyLCBsZW4pKTsKfQoKaW50CnNubXBfb2lkc3VidHJlZV9jb21wYXJlKGNvbnN0IG9pZCAqIGluX25hbWUxLAogICAgICAgICAgICAgICAgICAgICBzaXplX3QgbGVuMSwgY29uc3Qgb2lkICogaW5fbmFtZTIsIHNpemVfdCBsZW4yKQp7CiAgICBpbnQgICAgICAgICAgICAgbGVuID0gKChsZW4xIDwgbGVuMikgPyBsZW4xIDogbGVuMik7CgogICAgcmV0dXJuIChzbm1wX29pZF9jb21wYXJlKGluX25hbWUxLCBsZW4xLCBpbl9uYW1lMiwgbGVuKSk7Cn0KCi8qKiBDb21wYXJlcyAyIE9JRHMgdG8gZGV0ZXJtaW5lIGlmIHRoZXkgYXJlIGV4YWN0bHkgZXF1YWwuCiAqICBUaGlzIHNob3VsZCBiZSBmYXN0ZXIgdGhhbiBkb2luZyBhIHNubXBfb2lkX2NvbXBhcmUgZm9yIGRpZmZlcmVudAogKiAgbGVuZ3RoIE9JRHMsIHNpbmNlIHRoZSBsZW5ndGggaXMgY2hlY2tlZCBmaXJzdCBhbmQgaWYgIT0gcmV0dXJucwogKiAgaW1tZWRpYXRlbHkuICBNaWdodCBiZSB2ZXJ5IHNsaWdobHkgZmFzdGVyIGlmIGxlbmd0aHMgYXJlID09LgogKiBAcGFyYW0gaW5fbmFtZTEgQSBwb2ludGVyIHRvIHRoZSBmaXJzdCBvaWQuCiAqIEBwYXJhbSBsZW4xICAgICBsZW5ndGggb2YgdGhlIGZpcnN0IE9JRCAoaW4gc2VnbWVudHMsIG5vdCBieXRlcykKICogQHBhcmFtIGluX25hbWUyIEEgcG9pbnRlciB0byB0aGUgc2Vjb25kIG9pZC4KICogQHBhcmFtIGxlbjIgICAgIGxlbmd0aCBvZiB0aGUgc2Vjb25kIE9JRCAoaW4gc2VnbWVudHMsIG5vdCBieXRlcykKICogQHJldHVybiAwIGlmIHRoZXkgYXJlIGVxdWFsLCAxIGlmIHRoZXkgYXJlIG5vdC4KICovIAppbnQKbmV0c25tcF9vaWRfZXF1YWxzKGNvbnN0IG9pZCAqIGluX25hbWUxLAogICAgICAgICAgICAgICAgICAgc2l6ZV90IGxlbjEsIGNvbnN0IG9pZCAqIGluX25hbWUyLCBzaXplX3QgbGVuMikKewogICAgcmVnaXN0ZXIgY29uc3Qgb2lkICpuYW1lMSA9IGluX25hbWUxOwogICAgcmVnaXN0ZXIgY29uc3Qgb2lkICpuYW1lMiA9IGluX25hbWUyOwogICAgcmVnaXN0ZXIgaW50ICAgIGxlbiA9IGxlbjE7CgogICAgLyoKICAgICAqIGxlbiA9IG1pbmltdW0gb2YgbGVuMSBhbmQgbGVuMiAKICAgICAqLwogICAgaWYgKGxlbjEgIT0gbGVuMikKICAgICAgICByZXR1cm4gMTsKICAgIC8qCiAgICAgKiBIYW5kbGUgJ251bGwnIE9JRHMKICAgICAqLwogICAgaWYgKGxlbjEgPT0gMCkKICAgICAgICByZXR1cm4gMDsgICAvKiBUd28gbnVsbCBPSURzIGFyZSAodHJpdmlhbGx5KSB0aGUgc2FtZSAqLwogICAgaWYgKCFuYW1lMSB8fCAhbmFtZTIpCiAgICAgICAgcmV0dXJuIDE7ICAgLyogT3RoZXJ3aXNlIHNvbWV0aGluZydzIHdyb25nLCBzbyByZXBvcnQgYSBub24tbWF0Y2ggKi8KICAgIC8qCiAgICAgKiBmaW5kIGZpcnN0IG5vbi1tYXRjaGluZyBPSUQgCiAgICAgKi8KICAgIHdoaWxlIChsZW4tLSA+IDApIHsKICAgICAgICAvKgogICAgICAgICAqIHRoZXNlIG11c3QgYmUgZG9uZSBpbiBzZXBlcmF0ZSBjb21wYXJpc29ucywgc2luY2UKICAgICAgICAgKiBzdWJ0cmFjdGluZyB0aGVtIGFuZCB1c2luZyB0aGF0IHJlc3VsdCBoYXMgcHJvYmxlbXMgd2l0aAogICAgICAgICAqIHN1YmlkcyA+IDJeMzEuIAogICAgICAgICAqLwogICAgICAgIGlmICgqKG5hbWUxKyspICE9ICoobmFtZTIrKykpCiAgICAgICAgICAgIHJldHVybiAxOwogICAgfQogICAgcmV0dXJuIDA7Cn0KCi8qKiBJZGVudGljYWwgdG8gbmV0c25tcF9vaWRfZXF1YWxzLCBleGNlcHQgb25seSB0aGUgbGVuZ3RoIHVwIHRvIGxlbjEgaXMgY29tcGFyZWQuCiAqIEZ1bmN0aW9uYWxseSwgdGhpcyBkZXRlcm1pbmVzIGlmIGluX25hbWUyIGlzIGVxdWFsIG9yIGEgc3VidHJlZSBvZiBpbl9uYW1lMQogKiBAcGFyYW0gaW5fbmFtZTEgQSBwb2ludGVyIHRvIHRoZSBmaXJzdCBvaWQuCiAqIEBwYXJhbSBsZW4xICAgICBsZW5ndGggb2YgdGhlIGZpcnN0IE9JRCAoaW4gc2VnbWVudHMsIG5vdCBieXRlcykKICogQHBhcmFtIGluX25hbWUyIEEgcG9pbnRlciB0byB0aGUgc2Vjb25kIG9pZC4KICogQHBhcmFtIGxlbjIgICAgIGxlbmd0aCBvZiB0aGUgc2Vjb25kIE9JRCAoaW4gc2VnbWVudHMsIG5vdCBieXRlcykKICogQHJldHVybiAwIGlmIG9uZSBpcyBhIGNvbW1vbiBwcmVmaXggb2YgdGhlIG90aGVyLgogKi8gCmludApuZXRzbm1wX29pZF9pc19zdWJ0cmVlKGNvbnN0IG9pZCAqIGluX25hbWUxLAogICAgICAgICAgICAgICAgICAgICAgIHNpemVfdCBsZW4xLCBjb25zdCBvaWQgKiBpbl9uYW1lMiwgc2l6ZV90IGxlbjIpCnsKICAgIGlmIChsZW4xID4gbGVuMikKICAgICAgICByZXR1cm4gMTsKCiAgICBpZiAobWVtY21wKGluX25hbWUxLCBpbl9uYW1lMiwgbGVuMSAqIHNpemVvZihvaWQpKSkKICAgICAgICByZXR1cm4gMTsKCiAgICByZXR1cm4gMDsKfQoKLyoqIEdpdmVuIHR3byBPSURzLCBkZXRlcm1pbmUgdGhlIGNvbW1vbiBwcmVmaXggdG8gdGhlbSBib3RoLgogKiBAcGFyYW0gaW5fbmFtZTEgQSBwb2ludGVyIHRvIHRoZSBmaXJzdCBvaWQuCiAqIEBwYXJhbSBsZW4xICAgICBMZW5ndGggb2YgdGhlIGZpcnN0IG9pZC4KICogQHBhcmFtIGluX25hbWUyIEEgcG9pbnRlciB0byB0aGUgc2Vjb25kIG9pZC4KICogQHBhcmFtIGxlbjIgICAgIExlbmd0aCBvZiB0aGUgc2Vjb25kIG9pZC4KICogQHJldHVybiAgICAgICAgIGxlbmd0aCBvZiBjb21tb24gcHJlZml4CiAqICAgICAgICAgICAgICAgICAwIGlmIG5vIGNvbW1vbiBwcmVmaXgsIC0xIG9uIGVycm9yLgogKi8KaW50Cm5ldHNubXBfb2lkX2ZpbmRfcHJlZml4KGNvbnN0IG9pZCAqIGluX25hbWUxLCBzaXplX3QgbGVuMSwKICAgICAgICAgICAgICAgICAgICAgICAgY29uc3Qgb2lkICogaW5fbmFtZTIsIHNpemVfdCBsZW4yKQp7CiAgICBpbnQgaTsKICAgIHNpemVfdCBtaW5fc2l6ZTsKCiAgICBpZiAoIWluX25hbWUxIHx8ICFpbl9uYW1lMiB8fCAhbGVuMSB8fCAhbGVuMikKICAgICAgICByZXR1cm4gLTE7CgogICAgaWYgKGluX25hbWUxWzBdICE9IGluX25hbWUyWzBdKQogICAgICAgIHJldHVybiAwOyAgIC8qIE5vIG1hdGNoICovCiAgICBtaW5fc2l6ZSA9IFNOTVBfTUlOKGxlbjEsIGxlbjIpOwogICAgZm9yKGkgPSAwOyBpIDwgKGludCltaW5fc2l6ZTsgaSsrKSB7CiAgICAgICAgaWYgKGluX25hbWUxW2ldICE9IGluX25hbWUyW2ldKQogICAgICAgICAgICByZXR1cm4gaTsgICAgLyogJ+0nIGlzIHRoZSBmaXJzdCBkaWZmZXJpbmcgc3ViaWRlbnRpZmllcgogICAgICAgICAgICAgICAgICAgICAgICAgICAgU28gdGhlIGNvbW1vbiBwcmVmaXggaXMgMC4uKGktMSksIG9mIGxlbmd0aCBpICovCiAgICB9CiAgICByZXR1cm4gbWluX3NpemU7CS8qIFRoZSBzaG9ydGVyIE9JRCBpcyBhIHByZWZpeCBvZiB0aGUgbG9uZ2VyLCBhbmQKICAgICAgICAgICAgICAgICAgICAgICAgICAgaGVuY2UgaXMgcHJlY2lzZWx5IHRoZSBjb21tb24gcHJlZml4IG9mIHRoZSB0d28uCiAgICAgICAgICAgICAgICAgICAgICAgICAgIFJldHVybiBpdHMgbGVuZ3RoLiAqLwp9CgpzdGF0aWMgaW50IF9jaGVja19yYW5nZShzdHJ1Y3QgdHJlZSAqdHAsIGxvbmcgbHRtcCwgaW50ICpyZXNwdHIsCgkgICAgICAgICAgICAgICAgY29uc3QgY2hhciAqZXJybXNnKQp7CiAgICBjaGFyICpjcCAgID0gTlVMTDsKICAgIGNoYXIgKnRlbXAgPSBOVUxMOwogICAgaW50ICAgdGVtcF9sZW4gPSAwOwogICAgaW50IGNoZWNrID0gIW5ldHNubXBfZHNfZ2V0X2Jvb2xlYW4oTkVUU05NUF9EU19MSUJSQVJZX0lELAoJICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBORVRTTk1QX0RTX0xJQl9ET05UX0NIRUNLX1JBTkdFKTsKICAKICAgIGlmIChjaGVjayAmJiB0cCAmJiB0cC0+cmFuZ2VzKSB7CglzdHJ1Y3QgcmFuZ2VfbGlzdCAqcnAgPSB0cC0+cmFuZ2VzOwoJd2hpbGUgKHJwKSB7CgkgICAgaWYgKHJwLT5sb3cgPD0gbHRtcCAmJiBsdG1wIDw9IHJwLT5oaWdoKSBicmVhazsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8qIEFsbG93IGZvdXIgZGlnaXRzIHBlciByYW5nZSB2YWx1ZSAqLwogICAgICAgICAgICB0ZW1wX2xlbiArPSAoKHJwLT5sb3cgIT0gcnAtPmhpZ2gpID8gMTQgOiA4ICk7CgkgICAgcnAgPSBycC0+bmV4dDsKCX0KCWlmICghcnApIHsKCSAgICAqcmVzcHRyID0gU05NUEVSUl9SQU5HRTsKICAgICAgICAgICAgdGVtcCA9IChjaGFyICopbWFsbG9jKCB0ZW1wX2xlbitzdHJsZW4oZXJybXNnKSs3KTsKICAgICAgICAgICAgaWYgKCB0ZW1wICkgewogICAgICAgICAgICAgICAgLyogQXBwZW5kIHRoZSBEaXNwbGF5IEhpbnQgcmFuZ2UgaW5mb3JtYXRpb24gdG8gdGhlIGVycm9yIG1lc3NhZ2UgKi8KICAgICAgICAgICAgICAgIHNwcmludGYoIHRlbXAsICIlcyA6OiB7IiwgZXJybXNnICk7CiAgICAgICAgICAgICAgICBjcCA9IHRlbXArKHN0cmxlbih0ZW1wKSk7CiAgICAgICAgICAgICAgICBmb3IgKCBycCA9IHRwLT5yYW5nZXM7IHJwOyBycD1ycC0+bmV4dCApIHsKICAgICAgICAgICAgICAgICAgICBpZiAoIHJwLT5sb3cgIT0gcnAtPmhpZ2ggKSAKICAgICAgICAgICAgICAgICAgICAgICAgc3ByaW50ZiggY3AsICIoJWQuLiVkKSwgIiwgcnAtPmxvdywgcnAtPmhpZ2ggKTsKICAgICAgICAgICAgICAgICAgICBlbHNlCiAgICAgICAgICAgICAgICAgICAgICAgIHNwcmludGYoIGNwLCAiKCVkKSwgIiwgcnAtPmxvdyApOwogICAgICAgICAgICAgICAgICAgIGNwICs9IHN0cmxlbihjcCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAqKGNwLTIpID0gJ30nOyAgIC8qIFJlcGxhY2UgdGhlIGZpbmFsIGNvbW1hIHdpdGggYSAnfScgKi8KICAgICAgICAgICAgICAgICooY3AtMSkgPSAwOwoJICAgICAgICBzbm1wX3NldF9kZXRhaWwodGVtcCk7CgkgICAgICAgIGZyZWUodGVtcCk7CiAgICAgICAgICAgIH0KCSAgICByZXR1cm4gMDsKCX0KICAgIH0KICAgIGZyZWUodGVtcCk7CiAgICByZXR1cm4gMTsKfQogICAgICAgIAoKLyoKICogQWRkIGEgdmFyaWFibGUgd2l0aCB0aGUgcmVxdWVzdGVkIG5hbWUgdG8gdGhlIGVuZCBvZiB0aGUgbGlzdCBvZgogKiB2YXJpYWJsZXMgZm9yIHRoaXMgcGR1LgogKi8KbmV0c25tcF92YXJpYWJsZV9saXN0ICoKc25tcF9wZHVfYWRkX3ZhcmlhYmxlKG5ldHNubXBfcGR1ICpwZHUsCiAgICAgICAgICAgICAgICAgICAgICBjb25zdCBvaWQgKiBuYW1lLAogICAgICAgICAgICAgICAgICAgICAgc2l6ZV90IG5hbWVfbGVuZ3RoLAogICAgICAgICAgICAgICAgICAgICAgdV9jaGFyIHR5cGUsIGNvbnN0IHVfY2hhciAqIHZhbHVlLCBzaXplX3QgbGVuKQp7CiAgICByZXR1cm4gc25tcF92YXJsaXN0X2FkZF92YXJpYWJsZSgmcGR1LT52YXJpYWJsZXMsIG5hbWUsIG5hbWVfbGVuZ3RoLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdHlwZSwgdmFsdWUsIGxlbik7Cn0KCi8qCiAqIEFkZCBhIHZhcmlhYmxlIHdpdGggdGhlIHJlcXVlc3RlZCBuYW1lIHRvIHRoZSBlbmQgb2YgdGhlIGxpc3Qgb2YKICogdmFyaWFibGVzIGZvciB0aGlzIHBkdS4KICovCm5ldHNubXBfdmFyaWFibGVfbGlzdCAqCnNubXBfdmFybGlzdF9hZGRfdmFyaWFibGUobmV0c25tcF92YXJpYWJsZV9saXN0ICoqIHZhcmxpc3QsCiAgICAgICAgICAgICAgICAgICAgICAgICAgY29uc3Qgb2lkICogbmFtZSwKICAgICAgICAgICAgICAgICAgICAgICAgICBzaXplX3QgbmFtZV9sZW5ndGgsCiAgICAgICAgICAgICAgICAgICAgICAgICAgdV9jaGFyIHR5cGUsIGNvbnN0IHVfY2hhciAqIHZhbHVlLCBzaXplX3QgbGVuKQp7CiAgICBuZXRzbm1wX3ZhcmlhYmxlX2xpc3QgKnZhcnMsICp2dG1wOwogICAgaW50IHJjOwoKICAgIGlmICh2YXJsaXN0ID09IE5VTEwpCiAgICAgICAgcmV0dXJuIE5VTEw7CgogICAgdmFycyA9IFNOTVBfTUFMTE9DX1RZUEVERUYobmV0c25tcF92YXJpYWJsZV9saXN0KTsKICAgIGlmICh2YXJzID09IE5VTEwpCiAgICAgICAgcmV0dXJuIE5VTEw7CgogICAgdmFycy0+dHlwZSA9IHR5cGU7CgogICAgcmMgPSBzbm1wX3NldF92YXJfdmFsdWUoIHZhcnMsIHZhbHVlLCBsZW4gKTsKICAgIGlmICgoIDAgIT0gcmMgKSB8fAogICAgICAgIChuYW1lICE9IE5VTEwgJiYgc25tcF9zZXRfdmFyX29iamlkKHZhcnMsIG5hbWUsIG5hbWVfbGVuZ3RoKSkpIHsKICAgICAgICBzbm1wX2ZyZWVfdmFyKHZhcnMpOwogICAgICAgIHJldHVybiAoMCk7CiAgICB9CgogICAgLyoKICAgICAqIHB1dCBvbmx5IHF1YWxpZmllZCB2YXJpYWJsZSBvbnRvIHZhcmxpc3QgCiAgICAgKi8KICAgIGlmICgqdmFybGlzdCA9PSBOVUxMKSB7CiAgICAgICAgKnZhcmxpc3QgPSB2YXJzOwogICAgfSBlbHNlIHsKICAgICAgICBmb3IgKHZ0bXAgPSAqdmFybGlzdDsgdnRtcC0+bmV4dF92YXJpYWJsZTsKICAgICAgICAgICAgIHZ0bXAgPSB2dG1wLT5uZXh0X3ZhcmlhYmxlKTsKCiAgICAgICAgdnRtcC0+bmV4dF92YXJpYWJsZSA9IHZhcnM7CiAgICB9CgogICAgcmV0dXJuIHZhcnM7Cn0KCgoKLyoKICogQWRkIGEgdmFyaWFibGUgd2l0aCB0aGUgcmVxdWVzdGVkIG5hbWUgdG8gdGhlIGVuZCBvZiB0aGUgbGlzdCBvZgogKiB2YXJpYWJsZXMgZm9yIHRoaXMgcGR1LgogKiBSZXR1cm5zOgogKiBtYXkgc2V0IHRoZXNlIGVycm9yIHR5cGVzIDoKICogU05NUEVSUl9SQU5HRSAtIHR5cGUsIHZhbHVlLCBvciBsZW5ndGggbm90IGZvdW5kIG9yIG91dCBvZiByYW5nZQogKiBTTk1QRVJSX1ZBTFVFIC0gdmFsdWUgaXMgbm90IGNvcnJlY3QKICogU05NUEVSUl9WQVJfVFlQRSAtIHR5cGUgaXMgbm90IGNvcnJlY3QKICogU05NUEVSUl9CQURfTkFNRSAtIG5hbWUgaXMgbm90IGZvdW5kCiAqCiAqIHJldHVybnMgMCBpZiBzdWNjZXNzLCBlcnJvciBpZiBmYWlsdXJlLgogKi8KaW50CnNubXBfYWRkX3ZhcihuZXRzbm1wX3BkdSAqcGR1LAogICAgICAgICAgICAgY29uc3Qgb2lkICogbmFtZSwgc2l6ZV90IG5hbWVfbGVuZ3RoLCBjaGFyIHR5cGUsIGNvbnN0IGNoYXIgKnZhbHVlKQp7CiAgICBjaGFyICAgICAgICAgICAqc3Q7CiAgICBjb25zdCBjaGFyICAgICAqY3A7CiAgICBjaGFyICAgICAgICAgICAqZWNwLCAqdnA7CiAgICBpbnQgICAgICAgICAgICAgcmVzdWx0ID0gU05NUEVSUl9TVUNDRVNTOwojaWZuZGVmIE5FVFNOTVBfRElTQUJMRV9NSUJfTE9BRElORwogICAgaW50ICAgICAgICAgICAgIGNoZWNrID0gIW5ldHNubXBfZHNfZ2V0X2Jvb2xlYW4oTkVUU05NUF9EU19MSUJSQVJZX0lELAoJCQkJCSAgICAgTkVUU05NUF9EU19MSUJfRE9OVF9DSEVDS19SQU5HRSk7CiAgICBpbnQgICAgICAgICAgICAgZG9faGludCA9ICFuZXRzbm1wX2RzX2dldF9ib29sZWFuKE5FVFNOTVBfRFNfTElCUkFSWV9JRCwKCQkJCQkgICAgIE5FVFNOTVBfRFNfTElCX05PX0RJU1BMQVlfSElOVCk7CiAgICB1X2NoYXIgICAgICAgICAqaGludHB0cjsKICAgIHN0cnVjdCB0cmVlICAgICp0cDsKI2VuZGlmIC8qIE5FVFNOTVBfRElTQUJMRV9NSUJfTE9BRElORyAqLwogICAgdV9jaGFyICAgICAgICAgKmJ1ZiA9IE5VTEw7CiAgICBjb25zdCB1X2NoYXIgICAqYnVmX3B0ciA9IE5VTEw7CiAgICBzaXplX3QgICAgICAgICAgYnVmX2xlbiA9IDAsIHZhbHVlX2xlbiA9IDAsIHRpbnQ7CiAgICBpbl9hZGRyX3QgICAgICAgYXRtcDsKICAgIGxvbmcgICAgICAgICAgICBsdG1wOwogICAgaW50ICAgICAgICAgICAgIGl0bXA7CiAgICBzdHJ1Y3QgZW51bV9saXN0ICplcDsKI2lmZGVmIE5FVFNOTVBfV0lUSF9PUEFRVUVfU1BFQ0lBTF9UWVBFUwogICAgZG91YmxlICAgICAgICAgIGR0bXA7CiAgICBmbG9hdCAgICAgICAgICAgZnRtcDsKI2VuZGlmICAgICAgICAgICAgICAgICAgICAgICAgICAvKiBORVRTTk1QX1dJVEhfT1BBUVVFX1NQRUNJQUxfVFlQRVMgKi8KICAgIHN0cnVjdCBjb3VudGVyNjQgYzY0dG1wOwoKI2lmbmRlZiBORVRTTk1QX0RJU0FCTEVfTUlCX0xPQURJTkcKICAgIHRwID0gZ2V0X3RyZWUobmFtZSwgbmFtZV9sZW5ndGgsIGdldF90cmVlX2hlYWQoKSk7CiAgICBpZiAoIXRwIHx8ICF0cC0+dHlwZSB8fCB0cC0+dHlwZSA+IFRZUEVfU0lNUExFX0xBU1QpIHsKICAgICAgICBjaGVjayA9IDA7CiAgICB9CiAgICBpZiAoISh0cCAmJiB0cC0+aGludCkpCglkb19oaW50ID0gMDsKCiAgICBpZiAodHAgJiYgdHlwZSA9PSAnPScpIHsKICAgICAgICAvKgogICAgICAgICAqIGdlbmVyaWMgYXNzaWdubWVudCAtIGxldCB0aGUgdHJlZSBub2RlIGRlY2lkZSB2YWx1ZSBmb3JtYXQgCiAgICAgICAgICovCiAgICAgICAgc3dpdGNoICh0cC0+dHlwZSkgewogICAgICAgIGNhc2UgVFlQRV9JTlRFR0VSOgogICAgICAgIGNhc2UgVFlQRV9JTlRFR0VSMzI6CiAgICAgICAgICAgIHR5cGUgPSAnaSc7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgIGNhc2UgVFlQRV9HQVVHRToKICAgICAgICBjYXNlIFRZUEVfVU5TSUdORUQzMjoKICAgICAgICAgICAgdHlwZSA9ICd1JzsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgY2FzZSBUWVBFX1VJTlRFR0VSOgogICAgICAgICAgICB0eXBlID0gJzMnOwogICAgICAgICAgICBicmVhazsKICAgICAgICBjYXNlIFRZUEVfQ09VTlRFUjoKICAgICAgICAgICAgdHlwZSA9ICdjJzsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgY2FzZSBUWVBFX0NPVU5URVI2NDoKICAgICAgICAgICAgdHlwZSA9ICdDJzsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgY2FzZSBUWVBFX1RJTUVUSUNLUzoKICAgICAgICAgICAgdHlwZSA9ICd0JzsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgY2FzZSBUWVBFX09DVEVUU1RSOgogICAgICAgICAgICB0eXBlID0gJ3MnOwogICAgICAgICAgICBicmVhazsKICAgICAgICBjYXNlIFRZUEVfQklUU1RSSU5HOgogICAgICAgICAgICB0eXBlID0gJ2InOwogICAgICAgICAgICBicmVhazsKICAgICAgICBjYXNlIFRZUEVfSVBBRERSOgogICAgICAgICAgICB0eXBlID0gJ2EnOwogICAgICAgICAgICBicmVhazsKICAgICAgICBjYXNlIFRZUEVfT0JKSUQ6CiAgICAgICAgICAgIHR5cGUgPSAnbyc7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgIH0KICAgIH0KI2VuZGlmIC8qIE5FVFNOTVBfRElTQUJMRV9NSUJfTE9BRElORyAqLwoKICAgIHN3aXRjaCAodHlwZSkgewogICAgY2FzZSAnaSc6CiNpZm5kZWYgTkVUU05NUF9ESVNBQkxFX01JQl9MT0FESU5HCiAgICAgICAgaWYgKGNoZWNrICYmIHRwLT50eXBlICE9IFRZUEVfSU5URUdFUgogICAgICAgICAgICAmJiB0cC0+dHlwZSAhPSBUWVBFX0lOVEVHRVIzMikgewogICAgICAgICAgICB2YWx1ZSA9ICJJTlRFR0VSIjsKICAgICAgICAgICAgcmVzdWx0ID0gU05NUEVSUl9WQUxVRTsKICAgICAgICAgICAgZ290byB0eXBlX2Vycm9yOwogICAgICAgIH0KI2VuZGlmIC8qIE5FVFNOTVBfRElTQUJMRV9NSUJfTE9BRElORyAqLwogICAgICAgIGlmICghKnZhbHVlKQogICAgICAgICAgICBnb3RvIGZhaWw7CiAgICAgICAgbHRtcCA9IHN0cnRvbCh2YWx1ZSwgJmVjcCwgMTApOwogICAgICAgIGlmICgqZWNwKSB7CiNpZm5kZWYgTkVUU05NUF9ESVNBQkxFX01JQl9MT0FESU5HCiAgICAgICAgICAgIGVwID0gdHAgPyB0cC0+ZW51bXMgOiBOVUxMOwogICAgICAgICAgICB3aGlsZSAoZXApIHsKICAgICAgICAgICAgICAgIGlmIChzdHJjbXAodmFsdWUsIGVwLT5sYWJlbCkgPT0gMCkgewogICAgICAgICAgICAgICAgICAgIGx0bXAgPSBlcC0+dmFsdWU7CiAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlcCA9IGVwLT5uZXh0OwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICghZXApIHsKI2VuZGlmIC8qIE5FVFNOTVBfRElTQUJMRV9NSUJfTE9BRElORyAqLwogICAgICAgICAgICAgICAgcmVzdWx0ID0gU05NUEVSUl9SQU5HRTsgICAvKiA/PyBvciBTTk1QRVJSX1ZBTFVFOyAqLwogICAgICAgICAgICAgICAgc25tcF9zZXRfZGV0YWlsKHZhbHVlKTsKICAgICAgICAgICAgICAgIGJyZWFrOwojaWZuZGVmIE5FVFNOTVBfRElTQUJMRV9NSUJfTE9BRElORwogICAgICAgICAgICB9CiNlbmRpZiAvKiBORVRTTk1QX0RJU0FCTEVfTUlCX0xPQURJTkcgKi8KICAgICAgICB9CgojaWZuZGVmIE5FVFNOTVBfRElTQUJMRV9NSUJfTE9BRElORwogICAgICAgIGlmICghX2NoZWNrX3JhbmdlKHRwLCBsdG1wLCAmcmVzdWx0LCB2YWx1ZSkpCiAgICAgICAgICAgIGJyZWFrOwojZW5kaWYgLyogTkVUU05NUF9ESVNBQkxFX01JQl9MT0FESU5HICovCiAgICAgICAgc25tcF9wZHVfYWRkX3ZhcmlhYmxlKHBkdSwgbmFtZSwgbmFtZV9sZW5ndGgsIEFTTl9JTlRFR0VSLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAodV9jaGFyICopICYgbHRtcCwgc2l6ZW9mKGx0bXApKTsKICAgICAgICBicmVhazsKCiAgICBjYXNlICd1JzoKI2lmbmRlZiBORVRTTk1QX0RJU0FCTEVfTUlCX0xPQURJTkcKICAgICAgICBpZiAoY2hlY2sgJiYgdHAtPnR5cGUgIT0gVFlQRV9HQVVHRSAmJiB0cC0+dHlwZSAhPSBUWVBFX1VOU0lHTkVEMzIpIHsKICAgICAgICAgICAgdmFsdWUgPSAiVW5zaWduZWQzMiI7CiAgICAgICAgICAgIHJlc3VsdCA9IFNOTVBFUlJfVkFMVUU7CiAgICAgICAgICAgIGdvdG8gdHlwZV9lcnJvcjsKICAgICAgICB9CiNlbmRpZiAvKiBORVRTTk1QX0RJU0FCTEVfTUlCX0xPQURJTkcgKi8KICAgICAgICBsdG1wID0gc3RydG91bCh2YWx1ZSwgJmVjcCwgMTApOwogICAgICAgIGlmICgqdmFsdWUgJiYgISplY3ApCiAgICAgICAgICAgIHNubXBfcGR1X2FkZF92YXJpYWJsZShwZHUsIG5hbWUsIG5hbWVfbGVuZ3RoLCBBU05fVU5TSUdORUQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAodV9jaGFyICopICYgbHRtcCwgc2l6ZW9mKGx0bXApKTsKICAgICAgICBlbHNlCiAgICAgICAgICAgIGdvdG8gZmFpbDsKICAgICAgICBicmVhazsKCiAgICBjYXNlICczJzoKI2lmbmRlZiBORVRTTk1QX0RJU0FCTEVfTUlCX0xPQURJTkcKICAgICAgICBpZiAoY2hlY2sgJiYgdHAtPnR5cGUgIT0gVFlQRV9VSU5URUdFUikgewogICAgICAgICAgICB2YWx1ZSA9ICJVSW50ZWdlcjMyIjsKICAgICAgICAgICAgcmVzdWx0ID0gU05NUEVSUl9WQUxVRTsKICAgICAgICAgICAgZ290byB0eXBlX2Vycm9yOwogICAgICAgIH0KI2VuZGlmIC8qIE5FVFNOTVBfRElTQUJMRV9NSUJfTE9BRElORyAqLwogICAgICAgIGx0bXAgPSBzdHJ0b3VsKHZhbHVlLCAmZWNwLCAxMCk7CiAgICAgICAgaWYgKCp2YWx1ZSAmJiAhKmVjcCkKICAgICAgICAgICAgc25tcF9wZHVfYWRkX3ZhcmlhYmxlKHBkdSwgbmFtZSwgbmFtZV9sZW5ndGgsIEFTTl9VSU5URUdFUiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICh1X2NoYXIgKikgJiBsdG1wLCBzaXplb2YobHRtcCkpOwogICAgICAgIGVsc2UKICAgICAgICAgICAgZ290byBmYWlsOwogICAgICAgIGJyZWFrOwoKICAgIGNhc2UgJ2MnOgojaWZuZGVmIE5FVFNOTVBfRElTQUJMRV9NSUJfTE9BRElORwogICAgICAgIGlmIChjaGVjayAmJiB0cC0+dHlwZSAhPSBUWVBFX0NPVU5URVIpIHsKICAgICAgICAgICAgdmFsdWUgPSAiQ291bnRlcjMyIjsKICAgICAgICAgICAgcmVzdWx0ID0gU05NUEVSUl9WQUxVRTsKICAgICAgICAgICAgZ290byB0eXBlX2Vycm9yOwogICAgICAgIH0KI2VuZGlmIC8qIE5FVFNOTVBfRElTQUJMRV9NSUJfTE9BRElORyAqLwogICAgICAgIGx0bXAgPSBzdHJ0b3VsKHZhbHVlLCAmZWNwLCAxMCk7CiAgICAgICAgaWYgKCp2YWx1ZSAmJiAhKmVjcCkKICAgICAgICAgICAgc25tcF9wZHVfYWRkX3ZhcmlhYmxlKHBkdSwgbmFtZSwgbmFtZV9sZW5ndGgsIEFTTl9DT1VOVEVSLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKHVfY2hhciAqKSAmIGx0bXAsIHNpemVvZihsdG1wKSk7CiAgICAgICAgZWxzZQogICAgICAgICAgICBnb3RvIGZhaWw7CiAgICAgICAgYnJlYWs7CgogICAgY2FzZSAnQyc6CiNpZm5kZWYgTkVUU05NUF9ESVNBQkxFX01JQl9MT0FESU5HCiAgICAgICAgaWYgKGNoZWNrICYmIHRwLT50eXBlICE9IFRZUEVfQ09VTlRFUjY0KSB7CiAgICAgICAgICAgIHZhbHVlID0gIkNvdW50ZXI2NCI7CiAgICAgICAgICAgIHJlc3VsdCA9IFNOTVBFUlJfVkFMVUU7CiAgICAgICAgICAgIGdvdG8gdHlwZV9lcnJvcjsKICAgICAgICB9CiNlbmRpZiAvKiBORVRTTk1QX0RJU0FCTEVfTUlCX0xPQURJTkcgKi8KICAgICAgICBpZiAocmVhZDY0KCZjNjR0bXAsIHZhbHVlKSkKICAgICAgICAgICAgc25tcF9wZHVfYWRkX3ZhcmlhYmxlKHBkdSwgbmFtZSwgbmFtZV9sZW5ndGgsIEFTTl9DT1VOVEVSNjQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAodV9jaGFyICopICYgYzY0dG1wLCBzaXplb2YoYzY0dG1wKSk7CiAgICAgICAgZWxzZQogICAgICAgICAgICBnb3RvIGZhaWw7CiAgICAgICAgYnJlYWs7CgogICAgY2FzZSAndCc6CiNpZm5kZWYgTkVUU05NUF9ESVNBQkxFX01JQl9MT0FESU5HCiAgICAgICAgaWYgKGNoZWNrICYmIHRwLT50eXBlICE9IFRZUEVfVElNRVRJQ0tTKSB7CiAgICAgICAgICAgIHZhbHVlID0gIlRpbWV0aWNrcyI7CiAgICAgICAgICAgIHJlc3VsdCA9IFNOTVBFUlJfVkFMVUU7CiAgICAgICAgICAgIGdvdG8gdHlwZV9lcnJvcjsKICAgICAgICB9CiNlbmRpZiAvKiBORVRTTk1QX0RJU0FCTEVfTUlCX0xPQURJTkcgKi8KICAgICAgICBsdG1wID0gc3RydG91bCh2YWx1ZSwgJmVjcCwgMTApOwogICAgICAgIGlmICgqdmFsdWUgJiYgISplY3ApCiAgICAgICAgICAgIHNubXBfcGR1X2FkZF92YXJpYWJsZShwZHUsIG5hbWUsIG5hbWVfbGVuZ3RoLCBBU05fVElNRVRJQ0tTLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKHVfY2hhciAqKSAmIGx0bXAsIHNpemVvZihsb25nKSk7CiAgICAgICAgZWxzZQogICAgICAgICAgICBnb3RvIGZhaWw7CiAgICAgICAgYnJlYWs7CgogICAgY2FzZSAnYSc6CiNpZm5kZWYgTkVUU05NUF9ESVNBQkxFX01JQl9MT0FESU5HCiAgICAgICAgaWYgKGNoZWNrICYmIHRwLT50eXBlICE9IFRZUEVfSVBBRERSKSB7CiAgICAgICAgICAgIHZhbHVlID0gIklwQWRkcmVzcyI7CiAgICAgICAgICAgIHJlc3VsdCA9IFNOTVBFUlJfVkFMVUU7CiAgICAgICAgICAgIGdvdG8gdHlwZV9lcnJvcjsKICAgICAgICB9CiNlbmRpZiAvKiBORVRTTk1QX0RJU0FCTEVfTUlCX0xPQURJTkcgKi8KICAgICAgICBhdG1wID0gaW5ldF9hZGRyKHZhbHVlKTsKICAgICAgICBpZiAoYXRtcCAhPSAoaW5fYWRkcl90KSAtMSB8fCAhc3RyY21wKHZhbHVlLCAiMjU1LjI1NS4yNTUuMjU1IikpCiAgICAgICAgICAgIHNubXBfcGR1X2FkZF92YXJpYWJsZShwZHUsIG5hbWUsIG5hbWVfbGVuZ3RoLCBBU05fSVBBRERSRVNTLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKHVfY2hhciAqKSAmIGF0bXAsIHNpemVvZihhdG1wKSk7CiAgICAgICAgZWxzZQogICAgICAgICAgICBnb3RvIGZhaWw7CiAgICAgICAgYnJlYWs7CgogICAgY2FzZSAnbyc6CiNpZm5kZWYgTkVUU05NUF9ESVNBQkxFX01JQl9MT0FESU5HCiAgICAgICAgaWYgKGNoZWNrICYmIHRwLT50eXBlICE9IFRZUEVfT0JKSUQpIHsKICAgICAgICAgICAgdmFsdWUgPSAiT0JKRUNUIElERU5USUZJRVIiOwogICAgICAgICAgICByZXN1bHQgPSBTTk1QRVJSX1ZBTFVFOwogICAgICAgICAgICBnb3RvIHR5cGVfZXJyb3I7CiAgICAgICAgfQojZW5kaWYgLyogTkVUU05NUF9ESVNBQkxFX01JQl9MT0FESU5HICovCiAgICAgICAgaWYgKChidWYgPSAodV9jaGFyICopbWFsbG9jKHNpemVvZihvaWQpICogTUFYX09JRF9MRU4pKSA9PSBOVUxMKSB7CiAgICAgICAgICAgIHJlc3VsdCA9IFNOTVBFUlJfTUFMTE9DOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIHRpbnQgPSBNQVhfT0lEX0xFTjsKICAgICAgICAgICAgaWYgKHNubXBfcGFyc2Vfb2lkKHZhbHVlLCAob2lkICopIGJ1ZiwgJnRpbnQpKSB7CiAgICAgICAgICAgICAgICBzbm1wX3BkdV9hZGRfdmFyaWFibGUocGR1LCBuYW1lLCBuYW1lX2xlbmd0aCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBBU05fT0JKRUNUX0lELCBidWYsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2l6ZW9mKG9pZCkgKiB0aW50KTsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgIHJlc3VsdCA9IHNubXBfZXJybm87ICAgIC8qTVRDUklUSUNBTF9SRVNPVVJDRSAqLwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIGJyZWFrOwoKICAgIGNhc2UgJ3MnOgogICAgY2FzZSAneCc6CiAgICBjYXNlICdkJzoKI2lmbmRlZiBORVRTTk1QX0RJU0FCTEVfTUlCX0xPQURJTkcKICAgICAgICBpZiAoY2hlY2sgJiYgdHAtPnR5cGUgIT0gVFlQRV9PQ1RFVFNUUiAmJiB0cC0+dHlwZSAhPSBUWVBFX0JJVFNUUklORykgewogICAgICAgICAgICB2YWx1ZSA9ICJPQ1RFVCBTVFJJTkciOwogICAgICAgICAgICByZXN1bHQgPSBTTk1QRVJSX1ZBTFVFOwogICAgICAgICAgICBnb3RvIHR5cGVfZXJyb3I7CiAgICAgICAgfQoJaWYgKCdzJyA9PSB0eXBlICYmIGRvX2hpbnQgJiYgIXBhcnNlX29jdGV0X2hpbnQodHAtPmhpbnQsIHZhbHVlLCAmaGludHB0ciwgJml0bXApKSB7CiAgICAgICAgICAgIGlmIChfY2hlY2tfcmFuZ2UodHAsIGl0bXAsICZyZXN1bHQsICJWYWx1ZSBkb2VzIG5vdCBtYXRjaCBESVNQTEFZLUhJTlQiKSkgewogICAgICAgICAgICAgICAgc25tcF9wZHVfYWRkX3ZhcmlhYmxlKHBkdSwgbmFtZSwgbmFtZV9sZW5ndGgsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgQVNOX09DVEVUX1NUUiwgaGludHB0ciwgaXRtcCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgU05NUF9GUkVFKGhpbnRwdHIpOwogICAgICAgICAgICBoaW50cHRyID0gYnVmOwogICAgICAgICAgICBicmVhazsKICAgICAgICB9CiNlbmRpZiAvKiBORVRTTk1QX0RJU0FCTEVfTUlCX0xPQURJTkcgKi8KICAgICAgICBpZiAodHlwZSA9PSAnZCcpIHsKICAgICAgICAgICAgaWYgKCFzbm1wX2RlY2ltYWxfdG9fYmluYXJ5CiAgICAgICAgICAgICAgICAoJmJ1ZiwgJmJ1Zl9sZW4sICZ2YWx1ZV9sZW4sIDEsIHZhbHVlKSkgewogICAgICAgICAgICAgICAgcmVzdWx0ID0gU05NUEVSUl9WQUxVRTsKICAgICAgICAgICAgICAgIHNubXBfc2V0X2RldGFpbCh2YWx1ZSk7CiAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgICAgICBidWZfcHRyID0gYnVmOwogICAgICAgIH0gZWxzZSBpZiAodHlwZSA9PSAneCcpIHsKICAgICAgICAgICAgaWYgKCFzbm1wX2hleF90b19iaW5hcnkoJmJ1ZiwgJmJ1Zl9sZW4sICZ2YWx1ZV9sZW4sIDEsIHZhbHVlKSkgewogICAgICAgICAgICAgICAgcmVzdWx0ID0gU05NUEVSUl9WQUxVRTsKICAgICAgICAgICAgICAgIHNubXBfc2V0X2RldGFpbCh2YWx1ZSk7CiAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgICAgICAvKiBpbml0aWFsaXplIGl0bXAgdmFsdWUgc28gdGhhdCByYW5nZSBjaGVjayBiZWxvdyB3b3JrcyAqLwogICAgICAgICAgICBpdG1wID0gdmFsdWVfbGVuOwogICAgICAgICAgICBidWZfcHRyID0gYnVmOwogICAgICAgIH0gZWxzZSBpZiAodHlwZSA9PSAncycpIHsKICAgICAgICAgICAgYnVmX3B0ciA9IChjb25zdCB1X2NoYXIgKil2YWx1ZTsKICAgICAgICAgICAgdmFsdWVfbGVuID0gc3RybGVuKHZhbHVlKTsKICAgICAgICB9CiNpZm5kZWYgTkVUU05NUF9ESVNBQkxFX01JQl9MT0FESU5HCiAgICAgICAgaWYgKCFfY2hlY2tfcmFuZ2UodHAsIHZhbHVlX2xlbiwgJnJlc3VsdCwgIkJhZCBzdHJpbmcgbGVuZ3RoIikpCiAgICAgICAgICAgIGJyZWFrOwojZW5kaWYgLyogTkVUU05NUF9ESVNBQkxFX01JQl9MT0FESU5HICovCiAgICAgICAgc25tcF9wZHVfYWRkX3ZhcmlhYmxlKHBkdSwgbmFtZSwgbmFtZV9sZW5ndGgsIEFTTl9PQ1RFVF9TVFIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGJ1Zl9wdHIsIHZhbHVlX2xlbik7CiAgICAgICAgYnJlYWs7CgogICAgY2FzZSAnbic6CiAgICAgICAgc25tcF9wZHVfYWRkX3ZhcmlhYmxlKHBkdSwgbmFtZSwgbmFtZV9sZW5ndGgsIEFTTl9OVUxMLCAwLCAwKTsKICAgICAgICBicmVhazsKCiAgICBjYXNlICdiJzoKI2lmbmRlZiBORVRTTk1QX0RJU0FCTEVfTUlCX0xPQURJTkcKICAgICAgICBpZiAoY2hlY2sgJiYgKHRwLT50eXBlICE9IFRZUEVfQklUU1RSSU5HIHx8ICF0cC0+ZW51bXMpKSB7CiAgICAgICAgICAgIHZhbHVlID0gIkJJVFMiOwogICAgICAgICAgICByZXN1bHQgPSBTTk1QRVJSX1ZBTFVFOwogICAgICAgICAgICBnb3RvIHR5cGVfZXJyb3I7CiAgICAgICAgfQojZW5kaWYgLyogTkVUU05NUF9ESVNBQkxFX01JQl9MT0FESU5HICovCiAgICAgICAgdGludCA9IDA7CiAgICAgICAgaWYgKChidWYgPSAodV9jaGFyICopIG1hbGxvYygyNTYpKSA9PSBOVUxMKSB7CiAgICAgICAgICAgIHJlc3VsdCA9IFNOTVBFUlJfTUFMTE9DOwogICAgICAgICAgICBicmVhazsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBidWZfbGVuID0gMjU2OwogICAgICAgICAgICBtZW1zZXQoYnVmLCAwLCBidWZfbGVuKTsKICAgICAgICB9CgojaWZuZGVmIE5FVFNOTVBfRElTQUJMRV9NSUJfTE9BRElORwogICAgICAgIGZvciAoZXAgPSB0cCA/IHRwLT5lbnVtcyA6IE5VTEw7IGVwOyBlcCA9IGVwLT5uZXh0KSB7CiAgICAgICAgICAgIGlmIChlcC0+dmFsdWUgLyA4ID49IChpbnQpIHRpbnQpIHsKICAgICAgICAgICAgICAgIHRpbnQgPSBlcC0+dmFsdWUgLyA4ICsgMTsKICAgICAgICAgICAgfQogICAgICAgIH0KI2VuZGlmIC8qIE5FVFNOTVBfRElTQUJMRV9NSUJfTE9BRElORyAqLwoKCXZwID0gc3RyZHVwKHZhbHVlKTsKCWZvciAoY3AgPSBzdHJ0b2tfcih2cCwgIiAsXHQiLCAmc3QpOyBjcDsgY3AgPSBzdHJ0b2tfcihOVUxMLCAiICxcdCIsICZzdCkpIHsKICAgICAgICAgICAgaW50ICAgICAgICAgICAgIGl4LCBiaXQ7CgogICAgICAgICAgICBsdG1wID0gc3RydG91bChjcCwgJmVjcCwgMCk7CiAgICAgICAgICAgIGlmICgqZWNwICE9IDApIHsKI2lmbmRlZiBORVRTTk1QX0RJU0FCTEVfTUlCX0xPQURJTkcKICAgICAgICAgICAgICAgIGZvciAoZXAgPSB0cCA/IHRwLT5lbnVtcyA6IE5VTEw7IGVwICE9IE5VTEw7IGVwID0gZXAtPm5leHQpIHsKICAgICAgICAgICAgICAgICAgICBpZiAoc3RybmNtcChlcC0+bGFiZWwsIGNwLCBzdHJsZW4oZXAtPmxhYmVsKSkgPT0gMCkgewogICAgICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBpZiAoZXAgIT0gTlVMTCkgewogICAgICAgICAgICAgICAgICAgIGx0bXAgPSBlcC0+dmFsdWU7CiAgICAgICAgICAgICAgICB9IGVsc2UgewojZW5kaWYgLyogTkVUU05NUF9ESVNBQkxFX01JQl9MT0FESU5HICovCiAgICAgICAgICAgICAgICAgICAgcmVzdWx0ID0gU05NUEVSUl9SQU5HRTsgICAvKiA/PyBvciBTTk1QRVJSX1ZBTFVFOyAqLwogICAgICAgICAgICAgICAgICAgIHNubXBfc2V0X2RldGFpbChjcCk7CiAgICAgICAgICAgICAgICAgICAgU05NUF9GUkVFKGJ1Zik7CgkJICAgIFNOTVBfRlJFRSh2cCk7CiAgICAgICAgICAgICAgICAgICAgZ290byBvdXQ7CiNpZm5kZWYgTkVUU05NUF9ESVNBQkxFX01JQl9MT0FESU5HCiAgICAgICAgICAgICAgICB9CiNlbmRpZiAvKiBORVRTTk1QX0RJU0FCTEVfTUlCX0xPQURJTkcgKi8KICAgICAgICAgICAgfQoKICAgICAgICAgICAgaXggPSBsdG1wIC8gODsKICAgICAgICAgICAgaWYgKGl4ID49IChpbnQpIHRpbnQpIHsKICAgICAgICAgICAgICAgIHRpbnQgPSBpeCArIDE7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKGl4ID49IChpbnQpYnVmX2xlbiAmJiAhc25tcF9yZWFsbG9jKCZidWYsICZidWZfbGVuKSkgewogICAgICAgICAgICAgICAgcmVzdWx0ID0gU05NUEVSUl9NQUxMT0M7CiAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgICAgICBiaXQgPSAweDgwID4+IGx0bXAgJSA4OwogICAgICAgICAgICBidWZbaXhdIHw9IGJpdDsKCSAgICAKICAgICAgICB9CglTTk1QX0ZSRUUodnApOwogICAgICAgIHNubXBfcGR1X2FkZF92YXJpYWJsZShwZHUsIG5hbWUsIG5hbWVfbGVuZ3RoLCBBU05fT0NURVRfU1RSLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICBidWYsIHRpbnQpOwogICAgICAgIGJyZWFrOwoKI2lmZGVmIE5FVFNOTVBfV0lUSF9PUEFRVUVfU1BFQ0lBTF9UWVBFUwogICAgY2FzZSAnVSc6CiAgICAgICAgaWYgKHJlYWQ2NCgmYzY0dG1wLCB2YWx1ZSkpCiAgICAgICAgICAgIHNubXBfcGR1X2FkZF92YXJpYWJsZShwZHUsIG5hbWUsIG5hbWVfbGVuZ3RoLCBBU05fT1BBUVVFX1U2NCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICh1X2NoYXIgKikgJiBjNjR0bXAsIHNpemVvZihjNjR0bXApKTsKICAgICAgICBlbHNlCiAgICAgICAgICAgIGdvdG8gZmFpbDsKICAgICAgICBicmVhazsKCiAgICBjYXNlICdJJzoKICAgICAgICBpZiAocmVhZDY0KCZjNjR0bXAsIHZhbHVlKSkKICAgICAgICAgICAgc25tcF9wZHVfYWRkX3ZhcmlhYmxlKHBkdSwgbmFtZSwgbmFtZV9sZW5ndGgsIEFTTl9PUEFRVUVfSTY0LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKHVfY2hhciAqKSAmIGM2NHRtcCwgc2l6ZW9mKGM2NHRtcCkpOwogICAgICAgIGVsc2UKICAgICAgICAgICAgZ290byBmYWlsOwogICAgICAgIGJyZWFrOwoKICAgIGNhc2UgJ0YnOgogICAgICAgIGlmIChzc2NhbmYodmFsdWUsICIlZiIsICZmdG1wKSA9PSAxKQogICAgICAgICAgICBzbm1wX3BkdV9hZGRfdmFyaWFibGUocGR1LCBuYW1lLCBuYW1lX2xlbmd0aCwgQVNOX09QQVFVRV9GTE9BVCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICh1X2NoYXIgKikgJiBmdG1wLCBzaXplb2YoZnRtcCkpOwogICAgICAgIGVsc2UKICAgICAgICAgICAgZ290byBmYWlsOwogICAgICAgIGJyZWFrOwoKICAgIGNhc2UgJ0QnOgogICAgICAgIGlmIChzc2NhbmYodmFsdWUsICIlbGYiLCAmZHRtcCkgPT0gMSkKICAgICAgICAgICAgc25tcF9wZHVfYWRkX3ZhcmlhYmxlKHBkdSwgbmFtZSwgbmFtZV9sZW5ndGgsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBBU05fT1BBUVVFX0RPVUJMRSwgKHVfY2hhciAqKSAmIGR0bXAsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzaXplb2YoZHRtcCkpOwogICAgICAgIGVsc2UKICAgICAgICAgICAgZ290byBmYWlsOwogICAgICAgIGJyZWFrOwojZW5kaWYgICAgICAgICAgICAgICAgICAgICAgICAgIC8qIE5FVFNOTVBfV0lUSF9PUEFRVUVfU1BFQ0lBTF9UWVBFUyAqLwoKICAgIGRlZmF1bHQ6CiAgICAgICAgcmVzdWx0ID0gU05NUEVSUl9WQVJfVFlQRTsKCWJ1ZiA9ICh1X2NoYXIgKiljYWxsb2MoMSwgNCk7CglpZiAoYnVmICE9IE5VTEwpIHsKCSAgICBzcHJpbnRmKChjaGFyICopYnVmLCAiXCIlY1wiIiwgdHlwZSk7CgkgICAgc25tcF9zZXRfZGV0YWlsKChjaGFyICopYnVmKTsKCX0KICAgICAgICBicmVhazsKICAgIH0KCiAgICBTTk1QX0ZSRUUoYnVmKTsKICAgIFNFVF9TTk1QX0VSUk9SKHJlc3VsdCk7CiAgICByZXR1cm4gcmVzdWx0OwoKI2lmbmRlZiBORVRTTk1QX0RJU0FCTEVfTUlCX0xPQURJTkcKICB0eXBlX2Vycm9yOgogICAgewogICAgICAgIGNoYXIgICAgICAgICAgICBlcnJvcl9tc2dbMjU2XTsKICAgICAgICBjaGFyICAgICAgICAgICAgdW5kZWZfbXNnWzMyXTsKICAgICAgICBjb25zdCBjaGFyICAgICAqdmFyX3R5cGU7CiAgICAgICAgc3dpdGNoICh0cC0+dHlwZSkgewogICAgICAgIGNhc2UgVFlQRV9PQkpJRDoKICAgICAgICAgICAgdmFyX3R5cGUgPSAiT0JKRUNUIElERU5USUZJRVIiOwogICAgICAgICAgICBicmVhazsKICAgICAgICBjYXNlIFRZUEVfT0NURVRTVFI6CiAgICAgICAgICAgIHZhcl90eXBlID0gIk9DVEVUIFNUUklORyI7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgIGNhc2UgVFlQRV9JTlRFR0VSOgogICAgICAgICAgICB2YXJfdHlwZSA9ICJJTlRFR0VSIjsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgY2FzZSBUWVBFX05FVEFERFI6CiAgICAgICAgICAgIHZhcl90eXBlID0gIk5ldHdvcmtBZGRyZXNzIjsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgY2FzZSBUWVBFX0lQQUREUjoKICAgICAgICAgICAgdmFyX3R5cGUgPSAiSXBBZGRyZXNzIjsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgY2FzZSBUWVBFX0NPVU5URVI6CiAgICAgICAgICAgIHZhcl90eXBlID0gIkNvdW50ZXIzMiI7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgIGNhc2UgVFlQRV9HQVVHRToKICAgICAgICAgICAgdmFyX3R5cGUgPSAiR2F1Z2UzMiI7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgIGNhc2UgVFlQRV9USU1FVElDS1M6CiAgICAgICAgICAgIHZhcl90eXBlID0gIlRpbWV0aWNrcyI7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgIGNhc2UgVFlQRV9PUEFRVUU6CiAgICAgICAgICAgIHZhcl90eXBlID0gIk9wYXF1ZSI7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgIGNhc2UgVFlQRV9OVUxMOgogICAgICAgICAgICB2YXJfdHlwZSA9ICJOdWxsIjsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgY2FzZSBUWVBFX0NPVU5URVI2NDoKICAgICAgICAgICAgdmFyX3R5cGUgPSAiQ291bnRlcjY0IjsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgY2FzZSBUWVBFX0JJVFNUUklORzoKICAgICAgICAgICAgdmFyX3R5cGUgPSAiQklUUyI7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgIGNhc2UgVFlQRV9OU0FQQUREUkVTUzoKICAgICAgICAgICAgdmFyX3R5cGUgPSAiTnNhcEFkZHJlc3MiOwogICAgICAgICAgICBicmVhazsKICAgICAgICBjYXNlIFRZUEVfVUlOVEVHRVI6CiAgICAgICAgICAgIHZhcl90eXBlID0gIlVJbnRlZ2VyIjsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgY2FzZSBUWVBFX1VOU0lHTkVEMzI6CiAgICAgICAgICAgIHZhcl90eXBlID0gIlVuc2lnbmVkMzIiOwogICAgICAgICAgICBicmVhazsKICAgICAgICBjYXNlIFRZUEVfSU5URUdFUjMyOgogICAgICAgICAgICB2YXJfdHlwZSA9ICJJbnRlZ2VyMzIiOwogICAgICAgICAgICBicmVhazsKICAgICAgICBkZWZhdWx0OgogICAgICAgICAgICBzcHJpbnRmKHVuZGVmX21zZywgIlRZUEVfJWQiLCB0cC0+dHlwZSk7CiAgICAgICAgICAgIHZhcl90eXBlID0gdW5kZWZfbXNnOwogICAgICAgIH0KICAgICAgICBzbnByaW50ZihlcnJvcl9tc2csIHNpemVvZihlcnJvcl9tc2cpLAogICAgICAgICAgICAgICAiVHlwZSBvZiBhdHRyaWJ1dGUgaXMgJXMsIG5vdCAlcyIsIHZhcl90eXBlLCB2YWx1ZSk7CiAgICAgICAgZXJyb3JfbXNnWyBzaXplb2YoZXJyb3JfbXNnKS0xIF0gPSAwOwogICAgICAgIHJlc3VsdCA9IFNOTVBFUlJfVkFSX1RZUEU7CiAgICAgICAgc25tcF9zZXRfZGV0YWlsKGVycm9yX21zZyk7CiAgICAgICAgZ290byBvdXQ7CiAgICB9CiNlbmRpZiAvKiBORVRTTk1QX0RJU0FCTEVfTUlCX0xPQURJTkcgKi8KICBmYWlsOgogICAgcmVzdWx0ID0gU05NUEVSUl9WQUxVRTsKICAgIHNubXBfc2V0X2RldGFpbCh2YWx1ZSk7CiAgb3V0OgogICAgU0VUX1NOTVBfRVJST1IocmVzdWx0KTsKICAgIHJldHVybiByZXN1bHQ7Cn0KCi8qCiAqIHJldHVybnMgTlVMTCBvciBpbnRlcm5hbCBwb2ludGVyIHRvIHNlc3Npb24KICogdXNlIHRoaXMgcG9pbnRlciBmb3IgdGhlIG90aGVyIHNubXBfc2Vzcyogcm91dGluZXMsCiAqIHdoaWNoIGd1YXJhbnRlZSBhY3Rpb24gd2lsbCBvY2N1ciBPTkxZIGZvciB0aGlzIGdpdmVuIHNlc3Npb24uCiAqLwp2b2lkICAgICAgICAgICAqCnNubXBfc2Vzc19wb2ludGVyKG5ldHNubXBfc2Vzc2lvbiAqIHNlc3Npb24pCnsKICAgIHN0cnVjdCBzZXNzaW9uX2xpc3QgKnNscDsKCiAgICBzbm1wX3Jlc19sb2NrKE1UX0xJQlJBUllfSUQsIE1UX0xJQl9TRVNTSU9OKTsKICAgIGZvciAoc2xwID0gU2Vzc2lvbnM7IHNscDsgc2xwID0gc2xwLT5uZXh0KSB7CiAgICAgICAgaWYgKHNscC0+c2Vzc2lvbiA9PSBzZXNzaW9uKSB7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgIH0KICAgIH0KICAgIHNubXBfcmVzX3VubG9jayhNVF9MSUJSQVJZX0lELCBNVF9MSUJfU0VTU0lPTik7CgogICAgaWYgKHNscCA9PSBOVUxMKSB7CiAgICAgICAgc25tcF9lcnJubyA9IFNOTVBFUlJfQkFEX1NFU1NJT047ICAgICAgIC8qTVRDUklUSUNBTF9SRVNPVVJDRSAqLwogICAgICAgIHJldHVybiAoTlVMTCk7CiAgICB9CiAgICByZXR1cm4gKCh2b2lkICopIHNscCk7Cn0KCi8qCiAqIElucHV0IDogYW4gb3BhcXVlIHBvaW50ZXIsIHJldHVybmVkIGJ5IHNubXBfc2Vzc19vcGVuLgogKiByZXR1cm5zIE5VTEwgb3IgcG9pbnRlciB0byBzZXNzaW9uLgogKi8KbmV0c25tcF9zZXNzaW9uICoKc25tcF9zZXNzX3Nlc3Npb24odm9pZCAqc2Vzc3ApCnsKICAgIHN0cnVjdCBzZXNzaW9uX2xpc3QgKnNscCA9IChzdHJ1Y3Qgc2Vzc2lvbl9saXN0ICopIHNlc3NwOwogICAgaWYgKHNscCA9PSBOVUxMKQogICAgICAgIHJldHVybiAoTlVMTCk7CiAgICByZXR1cm4gKHNscC0+c2Vzc2lvbik7Cn0KCi8qKgogKiBMb29rIHVwIGEgc2Vzc2lvbiB0aGF0IGFscmVhZHkgbWF5IGhhdmUgYmVlbiBjbG9zZWQuCiAqCiAqIEBwYXJhbSBzZXNzcCBPcGFxdWUgcG9pbnRlciwgcmV0dXJuZWQgYnkgc25tcF9zZXNzX29wZW4uCiAqCiAqIEByZXR1cm4gUG9pbnRlciB0byBzZXNzaW9uIHVwb24gc3VjY2VzcyBvciBOVUxMIHVwb24gZmFpbHVyZS4KICoKICogQHNlZSBzbm1wX3Nlc3Nfc2Vzc2lvbigpCiAqLwpuZXRzbm1wX3Nlc3Npb24gKgpzbm1wX3Nlc3Nfc2Vzc2lvbl9sb29rdXAodm9pZCAqc2Vzc3ApCnsKICAgIHN0cnVjdCBzZXNzaW9uX2xpc3QgKnNscDsKCiAgICBzbm1wX3Jlc19sb2NrKE1UX0xJQlJBUllfSUQsIE1UX0xJQl9TRVNTSU9OKTsKICAgIGZvciAoc2xwID0gU2Vzc2lvbnM7IHNscDsgc2xwID0gc2xwLT5uZXh0KSB7CiAgICAgICAgaWYgKHNscCA9PSBzZXNzcCkgewogICAgICAgICAgICBicmVhazsKICAgICAgICB9CiAgICB9CiAgICBzbm1wX3Jlc191bmxvY2soTVRfTElCUkFSWV9JRCwgTVRfTElCX1NFU1NJT04pOwoKICAgIHJldHVybiAobmV0c25tcF9zZXNzaW9uICopc2xwOwp9CgoKLyoKICogc25tcF9zZXNzX3RyYW5zcG9ydDogdGFrZXMgYW4gb3BhcXVlIHBvaW50ZXIgKGFzIHJldHVybmVkIGJ5CiAqIHNubXBfc2Vzc19vcGVuIG9yIHNubXBfc2Vzc19wb2ludGVyKSBhbmQgcmV0dXJucyB0aGUgY29ycmVzcG9uZGluZwogKiBuZXRzbm1wX3RyYW5zcG9ydCBwb2ludGVyIChvciBOVUxMIGlmIHRoZSBvcGFxdWUgcG9pbnRlciBkb2VzIG5vdCBjb3JyZXNwb25kCiAqIHRvIGFuIGFjdGl2ZSBpbnRlcm5hbCBzZXNzaW9uKS4gIAogKi8KCm5ldHNubXBfdHJhbnNwb3J0ICoKc25tcF9zZXNzX3RyYW5zcG9ydCh2b2lkICpzZXNzcCkKewogICAgc3RydWN0IHNlc3Npb25fbGlzdCAqc2xwID0gKHN0cnVjdCBzZXNzaW9uX2xpc3QgKikgc2Vzc3A7CiAgICBpZiAoc2xwID09IE5VTEwpIHsKICAgICAgICByZXR1cm4gTlVMTDsKICAgIH0gZWxzZSB7CiAgICAgICAgcmV0dXJuIHNscC0+dHJhbnNwb3J0OwogICAgfQp9CgoKCi8qCiAqIHNubXBfc2Vzc190cmFuc3BvcnRfc2V0OiBzZXQgdGhlIHRyYW5zcG9ydCBwb2ludGVyIGZvciB0aGUgb3BhcXVlCiAqIHNlc3Npb24gcG9pbnRlciBzcC4gIAogKi8KCnZvaWQKc25tcF9zZXNzX3RyYW5zcG9ydF9zZXQodm9pZCAqc3AsIG5ldHNubXBfdHJhbnNwb3J0ICp0KQp7CiAgICBzdHJ1Y3Qgc2Vzc2lvbl9saXN0ICpzbHAgPSAoc3RydWN0IHNlc3Npb25fbGlzdCAqKSBzcDsKICAgIGlmIChzbHAgIT0gTlVMTCkgewogICAgICAgIHNscC0+dHJhbnNwb3J0ID0gdDsKICAgIH0KfQoKCi8qCiAqIHNubXBfZHVwbGljYXRlX29iamlkOiBkdXBsaWNhdGVzIChtYWxsb2NzKSBhbiBvYmppZCBiYXNlZCBvbiB0aGUKICogaW5wdXQgb2JqaWQgCiAqLwpvaWQgICAgICAgICAgICAqCnNubXBfZHVwbGljYXRlX29iamlkKGNvbnN0IG9pZCAqIG9ialRvQ29weSwgc2l6ZV90IG9ialRvQ29weUxlbikKewogICAgb2lkICAgICAgICAgICAgKnJldHVybk9pZCA9IE5VTEw7CiAgICBpZiAob2JqVG9Db3B5ICE9IE5VTEwgJiYgb2JqVG9Db3B5TGVuICE9IDApIHsKICAgICAgICByZXR1cm5PaWQgPSAob2lkICopIG1hbGxvYyhvYmpUb0NvcHlMZW4gKiBzaXplb2Yob2lkKSk7CiAgICAgICAgaWYgKHJldHVybk9pZCkgewogICAgICAgICAgICBtZW1tb3ZlKHJldHVybk9pZCwgb2JqVG9Db3B5LCBvYmpUb0NvcHlMZW4gKiBzaXplb2Yob2lkKSk7CiAgICAgICAgfQogICAgfQogICAgcmV0dXJuIHJldHVybk9pZDsKfQoKLyoKICogZ2VuZXJpYyBzdGF0aXN0aWNzIGNvdW50ZXIgZnVuY3Rpb25zIAogKi8Kc3RhdGljIHVfaW50ICAgIHN0YXRpc3RpY3NbTUFYX1NUQVRTXTsKCnVfaW50CnNubXBfaW5jcmVtZW50X3N0YXRpc3RpYyhpbnQgd2hpY2gpCnsKICAgIGlmICh3aGljaCA+PSAwICYmIHdoaWNoIDwgTUFYX1NUQVRTKSB7CiAgICAgICAgc3RhdGlzdGljc1t3aGljaF0rKzsKICAgICAgICByZXR1cm4gc3RhdGlzdGljc1t3aGljaF07CiAgICB9CiAgICByZXR1cm4gMDsKfQoKdV9pbnQKc25tcF9pbmNyZW1lbnRfc3RhdGlzdGljX2J5KGludCB3aGljaCwgaW50IGNvdW50KQp7CiAgICBpZiAod2hpY2ggPj0gMCAmJiB3aGljaCA8IE1BWF9TVEFUUykgewogICAgICAgIHN0YXRpc3RpY3Nbd2hpY2hdICs9IGNvdW50OwogICAgICAgIHJldHVybiBzdGF0aXN0aWNzW3doaWNoXTsKICAgIH0KICAgIHJldHVybiAwOwp9Cgp1X2ludApzbm1wX2dldF9zdGF0aXN0aWMoaW50IHdoaWNoKQp7CiAgICBpZiAod2hpY2ggPj0gMCAmJiB3aGljaCA8IE1BWF9TVEFUUykKICAgICAgICByZXR1cm4gc3RhdGlzdGljc1t3aGljaF07CiAgICByZXR1cm4gMDsKfQoKdm9pZApzbm1wX2luaXRfc3RhdGlzdGljcyh2b2lkKQp7CiAgICBtZW1zZXQoc3RhdGlzdGljcywgMCwgc2l6ZW9mKHN0YXRpc3RpY3MpKTsKfQovKiogIEB9ICovCgo=