Ci8qIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tClNvZnR3YXJlIExpY2Vuc2UgZm9yIFRoZSBGcmF1bmhvZmVyIEZESyBBQUMgQ29kZWMgTGlicmFyeSBmb3IgQW5kcm9pZAoKqSBDb3B5cmlnaHQgIDE5OTUgLSAyMDEzIEZyYXVuaG9mZXItR2VzZWxsc2NoYWZ0IHp1ciBG9nJkZXJ1bmcgZGVyIGFuZ2V3YW5kdGVuIEZvcnNjaHVuZyBlLlYuCiAgQWxsIHJpZ2h0cyByZXNlcnZlZC4KCiAxLiAgICBJTlRST0RVQ1RJT04KVGhlIEZyYXVuaG9mZXIgRkRLIEFBQyBDb2RlYyBMaWJyYXJ5IGZvciBBbmRyb2lkICgiRkRLIEFBQyBDb2RlYyIpIGlzIHNvZnR3YXJlIHRoYXQgaW1wbGVtZW50cwp0aGUgTVBFRyBBZHZhbmNlZCBBdWRpbyBDb2RpbmcgKCJBQUMiKSBlbmNvZGluZyBhbmQgZGVjb2Rpbmcgc2NoZW1lIGZvciBkaWdpdGFsIGF1ZGlvLgpUaGlzIEZESyBBQUMgQ29kZWMgc29mdHdhcmUgaXMgaW50ZW5kZWQgdG8gYmUgdXNlZCBvbiBhIHdpZGUgdmFyaWV0eSBvZiBBbmRyb2lkIGRldmljZXMuCgpBQUMncyBIRS1BQUMgYW5kIEhFLUFBQyB2MiB2ZXJzaW9ucyBhcmUgcmVnYXJkZWQgYXMgdG9kYXkncyBtb3N0IGVmZmljaWVudCBnZW5lcmFsIHBlcmNlcHR1YWwKYXVkaW8gY29kZWNzLiBBQUMtRUxEIGlzIGNvbnNpZGVyZWQgdGhlIGJlc3QtcGVyZm9ybWluZyBmdWxsLWJhbmR3aWR0aCBjb21tdW5pY2F0aW9ucyBjb2RlYyBieQppbmRlcGVuZGVudCBzdHVkaWVzIGFuZCBpcyB3aWRlbHkgZGVwbG95ZWQuIEFBQyBoYXMgYmVlbiBzdGFuZGFyZGl6ZWQgYnkgSVNPIGFuZCBJRUMgYXMgcGFydApvZiB0aGUgTVBFRyBzcGVjaWZpY2F0aW9ucy4KClBhdGVudCBsaWNlbnNlcyBmb3IgbmVjZXNzYXJ5IHBhdGVudCBjbGFpbXMgZm9yIHRoZSBGREsgQUFDIENvZGVjIChpbmNsdWRpbmcgdGhvc2Ugb2YgRnJhdW5ob2ZlcikKbWF5IGJlIG9idGFpbmVkIHRocm91Z2ggVmlhIExpY2Vuc2luZyAod3d3LnZpYWxpY2Vuc2luZy5jb20pIG9yIHRocm91Z2ggdGhlIHJlc3BlY3RpdmUgcGF0ZW50IG93bmVycwppbmRpdmlkdWFsbHkgZm9yIHRoZSBwdXJwb3NlIG9mIGVuY29kaW5nIG9yIGRlY29kaW5nIGJpdCBzdHJlYW1zIGluIHByb2R1Y3RzIHRoYXQgYXJlIGNvbXBsaWFudCB3aXRoCnRoZSBJU08vSUVDIE1QRUcgYXVkaW8gc3RhbmRhcmRzLiBQbGVhc2Ugbm90ZSB0aGF0IG1vc3QgbWFudWZhY3R1cmVycyBvZiBBbmRyb2lkIGRldmljZXMgYWxyZWFkeSBsaWNlbnNlCnRoZXNlIHBhdGVudCBjbGFpbXMgdGhyb3VnaCBWaWEgTGljZW5zaW5nIG9yIGRpcmVjdGx5IGZyb20gdGhlIHBhdGVudCBvd25lcnMsIGFuZCB0aGVyZWZvcmUgRkRLIEFBQyBDb2RlYwpzb2Z0d2FyZSBtYXkgYWxyZWFkeSBiZSBjb3ZlcmVkIHVuZGVyIHRob3NlIHBhdGVudCBsaWNlbnNlcyB3aGVuIGl0IGlzIHVzZWQgZm9yIHRob3NlIGxpY2Vuc2VkIHB1cnBvc2VzIG9ubHkuCgpDb21tZXJjaWFsbHktbGljZW5zZWQgQUFDIHNvZnR3YXJlIGxpYnJhcmllcywgaW5jbHVkaW5nIGZsb2F0aW5nLXBvaW50IHZlcnNpb25zIHdpdGggZW5oYW5jZWQgc291bmQgcXVhbGl0eSwKYXJlIGFsc28gYXZhaWxhYmxlIGZyb20gRnJhdW5ob2Zlci4gVXNlcnMgYXJlIGVuY291cmFnZWQgdG8gY2hlY2sgdGhlIEZyYXVuaG9mZXIgd2Vic2l0ZSBmb3IgYWRkaXRpb25hbAphcHBsaWNhdGlvbnMgaW5mb3JtYXRpb24gYW5kIGRvY3VtZW50YXRpb24uCgoyLiAgICBDT1BZUklHSFQgTElDRU5TRQoKUmVkaXN0cmlidXRpb24gYW5kIHVzZSBpbiBzb3VyY2UgYW5kIGJpbmFyeSBmb3Jtcywgd2l0aCBvciB3aXRob3V0IG1vZGlmaWNhdGlvbiwgYXJlIHBlcm1pdHRlZCB3aXRob3V0CnBheW1lbnQgb2YgY29weXJpZ2h0IGxpY2Vuc2UgZmVlcyBwcm92aWRlZCB0aGF0IHlvdSBzYXRpc2Z5IHRoZSBmb2xsb3dpbmcgY29uZGl0aW9uczoKCllvdSBtdXN0IHJldGFpbiB0aGUgY29tcGxldGUgdGV4dCBvZiB0aGlzIHNvZnR3YXJlIGxpY2Vuc2UgaW4gcmVkaXN0cmlidXRpb25zIG9mIHRoZSBGREsgQUFDIENvZGVjIG9yCnlvdXIgbW9kaWZpY2F0aW9ucyB0aGVyZXRvIGluIHNvdXJjZSBjb2RlIGZvcm0uCgpZb3UgbXVzdCByZXRhaW4gdGhlIGNvbXBsZXRlIHRleHQgb2YgdGhpcyBzb2Z0d2FyZSBsaWNlbnNlIGluIHRoZSBkb2N1bWVudGF0aW9uIGFuZC9vciBvdGhlciBtYXRlcmlhbHMKcHJvdmlkZWQgd2l0aCByZWRpc3RyaWJ1dGlvbnMgb2YgdGhlIEZESyBBQUMgQ29kZWMgb3IgeW91ciBtb2RpZmljYXRpb25zIHRoZXJldG8gaW4gYmluYXJ5IGZvcm0uCllvdSBtdXN0IG1ha2UgYXZhaWxhYmxlIGZyZWUgb2YgY2hhcmdlIGNvcGllcyBvZiB0aGUgY29tcGxldGUgc291cmNlIGNvZGUgb2YgdGhlIEZESyBBQUMgQ29kZWMgYW5kIHlvdXIKbW9kaWZpY2F0aW9ucyB0aGVyZXRvIHRvIHJlY2lwaWVudHMgb2YgY29waWVzIGluIGJpbmFyeSBmb3JtLgoKVGhlIG5hbWUgb2YgRnJhdW5ob2ZlciBtYXkgbm90IGJlIHVzZWQgdG8gZW5kb3JzZSBvciBwcm9tb3RlIHByb2R1Y3RzIGRlcml2ZWQgZnJvbSB0aGlzIGxpYnJhcnkgd2l0aG91dApwcmlvciB3cml0dGVuIHBlcm1pc3Npb24uCgpZb3UgbWF5IG5vdCBjaGFyZ2UgY29weXJpZ2h0IGxpY2Vuc2UgZmVlcyBmb3IgYW55b25lIHRvIHVzZSwgY29weSBvciBkaXN0cmlidXRlIHRoZSBGREsgQUFDIENvZGVjCnNvZnR3YXJlIG9yIHlvdXIgbW9kaWZpY2F0aW9ucyB0aGVyZXRvLgoKWW91ciBtb2RpZmllZCB2ZXJzaW9ucyBvZiB0aGUgRkRLIEFBQyBDb2RlYyBtdXN0IGNhcnJ5IHByb21pbmVudCBub3RpY2VzIHN0YXRpbmcgdGhhdCB5b3UgY2hhbmdlZCB0aGUgc29mdHdhcmUKYW5kIHRoZSBkYXRlIG9mIGFueSBjaGFuZ2UuIEZvciBtb2RpZmllZCB2ZXJzaW9ucyBvZiB0aGUgRkRLIEFBQyBDb2RlYywgdGhlIHRlcm0KIkZyYXVuaG9mZXIgRkRLIEFBQyBDb2RlYyBMaWJyYXJ5IGZvciBBbmRyb2lkIiBtdXN0IGJlIHJlcGxhY2VkIGJ5IHRoZSB0ZXJtCiJUaGlyZC1QYXJ0eSBNb2RpZmllZCBWZXJzaW9uIG9mIHRoZSBGcmF1bmhvZmVyIEZESyBBQUMgQ29kZWMgTGlicmFyeSBmb3IgQW5kcm9pZC4iCgozLiAgICBOTyBQQVRFTlQgTElDRU5TRQoKTk8gRVhQUkVTUyBPUiBJTVBMSUVEIExJQ0VOU0VTIFRPIEFOWSBQQVRFTlQgQ0xBSU1TLCBpbmNsdWRpbmcgd2l0aG91dCBsaW1pdGF0aW9uIHRoZSBwYXRlbnRzIG9mIEZyYXVuaG9mZXIsCkFSRSBHUkFOVEVEIEJZIFRISVMgU09GVFdBUkUgTElDRU5TRS4gRnJhdW5ob2ZlciBwcm92aWRlcyBubyB3YXJyYW50eSBvZiBwYXRlbnQgbm9uLWluZnJpbmdlbWVudCB3aXRoCnJlc3BlY3QgdG8gdGhpcyBzb2Z0d2FyZS4KCllvdSBtYXkgdXNlIHRoaXMgRkRLIEFBQyBDb2RlYyBzb2Z0d2FyZSBvciBtb2RpZmljYXRpb25zIHRoZXJldG8gb25seSBmb3IgcHVycG9zZXMgdGhhdCBhcmUgYXV0aG9yaXplZApieSBhcHByb3ByaWF0ZSBwYXRlbnQgbGljZW5zZXMuCgo0LiAgICBESVNDTEFJTUVSCgpUaGlzIEZESyBBQUMgQ29kZWMgc29mdHdhcmUgaXMgcHJvdmlkZWQgYnkgRnJhdW5ob2ZlciBvbiBiZWhhbGYgb2YgdGhlIGNvcHlyaWdodCBob2xkZXJzIGFuZCBjb250cmlidXRvcnMKIkFTIElTIiBhbmQgV0lUSE9VVCBBTlkgRVhQUkVTUyBPUiBJTVBMSUVEIFdBUlJBTlRJRVMsIGluY2x1ZGluZyBidXQgbm90IGxpbWl0ZWQgdG8gdGhlIGltcGxpZWQgd2FycmFudGllcwpvZiBtZXJjaGFudGFiaWxpdHkgYW5kIGZpdG5lc3MgZm9yIGEgcGFydGljdWxhciBwdXJwb3NlLiBJTiBOTyBFVkVOVCBTSEFMTCBUSEUgQ09QWVJJR0hUIEhPTERFUiBPUgpDT05UUklCVVRPUlMgQkUgTElBQkxFIGZvciBhbnkgZGlyZWN0LCBpbmRpcmVjdCwgaW5jaWRlbnRhbCwgc3BlY2lhbCwgZXhlbXBsYXJ5LCBvciBjb25zZXF1ZW50aWFsIGRhbWFnZXMsCmluY2x1ZGluZyBidXQgbm90IGxpbWl0ZWQgdG8gcHJvY3VyZW1lbnQgb2Ygc3Vic3RpdHV0ZSBnb29kcyBvciBzZXJ2aWNlczsgbG9zcyBvZiB1c2UsIGRhdGEsIG9yIHByb2ZpdHMsCm9yIGJ1c2luZXNzIGludGVycnVwdGlvbiwgaG93ZXZlciBjYXVzZWQgYW5kIG9uIGFueSB0aGVvcnkgb2YgbGlhYmlsaXR5LCB3aGV0aGVyIGluIGNvbnRyYWN0LCBzdHJpY3QKbGlhYmlsaXR5LCBvciB0b3J0IChpbmNsdWRpbmcgbmVnbGlnZW5jZSksIGFyaXNpbmcgaW4gYW55IHdheSBvdXQgb2YgdGhlIHVzZSBvZiB0aGlzIHNvZnR3YXJlLCBldmVuIGlmCmFkdmlzZWQgb2YgdGhlIHBvc3NpYmlsaXR5IG9mIHN1Y2ggZGFtYWdlLgoKNS4gICAgQ09OVEFDVCBJTkZPUk1BVElPTgoKRnJhdW5ob2ZlciBJbnN0aXR1dGUgZm9yIEludGVncmF0ZWQgQ2lyY3VpdHMgSUlTCkF0dGVudGlvbjogQXVkaW8gYW5kIE11bHRpbWVkaWEgRGVwYXJ0bWVudHMgLSBGREsgQUFDIExMCkFtIFdvbGZzbWFudGVsIDMzCjkxMDU4IEVybGFuZ2VuLCBHZXJtYW55Cgp3d3cuaWlzLmZyYXVuaG9mZXIuZGUvYW1tCmFtbS1pbmZvQGlpcy5mcmF1bmhvZmVyLmRlCi0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tICovCgovKioqKioqKioqKioqKioqKioqKioqKioqKioqICBGcmF1bmhvZmVyIElJUyBGREsgVG9vbHMgICoqKioqKioqKioqKioqKioqKioqKioqCgogICBBdXRob3Iocyk6IEFuZHJlYXMgRWhyZXQsIFRvYmlhcyBDaGFsdXBrYQogICBEZXNjcmlwdGlvbjogU0JSIGVuY29kZXIgdG9wIGxldmVsIHByb2Nlc3NpbmcuCgoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCgojaW5jbHVkZSAic2JyX2VuY29kZXIuaCIKCiNpbmNsdWRlICJzYnJfcmFtLmgiCiNpbmNsdWRlICJzYnJfcm9tLmgiCiNpbmNsdWRlICJzYnJlbmNfZnJlcV9zY2EuaCIKI2luY2x1ZGUgImVudl9iaXQuaCIKI2luY2x1ZGUgImNtb25kYXRhLmgiCiNpbmNsdWRlICJzYnJfbWlzYy5oIgojaW5jbHVkZSAic2JyLmgiCiNpbmNsdWRlICJxbWYuaCIKCiNpbmNsdWRlICJwc19tYWluLmgiCgojZGVmaW5lIFNCUkVOQ09ERVJfTElCX1ZMMCAzCiNkZWZpbmUgU0JSRU5DT0RFUl9MSUJfVkwxIDMKI2RlZmluZSBTQlJFTkNPREVSX0xJQl9WTDIgNAoKCgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwovKgogKiBTQlIgRGVsYXkgYmFsYW5jaW5nIGRlZmluaXRpb25zLgogKi8KCi8qCiAgICAgIGlucHV0IGJ1ZmZlciAoMWNoKQoKICAgICAgfC0tLS0tLS0tLS0tLSAxNTM3ICAgLS0tLS0tLS0tLS0tLXwtLS0tLXwtLS0tLS0tLS0tIDIwNDggLS0tLS0tLS0tLS0tLXwKICAgICAgICAgICAoY29yZTJzYnIgZGVsYXkgICAgICkgICAgICAgICAgZHMgICAgIChyZWFkLCBjb3JlIGFuZCBkcyBhcmVhKQoqLwoKI2RlZmluZSBTRkIoZHduc21wKSAgICAgICAgKDMyIDw8IChkd25zbXAtMSkpICAgICAvKiBTQlIgRnJlcXVlbmN5IGJhbmRzOiA2NCBmb3IgZHVhbC1yYXRlLCAzMiBmb3Igc2luZ2xlLXJhdGUgKi8KI2RlZmluZSBTVFMoZmwpICAgICAgICAgICAgKCgoZmwpPT0xMDI0KT8zMjozMCkgICAvKiBTQlIgVGltZSBTbG90czogMzIgZm9yIGNvcmUgZnJhbWUgbGVuZ3RoIDEwMjQsIDMwIGZvciBjb3JlIGZyYW1lIGxlbmd0aCA5NjAgKi8KCiNkZWZpbmUgREVMQVlfUU1GX0FOQShkd25zbXApICgoMzIwPDwoKGR3bnNtcCktMSkpIC0gKDMyPDwoKGR3bnNtcCktMSkpKSAvKiBGdWxsIGJhbmR3aWR0aCAqLwojZGVmaW5lIERFTEFZX0hZQl9BTkEgICAgICAgICAoMTAqNjQpICAgICAgIC8qICsgMC41ICovICAgICAgICAgICAgICAvKiAgKi8KI2RlZmluZSBERUxBWV9IWUJfU1lOICAgICAgICAgKDYqNjQgLSAzMikgICAgICAgICAgICAgICAgICAgICAgICAgICAgLyogICovCiNkZWZpbmUgREVMQVlfUU1GX1BPU1RQUk9DKGR3bnNtcCkgKDMyKihkd25zbXApKSAgICAgICAgICAgICAgICAgICAgIC8qIFFNRiBwb3N0cHJvY2Vzc2luZyBkZWxheSAqLwojZGVmaW5lIERFTEFZX0RFQ19RTUYoZHduc21wKSAoNiAqIFNGQihkd25zbXApICkgICAgICAgICAgICAgICAgICAgICAvKiBEZWNvZGVyIFFNRiBvdmVybGFwICovCiNkZWZpbmUgREVMQVlfUU1GX1NZTiAgICAgICAgICgyKSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8qIE5PX1BPTFkvMj0yLjUsIHJvdW5kZWQgZG93biB0byAyICovCiNkZWZpbmUgREVMQVlfUU1GX0RTICAgICAgICAgICgzMikgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8qIFFNRiBzeW50aGVzaXMgZm9yIGRvd25zYW1wbGVkIHRpbWUgc2lnbmFsICovCgovKiBEZWxheSBpbiBRTUYgcGF0aHMgKi8KI2RlZmluZSBERUxBWV9TQlIoZmwsZHduc21wKSAgICAgKERFTEFZX1FNRl9BTkEoZHduc21wKSArIChTRkIoZHduc21wKSpTVFMoZmwpIC0gMSkgKyBERUxBWV9RTUZfU1lOKQojZGVmaW5lIERFTEFZX1BTKGZsLGR3bnNtcCkgICAgICAoREVMQVlfUU1GX0FOQShkd25zbXApICsgREVMQVlfSFlCX0FOQSArIERFTEFZX0RFQ19RTUYoZHduc21wKSArIChTRkIoZHduc21wKSpTVFMoZmwpLTEpICsgREVMQVlfSFlCX1NZTiArIERFTEFZX1FNRl9TWU4pCiNkZWZpbmUgREVMQVlfRUxEU0JSKGZsLGR3bnNtcCkgICggKCAoKGZsKS8yKSooZHduc21wKSApIC0gMSArIERFTEFZX1FNRl9QT1NUUFJPQyhkd25zbXApICkKCi8qIERlbGF5IGRpZmZlcmVuY2VzIGZvciBTQlIgYW5kIFNCUitQUyAqLwojZGVmaW5lIE1BWF9EU19GSUxURVJfREVMQVkgKDUpICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8qIHRoZSBhZGRpdGlvbmFsIG1heCBkb3duc2FtcGxlciBmaWx0ZXIgZGVsYXkgKHNvdXJjZSBmcykgKi8KI2RlZmluZSBERUxBWV9BQUMyU0JSKGZsLGR3bnNtcCkgKChERUxBWV9RTUZfQU5BKGR3bnNtcCkgKyBERUxBWV9ERUNfUU1GKGR3bnNtcCkgKyBERUxBWV9RTUZfU1lOKSAtIERFTEFZX1NCUigoZmwpLChkd25zbXApKSkKI2RlZmluZSBERUxBWV9FTEQyU0JSKGZsLGR3bnNtcCkgKChERUxBWV9RTUZfUE9TVFBST0MoZHduc21wKSkgLSBERUxBWV9FTERTQlIoZmwsZHduc21wKSkKI2RlZmluZSBERUxBWV9BQUMyUFMoZmwsZHduc21wKSAoKERFTEFZX1FNRl9BTkEoZHduc21wKSArIERFTEFZX1FNRl9EUyArIC8qKERFTEFZX0FBQyhmbCkqMikgKyAqLyBERUxBWV9RTUZfQU5BKGR3bnNtcCkgKyBERUxBWV9ERUNfUU1GKGR3bnNtcCkgKyBERUxBWV9IWUJfU1lOICsgREVMQVlfUU1GX1NZTikgLSBERUxBWV9QUyhmbCxkd25zbXApKSAvKiAyMDQ4IC0gNDYzKjIgKi8KCi8qIEFzc3VtcHRpb246IFRoZSBzYW1wbGUgZGVsYXkgcmVzdWx0aW5nIG9mIG9mIERFTEFZX0FBQzJQUyBpcyBhbHdheXMgc21hbGxlciB0aGFuIHRoZSBzYW1wbGUgZGVsYXkgaW1wbGllZCBieSBERUxBWV9BQUMyU0JSICovCiNkZWZpbmUgTUFYX1NBTVBMRV9ERUxBWSAgICAgICAoREVMQVlfQUFDMlNCUigxMDI0LDIpICsgTUFYX0RTX0ZJTFRFUl9ERUxBWSkgLyogbWF4aW11bSBkZWxheTogZnJhbWUgbGVuZ3RoIG9mIDEwMjQgYW5kIGR1YWwtcmF0ZSBzYnIgKi8KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCgoKCiNkZWZpbmUgSU5WQUxJRF9UQUJMRV9JRFggLTEKCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCi8qIQoKICBcYnJpZWYgIFNlbGVjdHMgdGhlIFNCUiB0dW5pbmcgc2V0dGluZ3MgdG8gdXNlIGRlcGVuZGVudCBvbiBudW1iZXIgb2YKICAgICAgICAgIGNoYW5uZWxzLCBiaXRyYXRlLCBzYW1wbGUgcmF0ZSBhbmQgY29yZSBjb2RlcgoKICBccmV0dXJuIEluZGV4IHRvIHRoZSBhcHByb3ByaWF0ZSB0YWJsZQoKKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8KI2RlZmluZSBESVNUQU5DRV9DRUlMX1ZBTFVFIDUwMDAwMDAKc3RhdGljIElOVApnZXRTYnJUdW5pbmdUYWJsZUluZGV4KFVJTlQgYml0cmF0ZSwgICAgLyohIHRoZSB0b3RhbCBiaXRyYXRlIGluIGJpdHMvc2VjICovCiAgICAgICAgICAgICAgICAgICAgICAgVUlOVCBudW1DaGFubmVscywvKiEgdGhlIG51bWJlciBvZiBjaGFubmVscyBmb3IgdGhlIGNvcmUgY29kZXIgKi8KICAgICAgICAgICAgICAgICAgICAgICBVSU5UIHNhbXBsZVJhdGUsICAvKiEgdGhlIHNhbXBsaW5nIHJhdGUgb2YgdGhlIGNvcmUgY29kZXIgKi8KICAgICAgICAgICAgICAgICAgICAgICBBVURJT19PQkpFQ1RfVFlQRSBjb3JlLAogICAgICAgICAgICAgICAgICAgICAgIFVJTlQgKnBCaXRSYXRlQ2xvc2VzdAogICAgICAgICAgICAgICAgICAgICAgICkKewogIGludCBpLCBiaXRSYXRlQ2xvc2VzdExvd2VySW5kZXg9LTEsIGJpdFJhdGVDbG9zZXN0VXBwZXJJbmRleD0tMSwgZm91bmQgPSAwOwogIFVJTlQgYml0UmF0ZUNsb3Nlc3RVcHBlciA9IDAsIGJpdFJhdGVDbG9zZXN0TG93ZXI9RElTVEFOQ0VfQ0VJTF9WQUxVRTsKICBpbnQgaXNmb3JUaGlzQ29kZWM9MDsKCiAgI2RlZmluZSBpc0ZvclRoaXNDb3JlKGkpIFwKICAgICggKCBzYnJUdW5pbmdUYWJsZVtpXS5jb3JlQ29kZXIgPT0gQ09ERUNfQUFDTEQgJiYgY29yZSA9PSBBT1RfRVJfQUFDX0VMRCApIHx8IFwKICAgICAgKCBzYnJUdW5pbmdUYWJsZVtpXS5jb3JlQ29kZXIgPT0gQ09ERUNfQUFDICAgJiYgY29yZSAhPSBBT1RfRVJfQUFDX0VMRCApICkKCiAgZm9yIChpPTA7IGkgPCBzYnJUdW5pbmdUYWJsZVNpemUgOyBpKyspIHsKICAgIGlmICggaXNGb3JUaGlzQ29yZShpKSApIC8qIHR1bmluZyB0YWJsZSBpcyBmb3IgdGhpcyBjb3JlIGNvZGVjICovCiAgICB7CiAgICAgIGlmICggbnVtQ2hhbm5lbHMgPT0gc2JyVHVuaW5nVGFibGUgW2ldLm51bUNoYW5uZWxzCiAgICAgICAgJiYgc2FtcGxlUmF0ZSA9PSBzYnJUdW5pbmdUYWJsZSBbaV0uc2FtcGxlUmF0ZSApCiAgICAgIHsKICAgICAgICBmb3VuZCA9IDE7CiAgICAgICAgaWYgKChiaXRyYXRlID49IHNiclR1bmluZ1RhYmxlIFtpXS5iaXRyYXRlRnJvbSkgJiYKICAgICAgICAgICAgKGJpdHJhdGUgPCBzYnJUdW5pbmdUYWJsZSBbaV0uYml0cmF0ZVRvKSkgewogICAgICAgICAgICAgIGJpdFJhdGVDbG9zZXN0TG93ZXIgPSBiaXRyYXRlOwogICAgICAgICAgICAgIGJpdFJhdGVDbG9zZXN0VXBwZXIgPSBiaXRyYXRlOwogICAgICAgICAgICAgIC8vRkRLcHJpbnRmKCJlbnRyeSAlZFxuIiwgaSk7CiAgICAgICAgICByZXR1cm4gaSA7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGlmICggc2JyVHVuaW5nVGFibGUgW2ldLmJpdHJhdGVGcm9tID4gYml0cmF0ZSApIHsKICAgICAgICAgICAgaWYgKHNiclR1bmluZ1RhYmxlIFtpXS5iaXRyYXRlRnJvbSA8IGJpdFJhdGVDbG9zZXN0TG93ZXIpIHsKICAgICAgICAgICAgICBiaXRSYXRlQ2xvc2VzdExvd2VyID0gc2JyVHVuaW5nVGFibGUgW2ldLmJpdHJhdGVGcm9tOwogICAgICAgICAgICAgIGJpdFJhdGVDbG9zZXN0TG93ZXJJbmRleCA9IGk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIGlmICggc2JyVHVuaW5nVGFibGUgW2ldLmJpdHJhdGVUbyA8PSBiaXRyYXRlICkgewogICAgICAgICAgICBpZiAoc2JyVHVuaW5nVGFibGUgW2ldLmJpdHJhdGVUbyA+IGJpdFJhdGVDbG9zZXN0VXBwZXIpIHsKICAgICAgICAgICAgICBiaXRSYXRlQ2xvc2VzdFVwcGVyID0gc2JyVHVuaW5nVGFibGUgW2ldLmJpdHJhdGVUby0xOwogICAgICAgICAgICAgIGJpdFJhdGVDbG9zZXN0VXBwZXJJbmRleCA9IGk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KICAgIH0KICB9CgogIGlmIChwQml0UmF0ZUNsb3Nlc3QgIT0gTlVMTCkKICB7CiAgICAvKiBJZiB0aGVyZSB3YXMgYXQgbGVhc3Qgb25lIG1hdGNoaW5nIHR1bmluZyBlbnRyeSBmb3VuZCB0aGVuIHBpY2sgdGhlIGxlYXN0IGRpc3RhbmNlIGJpdCByYXRlICovCiAgICBpZiAoZm91bmQpCiAgICB7CiAgICAgIGludCBkaXN0YW5jZVVwcGVyPURJU1RBTkNFX0NFSUxfVkFMVUUsIGRpc3RhbmNlTG93ZXI9RElTVEFOQ0VfQ0VJTF9WQUxVRTsKICAgICAgaWYgKGJpdFJhdGVDbG9zZXN0TG93ZXJJbmRleCA+PSAwKSB7CiAgICAgICAgZGlzdGFuY2VMb3dlciA9IHNiclR1bmluZ1RhYmxlIFtiaXRSYXRlQ2xvc2VzdExvd2VySW5kZXhdLmJpdHJhdGVGcm9tIC0gYml0cmF0ZTsKICAgICAgfQogICAgICBpZiAoYml0UmF0ZUNsb3Nlc3RVcHBlckluZGV4ID49IDApIHsKICAgICAgICBkaXN0YW5jZVVwcGVyID0gYml0cmF0ZSAtIHNiclR1bmluZ1RhYmxlIFtiaXRSYXRlQ2xvc2VzdFVwcGVySW5kZXhdLmJpdHJhdGVUbzsKICAgICAgfQogICAgICBpZiAoIGRpc3RhbmNlVXBwZXIgPCBkaXN0YW5jZUxvd2VyICkKICAgICAgewogICAgICAgICpwQml0UmF0ZUNsb3Nlc3QgPSBiaXRSYXRlQ2xvc2VzdFVwcGVyOwogICAgICB9IGVsc2UgewogICAgICAgICpwQml0UmF0ZUNsb3Nlc3QgPSBiaXRSYXRlQ2xvc2VzdExvd2VyOwogICAgICB9CiAgICB9IGVsc2UgewogICAgICAqcEJpdFJhdGVDbG9zZXN0ID0gMDsKICAgIH0KICB9CgogIHJldHVybiBJTlZBTElEX1RBQkxFX0lEWDsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8KLyohCgogIFxicmllZiAgU2VsZWN0cyB0aGUgUFMgdHVuaW5nIHNldHRpbmdzIHRvIHVzZSBkZXBlbmRlbnQgb24gYml0cmF0ZQogIGFuZCBjb3JlIGNvZGVyCgogIFxyZXR1cm4gSW5kZXggdG8gdGhlIGFwcHJvcHJpYXRlIHRhYmxlCgoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSU5UCmdldFBzVHVuaW5nVGFibGVJbmRleChVSU5UIGJpdHJhdGUsIFVJTlQgKnBCaXRSYXRlQ2xvc2VzdCl7CgogIElOVCBpLCBwYXJhbVNldHMgPSBzaXplb2YgKHBzVHVuaW5nVGFibGUpIC8gc2l6ZW9mIChwc1R1bmluZ1RhYmxlIFswXSk7CiAgaW50IGJpdFJhdGVDbG9zZXN0TG93ZXJJbmRleD0tMSwgYml0UmF0ZUNsb3Nlc3RVcHBlckluZGV4PS0xOwogIFVJTlQgYml0UmF0ZUNsb3Nlc3RVcHBlciA9IDAsIGJpdFJhdGVDbG9zZXN0TG93ZXI9RElTVEFOQ0VfQ0VJTF9WQUxVRTsKCiAgZm9yIChpID0gMCA7IGkgPCBwYXJhbVNldHMgOyBpKyspICB7CiAgICBpZiAoKGJpdHJhdGUgPj0gcHNUdW5pbmdUYWJsZSBbaV0uYml0cmF0ZUZyb20pICYmCiAgICAgICAgKGJpdHJhdGUgPCBwc1R1bmluZ1RhYmxlIFtpXS5iaXRyYXRlVG8pKSB7CiAgICAgIHJldHVybiBpIDsKICAgIH0gZWxzZSB7CiAgICAgIGlmICggcHNUdW5pbmdUYWJsZSBbaV0uYml0cmF0ZUZyb20gPiBiaXRyYXRlICkgewogICAgICAgIGlmIChwc1R1bmluZ1RhYmxlIFtpXS5iaXRyYXRlRnJvbSA8IGJpdFJhdGVDbG9zZXN0TG93ZXIpIHsKICAgICAgICAgIGJpdFJhdGVDbG9zZXN0TG93ZXIgPSBwc1R1bmluZ1RhYmxlIFtpXS5iaXRyYXRlRnJvbTsKICAgICAgICAgIGJpdFJhdGVDbG9zZXN0TG93ZXJJbmRleCA9IGk7CiAgICAgICAgfQogICAgICB9CiAgICAgIGlmICggcHNUdW5pbmdUYWJsZSBbaV0uYml0cmF0ZVRvIDw9IGJpdHJhdGUgKSB7CiAgICAgICAgaWYgKHBzVHVuaW5nVGFibGUgW2ldLmJpdHJhdGVUbyA+IGJpdFJhdGVDbG9zZXN0VXBwZXIpIHsKICAgICAgICAgIGJpdFJhdGVDbG9zZXN0VXBwZXIgPSBwc1R1bmluZ1RhYmxlIFtpXS5iaXRyYXRlVG8tMTsKICAgICAgICAgIGJpdFJhdGVDbG9zZXN0VXBwZXJJbmRleCA9IGk7CiAgICAgICAgfQogICAgICB9CiAgICB9CiAgfQoKICBpZiAocEJpdFJhdGVDbG9zZXN0ICE9IE5VTEwpCiAgewogICAgaW50IGRpc3RhbmNlVXBwZXI9RElTVEFOQ0VfQ0VJTF9WQUxVRSwgZGlzdGFuY2VMb3dlcj1ESVNUQU5DRV9DRUlMX1ZBTFVFOwogICAgaWYgKGJpdFJhdGVDbG9zZXN0TG93ZXJJbmRleCA+PSAwKSB7CiAgICAgIGRpc3RhbmNlTG93ZXIgPSBzYnJUdW5pbmdUYWJsZSBbYml0UmF0ZUNsb3Nlc3RMb3dlckluZGV4XS5iaXRyYXRlRnJvbSAtIGJpdHJhdGU7CiAgICB9CiAgICBpZiAoYml0UmF0ZUNsb3Nlc3RVcHBlckluZGV4ID49IDApIHsKICAgICAgZGlzdGFuY2VVcHBlciA9IGJpdHJhdGUgLSBzYnJUdW5pbmdUYWJsZSBbYml0UmF0ZUNsb3Nlc3RVcHBlckluZGV4XS5iaXRyYXRlVG87CiAgICB9CiAgICBpZiAoIGRpc3RhbmNlVXBwZXIgPCBkaXN0YW5jZUxvd2VyICkKICAgIHsKICAgICAgKnBCaXRSYXRlQ2xvc2VzdCA9IGJpdFJhdGVDbG9zZXN0VXBwZXI7CiAgICB9IGVsc2UgewogICAgICAqcEJpdFJhdGVDbG9zZXN0ID0gYml0UmF0ZUNsb3Nlc3RMb3dlcjsKICAgIH0KICB9CgogIHJldHVybiBJTlZBTElEX1RBQkxFX0lEWDsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8KLyohCgogIFxicmllZiAgSW4gY2FzZSBvZiBkb3duc2FtcGxlZCBTQlIgd2UgbWF5IG5lZWQgdG8gbG93ZXIgdGhlIHN0b3AgZnJlcQogICAgICAgICAgb2YgYSB0dW5pbmcgc2V0dGluZyB0byBmaXQgaW50byB0aGUgbG93ZXIgaGFsZiBvZiB0aGUKICAgICAgICAgIHNwZWN0cnVtICggd2hpY2ggaXMgc2FtcGxlUmF0ZS80ICkKCiAgXHJldHVybiB0aGUgYWRhcHRlZCBzdG9wIGZyZXF1ZW5jeSBpbmRleCAoLTEgLT4gZXJyb3IpCgogIFxpbmdyb3VwIFNickVuY0NmZwoKKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIElOVApGREtzYnJFbmNfR2V0RG93bnNhbXBsZWRTdG9wRnJlcSAoCiAgICAgICAgY29uc3QgSU5UIHNhbXBsZVJhdGVDb3JlLAogICAgICAgIGNvbnN0IElOVCBzdGFydEZyZXEsCiAgICAgICAgICAgICAgSU5UIHN0b3BGcmVxLAogICAgICAgIGNvbnN0IElOVCBkb3duU2FtcGxlRmFjdG9yCiAgICAgICAgKQp7CiAgSU5UIG1heFN0b3BGcmVxUmF3ID0gc2FtcGxlUmF0ZUNvcmUgLyAyOwogIElOVCBzdGFydEJhbmQsIHN0b3BCYW5kOwogIEhBTkRMRV9FUlJPUl9JTkZPIGVycjsKCiAgd2hpbGUgKHN0b3BGcmVxID4gMCAmJiBGREtzYnJFbmNfZ2V0U2JyU3RvcEZyZXFSQVcoc3RvcEZyZXEsIHNhbXBsZVJhdGVDb3JlKSA+IG1heFN0b3BGcmVxUmF3KSB7CiAgICBzdG9wRnJlcS0tOwogIH0KCiAgaWYgKEZES3NickVuY19nZXRTYnJTdG9wRnJlcVJBVyggc3RvcEZyZXEsIHNhbXBsZVJhdGVDb3JlKSA+IG1heFN0b3BGcmVxUmF3KQogICAgcmV0dXJuIC0xOwoKICBlcnIgPSBGREtzYnJFbmNfRmluZFN0YXJ0QW5kU3RvcEJhbmQgKAogICAgICAgICAgICAgICAgc2FtcGxlUmF0ZUNvcmU8PChkb3duU2FtcGxlRmFjdG9yLTEpLAogICAgICAgICAgICAgICAgc2FtcGxlUmF0ZUNvcmUsCiAgICAgICAgICAgICAgICAzMjw8KGRvd25TYW1wbGVGYWN0b3ItMSksCiAgICAgICAgICAgICAgICBzdGFydEZyZXEsCiAgICAgICAgICAgICAgICBzdG9wRnJlcSwKICAgICAgICAgICAgICAgJnN0YXJ0QmFuZCwKICAgICAgICAgICAgICAgJnN0b3BCYW5kCiAgICAgICAgICAgICAgICApOwogIGlmIChlcnIpCiAgICByZXR1cm4gLTE7CgogIHJldHVybiBzdG9wRnJlcTsKfQoKCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCi8qIQoKICBcYnJpZWYgIHRlbGxzIHVzLCBpZiBmb3IgdGhlIGdpdmVuIGNvcmVDb2RlciwgYml0cmF0ZSwgbnVtYmVyIG9mIGNoYW5uZWxzCiAgICAgICAgICBhbmQgaW5wdXQgc2FtcGxpbmcgcmF0ZSBhbiBTQlIgc2V0dGluZyBpcyBhdmFpbGFibGUuIElmIHllcywgaXQKICAgICAgICAgIHRlbGxzIHVzIGFsc28gdGhlIGNvcmUgc2FtcGxpbmcgcmF0ZSB3ZSB3b3VsZCBuZWVkIHRvIHJ1biB3aXRoCgogIFxyZXR1cm4gYSBmbGFnIGluZGljYXRpbmcgc3VjY2VzczogeWVzICgxKSBvciBubyAoMCkKCioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBVSU5UCkZES3NickVuY19Jc1NiclNldHRpbmdBdmFpbCAoCiAgICAgICAgVUlOVCBiaXRyYXRlLCAgICAgICAgICAgLyohIHRoZSB0b3RhbCBiaXRyYXRlIGluIGJpdHMvc2VjICovCiAgICAgICAgVUlOVCB2YnJNb2RlLCAgICAgICAgICAgLyohIHRoZSB2YnIgcGFyYW10ZXIsIDAgbWVhbnMgY29uc3RhbnQgYml0cmF0ZSAqLwogICAgICAgIFVJTlQgbnVtT3V0cHV0Q2hhbm5lbHMsIC8qISB0aGUgbnVtYmVyIG9mIGNoYW5uZWxzIGZvciB0aGUgY29yZSBjb2RlciAqLwogICAgICAgIFVJTlQgc2FtcGxlUmF0ZUlucHV0LCAgIC8qISB0aGUgaW5wdXQgc2FtcGxlIHJhdGUgW2luIEh6XSAqLwogICAgICAgIFVJTlQgc2FtcGxlUmF0ZUNvcmUsICAgIC8qISB0aGUgY29yZSdzIHNhbXBsaW5nIHJhdGUgKi8KICAgICAgICBBVURJT19PQkpFQ1RfVFlQRSBjb3JlCiAgICAgICAgKQp7CiAgSU5UIGlkeCA9IElOVkFMSURfVEFCTEVfSURYOwoKICBpZiAoc2FtcGxlUmF0ZUlucHV0IDwgMTYwMDApCiAgICByZXR1cm4gMDsKCiAgaWYgKGJpdHJhdGU9PTApIHsKICAgIC8qIG1hcCB2YnIgcXVhbGl0eSB0byBiaXRyYXRlICovCiAgICBpZiAodmJyTW9kZSA8IDMwKQogICAgICBiaXRyYXRlID0gMjQwMDA7CiAgICBlbHNlIGlmICh2YnJNb2RlIDwgNDApCiAgICAgIGJpdHJhdGUgPSAyODAwMDsKICAgIGVsc2UgaWYgKHZick1vZGUgPCA2MCkKICAgICAgYml0cmF0ZSA9IDMyMDAwOwogICAgZWxzZSBpZiAodmJyTW9kZSA8IDc1KQogICAgICBiaXRyYXRlID0gNDAwMDA7CiAgICBlbHNlCiAgICAgIGJpdHJhdGUgPSA0ODAwMDsKICAgIGJpdHJhdGUgKj0gbnVtT3V0cHV0Q2hhbm5lbHM7CiAgfQoKICBpZHggPSBnZXRTYnJUdW5pbmdUYWJsZUluZGV4KGJpdHJhdGUsIG51bU91dHB1dENoYW5uZWxzLCBzYW1wbGVSYXRlQ29yZSwgY29yZSwgTlVMTCk7CgogIHJldHVybiAoaWR4ID09IElOVkFMSURfVEFCTEVfSURYID8gMCA6IDEpOwp9CgoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8KLyohCgogIFxicmllZiAgQWRqdXN0cyB0aGUgU0JSIHNldHRpbmdzIGFjY29yZGluZyB0byB0aGUgY2hvc2VuIGNvcmUgY29kZXIKICAgICAgICAgIHNldHRpbmdzIHdoaWNoIGFyZSBhY2Nlc3NpYmxlIHZpYSBjb25maWctPmNvZGVjU2V0dGluZ3MKCiAgXHJldHVybiBBIGZsYWcgaW5kaWNhdGluZyBzdWNjZXNzOiB5ZXMgKDEpIG9yIG5vICgwKQoKKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIFVJTlQKRkRLc2JyRW5jX0FkanVzdFNiclNldHRpbmdzIChjb25zdCBzYnJDb25maWd1cmF0aW9uUHRyIGNvbmZpZywgLyohIG91dHB1dCwgbW9kaWZpZWQgKi8KICAgICAgICAgICAgICAgICAgIFVJTlQgYml0UmF0ZSwgICAgICAgICAgICAgLyohIHRoZSB0b3RhbCBiaXRyYXRlIGluIGJpdHMvc2VjICovCiAgICAgICAgICAgICAgICAgICBVSU5UIG51bUNoYW5uZWxzLCAgICAgICAgIC8qISB0aGUgY29yZSBjb2RlciBudW1iZXIgb2YgY2hhbm5lbHMgKi8KICAgICAgICAgICAgICAgICAgIFVJTlQgc2FtcGxlUmF0ZUNvcmUsICAgICAgLyohIHRoZSBjb3JlIGNvZGVyIHNhbXBsaW5nIHJhdGUgaW4gSHogKi8KICAgICAgICAgICAgICAgICAgIFVJTlQgc2FtcGxlUmF0ZVNiciwgICAgICAgLyohIHRoZSBzYnIgY29kZXIgc2FtcGxpbmcgcmF0ZSBpbiBIeiAqLwogICAgICAgICAgICAgICAgICAgVUlOVCB0cmFuc0ZhYywgICAgICAgICAgICAvKiEgdGhlIHNob3J0IGJsb2NrIHRvIGxvbmcgYmxvY2sgcmF0aW8gKi8KICAgICAgICAgICAgICAgICAgIFVJTlQgc3RhbmRhcmRCaXRyYXRlLCAgICAgLyohIHRoZSBzdGFuZGFyZCBiaXRyYXRlIHBlciBjaGFubmVsIGluIGJpdHMvc2VjICovCiAgICAgICAgICAgICAgICAgICBVSU5UIHZick1vZGUsICAgICAgICAgICAgIC8qISB0aGUgdmJyIHBhcmFtdGVyLCAwIHBvb3IgcXVhbGl0eSAuLiAxMDAgaGlnaCBxdWFsaXR5Ki8KICAgICAgICAgICAgICAgICAgIFVJTlQgdXNlU3BlZWNoQ29uZmlnLCAgICAgLyohPCBhZGFwdCB0dW5pbmcgcGFyYW1ldGVycyBmb3Igc3BlZWNoID8gKi8KICAgICAgICAgICAgICAgICAgIFVJTlQgbGNzTW9kZSwgICAgICAgICAgICAgLyohIHRoZSBsb3cgY29tcGxleGl0eSBzdGVyZW8gbW9kZSAqLwogICAgICAgICAgICAgICAgICAgVUlOVCBiUGFyYW1ldHJpY1N0ZXJlbywgICAvKiE8IHVzZSBwYXJhbWV0cmljIHN0ZXJlbyAqLwogICAgICAgICAgICAgICAgICAgQVVESU9fT0JKRUNUX1RZUEUgY29yZSkgICAvKiBDb3JlIGF1ZGlvIGNvZGVjIG9iamVjdCB0eXBlICovCnsKICBJTlQgaWR4ID0gSU5WQUxJRF9UQUJMRV9JRFg7CiAgLyogc2V0IHRoZSBjb3JlIGNvZGVjIHNldHRpbmdzICovCiAgY29uZmlnLT5jb2RlY1NldHRpbmdzLmJpdFJhdGUgICAgICAgICA9IGJpdFJhdGU7CiAgY29uZmlnLT5jb2RlY1NldHRpbmdzLm5DaGFubmVscyAgICAgICA9IG51bUNoYW5uZWxzOwogIGNvbmZpZy0+Y29kZWNTZXR0aW5ncy5zYW1wbGVGcmVxICAgICAgPSBzYW1wbGVSYXRlQ29yZTsKICBjb25maWctPmNvZGVjU2V0dGluZ3MudHJhbnNGYWMgICAgICAgID0gdHJhbnNGYWM7CiAgY29uZmlnLT5jb2RlY1NldHRpbmdzLnN0YW5kYXJkQml0cmF0ZSA9IHN0YW5kYXJkQml0cmF0ZTsKCiAgaWYgKGJpdFJhdGU9PTApIHsKICAgIC8qIG1hcCB2YnIgcXVhbGl0eSB0byBiaXRyYXRlICovCiAgICBpZiAodmJyTW9kZSA8IDMwKQogICAgICBiaXRSYXRlID0gMjQwMDA7CiAgICBlbHNlIGlmICh2YnJNb2RlIDwgNDApCiAgICAgIGJpdFJhdGUgPSAyODAwMDsKICAgIGVsc2UgaWYgKHZick1vZGUgPCA2MCkKICAgICAgYml0UmF0ZSA9IDMyMDAwOwogICAgZWxzZSBpZiAodmJyTW9kZSA8IDc1KQogICAgICBiaXRSYXRlID0gNDAwMDA7CiAgICBlbHNlCiAgICAgIGJpdFJhdGUgPSA0ODAwMDsKICAgIGJpdFJhdGUgKj0gbnVtQ2hhbm5lbHM7CiAgICAvKiBmaXggdG8gZW5hYmxlIG1vbm8gdmJyTW9kZTw0MCBAIDQ0LjEgb2YgNDhrSHogKi8KICAgIGlmIChudW1DaGFubmVscz09MSkgewogICAgICBpZiAoc2FtcGxlUmF0ZVNicj09NDQxMDAgfHwgc2FtcGxlUmF0ZVNicj09NDgwMDApIHsKICAgICAgICBpZiAodmJyTW9kZTw0MCkgYml0UmF0ZSA9IDMyMDAwOwogICAgICB9CiAgICB9CiAgfQoKICBpZHggPSBnZXRTYnJUdW5pbmdUYWJsZUluZGV4KGJpdFJhdGUsbnVtQ2hhbm5lbHMsc2FtcGxlUmF0ZUNvcmUsIGNvcmUsIE5VTEwpOwoKICBpZiAoaWR4ICE9IElOVkFMSURfVEFCTEVfSURYKSB7CiAgICBjb25maWctPnN0YXJ0RnJlcSAgICAgICA9IHNiclR1bmluZ1RhYmxlW2lkeF0uc3RhcnRGcmVxIDsKICAgIGNvbmZpZy0+c3RvcEZyZXEgICAgICAgID0gc2JyVHVuaW5nVGFibGVbaWR4XS5zdG9wRnJlcSA7CiAgICBpZiAodXNlU3BlZWNoQ29uZmlnKSB7CiAgICAgIGNvbmZpZy0+c3RhcnRGcmVxICAgICA9IHNiclR1bmluZ1RhYmxlW2lkeF0uc3RhcnRGcmVxU3BlZWNoOwogICAgICBjb25maWctPnN0b3BGcmVxICAgICAgPSBzYnJUdW5pbmdUYWJsZVtpZHhdLnN0b3BGcmVxU3BlZWNoOwogICAgfQoKICAgIC8qIEFkYXB0IHN0b3AgZnJlcXVlbmN5IGluIGNhc2Ugb2YgZG93bnNhbXBsZWQgU0JSIC0gb25seSAzMiBiYW5kcyB0aGVuICovCiAgICBpZiAoMSA9PSBjb25maWctPmRvd25TYW1wbGVGYWN0b3IpIHsKICAgICAgSU5UIGRzU3RvcEZyZXEgPSBGREtzYnJFbmNfR2V0RG93bnNhbXBsZWRTdG9wRnJlcSgKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNhbXBsZVJhdGVDb3JlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY29uZmlnLT5zdGFydEZyZXEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBjb25maWctPnN0b3BGcmVxLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY29uZmlnLT5kb3duU2FtcGxlRmFjdG9yCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICApOwogICAgICBpZiAoZHNTdG9wRnJlcSA8IDApIHsKICAgICAgICByZXR1cm4gMDsKICAgICAgfQoKICAgICAgY29uZmlnLT5zdG9wRnJlcSA9IGRzU3RvcEZyZXE7CiAgICB9CgogICAgY29uZmlnLT5zYnJfbm9pc2VfYmFuZHMgPSBzYnJUdW5pbmdUYWJsZVtpZHhdLm51bU5vaXNlQmFuZHMgOwogICAgaWYgKGNvcmUgPT0gQU9UX0VSX0FBQ19FTEQpCiAgICAgIGNvbmZpZy0+aW5pdF9hbXBfcmVzX0ZGID0gU0JSX0FNUF9SRVNfMV81OwogICAgY29uZmlnLT5ub2lzZUZsb29yT2Zmc2V0PSBzYnJUdW5pbmdUYWJsZVtpZHhdLm5vaXNlRmxvb3JPZmZzZXQ7CgogICAgY29uZmlnLT5hbmFfbWF4X2xldmVsICAgPSBzYnJUdW5pbmdUYWJsZVtpZHhdLm5vaXNlTWF4TGV2ZWwgOwogICAgY29uZmlnLT5zdGVyZW9Nb2RlICAgICAgPSBzYnJUdW5pbmdUYWJsZVtpZHhdLnN0ZXJlb01vZGUgOwogICAgY29uZmlnLT5mcmVxU2NhbGUgICAgICAgPSBzYnJUdW5pbmdUYWJsZVtpZHhdLmZyZXFTY2FsZSA7CgogICAgLyogYWRqdXN0IHVzYWdlIG9mIHBhcmFtZXRyaWMgY29kaW5nIGRlcGVuZGVudCBvbiBiaXRyYXRlIGFuZCBzcGVlY2ggY29uZmlnIGZsYWcgKi8KICAgIGlmICh1c2VTcGVlY2hDb25maWcpCiAgICAgIGNvbmZpZy0+cGFyYW1ldHJpY0NvZGluZyAgPSAwOwoKICAgIGlmIChjb3JlID09IEFPVF9FUl9BQUNfRUxEKSB7CiAgICAgIGlmIChiaXRSYXRlIDwgMjgwMDApCiAgICAgICAgY29uZmlnLT5pbml0X2FtcF9yZXNfRkYgPSBTQlJfQU1QX1JFU18zXzA7CiAgICAgIGNvbmZpZy0+U2VuZEhlYWRlckRhdGFUaW1lID0gLTE7CiAgICB9CgogICAgaWYgKG51bUNoYW5uZWxzID09IDEpIHsKICAgICAgaWYgKGJpdFJhdGUgPCAxNjAwMCkgewogICAgICAgIGNvbmZpZy0+cGFyYW1ldHJpY0NvZGluZyAgPSAwOwogICAgICB9CiAgICB9CiAgICBlbHNlIHsKICAgICAgaWYgKGJpdFJhdGUgPCAyMDAwMCkgewogICAgICAgIGNvbmZpZy0+cGFyYW1ldHJpY0NvZGluZyAgPSAwOwogICAgICB9CiAgICB9CgogICAgY29uZmlnLT51c2VTcGVlY2hDb25maWcgPSB1c2VTcGVlY2hDb25maWc7CgogICAgLyogUFMgc2V0dGluZ3MgKi8KICAgIGNvbmZpZy0+YlBhcmFtZXRyaWNTdGVyZW8gPSBiUGFyYW1ldHJpY1N0ZXJlbzsKCiAgICByZXR1cm4gMSA7CiAgfQogIGVsc2UgewogICAgcmV0dXJuIDAgOwogIH0KfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCgogZnVuY3Rpb25uYW1lOiBGREtzYnJFbmNfSW5pdGlhbGl6ZVNickRlZmF1bHRzCiBkZXNjcmlwdGlvbjogIGluaXRpYWxpemVzIHRoZSBTQlIgY29uZmlmdXJhdGlvbgogcmV0dXJuczogICAgICBlcnJvciBzdGF0dXMKIGlucHV0OiAgICAgICAgLSBjb3JlIGNvZGVjIHR5cGUsCiAgICAgICAgICAgICAgIC0gZmFjdG9yIG9mIFNCUiB0byBjb3JlIGZyYW1lIGxlbmd0aCwKICAgICAgICAgICAgICAgLSBjb3JlIGZyYW1lIGxlbmd0aAogb3V0cHV0OiAgICAgICBpbml0aWFsaXplZCBTQlIgY29uZmlndXJhdGlvbgoKKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBVSU5UCkZES3NickVuY19Jbml0aWFsaXplU2JyRGVmYXVsdHMgKHNickNvbmZpZ3VyYXRpb25QdHIgY29uZmlnLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBJTlQgICAgICAgICAgICAgICAgIGRvd25TYW1wbGVGYWN0b3IsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFVJTlQgICAgICAgICAgICAgICAgY29kZWNHcmFudWxlTGVuCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICkKewogICAgaWYgKCAoZG93blNhbXBsZUZhY3RvciA8IDEgfHwgZG93blNhbXBsZUZhY3RvciA+IDIpIHx8CiAgICAgICAgIChjb2RlY0dyYW51bGVMZW4qZG93blNhbXBsZUZhY3RvciA+IFFNRl9DSEFOTkVMUypRTUZfTUFYX1RJTUVfU0xPVFMpICkKICAgICAgIHJldHVybigwKTsgLyogZXJyb3IgKi8KCiAgICBjb25maWctPlNlbmRIZWFkZXJEYXRhVGltZSAgICAgPSAxMDAwOwogICAgY29uZmlnLT51c2VXYXZlQ29kaW5nICAgICAgICAgID0gMDsKICAgIGNvbmZpZy0+Y3JjU2JyICAgICAgICAgICAgICAgICA9IDA7CiAgICBjb25maWctPmR5bkJ3U3VwcG9ydGVkICAgICAgICAgPSAxOwogICAgY29uZmlnLT50cmFuX3RociAgICAgICAgICAgICAgID0gMTMwMDA7CiAgICBjb25maWctPnBhcmFtZXRyaWNDb2RpbmcgICAgICAgPSAxOwoKICAgIGNvbmZpZy0+c2JyRnJhbWVTaXplICAgICAgICAgICA9IGNvZGVjR3JhbnVsZUxlbiAqIGRvd25TYW1wbGVGYWN0b3I7CiAgICBjb25maWctPmRvd25TYW1wbGVGYWN0b3IgICAgICAgPSBkb3duU2FtcGxlRmFjdG9yOwoKICAgIC8qIHNiciBkZWZhdWx0IHBhcmFtZXRlcnMgKi8KICAgIGNvbmZpZy0+c2JyX2RhdGFfZXh0cmEgICAgICAgICA9IDA7CiAgICBjb25maWctPmFtcF9yZXMgICAgICAgICAgICAgICAgPSBTQlJfQU1QX1JFU18zXzAgOwogICAgY29uZmlnLT50cmFuX2ZjICAgICAgICAgICAgICAgID0gMCA7CiAgICBjb25maWctPnRyYW5fZGV0X21vZGUgICAgICAgICAgPSAxIDsKICAgIGNvbmZpZy0+c3ByZWFkICAgICAgICAgICAgICAgICA9IDEgOwogICAgY29uZmlnLT5zdGF0ICAgICAgICAgICAgICAgICAgID0gMCA7CiAgICBjb25maWctPmUgICAgICAgICAgICAgICAgICAgICAgPSAxIDsKICAgIGNvbmZpZy0+ZGVsdGFUQWNyb3NzRnJhbWVzICAgICA9IDEgOwogICAgY29uZmlnLT5kRl9lZGdlXzFzdEVudiAgICAgICAgID0gRkwyRlhDT05TVF9EQkwoMC4zZikgOwogICAgY29uZmlnLT5kRl9lZGdlX2luY3IgICAgICAgICAgID0gRkwyRlhDT05TVF9EQkwoMC4zZikgOwoKICAgIGNvbmZpZy0+c2JyX2ludmZfbW9kZSAgID0gSU5WRl9TV0lUQ0hFRDsKICAgIGNvbmZpZy0+c2JyX3hwb3NfbW9kZSAgID0gWFBPU19MQzsKICAgIGNvbmZpZy0+c2JyX3hwb3NfY3RybCAgID0gU0JSX1hQT1NfQ1RSTF9ERUZBVUxUOwogICAgY29uZmlnLT5zYnJfeHBvc19sZXZlbCAgPSAwOwogICAgY29uZmlnLT51c2VTYVBhbiAgICAgICAgPSAwOwogICAgY29uZmlnLT5keW5Cd0VuYWJsZWQgICAgPSAwOwoKCiAgICAvKiB0aGUgZm9sbG93aW5nIHBhcmFtZXRlcnMgYXJlIG92ZXJ3cml0dGVuIGJ5IHRoZSBGREtzYnJFbmNfQWRqdXN0U2JyU2V0dGluZ3MoKSBmdW5jdGlvbiBzaW5jZQogICAgICAgdGhleSBhcmUgaW5jbHVkZWQgaW4gdGhlIHR1bmluZyB0YWJsZSAqLwogICAgY29uZmlnLT5zdGVyZW9Nb2RlICAgICAgICAgICAgID0gU0JSX1NXSVRDSF9MUkM7CiAgICBjb25maWctPmFuYV9tYXhfbGV2ZWwgICAgICAgICAgPSA2OwogICAgY29uZmlnLT5ub2lzZUZsb29yT2Zmc2V0ICAgICAgID0gMDsKICAgIGNvbmZpZy0+c3RhcnRGcmVxICAgICAgICAgICAgICA9IDU7IC8qICA1LjkgcmVzcGVjdGl2ZWx5ICA2LjAga0h6IGF0IGZzID0gNDQuMS80OCBrSHogKi8KICAgIGNvbmZpZy0+c3RvcEZyZXEgICAgICAgICAgICAgICA9IDk7IC8qIDE2LjIgcmVzcGVjdGl2ZWx5IDE2Ljgga0h6IGF0IGZzID0gNDQuMS80OCBrSHogKi8KCgogICAgLyogaGVhZGVyX2V4dHJhXzEgKi8KICAgIGNvbmZpZy0+ZnJlcVNjYWxlICAgICAgID0gU0JSX0ZSRVFfU0NBTEVfREVGQVVMVDsKICAgIGNvbmZpZy0+YWx0ZXJTY2FsZSAgICAgID0gU0JSX0FMVEVSX1NDQUxFX0RFRkFVTFQ7CiAgICBjb25maWctPnNicl9ub2lzZV9iYW5kcyA9IFNCUl9OT0lTRV9CQU5EU19ERUZBVUxUOwoKICAgIC8qIGhlYWRlcl9leHRyYV8yICovCiAgICBjb25maWctPnNicl9saW1pdGVyX2JhbmRzICAgID0gU0JSX0xJTUlURVJfQkFORFNfREVGQVVMVDsKICAgIGNvbmZpZy0+c2JyX2xpbWl0ZXJfZ2FpbnMgICAgPSBTQlJfTElNSVRFUl9HQUlOU19ERUZBVUxUOwogICAgY29uZmlnLT5zYnJfaW50ZXJwb2xfZnJlcSAgICA9IFNCUl9JTlRFUlBPTF9GUkVRX0RFRkFVTFQ7CiAgICBjb25maWctPnNicl9zbW9vdGhpbmdfbGVuZ3RoID0gU0JSX1NNT09USElOR19MRU5HVEhfREVGQVVMVDsKCiAgICByZXR1cm4gMTsKfQoKCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgoKIGZ1bmN0aW9ubmFtZTogRGVsZXRlRW52Q2hhbm5lbAogZGVzY3JpcHRpb246ICBmcmVlcyBtZW1vcnkgb2Ygb25lIFNCUiBjaGFubmVsCiByZXR1cm5zOiAgICAgIC0KIGlucHV0OiAgICAgICAgaGFuZGxlIG9mIGNoYW5uZWwKIG91dHB1dDogICAgICAgcmVsZWFzZWQgaGFuZGxlCgoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIHZvaWQKZGVsZXRlRW52Q2hhbm5lbCAoSEFORExFX0VOVl9DSEFOTkVMIGhFbnZDdXQpCnsKICBpZiAoaEVudkN1dCkgewoKICAgIEZES3NickVuY19EZWxldGVUb25Db3JyUGFyYW1FeHRyKCZoRW52Q3V0LT5Ub25Db3JyKTsKCiAgICBGREtzYnJFbmNfZGVsZXRlRXh0cmFjdFNickVudmVsb3BlICgmaEVudkN1dC0+c2JyRXh0cmFjdEVudmVsb3BlKTsKICB9Cgp9CgoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCgogZnVuY3Rpb25uYW1lOiBzYnJFbmNvZGVyX0NoYW5uZWxDbG9zZQogZGVzY3JpcHRpb246ICBjbG9zZSB0aGUgY2hhbm5lbCBjb2RpbmcgaGFuZGxlCiByZXR1cm5zOgogaW5wdXQ6ICAgICAgICBwaFNickNoYW5uZWwKIG91dHB1dDoKCioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgdm9pZApzYnJFbmNvZGVyX0NoYW5uZWxDbG9zZShIQU5ETEVfU0JSX0NIQU5ORUwgaFNickNoYW5uZWwpCnsKICBpZiAoaFNickNoYW5uZWwgIT0gTlVMTCkKICB7CiAgICBkZWxldGVFbnZDaGFubmVsICgmaFNickNoYW5uZWwtPmhFbnZDaGFubmVsKTsKICB9Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgoKIGZ1bmN0aW9ubmFtZTogc2JyRW5jb2Rlcl9FbGVtZW50Q2xvc2UKIGRlc2NyaXB0aW9uOiAgY2xvc2UgdGhlIGNoYW5uZWwgY29kaW5nIGhhbmRsZQogcmV0dXJuczoKIGlucHV0OiAgICAgICAgcGhTYnJDaGFubmVsCiBvdXRwdXQ6CgoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIHZvaWQKc2JyRW5jb2Rlcl9FbGVtZW50Q2xvc2UoSEFORExFX1NCUl9FTEVNRU5UICpwaFNickVsZW1lbnQpCnsKICBIQU5ETEVfU0JSX0VMRU1FTlQgaFNickVsZW1lbnQgPSAqcGhTYnJFbGVtZW50OwoKICBpZiAoaFNickVsZW1lbnQhPU5VTEwpIHsKICAgIGlmIChoU2JyRWxlbWVudC0+c2JyQ29uZmlnRGF0YS52X2tfbWFzdGVyKQogICAgICBGcmVlUmFtX1Nicl92X2tfbWFzdGVyKCZoU2JyRWxlbWVudC0+c2JyQ29uZmlnRGF0YS52X2tfbWFzdGVyKTsKICAgIGlmIChoU2JyRWxlbWVudC0+c2JyQ29uZmlnRGF0YS5mcmVxQmFuZFRhYmxlW0xPXSkKICAgICAgRnJlZVJhbV9TYnJfZnJlcUJhbmRUYWJsZUxPKCZoU2JyRWxlbWVudC0+c2JyQ29uZmlnRGF0YS5mcmVxQmFuZFRhYmxlW0xPXSk7CiAgICBpZiAoaFNickVsZW1lbnQtPnNickNvbmZpZ0RhdGEuZnJlcUJhbmRUYWJsZVtISV0pCiAgICAgIEZyZWVSYW1fU2JyX2ZyZXFCYW5kVGFibGVISSgmaFNickVsZW1lbnQtPnNickNvbmZpZ0RhdGEuZnJlcUJhbmRUYWJsZVtISV0pOwoKICAgIEZyZWVSYW1fU2JyRWxlbWVudChwaFNickVsZW1lbnQpOwogIH0KICByZXR1cm4gOwoKfQoKCnZvaWQgc2JyRW5jb2Rlcl9DbG9zZSAoSEFORExFX1NCUl9FTkNPREVSICpwaFNickVuY29kZXIpCnsKICBIQU5ETEVfU0JSX0VOQ09ERVIgaFNickVuY29kZXIgPSAqcGhTYnJFbmNvZGVyOwoKICBpZiAoaFNickVuY29kZXIgIT0gTlVMTCkKICB7CiAgICBpbnQgZWwsIGNoOwoKICAgIGZvciAoZWw9MDsgZWw8KDgpOyBlbCsrKQogICAgewogICAgICBpZiAoaFNickVuY29kZXItPnNickVsZW1lbnRbZWxdIT1OVUxMKSB7CiAgICAgICAgc2JyRW5jb2Rlcl9FbGVtZW50Q2xvc2UoJmhTYnJFbmNvZGVyLT5zYnJFbGVtZW50W2VsXSk7CiAgICAgIH0KICAgIH0KCiAgICAvKiBDbG9zZSBzYnIgQ2hhbm5lbHMgKi8KICAgIGZvciAoY2g9MDsgY2g8KDgpOyBjaCsrKQogICAgewogICAgICBpZiAoaFNickVuY29kZXItPnBTYnJDaGFubmVsW2NoXSkgewogICAgICAgIHNickVuY29kZXJfQ2hhbm5lbENsb3NlKGhTYnJFbmNvZGVyLT5wU2JyQ2hhbm5lbFtjaF0pOwogICAgICAgIEZyZWVSYW1fU2JyQ2hhbm5lbCgmaFNickVuY29kZXItPnBTYnJDaGFubmVsW2NoXSk7CiAgICAgIH0KCiAgICAgIGlmIChoU2JyRW5jb2Rlci0+UW1mQW5hbHlzaXNbY2hdLkZpbHRlclN0YXRlcykKICAgICAgICBGcmVlUmFtX1Nicl9RbWZTdGF0ZXNBbmFseXNpcygoRklYUF9RQVMqKikmaFNickVuY29kZXItPlFtZkFuYWx5c2lzW2NoXS5GaWx0ZXJTdGF0ZXMpOwoKCiAgICB9CgogICAgaWYgKGhTYnJFbmNvZGVyLT5oUGFyYW1ldHJpY1N0ZXJlbykKICAgICAgUFNFbmNfRGVzdHJveSgmaFNickVuY29kZXItPmhQYXJhbWV0cmljU3RlcmVvKTsKICAgIGlmIChoU2JyRW5jb2Rlci0+cW1mU3ludGhlc2lzUFMuRmlsdGVyU3RhdGVzKQogICAgICBGcmVlUmFtX1BzUW1mU3RhdGVzU3ludGhlc2lzKChGSVhQX0RCTCoqKSZoU2JyRW5jb2Rlci0+cW1mU3ludGhlc2lzUFMuRmlsdGVyU3RhdGVzKTsKCiAgICAvKiBSZWxlYXNlIE92ZXJsYXkgKi8KICAgIEZyZWVSYW1fU2JyRHluYW1pY19SQU0oKEZJWFBfREJMKiopJmhTYnJFbmNvZGVyLT5wU0JSZHluYW1pY19SQU0pOwoKCiAgICBGcmVlUmFtX1NickVuY29kZXIocGhTYnJFbmNvZGVyKTsKICB9Cgp9CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKCiBmdW5jdGlvbm5hbWU6IHVwZGF0ZUZyZXFCYW5kVGFibGUKIGRlc2NyaXB0aW9uOiAgdXBkYXRlcyB2a19tYXN0ZXIKIHJldHVybnM6ICAgICAgLQogaW5wdXQ6ICAgICAgICBjb25maWcgaGFuZGxlCiBvdXRwdXQ6ICAgICAgIGVycm9yIGluZm8KCioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSU5UIHVwZGF0ZUZyZXFCYW5kVGFibGUoCiAgICAgICAgSEFORExFX1NCUl9DT05GSUdfREFUQSAgc2JyQ29uZmlnRGF0YSwKICAgICAgICBIQU5ETEVfU0JSX0hFQURFUl9EQVRBICBzYnJIZWFkZXJEYXRhLAogICAgICAgIGNvbnN0IElOVCAgICAgICAgICAgICAgIGRvd25TYW1wbGVGYWN0b3IKICAgICAgICApCnsKICBJTlQgazAsIGsyOwoKICBpZiggRkRLc2JyRW5jX0ZpbmRTdGFydEFuZFN0b3BCYW5kICgKICAgICAgICAgICAgICBzYnJDb25maWdEYXRhLT5zYW1wbGVGcmVxLAogICAgICAgICAgICAgIHNickNvbmZpZ0RhdGEtPnNhbXBsZUZyZXEgPj4gKGRvd25TYW1wbGVGYWN0b3ItMSksCiAgICAgICAgICAgICAgc2JyQ29uZmlnRGF0YS0+bm9RbWZCYW5kcywKICAgICAgICAgICAgICBzYnJIZWFkZXJEYXRhLT5zYnJfc3RhcnRfZnJlcXVlbmN5LAogICAgICAgICAgICAgIHNickhlYWRlckRhdGEtPnNicl9zdG9wX2ZyZXF1ZW5jeSwKICAgICAgICAgICAgICZrMCwKICAgICAgICAgICAgICZrMgogICAgICAgICAgICAgICkKICAgICkKICAgIHJldHVybigxKTsKCgogIGlmKCBGREtzYnJFbmNfVXBkYXRlRnJlcVNjYWxlKAogICAgICAgICAgICAgIHNickNvbmZpZ0RhdGEtPnZfa19tYXN0ZXIsCiAgICAgICAgICAgICAmc2JyQ29uZmlnRGF0YS0+bnVtX01hc3RlciwKICAgICAgICAgICAgICBrMCwKICAgICAgICAgICAgICBrMiwKICAgICAgICAgICAgICBzYnJIZWFkZXJEYXRhLT5mcmVxU2NhbGUsCiAgICAgICAgICAgICAgc2JySGVhZGVyRGF0YS0+YWx0ZXJTY2FsZQogICAgICAgICAgICAgICkKICAgICkKICAgIHJldHVybigxKTsKCgogIHNickhlYWRlckRhdGEtPnNicl94b3Zlcl9iYW5kPTA7CgoKICBpZiggRkRLc2JyRW5jX1VwZGF0ZUhpUmVzKAogICAgICAgICAgICAgIHNickNvbmZpZ0RhdGEtPmZyZXFCYW5kVGFibGVbSEldLAogICAgICAgICAgICAgICZzYnJDb25maWdEYXRhLT5uU2ZiW0hJXSwKICAgICAgICAgICAgICBzYnJDb25maWdEYXRhLT52X2tfbWFzdGVyLAogICAgICAgICAgICAgIHNickNvbmZpZ0RhdGEtPm51bV9NYXN0ZXIsCiAgICAgICAgICAgICAgJnNickhlYWRlckRhdGEtPnNicl94b3Zlcl9iYW5kCiAgICAgICAgICAgICAgKQogICAgKQogICAgcmV0dXJuKDEpOwoKCiAgRkRLc2JyRW5jX1VwZGF0ZUxvUmVzKAogICAgICAgICAgc2JyQ29uZmlnRGF0YS0+ZnJlcUJhbmRUYWJsZVtMT10sCiAgICAgICAgICAmc2JyQ29uZmlnRGF0YS0+blNmYltMT10sCiAgICAgICAgICBzYnJDb25maWdEYXRhLT5mcmVxQmFuZFRhYmxlW0hJXSwKICAgICAgICAgIHNickNvbmZpZ0RhdGEtPm5TZmJbSEldCiAgICAgICAgICApOwoKCiAgc2JyQ29uZmlnRGF0YS0+eE92ZXJGcmVxID0gKHNickNvbmZpZ0RhdGEtPmZyZXFCYW5kVGFibGVbTE9XX1JFU11bMF0gKiBzYnJDb25maWdEYXRhLT5zYW1wbGVGcmVxIC8gc2JyQ29uZmlnRGF0YS0+bm9RbWZCYW5kcysxKT4+MTsKCiAgcmV0dXJuICgwKTsKfQoKCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgoKIGZ1bmN0aW9ubmFtZTogcmVzZXRFbnZDaGFubmVsCiBkZXNjcmlwdGlvbjogIHJlc2V0cyBwYXJhbWV0ZXJzIGFuZCBhbGxvY2F0ZXMgbWVtb3J5CiByZXR1cm5zOiAgICAgIGVycm9yIHN0YXR1cwogaW5wdXQ6CiBvdXRwdXQ6ICAgICAgIGhFbnYKCioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSU5UIHJlc2V0RW52Q2hhbm5lbCAoSEFORExFX1NCUl9DT05GSUdfREFUQSAgc2JyQ29uZmlnRGF0YSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIEhBTkRMRV9TQlJfSEVBREVSX0RBVEEgIHNickhlYWRlckRhdGEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBIQU5ETEVfRU5WX0NIQU5ORUwgICAgICBoRW52KQp7CiAgLyogbm90ZSAhISEgaEVudi0+ZW5jRW52RGF0YS5ub09mbm9pc2ViYW5kcyB3aWxsIGJlIHVwZGF0ZWQgbGF0ZXIgaW4gZnVuY3Rpb24gRkRLc2JyRW5jX2V4dHJhY3RTYnJFbnZlbG9wZSAhISEqLwogIGhFbnYtPlRvbkNvcnIuc2JyTm9pc2VGbG9vckVzdGltYXRlLm5vaXNlQmFuZHMgPSAgc2JySGVhZGVyRGF0YS0+c2JyX25vaXNlX2JhbmRzOwoKCiAgaWYoRkRLc2JyRW5jX1Jlc2V0VG9uQ29yclBhcmFtRXh0cigmaEVudi0+VG9uQ29yciwKICAgICAgICAgICAgICAgICAgICAgICAgICAgc2JyQ29uZmlnRGF0YS0+eHBvc0N0cmxTd2l0Y2gsCiAgICAgICAgICAgICAgICAgICAgICAgICAgIHNickNvbmZpZ0RhdGEtPmZyZXFCYW5kVGFibGVbSEldWzBdLAogICAgICAgICAgICAgICAgICAgICAgICAgICBzYnJDb25maWdEYXRhLT52X2tfbWFzdGVyLAogICAgICAgICAgICAgICAgICAgICAgICAgICBzYnJDb25maWdEYXRhLT5udW1fTWFzdGVyLAogICAgICAgICAgICAgICAgICAgICAgICAgICBzYnJDb25maWdEYXRhLT5zYW1wbGVGcmVxLAogICAgICAgICAgICAgICAgICAgICAgICAgICBzYnJDb25maWdEYXRhLT5mcmVxQmFuZFRhYmxlLAogICAgICAgICAgICAgICAgICAgICAgICAgICBzYnJDb25maWdEYXRhLT5uU2ZiLAogICAgICAgICAgICAgICAgICAgICAgICAgICBzYnJDb25maWdEYXRhLT5ub1FtZkJhbmRzKSkKICAgIHJldHVybigxKTsKCiAgaEVudi0+c2JyQ29kZU5vaXNlRmxvb3IublNmYltMT10gPSBoRW52LT5Ub25Db3JyLnNick5vaXNlRmxvb3JFc3RpbWF0ZS5ub05vaXNlQmFuZHM7CiAgaEVudi0+c2JyQ29kZU5vaXNlRmxvb3IublNmYltISV0gPSBoRW52LT5Ub25Db3JyLnNick5vaXNlRmxvb3JFc3RpbWF0ZS5ub05vaXNlQmFuZHM7CgogIGhFbnYtPnNickNvZGVFbnZlbG9wZS5uU2ZiW0xPXSA9IHNickNvbmZpZ0RhdGEtPm5TZmJbTE9dOwogIGhFbnYtPnNickNvZGVFbnZlbG9wZS5uU2ZiW0hJXSA9IHNickNvbmZpZ0RhdGEtPm5TZmJbSEldOwoKICBoRW52LT5lbmNFbnZEYXRhLm5vSGFybW9uaWNzID0gc2JyQ29uZmlnRGF0YS0+blNmYltISV07CgogIGhFbnYtPnNickNvZGVFbnZlbG9wZS51cERhdGUgPSAwOwogIGhFbnYtPnNickNvZGVOb2lzZUZsb29yLnVwRGF0ZSA9IDA7CgogIHJldHVybiAoMCk7Cn0KCi8qICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiBGREtzYnJFbmNfU2JyR2V0WE92ZXJGcmVxICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8KLyoqCiAqIEBmbgogKiBAYnJpZWYgICAgICAgY2FsY3VsYXRlcyB0aGUgY2xvc2VzdCBwb3NzaWJsZSBjcm9zc292ZXIgZnJlcXVlbmN5CiAqIEByZXR1cm4gICAgICB0aGUgY3Jvc3NvdmVyIGZyZXF1ZW5jeSBTQlIgYWNjZXB0cwogKgogKi8Kc3RhdGljIElOVApGREtzYnJFbmNfU2JyR2V0WE92ZXJGcmVxKEhBTkRMRV9TQlJfRUxFTUVOVCAgaEVudiwgICAgICAgIC8qITwgaGFuZGxlIHRvIFNCUiBlbmNvZGVyIGluc3RhbmNlICovCiAgICAgICAgICAgICAgICAgICAgICAgICAgSU5UICAgICAgICAgICAgICAgICB4b3ZlckZyZXEpICAgLyohPCBmcm9tIGNvcmUgY29kZXIgc3VnZ2VzdGVkIGNyb3Nzb3ZlciBmcmVxdWVuY3kgKi8KewogIElOVCBiYW5kOwogIElOVCBsYXN0RGlmZiwgbmV3RGlmZjsKICBJTlQgY3V0b2ZmU2I7CgogIFVDSEFSICpSRVNUUklDVCBwVktNYXN0ZXIgPSBoRW52LT5zYnJDb25maWdEYXRhLnZfa19tYXN0ZXI7CgogIC8qIENoZWNrIGlmIHRoZXJlIGlzIGEgbWF0Y2hpbmcgY3V0b2ZmIGZyZXF1ZW5jeSBpbiB0aGUgbWFzdGVyIHRhYmxlICovCiAgY3V0b2ZmU2IgPSAoNCp4b3ZlckZyZXEgKiBoRW52LT5zYnJDb25maWdEYXRhLm5vUW1mQmFuZHMgLyBoRW52LT5zYnJDb25maWdEYXRhLnNhbXBsZUZyZXEgKyAxKT4+MTsKICBsYXN0RGlmZiA9IGN1dG9mZlNiOwogIGZvciAoYmFuZCA9IDA7IGJhbmQgPCBoRW52LT5zYnJDb25maWdEYXRhLm51bV9NYXN0ZXI7IGJhbmQrKykgewoKICAgIG5ld0RpZmYgPSBmaXhwX2FicygoSU5UKXBWS01hc3RlcltiYW5kXSAtIGN1dG9mZlNiKTsKCiAgICBpZihuZXdEaWZmID49IGxhc3REaWZmKSB7CiAgICAgIGJhbmQtLTsKICAgICAgYnJlYWs7CiAgICB9CgogICAgbGFzdERpZmYgPSBuZXdEaWZmOwogIH0KCiAgcmV0dXJuICgocFZLTWFzdGVyW2JhbmRdICogaEVudi0+c2JyQ29uZmlnRGF0YS5zYW1wbGVGcmVxL2hFbnYtPnNickNvbmZpZ0RhdGEubm9RbWZCYW5kcysxKT4+MSk7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgoKIGZ1bmN0aW9ubmFtZTogRkRLc2JyRW5jX0VudkVuY29kZUZyYW1lCiBkZXNjcmlwdGlvbjogcGVyZm9ybXMgdGhlIHNiciBlbnZlbG9wZSBjYWxjdWxhdGlvbiBmb3Igb25lIGVsZW1lbnQKIHJldHVybnM6CiBpbnB1dDoKIG91dHB1dDoKCioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpJTlQKRkRLc2JyRW5jX0VudkVuY29kZUZyYW1lKEhBTkRMRV9TQlJfRU5DT0RFUiAgIGhFbnZFbmNvZGVyLAogICAgICAgICAgICAgICAgICAgICAgICAgaW50ICAgICAgICAgICAgICAgICAgaUVsZW1lbnQsCiAgICAgICAgICAgICAgICAgICAgICAgICBJTlRfUENNICAgICAgICAgICAgICpzYW1wbGVzLCAgICAgICAgICAgICAgICAgLyohPCB0aW1lIHNhbXBsZXMsIGFsd2F5cyBpbnRlcmxlYXZlZCAqLwogICAgICAgICAgICAgICAgICAgICAgICAgVUlOVCAgICAgICAgICAgICAgICAgdGltZUluU3RyaWRlLCAgICAgICAgICAgIC8qITwgdGltZSBidWZmZXIgY2hhbm5lbCBpbnRlcmxlYXZpbmcgc3RyaWRlICovCiAgICAgICAgICAgICAgICAgICAgICAgICBVSU5UICAgICAgICAgICAgICAgICpzYnJEYXRhQml0cywgICAgICAgICAgICAgLyohPCBTaXplIG9mIFNCUiBwYXlsb2FkICAqLwogICAgICAgICAgICAgICAgICAgICAgICAgVUNIQVIgICAgICAgICAgICAgICAqc2JyRGF0YSwgICAgICAgICAgICAgICAgIC8qITwgU0JSIHBheWxvYWQgICovCiAgICAgICAgICAgICAgICAgICAgICAgICBpbnQgICAgICAgICAgICAgICAgICBjbGVhck91dHB1dCAgICAgICAgICAgICAgLyohPCBEbyBub3QgY29uc2lkZXIgYW55IGlucHV0IHNpZ25hbCAqLwogICAgICAgICAgICAgICAgICAgICAgICApCnsKICBIQU5ETEVfU0JSX0VMRU1FTlQgaFNickVsZW1lbnQgPSBoRW52RW5jb2Rlci0+c2JyRWxlbWVudFtpRWxlbWVudF07CiAgRkRLX0NSQ0lORk8gIGNyY0luZm87CiAgSU5UICAgIGNyY1JlZzsKICBJTlQgICAgY2g7CiAgSU5UICAgIGJhbmQ7CiAgSU5UICAgIGN1dG9mZlNiOwogIElOVCAgICBuZXdYT3ZlcjsKCiAgaWYgKGhFbnZFbmNvZGVyID09IE5VTEwpCiAgICByZXR1cm4gLTE7CgogIGhTYnJFbGVtZW50ID0gaEVudkVuY29kZXItPnNickVsZW1lbnRbaUVsZW1lbnRdOwoKICBpZiAoaFNickVsZW1lbnQgPT0gTlVMTCkKICAgIHJldHVybiAtMTsKCgogIC8qIGhlYWRlciBiaXRzdHJlYW0gaGFuZGxpbmcgKi8KICBIQU5ETEVfU0JSX0JJVFNUUkVBTV9EQVRBIHNickJpdHN0cmVhbURhdGEgPSAmaFNickVsZW1lbnQtPnNickJpdHN0cmVhbURhdGE7CgogIElOVCBwc0hlYWRlckFjdGl2ZSA9IDA7CiAgc2JyQml0c3RyZWFtRGF0YS0+SGVhZGVyQWN0aXZlID0gMDsKCiAgLyogQW50aWNpcGF0ZSBQUyBoZWFkZXIgYmVjYXVzZSBvZiBpbnRlcm5hbCBQUyBiaXRzdHJlYW0gZGVsYXkgaW4gb3JkZXIgdG8gYmUgaW4gc3luYyB3aXRoIFNCUiBoZWFkZXIuICovCiAgaWYgKCBzYnJCaXRzdHJlYW1EYXRhLT5Db3VudFNlbmRIZWFkZXJEYXRhPT0oc2JyQml0c3RyZWFtRGF0YS0+TnJTZW5kSGVhZGVyRGF0YS0xKSApCiAgewogICAgICBwc0hlYWRlckFjdGl2ZSA9IDE7CiAgfQoKICAvKiBTaWduYWwgU0JSIGhlYWRlciB0byBiZSB3cml0dGVuIGludG8gYml0c3RyZWFtICovCiAgaWYgKCBzYnJCaXRzdHJlYW1EYXRhLT5Db3VudFNlbmRIZWFkZXJEYXRhPT0wICApCiAgewogICAgIHNickJpdHN0cmVhbURhdGEtPkhlYWRlckFjdGl2ZSA9IDE7CiAgfQoKICAvKiBJbmNyZW1lbnQgaGVhZGVyIGludGVydmFsIGNvdW50ZXIgKi8KICBpZiAoc2JyQml0c3RyZWFtRGF0YS0+TnJTZW5kSGVhZGVyRGF0YSA9PSAwKSB7CiAgICBzYnJCaXRzdHJlYW1EYXRhLT5Db3VudFNlbmRIZWFkZXJEYXRhID0gMTsKICB9CiAgZWxzZSB7CiAgICBpZiAoc2JyQml0c3RyZWFtRGF0YS0+Q291bnRTZW5kSGVhZGVyRGF0YSA+PSAwKSB7CiAgICAgIHNickJpdHN0cmVhbURhdGEtPkNvdW50U2VuZEhlYWRlckRhdGErKzsKICAgICAgc2JyQml0c3RyZWFtRGF0YS0+Q291bnRTZW5kSGVhZGVyRGF0YSAlPSBzYnJCaXRzdHJlYW1EYXRhLT5OclNlbmRIZWFkZXJEYXRhOwogICAgfQogIH0KCiAgaWYgKGhTYnJFbGVtZW50LT5DbW9uRGF0YS5keW5Cd0VuYWJsZWQgKSB7CiAgICBJTlQgaTsKICAgIGZvciAoIGkgPSA0OyBpID4gMDsgaS0tICkKICAgICAgaFNickVsZW1lbnQtPmR5blhPdmVyRnJlcURlbGF5W2ldID0gaFNickVsZW1lbnQtPmR5blhPdmVyRnJlcURlbGF5W2ktMV07CgogICAgaFNickVsZW1lbnQtPmR5blhPdmVyRnJlcURlbGF5WzBdID0gaFNickVsZW1lbnQtPkNtb25EYXRhLmR5blhPdmVyRnJlcUVuYzsKICAgIGlmIChoU2JyRWxlbWVudC0+ZHluWE92ZXJGcmVxRGVsYXlbMV0gPiBoU2JyRWxlbWVudC0+ZHluWE92ZXJGcmVxRGVsYXlbMl0pCiAgICAgIG5ld1hPdmVyID0gaFNickVsZW1lbnQtPmR5blhPdmVyRnJlcURlbGF5WzJdOwogICAgZWxzZQogICAgICBuZXdYT3ZlciA9IGhTYnJFbGVtZW50LT5keW5YT3ZlckZyZXFEZWxheVsxXTsKCiAgICAvKiBoYXMgdGhlIGNyb3Nzb3ZlciBmcmVxdWVuY3kgY2hhbmdlZD8gKi8KICAgIGlmICggaFNickVsZW1lbnQtPnNickNvbmZpZ0RhdGEuZHluWE92ZXJGcmVxICE9IG5ld1hPdmVyICkgewoKICAgICAgLyogZ2V0IGNvcnJlc3BvbmRpbmcgbWFzdGVyIGJhbmQgKi8KICAgICAgY3V0b2ZmU2IgPSAoKDQqIG5ld1hPdmVyICogaFNickVsZW1lbnQtPnNickNvbmZpZ0RhdGEubm9RbWZCYW5kcwogICAgICAgICAgICAgICAgICAvIGhTYnJFbGVtZW50LT5zYnJDb25maWdEYXRhLnNhbXBsZUZyZXEpKzEpPj4xOwoKICAgICAgZm9yICggYmFuZCA9IDA7IGJhbmQgPCBoU2JyRWxlbWVudC0+c2JyQ29uZmlnRGF0YS5udW1fTWFzdGVyOyBiYW5kKysgKSB7CiAgICAgICAgaWYgKCBjdXRvZmZTYiA9PSBoU2JyRWxlbWVudC0+c2JyQ29uZmlnRGF0YS52X2tfbWFzdGVyW2JhbmRdICkKICAgICAgICAgIGJyZWFrOwogICAgICB9CiAgICAgIEZES19BU1NFUlQoIGJhbmQgPCBoU2JyRWxlbWVudC0+c2JyQ29uZmlnRGF0YS5udW1fTWFzdGVyICk7CgogICAgICBoU2JyRWxlbWVudC0+c2JyQ29uZmlnRGF0YS5keW5YT3ZlckZyZXEgPSBuZXdYT3ZlcjsKICAgICAgaFNickVsZW1lbnQtPnNickhlYWRlckRhdGEuc2JyX3hvdmVyX2JhbmQgPSBiYW5kOwogICAgICBoU2JyRWxlbWVudC0+c2JyQml0c3RyZWFtRGF0YS5IZWFkZXJBY3RpdmU9MTsKICAgICAgcHNIZWFkZXJBY3RpdmUgPSAxOyAvKiBwcyBoZWFkZXIgaXMgb25lIGZyYW1lIGRlbGF5ZWQgKi8KCiAgICAgIC8qCiAgICAgICAgdXBkYXRlIHZrX21hc3RlciB0YWJsZQogICAgICAqLwogICAgICBpZih1cGRhdGVGcmVxQmFuZFRhYmxlKCZoU2JyRWxlbWVudC0+c2JyQ29uZmlnRGF0YSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmaFNickVsZW1lbnQtPnNickhlYWRlckRhdGEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaEVudkVuY29kZXItPmRvd25TYW1wbGVGYWN0b3IKICAgICAgICAgICAgICAgICAgICAgICAgICAgICApKQogICAgICAgIHJldHVybigxKTsKCgogICAgICAvKiByZXNldCBTQlIgY2hhbm5lbHMgKi8KICAgICAgSU5UIG5FbnZDaCA9IGhTYnJFbGVtZW50LT5zYnJDb25maWdEYXRhLm5DaGFubmVsczsKICAgICAgZm9yICggY2ggPSAwOyBjaCA8IG5FbnZDaDsgY2grKyApIHsKICAgICAgICBpZihyZXNldEVudkNoYW5uZWwgKCZoU2JyRWxlbWVudC0+c2JyQ29uZmlnRGF0YSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICZoU2JyRWxlbWVudC0+c2JySGVhZGVyRGF0YSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICZoU2JyRWxlbWVudC0+c2JyQ2hhbm5lbFtjaF0tPmhFbnZDaGFubmVsKSkKICAgICAgICAgIHJldHVybigxKTsKCiAgICAgIH0KICAgIH0KICB9CgogIC8qCiAgICBhbGxvY2F0ZSBzcGFjZSBmb3IgZHVtbXkgaGVhZGVyIGFuZCBjcmMKICAqLwogIGNyY1JlZyA9IEZES3NickVuY19Jbml0U2JyQml0c3RyZWFtKCZoU2JyRWxlbWVudC0+Q21vbkRhdGEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGhTYnJFbGVtZW50LT5wYXlsb2FkRGVsYXlMaW5lW2hFbnZFbmNvZGVyLT5uQml0c3RyRGVsYXldLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBNQVhfUEFZTE9BRF9TSVpFKnNpemVvZihVQ0hBUiksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJmNyY0luZm8sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGhTYnJFbGVtZW50LT5zYnJDb25maWdEYXRhLnNiclN5bnRheEZsYWdzKTsKCiAgLyogVGVtcG9yYWwgRW52ZWxvcGUgRGF0YSAqLwogIFNCUl9GUkFNRV9URU1QX0RBVEEgX2ZEYXRhOwogIFNCUl9GUkFNRV9URU1QX0RBVEEgKmZEYXRhID0gJl9mRGF0YTsKICBTQlJfRU5WX1RFTVBfREFUQSBlRGF0YVtNQVhfTlVNX0NIQU5ORUxTXTsKCiAgLyogSW5pdCBUZW1wb3JhbCBFbnZlbG9wZSBEYXRhICovCiAgewogICAgaW50IGk7CgogICAgRkRLbWVtY2xlYXIoJmVEYXRhWzBdLCBzaXplb2YoU0JSX0VOVl9URU1QX0RBVEEpKTsKICAgIEZES21lbWNsZWFyKCZlRGF0YVsxXSwgc2l6ZW9mKFNCUl9FTlZfVEVNUF9EQVRBKSk7CiAgICBGREttZW1jbGVhcihmRGF0YSwgc2l6ZW9mKFNCUl9GUkFNRV9URU1QX0RBVEEpKTsKCiAgICBmb3IoaT0wOyBpPE1BWF9OVU1fTk9JU0VfVkFMVUVTOyBpKyspCiAgICAgIGZEYXRhLT5yZXNbaV0gPSBGUkVRX1JFU19ISUdIOwogIH0KCgogIGlmICghY2xlYXJPdXRwdXQpCiAgewogICAgLyoKICAgICAqIFRyYW5zZm9ybSBhdWRpbyBkYXRhIGludG8gUU1GIGRvbWFpbgogICAgICovCiAgICBmb3IoY2ggPSAwOyBjaCA8IGhTYnJFbGVtZW50LT5zYnJDb25maWdEYXRhLm5DaGFubmVsczsgY2grKykKICAgIHsKICAgICAgSEFORExFX0VOVl9DSEFOTkVMIGhfZW52Q2hhbiA9ICZoU2JyRWxlbWVudC0+c2JyQ2hhbm5lbFtjaF0tPmhFbnZDaGFubmVsOwogICAgICBIQU5ETEVfU0JSX0VYVFJBQ1RfRU5WRUxPUEUgc2JyRXh0ckVudiA9ICZoX2VudkNoYW4tPnNickV4dHJhY3RFbnZlbG9wZTsKCiAgICAgIGlmKGhTYnJFbGVtZW50LT5lbEluZm8uZlBhcmFtZXRyaWNTdGVyZW8gPT0gMCkKICAgICAgewogICAgICAgIFFNRl9TQ0FMRV9GQUNUT1IgdG1wU2NhbGU7CiAgICAgICAgRklYUF9EQkwgKipwUW1mUmVhbCwgKipwUW1mSW1hZzsKICAgICAgICBDX0FBTExPQ19TQ1JBVENIX1NUQVJUKHFtZldvcmtCdWZmZXIsIEZJWFBfREJMLCBRTUZfQ0hBTk5FTFMqMikKCgogICAgICAgIC8qIE9idGFpbiBwb2ludGVycyB0byBRTUYgYnVmZmVycy4gKi8KICAgICAgICBwUW1mUmVhbCA9IHNickV4dHJFbnYtPnJCdWZmZXI7CiAgICAgICAgcFFtZkltYWcgPSBzYnJFeHRyRW52LT5pQnVmZmVyOwoKICAgICAgICBxbWZBbmFseXNpc0ZpbHRlcmluZyggaFNickVsZW1lbnQtPmhRbWZBbmFseXNpc1tjaF0sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBwUW1mUmVhbCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHBRbWZJbWFnLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmdG1wU2NhbGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzYW1wbGVzICsgaFNickVsZW1lbnQtPmVsSW5mby5DaGFubmVsSW5kZXhbY2hdLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdGltZUluU3RyaWRlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcW1mV29ya0J1ZmZlciApOwoKICAgICAgICBoX2VudkNoYW4tPnFtZlNjYWxlID0gdG1wU2NhbGUubGJfc2NhbGUgKyA3OwoKCiAgICAgICAgQ19BQUxMT0NfU0NSQVRDSF9FTkQocW1mV29ya0J1ZmZlciwgRklYUF9EQkwsIFFNRl9DSEFOTkVMUyoyKQoKICAgICAgfSAvKiBmUGFyYW1ldHJpY1N0ZXJlbyA9PSAwICovCgoKICAgICAgLyoKICAgICAgICBQYXJhbWV0cmljIFN0ZXJlbyBwcm9jZXNzaW5nCiAgICAgICovCiAgICAgIGlmIChoU2JyRWxlbWVudC0+ZWxJbmZvLmZQYXJhbWV0cmljU3RlcmVvKQogICAgICB7CiAgICAgICAgSU5UIGVycm9yID0gbm9FcnJvcjsKCgogICAgICAgIC8qIExpbWl0IFBhcmFtZXRyaWMgU3RlcmVvIHRvIG9uZSBpbnN0YW5jZSAqLwogICAgICAgIEZES19BU1NFUlQoY2ggPT0gMCk7CgoKICAgICAgICBpZihlcnJvciA9PSBub0Vycm9yKXsKICAgICAgICAgIC8qIHBhcmFtZXRyaWMgc3RlcmVvIHByb2Nlc3Npbmc6CiAgICAgICAgICAgICAtIGlucHV0OgogICAgICAgICAgICAgICBvIGxlZnQgYW5kIHJpZ2h0IHRpbWUgZG9tYWluIHNhbXBsZXMKICAgICAgICAgICAgIC0gcHJvY2Vzc2luZzoKICAgICAgICAgICAgICAgbyBzdGVyZW8gcW1mIGFuYWx5c2lzCiAgICAgICAgICAgICAgIG8gc3RlcmVvIGh5YnJpZCBhbmFseXNpcwogICAgICAgICAgICAgICBvIHBzIHBhcmFtZXRlciBleHRyYWN0aW9uCiAgICAgICAgICAgICAgIG8gZG93bm1peCArIGh5YnJpZCBzeW50aGVzaXMKICAgICAgICAgICAgIC0gb3V0cHV0OgogICAgICAgICAgICAgICBvIGRvd25taXhlZCBxbWYgZGF0YSBpcyB3cml0dGVuIHRvIHNickV4dHJFbnYtPnJCdWZmZXIgYW5kIHNickV4dHJFbnYtPmlCdWZmZXIKICAgICAgICAgICovCiAgICAgICAgICBTQ0hBUiBxbWZTY2FsZTsKICAgICAgICAgIElOVF9QQ00qIHBTYW1wbGVzWzJdID0ge3NhbXBsZXMgKyBoU2JyRWxlbWVudC0+ZWxJbmZvLkNoYW5uZWxJbmRleFswXSxzYW1wbGVzICsgaFNickVsZW1lbnQtPmVsSW5mby5DaGFubmVsSW5kZXhbMV19OwogICAgICAgICAgZXJyb3IgPSBGREtzYnJFbmNfUFNFbmNfUGFyYW1ldHJpY1N0ZXJlb1Byb2Nlc3NpbmcoIGhFbnZFbmNvZGVyLT5oUGFyYW1ldHJpY1N0ZXJlbywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBwU2FtcGxlcywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB0aW1lSW5TdHJpZGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaFNickVsZW1lbnQtPmhRbWZBbmFseXNpcywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzYnJFeHRyRW52LT5yQnVmZmVyLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNickV4dHJFbnYtPmlCdWZmZXIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2FtcGxlcyArIGhTYnJFbGVtZW50LT5lbEluZm8uQ2hhbm5lbEluZGV4W2NoXSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICZoRW52RW5jb2Rlci0+cW1mU3ludGhlc2lzUFMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmcW1mU2NhbGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcHNIZWFkZXJBY3RpdmUgKTsKICAgICAgICAgIGlmIChub0Vycm9yICE9IGVycm9yKQogICAgICAgICAgewogICAgICAgICAgICBlcnJvciA9IGhhbmRCYWNrKGVycm9yKTsKICAgICAgICAgIH0KICAgICAgICAgIGhfZW52Q2hhbi0+cW1mU2NhbGUgPSAoaW50KXFtZlNjYWxlOwogICAgICAgIH0KCgogICAgICB9IC8qIGlmIChoRW52RW5jb2Rlci0+aFBhcmFtZXRyaWNTdGVyZW8pICovCgogICAgICAvKgoKICAgICAgICAgRXh0cmFjdCBFbnZlbG9wZSByZWxldmFudCB0aGluZ3MgZnJvbSBRTUYgZGF0YQoKICAgICAgKi8KICAgICAgRkRLc2JyRW5jX2V4dHJhY3RTYnJFbnZlbG9wZTEoCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJmhTYnJFbGVtZW50LT5zYnJDb25maWdEYXRhLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICZoU2JyRWxlbWVudC0+c2JySGVhZGVyRGF0YSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmaFNickVsZW1lbnQtPnNickJpdHN0cmVhbURhdGEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGhfZW52Q2hhbiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmaFNickVsZW1lbnQtPkNtb25EYXRhLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICZlRGF0YVtjaF0sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGZEYXRhCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICk7CgogICAgfSAvKiBoRW52RW5jb2Rlci0+c2JyQ29uZmlnRGF0YS5uQ2hhbm5lbHMgKi8KIH0KCiAgLyoKICAgICBQcm9jZXNzIEVudmVsb3BlIHJlbGV2YW50IHRoaW5ncyBhbmQgY2FsY3VsYXRlIGVudmVsb3BlIGRhdGEgYW5kIHdyaXRlIHBheWxvYWQKICAqLwogIEZES3NickVuY19leHRyYWN0U2JyRW52ZWxvcGUyKAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICZoU2JyRWxlbWVudC0+c2JyQ29uZmlnRGF0YSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmaFNickVsZW1lbnQtPnNickhlYWRlckRhdGEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKGhTYnJFbGVtZW50LT5lbEluZm8uZlBhcmFtZXRyaWNTdGVyZW8pID8gaEVudkVuY29kZXItPmhQYXJhbWV0cmljU3RlcmVvIDogTlVMTCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmaFNickVsZW1lbnQtPnNickJpdHN0cmVhbURhdGEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJmhTYnJFbGVtZW50LT5zYnJDaGFubmVsWzBdLT5oRW52Q2hhbm5lbCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmaFNickVsZW1lbnQtPnNickNoYW5uZWxbMV0tPmhFbnZDaGFubmVsLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICZoU2JyRWxlbWVudC0+Q21vbkRhdGEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGVEYXRhLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBmRGF0YSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY2xlYXJPdXRwdXQKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICk7CgogIC8qCiAgICBmb3JtYXQgcGF5bG9hZCwgY2FsY3VsYXRlIGNyYwogICovCiAgRkRLc2JyRW5jX0Fzc2VtYmxlU2JyQml0c3RyZWFtKCZoU2JyRWxlbWVudC0+Q21vbkRhdGEsICZjcmNJbmZvLCBjcmNSZWcsIGhTYnJFbGVtZW50LT5zYnJDb25maWdEYXRhLnNiclN5bnRheEZsYWdzKTsKCiAgLyoKICAgIHNhdmUgbmV3IHBheWxvYWQsIHNldCB0byB6ZXJvIGxlbmd0aCBpZiBncmVhdGVyIHRoYW4gTUFYX1BBWUxPQURfU0laRQogICovCiAgaFNickVsZW1lbnQtPnBheWxvYWREZWxheUxpbmVTaXplW2hFbnZFbmNvZGVyLT5uQml0c3RyRGVsYXldID0gRkRLZ2V0VmFsaWRCaXRzKCZoU2JyRWxlbWVudC0+Q21vbkRhdGEuc2JyQml0YnVmKTsKCiAgaWYoaFNickVsZW1lbnQtPnBheWxvYWREZWxheUxpbmVTaXplW2hFbnZFbmNvZGVyLT5uQml0c3RyRGVsYXldID4gKE1BWF9QQVlMT0FEX1NJWkU8PDMpKQogICAgaFNickVsZW1lbnQtPnBheWxvYWREZWxheUxpbmVTaXplW2hFbnZFbmNvZGVyLT5uQml0c3RyRGVsYXldPTA7CgogIC8qIFdoaWxlIGZpbGxpbmcgdGhlIERlbGF5IGxpbmVzLCBzYnJEYXRhIGlzIE5VTEwgKi8KICBpZiAoc2JyRGF0YSkgewogICAgKnNickRhdGFCaXRzID0gaFNickVsZW1lbnQtPnBheWxvYWREZWxheUxpbmVTaXplWzBdOwogICAgRkRLbWVtY3B5KHNickRhdGEsIGhTYnJFbGVtZW50LT5wYXlsb2FkRGVsYXlMaW5lWzBdLCAoaFNickVsZW1lbnQtPnBheWxvYWREZWxheUxpbmVTaXplWzBdKzcpPj4zKTsKCgogIH0KCgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8KCiAgaWYgKGhFbnZFbmNvZGVyLT5mVGltZURvbWFpbkRvd25zYW1wbGluZykKICB7CiAgICBpbnQgY2g7CiAgICBpbnQgbkNoYW5uZWxzID0gaFNickVsZW1lbnQtPnNickNvbmZpZ0RhdGEubkNoYW5uZWxzOwoKICAgIGZvciAoY2g9MDsgY2ggPCBuQ2hhbm5lbHM7IGNoKyspCiAgICB7CiAgICAgIElOVCBuT3V0U2FtcGxlczsKCiAgICAgIEZES2FhY0VuY19Eb3duc2FtcGxlKCZoU2JyRWxlbWVudC0+c2JyQ2hhbm5lbFtjaF0tPmRvd25TYW1wbGVyLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgc2FtcGxlcyArIGhTYnJFbGVtZW50LT5lbEluZm8uQ2hhbm5lbEluZGV4W2NoXSArIGhFbnZFbmNvZGVyLT5idWZmZXJPZmZzZXQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBoU2JyRWxlbWVudC0+c2JyQ29uZmlnRGF0YS5mcmFtZVNpemUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICB0aW1lSW5TdHJpZGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBzYW1wbGVzICsgaFNickVsZW1lbnQtPmVsSW5mby5DaGFubmVsSW5kZXhbY2hdLAogICAgICAgICAgICAgICAgICAgICAgICAgICAmbk91dFNhbXBsZXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBoRW52RW5jb2Rlci0+bkNoYW5uZWxzKTsKICAgIH0KICB9IC8qIGRvd25zYW1wbGUgKi8KCgogIHJldHVybiAoMCk7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgoKIGZ1bmN0aW9ubmFtZTogY3JlYXRlRW52Q2hhbm5lbAogZGVzY3JpcHRpb246ICBpbml0aWFsaXplcyBwYXJhbWV0ZXJzIGFuZCBhbGxvY2F0ZXMgbWVtb3J5CiByZXR1cm5zOiAgICAgIGVycm9yIHN0YXR1cwogaW5wdXQ6CiBvdXRwdXQ6ICAgICAgIGhFbnYKCioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwoKc3RhdGljIElOVApjcmVhdGVFbnZDaGFubmVsIChIQU5ETEVfRU5WX0NIQU5ORUwgICAgIGhFbnYsCiAgICAgICAgICAgICAgICAgIElOVCAgICAgICAgICAgICAgICAgICAgY2hhbm5lbAogICAgICAgICAgICAgICAgICxVQ0hBUiogICAgICAgICAgICAgICAgIGR5bmFtaWNfUkFNCiAgICAgICAgICAgICAgICAgKQp7CiAgRkRLbWVtY2xlYXIoaEVudixzaXplb2YgKHN0cnVjdCBFTlZfQ0hBTk5FTCkpOwoKICBpZiAoIEZES3NickVuY19DcmVhdGVUb25Db3JyUGFyYW1FeHRyKCZoRW52LT5Ub25Db3JyLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNoYW5uZWwpICkKICB7CiAgICByZXR1cm4oMSk7CiAgfQoKICBpZiAoIEZES3NickVuY19DcmVhdGVFeHRyYWN0U2JyRW52ZWxvcGUgKCZoRW52LT5zYnJFeHRyYWN0RW52ZWxvcGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBjaGFubmVsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICwvKmNoYW4qLzAKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgLGR5bmFtaWNfUkFNCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICkgKQogIHsKICAgIHJldHVybigxKTsKICB9CgogIHJldHVybiAwOwp9CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKCiBmdW5jdGlvbm5hbWU6IGluaXRFbnZDaGFubmVsCiBkZXNjcmlwdGlvbjogIGluaXRpYWxpemVzIHBhcmFtZXRlcnMKIHJldHVybnM6ICAgICAgZXJyb3Igc3RhdHVzCiBpbnB1dDoKIG91dHB1dDoKCioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSU5UCmluaXRFbnZDaGFubmVsICggIEhBTkRMRV9TQlJfQ09ORklHX0RBVEEgc2JyQ29uZmlnRGF0YSwKICAgICAgICAgICAgICAgICAgSEFORExFX1NCUl9IRUFERVJfREFUQSBzYnJIZWFkZXJEYXRhLAogICAgICAgICAgICAgICAgICBIQU5ETEVfRU5WX0NIQU5ORUwgICAgIGhFbnYsCiAgICAgICAgICAgICAgICAgIHNickNvbmZpZ3VyYXRpb25QdHIgICAgcGFyYW1zLAogICAgICAgICAgICAgICAgICBVTE9ORyAgICAgICAgICAgICAgICAgIHN0YXRlc0luaXRGbGFnCiAgICAgICAgICAgICAgICAgLElOVCAgICAgICAgICAgICAgICAgICAgY2hhbkluRWwKICAgICAgICAgICAgICAgICAsVUNIQVIqICAgICAgICAgICAgICAgICBkeW5hbWljX1JBTQogICAgICAgICAgICAgICAgICkKewogIGludCBmcmFtZVNoaWZ0LCB0cmFuX29mZj0wOwogIElOVCBlOwogIElOVCB0cmFuX2ZjOwogIElOVCB0aW1lU2xvdHMsIHRpbWVTdGVwLCBzdGFydEluZGV4OwogIElOVCBub2lzZUJhbmRzWzJdID0geyAzLCAzIH07CgogIGUgPSAxIDw8IHBhcmFtcy0+ZTsKCiAgRkRLX0FTU0VSVChwYXJhbXMtPmUgPj0gMCk7CgogIGhFbnYtPmVuY0VudkRhdGEuZnJlcV9yZXNfZml4Zml4ID0gMTsKICBoRW52LT5mTGV2ZWxQcm90ZWN0ID0gMDsKCiAgaEVudi0+ZW5jRW52RGF0YS5sZEdyaWQgPSAoc2JyQ29uZmlnRGF0YS0+c2JyU3ludGF4RmxhZ3MgJiBTQlJfU1lOVEFYX0xPV19ERUxBWSkgPyAxIDogMDsKCiAgaEVudi0+ZW5jRW52RGF0YS5zYnJfeHBvc19tb2RlID0gKFhQT1NfTU9ERSlwYXJhbXMtPnNicl94cG9zX21vZGU7CgogIGlmIChoRW52LT5lbmNFbnZEYXRhLnNicl94cG9zX21vZGUgPT0gWFBPU19TV0lUQ0hFRCkgewogICAgLyoKICAgICAgIG5vIG90aGVyIHR5cGUgdGhhbiBYUE9TX01EQ1Qgb3IgWFBPU19TUEVFQ0ggYWxsb3dlZCwKICAgICAgIGJ1dCBlbmFibGUgc3dpdGNoaW5nCiAgICAqLwogICAgc2JyQ29uZmlnRGF0YS0+c3dpdGNoVHJhbnNwb3NlcnMgPSBUUlVFOwogICAgaEVudi0+ZW5jRW52RGF0YS5zYnJfeHBvc19tb2RlID0gWFBPU19NRENUOwogIH0KICBlbHNlIHsKICAgIHNickNvbmZpZ0RhdGEtPnN3aXRjaFRyYW5zcG9zZXJzID0gRkFMU0U7CiAgfQoKICBoRW52LT5lbmNFbnZEYXRhLnNicl94cG9zX2N0cmwgPSBwYXJhbXMtPnNicl94cG9zX2N0cmw7CgoKICAvKiBleHRlbmRlZCBkYXRhICovCiAgaWYocGFyYW1zLT5wYXJhbWV0cmljQ29kaW5nKSB7CiAgICBoRW52LT5lbmNFbnZEYXRhLmV4dGVuZGVkX2RhdGEgPSAxOwogIH0KICBlbHNlIHsKICAgIGhFbnYtPmVuY0VudkRhdGEuZXh0ZW5kZWRfZGF0YSA9IDA7CiAgfQoKICBoRW52LT5lbmNFbnZEYXRhLmV4dGVuc2lvbl9zaXplID0gMDsKCiAgc3RhcnRJbmRleCA9IFFNRl9GSUxURVJfUFJPVE9UWVBFX1NJWkUgLSBzYnJDb25maWdEYXRhLT5ub1FtZkJhbmRzOwoKICBzd2l0Y2ggKHBhcmFtcy0+c2JyRnJhbWVTaXplKSB7CiAgY2FzZSAyMzA0OgogICAgdGltZVNsb3RzID0gMTg7CiAgICBicmVhazsKICBjYXNlIDIwNDg6CiAgY2FzZSAxMDI0OgogIGNhc2UgNTEyOgogICAgdGltZVNsb3RzID0gMTY7CiAgICBicmVhazsKICBjYXNlIDE5MjA6CiAgY2FzZSA5NjA6CiAgY2FzZSA0ODA6CiAgICB0aW1lU2xvdHMgPSAxNTsKICAgIGJyZWFrOwogIGNhc2UgMTE1MjoKICAgIHRpbWVTbG90cyA9IDk7CiAgICBicmVhazsKICBkZWZhdWx0OgogICAgcmV0dXJuICgxKTsgLyogSWxsZWdhbCBmcmFtZSBzaXplICovCiAgfQoKICB0aW1lU3RlcCA9IHNickNvbmZpZ0RhdGEtPm5vUW1mU2xvdHMgLyB0aW1lU2xvdHM7CgogIGlmICggRkRLc2JyRW5jX0luaXRUb25Db3JyUGFyYW1FeHRyKHBhcmFtcy0+c2JyRnJhbWVTaXplLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJmhFbnYtPlRvbkNvcnIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2JyQ29uZmlnRGF0YSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB0aW1lU2xvdHMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcGFyYW1zLT5zYnJfeHBvc19jdHJsLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHBhcmFtcy0+YW5hX21heF9sZXZlbCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzYnJIZWFkZXJEYXRhLT5zYnJfbm9pc2VfYmFuZHMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcGFyYW1zLT5ub2lzZUZsb29yT2Zmc2V0LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHBhcmFtcy0+dXNlU3BlZWNoQ29uZmlnKSApCiAgICByZXR1cm4oMSk7CgogIGhFbnYtPmVuY0VudkRhdGEubm9PZm5vaXNlYmFuZHMgPSBoRW52LT5Ub25Db3JyLnNick5vaXNlRmxvb3JFc3RpbWF0ZS5ub05vaXNlQmFuZHM7CgogIG5vaXNlQmFuZHNbMF0gPSBoRW52LT5lbmNFbnZEYXRhLm5vT2Zub2lzZWJhbmRzOwogIG5vaXNlQmFuZHNbMV0gPSBoRW52LT5lbmNFbnZEYXRhLm5vT2Zub2lzZWJhbmRzOwoKICBoRW52LT5lbmNFbnZEYXRhLnNicl9pbnZmX21vZGUgPSAoSU5WRl9NT0RFKXBhcmFtcy0+c2JyX2ludmZfbW9kZTsKCiAgaWYgKGhFbnYtPmVuY0VudkRhdGEuc2JyX2ludmZfbW9kZSA9PSBJTlZGX1NXSVRDSEVEKSB7CiAgICBoRW52LT5lbmNFbnZEYXRhLnNicl9pbnZmX21vZGUgPSBJTlZGX01JRF9MRVZFTDsKICAgIGhFbnYtPlRvbkNvcnIuc3dpdGNoSW52ZXJzZUZpbHQgPSBUUlVFOwogIH0KICBlbHNlIHsKICAgIGhFbnYtPlRvbkNvcnIuc3dpdGNoSW52ZXJzZUZpbHQgPSBGQUxTRTsKICB9CgoKICB0cmFuX2ZjICA9IHBhcmFtcy0+dHJhbl9mYzsKCiAgaWYgKHRyYW5fZmMgPT0gMCkgewogICAgdHJhbl9mYyA9IGZpeE1pbiAoNTAwMCwgRkRLc2JyRW5jX2dldFNiclN0YXJ0RnJlcVJBVyAoc2JySGVhZGVyRGF0YS0+c2JyX3N0YXJ0X2ZyZXF1ZW5jeSxwYXJhbXMtPmNvZGVjU2V0dGluZ3Muc2FtcGxlRnJlcSkpOwogIH0KCiAgdHJhbl9mYyA9ICh0cmFuX2ZjKjQqc2JyQ29uZmlnRGF0YS0+bm9RbWZCYW5kcy9zYnJDb25maWdEYXRhLT5zYW1wbGVGcmVxICsgMSk+PjE7CgogIGlmIChzYnJDb25maWdEYXRhLT5zYnJTeW50YXhGbGFncyAmIFNCUl9TWU5UQVhfTE9XX0RFTEFZKSB7CiAgICBmcmFtZVNoaWZ0ID0gTERfUFJFVFJBTl9PRkY7CiAgICB0cmFuX29mZiA9IExEX1BSRVRSQU5fT0ZGICsgRlJBTUVfTUlERExFX1NMT1RfNTEyTEQqdGltZVN0ZXA7CiAgfSBlbHNlCiAgewogICAgZnJhbWVTaGlmdCA9IDA7CiAgICBzd2l0Y2ggKHRpbWVTbG90cykgewogICAgICAvKiBUaGUgZmFjdG9yIG9mIDIgaXMgYnkgZGVmaW5pdGlvbi4gKi8KICAgICAgY2FzZSBOVU1CRVJfVElNRV9TTE9UU18yMDQ4OiB0cmFuX29mZiA9IDggKyBGUkFNRV9NSURETEVfU0xPVF8yMDQ4ICogdGltZVN0ZXA7IGJyZWFrOwogICAgICBjYXNlIE5VTUJFUl9USU1FX1NMT1RTXzE5MjA6IHRyYW5fb2ZmID0gNyArIEZSQU1FX01JRERMRV9TTE9UXzE5MjAgKiB0aW1lU3RlcDsgYnJlYWs7CiAgICAgIGRlZmF1bHQ6IHJldHVybiAxOwogICAgfQogIH0KICBpZiAoIEZES3NickVuY19Jbml0RXh0cmFjdFNickVudmVsb3BlICgmaEVudi0+c2JyRXh0cmFjdEVudmVsb3BlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2JyQ29uZmlnRGF0YS0+bm9RbWZTbG90cywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNickNvbmZpZ0RhdGEtPm5vUW1mQmFuZHMsIHN0YXJ0SW5kZXgsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB0aW1lU2xvdHMsIHRpbWVTdGVwLCB0cmFuX29mZiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHN0YXRlc0luaXRGbGFnCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICxjaGFuSW5FbAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAsZHluYW1pY19SQU0KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgLHNickNvbmZpZ0RhdGEtPnNiclN5bnRheEZsYWdzCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICApICkKICAgIHJldHVybigxKTsKCiAgaWYoRkRLc2JyRW5jX0luaXRTYnJDb2RlRW52ZWxvcGUgKCZoRW52LT5zYnJDb2RlRW52ZWxvcGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBzYnJDb25maWdEYXRhLT5uU2ZiLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgcGFyYW1zLT5kZWx0YVRBY3Jvc3NGcmFtZXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBwYXJhbXMtPmRGX2VkZ2VfMXN0RW52LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgcGFyYW1zLT5kRl9lZGdlX2luY3IpKQogICAgcmV0dXJuKDEpOwoKICBpZihGREtzYnJFbmNfSW5pdFNickNvZGVFbnZlbG9wZSAoJmhFbnYtPnNickNvZGVOb2lzZUZsb29yLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgbm9pc2VCYW5kcywKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHBhcmFtcy0+ZGVsdGFUQWNyb3NzRnJhbWVzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgMCwwKSkKICAgIHJldHVybigxKTsKCiAgc2JyQ29uZmlnRGF0YS0+aW5pdEFtcFJlc0ZGID0gcGFyYW1zLT5pbml0X2FtcF9yZXNfRkY7CgogIGlmKEZES3NickVuY19Jbml0U2JySHVmZm1hblRhYmxlcyAoJmhFbnYtPmVuY0VudkRhdGEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICZoRW52LT5zYnJDb2RlRW52ZWxvcGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICZoRW52LT5zYnJDb2RlTm9pc2VGbG9vciwKICAgICAgICAgICAgICAgICAgICAgICAgICAgc2JySGVhZGVyRGF0YS0+c2JyX2FtcF9yZXMpKQogICByZXR1cm4oMSk7CgogIEZES3NickVuY19pbml0RnJhbWVJbmZvR2VuZXJhdG9yICgmaEVudi0+U2JyRW52RnJhbWUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBwYXJhbXMtPnNwcmVhZCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBwYXJhbXMtPnN0YXQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICB0aW1lU2xvdHMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBoRW52LT5lbmNFbnZEYXRhLmZyZXFfcmVzX2ZpeGZpeAogICAgICAgICAgICAgICAgICAgICAgICAgICAgLGhFbnYtPmVuY0VudkRhdGEubGRHcmlkCiAgICAgICAgICAgICAgICAgICAgICAgICAgICApOwoKICBpZihGREtzYnJFbmNfSW5pdFNiclRyYW5zaWVudERldGVjdG9yICgmaEVudi0+c2JyVHJhbnNpZW50RGV0ZWN0b3IsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNickNvbmZpZ0RhdGEtPmZyYW1lU2l6ZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2JyQ29uZmlnRGF0YS0+c2FtcGxlRnJlcSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcGFyYW1zLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB0cmFuX2ZjLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzYnJDb25maWdEYXRhLT5ub1FtZlNsb3RzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzYnJDb25maWdEYXRhLT5ub1FtZkJhbmRzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBoRW52LT5zYnJFeHRyYWN0RW52ZWxvcGUuWUJ1ZmZlcldyaXRlT2Zmc2V0LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBoRW52LT5zYnJFeHRyYWN0RW52ZWxvcGUuWUJ1ZmZlclN6U2hpZnQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGZyYW1lU2hpZnQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHRyYW5fb2ZmCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICkpCiAgcmV0dXJuKDEpOwoKCiAgc2JyQ29uZmlnRGF0YS0+eHBvc0N0cmxTd2l0Y2ggPSBwYXJhbXMtPnNicl94cG9zX2N0cmw7CgogIGhFbnYtPmVuY0VudkRhdGEubm9IYXJtb25pY3MgPSBzYnJDb25maWdEYXRhLT5uU2ZiW0hJXTsKICBoRW52LT5lbmNFbnZEYXRhLmFkZEhhcm1vbmljRmxhZyA9IDA7CgogIHJldHVybiAoMCk7Cn0KCklOVCBzYnJFbmNvZGVyX09wZW4oCiAgICAgICAgSEFORExFX1NCUl9FTkNPREVSICAqcGhTYnJFbmNvZGVyLAogICAgICAgIElOVCAgICAgICAgICAgICAgICAgIG5FbGVtZW50cywKICAgICAgICBJTlQgICAgICAgICAgICAgICAgICBuQ2hhbm5lbHMsCiAgICAgICAgSU5UICAgICAgICAgICAgICAgICAgc3VwcG9ydFBTCiAgICAgICAgKQp7CiAgSU5UIGk7CiAgSU5UIGVycm9yU3RhdHVzID0gMTsKICBIQU5ETEVfU0JSX0VOQ09ERVIgaFNickVuY29kZXIgPSBOVUxMOwoKICBpZiAocGhTYnJFbmNvZGVyPT1OVUxMCiAgICAgKQogIHsKICAgIGdvdG8gYmFpbDsKICB9CgogIGhTYnJFbmNvZGVyID0gR2V0UmFtX1NickVuY29kZXIoKTsKICBpZiAoaFNickVuY29kZXI9PU5VTEwpIHsKICAgIGdvdG8gYmFpbDsKICB9CiAgRkRLbWVtY2xlYXIoaFNickVuY29kZXIsIHNpemVvZihTQlJfRU5DT0RFUikpOwoKICAgICAgaFNickVuY29kZXItPnBTQlJkeW5hbWljX1JBTSA9IChVQ0hBUiopR2V0UmFtX1NickR5bmFtaWNfUkFNKCk7CiAgICAgIGhTYnJFbmNvZGVyLT5keW5hbWljUmFtID0gaFNickVuY29kZXItPnBTQlJkeW5hbWljX1JBTTsKCiAgZm9yIChpPTA7IGk8bkVsZW1lbnRzOyBpKyspIHsKICAgIGhTYnJFbmNvZGVyLT5zYnJFbGVtZW50W2ldID0gR2V0UmFtX1NickVsZW1lbnQoaSk7CiAgICBpZiAoaFNickVuY29kZXItPnNickVsZW1lbnRbaV09PU5VTEwpIHsKICAgICAgICBnb3RvIGJhaWw7CiAgICB9CiAgICBGREttZW1jbGVhcihoU2JyRW5jb2Rlci0+c2JyRWxlbWVudFtpXSwgc2l6ZW9mKFNCUl9FTEVNRU5UKSk7CiAgICBoU2JyRW5jb2Rlci0+c2JyRWxlbWVudFtpXS0+c2JyQ29uZmlnRGF0YS5mcmVxQmFuZFRhYmxlW0xPXSA9ICBHZXRSYW1fU2JyX2ZyZXFCYW5kVGFibGVMTyhpKTsKICAgIGhTYnJFbmNvZGVyLT5zYnJFbGVtZW50W2ldLT5zYnJDb25maWdEYXRhLmZyZXFCYW5kVGFibGVbSEldID0gIEdldFJhbV9TYnJfZnJlcUJhbmRUYWJsZUhJKGkpOwogICAgaFNickVuY29kZXItPnNickVsZW1lbnRbaV0tPnNickNvbmZpZ0RhdGEudl9rX21hc3RlciAgICAgICAgPSAgR2V0UmFtX1Nicl92X2tfbWFzdGVyKGkpOwogICAgaWYgKCAoaFNickVuY29kZXItPnNickVsZW1lbnRbaV0tPnNickNvbmZpZ0RhdGEuZnJlcUJhbmRUYWJsZVtMT109PU5VTEwpIHx8CiAgICAgICAgIChoU2JyRW5jb2Rlci0+c2JyRWxlbWVudFtpXS0+c2JyQ29uZmlnRGF0YS5mcmVxQmFuZFRhYmxlW0hJXT09TlVMTCkgfHwKICAgICAgICAgKGhTYnJFbmNvZGVyLT5zYnJFbGVtZW50W2ldLT5zYnJDb25maWdEYXRhLnZfa19tYXN0ZXI9PU5VTEwpICkKICAgIHsKICAgICAgICBnb3RvIGJhaWw7CiAgICB9CiAgfQoKICBmb3IgKGk9MDsgaTxuQ2hhbm5lbHM7IGkrKykgewogICAgaFNickVuY29kZXItPnBTYnJDaGFubmVsW2ldID0gR2V0UmFtX1NickNoYW5uZWwoaSk7CiAgICBpZiAoaFNickVuY29kZXItPnBTYnJDaGFubmVsW2ldPT1OVUxMKSB7CiAgICAgICAgZ290byBiYWlsOwogICAgfQoKICAgIGlmICggY3JlYXRlRW52Q2hhbm5lbCgmaFNickVuY29kZXItPnBTYnJDaGFubmVsW2ldLT5oRW52Q2hhbm5lbCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgaQogICAgICAgICAgICAgICAgICAgICAgICAgICxoU2JyRW5jb2Rlci0+ZHluYW1pY1JhbQogICAgICAgICAgICAgICAgICAgICAgICAgICApICkKICAgIHsKICAgICAgICBnb3RvIGJhaWw7CiAgICB9CgogIH0KCiAgZm9yIChpPTA7IGk8Zml4TWF4KG5DaGFubmVscywoc3VwcG9ydFBTKT8yOjApOyBpKyspIHsKICAgIGhTYnJFbmNvZGVyLT5RbWZBbmFseXNpc1tpXS5GaWx0ZXJTdGF0ZXMgPSBHZXRSYW1fU2JyX1FtZlN0YXRlc0FuYWx5c2lzKGkpOwogICAgaWYgKGhTYnJFbmNvZGVyLT5RbWZBbmFseXNpc1tpXS5GaWx0ZXJTdGF0ZXM9PU5VTEwpIHsKICAgICAgICBnb3RvIGJhaWw7CiAgICB9CiAgfQoKICBpZiAoc3VwcG9ydFBTKSB7CiAgICBpZiAoUFNFbmNfQ3JlYXRlKCZoU2JyRW5jb2Rlci0+aFBhcmFtZXRyaWNTdGVyZW8pKQogICAgewogICAgICBnb3RvIGJhaWw7CiAgICB9CgogICAgaFNickVuY29kZXItPnFtZlN5bnRoZXNpc1BTLkZpbHRlclN0YXRlcyA9IEdldFJhbV9Qc1FtZlN0YXRlc1N5bnRoZXNpcygpOwogICAgaWYgKGhTYnJFbmNvZGVyLT5xbWZTeW50aGVzaXNQUy5GaWx0ZXJTdGF0ZXM9PU5VTEwpIHsKICAgICAgZ290byBiYWlsOwogICAgfQogIH0gIC8qIHN1cHBvcnRQUyAqLwoKICAqcGhTYnJFbmNvZGVyID0gaFNickVuY29kZXI7CgogIGVycm9yU3RhdHVzID0gMDsKICByZXR1cm4gZXJyb3JTdGF0dXM7CgpiYWlsOgogIC8qIENsb3NlIFNCUiBlbmNvZGVyIGluc3RhbmNlICovCiAgc2JyRW5jb2Rlcl9DbG9zZSgmaFNickVuY29kZXIpOwogIHJldHVybiBlcnJvclN0YXR1czsKfQoKc3RhdGljCklOVCBGREtzYnJFbmNfUmVhbGxvY2F0ZSgKICAgICAgICAgICAgICAgICAgICBIQU5ETEVfU0JSX0VOQ09ERVIgICBoU2JyRW5jb2RlciwKICAgICAgICAgICAgICAgICAgICBTQlJfRUxFTUVOVF9JTkZPICAgICBlbEluZm9bKDgpXSwKICAgICAgICAgICAgICAgICAgICBjb25zdCBJTlQgICAgICAgICAgICBub0VsZW1lbnRzKQp7CiAgSU5UIHRvdGFsQ2ggPSAwOwogIElOVCB0b3RhbFFtZiA9IDA7CiAgSU5UIGNvcmVFbDsKICBJTlQgZWw9LTE7CgogIGhTYnJFbmNvZGVyLT5sZmVDaElkeCA9IC0xOyAvKiBkZWZhdWx0IHZhbHVlLCB1bnRpbCBsZmUgZm91bmQgKi8KCiAgZm9yIChjb3JlRWw9MDsgY29yZUVsPG5vRWxlbWVudHM7IGNvcmVFbCsrKQogIHsKICAgIC8qIFNCUiBvbmx5IGhhbmRsZXMgU0NFIGFuZCBDUEUncyAqLwogICAgaWYgKGVsSW5mb1tjb3JlRWxdLmVsVHlwZSA9PSBJRF9TQ0UgfHwgZWxJbmZvW2NvcmVFbF0uZWxUeXBlID09IElEX0NQRSkgewogICAgICBlbCsrOwogICAgfSBlbHNlIHsKICAgICAgaWYgKGVsSW5mb1tjb3JlRWxdLmVsVHlwZSA9PSBJRF9MRkUpIHsKICAgICAgICAgIGhTYnJFbmNvZGVyLT5sZmVDaElkeCA9IGVsSW5mb1tjb3JlRWxdLkNoYW5uZWxJbmRleFswXTsKICAgICAgfQogICAgICBjb250aW51ZTsKICAgIH0KCiAgICBTQlJfRUxFTUVOVF9JTkZPICAgICpwZWxJbmZvID0gJmVsSW5mb1tjb3JlRWxdOwogICAgSEFORExFX1NCUl9FTEVNRU5UICBoU2JyRWxlbWVudCA9IGhTYnJFbmNvZGVyLT5zYnJFbGVtZW50W2VsXTsKCiAgICBpbnQgY2g7CiAgICBmb3IgKCBjaCA9IDA7IGNoIDwgcGVsSW5mby0+bkNoYW5uZWxzSW5FbDsgY2grKyApIHsKICAgICAgaFNickVsZW1lbnQtPnNickNoYW5uZWxbY2hdID0gaFNickVuY29kZXItPnBTYnJDaGFubmVsW3RvdGFsQ2hdOwogICAgICB0b3RhbENoKys7CiAgICB9CiAgICAvKiBhbmFseXNpcyBRTUYgKi8KICAgIGZvciAoIGNoID0gMDsgY2ggPCAoKHBlbEluZm8tPmZQYXJhbWV0cmljU3RlcmVvKT8yOnBlbEluZm8tPm5DaGFubmVsc0luRWwpOyBjaCsrICkgewogICAgICBoU2JyRWxlbWVudC0+ZWxJbmZvLkNoYW5uZWxJbmRleFtjaF0gPSBwZWxJbmZvLT5DaGFubmVsSW5kZXhbY2hdOwogICAgICBoU2JyRWxlbWVudC0+aFFtZkFuYWx5c2lzW2NoXSA9ICZoU2JyRW5jb2Rlci0+UW1mQW5hbHlzaXNbdG90YWxRbWYrK107CiAgICB9CgogICAgLyogQ29weSBFbGVtZW50IGluZm8gKi8KICAgIGhTYnJFbGVtZW50LT5lbEluZm8uZWxUeXBlICAgICAgICAgICAgPSBwZWxJbmZvLT5lbFR5cGU7CiAgICBoU2JyRWxlbWVudC0+ZWxJbmZvLmluc3RhbmNlVGFnICAgICAgID0gcGVsSW5mby0+aW5zdGFuY2VUYWc7CiAgICBoU2JyRWxlbWVudC0+ZWxJbmZvLm5DaGFubmVsc0luRWwgICAgID0gcGVsSW5mby0+bkNoYW5uZWxzSW5FbDsKICAgIGhTYnJFbGVtZW50LT5lbEluZm8uZlBhcmFtZXRyaWNTdGVyZW8gPSBwZWxJbmZvLT5mUGFyYW1ldHJpY1N0ZXJlbzsKICB9IC8qIGNvcmVFbCAqLwoKICByZXR1cm4gMDsKfQoKCgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKCiBmdW5jdGlvbm5hbWU6IEZES3NickVuY19FbnZJbml0CiBkZXNjcmlwdGlvbjogIGluaXRpYWxpemVzIHBhcmFtZXRlcnMKIHJldHVybnM6ICAgICAgZXJyb3Igc3RhdHVzCiBpbnB1dDoKIG91dHB1dDogICAgICAgaEVudgoKKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYwpJTlQgRkRLc2JyRW5jX0VudkluaXQgKAogICAgICAgICAgICAgICAgICAgICAgIEhBTkRMRV9TQlJfRUxFTUVOVCAgIGhTYnJFbGVtZW50LAogICAgICAgICAgICAgICAgICAgICAgIHNickNvbmZpZ3VyYXRpb25QdHIgcGFyYW1zLAogICAgICAgICAgICAgICAgICAgICAgIElOVCAgICAgICpjb3JlQmFuZFdpdGgsCiAgICAgICAgICAgICAgICAgICAgICAgQVVESU9fT0JKRUNUX1RZUEUgYW90LAogICAgICAgICAgICAgICAgICAgICAgIGludCAgICAgICBuQml0c3RyRGVsYXksCiAgICAgICAgICAgICAgICAgICAgICAgaW50ICAgICAgIG5FbGVtZW50LAogICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IGludCBoZWFkZXJQZXJpb2QsCiAgICAgICAgICAgICAgICAgICAgICAgVUxPTkcgICAgIHN0YXRlc0luaXRGbGFnLAogICAgICAgICAgICAgICAgICAgICAgIGludCAgICAgICBmVGltZURvbWFpbkRvd25zYW1wbGluZwogICAgICAgICAgICAgICAgICAgICAgLFVDSEFSICAgICpkeW5hbWljX1JBTQogICAgICAgICAgICAgICAgICAgICAgKQp7CiAgVUNIQVIgICAgKmJpdHN0cmVhbUJ1ZmZlcjsKICBpbnQgY2gsIGk7CgogIGlmICgocGFyYW1zLT5jb2RlY1NldHRpbmdzLm5DaGFubmVscyA8IDEpIHx8IChwYXJhbXMtPmNvZGVjU2V0dGluZ3MubkNoYW5uZWxzID4gTUFYX05VTV9DSEFOTkVMUykpewogICAgcmV0dXJuKDEpOwogIH0KCiAgLyogaW5pdGlhbGl6ZSB0aGUgZW5jb2RlciBoYW5kbGUgIGFuZCBzdHJ1Y3RzKi8KICBiaXRzdHJlYW1CdWZmZXIgPSBoU2JyRWxlbWVudC0+cGF5bG9hZERlbGF5TGluZVtuQml0c3RyRGVsYXldOwoKICAvKiBpbml0IGFuZCBzZXQgc3ludGF4IGZsYWdzICovCiAgaFNickVsZW1lbnQtPnNickNvbmZpZ0RhdGEuc2JyU3ludGF4RmxhZ3MgPSAwOwoKICBzd2l0Y2ggKGFvdCkgewogIGNhc2UgQU9UX0RSTV9NUEVHX1BTOgogIGNhc2UgQU9UX0RSTV9TQlI6CiAgICBoU2JyRWxlbWVudC0+c2JyQ29uZmlnRGF0YS5zYnJTeW50YXhGbGFncyB8PSBTQlJfU1lOVEFYX1NDQUxBQkxFOwogICAgaFNickVsZW1lbnQtPnNickNvbmZpZ0RhdGEuc2JyU3ludGF4RmxhZ3MgfD0gU0JSX1NZTlRBWF9EUk1fQ1JDOwogICAgaFNickVsZW1lbnQtPnNickNvbmZpZ0RhdGEuc2JyU3ludGF4RmxhZ3MgfD0gU0JSX1NZTlRBWF9DUkM7CiAgICBicmVhazsKICBjYXNlIEFPVF9FUl9BQUNfRUxEOgogICAgaFNickVsZW1lbnQtPnNickNvbmZpZ0RhdGEuc2JyU3ludGF4RmxhZ3MgfD0gU0JSX1NZTlRBWF9MT1dfREVMQVk7CiAgICBicmVhazsKICBkZWZhdWx0OgogICAgYnJlYWs7CiAgfQogIGlmIChwYXJhbXMtPmNyY1NicikgewogICAgaFNickVsZW1lbnQtPnNickNvbmZpZ0RhdGEuc2JyU3ludGF4RmxhZ3MgfD0gU0JSX1NZTlRBWF9DUkM7CiAgfQoKICBoU2JyRWxlbWVudC0+c2JyQ29uZmlnRGF0YS5ub1FtZkJhbmRzID0gUU1GX0NIQU5ORUxTPj4oMi1wYXJhbXMtPmRvd25TYW1wbGVGYWN0b3IpOwogIHN3aXRjaCAoaFNickVsZW1lbnQtPnNickNvbmZpZ0RhdGEubm9RbWZCYW5kcykKICB7CiAgICBjYXNlIDY0OiBoU2JyRWxlbWVudC0+c2JyQ29uZmlnRGF0YS5ub1FtZlNsb3RzID0gcGFyYW1zLT5zYnJGcmFtZVNpemU+PjY7CiAgICAgICAgICAgICBicmVhazsKICAgIGNhc2UgMzI6IGhTYnJFbGVtZW50LT5zYnJDb25maWdEYXRhLm5vUW1mU2xvdHMgPSBwYXJhbXMtPnNickZyYW1lU2l6ZT4+NTsKICAgICAgICAgICAgIGJyZWFrOwogICAgZGVmYXVsdDogaFNickVsZW1lbnQtPnNickNvbmZpZ0RhdGEubm9RbWZTbG90cyA9IHBhcmFtcy0+c2JyRnJhbWVTaXplPj42OwogICAgICAgICAgICAgcmV0dXJuKDIpOwogIH0KCiAgRkRLaW5pdEJpdFN0cmVhbSgmaFNickVsZW1lbnQtPkNtb25EYXRhLnNickJpdGJ1ZiwgYml0c3RyZWFtQnVmZmVyLCBNQVhfUEFZTE9BRF9TSVpFKnNpemVvZihVQ0hBUiksIDAsIEJTX1dSSVRFUik7CgogIC8qCiAgICBub3cgaW5pdGlhbGl6ZSBzYnJDb25maWdEYXRhLCBzYnJIZWFkZXJEYXRhIGFuZCBzYnJCaXRzdHJlYW1EYXRhLAogICovCiAgaFNickVsZW1lbnQtPnNickNvbmZpZ0RhdGEubkNoYW5uZWxzID0gcGFyYW1zLT5jb2RlY1NldHRpbmdzLm5DaGFubmVsczsKCiAgaWYocGFyYW1zLT5jb2RlY1NldHRpbmdzLm5DaGFubmVscyA9PSAyKQogICAgIGhTYnJFbGVtZW50LT5zYnJDb25maWdEYXRhLnN0ZXJlb01vZGUgPSBwYXJhbXMtPnN0ZXJlb01vZGU7CiAgZWxzZQogICAgIGhTYnJFbGVtZW50LT5zYnJDb25maWdEYXRhLnN0ZXJlb01vZGUgPSBTQlJfTU9OTzsKCiAgaFNickVsZW1lbnQtPnNickNvbmZpZ0RhdGEuZnJhbWVTaXplICAgPSBwYXJhbXMtPnNickZyYW1lU2l6ZTsKCiAgaFNickVsZW1lbnQtPnNickNvbmZpZ0RhdGEuc2FtcGxlRnJlcSA9IHBhcmFtcy0+ZG93blNhbXBsZUZhY3RvciAqIHBhcmFtcy0+Y29kZWNTZXR0aW5ncy5zYW1wbGVGcmVxOwoKICBoU2JyRWxlbWVudC0+c2JyQml0c3RyZWFtRGF0YS5Db3VudFNlbmRIZWFkZXJEYXRhID0gMDsKICBpZiAocGFyYW1zLT5TZW5kSGVhZGVyRGF0YVRpbWUgPiAwICkgewoKICAgIGlmIChoZWFkZXJQZXJpb2Q9PS0xKSB7CgogICAgICBoU2JyRWxlbWVudC0+c2JyQml0c3RyZWFtRGF0YS5OclNlbmRIZWFkZXJEYXRhID0gKElOVCkocGFyYW1zLT5TZW5kSGVhZGVyRGF0YVRpbWUgKiBoU2JyRWxlbWVudC0+c2JyQ29uZmlnRGF0YS5zYW1wbGVGcmVxCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgLyAoMTAwMCAqIGhTYnJFbGVtZW50LT5zYnJDb25maWdEYXRhLmZyYW1lU2l6ZSkpOwogICAgICBoU2JyRWxlbWVudC0+c2JyQml0c3RyZWFtRGF0YS5OclNlbmRIZWFkZXJEYXRhID0gZml4TWF4KGhTYnJFbGVtZW50LT5zYnJCaXRzdHJlYW1EYXRhLk5yU2VuZEhlYWRlckRhdGEsMSk7CiAgICB9CiAgICBlbHNlIHsKICAgICAgLyogYXNzdXJlIGhlYWRlciBwZXJpb2QgYXQgbGVhc3Qgb25jZSBwZXIgc2Vjb25kICovCiAgICAgIGhTYnJFbGVtZW50LT5zYnJCaXRzdHJlYW1EYXRhLk5yU2VuZEhlYWRlckRhdGEgPSBmaXhNaW4oZml4TWF4KGhlYWRlclBlcmlvZCwxKSwoaFNickVsZW1lbnQtPnNickNvbmZpZ0RhdGEuc2FtcGxlRnJlcS9oU2JyRWxlbWVudC0+c2JyQ29uZmlnRGF0YS5mcmFtZVNpemUpKTsKICAgIH0KICB9CiAgZWxzZSB7CiAgIGhTYnJFbGVtZW50LT5zYnJCaXRzdHJlYW1EYXRhLk5yU2VuZEhlYWRlckRhdGEgPSAwOwogIH0KCiAgaFNickVsZW1lbnQtPnNickhlYWRlckRhdGEuc2JyX2RhdGFfZXh0cmEgPSBwYXJhbXMtPnNicl9kYXRhX2V4dHJhOwogIGhTYnJFbGVtZW50LT5zYnJCaXRzdHJlYW1EYXRhLkhlYWRlckFjdGl2ZSA9IDA7CiAgaFNickVsZW1lbnQtPnNickhlYWRlckRhdGEuc2JyX3N0YXJ0X2ZyZXF1ZW5jeSA9IHBhcmFtcy0+c3RhcnRGcmVxOwogIGhTYnJFbGVtZW50LT5zYnJIZWFkZXJEYXRhLnNicl9zdG9wX2ZyZXF1ZW5jeSAgPSBwYXJhbXMtPnN0b3BGcmVxOwogIGhTYnJFbGVtZW50LT5zYnJIZWFkZXJEYXRhLnNicl94b3Zlcl9iYW5kID0gMDsKICBoU2JyRWxlbWVudC0+c2JySGVhZGVyRGF0YS5zYnJfbGNfc3RlcmVvX21vZGUgPSAwOwoKICAvKiBkYXRhX2V4dHJhICovCiAgaWYgKHBhcmFtcy0+c2JyX3hwb3NfY3RybCE9IFNCUl9YUE9TX0NUUkxfREVGQVVMVCkKICAgICBoU2JyRWxlbWVudC0+c2JySGVhZGVyRGF0YS5zYnJfZGF0YV9leHRyYSA9IDE7CgogIGhTYnJFbGVtZW50LT5zYnJIZWFkZXJEYXRhLnNicl9hbXBfcmVzID0gKEFNUF9SRVMpcGFyYW1zLT5hbXBfcmVzOwoKICAvKiBoZWFkZXJfZXh0cmFfMSAqLwogIGhTYnJFbGVtZW50LT5zYnJIZWFkZXJEYXRhLmZyZXFTY2FsZSAgPSBwYXJhbXMtPmZyZXFTY2FsZTsKICBoU2JyRWxlbWVudC0+c2JySGVhZGVyRGF0YS5hbHRlclNjYWxlID0gcGFyYW1zLT5hbHRlclNjYWxlOwogIGhTYnJFbGVtZW50LT5zYnJIZWFkZXJEYXRhLnNicl9ub2lzZV9iYW5kcyA9IHBhcmFtcy0+c2JyX25vaXNlX2JhbmRzOwogIGhTYnJFbGVtZW50LT5zYnJIZWFkZXJEYXRhLmhlYWRlcl9leHRyYV8xID0gMDsKCiAgaWYgKChwYXJhbXMtPmZyZXFTY2FsZSAhPSBTQlJfRlJFUV9TQ0FMRV9ERUZBVUxUKSB8fAogICAgICAocGFyYW1zLT5hbHRlclNjYWxlICE9IFNCUl9BTFRFUl9TQ0FMRV9ERUZBVUxUKSB8fAogICAgICAocGFyYW1zLT5zYnJfbm9pc2VfYmFuZHMgIT0gU0JSX05PSVNFX0JBTkRTX0RFRkFVTFQpKQogIHsKICAgaFNickVsZW1lbnQtPnNickhlYWRlckRhdGEuaGVhZGVyX2V4dHJhXzEgPSAxOwogIH0KCiAgLyogaGVhZGVyX2V4dHJhXzIgKi8KICBoU2JyRWxlbWVudC0+c2JySGVhZGVyRGF0YS5zYnJfbGltaXRlcl9iYW5kcyA9IHBhcmFtcy0+c2JyX2xpbWl0ZXJfYmFuZHM7CiAgaFNickVsZW1lbnQtPnNickhlYWRlckRhdGEuc2JyX2xpbWl0ZXJfZ2FpbnMgPSBwYXJhbXMtPnNicl9saW1pdGVyX2dhaW5zOwoKICBpZiAoKGhTYnJFbGVtZW50LT5zYnJDb25maWdEYXRhLnNhbXBsZUZyZXEgPiA0ODAwMCkgJiYKICAgICAgKGhTYnJFbGVtZW50LT5zYnJIZWFkZXJEYXRhLnNicl9zdGFydF9mcmVxdWVuY3kgPj0gOSkpCiAgewogICAgaFNickVsZW1lbnQtPnNickhlYWRlckRhdGEuc2JyX2xpbWl0ZXJfZ2FpbnMgPSBTQlJfTElNSVRFUl9HQUlOU19JTkZJTklURTsKICB9CgogIGhTYnJFbGVtZW50LT5zYnJIZWFkZXJEYXRhLnNicl9pbnRlcnBvbF9mcmVxID0gcGFyYW1zLT5zYnJfaW50ZXJwb2xfZnJlcTsKICBoU2JyRWxlbWVudC0+c2JySGVhZGVyRGF0YS5zYnJfc21vb3RoaW5nX2xlbmd0aCA9IHBhcmFtcy0+c2JyX3Ntb290aGluZ19sZW5ndGg7CiAgaFNickVsZW1lbnQtPnNickhlYWRlckRhdGEuaGVhZGVyX2V4dHJhXzIgPSAwOwoKICBpZiAoKHBhcmFtcy0+c2JyX2xpbWl0ZXJfYmFuZHMgIT0gU0JSX0xJTUlURVJfQkFORFNfREVGQVVMVCkgfHwKICAgICAgKHBhcmFtcy0+c2JyX2xpbWl0ZXJfZ2FpbnMgIT0gU0JSX0xJTUlURVJfR0FJTlNfREVGQVVMVCkgfHwKICAgICAgKHBhcmFtcy0+c2JyX2ludGVycG9sX2ZyZXEgIT0gU0JSX0lOVEVSUE9MX0ZSRVFfREVGQVVMVCkgfHwKICAgICAgKHBhcmFtcy0+c2JyX3Ntb290aGluZ19sZW5ndGggIT0gU0JSX1NNT09USElOR19MRU5HVEhfREVGQVVMVCkpCiAgewogICAgIGhTYnJFbGVtZW50LT5zYnJIZWFkZXJEYXRhLmhlYWRlcl9leHRyYV8yID0gMTsKICB9CgogICAvKiBvdGhlciBzd2l0Y2hlcyAqLwogIGhTYnJFbGVtZW50LT5zYnJDb25maWdEYXRhLnVzZVdhdmVDb2RpbmcgICAgICAgICAgICAgPSBwYXJhbXMtPnVzZVdhdmVDb2Rpbmc7CiAgaFNickVsZW1lbnQtPnNickNvbmZpZ0RhdGEudXNlUGFyYW1ldHJpY0NvZGluZyAgICAgICA9IHBhcmFtcy0+cGFyYW1ldHJpY0NvZGluZzsKCiAgLyogaW5pdCBmcmVxIGJhbmQgdGFibGUgKi8KICBpZih1cGRhdGVGcmVxQmFuZFRhYmxlKCZoU2JyRWxlbWVudC0+c2JyQ29uZmlnRGF0YSwKICAgICAgICAgICAgICAgICAgICAgICAgICZoU2JyRWxlbWVudC0+c2JySGVhZGVyRGF0YSwKICAgICAgICAgICAgICAgICAgICAgICAgIHBhcmFtcy0+ZG93blNhbXBsZUZhY3RvcgogICAgICAgICAgICAgICAgICAgICAgICAgKSkKICB7CiAgICByZXR1cm4oMSk7CiAgfQoKICAvKiBub3cgY3JlYXRlIGVudmVsb3BlIGV4dCBhbmQgUU1GIGZvciBlYWNoIGF2YWlsYWJsZSBjaGFubmVsICovCiAgZm9yICggY2ggPSAwOyBjaCA8IGhTYnJFbGVtZW50LT5zYnJDb25maWdEYXRhLm5DaGFubmVsczsgY2grKyApIHsKCiAgICAgaWYgKCBpbml0RW52Q2hhbm5lbCgmaFNickVsZW1lbnQtPnNickNvbmZpZ0RhdGEsCiAgICAgICAgICAgICAgICAgICAgICAgICAmaFNickVsZW1lbnQtPnNickhlYWRlckRhdGEsCiAgICAgICAgICAgICAgICAgICAgICAgICAmaFNickVsZW1lbnQtPnNickNoYW5uZWxbY2hdLT5oRW52Q2hhbm5lbCwKICAgICAgICAgICAgICAgICAgICAgICAgICBwYXJhbXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgc3RhdGVzSW5pdEZsYWcKICAgICAgICAgICAgICAgICAgICAgICAgLGNoCiAgICAgICAgICAgICAgICAgICAgICAgICxkeW5hbWljX1JBTQogICAgICAgICAgICAgICAgICAgICAgICAgKSApCiAgICAgewogICAgICAgcmV0dXJuKDEpOwogICAgIH0KCgogIH0gLyogbkNoYW5uZWxzICovCgogIC8qIHJlc2V0IGFuZCBpbnRpYWxpemUgYW5hbHlzaXMgcW1mICovCiAgZm9yICggY2ggPSAwOyBjaCA8ICgoaFNickVsZW1lbnQtPmVsSW5mby5mUGFyYW1ldHJpY1N0ZXJlbyk/MjpoU2JyRWxlbWVudC0+c2JyQ29uZmlnRGF0YS5uQ2hhbm5lbHMpOyBjaCsrICkKICB7CiAgICBpbnQgZXJyOwogICAgVUlOVCBxbWZGbGFncyA9IChoU2JyRWxlbWVudC0+c2JyQ29uZmlnRGF0YS5zYnJTeW50YXhGbGFncyAmIFNCUl9TWU5UQVhfTE9XX0RFTEFZKSA/IFFNRl9GTEFHX0NMREZCIDogMDsKICAgIGlmIChzdGF0ZXNJbml0RmxhZykKICAgICAgcW1mRmxhZ3MgJj0gflFNRl9GTEFHX0tFRVBfU1RBVEVTOwogICAgZWxzZQogICAgICBxbWZGbGFncyB8PSAgUU1GX0ZMQUdfS0VFUF9TVEFURVM7CgogICAgZXJyID0gcW1mSW5pdEFuYWx5c2lzRmlsdGVyQmFuayggaFNickVsZW1lbnQtPmhRbWZBbmFseXNpc1tjaF0sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAoRklYUF9RQVMqKWhTYnJFbGVtZW50LT5oUW1mQW5hbHlzaXNbY2hdLT5GaWx0ZXJTdGF0ZXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBoU2JyRWxlbWVudC0+c2JyQ29uZmlnRGF0YS5ub1FtZlNsb3RzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaFNickVsZW1lbnQtPnNickNvbmZpZ0RhdGEubm9RbWZCYW5kcywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGhTYnJFbGVtZW50LT5zYnJDb25maWdEYXRhLm5vUW1mQmFuZHMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBoU2JyRWxlbWVudC0+c2JyQ29uZmlnRGF0YS5ub1FtZkJhbmRzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcW1mRmxhZ3MgKTsKICAgIGlmICgwIT1lcnIpIHsKICAgICAgcmV0dXJuIGVycjsKICAgIH0KICB9CgogIC8qICAqLwogIGhTYnJFbGVtZW50LT5DbW9uRGF0YS54T3ZlckZyZXEgPSBoU2JyRWxlbWVudC0+c2JyQ29uZmlnRGF0YS54T3ZlckZyZXE7CiAgaFNickVsZW1lbnQtPkNtb25EYXRhLmR5bkJ3RW5hYmxlZCA9IChwYXJhbXMtPmR5bkJ3U3VwcG9ydGVkICYmIHBhcmFtcy0+ZHluQndFbmFibGVkKTsKICBoU2JyRWxlbWVudC0+Q21vbkRhdGEuZHluWE92ZXJGcmVxRW5jID0gRkRLc2JyRW5jX1NickdldFhPdmVyRnJlcSggaFNickVsZW1lbnQsIGhTYnJFbGVtZW50LT5DbW9uRGF0YS54T3ZlckZyZXEpOwogIGZvciAoIGkgPSAwOyBpIDwgNTsgaSsrICkKICAgICAgaFNickVsZW1lbnQtPmR5blhPdmVyRnJlcURlbGF5W2ldID0gaFNickVsZW1lbnQtPkNtb25EYXRhLmR5blhPdmVyRnJlcUVuYzsKICBoU2JyRWxlbWVudC0+Q21vbkRhdGEuc2JyTnVtQ2hhbm5lbHMgID0gaFNickVsZW1lbnQtPnNickNvbmZpZ0RhdGEubkNoYW5uZWxzOwogIGhTYnJFbGVtZW50LT5zYnJDb25maWdEYXRhLmR5blhPdmVyRnJlcSA9IGhTYnJFbGVtZW50LT5DbW9uRGF0YS54T3ZlckZyZXE7CgogIC8qIFVwZGF0ZSBCYW5kd2l0aCB0byBiZSBwYXNzZWQgdG8gdGhlIGNvcmUgZW5jb2RlciAqLwogICpjb3JlQmFuZFdpdGggPSBoU2JyRWxlbWVudC0+Q21vbkRhdGEueE92ZXJGcmVxOwoKICByZXR1cm4oMCk7CiB9CgpJTlQgc2JyRW5jb2Rlcl9HZXRJbkJ1ZmZlclNpemUoaW50IG5vQ2hhbm5lbHMpCnsKICBJTlQgdGVtcDsKCiAgdGVtcCA9ICgyMDQ4KTsKICB0ZW1wICs9IDEwMjQgKyBNQVhfU0FNUExFX0RFTEFZOwogIHRlbXAgKj0gbm9DaGFubmVsczsKICB0ZW1wICo9IHNpemVvZihJTlRfUENNKTsKICByZXR1cm4gdGVtcDsKfQoKLyoKICogRW5jb2RlIER1bW15IFNCUiBwYXlsb2FkIGZyYW1lcyB0byBmaWxsIHRoZSBkZWxheSBsaW5lcy4KICovCnN0YXRpYwpJTlQgRkRLc2JyRW5jX0RlbGF5Q29tcGVuc2F0aW9uICgKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEhBTkRMRV9TQlJfRU5DT0RFUiBoRW52RW5jLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgSU5UX1BDTSAqdGltZUJ1ZmZlcgogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICApCnsKICAgIGludCBuLCBlbDsKCiAgICBmb3IgKG49aEVudkVuYy0+bkJpdHN0ckRlbGF5OyBuPjA7IG4tLSkKICAgIHsKICAgICAgZm9yIChlbD0wOyBlbDxoRW52RW5jLT5ub0VsZW1lbnRzOyBlbCsrKQogICAgICB7CiAgICAgICAgaWYgKEZES3NickVuY19FbnZFbmNvZGVGcmFtZSgKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGhFbnZFbmMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBlbCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHRpbWVCdWZmZXIgKyBoRW52RW5jLT5kb3duc2FtcGxlZE9mZnNldCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGhFbnZFbmMtPnNickVsZW1lbnRbZWxdLT5zYnJDb25maWdEYXRhLm5DaGFubmVscywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIE5VTEwsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBOVUxMLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgMQogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICApKQogICAgICAgICAgcmV0dXJuIC0xOwogICAgICB9CiAgICAgIHNickVuY29kZXJfVXBkYXRlQnVmZmVycyhoRW52RW5jLCB0aW1lQnVmZmVyKTsKICAgIH0KCSAgcmV0dXJuIDA7Cn0KClVJTlQgc2JyRW5jb2Rlcl9MaW1pdEJpdFJhdGUoVUlOVCBiaXRSYXRlLCBVSU5UIG51bUNoYW5uZWxzLCBVSU5UIGNvcmVTYW1wbGVSYXRlLCBBVURJT19PQkpFQ1RfVFlQRSBhb3QpCnsKICBVSU5UIG5ld0JpdFJhdGU7CiAgSU5UIGluZGV4OwoKICBGREtfQVNTRVJUKG51bUNoYW5uZWxzID4gMCAmJiBudW1DaGFubmVscyA8PSAyKTsKICBpZiAoYW90ID09IEFPVF9QUykgewogICAgaWYgKG51bUNoYW5uZWxzID09IDIpIHsKICAgICAgaW5kZXggPSBnZXRQc1R1bmluZ1RhYmxlSW5kZXgoYml0UmF0ZSwgJm5ld0JpdFJhdGUpOwogICAgICBpZiAoaW5kZXggPT0gSU5WQUxJRF9UQUJMRV9JRFgpIHsKICAgICAgICBiaXRSYXRlID0gbmV3Qml0UmF0ZTsKICAgICAgfQogICAgICAvKiBTZXQgbnVtQ2hhbm5lbHMgdG8gMSBiZWNhdXNlIGZvciBQUyB3ZSBuZWVkIGEgU0JSIFNDRSAobW9ubykgZWxlbWVudC4gKi8KICAgICAgbnVtQ2hhbm5lbHMgPSAxOwogICAgfSBlbHNlIHsKICAgICAgcmV0dXJuIDA7CiAgICB9CiAgfQogIGluZGV4ID0gZ2V0U2JyVHVuaW5nVGFibGVJbmRleChiaXRSYXRlLCBudW1DaGFubmVscywgY29yZVNhbXBsZVJhdGUsIGFvdCwgJm5ld0JpdFJhdGUpOwogIGlmIChpbmRleCAhPSBJTlZBTElEX1RBQkxFX0lEWCkgewogICAgbmV3Qml0UmF0ZSA9IGJpdFJhdGU7CiAgfQoKICByZXR1cm4gbmV3Qml0UmF0ZTsKfQoKVUlOVCBzYnJFbmNvZGVyX0lzU2luZ2xlUmF0ZVBvc3NpYmxlKEFVRElPX09CSkVDVF9UWVBFIGFvdCkKewogIFVJTlQgaXNQb3NzaWJsZT0oQU9UX1BTPT1hb3QpPzA6MTsKICByZXR1cm4gaXNQb3NzaWJsZTsKfQoKSU5UIHNickVuY29kZXJfSW5pdCgKICAgICAgICBIQU5ETEVfU0JSX0VOQ09ERVIgICBoU2JyRW5jb2RlciwKICAgICAgICBTQlJfRUxFTUVOVF9JTkZPICAgICBlbEluZm9bKDgpXSwKICAgICAgICBpbnQgICAgICAgICAgICAgICAgICBub0VsZW1lbnRzLAogICAgICAgIElOVF9QQ00gICAgICAgICAgICAgKmlucHV0QnVmZmVyLAogICAgICAgIElOVCAgICAgICAgICAgICAgICAgKmNvcmVCYW5kd2lkdGgsCiAgICAgICAgSU5UICAgICAgICAgICAgICAgICAqaW5wdXRCdWZmZXJPZmZzZXQsCiAgICAgICAgSU5UICAgICAgICAgICAgICAgICAqbnVtQ2hhbm5lbHMsCiAgICAgICAgSU5UICAgICAgICAgICAgICAgICAqY29yZVNhbXBsZVJhdGUsCiAgICAgICAgVUlOVCAgICAgICAgICAgICAgICAqZG93blNhbXBsZUZhY3RvciwKICAgICAgICBJTlQgICAgICAgICAgICAgICAgICpmcmFtZUxlbmd0aCwKICAgICAgICBBVURJT19PQkpFQ1RfVFlQRSAgICBhb3QsCiAgICAgICAgaW50ICAgICAgICAgICAgICAgICAqZGVsYXksCiAgICAgICAgaW50ICAgICAgICAgICAgICAgICAgdHJhbnNmb3JtRmFjdG9yLAogICAgICAgIGNvbnN0IGludCAgICAgICAgICAgIGhlYWRlclBlcmlvZCwKICAgICAgICBVTE9ORyAgICAgICAgICAgICAgICBzdGF0ZXNJbml0RmxhZwogICAgICAgICkKewogICAgSEFORExFX0VSUk9SX0lORk8gZXJyb3JJbmZvID0gbm9FcnJvcjsKICAgIHNickNvbmZpZ3VyYXRpb24gc2JyQ29uZmlnWyg4KV07CiAgICBJTlQgZXJyb3IgPSAwOwogICAgSU5UIGxvd2VzdEJhbmR3aWR0aDsKICAgIC8qIFNhdmUgaW5wdXQgcGFyYW1ldGVycyAqLwogICAgSU5UIGlucHV0U2FtcGxlUmF0ZSA9ICpjb3JlU2FtcGxlUmF0ZTsKICAgIGludCBjb3JlRnJhbWVMZW5ndGggPSAqZnJhbWVMZW5ndGg7CiAgICBpbnQgaW5wdXRCYW5kV2lkdGggPSAqY29yZUJhbmR3aWR0aDsKICAgIGludCBpbnB1dENoYW5uZWxzID0gKm51bUNoYW5uZWxzOwoKICAgIGludCBkb3duc2FtcGxlZE9mZnNldCA9IDA7CiAgICBpbnQgc2JyT2Zmc2V0ID0gMDsKICAgIGludCBkb3duc2FtcGxlckRlbGF5ID0gMDsKICAgIGludCB0aW1lRG9tYWluRG93bnNhbXBsZSA9IDA7CiAgICBpbnQgbkJpdHN0ckRlbGF5ID0gMDsKICAgIGludCBoaWdoZXN0U2JyU3RhcnRGcmVxLCBoaWdoZXN0U2JyU3RvcEZyZXE7CiAgICBpbnQgbG93RGVsYXkgPSAwOwogICAgaW50IHVzZVBzID0gMDsKCiAgICAvKiBjaGVjayB3aGV0aGVyIFNCUiBzZXR0aW5nIGlzIGF2YWlsYWJsZSBmb3IgdGhlIGN1cnJlbnQgZW5jb2RlciBjb25maWd1cmF0aW9uIChiaXRyYXRlLCBzYW1wbGVyYXRlKSAqLwogICAgaWYgKCFzYnJFbmNvZGVyX0lzU2luZ2xlUmF0ZVBvc3NpYmxlKGFvdCkpIHsKICAgICAgKmRvd25TYW1wbGVGYWN0b3IgPSAyOwogICAgfQoKCgogICAgaWYgKCAoYW90PT1BT1RfUFMpIHx8IChhb3Q9PUFPVF9NUDJfUFMpIHx8IChhb3Q9PUFPVF9EQUJQTFVTX1BTKSB8fCAoYW90PT1BT1RfRFJNX01QRUdfUFMpICkgewogICAgICAgIHVzZVBzID0gMTsKICAgIH0KICAgIGlmICggYW90PT1BT1RfRVJfQUFDX0VMRCApIHsKICAgICAgICBsb3dEZWxheSA9IDE7CiAgICB9CiAgICBlbHNlIGlmICggYW90PT1BT1RfRVJfQUFDX0xEICkgewogICAgICAgIGVycm9yID0gMTsKICAgICAgICBnb3RvIGJhaWw7CiAgICB9CgogICAgLyogUGFyYW1ldHJpYyBTdGVyZW8gKi8KICAgIGlmICggdXNlUHMgKSB7CiAgICAgIGlmICggKm51bUNoYW5uZWxzID09IDIgJiYgbm9FbGVtZW50cyA9PSAxKSB7CiAgICAgICAgLyogT3ZlcnJpZGUgRWxlbWVudCB0eXBlIGluIGNhc2Ugb2YgUGFyYW1ldHJpYyBzdGVyZW8gKi8KICAgICAgICBlbEluZm9bMF0uZWxUeXBlID0gSURfU0NFOwogICAgICAgIGVsSW5mb1swXS5mUGFyYW1ldHJpY1N0ZXJlbyA9IDE7CiAgICAgICAgZWxJbmZvWzBdLm5DaGFubmVsc0luRWwgPSAxOwogICAgICAgIC8qIGNvcmUgZW5jb2RlciBnZXRzIGRvd25taXhlZCBtb25vIHNpZ25hbCAqLwogICAgICAgICpudW1DaGFubmVscyAgPSAxOwogICAgICB9IGVsc2UgewogICAgICAgIGVycm9yID0gMTsKICAgICAgICBnb3RvIGJhaWw7CiAgICAgIH0KICAgIH0gLyogdXNlUHMgKi8KCiAgICAvKiBzZXQgdGhlIGNvcmUncyBzYW1wbGUgcmF0ZSAqLwogICAgc3dpdGNoICgqZG93blNhbXBsZUZhY3RvcikgewogICAgY2FzZSAxOgogICAgICAqY29yZVNhbXBsZVJhdGUgPSBpbnB1dFNhbXBsZVJhdGU7CiAgICAgIGJyZWFrOwogICAgY2FzZSAyOgogICAgICAqY29yZVNhbXBsZVJhdGUgPSBpbnB1dFNhbXBsZVJhdGU+PjE7CiAgICAgIGJyZWFrOwogICAgZGVmYXVsdDoKICAgICAgKmNvcmVTYW1wbGVSYXRlID0gaW5wdXRTYW1wbGVSYXRlPj4xOwogICAgICByZXR1cm4gMDsgLyogcmV0dXJuIGVycm9yICovCiAgICB9CgogICAgLyogY2hlY2sgd2hldGhlciBTQlIgc2V0dGluZyBpcyBhdmFpbGFibGUgZm9yIHRoZSBjdXJyZW50IGVuY29kZXIgY29uZmlndXJhdGlvbiAoYml0cmF0ZSwgY29yZVNhbXBsZVJhdGUpICovCiAgICB7CiAgICAgIGludCBkZWxheURpZmYgPSAwOwogICAgICBpbnQgZWwsIGNvcmVFbDsKCiAgICAgIC8qIENoZWNrIGlmIGV2ZXJ5IGVsZW1lbnQgY29uZmlnIGlzIGZlYXNpYmxlICovCiAgICAgIGZvciAoY29yZUVsPTA7IGNvcmVFbDxub0VsZW1lbnRzOyBjb3JlRWwrKykKICAgICAgewogICAgICAgIC8qIFNCUiBvbmx5IGhhbmRsZXMgU0NFIGFuZCBDUEUncyAqLwogICAgICAgIGlmIChlbEluZm9bY29yZUVsXS5lbFR5cGUgIT0gSURfU0NFICYmIGVsSW5mb1tjb3JlRWxdLmVsVHlwZSAhPSBJRF9DUEUpIHsKICAgICAgICAgIGNvbnRpbnVlOwogICAgICAgIH0KICAgICAgICAvKiBjaGVjayBpZiBkZXNpcmVkIGNvbmZpZ3VyYXRpb24gaXMgYXZhaWxhYmxlICovCiAgICAgICAgaWYgKCAhRkRLc2JyRW5jX0lzU2JyU2V0dGluZ0F2YWlsIChlbEluZm9bY29yZUVsXS5iaXRSYXRlLCAwLCBlbEluZm9bY29yZUVsXS5uQ2hhbm5lbHNJbkVsLCBpbnB1dFNhbXBsZVJhdGUsICpjb3JlU2FtcGxlUmF0ZSwgYW90KSApCiAgICAgICAgewogICAgICAgICAgICBlcnJvciA9IDE7CiAgICAgICAgICAgIGdvdG8gYmFpbDsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8qIERldGVybWluZSBEZWxheSBiYWxhbmNpbmcgYW5kIG5ldyBlbmNvZGVyIGRlbGF5ICovCiAgICAgIGlmIChsb3dEZWxheSkgewogICAgICAgIHsKICAgICAgICBkZWxheURpZmYgPSAoKmRlbGF5ICogKmRvd25TYW1wbGVGYWN0b3IpICsgREVMQVlfRUxEMlNCUihjb3JlRnJhbWVMZW5ndGgsKmRvd25TYW1wbGVGYWN0b3IpOwogICAgICAgICpkZWxheSA9IERFTEFZX0VMRFNCUihjb3JlRnJhbWVMZW5ndGgsKmRvd25TYW1wbGVGYWN0b3IpOwogICAgICAgIH0KICAgICAgfQogICAgICBlbHNlIGlmICh1c2VQcykgewogICAgICAgIGRlbGF5RGlmZiA9ICgqZGVsYXkgKiAqZG93blNhbXBsZUZhY3RvcikgKyBERUxBWV9BQUMyUFMoY29yZUZyYW1lTGVuZ3RoLCpkb3duU2FtcGxlRmFjdG9yKTsKICAgICAgICAqZGVsYXkgPSBERUxBWV9QUyhjb3JlRnJhbWVMZW5ndGgsKmRvd25TYW1wbGVGYWN0b3IpOwogICAgICB9CiAgICAgIGVsc2UgewogICAgICAgIGRlbGF5RGlmZiA9IERFTEFZX0FBQzJTQlIoY29yZUZyYW1lTGVuZ3RoLCpkb3duU2FtcGxlRmFjdG9yKTsKICAgICAgICBkZWxheURpZmYgKz0gKCpkZWxheSAqICpkb3duU2FtcGxlRmFjdG9yKTsKICAgICAgICAqZGVsYXkgPSBERUxBWV9TQlIoY29yZUZyYW1lTGVuZ3RoLCpkb3duU2FtcGxlRmFjdG9yKTsKICAgICAgfQoKICAgICAgaWYgKCF1c2VQcykgewogICAgICAgICAgdGltZURvbWFpbkRvd25zYW1wbGUgPSAqZG93blNhbXBsZUZhY3Rvci0xOyAgLyogYWN0aXZhdGUgdGltZSBkb21haW4gZG93bnNhbXBsZXIgd2hlbiBkb3duU2FtcGxlRmFjdG9yIGlzICE9IDEgKi8KICAgICAgfQoKCiAgICAgIC8qIFRha2UgY2FyZSBhYm91dCBkb3duc2FtcGxlZCBkYXRhIGJvdW5kIHRvIHRoZSBTQlIgcGF0aCAqLwogICAgICBpZiAoIXRpbWVEb21haW5Eb3duc2FtcGxlICYmIGRlbGF5RGlmZiA+IDApIHsKICAgICAgICAvKgogICAgICAgICAqIFdlIG11c3QgdHdlYWsgdGhlIGJhbGFuY2luZyBpbnRvIGEgc2l0dWF0aW9uIHdoZXJlIHRoZSBkb3duc2FtcGxlZCBwYXRoCiAgICAgICAgICogaXMgdGhlIG9uZSB0byBiZSBkZWxheWVkLCBiZWNhdXNlIGRlbGF5aW5nIHRoZSBRTUYgZG9tYWluIGlucHV0LCBhbHNvIGRlbGF5cwogICAgICAgICAqIHRoZSBkb3duc2FtcGxlZCBhdWRpbywgY291bnRlcmFjdGluZyB0byB0aGUgcHVycG9zZSBvZiBkZWxheSBiYWxhbmNpbmcuCiAgICAgICAgICovCiAgICAgICAgd2hpbGUgKCBkZWxheURpZmYgPiAwICkKICAgICAgICB7CiAgICAgICAgICAvKiBFbmNvZGVyIGRlbGF5IGluY3JlYXNlcyAqLwogICAgICAgICAgewogICAgICAgICAgICAqZGVsYXkgKz0gY29yZUZyYW1lTGVuZ3RoICogKmRvd25TYW1wbGVGYWN0b3I7CiAgICAgICAgICAgIC8qIEFkZCBvbmUgZnJhbWUgZGVsYXkgdG8gU0JSIHBhdGggKi8KICAgICAgICAgICAgZGVsYXlEaWZmIC09IGNvcmVGcmFtZUxlbmd0aCAqICpkb3duU2FtcGxlRmFjdG9yOwogICAgICAgICAgfQogICAgICAgICAgbkJpdHN0ckRlbGF5ICs9IDE7CiAgICAgICAgfQogICAgICB9IGVsc2UKICAgICAgewogICAgICAgICpkZWxheSArPSBmaXhwX2FicyhkZWxheURpZmYpOwogICAgICB9CgogICAgICBpZiAoZGVsYXlEaWZmIDwgMCkgewogICAgICAgIC8qIERlbGF5IEFBQyBkYXRhICovCiAgICAgICAgZGVsYXlEaWZmID0gLWRlbGF5RGlmZjsKICAgICAgICAvKiBNdWx0aXBseSBkb3duc2FtcGxlZCBvZmZzZXQgYnkgQUFDIGNvcmUgY2hhbm5lbHMuIERpdmlkZSBieSAyIGJlY2F1c2Ugb2YgaGFsZiBzYW1wbGVyYXRlIG9mIGRvd25zYW1wbGVkIGRhdGEuICovCiAgICAgICAgRkRLX0FTU0VSVCgqZG93blNhbXBsZUZhY3Rvcj4wICYmICpkb3duU2FtcGxlRmFjdG9yPD0yKTsKICAgICAgICBkb3duc2FtcGxlZE9mZnNldCA9IChkZWxheURpZmYqKCpudW1DaGFubmVscykpPj4oKmRvd25TYW1wbGVGYWN0b3ItMSk7CiAgICAgICAgc2JyT2Zmc2V0ID0gMDsKICAgICAgfSBlbHNlIHsKICAgICAgICAvKiBEZWxheSBTQlIgaW5wdXQgKi8KICAgICAgICBpZiAoIGRlbGF5RGlmZiA+IChpbnQpY29yZUZyYW1lTGVuZ3RoICogKGludCkqZG93blNhbXBsZUZhY3RvciApCiAgICAgICAgewogICAgICAgICAgLyogRG8gYml0c3RyZWFtIGZyYW1lLXdpc2UgZGVsYXkgYmFsYW5jaW5nIGlmIHdlIGhhdmUgbW9yZSB0aGFuIFNCUiBmcmFtZWxlbmd0aCBzYW1wbGVzIGRlbGF5IGRpZmZlcmVuY2UgKi8KICAgICAgICAgIGRlbGF5RGlmZiAtPSBjb3JlRnJhbWVMZW5ndGggKiAqZG93blNhbXBsZUZhY3RvcjsKICAgICAgICAgIG5CaXRzdHJEZWxheSA9IDE7CiAgICAgICAgfQogICAgICAgIC8qIE11bHRpcGx5IGlucHV0IG9mZnNldCBieSBpbnB1dCBjaGFubmVscyAqLwogICAgICAgIHNick9mZnNldCA9IGRlbGF5RGlmZiooKm51bUNoYW5uZWxzKTsKICAgICAgICBkb3duc2FtcGxlZE9mZnNldCA9IDA7CiAgICAgIH0KICAgICAgaFNickVuY29kZXItPm5CaXRzdHJEZWxheSAgICAgICAgICAgID0gbkJpdHN0ckRlbGF5OwogICAgICBoU2JyRW5jb2Rlci0+bkNoYW5uZWxzICAgICAgICAgICAgICAgPSAqbnVtQ2hhbm5lbHM7CiAgICAgIGhTYnJFbmNvZGVyLT5mcmFtZVNpemUgICAgICAgICAgICAgICA9IGNvcmVGcmFtZUxlbmd0aCAqICpkb3duU2FtcGxlRmFjdG9yOwogICAgICBoU2JyRW5jb2Rlci0+ZlRpbWVEb21haW5Eb3duc2FtcGxpbmcgPSB0aW1lRG9tYWluRG93bnNhbXBsZTsKICAgICAgaFNickVuY29kZXItPmRvd25TYW1wbGVGYWN0b3IgICAgICAgID0gKmRvd25TYW1wbGVGYWN0b3I7CiAgICAgIGhTYnJFbmNvZGVyLT5lc3RpbWF0ZUJpdHJhdGUgICAgICAgICA9IDA7CiAgICAgIGhTYnJFbmNvZGVyLT5pbnB1dERhdGFEZWxheSAgICAgICAgICA9IDA7CgoKICAgICAgLyogT3BlbiBTQlIgZWxlbWVudHMgKi8KICAgICAgZWwgPSAtMTsKICAgICAgaGlnaGVzdFNiclN0YXJ0RnJlcSA9IGhpZ2hlc3RTYnJTdG9wRnJlcSA9IDA7CiAgICAgIGxvd2VzdEJhbmR3aWR0aCA9IDk5OTk5OwoKICAgICAgLyogTG9vcCB0aHJvdWdoIGVhY2ggY29yZSBlbmNvZGVyIGVsZW1lbnQgYW5kIGdldCBhIG1hdGNoaW5nIFNCUiBlbGVtZW50IGNvbmZpZyAqLwogICAgICBmb3IgKGNvcmVFbD0wOyBjb3JlRWw8bm9FbGVtZW50czsgY29yZUVsKyspCiAgICAgIHsKICAgICAgICAvKiBTQlIgb25seSBoYW5kbGVzIFNDRSBhbmQgQ1BFJ3MgKi8KICAgICAgICBpZiAoZWxJbmZvW2NvcmVFbF0uZWxUeXBlID09IElEX1NDRSB8fCBlbEluZm9bY29yZUVsXS5lbFR5cGUgPT0gSURfQ1BFKSB7CiAgICAgICAgICBlbCsrOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBjb250aW51ZTsKICAgICAgICB9CgogICAgICAgIC8qIFNldCBwYXJhbWV0cmljIFN0ZXJlbyBGbGFnLiAqLwogICAgICAgIGlmICh1c2VQcykgewogICAgICAgICAgZWxJbmZvW2NvcmVFbF0uZlBhcmFtZXRyaWNTdGVyZW8gPSAxOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBlbEluZm9bY29yZUVsXS5mUGFyYW1ldHJpY1N0ZXJlbyA9IDA7CiAgICAgICAgfQoKICAgICAgICAvKgogICAgICAgICAqIEluaXQgc2JyQ29uZmlnIHN0cnVjdHVyZQogICAgICAgICAqLwogICAgICAgIGlmICggISBGREtzYnJFbmNfSW5pdGlhbGl6ZVNickRlZmF1bHRzICggJnNickNvbmZpZ1tlbF0sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAqZG93blNhbXBsZUZhY3RvciwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBjb3JlRnJhbWVMZW5ndGgKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICApICkKICAgICAgICB7CiAgICAgICAgICBlcnJvciA9IDE7CiAgICAgICAgICBnb3RvIGJhaWw7CiAgICAgICAgfQoKICAgICAgICAvKgogICAgICAgICAqIE1vZGlmeSBzYnJDb25maWcgc3RydWN0dXJlIGFjY29yZGluZyB0byBFbGVtZW50IHBhcmFtZXRlcnMKICAgICAgICAgKi8KICAgICAgICBpZiAoICEgRkRLc2JyRW5jX0FkanVzdFNiclNldHRpbmdzICgmc2JyQ29uZmlnW2VsXSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZWxJbmZvW2NvcmVFbF0uYml0UmF0ZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZWxJbmZvW2NvcmVFbF0ubkNoYW5uZWxzSW5FbCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAqY29yZVNhbXBsZVJhdGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGlucHV0U2FtcGxlUmF0ZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdHJhbnNmb3JtRmFjdG9yLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAyNDAwMCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgMCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgMCwgICAgIC8qIHVzZVNwZWVjaENvbmZpZyAqLwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAwLCAgICAgLyogbGNzTW9kZSAqLwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB1c2VQcywgLyogYlBhcmFtZXRyaWNTdGVyZW8gKi8KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgYW90KSApCiAgICAgICAgewogICAgICAgICAgZXJyb3IgPSAxOwogICAgICAgICAgZ290byBiYWlsOwogICAgICAgIH0KCiAgICAgICAgLyogRmluZCBjb21tb24gZnJlcXVlbmN5IGJvcmRlciBmb3IgYWxsIFNCUiBlbGVtZW50cyAqLwogICAgICAgIGhpZ2hlc3RTYnJTdGFydEZyZXEgPSBmaXhNYXgoaGlnaGVzdFNiclN0YXJ0RnJlcSwgc2JyQ29uZmlnW2VsXS5zdGFydEZyZXEpOwogICAgICAgIGhpZ2hlc3RTYnJTdG9wRnJlcSA9IGZpeE1heChoaWdoZXN0U2JyU3RvcEZyZXEsIHNickNvbmZpZ1tlbF0uc3RvcEZyZXEpOwoKICAgICAgfSAvKiBmaXJzdCBlbGVtZW50IGxvb3AgKi8KCiAgICAgIC8qIFNldCBlbGVtZW50IGNvdW50IChjYW4gYmUgbGVzcyB0aGFuIGNvcmUgZW5jb2RlciBlbGVtZW50IGNvdW50KSAqLwogICAgICBoU2JyRW5jb2Rlci0+bm9FbGVtZW50cyA9IGVsKzE7CgogICAgICBGREtzYnJFbmNfUmVhbGxvY2F0ZShoU2JyRW5jb2RlciwKICAgICAgICAgICAgICAgICAgICAgICAgICAgZWxJbmZvLAogICAgICAgICAgICAgICAgICAgICAgICAgICBub0VsZW1lbnRzKTsKCiAgICAgIGZvciAoZWw9MDsgZWw8aFNickVuY29kZXItPm5vRWxlbWVudHM7IGVsKyspIHsKCiAgICAgICAgaW50IGJhbmR3aWR0aCA9ICpjb3JlQmFuZHdpZHRoOwoKICAgICAgICAvKiBVc2UgbG93ZXN0IGNvbW1vbiBiYW5kd2lkdGggKi8KICAgICAgICBzYnJDb25maWdbZWxdLnN0YXJ0RnJlcSA9IGhpZ2hlc3RTYnJTdGFydEZyZXE7CiAgICAgICAgc2JyQ29uZmlnW2VsXS5zdG9wRnJlcSA9IGhpZ2hlc3RTYnJTdG9wRnJlcTsKCiAgICAgICAgLyogaW5pdGlhbGl6ZSBTQlIgZWxlbWVudCwgYW5kIGdldCBjb3JlIGJhbmR3aWR0aCAqLwogICAgICAgIGVycm9yID0gRkRLc2JyRW5jX0VudkluaXQoaFNickVuY29kZXItPnNickVsZW1lbnRbZWxdLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJnNickNvbmZpZ1tlbF0sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmYmFuZHdpZHRoLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGFvdCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBuQml0c3RyRGVsYXksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZWwsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaGVhZGVyUGVyaW9kLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHN0YXRlc0luaXRGbGFnLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGhTYnJFbmNvZGVyLT5mVGltZURvbWFpbkRvd25zYW1wbGluZwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgLGhTYnJFbmNvZGVyLT5keW5hbWljUmFtCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICApOwoKICAgICAgICBpZiAoZXJyb3IgIT0gMCkgewogICAgICAgICAgZXJyb3IgPSAyOwogICAgICAgICAgZ290byBiYWlsOwogICAgICAgIH0KCiAgICAgICAgLyogR2V0IGxvd2VzdCBjb3JlIGVuY29kZXIgYmFuZHdpZHRoIHRvIGJlIHJldHVybmVkIGxhdGVyLiAqLwogICAgICAgIGxvd2VzdEJhbmR3aWR0aCA9IGZpeE1pbihsb3dlc3RCYW5kd2lkdGgsIGJhbmR3aWR0aCk7CgogICAgICB9IC8qIHNlY29uZCBlbGVtZW50IGxvb3AgKi8KCiAgICAgIC8qIEluaXRpYWxpemUgYSBkb3duc2FtcGxlciBmb3IgZWFjaCBjaGFubmVsIGluIGVhY2ggU0JSIGVsZW1lbnQgKi8KICAgICAgaWYgKGhTYnJFbmNvZGVyLT5mVGltZURvbWFpbkRvd25zYW1wbGluZykKICAgICAgewogICAgICAgIGZvciAoZWw9MDsgZWw8aFNickVuY29kZXItPm5vRWxlbWVudHM7IGVsKyspCiAgICAgICAgewogICAgICAgICAgSEFORExFX1NCUl9FTEVNRU5UIGhTYnJFbCA9IGhTYnJFbmNvZGVyLT5zYnJFbGVtZW50W2VsXTsKICAgICAgICAgIElOVCBXYywgY2g7CgogICAgICAgICAgLyogQ2FsY3VsYXRlZCByZXF1aXJlZCBub3JtYWxpemVkIGN1dG9mZiBmcmVxdWVuY3kgKFdjID0gMS4wIC0+IGxvd2VzdEJhbmR3aWR0aCA9IGlucHV0U2FtcGxlUmF0ZS8yKSAqLwogICAgICAgICAgV2MgPSAoMipsb3dlc3RCYW5kd2lkdGgpKjEwMDAgLyBpbnB1dFNhbXBsZVJhdGU7CgogICAgICAgICAgZm9yIChjaD0wOyBjaDxoU2JyRWwtPmVsSW5mby5uQ2hhbm5lbHNJbkVsOyBjaCsrKQogICAgICAgICAgewogICAgICAgICAgICBGREthYWNFbmNfSW5pdERvd25zYW1wbGVyICgmaFNickVsLT5zYnJDaGFubmVsW2NoXS0+ZG93blNhbXBsZXIsIFdjLCAqZG93blNhbXBsZUZhY3Rvcik7CiAgICAgICAgICAgIEZES19BU1NFUlQgKGhTYnJFbC0+c2JyQ2hhbm5lbFtjaF0tPmRvd25TYW1wbGVyLmRlbGF5IDw9TUFYX0RTX0ZJTFRFUl9ERUxBWSk7CiAgICAgICAgICB9CgogICAgICAgICAgZG93bnNhbXBsZXJEZWxheSA9IGhTYnJFbC0+c2JyQ2hhbm5lbFswXS0+ZG93blNhbXBsZXIuZGVsYXk7CiAgICAgICAgfSAvKiB0aGlyZCBlbGVtZW50IGxvb3AgKi8KCiAgICAgICAgLyogbGZlICovCiAgICAgICAgRkRLYWFjRW5jX0luaXREb3duc2FtcGxlciAoJmhTYnJFbmNvZGVyLT5sZmVEb3duU2FtcGxlciwgMCwgKmRvd25TYW1wbGVGYWN0b3IpOwoKICAgICAgICAvKiBBZGQgdGhlIHJlc2FtcGxlciBhZGRpdGlvbmFsIGRlbGF5IHRvIGdldCB0aGUgZmluYWwgZGVsYXkgYW5kIGJ1ZmZlciBvZmZzZXQgdmFsdWVzLiAqLwogICAgICAgIGlmIChzYnJPZmZzZXQgPiAwIHx8IGRvd25zYW1wbGVkT2Zmc2V0IDw9ICgoZG93bnNhbXBsZXJEZWxheSAqICgqbnVtQ2hhbm5lbHMpKT4+KCpkb3duU2FtcGxlRmFjdG9yLTEpKSkgewogICAgICAgICAgc2JyT2Zmc2V0ICs9IChkb3duc2FtcGxlckRlbGF5IC0gZG93bnNhbXBsZWRPZmZzZXQpICogKCpudW1DaGFubmVscykgOwogICAgICAgICAgKmRlbGF5ICs9IGRvd25zYW1wbGVyRGVsYXkgLSBkb3duc2FtcGxlZE9mZnNldDsKICAgICAgICAgIGRvd25zYW1wbGVkT2Zmc2V0ID0gMDsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgZG93bnNhbXBsZWRPZmZzZXQgLT0gKGRvd25zYW1wbGVyRGVsYXkgKiAoKm51bUNoYW5uZWxzKSk+PigqZG93blNhbXBsZUZhY3Rvci0xKTsKICAgICAgICAgIHNick9mZnNldCA9IDA7CiAgICAgICAgfQoKICAgICAgICBoU2JyRW5jb2Rlci0+aW5wdXREYXRhRGVsYXkgPSBkb3duc2FtcGxlckRlbGF5OwogICAgICB9CgogICAgICAvKiBBc3NpZ24gY29yZSBlbmNvZGVyIEJhbmR3aWR0aCAqLwogICAgICAqY29yZUJhbmR3aWR0aCA9IGxvd2VzdEJhbmR3aWR0aDsKCiAgICAgIC8qIEVzdGltYXRlIHNiciBiaXRyYXRlLCAyLjUga0JpdC9zIHBlciBzYnIgY2hhbm5lbCAqLwogICAgICBoU2JyRW5jb2Rlci0+ZXN0aW1hdGVCaXRyYXRlICs9IDI1MDAgKiAoKm51bUNoYW5uZWxzKTsKCiAgICAgIC8qIGluaXRpYWxpemUgcGFyYW1ldHJpYyBzdGVyZW8gKi8KICAgICAgaWYgKHVzZVBzKQogICAgICB7CiAgICAgICAgUFNFTkNfQ09ORklHIHBzRW5jQ29uZmlnOwogICAgICAgIEZES19BU1NFUlQoaFNickVuY29kZXItPm5vRWxlbWVudHMgPT0gMSk7CiAgICAgICAgSU5UIHBzVHVuaW5nVGFibGVJZHggPSBnZXRQc1R1bmluZ1RhYmxlSW5kZXgoZWxJbmZvWzBdLmJpdFJhdGUsIE5VTEwpOwoKICAgICAgICBwc0VuY0NvbmZpZy5mcmFtZVNpemUgICAgICAgICAgID0gY29yZUZyYW1lTGVuZ3RoOyAvL3NickNvbmZpZy5zYnJGcmFtZVNpemU7CiAgICAgICAgcHNFbmNDb25maWcucW1mRmlsdGVyTW9kZSAgICAgICA9IDA7CiAgICAgICAgcHNFbmNDb25maWcuc2JyUHNEZWxheSAgICAgICAgICA9IDA7CgogICAgICAgIC8qIHR1bmluZyBwYXJhbWV0ZXJzICovCiAgICAgICAgaWYgKHBzVHVuaW5nVGFibGVJZHggICE9IElOVkFMSURfVEFCTEVfSURYKSB7CiAgICAgICAgICBwc0VuY0NvbmZpZy5uU3RlcmVvQmFuZHMgICAgICAgICAgID0gcHNUdW5pbmdUYWJsZVtwc1R1bmluZ1RhYmxlSWR4XS5uU3RlcmVvQmFuZHM7CiAgICAgICAgICBwc0VuY0NvbmZpZy5tYXhFbnZlbG9wZXMgICAgICAgICAgID0gcHNUdW5pbmdUYWJsZVtwc1R1bmluZ1RhYmxlSWR4XS5uRW52ZWxvcGVzOwogICAgICAgICAgcHNFbmNDb25maWcuaWlkUXVhbnRFcnJvclRocmVzaG9sZCA9IChGSVhQX0RCTClwc1R1bmluZ1RhYmxlW3BzVHVuaW5nVGFibGVJZHhdLmlpZFF1YW50RXJyb3JUaHJlc2hvbGQ7CgogICAgICAgICAgLyogY2FsY3VsYXRpb24gaXMgbm90IHF1aXRlIGxpbmVhciwgaW5jcmVhc2VkIG51bWJlciBvZiBlbnZlbG9wZXMgY2F1c2VzIG1vcmUgYml0cyAqLwogICAgICAgICAgLyogYXNzdW1lIGF2Zy4gNTAgYml0cyBwZXIgZnJhbWUgZm9yIDEwIHN0ZXJlbyBiYW5kcyAvIDEgZW52ZWxvcGUgY29uZmlndXJhdGlvbiAqLwogICAgICAgICAgaFNickVuY29kZXItPmVzdGltYXRlQml0cmF0ZSArPSAoICgoKCpjb3JlU2FtcGxlUmF0ZSkgKiA1ICogcHNFbmNDb25maWcublN0ZXJlb0JhbmRzICogcHNFbmNDb25maWcubWF4RW52ZWxvcGVzKSAvIGhTYnJFbmNvZGVyLT5mcmFtZVNpemUpKTsKCiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGVycm9yID0gRVJST1IoQ0RJLCAiSW52YWxpZCBwcyB0dW5pbmcgdGFibGUgaW5kZXguIik7CiAgICAgICAgICBnb3RvIGJhaWw7CiAgICAgICAgfQoKICAgICAgICBxbWZJbml0U3ludGhlc2lzRmlsdGVyQmFuaygmaFNickVuY29kZXItPnFtZlN5bnRoZXNpc1BTLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAoRklYUF9EQkwqKWhTYnJFbmNvZGVyLT5xbWZTeW50aGVzaXNQUy5GaWx0ZXJTdGF0ZXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGhTYnJFbmNvZGVyLT5zYnJFbGVtZW50WzBdLT5zYnJDb25maWdEYXRhLm5vUW1mU2xvdHMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGhTYnJFbmNvZGVyLT5zYnJFbGVtZW50WzBdLT5zYnJDb25maWdEYXRhLm5vUW1mQmFuZHM+PjEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGhTYnJFbmNvZGVyLT5zYnJFbGVtZW50WzBdLT5zYnJDb25maWdEYXRhLm5vUW1mQmFuZHM+PjEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGhTYnJFbmNvZGVyLT5zYnJFbGVtZW50WzBdLT5zYnJDb25maWdEYXRhLm5vUW1mQmFuZHM+PjEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIChzdGF0ZXNJbml0RmxhZykgPyAwIDogUU1GX0ZMQUdfS0VFUF9TVEFURVMpOwoKICAgICAgICBpZihlcnJvckluZm8gPT0gbm9FcnJvcil7CiAgICAgICAgICAvKiB1cGRhdGUgZGVsYXkgKi8KICAgICAgICAgIHBzRW5jQ29uZmlnLnNiclBzRGVsYXkgPSBGREtzYnJFbmNfR2V0RW52RXN0RGVsYXkoJmhTYnJFbmNvZGVyLT5zYnJFbGVtZW50WzBdLT5zYnJDaGFubmVsWzBdLT5oRW52Q2hhbm5lbC5zYnJFeHRyYWN0RW52ZWxvcGUpOwoKICAgICAgICAgIGlmKG5vRXJyb3IgIT0gKGVycm9ySW5mbyA9IFBTRW5jX0luaXQoIGhTYnJFbmNvZGVyLT5oUGFyYW1ldHJpY1N0ZXJlbywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJnBzRW5jQ29uZmlnLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaFNickVuY29kZXItPnNickVsZW1lbnRbMF0tPnNickNvbmZpZ0RhdGEubm9RbWZTbG90cywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGhTYnJFbmNvZGVyLT5zYnJFbGVtZW50WzBdLT5zYnJDb25maWdEYXRhLm5vUW1mQmFuZHMKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgLGhTYnJFbmNvZGVyLT5keW5hbWljUmFtCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICApKSkKICAgICAgICAgIHsKICAgICAgICAgICAgZXJyb3JJbmZvID0gaGFuZEJhY2soZXJyb3JJbmZvKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qIFFNRiBhbmFseXNpcyArIEh5YnJpZCBhbmFseXNpcyArIEh5YnJpZCBzeW50aGVzaXMgKyBRTUYgc3ludGhlc2lzICsgZG93bnNhbXBsZWQgaW5wdXQgYnVmZmVyIGRlbGF5ICovCiAgICAgICAgaFNickVuY29kZXItPmlucHV0RGF0YURlbGF5ID0gKDY0KjEwLzIpICsgKDYqNjQpICsgICgwKSArICg2NCoxMC8yLTY0KzEpICsgKCgqZG93blNhbXBsZUZhY3RvcikqZG93bnNhbXBsZWRPZmZzZXQpOwogICAgICB9CgogICAgICBoU2JyRW5jb2Rlci0+ZG93bnNhbXBsZWRPZmZzZXQgPSBkb3duc2FtcGxlZE9mZnNldDsKICAgICAgewogICAgICAgIGhTYnJFbmNvZGVyLT5kb3dubWl4U2l6ZSA9IGNvcmVGcmFtZUxlbmd0aCooKm51bUNoYW5uZWxzKTsKICAgICAgfQoKICAgICAgaFNickVuY29kZXItPmJ1ZmZlck9mZnNldCA9IHNick9mZnNldDsKICAgICAgLyogRGVsYXkgQ29tcGVuc2F0aW9uOiBmaWxsIGJpdHN0cmVhbSBkZWxheSBidWZmZXIgd2l0aCB6ZXJvIGlucHV0IHNpZ25hbCAqLwogICAgICBpZiAoIGhTYnJFbmNvZGVyLT5uQml0c3RyRGVsYXkgPiAwICkKICAgICAgewogICAgICAgIGVycm9yID0gRkRLc2JyRW5jX0RlbGF5Q29tcGVuc2F0aW9uIChoU2JyRW5jb2RlciwgaW5wdXRCdWZmZXIpOwogICAgICAgIGlmIChlcnJvciAhPSAwKQogICAgICAgICAgZ290byBiYWlsOwogICAgICB9CgogICAgICAvKiBTZXQgT3V0cHV0IGZyYW1lIGxlbmd0aCAqLwogICAgICAqZnJhbWVMZW5ndGggPSBjb3JlRnJhbWVMZW5ndGggKiAqZG93blNhbXBsZUZhY3RvcjsKICAgICAgLyogSW5wdXQgYnVmZmVyIG9mZnNldCAqLwogICAgICAqaW5wdXRCdWZmZXJPZmZzZXQgPSBmaXhNYXgoc2JyT2Zmc2V0LCBkb3duc2FtcGxlZE9mZnNldCk7CgoKICAgIH0KCiAgICByZXR1cm4gZXJyb3I7CgpiYWlsOgogICAgLyogUmVzdG9yZSBpbnB1dCBzZXR0aW5ncyAqLwogICAgKmNvcmVTYW1wbGVSYXRlID0gaW5wdXRTYW1wbGVSYXRlOwogICAgKmZyYW1lTGVuZ3RoID0gY29yZUZyYW1lTGVuZ3RoOwogICAgKm51bUNoYW5uZWxzID0gaW5wdXRDaGFubmVsczsKICAgICpjb3JlQmFuZHdpZHRoID0gaW5wdXRCYW5kV2lkdGg7CgogICAgcmV0dXJuIGVycm9yOwogfQoKCklOVApzYnJFbmNvZGVyX0VuY29kZUZyYW1lKCAgSEFORExFX1NCUl9FTkNPREVSICAgaFNickVuY29kZXIsCiAgICAgICAgICAgICAgICAgICAgICAgICBJTlRfUENNICAgICAgICAgICAgICpzYW1wbGVzLAogICAgICAgICAgICAgICAgICAgICAgICAgVUlOVCAgICAgICAgICAgICAgICAgdGltZUluU3RyaWRlLAogICAgICAgICAgICAgICAgICAgICAgICAgVUlOVCAgICAgICAgICAgICAgICAgc2JyRGF0YUJpdHNbKDgpXSwKICAgICAgICAgICAgICAgICAgICAgICAgIFVDSEFSICAgICAgICAgICAgICAgIHNickRhdGFbKDgpXVtNQVhfUEFZTE9BRF9TSVpFXQogICAgICAgICAgICAgICAgICAgICAgICApCnsKICBJTlQgZXJyb3I7CiAgaW50IGVsOwoKICBmb3IgKGVsPTA7IGVsPGhTYnJFbmNvZGVyLT5ub0VsZW1lbnRzOyBlbCsrKQogIHsKICAgIGlmIChoU2JyRW5jb2Rlci0+c2JyRWxlbWVudFtlbF0gIT0gTlVMTCkKICAgIHsKICAgICAgZXJyb3IgPSBGREtzYnJFbmNfRW52RW5jb2RlRnJhbWUoCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBoU2JyRW5jb2RlciwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGVsLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2FtcGxlcyArIGhTYnJFbmNvZGVyLT5kb3duc2FtcGxlZE9mZnNldCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHRpbWVJblN0cmlkZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJnNickRhdGFCaXRzW2VsXSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNickRhdGFbZWxdLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgMAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICApOwogICAgICBpZiAoZXJyb3IpCiAgICAgICAgcmV0dXJuIGVycm9yOwogICAgfQogIH0KCiAgaWYgKCAoIGhTYnJFbmNvZGVyLT5sZmVDaElkeCE9LTEpICYmIChoU2JyRW5jb2Rlci0+ZG93blNhbXBsZUZhY3RvciA+IDEpICkKICB7ICAgLyogbGZlIGRvd25zYW1wbGVyICovCiAgICAgIElOVCBuT3V0U2FtcGxlczsKCiAgICAgIEZES2FhY0VuY19Eb3duc2FtcGxlKCZoU2JyRW5jb2Rlci0+bGZlRG93blNhbXBsZXIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBzYW1wbGVzICsgaFNickVuY29kZXItPmRvd25zYW1wbGVkT2Zmc2V0ICsgaFNickVuY29kZXItPmJ1ZmZlck9mZnNldCArIGhTYnJFbmNvZGVyLT5sZmVDaElkeCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGhTYnJFbmNvZGVyLT5mcmFtZVNpemUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICB0aW1lSW5TdHJpZGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBzYW1wbGVzICsgaFNickVuY29kZXItPmRvd25zYW1wbGVkT2Zmc2V0ICsgaFNickVuY29kZXItPmxmZUNoSWR4LAogICAgICAgICAgICAgICAgICAgICAgICAgICAmbk91dFNhbXBsZXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBoU2JyRW5jb2Rlci0+bkNoYW5uZWxzKTsKCgogIH0KCiAgcmV0dXJuIDA7Cn0KCgpJTlQgc2JyRW5jb2Rlcl9VcGRhdGVCdWZmZXJzKAogICAgICAgICAgICAgICAgICAgICAgICAgICAgSEFORExFX1NCUl9FTkNPREVSIGhTYnJFbmNvZGVyLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgSU5UX1BDTSAqdGltZUJ1ZmZlcgogICAgICAgICAgICAgICAgICAgICAgICAgICAgKQogewogICAgaWYgKCBoU2JyRW5jb2Rlci0+ZG93bnNhbXBsZWRPZmZzZXQgPiAwICkgewogICAgICAvKiBNb3ZlIGRlbGF5ZWQgZG93bnNhbXBsZWQgZGF0YSAqLwogICAgICBGREttZW1jcHkgKCB0aW1lQnVmZmVyLAogICAgICAgICAgICAgICAgICB0aW1lQnVmZmVyICsgaFNickVuY29kZXItPmRvd25taXhTaXplLAogICAgICAgICAgICAgICAgICBzaXplb2YoSU5UX1BDTSkgKiAoaFNickVuY29kZXItPmRvd25zYW1wbGVkT2Zmc2V0KSApOwogICAgfSBlbHNlIHsKICAgICAgLyogTW92ZSBkZWxheWVkIGlucHV0IGRhdGEgKi8KICAgICAgRkRLbWVtY3B5ICggdGltZUJ1ZmZlciwKICAgICAgICB0aW1lQnVmZmVyICsgaFNickVuY29kZXItPm5DaGFubmVscyAqIGhTYnJFbmNvZGVyLT5mcmFtZVNpemUsCiAgICAgICAgICAgICAgICAgIHNpemVvZihJTlRfUENNKSAqIGhTYnJFbmNvZGVyLT5idWZmZXJPZmZzZXQgKTsKICAgIH0KICAgIGlmICggaFNickVuY29kZXItPm5CaXRzdHJEZWxheSA+IDAgICkKICAgIHsKICAgICAgaW50IGVsOwoKICAgICAgZm9yIChlbD0wOyBlbDxoU2JyRW5jb2Rlci0+bm9FbGVtZW50czsgZWwrKykKICAgICAgewogICAgICAgIEZES21lbW1vdmUgKCBoU2JyRW5jb2Rlci0+c2JyRWxlbWVudFtlbF0tPnBheWxvYWREZWxheUxpbmVbMF0sCiAgICAgICAgICAgICAgICAgICAgIGhTYnJFbmNvZGVyLT5zYnJFbGVtZW50W2VsXS0+cGF5bG9hZERlbGF5TGluZVsxXSwKICAgICAgICAgICAgICAgICAgICAgc2l6ZW9mKFVDSEFSKSAqIChoU2JyRW5jb2Rlci0+bkJpdHN0ckRlbGF5Kk1BWF9QQVlMT0FEX1NJWkUpICk7CgogICAgICAgIEZES21lbW1vdmUoICZoU2JyRW5jb2Rlci0+c2JyRWxlbWVudFtlbF0tPnBheWxvYWREZWxheUxpbmVTaXplWzBdLAogICAgICAgICAgICAgICAgICAgICZoU2JyRW5jb2Rlci0+c2JyRWxlbWVudFtlbF0tPnBheWxvYWREZWxheUxpbmVTaXplWzFdLAogICAgICAgICAgICAgICAgICAgIHNpemVvZihVSU5UKSAqIChoU2JyRW5jb2Rlci0+bkJpdHN0ckRlbGF5KSApOwogICAgICB9CiAgICB9CiAgICByZXR1cm4gMDsKIH0KCgpJTlQgc2JyRW5jb2Rlcl9HZXRFc3RpbWF0ZUJpdHJhdGUoSEFORExFX1NCUl9FTkNPREVSIGhTYnJFbmNvZGVyKQp7CiAgSU5UIGVzdGltYXRlQml0cmF0ZSA9IDA7CgogIGlmKGhTYnJFbmNvZGVyKSB7CiAgICBlc3RpbWF0ZUJpdHJhdGUgKz0gaFNickVuY29kZXItPmVzdGltYXRlQml0cmF0ZTsKICB9CgogIHJldHVybiBlc3RpbWF0ZUJpdHJhdGU7Cn0KCklOVCBzYnJFbmNvZGVyX0dldElucHV0RGF0YURlbGF5KEhBTkRMRV9TQlJfRU5DT0RFUiBoU2JyRW5jb2RlcikKewogIElOVCBkZWxheSA9IC0xOwoKICBpZihoU2JyRW5jb2RlcikgewogICAgZGVsYXkgPSBoU2JyRW5jb2Rlci0+aW5wdXREYXRhRGVsYXk7CiAgfQogIHJldHVybiBkZWxheTsKfQoKCklOVCBzYnJFbmNvZGVyX0dldExpYkluZm8oIExJQl9JTkZPICppbmZvICkKewogIGludCBpOwoKICBpZiAoaW5mbyA9PSBOVUxMKSB7CiAgICByZXR1cm4gLTE7CiAgfQogIC8qIHNlYXJjaCBmb3IgbmV4dCBmcmVlIHRhYiAqLwogIGZvciAoaSA9IDA7IGkgPCBGREtfTU9EVUxFX0xBU1Q7IGkrKykgewogICAgaWYgKGluZm9baV0ubW9kdWxlX2lkID09IEZES19OT05FKSBicmVhazsKICB9CiAgaWYgKGkgPT0gRkRLX01PRFVMRV9MQVNUKSB7CiAgICByZXR1cm4gLTE7CiAgfQogIGluZm8gKz0gaTsKCiAgaW5mby0+bW9kdWxlX2lkID0gRkRLX1NCUkVOQzsKICBpbmZvLT52ZXJzaW9uID0gTElCX1ZFUlNJT04oU0JSRU5DT0RFUl9MSUJfVkwwLCBTQlJFTkNPREVSX0xJQl9WTDEsIFNCUkVOQ09ERVJfTElCX1ZMMik7CiAgTElCX1ZFUlNJT05fU1RSSU5HKGluZm8pOwojaWZkZWYgX19BTkRST0lEX18KICBpbmZvLT5idWlsZF9kYXRlID0gIiI7CiAgaW5mby0+YnVpbGRfdGltZSA9ICIiOwojZWxzZQogIGluZm8tPmJ1aWxkX2RhdGUgPSBfX0RBVEVfXzsKICBpbmZvLT5idWlsZF90aW1lID0gX19USU1FX187CiNlbmRpZgogIGluZm8tPnRpdGxlID0gIlNCUiBFbmNvZGVyIjsKCiAgLyogU2V0IGZsYWdzICovCiAgaW5mby0+ZmxhZ3MgPSAwCiAgICB8IENBUEZfU0JSX0hRCiAgICB8IENBUEZfU0JSX1BTX01QRUcKICAgIDsKICAvKiBFbmQgb2YgZmxhZ3MgKi8KCiAgcmV0dXJuIDA7Cn0K