Ci8qIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tClNvZnR3YXJlIExpY2Vuc2UgZm9yIFRoZSBGcmF1bmhvZmVyIEZESyBBQUMgQ29kZWMgTGlicmFyeSBmb3IgQW5kcm9pZAoKqSBDb3B5cmlnaHQgIDE5OTUgLSAyMDEzIEZyYXVuaG9mZXItR2VzZWxsc2NoYWZ0IHp1ciBG9nJkZXJ1bmcgZGVyIGFuZ2V3YW5kdGVuIEZvcnNjaHVuZyBlLlYuCiAgQWxsIHJpZ2h0cyByZXNlcnZlZC4KCiAxLiAgICBJTlRST0RVQ1RJT04KVGhlIEZyYXVuaG9mZXIgRkRLIEFBQyBDb2RlYyBMaWJyYXJ5IGZvciBBbmRyb2lkICgiRkRLIEFBQyBDb2RlYyIpIGlzIHNvZnR3YXJlIHRoYXQgaW1wbGVtZW50cwp0aGUgTVBFRyBBZHZhbmNlZCBBdWRpbyBDb2RpbmcgKCJBQUMiKSBlbmNvZGluZyBhbmQgZGVjb2Rpbmcgc2NoZW1lIGZvciBkaWdpdGFsIGF1ZGlvLgpUaGlzIEZESyBBQUMgQ29kZWMgc29mdHdhcmUgaXMgaW50ZW5kZWQgdG8gYmUgdXNlZCBvbiBhIHdpZGUgdmFyaWV0eSBvZiBBbmRyb2lkIGRldmljZXMuCgpBQUMncyBIRS1BQUMgYW5kIEhFLUFBQyB2MiB2ZXJzaW9ucyBhcmUgcmVnYXJkZWQgYXMgdG9kYXkncyBtb3N0IGVmZmljaWVudCBnZW5lcmFsIHBlcmNlcHR1YWwKYXVkaW8gY29kZWNzLiBBQUMtRUxEIGlzIGNvbnNpZGVyZWQgdGhlIGJlc3QtcGVyZm9ybWluZyBmdWxsLWJhbmR3aWR0aCBjb21tdW5pY2F0aW9ucyBjb2RlYyBieQppbmRlcGVuZGVudCBzdHVkaWVzIGFuZCBpcyB3aWRlbHkgZGVwbG95ZWQuIEFBQyBoYXMgYmVlbiBzdGFuZGFyZGl6ZWQgYnkgSVNPIGFuZCBJRUMgYXMgcGFydApvZiB0aGUgTVBFRyBzcGVjaWZpY2F0aW9ucy4KClBhdGVudCBsaWNlbnNlcyBmb3IgbmVjZXNzYXJ5IHBhdGVudCBjbGFpbXMgZm9yIHRoZSBGREsgQUFDIENvZGVjIChpbmNsdWRpbmcgdGhvc2Ugb2YgRnJhdW5ob2ZlcikKbWF5IGJlIG9idGFpbmVkIHRocm91Z2ggVmlhIExpY2Vuc2luZyAod3d3LnZpYWxpY2Vuc2luZy5jb20pIG9yIHRocm91Z2ggdGhlIHJlc3BlY3RpdmUgcGF0ZW50IG93bmVycwppbmRpdmlkdWFsbHkgZm9yIHRoZSBwdXJwb3NlIG9mIGVuY29kaW5nIG9yIGRlY29kaW5nIGJpdCBzdHJlYW1zIGluIHByb2R1Y3RzIHRoYXQgYXJlIGNvbXBsaWFudCB3aXRoCnRoZSBJU08vSUVDIE1QRUcgYXVkaW8gc3RhbmRhcmRzLiBQbGVhc2Ugbm90ZSB0aGF0IG1vc3QgbWFudWZhY3R1cmVycyBvZiBBbmRyb2lkIGRldmljZXMgYWxyZWFkeSBsaWNlbnNlCnRoZXNlIHBhdGVudCBjbGFpbXMgdGhyb3VnaCBWaWEgTGljZW5zaW5nIG9yIGRpcmVjdGx5IGZyb20gdGhlIHBhdGVudCBvd25lcnMsIGFuZCB0aGVyZWZvcmUgRkRLIEFBQyBDb2RlYwpzb2Z0d2FyZSBtYXkgYWxyZWFkeSBiZSBjb3ZlcmVkIHVuZGVyIHRob3NlIHBhdGVudCBsaWNlbnNlcyB3aGVuIGl0IGlzIHVzZWQgZm9yIHRob3NlIGxpY2Vuc2VkIHB1cnBvc2VzIG9ubHkuCgpDb21tZXJjaWFsbHktbGljZW5zZWQgQUFDIHNvZnR3YXJlIGxpYnJhcmllcywgaW5jbHVkaW5nIGZsb2F0aW5nLXBvaW50IHZlcnNpb25zIHdpdGggZW5oYW5jZWQgc291bmQgcXVhbGl0eSwKYXJlIGFsc28gYXZhaWxhYmxlIGZyb20gRnJhdW5ob2Zlci4gVXNlcnMgYXJlIGVuY291cmFnZWQgdG8gY2hlY2sgdGhlIEZyYXVuaG9mZXIgd2Vic2l0ZSBmb3IgYWRkaXRpb25hbAphcHBsaWNhdGlvbnMgaW5mb3JtYXRpb24gYW5kIGRvY3VtZW50YXRpb24uCgoyLiAgICBDT1BZUklHSFQgTElDRU5TRQoKUmVkaXN0cmlidXRpb24gYW5kIHVzZSBpbiBzb3VyY2UgYW5kIGJpbmFyeSBmb3Jtcywgd2l0aCBvciB3aXRob3V0IG1vZGlmaWNhdGlvbiwgYXJlIHBlcm1pdHRlZCB3aXRob3V0CnBheW1lbnQgb2YgY29weXJpZ2h0IGxpY2Vuc2UgZmVlcyBwcm92aWRlZCB0aGF0IHlvdSBzYXRpc2Z5IHRoZSBmb2xsb3dpbmcgY29uZGl0aW9uczoKCllvdSBtdXN0IHJldGFpbiB0aGUgY29tcGxldGUgdGV4dCBvZiB0aGlzIHNvZnR3YXJlIGxpY2Vuc2UgaW4gcmVkaXN0cmlidXRpb25zIG9mIHRoZSBGREsgQUFDIENvZGVjIG9yCnlvdXIgbW9kaWZpY2F0aW9ucyB0aGVyZXRvIGluIHNvdXJjZSBjb2RlIGZvcm0uCgpZb3UgbXVzdCByZXRhaW4gdGhlIGNvbXBsZXRlIHRleHQgb2YgdGhpcyBzb2Z0d2FyZSBsaWNlbnNlIGluIHRoZSBkb2N1bWVudGF0aW9uIGFuZC9vciBvdGhlciBtYXRlcmlhbHMKcHJvdmlkZWQgd2l0aCByZWRpc3RyaWJ1dGlvbnMgb2YgdGhlIEZESyBBQUMgQ29kZWMgb3IgeW91ciBtb2RpZmljYXRpb25zIHRoZXJldG8gaW4gYmluYXJ5IGZvcm0uCllvdSBtdXN0IG1ha2UgYXZhaWxhYmxlIGZyZWUgb2YgY2hhcmdlIGNvcGllcyBvZiB0aGUgY29tcGxldGUgc291cmNlIGNvZGUgb2YgdGhlIEZESyBBQUMgQ29kZWMgYW5kIHlvdXIKbW9kaWZpY2F0aW9ucyB0aGVyZXRvIHRvIHJlY2lwaWVudHMgb2YgY29waWVzIGluIGJpbmFyeSBmb3JtLgoKVGhlIG5hbWUgb2YgRnJhdW5ob2ZlciBtYXkgbm90IGJlIHVzZWQgdG8gZW5kb3JzZSBvciBwcm9tb3RlIHByb2R1Y3RzIGRlcml2ZWQgZnJvbSB0aGlzIGxpYnJhcnkgd2l0aG91dApwcmlvciB3cml0dGVuIHBlcm1pc3Npb24uCgpZb3UgbWF5IG5vdCBjaGFyZ2UgY29weXJpZ2h0IGxpY2Vuc2UgZmVlcyBmb3IgYW55b25lIHRvIHVzZSwgY29weSBvciBkaXN0cmlidXRlIHRoZSBGREsgQUFDIENvZGVjCnNvZnR3YXJlIG9yIHlvdXIgbW9kaWZpY2F0aW9ucyB0aGVyZXRvLgoKWW91ciBtb2RpZmllZCB2ZXJzaW9ucyBvZiB0aGUgRkRLIEFBQyBDb2RlYyBtdXN0IGNhcnJ5IHByb21pbmVudCBub3RpY2VzIHN0YXRpbmcgdGhhdCB5b3UgY2hhbmdlZCB0aGUgc29mdHdhcmUKYW5kIHRoZSBkYXRlIG9mIGFueSBjaGFuZ2UuIEZvciBtb2RpZmllZCB2ZXJzaW9ucyBvZiB0aGUgRkRLIEFBQyBDb2RlYywgdGhlIHRlcm0KIkZyYXVuaG9mZXIgRkRLIEFBQyBDb2RlYyBMaWJyYXJ5IGZvciBBbmRyb2lkIiBtdXN0IGJlIHJlcGxhY2VkIGJ5IHRoZSB0ZXJtCiJUaGlyZC1QYXJ0eSBNb2RpZmllZCBWZXJzaW9uIG9mIHRoZSBGcmF1bmhvZmVyIEZESyBBQUMgQ29kZWMgTGlicmFyeSBmb3IgQW5kcm9pZC4iCgozLiAgICBOTyBQQVRFTlQgTElDRU5TRQoKTk8gRVhQUkVTUyBPUiBJTVBMSUVEIExJQ0VOU0VTIFRPIEFOWSBQQVRFTlQgQ0xBSU1TLCBpbmNsdWRpbmcgd2l0aG91dCBsaW1pdGF0aW9uIHRoZSBwYXRlbnRzIG9mIEZyYXVuaG9mZXIsCkFSRSBHUkFOVEVEIEJZIFRISVMgU09GVFdBUkUgTElDRU5TRS4gRnJhdW5ob2ZlciBwcm92aWRlcyBubyB3YXJyYW50eSBvZiBwYXRlbnQgbm9uLWluZnJpbmdlbWVudCB3aXRoCnJlc3BlY3QgdG8gdGhpcyBzb2Z0d2FyZS4KCllvdSBtYXkgdXNlIHRoaXMgRkRLIEFBQyBDb2RlYyBzb2Z0d2FyZSBvciBtb2RpZmljYXRpb25zIHRoZXJldG8gb25seSBmb3IgcHVycG9zZXMgdGhhdCBhcmUgYXV0aG9yaXplZApieSBhcHByb3ByaWF0ZSBwYXRlbnQgbGljZW5zZXMuCgo0LiAgICBESVNDTEFJTUVSCgpUaGlzIEZESyBBQUMgQ29kZWMgc29mdHdhcmUgaXMgcHJvdmlkZWQgYnkgRnJhdW5ob2ZlciBvbiBiZWhhbGYgb2YgdGhlIGNvcHlyaWdodCBob2xkZXJzIGFuZCBjb250cmlidXRvcnMKIkFTIElTIiBhbmQgV0lUSE9VVCBBTlkgRVhQUkVTUyBPUiBJTVBMSUVEIFdBUlJBTlRJRVMsIGluY2x1ZGluZyBidXQgbm90IGxpbWl0ZWQgdG8gdGhlIGltcGxpZWQgd2FycmFudGllcwpvZiBtZXJjaGFudGFiaWxpdHkgYW5kIGZpdG5lc3MgZm9yIGEgcGFydGljdWxhciBwdXJwb3NlLiBJTiBOTyBFVkVOVCBTSEFMTCBUSEUgQ09QWVJJR0hUIEhPTERFUiBPUgpDT05UUklCVVRPUlMgQkUgTElBQkxFIGZvciBhbnkgZGlyZWN0LCBpbmRpcmVjdCwgaW5jaWRlbnRhbCwgc3BlY2lhbCwgZXhlbXBsYXJ5LCBvciBjb25zZXF1ZW50aWFsIGRhbWFnZXMsCmluY2x1ZGluZyBidXQgbm90IGxpbWl0ZWQgdG8gcHJvY3VyZW1lbnQgb2Ygc3Vic3RpdHV0ZSBnb29kcyBvciBzZXJ2aWNlczsgbG9zcyBvZiB1c2UsIGRhdGEsIG9yIHByb2ZpdHMsCm9yIGJ1c2luZXNzIGludGVycnVwdGlvbiwgaG93ZXZlciBjYXVzZWQgYW5kIG9uIGFueSB0aGVvcnkgb2YgbGlhYmlsaXR5LCB3aGV0aGVyIGluIGNvbnRyYWN0LCBzdHJpY3QKbGlhYmlsaXR5LCBvciB0b3J0IChpbmNsdWRpbmcgbmVnbGlnZW5jZSksIGFyaXNpbmcgaW4gYW55IHdheSBvdXQgb2YgdGhlIHVzZSBvZiB0aGlzIHNvZnR3YXJlLCBldmVuIGlmCmFkdmlzZWQgb2YgdGhlIHBvc3NpYmlsaXR5IG9mIHN1Y2ggZGFtYWdlLgoKNS4gICAgQ09OVEFDVCBJTkZPUk1BVElPTgoKRnJhdW5ob2ZlciBJbnN0aXR1dGUgZm9yIEludGVncmF0ZWQgQ2lyY3VpdHMgSUlTCkF0dGVudGlvbjogQXVkaW8gYW5kIE11bHRpbWVkaWEgRGVwYXJ0bWVudHMgLSBGREsgQUFDIExMCkFtIFdvbGZzbWFudGVsIDMzCjkxMDU4IEVybGFuZ2VuLCBHZXJtYW55Cgp3d3cuaWlzLmZyYXVuaG9mZXIuZGUvYW1tCmFtbS1pbmZvQGlpcy5mcmF1bmhvZmVyLmRlCi0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tICovCgovKiEKICBcZmlsZQogIFxicmllZiAgRnJlcXVlbmN5IHNjYWxlIGNhbGN1bGF0aW9uICAKKi8KCiNpbmNsdWRlICJzYnJkZWNfZnJlcV9zY2EuaCIKCiNpbmNsdWRlICJ0cmFuc2NlbmRlbnQuaCIKI2luY2x1ZGUgInNicl9yb20uaCIKI2luY2x1ZGUgImVudl9leHRyLmgiCgojaW5jbHVkZSAiZ2VuZXJpY1N0ZHMuaCIgICAgICAvKiBuZWVkIGxvZygpIGZvciBkZWJ1Zy1jb2RlIG9ubHkgKi8KCiNkZWZpbmUgTUFYX09DVEFWRSAgICAgICAgIDI5CiNkZWZpbmUgTUFYX1NFQ09ORF9SRUdJT04gIDUwCgoKc3RhdGljIGludCAgbnVtYmVyT2ZCYW5kcyhGSVhQX1NHTCBicG9fZGl2MTYsIGludCBzdGFydCwgaW50IHN0b3AsIGludCB3YXJwRmxhZyk7CnN0YXRpYyB2b2lkIENhbGNCYW5kcyhVQ0hBUiAqIGRpZmYsIFVDSEFSIHN0YXJ0LCBVQ0hBUiBzdG9wLCBVQ0hBUiBudW1fYmFuZHMpOwpzdGF0aWMgU0JSX0VSUk9SIG1vZGlmeUJhbmRzKFVDSEFSIG1heF9iYW5kLCBVQ0hBUiAqIGRpZmYsIFVDSEFSIGxlbmd0aCk7CnN0YXRpYyB2b2lkIGN1bVN1bShVQ0hBUiBzdGFydF92YWx1ZSwgVUNIQVIqIGRpZmYsIFVDSEFSIGxlbmd0aCwgVUNIQVIgKnN0YXJ0X2FkcmVzcyk7CgoKCi8qIQogIFxicmllZiAgICAgUmV0cmlldmUgUU1GLWJhbmQgd2hlcmUgdGhlIFNCUiByYW5nZSBzdGFydHMKCiAgQ29udmVydCBzdGFydEZyZXEgd2hpY2ggd2FzIHJlYWQgZnJvbSB0aGUgYml0c3RyZWFtIGludG8gYQogIFFNRi1jaGFubmVsIG51bWJlci4KCiAgXHJldHVybiAgTnVtYmVyIG9mIHN0YXJ0IGJhbmQKKi8Kc3RhdGljIFVDSEFSCmdldFN0YXJ0QmFuZChVSU5UICAgZnMsICAgICAgICAgICAgICAgLyohPCBPdXRwdXQgc2FtcGxpbmcgZnJlcXVlbmN5ICovCiAgICAgICAgICAgICBVQ0hBUiAgc3RhcnRGcmVxLCAgICAgICAgLyohPCBJbmRleCB0byB0YWJsZSBvZiBwb3NzaWJsZSBzdGFydCBiYW5kcyAqLwogICAgICAgICAgICAgVUlOVCAgIGhlYWRlckRhdGFGbGFncykgIC8qITwgSW5mbyB0byBTQlIgbW9kZSAqLwp7CiAgSU5UICBiYW5kOwogIFVJTlQgZnNNYXBwZWQ7CgogICAgZnNNYXBwZWQgPSBmczsKCiAgc3dpdGNoIChmc01hcHBlZCkgewogICAgY2FzZSA5NjAwMDoKICAgIGNhc2UgODgyMDA6CiAgICAgIGJhbmQgPSBGREtfc2JyRGVjb2Rlcl9zYnJfc3RhcnRfZnJlcV84OFtzdGFydEZyZXFdOwogICAgICBicmVhazsKICAgIGNhc2UgNjQwMDA6CiAgICAgIGJhbmQgPSBGREtfc2JyRGVjb2Rlcl9zYnJfc3RhcnRfZnJlcV82NFtzdGFydEZyZXFdOwogICAgICBicmVhazsKICAgIGNhc2UgNDgwMDA6CiAgICAgIGJhbmQgPSBGREtfc2JyRGVjb2Rlcl9zYnJfc3RhcnRfZnJlcV80OFtzdGFydEZyZXFdOwogICAgICBicmVhazsKICAgIGNhc2UgNDQxMDA6CiAgICAgIGJhbmQgPSBGREtfc2JyRGVjb2Rlcl9zYnJfc3RhcnRfZnJlcV80NFtzdGFydEZyZXFdOwogICAgICBicmVhazsKICAgIGNhc2UgMzIwMDA6CiAgICAgIGJhbmQgPSBGREtfc2JyRGVjb2Rlcl9zYnJfc3RhcnRfZnJlcV8zMltzdGFydEZyZXFdOwogICAgICBicmVhazsKICAgIGNhc2UgMjQwMDA6CiAgICAgIGJhbmQgPSBGREtfc2JyRGVjb2Rlcl9zYnJfc3RhcnRfZnJlcV8yNFtzdGFydEZyZXFdOwogICAgICBicmVhazsKICAgIGNhc2UgMjIwNTA6CiAgICAgIGJhbmQgPSBGREtfc2JyRGVjb2Rlcl9zYnJfc3RhcnRfZnJlcV8yMltzdGFydEZyZXFdOwogICAgICBicmVhazsKICAgIGNhc2UgMTYwMDA6CiAgICAgIGJhbmQgPSBGREtfc2JyRGVjb2Rlcl9zYnJfc3RhcnRfZnJlcV8xNltzdGFydEZyZXFdOwogICAgICBicmVhazsKICAgIGRlZmF1bHQ6CiAgICAgIGJhbmQgPSAyNTU7CiAgfQoKICByZXR1cm4gYmFuZDsKfQoKCi8qIQogIFxicmllZiAgICAgUmV0cmlldmUgUU1GLWJhbmQgd2hlcmUgdGhlIFNCUiByYW5nZSBzdGFydHMKCiAgQ29udmVydCBzdGFydEZyZXEgd2hpY2ggd2FzIHJlYWQgZnJvbSB0aGUgYml0c3RyZWFtIGludG8gYQogIFFNRi1jaGFubmVsIG51bWJlci4KCiAgXHJldHVybiAgTnVtYmVyIG9mIHN0YXJ0IGJhbmQKKi8Kc3RhdGljIFVDSEFSCmdldFN0b3BCYW5kKFVJTlQgICBmcywgICAgICAgICAgICAgICAvKiE8IE91dHB1dCBzYW1wbGluZyBmcmVxdWVuY3kgKi8KICAgICAgICAgICAgVUNIQVIgIHN0b3BGcmVxLCAgICAgICAgIC8qITwgSW5kZXggdG8gdGFibGUgb2YgcG9zc2libGUgc3RhcnQgYmFuZHMgKi8KICAgICAgICAgICAgVUlOVCAgIGhlYWRlckRhdGFGbGFncywgIC8qITwgSW5mbyB0byBTQlIgbW9kZSAqLwogICAgICAgICAgICBVQ0hBUiAgazApICAgICAgICAgICAgICAgLyohPCBTdGFydCBmcmVxIGluZGV4ICovCnsKICBVQ0hBUiBrMjsKCiAgaWYgKHN0b3BGcmVxIDwgMTQpIHsKICAgIElOVCAgICBzdG9wTWluOwogICAgVUNIQVIgIGRpZmZfdG90W01BWF9PQ1RBVkUgKyBNQVhfU0VDT05EX1JFR0lPTl07CiAgICBVQ0hBUiAqZGlmZjAgPSBkaWZmX3RvdDsKICAgIFVDSEFSICpkaWZmMSA9IGRpZmZfdG90K01BWF9PQ1RBVkU7CgogICAgaWYgKGZzIDwgMzIwMDApIHsKICAgICAgc3RvcE1pbiA9ICgoKDIqNjAwMCoyKig2NCkpIC8gZnMpICsgMSkgPj4gMTsKICAgIH0KICAgIGVsc2UgewogICAgICBpZiAoZnMgPCA2NDAwMCkgewogICAgICAgIHN0b3BNaW4gPSAoKCgyKjgwMDAqMiooNjQpKSAvIGZzKSArIDEpID4+IDE7CiAgICAgIH0KICAgICAgZWxzZSB7CiAgICAgICAgc3RvcE1pbiA9ICgoKDIqMTAwMDAqMiooNjQpKSAvIGZzKSArIDEpID4+IDE7CiAgICAgIH0KICAgIH0KCiAgICAvKgogICAgICBDaG9vc2UgYSBzdG9wIGJhbmQgYmV0d2VlbiBrMSBhbmQgNjQgZGVwZW5kaW5nIG9uIHN0b3BGcmVxICgwLi4xMyksCiAgICAgIGJhc2VkIG9uIGEgbG9nYXJpdGhtaWMgc2NhbGUuCiAgICAgIFRoZSB2ZWN0b3JzIGRpZmYwIGFuZCBkaWZmMSBhcmUgdXNlZCB0ZW1wb3JhcmlseSBoZXJlLgogICAgKi8KICAgIENhbGNCYW5kcyggZGlmZjAsIHN0b3BNaW4sIDY0LCAxMyk7CiAgICBzaGVsbHNvcnQoIGRpZmYwLCAxMyk7CiAgICBjdW1TdW0oc3RvcE1pbiwgZGlmZjAsIDEzLCBkaWZmMSk7CiAgICBrMiA9IGRpZmYxW3N0b3BGcmVxXTsKICB9CiAgZWxzZSBpZiAoc3RvcEZyZXE9PTE0KQogICAgazIgPSAyKmswOwogIGVsc2UKICAgIGsyID0gMyprMDsKCiAgLyogTGltaXQgdG8gTnlxdWlzdCAqLwogIGlmIChrMiA+ICg2NCkpCiAgICBrMiA9ICg2NCk7CgoKICAvKiBSYW5nZSBjaGVja3MgKi8KICAvKiAxIDw9IGRpZmZlcmVuY2UgPD0gNDg7IDEgPD0gZnMgPD0gOTYwMDAgKi8KICBpZiAoICgoazIgLSBrMCkgPiBNQVhfRlJFUV9DT0VGRlMpIHx8IChrMiA8PSBrMCkgKSB7CiAgICByZXR1cm4gMjU1OwogIH0KCiAgaWYgKGhlYWRlckRhdGFGbGFncyAmIChTQlJERUNfU1lOVEFYX1VTQUN8U0JSREVDX1NZTlRBWF9SU1ZENTApKSB7CiAgICAvKiAxIDw9IGRpZmZlcmVuY2UgPD0gMzU7IDQyMDAwIDw9IGZzIDw9IDk2MDAwICovCiAgICBpZiAoIChmcyA+PSA0MjAwMCkgJiYgKCAoazIgLSBrMCkgPiBNQVhfRlJFUV9DT0VGRlNfRlM0NDEwMCApICkgewogICAgICByZXR1cm4gMjU1OwogICAgfQogICAgLyogMSA8PSBkaWZmZXJlbmNlIDw9IDMyOyA0NjAwOSA8PSBmcyA8PSA5NjAwMCAqLwogICAgaWYgKCAoZnMgPj0gNDYwMDkpICYmICggKGsyIC0gazApID4gTUFYX0ZSRVFfQ09FRkZTX0ZTNDgwMDAgKSApIHsKICAgICAgcmV0dXJuIDI1NTsKICAgIH0KICB9CiAgZWxzZSB7CiAgICAvKiAxIDw9IGRpZmZlcmVuY2UgPD0gMzU7IGZzID09IDQ0MTAwICovCiAgICBpZiAoIChmcyA9PSA0NDEwMCkgJiYgKCAoazIgLSBrMCkgPiBNQVhfRlJFUV9DT0VGRlNfRlM0NDEwMCApICkgewogICAgICByZXR1cm4gMjU1OwogICAgfQogICAgLyogMSA8PSBkaWZmZXJlbmNlIDw9IDMyOyA0ODAwMCA8PSBmcyA8PSA5NjAwMCAqLwogICAgaWYgKCAoZnMgPj0gNDgwMDApICYmICggKGsyIC0gazApID4gTUFYX0ZSRVFfQ09FRkZTX0ZTNDgwMDAgKSApIHsKICAgICAgcmV0dXJuIDI1NTsKICAgIH0KICB9CgogIHJldHVybiBrMjsKfQoKCi8qIQogIFxicmllZiAgICAgR2VuZXJhdGVzIG1hc3RlciBmcmVxdWVuY3kgdGFibGVzCgogIEZyZXF1ZW5jeSB0YWJsZXMgYXJlIGNhbGN1bGF0ZWQgYWNjb3JkaW5nIHRvIHRoZSBzZWxlY3RlZCBkb21haW4KICAobGluZWFyL2xvZ2FyaXRobWljKSBhbmQgZ3JhbnVsYXJpdHkuCiAgSUVDIDE0NDk2LTMgNC42LjE4LjMuMi4xCgogIFxyZXR1cm4gIGVycm9yQ29kZSwgMCBpZiBzdWNjZXNzZnVsCiovClNCUl9FUlJPUgpzYnJkZWNVcGRhdGVGcmVxU2NhbGUoVUNIQVIgKiB2X2tfbWFzdGVyLCAgICAvKiE8IE1hc3RlciB0YWJsZSB0byBiZSBjcmVhdGVkICovCiAgICAgICAgICAgICAgICAgICAgICBVQ0hBUiAqbnVtTWFzdGVyLCAgICAgIC8qITwgTnVtYmVyIG9mIGVudHJpZXMgaW4gbWFzdGVyIHRhYmxlICovCiAgICAgICAgICAgICAgICAgICAgICBVSU5UICAgZnMsICAgICAgICAgICAgIC8qITwgU0JSIHdvcmtpbmcgc2FtcGxpbmcgcmF0ZSAqLwogICAgICAgICAgICAgICAgICAgICAgSEFORExFX1NCUl9IRUFERVJfREFUQSBoSGVhZGVyRGF0YSwgLyohPCBDb250cm9sIGRhdGEgZnJvbSBiaXRzdHJlYW0gKi8KICAgICAgICAgICAgICAgICAgICAgIFVJTlQgZmxhZ3MpCnsKICBGSVhQX1NHTCBicG9fZGl2MTY7ICAgICAgICAvKiBiYW5kc19wZXJfb2N0YXZlIGRpdmlkZWQgYnkgMTYgKi8KICBJTlQgICAgICBkaz0wOwoKICAvKiBJbnRlcm5hbCB2YXJpYWJsZXMgKi8KICBVQ0hBUiAgazAsIGsyLCBpOwogIFVDSEFSICBudW1fYmFuZHMwID0gMDsKICBVQ0hBUiAgbnVtX2JhbmRzMSA9IDA7CiAgVUNIQVIgIGRpZmZfdG90W01BWF9PQ1RBVkUgKyBNQVhfU0VDT05EX1JFR0lPTl07CiAgVUNIQVIgKmRpZmYwID0gZGlmZl90b3Q7CiAgVUNIQVIgKmRpZmYxID0gZGlmZl90b3QrTUFYX09DVEFWRTsKICBJTlQgICAgazJfYWNoaXZlZDsKICBJTlQgICAgazJfZGlmZjsKICBJTlQgICAgaW5jcj0wOwoKICAvKgogICAgRGV0ZXJtaW5lIHN0YXJ0IGJhbmQKICAqLwogIGswID0gZ2V0U3RhcnRCYW5kKGZzLCBoSGVhZGVyRGF0YS0+YnNfZGF0YS5zdGFydEZyZXEsIGZsYWdzKTsKICBpZiAoazAgPT0gMjU1KSB7CiAgICByZXR1cm4gU0JSREVDX1VOU1VQUE9SVEVEX0NPTkZJRzsKICB9CgogIC8qCiAgICBEZXRlcm1pbmUgc3RvcCBiYW5kCiAgKi8KICBrMiA9IGdldFN0b3BCYW5kKGZzLCBoSGVhZGVyRGF0YS0+YnNfZGF0YS5zdG9wRnJlcSwgZmxhZ3MsIGswKTsKICBpZiAoazIgPT0gMjU1KSB7CiAgICByZXR1cm4gU0JSREVDX1VOU1VQUE9SVEVEX0NPTkZJRzsKICB9CgogIGlmKGhIZWFkZXJEYXRhLT5ic19kYXRhLmZyZXFTY2FsZT4wKSB7IC8qIEJhcmsgKi8KICAgIElOVCBrMTsKCiAgICBpZihoSGVhZGVyRGF0YS0+YnNfZGF0YS5mcmVxU2NhbGU9PTEpIHsKICAgICAgYnBvX2RpdjE2ID0gRkwyRlhDT05TVF9TR0woMTIuMGYvMTYuMGYpOwogICAgfQogICAgZWxzZSBpZihoSGVhZGVyRGF0YS0+YnNfZGF0YS5mcmVxU2NhbGU9PTIpIHsKICAgICAgYnBvX2RpdjE2ID0gRkwyRlhDT05TVF9TR0woMTAuMGYvMTYuMGYpOwogICAgfQogICAgZWxzZSB7CiAgICAgIGJwb19kaXYxNiA9ICBGTDJGWENPTlNUX1NHTCg4LjBmLzE2LjBmKTsKICAgIH0KCgogICAgaWYoIDEwMDAgKiBrMiA+IDIyNDUgKiBrMCApIHsgLyogVHdvIG9yIG1vcmUgcmVnaW9ucyAqLwogICAgICBrMSA9IDIqazA7CgogICAgICBudW1fYmFuZHMwID0gbnVtYmVyT2ZCYW5kcyhicG9fZGl2MTYsIGswLCBrMSwgMCk7CiAgICAgIG51bV9iYW5kczEgPSBudW1iZXJPZkJhbmRzKGJwb19kaXYxNiwgazEsIGsyLCBoSGVhZGVyRGF0YS0+YnNfZGF0YS5hbHRlclNjYWxlICk7CiAgICAgIGlmICggbnVtX2JhbmRzMCA8IDEpIHsKICAgICAgICByZXR1cm4gU0JSREVDX1VOU1VQUE9SVEVEX0NPTkZJRzsKICAgICAgfQogICAgICBpZiAoIG51bV9iYW5kczEgPCAxICkgewogICAgICAgIHJldHVybiBTQlJERUNfVU5TVVBQT1JURURfQ09ORklHOwogICAgICB9CgogICAgICBDYWxjQmFuZHMoZGlmZjAsIGswLCBrMSwgbnVtX2JhbmRzMCk7CiAgICAgIHNoZWxsc29ydCggZGlmZjAsIG51bV9iYW5kczApOwogICAgICBpZiAoZGlmZjBbMF0gPT0gMCkgewojaWZkZWYgREVCVUdfVE9PTFMKI2VuZGlmCiAgICAgICAgcmV0dXJuIFNCUkRFQ19VTlNVUFBPUlRFRF9DT05GSUc7CiAgICAgIH0KCiAgICAgIGN1bVN1bShrMCwgZGlmZjAsIG51bV9iYW5kczAsIHZfa19tYXN0ZXIpOwoKICAgICAgQ2FsY0JhbmRzKGRpZmYxLCBrMSwgazIsIG51bV9iYW5kczEpOwogICAgICBzaGVsbHNvcnQoIGRpZmYxLCBudW1fYmFuZHMxKTsKICAgICAgaWYoZGlmZjBbbnVtX2JhbmRzMC0xXSA+IGRpZmYxWzBdKSB7CiAgICAgICAgU0JSX0VSUk9SIGVycjsKCiAgICAgICAgZXJyID0gbW9kaWZ5QmFuZHMoZGlmZjBbbnVtX2JhbmRzMC0xXSxkaWZmMSwgbnVtX2JhbmRzMSk7CiAgICAgICAgaWYgKGVycikKICAgICAgICAgIHJldHVybiBTQlJERUNfVU5TVVBQT1JURURfQ09ORklHOwogICAgICB9CgogICAgICAvKiBBZGQgMm5kIHJlZ2lvbiAqLwogICAgICBjdW1TdW0oazEsIGRpZmYxLCBudW1fYmFuZHMxLCAmdl9rX21hc3RlcltudW1fYmFuZHMwXSk7CiAgICAgICpudW1NYXN0ZXIgPSBudW1fYmFuZHMwICsgbnVtX2JhbmRzMTsgICAgIC8qIE91dHB1dCBuciBvZiBiYW5kcyAqLwoKICAgIH0KICAgIGVsc2UgeyAvKiBPbmx5IG9uZSByZWdpb24gKi8KICAgICAgazE9azI7CgogICAgICBudW1fYmFuZHMwID0gbnVtYmVyT2ZCYW5kcyhicG9fZGl2MTYsIGswLCBrMSwgMCk7CiAgICAgIGlmICggbnVtX2JhbmRzMCA8IDEpIHsKICAgICAgICByZXR1cm4gU0JSREVDX1VOU1VQUE9SVEVEX0NPTkZJRzsKICAgICAgfQogICAgICBDYWxjQmFuZHMoZGlmZjAsIGswLCBrMSwgbnVtX2JhbmRzMCk7CiAgICAgIHNoZWxsc29ydChkaWZmMCwgbnVtX2JhbmRzMCk7CiAgICAgIGlmIChkaWZmMFswXSA9PSAwKSB7CiNpZmRlZiBERUJVR19UT09MUwojZW5kaWYKICAgICAgICByZXR1cm4gU0JSREVDX1VOU1VQUE9SVEVEX0NPTkZJRzsKICAgICAgfQoKICAgICAgY3VtU3VtKGswLCBkaWZmMCwgbnVtX2JhbmRzMCwgdl9rX21hc3Rlcik7CiAgICAgICpudW1NYXN0ZXIgPSBudW1fYmFuZHMwOyAgICAgICAgLyogT3V0cHV0IG5yIG9mIGJhbmRzICovCgogICAgfQogIH0KICBlbHNlIHsgLyogTGluZWFyIG1vZGUgKi8KICAgICBpZiAoaEhlYWRlckRhdGEtPmJzX2RhdGEuYWx0ZXJTY2FsZT09MCkgewogICAgICAgIGRrID0gMTsKICAgICAgICAvKiBGTE9PUiB0byBnZXQgdG8gZmV3IG51bWJlciBvZiBiYW5kcyAobmV4dCBsb3dlciBldmVuIG51bWJlcikgKi8KICAgICAgICBudW1fYmFuZHMwID0gKGsyIC0gazApICYgMjU0OwogICAgICB9IGVsc2UgewogICAgICAgIGRrID0gMjsKICAgICAgICBudW1fYmFuZHMwID0gKCAoKGsyIC0gazApID4+IDEpICsgMSApICYgMjU0OyAvKiBST1VORCB0byB0aGUgY2xvc2VzdCBmaXQgKi8KICAgICAgfQoKICAgICAgaWYgKG51bV9iYW5kczAgPCAxKSB7CiAgICAgICAgcmV0dXJuIFNCUkRFQ19VTlNVUFBPUlRFRF9DT05GSUc7CiAgICAgICAgLyogV2UgbXVzdCByZXR1cm4gYWxyZWFkeSBoZXJlIGJlY2F1c2UgJ2knIGNhbiBiZWNvbWUgbmVnYXRpdmUgYmVsb3cuICovCiAgICAgIH0KCiAgICAgIGsyX2FjaGl2ZWQgPSBrMCArIG51bV9iYW5kczAqZGs7CiAgICAgIGsyX2RpZmYgPSBrMiAtIGsyX2FjaGl2ZWQ7CgogICAgICBmb3IoaT0wO2k8bnVtX2JhbmRzMDtpKyspCiAgICAgICAgZGlmZl90b3RbaV0gPSBkazsKCiAgICAgIC8qIElmIGxpbmVhciBzY2FsZSB3YXNuJ3QgYWNoaWV2ZWQgKi8KICAgICAgLyogYW5kIHdlIGdvdCB0b28gd2lkZSBTQlIgYXJlYSAqLwogICAgICBpZiAoazJfZGlmZiA8IDApIHsKICAgICAgICAgIGluY3IgPSAxOwogICAgICAgICAgaSA9IDA7CiAgICAgIH0KCiAgICAgIC8qIElmIGxpbmVhciBzY2FsZSB3YXNuJ3QgYWNoaWV2ZWQgKi8KICAgICAgLyogYW5kIHdlIGdvdCB0b28gc21hbGwgU0JSIGFyZWEgKi8KICAgICAgaWYgKGsyX2RpZmYgPiAwKSB7CiAgICAgICAgICBpbmNyID0gLTE7CiAgICAgICAgICBpID0gbnVtX2JhbmRzMC0xOwogICAgICB9CgogICAgICAvKiBBZGp1c3QgZGlmZiB2ZWN0b3IgdG8gZ2V0IHNlcGMuIFNCUiByYW5nZSAqLwogICAgICB3aGlsZSAoazJfZGlmZiAhPSAwKSB7CiAgICAgICAgZGlmZl90b3RbaV0gPSBkaWZmX3RvdFtpXSAtIGluY3I7CiAgICAgICAgaSA9IGkgKyBpbmNyOwogICAgICAgIGsyX2RpZmYgPSBrMl9kaWZmICsgaW5jcjsKICAgICAgfQoKICAgICAgY3VtU3VtKGswLCBkaWZmX3RvdCwgbnVtX2JhbmRzMCwgdl9rX21hc3Rlcik7LyogY3Vtc3VtICovCiAgICAqbnVtTWFzdGVyID0gbnVtX2JhbmRzMDsgIC8qIE91dHB1dCBuciBvZiBiYW5kcyAqLwogIH0KCiAgaWYgKCpudW1NYXN0ZXIgPCAxKSB7CiAgICByZXR1cm4gU0JSREVDX1VOU1VQUE9SVEVEX0NPTkZJRzsKICB9CgoKICAvKgogICAgUHJpbnQgb3V0IHRoZSBjYWxjdWxhdGVkIHRhYmxlCiAgKi8KCiAgcmV0dXJuIFNCUkRFQ19PSzsKfQoKCi8qIQogIFxicmllZiAgICAgQ2FsY3VsYXRlIGZyZXF1ZW5jeSByYXRpbyBvZiBvbmUgU0JSIGJhbmQKCiAgQWxsIFNCUiBiYW5kcyBzaG91bGQgc3BhbiBhIGNvbnN0YW50IGZyZXF1ZW5jeSByYW5nZSBpbiB0aGUgbG9nYXJpdGhtaWMKICBkb21haW4uIFRoaXMgZnVuY3Rpb24gY2FsY3VsYXRlcyB0aGUgcmF0aW8gb2YgYW55IFNCUiBiYW5kJ3MgdXBwZXIgYW5kIGxvd2VyCiAgZnJlcXVlbmN5LgoKIFxyZXR1cm4gICAgbnVtX2JhbmQtdGggcm9vdCBvZiBrX3N0YXJ0L2tfc3RvcAoqLwpzdGF0aWMgRklYUF9TR0wgY2FsY0ZhY3RvclBlckJhbmQoaW50IGtfc3RhcnQsIGludCBrX3N0b3AsIGludCBudW1fYmFuZHMpCnsKLyogU2NhbGVkIGJhbmRmYWN0b3IgYW5kIHN0ZXAgMSBiaXQgcmlnaHQgdG8gYXZvaWQgb3ZlcmZsb3cKICogdXNlIGRvdWJsZSBkYXRhIHR5cGUgKi8KICBGSVhQX0RCTCBiYW5kZmFjdG9yID0gRkwyRlhDT05TVF9EQkwoMC4yNWYpOyAvKiBTdGFydCB2YWx1ZSAqLwogIEZJWFBfREJMIHN0ZXAgPSBGTDJGWENPTlNUX0RCTCgwLjEyNWYpOyAgICAgIC8qIEluaXRpYWwgaW5jcmVtZW50IGZvciBmYWN0b3IgKi8KCiAgaW50ICAgIGRpcmVjdGlvbiA9IDE7CgovKiBCZWNhdXNlIHNhdHVyYXRpb24gY2FuJ3QgYmUgZG9uZSBpbiBJTlQgSUlTLAogKiBjaGFuZ2VkIHN0YXJ0IGFuZCBzdG9wIGRhdGEgdHlwZSBmcm9tIEZJWFBfU0dMIHRvIEZJWFBfREJMICovCiAgRklYUF9EQkwgc3RhcnQgPSBrX3N0YXJ0IDw8IChERlJBQ1RfQklUUy04KTsKICBGSVhQX0RCTCBzdG9wID0ga19zdG9wIDw8IChERlJBQ1RfQklUUy04KTsKCiAgRklYUF9EQkwgdGVtcDsKCiAgaW50ICAgaiwgaT0wOwoKICB3aGlsZSAoIHN0ZXAgPiBGTDJGWENPTlNUX0RCTCgwLjBmKSkgewogICAgaSsrOwogICAgdGVtcCA9IHN0b3A7CgogICAgLyogQ2FsY3VsYXRlIHRlbXBebnVtX2JhbmRzOiAqLwogICAgZm9yIChqPTA7IGo8bnVtX2JhbmRzOyBqKyspCiAgICAgIC8vdGVtcCA9IGZNdWx0KHRlbXAsYmFuZGZhY3Rvcik7CiAgICAgIHRlbXAgPSBmTXVsdERpdjIodGVtcCxiYW5kZmFjdG9yKTw8MjsKCiAgICBpZiAodGVtcDxzdGFydCkgeyAvKiBGYWN0b3IgdG9vIHN0cm9uZywgbWFrZSBpdCB3ZWFrZXIgKi8KICAgICAgaWYgKGRpcmVjdGlvbiA9PSAwKQogICAgICAgIC8qIEhhbGZlbiBzdGVwLiBSaWdodCBzaGlmdCBpcyBub3QgZG9uZSBhcyBmcmFjdCBiZWNhdXNlIG90aGVyd2lzZSB0aGUKICAgICAgICAgICBsb3dlc3QgYml0IGNhbm5vdCBiZSBjbGVhcmVkIGR1ZSB0byByb3VuZGluZyAqLwogICAgICAgIHN0ZXAgPSAoRklYUF9EQkwpKChMT05HKXN0ZXAgPj4gMSk7CiAgICAgIGRpcmVjdGlvbiA9IDE7CiAgICAgIGJhbmRmYWN0b3IgPSBiYW5kZmFjdG9yICsgc3RlcDsKICAgIH0KICAgIGVsc2UgeyAgLyogRmFjdG9yIGlzIHRvbyB3ZWFrOiBtYWtlIGl0IHN0cm9uZ2VyICovCiAgICAgIGlmIChkaXJlY3Rpb24gPT0gMSkKICAgICAgICBzdGVwID0gKEZJWFBfREJMKSgoTE9ORylzdGVwID4+IDEpOwogICAgICBkaXJlY3Rpb24gPSAwOwogICAgICBiYW5kZmFjdG9yID0gYmFuZGZhY3RvciAtIHN0ZXA7CiAgICB9CgogICAgaWYgKGk+MTAwKSB7CiAgICAgIHN0ZXAgPSBGTDJGWENPTlNUX0RCTCgwLjBmKTsKICAgIH0KICB9CiAgcmV0dXJuIEZYX0RCTDJGWF9TR0woYmFuZGZhY3Rvcjw8MSk7Cn0KCgovKiEKICBcYnJpZWYgICAgIENhbGN1bGF0ZSBudW1iZXIgb2YgU0JSIGJhbmRzIGJldHdlZW4gc3RhcnQgYW5kIHN0b3AgYmFuZAoKICBHaXZlbiB0aGUgbnVtYmVyIG9mIGJhbmRzIHBlciBvY3RhdmUsIHRoaXMgZnVuY3Rpb24gY2FsY3VsYXRlcyBob3cgbWFueQogIGJhbmRzIGZpdCBpbiB0aGUgZ2l2ZW4gZnJlcXVlbmN5IHJhbmdlLgogIFdoZW4gdGhlIHdhcnBGbGFnIGlzIHNldCwgdGhlICdiYW5kIGRlbnNpdHknIGlzIGRlY3JlYXNlZCBieSBhIGZhY3RvcgogIG9mIDEvMS4zCgogIFxyZXR1cm4gICAgbnVtYmVyIG9mIGJhbmRzCiovCnN0YXRpYyBpbnQKbnVtYmVyT2ZCYW5kcyhGSVhQX1NHTCBicG9fZGl2MTYsIC8qITwgSW5wdXQ6IG51bWJlciBvZiBiYW5kcyBwZXIgb2N0YXZlIGRpdmlkZWQgYnkgMTYgKi8KICAgICAgICAgICAgICBpbnQgICAgc3RhcnQsICAgICAvKiE8IEZpcnN0IFFNRiBiYW5kIG9mIFNCUiBmcmVxdWVuY3kgcmFuZ2UgKi8KICAgICAgICAgICAgICBpbnQgICAgc3RvcCwgICAgICAvKiE8IExhc3QgUU1GIGJhbmQgb2YgU0JSIGZyZXF1ZW5jeSByYW5nZSArIDEgKi8KICAgICAgICAgICAgICBpbnQgICAgd2FycEZsYWcpICAvKiE8IFN0cmV0Y2hpbmcgZmxhZyAqLwp7CiAgRklYUF9TR0wgbnVtX2JhbmRzX2RpdjEyODsKICBpbnQgICAgbnVtX2JhbmRzOwoKICBudW1fYmFuZHNfZGl2MTI4ID0gRlhfREJMMkZYX1NHTChmTXVsdChGREtfZ2V0TnVtT2N0YXZlc0Rpdjgoc3RhcnQsc3RvcCksYnBvX2RpdjE2KSk7CgogIGlmICh3YXJwRmxhZykgewogICAgLyogQXBwbHkgdGhlIHdhcnAgZmFjdG9yIG9mIDEuMyB0byBnZXQgd2lkZXIgYmFuZHMuICBXZSB1c2UgYSB2YWx1ZQogICAgICAgb2YgMzI3NjgvMjUyMDAgaW5zdGVhZCBvZiB0aGUgZXhhY3QgdmFsdWUgdG8gYXZvaWQgY3JpdGljYWwgY2FzZXMKICAgICAgIG9mIHJvdW5kaW5nLgogICAgKi8KICAgIG51bV9iYW5kc19kaXYxMjggPSBGWF9EQkwyRlhfU0dMKGZNdWx0KG51bV9iYW5kc19kaXYxMjgsIEZMMkZYQ09OU1RfU0dMKDI1MjAwLjAvMzI3NjguMCkpKTsKICB9CgogIC8qIGFkZCBzY2FsZWQgMSBmb3Igcm91bmRpbmcgdG8gZXZlbiBudW1iZXJzOiAqLwogIG51bV9iYW5kc19kaXYxMjggPSBudW1fYmFuZHNfZGl2MTI4ICsgRkwyRlhDT05TVF9TR0woIDEuMGYvMTI4LjBmICk7CiAgLyogc2NhbGUgYmFjayB0byByaWdodCBhbGlnbmVkIGludGVnZXIgYW5kIGRvdWJsZSB0aGUgdmFsdWU6ICovCiAgbnVtX2JhbmRzID0gMiAqICgoTE9ORyludW1fYmFuZHNfZGl2MTI4ID4+IChGUkFDVF9CSVRTIC0gNykpOwoKICByZXR1cm4obnVtX2JhbmRzKTsKfQoKCi8qIQogIFxicmllZiAgICAgQ2FsY3VsYXRlIHdpZHRoIG9mIFNCUiBiYW5kcwoKICBHaXZlbiB0aGUgZGVzaXJlZCBudW1iZXIgb2YgYmFuZHMgd2l0aGluIHRoZSBTQlIgZnJlcXVlbmN5IHJhbmdlLAogIHRoaXMgZnVuY3Rpb24gY2FsY3VsYXRlcyB0aGUgd2lkdGggb2YgZWFjaCBTQlIgYmFuZCBpbiBRTUYgY2hhbm5lbHMuCiAgVGhlIGJhbmRzIGdldCB3aWRlciBmcm9tIHN0YXJ0IHRvIHN0b3AgKGJhcmsgc2NhbGUpLgoqLwpzdGF0aWMgdm9pZApDYWxjQmFuZHMoVUNIQVIgKiBkaWZmLCAgICAvKiE8IFZlY3RvciBvZiB3aWR0aHMgdG8gYmUgY2FsY3VsYXRlZCAqLwogICAgICAgICAgVUNIQVIgc3RhcnQsICAgICAvKiE8IExvd2VyIGVuZCBvZiBzdWJiYW5kIHJhbmdlICovCiAgICAgICAgICBVQ0hBUiBzdG9wLCAgICAgIC8qITwgVXBwZXIgZW5kIG9mIHN1YmJhbmQgcmFuZ2UgKi8KICAgICAgICAgIFVDSEFSIG51bV9iYW5kcykgLyohPCBEZXNpcmVkIG51bWJlciBvZiBiYW5kcyAqLwp7CiAgaW50IGk7CiAgaW50IHByZXZpb3VzOwogIGludCBjdXJyZW50OwogIEZJWFBfU0dMIGV4YWN0LCB0ZW1wOwogIEZJWFBfU0dMIGJhbmRmYWN0b3IgPSBjYWxjRmFjdG9yUGVyQmFuZChzdGFydCwgc3RvcCwgbnVtX2JhbmRzKTsKCiAgcHJldmlvdXMgPSBzdG9wOyAvKiBTdGFydCB3aXRoIGhpZ2hlc3QgUU1GIGNoYW5uZWwgKi8KICBleGFjdCA9IChGSVhQX1NHTCkoc3RvcCA8PCAoRlJBQ1RfQklUUy04KSk7IC8qIFNoaWZ0IGxlZnQgdG8gZ2FpbiBzb21lIGFjY3VyYWN5ICovCgogIGZvcihpPW51bV9iYW5kcy0xOyBpPj0wOyBpLS0pIHsKICAgIC8qIENhbGN1bGF0ZSBib3JkZXIgb2YgbmV4dCBsb3dlciBzYnIgYmFuZCAqLwogICAgZXhhY3QgPSBGWF9EQkwyRlhfU0dMKGZNdWx0KGV4YWN0LGJhbmRmYWN0b3IpKTsKCiAgICAvKiBBZGQgc2NhbGVkIDAuNSBmb3Igcm91bmRpbmc6CiAgICAgICBXZSB1c2UgYSB2YWx1ZSAxMjgvMjU2IGluc3RlYWQgb2YgMC41IHRvIGF2b2lkIHNvbWUgY3JpdGljYWwgY2FzZXMgb2Ygcm91bmRpbmcuICovCiAgICB0ZW1wID0gZXhhY3QgKyAgRkwyRlhDT05TVF9TR0woMTI4LjAvMzI3NjguMCk7CgogICAgLyogc2NhbGUgYmFjayB0byByaWdodCBhbGluZ2VkIGludGVnZXI6ICovCiAgICBjdXJyZW50ID0gKExPTkcpdGVtcCA+PiAoRlJBQ1RfQklUUy04KTsKCiAgICAvKiBTYXZlIHdpZHRoIG9mIGJhbmQgaSAqLwogICAgZGlmZltpXSA9IHByZXZpb3VzIC0gY3VycmVudDsKICAgIHByZXZpb3VzID0gY3VycmVudDsKICB9Cn0KCgovKiEKICBcYnJpZWYgICAgIENhbGN1bGF0ZSBjdW11bGF0ZWQgc3VtIHZlY3RvciBmcm9tIGRlbHRhIHZlY3RvcgoqLwpzdGF0aWMgdm9pZApjdW1TdW0oVUNIQVIgc3RhcnRfdmFsdWUsIFVDSEFSKiBkaWZmLCBVQ0hBUiBsZW5ndGgsIFVDSEFSICpzdGFydF9hZHJlc3MpCnsKICBpbnQgaTsKICBzdGFydF9hZHJlc3NbMF09c3RhcnRfdmFsdWU7CiAgZm9yKGk9MTsgaTw9bGVuZ3RoOyBpKyspCiAgICBzdGFydF9hZHJlc3NbaV0gPSBzdGFydF9hZHJlc3NbaS0xXSArIGRpZmZbaS0xXTsKfQoKCi8qIQogIFxicmllZiAgICAgQWRhcHQgd2lkdGggb2YgZnJlcXVlbmN5IGJhbmRzIGluIHRoZSBzZWNvbmQgcmVnaW9uCgogIElmIFNCUiBzcGFucyBtb3JlIHRoYW4gMiBvY3RhdmVzLCB0aGUgdXBwZXIgcGFydCBvZiBhIGJhcmstZnJlcXVlbmN5LXNjYWxlCiAgaXMgY2FsY3VsYXRlZCBzZXBhcmF0ZWx5LiBUaGlzIGZ1bmN0aW9uIHRyaWVzIHRvIGF2b2lkIHRoYXQgdGhlIHNlY29uZCByZWdpb24KICBzdGFydHMgd2l0aCBhIGJhbmQgc21hbGxlciB0aGFuIHRoZSBoaWdoZXN0IGJhbmQgb2YgdGhlIGZpcnN0IHJlZ2lvbi4KKi8Kc3RhdGljIFNCUl9FUlJPUgptb2RpZnlCYW5kcyhVQ0hBUiBtYXhfYmFuZF9wcmV2aW91cywgVUNIQVIgKiBkaWZmLCBVQ0hBUiBsZW5ndGgpCnsKICBpbnQgY2hhbmdlID0gbWF4X2JhbmRfcHJldmlvdXMgLSBkaWZmWzBdOwoKICAvKiBMaW1pdCB0aGUgY2hhbmdlIHNvIHRoYXQgdGhlIGxhc3QgYmFuZCBjYW5ub3QgZ2V0IG5hcnJvd2VyIHRoYW4gdGhlIGZpcnN0IG9uZSAqLwogIGlmICggY2hhbmdlID4gKGRpZmZbbGVuZ3RoLTFdLWRpZmZbMF0pPj4xICkKICAgIGNoYW5nZSA9IChkaWZmW2xlbmd0aC0xXS1kaWZmWzBdKT4+MTsKCiAgZGlmZlswXSArPSBjaGFuZ2U7CiAgZGlmZltsZW5ndGgtMV0gLT0gY2hhbmdlOwogIHNoZWxsc29ydChkaWZmLCBsZW5ndGgpOwoKICByZXR1cm4gU0JSREVDX09LOwp9CgoKLyohCiAgXGJyaWVmICAgVXBkYXRlIGhpZ2ggcmVzb2x1dGlvbiBmcmVxdWVuY3kgYmFuZCB0YWJsZQoqLwpzdGF0aWMgdm9pZApzYnJkZWNVcGRhdGVIaVJlcyhVQ0hBUiAqIGhfaGlyZXMsCiAgICAgICAgICAgICAgICAgIFVDSEFSICogbnVtX2hpcmVzLAogICAgICAgICAgICAgICAgICBVQ0hBUiAqIHZfa19tYXN0ZXIsCiAgICAgICAgICAgICAgICAgIFVDSEFSIG51bV9iYW5kcywKICAgICAgICAgICAgICAgICAgVUNIQVIgeG92ZXJfYmFuZCkKewogIFVDSEFSIGk7CgogICpudW1faGlyZXMgPSBudW1fYmFuZHMteG92ZXJfYmFuZDsKCiAgZm9yKGk9eG92ZXJfYmFuZDsgaTw9bnVtX2JhbmRzOyBpKyspIHsKICAgIGhfaGlyZXNbaS14b3Zlcl9iYW5kXSA9IHZfa19tYXN0ZXJbaV07CiAgfQp9CgoKLyohCiAgXGJyaWVmICBCdWlsZCBsb3cgcmVzb2x1dGlvbiB0YWJsZSBvdXQgb2YgaGlnaCByZXNvbHV0aW9uIHRhYmxlCiovCnN0YXRpYyB2b2lkCnNicmRlY1VwZGF0ZUxvUmVzKFVDSEFSICogaF9sb3JlcywKICAgICAgICAgICAgICAgICAgVUNIQVIgKiBudW1fbG9yZXMsCiAgICAgICAgICAgICAgICAgIFVDSEFSICogaF9oaXJlcywKICAgICAgICAgICAgICAgICAgVUNIQVIgbnVtX2hpcmVzKQp7CiAgVUNIQVIgaTsKCiAgaWYoIChudW1faGlyZXMgJiAxKSA9PSAwKSB7CiAgICAvKiBJZiBldmVuIG51bWJlciBvZiBoaXJlcyBiYW5kcyAqLwogICAgKm51bV9sb3JlcyA9IG51bV9oaXJlcyA+PiAxOwogICAgLyogVXNlIGV2ZXJ5IHNlY29uZCBsb3Jlcz1oaXJlc1swLDIsNC4uLl0gKi8KICAgIGZvcihpPTA7IGk8PSpudW1fbG9yZXM7IGkrKykKICAgICAgaF9sb3Jlc1tpXSA9IGhfaGlyZXNbaSoyXTsKICB9CiAgZWxzZSB7CiAgICAvKiBPZGQgbnVtYmVyIG9mIGhpcmVzLCB3aGljaCBtZWFucyB4b3ZlciBpcyBvZGQgKi8KICAgICpudW1fbG9yZXMgPSAobnVtX2hpcmVzKzEpID4+IDE7CiAgICAvKiBVc2UgbG9yZXM9aGlyZXNbMCwxLDMsNSAuLi5dICovCiAgICBoX2xvcmVzWzBdID0gaF9oaXJlc1swXTsKICAgIGZvcihpPTE7IGk8PSpudW1fbG9yZXM7IGkrKykgewogICAgICBoX2xvcmVzW2ldID0gaF9oaXJlc1tpKjItMV07CiAgICB9CiAgfQp9CgoKLyohCiAgXGJyaWVmICAgRGVyaXZlIGEgbG93LXJlc29sdXRpb24gZnJlcXVlbmN5LXRhYmxlIGZyb20gdGhlIG1hc3RlciBmcmVxdWVuY3kgdGFibGUKKi8Kdm9pZApzYnJkZWNEb3duU2FtcGxlTG9SZXMoVUNIQVIgKnZfcmVzdWx0LAogICAgICAgICAgICAgICAgICAgICAgVUNIQVIgbnVtX3Jlc3VsdCwKICAgICAgICAgICAgICAgICAgICAgIFVDSEFSICpmcmVxQmFuZFRhYmxlUmVmLAogICAgICAgICAgICAgICAgICAgICAgVUNIQVIgbnVtX1JlZikKewogIGludCBzdGVwOwogIGludCBpLGo7CiAgaW50IG9yZ19sZW5ndGgscmVzdWx0X2xlbmd0aDsKICBpbnQgdl9pbmRleFtNQVhfRlJFUV9DT0VGRlM+PjFdOwoKICAvKiBpbml0ICovCiAgb3JnX2xlbmd0aCA9IG51bV9SZWY7CiAgcmVzdWx0X2xlbmd0aCA9IG51bV9yZXN1bHQ7CgogIHZfaW5kZXhbMF0gPSAwOyAgIC8qIEFsd2F5cyB1c2UgbGVmdCBib3JkZXIgKi8KICBpPTA7CiAgd2hpbGUob3JnX2xlbmd0aCA+IDApIHsKICAgIC8qIENyZWF0ZSBkb3duc2FtcGxlIHZlY3RvciAqLwogICAgaSsrOwogICAgc3RlcCA9IG9yZ19sZW5ndGggLyByZXN1bHRfbGVuZ3RoOwogICAgb3JnX2xlbmd0aCA9IG9yZ19sZW5ndGggLSBzdGVwOwogICAgcmVzdWx0X2xlbmd0aC0tOwogICAgdl9pbmRleFtpXSA9IHZfaW5kZXhbaS0xXSArIHN0ZXA7CiAgfQoKICBmb3Ioaj0wO2o8PWk7aisrKSB7CiAgICAvKiBVc2UgZG93bnNhbXBsZSB2ZWN0b3IgdG8gaW5kZXggTG9SZXNvbHV0aW9uIHZlY3RvciAqLwogICAgdl9yZXN1bHRbal09ZnJlcUJhbmRUYWJsZVJlZlt2X2luZGV4W2pdXTsKICB9Cgp9CgoKLyohCiAgXGJyaWVmICAgU29ydGluZyByb3V0aW5lCiovCnZvaWQgc2hlbGxzb3J0KFVDSEFSICppbiwgVUNIQVIgbikKewoKICBpbnQgaSwgaiwgdiwgdzsKICBpbnQgaW5jID0gMTsKCiAgZG8KICAgIGluYyA9IDMgKiBpbmMgKyAxOwogIHdoaWxlIChpbmMgPD0gbik7CgogIGRvIHsKICAgIGluYyA9IGluYyAvIDM7CiAgICBmb3IgKGkgPSBpbmM7IGkgPCBuOyBpKyspIHsKICAgICAgdiA9IGluW2ldOwogICAgICBqID0gaTsKICAgICAgd2hpbGUgKCh3PWluW2otaW5jXSkgPiB2KSB7CiAgICAgICAgaW5bal0gPSB3OwogICAgICAgIGogLT0gaW5jOwogICAgICAgIGlmIChqIDwgaW5jKQogICAgICAgICAgYnJlYWs7CiAgICAgIH0KICAgICAgaW5bal0gPSB2OwogICAgfQogIH0gd2hpbGUgKGluYyA+IDEpOwoKfQoKCgovKiEKICBcYnJpZWYgICBSZXNldCBmcmVxdWVuY3kgYmFuZCB0YWJsZXMKICBccmV0dXJuICBlcnJvckNvZGUsIDAgaWYgc3VjY2Vzc2Z1bAoqLwpTQlJfRVJST1IKcmVzZXRGcmVxQmFuZFRhYmxlcyhIQU5ETEVfU0JSX0hFQURFUl9EQVRBIGhIZWFkZXJEYXRhLCBjb25zdCBVSU5UIGZsYWdzKQp7CiAgU0JSX0VSUk9SIGVyciA9IFNCUkRFQ19PSzsKICBpbnQgazIsa3gsIGxzYiwgdXNiOwogIGludCAgICAgaW50VGVtcDsKICBVQ0hBUiAgICBuQmFuZHNMbywgbkJhbmRzSGk7CiAgSEFORExFX0ZSRVFfQkFORF9EQVRBIGhGcmVxID0gJmhIZWFkZXJEYXRhLT5mcmVxQmFuZERhdGE7CgogIC8qIENhbGN1bGF0ZSBtYXN0ZXIgZnJlcXVlbmN5IGZ1bmN0aW9uICovCiAgZXJyID0gc2JyZGVjVXBkYXRlRnJlcVNjYWxlKGhGcmVxLT52X2tfbWFzdGVyLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmaEZyZXEtPm51bU1hc3RlciwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaEhlYWRlckRhdGEtPnNiclByb2NTbXBsUmF0ZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaEhlYWRlckRhdGEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGZsYWdzKTsKCiAgaWYgKCBlcnIgfHwgKGhIZWFkZXJEYXRhLT5ic19pbmZvLnhvdmVyX2JhbmQgPiBoRnJlcS0+bnVtTWFzdGVyKSApIHsKICAgIHJldHVybiBTQlJERUNfVU5TVVBQT1JURURfQ09ORklHOwogIH0KCiAgLyogRGVyaXZlIEhpcmVzb2x1dGlvbiBmcm9tIG1hc3RlciBmcmVxdWVuY3kgZnVuY3Rpb24gKi8KICBzYnJkZWNVcGRhdGVIaVJlcyhoRnJlcS0+ZnJlcUJhbmRUYWJsZVsxXSwgJm5CYW5kc0hpLCBoRnJlcS0+dl9rX21hc3RlciwgaEZyZXEtPm51bU1hc3RlciwgaEhlYWRlckRhdGEtPmJzX2luZm8ueG92ZXJfYmFuZCApOwogIC8qIERlcml2ZSBMb3Jlc29sdXRpb24gZnJvbSBIaXJlc29sdXRpb24gKi8KICBzYnJkZWNVcGRhdGVMb1JlcyhoRnJlcS0+ZnJlcUJhbmRUYWJsZVswXSwgJm5CYW5kc0xvLCBoRnJlcS0+ZnJlcUJhbmRUYWJsZVsxXSwgbkJhbmRzSGkpOwoKCiAgaEZyZXEtPm5TZmJbMF0gPSBuQmFuZHNMbzsKICBoRnJlcS0+blNmYlsxXSA9IG5CYW5kc0hpOwoKICAvKiBDaGVjayBpbmRleCB0byBmcmVxQmFuZFRhYmxlWzBdICovCiAgaWYgKCAhKG5CYW5kc0xvID4gMCkgfHwgKG5CYW5kc0xvID4gKE1BWF9GUkVRX0NPRUZGUz4+MSkpICkgewogICAgcmV0dXJuIFNCUkRFQ19VTlNVUFBPUlRFRF9DT05GSUc7CiAgfQoKICBsc2IgPSBoRnJlcS0+ZnJlcUJhbmRUYWJsZVswXVswXTsKICB1c2IgPSBoRnJlcS0+ZnJlcUJhbmRUYWJsZVswXVtuQmFuZHNMb107CgogIC8qIEFkZGl0aW9uYWwgY2hlY2sgZm9yIGxzYiAqLwogIGlmICggKGxzYiA+ICgzMikpIHx8IChsc2IgPj0gdXNiKSApIHsKICAgIHJldHVybiBTQlJERUNfVU5TVVBQT1JURURfQ09ORklHOwogIH0KCgogIC8qIENhbGN1bGF0ZSBudW1iZXIgb2Ygbm9pc2UgYmFuZHMgKi8KCiAgazIgPSBoRnJlcS0+ZnJlcUJhbmRUYWJsZVsxXVtuQmFuZHNIaV07CiAga3ggPSBoRnJlcS0+ZnJlcUJhbmRUYWJsZVsxXVswXTsKCiAgaWYgKGhIZWFkZXJEYXRhLT5ic19kYXRhLm5vaXNlX2JhbmRzID09IDApCiAgewogICAgaEZyZXEtPm5OZmIgPSAxOwogIH0KICBlbHNlIC8qIENhbGN1bGF0ZSBubyBvZiBub2lzZSBiYW5kcyAxLDIgb3IgMyBiYW5kcy9vY3RhdmUgKi8KICB7CiAgICAvKiBGZXRjaCBudW1iZXIgb2Ygb2N0YXZlcyBkaXZpZGVkIGJ5IDMyICovCiAgICBpbnRUZW1wID0gKExPTkcpRkRLX2dldE51bU9jdGF2ZXNEaXY4KGt4LGsyKSA+PiAyOwoKICAgIC8qIEludGVnZXItTXVsdGlwbGljYXRpb24gd2l0aCBudW1iZXIgb2YgYmFuZHM6ICovCiAgICBpbnRUZW1wID0gaW50VGVtcCAqIGhIZWFkZXJEYXRhLT5ic19kYXRhLm5vaXNlX2JhbmRzOwoKICAgIC8qIEFkZCBzY2FsZWQgMC41IGZvciByb3VuZGluZzogKi8KICAgIGludFRlbXAgPSBpbnRUZW1wICsgKExPTkcpRkwyRlhDT05TVF9TR0woMC41Zi8zMi4wZik7CgogICAgLyogQ29udmVydCB0byByaWdodC1hbGlnbmVkIGludGVnZXI6ICovCiAgICBpbnRUZW1wID0gaW50VGVtcCA+PiAoRlJBQ1RfQklUUyAtIDEgLypzaWduKi8gLSA1IC8qIHJlc2NhbGUgKi8pOwoKICAgIC8qIENvbXBhcmUgd2l0aCBmbG9hdCBjYWxjdWxhdGlvbiAqLwogICAgRkRLX0FTU0VSVCggaW50VGVtcCA9PSAgKGludCkoKGhIZWFkZXJEYXRhLT5ic19kYXRhLm5vaXNlX2JhbmRzICogRkRLbG9nKCAoZmxvYXQpazIva3gpIC8gKGZsb2F0KShGREtsb2coMi4wKSkpKzAuNSkgKTsKCiAgICBpZiggaW50VGVtcD09MCkKICAgICAgaW50VGVtcD0xOwoKICAgIGhGcmVxLT5uTmZiID0gaW50VGVtcDsKICB9CgogIGhGcmVxLT5uSW52ZkJhbmRzID0gaEZyZXEtPm5OZmI7CgogIGlmKCBoRnJlcS0+bk5mYiA+IE1BWF9OT0lTRV9DT0VGRlMgKSB7CiAgICByZXR1cm4gU0JSREVDX1VOU1VQUE9SVEVEX0NPTkZJRzsKICB9CgogIC8qIEdldCBub2lzZSBiYW5kcyAqLwogIHNicmRlY0Rvd25TYW1wbGVMb1JlcyhoRnJlcS0+ZnJlcUJhbmRUYWJsZU5vaXNlLAogICAgICAgICAgICAgICAgICAgICAgICBoRnJlcS0+bk5mYiwKICAgICAgICAgICAgICAgICAgICAgICAgaEZyZXEtPmZyZXFCYW5kVGFibGVbMF0sCiAgICAgICAgICAgICAgICAgICAgICAgIG5CYW5kc0xvKTsKCgoKCiAgaEZyZXEtPmxvd1N1YmJhbmQgID0gbHNiOwogIGhGcmVxLT5oaWdoU3ViYmFuZCA9IHVzYjsKCiAgcmV0dXJuIFNCUkRFQ19PSzsKfQo=