Ci8qIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tClNvZnR3YXJlIExpY2Vuc2UgZm9yIFRoZSBGcmF1bmhvZmVyIEZESyBBQUMgQ29kZWMgTGlicmFyeSBmb3IgQW5kcm9pZAoKqSBDb3B5cmlnaHQgIDE5OTUgLSAyMDEzIEZyYXVuaG9mZXItR2VzZWxsc2NoYWZ0IHp1ciBG9nJkZXJ1bmcgZGVyIGFuZ2V3YW5kdGVuIEZvcnNjaHVuZyBlLlYuCiAgQWxsIHJpZ2h0cyByZXNlcnZlZC4KCiAxLiAgICBJTlRST0RVQ1RJT04KVGhlIEZyYXVuaG9mZXIgRkRLIEFBQyBDb2RlYyBMaWJyYXJ5IGZvciBBbmRyb2lkICgiRkRLIEFBQyBDb2RlYyIpIGlzIHNvZnR3YXJlIHRoYXQgaW1wbGVtZW50cwp0aGUgTVBFRyBBZHZhbmNlZCBBdWRpbyBDb2RpbmcgKCJBQUMiKSBlbmNvZGluZyBhbmQgZGVjb2Rpbmcgc2NoZW1lIGZvciBkaWdpdGFsIGF1ZGlvLgpUaGlzIEZESyBBQUMgQ29kZWMgc29mdHdhcmUgaXMgaW50ZW5kZWQgdG8gYmUgdXNlZCBvbiBhIHdpZGUgdmFyaWV0eSBvZiBBbmRyb2lkIGRldmljZXMuCgpBQUMncyBIRS1BQUMgYW5kIEhFLUFBQyB2MiB2ZXJzaW9ucyBhcmUgcmVnYXJkZWQgYXMgdG9kYXkncyBtb3N0IGVmZmljaWVudCBnZW5lcmFsIHBlcmNlcHR1YWwKYXVkaW8gY29kZWNzLiBBQUMtRUxEIGlzIGNvbnNpZGVyZWQgdGhlIGJlc3QtcGVyZm9ybWluZyBmdWxsLWJhbmR3aWR0aCBjb21tdW5pY2F0aW9ucyBjb2RlYyBieQppbmRlcGVuZGVudCBzdHVkaWVzIGFuZCBpcyB3aWRlbHkgZGVwbG95ZWQuIEFBQyBoYXMgYmVlbiBzdGFuZGFyZGl6ZWQgYnkgSVNPIGFuZCBJRUMgYXMgcGFydApvZiB0aGUgTVBFRyBzcGVjaWZpY2F0aW9ucy4KClBhdGVudCBsaWNlbnNlcyBmb3IgbmVjZXNzYXJ5IHBhdGVudCBjbGFpbXMgZm9yIHRoZSBGREsgQUFDIENvZGVjIChpbmNsdWRpbmcgdGhvc2Ugb2YgRnJhdW5ob2ZlcikKbWF5IGJlIG9idGFpbmVkIHRocm91Z2ggVmlhIExpY2Vuc2luZyAod3d3LnZpYWxpY2Vuc2luZy5jb20pIG9yIHRocm91Z2ggdGhlIHJlc3BlY3RpdmUgcGF0ZW50IG93bmVycwppbmRpdmlkdWFsbHkgZm9yIHRoZSBwdXJwb3NlIG9mIGVuY29kaW5nIG9yIGRlY29kaW5nIGJpdCBzdHJlYW1zIGluIHByb2R1Y3RzIHRoYXQgYXJlIGNvbXBsaWFudCB3aXRoCnRoZSBJU08vSUVDIE1QRUcgYXVkaW8gc3RhbmRhcmRzLiBQbGVhc2Ugbm90ZSB0aGF0IG1vc3QgbWFudWZhY3R1cmVycyBvZiBBbmRyb2lkIGRldmljZXMgYWxyZWFkeSBsaWNlbnNlCnRoZXNlIHBhdGVudCBjbGFpbXMgdGhyb3VnaCBWaWEgTGljZW5zaW5nIG9yIGRpcmVjdGx5IGZyb20gdGhlIHBhdGVudCBvd25lcnMsIGFuZCB0aGVyZWZvcmUgRkRLIEFBQyBDb2RlYwpzb2Z0d2FyZSBtYXkgYWxyZWFkeSBiZSBjb3ZlcmVkIHVuZGVyIHRob3NlIHBhdGVudCBsaWNlbnNlcyB3aGVuIGl0IGlzIHVzZWQgZm9yIHRob3NlIGxpY2Vuc2VkIHB1cnBvc2VzIG9ubHkuCgpDb21tZXJjaWFsbHktbGljZW5zZWQgQUFDIHNvZnR3YXJlIGxpYnJhcmllcywgaW5jbHVkaW5nIGZsb2F0aW5nLXBvaW50IHZlcnNpb25zIHdpdGggZW5oYW5jZWQgc291bmQgcXVhbGl0eSwKYXJlIGFsc28gYXZhaWxhYmxlIGZyb20gRnJhdW5ob2Zlci4gVXNlcnMgYXJlIGVuY291cmFnZWQgdG8gY2hlY2sgdGhlIEZyYXVuaG9mZXIgd2Vic2l0ZSBmb3IgYWRkaXRpb25hbAphcHBsaWNhdGlvbnMgaW5mb3JtYXRpb24gYW5kIGRvY3VtZW50YXRpb24uCgoyLiAgICBDT1BZUklHSFQgTElDRU5TRQoKUmVkaXN0cmlidXRpb24gYW5kIHVzZSBpbiBzb3VyY2UgYW5kIGJpbmFyeSBmb3Jtcywgd2l0aCBvciB3aXRob3V0IG1vZGlmaWNhdGlvbiwgYXJlIHBlcm1pdHRlZCB3aXRob3V0CnBheW1lbnQgb2YgY29weXJpZ2h0IGxpY2Vuc2UgZmVlcyBwcm92aWRlZCB0aGF0IHlvdSBzYXRpc2Z5IHRoZSBmb2xsb3dpbmcgY29uZGl0aW9uczoKCllvdSBtdXN0IHJldGFpbiB0aGUgY29tcGxldGUgdGV4dCBvZiB0aGlzIHNvZnR3YXJlIGxpY2Vuc2UgaW4gcmVkaXN0cmlidXRpb25zIG9mIHRoZSBGREsgQUFDIENvZGVjIG9yCnlvdXIgbW9kaWZpY2F0aW9ucyB0aGVyZXRvIGluIHNvdXJjZSBjb2RlIGZvcm0uCgpZb3UgbXVzdCByZXRhaW4gdGhlIGNvbXBsZXRlIHRleHQgb2YgdGhpcyBzb2Z0d2FyZSBsaWNlbnNlIGluIHRoZSBkb2N1bWVudGF0aW9uIGFuZC9vciBvdGhlciBtYXRlcmlhbHMKcHJvdmlkZWQgd2l0aCByZWRpc3RyaWJ1dGlvbnMgb2YgdGhlIEZESyBBQUMgQ29kZWMgb3IgeW91ciBtb2RpZmljYXRpb25zIHRoZXJldG8gaW4gYmluYXJ5IGZvcm0uCllvdSBtdXN0IG1ha2UgYXZhaWxhYmxlIGZyZWUgb2YgY2hhcmdlIGNvcGllcyBvZiB0aGUgY29tcGxldGUgc291cmNlIGNvZGUgb2YgdGhlIEZESyBBQUMgQ29kZWMgYW5kIHlvdXIKbW9kaWZpY2F0aW9ucyB0aGVyZXRvIHRvIHJlY2lwaWVudHMgb2YgY29waWVzIGluIGJpbmFyeSBmb3JtLgoKVGhlIG5hbWUgb2YgRnJhdW5ob2ZlciBtYXkgbm90IGJlIHVzZWQgdG8gZW5kb3JzZSBvciBwcm9tb3RlIHByb2R1Y3RzIGRlcml2ZWQgZnJvbSB0aGlzIGxpYnJhcnkgd2l0aG91dApwcmlvciB3cml0dGVuIHBlcm1pc3Npb24uCgpZb3UgbWF5IG5vdCBjaGFyZ2UgY29weXJpZ2h0IGxpY2Vuc2UgZmVlcyBmb3IgYW55b25lIHRvIHVzZSwgY29weSBvciBkaXN0cmlidXRlIHRoZSBGREsgQUFDIENvZGVjCnNvZnR3YXJlIG9yIHlvdXIgbW9kaWZpY2F0aW9ucyB0aGVyZXRvLgoKWW91ciBtb2RpZmllZCB2ZXJzaW9ucyBvZiB0aGUgRkRLIEFBQyBDb2RlYyBtdXN0IGNhcnJ5IHByb21pbmVudCBub3RpY2VzIHN0YXRpbmcgdGhhdCB5b3UgY2hhbmdlZCB0aGUgc29mdHdhcmUKYW5kIHRoZSBkYXRlIG9mIGFueSBjaGFuZ2UuIEZvciBtb2RpZmllZCB2ZXJzaW9ucyBvZiB0aGUgRkRLIEFBQyBDb2RlYywgdGhlIHRlcm0KIkZyYXVuaG9mZXIgRkRLIEFBQyBDb2RlYyBMaWJyYXJ5IGZvciBBbmRyb2lkIiBtdXN0IGJlIHJlcGxhY2VkIGJ5IHRoZSB0ZXJtCiJUaGlyZC1QYXJ0eSBNb2RpZmllZCBWZXJzaW9uIG9mIHRoZSBGcmF1bmhvZmVyIEZESyBBQUMgQ29kZWMgTGlicmFyeSBmb3IgQW5kcm9pZC4iCgozLiAgICBOTyBQQVRFTlQgTElDRU5TRQoKTk8gRVhQUkVTUyBPUiBJTVBMSUVEIExJQ0VOU0VTIFRPIEFOWSBQQVRFTlQgQ0xBSU1TLCBpbmNsdWRpbmcgd2l0aG91dCBsaW1pdGF0aW9uIHRoZSBwYXRlbnRzIG9mIEZyYXVuaG9mZXIsCkFSRSBHUkFOVEVEIEJZIFRISVMgU09GVFdBUkUgTElDRU5TRS4gRnJhdW5ob2ZlciBwcm92aWRlcyBubyB3YXJyYW50eSBvZiBwYXRlbnQgbm9uLWluZnJpbmdlbWVudCB3aXRoCnJlc3BlY3QgdG8gdGhpcyBzb2Z0d2FyZS4KCllvdSBtYXkgdXNlIHRoaXMgRkRLIEFBQyBDb2RlYyBzb2Z0d2FyZSBvciBtb2RpZmljYXRpb25zIHRoZXJldG8gb25seSBmb3IgcHVycG9zZXMgdGhhdCBhcmUgYXV0aG9yaXplZApieSBhcHByb3ByaWF0ZSBwYXRlbnQgbGljZW5zZXMuCgo0LiAgICBESVNDTEFJTUVSCgpUaGlzIEZESyBBQUMgQ29kZWMgc29mdHdhcmUgaXMgcHJvdmlkZWQgYnkgRnJhdW5ob2ZlciBvbiBiZWhhbGYgb2YgdGhlIGNvcHlyaWdodCBob2xkZXJzIGFuZCBjb250cmlidXRvcnMKIkFTIElTIiBhbmQgV0lUSE9VVCBBTlkgRVhQUkVTUyBPUiBJTVBMSUVEIFdBUlJBTlRJRVMsIGluY2x1ZGluZyBidXQgbm90IGxpbWl0ZWQgdG8gdGhlIGltcGxpZWQgd2FycmFudGllcwpvZiBtZXJjaGFudGFiaWxpdHkgYW5kIGZpdG5lc3MgZm9yIGEgcGFydGljdWxhciBwdXJwb3NlLiBJTiBOTyBFVkVOVCBTSEFMTCBUSEUgQ09QWVJJR0hUIEhPTERFUiBPUgpDT05UUklCVVRPUlMgQkUgTElBQkxFIGZvciBhbnkgZGlyZWN0LCBpbmRpcmVjdCwgaW5jaWRlbnRhbCwgc3BlY2lhbCwgZXhlbXBsYXJ5LCBvciBjb25zZXF1ZW50aWFsIGRhbWFnZXMsCmluY2x1ZGluZyBidXQgbm90IGxpbWl0ZWQgdG8gcHJvY3VyZW1lbnQgb2Ygc3Vic3RpdHV0ZSBnb29kcyBvciBzZXJ2aWNlczsgbG9zcyBvZiB1c2UsIGRhdGEsIG9yIHByb2ZpdHMsCm9yIGJ1c2luZXNzIGludGVycnVwdGlvbiwgaG93ZXZlciBjYXVzZWQgYW5kIG9uIGFueSB0aGVvcnkgb2YgbGlhYmlsaXR5LCB3aGV0aGVyIGluIGNvbnRyYWN0LCBzdHJpY3QKbGlhYmlsaXR5LCBvciB0b3J0IChpbmNsdWRpbmcgbmVnbGlnZW5jZSksIGFyaXNpbmcgaW4gYW55IHdheSBvdXQgb2YgdGhlIHVzZSBvZiB0aGlzIHNvZnR3YXJlLCBldmVuIGlmCmFkdmlzZWQgb2YgdGhlIHBvc3NpYmlsaXR5IG9mIHN1Y2ggZGFtYWdlLgoKNS4gICAgQ09OVEFDVCBJTkZPUk1BVElPTgoKRnJhdW5ob2ZlciBJbnN0aXR1dGUgZm9yIEludGVncmF0ZWQgQ2lyY3VpdHMgSUlTCkF0dGVudGlvbjogQXVkaW8gYW5kIE11bHRpbWVkaWEgRGVwYXJ0bWVudHMgLSBGREsgQUFDIExMCkFtIFdvbGZzbWFudGVsIDMzCjkxMDU4IEVybGFuZ2VuLCBHZXJtYW55Cgp3d3cuaWlzLmZyYXVuaG9mZXIuZGUvYW1tCmFtbS1pbmZvQGlpcy5mcmF1bmhvZmVyLmRlCi0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tICovCgovKiEKICBcZmlsZQogIFxicmllZiAgU2JyIGRlY29kZXIgIAogIFRoaXMgbW9kdWxlIHByb3ZpZGVzIHRoZSBhY3R1YWwgZGVjb2RlciBpbXBsZW1lbnRhdGlvbi4gVGhlIFNCUiBkYXRhIChzaWRlIGluZm9ybWF0aW9uKSBpcyBhbHJlYWR5CiAgZGVjb2RlZC4gT25seSB0aHJlZSBmdW5jdGlvbnMgYXJlIHByb3ZpZGVkOgoKICBcbGkgMS4pIGNyZWF0ZVNickRlYygpOiBPbmUgdGltZSBpbml0aWFsaXphdGlvbgogIFxsaSAyLikgcmVzZXRTYnJEZWMoKTogQ2FsbGVkIGJ5IHNicl9BcHBseSgpIHdoZW4gdGhlIGluZm9ybWF0aW9uIGNvbnRhaW5lZCBpbiBhbiBTQlJfSEVBREVSX0VMRU1FTlQgcmVxdWlyZXMgYSByZXNldAogIGFuZCByZWNhbGN1bGF0aW9uIG9mIGltcG9ydGFudCBTQlIgc3RydWN0dXJlcy4KICBcbGkgMy4pIHNicl9kZWMoKTogVGhlIGFjdHVhbCBkZWNvZGVyLiBDYWxscyB0aGUgZGlmZmVyZW50IHRvb2xzIHN1Y2ggYXMgZmlsdGVyYmFua3MsIGxwcFRyYW5zcG9zZXIoKSwgYW5kIGNhbGN1bGF0ZVNickVudmVsb3BlKCkKICBbdGhlIGVudmVsb3BlIGFkanVzdGVyXS4KCiAgXHNhIHNicl9kZWMoKSwgXHJlZiBkb2N1bWVudGF0aW9uT3ZlcnZpZXcKKi8KCiNpbmNsdWRlICJzYnJfZGVjLmgiCgojaW5jbHVkZSAic2JyX3JhbS5oIgojaW5jbHVkZSAiZW52X2V4dHIuaCIKI2luY2x1ZGUgImVudl9jYWxjLmgiCiNpbmNsdWRlICJzY2FsZS5oIgoKI2luY2x1ZGUgImdlbmVyaWNTdGRzLmgiCgojaW5jbHVkZSAic2JyZGVjX2RyYy5oIgoKCgpzdGF0aWMgdm9pZCBhc3NpZ25MY1RpbWVTbG90cyggSEFORExFX1NCUl9ERUMgaFNickRlYywgICAgICAgICAgICAgICAgICAgICAvKiE8IGhhbmRsZSB0byBEZWNvZGVyIGNoYW5uZWwgKi8KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEZJWFBfREJMICAqKlFtZkJ1ZmZlclJlYWwsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBpbnQgbm9Db2xzICkKewogIGludCBzbG90LCBpOwogIEZJWFBfREJMICAqcHRyOwoKICAvKiBOdW1iZXIgb2YgUU1GIHRpbWVzbG90cyBpbiB0aGUgb3ZlcmxhcCBidWZmZXI6ICovCiAgcHRyID0gaFNickRlYy0+cFNick92ZXJsYXBCdWZmZXI7CiAgZm9yKHNsb3Q9MDsgc2xvdDxoU2JyRGVjLT5McHBUcmFucy5wU2V0dGluZ3MtPm92ZXJsYXA7IHNsb3QrKykgewogICAgUW1mQnVmZmVyUmVhbFtzbG90XSA9IHB0cjsgcHRyICs9ICg2NCk7CiAgfQoKICAvKiBBc3NpZ24gdGltZXNsb3RzIHRvIFdvcmtidWZmZXIxICovCiAgcHRyID0gaFNickRlYy0+V29ya0J1ZmZlcjE7CiAgZm9yKGk9MDsgaTxub0NvbHM7IGkrKykgewogICAgUW1mQnVmZmVyUmVhbFtzbG90XSA9IHB0cjsgcHRyICs9ICg2NCk7CiAgICBzbG90Kys7CiAgfQp9CgoKc3RhdGljIHZvaWQgYXNzaWduSHFUaW1lU2xvdHMoIEhBTkRMRV9TQlJfREVDIGhTYnJEZWMsICAgICAgICAgICAgICAgICAgICAgLyohPCBoYW5kbGUgdG8gRGVjb2RlciBjaGFubmVsICovCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBGSVhQX0RCTCAgKipRbWZCdWZmZXJSZWFsLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRklYUF9EQkwgICoqUW1mQnVmZmVySW1hZywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGludCBub0NvbHMgKQp7CiAgRklYUF9EQkwgICpwdHI7CiAgaW50IHNsb3Q7CgogIC8qIE51bWJlciBvZiBRTUYgdGltZXNsb3RzIGluIG9uZSBoYWxmIG9mIGEgZnJhbWUgKHNpemUgb2YgV29ya2J1ZmZlcjEgb3IgMik6ICovCiAgaW50IGhhbGZsZW4gPSAobm9Db2xzID4+IDEpICsgaFNickRlYy0+THBwVHJhbnMucFNldHRpbmdzLT5vdmVybGFwOwogIGludCB0b3RDb2xzID0gbm9Db2xzICsgaFNickRlYy0+THBwVHJhbnMucFNldHRpbmdzLT5vdmVybGFwOwoKICAvKiBOdW1iZXIgb2YgUU1GIHRpbWVzbG90cyBpbiB0aGUgb3ZlcmxhcCBidWZmZXI6ICovCiAgcHRyID0gaFNickRlYy0+cFNick92ZXJsYXBCdWZmZXI7CiAgZm9yKHNsb3Q9MDsgc2xvdDxoU2JyRGVjLT5McHBUcmFucy5wU2V0dGluZ3MtPm92ZXJsYXA7IHNsb3QrKykgewogICAgUW1mQnVmZmVyUmVhbFtzbG90XSA9IHB0cjsgcHRyICs9ICg2NCk7CiAgICBRbWZCdWZmZXJJbWFnW3Nsb3RdID0gcHRyOyBwdHIgKz0gKDY0KTsKICB9CgogIC8qIEFzc2lnbiBmaXJzdCBoYWxmIG9mIHRpbWVzbG90cyB0byBXb3JrYnVmZmVyMSAqLwogIHB0ciA9IGhTYnJEZWMtPldvcmtCdWZmZXIxOwogIGZvcig7IHNsb3Q8aGFsZmxlbjsgc2xvdCsrKSB7CiAgICBRbWZCdWZmZXJSZWFsW3Nsb3RdID0gcHRyOyBwdHIgKz0gKDY0KTsKICAgIFFtZkJ1ZmZlckltYWdbc2xvdF0gPSBwdHI7IHB0ciArPSAoNjQpOwogIH0KCiAgLyogQXNzaWduIHNlY29uZCBoYWxmIG9mIHRpbWVzbG90cyB0byBXb3JrYnVmZmVyMiAqLwogIHB0ciA9IGhTYnJEZWMtPldvcmtCdWZmZXIyOwogIGZvcig7IHNsb3Q8dG90Q29sczsgc2xvdCsrKSB7CiAgICBRbWZCdWZmZXJSZWFsW3Nsb3RdID0gcHRyOyBwdHIgKz0gKDY0KTsKICAgIFFtZkJ1ZmZlckltYWdbc2xvdF0gPSBwdHI7IHB0ciArPSAoNjQpOwogIH0KfQoKCnN0YXRpYyB2b2lkIGFzc2lnblRpbWVTbG90cyggSEFORExFX1NCUl9ERUMgaFNickRlYywgICAgICAgICAgICAgICAgICAgICAvKiE8IGhhbmRsZSB0byBEZWNvZGVyIGNoYW5uZWwgKi8KICAgICAgICAgICAgICAgICAgICAgICAgICAgICBpbnQgbm9Db2xzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgIGludCB1c2VMUCApCnsKIC8qIGFzc2lnbiBxbWYgdGltZSBzbG90cyAqLwogIGhTYnJEZWMtPnVzZUxQID0gdXNlTFA7CiAgaWYgKHVzZUxQKSB7CiAgICBoU2JyRGVjLT5TeW50aGVzaXNRTUYuZmxhZ3MgfD0gUU1GX0ZMQUdfTFA7CiAgICBoU2JyRGVjLT5BbmFseXNpc2NRTUYuZmxhZ3MgfD0gUU1GX0ZMQUdfTFA7CiAgfSBlbHNlIHsKICAgIGhTYnJEZWMtPlN5bnRoZXNpc1FNRi5mbGFncyAmPSB+UU1GX0ZMQUdfTFA7CiAgICBoU2JyRGVjLT5BbmFseXNpc2NRTUYuZmxhZ3MgJj0gflFNRl9GTEFHX0xQOwogIH0KICBpZiAoIXVzZUxQKQogICAgYXNzaWduSHFUaW1lU2xvdHMoIGhTYnJEZWMsIGhTYnJEZWMtPlFtZkJ1ZmZlclJlYWwsIGhTYnJEZWMtPlFtZkJ1ZmZlckltYWcsIG5vQ29scyApOwogIGVsc2UKICB7CiAgICBhc3NpZ25MY1RpbWVTbG90cyggaFNickRlYywgaFNickRlYy0+UW1mQnVmZmVyUmVhbCwgbm9Db2xzICk7CiAgfQp9CgpzdGF0aWMgdm9pZCBjaGFuZ2VRbWZUeXBlKCBIQU5ETEVfU0JSX0RFQyBoU2JyRGVjLCAgICAgICAgICAgICAgICAgICAgIC8qITwgaGFuZGxlIHRvIERlY29kZXIgY2hhbm5lbCAqLwogICAgICAgICAgICAgICAgICAgICAgICAgICBpbnQgdXNlTGRUaW1lQWxpZ24gKQp7CiAgVUlOVCBzeW5RbWZGbGFncyA9IGhTYnJEZWMtPlN5bnRoZXNpc1FNRi5mbGFnczsKICBVSU5UIGFuYVFtZkZsYWdzID0gaFNickRlYy0+QW5hbHlzaXNjUU1GLmZsYWdzOwogIGludCAgcmVzZXRTeW5RbWYgPSAwOwogIGludCAgcmVzZXRBbmFRbWYgPSAwOwoKICAvKiBhc3NpZ24gcW1mIHR5cGUgKi8KICBpZiAodXNlTGRUaW1lQWxpZ24pIHsKICAgIGlmIChzeW5RbWZGbGFncyAmIFFNRl9GTEFHX0NMREZCKSB7CiAgICAgIC8qIGNoYW5nZSB0aGUgdHlwZSB0byBNUFNMRCAqLwogICAgICBzeW5RbWZGbGFncyAmPSB+UU1GX0ZMQUdfQ0xERkI7CiAgICAgIHN5blFtZkZsYWdzIHw9ICBRTUZfRkxBR19NUFNMREZCOwogICAgICByZXNldFN5blFtZiA9IDE7CiAgICB9CiAgICBpZiAoYW5hUW1mRmxhZ3MgJiBRTUZfRkxBR19DTERGQikgewogICAgICAvKiBjaGFuZ2UgdGhlIHR5cGUgdG8gTVBTTEQgKi8KICAgICAgYW5hUW1mRmxhZ3MgJj0gflFNRl9GTEFHX0NMREZCOwogICAgICBhbmFRbWZGbGFncyB8PSAgUU1GX0ZMQUdfTVBTTERGQjsKICAgICAgcmVzZXRBbmFRbWYgPSAxOwogICAgfQogIH0gZWxzZSB7CiAgICBpZiAoc3luUW1mRmxhZ3MgJiBRTUZfRkxBR19NUFNMREZCKSB7CiAgICAgIC8qIGNoYW5nZSB0aGUgdHlwZSB0byBDTERGQiAqLwogICAgICBzeW5RbWZGbGFncyAmPSB+UU1GX0ZMQUdfTVBTTERGQjsKICAgICAgc3luUW1mRmxhZ3MgfD0gIFFNRl9GTEFHX0NMREZCOwogICAgICByZXNldFN5blFtZiA9IDE7CiAgICB9CiAgICBpZiAoYW5hUW1mRmxhZ3MgJiBRTUZfRkxBR19NUFNMREZCKSB7CiAgICAgIC8qIGNoYW5nZSB0aGUgdHlwZSB0byBDTERGQiAqLwogICAgICBhbmFRbWZGbGFncyAmPSB+UU1GX0ZMQUdfTVBTTERGQjsKICAgICAgYW5hUW1mRmxhZ3MgfD0gIFFNRl9GTEFHX0NMREZCOwogICAgICByZXNldEFuYVFtZiA9IDE7CiAgICB9CiAgfQoKICBpZiAocmVzZXRBbmFRbWYpIHsKICAgIGludCBxbWZFcnIgPSBxbWZJbml0QW5hbHlzaXNGaWx0ZXJCYW5rICgKICAgICAgICAgICAmaFNickRlYy0+QW5hbHlzaXNjUU1GLAogICAgICAgICAgICBoU2JyRGVjLT5hbmFRbWZTdGF0ZXMsCiAgICAgICAgICAgIGhTYnJEZWMtPkFuYWx5c2lzY1FNRi5ub19jb2wsCiAgICAgICAgICAgIGhTYnJEZWMtPkFuYWx5c2lzY1FNRi5sc2IsCiAgICAgICAgICAgIGhTYnJEZWMtPkFuYWx5c2lzY1FNRi51c2IsCiAgICAgICAgICAgIGhTYnJEZWMtPkFuYWx5c2lzY1FNRi5ub19jaGFubmVscywKICAgICAgICAgICAgYW5hUW1mRmxhZ3MgfCBRTUZfRkxBR19LRUVQX1NUQVRFUwogICAgICAgICAgICApOwogICAgaWYgKHFtZkVyciAhPSAwKSB7CiAgICAgIEZES19BU1NFUlQoMCk7CiAgICB9CiAgfQoKICBpZiAocmVzZXRTeW5RbWYpIHsKICAgIGludCBxbWZFcnIgPSBxbWZJbml0U3ludGhlc2lzRmlsdGVyQmFuayAoCiAgICAgICAgICAgJmhTYnJEZWMtPlN5bnRoZXNpc1FNRiwKICAgICAgICAgICAgaFNickRlYy0+cFN5blFtZlN0YXRlcywKICAgICAgICAgICAgaFNickRlYy0+U3ludGhlc2lzUU1GLm5vX2NvbCwKICAgICAgICAgICAgaFNickRlYy0+U3ludGhlc2lzUU1GLmxzYiwKICAgICAgICAgICAgaFNickRlYy0+U3ludGhlc2lzUU1GLnVzYiwKICAgICAgICAgICAgaFNickRlYy0+U3ludGhlc2lzUU1GLm5vX2NoYW5uZWxzLAogICAgICAgICAgICBzeW5RbWZGbGFncyB8IFFNRl9GTEFHX0tFRVBfU1RBVEVTCiAgICAgICAgICAgICk7CgogICAgaWYgKHFtZkVyciAhPSAwKSB7CiAgICAgIEZES19BU1NFUlQoMCk7CiAgICB9CiAgfQp9CgoKLyohCiAgXGJyaWVmICAgICAgU0JSIGRlY29kZXIgY29yZSBmdW5jdGlvbiBmb3Igb25lIGNoYW5uZWwKCiAgXGltYWdlIGh0bWwgIEJ1ZmZlck1nbXREZXRhaWxlZC0xNjMyLnBuZwoKICBCZXNpZGVzIHRoZSBmaWx0ZXIgc3RhdGVzIG9mIHRoZSBRTUYgZmlsdGVyIGJhbmsgYW5kIHRoZSBMUEMtc3RhdGVzIG9mCiAgdGhlIExQUC1UcmFuc3Bvc2VyLCBwcm9jZXNzaW5nIGlzIG1haW5seSBiYXNlZCBvbiBmb3VyIGJ1ZmZlcnM6CiAgI3RpbWVJbiwgI3RpbWVPdXQsICNXb3JrQnVmZmVyMiBhbmQgI092ZXJsYXBCdWZmZXIuIFRoZSAjV29ya0J1ZmZlcjIKICBpcyByZXVzZWQgZm9yIGFsbCBjaGFubmVscyBhbmQgbWlnaHQgYmUgdXNlZCBieSB0aGUgY29yZSBkZWNvZGVyLCBhCiAgc3RhdGljIG92ZXJsYXAgYnVmZmVyIGlzIHJlcXVpcmVkIGZvciBlYWNoIGNoYW5uZWwuIER1IHRvIGluLXBsYWNlCiAgcHJvY2Vzc2luZywgI3RpbWVJbiBhbmQgI3RpbWVPdXQgcG9pbnQgdG8gaWRlbnRpY2FsIGxvY2F0aW9ucy4KCiAgVGhlIHNwZWN0cmFsIGRhdGEgaXMgb3JnYW5pemVkIGluIHNvLWNhbGxlZCBzbG90cywgZWFjaCBzbG90CiAgY29udGFpbmluZyA2NCBiYW5kcyBvZiBjb21wbGV4IGRhdGEuIFRoZSBudW1iZXIgb2Ygc2xvdHMgcGVyIGZyYW1lIGlzCiAgZGVwZW5kZW5kIG9uIHRoZSBmcmFtZSBzaXplLiBGb3IgbXAzUFJPLCB0aGVyZSBhcmUgMTggc2xvdHMgcGVyIGZyYW1lCiAgYW5kIDYgc2xvdHMgcGVyICNPdmVybGFwQnVmZmVyLiBJdCBpcyBub3QgbmVjZXNzYXJ5IHRvIGhhdmUgdGhlIHNsb3RzCiAgaW4gbG9jYXRlZCBjb25zZWN1dGl2ZSBhZGRyZXNzIHJhbmdlcy4KCiAgVG8gb3B0aW1pemUgbWVtb3J5IHVzYWdlIGFuZCB0byBtaW5pbWl6ZSB0aGUgbnVtYmVyIG9mIG1lbW9yeQogIGFjY2Vzc2VzLCB0aGUgbWVtb3J5IG1hbmFnZW1lbnQgaXMgb3JnYW5pemVkIGFzIGZvbGxvd3MgKFNsb3QgbnVtYmVycwogIGJhc2VkIG9uIG1wM1BSTyk6CgogIDEuKSBJbnB1dCB0aW1lIGRvbWFpbiBzaWduYWwgaXMgbG9jYXRlZCBpbiAjdGltZUluLCB0aGUgbGFzdCBzbG90cwogICgwLi41KSBvZiB0aGUgc3BlY3RyYWwgZGF0YSBvZiB0aGUgcHJldmlvdXMgZnJhbWUgYXJlIGxvY2F0ZWQgaW4gdGhlCiAgI092ZXJsYXBCdWZmZXIuIEluIGFkZGl0aW9uLCAjZnJhbWVEYXRhIG9mIHRoZSBjdXJyZW50IGZyYW1lIHJlc2lkZXMKICBpbiB0aGUgdXBwZXIgcGFydCBvZiAjdGltZUluLgoKICAyLikgRHVyaW5nIHRoZSBjcGx4QW5hbHlzaXNRbWZGaWx0ZXJpbmcoKSwgMzIgc2FtcGxlcyBmcm9tICN0aW1lSW4gYXJlIHRyYW5zZm9ybWVkCiAgaW50byBhIHNsb3Qgb2YgdXAgdG8gMzIgY29tcGxleCBzcGVjdHJhbCBsb3cgYmFuZCB2YWx1ZXMgYXQgYQogIHRpbWUuIFRoZSBmaXJzdCBzcGVjdHJhbCBzbG90IC0tIG5yLiA2IC0tIGlzIHdyaXR0ZW4gYXQgc2xvdCBudW1iZXIKICB6ZXJvIG9mICNXb3JrQnVmZmVyMi4gI1dvcmtCdWZmZXIyIHdpbGwgYmUgY29tcGxldGVseSBmaWxsZWQgd2l0aAogIHNwZWN0cmFsIGRhdGEuCgogIDMuKSBMUFAtVHJhbnNwb3NpdGlvbiBpbiBscHBUcmFuc3Bvc2VyKCkgaXMgcHJvY2Vzc2VkIG9uIDI0IHNsb3RzLiBEdXJpbmcgdGhlCiAgdHJhbnNwb3NpdGlvbiwgdGhlIGhpZ2ggYmFuZCBwYXJ0IG9mIHRoZSBzcGVjdHJhbCBkYXRhIGlzIHJlcGxpY2F0ZWQKICBiYXNlZCBvbiB0aGUgbG93IGJhbmQgZGF0YS4KCiAgRW52ZWxvcGUgQWRqdXN0bWVudCBpcyBwcm9jZXNzZWQgb24gdGhlIGhpZ2ggYmFuZCBwYXJ0IG9mIHRoZSBzcGVjdHJhbAogIGRhdGEgb25seSBieSBjYWxjdWxhdGVTYnJFbnZlbG9wZSgpLgoKICA0LikgVGhlIGNwbHhTeW50aGVzaXNRbWZGaWx0ZXJpbmcoKSBjcmVhdGVzIDY0IHRpbWUgZG9tYWluIHNhbXBsZXMgb3V0CiAgb2YgYSBzbG90IG9mIDY0IGNvbXBsZXggc3BlY3RyYWwgdmFsdWVzIGF0IGEgdGltZS4gVGhlIGZpcnN0IDYgc2xvdHMKICBpbiAjdGltZU91dCBhcmUgZmlsbGVkIGZyb20gdGhlIHJlc3VsdHMgb2Ygc3BlY3RyYWwgc2xvdHMgMC4uNSBpbiB0aGUKICAjT3ZlcmxhcEJ1ZmZlci4gVGhlIGNvbnNlY3V0aXZlIHNsb3RzIGluIHRpbWVPdXQgYXJlIG5vdyBmaWxsZWQgd2l0aAogIHRoZSByZXN1bHRzIG9mIHNwZWN0cmFsIHNsb3RzIDYuLjE3LgoKICA1LikgVGhlIHByZXByb2Nlc3NlZCBzbG90cyAxOC4uMjMgaGF2ZSB0byBiZSBzdG9yZWQgaW4gdGhlCiAgI092ZXJsYXBCdWZmZXIuCgoqLwoKdm9pZApzYnJfZGVjICggSEFORExFX1NCUl9ERUMgaFNickRlYywgICAgICAgICAgICAvKiE8IGhhbmRsZSB0byBEZWNvZGVyIGNoYW5uZWwgKi8KICAgICAgICAgIElOVF9QQ00gKnRpbWVJbiwgICAgICAgICAgICAgICAgICAgLyohPCBwb2ludGVyIHRvIGlucHV0IHRpbWUgc2lnbmFsICovCiAgICAgICAgICBJTlRfUENNICp0aW1lT3V0LCAgICAgICAgICAgICAgICAgIC8qITwgcG9pbnRlciB0byBvdXRwdXQgdGltZSBzaWduYWwgKi8KICAgICAgICAgIEhBTkRMRV9TQlJfREVDIGhTYnJEZWNSaWdodCwgICAgICAgLyohPCBoYW5kbGUgdG8gRGVjb2RlciBjaGFubmVsIHJpZ2h0ICovCiAgICAgICAgICBJTlRfUENNICp0aW1lT3V0UmlnaHQsICAgICAgICAgICAgIC8qITwgcG9pbnRlciB0byBvdXRwdXQgdGltZSBzaWduYWwgKi8KICAgICAgICAgIGNvbnN0IGludCBzdHJpZGVJbiwgICAgICAgICAgICAgICAgLyohPCBUaW1lIGRhdGEgdHJhdmVyc2FsIHN0cmlkZUluICovCiAgICAgICAgICBjb25zdCBpbnQgc3RyaWRlT3V0LCAgICAgICAgICAgICAgIC8qITwgVGltZSBkYXRhIHRyYXZlcnNhbCBzdHJpZGVPdXQgKi8KICAgICAgICAgIEhBTkRMRV9TQlJfSEVBREVSX0RBVEEgaEhlYWRlckRhdGEsLyohPCBTdGF0aWMgY29udHJvbCBkYXRhICovCiAgICAgICAgICBIQU5ETEVfU0JSX0ZSQU1FX0RBVEEgaEZyYW1lRGF0YSwgIC8qITwgQ29udHJvbCBkYXRhIG9mIGN1cnJlbnQgZnJhbWUgKi8KICAgICAgICAgIEhBTkRMRV9TQlJfUFJFVl9GUkFNRV9EQVRBIGhQcmV2RnJhbWVEYXRhLCAgLyohPCBTb21lIGNvbnRyb2wgZGF0YSBvZiBsYXN0IGZyYW1lICovCiAgICAgICAgICBjb25zdCBpbnQgYXBwbHlQcm9jZXNzaW5nLCAgICAgICAgIC8qITwgRmxhZyBmb3IgU0JSIG9wZXJhdGlvbiAqLwogICAgICAgICAgSEFORExFX1BTX0RFQyBoX3BzX2QsCiAgICAgICAgICBjb25zdCBVSU5UIGZsYWdzCiAgICAgICAgICkKewogIGludCBpLCBzbG90LCByZXNlcnZlOwogIGludCBzYXZlTGJTY2FsZTsKICBpbnQgb3ZfbGVuOwogIGludCBsYXN0U2xvdE9mZnM7CiAgRklYUF9EQkwgbWF4VmFsOwoKICAvKiAxKzEvMyBmcmFtZXMgb2Ygc3BlY3RyYWwgZGF0YTogKi8KICBGSVhQX0RCTCAqKlFtZkJ1ZmZlclJlYWwgPSBoU2JyRGVjLT5RbWZCdWZmZXJSZWFsOwogIEZJWFBfREJMICoqUW1mQnVmZmVySW1hZyA9IGhTYnJEZWMtPlFtZkJ1ZmZlckltYWc7CgogLyogTnVtYmVyIG9mIFFNRiB0aW1lc2xvdHMgaW4gdGhlIG92ZXJsYXAgYnVmZmVyOiAqLwogb3ZfbGVuID0gaFNickRlYy0+THBwVHJhbnMucFNldHRpbmdzLT5vdmVybGFwOwoKIC8qIE51bWJlciBvZiBRTUYgc2xvdHMgcGVyIGZyYW1lICovCiAgaW50IG5vQ29scyA9IGhIZWFkZXJEYXRhLT5udW1iZXJUaW1lU2xvdHMgKiBoSGVhZGVyRGF0YS0+dGltZVN0ZXA7CgogLyogYXNzaWduIHFtZiB0aW1lIHNsb3RzICovCiAgaWYgKCAoKGZsYWdzICYgU0JSREVDX0xPV19QT1dFUiApID8gMSA6IDApICE9ICgoaFNickRlYy0+U3ludGhlc2lzUU1GLmZsYWdzICYgUU1GX0ZMQUdfTFApID8gMSA6IDApICkgewogICAgYXNzaWduVGltZVNsb3RzKCBoU2JyRGVjLCBoSGVhZGVyRGF0YS0+bnVtYmVyVGltZVNsb3RzICogaEhlYWRlckRhdGEtPnRpbWVTdGVwLCBmbGFncyAmIFNCUkRFQ19MT1dfUE9XRVIpOwogIH0KCiAgaWYgKGZsYWdzICYgU0JSREVDX0VMRF9HUklEKSB7CiAgICAvKiBDaG9vc2UgdGhlIHJpZ2h0IGxvdyBkZWxheSBmaWx0ZXIgYmFuayAqLwogICAgY2hhbmdlUW1mVHlwZSggaFNickRlYywgKGZsYWdzICYgU0JSREVDX0xEX01QU19RTUYpID8gMSA6IDAgKTsKICB9CgogIC8qCiAgICBsb3cgYmFuZCBjb2RlYyBzaWduYWwgc3ViYmFuZCBmaWx0ZXJpbmcKICAgKi8KCiAgewogICAgQ19BQUxMT0NfU0NSQVRDSF9TVEFSVChxbWZUZW1wLCBGSVhQX0RCTCwgMiooNjQpKTsKCiAgICBxbWZBbmFseXNpc0ZpbHRlcmluZyggJmhTYnJEZWMtPkFuYWx5c2lzY1FNRiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgUW1mQnVmZmVyUmVhbCArIG92X2xlbiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgUW1mQnVmZmVySW1hZyArIG92X2xlbiwKICAgICAgICAgICAgICAgICAgICAgICAgICAmaFNickRlYy0+c2JyU2NhbGVGYWN0b3IsCiAgICAgICAgICAgICAgICAgICAgICAgICAgIHRpbWVJbiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgc3RyaWRlSW4sCiAgICAgICAgICAgICAgICAgICAgICAgICAgIHFtZlRlbXAKICAgICAgICAgICAgICAgICAgICAgICAgICk7CgogICAgQ19BQUxMT0NfU0NSQVRDSF9FTkQocW1mVGVtcCwgRklYUF9EQkwsIDIqKDY0KSk7CiAgfQoKICAvKgogICAgQ2xlYXIgdXBwZXIgaGFsZiBvZiBzcGVjdHJ1bQogICovCiAgewogICAgaW50IG5BbmFseXNpc0JhbmRzID0gaEhlYWRlckRhdGEtPm51bWJlck9mQW5hbHlzaXNCYW5kczsKCiAgICBpZiAoISAoZmxhZ3MgJiBTQlJERUNfTE9XX1BPV0VSKSkgewogICAgICBmb3IgKHNsb3QgPSBvdl9sZW47IHNsb3QgPCBub0NvbHMrb3ZfbGVuOyBzbG90KyspIHsKICAgICAgICBGREttZW1jbGVhcigmUW1mQnVmZmVyUmVhbFtzbG90XVtuQW5hbHlzaXNCYW5kc10sKCg2NCktbkFuYWx5c2lzQmFuZHMpKnNpemVvZihGSVhQX0RCTCkpOwogICAgICAgIEZES21lbWNsZWFyKCZRbWZCdWZmZXJJbWFnW3Nsb3RdW25BbmFseXNpc0JhbmRzXSwoKDY0KS1uQW5hbHlzaXNCYW5kcykqc2l6ZW9mKEZJWFBfREJMKSk7CiAgICAgIH0KICAgIH0gZWxzZQogICAgZm9yIChzbG90ID0gb3ZfbGVuOyBzbG90IDwgbm9Db2xzK292X2xlbjsgc2xvdCsrKSB7CiAgICAgIEZES21lbWNsZWFyKCZRbWZCdWZmZXJSZWFsW3Nsb3RdW25BbmFseXNpc0JhbmRzXSwoKDY0KS1uQW5hbHlzaXNCYW5kcykqc2l6ZW9mKEZJWFBfREJMKSk7CiAgICB9CiAgfQoKCgogIC8qCiAgICBTaGlmdCBzcGVjdHJhbCBkYXRhIGxlZnQgdG8gZ2FpbiBhY2N1cmFjeSBpbiB0cmFuc3Bvc2VyIGFuZCBhZGp1c3RvcgogICovCiAgbWF4VmFsID0gbWF4U3ViYmFuZFNhbXBsZSggUW1mQnVmZmVyUmVhbCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIChmbGFncyAmIFNCUkRFQ19MT1dfUE9XRVIpID8gTlVMTCA6IFFtZkJ1ZmZlckltYWcsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgMCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICBoU2JyRGVjLT5BbmFseXNpc2NRTUYubHNiLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgIG92X2xlbiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICBub0NvbHMrb3ZfbGVuICk7CgogIHJlc2VydmUgPSBmaXhNYXgoMCxDbnRMZWFkaW5nWmVyb3MobWF4VmFsKS0xKSA7CiAgcmVzZXJ2ZSA9IGZpeE1pbihyZXNlcnZlLERGUkFDVF9CSVRTLTEtaFNickRlYy0+c2JyU2NhbGVGYWN0b3IubGJfc2NhbGUpOwoKICAvKiBJZiBhbGwgZGF0YSBpcyB6ZXJvLCBsYl9zY2FsZSBjb3VsZCBiZWNvbWUgdG9vIGxhcmdlICovCiAgcmVzY2FsZVN1YmJhbmRTYW1wbGVzKCBRbWZCdWZmZXJSZWFsLAogICAgICAgICAgICAgICAgICAgICAgICAgKGZsYWdzICYgU0JSREVDX0xPV19QT1dFUikgPyBOVUxMIDogUW1mQnVmZmVySW1hZywKICAgICAgICAgICAgICAgICAgICAgICAgIDAsCiAgICAgICAgICAgICAgICAgICAgICAgICBoU2JyRGVjLT5BbmFseXNpc2NRTUYubHNiLAogICAgICAgICAgICAgICAgICAgICAgICAgb3ZfbGVuLAogICAgICAgICAgICAgICAgICAgICAgICAgbm9Db2xzK292X2xlbiwKICAgICAgICAgICAgICAgICAgICAgICAgIHJlc2VydmUpOwoKICBoU2JyRGVjLT5zYnJTY2FsZUZhY3Rvci5sYl9zY2FsZSArPSByZXNlcnZlOwoKICAvKgogICAgc2F2ZSBsb3cgYmFuZCBzY2FsZSwgd2F2ZWNvZGluZyBvciBwYXJhbWV0cmljIHN0ZXJlbyBtYXkgbW9kaWZ5IGl0CiAgKi8KICBzYXZlTGJTY2FsZSA9IGhTYnJEZWMtPnNiclNjYWxlRmFjdG9yLmxiX3NjYWxlOwoKCiAgaWYgKGFwcGx5UHJvY2Vzc2luZykKICB7CiAgICBVQ0hBUiAqIGJvcmRlcnMgPSBoRnJhbWVEYXRhLT5mcmFtZUluZm8uYm9yZGVyczsKICAgIGxhc3RTbG90T2ZmcyA9ICBib3JkZXJzW2hGcmFtZURhdGEtPmZyYW1lSW5mby5uRW52ZWxvcGVzXSAtIGhIZWFkZXJEYXRhLT5udW1iZXJUaW1lU2xvdHM7CgogICAgRklYUF9EQkwgZGVncmVlQWxpYXNbKDY0KV07CgogICAgLyogVGhlIHRyYW5zcG9zZXIgd2lsbCBvdmVycmlkZSBtb3N0IHZhbHVlcyBpbiBkZWdyZWVBbGlhc1tdLgogICAgICAgVGhlIGFycmF5IG5lZWRzIHRvIGJlIGNsZWFyZWQgYXQgbGVhc3QgZnJvbSBsb3dTdWJiYW5kIHRvIGhpZ2hTdWJiYW5kIGJlZm9yZS4gKi8KICAgIGlmIChmbGFncyAmIFNCUkRFQ19MT1dfUE9XRVIpCiAgICAgIEZES21lbWNsZWFyKCZkZWdyZWVBbGlhc1toSGVhZGVyRGF0YS0+ZnJlcUJhbmREYXRhLmxvd1N1YmJhbmRdLCAoaEhlYWRlckRhdGEtPmZyZXFCYW5kRGF0YS5oaWdoU3ViYmFuZC1oSGVhZGVyRGF0YS0+ZnJlcUJhbmREYXRhLmxvd1N1YmJhbmQpKnNpemVvZihGSVhQX0RCTCkpOwoKICAgIC8qCiAgICAgIEludmVyc2UgZmlsdGVyaW5nIG9mIGxvd2JhbmQgYW5kIHRyYW5zcG9zaXRpb24gaW50byB0aGUgU0JSLWZyZXF1ZW5jeSByYW5nZQogICAgKi8KCiAgICBscHBUcmFuc3Bvc2VyICggJmhTYnJEZWMtPkxwcFRyYW5zLAogICAgICAgICAgICAgICAgICAgICZoU2JyRGVjLT5zYnJTY2FsZUZhY3RvciwKICAgICAgICAgICAgICAgICAgICBRbWZCdWZmZXJSZWFsLAogICAgICAgICAgICAgICAgICAgIGRlZ3JlZUFsaWFzLCAgICAgICAgICAgICAgICAgIC8vIG9ubHkgdXNlZCBpZiB1c2VMUCA9IDEKICAgICAgICAgICAgICAgICAgICBRbWZCdWZmZXJJbWFnLAogICAgICAgICAgICAgICAgICAgIGZsYWdzICYgU0JSREVDX0xPV19QT1dFUiwKICAgICAgICAgICAgICAgICAgICBoSGVhZGVyRGF0YS0+dGltZVN0ZXAsCiAgICAgICAgICAgICAgICAgICAgYm9yZGVyc1swXSwKICAgICAgICAgICAgICAgICAgICBsYXN0U2xvdE9mZnMsCiAgICAgICAgICAgICAgICAgICAgaEhlYWRlckRhdGEtPmZyZXFCYW5kRGF0YS5uSW52ZkJhbmRzLAogICAgICAgICAgICAgICAgICAgIGhGcmFtZURhdGEtPnNicl9pbnZmX21vZGUsCiAgICAgICAgICAgICAgICAgICAgaFByZXZGcmFtZURhdGEtPnNicl9pbnZmX21vZGUgKTsKCgoKCgogICAgLyoKICAgICAgQWRqdXN0IGVudmVsb3BlIG9mIGN1cnJlbnQgZnJhbWUuCiAgICAqLwoKICAgIGNhbGN1bGF0ZVNickVudmVsb3BlICgmaFNickRlYy0+c2JyU2NhbGVGYWN0b3IsCiAgICAgICAgICAgICAgICAgICAgICAgICAgJmhTYnJEZWMtPlNickNhbGN1bGF0ZUVudmVsb3BlLAogICAgICAgICAgICAgICAgICAgICAgICAgIGhIZWFkZXJEYXRhLAogICAgICAgICAgICAgICAgICAgICAgICAgIGhGcmFtZURhdGEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgUW1mQnVmZmVyUmVhbCwKICAgICAgICAgICAgICAgICAgICAgICAgICBRbWZCdWZmZXJJbWFnLAogICAgICAgICAgICAgICAgICAgICAgICAgIGZsYWdzICYgU0JSREVDX0xPV19QT1dFUiwKCiAgICAgICAgICAgICAgICAgICAgICAgICAgZGVncmVlQWxpYXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgZmxhZ3MsCiAgICAgICAgICAgICAgICAgICAgICAgICAgKGhIZWFkZXJEYXRhLT5mcmFtZUVycm9yRmxhZyB8fCBoUHJldkZyYW1lRGF0YS0+ZnJhbWVFcnJvckZsYWcpKTsKCgogICAgLyoKICAgICAgVXBkYXRlIGhQcmV2RnJhbWVEYXRhICh0byBiZSB1c2VkIGluIHRoZSBuZXh0IGZyYW1lKQogICAgKi8KICAgIGZvciAoaT0wOyBpPGhIZWFkZXJEYXRhLT5mcmVxQmFuZERhdGEubkludmZCYW5kczsgaSsrKSB7CiAgICAgIGhQcmV2RnJhbWVEYXRhLT5zYnJfaW52Zl9tb2RlW2ldID0gaEZyYW1lRGF0YS0+c2JyX2ludmZfbW9kZVtpXTsKICAgIH0KICAgIGhQcmV2RnJhbWVEYXRhLT5jb3VwbGluZyA9IGhGcmFtZURhdGEtPmNvdXBsaW5nOwogICAgaFByZXZGcmFtZURhdGEtPnN0b3BQb3MgPSBib3JkZXJzW2hGcmFtZURhdGEtPmZyYW1lSW5mby5uRW52ZWxvcGVzXTsKICAgIGhQcmV2RnJhbWVEYXRhLT5hbXBSZXMgPSBoRnJhbWVEYXRhLT5hbXBSZXNvbHV0aW9uQ3VycmVudEZyYW1lOwogIH0KICBlbHNlIHsKICAgIC8qIFJlc2V0IGhiX3NjYWxlIGlmIG5vIGhpZ2hiYW5kIGlzIHByZXNlbnQsIGJlY2F1c2UgaGJfc2NhbGUgaXMgY29uc2lkZXJlZCBpbiB0aGUgUU1GLXN5bnRoZXNpcyAqLwogICAgaFNickRlYy0+c2JyU2NhbGVGYWN0b3IuaGJfc2NhbGUgPSBzYXZlTGJTY2FsZTsKICB9CgoKICBmb3IgKGk9MDsgaTxMUENfT1JERVI7IGkrKyl7CiAgICAvKgogICAgICBTdG9yZSB0aGUgdW5tb2RpZmllZCBxbWYgU2xvdHMgdmFsdWVzIChyZXF1aXJlZCBmb3IgTFBDIGZpbHRlcmluZykKICAgICovCiAgICBpZiAoISAoZmxhZ3MgJiBTQlJERUNfTE9XX1BPV0VSKSkgewogICAgICBGREttZW1jcHkoaFNickRlYy0+THBwVHJhbnMubHBjRmlsdGVyU3RhdGVzUmVhbFtpXSwgUW1mQnVmZmVyUmVhbFtub0NvbHMtTFBDX09SREVSK2ldLCBoU2JyRGVjLT5BbmFseXNpc2NRTUYubHNiKnNpemVvZihGSVhQX0RCTCkpOwogICAgICBGREttZW1jcHkoaFNickRlYy0+THBwVHJhbnMubHBjRmlsdGVyU3RhdGVzSW1hZ1tpXSwgUW1mQnVmZmVySW1hZ1tub0NvbHMtTFBDX09SREVSK2ldLCBoU2JyRGVjLT5BbmFseXNpc2NRTUYubHNiKnNpemVvZihGSVhQX0RCTCkpOwogICAgfSBlbHNlCiAgICBGREttZW1jcHkoaFNickRlYy0+THBwVHJhbnMubHBjRmlsdGVyU3RhdGVzUmVhbFtpXSwgUW1mQnVmZmVyUmVhbFtub0NvbHMtTFBDX09SREVSK2ldLCBoU2JyRGVjLT5BbmFseXNpc2NRTUYubHNiKnNpemVvZihGSVhQX0RCTCkpOwogIH0KCiAgLyoKICAgIFN5bnRoZXNpcyBzdWJiYW5kIGZpbHRlcmluZy4KICAqLwoKICBpZiAoICEgKGZsYWdzICYgU0JSREVDX1BTX0RFQ09ERUQpICkgewoKICAgIHsKICAgICAgaW50IG91dFNjYWxlZmFjdG9yID0gMDsKCiAgICAgIGlmIChoX3BzX2QgIT0gTlVMTCkgewogICAgICAgIGhfcHNfZC0+cHJvY0ZyYW1lQmFzZWQgPSAxOyAgLyogd2UgaGVyZSBkbyBmcmFtZSBiYXNlZCBwcm9jZXNzaW5nICovCiAgICAgIH0KCgogICAgICBzYnJEZWNvZGVyX2RyY0FwcGx5KCZoU2JyRGVjLT5zYnJEcmNDaGFubmVsLAogICAgICAgICAgICAgICAgICAgICAgICAgICBRbWZCdWZmZXJSZWFsLAogICAgICAgICAgICAgICAgICAgICAgICAgICAoZmxhZ3MgJiBTQlJERUNfTE9XX1BPV0VSKSA/IE5VTEwgOiBRbWZCdWZmZXJJbWFnLAogICAgICAgICAgICAgICAgICAgICAgICAgICBoU2JyRGVjLT5TeW50aGVzaXNRTUYubm9fY29sLAogICAgICAgICAgICAgICAgICAgICAgICAgICZvdXRTY2FsZWZhY3RvcgogICAgICAgICAgICAgICAgICAgICAgICAgICk7CgoKCiAgICAgIHFtZkNoYW5nZU91dFNjYWxlZmFjdG9yKCZoU2JyRGVjLT5TeW50aGVzaXNRTUYsIG91dFNjYWxlZmFjdG9yICk7CgogICAgICB7CiAgICAgICAgQ19BQUxMT0NfU0NSQVRDSF9TVEFSVChxbWZUZW1wLCBGSVhQX0RCTCwgMiooNjQpKTsKCiAgICAgICAgcW1mU3ludGhlc2lzRmlsdGVyaW5nKCAmaFNickRlYy0+U3ludGhlc2lzUU1GLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFFtZkJ1ZmZlclJlYWwsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKGZsYWdzICYgU0JSREVDX0xPV19QT1dFUikgPyBOVUxMIDogUW1mQnVmZmVySW1hZywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICZoU2JyRGVjLT5zYnJTY2FsZUZhY3RvciwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBoU2JyRGVjLT5McHBUcmFucy5wU2V0dGluZ3MtPm92ZXJsYXAsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdGltZU91dCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzdHJpZGVPdXQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcW1mVGVtcCk7CgogICAgICAgIENfQUFMTE9DX1NDUkFUQ0hfRU5EKHFtZlRlbXAsIEZJWFBfREJMLCAyKig2NCkpOwogICAgICB9CgogICAgfQoKICB9IGVsc2UgeyAvKiAoZmxhZ3MgJiBTQlJERUNfUFNfREVDT0RFRCkgKi8KICAgIElOVCBpLCBzZGlmZiwgb3V0U2NhbGVmYWN0b3IsIHNjYWxlRmFjdG9yTG93QmFuZCwgc2NhbGVGYWN0b3JIaWdoQmFuZDsKICAgIFNDSEFSIHNjYWxlRmFjdG9yTG93QmFuZF9vdiwgc2NhbGVGYWN0b3JMb3dCYW5kX25vX292OwoKICAgIEhBTkRMRV9RTUZfRklMVEVSX0JBTksgc3luUW1mICAgICAgPSAmaFNickRlYy0+U3ludGhlc2lzUU1GOwogICAgSEFORExFX1FNRl9GSUxURVJfQkFOSyBzeW5RbWZSaWdodCA9ICZoU2JyRGVjUmlnaHQtPlN5bnRoZXNpc1FNRjsKCiAgICAvKiBhZGFwdCBzY2FsaW5nICovCiAgICBzZGlmZiA9IGhTYnJEZWMtPnNiclNjYWxlRmFjdG9yLmxiX3NjYWxlIC0gcmVzZXJ2ZTsgICAgICAgICAgICAgICAgICAvKiBTY2FsaW5nIGRpZmZlcmVuY2UgICAgICAgICAqLwogICAgc2NhbGVGYWN0b3JIaWdoQmFuZCAgID0gc2RpZmYgLSBoU2JyRGVjLT5zYnJTY2FsZUZhY3Rvci5oYl9zY2FsZTsgICAgLyogU2NhbGUgb2YgY3VycmVudCBoaWdoIGJhbmQgKi8KICAgIHNjYWxlRmFjdG9yTG93QmFuZF9vdiA9IHNkaWZmIC0gaFNickRlYy0+c2JyU2NhbGVGYWN0b3Iub3ZfbGJfc2NhbGU7IC8qIFNjYWxlIG9mIGxvdyBiYW5kIG92ZXJsYXBwaW5nIFFNRiBkYXRhICovCiAgICBzY2FsZUZhY3Rvckxvd0JhbmRfbm9fb3YgPSBzZGlmZiAtIGhTYnJEZWMtPnNiclNjYWxlRmFjdG9yLmxiX3NjYWxlOyAvKiBTY2FsZSBvZiBsb3cgYmFuZCBjdXJyZW50IFFNRiBkYXRhICAgICAqLwogICAgb3V0U2NhbGVmYWN0b3IgID0gMDsgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgLyogSW5pdGlhbCBvdXRwdXQgc2NhbGUgKi8KCiAgICBpZiAoaF9wc19kLT5wcm9jRnJhbWVCYXNlZCA9PSAxKSAgICAvKiBJZiB3ZSBoYXZlIHN3aXRjaGVkIGZyb20gZnJhbWUgdG8gc2xvdCBiYXNlZCBwcm9jZXNzaW5nIGNvcHkgZmlsdGVyIHN0YXRlcyAqLwogICAgeyAvKiBwcm9jRnJhbWVCYXNlZCB3aWxsIGJlIHVuc2V0IGxhdGVyICovCiAgICAgIC8qIGNvcHkgZmlsdGVyIHN0YXRlcyBmcm9tIGxlZnQgdG8gcmlnaHQgKi8KICAgICAgRkRLbWVtY3B5KHN5blFtZlJpZ2h0LT5GaWx0ZXJTdGF0ZXMsIHN5blFtZi0+RmlsdGVyU3RhdGVzLCAoKDY0MCktKDY0KSkqc2l6ZW9mKEZJWFBfUVNTKSk7CiAgICB9CgogICAgLyogc2NhbGUgQUxMIHFtZiB2YWxlcyAoIHJlYWwgYW5kIGltYWcgKSBvZiBtb25vIC8gbGVmdCBjaGFubmVsIHRvIHRoZQogICAgICAgc2FtZSBzY2FsZSBmYWN0b3IgKCBvdl9sYl9zZiwgbGJfc2YgYW5kIGhxX3NmICkgICAgICAgICAgICAgICAgICAgICAgKi8KICAgIHNjYWxGaWx0ZXJCYW5rVmFsdWVzKCBoX3BzX2QsICAgICAgICAgICAgICAgICAgICAgICAgICAgICAvKiBwYXJhbWV0cmljIHN0ZXJlbyBkZWNvZGVyIGhhbmRsZSAgICAgKi8KICAgICAgICAgICAgICAgICAgICAgICAgICBRbWZCdWZmZXJSZWFsLCAgICAgICAgICAgICAgICAgICAgICAvKiBxbWYgZmlsdGVyYmFuayB2YWx1ZXMgICAgICAgICAgICAgICAgKi8KICAgICAgICAgICAgICAgICAgICAgICAgICBRbWZCdWZmZXJJbWFnLCAgICAgICAgICAgICAgICAgICAgICAvKiBxbWYgZmlsdGVyYmFuayB2YWx1ZXMgICAgICAgICAgICAgICAgKi8KICAgICAgICAgICAgICAgICAgICAgICAgICBzeW5RbWYtPmxzYiwgICAgICAgICAgICAgICAgICAgICAgICAvKiBzYnIgc3RhcnQgc3ViYmFuZCAgICAgICAgICAgICAgICAgICAgKi8KICAgICAgICAgICAgICAgICAgICAgICAgICBoU2JyRGVjLT5zYnJTY2FsZUZhY3Rvci5vdl9sYl9zY2FsZSwKICAgICAgICAgICAgICAgICAgICAgICAgICBoU2JyRGVjLT5zYnJTY2FsZUZhY3Rvci5sYl9zY2FsZSwKICAgICAgICAgICAgICAgICAgICAgICAgICZzY2FsZUZhY3Rvckxvd0JhbmRfb3YsICAgICAgICAgICAgICAvKiBhZGFwdCBzY2FsaW5nIHZhbHVlcyAqLwogICAgICAgICAgICAgICAgICAgICAgICAgJnNjYWxlRmFjdG9yTG93QmFuZF9ub19vdiwgICAgICAgICAgIC8qIGFkYXB0IHNjYWxpbmcgdmFsdWVzICovCiAgICAgICAgICAgICAgICAgICAgICAgICAgaFNickRlYy0+c2JyU2NhbGVGYWN0b3IuaGJfc2NhbGUsICAgLyogY3VycmVudCBmcmFtZSAoIGhpZ2hiYW5kICkgKi8KICAgICAgICAgICAgICAgICAgICAgICAgICZzY2FsZUZhY3RvckhpZ2hCYW5kLAogICAgICAgICAgICAgICAgICAgICAgICAgIHN5blFtZi0+bm9fY29sKTsKCiAgICAvKiB1c2UgdGhlIHNhbWUgc3ludGhlc2UgcW1mIHZhbHVlcyBmb3IgbGVmdCBhbmQgcmlnaHQgY2hhbm5lbCAqLwogICAgc3luUW1mUmlnaHQtPm5vX2NvbCA9IHN5blFtZi0+bm9fY29sOwogICAgc3luUW1mUmlnaHQtPmxzYiAgICA9IHN5blFtZi0+bHNiOwogICAgc3luUW1mUmlnaHQtPnVzYiAgICA9IHN5blFtZi0+dXNiOwoKICAgIGludCBlbnY9MDsKCiAgICAgIG91dFNjYWxlZmFjdG9yICs9IChTQ0FMX0hFQURST09NKzEpOyAvKiBwc0RpZmZTY2FsZSEgKi8KCiAgICB7CiAgICAgIENfQUFMTE9DX1NDUkFUQ0hfU1RBUlQocFdvcmtCdWZmZXIsIEZJWFBfREJMLCAyKig2NCkpOwoKICAgICAgaW50IG1heFNoaWZ0ID0gMDsKCiAgICAgIGlmIChoU2JyRGVjLT5zYnJEcmNDaGFubmVsLmVuYWJsZSAhPSAwKSB7CiAgICAgICAgaWYgKGhTYnJEZWMtPnNickRyY0NoYW5uZWwucHJldkZhY3RfZXhwID4gbWF4U2hpZnQpIHsKICAgICAgICAgIG1heFNoaWZ0ID0gaFNickRlYy0+c2JyRHJjQ2hhbm5lbC5wcmV2RmFjdF9leHA7CiAgICAgICAgfQogICAgICAgIGlmIChoU2JyRGVjLT5zYnJEcmNDaGFubmVsLmN1cnJGYWN0X2V4cCA+IG1heFNoaWZ0KSB7CiAgICAgICAgICBtYXhTaGlmdCA9IGhTYnJEZWMtPnNickRyY0NoYW5uZWwuY3VyckZhY3RfZXhwOwogICAgICAgIH0KICAgICAgICBpZiAoaFNickRlYy0+c2JyRHJjQ2hhbm5lbC5uZXh0RmFjdF9leHAgPiBtYXhTaGlmdCkgewogICAgICAgICAgbWF4U2hpZnQgPSBoU2JyRGVjLT5zYnJEcmNDaGFubmVsLm5leHRGYWN0X2V4cDsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8qIGNvcHkgRFJDIGRhdGEgdG8gcmlnaHQgY2hhbm5lbCAod2l0aCBQUyBib3RoIGNoYW5uZWxzIHVzZSB0aGUgc2FtZSBEUkMgZ2FpbnMpICovCiAgICAgIEZES21lbWNweSgmaFNickRlY1JpZ2h0LT5zYnJEcmNDaGFubmVsLCAmaFNickRlYy0+c2JyRHJjQ2hhbm5lbCwgc2l6ZW9mKFNCUkRFQ19EUkNfQ0hBTk5FTCkpOwoKICAgICAgZm9yIChpID0gMDsgaSA8IHN5blFtZi0+bm9fY29sOyBpKyspIHsgIC8qIC0tLS0tIG5vX2NvbCBsb29wIC0tLS0tICovCgogICAgICAgIElOVCBvdXRTY2FsZWZhY3RvclIsIG91dFNjYWxlZmFjdG9yTDsKICAgICAgICBvdXRTY2FsZWZhY3RvclIgPSBvdXRTY2FsZWZhY3RvckwgPSBvdXRTY2FsZWZhY3RvcjsKCiAgICAgICAgLyogcW1mIHRpbWVzbG90IG9mIHJpZ2h0IGNoYW5uZWwgKi8KICAgICAgICBGSVhQX0RCTCogclFtZlJlYWwgPSBwV29ya0J1ZmZlcjsKICAgICAgICBGSVhQX0RCTCogclFtZkltYWcgPSBwV29ya0J1ZmZlciArIDY0OwoKCiAgICAgICAgewogICAgICAgICAgaWYgKCBpID09IGhfcHNfZC0+YnNEYXRhW2hfcHNfZC0+cHJvY2Vzc1Nsb3RdLm1wZWcuYUVudlN0YXJ0U3RvcFtlbnZdICkgewogICAgICAgICAgICBpbml0U2xvdEJhc2VkUm90YXRpb24oIGhfcHNfZCwgZW52LCBoSGVhZGVyRGF0YS0+ZnJlcUJhbmREYXRhLmhpZ2hTdWJiYW5kICk7CiAgICAgICAgICAgIGVudisrOwogICAgICAgICAgfQoKICAgICAgICAgIEFwcGx5UHNTbG90KCBoX3BzX2QsICAgICAgICAgICAgICAgICAgIC8qIHBhcmFtZXRyaWMgc3RlcmVvIGRlY29kZXIgaGFuZGxlICAqLwogICAgICAgICAgICAgICAgICAgICAgKFFtZkJ1ZmZlclJlYWwgKyBpKSwgICAgICAgLyogb25lIHRpbWVzbG90IG9mIGxlZnQvbW9ubyBjaGFubmVsICovCiAgICAgICAgICAgICAgICAgICAgICAoUW1mQnVmZmVySW1hZyArIGkpLCAgICAgICAvKiBvbmUgdGltZXNsb3Qgb2YgbGVmdC9tb25vIGNoYW5uZWwgKi8KICAgICAgICAgICAgICAgICAgICAgICByUW1mUmVhbCwgICAgICAgICAgICAgICAgIC8qIG9uZSB0aW1lc2xvdCBvciByaWdodCBjaGFubmVsICAgICAqLwogICAgICAgICAgICAgICAgICAgICAgIHJRbWZJbWFnKTsgICAgICAgICAgICAgICAgLyogb25lIHRpbWVzbG90IG9yIHJpZ2h0IGNoYW5uZWwgICAgICovCiAgICAgICAgfQoKCiAgICAgICAgc2NhbGVGYWN0b3JMb3dCYW5kID0gKGk8KDYpKSA/IHNjYWxlRmFjdG9yTG93QmFuZF9vdiA6IHNjYWxlRmFjdG9yTG93QmFuZF9ub19vdjsKCgogICAgICAgIHNickRlY29kZXJfZHJjQXBwbHlTbG90ICggLyogcmlnaHQgY2hhbm5lbCAqLwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmaFNickRlY1JpZ2h0LT5zYnJEcmNDaGFubmVsLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgclFtZlJlYWwsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICByUW1mSW1hZywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzeW5RbWZSaWdodC0+bm9fY29sLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgbWF4U2hpZnQKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICApOwoKICAgICAgICBvdXRTY2FsZWZhY3RvclIgKz0gbWF4U2hpZnQ7CgogICAgICAgIHNickRlY29kZXJfZHJjQXBwbHlTbG90ICggLyogbGVmdCBjaGFubmVsICovCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICZoU2JyRGVjLT5zYnJEcmNDaGFubmVsLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAqKFFtZkJ1ZmZlclJlYWwgKyBpKSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKihRbWZCdWZmZXJJbWFnICsgaSksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc3luUW1mLT5ub19jb2wsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBtYXhTaGlmdAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICk7CgogICAgICAgIG91dFNjYWxlZmFjdG9yTCArPSBtYXhTaGlmdDsKCgogICAgICAgIC8qIHNjYWxlIGZpbHRlciBzdGF0ZXMgZm9yIGxlZnQgYW5kIHJpZ2h0IGNoYW5uZWwgKi8KICAgICAgICBxbWZDaGFuZ2VPdXRTY2FsZWZhY3Rvciggc3luUW1mLCBvdXRTY2FsZWZhY3RvckwgKTsKICAgICAgICBxbWZDaGFuZ2VPdXRTY2FsZWZhY3Rvciggc3luUW1mUmlnaHQsIG91dFNjYWxlZmFjdG9yUiApOwoKICAgICAgICB7CgogICAgICAgICAgcW1mU3ludGhlc2lzRmlsdGVyaW5nU2xvdCggc3luUW1mUmlnaHQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICByUW1mUmVhbCwgICAgICAgICAgICAgICAgLyogUU1GIHJlYWwgYnVmZmVyICovCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICByUW1mSW1hZywgICAgICAgICAgICAgICAgLyogUU1GIGltYWcgYnVmZmVyICovCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzY2FsZUZhY3Rvckxvd0JhbmQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzY2FsZUZhY3RvckhpZ2hCYW5kLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdGltZU91dFJpZ2h0KyhpKnN5blFtZi0+bm9fY2hhbm5lbHMqc3RyaWRlT3V0KSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHN0cmlkZU91dCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHBXb3JrQnVmZmVyKTsKCiAgICAgICAgICBxbWZTeW50aGVzaXNGaWx0ZXJpbmdTbG90KCBzeW5RbWYsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKihRbWZCdWZmZXJSZWFsICsgaSksICAgICAgLyogUU1GIHJlYWwgYnVmZmVyICovCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKihRbWZCdWZmZXJJbWFnICsgaSksICAgICAgLyogUU1GIGltYWcgYnVmZmVyICovCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzY2FsZUZhY3Rvckxvd0JhbmQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzY2FsZUZhY3RvckhpZ2hCYW5kLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdGltZU91dCsoaSpzeW5RbWYtPm5vX2NoYW5uZWxzKnN0cmlkZU91dCksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzdHJpZGVPdXQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBwV29ya0J1ZmZlcik7CgogICAgICAgIH0KICAgICAgfSAvKiBub19jb2wgbG9vcCAgaSAgKi8KCiAgICAgIC8qIHNjYWxlIGJhY2sgKDYpIHRpbWVzbG90cyBsb29rIGFoZWFkIGZvciBoeWJyaWQgZmlsdGVyYmFuayB0byBvcmlnaW5hbCB2YWx1ZSAqLwogICAgICByZXNjYWxGaWx0ZXJCYW5rVmFsdWVzKCBoX3BzX2QsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFFtZkJ1ZmZlclJlYWwsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFFtZkJ1ZmZlckltYWcsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHN5blFtZi0+bHNiLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzeW5RbWYtPm5vX2NvbCApOwoKICAgICAgQ19BQUxMT0NfU0NSQVRDSF9FTkQocFdvcmtCdWZmZXIsIEZJWFBfREJMLCAyKig2NCkpOwogICAgfQogIH0KCiAgc2JyRGVjb2Rlcl9kcmNVcGRhdGVDaGFubmVsKCAmaFNickRlYy0+c2JyRHJjQ2hhbm5lbCApOwoKCiAgLyoKICAgIFVwZGF0ZSBvdmVybGFwIGJ1ZmZlcgogICAgRXZlbiBiYW5kcyBhYm92ZSB1c2IgYXJlIGNvcGllZCB0byBhdm9pZCBvdXRkYXRlZCBzcGVjdHJhbCBkYXRhIGluIGNhc2UKICAgIHRoZSBzdG9wIGZyZXF1ZW5jeSByYWlzZXMuCiAgKi8KCiAgaWYgKGhTYnJEZWMtPkxwcFRyYW5zLnBTZXR0aW5ncy0+b3ZlcmxhcCA+IDApCiAgewogICAgaWYgKCEgKGZsYWdzICYgU0JSREVDX0xPV19QT1dFUikpIHsKICAgICAgZm9yICggaT0wOyBpPGhTYnJEZWMtPkxwcFRyYW5zLnBTZXR0aW5ncy0+b3ZlcmxhcDsgaSsrICkgewogICAgICAgIEZES21lbWNweShRbWZCdWZmZXJSZWFsW2ldLCBRbWZCdWZmZXJSZWFsW2krbm9Db2xzXSwgKDY0KSpzaXplb2YoRklYUF9EQkwpKTsKICAgICAgICBGREttZW1jcHkoUW1mQnVmZmVySW1hZ1tpXSwgUW1mQnVmZmVySW1hZ1tpK25vQ29sc10sICg2NCkqc2l6ZW9mKEZJWFBfREJMKSk7CiAgICAgIH0KICAgIH0gZWxzZQogICAgICBmb3IgKCBpPTA7IGk8aFNickRlYy0+THBwVHJhbnMucFNldHRpbmdzLT5vdmVybGFwOyBpKysgKSB7CiAgICAgICAgRkRLbWVtY3B5KFFtZkJ1ZmZlclJlYWxbaV0sIFFtZkJ1ZmZlclJlYWxbaStub0NvbHNdLCAoNjQpKnNpemVvZihGSVhQX0RCTCkpOwogICAgICB9CiAgfQoKICBoU2JyRGVjLT5zYnJTY2FsZUZhY3Rvci5vdl9sYl9zY2FsZSA9IHNhdmVMYlNjYWxlOwoKICAvKiBTYXZlIGN1cnJlbnQgZnJhbWUgc3RhdHVzICovCiAgaFByZXZGcmFtZURhdGEtPmZyYW1lRXJyb3JGbGFnID0gaEhlYWRlckRhdGEtPmZyYW1lRXJyb3JGbGFnOwoKfSAvLyBzYnJfZGVjKCkKCgovKiEKICBcYnJpZWYgICAgIENyZWF0ZXMgc2JyIGRlY29kZXIgc3RydWN0dXJlCiAgXHJldHVybiAgICBlcnJvckNvZGUsIDAgaWYgc3VjY2Vzc2Z1bAoqLwpTQlJfRVJST1IKY3JlYXRlU2JyRGVjIChTQlJfQ0hBTk5FTCAqIGhTYnJDaGFubmVsLAogICAgICAgICAgICAgIEhBTkRMRV9TQlJfSEVBREVSX0RBVEEgaEhlYWRlckRhdGEsIC8qITwgU3RhdGljIGNvbnRyb2wgZGF0YSAqLwogICAgICAgICAgICAgIFRSQU5TUE9TRVJfU0VUVElOR1MgKnBTZXR0aW5ncywKICAgICAgICAgICAgICBjb25zdCBpbnQgICAgIGRvd25zYW1wbGVGYWMsICAgICAgICAvKiE8IERvd25zYW1wbGluZyBmYWN0b3IgKi8KICAgICAgICAgICAgICBjb25zdCBVSU5UICAgIHFtZkZsYWdzLCAgICAgICAgICAgICAvKiE8IGZsYWdzIC0+IDE6IEhRL0xQIHNlbGVjdG9yLCAyOiBDTERGQiAqLwogICAgICAgICAgICAgIGNvbnN0IFVJTlQgICAgZmxhZ3MsCiAgICAgICAgICAgICAgY29uc3QgaW50ICAgICBvdmVybGFwLCAKICAgICAgICAgICAgICBpbnQgICAgICAgICAgIGNoYW4pICAgICAgICAgICAgICAgICAvKiE8IENoYW5uZWwgZm9yIHdoaWNoIHRvIGFzc2lnbiBidWZmZXJzIGV0Yy4gKi8KCnsKICBTQlJfRVJST1IgZXJyID0gU0JSREVDX09LOwogIGludCB0aW1lU2xvdHMgPSBoSGVhZGVyRGF0YS0+bnVtYmVyVGltZVNsb3RzOyAgIC8qIE51bWJlciBvZiBTQlIgc2xvdHMgcGVyIGZyYW1lICovCiAgaW50IG5vQ29scyA9IHRpbWVTbG90cyAqIGhIZWFkZXJEYXRhLT50aW1lU3RlcDsgLyogTnVtYmVyIG9mIFFNRiBzbG90cyBwZXIgZnJhbWUgKi8KICBIQU5ETEVfU0JSX0RFQyBocyA9ICYoaFNickNoYW5uZWwtPlNickRlYyk7CgogIC8qIEluaXRpYWxpemUgc2NhbGUgZmFjdG9ycyAqLwogIGhzLT5zYnJTY2FsZUZhY3Rvci5vdl9sYl9zY2FsZSAgPSAwOwogIGhzLT5zYnJTY2FsZUZhY3Rvci5vdl9oYl9zY2FsZSAgPSAwOwogIGhzLT5zYnJTY2FsZUZhY3Rvci5oYl9zY2FsZSAgICAgPSAwOwoKCiAgLyoKICAgIGNyZWF0ZSBlbnZlbG9wZSBjYWxjdWxhdG9yCiAgKi8KICBlcnIgPSBjcmVhdGVTYnJFbnZlbG9wZUNhbGMgKCZocy0+U2JyQ2FsY3VsYXRlRW52ZWxvcGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBoSGVhZGVyRGF0YSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNoYW4sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBmbGFncyk7CiAgaWYgKGVyciAhPSBTQlJERUNfT0spIHsKICAgIHJldHVybiBlcnI7CiAgfQoKICAvKgogICAgY3JlYXRlIFFNRiBmaWx0ZXIgYmFua3MKICAqLwogIHsKICAgIGludCBxbWZFcnI7CiAgICAvKiBBZGFwdGVkIFFNRiBhbmFseXNpcyBwb3N0LXR3aWRkbGVzIGZvciBkb3duLXNhbXBsZWQgSFEgU0JSICovCiAgICBjb25zdCBVSU5UIGRvd25TYW1wbGVkRmxhZyA9IChkb3duc2FtcGxlRmFjPT0yKSA/IFFNRl9GTEFHX0RPV05TQU1QTEVEIDogMDsKCiAgICBxbWZFcnIgPSBxbWZJbml0QW5hbHlzaXNGaWx0ZXJCYW5rICgKICAgICAgICAgICAgICAgICAgICAmaHMtPkFuYWx5c2lzY1FNRiwKICAgICAgICAgICAgICAgICAgICAgaHMtPmFuYVFtZlN0YXRlcywKICAgICAgICAgICAgICAgICAgICAgbm9Db2xzLAogICAgICAgICAgICAgICAgICAgICBoSGVhZGVyRGF0YS0+ZnJlcUJhbmREYXRhLmxvd1N1YmJhbmQsCiAgICAgICAgICAgICAgICAgICAgIGhIZWFkZXJEYXRhLT5mcmVxQmFuZERhdGEuaGlnaFN1YmJhbmQsCiAgICAgICAgICAgICAgICAgICAgIGhIZWFkZXJEYXRhLT5udW1iZXJPZkFuYWx5c2lzQmFuZHMsCiAgICAgICAgICAgICAgICAgICAgIChxbWZGbGFncyAmICh+UU1GX0ZMQUdfS0VFUF9TVEFURVMpKSB8IGRvd25TYW1wbGVkRmxhZwogICAgICAgICAgICAgICAgICAgICApOwogICAgaWYgKHFtZkVyciAhPSAwKSB7CiAgICAgIHJldHVybiBTQlJERUNfVU5TVVBQT1JURURfQ09ORklHOwogICAgfQogIH0KICBpZiAoaHMtPnBTeW5RbWZTdGF0ZXMgPT0gTlVMTCkgewogICAgaHMtPnBTeW5RbWZTdGF0ZXMgPSBHZXRSYW1fc2JyX1FtZlN0YXRlc1N5bnRoZXNpcyhjaGFuKTsKICAgIGlmIChocy0+cFN5blFtZlN0YXRlcyA9PSBOVUxMKQogICAgICByZXR1cm4gU0JSREVDX01FTV9BTExPQ19GQUlMRUQ7CiAgfQoKICB7CiAgICBpbnQgcW1mRXJyOwoKICAgIHFtZkVyciA9IHFtZkluaXRTeW50aGVzaXNGaWx0ZXJCYW5rICgKICAgICAgICAgICAmaHMtPlN5bnRoZXNpc1FNRiwKICAgICAgICAgICAgaHMtPnBTeW5RbWZTdGF0ZXMsCiAgICAgICAgICAgIG5vQ29scywKICAgICAgICAgICAgaEhlYWRlckRhdGEtPmZyZXFCYW5kRGF0YS5sb3dTdWJiYW5kLAogICAgICAgICAgICBoSGVhZGVyRGF0YS0+ZnJlcUJhbmREYXRhLmhpZ2hTdWJiYW5kLAogICAgICAgICAgICAoNjQpIC8gZG93bnNhbXBsZUZhYywKICAgICAgICAgICAgcW1mRmxhZ3MgJiAoflFNRl9GTEFHX0tFRVBfU1RBVEVTKQogICAgICAgICAgICApOwoKICAgIGlmIChxbWZFcnIgIT0gMCkgewogICAgICByZXR1cm4gU0JSREVDX1VOU1VQUE9SVEVEX0NPTkZJRzsKICAgIH0KICB9CiAgaW5pdFNiclByZXZGcmFtZURhdGEgKCZoU2JyQ2hhbm5lbC0+cHJldkZyYW1lRGF0YSwgdGltZVNsb3RzKTsKCiAgLyoKICAgIGNyZWF0ZSB0cmFuc3Bvc2VyCiAgKi8KICBlcnIgPSBjcmVhdGVMcHBUcmFuc3Bvc2VyICgmaHMtPkxwcFRyYW5zLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgIHBTZXR0aW5ncywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICBoSGVhZGVyRGF0YS0+ZnJlcUJhbmREYXRhLmxvd1N1YmJhbmQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaEhlYWRlckRhdGEtPmZyZXFCYW5kRGF0YS52X2tfbWFzdGVyLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgIGhIZWFkZXJEYXRhLT5mcmVxQmFuZERhdGEubnVtTWFzdGVyLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgIGhzLT5TeW50aGVzaXNRTUYudXNiLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgIHRpbWVTbG90cywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICBocy0+QW5hbHlzaXNjUU1GLm5vX2NvbCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICBoSGVhZGVyRGF0YS0+ZnJlcUJhbmREYXRhLmZyZXFCYW5kVGFibGVOb2lzZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICBoSGVhZGVyRGF0YS0+ZnJlcUJhbmREYXRhLm5OZmIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaEhlYWRlckRhdGEtPnNiclByb2NTbXBsUmF0ZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICBjaGFuLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgIG92ZXJsYXAgKTsKICBpZiAoZXJyICE9IFNCUkRFQ19PSykgewogICAgcmV0dXJuIGVycjsKICB9CgogIC8qIFRoZSBDTERGQiBkb2VzIG5vdCBoYXZlIG92ZXJsYXAgKi8KICBpZiAoKHFtZkZsYWdzICYgUU1GX0ZMQUdfQ0xERkIpID09IDApIHsKICAgIGlmIChocy0+cFNick92ZXJsYXBCdWZmZXIgPT0gTlVMTCkgewogICAgICBocy0+cFNick92ZXJsYXBCdWZmZXIgPSBHZXRSYW1fc2JyX092ZXJsYXBCdWZmZXIoY2hhbik7CiAgICAgIGlmIChocy0+cFNick92ZXJsYXBCdWZmZXIgPT0gTlVMTCkgIHsKICAgICAgICByZXR1cm4gU0JSREVDX01FTV9BTExPQ19GQUlMRUQ7CiAgICAgIH0KICAgIH0gZWxzZSB7CiAgICAgIC8qIENsZWFyIG92ZXJsYXAgYnVmZmVyICovCiAgICAgIEZES21lbWNsZWFyKCBocy0+cFNick92ZXJsYXBCdWZmZXIsCiAgICAgICAgICAgICAgICAgICBzaXplb2YoRklYUF9EQkwpICogMiAqICg2KSAqICg2NCkKICAgICAgICAgICAgICAgICApOwogICAgfQogIH0KCiAgLyogYXNzaWduIHFtZiB0aW1lIHNsb3RzICovCiAgYXNzaWduVGltZVNsb3RzKCAmaFNickNoYW5uZWwtPlNickRlYywgaEhlYWRlckRhdGEtPm51bWJlclRpbWVTbG90cyAqIGhIZWFkZXJEYXRhLT50aW1lU3RlcCwgcW1mRmxhZ3MgJiBRTUZfRkxBR19MUCk7CgogIHJldHVybiBlcnI7Cn0KCi8qIQogIFxicmllZiAgICAgRGVsZXRlIHNiciBkZWNvZGVyIHN0cnVjdHVyZQogIFxyZXR1cm4gICAgZXJyb3JDb2RlLCAwIGlmIHN1Y2Nlc3NmdWwKKi8KaW50CmRlbGV0ZVNickRlYyAoU0JSX0NIQU5ORUwgKiBoU2JyQ2hhbm5lbCkKewogIEhBTkRMRV9TQlJfREVDIGhzID0gJmhTYnJDaGFubmVsLT5TYnJEZWM7CgogIGRlbGV0ZVNickVudmVsb3BlQ2FsYyAoJmhzLT5TYnJDYWxjdWxhdGVFbnZlbG9wZSk7CgogIC8qIGRlbGV0ZSBRTUYgZmlsdGVyIHN0YXRlcyAqLwogIGlmIChocy0+cFN5blFtZlN0YXRlcyAhPSBOVUxMKSB7CiAgICBGcmVlUmFtX3Nicl9RbWZTdGF0ZXNTeW50aGVzaXMoJmhzLT5wU3luUW1mU3RhdGVzKTsKICB9CgoKICBpZiAoaHMtPnBTYnJPdmVybGFwQnVmZmVyICE9IE5VTEwpIHsKICAgIEZyZWVSYW1fc2JyX092ZXJsYXBCdWZmZXIoJmhzLT5wU2JyT3ZlcmxhcEJ1ZmZlcik7CiAgfQoKICByZXR1cm4gMDsKfQoKCi8qIQogIFxicmllZiAgICAgcmVzZXRzIHNiciBkZWNvZGVyIHN0cnVjdHVyZQogIFxyZXR1cm4gICAgZXJyb3JDb2RlLCAwIGlmIHN1Y2Nlc3NmdWwKKi8KU0JSX0VSUk9SCnJlc2V0U2JyRGVjIChIQU5ETEVfU0JSX0RFQyBoU2JyRGVjLAogICAgICAgICAgICAgSEFORExFX1NCUl9IRUFERVJfREFUQSBoSGVhZGVyRGF0YSwKICAgICAgICAgICAgIEhBTkRMRV9TQlJfUFJFVl9GUkFNRV9EQVRBIGhQcmV2RnJhbWVEYXRhLAogICAgICAgICAgICAgY29uc3QgaW50IHVzZUxQLAogICAgICAgICAgICAgY29uc3QgaW50IGRvd25zYW1wbGVGYWMKICAgICAgICAgICAgICkKewogIFNCUl9FUlJPUiBzYnJFcnJvciA9IFNCUkRFQ19PSzsKICAKICBpbnQgb2xkX2xzYiA9IGhTYnJEZWMtPlN5bnRoZXNpc1FNRi5sc2I7CiAgaW50IG5ld19sc2IgPSBoSGVhZGVyRGF0YS0+ZnJlcUJhbmREYXRhLmxvd1N1YmJhbmQ7CiAgaW50IGwsIHN0YXJ0QmFuZCwgc3RvcEJhbmQsIHN0YXJ0U2xvdCwgc2l6ZTsKCiAgaW50IHNvdXJjZV9zY2FsZSwgdGFyZ2V0X3NjYWxlLCBkZWx0YV9zY2FsZSwgdGFyZ2V0X2xzYiwgdGFyZ2V0X3VzYiwgcmVzZXJ2ZTsKICBGSVhQX0RCTCBtYXhWYWw7CgogIC8qIG92ZXJsYXBCdWZmZXIgcG9pbnQgdG8gZmlyc3QgKDYpIHNsb3RzICovCiAgRklYUF9EQkwgICoqT3ZlcmxhcEJ1ZmZlclJlYWwgPSBoU2JyRGVjLT5RbWZCdWZmZXJSZWFsOwogIEZJWFBfREJMICAqKk92ZXJsYXBCdWZmZXJJbWFnID0gaFNickRlYy0+UW1mQnVmZmVySW1hZzsKCiAgLyogYXNzaWduIHFtZiB0aW1lIHNsb3RzICovCiAgYXNzaWduVGltZVNsb3RzKCBoU2JyRGVjLCBoSGVhZGVyRGF0YS0+bnVtYmVyVGltZVNsb3RzICogaEhlYWRlckRhdGEtPnRpbWVTdGVwLCB1c2VMUCk7CgoKCiAgcmVzZXRTYnJFbnZlbG9wZUNhbGMgKCZoU2JyRGVjLT5TYnJDYWxjdWxhdGVFbnZlbG9wZSk7CgogIGhTYnJEZWMtPlN5bnRoZXNpc1FNRi5sc2IgPSBoSGVhZGVyRGF0YS0+ZnJlcUJhbmREYXRhLmxvd1N1YmJhbmQ7CiAgaFNickRlYy0+U3ludGhlc2lzUU1GLnVzYiA9IGZpeE1pbigoSU5UKWhTYnJEZWMtPlN5bnRoZXNpc1FNRi5ub19jaGFubmVscywgKElOVCloSGVhZGVyRGF0YS0+ZnJlcUJhbmREYXRhLmhpZ2hTdWJiYW5kKTsKCiAgaFNickRlYy0+QW5hbHlzaXNjUU1GLmxzYiA9IGhTYnJEZWMtPlN5bnRoZXNpc1FNRi5sc2I7CiAgaFNickRlYy0+QW5hbHlzaXNjUU1GLnVzYiA9IGhTYnJEZWMtPlN5bnRoZXNpc1FNRi51c2I7CgoKICAvKgogICAgVGhlIGZvbGxvd2luZyBpbml0aWFsaXphdGlvbiBvZiBzcGVjdHJhbCBkYXRhIGluIHRoZSBvdmVybGFwIGJ1ZmZlcgogICAgaXMgcmVxdWlyZWQgZm9yIGR5bmFtaWMgeC1vdmVyIG9yIGEgY2hhbmdlIG9mIHRoZSBzdGFydC1mcmVxIGZvciAyIHJlYXNvbnM6CgogICAgMS4gSWYgdGhlIGxvd2JhbmQgZ2V0cyBfd2lkZXJfLCB1bmFkanVzdGVkIGRhdGEgd291bGQgcmVtYWluCgogICAgMi4gSWYgdGhlIGxvd2JhbmQgYmVjb21lcyBfc21hbGxlcl8sIHRoZSBoaWdoZXN0IGJhbmRzIG9mIHRoZSBvbGQgbG93YmFuZAogICAgICAgbXVzdCBiZSBjbGVhcmVkIGJlY2F1c2UgdGhlIHdoaXRlbmluZyB3b3VsZCBiZSBhZmZlY3RlZAogICovCiAgc3RhcnRCYW5kID0gb2xkX2xzYjsKICBzdG9wQmFuZCAgPSBuZXdfbHNiOwogIHN0YXJ0U2xvdCA9IGhIZWFkZXJEYXRhLT50aW1lU3RlcCAqIChoUHJldkZyYW1lRGF0YS0+c3RvcFBvcyAtIGhIZWFkZXJEYXRhLT5udW1iZXJUaW1lU2xvdHMpOwogIHNpemUgICAgICA9IGZpeE1heCgwLHN0b3BCYW5kLXN0YXJ0QmFuZCk7CgogIC8qIGtlZXAgYWxyZWFkeSBhZGp1c3RlZCBkYXRhIGluIHRoZSB4LW92ZXItYXJlYSAqLwogIGlmICghdXNlTFApIHsKICAgIGZvciAobD1zdGFydFNsb3Q7IGw8aFNickRlYy0+THBwVHJhbnMucFNldHRpbmdzLT5vdmVybGFwOyBsKyspIHsKICAgICAgRkRLbWVtY2xlYXIoJk92ZXJsYXBCdWZmZXJSZWFsW2xdW3N0YXJ0QmFuZF0sIHNpemUqc2l6ZW9mKEZJWFBfREJMKSk7CiAgICAgIEZES21lbWNsZWFyKCZPdmVybGFwQnVmZmVySW1hZ1tsXVtzdGFydEJhbmRdLCBzaXplKnNpemVvZihGSVhQX0RCTCkpOwogICAgfQogIH0gZWxzZQogIGZvciAobD1zdGFydFNsb3Q7IGw8aFNickRlYy0+THBwVHJhbnMucFNldHRpbmdzLT5vdmVybGFwIDsgbCsrKSB7CiAgICBGREttZW1jbGVhcigmT3ZlcmxhcEJ1ZmZlclJlYWxbbF1bc3RhcnRCYW5kXSwgc2l6ZSpzaXplb2YoRklYUF9EQkwpKTsKICB9CgoKICAvKgogICAgcmVzZXQgTFBDIGZpbHRlciBzdGF0ZXMKICAqLwogIHN0YXJ0QmFuZCA9IGZpeE1pbihvbGRfbHNiLG5ld19sc2IpOwogIHN0b3BCYW5kICA9IGZpeE1heChvbGRfbHNiLG5ld19sc2IpOwogIHNpemUgICAgICA9IGZpeE1heCgwLHN0b3BCYW5kLXN0YXJ0QmFuZCk7CgogIEZES21lbWNsZWFyKCZoU2JyRGVjLT5McHBUcmFucy5scGNGaWx0ZXJTdGF0ZXNSZWFsWzBdW3N0YXJ0QmFuZF0sIHNpemUqc2l6ZW9mKEZJWFBfREJMKSk7CiAgRkRLbWVtY2xlYXIoJmhTYnJEZWMtPkxwcFRyYW5zLmxwY0ZpbHRlclN0YXRlc1JlYWxbMV1bc3RhcnRCYW5kXSwgc2l6ZSpzaXplb2YoRklYUF9EQkwpKTsKICBpZiAoIXVzZUxQKSB7CiAgICBGREttZW1jbGVhcigmaFNickRlYy0+THBwVHJhbnMubHBjRmlsdGVyU3RhdGVzSW1hZ1swXVtzdGFydEJhbmRdLCBzaXplKnNpemVvZihGSVhQX0RCTCkpOwogICAgRkRLbWVtY2xlYXIoJmhTYnJEZWMtPkxwcFRyYW5zLmxwY0ZpbHRlclN0YXRlc0ltYWdbMV1bc3RhcnRCYW5kXSwgc2l6ZSpzaXplb2YoRklYUF9EQkwpKTsKICB9CgoKICAvKgogICAgUmVzY2FsZSBhbHJlYWR5IHByb2Nlc3NlZCBzcGVjdHJhbCBkYXRhIGJldHdlZW4gb2xkIGFuZCBuZXcgeC1vdmVyIGZyZXF1ZW5jeS4KICAgIFRoaXMgbXVzdCBiZSBkb25lIGJlY2F1c2Ugb2YgdGhlIHNlcGFyYXRlIHNjYWxlZmFjdG9ycyBmb3IgbG93YmFuZCBhbmQgaGlnaGJhbmQuCiAgKi8KICBzdGFydEJhbmQgPSBmaXhNaW4ob2xkX2xzYixuZXdfbHNiKTsKICBzdG9wQmFuZCA9ICBmaXhNYXgob2xkX2xzYixuZXdfbHNiKTsKCiAgaWYgKG5ld19sc2IgPiBvbGRfbHNiKSB7CiAgICAvKiBUaGUgeC1vdmVyLWFyZWEgd2FzIHBhcnQgb2YgdGhlIGhpZ2hiYW5kIGJlZm9yZSBhbmQgd2lsbCBub3cgYmVsb25nIHRvIHRoZSBsb3diYW5kICovCiAgICBzb3VyY2Vfc2NhbGUgPSBoU2JyRGVjLT5zYnJTY2FsZUZhY3Rvci5vdl9oYl9zY2FsZTsKICAgIHRhcmdldF9zY2FsZSA9IGhTYnJEZWMtPnNiclNjYWxlRmFjdG9yLm92X2xiX3NjYWxlOwogICAgdGFyZ2V0X2xzYiAgID0gMDsKICAgIHRhcmdldF91c2IgICA9IG9sZF9sc2I7CiAgfQogIGVsc2UgewogICAgLyogVGhlIHgtb3Zlci1hcmVhIHdhcyBwYXJ0IG9mIHRoZSBsb3diYW5kIGJlZm9yZSBhbmQgd2lsbCBub3cgYmVsb25nIHRvIHRoZSBoaWdoYmFuZCAqLwogICAgc291cmNlX3NjYWxlID0gaFNickRlYy0+c2JyU2NhbGVGYWN0b3Iub3ZfbGJfc2NhbGU7CiAgICB0YXJnZXRfc2NhbGUgPSBoU2JyRGVjLT5zYnJTY2FsZUZhY3Rvci5vdl9oYl9zY2FsZTsKICAgIC8qIGpkcjogVGhlIHZhbHVlcyBvbGRfbHNiIGFuZCBvbGRfdXNiIG1pZ2h0IGJlIHdyb25nIGJlY2F1c2UgdGhlIHByZXZpb3VzIGZyYW1lIG1pZ2h0IGhhdmUgYmVlbiAidXBzYW1saW5nIi4gKi8KICAgIHRhcmdldF9sc2IgICA9IGhTYnJEZWMtPlN5bnRoZXNpc1FNRi5sc2I7CiAgICB0YXJnZXRfdXNiICAgPSBoU2JyRGVjLT5TeW50aGVzaXNRTUYudXNiOwogIH0KCiAgLyogU2hpZnQgbGVmdCBhbGwgc2FtcGxlcyBvZiB0aGUgeC1vdmVyLWFyZWEgYXMgbXVjaCBhcyBwb3NzaWJsZQogICAgIEFuIHVubmVjZXNzYXJ5IGNvYXJzZSBzY2FsZSBjb3VsZCBjYXVzZSBvdl9sYl9zY2FsZSBvciBvdl9oYl9zY2FsZSB0byBiZQogICAgIGFkYXB0ZWQgYW5kIHRoZSBhY2N1cmFjeSBpbiB0aGUgbmV4dCBmcmFtZSB3b3VsZCBzZXJpb3VzbHkgc3VmZmVyISAqLwoKICBtYXhWYWwgPSBtYXhTdWJiYW5kU2FtcGxlKCBPdmVybGFwQnVmZmVyUmVhbCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAodXNlTFApID8gTlVMTCA6IE92ZXJsYXBCdWZmZXJJbWFnLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgIHN0YXJ0QmFuZCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzdG9wQmFuZCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAwLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgIHN0YXJ0U2xvdCk7CgogIHJlc2VydmUgPSBDbnRMZWFkaW5nWmVyb3MobWF4VmFsKS0xOwogIHJlc2VydmUgPSBmaXhNaW4ocmVzZXJ2ZSxERlJBQ1RfQklUUy0xLXNvdXJjZV9zY2FsZSk7CgogIHJlc2NhbGVTdWJiYW5kU2FtcGxlcyggT3ZlcmxhcEJ1ZmZlclJlYWwsCiAgICAgICAgICAgICAgICAgICAgICAgICAodXNlTFApID8gTlVMTCA6IE92ZXJsYXBCdWZmZXJJbWFnLAogICAgICAgICAgICAgICAgICAgICAgICAgc3RhcnRCYW5kLAogICAgICAgICAgICAgICAgICAgICAgICAgc3RvcEJhbmQsCiAgICAgICAgICAgICAgICAgICAgICAgICAwLAogICAgICAgICAgICAgICAgICAgICAgICAgc3RhcnRTbG90LAogICAgICAgICAgICAgICAgICAgICAgICAgcmVzZXJ2ZSk7CiAgc291cmNlX3NjYWxlICs9IHJlc2VydmU7CgogIGRlbHRhX3NjYWxlID0gdGFyZ2V0X3NjYWxlIC0gc291cmNlX3NjYWxlOwoKICBpZiAoZGVsdGFfc2NhbGUgPiAwKSB7IC8qIHgtb3Zlci1hcmVhIGlzIGRvbWluYW50ICovCiAgICBkZWx0YV9zY2FsZSA9IC1kZWx0YV9zY2FsZTsKICAgIHN0YXJ0QmFuZCA9IHRhcmdldF9sc2I7CiAgICBzdG9wQmFuZCA9IHRhcmdldF91c2I7CgogICAgaWYgKG5ld19sc2IgPiBvbGRfbHNiKSB7CiAgICAgIC8qIFRoZSBsb3diYW5kIGhhcyB0byBiZSByZXNjYWxlZCAqLwogICAgICBoU2JyRGVjLT5zYnJTY2FsZUZhY3Rvci5vdl9sYl9zY2FsZSA9IHNvdXJjZV9zY2FsZTsKICAgIH0KICAgIGVsc2UgewogICAgICAvKiBUaGUgaGlnaGJhbmQgaGFzIGJlIGJlIHJlc2NhbGVkICovCiAgICAgIGhTYnJEZWMtPnNiclNjYWxlRmFjdG9yLm92X2hiX3NjYWxlID0gc291cmNlX3NjYWxlOwogICAgfQogIH0KCiAgRkRLX0FTU0VSVChzdGFydEJhbmQgPD0gc3RvcEJhbmQpOwoKICBpZiAoIXVzZUxQKSB7CiAgICBmb3IgKGw9MDsgbDxzdGFydFNsb3Q7IGwrKykgewogICAgICBzY2FsZVZhbHVlcyggT3ZlcmxhcEJ1ZmZlclJlYWxbbF0gKyBzdGFydEJhbmQsIHN0b3BCYW5kLXN0YXJ0QmFuZCwgZGVsdGFfc2NhbGUgKTsKICAgICAgc2NhbGVWYWx1ZXMoIE92ZXJsYXBCdWZmZXJJbWFnW2xdICsgc3RhcnRCYW5kLCBzdG9wQmFuZC1zdGFydEJhbmQsIGRlbHRhX3NjYWxlICk7CiAgICB9CiAgfSBlbHNlCiAgZm9yIChsPTA7IGw8c3RhcnRTbG90OyBsKyspIHsKICAgIHNjYWxlVmFsdWVzKCBPdmVybGFwQnVmZmVyUmVhbFtsXSArIHN0YXJ0QmFuZCwgc3RvcEJhbmQtc3RhcnRCYW5kLCBkZWx0YV9zY2FsZSApOwogIH0KCgogIC8qCiAgICBJbml0aWFsaXplIHRyYW5zcG9zZXIgYW5kIGxpbWl0ZXIKICAqLwogIHNickVycm9yID0gcmVzZXRMcHBUcmFuc3Bvc2VyICgmaFNickRlYy0+THBwVHJhbnMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGhIZWFkZXJEYXRhLT5mcmVxQmFuZERhdGEubG93U3ViYmFuZCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaEhlYWRlckRhdGEtPmZyZXFCYW5kRGF0YS52X2tfbWFzdGVyLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBoSGVhZGVyRGF0YS0+ZnJlcUJhbmREYXRhLm51bU1hc3RlciwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaEhlYWRlckRhdGEtPmZyZXFCYW5kRGF0YS5mcmVxQmFuZFRhYmxlTm9pc2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGhIZWFkZXJEYXRhLT5mcmVxQmFuZERhdGEubk5mYiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaEhlYWRlckRhdGEtPmZyZXFCYW5kRGF0YS5oaWdoU3ViYmFuZCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaEhlYWRlckRhdGEtPnNiclByb2NTbXBsUmF0ZSk7CiAgaWYgKHNickVycm9yICE9IFNCUkRFQ19PSykKICAgIHJldHVybiBzYnJFcnJvcjsKCiAgc2JyRXJyb3IgPSBSZXNldExpbWl0ZXJCYW5kcyAoIGhIZWFkZXJEYXRhLT5mcmVxQmFuZERhdGEubGltaXRlckJhbmRUYWJsZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJmhIZWFkZXJEYXRhLT5mcmVxQmFuZERhdGEubm9MaW1pdGVyQmFuZHMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGhIZWFkZXJEYXRhLT5mcmVxQmFuZERhdGEuZnJlcUJhbmRUYWJsZVswXSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaEhlYWRlckRhdGEtPmZyZXFCYW5kRGF0YS5uU2ZiWzBdLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBoU2JyRGVjLT5McHBUcmFucy5wU2V0dGluZ3MtPnBhdGNoUGFyYW0sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGhTYnJEZWMtPkxwcFRyYW5zLnBTZXR0aW5ncy0+bm9PZlBhdGNoZXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGhIZWFkZXJEYXRhLT5ic19kYXRhLmxpbWl0ZXJCYW5kcyk7CgoKICByZXR1cm4gc2JyRXJyb3I7Cn0K