ZGlmZiAtLWdpdCBhL3NyYy9ndWlfbWFjLmMgYi9zcmMvZ3VpX21hYy5jCm5ldyBmaWxlIG1vZGUgMTAwNjQ0CmluZGV4IDAwMDAwMDAuLjJiNzRjNjMKLS0tIC9kZXYvbnVsbAorKysgYi9zcmMvZ3VpX21hYy5jCkBAIC0wLDAgKzEsNTgyMCBAQAorLyogdmk6c2V0IHRzPTggc3RzPTQgc3c9NDoKKyAqCisgKiBWSU0gLSBWaSBJTXByb3ZlZAkJYnkgQnJhbSBNb29sZW5hYXIKKyAqCQkJCUdVSS9Nb3RpZiBzdXBwb3J0IGJ5IFJvYmVydCBXZWJiCisgKgkJCQlNYWNpbnRvc2ggcG9ydCBieSBEYW55IFN0LUFtYW50CisgKgkJCQkJICAgICAgYW5kIEF4ZWwgS2llbGhvcm4KKyAqCQkJCVBvcnQgdG8gTVBXIGJ5IEJlcm5oYXJkIFByn21tZXIKKyAqCQkJCUluaXRpYWwgQ2FyYm9uIHBvcnQgYnkgQW1tb24gU2tpZG1vcmUKKyAqCisgKiBEbyAiOmhlbHAgdWdhbmRhIiAgaW4gVmltIHRvIHJlYWQgY29weWluZyBhbmQgdXNhZ2UgY29uZGl0aW9ucy4KKyAqIERvICI6aGVscCBjcmVkaXRzIiBpbiBWaW0gdG8gc2VlIGEgbGlzdCBvZiBwZW9wbGUgd2hvIGNvbnRyaWJ1dGVkLgorICogU2VlIFJFQURNRS50eHQgZm9yIGFuIG92ZXJ2aWV3IG9mIHRoZSBWaW0gc291cmNlIGNvZGUuCisgKi8KKworLyoKKyAqIE5PVEU6IENvbW1lbnQgbWVudGlvbm5pbmcgRkFRIHJlZmVyIHRvIHRoZSBib29rOgorICogICAgICAgIk1hY3dvcmxkIE1hYyBQcm9ncmFtbWluZyBGQVFzIiBmcm9tICJJREcgQm9va3MiCisgKi8KKworLyoKKyAqIFdBUk5JTkc6IFZpbSBtdXN0IGJlIGFibGUgdG8gY29tcGlsZSB3aXRob3V0IENhcmJvbgorICoJICAgIEFzIHRoZSBkZXNpcmVkIG1pbmltdW0gcmVxdWlyZW1lbnQgYXJlIGNpcmNhIFN5c3RlbSA3CisgKgkgICAgKEkgd2FudCB0byBydW4gaXQgb24gbXkgTWFjIENsYXNzaWMpIChEYW55KQorICovCisKKy8qCisgKiBUT0RPOiBDaGFuZ2Ugc3RpbGwgdG8gbWVyZ2UgZnJvbSB0aGUgbWFjdmltJ3MgaURpc2sKKyAqCisgKiBlcnJvcl9nYSwgbWNoX2Vycm1zZywgTmF2aWdhdGlvbidzIGNoYW5nZXMgaW4gZ3VpX21jaF9icm93c2UKKyAqIHVzZXMgb2YgTWVudUl0ZW1JbmRleCwgY2hhbmdlcyBpbiBndWlfbWNoX3NldF9zaGVsbHNpemUsCisgKiBTY3JhcE1hbmFnZXIgZXJyb3IgaGFuZGxpbmcuCisgKiBDb21tZW50cyBhYm91dCBmdW5jdGlvbiByZW1haW5pbmcgdG8gQ2FyYm9uaXplLgorICoKKyAqLworCisvKiBUT0RPOiBmaW5kIHRoZSBiZXN0IHBsYWNlIGZvciB0aGlzIChEYW55KSAqLworI2lmIDAKKyMgIGlmICEgVEFSR0VUX0FQSV9NQUNfQ0FSQk9OCisvKiBFbmFibGUgdGhlIG5ldyBBUEkgZnVuY3Rpb25zIGV2ZW4gd2hlbiBub3QgY29tcGlsaW5nIGZvciBDYXJib24gKi8KKy8qIEFwcGxlIHJlY29tZW5kcyBVbml2ZXJzYWwgSW50ZXJmYWNlIDMuMy4yIG9yIGxhdGVyICovCisjICBkZWZpbmUgT1BBUVVFX1RPT0xCT1hfU1RSVUNUUwkJMQorIyAgZGVmaW5lIEFDQ0VTU09SX0NBTExTX0FSRV9GVU5DVElPTlMJMQorLyogSGVscCBNZW51IG5vdCBzdXBwb3J0ZWQgYnkgQ2FyYm9uICovCisjICBkZWZpbmUgVVNFX0hFTFBNRU5VCisjIGVuZGlmCisjZW5kaWYKKworI2luY2x1ZGUgPERldmljZXMuaD4gLyogaW5jbHVkZWQgZmlyc3QgdG8gYXZvaWQgQ1IgcHJvYmxlbXMgKi8KKyNpbmNsdWRlICJ2aW0uaCIKKworLyogRW5hYmxlIENvbnRleHR1YWwgTWVudSBTdXBwb3J0ICovCisjaWYgVU5JVkVSU0FMX0lOVEVSRkFDRVNfVkVSU0lPTiA+PSAweDAzMjAKKyMgZGVmaW5lIFVTRV9DVFJMQ0xJQ0tNRU5VCisjZW5kaWYKKworLyogUHV0IFZpbSBIZWxwIGluIE1hY09TIEhlbHAgKi8KKyNkZWZpbmUgVVNFX0hFTFBNRU5VCisKKy8qIEVuYWJsZSBBRVZFTlQgKi8KKyNkZWZpbmUgVVNFX0FFVkVOVAorCisvKiBDb21waWxlIGFzIENvZGVXYXJpb3IgRXh0ZXJuYWwgRWRpdG9yICovCisjaWYgZGVmaW5lZChGRUFUX0NXX0VESVRPUikgJiYgIWRlZmluZWQoVVNFX0FFVkVOVCkKKyMgZGVmaW5lIFVTRV9BRVZFTlQgLyogTmVlZCBBcHBsZSBFdmVudCBTdXBwb3J0ICovCisjZW5kaWYKKworLyogVGhlIFZJTSBjcmVhdG9yIGlzIENvZGVXYXJpb3Igc3BlY2lmaWMgKi8KKyNpZiAhKGRlZmluZWQoX19NUkNfXykgfHwgZGVmaW5lZChfX1NDX18pIHx8IGRlZmluZWQoX19BUFBMRV9DQ19fKSkKKyMgZGVmaW5lIFVTRV9WSU1fQ1JFQVRPUl9JRAorI2Vsc2UKKyMgaWYgMCAvKiBXYXMgdGhpcyB1c2VmdWxsIGZvciBzb21lIGNvbXBpbGVyPyAoRGFueSkgKi8KK3N0YXRpYyAgICBPU1R5cGUJX2ZjcmVhdG9yID0gJ1ZJTSEnOworc3RhdGljICAgIE9TVHlwZQlfZnR5cGUgPSAnVEVYVCc7CisjIGVuZGlmCisjZW5kaWYKKworLyogQ0FSQk9OIHZlcnNpb24gb25seSB0ZXN0ZWQgd2l0aCBQcm9qZWN0IEJ1aWxkZXIgdW5kZXIgTWFjT1MgWCAqLworI3VuZGVmIFVTRV9DQVJCT05JWkVECisjaWYgKGRlZmluZWQoX19BUFBMRV9DQ19fKSB8fCBkZWZpbmVkKF9fTVJDX18pKSAmJiBkZWZpbmVkKFRBUkdFVF9BUElfTUFDX0NBUkJPTikKKyMgaWYgVEFSR0VUX0FQSV9NQUNfQ0FSQk9OCisjICBkZWZpbmUgVVNFX0NBUkJPTklaRUQKKyMgZW5kaWYKKyNlbmRpZgorCisjdW5kZWYgVVNFX01PVVNFV0hFRUwKKyNpZiBkZWZpbmVkKE1BQ09TX1gpICYmIGRlZmluZWQoVVNFX0NBUkJPTklaRUQpCisjIGRlZmluZSBVU0VfTU9VU0VXSEVFTAorc3RhdGljIEV2ZW50SGFuZGxlclVQUCBtb3VzZVdoZWVsSGFuZGxlclVQUCA9IE5VTEw7CisjZW5kaWYKKworLyogRGVidWdnaW5nIGZlYXR1cmU6IHN0YXJ0IFZpbSB3aW5kb3cgT0ZGU0VUZWQgKi8KKyN1bmRlZiBVU0VfT0ZGU0VURURfV0lORE9XCisKKy8qIERlYnVnZ2luZyBmZWF0dXJlOiB1c2UgQ29kZVdhcmlvciBTSU9VWCAqLworI3VuZGVmIFVTRV9TSU9VWAorCisKKy8qIEluY2x1ZGUgc29tZSBmaWxlLiBUT0RPOiBtb3ZlIGludG8gb3NfbWFjLmggKi8KKyNpbmNsdWRlIDxNZW51cy5oPgorI2luY2x1ZGUgPFJlc291cmNlcy5oPgorI2lmICFUQVJHRVRfQVBJX01BQ19DQVJCT04KKyNpbmNsdWRlIDxTdGFuZGFyZEZpbGUuaD4KKyNpbmNsdWRlIDxUcmFwcy5oPgorI2VuZGlmCisjaW5jbHVkZSA8QmFsbG9vbnMuaD4KKyNpbmNsdWRlIDxQcm9jZXNzZXMuaD4KKyNpZmRlZiBVU0VfQUVWRU5UCisjIGluY2x1ZGUgPEFwcGxlRXZlbnRzLmg+CisjIGluY2x1ZGUgPEFFUmVnaXN0cnkuaD4KKyNlbmRpZgorI2lmZGVmIFVTRV9DVFJMQ0xJQ0tNRU5VCisjIGluY2x1ZGUgPEdlc3RhbHQuaD4KKyNlbmRpZgorI2lmZGVmIFVTRV9TSU9VWAorIyBpbmNsdWRlIDxzdGRpby5oPgorIyBpbmNsdWRlIDxzaW91eC5oPgorIyBpbmNsdWRlIDxjb25zb2xlLmg+CisjZW5kaWYKKyNpZiBVTklWRVJTQUxfSU5URVJGQUNFU19WRVJTSU9OID49IDB4MDMzMAorIyBpbmNsdWRlIDxDb250cm9sRGVmaW5pdGlvbnMuaD4KKyMgaW5jbHVkZSA8TmF2aWdhdGlvbi5oPiAgLyogTmF2aWdhdGlvbiBvbmx5IHBhcnQgb2YgPz8gKi8KKyNlbmRpZgorCisjaWYgVEFSR0VUX0FQSV9NQUNfQ0FSQk9OICYmIDAKKy8qIE5ldyBIZWxwIEludGVyZmFjZSBmb3IgTWFjLCBub3QgaW1wbGVtZW50ZWQgeWV0LiovCisjIGluY2x1ZGUgPE1hY0hlbHAuaD4KKyNlbmRpZgorCisvKgorICogVHJhbnNsYXRlIG5ldyBuYW1lIHRvIG9sZCBvbmVzCisgKiBOZXcgZnVuY3Rpb24gb25seSBhdmFpbGFibGUgaW4gTWFjT1MgOC41LAorICogU28gdXNlIG9sZCBvbmUgdG8gYmUgY29tcGF0aWJsZSBiYWNrIHRvIFN5c3RlbSA3CisgKi8KKyNpZm5kZWYgVVNFX0NBUkJPTklaRUQKKyMgdW5kZWYgIEVuYWJsZU1lbnVJdGVtCisjIGRlZmluZSBFbmFibGVNZW51SXRlbSBFbmFibGVJdGVtCisjIHVuZGVmICBEaXNhYmxlTWVudUl0ZW0KKyMgZGVmaW5lIERpc2FibGVNZW51SXRlbSBEaXNhYmxlSXRlbQorI2VuZGlmCisKKy8qIENhcmJvbiBkb2VzIG5vdCBzdXBwb3J0IHRoZSBHZXQvU2V0Q29udHJvbGwgZnVuY3Rpb25zLAorICogdXNlIEdldC9TZXRDb250cm9sMzJCaXQgaW5zdGVhZCBhbmQgcmVuYW1lIGZvciBub24tY2FyYm9uCisgKiBzeXN0ZW1zLgorICovCisKKyNpZm5kZWYgVVNFX0NBUkJPTklaRUQKKyMgdW5kZWYgICAgU2V0Q29udHJvbDMyQml0TWF4aW11bQorIyBkZWZpbmUgICBTZXRDb250cm9sMzJCaXRNYXhpbXVtIFNldENvbnRyb2xNYXhpbXVtCisjIHVuZGVmICAgIFNldENvbnRyb2wzMkJpdE1pbmltdW0KKyMgZGVmaW5lICAgU2V0Q29udHJvbDMyQml0TWluaW11bSBTZXRDb250cm9sTWluaW11bQorIyB1bmRlZiAgICBTZXRDb250cm9sMzJCaXRWYWx1ZQorIyBkZWZpbmUgICBTZXRDb250cm9sMzJCaXRWYWx1ZSBTZXRDb250cm9sVmFsdWUKKyMgdW5kZWYgICAgR2V0Q29udHJvbDMyQml0VmFsdWUKKyMgZGVmaW5lICAgR2V0Q29udHJvbDMyQml0VmFsdWUgR2V0Q29udHJvbFZhbHVlCisjZW5kaWYKKworLyoKKyAqID8/PworICovCisKKyNkZWZpbmUga05vdGhpbmcgMAorI2RlZmluZSBrQ3JlYXRlRW1wdHkgMiAvKjEqLworI2RlZmluZSBrQ3JlYXRlUmVjdCAyCisjZGVmaW5lIGtEZXN0cm95IDMKKworLyoKKyAqIERhbnk6IERvbid0IGxpa2UgdGhvc2UuLi4KKyAqLworCisjZGVmaW5lIHRvcExlZnQocikJKCgoUG9pbnQqKSYocikpWzBdKQorI2RlZmluZSBib3RSaWdodChyKQkoKChQb2ludCopJihyKSlbMV0pCisKKworLyogVGltZSBvZiBsYXN0IG1vdXNlIGNsaWNrLCB0byBkZXRlY3QgZG91YmxlLWNsaWNrICovCitzdGF0aWMgbG9uZyBsYXN0TW91c2VUaWNrID0gMDsKKworLyogPz8/ICovCitzdGF0aWMgUmduSGFuZGxlIGN1cnNvclJnbjsKK3N0YXRpYyBSZ25IYW5kbGUgZHJhZ1JnbjsKK3N0YXRpYyBSZWN0IGRyYWdSZWN0Oworc3RhdGljIHNob3J0IGRyYWdSZWN0RW5ibDsKK3N0YXRpYyBzaG9ydCBkcmFnUmVjdENvbnRyb2w7CisKKy8qIFRoaXMgdmFyaWFibGUgaXMgc2V0IHdoZW4gd2FpdGluZyBmb3IgYW4gZXZlbnQsIHdoaWNoIGlzIHRoZSBvbmx5IG1vbWVudAorICogc2Nyb2xsYmFyIGRyYWdnaW5nIGNhbiBiZSBkb25lIGRpcmVjdGx5LiAgSXQncyBub3QgYWxsb3dlZCB3aGlsZSBjb21tYW5kcworICogYXJlIGV4ZWN1dGVkLCBiZWNhdXNlIGl0IG1heSBtb3ZlIHRoZSBjdXJzb3IgYW5kIHRoYXQgbWF5IGNhdXNlIHVuZXhwZWN0ZWQKKyAqIHByb2JsZW1zIChlLmcuLCB3aGlsZSAiOnMiIGlzIHdvcmtpbmcpLgorICovCitzdGF0aWMgaW50IGFsbG93X3Njcm9sbGJhciA9IEZBTFNFOworCisvKiBMYXN0IG1vdXNlIGNsaWNrIGNhdXNlZCBjb250ZXh0dWFsIG1lbnUsICh0byBwcm92aWRlIHByb3BlciByZWxlYXNlKSAqLworI2lmZGVmIFVTRV9DVFJMQ0xJQ0tNRU5VCitzdGF0aWMgc2hvcnQgY2xpY2tJc1BvcHVwOworI2VuZGlmCisKKy8qIEZlZWRiYWNrIEFjdGlvbiBmb3IgU2Nyb2xsYmFyICovCitDb250cm9sQWN0aW9uVVBQIGdTY3JvbGxBY3Rpb247CitDb250cm9sQWN0aW9uVVBQIGdTY3JvbGxEcmFnOworCisvKiBLZWVwaW5nIHRyYWNrIG9mIHdoaWNoIHNjcm9sbGJhciBpcyBiZWluZyBkcmFnZ2VkICovCitzdGF0aWMgQ29udHJvbEhhbmRsZSBkcmFnZ2VkX3NiID0gTlVMTDsKKworLyoKKyAqIFRoZSBRdWlja2RyYXcgZ2xvYmFsIGlzIHByZWRlZmluZWQgaW4gQ29kZVdhcmlvcgorICogYnV0IGlzIG5vdCBpbiBBcHBsZSBNUFcKKyAqLworI2lmIChkZWZpbmVkKF9fTVJDX18pIHx8IGRlZmluZWQoX19TQ19fKSkKKyMgaWYgIShkZWZpbmVkKFRBUkdFVF9BUElfTUFDX0NBUkJPTikgJiYgVEFSR0VUX0FQSV9NQUNfQ0FSQk9OKQorUURHbG9iYWxzIHFkOworIyBlbmRpZgorI2VuZGlmCisKKy8qIENvbG9ycyBNYWNyb3MgKi8KKyNkZWZpbmUgUkdCKHIsZyxiKQkoKHIpIDw8IDE2KSArICgoZykgPDwgOCkgKyAoYikKKyNkZWZpbmUgUmVkKGMpCQkoKGMgJiAweDAwRkYwMDAwKSA+PiAxNikKKyNkZWZpbmUgR3JlZW4oYykJKChjICYgMHgwMDAwRkYwMCkgPj4gIDgpCisjZGVmaW5lIEJsdWUoYykJCSgoYyAmIDB4MDAwMDAwRkYpID4+ICAwKQorCisvKiBLZXkgbWFwcGluZyAqLworCisjZGVmaW5lIHZrX0VzYwkJMHgzNQkvKiAtPiAxQiAqLworCisjZGVmaW5lIHZrX0YxCQkweDdBCS8qIC0+IDEwICovCisjZGVmaW5lIHZrX0YyCQkweDc4ICAvKjB4NjMqLworI2RlZmluZSB2a19GMwkJMHg2MyAgLyoweDc2Ki8KKyNkZWZpbmUgdmtfRjQJCTB4NzYgIC8qMHg2MCovCisjZGVmaW5lIHZrX0Y1CQkweDYwICAvKjB4NjEqLworI2RlZmluZSB2a19GNgkJMHg2MSAgLyoweDYyKi8KKyNkZWZpbmUgdmtfRjcJCTB4NjIgIC8qMHg2MyovICAvKj8qLworI2RlZmluZSB2a19GOAkJMHg2NAorI2RlZmluZSB2a19GOQkJMHg2NQorI2RlZmluZSB2a19GMTAJCTB4NkQKKyNkZWZpbmUgdmtfRjExCQkweDY3CisjZGVmaW5lIHZrX0YxMgkJMHg2RgorI2RlZmluZSB2a19GMTMJCTB4NjkKKyNkZWZpbmUgdmtfRjE0CQkweDZCCisjZGVmaW5lIHZrX0YxNQkJMHg3MQorCisjZGVmaW5lIHZrX0NscgkJMHg0NwkvKiAtPiAxQiAoRVNDKSAqLworI2RlZmluZSB2a19FbnRlcgkweDRDCS8qIC0+IDAzICovCisKKyNkZWZpbmUgdmtfU3BhY2UJMHgzMQkvKiAtPiAyMCAqLworI2RlZmluZSB2a19UYWIJCTB4MzAJLyogLT4gMDkgKi8KKyNkZWZpbmUgdmtfUmV0dXJuCTB4MjQJLyogLT4gMEQgKi8KKy8qIFRoaXMgaXMgd3JvbmcgZm9yIE9TWCwgd2hhdCBpcyBpdCBmb3I/ICovCisjZGVmaW5lIHZrX0RlbGV0ZQkwWDA4CS8qIC0+IDA4IEJhY2tTcGFjZSAqLworCisjZGVmaW5lIHZrX0hlbHAJCTB4NzIJLyogLT4gMDUgKi8KKyNkZWZpbmUgdmtfSG9tZQkJMHg3MwkvKiAtPiAwMSAqLworI2RlZmluZQl2a19QYWdlVXAJMHg3NAkvKiAtPiAwRCAqLworI2RlZmluZSB2a19Gd2REZWxldGUJMHg3NQkvKiAtPiA3RiAqLworI2RlZmluZQl2a19FbmQJCTB4NzcJLyogLT4gMDQgKi8KKyNkZWZpbmUgdmtfUGFnZURvd24JMHg3OQkvKiAtPiAwQyAqLworCisjZGVmaW5lIHZrX1VwCQkweDdFCS8qIC0+IDFFICovCisjZGVmaW5lIHZrX0Rvd24JCTB4N0QJLyogLT4gMUYgKi8KKyNkZWZpbmUJdmtfTGVmdAkJMHg3QgkvKiAtPiAxQyAqLworI2RlZmluZSB2a19SaWdodAkweDdDCS8qIC0+IDFEICovCisKKyNkZWZpbmUgdmtfVW5kbwkJdmtfRjEKKyNkZWZpbmUgdmtfQ3V0CQl2a19GMgorI2RlZmluZQl2a19Db3B5CQl2a19GMworI2RlZmluZQl2a19QYXN0ZQl2a19GNAorI2RlZmluZSB2a19QcmludFNjcmVlbgl2a19GMTMKKyNkZWZpbmUgdmtfU0Nyb2xsTG9jawl2a19GMTQKKyNkZWZpbmUJdmtfUGF1c2UJdmtfRjE1CisjZGVmaW5lCXZrX051bUxvY2sJdmtfQ2xyCisjZGVmaW5lIHZrX0luc2VydAl2a19IZWxwCisKKyNkZWZpbmUgS2V5U3ltCWNoYXIKKworc3RhdGljIHN0cnVjdAoreworICAgIEtleVN5bSAga2V5X3N5bTsKKyAgICBjaGFyX3UgIHZpbV9jb2RlMDsKKyAgICBjaGFyX3UgIHZpbV9jb2RlMTsKK30gc3BlY2lhbF9rZXlzW10gPQoreworICAgIHt2a19VcCwJCSdrJywgJ3UnfSwKKyAgICB7dmtfRG93biwJCSdrJywgJ2QnfSwKKyAgICB7dmtfTGVmdCwJCSdrJywgJ2wnfSwKKyAgICB7dmtfUmlnaHQsCQknaycsICdyJ30sCisKKyAgICB7dmtfRjEsCQknaycsICcxJ30sCisgICAge3ZrX0YyLAkJJ2snLCAnMid9LAorICAgIHt2a19GMywJCSdrJywgJzMnfSwKKyAgICB7dmtfRjQsCQknaycsICc0J30sCisgICAge3ZrX0Y1LAkJJ2snLCAnNSd9LAorICAgIHt2a19GNiwJCSdrJywgJzYnfSwKKyAgICB7dmtfRjcsCQknaycsICc3J30sCisgICAge3ZrX0Y4LAkJJ2snLCAnOCd9LAorICAgIHt2a19GOSwJCSdrJywgJzknfSwKKyAgICB7dmtfRjEwLAkJJ2snLCAnOyd9LAorCisgICAge3ZrX0YxMSwJCSdGJywgJzEnfSwKKyAgICB7dmtfRjEyLAkJJ0YnLCAnMid9LAorICAgIHt2a19GMTMsCQknRicsICczJ30sCisgICAge3ZrX0YxNCwJCSdGJywgJzQnfSwKKyAgICB7dmtfRjE1LAkJJ0YnLCAnNSd9LAorCisvKiAge1hLX0hlbHAsCQknJScsICcxJ30sICovCisvKiAge1hLX1VuZG8sCQknJicsICc4J30sICovCisvKiAge1hLX0JhY2tTcGFjZSwJJ2snLCAnYid9LCAqLworI2lmbmRlZiBNQUNPU19YCisgICAge3ZrX0RlbGV0ZSwJCSdrJywgJ2InfSwKKyNlbmRpZgorICAgIHt2a19JbnNlcnQsCQknaycsICdJJ30sCisgICAge3ZrX0Z3ZERlbGV0ZSwJJ2snLCAnRCd9LAorICAgIHt2a19Ib21lLAkJJ2snLCAnaCd9LAorICAgIHt2a19FbmQsCQknQCcsICc3J30sCisvKiAge1hLX1ByaW9yLAkJJ2snLCAnUCd9LCAqLworLyogIHtYS19OZXh0LAkJJ2snLCAnTid9LCAqLworLyogIHtYS19QcmludCwJCSclJywgJzknfSwgKi8KKworICAgIHt2a19QYWdlVXAsCQknaycsICdQJ30sCisgICAge3ZrX1BhZ2VEb3duLAknaycsICdOJ30sCisKKyAgICAvKiBFbmQgb2YgbGlzdCBtYXJrZXI6ICovCisgICAgeyhLZXlTeW0pMCwJCTAsIDB9Cit9OworCisvKgorICogLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCisgKiBGb3J3YXJkIGRlY2xhcmF0aW9uIChmb3IgdGhvc2UgbmVlZGVkKQorICogLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCisgKi8KKworI2lmZGVmIFVTRV9BRVZFTlQKK09TRXJyIEhhbmRsZVVudXNlZFBhcm1zIChjb25zdCBBcHBsZUV2ZW50ICp0aGVBRXZlbnQpOworI2VuZGlmCisKKy8qCisgKiAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KKyAqIENvbnZlcnNpb24gVXRpbGl0eQorICogLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCisgKi8KKworLyoKKyAqIEMyUGFzY2FsX3NhdmUKKyAqCisgKiBBbGxvY2F0ZSBtZW1vcnkgYW5kIGNvbnZlcnQgdGhlIEMtU3RyaW5nIHBhc3NlZCBpbgorICogaW50byBhIHBhc2NhbCBzdHJpbmcKKyAqCisgKi8KKworY2hhcl91ICpDMlBhc2NhbF9zYXZlKGNoYXJfdSAqQ3N0cmluZykKK3sKKyAgICBjaGFyX3UgICpQYXNjYWxTdHJpbmc7CisgICAgaW50CSAgICBsZW47CisKKyAgICBpZiAoQ3N0cmluZyA9PSBOVUxMKQorCXJldHVybiBOVUxMOworCisgICAgbGVuID0gU1RSTEVOKENzdHJpbmcpOworCisgICAgaWYgKGxlbiA+IDI1NSkgLyogVHJ1bmNhdGUgaWYgbmVjZXNzYXJ5ICovCisJbGVuID0gMjU1OworCisgICAgUGFzY2FsU3RyaW5nID0gYWxsb2MobGVuICsgMSk7CisgICAgaWYgKFBhc2NhbFN0cmluZyAhPSBOVUxMKQorICAgIHsKKwltY2hfbWVtbW92ZShQYXNjYWxTdHJpbmcgKyAxLCBDc3RyaW5nLCBsZW4pOworCVBhc2NhbFN0cmluZ1swXSA9IGxlbjsKKyAgICB9CisKKyAgICByZXR1cm4gUGFzY2FsU3RyaW5nOworfQorCisvKgorICogQzJQYXNjYWxfc2F2ZV9hbmRfcmVtb3ZlX2JhY2tzbGFzaAorICoKKyAqIEFsbG9jYXRlIG1lbW9yeSBhbmQgY29udmVydCB0aGUgQy1TdHJpbmcgcGFzc2VkIGluCisgKiBpbnRvIGEgcGFzY2FsIHN0cmluZy4gQWxzbyByZW1vdmUgdGhlIGJhY2tzbGFzaCBhdCB0aGUgc2FtZSB0aW1lCisgKgorICovCisKK2NoYXJfdSAqQzJQYXNjYWxfc2F2ZV9hbmRfcmVtb3ZlX2JhY2tzbGFzaChjaGFyX3UgKkNzdHJpbmcpCit7CisgICAgY2hhcl91ICAqUGFzY2FsU3RyaW5nOworICAgIGludAkgICAgbGVuOworICAgIGNoYXJfdSAgKnAsICpjOworCisgICAgbGVuID0gU1RSTEVOKENzdHJpbmcpOworCisgICAgaWYgKGxlbiA+IDI1NSkgLyogVHJ1bmNhdGUgaWYgbmVjZXNzYXJ5ICovCisJbGVuID0gMjU1OworCisgICAgUGFzY2FsU3RyaW5nID0gYWxsb2MobGVuICsgMSk7CisgICAgaWYgKFBhc2NhbFN0cmluZyAhPSBOVUxMKQorICAgIHsKKwlmb3IgKGMgPSBDc3RyaW5nLCBwID0gUGFzY2FsU3RyaW5nKzEsIGxlbiA9IDA7ICgqYyAhPSAwKSAmJiAobGVuIDwgMjU1KTsgYysrKQorCXsKKwkgICAgaWYgKCgqYyA9PSAnXFwnKSAmJiAoY1sxXSAhPSAwKSkKKwkgICAgeworCQljKys7CisJICAgIH0KKwkgICAgKnAgPSAqYzsKKwkgICAgcCsrOworCSAgICBsZW4rKzsKKwl9CisJUGFzY2FsU3RyaW5nWzBdID0gbGVuOworICAgIH0KKworICAgIHJldHVybiBQYXNjYWxTdHJpbmc7Cit9CisKKy8qCisgKiBDb252ZXJ0IHRoZSBtb2RpZmllcnMgb2YgYW4gRXZlbnQgaW50byB2aW0ncyBtb2RpZmllcnMgKG1vdXNlKQorICovCisKKyAgICBpbnRfdQorRXZlbnRNb2RpZmllcnMyVmltTW91c2VNb2RpZmllcnMoRXZlbnRNb2RpZmllcnMgbWFjTW9kaWZpZXJzKQoreworICAgIGludF91IHZpbU1vZGlmaWVycyA9IDB4MDA7CisKKyAgICBpZiAobWFjTW9kaWZpZXJzICYgKHNoaWZ0S2V5IHwgcmlnaHRTaGlmdEtleSkpCisJdmltTW9kaWZpZXJzIHw9IE1PVVNFX1NISUZUOworICAgIGlmIChtYWNNb2RpZmllcnMgJiAoY29udHJvbEtleSB8IHJpZ2h0Q29udHJvbEtleSkpCisJdmltTW9kaWZpZXJzIHw9IE1PVVNFX0NUUkw7CisgICAgaWYgKG1hY01vZGlmaWVycyAmIChvcHRpb25LZXkgfCByaWdodE9wdGlvbktleSkpCisJdmltTW9kaWZpZXJzIHw9IE1PVVNFX0FMVDsKKyNpZiAwCisgICAgLyogTm90IHlldCBzdXBwb3J0ZWQgKi8KKyAgICBpZiAobWFjTW9kaWZpZXJzICYgKGNtZEtleSkpIC8qIFRoZXJlJ3Mgbm8gcmlnaHRDbWRLZXkgKi8KKwl2aW1Nb2RpZmllcnMgfD0gTU9VU0VfQ01EOworI2VuZGlmCisgICAgcmV0dXJuICh2aW1Nb2RpZmllcnMpOworfQorCisvKgorICogQ29udmVydCB0aGUgbW9kaWZpZXJzIG9mIGFuIEV2ZW50IGludG8gdmltJ3MgbW9kaWZpZXJzIChrZXlzKQorICovCisKKyAgICBzdGF0aWMgaW50X3UKK0V2ZW50TW9kaWZpZXJzMlZpbU1vZGlmaWVycyhFdmVudE1vZGlmaWVycyBtYWNNb2RpZmllcnMpCit7CisgICAgaW50X3UgdmltTW9kaWZpZXJzID0gMHgwMDsKKworICAgIGlmIChtYWNNb2RpZmllcnMgJiAoc2hpZnRLZXkgfCByaWdodFNoaWZ0S2V5KSkKKwl2aW1Nb2RpZmllcnMgfD0gTU9EX01BU0tfU0hJRlQ7CisgICAgaWYgKG1hY01vZGlmaWVycyAmIChjb250cm9sS2V5IHwgcmlnaHRDb250cm9sS2V5KSkKKwl2aW1Nb2RpZmllcnMgfD0gTU9EX01BU0tfQ1RSTDsKKyAgICBpZiAobWFjTW9kaWZpZXJzICYgKG9wdGlvbktleSB8IHJpZ2h0T3B0aW9uS2V5KSkKKwl2aW1Nb2RpZmllcnMgfD0gTU9EX01BU0tfQUxUOworI2lmZGVmIFVTRV9DTURfS0VZCisgICAgaWYgKG1hY01vZGlmaWVycyAmIChjbWRLZXkpKSAvKiBUaGVyZSdzIG5vIHJpZ2h0Q21kS2V5ICovCisJdmltTW9kaWZpZXJzIHw9IE1PRF9NQVNLX0NNRDsKKyNlbmRpZgorICAgIHJldHVybiAodmltTW9kaWZpZXJzKTsKK30KKworLyogQ29udmVydCBhIHN0cmluZyByZXByZXNlbnRpbmcgYSBwb2ludCBzaXplIGludG8gcGl4ZWxzLiBUaGUgc3RyaW5nIHNob3VsZAorICogYmUgYSBwb3NpdGl2ZSBkZWNpbWFsIG51bWJlciwgd2l0aCBhbiBvcHRpb25hbCBkZWNpbWFsIHBvaW50IChlZywgIjEyIiwgb3IKKyAqICIxMC41IikuIFRoZSBwaXhlbCB2YWx1ZSBpcyByZXR1cm5lZCwgYW5kIGEgcG9pbnRlciB0byB0aGUgbmV4dCB1bmNvbnZlcnRlZAorICogY2hhcmFjdGVyIGlzIHN0b3JlZCBpbiAqZW5kLiBUaGUgZmxhZyAidmVydGljYWwiIHNheXMgd2hldGhlciB0aGlzCisgKiBjYWxjdWxhdGlvbiBpcyBmb3IgYSB2ZXJ0aWNhbCAoaGVpZ2h0KSBzaXplIG9yIGEgaG9yaXpvbnRhbCAod2lkdGgpIG9uZS4KKyAqCisgKiBGcm9tIGd1aV93NDguYworICovCisgICAgc3RhdGljIGludAorcG9pbnRzX3RvX3BpeGVscyhjaGFyX3UgKnN0ciwgY2hhcl91ICoqZW5kLCBpbnQgdmVydGljYWwpCit7CisgICAgaW50CQlwaXhlbHM7CisgICAgaW50CQlwb2ludHMgPSAwOworICAgIGludAkJZGl2aXNvciA9IDA7CisKKyAgICB3aGlsZSAoKnN0cikKKyAgICB7CisJaWYgKCpzdHIgPT0gJy4nICYmIGRpdmlzb3IgPT0gMCkKKwl7CisJICAgIC8qIFN0YXJ0IGtlZXBpbmcgYSBkaXZpc29yLCBmb3IgbGF0ZXIgKi8KKwkgICAgZGl2aXNvciA9IDE7CisJICAgIGNvbnRpbnVlOworCX0KKworCWlmICghaXNkaWdpdCgqc3RyKSkKKwkgICAgYnJlYWs7CisKKwlwb2ludHMgKj0gMTA7CisJcG9pbnRzICs9ICpzdHIgLSAnMCc7CisJZGl2aXNvciAqPSAxMDsKKworCSsrc3RyOworICAgIH0KKworICAgIGlmIChkaXZpc29yID09IDApCisJZGl2aXNvciA9IDE7CisKKyAgICBwaXhlbHMgPSBwb2ludHMvZGl2aXNvcjsKKyAgICAqZW5kID0gc3RyOworICAgIHJldHVybiBwaXhlbHM7Cit9CisKKy8qCisgKiBDb252ZXJ0IGEgbGlzdCBvZiBGU1NwZWMgYWxpYXNlcyBpbnRvIGEgbGlzdCBvZiBmdWxscGF0aG5hbWUKKyAqIGNoYXJhY3RlciBzdHJpbmdzLgorICovCisKK2NoYXJfdSAqKm5ld19mbmFtZXNfZnJvbV9BRURlc2MoQUVEZXNjICp0aGVMaXN0LCBsb25nICpudW1GaWxlcywgT1NFcnIgKmVycm9yKQoreworICAgIGNoYXJfdQkqKmZuYW1lcyA9IE5VTEw7CisgICAgT1NFcnIJbmV3RXJyb3I7CisgICAgbG9uZwlmaWxlQ291bnQ7CisgICAgRlNTcGVjCWZpbGVUb09wZW47CisgICAgbG9uZwlhY3R1YWxTaXplOworICAgIEFFS2V5d29yZAlkdW1teUtleXdvcmQ7CisgICAgRGVzY1R5cGUJZHVtbXlUeXBlOworCisgICAgLyogR2V0IG51bWJlciBvZiBmaWxlcyBpbiBsaXN0ICovCisgICAgKmVycm9yID0gQUVDb3VudEl0ZW1zKHRoZUxpc3QsIG51bUZpbGVzKTsKKyAgICBpZiAoKmVycm9yKQorICAgIHsKKyNpZmRlZiBVU0VfU0lPVVgKKwlwcmludGYgKCJmbmFtZV9mcm9tX0FFRGVzYzogQUVDb3VudEl0ZW1zIGVycm9yOiAlZFxuIiwgZXJyb3IpOworI2VuZGlmCisJcmV0dXJuKGZuYW1lcyk7CisgICAgfQorCisgICAgLyogQWxsb2NhdGUgdGhlIHBvaW50ZXIgbGlzdCAqLworICAgIGZuYW1lcyA9IChjaGFyX3UgKiopIGFsbG9jKCpudW1GaWxlcyAqIHNpemVvZihjaGFyX3UgKikpOworCisgICAgLyogRW1wdHkgb3V0IHRoZSBsaXN0ICovCisgICAgZm9yIChmaWxlQ291bnQgPSAwOyBmaWxlQ291bnQgPCAqbnVtRmlsZXM7IGZpbGVDb3VudCsrKQorCWZuYW1lc1tmaWxlQ291bnRdID0gTlVMTDsKKworICAgIC8qIFNjYW4gdGhlIGxpc3Qgb2YgRlNTcGVjICovCisgICAgZm9yIChmaWxlQ291bnQgPSAxOyBmaWxlQ291bnQgPD0gKm51bUZpbGVzOyBmaWxlQ291bnQrKykKKyAgICB7CisJLyogR2V0IHRoZSBhbGlhcyBmb3IgdGhlIG50aCBmaWxlLCBjb252ZXJ0IHRvIGFuIEZTU3BlYyAqLworCW5ld0Vycm9yID0gQUVHZXROdGhQdHIodGhlTGlzdCwgZmlsZUNvdW50LCB0eXBlRlNTLAorCQkJCSZkdW1teUtleXdvcmQsICZkdW1teVR5cGUsCisJCQkJKFB0cikgJmZpbGVUb09wZW4sIHNpemVvZihGU1NwZWMpLCAmYWN0dWFsU2l6ZSk7CisJaWYgKG5ld0Vycm9yKQorCXsKKwkgICAgLyogQ2FsbGVyIGlzIGFibGUgdG8gY2xlYW4gdXAgKi8KKwkgICAgLyogVE9ETzogU2hvdWxkIGJlIGNsZWFuIHVwIG9yIG5vdD8gRm9yIHNhZmV0eS4gKi8KKyNpZmRlZiBVU0VfU0lPVVgKKwkgICAgcHJpbnRmICgiYWV2dF9vZG9jOiBBRUdldE50aFB0ciBlcnJvcjogJWRcbiIsIG5ld0Vycm9yKTsKKyNlbmRpZgorCSAgICByZXR1cm4oZm5hbWVzKTsKKwl9CisKKwkvKiBDb252ZXJ0IHRoZSBGU1NwZWMgdG8gYSBwYXRobmFtZSAqLworCWZuYW1lc1tmaWxlQ291bnQgLSAxXSA9IEZ1bGxQYXRoRnJvbUZTU3BlY19zYXZlIChmaWxlVG9PcGVuKTsKKyAgICB9CisKKyAgICByZXR1cm4gKGZuYW1lcyk7Cit9CisKKy8qCisgKiAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KKyAqIENvZGVXYXJyaW9yIEV4dGVybmFsIEVkaXRvciBTdXBwb3J0CisgKiAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KKyAqLworI2lmZGVmIEZFQVRfQ1dfRURJVE9SCisKKy8qCisgKiBIYW5kbGUgdGhlIFdpbmRvdyBTZWFyY2ggZXZlbnQgZnJvbSBDb2RlV2FycmlvcgorICoKKyAqIERlc2NyaXB0aW9uCisgKiAtLS0tLS0tLS0tLQorICoKKyAqIFRoZSBJREUgc2VuZHMgdGhlIFdpbmRvdyBTZWFyY2ggQXBwbGVFdmVudCB0byB0aGUgZWRpdG9yIHdoZW4gaXQKKyAqIG5lZWRzIHRvIGtub3cgd2hldGhlciBhIHBhcnRpY3VsYXIgZmlsZSBpcyBvcGVuIGluIHRoZSBlZGl0b3IuCisgKgorICogRXZlbnQgUmVwbHkKKyAqIC0tLS0tLS0tLS0tCisgKgorICogTm9uZS4gUHV0IGRhdGEgaW4gdGhlIGxvY2F0aW9uIHNwZWNpZmllZCBpbiB0aGUgc3RydWN0dXJlIHJlY2VpdmVkLgorICoKKyAqIFJlbWFya3MKKyAqIC0tLS0tLS0KKyAqCisgKiBXaGVuIHRoZSBlZGl0b3IgcmVjZWl2ZXMgdGhpcyBldmVudCwgZGV0ZXJtaW5lIHdoZXRoZXIgdGhlIHNwZWNpZmllZAorICogZmlsZSBpcyBvcGVuLiBJZiBpdCBpcywgcmV0dXJuIHRoZSBtb2RpZmljYXRpb24gZGF0ZS90aW1lIGZvciB0aGF0IGZpbGUKKyAqIGluIHRoZSBhcHByb3ByaWF0ZSBsb2NhdGlvbiBzcGVjaWZpZWQgaW4gdGhlIHN0cnVjdHVyZS4gSWYgdGhlIGZpbGUgaXMKKyAqIG5vdCBvcGVuZWQsIHB1dCB0aGUgdmFsdWUgZm5mRXJyIChmaWxlIG5vdCBmb3VuZCkgaW4gdGhhdCBsb2NhdGlvbi4KKyAqCisgKi8KKworI2lmIGRlZmluZWQoX19NV0VSS1NfXykgIC8qIG9ubHkgaW4gQ29kZXdhcnJpb3IgKi8KKyMgcHJhZ21hIG9wdGlvbnMgYWxpZ249bWFjNjhrCisjZW5kaWYKK3R5cGVkZWYgc3RydWN0IFdpbmRvd1NlYXJjaCBXaW5kb3dTZWFyY2g7CitzdHJ1Y3QgV2luZG93U2VhcmNoIC8qIGZvciBoYW5kbGluZyBjbGFzcyAnS0FITCcsIGV2ZW50ICdTUkNIJywga2V5RGlyZWN0T2JqZWN0IHR5cGVDaGFyKi8KK3sKKyAgICBGU1NwZWMgdGhlRmlsZTsgLy8gaWRlbnRpZmllcyB0aGUgZmlsZQorICAgIGxvbmcgKnRoZURhdGU7IC8vIHdoZXJlIHRvIHB1dCB0aGUgbW9kaWZpY2F0aW9uIGRhdGUvdGltZQorfTsKKyNpZiBkZWZpbmVkKF9fTVdFUktTX18pICAvKiBvbmx5IGluIENvZGV3YXJyaW9yICovCisjIHByYWdtYSBvcHRpb25zIGFsaWduPXJlc2V0CisjZW5kaWYKKworcGFzY2FsIE9TRXJyIEhhbmRsZV9LQUhMX1NSQ0hfQUUgKGNvbnN0IEFwcGxlRXZlbnQgKnRoZUFFdmVudCwgQXBwbGVFdmVudCAqdGhlUmVwbHksIGxvbmcgcmVmQ29uKQoreworICAgIE9TRXJyCWVycm9yID0gbm9FcnI7CisgICAgYnVmX1QJKmJ1ZjsKKyAgICBpbnQJCWZvdW5kRmlsZSA9IGZhbHNlOworICAgIERlc2NUeXBlCXR5cGVDb2RlOworICAgIFdpbmRvd1NlYXJjaCBTZWFyY2hEYXRhOworICAgIFNpemUJYWN0dWFsU2l6ZTsKKworICAgIGVycm9yID0gQUVHZXRQYXJhbVB0cih0aGVBRXZlbnQsIGtleURpcmVjdE9iamVjdCwgdHlwZUNoYXIsICZ0eXBlQ29kZSwgKFB0cikgJlNlYXJjaERhdGEsIHNpemVvZihXaW5kb3dTZWFyY2gpLCAmYWN0dWFsU2l6ZSk7CisgICAgaWYgKGVycm9yKQorICAgIHsKKyNpZmRlZiBVU0VfU0lPVVgKKwlwcmludGYgKCJLQUhMX1NSQ0g6IEFFR2V0UGFyYW1QdHIgZXJyb3I6ICVkXG4iLCBlcnJvcik7CisjZW5kaWYKKwlyZXR1cm4oZXJyb3IpOworICAgIH0KKworICAgIGVycm9yID0gSGFuZGxlVW51c2VkUGFybXMgKHRoZUFFdmVudCk7CisgICAgaWYgKGVycm9yKQorICAgIHsKKyNpZmRlZiBVU0VfU0lPVVgKKwlwcmludGYgKCJLQUhMX1NSQ0g6IEhhbmRsZVVudXNlZFBhcm1zIGVycm9yOiAlZFxuIiwgZXJyb3IpOworI2VuZGlmCisJcmV0dXJuKGVycm9yKTsKKyAgICB9CisKKyAgICBmb3IgKGJ1ZiA9IGZpcnN0YnVmOyBidWYgIT0gTlVMTDsgYnVmID0gYnVmLT5iX25leHQpCisJaWYgKGJ1Zi0+Yl9tbC5tbF9tZnAgIT0gTlVMTAorCQkmJiBTZWFyY2hEYXRhLnRoZUZpbGUucGFySUQgPT0gYnVmLT5iX0ZTU3BlYy5wYXJJRAorCQkmJiBTZWFyY2hEYXRhLnRoZUZpbGUubmFtZVswXSA9PSBidWYtPmJfRlNTcGVjLm5hbWVbMF0KKwkJJiYgU1RSTkNNUChTZWFyY2hEYXRhLnRoZUZpbGUubmFtZSwgYnVmLT5iX0ZTU3BlYy5uYW1lLCBidWYtPmJfRlNTcGVjLm5hbWVbMF0gKyAxKSA9PSAwKQorCSAgICB7CisJCWZvdW5kRmlsZSA9IHRydWU7CisJCWJyZWFrOworCSAgICB9CisKKyAgICBpZiAoZm91bmRGaWxlID09IGZhbHNlKQorCSpTZWFyY2hEYXRhLnRoZURhdGUgPSBmbmZFcnI7CisgICAgZWxzZQorCSpTZWFyY2hEYXRhLnRoZURhdGUgPSBidWYtPmJfbXRpbWU7CisKKyNpZmRlZiBVU0VfU0lPVVgKKyAgICBwcmludGYgKCJLQUhMX1NSQ0g6IGZpbGUgXCIlI3NcIiB7JWR9IiwgU2VhcmNoRGF0YS50aGVGaWxlLm5hbWUsU2VhcmNoRGF0YS50aGVGaWxlLnBhcklEKTsKKyAgICBpZiAoZm91bmRGaWxlID09IGZhbHNlKQorCXByaW50ZiAoIiBOT1QiKTsKKyAgICBwcmludGYgKCIgZm91bmQuIFtkYXRlICVseCwgJWx4XVxuIiwgKlNlYXJjaERhdGEudGhlRGF0ZSwgYnVmLT5iX210aW1lX3JlYWQpOworI2VuZGlmCisKKyAgICByZXR1cm4gZXJyb3I7Cit9OworCisvKgorICogSGFuZGxlIHRoZSBNb2RpZmllZCAoZnJvbSBJREUgdG8gRWRpdG9yKSBldmVudCBmcm9tIENvZGVXYXJyaW9yCisgKgorICogRGVzY3JpcHRpb24KKyAqIC0tLS0tLS0tLS0tCisgKgorICogVGhlIElERSBzZW5kcyB0aGlzIGV2ZW50IHRvIHRoZSBleHRlcm5hbCBlZGl0b3Igd2hlbiBpdCB3YW50cyB0bworICoga25vdyB3aGljaCBmaWxlcyB0aGF0IGFyZSBvcGVuIGluIHRoZSBlZGl0b3IgaGF2ZSBiZWVuIG1vZGlmaWVkLgorICoKKyAqIFBhcmFtZXRlcnMgICBOb25lLgorICogLS0tLS0tLS0tLQorICoKKyAqIEV2ZW50IFJlcGx5CisgKiAtLS0tLS0tLS0tLQorICogVGhlIHJlcGx5IGZvciB0aGlzIGV2ZW50IGlzOgorICoKKyAqIGtleURpcmVjdE9iamVjdCB0eXBlQUVMaXN0IHJlcXVpcmVkCisgKiAgZWFjaCBlbGVtZW50IGluIHRoZSBsaXN0IGlzIGEgc3RydWN0dXJlIG9mIHR5cGVDaGFyCisgKgorICogUmVtYXJrcworICogLS0tLS0tLQorICoKKyAqIFdoZW4gYnVpbGRpbmcgdGhlIHJlcGx5IGV2ZW50LCBpbmNsdWRlIG9uZSBlbGVtZW50IGluIHRoZSBsaXN0IGZvcgorICogZWFjaCBvcGVuIGZpbGUgdGhhdCBoYXMgYmVlbiBtb2RpZmllZC4KKyAqCisgKi8KKworI2lmIGRlZmluZWQoX19NV0VSS1NfXykgIC8qIG9ubHkgaW4gQ29kZXdhcnJpb3IgKi8KKyMgcHJhZ21hIG9wdGlvbnMgYWxpZ249bWFjNjhrCisjZW5kaWYKK3R5cGVkZWYgc3RydWN0IE1vZGlmaWNhdGlvbkluZm8gTW9kaWZpY2F0aW9uSW5mbzsKK3N0cnVjdCBNb2RpZmljYXRpb25JbmZvIC8qIGZvciByZXBseWluZyB0byBjbGFzcyAnS0FITCcsIGV2ZW50ICdNT0QgJywga2V5RGlyZWN0T2JqZWN0IHR5cGVBRUxpc3QqLworeworICAgIEZTU3BlYyB0aGVGaWxlOyAvLyBpZGVudGlmaWVzIHRoZSBmaWxlCisgICAgbG9uZyB0aGVEYXRlOyAvLyB0aGUgZGF0ZS90aW1lIHRoZSBmaWxlIHdhcyBsYXN0IG1vZGlmaWVkCisgICAgc2hvcnQgc2F2ZWQ7IC8vIHNldCB0aGlzIHRvIHplcm8gd2hlbiByZXBseWluZywgdW51c2VkCit9OworI2lmIGRlZmluZWQoX19NV0VSS1NfXykgIC8qIG9ubHkgaW4gQ29kZXdhcnJpb3IgKi8KKyMgcHJhZ21hIG9wdGlvbnMgYWxpZ249cmVzZXQKKyNlbmRpZgorCitwYXNjYWwgT1NFcnIgSGFuZGxlX0tBSExfTU9EX0FFIChjb25zdCBBcHBsZUV2ZW50ICp0aGVBRXZlbnQsIEFwcGxlRXZlbnQgKnRoZVJlcGx5LCBsb25nIHJlZkNvbikKK3sKKyAgICBPU0VycgllcnJvciA9IG5vRXJyOworICAgIEFFRGVzY0xpc3QJcmVwbHlMaXN0OworICAgIGxvbmcJbnVtRmlsZXM7CisgICAgTW9kaWZpY2F0aW9uSW5mbyB0aGVGaWxlOworICAgIGJ1Zl9UCSpidWY7CisKKyAgICB0aGVGaWxlLnNhdmVkID0gMDsKKworICAgIGVycm9yID0gSGFuZGxlVW51c2VkUGFybXMgKHRoZUFFdmVudCk7CisgICAgaWYgKGVycm9yKQorICAgIHsKKyNpZmRlZiBVU0VfU0lPVVgKKwlwcmludGYgKCJLQUhMX01PRDogSGFuZGxlVW51c2VkUGFybXMgZXJyb3I6ICVkXG4iLCBlcnJvcik7CisjZW5kaWYKKwlyZXR1cm4oZXJyb3IpOworICAgIH0KKworICAgIC8qIFNlbmQgdGhlIHJlcGx5ICovCisvKiAgcmVwbHlPYmplY3QuZGVzY3JpcHRvclR5cGUgPSB0eXBlTnVsbDsKKyAgICByZXBseU9iamVjdC5kYXRhSGFuZGxlICAgICA9IG5pbDsqLworCisvKiBBRUNyZWF0ZURlc2ModHlwZUNoYXIsIChQdHIpJnRpdGxlWzFdLCB0aXRsZVswXSwgJmRhdGEpICovCisgICAgZXJyb3IgPSBBRUNyZWF0ZUxpc3QobmlsLCAwLCBmYWxzZSwgJnJlcGx5TGlzdCk7CisgICAgaWYgKGVycm9yKQorICAgIHsKKyNpZmRlZiBVU0VfU0lPVVgKKwlwcmludGYgKCJLQUhMX01PRDogQUVDcmVhdGVMaXN0IGVycm9yOiAlZFxuIiwgZXJyb3IpOworI2VuZGlmCisJcmV0dXJuKGVycm9yKTsKKyAgICB9CisKKyNpZiAwCisgICAgZXJyb3IgPSBBRUNvdW50SXRlbXMoJnJlcGx5TGlzdCwgJm51bUZpbGVzKTsKKyNpZmRlZiBVU0VfU0lPVVgKKyAgICBwcmludGYgKCJLQUhMX01PRCBSZXBseUxpc3Q6ICV4ICV4XG4iLCByZXBseUxpc3QuZGVzY3JpcHRvclR5cGUsIHJlcGx5TGlzdC5kYXRhSGFuZGxlKTsKKyAgICBwcmludGYgKCJLQUhMX01PRCBJdGVtSW5MaXN0OiAlZFxuIiwgbnVtRmlsZXMpOworI2VuZGlmCisKKyAgICAvKiBBRVB1dEtleURlc2MgKCZyZXBseUxpc3QsIGtleUFFUG5qZWN0LCAmYURlc2MpCisgICAgICogQUVQdXRLZXlQdHIgICgmcmVwbHlMaXN0LCBrZXlBRVBvc2l0aW9uLCB0eXBlQ2hhciwgKFB0cikmdGhlVHlwZSwKKyAgICAgKiBzaXplb2YoRGVzY1R5cGUpKQorICAgICAqLworCisgICAgLyogQUVQdXREZXNjICovCisjZW5kaWYKKworICAgIG51bUZpbGVzID0gMDsKKyAgICBmb3IgKGJ1ZiA9IGZpcnN0YnVmOyBidWYgIT0gTlVMTDsgYnVmID0gYnVmLT5iX25leHQpCisJaWYgKGJ1Zi0+Yl9tbC5tbF9tZnAgIT0gTlVMTCkKKwl7CisJICAgIC8qIEFkZCB0aGlzIGZpbGUgdG8gdGhlIGxpc3QgKi8KKwkgICAgdGhlRmlsZS50aGVGaWxlID0gYnVmLT5iX0ZTU3BlYzsKKwkgICAgdGhlRmlsZS50aGVEYXRlID0gYnVmLT5iX210aW1lOworLyoJICAgIHRoZUZpbGUudGhlRGF0ZSA9IHRpbWUgKE5VTEwpICYgKHRpbWVfdCkgMHhGRkZGRkZGMDsgKi8KKwkgICAgZXJyb3IgPSBBRVB1dFB0ciAoJnJlcGx5TGlzdCwgbnVtRmlsZXMsIHR5cGVDaGFyLCAoUHRyKSAmdGhlRmlsZSwgc2l6ZW9mKHRoZUZpbGUpKTsKKyNpZmRlZiBVU0VfU0lPVVgKKwkgICAgaWYgKG51bUZpbGVzID09IDApCisJCXByaW50ZiAoIktBSExfTU9EOiAiKTsKKwkgICAgZWxzZQorCQlwcmludGYgKCIsICIpOworCSAgICBwcmludGYgKCJcIiUjc1wiIHslZH0gW2RhdGUgJWx4LCAlbHhdIiwgdGhlRmlsZS50aGVGaWxlLm5hbWUsIHRoZUZpbGUudGhlRmlsZS5wYXJJRCwgdGhlRmlsZS50aGVEYXRlLCBidWYtPmJfbXRpbWVfcmVhZCk7CisJICAgIGlmIChlcnJvcikKKwkJcHJpbnRmICgiICglZCkiLCBlcnJvcik7CisJICAgIG51bUZpbGVzKys7CisjZW5kaWYKKwl9OworCisjaWZkZWYgVVNFX1NJT1VYCisgICAgcHJpbnRmICgiXG4iKTsKKyNlbmRpZgorCisjaWYgMAorICAgIGVycm9yID0gQUVDb3VudEl0ZW1zKCZyZXBseUxpc3QsICZudW1GaWxlcyk7CisjaWZkZWYgVVNFX1NJT1VYCisgICAgcHJpbnRmICgiS0FITF9NT0QgSXRlbUluTGlzdDogJWRcbiIsIG51bUZpbGVzKTsKKyNlbmRpZgorI2VuZGlmCisKKyAgICAvKiBXZSBjYW4gYWRkIGRhdGEgb25seSBpZiBzb21ldGhpbmcgdG8gcmVwbHkgKi8KKyAgICBlcnJvciA9IEFFUHV0UGFyYW1EZXNjICh0aGVSZXBseSwga2V5RGlyZWN0T2JqZWN0LCAmcmVwbHlMaXN0KTsKKworI2lmZGVmIFVTRV9TSU9VWAorICAgIGlmIChlcnJvcikKKwlwcmludGYgKCJLQUhMX01PRDogQUVQdXRQYXJhbURlc2MgZXJyb3I6ICVkXG4iLCBlcnJvcik7CisjZW5kaWYKKworICAgIGlmIChyZXBseUxpc3QuZGF0YUhhbmRsZSkKKwlBRURpc3Bvc2VEZXNjKCZyZXBseUxpc3QpOworCisgICAgcmV0dXJuIGVycm9yOworfTsKKworLyoKKyAqIEhhbmRsZSB0aGUgR2V0IFRleHQgZXZlbnQgZnJvbSBDb2RlV2FycmlvcgorICoKKyAqIERlc2NyaXB0aW9uCisgKiAtLS0tLS0tLS0tLQorICoKKyAqIFRoZSBJREUgc2VuZHMgdGhlIEdldCBUZXh0IEFwcGxlRXZlbnQgdG8gdGhlIGVkaXRvciB3aGVuIGl0IG5lZWRzCisgKiB0aGUgc291cmNlIGNvZGUgZnJvbSBhIGZpbGUuIEZvciBleGFtcGxlLCB3aGVuIHRoZSB1c2VyIGlzc3VlcyBhCisgKiBDaGVjayBTeW50YXggb3IgQ29tcGlsZSBjb21tYW5kLCB0aGUgY29tcGlsZXIgbmVlZHMgYWNjZXNzIHRvCisgKiB0aGUgc291cmNlIGNvZGUgY29udGFpbmVkIGluIHRoZSBmaWxlLgorICoKKyAqIEV2ZW50IFJlcGx5CisgKiAtLS0tLS0tLS0tLQorICoKKyAqIE5vbmUuIFB1dCBkYXRhIGluIGxvY2F0aW9ucyBzcGVjaWZpZWQgaW4gdGhlIHN0cnVjdHVyZSByZWNlaXZlZC4KKyAqCisgKiBSZW1hcmtzCisgKiAtLS0tLS0tCisgKgorICogV2hlbiB0aGUgZWRpdG9yIHJlY2VpdmVzIHRoaXMgZXZlbnQsIGl0IG11c3Qgc2V0IHRoZSBzaXplIG9mIHRoZSBoYW5kbGUKKyAqIGluIHRoZVRleHQgdG8gZml0IHRoZSBkYXRhIGluIHRoZSBmaWxlLiBJdCBtdXN0IHRoZW4gY29weSB0aGUgZW50aXJlCisgKiBjb250ZW50cyBvZiB0aGUgc3BlY2lmaWVkIGZpbGUgaW50byB0aGUgbWVtb3J5IGxvY2F0aW9uIHNwZWNpZmllZCBpbgorICogdGhlVGV4dC4KKyAqCisgKi8KKworI2lmIGRlZmluZWQoX19NV0VSS1NfXykgIC8qIG9ubHkgaW4gQ29kZXdhcnJpb3IgKi8KKyMgcHJhZ21hIG9wdGlvbnMgYWxpZ249bWFjNjhrCisjZW5kaWYKK3R5cGVkZWYgc3RydWN0IENXX0dldFRleHQgQ1dfR2V0VGV4dDsKK3N0cnVjdCBDV19HZXRUZXh0IC8qIGZvciBoYW5kbGluZyBjbGFzcyAnS0FITCcsIGV2ZW50ICdHVFRYJywga2V5RGlyZWN0T2JqZWN0IHR5cGVDaGFyKi8KK3sKKyAgICBGU1NwZWMgdGhlRmlsZTsgLyogaWRlbnRpZmllcyB0aGUgZmlsZSAqLworICAgIEhhbmRsZSB0aGVUZXh0OyAvKiB0aGUgbG9jYXRpb24gd2hlcmUgeW91IHJldHVybiB0aGUgdGV4dCAobXVzdCBiZSByZXNpemVkIHByb3Blcmx5KSAqLworICAgIGxvbmcgKnVudXNlZDsgICAvKiAwIChub3QgdXNlZCkgKi8KKyAgICBsb25nICp0aGVEYXRlOyAgLyogd2hlcmUgdG8gcHV0IHRoZSBtb2RpZmljYXRpb24gZGF0ZS90aW1lICovCit9OworI2lmIGRlZmluZWQoX19NV0VSS1NfXykgIC8qIG9ubHkgaW4gQ29kZXdhcnJpb3IgKi8KKyMgcHJhZ21hIG9wdGlvbnMgYWxpZ249cmVzZXQKKyNlbmRpZgorCitwYXNjYWwgT1NFcnIgSGFuZGxlX0tBSExfR1RUWF9BRSAoY29uc3QgQXBwbGVFdmVudCAqdGhlQUV2ZW50LCBBcHBsZUV2ZW50ICp0aGVSZXBseSwgbG9uZyByZWZDb24pCit7CisgICAgT1NFcnIJZXJyb3IgPSBub0VycjsKKyAgICBidWZfVAkqYnVmOworICAgIGludAkJZm91bmRGaWxlID0gZmFsc2U7CisgICAgRGVzY1R5cGUJdHlwZUNvZGU7CisgICAgQ1dfR2V0VGV4dAlHZXRUZXh0RGF0YTsKKyAgICBTaXplCWFjdHVhbFNpemU7CisgICAgY2hhcl91CSpsaW5lOworICAgIGNoYXJfdQkqZnVsbGJ1ZmZlciA9IE5VTEw7CisgICAgbG9uZwlsaW5lc2l6ZTsKKyAgICBsb25nCWxpbmVTdGFydDsKKyAgICBsb25nCUJ1ZmZlclNpemU7CisgICAgbG9uZwlsaW5lbm87CisKKyAgICBlcnJvciA9IEFFR2V0UGFyYW1QdHIodGhlQUV2ZW50LCBrZXlEaXJlY3RPYmplY3QsIHR5cGVDaGFyLCAmdHlwZUNvZGUsIChQdHIpICZHZXRUZXh0RGF0YSwgc2l6ZW9mKEdldFRleHREYXRhKSwgJmFjdHVhbFNpemUpOworCisgICAgaWYgKGVycm9yKQorICAgIHsKKyNpZmRlZiBVU0VfU0lPVVgKKwlwcmludGYgKCJLQUhMX0dUVFg6IEFFR2V0UGFyYW1QdHIgZXJyb3I6ICVkXG4iLCBlcnJvcik7CisjZW5kaWYKKwlyZXR1cm4oZXJyb3IpOworICAgIH0KKworICAgIGZvciAoYnVmID0gZmlyc3RidWY7IGJ1ZiAhPSBOVUxMOyBidWYgPSBidWYtPmJfbmV4dCkKKwlpZiAoYnVmLT5iX21sLm1sX21mcCAhPSBOVUxMKQorCSAgICBpZiAoR2V0VGV4dERhdGEudGhlRmlsZS5wYXJJRCA9PSBidWYtPmJfRlNTcGVjLnBhcklEKQorCSAgICB7CisJCWZvdW5kRmlsZSA9IHRydWU7CisJCWJyZWFrOworCSAgICB9CisKKyAgICBpZiAoZm91bmRGaWxlKQorICAgIHsKKwlCdWZmZXJTaXplID0gMDsgLyogR2V0SGFuZGxlU2l6ZSAoR2V0VGV4dERhdGEudGhlVGV4dCk7ICovCisJZm9yIChsaW5lbm8gPSAwOyBsaW5lbm8gPD0gYnVmLT5iX21sLm1sX2xpbmVfY291bnQ7IGxpbmVubysrKQorCXsKKwkgICAgLyogTXVzdCB1c2UgdGhlIHJpZ2h0IGJ1ZmZlciAqLworCSAgICBsaW5lID0gbWxfZ2V0X2J1ZihidWYsIChsaW5lbnJfVCkgbGluZW5vLCBGQUxTRSk7CisJICAgIGxpbmVzaXplID0gU1RSTEVOKGxpbmUpICsgMTsKKwkgICAgbGluZVN0YXJ0ID0gQnVmZmVyU2l6ZTsKKwkgICAgQnVmZmVyU2l6ZSArPSBsaW5lc2l6ZTsKKwkgICAgLyogUmVzaXplIGhhbmRsZSB0byBsaW5lc2l6ZSsxIHRvIGluY2x1ZGUgdGhlIGxpbmVmZWVkICovCisJICAgIFNldEhhbmRsZVNpemUgKEdldFRleHREYXRhLnRoZVRleHQsIEJ1ZmZlclNpemUpOworCSAgICBpZiAoR2V0SGFuZGxlU2l6ZSAoR2V0VGV4dERhdGEudGhlVGV4dCkgIT0gQnVmZmVyU2l6ZSkKKwkgICAgeworCSNpZmRlZiBVU0VfU0lPVVgKKwkJcHJpbnRmICgiS0FITF9HVFRYOiBTZXRIYW5kbGVTaXplIGluY3JlYXNlOiAlZCwgc2l6ZSAlZFxuIiwKKwkJCWxpbmVzaXplLCBCdWZmZXJTaXplKTsKKwkjZW5kaWYKKwkJYnJlYWs7IC8qIFNpbXBsZSBoYW5kbGluZyBmb3Igbm93ICovCisJICAgIH0KKwkgICAgZWxzZQorCSAgICB7CisJCUhMb2NrIChHZXRUZXh0RGF0YS50aGVUZXh0KTsKKwkJZnVsbGJ1ZmZlciA9IChjaGFyX3UgKikgKkdldFRleHREYXRhLnRoZVRleHQ7CisJCVNUUkNQWSAoKGNoYXJfdSAqKSAoZnVsbGJ1ZmZlciArIGxpbmVTdGFydCksIGxpbmUpOworCQlmdWxsYnVmZmVyW0J1ZmZlclNpemUtMV0gPSAnXHInOworCQlIVW5sb2NrIChHZXRUZXh0RGF0YS50aGVUZXh0KTsKKwkgICAgfQorCX0KKwlpZiAoZnVsbGJ1ZmZlciAhPSBOVUxMKQorCXsKKwkgICAgSExvY2sgKEdldFRleHREYXRhLnRoZVRleHQpOworCSAgICBmdWxsYnVmZmVyW0J1ZmZlclNpemUtMV0gPSAwOworCSAgICBIVW5sb2NrIChHZXRUZXh0RGF0YS50aGVUZXh0KTsKKwl9CisJaWYgKGZvdW5kRmlsZSA9PSBmYWxzZSkKKwkgICAgKkdldFRleHREYXRhLnRoZURhdGUgPSBmbmZFcnI7CisJZWxzZQorLyoJICAgICpHZXRUZXh0RGF0YS50aGVEYXRlID0gdGltZSAoTlVMTCkgJiAodGltZV90KSAweEZGRkZGRkYwOyovCisJICAgICpHZXRUZXh0RGF0YS50aGVEYXRlID0gYnVmLT5iX210aW1lOworICAgIH0KKyNpZmRlZiBVU0VfU0lPVVgKKyAgICBwcmludGYgKCJLQUhMX0dUVFg6IGZpbGUgXCIlI3NcIiB7JWR9IFtkYXRlICVseCwgJWx4XSIsIEdldFRleHREYXRhLnRoZUZpbGUubmFtZSwgR2V0VGV4dERhdGEudGhlRmlsZS5wYXJJRCwgKkdldFRleHREYXRhLnRoZURhdGUsIGJ1Zi0+Yl9tdGltZV9yZWFkKTsKKyAgICBpZiAoZm91bmRGaWxlID09IGZhbHNlKQorCXByaW50ZiAoIiBOT1QiKTsKKyAgICBwcmludGYgKCIgZm91bmQuIChCdWZmZXJTaXplID0gJWQpXG4iLCBCdWZmZXJTaXplKTsKKyNlbmRpZgorCisgICAgZXJyb3IgPSBIYW5kbGVVbnVzZWRQYXJtcyAodGhlQUV2ZW50KTsKKyAgICBpZiAoZXJyb3IpCisgICAgeworI2lmZGVmIFVTRV9TSU9VWAorCXByaW50ZiAoIktBSExfR1RUWDogSGFuZGxlVW51c2VkUGFybXMgZXJyb3I6ICVkXG4iLCBlcnJvcik7CisjZW5kaWYKKwlyZXR1cm4oZXJyb3IpOworICAgIH0KKworICAgIHJldHVybihlcnJvcik7Cit9CisKKy8qCisgKgorICovCisKKy8qIFRha2VuIGZyb20gTW9yZUFwcGxlRXZlbnRzOlByb2Nlc3NIZWxwZXJzKi8KK3Bhc2NhbAlPU0VycglGaW5kUHJvY2Vzc0J5U2lnbmF0dXJlKCBjb25zdCBPU1R5cGUgdGFyZ2V0VHlwZSwKKwkJCQkJY29uc3QgT1NUeXBlIHRhcmdldENyZWF0b3IsCisJCQkJCSAgICAgIFByb2Nlc3NTZXJpYWxOdW1iZXJQdHIgcHNuUHRyICkKK3sKKyAgICBPU0VycglhbkVyciA9IG5vRXJyOworICAgIEJvb2xlYW4JbG9va2luZ0ZvclByb2Nlc3MgPSB0cnVlOworCisgICAgUHJvY2Vzc0luZm9SZWMgIGluZm9SZWM7CisKKyAgICBpbmZvUmVjLnByb2Nlc3NJbmZvTGVuZ3RoID0gc2l6ZW9mKCBQcm9jZXNzSW5mb1JlYyApOworICAgIGluZm9SZWMucHJvY2Vzc05hbWUgPSBuaWw7CisgICAgaW5mb1JlYy5wcm9jZXNzQXBwU3BlYyA9IG5pbDsKKworICAgIHBzblB0ci0+bG93TG9uZ09mUFNOID0ga05vUHJvY2VzczsKKyAgICBwc25QdHItPmhpZ2hMb25nT2ZQU04gPSBrTm9Qcm9jZXNzOworCisgICAgd2hpbGUgKCBsb29raW5nRm9yUHJvY2VzcyApCisgICAgeworCWFuRXJyID0gR2V0TmV4dFByb2Nlc3MoIHBzblB0ciApOworCWlmICggYW5FcnIgIT0gbm9FcnIgKQorCXsKKwkgICAgbG9va2luZ0ZvclByb2Nlc3MgPSBmYWxzZTsKKwl9CisJZWxzZQorCXsKKwkgICAgYW5FcnIgPSBHZXRQcm9jZXNzSW5mb3JtYXRpb24oIHBzblB0ciwgJmluZm9SZWMgKTsKKwkgICAgaWYgKCAoIGFuRXJyID09IG5vRXJyICkKKwkJICYmICggaW5mb1JlYy5wcm9jZXNzVHlwZSA9PSB0YXJnZXRUeXBlICkKKwkJICYmICggaW5mb1JlYy5wcm9jZXNzU2lnbmF0dXJlID09IHRhcmdldENyZWF0b3IgKSApCisJICAgIHsKKwkJbG9va2luZ0ZvclByb2Nlc3MgPSBmYWxzZTsKKwkgICAgfQorCX0KKyAgICB9CisKKyAgICByZXR1cm4gYW5FcnI7Cit9Ly9lbmQgRmluZFByb2Nlc3NCeVNpZ25hdHVyZQorCit2b2lkIFNlbmRfS0FITF9NT0RfQUUgKGJ1Zl9UICpidWYpCit7CisgICAgT1NFcnIgICBhbkVyciA9IG5vRXJyOworICAgIEFFRGVzYyAgdGFyZ2V0QXBwRGVzYyA9IHsgdHlwZU51bGwsIG5pbCB9OworICAgIFByb2Nlc3NTZXJpYWxOdW1iZXIJICAgIHBzbiA9IHsga05vUHJvY2Vzcywga05vUHJvY2VzcyB9OworICAgIEFwcGxlRXZlbnQJdGhlUmVwbHkgPSB7IHR5cGVOdWxsLCBuaWwgfTsKKyAgICBBRVNlbmRNb2RlCXNlbmRNb2RlOworICAgIEFwcGxlRXZlbnQgIHRoZUV2ZW50ID0ge3R5cGVOdWxsLCBuaWwgfTsKKyAgICBBRUlkbGVVUFAgICBpZGxlUHJvY1VQUCA9IG5pbDsKKyAgICBNb2RpZmljYXRpb25JbmZvIE1vZERhdGE7CisKKworICAgIGFuRXJyID0gRmluZFByb2Nlc3NCeVNpZ25hdHVyZSggJ0FQUEwnLCAnQ1dJRScsICZwc24gKTsKKyNpZmRlZiBVU0VfU0lPVVgKKyAgICBwcmludGYgKCJDb2RlV2FycmlvciBpcyIpOworICAgIGlmIChhbkVyciAhPSBub0VycikKKwlwcmludGYgKCIgTk9UIik7CisgICAgcHJpbnRmICgiIHJ1bm5pbmdcbiIpOworI2VuZGlmCisgICAgaWYgKCBhbkVyciA9PSBub0VyciApCisgICAgeworCWFuRXJyID0gQUVDcmVhdGVEZXNjICh0eXBlUHJvY2Vzc1NlcmlhbE51bWJlciwgJnBzbiwKKwkJCSAgICAgIHNpemVvZiggUHJvY2Vzc1NlcmlhbE51bWJlciApLCAmdGFyZ2V0QXBwRGVzYyk7CisKKwlpZiAoIGFuRXJyID09IG5vRXJyICkKKwl7CisJICAgIGFuRXJyID0gQUVDcmVhdGVBcHBsZUV2ZW50KCAnS0FITCcsICdNT0QgJywgJnRhcmdldEFwcERlc2MsCisJCQkJCWtBdXRvR2VuZXJhdGVSZXR1cm5JRCwga0FueVRyYW5zYWN0aW9uSUQsICZ0aGVFdmVudCk7CisJfQorCisJQUVEaXNwb3NlRGVzYyggJnRhcmdldEFwcERlc2MgKTsKKworCS8qIEFkZCB0aGUgcGFybXMgKi8KKwlNb2REYXRhLnRoZUZpbGUgPSBidWYtPmJfRlNTcGVjOworCU1vZERhdGEudGhlRGF0ZSA9IGJ1Zi0+Yl9tdGltZTsKKworCWlmIChhbkVyciA9PSBub0VycikKKwkgICAgYW5FcnIgPUFFUHV0UGFyYW1QdHIgKCZ0aGVFdmVudCwga2V5RGlyZWN0T2JqZWN0LCB0eXBlQ2hhciwgJk1vZERhdGEsIHNpemVvZihNb2REYXRhKSk7CisKKwlpZiAoIGlkbGVQcm9jVVBQID09IG5pbCApCisJICAgIHNlbmRNb2RlID0ga0FFTm9SZXBseTsKKwllbHNlCisJICAgIHNlbmRNb2RlID0ga0FFV2FpdFJlcGx5OworCisJaWYgKCBhbkVyciA9PSBub0VyciApCisJICAgIGFuRXJyID0gQUVTZW5kKCAmdGhlRXZlbnQsICZ0aGVSZXBseSwgc2VuZE1vZGUsIGtBRU5vcm1hbFByaW9yaXR5LCBrTm9UaW1lT3V0LCBpZGxlUHJvY1VQUCwgbmlsICk7CisJaWYgKCBhbkVyciA9PSBub0VyciAgJiYgIHNlbmRNb2RlID09IGtBRVdhaXRSZXBseSApCisJeworI2lmZGVmIFVTRV9TSU9VWAorCSAgICBwcmludGYgKCJLQUhMX01PRDogU2VuZCBlcnJvcjogJWRcbiIsIGFuRXJyKTsKKyNlbmRpZgorLyoJICAgIGFuRXJyID0gIEFFSEdldEhhbmRsZXJFcnJvciggJnRoZVJlcGx5ICk7Ki8KKwl9CisJKHZvaWQpIEFFRGlzcG9zZURlc2MoICZ0aGVSZXBseSApOworICAgIH0KK30KKyNlbmRpZiAvKiBGRUFUX0NXX0VESVRPUiAqLworCisvKgorICogLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCisgKiBBcHBsZSBFdmVudCBIYW5kbGluZyBwcm9jZWR1cmUKKyAqIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQorICovCisjaWZkZWYgVVNFX0FFVkVOVAorCisvKgorICogSGFuZGxlIHRoZSBVbnVzZWQgcGFybXMgb2YgYW4gQXBwbGVFdmVudAorICovCisKK09TRXJyIEhhbmRsZVVudXNlZFBhcm1zIChjb25zdCBBcHBsZUV2ZW50ICp0aGVBRXZlbnQpCit7CisgICAgT1NFcnIJZXJyb3I7CisgICAgbG9uZwlhY3R1YWxTaXplOworICAgIERlc2NUeXBlCWR1bW15VHlwZTsKKyAgICBBRUtleXdvcmQJbWlzc2VkS2V5d29yZDsKKworICAgIC8qIEdldCB0aGUgIm1pc3NlZCBrZXl3b3JkIiBhdHRyaWJ1dGUgZnJvbSB0aGUgQXBwbGVFdmVudC4gKi8KKyAgICBlcnJvciA9IEFFR2V0QXR0cmlidXRlUHRyKHRoZUFFdmVudCwga2V5TWlzc2VkS2V5d29yZEF0dHIsCisJCQkgICAgICB0eXBlS2V5d29yZCwgJmR1bW15VHlwZSwKKwkJCSAgICAgIChQdHIpJm1pc3NlZEtleXdvcmQsIHNpemVvZihtaXNzZWRLZXl3b3JkKSwKKwkJCSAgICAgICZhY3R1YWxTaXplKTsKKworICAgIC8qIElmIHRoZSBkZXNjcmlwdG9yIGlzbid0IGZvdW5kLCB0aGVuIHdlIGdvdCB0aGUgcmVxdWlyZWQgcGFyYW1ldGVycy4gKi8KKyAgICBpZiAoZXJyb3IgPT0gZXJyQUVEZXNjTm90Rm91bmQpCisgICAgeworCWVycm9yID0gbm9FcnI7CisgICAgfQorICAgIGVsc2UKKyAgICB7CisjaWYgMAorCS8qIFdoeSBpcyB0aGlzIHJlbW92ZWQ/ICovCisJZXJyb3IgPSBlcnJBRUV2ZW50Tm90SGFuZGxlZDsKKyNlbmRpZgorICAgIH0KKworICAgIHJldHVybiBlcnJvcjsKK30KKworCisvKgorICogSGFuZGxlIHRoZSBPRG9jIEFwcGxlRXZlbnQKKyAqCisgKiBEZWFscyB3aXRoIGFsbCBmaWxlcyBkcmFnZ2VkIHRvIHRoZSBhcHBsaWNhdGlvbiBpY29uLgorICoKKyAqLworCisjaWYgZGVmaW5lZChfX01XRVJLU19fKSAgLyogb25seSBpbiBDb2Rld2FycmlvciAqLworIyBwcmFnbWEgb3B0aW9ucyBhbGlnbj1tYWM2OGsKKyNlbmRpZgordHlwZWRlZiBzdHJ1Y3QgU2VsZWN0aW9uUmFuZ2UgU2VsZWN0aW9uUmFuZ2U7CitzdHJ1Y3QgU2VsZWN0aW9uUmFuZ2UgLyogZm9yIGhhbmRsaW5nIGtDb3JlQ2xhc3NFdmVudDprT3BlbkRvY3VtZW50czprZXlBRVBvc2l0aW9uIHR5cGVDaGFyICovCit7CisgICAgc2hvcnQgdW51c2VkMTsgLy8gMCAobm90IHVzZWQpCisgICAgc2hvcnQgbGluZU51bTsgLy8gbGluZSB0byBzZWxlY3QgKDwwIHRvIHNwZWNpZnkgcmFuZ2UpCisgICAgbG9uZyBzdGFydFJhbmdlOyAvLyBzdGFydCBvZiBzZWxlY3Rpb24gcmFuZ2UgKGlmIGxpbmUgPCAwKQorICAgIGxvbmcgZW5kUmFuZ2U7IC8vIGVuZCBvZiBzZWxlY3Rpb24gcmFuZ2UgKGlmIGxpbmUgPCAwKQorICAgIGxvbmcgdW51c2VkMjsgLy8gMCAobm90IHVzZWQpCisgICAgbG9uZyB0aGVEYXRlOyAvLyBtb2RpZmljYXRpb24gZGF0ZS90aW1lCit9OworI2lmIGRlZmluZWQoX19NV0VSS1NfXykgIC8qIG9ubHkgaW4gQ29kZXdhcnJpb3IgKi8KKyMgcHJhZ21hIG9wdGlvbnMgYWxpZ249cmVzZXQKKyNlbmRpZgorCisvKiBUaGUgSURFIHVzZXMgdGhlIG9wdGlvbmFsIGtleUFFUG9zaXRpb24gcGFyYW1ldGVyIHRvIHRlbGwgdGhlIGVkLQorICAgaXRvciB0aGUgc2VsZWN0aW9uIHJhbmdlLiBJZiBsaW5lTnVtIGlzIHplcm8gb3IgZ3JlYXRlciwgc2Nyb2xsIHRoZSB0ZXh0CisgICB0byB0aGUgc3BlY2lmaWVkIGxpbmUuIElmIGxpbmVOdW0gaXMgbGVzcyB0aGFuIHplcm8sIHVzZSB0aGUgdmFsdWVzIGluCisgICBzdGFydFJhbmdlIGFuZCBlbmRSYW5nZSB0byBzZWxlY3QgdGhlIHNwZWNpZmllZCBjaGFyYWN0ZXJzLiBTY3JvbGwKKyAgIHRoZSB0ZXh0IHRvIGRpc3BsYXkgdGhlIHNlbGVjdGlvbi4gSWYgbGluZU51bSwgc3RhcnRSYW5nZSwgYW5kCisgICBlbmRSYW5nZSBhcmUgYWxsIG5lZ2F0aXZlLCB0aGVyZSBpcyBubyBzZWxlY3Rpb24gcmFuZ2Ugc3BlY2lmaWVkLgorICovCisKK3Bhc2NhbCBPU0VyciBIYW5kbGVPRG9jQUUgKGNvbnN0IEFwcGxlRXZlbnQgKnRoZUFFdmVudCwgQXBwbGVFdmVudCAqdGhlUmVwbHksIGxvbmcgcmVmQ29uKQoreworICAgIC8qCisgICAgICogVE9ETzogQ2xlYW4gdXAgdGhlIGNvZGUgd2l0aCBjb252ZXJ0IHRoZSBBcHBsZUV2ZW50IGludG8KKyAgICAgKiAgICAgICBhICI6YXJncyIKKyAgICAgKi8KKyAgICBPU0VycgllcnJvciA9IG5vRXJyOworLy8gICAgT1NFcnIJZmlyc3RFcnJvciA9IG5vRXJyOworLy8gICAgc2hvcnQJbnVtRXJyb3JzID0gMDsKKyAgICBBRURlc2MJdGhlTGlzdDsKKyAgICBEZXNjVHlwZQl0eXBlQ29kZTsKKyAgICBsb25nCW51bUZpbGVzOworIC8vICAgbG9uZwkgZmlsZUNvdW50OworICAgIGNoYXJfdQkqKmZuYW1lczsKKy8vICAgIGNoYXJfdQlmbmFtZVsyNTZdOworICAgIFNpemUJYWN0dWFsU2l6ZTsKKyAgICBTZWxlY3Rpb25SYW5nZSB0aGVQb3NpdGlvbjsKKyAgICBzaG9ydAlnb3RQb3NpdGlvbiA9IGZhbHNlOworICAgIGxvbmcJbG51bTsKKworI2lmZGVmIFVTRV9TSU9VWAorICAgIHByaW50ZiAoImFldnRfb2RvYzpcbiIpOworI2VuZGlmCisKKyAgICAvKiB0aGUgZGlyZWN0IG9iamVjdCBwYXJhbWV0ZXIgaXMgdGhlIGxpc3Qgb2YgYWxpYXNlcyB0byBmaWxlcyAob25lIG9yIG1vcmUpICovCisgICAgZXJyb3IgPSBBRUdldFBhcmFtRGVzYyh0aGVBRXZlbnQsIGtleURpcmVjdE9iamVjdCwgdHlwZUFFTGlzdCwgJnRoZUxpc3QpOworICAgIGlmIChlcnJvcikKKyAgICB7CisjaWZkZWYgVVNFX1NJT1VYCisJcHJpbnRmICgiYWV2dF9vZG9jOiBBRUdldFBhcmFtRGVzYyBlcnJvcjogJWRcbiIsIGVycm9yKTsKKyNlbmRpZgorCXJldHVybihlcnJvcik7CisgICAgfQorCisKKyAgICBlcnJvciA9IEFFR2V0UGFyYW1QdHIodGhlQUV2ZW50LCBrZXlBRVBvc2l0aW9uLCB0eXBlQ2hhciwgJnR5cGVDb2RlLCAoUHRyKSAmdGhlUG9zaXRpb24sIHNpemVvZihTZWxlY3Rpb25SYW5nZSksICZhY3R1YWxTaXplKTsKKyAgICBpZiAoZXJyb3IgPT0gbm9FcnIpCisJZ290UG9zaXRpb24gPSB0cnVlOworICAgIGlmIChlcnJvciA9PSBlcnJBRURlc2NOb3RGb3VuZCkKKwllcnJvciA9IG5vRXJyOworICAgIGlmIChlcnJvcikKKyAgICB7CisjaWZkZWYgVVNFX1NJT1VYCisJcHJpbnRmICgiYWV2dF9vZG9jOiBBRUdldFBhcmFtUHRyIGVycm9yOiAlZFxuIiwgZXJyb3IpOworI2VuZGlmCisJcmV0dXJuKGVycm9yKTsKKyAgICB9CisKKyNpZmRlZiBVU0VfU0lPVVgKKyAgICBwcmludGYgKCJhZXZ0X29kb2M6IGxpbmVOdW06ICVkLCBzdGFydFJhbmdlICVkLCBlbmRSYW5nZSAlZCwgW2RhdGUgJWx4XVxuIiwKKwkgICAgdGhlUG9zaXRpb24ubGluZU51bSwgdGhlUG9zaXRpb24uc3RhcnRSYW5nZSwgdGhlUG9zaXRpb24uZW5kUmFuZ2UsCisJICAgIHRoZVBvc2l0aW9uLnRoZURhdGUpOworI2VuZGlmCisvKgorICAgIGVycm9yID0gQUVHZXRQYXJhbURlc2ModGhlQUV2ZW50LCBrZXlBRVBvc2l0aW9uLCB0eXBlQ2hhciwgJnRoZVBvc2l0aW9uKTsKKworICAgIGlmICheZXJyb3IpIHRoZW4KKyAgICB7CisJaWYgKHRoZVBvc2l0aW9uLmxpbmVOdW0gPj0gMCkKKwl7CisJICAvLyBHb3RvIHRoaXMgbGluZQorCX0KKwllbHNlCisJeworCSAgLy8gU2V0IHRoZSByYW5nZSBjaGFyIHdpc2UKKwl9CisgICAgfQorICovCisKKworI2lmZGVmIEZFQVRfVklTVUFMCisgICAgcmVzZXRfVklzdWFsKCk7CisjZW5kaWYKKworICAgIGZuYW1lcyA9IG5ld19mbmFtZXNfZnJvbV9BRURlc2MoJnRoZUxpc3QsICZudW1GaWxlcywgJmVycm9yKTsKKworICAgIGlmIChlcnJvcikKKyAgICB7CisgICAgICAvKiBUT0RPOiBlbXB0eSBmbmFtZXNbXSBmaXJzdCAqLworICAgICAgdmltX2ZyZWUoZm5hbWVzKTsKKyAgICAgIHJldHVybiAoZXJyb3IpOworICAgIH0KKworICAgIGlmIChzdGFydGluZyA+IDApCisgICAgeworCWludCBpOworCWNoYXJfdSAqcDsKKworCS8qIHRoZXNlIGFyZSB0aGUgaW5pdGlhbCBmaWxlcyBkcm9wcGVkIG9uIHRoZSBWaW0gaWNvbiAqLworCWZvciAoaSA9IDAgOyBpIDwgbnVtRmlsZXM7IGkrKykKKwl7CisJICAgIGlmIChnYV9ncm93KCZnbG9iYWxfYWxpc3QuYWxfZ2EsIDEpID09IEZBSUwKKwkJCQkgICAgICB8fCAocCA9IHZpbV9zdHJzYXZlKGZuYW1lc1tpXSkpID09IE5VTEwpCisJCW1jaF9leGl0KDIpOworCSAgICBlbHNlCisJCWFsaXN0X2FkZCgmZ2xvYmFsX2FsaXN0LCBwLCAyKTsKKwl9CisJZ290byBmaW5pc2hlZDsKKyAgICB9CisKKyAgICAvKiBIYW5kbGUgdGhlIGRyb3AsIDplZGl0IHRvIGdldCB0byB0aGUgZmlsZSAqLworICAgIGhhbmRsZV9kcm9wKG51bUZpbGVzLCBmbmFtZXMsIEZBTFNFKTsKKworICAgIC8qIFRPRE86IEhhbmRsZSB0aGUgZ290by9zZWxlY3QgbGluZSBtb3JlIGNsZWFubHkgKi8KKyAgICBpZiAoKG51bUZpbGVzID09IDEpICYgKGdvdFBvc2l0aW9uKSkKKyAgICB7CisJaWYgKHRoZVBvc2l0aW9uLmxpbmVOdW0gPj0gMCkKKwl7CisJICAgIGxudW0gPSB0aGVQb3NpdGlvbi5saW5lTnVtOworCS8qICBvYXAtPm1vdGlvbl90eXBlID0gTUxJTkU7CisJICAgIHNldHBjbWFyaygpOyovCisJICAgIGlmIChsbnVtIDwgMUwpCisJCWxudW0gPSAxTDsKKwkgICAgZWxzZSBpZiAobG51bSA+IGN1cmJ1Zi0+Yl9tbC5tbF9saW5lX2NvdW50KQorCQlsbnVtID0gY3VyYnVmLT5iX21sLm1sX2xpbmVfY291bnQ7CisJICAgIGN1cndpbi0+d19jdXJzb3IubG51bSA9IGxudW07CisJLyogIGJlZ2lubGluZShCTF9TT0wgfCBCTF9GSVgpOyovCisJfQorCWVsc2UKKwkgICAgZ290b19ieXRlKHRoZVBvc2l0aW9uLnN0YXJ0UmFuZ2UgKyAxKTsKKyAgICB9CisKKyAgICAvKiBVcGRhdGUgdGhlIHNjcmVlbiBkaXNwbGF5ICovCisgICAgdXBkYXRlX3NjcmVlbihOT1RfVkFMSUQpOworICAgIHNldGN1cnNvcigpOworICAgIG91dF9mbHVzaCgpOworCisgIGZpbmlzaGVkOgorICAgIEFFRGlzcG9zZURlc2MoJnRoZUxpc3QpOyAvKiBkaXNwb3NlIHdoYXQgd2UgYWxsb2NhdGVkICovCisKKyAgICBlcnJvciA9IEhhbmRsZVVudXNlZFBhcm1zICh0aGVBRXZlbnQpOworICAgIGlmIChlcnJvcikKKyAgICB7CisjaWZkZWYgVVNFX1NJT1VYCisJcHJpbnRmICgiYWV2dF9vZG9jOiBIYW5kbGVVbnVzZWRQYXJtcyBlcnJvcjogJWRcbiIsIGVycm9yKTsKKyNlbmRpZgorCXJldHVybihlcnJvcik7CisgICAgfQorICAgIHJldHVybihlcnJvcik7Cit9CisKKy8qCisgKgorICovCisKK3Bhc2NhbCBPU0VyciBIYW5kbGVfYWV2dF9vYXBwX0FFIChjb25zdCBBcHBsZUV2ZW50ICp0aGVBRXZlbnQsIEFwcGxlRXZlbnQgKnRoZVJlcGx5LCBsb25nIHJlZkNvbikKK3sKKyAgICBPU0VycgllcnJvciA9IG5vRXJyOworCisjaWZkZWYgVVNFX1NJT1VYCisgICAgcHJpbnRmICgiYWV2dF9vYXBwOlxuIik7CisjZW5kaWYKKworICAgIGVycm9yID0gSGFuZGxlVW51c2VkUGFybXMgKHRoZUFFdmVudCk7CisgICAgaWYgKGVycm9yKQorICAgIHsKKwlyZXR1cm4oZXJyb3IpOworICAgIH0KKworICAgIHJldHVybihlcnJvcik7Cit9CisKKy8qCisgKgorICovCisKK3Bhc2NhbCBPU0VyciBIYW5kbGVfYWV2dF9xdWl0X0FFIChjb25zdCBBcHBsZUV2ZW50ICp0aGVBRXZlbnQsIEFwcGxlRXZlbnQgKnRoZVJlcGx5LCBsb25nIHJlZkNvbikKK3sKKyAgICBPU0VycgllcnJvciA9IG5vRXJyOworCisjaWZkZWYgVVNFX1NJT1VYCisgICAgcHJpbnRmICgiYWV2dF9xdWl0XG4iKTsKKyNlbmRpZgorCisgICAgZXJyb3IgPSBIYW5kbGVVbnVzZWRQYXJtcyAodGhlQUV2ZW50KTsKKyAgICBpZiAoZXJyb3IpCisgICAgeworCXJldHVybihlcnJvcik7CisgICAgfQorCisgICAgLyogTmVlZCB0byBmYWtlIGEgOmNvbmZpcm0gcWEgKi8KKyAgICBkb19jbWRsaW5lX2NtZCgoY2hhcl91ICopImNvbmZpcm0gcWEiKTsKKworICAgIHJldHVybihlcnJvcik7Cit9CisKKy8qCisgKgorICovCisKK3Bhc2NhbCBPU0VyciBIYW5kbGVfYWV2dF9wZG9jX0FFIChjb25zdCBBcHBsZUV2ZW50ICp0aGVBRXZlbnQsIEFwcGxlRXZlbnQgKnRoZVJlcGx5LCBsb25nIHJlZkNvbikKK3sKKyAgICBPU0VycgllcnJvciA9IG5vRXJyOworCisjaWZkZWYgVVNFX1NJT1VYCisgICAgcHJpbnRmICgiYWV2dF9wZG9jOlxuIik7CisjZW5kaWYKKworICAgIGVycm9yID0gSGFuZGxlVW51c2VkUGFybXMgKHRoZUFFdmVudCk7CisgICAgaWYgKGVycm9yKQorICAgIHsKKwlyZXR1cm4oZXJyb3IpOworICAgIH0KKworICAgIHJldHVybihlcnJvcik7Cit9CisKKy8qCisgKiBIYW5kbGluZyBvZiB1bmtub3duIEFwcGxlRXZlbnQKKyAqCisgKiAoSnVzdCBnZXQgcmlkIG9mIGFsbCB0aGUgcGFybXMpCisgKi8KK3Bhc2NhbCBPU0VyciBIYW5kbGVfdW5rbm93bl9BRSAoY29uc3QgQXBwbGVFdmVudCAqdGhlQUV2ZW50LCBBcHBsZUV2ZW50ICp0aGVSZXBseSwgbG9uZyByZWZDb24pCit7CisgICAgT1NFcnIJZXJyb3IgPSBub0VycjsKKworI2lmZGVmIFVTRV9TSU9VWAorICAgIHByaW50ZiAoIlVua25vd24gRXZlbnQ6ICV4XG4iLCB0aGVBRXZlbnQtPmRlc2NyaXB0b3JUeXBlKTsKKyNlbmRpZgorCisgICAgZXJyb3IgPSBIYW5kbGVVbnVzZWRQYXJtcyAodGhlQUV2ZW50KTsKKyAgICBpZiAoZXJyb3IpCisgICAgeworCXJldHVybihlcnJvcik7CisgICAgfQorCisgICAgcmV0dXJuKGVycm9yKTsKK30KKworCisKKyNpZiBUQVJHRVRfQVBJX01BQ19DQVJCT04KKyMgZGVmaW5lIE5ld0FFRXZlbnRIYW5kbGVyUHJvYyh4KSBOZXdBRUV2ZW50SGFuZGxlclVQUCh4KQorI2VuZGlmCisKKy8qCisgKiBJbnN0YWxsIHRoZSB2YXJpb3VzIEFwcGxlRXZlbnQgSGFuZGxlcnMKKyAqLworT1NFcnIgICBJbnN0YWxsQUVIYW5kbGVycyAodm9pZCkKK3sKKyAgICBPU0VyciAgIGVycm9yOworCisgICAgLyogaW5zdGFsbCBvcGVuIGFwcGxpY2F0aW9uIGhhbmRsZXIgKi8KKyAgICBlcnJvciA9IEFFSW5zdGFsbEV2ZW50SGFuZGxlcihrQ29yZUV2ZW50Q2xhc3MsIGtBRU9wZW5BcHBsaWNhdGlvbiwKKwkJICAgIE5ld0FFRXZlbnRIYW5kbGVyUHJvYyhIYW5kbGVfYWV2dF9vYXBwX0FFKSwgMCwgZmFsc2UpOworICAgIGlmIChlcnJvcikKKyAgICB7CisJcmV0dXJuIGVycm9yOworICAgIH0KKworICAgIC8qIGluc3RhbGwgcXVpdCBhcHBsaWNhdGlvbiBoYW5kbGVyICovCisgICAgZXJyb3IgPSBBRUluc3RhbGxFdmVudEhhbmRsZXIoa0NvcmVFdmVudENsYXNzLCBrQUVRdWl0QXBwbGljYXRpb24sCisJCSAgICBOZXdBRUV2ZW50SGFuZGxlclByb2MoSGFuZGxlX2FldnRfcXVpdF9BRSksIDAsIGZhbHNlKTsKKyAgICBpZiAoZXJyb3IpCisgICAgeworCXJldHVybiBlcnJvcjsKKyAgICB9CisKKyAgICAvKiBpbnN0YWxsIG9wZW4gZG9jdW1lbnQgaGFuZGxlciAqLworICAgIGVycm9yID0gQUVJbnN0YWxsRXZlbnRIYW5kbGVyKGtDb3JlRXZlbnRDbGFzcywga0FFT3BlbkRvY3VtZW50cywKKwkJICAgIE5ld0FFRXZlbnRIYW5kbGVyUHJvYyhIYW5kbGVPRG9jQUUpLCAwLCBmYWxzZSk7CisgICAgaWYgKGVycm9yKQorICAgIHsKKwlyZXR1cm4gZXJyb3I7CisgICAgfQorCisgICAgLyogaW5zdGFsbCBwcmludCBkb2N1bWVudCBoYW5kbGVyICovCisgICAgZXJyb3IgPSBBRUluc3RhbGxFdmVudEhhbmRsZXIoa0NvcmVFdmVudENsYXNzLCBrQUVQcmludERvY3VtZW50cywKKwkJICAgIE5ld0FFRXZlbnRIYW5kbGVyUHJvYyhIYW5kbGVfYWV2dF9wZG9jX0FFKSwgMCwgZmFsc2UpOworCisvKiBJbnN0YWxsIENvcmUgU3VpdGUgKi8KKy8qICBlcnJvciA9IEFFSW5zdGFsbEV2ZW50SGFuZGxlcihrQUVDb3JlU3VpdGUsIGtBRUNsb25lLAorCQkgICAgTmV3QUVFdmVudEhhbmRsZXJQcm9jKEhhbmRsZV91bmtub3duX0FFKSwgbmlsLCBmYWxzZSk7CisKKyAgICBlcnJvciA9IEFFSW5zdGFsbEV2ZW50SGFuZGxlcihrQUVDb3JlU3VpdGUsIGtBRUNsb3NlLAorCQkgICAgTmV3QUVFdmVudEhhbmRsZXJQcm9jKEhhbmRsZV91bmtub3duX0FFKSwgbmlsLCBmYWxzZSk7CisKKyAgICBlcnJvciA9IEFFSW5zdGFsbEV2ZW50SGFuZGxlcihrQUVDb3JlU3VpdGUsIGtBRUNvdW50RWxlbWVudHMsCisJCSAgICBOZXdBRUV2ZW50SGFuZGxlclByb2MoSGFuZGxlX3Vua25vd25fQUUpLCBuaWwsIGZhbHNlKTsKKworICAgIGVycm9yID0gQUVJbnN0YWxsRXZlbnRIYW5kbGVyKGtBRUNvcmVTdWl0ZSwga0FFQ3JlYXRlRWxlbWVudCwKKwkJICAgIE5ld0FFRXZlbnRIYW5kbGVyUHJvYyhIYW5kbGVfdW5rbm93bl9BRSksIG5pbCwgZmFsc2UpOworCisgICAgZXJyb3IgPSBBRUluc3RhbGxFdmVudEhhbmRsZXIoa0FFQ29yZVN1aXRlLCBrQUVEZWxldGUsCisJCSAgICBOZXdBRUV2ZW50SGFuZGxlclByb2MoSGFuZGxlX3Vua25vd25fQUUpLCBuaWwsIGZhbHNlKTsKKworICAgIGVycm9yID0gQUVJbnN0YWxsRXZlbnRIYW5kbGVyKGtBRUNvcmVTdWl0ZSwga0FFRG9PYmplY3RzRXhpc3QsCisJCSAgICBOZXdBRUV2ZW50SGFuZGxlclByb2MoSGFuZGxlX3Vua25vd25fQUUpLCBuaWwsIGZhbHNlKTsKKworICAgIGVycm9yID0gQUVJbnN0YWxsRXZlbnRIYW5kbGVyKGtBRUNvcmVTdWl0ZSwga0FFR2V0RGF0YSwKKwkJICAgIE5ld0FFRXZlbnRIYW5kbGVyUHJvYyhIYW5kbGVfdW5rbm93bl9BRSksIGtBRUdldERhdGEsIGZhbHNlKTsKKworICAgIGVycm9yID0gQUVJbnN0YWxsRXZlbnRIYW5kbGVyKGtBRUNvcmVTdWl0ZSwga0FFR2V0RGF0YVNpemUsCisJCSAgICBOZXdBRUV2ZW50SGFuZGxlclByb2MoSGFuZGxlX3Vua25vd25fQUUpLCBrQUVHZXREYXRhU2l6ZSwgZmFsc2UpOworCisgICAgZXJyb3IgPSBBRUluc3RhbGxFdmVudEhhbmRsZXIoa0FFQ29yZVN1aXRlLCBrQUVHZXRDbGFzc0luZm8sCisJCSAgICBOZXdBRUV2ZW50SGFuZGxlclByb2MoSGFuZGxlX3Vua25vd25fQUUpLCBuaWwsIGZhbHNlKTsKKworICAgIGVycm9yID0gQUVJbnN0YWxsRXZlbnRIYW5kbGVyKGtBRUNvcmVTdWl0ZSwga0FFR2V0RXZlbnRJbmZvLAorCQkgICAgTmV3QUVFdmVudEhhbmRsZXJQcm9jKEhhbmRsZV91bmtub3duX0FFKSwgbmlsLCBmYWxzZSk7CisKKyAgICBlcnJvciA9IEFFSW5zdGFsbEV2ZW50SGFuZGxlcihrQUVDb3JlU3VpdGUsIGtBRU1vdmUsCisJCSAgICBOZXdBRUV2ZW50SGFuZGxlclByb2MoSGFuZGxlX3Vua25vd25fQUUpLCBuaWwsIGZhbHNlKTsKKworICAgIGVycm9yID0gQUVJbnN0YWxsRXZlbnRIYW5kbGVyKGtBRUNvcmVTdWl0ZSwga0FFU2F2ZSwKKwkJICAgIE5ld0FFRXZlbnRIYW5kbGVyUHJvYyhIYW5kbGVfdW5rbm93bl9BRSksIG5pbCwgZmFsc2UpOworCisgICAgZXJyb3IgPSBBRUluc3RhbGxFdmVudEhhbmRsZXIoa0FFQ29yZVN1aXRlLCBrQUVTZXREYXRhLAorCQkgICAgTmV3QUVFdmVudEhhbmRsZXJQcm9jKEhhbmRsZV91bmtub3duX0FFKSwgbmlsLCBmYWxzZSk7CisqLworCisjaWZkZWYgRkVBVF9DV19FRElUT1IKKyAgICAvKgorICAgICAqIEJpbmQgY29kZXdhcnJpb3Igc3VwcG9ydCBoYW5kbGVycworICAgICAqLworICAgIGVycm9yID0gQUVJbnN0YWxsRXZlbnRIYW5kbGVyKCdLQUhMJywgJ0dUVFgnLAorCQkgICAgTmV3QUVFdmVudEhhbmRsZXJQcm9jKEhhbmRsZV9LQUhMX0dUVFhfQUUpLCAwLCBmYWxzZSk7CisgICAgaWYgKGVycm9yKQorICAgIHsKKwlyZXR1cm4gZXJyb3I7CisgICAgfQorICAgIGVycm9yID0gQUVJbnN0YWxsRXZlbnRIYW5kbGVyKCdLQUhMJywgJ1NSQ0gnLAorCQkgICAgTmV3QUVFdmVudEhhbmRsZXJQcm9jKEhhbmRsZV9LQUhMX1NSQ0hfQUUpLCAwLCBmYWxzZSk7CisgICAgaWYgKGVycm9yKQorICAgIHsKKwlyZXR1cm4gZXJyb3I7CisgICAgfQorICAgIGVycm9yID0gQUVJbnN0YWxsRXZlbnRIYW5kbGVyKCdLQUhMJywgJ01PRCAnLAorCQkgICAgTmV3QUVFdmVudEhhbmRsZXJQcm9jKEhhbmRsZV9LQUhMX01PRF9BRSksIDAsIGZhbHNlKTsKKyAgICBpZiAoZXJyb3IpCisgICAgeworCXJldHVybiBlcnJvcjsKKyAgICB9CisjZW5kaWYKKworICAgIHJldHVybiBlcnJvcjsKKworfQorI2VuZGlmIC8qIFVTRV9BRVZFTlQgKi8KKworLyoKKyAqIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQorICogVW5maWxlZCB5ZXQKKyAqIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQorICovCisKKy8qCisgKiAgZ3VpX21hY19nZXRfbWVudV9pdGVtX2luZGV4CisgKgorICogIFJldHVybnMgdGhlIGluZGV4IGluc2lkZSB0aGUgbWVudSB3aGVyCisgKi8KKyAgICBzaG9ydCAvKiBTaG91bGRlIHdlIHJldHVybiBNZW51SXRlbUluZGV4PyAqLworZ3VpX21hY19nZXRfbWVudV9pdGVtX2luZGV4IChwTWVudSkKKyAgICB2aW1tZW51X1QgKnBNZW51OworeworICAgIHNob3J0CWluZGV4OworICAgIHNob3J0CWl0ZW1JbmRleCA9IC0xOworICAgIHZpbW1lbnVfVAkqcEJyb3RoZXI7CisKKyAgICAvKiBPbmx5IG1lbnUgd2l0aG91dCBwYXJlbnQgYXJlIHRoZToKKyAgICAgKiAtbWVudSBpbiB0aGUgbWVudWJhcgorICAgICAqIC1wb3B1cCBtZW51CisgICAgICogLXRvb2xiYXIgKGd1ZXNzKQorICAgICAqCisgICAgICogV2hpY2ggYXJlIG5vdCBpdGVtcyBhbnl3YXkuCisgICAgICovCisgICAgaWYgKHBNZW51LT5wYXJlbnQpCisgICAgeworCS8qIFN0YXJ0IGZyb20gdGhlIE9sZGVzdCBCcm90aGVyICovCisJcEJyb3RoZXIgPSBwTWVudS0+cGFyZW50LT5jaGlsZHJlbjsKKwlpbmRleCA9IDE7CisJd2hpbGUgKChwQnJvdGhlcikgJiYgKGl0ZW1JbmRleCA9PSAtMSkpCisJeworCSAgICBpZiAocEJyb3RoZXIgPT0gcE1lbnUpCisJCWl0ZW1JbmRleCA9IGluZGV4OworCSAgICBpbmRleCsrOworCSAgICBwQnJvdGhlciA9IHBCcm90aGVyLT5uZXh0OworCX0KKyNpZmRlZiBVU0VfSEVMUE1FTlUKKwkvKiBBZGp1c3QgaW5kZXggaW4gaGVscCBtZW51IChmb3IgcHJlZGVmaW5lZCBvbmVzKSAqLworCWlmIChpdGVtSW5kZXggIT0gLTEpCisJICAgIGlmIChwTWVudS0+cGFyZW50LT5zdWJtZW51X2lkID09IGtITUhlbHBNZW51SUQpCisJCWl0ZW1JbmRleCArPSBndWkuTWFjT1NIZWxwSXRlbXM7CisjZW5kaWYKKyAgICB9CisgICAgcmV0dXJuIGl0ZW1JbmRleDsKK30KKworICAgIHN0YXRpYyB2aW1tZW51X1QgKgorZ3VpX21hY19nZXRfdmltX21lbnUgKG1lbnVJRCwgaXRlbUluZGV4LCBwTWVudSkKKyAgICBzaG9ydAltZW51SUQ7CisgICAgc2hvcnQJaXRlbUluZGV4OworICAgIHZpbW1lbnVfVAkqcE1lbnU7Cit7CisgICAgc2hvcnQJaW5kZXg7CisgICAgdmltbWVudV9UCSpwQ2hpbGRNZW51OworICAgIHZpbW1lbnVfVAkqcEVsZGVyID0gcE1lbnUtPnBhcmVudDsKKworCisgICAgLyogT25seSBtZW51IHdpdGhvdXQgcGFyZW50IGFyZSB0aGU6CisgICAgICogLW1lbnUgaW4gdGhlIG1lbnViYXIKKyAgICAgKiAtcG9wdXAgbWVudQorICAgICAqIC10b29sYmFyIChndWVzcykKKyAgICAgKgorICAgICAqIFdoaWNoIGFyZSBub3QgaXRlbXMgYW55d2F5LgorICAgICAqLworCisgICAgaWYgKChwRWxkZXIpICYmIChwRWxkZXItPnN1Ym1lbnVfaWQgPT0gbWVudUlEKSkKKyAgICB7CisjaWZkZWYgVVNFX0hFTFBNRU5VCisJaWYgKG1lbnVJRCA9PSBrSE1IZWxwTWVudUlEKQorCSAgICBpdGVtSW5kZXggLT0gZ3VpLk1hY09TSGVscEl0ZW1zOworI2VuZGlmCisKKwlmb3IgKGluZGV4ID0gMTsgKGluZGV4ICE9IGl0ZW1JbmRleCkgJiYgKHBNZW51ICE9IE5VTEwpOyBpbmRleCsrKQorCSAgICBwTWVudSA9IHBNZW51LT5uZXh0OworICAgIH0KKyAgICBlbHNlCisgICAgeworCWZvciAoOyBwTWVudSAhPSBOVUxMOyBwTWVudSA9IHBNZW51LT5uZXh0KQorCXsKKwkgICAgaWYgKHBNZW51LT5jaGlsZHJlbiAhPSBOVUxMKQorCSAgICB7CisJCXBDaGlsZE1lbnUgPSBndWlfbWFjX2dldF92aW1fbWVudQorCQkJICAgKG1lbnVJRCwgaXRlbUluZGV4LCBwTWVudS0+Y2hpbGRyZW4pOworCQlpZiAocENoaWxkTWVudSkKKwkJeworCQkgICAgcE1lbnUgPSBwQ2hpbGRNZW51OworCQkgICAgYnJlYWs7CisJCX0KKwkgICAgfQorCX0KKyAgICB9CisgICAgcmV0dXJuIHBNZW51OworfQorCisvKgorICogLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCisgKiBNYWNPUyBGZWVkYmFjayBwcm9jZWR1cmVzCisgKiAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KKyAqLworICAgIHBhc2NhbAorICAgIHZvaWQKK2d1aV9tYWNfZHJhZ190aHVtYiAoQ29udHJvbEhhbmRsZSB0aGVDb250cm9sLCBzaG9ydCBwYXJ0Q29kZSkKK3sKKyAgICBzY3JvbGxiYXJfVAkJKnNiOworICAgIGludAkJCXZhbHVlLCBkcmFnZ2luZzsKKyAgICBDb250cm9sSGFuZGxlCXRoZUNvbnRyb2xUb1VzZTsKKyAgICBpbnQJCQlkb250X3Njcm9sbF9zYXZlID0gZG9udF9zY3JvbGw7CisKKyAgICB0aGVDb250cm9sVG9Vc2UgPSBkcmFnZ2VkX3NiOworCisgICAgc2IgPSBndWlfZmluZF9zY3JvbGxiYXIoKGxvbmcpIEdldENvbnRyb2xSZWZlcmVuY2UgKHRoZUNvbnRyb2xUb1VzZSkpOworCisgICAgaWYgKHNiID09IE5VTEwpCisJcmV0dXJuOworCisgICAgLyogTmVlZCB0byBmaW5kIHZhbHVlIGJ5IGRpZmYgYmV0d2VlbiBPbGQgUG9zcyBOZXcgUG9zICovCisgICAgdmFsdWUgPSBHZXRDb250cm9sMzJCaXRWYWx1ZSAodGhlQ29udHJvbFRvVXNlKTsKKyAgICBkcmFnZ2luZyA9IChwYXJ0Q29kZSAhPSAwKTsKKworICAgIC8qIFdoZW4gImFsbG93X3Njcm9sbGJhciIgaXMgRkFMU0Ugc3RpbGwgbmVlZCB0byByZW1lbWJlciB0aGUgbmV3CisgICAgICogcG9zaXRpb24sIGJ1dCBkb24ndCBhY3R1YWxseSBzY3JvbGwgYnkgc2V0dGluZyAiZG9udF9zY3JvbGwiLiAqLworICAgIGRvbnRfc2Nyb2xsID0gIWFsbG93X3Njcm9sbGJhcjsKKyAgICBndWlfZHJhZ19zY3JvbGxiYXIoc2IsIHZhbHVlLCBkcmFnZ2luZyk7CisgICAgZG9udF9zY3JvbGwgPSBkb250X3Njcm9sbF9zYXZlOworfQorCisgICAgcGFzY2FsCisgICAgdm9pZAorZ3VpX21hY19zY3JvbGxfYWN0aW9uIChDb250cm9sSGFuZGxlIHRoZUNvbnRyb2wsIHNob3J0IHBhcnRDb2RlKQoreworICAgIC8qIFRPRE86IGhhdmUgbGl2ZSBzdXBwb3J0ICovCisgICAgc2Nyb2xsYmFyX1QgKnNiLCAqc2JfaW5mbzsKKyAgICBsb25nCWRhdGE7CisgICAgbG9uZwl2YWx1ZTsKKyAgICBpbnQJCXBhZ2U7CisgICAgaW50CQlkcmFnZ2luZyA9IEZBTFNFOworICAgIGludAkJZG9udF9zY3JvbGxfc2F2ZSA9IGRvbnRfc2Nyb2xsOworCisgICAgc2IgPSBndWlfZmluZF9zY3JvbGxiYXIoKGxvbmcpIEdldENvbnRyb2xSZWZlcmVuY2UgKHRoZUNvbnRyb2wpKTsKKworICAgIGlmIChzYiA9PSBOVUxMKQorCXJldHVybjsKKworICAgIGlmIChzYi0+d3AgIT0gTlVMTCkJCS8qIExlZnQgb3IgcmlnaHQgc2Nyb2xsYmFyICovCisgICAgeworCS8qCisJICogQ2FyZWZ1bDogbmVlZCB0byBnZXQgc2Nyb2xsYmFyIGluZm8gb3V0IG9mIGZpcnN0IChsZWZ0KSBzY3JvbGxiYXIKKwkgKiBmb3Igd2luZG93LCBidXQga2VlcCByZWFsIHNjcm9sbGJhciB0b28gYmVjYXVzZSB3ZSBtdXN0IHBhc3MgaXQgdG8KKwkgKiBndWlfZHJhZ19zY3JvbGxiYXIoKS4KKwkgKi8KKwlzYl9pbmZvID0gJnNiLT53cC0+d19zY3JvbGxiYXJzWzBdOworCisJaWYgKHNiX2luZm8tPnNpemUgPiA1KQorCSAgICBwYWdlID0gc2JfaW5mby0+c2l6ZSAtIDI7CS8qIHVzZSB0d28gbGluZXMgb2YgY29udGV4dCAqLworCWVsc2UKKwkgICAgcGFnZSA9IHNiX2luZm8tPnNpemU7CisgICAgfQorICAgIGVsc2UJCQkvKiBCb3R0b20gc2Nyb2xsYmFyICovCisgICAgeworCXNiX2luZm8gPSBzYjsKKwlwYWdlID0gV19XSURUSChjdXJ3aW4pIC0gNTsKKyAgICB9CisKKyAgICBzd2l0Y2ggKHBhcnRDb2RlKQorICAgIHsKKwljYXNlICBrQ29udHJvbFVwQnV0dG9uUGFydDogICBkYXRhID0gLTE7ICAgIGJyZWFrOworCWNhc2UgIGtDb250cm9sRG93bkJ1dHRvblBhcnQ6IGRhdGEgPSAxOyAgICAgYnJlYWs7CisJY2FzZSAga0NvbnRyb2xQYWdlRG93blBhcnQ6ICAgZGF0YSA9IHBhZ2U7ICBicmVhazsKKwljYXNlICBrQ29udHJvbFBhZ2VVcFBhcnQ6ICAgICBkYXRhID0gLXBhZ2U7IGJyZWFrOworCQkgICAgZGVmYXVsdDogZGF0YSA9IDA7IGJyZWFrOworICAgIH0KKworICAgIHZhbHVlID0gc2JfaW5mby0+dmFsdWUgKyBkYXRhOworLyogIGlmICh2YWx1ZSA+IHNiX2luZm8tPm1heCkKKwl2YWx1ZSA9IHNiX2luZm8tPm1heDsKKyAgICBlbHNlIGlmICh2YWx1ZSA8IDApCisJdmFsdWUgPSAwOyovCisKKyAgICAvKiBXaGVuICJhbGxvd19zY3JvbGxiYXIiIGlzIEZBTFNFIHN0aWxsIG5lZWQgdG8gcmVtZW1iZXIgdGhlIG5ldworICAgICAqIHBvc2l0aW9uLCBidXQgZG9uJ3QgYWN0dWFsbHkgc2Nyb2xsIGJ5IHNldHRpbmcgImRvbnRfc2Nyb2xsIi4gKi8KKyAgICBkb250X3Njcm9sbCA9ICFhbGxvd19zY3JvbGxiYXI7CisgICAgZ3VpX2RyYWdfc2Nyb2xsYmFyKHNiLCB2YWx1ZSwgZHJhZ2dpbmcpOworICAgIGRvbnRfc2Nyb2xsID0gZG9udF9zY3JvbGxfc2F2ZTsKKworICAgIG91dF9mbHVzaCgpOworICAgIGd1aV9tY2hfc2V0X3Njcm9sbGJhcl90aHVtYihzYiwgdmFsdWUsIHNiX2luZm8tPnNpemUsIHNiX2luZm8tPm1heCk7CisKKy8qICBpZiAoc2JfaW5mby0+d3AgIT0gTlVMTCkKKyAgICB7CisJd2luX1QJKndwOworCWludAlzYl9udW07CisKKwlzYl9udW0gPSAwOworCWZvciAod3AgPSBmaXJzdHdpbjsgd3AgIT0gc2ItPndwICYmIHdwICE9IE5VTEw7IHdwID0gV19ORVhUKHdwKSkKKwlzYl9udW0rKzsKKworCWlmICh3cCAhPSBOVUxMKQorCXsKKwkgICAgY3VycmVudF9zY3JvbGxiYXIgPSBzYl9udW07CisJICAgIHNjcm9sbGJhcl92YWx1ZSA9IHZhbHVlOworCSAgICBndWlfZG9fc2Nyb2xsKCk7CisJICAgIGd1aV9tY2hfc2V0X3Njcm9sbGJhcl90aHVtYihzYiwgdmFsdWUsIHNiX2luZm8tPnNpemUsIHNiX2luZm8tPm1heCk7CisJfQorICAgIH0qLworfQorCisvKgorICogLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCisgKiBNYWNPUyBDbGljayBIYW5kbGluZyBwcm9jZWR1cmVzCisgKiAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KKyAqLworCisKKy8qCisgKiBIYW5kbGUgYSBjbGljayBpbnNpZGUgdGhlIHdpbmRvdywgaXQgbWF5IGhhcHBlbnMgaW4gdGhlCisgKiBzY3JvbGxiYXIgb3IgdGhlIGNvbnRlbnRzLgorICoKKyAqIFRPRE86IEFkZCBzdXBwb3J0IGZvciBwb3RlbnRpYWwgVE9PTEJBUgorICovCisgICAgdm9pZAorZ3VpX21hY19kb0luQ29udGVudENsaWNrICh0aGVFdmVudCwgd2hpY2hXaW5kb3cpCisgICAgRXZlbnRSZWNvcmQgKnRoZUV2ZW50OworICAgIFdpbmRvd1B0cgkgd2hpY2hXaW5kb3c7Cit7CisgICAgUG9pbnQJCXRoZVBvaW50OworICAgIGludF91CQl2aW1Nb2RpZmllcnM7CisgICAgc2hvcnQJCXRoZVBvcnRpb247CisgICAgQ29udHJvbEhhbmRsZQl0aGVDb250cm9sOworICAgIGludAkJCXZpbU1vdXNlQnV0dG9uOworICAgIHNob3J0CQlkYmxDbGljazsKKworICAgIHRoZVBvaW50ID0gdGhlRXZlbnQtPndoZXJlOworICAgIEdsb2JhbFRvTG9jYWwgKCZ0aGVQb2ludCk7CisgICAgU2VsZWN0V2luZG93ICh3aGljaFdpbmRvdyk7CisKKyAgICB0aGVQb3J0aW9uID0gRmluZENvbnRyb2wgKHRoZVBvaW50LCB3aGljaFdpbmRvdywgJnRoZUNvbnRyb2wpOworCisgICAgaWYgKHRoZUNvbnRyb2wgIT0gTlVMKQorICAgIHsKKwkvKiBXZSBoaXQgYSBzY29sbGJhciAqLworCisJaWYgKHRoZVBvcnRpb24gIT0ga0NvbnRyb2xJbmRpY2F0b3JQYXJ0KQorCXsKKwkgICAgZHJhZ2dlZF9zYiA9IHRoZUNvbnRyb2w7CisJICAgIFRyYWNrQ29udHJvbCh0aGVDb250cm9sLCB0aGVQb2ludCwgZ1Njcm9sbEFjdGlvbik7CisJICAgIGRyYWdnZWRfc2IgPSBOVUxMOworCX0KKwllbHNlCisJeworCSAgICBkcmFnZ2VkX3NiID0gdGhlQ29udHJvbDsKKyNpZiAxCisJICAgIFRyYWNrQ29udHJvbCh0aGVDb250cm9sLCB0aGVQb2ludCwgZ1Njcm9sbERyYWcpOworI2Vsc2UKKwkgICAgVHJhY2tDb250cm9sKHRoZUNvbnRyb2wsIHRoZVBvaW50LCBOVUxMKTsKKyNlbmRpZgorCSAgICAvKiBwYXNzIDAgYXMgdGhlIHBhcnQgdG8gdGVsbCBndWlfbWFjX2RyYWdfdGh1bWIsIHRoYXQgdGhlIG1vdXNlCisJICAgICAqIGJ1dHRvbiBoYXMgYmVlbiByZWxlYXNlZCAqLworCSAgICBndWlfbWFjX2RyYWdfdGh1bWIgKHRoZUNvbnRyb2wsIDApOyAvKiBTaG91bGQgaXQgYmUgdGhlUG9ydGlvbiA/IChEYW55KSAqLworCSAgICBkcmFnZ2VkX3NiID0gTlVMTDsKKwl9CisgICAgfQorICAgIGVsc2UKKyAgICB7CisJLyogV2UgYXJlIGluc2lkZSB0aGUgY29udGVudHMgKi8KKworCS8qIENvbnZlcnQgdGhlIENUUkwsIE9QVElPTiwgU0hJRlQgYW5kIENNRCBrZXkgKi8KKwl2aW1Nb2RpZmllcnMgPSBFdmVudE1vZGlmaWVyczJWaW1Nb3VzZU1vZGlmaWVycyh0aGVFdmVudC0+bW9kaWZpZXJzKTsKKworCS8qIERlZmF1bHRzIHRvIE1PVVNFX0xFRlQgYXMgdGhlcmUncyBvbmx5IG9uZSBtb3VzZSBidXR0b24gKi8KKwl2aW1Nb3VzZUJ1dHRvbiA9IE1PVVNFX0xFRlQ7CisKKyNpZmRlZiBVU0VfQ1RSTENMSUNLTUVOVQorCS8qIENvbnZlcnQgdGhlIENUUkxfTU9VU0VfTEVGVCB0byBNT1VTRV9SSUdIVCAqLworCWNsaWNrSXNQb3B1cCA9IEZBTFNFOworCisJaWYgKChndWkuTWFjT1NIYXZlQ250eE1lbnUpICYmIChtb3VzZV9tb2RlbF9wb3B1cCgpKSkKKwkgICAgaWYgKElzU2hvd0NvbnRleHR1YWxNZW51Q2xpY2sodGhlRXZlbnQpKQorCSAgICB7CisJCXZpbU1vdXNlQnV0dG9uID0gTU9VU0VfUklHSFQ7CisJCXZpbU1vZGlmaWVycyAmPSB+TU9VU0VfQ1RSTDsKKwkJY2xpY2tJc1BvcHVwID0gVFJVRTsKKwkgICAgfQorI2VuZGlmCisKKwkvKiBJcyBpdCBhIGRvdWJsZSBjbGljayA/ICovCisJZGJsQ2xpY2sgPSAoKHRoZUV2ZW50LT53aGVuIC0gbGFzdE1vdXNlVGljaykgPCBHZXREYmxUaW1lKCkpOworCisJLyogU2VuZCB0aGUgbW91c2UgY2xpY2ogdG8gVmltICovCisJZ3VpX3NlbmRfbW91c2VfZXZlbnQodmltTW91c2VCdXR0b24sIHRoZVBvaW50LmgsCisJCQkJCSAgdGhlUG9pbnQudiwgZGJsQ2xpY2ssIHZpbU1vZGlmaWVycyk7CisKKwkvKiBDcmVhdGUgdGhlIHJlY3RhbmdsZSBhcm91bmQgdGhlIGN1cnNvciB0byBkZXRlY3QKKwkgKiB0aGUgbW91c2UgZHJhZ2dpbmcKKwkgKi8KKyNpZmRlZiBVU0VfQ1RSTENMSUNLTUVOVQorI2lmIDAKKwkvKiBUT0RPOiBEbyB3ZSBuZWVkIHRvIHRoaXMgZXZlbiBmb3IgdGhlIGNvbnRleHR1YWwgbWVudT8KKwkgKiBJdCBtYXkgYmUgcmVxdWlyZSBmb3IgcG9wdXBfc2V0cG9zLCBidXQgZm9yIHBvcHVwPworCSAqLworCWlmICh2aW1Nb3VzZUJ1dHRvbiA9PSBNT1VTRV9MRUZUKQorI2VuZGlmCisjZW5kaWYKKwl7CisJICAgIFNldFJlY3QgKCZkcmFnUmVjdCwgRklMTF9YKFhfMl9DT0wodGhlUG9pbnQuaCkpLAorCQkJCUZJTExfWShZXzJfUk9XKHRoZVBvaW50LnYpKSwKKwkJCQlGSUxMX1goWF8yX0NPTCh0aGVQb2ludC5oKSsxKSwKKwkJCQlGSUxMX1koWV8yX1JPVyh0aGVQb2ludC52KSsxKSk7CisKKwkgICAgZHJhZ1JlY3RFbmJsID0gVFJVRTsKKwkgICAgZHJhZ1JlY3RDb250cm9sID0ga0NyZWF0ZVJlY3Q7CisJfQorICAgIH0KK30KKworLyoKKyAqIEhhbmRsZSB0aGUgY2xpY2sgaW4gdGhlIHRpdGxlYmFyICh0byBtb3ZlIHRoZSB3aW5kb3cpCisgKi8KKyAgICB2b2lkCitndWlfbWFjX2RvSW5EcmFnQ2xpY2sgKHdoZXJlLCB3aGljaFdpbmRvdykKKyAgICBQb2ludAl3aGVyZTsKKyAgICBXaW5kb3dQdHIJd2hpY2hXaW5kb3c7Cit7CisgICAgUmVjdAltb3ZpbmdMaW1pdHM7CisgICAgUmVjdAkqbW92aW5nTGltaXRzUHRyID0gJm1vdmluZ0xpbWl0czsKKworICAgIC8qIFRPRE86IG1heSB0cnkgdG8gcHJldmVudCBtb3ZlIG91dHNpZGUgc2NyZWVuPyAqLworI2lmZGVmIFVTRV9DQVJCT05JWkVECisgICAgbW92aW5nTGltaXRzUHRyID0gR2V0UmVnaW9uQm91bmRzICggR2V0R3JheVJnbigpLCAmbW92aW5nTGltaXRzICk7CisjZWxzZQorICAgIG1vdmluZ0xpbWl0c1B0ciA9ICYoKkdldEdyYXlSZ24oKSktPnJnbkJCb3g7CisjZW5kaWYKKyAgICBEcmFnV2luZG93ICh3aGljaFdpbmRvdywgd2hlcmUsIG1vdmluZ0xpbWl0c1B0cik7Cit9CisKKy8qCisgKiBIYW5kbGUgdGhlIGNsaWNrIGluIHRoZSBncm93IGJveAorICovCisgICAgdm9pZAorZ3VpX21hY19kb0luR3Jvd0NsaWNrKHdoZXJlLCB3aGljaFdpbmRvdykKKyAgICBQb2ludAl3aGVyZTsKKyAgICBXaW5kb3dQdHIJd2hpY2hXaW5kb3c7Cit7CisKKyAgICBsb25nCSAgICBuZXdTaXplOworICAgIHVuc2lnbmVkIHNob3J0ICBuZXdXaWR0aDsKKyAgICB1bnNpZ25lZCBzaG9ydCAgbmV3SGVpZ2h0OworICAgIFJlY3QJICAgIHJlc2l6ZUxpbWl0czsKKyAgICBSZWN0CSAgICAqcmVzaXplTGltaXRzUHRyID0gJnJlc2l6ZUxpbWl0czsKKyNpZmRlZiBVU0VfQ0FSQk9OSVpFRAorICAgIFJlY3QJICAgIE5ld0NvbnRlbnRSZWN0OworCisgICAgcmVzaXplTGltaXRzUHRyID0gR2V0UmVnaW9uQm91bmRzICggR2V0R3JheVJnbigpLCAmcmVzaXplTGltaXRzICk7CisjZWxzZQorICAgIHJlc2l6ZUxpbWl0cyA9IHFkLnNjcmVlbkJpdHMuYm91bmRzOworI2VuZGlmCisKKyAgICAvKiBTZXQgdGhlIG1pbmltdW4gc2l6ZSAqLworICAgIC8qIFRPRE86IFNob3VsZCB0aGlzIGNvbWUgZnJvbSBWaW0/ICovCisgICAgcmVzaXplTGltaXRzLnRvcCA9IDEwMDsKKyAgICByZXNpemVMaW1pdHMubGVmdCA9IDEwMDsKKworI2lmZGVmIFVTRV9DQVJCT05JWkVECisgICAgbmV3U2l6ZSA9IFJlc2l6ZVdpbmRvdyh3aGljaFdpbmRvdywgd2hlcmUsICZyZXNpemVMaW1pdHMsICZOZXdDb250ZW50UmVjdCk7CisgICAgbmV3V2lkdGggID0gTmV3Q29udGVudFJlY3QucmlnaHQgLSBOZXdDb250ZW50UmVjdC5sZWZ0OworICAgIG5ld0hlaWdodCA9IE5ld0NvbnRlbnRSZWN0LmJvdHRvbSAtIE5ld0NvbnRlbnRSZWN0LnRvcDsKKyAgICBndWlfcmVzaXplX3NoZWxsKG5ld1dpZHRoLCBuZXdIZWlnaHQpOworICAgIGd1aV9tY2hfc2V0X2JnX2NvbG9yKGd1aS5iYWNrX3BpeGVsKTsKKyAgICBndWlfc2V0X3NoZWxsc2l6ZShUUlVFLCBGQUxTRSk7CisjZWxzZQorICAgIG5ld1NpemUgPSBHcm93V2luZG93KHdoaWNoV2luZG93LCB3aGVyZSwgJnJlc2l6ZUxpbWl0cyk7CisgICAgaWYgKG5ld1NpemUgIT0gMCkKKyAgICB7CisJbmV3V2lkdGggID0gbmV3U2l6ZSAmIDB4MDAwMEZGRkY7CisJbmV3SGVpZ2h0ID0gKG5ld1NpemUgPj4gMTYpICYgMHgwMDAwRkZGRjsKKworCWd1aV9tY2hfc2V0X2JnX2NvbG9yKGd1aS5iYWNrX3BpeGVsKTsKKworCWd1aV9yZXNpemVfc2hlbGwobmV3V2lkdGgsIG5ld0hlaWdodCk7CisKKwkvKgorCSAqIFdlIG5lZWQgdG8gY2FsbCBndWlfc2V0X3NoZWxsc2l6ZSBhcyB0aGUgc2l6ZQorCSAqIHVzZWQgYnkgVmltIG1heSBiZSBzbWFsbGVyIHRoYW4gdGhlIHNpemUgc2VsZWN0ZWQKKwkgKiBieSB0aGUgdXNlci4gVGhpcyBjYXVzZSBzb21lIG92ZXJoZWFkCisJICogVE9ETzogYWRkIGEgY2hlY2sgaW5zaWRlIGd1aV9yZXNpemVfc2hlbGw/CisJICovCisJZ3VpX3NldF9zaGVsbHNpemUoVFJVRSwgRkFMU0UpOworCisJLyoKKwkgKiBPcmlnaW4gb2YgdGhlIGNvZGUgYmVsb3cgaXMgdW5rbm93bi4KKwkgKiBGdW5jdGlvbmFsaXR5IGlzIHVua25vd24uCisJICogVGltZSBvZiBjb21tZW50ZWQgb3V0IGlzIHVua25vd24uCisJICovCisvKglTZXRQb3J0KHdwKTsKKwlJbnZhbFJlY3QoJndwLT5wb3J0UmVjdCk7CisJaWYgKGlzVXNlcldpbmRvdyh3cCkpIHsKKwkgICAgRHJhd2luZ1dpbmRvd1BlZWsJYVdpbmRvdyA9IChEcmF3aW5nV2luZG93UGVlayl3cDsKKworCSAgICBpZiAoYVdpbmRvdy0+dG9vbFJvdXRpbmVzLnRvb2xXaW5kb3dSZXNpemVkUHJvYykKKwkJQ2FsbFRvb2xXaW5kb3dSZXNpemVkUHJvYyhhV2luZG93LT50b29sUm91dGluZXMudG9vbFdpbmRvd1Jlc2l6ZWRQcm9jLCB3cCk7CisJfSovCisgICAgfTsKKyNlbmRpZgorCit9CisKKy8qCisgKiBIYW5kbGUgdGhlIGNsaWNrIGluIHRoZSB6b29tIGJveAorICovCisjaWZkZWYgVVNFX0NBUkJPTklaRUQKKyAgICBzdGF0aWMgdm9pZAorZ3VpX21hY19kb0luWm9vbUNsaWNrKHRoZUV2ZW50LCB3aGljaFdpbmRvdykKKyAgICBFdmVudFJlY29yZAkqdGhlRXZlbnQ7CisgICAgV2luZG93UHRyCXdoaWNoV2luZG93OworeworICAgIFJlY3QJcjsKKyAgICBQb2ludAlwOworICAgIHNob3J0CXRoZVBhcnQ7CisKKyAgICAvKiBpZGVhbCB3aWR0aCBpcyBjdXJyZW50ICovCisgICAgcC5oID0gQ29sdW1ucyAqIGd1aS5jaGFyX3dpZHRoICsgMiAqIGd1aS5ib3JkZXJfb2Zmc2V0OworICAgIGlmIChndWkud2hpY2hfc2Nyb2xsYmFyc1tTQkFSX0xFRlRdKQorCXAuaCArPSBndWkuc2Nyb2xsYmFyX3dpZHRoOworICAgIGlmIChndWkud2hpY2hfc2Nyb2xsYmFyc1tTQkFSX1JJR0hUXSkKKwlwLmggKz0gZ3VpLnNjcm9sbGJhcl93aWR0aDsKKyAgICAvKiBpZGVhbCBoZWlnaHQgaXMgYXMgaGVpZ2ggYXMgd2UgY2FuIGdldCAqLworICAgIHAudiA9IDE1ICogMTAyNDsKKworICAgIHRoZVBhcnQgPSBJc1dpbmRvd0luU3RhbmRhcmRTdGF0ZSh3aGljaFdpbmRvdywgJnAsICZyKQorCQkJCQkJICAgICAgID8gaW5ab29tSW4gOiBpblpvb21PdXQ7CisKKyAgICBpZiAoIVRyYWNrQm94KHdoaWNoV2luZG93LCB0aGVFdmVudC0+d2hlcmUsIHRoZVBhcnQpKQorCXJldHVybjsKKworICAgIC8qIHVzZSByZXR1cm5lZCB3aWR0aCAqLworICAgIHAuaCA9IHIucmlnaHQgLSByLmxlZnQ7CisgICAgLyogYWRqdXN0IHJldHVybmVkIGhlaWdodCAqLworICAgIHAudiA9IHIuYm90dG9tIC0gci50b3AgLSAyICogZ3VpLmJvcmRlcl9vZmZzZXQ7CisgICAgaWYgKGd1aS53aGljaF9zY3JvbGxiYXJzW1NCQVJfQk9UVE9NXSkKKwlwLnYgLT0gZ3VpLnNjcm9sbGJhcl9oZWlnaHQ7CisgICAgcC52IC09IHAudiAlIGd1aS5jaGFyX2hlaWdodDsKKyAgICBwLnYgKz0gMiAqIGd1aS5ib3JkZXJfd2lkdGg7CisgICAgaWYgKGd1aS53aGljaF9zY3JvbGxiYXJzW1NCQVJfQk9UVE9NXSk7CisJcC52ICs9IGd1aS5zY3JvbGxiYXJfaGVpZ2h0OworCisgICAgWm9vbVdpbmRvd0lkZWFsKHdoaWNoV2luZG93LCB0aGVQYXJ0LCAmcCk7CisKKyAgICBHZXRXaW5kb3dCb3VuZHMod2hpY2hXaW5kb3csIGtXaW5kb3dDb250ZW50UmduLCAmcik7CisgICAgZ3VpX3Jlc2l6ZV9zaGVsbChyLnJpZ2h0IC0gci5sZWZ0LCByLmJvdHRvbSAtIHIudG9wKTsKKyAgICBndWlfbWNoX3NldF9iZ19jb2xvcihndWkuYmFja19waXhlbCk7CisgICAgZ3VpX3NldF9zaGVsbHNpemUoVFJVRSwgRkFMU0UpOworfQorI2VuZGlmIC8qIGRlZmluZWQoVVNFX0NBUkJPTklaRUQpICovCisKKy8qCisgKiAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KKyAqIE1hY09TIEV2ZW50IEhhbmRsaW5nIHByb2NlZHVyZQorICogLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCisgKi8KKworLyoKKyAqIEhhbmRsZSB0aGUgVXBkYXRlIEV2ZW50CisgKi8KKworICAgIHZvaWQKK2d1aV9tYWNfZG9VcGRhdGVFdmVudChldmVudCkKKyAgICBFdmVudFJlY29yZAkqZXZlbnQ7Cit7CisgICAgV2luZG93UHRyCXdoaWNoV2luZG93OworICAgIEdyYWZQdHIJc2F2ZVBvcnQ7CisgICAgUmduSGFuZGxlCXVwZGF0ZVJnbjsKKyNpZmRlZiBVU0VfQ0FSQk9OSVpFRAorICAgIFJlY3QJdXBkYXRlUmVjdDsKKyNlbmRpZgorICAgIFJlY3QJKnVwZGF0ZVJlY3RQdHI7CisgICAgUmVjdAlyYzsKKyAgICBSZWN0CWdyb3dSZWN0OworICAgIFJnbkhhbmRsZQlzYXZlUmduOworCisKKyNpZmRlZiBVU0VfQ0FSQk9OSVpFRAorICAgIHVwZGF0ZVJnbiA9IE5ld1JnbigpOworICAgIGlmICh1cGRhdGVSZ24gPT0gTlVMTCkKKwlyZXR1cm47CisjZW5kaWYKKworICAgIC8qIFRoaXMgY291bGQgYmUgZG9uZSBieSB0aGUgY2FsbGVyIGFzIHdlCisgICAgICogZG9uJ3QgcmVxdWlyZSBhbnl0aGluZyBlbHNlIG91dCBvZiB0aGUgZXZlbnQKKyAgICAgKi8KKyAgICB3aGljaFdpbmRvdyA9IChXaW5kb3dQdHIpIGV2ZW50LT5tZXNzYWdlOworCisgICAgLyogU2F2ZSBDdXJyZW50IFBvcnQgKi8KKyAgICBHZXRQb3J0ICgmc2F2ZVBvcnQpOworCisgICAgLyogU2VsZWN0IHRoZSBXaW5kb3cncyBQb3J0ICovCisjaWZkZWYgVVNFX0NBUkJPTklaRUQKKyAgICBTZXRQb3J0V2luZG93UG9ydCAod2hpY2hXaW5kb3cpOworI2Vsc2UKKyAgICBTZXRQb3J0ICh3aGljaFdpbmRvdyk7CisjZW5kaWYKKworICAgIC8qIExldCdzIHVwZGF0ZSB0aGUgd2luZG93ICovCisgICAgICBCZWdpblVwZGF0ZSAod2hpY2hXaW5kb3cpOworCS8qIFJlZHJhdyB0aGUgYmlnZ2VzdCByZWN0YW5nbGUgY292ZXJpbmcgdGhlIGFyZWEKKwkgKiB0byBiZSB1cGRhdGVkLgorCSAqLworI2lmZGVmIFVTRV9DQVJCT05JWkVECisJR2V0UG9ydFZpc2libGVSZWdpb24oR2V0V2luZG93UG9ydCh3aGljaFdpbmRvdyksIHVwZGF0ZVJnbik7CisjIGlmIDAKKwkvKiBXb3VsZCBiZSBtb3JlIGFwcHJvcHJpYXRlIHRvIHVzZSB0aGUgZm9sbHdpbmcgYnV0IGRvZXNuJ3QKKwkgKiBzZWVtIHRvIHdvcmsgdW5kZXIgTWFjT1MgWCAoRGFueSkKKwkgKi8KKwlHZXRXaW5kb3dSZWdpb24od2hpY2hXaW5kb3csIGtXaW5kb3dVcGRhdGVSZ24sIHVwZGF0ZVJnbik7CisjIGVuZGlmCisjZWxzZQorCXVwZGF0ZVJnbiA9IHdoaWNoV2luZG93LT52aXNSZ247CisjZW5kaWYKKwkvKiBVc2UgdGhlIEhMb2NrIHVzZWxlc3MgaW4gQ2FyYm9uPyBJcyBpdCBoYXJtZnVsPyovCisJSExvY2sgKChIYW5kbGUpIHVwZGF0ZVJnbik7CisjaWZkZWYgVVNFX0NBUkJPTklaRUQKKwkgIHVwZGF0ZVJlY3RQdHIgPSBHZXRSZWdpb25Cb3VuZHMgKCB1cGRhdGVSZ24sICZ1cGRhdGVSZWN0ICk7CisjIGlmIDAKKwkgIC8qIENvZGUgZnJvbSBvcmlnaW5hbCBDYXJib24gUG9ydCAodXNpbmcgR2V0V2luZG93UmVnaW9uLgorCSAgICogSSBiZWxpZXZlIHRoZSBVcGRhdGVSZ24gaXMgYWxyZWFkeSBpbiBsb2NhbCAoRGFueSkKKwkgICAqLworCSAgR2xvYmFsVG9Mb2NhbCgmdG9wTGVmdCh1cGRhdGVSZWN0KSk7IC8qIHByZUNhcmJvbj8gKi8KKwkgIEdsb2JhbFRvTG9jYWwoJmJvdFJpZ2h0KHVwZGF0ZVJlY3QpKTsKKyMgZW5kaWYKKyNlbHNlCisJICB1cGRhdGVSZWN0UHRyID0gJigqdXBkYXRlUmduKS0+cmduQkJveDsKKyNlbmRpZgorCSAgLyogVXBkYXRlIHRoZSBjb250ZW50IChpLmUuIHRoZSB0ZXh0KSAqLworCSAgZ3VpX3JlZHJhdyh1cGRhdGVSZWN0UHRyLT5sZWZ0LCB1cGRhdGVSZWN0UHRyLT50b3AsCisJCSAgICAgIHVwZGF0ZVJlY3RQdHItPnJpZ2h0IC0gdXBkYXRlUmVjdFB0ci0+bGVmdCwKKwkJICAgICAgdXBkYXRlUmVjdFB0ci0+Ym90dG9tICAgLSB1cGRhdGVSZWN0UHRyLT50b3ApOworCSAgLyogQ2xlYXIgdGhlIGJvcmRlciBhcmVhcyBpZiBuZWVkZWQgKi8KKwkgIGd1aV9tY2hfc2V0X2JnX2NvbG9yKGd1aS5iYWNrX3BpeGVsKTsKKwkgIGlmICh1cGRhdGVSZWN0UHRyLT5sZWZ0IDwgRklMTF9YKDApKQorCSAgeworCSAgICBTZXRSZWN0ICgmcmMsIDAsIDAsIEZJTExfWCgwKSwgRklMTF9ZKFJvd3MpKTsKKwkgICAgRXJhc2VSZWN0ICgmcmMpOworCSAgfQorCSAgaWYgKHVwZGF0ZVJlY3RQdHItPnRvcCA8IEZJTExfWSgwKSkKKwkgIHsKKwkgICAgU2V0UmVjdCAoJnJjLCAwLCAwLCBGSUxMX1goQ29sdW1ucyksIEZJTExfWSgwKSk7CisJICAgIEVyYXNlUmVjdCAoJnJjKTsKKwkgIH0KKwkgIGlmICh1cGRhdGVSZWN0UHRyLT5yaWdodCA+IEZJTExfWChDb2x1bW5zKSkKKwkgIHsKKwkgICAgU2V0UmVjdCAoJnJjLCBGSUxMX1goQ29sdW1ucyksIDAsCisJCQkgICBGSUxMX1goQ29sdW1ucykgKyBndWkuYm9yZGVyX29mZnNldCwgRklMTF9ZKFJvd3MpKTsKKwkgICAgRXJhc2VSZWN0ICgmcmMpOworCSAgfQorCSAgaWYgKHVwZGF0ZVJlY3RQdHItPmJvdHRvbSA+IEZJTExfWShSb3dzKSkKKwkgIHsKKwkgICAgU2V0UmVjdCAoJnJjLCAwLCBGSUxMX1koUm93cyksIEZJTExfWChDb2x1bW5zKSArIGd1aS5ib3JkZXJfb2Zmc2V0LAorCQkJCQkgICAgRklMTF9ZKFJvd3MpICsgZ3VpLmJvcmRlcl9vZmZzZXQpOworCSAgICBFcmFzZVJlY3QgKCZyYyk7CisJICB9CisJSFVubG9jayAoKEhhbmRsZSkgdXBkYXRlUmduKTsKKyNpZmRlZiBVU0VfQ0FSQk9OSVpFRAorCURpc3Bvc2VSZ24gKHVwZGF0ZVJnbik7CisjZW5kaWYKKworCS8qIFVwZGF0ZSBzY3JvbGxiYXJzICovCisJRHJhd0NvbnRyb2xzICh3aGljaFdpbmRvdyk7CisKKwkvKiBVcGRhdGUgdGhlIEdyb3dCb3ggKi8KKwkvKiBUYWtlbiBmcm9tIEZBUSAzMy0yNyAqLworCXNhdmVSZ24gPSBOZXdSZ24oKTsKKyNpZmRlZiBVU0VfQ0FSQk9OSVpFRAorCUdldFdpbmRvd0JvdW5kcyh3aGljaFdpbmRvdywga1dpbmRvd0dyb3dSZ24sICZncm93UmVjdCk7CisjZWxzZQorCWdyb3dSZWN0ID0gd2hpY2hXaW5kb3ctPnBvcnRSZWN0OworCWdyb3dSZWN0LnRvcCAgPSBncm93UmVjdC5ib3R0b20gLSAxNTsKKwlncm93UmVjdC5sZWZ0ID0gZ3Jvd1JlY3QucmlnaHQgIC0gMTU7CisjZW5kaWYKKwlHZXRDbGlwIChzYXZlUmduKTsKKwlDbGlwUmVjdCAoJmdyb3dSZWN0KTsKKwlEcmF3R3Jvd0ljb24gKHdoaWNoV2luZG93KTsKKwlTZXRDbGlwIChzYXZlUmduKTsKKwlEaXNwb3NlUmduIChzYXZlUmduKTsKKyAgICAgIEVuZFVwZGF0ZSAod2hpY2hXaW5kb3cpOworCisgICAgLyogUmVzdG9yZSBvcmlnaW5hbCBQb3J0ICovCisgICAgU2V0UG9ydCAoc2F2ZVBvcnQpOworfQorCisvKgorICogSGFuZGxlIHRoZSBhY3RpdmF0ZS9kZWFjdGl2YXRlIGV2ZW50CisgKiAoYXBwbHkgdG8gYSB3aW5kb3cpCisgKi8KKyAgICB2b2lkCitndWlfbWFjX2RvQWN0aXZhdGVFdmVudChldmVudCkKKyAgICBFdmVudFJlY29yZAkqZXZlbnQ7Cit7CisgICAgV2luZG93UHRyCXdoaWNoV2luZG93OworCisgICAgd2hpY2hXaW5kb3cgPSAoV2luZG93UHRyKSBldmVudC0+bWVzc2FnZTsKKyAgICBpZiAoKGV2ZW50LT5tb2RpZmllcnMpICYgYWN0aXZlRmxhZykKKwkvKiBBY3RpdmF0ZSAqLworCWd1aV9mb2N1c19jaGFuZ2UoVFJVRSk7CisgICAgZWxzZQorICAgIHsKKwkvKiBEZWFjdGl2YXRlICovCisJZ3VpX2ZvY3VzX2NoYW5nZShGQUxTRSk7CisvKglET04nVCBLTk9XIHdoYXQgdGhlIGNvZGUgYmVsb3cgd2FzIGRvaW5nCisJZm91bmQgaW4gdGhlIGRlYWN0aXZhdGUgY2xhdXNlLCBidXQgdGhlCisJY2xhdXNlIHdyaXR0aW5nIFRSVUUgaW50byBpbl9mb2N1cyAoQlVHKQorICovCisKKyNpZiAwCS8qIFJlbW92ZWQgYnkgRGFueSBhcyBwZXIgYWJvdmUgSnVuZSAyMDAxICovCisJYV9ib29sID0gZmFsc2U7CisJU2V0UHJlc2VydmVHbHlwaCAoYV9ib29sKTsKKwlTZXRPdXRsaW5lUHJlZmVycmVkIChhX2Jvb2wpOworI2VuZGlmCisgICAgfQorfQorCisKKy8qCisgKiBIYW5kbGUgdGhlIHN1c3BlbmQvcmVzdW1lIGV2ZW50CisgKiAoYXBwbHkgdG8gdGhlIGFwcGxpY2F0aW9uKQorICovCisgICAgdm9pZAorZ3VpX21hY19kb1N1c3BlbmRFdmVudChldmVudCkKKyAgICBFdmVudFJlY29yZAkqZXZlbnQ7Cit7CisgICAgLyogVGhlIGZyb250bW9zdCBhcHBsaWNhdGlvbiBqdXN0IGNoYW5nZWQgKi8KKworICAgIC8qIE5PVEU6IHRoZSBzdXNwZW5kIG1heSBoYXBwZW4gYmVmb3JlIHRoZSBkZWFjdGl2YXRlCisgICAgICogICAgICAgc2VlbiBvbiBNYWNPUyBYCisgICAgICovCisKKyAgICAvKiBNYXkgbm90IG5lZWQgdG8gY2hhbmdlIGZvY3VzIGFzIHRoZSB3aW5kb3cgd2lsbAorICAgICAqIGdldCBhbiBhY3RpdmF0ZS9kZXNhY3RpdmF0ZSBldmVudAorICAgICAqLworICAgIGlmIChldmVudC0+bWVzc2FnZSAmIDEpCisJLyogUmVzdW1lICovCisJZ3VpX2ZvY3VzX2NoYW5nZShUUlVFKTsKKyAgICBlbHNlCisJLyogU3VzcGVuZCAqLworCWd1aV9mb2N1c19jaGFuZ2UoRkFMU0UpOworfQorCisvKgorICogSGFuZGxlIHRoZSBrZXkKKyAqLworCisgICAgdm9pZAorZ3VpX21hY19kb0tleUV2ZW50KEV2ZW50UmVjb3JkICp0aGVFdmVudCkKK3sKKyAgICAvKiBUT0RPOiBhZGQgc3VwcG9ydCBmb3IgQ09NTUFORCBLRVkgKi8KKyAgICBsb25nCQltZW51OworICAgIHVuc2lnbmVkIGNoYXIJc3RyaW5nWzIwXTsKKyAgICBzaG9ydAkJbnVtLCBpOworICAgIHNob3J0CQlsZW4gPSAwOworICAgIEtleVN5bQkJa2V5X3N5bTsKKyAgICBpbnQJCQlrZXlfY2hhcjsKKyAgICBpbnQJCQltb2RpZmllcnM7CisKKyAgICAvKiBNYXNrIHRoZSBtb3VzZSAoYXMgcGVyIHVzZXIgc2V0dGluZykgKi8KKyAgICBpZiAocF9taCkKKwlPYnNjdXJlQ3Vyc29yKCk7CisKKyAgICAvKiBHZXQgdGhlIGtleSBjb2RlIGFuZCBpdCdzIEFTQ0lJIHJlcHJlc2VudGF0aW9uICovCisgICAga2V5X3N5bSA9ICgodGhlRXZlbnQtPm1lc3NhZ2UgJiBrZXlDb2RlTWFzaykgPj4gOCk7CisgICAga2V5X2NoYXIgPSB0aGVFdmVudC0+bWVzc2FnZSAmIGNoYXJDb2RlTWFzazsKKyAgICBudW0gPSAxOworCisgICAgLyogSW50ZXJjZXB0IENUUkwtQyAqLworICAgIGlmICh0aGVFdmVudC0+bW9kaWZpZXJzICYgY29udHJvbEtleSkKKwlpZiAoa2V5X2NoYXIgPT0gQ3RybF9DICYmIGN0cmxfY19pbnRlcnJ1cHRzKQorCSAgICBnb3RfaW50ID0gVFJVRTsKKworICAgIC8qIEludGVyY2VwdCBDTUQtLiAqLworICAgIGlmICh0aGVFdmVudC0+bW9kaWZpZXJzICYgY21kS2V5KQorCWlmIChrZXlfY2hhciA9PSAnLicpCisJICAgIGdvdF9pbnQgPSBUUlVFOworCisgICAgLyogSGFuZGxlIGNvbW1hbmQga2V5IGFzIHBlciBtZW51ICovCisgICAgLyogVE9ETzogc2hvdWxkIG92ZXJyaWRlIGJlIGFsbG93ZWQ/IFJlcXVpcmUgWUFPIG9yIGNvdWxkIHVzZSAnd2luYWx0a2V5JyAqLworICAgIGlmICh0aGVFdmVudC0+bW9kaWZpZXJzICYgY21kS2V5KQorCS8qIE9ubHkgYWNjZXB0IENNRCBhbG9uZSBvciB3aXRoIENBUExPQ0tTIGFuZCB0aGUgbW91c2UgYnV0dG9uLgorCSAqIFdoeSB0aGUgbW91c2UgYnV0dG9uPyAqLworCWlmICgodGhlRXZlbnQtPm1vZGlmaWVycyAmICh+KGNtZEtleSB8IGJ0blN0YXRlIHwgYWxwaGFMb2NrKSkpID09IDApCisJeworCSAgICBtZW51ID0gTWVudUtleShrZXlfY2hhcik7CisJICAgIGlmIChIaVdvcmQobWVudSkpCisJICAgIHsKKwkJZ3VpX21hY19oYW5kbGVfbWVudShtZW51KTsKKwkJcmV0dXJuOworCSAgICB9CisJfQorCisgICAgLyogQ29udmVydCB0aGUgbW9kaWZpZXJzICovCisgICAgbW9kaWZpZXJzID0gRXZlbnRNb2RpZmllcnMyVmltTW9kaWZpZXJzKHRoZUV2ZW50LT5tb2RpZmllcnMpOworCisKKyAgICAvKiBIYW5kbGUgc3BlY2lhbCBrZXlzLiAqLworI2lmIDAKKyAgICAvKiBXaHkgaGF2ZSB0aGlzIGJlZW4gcmVtb3ZlZD8gKi8KKyAgICBpZgkoISh0aGVFdmVudC0+bW9kaWZpZXJzICYgKGNtZEtleSB8IGNvbnRyb2xLZXkgfCByaWdodENvbnRyb2xLZXkpKSkKKyNlbmRpZgorICAgIHsKKwkvKiBGaW5kIHRoZSBzcGVjaWFsIGtleSAoZm9yIG5vbi1wcmludGFibGUga2V5dF9jaGFyKSAqLworCWlmICAoKGtleV9jaGFyIDwgMHgyMCkgfHwgKGtleV9jaGFyID09IDB4N2YpKQorCSAgICBmb3IgKGkgPSAwOyBzcGVjaWFsX2tleXNbaV0ua2V5X3N5bSAhPSAoS2V5U3ltKTA7IGkrKykKKwkJaWYgKHNwZWNpYWxfa2V5c1tpXS5rZXlfc3ltID09IGtleV9zeW0pCisJCXsKKyMgaWYgMAorCQkgICAgLyogV2UgY3VycmVudGx5IGRvbid0IGhhdmUgbm90IHNvIHNwZWNpYWwga2V5ICovCisJCSAgICBpZiAoc3BlY2lhbF9rZXlzW2ldLnZpbV9jb2RlMSA9PSBOVUwpCisJCQlrZXlfY2hhciA9IHNwZWNpYWxfa2V5c1tpXS52aW1fY29kZTA7CisJCSAgICBlbHNlCisjIGVuZGlmCisJCQlrZXlfY2hhciA9IFRPX1NQRUNJQUwoIHNwZWNpYWxfa2V5c1tpXS52aW1fY29kZTAsCisJCQkJCQlzcGVjaWFsX2tleXNbaV0udmltX2NvZGUxICk7CisJCSAgICBrZXlfY2hhciA9IHNpbXBsaWZ5X2tleShrZXlfY2hhciwmbW9kaWZpZXJzKTsKKwkJICAgIGJyZWFrOworCQl9CisgICAgfQorCisKKyAgICAvKiBBZGQgdGhlIG1vZGlmaWVyIHRvIHRoZSBpbnB1dCBidSBpZiBuZWVkZWQgKi8KKyAgICAvKiBEbyBub3Qgd2FudCBTSElGVC1BIG9yIENUUkwtQSB3aXRoIG1vZGlmaWVyICovCisgICAgaWYgKCFJU19TUEVDSUFMKGtleV9jaGFyKQorCSAgICAmJiBrZXlfc3ltICE9IHZrX1NwYWNlCisJICAgICYmIGtleV9zeW0gIT0gdmtfVGFiCisJICAgICYmIGtleV9zeW0gIT0gdmtfUmV0dXJuCisJICAgICYmIGtleV9zeW0gIT0gdmtfRW50ZXIKKwkgICAgJiYga2V5X3N5bSAhPSB2a19Fc2MpCisgICAgeworI2lmIDEKKyAgICAvKiBDbGVhciBtb2RpZmllcnMgd2hlbiBvbmx5IG9uZSBtb2RpZmllciBpcyBzZXQgKi8KKwlpZiggKG1vZGlmaWVycyA9PSBNT0RfTUFTS19TSElGVCkgfHwKKwkgICAgKG1vZGlmaWVycyA9PSBNT0RfTUFTS19DVFJMKSAgfHwKKwkgICAgKG1vZGlmaWVycyA9PSBNT0RfTUFTS19BTFQpKQorCSAgICBtb2RpZmllcnMgPSAwOworI2Vsc2UKKwlpZiggbW9kaWZpZXJzICYgTU9EX01BU0tfQ1RSTCkKKwkgICAgbW9kaWZpZXJzID0gbW9kaWZpZXJzICYgfk1PRF9NQVNLX0NUUkw7CisJaWYoIG1vZGlmaWVycyAmIE1PRF9NQVNLX0FMVCkKKwkgICAgbW9kaWZpZXJzID0gbW9kaWZpZXJzICYgfk1PRF9NQVNLX0FMVDsKKwlpZiggbW9kaWZpZXJzICYgTU9EX01BU0tfU0hJRlQpCisJICAgIG1vZGlmaWVycyA9IG1vZGlmaWVycyAmIH5NT0RfTUFTS19TSElGVDsKKyNlbmRpZgorICAgIH0KKwlpZiggbW9kaWZpZXJzICkKKwl7CisJICAgIHN0cmluZ1sgbGVuKysgXSA9IENTSTsKKwkgICAgc3RyaW5nWyBsZW4rKyBdID0gS1NfTU9ESUZJRVI7CisJICAgIHN0cmluZ1sgbGVuKysgXSA9IG1vZGlmaWVyczsKKwl9CisKKwlpZiggSVNfU1BFQ0lBTCgga2V5X2NoYXIgKSApCisJeworCSAgICBzdHJpbmdbIGxlbisrIF0gPSBDU0k7CisJICAgIHN0cmluZ1sgbGVuKysgXSA9IEtfU0VDT05EKCBrZXlfY2hhciApOworCSAgICBzdHJpbmdbIGxlbisrIF0gPSBLX1RISVJEKCBrZXlfY2hhciApOworCX0KKwllbHNlCisJeworI2lmZGVmIEZFQVRfTUJZVEUKKwkgICAgaWYgKGlucHV0X2NvbnYudmNfdHlwZSAhPSBDT05WX05PTkUpCisJICAgIHsKKwkJY2hhcl91CWZyb21bMl0sICp0bzsKKwkJaW50CWw7CisKKwkJZnJvbVswXSA9IGtleV9jaGFyOworCQlmcm9tWzFdID0gTlVMOworCQlsID0gMTsKKwkJdG8gPSBzdHJpbmdfY29udmVydCgmaW5wdXRfY29udiwgZnJvbSwgJmwpOworCQlpZiAodG8gIT0gTlVMTCkKKwkJeworCQkgICAgZm9yIChpID0gMDsgaSA8IGwgJiYgbGVuIDwgMTk7IGkrKykKKwkJICAgIHsKKwkJCWlmICh0b1tpXSA9PSBDU0kpCisJCQl7CisJCQkgICAgc3RyaW5nW2xlbisrXSA9IEtTX0VYVFJBOworCQkJICAgIHN0cmluZ1tsZW4rK10gPSBLRV9DU0k7CisJCQl9CisJCQllbHNlCisJCQkgICAgc3RyaW5nW2xlbisrXSA9IHRvW2ldOworCQkgICAgfQorCQkgICAgdmltX2ZyZWUodG8pOworCQl9CisJCWVsc2UKKwkJICAgIHN0cmluZ1tsZW4rK10gPSBrZXlfY2hhcjsKKwkgICAgfQorCSAgICBlbHNlCisjZW5kaWYKKwkJc3RyaW5nW2xlbisrXSA9IGtleV9jaGFyOworCX0KKworCWlmIChsZW4gPT0gMSAmJiBzdHJpbmdbMF0gPT0gQ1NJKQorCXsKKwkgICAgLyogVHVybiBDU0kgaW50byBLX0NTSS4gKi8KKwkgICAgc3RyaW5nWyBsZW4rKyBdID0gS1NfRVhUUkE7CisJICAgIHN0cmluZ1sgbGVuKysgXSA9IEtFX0NTSTsKKwl9CisKKyAgICBhZGRfdG9faW5wdXRfYnVmKHN0cmluZywgbGVuKTsKK30KKworLyoKKyAqIEhhbmRsZSBNb3VzZUNsaWNrCisgKi8KKyAgICB2b2lkCitndWlfbWFjX2RvTW91c2VEb3duRXZlbnQgKHRoZUV2ZW50KQorICAgIEV2ZW50UmVjb3JkICp0aGVFdmVudDsKK3sKKyAgICBzaG9ydAkJdGhlUGFydDsKKyAgICBXaW5kb3dQdHIJCXdoaWNoV2luZG93OworCisgICAgdGhlUGFydCA9IEZpbmRXaW5kb3cgKHRoZUV2ZW50LT53aGVyZSwgJndoaWNoV2luZG93KTsKKworICAgIHN3aXRjaCAodGhlUGFydCkKKyAgICB7CisJY2FzZSAoaW5EZXNrKToKKwkgICAgLyogVE9ETzogd2hhdCB0byBkbz8gKi8KKwkgICAgYnJlYWs7CisKKwljYXNlIChpbk1lbnVCYXIpOgorCSAgICBndWlfbWFjX2hhbmRsZV9tZW51KE1lbnVTZWxlY3QgKHRoZUV2ZW50LT53aGVyZSkpOworCSAgICBicmVhazsKKworCWNhc2UgKGluQ29udGVudCk6CisJICAgIGd1aV9tYWNfZG9JbkNvbnRlbnRDbGljayAodGhlRXZlbnQsIHdoaWNoV2luZG93KTsKKwkgICAgYnJlYWs7CisKKwljYXNlIChpbkRyYWcpOgorCSAgICBndWlfbWFjX2RvSW5EcmFnQ2xpY2sgKHRoZUV2ZW50LT53aGVyZSwgd2hpY2hXaW5kb3cpOworCSAgICBicmVhazsKKworCWNhc2UgKGluR3Jvdyk6CisJICAgIGd1aV9tYWNfZG9Jbkdyb3dDbGljayAodGhlRXZlbnQtPndoZXJlLCB3aGljaFdpbmRvdyk7CisJICAgIGJyZWFrOworCisJY2FzZSAoaW5Hb0F3YXkpOgorCSAgICBpZiAoVHJhY2tHb0F3YXkod2hpY2hXaW5kb3csIHRoZUV2ZW50LT53aGVyZSkpCisJCWd1aV9zaGVsbF9jbG9zZWQoKTsKKwkgICAgYnJlYWs7CisKKwljYXNlIChpblpvb21Jbik6CisJY2FzZSAoaW5ab29tT3V0KToKKyNpZmRlZiBVU0VfQ0FSQk9OSVpFRAorCSAgICBndWlfbWFjX2RvSW5ab29tQ2xpY2sodGhlRXZlbnQsIHdoaWNoV2luZG93KTsKKyNlbmRpZgorCSAgICBicmVhazsKKyAgICB9Cit9CisKKy8qCisgKiBIYW5kbGUgTW91c2VNb3ZlZAorICogW3RoaXMgZXZlbnQgaXMgYSBtb3ZpbmcgaW4gYW5kIG91dCBvZiBhIHJlZ2lvbl0KKyAqLworICAgIHZvaWQKK2d1aV9tYWNfZG9Nb3VzZU1vdmVkRXZlbnQgKGV2ZW50KQorICAgIEV2ZW50UmVjb3JkICpldmVudDsKK3sKKyAgICBQb2ludCAgIHRoZVBvaW50OworICAgIGludF91ICAgdmltTW9kaWZpZXJzOworCisgICAgdGhlUG9pbnQgPSBldmVudC0+d2hlcmU7CisgICAgR2xvYmFsVG9Mb2NhbCAoJnRoZVBvaW50KTsKKyAgICB2aW1Nb2RpZmllcnMgPSBFdmVudE1vZGlmaWVyczJWaW1Nb3VzZU1vZGlmaWVycyhldmVudC0+bW9kaWZpZXJzKTsKKworICAgIGlmICghQnV0dG9uKCkpCisJZ3VpX21vdXNlX21vdmVkICh0aGVQb2ludC5oLCB0aGVQb2ludC52KTsKKyAgICBlbHNlCisjaWZkZWYgVVNFX0NUUkxDTElDS01FTlUKKwlpZiAoIWNsaWNrSXNQb3B1cCkKKyNlbmRpZgorCSAgICBndWlfc2VuZF9tb3VzZV9ldmVudChNT1VTRV9EUkFHLCB0aGVQb2ludC5oLAorCQkJCQkgICAgIHRoZVBvaW50LnYsIEZBTFNFLCB2aW1Nb2RpZmllcnMpOworCisgICAgLyogUmVzZXQgdGhlIHJlZ2lvbiBmcm9tIHdoaWNoIHdlIG1vdmUgaW4gYW5kIG91dCAqLworICAgIFNldFJlY3QgKCZkcmFnUmVjdCwgRklMTF9YKFhfMl9DT0wodGhlUG9pbnQuaCkpLAorCQkJRklMTF9ZKFlfMl9ST1codGhlUG9pbnQudikpLAorCQkJRklMTF9YKFhfMl9DT0wodGhlUG9pbnQuaCkrMSksCisJCQlGSUxMX1koWV8yX1JPVyh0aGVQb2ludC52KSsxKSk7CisKKyAgICBpZiAoZHJhZ1JlY3RFbmJsKQorCWRyYWdSZWN0Q29udHJvbCA9IGtDcmVhdGVSZWN0OworCit9CisKKy8qCisgKiBIYW5kbGUgdGhlIG1vdXNlIHJlbGVhc2UKKyAqLworICAgIHZvaWQKK2d1aV9tYWNfZG9Nb3VzZVVwRXZlbnQgKHRoZUV2ZW50KQorICAgIEV2ZW50UmVjb3JkICp0aGVFdmVudDsKK3sKKyAgICBQb2ludCAgIHRoZVBvaW50OworICAgIGludF91ICAgdmltTW9kaWZpZXJzOworCisgICAgLyogVE9ETzogUHJvcGVybHkgY29udmVydCB0aGUgQ29udGV4dHVhbCBtZW51IG1vdXNlLXVwICovCisgICAgLyogICAgICAgUG90ZW50aWFsIHNvdXJjZSBvZiB0aGUgZG91YmxlIG1lbnUgKi8KKyAgICBsYXN0TW91c2VUaWNrID0gdGhlRXZlbnQtPndoZW47CisgICAgZHJhZ1JlY3RFbmJsID0gRkFMU0U7CisgICAgZHJhZ1JlY3RDb250cm9sID0ga0NyZWF0ZUVtcHR5OworICAgIHRoZVBvaW50ID0gdGhlRXZlbnQtPndoZXJlOworICAgIEdsb2JhbFRvTG9jYWwgKCZ0aGVQb2ludCk7CisKKyAgICB2aW1Nb2RpZmllcnMgPSBFdmVudE1vZGlmaWVyczJWaW1Nb3VzZU1vZGlmaWVycyh0aGVFdmVudC0+bW9kaWZpZXJzKTsKKyNpZmRlZiBVU0VfQ1RSTENMSUNLTUVOVQorICAgIGlmIChjbGlja0lzUG9wdXApCisgICAgeworCXZpbU1vZGlmaWVycyAmPSB+TU9VU0VfQ1RSTDsKKwljbGlja0lzUG9wdXAgPSBGQUxTRTsKKyAgICB9CisjZW5kaWYKKyAgICBndWlfc2VuZF9tb3VzZV9ldmVudAorICAgICAgKE1PVVNFX1JFTEVBU0UsIHRoZVBvaW50LmgsIHRoZVBvaW50LnYsIEZBTFNFLCB2aW1Nb2RpZmllcnMpOworfQorCisjaWZkZWYgVVNFX01PVVNFV0hFRUwKKyAgICBzdGF0aWMgcGFzY2FsIE9TU3RhdHVzCitndWlfbWFjX21vdXNlX3doZWVsKEV2ZW50SGFuZGxlckNhbGxSZWYgbmV4dEhhbmRsZXIsIEV2ZW50UmVmIHRoZUV2ZW50LAorCQkJCQkJCQkgICB2b2lkICpkYXRhKQoreworICAgIEV2ZW50UmVmCWJvZ3VzRXZlbnQ7CisgICAgUG9pbnQJcG9pbnQ7CisgICAgUmVjdAlib3VuZHM7CisgICAgVUludDMyCW1vZDsKKyAgICBTSW50MzIJZGVsdGE7CisgICAgaW50X3UJdmltX21vZDsKKworICAgIGlmIChub0VyciAhPSBHZXRFdmVudFBhcmFtZXRlcih0aGVFdmVudCwga0V2ZW50UGFyYW1Nb3VzZVdoZWVsRGVsdGEsCisJCQkgICAgICB0eXBlU0ludDMyLCBOVUxMLCBzaXplb2YoU0ludDMyKSwgTlVMTCwgJmRlbHRhKSkKKwlnb3RvIGJhaWw7CisgICAgaWYgKG5vRXJyICE9IEdldEV2ZW50UGFyYW1ldGVyKHRoZUV2ZW50LCBrRXZlbnRQYXJhbU1vdXNlTG9jYXRpb24sCisJCQkgICAgICB0eXBlUURQb2ludCwgTlVMTCwgc2l6ZW9mKFBvaW50KSwgTlVMTCwgJnBvaW50KSkKKwlnb3RvIGJhaWw7CisgICAgaWYgKG5vRXJyICE9IEdldEV2ZW50UGFyYW1ldGVyKHRoZUV2ZW50LCBrRXZlbnRQYXJhbUtleU1vZGlmaWVycywKKwkJCQl0eXBlVUludDMyLCBOVUxMLCBzaXplb2YoVUludDMyKSwgTlVMTCwgJm1vZCkpCisJZ290byBiYWlsOworCisgICAgdmltX21vZCA9IDA7CisgICAgaWYgKG1vZCAmIHNoaWZ0S2V5KQorCXZpbV9tb2QgfD0gTU9VU0VfU0hJRlQ7CisgICAgaWYgKG1vZCAmIGNvbnRyb2xLZXkpCisJdmltX21vZCB8PSBNT1VTRV9DVFJMOworICAgIGlmIChtb2QgJiBvcHRpb25LZXkpCisJdmltX21vZCB8PSBNT1VTRV9BTFQ7CisKKyAgICAvKiBwb3N0IGEgYm9ndXMgZXZlbnQgdG8gd2FrZSB1cCBXYWl0TmV4dEV2ZW50ICovCisgICAgaWYgKG5vRXJyICE9IENyZWF0ZUV2ZW50KE5VTEwsIGtFdmVudENsYXNzTW91c2UsIGtFdmVudE1vdXNlTW92ZWQsIDAsCisJCQkJCSAgICBrRXZlbnRBdHRyaWJ1dGVOb25lLCAmYm9ndXNFdmVudCkpCisJZ290byBiYWlsOworICAgIGlmIChub0VyciAhPSBQb3N0RXZlbnRUb1F1ZXVlKEdldE1haW5FdmVudFF1ZXVlKCksIGJvZ3VzRXZlbnQsCisJCQkJCQkJICAga0V2ZW50UHJpb3JpdHlMb3cpKQorCWdvdG8gYmFpbDsKKworICAgIGlmIChub0VyciA9PSBHZXRXaW5kb3dCb3VuZHMoZ3VpLlZpbVdpbmRvdywga1dpbmRvd0NvbnRlbnRSZ24sICZib3VuZHMpKQorICAgIHsKKwlwb2ludC5oIC09IGJvdW5kcy5sZWZ0OworCXBvaW50LnYgLT0gYm91bmRzLnRvcDsKKyAgICB9CisKKyAgICBndWlfc2VuZF9tb3VzZV9ldmVudCgoZGVsdGEgPiAwKSA/IE1PVVNFXzQgOiBNT1VTRV81LAorCQkJCQkgICAgcG9pbnQuaCwgcG9pbnQudiwgRkFMU0UsIHZpbV9tb2QpOworCisgICAgcmV0dXJuIG5vRXJyOworCisgIGJhaWw6CisgICAgLyoKKyAgICAgKiB3aGVuIHdlIGZhaWwgZ2l2ZSBhbnkgYWRkaXRpb25hbCBjYWxsYmFjayBoYW5kbGVyIGEgY2hhbmNlIHRvIHBlcmZvcm0KKyAgICAgKiBpdCdzIGFjdGlvbnMKKyAgICAgKi8KKyAgICByZXR1cm4gQ2FsbE5leHRFdmVudEhhbmRsZXIobmV4dEhhbmRsZXIsIHRoZUV2ZW50KTsKK30KKyNlbmRpZiAvKiBkZWZpbmVkKFVTRV9NT1VTRVdIRUVMKSAqLworCisjaWYgMAorCisvKgorICogVGhpcyB3b3VsZCBiZSB0aGUgbm9ybWFsIHdheSBvZiBpbnZva2luZyB0aGUgY29udGV4dHVhbCBtZW51CisgKiBidXQgdGhlIFZpbSBBUEkgZG9lc24ndCBzZWVtIHRvIGEgc3VwcG9ydCBhIHJlcXVlc3QgdG8gZ2V0CisgKiB0aGUgbWVudSB0aGF0IHdlIHNob3VsZCBkaXNwbGF5CisgKi8KKyAgICB2b2lkCitndWlfbWFjX2hhbmRsZV9jb250ZXh0dWFsX21lbnUoZXZlbnQpCisgICAgRXZlbnRSZWNvcmQgKmV2ZW50OworeworLyoKKyAqICBDbG9uZSBQb3BVcCB0byB1c2UgbWVudQorICogIENyZWF0ZSBhIG9iamVjdCBkZXNjcmlwdG9yIGZvciB0aGUgY3VycmVudCBzZWxlY3Rpb24KKyAqICBDYWxsIHRoZSBwcm9jZWR1cmUKKyAqLworCisvLyAgQ2FsbCB0byBIYW5kbGUgUG9wdXAKKyAgICBPU1N0YXR1cyBzdGF0dXMgPSBDb250ZXh0dWFsTWVudVNlbGVjdChDbnR4TWVudSwgZXZlbnQtPndoZXJlLCBmYWxzZSwga0NNSGVscEl0ZW1Ob0hlbHAsICIiLCBOVUxMLCAmQ250eFR5cGUsICZDbnR4TWVudUlELCAmQ250eE1lbnVJdGVtKTsKKworICAgIGlmIChzdGF0dXMgIT0gbm9FcnIpCisJcmV0dXJuOworCisgICAgaWYgKENudHhUeXBlID09IGtDTU1lbnVJdGVtU2VsZWN0ZWQpCisgICAgeworCS8qIEhhbmRsZSB0aGUgbWVudSBDbnR4TWVudUlELCBDbnR4TWVudUl0ZW0gKi8KKwkvKiBUaGUgc3VibWVudSBjYW4gYmUgaGFuZGxlIGRpcmVjdGx5IGJ5IGd1aV9tYWNfaGFuZGxlX21lbnUgKi8KKwkvKiBCdXQgd2hhdCBhYm91dCB0aGUgY3VycmVudCBtZW51LCBpcyB0aGUgbWVueSBjaGFuZ2VkIGJ5IENvbnRleHR1YWxNZW51U2VsZWN0ICovCisJZ3VpX21hY19oYW5kbGVfbWVudSAoKENudHhNZW51SUQgPDwgMTYpICsgQ250eE1lbnVJdGVtKTsKKyAgICB9CisgICAgZWxzZSBpZiAoQ250eE1lbnVJRCA9PSBrQ01TaG93SGVscFNlbGVjdGVkKQorICAgIHsKKwkvKiBTaG91bGQgY29tZSB1cCB3aXRoIHRoZSBoZWxwICovCisgICAgfQorCit9CisjZW5kaWYKKworLyoKKyAqIEhhbmRsZSBtZW51YmFyIHNlbGVjdGlvbgorICovCisgICAgdm9pZAorZ3VpX21hY19oYW5kbGVfbWVudShtZW51Q2hvaWNlKQorICAgIGxvbmcgbWVudUNob2ljZTsKK3sKKyAgICBzaG9ydAltZW51ID0gSGlXb3JkKG1lbnVDaG9pY2UpOworICAgIHNob3J0CWl0ZW0gPSBMb1dvcmQobWVudUNob2ljZSk7CisgICAgdmltbWVudV9UCSp0aGVWaW1NZW51ID0gcm9vdF9tZW51OworI2lmbmRlZiBVU0VfQ0FSQk9OSVpFRAorICAgIE1lbnVIYW5kbGUJYXBwbGVNZW51OworICAgIFN0cjI1NQlpdGVtTmFtZTsKKyNlbmRpZgorCisgICAgaWYgKG1lbnUgPT0gMjU2KSAgLyogVE9ETzogdXNlIGNvbnN0YW50IG9yIGd1aS54eXogKi8KKyAgICB7CisJaWYgKGl0ZW0gPT0gMSkKKwkgICAgZ3VpX21jaF9iZWVwKCk7IC8qIFRPRE86IFBvcHVwIGRpYWxvZyBvciBkbyA6aW50cm8gKi8KKwllbHNlCisJeworI2lmbmRlZiBVU0VfQ0FSQk9OSVpFRAorCSAgICAvKiBEZXNrIEFjY2Vzc29yeSBkb2Vzbid0IGV4aXN0IGluIENhcmJvbiAqLworCSAgICBhcHBsZU1lbnUgPSBHZXRNZW51SGFuZGxlIChtZW51KTsKKwkgICAgR2V0TWVudUl0ZW1UZXh0IChhcHBsZU1lbnUsIGl0ZW0sIGl0ZW1OYW1lKTsKKwkgICAgKHZvaWQpIE9wZW5EZXNrQWNjIChpdGVtTmFtZSk7CisjZW5kaWYKKwl9CisgICAgfQorICAgIGVsc2UgaWYgKGl0ZW0gIT0gMCkKKyAgICB7CisJdGhlVmltTWVudSA9IGd1aV9tYWNfZ2V0X3ZpbV9tZW51KG1lbnUsIGl0ZW0sIHJvb3RfbWVudSk7CisKKwlpZiAodGhlVmltTWVudSkKKwkgICAgZ3VpX21lbnVfY2IodGhlVmltTWVudSk7CisgICAgfQorICAgIEhpbGl0ZU1lbnUgKDApOworfQorCisvKgorICogRGlzcGF0Y2ggdGhlIGV2ZW50IHRvIHByb3BlciBoYW5kbGVyCisgKi8KKworICAgIHZvaWQKK2d1aV9tYWNfaGFuZGxlX2V2ZW50IChldmVudCkKKyAgICBFdmVudFJlY29yZCAqZXZlbnQ7Cit7CisgICAgT1NFcnIJZXJyb3I7CisKKyAgICAvKiBIYW5kbGUgY29udGV4dHVhbCBtZW51IHJpZ2h0IG5vdyAoaWYgbmVlZGVkKSAqLworI2lmZGVmIFVTRV9DVFJMQ0xJQ0tNRU5VCisgICAgaWYgKGd1aS5NYWNPU0hhdmVDbnR4TWVudSkKKwlpZiAoSXNTaG93Q29udGV4dHVhbE1lbnVDbGljayhldmVudCkpCisJeworIyBpZiAwCisJICAgIGd1aV9tYWNfaGFuZGxlX2NvbnRleHR1YWxfbWVudShldmVudCk7CisjIGVsc2UKKwkgICAgZ3VpX21hY19kb01vdXNlRG93bkV2ZW50KGV2ZW50KTsKKyMgZW5kaWYKKwkgICAgcmV0dXJuOworCX0KKyNlbmRpZgorCisgICAgLyogSGFuZGxlIG5vcm1hbCBldmVudCAqLworICAgIHN3aXRjaCAoZXZlbnQtPndoYXQpCisgICAgeworCWNhc2UgKGtleURvd24pOgorCWNhc2UgKGF1dG9LZXkpOgorCSAgICBndWlfbWFjX2RvS2V5RXZlbnQgKGV2ZW50KTsKKwkgICAgYnJlYWs7CisKKwljYXNlIChrZXlVcCk6CisJICAgIC8qIFdlIGRvbid0IGNhcmUgYWJvdXQgd2hlbiB0aGUga2V5IGdldCByZWxlYXNlICovCisJICAgIGJyZWFrOworCisJY2FzZSAobW91c2VEb3duKToKKwkgICAgZ3VpX21hY19kb01vdXNlRG93bkV2ZW50KGV2ZW50KTsKKwkgICAgYnJlYWs7CisKKwljYXNlIChtb3VzZVVwKToKKwkgICAgZ3VpX21hY19kb01vdXNlVXBFdmVudChldmVudCk7CisJICAgIGJyZWFrOworCisJY2FzZSAodXBkYXRlRXZ0KToKKwkgICAgZ3VpX21hY19kb1VwZGF0ZUV2ZW50IChldmVudCk7CisJICAgIGJyZWFrOworCisJY2FzZSAoZGlza0V2dCk6CisJICAgIC8qIFdlIGRvbid0IG5lZWQgc3BlY2lhbCBoYW5kbGluZyBmb3IgZGlzayBpbnNlcnRpb24gKi8KKwkgICAgYnJlYWs7CisKKwljYXNlIChhY3RpdmF0ZUV2dCk6CisJICAgIGd1aV9tYWNfZG9BY3RpdmF0ZUV2ZW50IChldmVudCk7CisJICAgIGJyZWFrOworCisJY2FzZSAob3NFdnQpOgorCSAgICBzd2l0Y2ggKChldmVudC0+bWVzc2FnZSA+PiAyNCkgJiAweEZGKQorCSAgICB7CisJCWNhc2UgKDB4RkEpOiAvKiBtb3VzZU1vdmVkTWVzc2FnZSAqLworCQkgICAgZ3VpX21hY19kb01vdXNlTW92ZWRFdmVudCAoZXZlbnQpOworCQkgICAgYnJlYWs7CisJCWNhc2UgKDB4MDEpOiAvKiBzdXNwZW5kUmVzdW1lTWVzc2FnZSAqLworCQkgICAgZ3VpX21hY19kb1N1c3BlbmRFdmVudCAoZXZlbnQpOworCQkgICAgYnJlYWs7CisJICAgIH0KKwkgICAgYnJlYWs7CisKKyNpZmRlZiBVU0VfQUVWRU5UCisJY2FzZSAoa0hpZ2hMZXZlbEV2ZW50KToKKwkgICAgLyogU29tZW9uZSdzIHRhbGtpbmcgdG8gdXMsIHRocm91Z2ggQXBwbGVFdmVudHMgKi8KKwkgICAgZXJyb3IgPSBBRVByb2Nlc3NBcHBsZUV2ZW50KGV2ZW50KTsgLyogVE9ETzogRXJyb3IgSGFuZGxpbmcgKi8KKwkgICAgYnJlYWs7CisjZW5kaWYKKyAgICB9Cit9CisKKy8qCisgKiAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KKyAqIFVua25vd24gU3R1ZmYKKyAqIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQorICovCisKKworICAgIEd1aUZvbnQKK2d1aV9tYWNfZmluZF9mb250IChmb250X25hbWUpCisgICAgY2hhcl91ICpmb250X25hbWU7Cit7CisgICAgY2hhcl91CWM7CisgICAgY2hhcl91CSpwOworICAgIGNoYXJfdQlwRm9udE5hbWVbMjU2XTsKKyAgICBTdHIyNTUJc3lzdGVtRm9udG5hbWU7CisgICAgc2hvcnQJZm9udF9pZDsKKyAgICBzaG9ydAlzaXplPTk7CisgICAgR3VpRm9udAlmb250OworI2lmIDAKKyAgICBjaGFyX3UgICAgICAqZm9udE5hbWVQdHI7CisjZW5kaWYKKworICAgIGZvciAocCA9IGZvbnRfbmFtZTsgKCgqcCAhPSAwKSAmJiAoKnAgIT0gJzonKSk7IHArKykKKwk7CisKKyAgICBjID0gKnA7CisgICAgKnAgPSAwOworCisjaWYgMQorICAgIFNUUkNQWSgmcEZvbnROYW1lWzFdLCBmb250X25hbWUpOworICAgIHBGb250TmFtZVswXSA9IFNUUkxFTihmb250X25hbWUpOworICAgICpwID0gYzsKKworICAgIEdldEZOdW0gKHBGb250TmFtZSwgJmZvbnRfaWQpOworI2Vsc2UKKyAgICAvKiBuYW1lID0gQzJQYXNjYWxfc2F2ZShtZW51LT5kbmFtZSk7ICovCisgICAgZm9udE5hbWVQdHIgPSBDMlBhc2NhbF9zYXZlX2FuZF9yZW1vdmVfYmFja3NsYXNoKGZvbnRfbmFtZSk7CisKKyAgICBHZXRGTnVtIChmb250TmFtZVB0ciwgJmZvbnRfaWQpOworI2VuZGlmCisKKworICAgIGlmIChmb250X2lkID09IDApCisgICAgeworCS8qIE91cHMsIHRoZSBzeXN0ZW0gZm9udCB3YXMgaXQgdGhlIG9uZSB0aGUgdXNlciB3YW50ICovCisKKwlHZXRGb250TmFtZSAoMCwgc3lzdGVtRm9udG5hbWUpOworCWlmICghRXF1YWxTdHJpbmcocEZvbnROYW1lLCBzeXN0ZW1Gb250bmFtZSwgZmFsc2UsIGZhbHNlKSkKKwkgICAgcmV0dXJuIE5PRk9OVDsKKyAgICB9CisgICAgaWYgKCpwID09ICc6JykKKyAgICB7CisJcCsrOworCS8qIFNldCB0aGUgdmFsdWVzIGZvdW5kIGFmdGVyICc6JyAqLworCXdoaWxlICgqcCkKKwl7CisJICAgIHN3aXRjaCAoKnArKykKKwkgICAgeworCQljYXNlICdoJzoKKwkJICAgIHNpemUgPSBwb2ludHNfdG9fcGl4ZWxzKHAsICZwLCBUUlVFKTsKKwkJICAgIGJyZWFrOworCQkgICAgLyoKKwkJICAgICAqIFRPRE86IE1heWJlIGFjY2VwdCB3aWR0aCBhbmQgc3R5bGVzCisJCSAgICAgKi8KKwkgICAgfQorCSAgICB3aGlsZSAoKnAgPT0gJzonKQorCQlwKys7CisJfQorICAgIH0KKworICAgIGlmIChzaXplIDwgMSkKKwlzaXplID0gMTsgICAvKiBBdm9pZCBoYXZpbmcgYSBzaXplIG9mIDAgd2l0aCBzeXN0ZW0gZm9udCAqLworCisgICAgZm9udCA9IChzaXplIDw8IDE2KSArICgobG9uZykgZm9udF9pZCAmIDB4RkZGRik7CisKKyAgICByZXR1cm4gZm9udDsKK30KKworLyoKKyAqIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQorICogR1VJX01DSCBmdW5jdGlvbm5hbGl0eQorICogLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCisgKi8KKworLyoKKyAqIFBhcnNlIHRoZSBHVUkgcmVsYXRlZCBjb21tYW5kLWxpbmUgYXJndW1lbnRzLiAgQW55IGFyZ3VtZW50cyB1c2VkIGFyZQorICogZGVsZXRlZCBmcm9tIGFyZ3YsIGFuZCAqYXJnYyBpcyBkZWNyZW1lbnRlZCBhY2NvcmRpbmdseS4gIFRoaXMgaXMgY2FsbGVkCisgKiB3aGVuIHZpbSBpcyBzdGFydGVkLCB3aGV0aGVyIG9yIG5vdCB0aGUgR1VJIGhhcyBiZWVuIHN0YXJ0ZWQuCisgKi8KKyAgICB2b2lkCitndWlfbWNoX3ByZXBhcmUoYXJnYywgYXJndikKKyAgICBpbnQJCSphcmdjOworICAgIGNoYXIJKiphcmd2OworeworICAgIC8qIFRPRE86IE1vdmUgbW9zdCBvZiB0aGlzIHN0dWZmIHRvd2FyZCBndWlfbWNoX2luaXQgKi8KKyNpZmRlZiBVU0VfRVhFX05BTUUKKyAgICBGU1NwZWMJYXBwbERpcjsKKyMgaWZuZGVmIFVTRV9GSU5EX0JVTkRMRV9QQVRICisgICAgc2hvcnQJYXBwbFZSZWZOdW07CisgICAgbG9uZwlhcHBsRGlySUQ7CisgICAgU3RyMjU1CXZvbE5hbWU7CisjIGVsc2UKKyAgICBQcm9jZXNzU2VyaWFsTnVtYmVyIHBzbjsKKyAgICBGU1JlZglhcHBsRlNSZWY7CisjIGVuZGlmCisjZW5kaWYKKworI2lmbmRlZiBVU0VfQ0FSQk9OSVpFRAorICAgIE1heEFwcGxab25lKCk7CSAgICAvKiBXaGF0IGNvdWxkIHJlcGxhY2UgdGhvcyAqLworICAgIC8qIEluIENhcmJvbiwgYWxsIHNoYXJlZCBsaWJyYXJ5IGFyZSBhdXRvbWF0aWNhbGx5IGxvYWQgaW4KKyAgICAgKiB0aGVyZSdzIG5vIG5lZWQgdG8gaW5pdCB0aGVtCisgICAgICovCisgICAgSW5pdEdyYWYoJnFkLnRoZVBvcnQpOworICAgIEluaXRGb250cygpOworICAgIEluaXRXaW5kb3dzKCk7CisgICAgSW5pdE1lbnVzKCk7CisgICAgVEVJbml0KCk7CisgICAgSW5pdERpYWxvZ3MobmlsKTsKKyNlbHNlCisgICAgLyogV2h5IGRpZCBJIHB1dCB0aGF0IGluPyAoRGFueSkgKi8KKyAgICBNb3JlTWFzdGVyUG9pbnRlcnMgKDB4NDAgKiAzKTsgLyogd2UgbG92ZSBoYW5kbGVzICovCisjZW5kaWYKKworI2lmIDAKKyAgICBJbml0Q3Vyc29yKCk7CisKKyNpZmRlZiBVU0VfQ0FSQk9OSVpFRAorICAgIFJlZ2lzdGVyQXBwZWFyYW5jZUNsaWVudCgpOworI2VuZGlmCisKKyNpZmRlZiBVU0VfQUVWRU5UCisgICAgKHZvaWQpIEluc3RhbGxBRUhhbmRsZXJzKCk7CisjZW5kaWYKKworI2lmZGVmIFVTRV9DVFJMQ0xJQ0tNRU5VCisgICAgaWYgKEdlc3RhbHQoZ2VzdGFsdENvbnRleHR1YWxNZW51QXR0ciwgJmdlc3RhbHRfcmMpID09IG5vRXJyKQorCWd1aS5NYWNPU0hhdmVDbnR4TWVudSA9IEJpdFRzdCgmZ2VzdGFsdF9yYywgMzEtZ2VzdGFsdENvbnRleHR1YWxNZW51VHJhcEF2YWlsYWJsZSk7CisgICAgZWxzZQorCWd1aS5NYWNPU0hhdmVDbnR4TWVudSA9IGZhbHNlOworCisgICAgaWYgKGd1aS5NYWNPU0hhdmVDbnR4TWVudSkKKwlndWkuTWFjT1NIYXZlQ250eE1lbnUgPSAoSW5pdENvbnRleHR1YWxNZW51cygpPT1ub0Vycik7CisjZW5kaWYKKworI2lmZGVmIFVTRV9TSU9VWAorICAgIFNJT1VYU2V0dGluZ3Muc3RhbmRhbG9uZSA9IGZhbHNlOworICAgIFNJT1VYU2V0dGluZ3MuaW5pdGlhbGl6ZVRCID0gZmFsc2U7CisgICAgU0lPVVhTZXR0aW5ncy5zZXR1cG1lbnVzID0gZmFsc2U7CisgICAgU0lPVVhTZXR0aW5ncy5hc2t0b3NhdmVvbmNsb3NlID0gZmFsc2U7CisgICAgU0lPVVhTZXR0aW5ncy5zaG93c3RhdHVzbGluZSA9IHRydWU7CisgICAgU0lPVVhTZXR0aW5ncy50b3BwaXhlbCA9IDMwMDsKKyAgICBTSU9VWFNldHRpbmdzLmxlZnRwaXhlbCA9IDEwOworICAgIEluc3RhbGxDb25zb2xlICgxKTsgLyogZmlsZW5vKHN0ZG91dCkgPSAxLCBvbiBwYWdlIDQzMCBvZiBNU0wgQyAqLworICAgIHByaW50ZiAoIkRlYnVnZ2luZyBjb25zb2xlIGVuYWJsZWRcbiIpOworICAgIC8qCVNJT1VYU2V0VGl0bGUgKChjaGFyX3UgKikgIlZpbSBTdGRvdXQiKTsgKi8KKyNlbmRpZgorCisgICAgcG9tbWUgPSBOZXdNZW51ICgyNTYsICJccFwwMjQiKTsgLyogMHgxND0gPSBBcHBsZSBNZW51ICovCisKKyAgICBBcHBlbmRNZW51IChwb21tZSwgIlxwQWJvdXQgVklNIik7CisjaWZuZGVmIFVTRV9DQVJCT05JWkVECisgICAgQXBwZW5kTWVudSAocG9tbWUsICJccC0iKTsKKyAgICBBcHBlbmRSZXNNZW51IChwb21tZSwgJ0RSVlInKTsKKyNlbmRpZgorCisgICAgSW5zZXJ0TWVudSAocG9tbWUsIDApOworCisgICAgRHJhd01lbnVCYXIoKTsKKworCisjaWZuZGVmIFVTRV9PRkZTRVRFRF9XSU5ET1cKKyAgICBTZXRSZWN0ICgmd2luZFJlY3QsIDEwLCA0OCwgMTArODAqNyArIDE2LCA0OCsyNCoxMSk7CisjZWxzZQorICAgIFNldFJlY3QgKCZ3aW5kUmVjdCwgMzAwLCA0MCwgMzAwKzgwKjcgKyAxNiwgNDArMjQqMTEpOworI2VuZGlmCisKKworI2lmZGVmIFVTRV9DQVJCT05JWkVECisgICAgQ3JlYXRlTmV3V2luZG93KGtEb2N1bWVudFdpbmRvd0NsYXNzLAorCQlrV2luZG93UmVzaXphYmxlQXR0cmlidXRlIHwga1dpbmRvd0NvbGxhcHNlQm94QXR0cmlidXRlLAorCQkmd2luZFJlY3QsICZndWkuVmltV2luZG93ICk7CisgICAgU2V0UG9ydFdpbmRvd1BvcnQgKCBndWkuVmltV2luZG93ICk7CisjZWxzZQorICAgIGd1aS5WaW1XaW5kb3cgPSBOZXdDV2luZG93KG5pbCwgJndpbmRSZWN0LCAiXHBnVmltIG9uIE1hY2ludG9zaCIsIHRydWUsIGRvY3VtZW50UHJvYywKKwkJCShXaW5kb3dQdHIpIC0xTCwgZmFsc2UsIDApOworICAgIFNldFBvcnQoZ3VpLlZpbVdpbmRvdyk7CisjZW5kaWYKKworICAgIGd1aS5jaGFyX3dpZHRoID0gNzsKKyAgICBndWkuY2hhcl9oZWlnaHQgPSAxMTsKKyAgICBndWkuY2hhcl9hc2NlbnQgPSA2OworICAgIGd1aS5udW1fcm93cyA9IDI0OworICAgIGd1aS5udW1fY29scyA9IDgwOworICAgIGd1aS5pbl9mb2N1cyA9IFRSVUU7IC8qIEZvciB0aGUgbW9tZW50IC0+IHN5bi4gb2YgZnJvbnQgYXBwbGljYXRpb24gKi8KKworI2lmIFRBUkdFVF9BUElfTUFDX0NBUkJPTgorICAgIGdTY3JvbGxBY3Rpb24gPSBOZXdDb250cm9sQWN0aW9uVVBQIChndWlfbWFjX3Njcm9sbF9hY3Rpb24pOworICAgIGdTY3JvbGxEcmFnICAgPSBOZXdDb250cm9sQWN0aW9uVVBQIChndWlfbWFjX2RyYWdfdGh1bWIpOworI2Vsc2UKKyAgICBnU2Nyb2xsQWN0aW9uID0gTmV3Q29udHJvbEFjdGlvblByb2MgKGd1aV9tYWNfc2Nyb2xsX2FjdGlvbik7CisgICAgZ1Njcm9sbERyYWcgICA9IE5ld0NvbnRyb2xBY3Rpb25Qcm9jIChndWlfbWFjX2RyYWdfdGh1bWIpOworI2VuZGlmCisKKyAgICAvKiBHZXR0aW5nIGEgaGFuZGxlIHRvIHRoZSBIZWxwIG1lbnUgKi8KKyNpZmRlZiBVU0VfSEVMUE1FTlUKKyMgaWZkZWYgVVNFX0NBUkJPTklaRUQKKyAgICBITUdldEhlbHBNZW51KCZndWkuTWFjT1NIZWxwTWVudSwgTlVMTCk7CisjIGVsc2UKKyAgICAodm9pZCkgSE1HZXRIZWxwTWVudUhhbmRsZSgmZ3VpLk1hY09TSGVscE1lbnUpOworIyBlbmRpZgorCisgICAgaWYgKGd1aS5NYWNPU0hlbHBNZW51ICE9IG5pbCkKKwlndWkuTWFjT1NIZWxwSXRlbXMgPSBDb3VudE1lbnVJdGVtcyAoZ3VpLk1hY09TSGVscE1lbnUpOworICAgIGVsc2UKKwlndWkuTWFjT1NIZWxwSXRlbXMgPSAwOworI2VuZGlmCisKKyAgICBkcmFnUmVjdEVuYmwgPSBGQUxTRTsKKyAgICBkcmFnUmduID0gTlVMTDsKKyAgICBkcmFnUmVjdENvbnRyb2wgPSBrQ3JlYXRlRW1wdHk7CisgICAgY3Vyc29yUmduID0gTmV3UmduKCk7CisjZW5kaWYKKyNpZmRlZiBVU0VfRVhFX05BTUUKKyMgaWZuZGVmIFVTRV9GSU5EX0JVTkRMRV9QQVRICisgICAgSEdldFZvbCAodm9sTmFtZSwgJmFwcGxWUmVmTnVtLCAmYXBwbERpcklEKTsKKyAgICAvKiBUTjIwMTU6IG1lbnRpb24gYSBwb3NzaWJsZSBiYWQgVlJlZk51bSAqLworICAgIEZTTWFrZUZTU3BlYyAoYXBwbFZSZWZOdW0sIGFwcGxEaXJJRCwgIlxwIiwgJmFwcGxEaXIpOworIyBlbHNlCisgICAgLyogT1NFcnIgR2V0QXBwbGljYXRpb25CdW5kbGVGU1NwZWMoRlNTcGVjUHRyIHRoZUZTU3BlY1B0cikKKyAgICAgKiBvZiBUTjIwMTUKKyAgICAgKiBUaGlzIHRlY2huaWMgcmVtb3ZlIHRoZSAuLi9Db250ZW50cy9NYWNPUy9ldGMgcGFydAorICAgICAqLworICAgICh2b2lkKSBHZXRDdXJyZW50UHJvY2VzcygmcHNuKTsKKyAgICAvKiBpZiAoZXJyICE9IG5vRXJyKSByZXR1cm4gZXJyOyAqLworCisgICAgKHZvaWQpIEdldFByb2Nlc3NCdW5kbGVMb2NhdGlvbigmcHNuLCAmYXBwbEZTUmVmKTsKKyAgICAvKiBpZiAoZXJyICE9IG5vRXJyKSByZXR1cm4gZXJyOyAqLworCisgICAgKHZvaWQpIEZTR2V0Q2F0YWxvZ0luZm8oJmFwcGxGU1JlZiwga0ZTQ2F0SW5mb05vbmUsIE5VTEwsIE5VTEwsICZhcHBsRGlyLCBOVUxMKTsKKworICAgIC8qIFRoaXMgdGVjaG5pYyByZXR1cm4gTklMIHdoZW4gd2UgZGlzYWxsb3dfZ3VpICovCisjIGVuZGlmCisgICAgZXhlX25hbWUgPSBGdWxsUGF0aEZyb21GU1NwZWNfc2F2ZSAoYXBwbERpcik7CisjZW5kaWYKKworI2lmZGVmIFVTRV9WSU1fQ1JFQVRPUl9JRAorICAgIF9mY3JlYXRvciA9ICdWSU0hJzsKKyAgICBfZnR5cGUgPSAnVEVYVCc7CisjZW5kaWYKK30KKworI2lmbmRlZiBBTFdBWVNfVVNFX0dVSQorLyoKKyAqIENoZWNrIGlmIHRoZSBHVUkgY2FuIGJlIHN0YXJ0ZWQuICBDYWxsZWQgYmVmb3JlIGd2aW1yYyBpcyBzb3VyY2VkLgorICogUmV0dXJuIE9LIG9yIEZBSUwuCisgKi8KKyAgICBpbnQKK2d1aV9tY2hfaW5pdF9jaGVjayh2b2lkKQoreworICAgIC8qIFRPRE86IEZvciBNYWNPUyBYIGZpbmQgYSB3YXkgdG8gcmV0dXJuIEZBSUwsIGlmIHRoZSB1c2VyIGxvZ2dlZCBpbgorICAgICAqIHVzaW5nIHRoZSA+Y29uc29sZQorICAgICAqLworICAgIGlmIChkaXNhbGxvd19ndWkpIC8qIHNlZSBtYWluLmMgZm9yIHJlYXNvbiB0byBkaXNhbGxvdyAqLworCXJldHVybiBGQUlMOworICAgIHJldHVybiBPSzsKK30KKyNlbmRpZgorCisgICAgc3RhdGljIE9TRXJyCityZWNlaXZlSGFuZGxlcihXaW5kb3dSZWYgdGhlV2luZG93LCB2b2lkKiBoYW5kbGVyUmVmQ29uLCBEcmFnUmVmIHRoZURyYWcpCit7CisgICAgaW50CQl4LCB5OworICAgIGludF91CW1vZGlmaWVyczsKKyAgICBjaGFyX3UJKipmbmFtZXMgPSBOVUxMOworICAgIGludAkJY291bnQ7CisgICAgaW50CQlpLCBqOworCisgICAgLyogR2V0IGRyb3AgcG9zaXRpb24sIG1vZGlmaWVycyBhbmQgY291bnQgb2YgaXRlbXMgKi8KKyAgICB7CisJUG9pbnQJcG9pbnQ7CisJU0ludDE2CW1vdXNlVXBNb2RpZmllcnM7CisJVUludDE2CWNvdW50SXRlbTsKKworCUdldERyYWdNb3VzZSh0aGVEcmFnLCAmcG9pbnQsIE5VTEwpOworCUdsb2JhbFRvTG9jYWwoJnBvaW50KTsKKwl4ID0gcG9pbnQuaDsKKwl5ID0gcG9pbnQudjsKKwlHZXREcmFnTW9kaWZpZXJzKHRoZURyYWcsIE5VTEwsIE5VTEwsICZtb3VzZVVwTW9kaWZpZXJzKTsKKwltb2RpZmllcnMgPSBFdmVudE1vZGlmaWVyczJWaW1Nb3VzZU1vZGlmaWVycyhtb3VzZVVwTW9kaWZpZXJzKTsKKwlDb3VudERyYWdJdGVtcyh0aGVEcmFnLCAmY291bnRJdGVtKTsKKwljb3VudCA9IGNvdW50SXRlbTsKKyAgICB9CisKKyAgICBmbmFtZXMgPSAoY2hhcl91ICoqKWFsbG9jKGNvdW50ICogc2l6ZW9mKGNoYXJfdSAqKSk7CisgICAgaWYgKGZuYW1lcyA9PSBOVUxMKQorCXJldHVybiBkcmFnTm90QWNjZXB0ZWRFcnI7CisKKyAgICAvKiBHZXQgZmlsZSBuYW1lcyBkcm9wcGVkICovCisgICAgZm9yIChpID0gaiA9IDA7IGkgPCBjb3VudDsgKytpKQorICAgIHsKKwlEcmFnSXRlbVJlZglpdGVtOworCU9TRXJyCQllcnI7CisJU2l6ZQkJc2l6ZTsKKwlGbGF2b3JUeXBlCXR5cGUgPSBmbGF2b3JUeXBlSEZTOworCUhGU0ZsYXZvcgloZnNGbGF2b3I7CisKKwlmbmFtZXNbaV0gPSBOVUxMOworCUdldERyYWdJdGVtUmVmZXJlbmNlTnVtYmVyKHRoZURyYWcsIGkgKyAxLCAmaXRlbSk7CisJZXJyID0gR2V0Rmxhdm9yRGF0YVNpemUodGhlRHJhZywgaXRlbSwgdHlwZSwgJnNpemUpOworCWlmIChlcnIgIT0gbm9FcnIgfHwgc2l6ZSA+IHNpemVvZihoZnNGbGF2b3IpKQorCSAgICBjb250aW51ZTsKKwllcnIgPSBHZXRGbGF2b3JEYXRhKHRoZURyYWcsIGl0ZW0sIHR5cGUsICZoZnNGbGF2b3IsICZzaXplLCAwKTsKKwlpZiAoZXJyICE9IG5vRXJyKQorCSAgICBjb250aW51ZTsKKwlmbmFtZXNbaisrXSA9IEZ1bGxQYXRoRnJvbUZTU3BlY19zYXZlKGhmc0ZsYXZvci5maWxlU3BlYyk7CisgICAgfQorICAgIGNvdW50ID0gajsKKworICAgIGd1aV9oYW5kbGVfZHJvcCh4LCB5LCBtb2RpZmllcnMsIGZuYW1lcywgY291bnQpOworICAgIHJldHVybiBub0VycjsKK30KKworLyoKKyAqIEluaXRpYWxpc2UgdGhlIEdVSS4gIENyZWF0ZSBhbGwgdGhlIHdpbmRvd3MsIHNldCB1cCBhbGwgdGhlIGNhbGwtYmFja3MKKyAqIGV0Yy4KKyAqLworICAgIGludAorZ3VpX21jaF9pbml0KCkKK3sKKyAgICAvKiBUT0RPOiBNb3ZlIG1vc3Qgb2YgdGhpcyBzdHVmZiB0b3dhcmQgZ3VpX21jaF9pbml0ICovCisgICAgUmVjdAl3aW5kUmVjdDsKKyAgICBNZW51SGFuZGxlCXBvbW1lOworI2lmZGVmIFVTRV9DVFJMQ0xJQ0tNRU5VCisgICAgbG9uZwlnZXN0YWx0X3JjOworI2VuZGlmCisjaWZkZWYgVVNFX01PVVNFV0hFRUwKKyAgICBFdmVudFR5cGVTcGVjICAgZXZlbnRUeXBlU3BlYzsKKyAgICBFdmVudEhhbmRsZXJSZWYgbW91c2VXaGVlbEhhbmRsZXJSZWY7CisjZW5kaWYKKyNpZiAxCisgICAgSW5pdEN1cnNvcigpOworCisjaWZkZWYgVVNFX0NBUkJPTklaRUQKKyAgICBSZWdpc3RlckFwcGVhcmFuY2VDbGllbnQoKTsKKyNlbmRpZgorCisjaWZkZWYgVVNFX0FFVkVOVAorICAgICh2b2lkKSBJbnN0YWxsQUVIYW5kbGVycygpOworI2VuZGlmCisKKyNpZmRlZiBVU0VfQ1RSTENMSUNLTUVOVQorICAgIGlmIChHZXN0YWx0KGdlc3RhbHRDb250ZXh0dWFsTWVudUF0dHIsICZnZXN0YWx0X3JjKSA9PSBub0VycikKKwlndWkuTWFjT1NIYXZlQ250eE1lbnUgPSBCaXRUc3QoJmdlc3RhbHRfcmMsIDMxLWdlc3RhbHRDb250ZXh0dWFsTWVudVRyYXBBdmFpbGFibGUpOworICAgIGVsc2UKKwlndWkuTWFjT1NIYXZlQ250eE1lbnUgPSBmYWxzZTsKKworICAgIGlmIChndWkuTWFjT1NIYXZlQ250eE1lbnUpCisJZ3VpLk1hY09TSGF2ZUNudHhNZW51ID0gKEluaXRDb250ZXh0dWFsTWVudXMoKT09bm9FcnIpOworI2VuZGlmCisKKyNpZmRlZiBVU0VfU0lPVVgKKyAgICBTSU9VWFNldHRpbmdzLnN0YW5kYWxvbmUgPSBmYWxzZTsKKyAgICBTSU9VWFNldHRpbmdzLmluaXRpYWxpemVUQiA9IGZhbHNlOworICAgIFNJT1VYU2V0dGluZ3Muc2V0dXBtZW51cyA9IGZhbHNlOworICAgIFNJT1VYU2V0dGluZ3MuYXNrdG9zYXZlb25jbG9zZSA9IGZhbHNlOworICAgIFNJT1VYU2V0dGluZ3Muc2hvd3N0YXR1c2xpbmUgPSB0cnVlOworICAgIFNJT1VYU2V0dGluZ3MudG9wcGl4ZWwgPSAzMDA7CisgICAgU0lPVVhTZXR0aW5ncy5sZWZ0cGl4ZWwgPSAxMDsKKyAgICBJbnN0YWxsQ29uc29sZSAoMSk7IC8qIGZpbGVubyhzdGRvdXQpID0gMSwgb24gcGFnZSA0MzAgb2YgTVNMIEMgKi8KKyAgICBwcmludGYgKCJEZWJ1Z2dpbmcgY29uc29sZSBlbmFibGVkXG4iKTsKKyAgICAvKglTSU9VWFNldFRpdGxlICgoY2hhcl91ICopICJWaW0gU3Rkb3V0Iik7ICovCisjZW5kaWYKKworICAgIHBvbW1lID0gTmV3TWVudSAoMjU2LCAiXHBcMDI0Iik7IC8qIDB4MTQ9ID0gQXBwbGUgTWVudSAqLworCisgICAgQXBwZW5kTWVudSAocG9tbWUsICJccEFib3V0IFZJTSIpOworI2lmbmRlZiBVU0VfQ0FSQk9OSVpFRAorICAgIEFwcGVuZE1lbnUgKHBvbW1lLCAiXHAtIik7CisgICAgQXBwZW5kUmVzTWVudSAocG9tbWUsICdEUlZSJyk7CisjZW5kaWYKKworICAgIEluc2VydE1lbnUgKHBvbW1lLCAwKTsKKworICAgIERyYXdNZW51QmFyKCk7CisKKworI2lmbmRlZiBVU0VfT0ZGU0VURURfV0lORE9XCisgICAgU2V0UmVjdCAoJndpbmRSZWN0LCAxMCwgNDgsIDEwKzgwKjcgKyAxNiwgNDgrMjQqMTEpOworI2Vsc2UKKyAgICBTZXRSZWN0ICgmd2luZFJlY3QsIDMwMCwgNDAsIDMwMCs4MCo3ICsgMTYsIDQwKzI0KjExKTsKKyNlbmRpZgorCisgICAgZ3VpLlZpbVdpbmRvdyA9IE5ld0NXaW5kb3cobmlsLCAmd2luZFJlY3QsICJccGdWaW0gb24gTWFjaW50b3NoIiwgdHJ1ZSwKKyNpZmRlZiBVU0VfQ0FSQk9OSVpFRAorCQkJem9vbURvY1Byb2MsCisjZWxzZQorCQkJZG9jdW1lbnRQcm9jLAorI2VuZGlmCisJCQkoV2luZG93UHRyKS0xTCwgdHJ1ZSwgMCk7CisgICAgSW5zdGFsbFJlY2VpdmVIYW5kbGVyKChEcmFnUmVjZWl2ZUhhbmRsZXJVUFApcmVjZWl2ZUhhbmRsZXIsCisJICAgIGd1aS5WaW1XaW5kb3csIE5VTEwpOworI2lmZGVmIFVTRV9DQVJCT05JWkVECisgICAgU2V0UG9ydFdpbmRvd1BvcnQgKCBndWkuVmltV2luZG93ICk7CisjZWxzZQorICAgIFNldFBvcnQoZ3VpLlZpbVdpbmRvdyk7CisjZW5kaWYKKworICAgIGd1aS5jaGFyX3dpZHRoID0gNzsKKyAgICBndWkuY2hhcl9oZWlnaHQgPSAxMTsKKyAgICBndWkuY2hhcl9hc2NlbnQgPSA2OworICAgIGd1aS5udW1fcm93cyA9IDI0OworICAgIGd1aS5udW1fY29scyA9IDgwOworICAgIGd1aS5pbl9mb2N1cyA9IFRSVUU7IC8qIEZvciB0aGUgbW9tZW50IC0+IHN5bi4gb2YgZnJvbnQgYXBwbGljYXRpb24gKi8KKworI2lmIFRBUkdFVF9BUElfTUFDX0NBUkJPTgorICAgIGdTY3JvbGxBY3Rpb24gPSBOZXdDb250cm9sQWN0aW9uVVBQIChndWlfbWFjX3Njcm9sbF9hY3Rpb24pOworICAgIGdTY3JvbGxEcmFnICAgPSBOZXdDb250cm9sQWN0aW9uVVBQIChndWlfbWFjX2RyYWdfdGh1bWIpOworI2Vsc2UKKyAgICBnU2Nyb2xsQWN0aW9uID0gTmV3Q29udHJvbEFjdGlvblByb2MgKGd1aV9tYWNfc2Nyb2xsX2FjdGlvbik7CisgICAgZ1Njcm9sbERyYWcgICA9IE5ld0NvbnRyb2xBY3Rpb25Qcm9jIChndWlfbWFjX2RyYWdfdGh1bWIpOworI2VuZGlmCisKKyAgICAvKiBHZXR0aW5nIGEgaGFuZGxlIHRvIHRoZSBIZWxwIG1lbnUgKi8KKyNpZmRlZiBVU0VfSEVMUE1FTlUKKyMgaWZkZWYgVVNFX0NBUkJPTklaRUQKKyAgICBITUdldEhlbHBNZW51KCZndWkuTWFjT1NIZWxwTWVudSwgTlVMTCk7CisjIGVsc2UKKyAgICAodm9pZCkgSE1HZXRIZWxwTWVudUhhbmRsZSgmZ3VpLk1hY09TSGVscE1lbnUpOworIyBlbmRpZgorCisgICAgaWYgKGd1aS5NYWNPU0hlbHBNZW51ICE9IG5pbCkKKwlndWkuTWFjT1NIZWxwSXRlbXMgPSBDb3VudE1lbnVJdGVtcyAoZ3VpLk1hY09TSGVscE1lbnUpOworICAgIGVsc2UKKwlndWkuTWFjT1NIZWxwSXRlbXMgPSAwOworI2VuZGlmCisKKyAgICBkcmFnUmVjdEVuYmwgPSBGQUxTRTsKKyAgICBkcmFnUmduID0gTlVMTDsKKyAgICBkcmFnUmVjdENvbnRyb2wgPSBrQ3JlYXRlRW1wdHk7CisgICAgY3Vyc29yUmduID0gTmV3UmduKCk7CisjZW5kaWYKKyAgICAvKiBEaXNwbGF5IGFueSBwZW5kaW5nIGVycm9yIG1lc3NhZ2VzICovCisgICAgZGlzcGxheV9lcnJvcnMoKTsKKworICAgIC8qIEdldCBiYWNrZ3JvdW5kL2ZvcmVncm91bmQgY29sb3JzIGZyb20gc3lzdGVtICovCisgICAgLyogVE9ETzogZG8gdGhlIGFwcHJvcmlhdGUgY2FsbCB0byBnZXQgcmVhbCBkZWZhdWx0cyAqLworICAgIGd1aS5ub3JtX3BpeGVsID0gMHgwMDAwMDAwMDsKKyAgICBndWkuYmFja19waXhlbCA9IDB4MDBGRkZGRkY7CisKKyAgICAvKiBHZXQgdGhlIGNvbG9ycyBmcm9tIHRoZSAiTm9ybWFsIiBncm91cCAoc2V0IGluIHN5bnRheC5jIG9yIGluIGEgdmltcmMKKyAgICAgKiBmaWxlKS4gKi8KKyAgICBzZXRfbm9ybWFsX2NvbG9ycygpOworCisgICAgLyoKKyAgICAgKiBDaGVjayB0aGF0IG5vbmUgb2YgdGhlIGNvbG9ycyBhcmUgdGhlIHNhbWUgYXMgdGhlIGJhY2tncm91bmQgY29sb3IuCisgICAgICogVGhlbiBzdG9yZSB0aGUgY3VycmVudCB2YWx1ZXMgYXMgdGhlIGRlZmF1bHRzLgorICAgICAqLworICAgIGd1aV9jaGVja19jb2xvcnMoKTsKKyAgICBndWkuZGVmX25vcm1fcGl4ZWwgPSBndWkubm9ybV9waXhlbDsKKyAgICBndWkuZGVmX2JhY2tfcGl4ZWwgPSBndWkuYmFja19waXhlbDsKKworICAgIC8qIEdldCB0aGUgY29sb3JzIGZvciB0aGUgaGlnaGxpZ2h0IGdyb3VwcyAoZ3VpX2NoZWNrX2NvbG9ycygpIG1pZ2h0IGhhdmUKKyAgICAgKiBjaGFuZ2VkIHRoZW0pICovCisgICAgaGlnaGxpZ2h0X2d1aV9zdGFydGVkKCk7CisKKyAgICAvKgorICAgICAqIFNldHRpbmcgdGhlIGd1aSBjb25zdGFudHMKKyAgICAgKi8KKyNpZmRlZiBGRUFUX01FTlUKKyAgICBndWkubWVudV9oZWlnaHQgPSAwOworI2VuZGlmCisgICAgZ3VpLnNjcm9sbGJhcl9oZWlnaHQgPSBndWkuc2Nyb2xsYmFyX3dpZHRoID0gMTU7IC8qIGNoZWF0IDEgb3ZlcmxhcCAqLworICAgIGd1aS5ib3JkZXJfb2Zmc2V0ID0gZ3VpLmJvcmRlcl93aWR0aCA9IDI7CisKKyNpZiBkZWZpbmVkKEZFQVRfR1VJKSAmJiBkZWZpbmVkKE1BQ09TX1gpCisgICAgLyogSWYgUXVhcnR6LXN0eWxlIHRleHQgYW50aWFsaWFzaW5nIGlzIGF2YWlsYWJsZSAoc2VlCisgICAgICAgZ3VpX21jaF9kcmF3X3N0cmluZygpIGJlbG93KSwgZW5hYmxlIGl0IGZvciBhbGwgZm9udCBzaXplcy4gKi8KKyAgICB2aW1fc2V0ZW52KChjaGFyX3UgKikiUURURVhUX01JTlNJWkUiLCAoY2hhcl91ICopIjEiKTsKKyNlbmRpZgorCisjaWZkZWYgVVNFX01PVVNFV0hFRUwKKyAgICBldmVudFR5cGVTcGVjLmV2ZW50Q2xhc3MgPSBrRXZlbnRDbGFzc01vdXNlOworICAgIGV2ZW50VHlwZVNwZWMuZXZlbnRLaW5kID0ga0V2ZW50TW91c2VXaGVlbE1vdmVkOworICAgIG1vdXNlV2hlZWxIYW5kbGVyVVBQID0gTmV3RXZlbnRIYW5kbGVyVVBQKGd1aV9tYWNfbW91c2Vfd2hlZWwpOworICAgIGlmIChub0VyciAhPSBJbnN0YWxsQXBwbGljYXRpb25FdmVudEhhbmRsZXIobW91c2VXaGVlbEhhbmRsZXJVUFAsIDEsCisJCQkJICZldmVudFR5cGVTcGVjLCBOVUxMLCAmbW91c2VXaGVlbEhhbmRsZXJSZWYpKQorICAgIHsKKwltb3VzZVdoZWVsSGFuZGxlclJlZiA9IE5VTEw7CisJRGlzcG9zZUV2ZW50SGFuZGxlclVQUChtb3VzZVdoZWVsSGFuZGxlclVQUCk7CisJbW91c2VXaGVlbEhhbmRsZXJVUFAgPSBOVUxMOworICAgIH0KKyNlbmRpZgorCisjaWZkZWYgRkVBVF9NQllURQorICAgIHNldF9vcHRpb25fdmFsdWUoKGNoYXJfdSAqKSJ0ZXJtZW5jb2RpbmciLCAwTCwgKGNoYXJfdSAqKSJtYWNyb21hbiIsIDApOworI2VuZGlmCisKKyAgICAvKiBUT0RPOiBMb2FkIGJpdG1hcCBpZiB1c2luZyBUT09MQkFSICovCisgICAgcmV0dXJuIE9LOworfQorCisvKgorICogQ2FsbGVkIHdoZW4gdGhlIGZvcmVncm91bmQgb3IgYmFja2dyb3VuZCBjb2xvciBoYXMgYmVlbiBjaGFuZ2VkLgorICovCisgICAgdm9pZAorZ3VpX21jaF9uZXdfY29sb3JzKCkKK3sKKyAgICAvKiBUT0RPOgorICAgICAqIFRoaXMgcHJvYyBpcyBjYWxsZWQgd2hlbiBOb3JtYWwgaXMgc2V0IHRvIGEgdmFsdWUKKyAgICAgKiBzbyB3aGF0IG1zdXQgYmUgZG9uZT8gSSBkb24ndCBrbm93CisgICAgICovCit9CisKKy8qCisgKiBPcGVuIHRoZSBHVUkgd2luZG93IHdoaWNoIHdhcyBjcmVhdGVkIGJ5IGEgY2FsbCB0byBndWlfbWNoX2luaXQoKS4KKyAqLworICAgIGludAorZ3VpX21jaF9vcGVuKCkKK3sKKyAgICBTaG93V2luZG93KGd1aS5WaW1XaW5kb3cpOworCisgICAgaWYgKGd1aV93aW5feCAhPSAtMSAmJiBndWlfd2luX3kgIT0gLTEpCisJZ3VpX21jaF9zZXRfd2lucG9zKGd1aV93aW5feCwgZ3VpX3dpbl95KTsKKworI2lmZGVmIFVTRV9DQVJCT05JWkVECisgICAgLyoKKyAgICAgKiBNYWtlIHRoZSBHVUkgdGhlIGZvcmVncm91bmQgcHJvY2VzcyAoaW4gY2FzZSBpdCB3YXMgbGF1bmNoZWQKKyAgICAgKiBmcm9tIHRoZSBUZXJtaW5hbCBvciB2aWEgOmd1aSkuCisgICAgICovCisgICAgeworCVByb2Nlc3NTZXJpYWxOdW1iZXIgcHNuOworCWlmIChHZXRDdXJyZW50UHJvY2VzcygmcHNuKSA9PSBub0VycikKKwkgICAgU2V0RnJvbnRQcm9jZXNzKCZwc24pOworICAgIH0KKyNlbmRpZgorCisgICAgcmV0dXJuIE9LOworfQorCisgICAgdm9pZAorZ3VpX21jaF9leGl0KGludCByYykKK3sKKyAgICAvKiBUT0RPOiBmaW5kIG91dCBhbGwgd2hhdCBpcyBtaXNzaW5nIGhlcmU/ICovCisgICAgRGlzcG9zZVJnbihjdXJzb3JSZ24pOworCisjaWZkZWYgVVNFX01PVVNFV0hFRUwKKyAgICBpZiAobW91c2VXaGVlbEhhbmRsZXJVUFAgIT0gTlVMTCkKKwlEaXNwb3NlRXZlbnRIYW5kbGVyVVBQKG1vdXNlV2hlZWxIYW5kbGVyVVBQKTsKKyNlbmRpZgorCisgICAgLyogRXhpdCB0byBzaGVsbD8gKi8KKyAgICBleGl0KHJjKTsKK30KKworLyoKKyAqIEdldCB0aGUgcG9zaXRpb24gb2YgdGhlIHRvcCBsZWZ0IGNvcm5lciBvZiB0aGUgd2luZG93LgorICovCisgICAgaW50CitndWlfbWNoX2dldF93aW5wb3MoaW50ICp4LCBpbnQgKnkpCit7CisgICAgLyogVE9ETyAqLworI2lmZGVmIFVTRV9DQVJCT05JWkVECisgICAgUmVjdAlib3VuZHM7CisgICAgT1NTdGF0dXMJc3RhdHVzOworCisgICAgLyogQ2FyYm9uID49IDEuMC4yLCBNYWNPUyA+PSA4LjUgKi8KKyAgICBzdGF0dXMgPSBHZXRXaW5kb3dCb3VuZHMgKGd1aS5WaW1XaW5kb3csIGtXaW5kb3dTdHJ1Y3R1cmVSZ24sICZib3VuZHMpOworCisgICAgaWYgKHN0YXR1cyAhPSBub0VycikKKwlyZXR1cm4gRkFJTDsKKyAgICAqeCA9IGJvdW5kcy5sZWZ0OworICAgICp5ID0gYm91bmRzLnRvcDsKKyAgICByZXR1cm4gT0s7CisjZW5kaWYKKyAgICByZXR1cm4gRkFJTDsKK30KKworLyoKKyAqIFNldCB0aGUgcG9zaXRpb24gb2YgdGhlIHRvcCBsZWZ0IGNvcm5lciBvZiB0aGUgd2luZG93IHRvIHRoZSBnaXZlbgorICogY29vcmRpbmF0ZXMuCisgKi8KKyAgICB2b2lkCitndWlfbWNoX3NldF93aW5wb3MoaW50IHgsIGludCB5KQoreworICAgIC8qIFRPRE86ICBTaG91bGQgbWFrZSBzdXJlIHRoZSB3aW5kb3cgaXMgbW92ZSB3aXRoaW4gcmFuZ2UKKyAgICAgKgkgICAgICBlLmcuOiB5ID4gfjE2IFtNZW51IGJhcl0sIHggPiAwLCB4IDwgc2NyZWVuIHdpZHRoCisgICAgICovCisgICAgTW92ZVdpbmRvdyhndWkuVmltV2luZG93LCB4LCB5LCBUUlVFKTsKK30KKworICAgIHZvaWQKK2d1aV9tY2hfc2V0X3NoZWxsc2l6ZSgKKyAgICBpbnQJCXdpZHRoLAorICAgIGludAkJaGVpZ2h0LAorICAgIGludAkJbWluX3dpZHRoLAorICAgIGludAkJbWluX2hlaWdodCwKKyAgICBpbnQJCWJhc2Vfd2lkdGgsCisgICAgaW50CQliYXNlX2hlaWdodCkKK3sKKyNpZmRlZiBVU0VfQ0FSQk9OSVpFRAorICAgIENHcmFmUHRyCVZpbVBvcnQ7CisgICAgUmVjdAlWaW1Cb3VuZDsKKyNlbmRpZgorCisgICAgaWYgKGd1aS53aGljaF9zY3JvbGxiYXJzW1NCQVJfTEVGVF0pCisgICAgeworI2lmZGVmIFVTRV9DQVJCT05JWkVECisJVmltUG9ydCA9IEdldFdpbmRvd1BvcnQgKCBndWkuVmltV2luZG93ICk7CisJR2V0UG9ydEJvdW5kcyAoVmltUG9ydCwgJlZpbUJvdW5kKTsKKwlWaW1Cb3VuZC5sZWZ0ID0gLWd1aS5zY3JvbGxiYXJfd2lkdGg7IC8qICsgMTsqLworCVNldFBvcnRCb3VuZHMgKFZpbVBvcnQsICZWaW1Cb3VuZCk7CisgICAgLyoJR2V0V2luZG93Qm91bmRzKGd1aS5WaW1XaW5kb3csIGtXaW5kb3dHbG9iYWxQb3J0UmduLCAmd2luUG9ydFJlY3QpOyA/PyovCisjZWxzZQorCWd1aS5WaW1XaW5kb3ctPnBvcnRSZWN0LmxlZnQgPSAtZ3VpLnNjcm9sbGJhcl93aWR0aDsgLyogKyAxOyovCisgICAgLyoJU2V0V2luZG93Qm91bmRzKGd1aS5WaW1XaW5kb3csIGtXaW5kb3dHbG9iYWxQb3J0UmduLCAmd2luUG9ydFJlY3QpOyA/PyovCisjZW5kaWYKKyAgICB9CisgICAgZWxzZQorICAgIHsKKyNpZmRlZiBVU0VfQ0FSQk9OSVpFRAorCVZpbVBvcnQgPSBHZXRXaW5kb3dQb3J0ICggZ3VpLlZpbVdpbmRvdyApOworCUdldFBvcnRCb3VuZHMgKFZpbVBvcnQsICZWaW1Cb3VuZCk7CisJVmltQm91bmQubGVmdCA9IDA7CisJU2V0UG9ydEJvdW5kcyAoVmltUG9ydCwgJlZpbUJvdW5kKTsKKyNlbHNlCisJZ3VpLlZpbVdpbmRvdy0+cG9ydFJlY3QubGVmdCA9IDA7CisjZW5kaWY7CisgICAgfQorCisgICAgU2l6ZVdpbmRvdyhndWkuVmltV2luZG93LCB3aWR0aCwgaGVpZ2h0LCBUUlVFKTsKKworICAgIGd1aV9yZXNpemVfc2hlbGwod2lkdGgsIGhlaWdodCk7Cit9CisKKy8qCisgKiBHZXQgdGhlIHNjcmVlbiBkaW1lbnNpb25zLgorICogQWxsb3cgMTAgcGl4ZWxzIGZvciBob3Jpem9udGFsIGJvcmRlcnMsIDQwIGZvciB2ZXJ0aWNhbCBib3JkZXJzLgorICogSXMgdGhlcmUgbm8gd2F5IHRvIGZpbmQgb3V0IGhvdyB3aWRlIHRoZSBib3JkZXJzIHJlYWxseSBhcmU/CisgKiBUT0RPOiBBZGQgbGl2ZSB1ZGF0ZSBvZiB0aG9zZSB2YWx1ZSBvbiBzdXNwZW5kL3Jlc3VtZS4KKyAqLworICAgIHZvaWQKK2d1aV9tY2hfZ2V0X3NjcmVlbl9kaW1lbnNpb25zKHNjcmVlbl93LCBzY3JlZW5faCkKKyAgICBpbnQJCSpzY3JlZW5fdzsKKyAgICBpbnQJCSpzY3JlZW5faDsKK3sKKyAgICBHREhhbmRsZQlkb21pbmFudERldmljZSA9IEdldE1haW5EZXZpY2UoKTsKKyAgICBSZWN0CXNjcmVlblJlY3QgPSAoKipkb21pbmFudERldmljZSkuZ2RSZWN0OworCisgICAgKnNjcmVlbl93ID0gc2NyZWVuUmVjdC5yaWdodCAtIDEwOworICAgICpzY3JlZW5faCA9IHNjcmVlblJlY3QuYm90dG9tIC0gNDA7Cit9CisKKworCisvKgorICogSW5pdGlhbGlzZSB2aW0gdG8gdXNlIHRoZSBmb250IHdpdGggdGhlIGdpdmVuIG5hbWUuCVJldHVybiBGQUlMIGlmIHRoZSBmb250CisgKiBjb3VsZCBub3QgYmUgbG9hZGVkLCBPSyBvdGhlcndpc2UuCisgKi8KKyAgICBpbnQKK2d1aV9tY2hfaW5pdF9mb250KGZvbnRfbmFtZSwgZm9udHNldCkKKyAgICBjaGFyX3UJKmZvbnRfbmFtZTsKKyAgICBpbnQJCWZvbnRzZXQ7CSAgICAvKiBub3QgdXNlZCAqLworeworICAgIC8qIFRPRE86IEFkZCBzdXBwb3J0IGZvciBib2xkIGl0YWxpYyB1bmRlcmxpbmUgcHJvcG9ydGlvbmFsIGV0Yy4uLiAqLworICAgIFN0cjI1NQlzdWdnZXN0ZWRGb250ID0gIlxwTW9uYWNvIjsKKyAgICBpbnQJCXN1Z2dlc3RlZFNpemUgPSA5OworICAgIEZvbnRJbmZvCWZvbnRfaW5mbzsKKyAgICBzaG9ydAlmb250X2lkOworICAgIEd1aUZvbnQJZm9udDsKKworICAgIGlmIChmb250X25hbWUgPT0gTlVMTCkKKyAgICB7CisJLyogRmlyc3QgdHJ5IHRvIGdldCB0aGUgc3VnZ2VzdGVkIGZvbnQgKi8KKwlHZXRGTnVtKHN1Z2dlc3RlZEZvbnQsICZmb250X2lkKTsKKworCWlmIChmb250X2lkID09IDApCisJeworCSAgICAvKiBUaGVuIHBpY2t1cCB0aGUgc3RhbmRhcmQgYXBwbGljYXRpb24gZm9udCAqLworCSAgICBmb250X2lkID0gR2V0QXBwRm9udCgpOworCX0KKwlmb250ID0gKHN1Z2dlc3RlZFNpemUgPDwgMTYpICsgKChsb25nKSBmb250X2lkICYgMHhGRkZGKTsKKyAgICB9CisgICAgZWxzZQorICAgIHsKKwlmb250ID0gZ3VpX21hY19maW5kX2ZvbnQgKGZvbnRfbmFtZSk7CisKKwlpZiAoZm9udCA9PSBOT0ZPTlQpCisJICAgIHJldHVybiBGQUlMOworICAgIH0KKyAgICBndWkubm9ybV9mb250ID0gZm9udDsKKworICAgIFRleHRTaXplIChmb250ID4+IDE2KTsKKyAgICBUZXh0Rm9udCAoZm9udCAmIDB4RkZGRik7CisKKyAgICBHZXRGb250SW5mbyAoJmZvbnRfaW5mbyk7CisKKyAgICBndWkuY2hhcl9hc2NlbnQgPSBmb250X2luZm8uYXNjZW50OworICAgIGd1aS5jaGFyX3dpZHRoICA9IENoYXJXaWR0aCAoJ18nKTsKKyAgICBndWkuY2hhcl9oZWlnaHQgPSBmb250X2luZm8uYXNjZW50ICsgZm9udF9pbmZvLmRlc2NlbnQgKyBwX2xpbmVzcGFjZTsKKworICAgIHJldHVybiBPSzsKKworfQorCisgICAgaW50CitndWlfbWNoX2FkanVzdF9jaGFyc2l6ZSgpCit7CisgICAgRm9udEluZm8gICAgZm9udF9pbmZvOworCisgICAgR2V0Rm9udEluZm8gKCZmb250X2luZm8pOworICAgIGd1aS5jaGFyX2hlaWdodCA9IGZvbnRfaW5mby5hc2NlbnQgKyBmb250X2luZm8uZGVzY2VudCArIHBfbGluZXNwYWNlOworICAgIGd1aS5jaGFyX2FzY2VudCA9IGZvbnRfaW5mby5hc2NlbnQgKyBwX2xpbmVzcGFjZSAvIDI7CisgICAgcmV0dXJuIE9LOworfQorCisvKgorICogR2V0IGEgZm9udCBzdHJ1Y3R1cmUgZm9yIGhpZ2hsaWdodGluZy4KKyAqLworICAgIEd1aUZvbnQKK2d1aV9tY2hfZ2V0X2ZvbnQobmFtZSwgZ2l2ZUVycm9ySWZNaXNzaW5nKQorICAgIGNoYXJfdQkqbmFtZTsKKyAgICBpbnQJCWdpdmVFcnJvcklmTWlzc2luZzsKK3sKKyAgICBHdWlGb250IGZvbnQ7CisKKyAgICBmb250ID0gZ3VpX21hY19maW5kX2ZvbnQobmFtZSk7CisKKyAgICBpZiAoZm9udCA9PSBOT0ZPTlQpCisgICAgeworCWlmIChnaXZlRXJyb3JJZk1pc3NpbmcpCisJICAgIEVNU0cyKF8oZV9mb250KSwgbmFtZSk7CisJcmV0dXJuIE5PRk9OVDsKKyAgICB9CisgICAgLyoKKyAgICAgKiBUT0RPIDogQWNjZXB0IG9ubHkgbW9ub3NwYWNlCisgICAgICovCisKKyAgICByZXR1cm4gZm9udDsKK30KKworLyoKKyAqIFNldCB0aGUgY3VycmVudCB0ZXh0IGZvbnQuCisgKi8KKyAgICB2b2lkCitndWlfbWNoX3NldF9mb250KGZvbnQpCisgICAgR3VpRm9udAlmb250OworeworICAgIC8qCisgICAgICogVE9ETzogbWF5YmUgYXZvaWQgc2V0IGFnYWluIHRoZSBjdXJyZW50IGZvbnQuCisgICAgICovCisgICAgVGV4dFNpemUoZm9udCA+PiAxNik7CisgICAgVGV4dEZvbnQoZm9udCAmIDB4RkZGRik7Cit9CisKKyNpZiAwIC8qIG5vdCB1c2VkICovCisvKgorICogUmV0dXJuIFRSVUUgaWYgdGhlIHR3byBmb250cyBnaXZlbiBhcmUgZXF1aXZhbGVudC4KKyAqLworICAgIGludAorZ3VpX21jaF9zYW1lX2ZvbnQoZjEsIGYyKQorICAgIEd1aUZvbnQJZjE7CisgICAgR3VpRm9udAlmMjsKK3sKKyAgICByZXR1cm4gZjEgPT0gZjI7Cit9CisjZW5kaWYKKworLyoKKyAqIElmIGEgZm9udCBpcyBub3QgZ29pbmcgdG8gYmUgdXNlZCwgZnJlZSBpdHMgc3RydWN0dXJlLgorICovCisgICAgdm9pZAorZ3VpX21jaF9mcmVlX2ZvbnQoZm9udCkKKyAgICBHdWlGb250CWZvbnQ7Cit7CisgICAgLyoKKyAgICAgKiBGcmVlIGZvbnQgd2hlbiAiZm9udCIgaXMgbm90IDAuCisgICAgICogTm90aGluZyB0byBkbyBpbiB0aGUgY3VycmVudCBpbXBsZW1lbnRhdGlvbiwgc2luY2UKKyAgICAgKiBub3RoaW5nIGlzIGFsbG9jYXRlZCBmb3IgZWFjaCBmb250IHVzZWQuCisgICAgICovCit9CisKKyAgICBzdGF0aWMgaW50CitoZXhfZGlnaXQoYykKKyAgICBpbnQJCWM7Cit7CisgICAgaWYgKGlzZGlnaXQoYykpCisJcmV0dXJuIGMgLSAnMCc7CisgICAgYyA9IFRPTE9XRVJfQVNDKGMpOworICAgIGlmIChjID49ICdhJyAmJiBjIDw9ICdmJykKKwlyZXR1cm4gYyAtICdhJyArIDEwOworICAgIHJldHVybiAtMTAwMDsKK30KKworLyoKKyAqIFJldHVybiB0aGUgUGl4ZWwgdmFsdWUgKGNvbG9yKSBmb3IgdGhlIGdpdmVuIGNvbG9yIG5hbWUuICBUaGlzIHJvdXRpbmUgd2FzCisgKiBwcmV0dHkgbXVjaCB0YWtlbiBmcm9tIGV4YW1wbGUgY29kZSBpbiB0aGUgU2lsaWNvbiBHcmFwaGljcyBPU0YvTW90aWYKKyAqIFByb2dyYW1tZXIncyBHdWlkZS4KKyAqIFJldHVybiBJTlZBTENPTE9SIHdoZW4gZmFpbGVkLgorICovCisgICAgZ3VpY29sb3JfVAorZ3VpX21jaF9nZXRfY29sb3IobmFtZSkKKyAgICBjaGFyX3UgKm5hbWU7Cit7CisgICAgLyogVE9ETzogQWRkIHN1cHBvcnQgZm9yIHRoZSBuZXcgbmFtZWQgY29sb3Igb2YgTWFjT1MgOAorICAgICAqLworICAgIFJHQkNvbG9yCU1hY0NvbG9yOworLy8gICAgZ3VpY29sb3JfVAljb2xvciA9IDA7CisKKyAgICB0eXBlZGVmIHN0cnVjdCBndWljb2xvcl90VGFibGUKKyAgICB7CisJY2hhcgkgICAgKm5hbWU7CisJZ3VpY29sb3JfVCAgY29sb3I7CisgICAgfSBndWljb2xvcl90VGFibGU7CisKKyAgICAvKgorICAgICAqIFRoZSBjb21tZW50IGF0IHRoZSBlbmQgb2YgZWFjaCBsaW5lIGlzIHRoZSBzb3VyY2UKKyAgICAgKiAoTWFjLCBXaW5kb3csIFVuaXgpIGFuZCB0aGUgbnVtYmVyIGlzIHRoZSB1bml4IHJnYi50eHQgdmFsdWUKKyAgICAgKi8KKyAgICBzdGF0aWMgZ3VpY29sb3JfdFRhYmxlIHRhYmxlW10gPQorICAgIHsKKwl7IkJsYWNrIiwJUkdCKDB4MDAsIDB4MDAsIDB4MDApfSwKKwl7ImRhcmtncmF5IiwJUkdCKDB4ODAsIDB4ODAsIDB4ODApfSwgLypXKi8KKwl7ImRhcmtncmV5IiwJUkdCKDB4ODAsIDB4ODAsIDB4ODApfSwgLypXKi8KKwl7IkdyYXkiLAlSR0IoMHhDMCwgMHhDMCwgMHhDMCl9LCAvKlcqLworCXsiR3JleSIsCVJHQigweEMwLCAweEMwLCAweEMwKX0sIC8qVyovCisJeyJsaWdodGdyYXkiLAlSR0IoMHhFMCwgMHhFMCwgMHhFMCl9LCAvKlcqLworCXsibGlnaHRncmV5IiwJUkdCKDB4RTAsIDB4RTAsIDB4RTApfSwgLypXKi8KKwl7IndoaXRlIiwJUkdCKDB4RkYsIDB4RkYsIDB4RkYpfSwKKwl7ImRhcmtyZWQiLAlSR0IoMHg4MCwgMHgwMCwgMHgwMCl9LCAvKlcqLworCXsicmVkIiwJCVJHQigweERELCAweDA4LCAweDA2KX0sIC8qTSovCisJeyJsaWdodHJlZCIsCVJHQigweEZGLCAweEEwLCAweEEwKX0sIC8qVyovCisJeyJEYXJrQmx1ZSIsCVJHQigweDAwLCAweDAwLCAweDgwKX0sIC8qVyovCisJeyJCbHVlIiwJUkdCKDB4MDAsIDB4MDAsIDB4RDQpfSwgLypNKi8KKwl7ImxpZ2h0Ymx1ZSIsCVJHQigweEEwLCAweEEwLCAweEZGKX0sIC8qVyovCisJeyJEYXJrR3JlZW4iLAlSR0IoMHgwMCwgMHg4MCwgMHgwMCl9LCAvKlcqLworCXsiR3JlZW4iLAlSR0IoMHgwMCwgMHg2NCwgMHgxMSl9LCAvKk0qLworCXsibGlnaHRncmVlbiIsCVJHQigweEEwLCAweEZGLCAweEEwKX0sIC8qVyovCisJeyJEYXJrQ3lhbiIsCVJHQigweDAwLCAweDgwLCAweDgwKX0sIC8qVyA/MHgzMDdEN0UgKi8KKwl7ImN5YW4iLAlSR0IoMHgwMiwgMHhBQiwgMHhFQSl9LCAvKk0qLworCXsibGlnaHRjeWFuIiwJUkdCKDB4QTAsIDB4RkYsIDB4RkYpfSwgLypXKi8KKwl7ImRhcmttYWdlbnRhIiwJUkdCKDB4ODAsIDB4MDAsIDB4ODApfSwgLypXKi8KKwl7Im1hZ2VudGEiLAlSR0IoMHhGMiwgMHgwOCwgMHg4NCl9LCAvKk0qLworCXsibGlnaHRtYWdlbnRhIixSR0IoMHhGMCwgMHhBMCwgMHhGMCl9LCAvKlcqLworCXsiYnJvd24iLAlSR0IoMHg4MCwgMHg0MCwgMHg0MCl9LCAvKlcqLworCXsieWVsbG93IiwJUkdCKDB4RkMsIDB4RjMsIDB4MDUpfSwgLypNKi8KKwl7ImxpZ2h0eWVsbG93IiwJUkdCKDB4RkYsIDB4RkYsIDB4QTApfSwgLypNKi8KKwl7IlNlYUdyZWVuIiwJUkdCKDB4MkUsIDB4OEIsIDB4NTcpfSwgLypXIDB4NEU4OTc1ICovCisJeyJvcmFuZ2UiLAlSR0IoMHhGQywgMHg4MCwgMHgwMCl9LCAvKlcgMHhGODdBMTcgKi8KKwl7IlB1cnBsZSIsCVJHQigweEEwLCAweDIwLCAweEYwKX0sIC8qVyAweDhlMzVlNSAqLworCXsiU2xhdGVCbHVlIiwJUkdCKDB4NkEsIDB4NUEsIDB4Q0QpfSwgLypXIDB4NzM3Q0ExICovCisJeyJWaW9sZXQiLAlSR0IoMHg4RCwgMHgzOCwgMHhDOSl9LCAvKlUqLworICAgIH07CisKKyAgICBpbnQJCXIsIGcsIGI7CisgICAgaW50CQlpOworCisgICAgaWYgKG5hbWVbMF0gPT0gJyMnICYmIHN0cmxlbigoY2hhciAqKSBuYW1lKSA9PSA3KQorICAgIHsKKwkvKiBOYW1lIGlzIGluICIjcnJnZ2JiIiBmb3JtYXQgKi8KKwlyID0gaGV4X2RpZ2l0KG5hbWVbMV0pICogMTYgKyBoZXhfZGlnaXQobmFtZVsyXSk7CisJZyA9IGhleF9kaWdpdChuYW1lWzNdKSAqIDE2ICsgaGV4X2RpZ2l0KG5hbWVbNF0pOworCWIgPSBoZXhfZGlnaXQobmFtZVs1XSkgKiAxNiArIGhleF9kaWdpdChuYW1lWzZdKTsKKwlpZiAociA8IDAgfHwgZyA8IDAgfHwgYiA8IDApCisJICAgIHJldHVybiBJTlZBTENPTE9SOworCXJldHVybiBSR0IociwgZywgYik7CisgICAgfQorICAgIGVsc2UKKyAgICB7CisJaWYgKFNUUklDTVAgKG5hbWUsICJoaWxpdGUiKSA9PSAwKQorCXsKKwkgICAgTE1HZXRIaWxpdGVSR0IgKCZNYWNDb2xvcik7CisJICAgIHJldHVybiAoUkdCIChNYWNDb2xvci5yZWQgPj4gOCwgTWFjQ29sb3IuZ3JlZW4gPj4gOCwgTWFjQ29sb3IuYmx1ZSA+PiA4KSk7CisJfQorCS8qIENoZWNrIGlmIHRoZSBuYW1lIGlzIG9uZSBvZiB0aGUgY29sb3JzIHdlIGtub3cgKi8KKwlmb3IgKGkgPSAwOyBpIDwgc2l6ZW9mKHRhYmxlKSAvIHNpemVvZih0YWJsZVswXSk7IGkrKykKKwkgICAgaWYgKFNUUklDTVAobmFtZSwgdGFibGVbaV0ubmFtZSkgPT0gMCkKKwkJcmV0dXJuIHRhYmxlW2ldLmNvbG9yOworICAgIH0KKworCisgICAgLyoKKyAgICAgKiBMYXN0IGF0dGVtcHQuIExvb2sgaW4gdGhlIGZpbGUgIiRWSU0vcmdiLnR4dCIuCisgICAgICovCisgICAgeworI2RlZmluZSBMSU5FX0xFTiAxMDAKKwlGSUxFCSpmZDsKKwljaGFyCWxpbmVbTElORV9MRU5dOworCWNoYXJfdQkqZm5hbWU7CisKKyNpZmRlZiBDT0xPTl9BU19QQVRIU0VQCisJZm5hbWUgPSBleHBhbmRfZW52X3NhdmUoKGNoYXJfdSAqKSIkVklNUlVOVElNRTpyZ2IudHh0Iik7CisjZWxzZQorCWZuYW1lID0gZXhwYW5kX2Vudl9zYXZlKChjaGFyX3UgKikiJFZJTVJVTlRJTUUvcmdiLnR4dCIpOworI2VuZGlmCisJaWYgKGZuYW1lID09IE5VTEwpCisJICAgIHJldHVybiBJTlZBTENPTE9SOworCisJZmQgPSBmb3BlbigoY2hhciAqKWZuYW1lLCAicnQiKTsKKwl2aW1fZnJlZShmbmFtZSk7CisJaWYgKGZkID09IE5VTEwpCisJICAgIHJldHVybiBJTlZBTENPTE9SOworCisJd2hpbGUgKCFmZW9mKGZkKSkKKwl7CisJICAgIGludAkJbGVuOworCSAgICBpbnQJCXBvczsKKwkgICAgY2hhcgkqY29sb3I7CisKKwkgICAgZmdldHMobGluZSwgTElORV9MRU4sIGZkKTsKKwkgICAgbGVuID0gc3RybGVuKGxpbmUpOworCisJICAgIGlmIChsZW4gPD0gMSB8fCBsaW5lW2xlbi0xXSAhPSAnXG4nKQorCQljb250aW51ZTsKKworCSAgICBsaW5lW2xlbi0xXSA9ICdcMCc7CisKKwkgICAgaSA9IHNzY2FuZihsaW5lLCAiJWQgJWQgJWQgJW4iLCAmciwgJmcsICZiLCAmcG9zKTsKKwkgICAgaWYgKGkgIT0gMykKKwkJY29udGludWU7CisKKwkgICAgY29sb3IgPSBsaW5lICsgcG9zOworCisJICAgIGlmIChTVFJJQ01QKGNvbG9yLCBuYW1lKSA9PSAwKQorCSAgICB7CisJCWZjbG9zZShmZCk7CisJCXJldHVybiAoZ3VpY29sb3JfVCkgUkdCKHIsIGcsIGIpOworCSAgICB9CisJfQorCWZjbG9zZShmZCk7CisgICAgfQorCisgICAgcmV0dXJuIElOVkFMQ09MT1I7Cit9CisKKy8qCisgKiBTZXQgdGhlIGN1cnJlbnQgdGV4dCBmb3JlZ3JvdW5kIGNvbG9yLgorICovCisgICAgdm9pZAorZ3VpX21jaF9zZXRfZmdfY29sb3IoY29sb3IpCisgICAgZ3VpY29sb3JfVAljb2xvcjsKK3sKKyAgICBSR0JDb2xvciBUaGVDb2xvcjsKKworICAgIFRoZUNvbG9yLnJlZCA9IFJlZChjb2xvcikgKiAweDAxMDE7CisgICAgVGhlQ29sb3IuZ3JlZW4gPSBHcmVlbihjb2xvcikgKiAweDAxMDE7CisgICAgVGhlQ29sb3IuYmx1ZSA9IEJsdWUoY29sb3IpICogMHgwMTAxOworCisgICAgUkdCRm9yZUNvbG9yICgmVGhlQ29sb3IpOworfQorCisvKgorICogU2V0IHRoZSBjdXJyZW50IHRleHQgYmFja2dyb3VuZCBjb2xvci4KKyAqLworICAgIHZvaWQKK2d1aV9tY2hfc2V0X2JnX2NvbG9yKGNvbG9yKQorICAgIGd1aWNvbG9yX1QJY29sb3I7Cit7CisgICAgUkdCQ29sb3IgVGhlQ29sb3I7CisKKyAgICBUaGVDb2xvci5yZWQgPSBSZWQoY29sb3IpICogMHgwMTAxOworICAgIFRoZUNvbG9yLmdyZWVuID0gR3JlZW4oY29sb3IpICogMHgwMTAxOworICAgIFRoZUNvbG9yLmJsdWUgPSBCbHVlKGNvbG9yKSAqIDB4MDEwMTsKKworICAgIFJHQkJhY2tDb2xvciAoJlRoZUNvbG9yKTsKK30KKworICAgIHZvaWQKK2d1aV9tY2hfZHJhd19zdHJpbmcocm93LCBjb2wsIHMsIGxlbiwgZmxhZ3MpCisgICAgaW50CQlyb3c7CisgICAgaW50CQljb2w7CisgICAgY2hhcl91CSpzOworICAgIGludAkJbGVuOworICAgIGludAkJZmxhZ3M7Cit7CisjaWYgZGVmaW5lZChGRUFUX0dVSSkgJiYgZGVmaW5lZChNQUNPU19YKQorICAgIFNJbnQzMglzeXNfdmVyc2lvbjsKKyNlbmRpZgorI2lmZGVmIEZFQVRfTUJZVEUKKyAgICBjaGFyX3UJKnRvZnJlZSA9IE5VTEw7CisKKyAgICBpZiAob3V0cHV0X2NvbnYudmNfdHlwZSAhPSBDT05WX05PTkUpCisgICAgeworCXRvZnJlZSA9IHN0cmluZ19jb252ZXJ0KCZvdXRwdXRfY29udiwgcywgJmxlbik7CisJaWYgKHRvZnJlZSAhPSBOVUxMKQorCSAgICBzID0gdG9mcmVlOworICAgIH0KKyNlbmRpZgorCisjaWYgZGVmaW5lZChGRUFUX0dVSSkgJiYgZGVmaW5lZChNQUNPU19YKQorICAgIC8qCisgICAgICogT24gT1MgWCwgdHJ5IHVzaW5nIFF1YXJ0ei1zdHlsZSB0ZXh0IGFudGlhbGlhc2luZy4KKyAgICAgKi8KKyAgICBzeXNfdmVyc2lvbiA9IDA7CisKKyAgICBHZXN0YWx0KGdlc3RhbHRTeXN0ZW1WZXJzaW9uLCAmc3lzX3ZlcnNpb24pOworICAgIGlmIChzeXNfdmVyc2lvbiA+PSAweDEwMjApCisgICAgeworCS8qIFF1YXJ0eiBhbnRpYWxpYXNpbmcgaXMgYXZhaWxhYmxlIG9ubHkgaW4gT1MgMTAuMiBhbmQgbGF0ZXIuICovCisJVUludDMyIHFkX2ZsYWdzID0gKHBfYW50aWFsaWFzID8KKwkJCSAgICAga1FEVXNlQ0dUZXh0UmVuZGVyaW5nIHwga1FEVXNlQ0dUZXh0TWV0cmljcyA6IDApOworCSh2b2lkKVN3YXBRRFRleHRGbGFncyhxZF9mbGFncyk7CisgICAgfQorCisgICAgaWYgKHN5c192ZXJzaW9uID49IDB4MTAyMCAmJiBwX2FudGlhbGlhcykKKyAgICB7CisJU3R5bGVQYXJhbWV0ZXIgZmFjZTsKKworCWZhY2UgPSBub3JtYWw7CisJaWYgKGZsYWdzICYgRFJBV19CT0xEKQorCSAgICBmYWNlIHw9IGJvbGQ7CisJaWYgKGZsYWdzICYgRFJBV19VTkRFUkwpCisJICAgIGZhY2UgfD0gdW5kZXJsaW5lOworCVRleHRGYWNlKGZhY2UpOworCisJLyogUXVhcnR6IGFudGlhbGlhc2luZyB3b3JrcyBvbmx5IGluIHNyY09yIHRyYW5zZmVyIG1vZGUuICovCisJVGV4dE1vZGUoc3JjT3IpOworCisJaWYgKCEoZmxhZ3MgJiBEUkFXX1RSQU5TUCkpCisJeworCSAgICAvKgorCSAgICAgKiBTaW5jZSB3ZSdyZSB1c2luZyBzcmNPciBtb2RlLCB3ZSBoYXZlIHRvIGNsZWFyIHRoZSBibG9jaworCSAgICAgKiBiZWZvcmUgZHJhd2luZyB0aGUgdGV4dC4gIFRoZSBmb2xsb3dpbmcgaXMgbGlrZSBjYWxsaW5nCisJICAgICAqIGd1aV9tY2hfY2xlYXJfYmxvY2socm93LCBjb2wsIHJvdywgY29sICsgbGVuIC0gMSksCisJICAgICAqIGJ1dCB3aXRob3V0IHNldHRpbmcgdGhlIGJnIGNvbG9yIHRvIGd1aS5iYWNrX3BpeGVsLgorCSAgICAgKi8KKwkgICAgUmVjdCByYzsKKwkgICAgcmMubGVmdCA9IEZJTExfWChjb2wpOworCSAgICByYy50b3AgPSBGSUxMX1kocm93KTsKKwkgICAgcmMucmlnaHQgPSBGSUxMX1goY29sICsgbGVuKSArIChjb2wgKyBsZW4gPT0gQ29sdW1ucyk7CisJICAgIHJjLmJvdHRvbSA9IEZJTExfWShyb3cgKyAxKTsKKwkgICAgRXJhc2VSZWN0KCZyYyk7CisJfQorCisJTW92ZVRvKFRFWFRfWChjb2wpLCBURVhUX1kocm93KSk7CisJRHJhd1RleHQoKGNoYXIqKXMsIDAsIGxlbik7CisgICAgfQorICAgIGVsc2UKKyNlbmRpZgorICAgIHsKKwkvKiBVc2Ugb2xkLXN0eWxlLCBub24tYW50aWFsaWFzZWQgUXVpY2tEcmF3IHRleHQgcmVuZGVyaW5nLiAqLworCVRleHRNb2RlIChzcmNDb3B5KTsKKwlUZXh0RmFjZSAobm9ybWFsKTsKKworICAgIC8qICBTZWxlY3RGb250KGhkYywgZ3VpLmN1cnJGb250KTsgKi8KKworCWlmIChmbGFncyAmIERSQVdfVFJBTlNQKQorCXsKKwkgICAgVGV4dE1vZGUgKHNyY09yKTsKKwl9CisKKwlNb3ZlVG8gKFRFWFRfWChjb2wpLCBURVhUX1kocm93KSk7CisJRHJhd1RleHQgKChjaGFyICopcywgMCwgbGVuKTsKKworCisJaWYgKGZsYWdzICYgRFJBV19CT0xEKQorCXsKKwkgICAgVGV4dE1vZGUgKHNyY09yKTsKKwkgICAgTW92ZVRvIChURVhUX1goY29sKSArIDEsIFRFWFRfWShyb3cpKTsKKwkgICAgRHJhd1RleHQgKChjaGFyICopcywgMCwgbGVuKTsKKwl9CisKKwlpZiAoZmxhZ3MgJiBEUkFXX1VOREVSTCkKKwl7CisJICAgIE1vdmVUbyAoRklMTF9YKGNvbCksIEZJTExfWShyb3cgKyAxKSAtIDEpOworCSAgICBMaW5lVG8gKEZJTExfWChjb2wgKyBsZW4pIC0gMSwgRklMTF9ZKHJvdyArIDEpIC0gMSk7CisJfQorICAgIH0KKworI2lmZGVmIEZFQVRfTUJZVEUKKyAgICB2aW1fZnJlZSh0b2ZyZWUpOworI2VuZGlmCit9CisKKy8qCisgKiBSZXR1cm4gT0sgaWYgdGhlIGtleSB3aXRoIHRoZSB0ZXJtY2FwIG5hbWUgIm5hbWUiIGlzIHN1cHBvcnRlZC4KKyAqLworICAgIGludAorZ3VpX21jaF9oYXNrZXkobmFtZSkKKyAgICBjaGFyX3UgICpuYW1lOworeworICAgIGludCBpOworCisgICAgZm9yIChpID0gMDsgc3BlY2lhbF9rZXlzW2ldLmtleV9zeW0gIT0gKEtleVN5bSkwOyBpKyspCisJaWYgKG5hbWVbMF0gPT0gc3BlY2lhbF9rZXlzW2ldLnZpbV9jb2RlMCAmJgorCQkJCQkgbmFtZVsxXSA9PSBzcGVjaWFsX2tleXNbaV0udmltX2NvZGUxKQorCSAgICByZXR1cm4gT0s7CisgICAgcmV0dXJuIEZBSUw7Cit9CisKKyAgICB2b2lkCitndWlfbWNoX2JlZXAoKQoreworICAgIFN5c0JlZXAgKDEpOyAvKiBTaG91bGQgdGhpcyBiZSAwPyAoPz8/PykgKi8KK30KKworICAgIHZvaWQKK2d1aV9tY2hfZmxhc2gobXNlYykKKyAgICBpbnQJICAgIG1zZWM7Cit7CisgICAgLyogRG8gYSB2aXN1YWwgYmVlcCBieSByZXZlcnNpbmcgdGhlIGZvcmVncm91bmQgYW5kIGJhY2tncm91bmQgY29sb3JzICovCisgICAgUmVjdCAgICByYzsKKworICAgIC8qCisgICAgICogTm90ZTogSW52ZXJ0UmVjdCgpIGV4Y2x1ZGVzIHJpZ2h0IGFuZCBib3R0b20gb2YgcmVjdGFuZ2xlLgorICAgICAqLworICAgIHJjLmxlZnQgPSAwOworICAgIHJjLnRvcCA9IDA7CisgICAgcmMucmlnaHQgPSBndWkubnVtX2NvbHMgKiBndWkuY2hhcl93aWR0aDsKKyAgICByYy5ib3R0b20gPSBndWkubnVtX3Jvd3MgKiBndWkuY2hhcl9oZWlnaHQ7CisgICAgSW52ZXJ0UmVjdCgmcmMpOworCisgICAgdWlfZGVsYXkoKGxvbmcpbXNlYywgVFJVRSk7CQkvKiB3YWl0IGZvciBzb21lIG1zZWMgKi8KKworICAgIEludmVydFJlY3QoJnJjKTsKK30KKworLyoKKyAqIEludmVydCBhIHJlY3RhbmdsZSBmcm9tIHJvdyByLCBjb2x1bW4gYywgZm9yIG5yIHJvd3MgYW5kIG5jIGNvbHVtbnMuCisgKi8KKyAgICB2b2lkCitndWlfbWNoX2ludmVydF9yZWN0YW5nbGUociwgYywgbnIsIG5jKQorICAgIGludAkJcjsKKyAgICBpbnQJCWM7CisgICAgaW50CQlucjsKKyAgICBpbnQJCW5jOworeworICAgIFJlY3QJcmM7CisKKyAgICAvKgorICAgICAqIE5vdGU6IEludmVydFJlY3QoKSBleGNsdWRlcyByaWdodCBhbmQgYm90dG9tIG9mIHJlY3RhbmdsZS4KKyAgICAgKi8KKyAgICByYy5sZWZ0ID0gRklMTF9YKGMpOworICAgIHJjLnRvcCA9IEZJTExfWShyKTsKKyAgICByYy5yaWdodCA9IHJjLmxlZnQgKyBuYyAqIGd1aS5jaGFyX3dpZHRoOworICAgIHJjLmJvdHRvbSA9IHJjLnRvcCArIG5yICogZ3VpLmNoYXJfaGVpZ2h0OworICAgIEludmVydFJlY3QoJnJjKTsKKworfQorCisvKgorICogSWNvbmlmeSB0aGUgR1VJIHdpbmRvdy4KKyAqLworICAgIHZvaWQKK2d1aV9tY2hfaWNvbmlmeSgpCit7CisgICAgLyogVE9ETzogZmluZCBvdXQgd2hhdCBjb3VsZCByZXBsYWNlIGljb25pZnkKKyAgICAgKgkgICAgIC13aW5kb3cgc2hhZGU/CisgICAgICoJICAgICAtaGlkZSBhcHBsaWNhdGlvbj8KKyAgICAgKi8KK30KKworI2lmIGRlZmluZWQoRkVBVF9FVkFMKSB8fCBkZWZpbmVkKFBST1RPKQorLyoKKyAqIEJyaW5nIHRoZSBWaW0gd2luZG93IHRvIHRoZSBmb3JlZ3JvdW5kLgorICovCisgICAgdm9pZAorZ3VpX21jaF9zZXRfZm9yZWdyb3VuZCgpCit7CisgICAgLyogVE9ETyAqLworfQorI2VuZGlmCisKKy8qCisgKiBEcmF3IGEgY3Vyc29yIHdpdGhvdXQgZm9jdXMuCisgKi8KKyAgICB2b2lkCitndWlfbWNoX2RyYXdfaG9sbG93X2N1cnNvcihjb2xvcikKKyAgICBndWljb2xvcl9UCWNvbG9yOworeworICAgIFJlY3QgcmM7CisKKyAgICBndWlfbWNoX3NldF9mZ19jb2xvcihjb2xvcik7CisKKyAgICAvKgorICAgICAqIE5vdGU6IEZyYW1lUmVjdCgpIGV4Y2x1ZGVzIHJpZ2h0IGFuZCBib3R0b20gb2YgcmVjdGFuZ2xlLgorICAgICAqLworICAgIHJjLmxlZnQgPSBGSUxMX1goZ3VpLmNvbCk7CisgICAgcmMudG9wID0gRklMTF9ZKGd1aS5yb3cpOworICAgIHJjLnJpZ2h0ID0gcmMubGVmdCArIGd1aS5jaGFyX3dpZHRoOworICAgIHJjLmJvdHRvbSA9IHJjLnRvcCArIGd1aS5jaGFyX2hlaWdodDsKKworICAgIGd1aV9tY2hfc2V0X2ZnX2NvbG9yKGNvbG9yKTsKKworICAgIEZyYW1lUmVjdCAoJnJjKTsKK30KKworLyoKKyAqIERyYXcgcGFydCBvZiBhIGN1cnNvciwgb25seSB3IHBpeGVscyB3aWRlLCBhbmQgaCBwaXhlbHMgaGlnaC4KKyAqLworICAgIHZvaWQKK2d1aV9tY2hfZHJhd19wYXJ0X2N1cnNvcih3LCBoLCBjb2xvcikKKyAgICBpbnQJCXc7CisgICAgaW50CQloOworICAgIGd1aWNvbG9yX1QJY29sb3I7Cit7CisgICAgUmVjdCByYzsKKworI2lmZGVmIEZFQVRfUklHSFRMRUZUCisgICAgLyogdmVydGljYWwgbGluZSBzaG91bGQgYmUgb24gdGhlIHJpZ2h0IG9mIGN1cnJlbnQgcG9pbnQgKi8KKyAgICBpZiAoQ1VSU09SX0JBUl9SSUdIVCkKKwlyYy5sZWZ0ID0gRklMTF9YKGd1aS5jb2wgKyAxKSAtIHc7CisgICAgZWxzZQorI2VuZGlmCisJcmMubGVmdCA9IEZJTExfWChndWkuY29sKTsKKyAgICByYy50b3AgPSBGSUxMX1koZ3VpLnJvdykgKyBndWkuY2hhcl9oZWlnaHQgLSBoOworICAgIHJjLnJpZ2h0ID0gcmMubGVmdCArIHc7CisgICAgcmMuYm90dG9tID0gcmMudG9wICsgaDsKKworICAgIGd1aV9tY2hfc2V0X2ZnX2NvbG9yKGNvbG9yKTsKKworICAgIFBhaW50UmVjdCAoJnJjKTsKK30KKworCisKKy8qCisgKiBDYXRjaCB1cCB3aXRoIGFueSBxdWV1ZWQgWCBldmVudHMuICBUaGlzIG1heSBwdXQga2V5Ym9hcmQgaW5wdXQgaW50byB0aGUKKyAqIGlucHV0IGJ1ZmZlciwgY2FsbCByZXNpemUgY2FsbC1iYWNrcywgdHJpZ2dlciB0aW1lcnMgZXRjLiAgSWYgdGhlcmUgaXMKKyAqIG5vdGhpbmcgaW4gdGhlIFggZXZlbnQgcXVldWUgKCYgbm8gdGltZXJzIHBlbmRpbmcpLCB0aGVuIHdlIHJldHVybgorICogaW1tZWRpYXRlbHkuCisgKi8KKyAgICB2b2lkCitndWlfbWNoX3VwZGF0ZSgpCit7CisgICAgLyogVE9ETzogZmluZCB3aGF0IHRvIGRvCisgICAgICoJICAgICBtYXliZSBjYWxsIGd1aV9tY2hfd2FpdF9mb3JfY2hhcnMgKDApCisgICAgICoJICAgICBtb3JlIGxpa2UgbG9vayBhdCBFdmVudFF1ZXVlIHRoZW4KKyAgICAgKgkgICAgIGNhbGwgaGVhcnQgb2YgZ3VpX21jaF93YWl0X2Zvcl9jaGFyczsKKyAgICAgKgorICAgICAqCWlmIChldmVudHRoZXIpCisgICAgICoJICAgIGd1aV9tYWNfaGFuZGxlX2V2ZW50KCZldmVudCk7CisgICAgICovCisgICAgRXZlbnRSZWNvcmQgdGhlRXZlbnQ7CisKKyAgICBpZiAoRXZlbnRBdmFpbCAoZXZlcnlFdmVudCwgJnRoZUV2ZW50KSkKKwlpZiAodGhlRXZlbnQud2hhdCAhPSBudWxsRXZlbnQpCisJICAgIGd1aV9tY2hfd2FpdF9mb3JfY2hhcnMoMCk7Cit9CisKKy8qCisgKiBTaW1wbGUgd3JhcHBlciB0byBuZWdsZWN0IG1vcmUgZWFzaWx5IHRoZSB0aW1lCisgKiBzcGVudCBpbnNpZGUgV2FpdE5leHRFdmVudCB3aGlsZSBwcm9maWxpbmcuCisgKi8KKworI2lmIGRlZmluZWQoX19NV0VSS1NfXykgIC8qIG9ubHkgaW4gQ29kZXdhcnJpb3IgKi8KKyMgcHJhZ21hIHByb2ZpbGUgcmVzZXQKKyNlbmRpZgorICAgIHBhc2NhbAorICAgIEJvb2xlYW4KK1dhaXROZXh0RXZlbnRXcnAgKEV2ZW50TWFzayBldmVudE1hc2ssIEV2ZW50UmVjb3JkICp0aGVFdmVudCwgVUludDMyIHNsZWVwLCBSZ25IYW5kbGUgbW91c2VSZ24pCit7CisgICAgaWYgKCgobG9uZykgc2xlZXApIDwgLTEpCisJc2xlZXAgPSAzMjc2NzsKKyAgICByZXR1cm4gV2FpdE5leHRFdmVudChldmVudE1hc2ssIHRoZUV2ZW50LCBzbGVlcCwgbW91c2VSZ24pOworfQorCisvKgorICogR1VJIGlucHV0IHJvdXRpbmUgY2FsbGVkIGJ5IGd1aV93YWl0X2Zvcl9jaGFycygpLiAgV2FpdHMgZm9yIGEgY2hhcmFjdGVyCisgKiBmcm9tIHRoZSBrZXlib2FyZC4KKyAqICB3dGltZSA9PSAtMQkgICAgV2FpdCBmb3JldmVyLgorICogIHd0aW1lID09IDAJICAgIFRoaXMgc2hvdWxkIG5ldmVyIGhhcHBlbi4KKyAqICB3dGltZSA+IDAJICAgIFdhaXQgd3RpbWUgbWlsbGlzZWNvbmRzIGZvciBhIGNoYXJhY3Rlci4KKyAqIFJldHVybnMgT0sgaWYgYSBjaGFyYWN0ZXIgd2FzIGZvdW5kIHRvIGJlIGF2YWlsYWJsZSB3aXRoaW4gdGhlIGdpdmVuIHRpbWUsCisgKiBvciBGQUlMIG90aGVyd2lzZS4KKyAqLworI2lmIGRlZmluZWQoX19NV0VSS1NfXykgIC8qIG9ubHkgaW4gQ29kZXdhcnJpb3IgKi8KKyMgcHJhZ21hIHByb2ZpbGUgcmVzZXQKKyNlbmRpZgorICAgIGludAorZ3VpX21jaF93YWl0X2Zvcl9jaGFycyh3dGltZSkKKyAgICBpbnQJICAgIHd0aW1lOworeworICAgIEV2ZW50TWFzawltYXNrICA9IChldmVyeUV2ZW50KTsKKyAgICBFdmVudFJlY29yZCBldmVudDsKKyAgICBsb25nCWVudHJ5VGljazsKKyAgICBsb25nCWN1cnJlbnRUaWNrOworICAgIGxvbmcJc2xlZXBweVRpY2s7CisKKyAgICAvKiBJZiB3ZSBhcmUgcHJvdmlkaW5nIGxpZmUgZmVlZGJhY2sgd2l0aCB0aGUgc2Nyb2xsYmFyLAorICAgICAqIHdlIGRvbid0IHdhbnQgdG8gdHJ5IHRvIHdhaXQgZm9yIGFuIGV2ZW50LCBvciBlbHNlCisgICAgICogdGhlcmUgd29uJ3QgYmUgYW55IGxpZmUgZmVlZGJhY2suCisgICAgICovCisgICAgaWYgKGRyYWdnZWRfc2IgIT0gTlVMTCkKKwlyZXR1cm4gRkFJTDsKKwkvKiBUT0RPOiBDaGVjayBpZiBGQUlMIGlzIHRoZSBwcm9wZXIgcmV0dXJuIGNvZGUgKi8KKworICAgIGVudHJ5VGljayA9IFRpY2tDb3VudCgpOworCisgICAgYWxsb3dfc2Nyb2xsYmFyID0gVFJVRTsKKworICAgIGRvCisgICAgeworLyoJaWYgKGRyYWdSZWN0Q29udHJvbCA9PSBrQ3JlYXRlRW1wdHkpCisJeworCSAgICBkcmFnUmduID0gTlVMTDsKKwkgICAgZHJhZ1JlY3RDb250cm9sID0ga05vdGhpbmc7CisJfQorCWVsc2UqLyBpZiAoZHJhZ1JlY3RDb250cm9sID09IGtDcmVhdGVSZWN0KQorCXsKKwkgICAgZHJhZ1JnbiA9IGN1cnNvclJnbjsKKwkgICAgUmVjdFJnbiAoZHJhZ1JnbiwgJmRyYWdSZWN0KTsKKwkgICAgZHJhZ1JlY3RDb250cm9sID0ga05vdGhpbmc7CisJfQorCS8qCisJICogRG9uJ3QgdXNlIGd1aV9tY2hfdXBkYXRlKCkgYmVjYXVzZSB0aGVuIHdlIHdpbGwgc3Bpbi1sb2NrIHVudGlsIGEKKwkgKiBjaGFyIGFycml2ZXMsIGluc3RlYWQgd2UgdXNlIFdhaXROZXh0RXZlbnRXcnAoKSB0byBoYW5nIHVudGlsIGFuCisJICogZXZlbnQgYXJyaXZlcy4gIE5vIG5lZWQgdG8gY2hlY2sgZm9yIGlucHV0X2J1Zl9mdWxsIGJlY2F1c2Ugd2UgYXJlCisJICogcmV0dXJuaW5nIGFzIHNvb24gYXMgaXQgY29udGFpbnMgYSBzaW5nbGUgY2hhci4KKwkgKi8KKwkvKiBUT0RPOiByZWR1Y2Ugd3RpbWUgYWNjb3JkaW5seT8/PyAgKi8KKwlpZiAod3RpbWUgPiAtMSkKKwkgICAgc2xlZXBweVRpY2sgPSA2MCp3dGltZS8xMDAwOworCWVsc2UKKwkgICAgc2xlZXBweVRpY2sgPSAzMjc2NzsKKwlpZiAoV2FpdE5leHRFdmVudFdycCAobWFzaywgJmV2ZW50LCBzbGVlcHB5VGljaywgZHJhZ1JnbikpCisJeworI2lmZGVmIFVTRV9TSU9VWAorCSAgICBpZiAoIVNJT1VYSGFuZGxlT25lRXZlbnQoJmV2ZW50KSkKKyNlbmRpZgorCQlndWlfbWFjX2hhbmRsZV9ldmVudCAoJmV2ZW50KTsKKwkgICAgaWYgKGlucHV0X2F2YWlsYWJsZSgpKQorCSAgICB7CisJCWFsbG93X3Njcm9sbGJhciA9IEZBTFNFOworCQlyZXR1cm4gT0s7CisJICAgIH0KKwl9CisJY3VycmVudFRpY2sgPSBUaWNrQ291bnQoKTsKKyAgICB9CisgICAgd2hpbGUgKCh3dGltZSA9PSAtMSkgfHwgKChjdXJyZW50VGljayAtIGVudHJ5VGljaykgPCA2MCp3dGltZS8xMDAwKSk7CisKKyAgICBhbGxvd19zY3JvbGxiYXIgPSBGQUxTRTsKKyAgICByZXR1cm4gRkFJTDsKK30KKworI2lmIGRlZmluZWQoX19NV0VSS1NfXykgIC8qIG9ubHkgaW4gQ29kZXdhcnJpb3IgKi8KKyMgcHJhZ21hIHByb2ZpbGUgcmVzZXQKKyNlbmRpZgorCisvKgorICogT3V0cHV0IHJvdXRpbmVzLgorICovCisKKy8qIEZsdXNoIGFueSBvdXRwdXQgdG8gdGhlIHNjcmVlbiAqLworICAgIHZvaWQKK2d1aV9tY2hfZmx1c2goKQoreworICAgIC8qIFRPRE86IElzIGFueXRoaW5nIG5lZWRlZCBoZXJlPyAqLworfQorCisvKgorICogQ2xlYXIgYSByZWN0YW5ndWxhciByZWdpb24gb2YgdGhlIHNjcmVlbiBmcm9tIHRleHQgcG9zIChyb3cxLCBjb2wxKSB0bworICogKHJvdzIsIGNvbDIpIGluY2x1c2l2ZS4KKyAqLworICAgIHZvaWQKK2d1aV9tY2hfY2xlYXJfYmxvY2socm93MSwgY29sMSwgcm93MiwgY29sMikKKyAgICBpbnQJCXJvdzE7CisgICAgaW50CQljb2wxOworICAgIGludAkJcm93MjsKKyAgICBpbnQJCWNvbDI7Cit7CisgICAgUmVjdCByYzsKKworICAgIC8qCisgICAgICogQ2xlYXIgb25lIGV4dHJhIHBpeGVsIGF0IHRoZSBmYXIgcmlnaHQsIGZvciB3aGVuIGJvbGQgY2hhcmFjdGVycyBoYXZlCisgICAgICogc3BpbGxlZCBvdmVyIHRvIHRoZSBuZXh0IGNvbHVtbi4KKyAgICAgKi8KKyAgICByYy5sZWZ0ID0gRklMTF9YKGNvbDEpOworICAgIHJjLnRvcCA9IEZJTExfWShyb3cxKTsKKyAgICByYy5yaWdodCA9IEZJTExfWChjb2wyICsgMSkgKyAoY29sMiA9PSBDb2x1bW5zIC0gMSk7CisgICAgcmMuYm90dG9tID0gRklMTF9ZKHJvdzIgKyAxKTsKKworICAgIGd1aV9tY2hfc2V0X2JnX2NvbG9yKGd1aS5iYWNrX3BpeGVsKTsKKyAgICBFcmFzZVJlY3QgKCZyYyk7Cit9CisKKy8qCisgKiBDbGVhciB0aGUgd2hvbGUgdGV4dCB3aW5kb3cuCisgKi8KKyAgICB2b2lkCitndWlfbWNoX2NsZWFyX2FsbCgpCit7CisgICAgUmVjdAlyYzsKKworICAgIHJjLmxlZnQgPSAwOworICAgIHJjLnRvcCA9IDA7CisgICAgcmMucmlnaHQgPSBDb2x1bW5zICogZ3VpLmNoYXJfd2lkdGggKyAyICogZ3VpLmJvcmRlcl93aWR0aDsKKyAgICByYy5ib3R0b20gPSBSb3dzICogZ3VpLmNoYXJfaGVpZ2h0ICsgMiAqIGd1aS5ib3JkZXJfd2lkdGg7CisKKyAgICBndWlfbWNoX3NldF9iZ19jb2xvcihndWkuYmFja19waXhlbCk7CisgICAgRXJhc2VSZWN0KCZyYyk7CisvKiAgZ3VpX21jaF9zZXRfZmdfY29sb3IoZ3VpLm5vcm1fcGl4ZWwpOworICAgIEZyYW1lUmVjdCgmcmMpOworKi8KK30KKworLyoKKyAqIERlbGV0ZSB0aGUgZ2l2ZW4gbnVtYmVyIG9mIGxpbmVzIGZyb20gdGhlIGdpdmVuIHJvdywgc2Nyb2xsaW5nIHVwIGFueQorICogdGV4dCBmdXJ0aGVyIGRvd24gd2l0aGluIHRoZSBzY3JvbGwgcmVnaW9uLgorICovCisgICAgdm9pZAorZ3VpX21jaF9kZWxldGVfbGluZXMocm93LCBudW1fbGluZXMpCisgICAgaW50CQlyb3c7CisgICAgaW50CQludW1fbGluZXM7Cit7CisgICAgUmVjdAlyYzsKKworICAgIC8qIGNoYW5nZWQgd2l0aG91dCBjaGVja2luZyEgKi8KKyAgICByYy5sZWZ0ID0gRklMTF9YKGd1aS5zY3JvbGxfcmVnaW9uX2xlZnQpOworICAgIHJjLnJpZ2h0ID0gRklMTF9YKGd1aS5zY3JvbGxfcmVnaW9uX3JpZ2h0ICsgMSk7CisgICAgcmMudG9wID0gRklMTF9ZKHJvdyk7CisgICAgcmMuYm90dG9tID0gRklMTF9ZKGd1aS5zY3JvbGxfcmVnaW9uX2JvdCArIDEpOworCisgICAgZ3VpX21jaF9zZXRfYmdfY29sb3IoZ3VpLmJhY2tfcGl4ZWwpOworICAgIFNjcm9sbFJlY3QgKCZyYywgMCwgLW51bV9saW5lcyAqIGd1aS5jaGFyX2hlaWdodCwgKFJnbkhhbmRsZSkgbmlsKTsKKworICAgIGd1aV9jbGVhcl9ibG9jayhndWkuc2Nyb2xsX3JlZ2lvbl9ib3QgLSBudW1fbGluZXMgKyAxLAorCQkJCQkJICAgICAgIGd1aS5zY3JvbGxfcmVnaW9uX2xlZnQsCisJZ3VpLnNjcm9sbF9yZWdpb25fYm90LCBndWkuc2Nyb2xsX3JlZ2lvbl9yaWdodCk7Cit9CisKKy8qCisgKiBJbnNlcnQgdGhlIGdpdmVuIG51bWJlciBvZiBsaW5lcyBiZWZvcmUgdGhlIGdpdmVuIHJvdywgc2Nyb2xsaW5nIGRvd24gYW55CisgKiBmb2xsb3dpbmcgdGV4dCB3aXRoaW4gdGhlIHNjcm9sbCByZWdpb24uCisgKi8KKyAgICB2b2lkCitndWlfbWNoX2luc2VydF9saW5lcyhyb3csIG51bV9saW5lcykKKyAgICBpbnQJCXJvdzsKKyAgICBpbnQJCW51bV9saW5lczsKK3sKKyAgICBSZWN0IHJjOworCisgICAgcmMubGVmdCA9IEZJTExfWChndWkuc2Nyb2xsX3JlZ2lvbl9sZWZ0KTsKKyAgICByYy5yaWdodCA9IEZJTExfWChndWkuc2Nyb2xsX3JlZ2lvbl9yaWdodCArIDEpOworICAgIHJjLnRvcCA9IEZJTExfWShyb3cpOworICAgIHJjLmJvdHRvbSA9IEZJTExfWShndWkuc2Nyb2xsX3JlZ2lvbl9ib3QgKyAxKTsKKworICAgIGd1aV9tY2hfc2V0X2JnX2NvbG9yKGd1aS5iYWNrX3BpeGVsKTsKKworICAgIFNjcm9sbFJlY3QgKCZyYywgMCwgZ3VpLmNoYXJfaGVpZ2h0ICogbnVtX2xpbmVzLCAoUmduSGFuZGxlKSBuaWwpOworCisgICAgLyogVXBkYXRlIGd1aS5jdXJzb3Jfcm93IGlmIHRoZSBjdXJzb3Igc2Nyb2xsZWQgb3IgY29waWVkIG92ZXIgKi8KKyAgICBpZiAoZ3VpLmN1cnNvcl9yb3cgPj0gZ3VpLnJvdworCSAgICAmJiBndWkuY3Vyc29yX2NvbCA+PSBndWkuc2Nyb2xsX3JlZ2lvbl9sZWZ0CisJICAgICYmIGd1aS5jdXJzb3JfY29sIDw9IGd1aS5zY3JvbGxfcmVnaW9uX3JpZ2h0KQorICAgIHsKKwlpZiAoZ3VpLmN1cnNvcl9yb3cgPD0gZ3VpLnNjcm9sbF9yZWdpb25fYm90IC0gbnVtX2xpbmVzKQorCSAgICBndWkuY3Vyc29yX3JvdyArPSBudW1fbGluZXM7CisJZWxzZSBpZiAoZ3VpLmN1cnNvcl9yb3cgPD0gZ3VpLnNjcm9sbF9yZWdpb25fYm90KQorCSAgICBndWkuY3Vyc29yX2lzX3ZhbGlkID0gRkFMU0U7CisgICAgfQorCisgICAgZ3VpX2NsZWFyX2Jsb2NrKHJvdywgZ3VpLnNjcm9sbF9yZWdpb25fbGVmdCwKKwkJCQlyb3cgKyBudW1fbGluZXMgLSAxLCBndWkuc2Nyb2xsX3JlZ2lvbl9yaWdodCk7Cit9CisKKyAgICAvKgorICAgICAqIFRPRE86IGFkZCBhIHZpbSBmb3JtYXQgdG8gdGhlIGNsaXBib2FyZCB3aGljaCByZW1lbWJlcgorICAgICAqCSAgICAgTElORVdJU0UsIENIQVJXSVNFLCBCTE9DS1dJU0UKKyAgICAgKi8KKworICAgIHZvaWQKK2NsaXBfbWNoX3JlcXVlc3Rfc2VsZWN0aW9uKGNiZCkKKyAgICBWaW1DbGlwYm9hcmQgKmNiZDsKK3sKKworICAgIEhhbmRsZQl0ZXh0T2ZDbGlwOworI2lmZGVmIFVTRV9DQVJCT05JWkVECisgICAgU2l6ZQlzY3JhcFNpemU7CisgICAgU2NyYXBGbGF2b3JGbGFncwlzY3JhcEZsYWdzOworICAgIFNjcmFwUmVmICAgIHNjcmFwID0gbmlsOworICAgIE9TU3RhdHVzCWVycm9yOworI2Vsc2UKKyAgICBsb25nCXNjcmFwT2Zmc2V0OworICAgIGxvbmcJc2NyYXBTaXplOworI2VuZGlmCisgICAgaW50CQl0eXBlOworICAgIGNoYXIJKnNlYXJjaENSOworICAgIGNoYXJfdQkqdGVtcGNsaXA7CisKKworI2lmZGVmIFVTRV9DQVJCT05JWkVECisgICAgZXJyb3IgPSBHZXRDdXJyZW50U2NyYXAgKCZzY3JhcCk7CisgICAgaWYgKGVycm9yICE9IG5vRXJyKQorCXJldHVybjsKKworICAgIGVycm9yID0gR2V0U2NyYXBGbGF2b3JGbGFncyhzY3JhcCwga1NjcmFwRmxhdm9yVHlwZVRleHQsICZzY3JhcEZsYWdzKTsKKyAgICBpZiAoZXJyb3IgIT0gbm9FcnIpCisJcmV0dXJuOworCisgICAgZXJyb3IgPSBHZXRTY3JhcEZsYXZvclNpemUgKHNjcmFwLCBrU2NyYXBGbGF2b3JUeXBlVGV4dCwgJnNjcmFwU2l6ZSk7CisgICAgaWYgKGVycm9yICE9IG5vRXJyKQorCXJldHVybjsKKworICAgIFJlc2VydmVNZW0gKHNjcmFwU2l6ZSk7CisjZWxzZQorICAgIC8qIENhbGwgdG8gTG9hZFNjcmFwIHNlZW0gdG8gYXZvaWQgcHJvYmxlbSB3aXRoIGNyYXNoIG9uIGZpcnN0IHBhc3RlICovCisgICAgc2NyYXBTaXplID0gTG9hZFNjcmFwKCk7CisgICAgc2NyYXBTaXplID0gR2V0U2NyYXAobmlsLCAnVEVYVCcsICZzY3JhcE9mZnNldCk7CisKKyAgICBpZiAoc2NyYXBTaXplID4gMCkKKyNlbmRpZgorICAgIHsKKyNpZmRlZiBVU0VfQ0FSQk9OSVpFRAorCS8qIEluIENBUkJPTiB3ZSBkb24ndCBuZWVkIGEgSGFuZGxlLCBhIHBvaW50ZXIgaXMgZ29vZCAqLworCXRleHRPZkNsaXAgPSBOZXdIYW5kbGUgKHNjcmFwU2l6ZSk7CisJLyogdGVtcGNsaXAgPSBsYWxsb2Moc2NyYXBTaXplKzEsIFRSVUUpOyAqLworI2Vsc2UKKwl0ZXh0T2ZDbGlwID0gTmV3SGFuZGxlKDApOworI2VuZGlmCisJSExvY2sgKHRleHRPZkNsaXApOworI2lmZGVmIFVTRV9DQVJCT05JWkVECisJZXJyb3IgPSBHZXRTY3JhcEZsYXZvckRhdGEgKHNjcmFwLCBrU2NyYXBGbGF2b3JUeXBlVGV4dCwgJnNjcmFwU2l6ZSwgKnRleHRPZkNsaXApOworI2Vsc2UKKwlzY3JhcFNpemUgPSBHZXRTY3JhcCh0ZXh0T2ZDbGlwLCAnVEVYVCcsICZzY3JhcE9mZnNldCk7CisjZW5kaWYKKworCXR5cGUgPSAoc3RyY2hyKCp0ZXh0T2ZDbGlwLCAnXHInKSAhPSBOVUxMKSA/IE1MSU5FIDogTUNIQVI7CisKKwl0ZW1wY2xpcCA9IGxhbGxvYyhzY3JhcFNpemUrMSwgVFJVRSk7CisJU1RSTkNQWSh0ZW1wY2xpcCwgKnRleHRPZkNsaXAsIHNjcmFwU2l6ZSk7CisJdGVtcGNsaXBbc2NyYXBTaXplXSA9IDA7CisKKwlzZWFyY2hDUiA9IChjaGFyICopdGVtcGNsaXA7CisJd2hpbGUgKHNlYXJjaENSICE9IE5VTEwpCisJeworCSAgICBzZWFyY2hDUiA9IHN0cmNocihzZWFyY2hDUiwgJ1xyJyk7CisKKwkgICAgaWYgKHNlYXJjaENSICE9IE5VTEwpCisJCXNlYXJjaENSWzBdID0gJ1xuJzsKKworCX0KKworI2lmZGVmIEZFQVRfTUJZVEUKKwlpZiAoaW5wdXRfY29udi52Y190eXBlICE9IENPTlZfTk9ORSkKKwl7CisJICAgIGNoYXJfdQkqdG87CisJICAgIGludAkJbCA9IHNjcmFwU2l6ZTsKKworCSAgICB0byA9IHN0cmluZ19jb252ZXJ0KCZpbnB1dF9jb252LCB0ZW1wY2xpcCwgJmwpOworCSAgICBpZiAodG8gIT0gTlVMTCkKKwkgICAgeworCQl2aW1fZnJlZSh0ZW1wY2xpcCk7CisJCXRlbXBjbGlwID0gdG87CisJCXNjcmFwU2l6ZSA9IGw7CisJICAgIH0KKwl9CisjZW5kaWYKKwljbGlwX3lhbmtfc2VsZWN0aW9uKHR5cGUsIHRlbXBjbGlwLCBzY3JhcFNpemUsIGNiZCk7CisKKwl2aW1fZnJlZSh0ZW1wY2xpcCk7CisJSFVubG9jayh0ZXh0T2ZDbGlwKTsKKworCURpc3Bvc2VIYW5kbGUodGV4dE9mQ2xpcCk7CisgICAgfQorfQorCisgICAgdm9pZAorY2xpcF9tY2hfbG9zZV9zZWxlY3Rpb24oY2JkKQorICAgIFZpbUNsaXBib2FyZCAqY2JkOworeworICAgIC8qCisgICAgICogVE9ETzogUmVhbGx5IG5vdGhpbmcgdG8gZG8/CisgICAgICovCit9CisKKyAgICBpbnQKK2NsaXBfbWNoX293bl9zZWxlY3Rpb24oY2JkKQorICAgIFZpbUNsaXBib2FyZCAqY2JkOworeworICAgIHJldHVybiBPSzsKK30KKworLyoKKyAqIFNlbmQgdGhlIGN1cnJlbnQgc2VsZWN0aW9uIHRvIHRoZSBjbGlwYm9hcmQuCisgKi8KKyAgICB2b2lkCitjbGlwX21jaF9zZXRfc2VsZWN0aW9uKGNiZCkKKyAgICBWaW1DbGlwYm9hcmQgKmNiZDsKK3sKKyAgICBIYW5kbGUJdGV4dE9mQ2xpcDsKKyAgICBsb25nCXNjcmFwU2l6ZTsKKyAgICBpbnQJCXR5cGU7CisjaWZkZWYgVVNFX0NBUkJPTklaRUQKKyAgICBTY3JhcFJlZiAgICBzY3JhcDsKKyNlbmRpZgorCisgICAgY2hhcl91CSpzdHIgPSBOVUxMOworCisgICAgaWYgKCFjYmQtPm93bmVkKQorCXJldHVybjsKKworICAgIGNsaXBfZ2V0X3NlbGVjdGlvbihjYmQpOworCisgICAgLyoKKyAgICAgKiBPbmNlIHdlIHNldCB0aGUgY2xpcGJvYXJkLCBsb3NlIG93bmVyc2hpcC4gIElmIGFub3RoZXIgYXBwbGljYXRpb24gc2V0cworICAgICAqIHRoZSBjbGlwYm9hcmQsIHdlIGRvbid0IHdhbnQgdG8gdGhpbmsgdGhhdCB3ZSBzdGlsbCBvd24gaXQuCisgICAgICoKKyAgICAgKi8KKworICAgIGNiZC0+b3duZWQgPSBGQUxTRTsKKworICAgIHR5cGUgPSBjbGlwX2NvbnZlcnRfc2VsZWN0aW9uKCZzdHIsIChsb25nX3UgKikgJnNjcmFwU2l6ZSwgY2JkKTsKKworI2lmZGVmIEZFQVRfTUJZVEUKKyAgICBpZiAoc3RyICE9IE5VTEwgJiYgb3V0cHV0X2NvbnYudmNfdHlwZSAhPSBDT05WX05PTkUpCisgICAgeworCWNoYXJfdQkqdG87CisJaW50CWwgPSBzY3JhcFNpemU7CisKKwl0byA9IHN0cmluZ19jb252ZXJ0KCZvdXRwdXRfY29udiwgc3RyLCAmbCk7CisJaWYgKHRvICE9IE5VTEwpCisJeworCSAgICB2aW1fZnJlZShzdHIpOworCSAgICBzdHIgPSB0bzsKKwkgICAgc2NyYXBTaXplID0gbDsKKwl9CisgICAgfQorI2VuZGlmCisKKyAgICBpZiAodHlwZSA+PSAwKQorICAgIHsKKyNpZmRlZiBVU0VfQ0FSQk9OSVpFRAorCUNsZWFyQ3VycmVudFNjcmFwKCk7CisjZWxzZQorCVplcm9TY3JhcCgpOworI2VuZGlmCisKKwl0ZXh0T2ZDbGlwID0gTmV3SGFuZGxlKHNjcmFwU2l6ZSk7CisJSExvY2sodGV4dE9mQ2xpcCk7CisKKwlTVFJOQ1BZKCp0ZXh0T2ZDbGlwLCBzdHIsIHNjcmFwU2l6ZSk7CisjaWZkZWYgVVNFX0NBUkJPTklaRUQKKwlHZXRDdXJyZW50U2NyYXAgKCZzY3JhcCk7CisJUHV0U2NyYXBGbGF2b3Ioc2NyYXAsIGtTY3JhcEZsYXZvclR5cGVUZXh0LCBrU2NyYXBGbGF2b3JNYXNrTm9uZSwKKwkJCXNjcmFwU2l6ZSwgKnRleHRPZkNsaXApOworI2Vsc2UKKwlQdXRTY3JhcChzY3JhcFNpemUsICdURVhUJywgKnRleHRPZkNsaXApOworI2VuZGlmCisJSFVubG9jayh0ZXh0T2ZDbGlwKTsKKwlEaXNwb3NlSGFuZGxlKHRleHRPZkNsaXApOworICAgIH0KKworICAgIHZpbV9mcmVlKHN0cik7Cit9CisKKyAgICB2b2lkCitndWlfbWNoX3NldF90ZXh0X2FyZWFfcG9zKHgsIHksIHcsIGgpCisgICAgaW50CQl4OworICAgIGludAkJeTsKKyAgICBpbnQJCXc7CisgICAgaW50CQloOworeworICAgIFJlY3QJVmltQm91bmQ7CisKKy8qICBIaWRlV2luZG93IChndWkuVmltV2luZG93KTsgKi8KKyNpZmRlZiBVU0VfQ0FSQk9OSVpFRAorICAgIEdldFdpbmRvd0JvdW5kcyhndWkuVmltV2luZG93LCBrV2luZG93R2xvYmFsUG9ydFJnbiwgJlZpbUJvdW5kKTsKKyNlbHNlCisgICAgVmltQm91bmQgPSBndWkuVmltV2luZG93LT5wb3J0UmVjdDsKKyNlbmRpZgorCisgICAgaWYgKGd1aS53aGljaF9zY3JvbGxiYXJzW1NCQVJfTEVGVF0pCisgICAgeworCVZpbUJvdW5kLmxlZnQgPSAtZ3VpLnNjcm9sbGJhcl93aWR0aCArIDE7CisgICAgfQorICAgIGVsc2UKKyAgICB7CisJVmltQm91bmQubGVmdCA9IDA7CisgICAgfQorCisjaWZkZWYgVVNFX0NBUkJPTklaRUQKKyAgICBTZXRXaW5kb3dCb3VuZHMoZ3VpLlZpbVdpbmRvdywga1dpbmRvd0dsb2JhbFBvcnRSZ24sICZWaW1Cb3VuZCk7CisjZW5kaWYKKworICAgIFNob3dXaW5kb3cgKGd1aS5WaW1XaW5kb3cpOworfQorCisvKgorICogTWVudSBzdHVmZi4KKyAqLworCisgICAgdm9pZAorZ3VpX21jaF9lbmFibGVfbWVudShmbGFnKQorICAgIGludAkJZmxhZzsKK3sKKyAgICAvKgorICAgICAqIE1lbnUgaXMgYWx3YXlzIGFjdGl2ZSBpbiBpdHNlbGYKKyAgICAgKiAobWF5YmUgd2Ugc2hvdWxkIG9ubHkgZGlzYWJsZSBhIHZpbSBtZW51CisgICAgICoJYW5kIGtlZXAgc3RhbmRhcmQgbWVudSkKKyAgICAgKgorICAgICAqLworfQorCisgICAgdm9pZAorZ3VpX21jaF9zZXRfbWVudV9wb3MoeCwgeSwgdywgaCkKKyAgICBpbnQJCXg7CisgICAgaW50CQl5OworICAgIGludAkJdzsKKyAgICBpbnQJCWg7Cit7CisgICAgLyoKKyAgICAgKiBUaGUgbWVudSBpcyBhbHdheXMgYXQgdGhlIHRvcCBvZiB0aGUgc2NyZWVuCisgICAgICogTWF5YmUgYSBmdXR1ciB2ZXJzaW9uIHdpbGwgcGVybWl0IGEgbWVudSBpbiB0aGUgd2luZG93CisgICAgICoKKyAgICAgKi8KK30KKworLyoKKyAqIEFkZCBhIHN1YiBtZW51IHRvIHRoZSBtZW51IGJhci4KKyAqLworICAgIHZvaWQKK2d1aV9tY2hfYWRkX21lbnUobWVudSwgaWR4KQorICAgIHZpbW1lbnVfVAkqbWVudTsKKyAgICBpbnQJCWlkeDsKK3sKKyAgICAvKgorICAgICAqIFRPRE86IFRyeSB0byB1c2Ugb25seSBtZW51X2lkIGluc3RlYWQgb2YgYm90aCBtZW51X2lkIGFuZCBtZW51X2hhbmRsZS4KKyAgICAgKiBUT0RPOiB1c2UgbWVudS0+bW5lbW9uaWMgYW5kIG1lbnUtPmFjdGV4dAorICAgICAqIFRPRE86IFRyeSB0byByZXVzZSBtZW51IGlkCisgICAgICogICAgICAgQ2FyYm9uIEhlbHAgc3VnZ2VzdCB0byB1c2Ugb25seSBpZCBiZXR3ZWVuIDEgYW5kIDIzNQorICAgICAqLworICAgIHN0YXRpYyBsb25nCSBuZXh0X2F2YWlsX2lkID0gMTI4OworICAgIGxvbmcJIG1lbnVfYWZ0ZXJfbWUgPSAwOyAvKiBEZWZhdWx0IHRvIHRoZSBlbmQgKi8KKyAgICBjaGFyX3UJKm5hbWU7CisgICAgc2hvcnQJIGluZGV4OworICAgIHZpbW1lbnVfVAkqcGFyZW50ID0gbWVudS0+cGFyZW50OworICAgIHZpbW1lbnVfVAkqYnJvdGhlciA9IG1lbnUtPm5leHQ7CisKKyAgICAvKiBDYW5ub3QgYWRkIGEgbWVudSBpZiAuLi4gKi8KKyAgICBpZiAoKHBhcmVudCAhPSBOVUxMICYmIHBhcmVudC0+c3VibWVudV9pZCA9PSAwKSkKKwlyZXR1cm47CisKKyAgICAvKiBtZW51IElEIGdyZWF0ZXIgdGhhbiAxMDI0IGFyZSByZXNlcnZlZCBmb3IgPz8/ICovCisgICAgaWYgKG5leHRfYXZhaWxfaWQgPT0gMTAyNCkKKwlyZXR1cm47CisKKyAgICAvKiBNeSBicm90aGVyIGNvdWxkIGJlIHRoZSBQb3BVcCwgZmluZCBteSByZWFsIGJyb3RoZXIgKi8KKyAgICB3aGlsZSAoKGJyb3RoZXIgIT0gTlVMTCkgJiYgKCFtZW51X2lzX21lbnViYXIoYnJvdGhlci0+bmFtZSkpKQorCWJyb3RoZXIgPSBicm90aGVyLT5uZXh0OworCisgICAgLyogIEZpbmQgd2hlcmUgdG8gaW5zZXJ0IHRoZSBtZW51IChmb3IgTWVudUJhcikgKi8KKyAgICBpZiAoKHBhcmVudCA9PSBOVUxMKSAmJiAoYnJvdGhlciAhPSBOVUxMKSkKKwltZW51X2FmdGVyX21lID0gYnJvdGhlci0+c3VibWVudV9pZDsKKworICAgIC8qIElmIHRoZSBtZW51IGlzIG5vdCBwYXJ0IG9mIHRoZSBtZW51YmFyIChhbmQgaXRzIHN1Ym1lbnVzKSwgYWRkIGl0ICdub3doZXJlJyAqLworICAgIGlmICghbWVudV9pc19tZW51YmFyKG1lbnUtPm5hbWUpKQorCW1lbnVfYWZ0ZXJfbWUgPSBoaWVyTWVudTsKKworICAgIC8qIENvbnZlcnQgdGhlIG5hbWUgKi8KKyAgICBuYW1lID0gQzJQYXNjYWxfc2F2ZShtZW51LT5kbmFtZSk7CisgICAgaWYgKG5hbWUgPT0gTlVMTCkKKwlyZXR1cm47CisKKyAgICAvKiBDcmVhdGUgdGhlIG1lbnUgdW5sZXNzIGl0J3MgdGhlIGhlbHAgbWVudSAqLworI2lmZGVmIFVTRV9IRUxQTUVOVQorICAgIGlmIChTVFJOQ01QKG5hbWUsICJcNEhlbHAiLCA1KSA9PSAwKQorICAgIHsKKwltZW51LT5zdWJtZW51X2lkID0ga0hNSGVscE1lbnVJRDsKKwltZW51LT5zdWJtZW51X2hhbmRsZSA9IGd1aS5NYWNPU0hlbHBNZW51OworICAgIH0KKyAgICBlbHNlCisjZW5kaWYKKyAgICB7CisJLyogQ2FyYm9uIHN1Z2dlc3QgdXNlIG9mCisJICogT1NTdGF0dXMgQ3JlYXRlTmV3TWVudSAoIE1lbnVJRCwgTWVudUF0dHJpYnV0ZXMsIE1lbnVSZWYgKik7CisJICogT1NTdGF0dXMgU2V0TWVudVRpdGxlICggTWVudVJlZiwgQ29uc3RTdHIyNTVQYXJhbSB0aXRsZSApOworCSAqLworCW1lbnUtPnN1Ym1lbnVfaWQgPSBuZXh0X2F2YWlsX2lkOworCW1lbnUtPnN1Ym1lbnVfaGFuZGxlID0gTmV3TWVudSAobWVudS0+c3VibWVudV9pZCwgbmFtZSk7CisJbmV4dF9hdmFpbF9pZCsrOworICAgIH0KKworICAgIGlmIChwYXJlbnQgPT0gTlVMTCkKKyAgICB7CisJLyogQWRkaW5nIGEgbWVudSB0byB0aGUgbWVudWJhciwgb3IgaW4gdGhlIG5vIG1hbnMgbGFuZCAoZm9yIFBvcFVwKSAqLworCisJLyogVE9ETzogVmVyaWZ5IGlmIHdlIGNvdWxkIG9ubHkgSW5zZXJ0IE1lbnUgaWYgcmVhbGx5IHBhcnQgb2YgdGhlCisJICogbWVudWJhciBUaGUgSW5zZXJ0ZWQgbWVudSBhcmUgc2Nhbm5lZCBvciB0aGUgQ29tbWFuZC1rZXkgY29tYm9zCisJICovCisKKwkvKiBJbnNlcnQgdGhlIG1lbnUgdW5sZXNzIGl0J3MgdGhlIEhlbHAgbWVudSAqLworI2lmZGVmIFVTRV9IRUxQTUVOVQorCWlmIChtZW51LT5zdWJtZW51X2lkICE9IGtITUhlbHBNZW51SUQpCisjZW5kaWYKKwkgICAgSW5zZXJ0TWVudSAobWVudS0+c3VibWVudV9oYW5kbGUsIG1lbnVfYWZ0ZXJfbWUpOyAvKiBpbnNlcnQgYmVmb3JlICovCisjaWYgMQorCS8qIFZpbSBzaG91bGQgbm9ybWFsbHkgdXBkYXRlIGl0LiBUT0RPOiB2ZXJpZnkgKi8KKwlEcmF3TWVudUJhcigpOworI2VuZGlmCisgICAgfQorICAgIGVsc2UKKyAgICB7CisJLyogQWRkaW5nIGFzIGEgc3VibWVudSAqLworCisJaW5kZXggPSBndWlfbWFjX2dldF9tZW51X2l0ZW1faW5kZXggKG1lbnUpOworCisJLyogQ2FsbCBJbnNlcnRNZW51SXRlbSBmb2xsb3dlZCBieSBTZXRNZW51SXRlbVRleHQKKwkgKiB0byBhdm9pZCBzcGVjaWFsIGNoYXJhY3RlciByZWNvZ25pdGlvbiBieSBJbnNlcnRNZW51SXRlbQorCSAqLworCUluc2VydE1lbnVJdGVtKHBhcmVudC0+c3VibWVudV9oYW5kbGUsICJccCAiLCBpZHgpOyAvKiBhZnRlckl0ZW0gKi8KKwlTZXRNZW51SXRlbVRleHQocGFyZW50LT5zdWJtZW51X2hhbmRsZSwgaWR4KzEsIG5hbWUpOworCVNldEl0ZW1DbWQocGFyZW50LT5zdWJtZW51X2hhbmRsZSwgaWR4KzEsIDB4MUIpOworCVNldEl0ZW1NYXJrKHBhcmVudC0+c3VibWVudV9oYW5kbGUsIGlkeCsxLCBtZW51LT5zdWJtZW51X2lkKTsKKwlJbnNlcnRNZW51KG1lbnUtPnN1Ym1lbnVfaGFuZGxlLCBoaWVyTWVudSk7CisgICAgfQorCisgICAgdmltX2ZyZWUgKG5hbWUpOworCisjaWYgMAorICAgIC8qIERvbmUgYnkgVmltIGxhdGVyIG9uICovCisgICAgRHJhd01lbnVCYXIoKTsKKyNlbmRpZgorfQorCisvKgorICogQWRkIGEgbWVudSBpdGVtIHRvIGEgbWVudQorICovCisgICAgdm9pZAorZ3VpX21jaF9hZGRfbWVudV9pdGVtKG1lbnUsIGlkeCkKKyAgICB2aW1tZW51X1QJKm1lbnU7CisgICAgaW50CQlpZHg7Cit7CisgICAgY2hhcl91CSpuYW1lOworICAgIHZpbW1lbnVfVAkqcGFyZW50ID0gbWVudS0+cGFyZW50OworICAgIGludAkJbWVudV9pbnNlcnRlZDsKKworICAgIC8qIENhbm5vdCBhZGQgaXRlbSwgaWYgdGhlIG1lbnUgaGF2ZSBub3QgYmVlbiBjcmVhdGVkICovCisgICAgaWYgKHBhcmVudC0+c3VibWVudV9pZCA9PSAwKQorCXJldHVybjsKKworICAgIC8qIENvdWxkIGNhbGwgU2V0TWVudVJlZkNvbiBbQ0FSQk9OXSB0byBhc3NvY2lhdGUgd2l0aCB0aGUgTWVudSwKKyAgICAgICBmb3Igb2xkZXIgT1MgY2FsbCBHZXRNZW51SXRlbURhdGEgKG1lbnUsIGl0ZW0sIGlzQ29tbWFuZElEPywgZGF0YSkgKi8KKworICAgIC8qIENvbnZlcnQgdGhlIG5hbWUgKi8KKyAgICBuYW1lID0gQzJQYXNjYWxfc2F2ZShtZW51LT5kbmFtZSk7CisKKyAgICAvKiBXaGVyZSBhcmUganVzdCBhIG1lbnUgaXRlbSwgc28gbm8gaGFuZGxlLCBubyBpZCAqLworICAgIG1lbnUtPnN1Ym1lbnVfaWQgPSAwOworICAgIG1lbnUtPnN1Ym1lbnVfaGFuZGxlID0gTlVMTDsKKworI2lmZGVmIFVTRV9IRUxQTUVOVQorICAgIC8qIFRoZSBpbmRleCBpbiB0aGUgaGVscCBtZW51IGFyZSBvZmZzZXRlZCAqLworICAgIGlmIChwYXJlbnQtPnN1Ym1lbnVfaWQgPT0ga0hNSGVscE1lbnVJRCkKKwlpZHggKz0gZ3VpLk1hY09TSGVscEl0ZW1zOworI2VuZGlmCisKKyAgICBtZW51X2luc2VydGVkID0gMDsKKyAgICBpZiAobWVudS0+YWN0ZXh0KQorICAgIHsKKwkvKiBJZiB0aGUgYWNjZWxlcmF0b3IgdGV4dCBmb3IgdGhlIG1lbnUgaXRlbSBsb29rcyBsaWtlIGl0IGRlc2NyaWJlcworCSAqIGEgY29tbWFuZCBrZXkgKGUuZy4sICI8RC1TLXQ+IiBvciAiPEMtNz4iKSwgZGlzcGxheSBpdCBhcyB0aGUKKwkgKiBpdGVtJ3MgY29tbWFuZCBlcXVpdmFsZW50LgorCSAqLworCWludAkgICAga2V5ID0gMDsKKwlpbnQJICAgIG1vZGlmaWVycyA9IDA7CisJY2hhcl91CSAgICAqcF9hY3RleHQ7CisKKwlwX2FjdGV4dCA9IG1lbnUtPmFjdGV4dDsKKwlrZXkgPSBmaW5kX3NwZWNpYWxfa2V5KCZwX2FjdGV4dCwgJm1vZGlmaWVycywgLyprZXljb2RlPSovMCk7CisJaWYgKCpwX2FjdGV4dCAhPSAwKQorCSAgICBrZXkgPSAwOyAvKiBlcnJvcjogdHJhaWxpbmcgdGV4dCAqLworCS8qIGZpbmRfc3BlY2lhbF9rZXkoKSByZXR1cm5zIGEga2V5Y29kZSB3aXRoIGFzIG1hbnkgb2YgdGhlCisJICogc3BlY2lmaWVkIG1vZGlmaWVycyBhcyBhcHByb3ByaWF0ZSBhbHJlYWR5IGFwcGxpZWQgKGUuZy4sIGZvcgorCSAqICI8RC1DLXg+IiBpdCByZXR1cm5zIEN0cmwtWCBhcyB0aGUga2V5Y29kZSBhbmQgTU9EX01BU0tfQ01ECisJICogYXMgdGhlIG9ubHkgbW9kaWZpZXIpLiAgU2luY2Ugd2Ugd2FudCB0byBkaXNwbGF5IGFsbCBvZiB0aGUKKwkgKiBtb2RpZmllcnMsIHdlIG5lZWQgdG8gY29udmVydCB0aGUga2V5Y29kZSBiYWNrIHRvIGEgcHJpbnRhYmxlCisJICogY2hhcmFjdGVyIHBsdXMgbW9kaWZpZXJzLgorCSAqIFRPRE86IFdyaXRlIGFuIGFsdGVybmF0aXZlIGZpbmRfc3BlY2lhbF9rZXkoKSB0aGF0IGRvZXNuJ3QKKwkgKiBhcHBseSBtb2RpZmllcnMuCisJICovCisJaWYgKGtleSA+IDAgJiYga2V5IDwgMzIpCisJeworCSAgICAvKiBDb252ZXJ0IGEgY29udHJvbCBrZXkgdG8gYW4gdXBwZXJjYXNlIGxldHRlci4gIE5vdGUgdGhhdAorCSAgICAgKiBieSB0aGlzIHBvaW50IGl0IGlzIG5vIGxvbmdlciBwb3NzaWJsZSB0byBkaXN0aW5ndWlzaAorCSAgICAgKiBiZXR3ZWVuLCBlLmcuLCBDdHJsLVMgYW5kIEN0cmwtU2hpZnQtUy4KKwkgICAgICovCisJICAgIG1vZGlmaWVycyB8PSBNT0RfTUFTS19DVFJMOworCSAgICBrZXkgKz0gJ0AnOworCX0KKwkvKiBJZiB0aGUga2V5Y29kZSBpcyBhbiB1cHBlcmNhc2UgbGV0dGVyLCBzZXQgdGhlIFNoaWZ0IG1vZGlmaWVyLgorCSAqIElmIGl0IGlzIGEgbG93ZXJjYXNlIGxldHRlciwgZG9uJ3Qgc2V0IHRoZSBtb2RpZmllciwgYnV0IGNvbnZlcnQKKwkgKiB0aGUgbGV0dGVyIHRvIHVwcGVyY2FzZSBmb3IgZGlzcGxheSBpbiB0aGUgbWVudS4KKwkgKi8KKwllbHNlIGlmIChrZXkgPj0gJ0EnICYmIGtleSA8PSAnWicpCisJICAgIG1vZGlmaWVycyB8PSBNT0RfTUFTS19TSElGVDsKKwllbHNlIGlmIChrZXkgPj0gJ2EnICYmIGtleSA8PSAneicpCisJICAgIGtleSArPSAnQScgLSAnYSc7CisJLyogTm90ZToga2V5Y29kZXMgYmVsb3cgMHgyMiBhcmUgcmVzZXJ2ZWQgYnkgQXBwbGUuICovCisJaWYgKGtleSA+PSAweDIyICYmIHZpbV9pc3ByaW50Y19zdHJpY3Qoa2V5KSkKKwl7CisJICAgIGludAkJdmFsaWQgPSAxOworCSAgICBjaGFyX3UgICAgICBtYWNfbW9kcyA9IGtNZW51Tm9Nb2RpZmllcnM7CisJICAgIC8qIENvbnZlcnQgVmltIG1vZGlmaWVyIGNvZGVzIHRvIE1lbnUgTWFuYWdlciBlcXVpdmFsZW50cy4gKi8KKwkgICAgaWYgKG1vZGlmaWVycyAmIE1PRF9NQVNLX1NISUZUKQorCQltYWNfbW9kcyB8PSBrTWVudVNoaWZ0TW9kaWZpZXI7CisJICAgIGlmIChtb2RpZmllcnMgJiBNT0RfTUFTS19DVFJMKQorCQltYWNfbW9kcyB8PSBrTWVudUNvbnRyb2xNb2RpZmllcjsKKwkgICAgaWYgKCEobW9kaWZpZXJzICYgTU9EX01BU0tfQ01EKSkKKwkJbWFjX21vZHMgfD0ga01lbnVOb0NvbW1hbmRNb2RpZmllcjsKKwkgICAgaWYgKG1vZGlmaWVycyAmIE1PRF9NQVNLX0FMVCB8fCBtb2RpZmllcnMgJiBNT0RfTUFTS19NVUxUSV9DTElDSykKKwkJdmFsaWQgPSAwOyAvKiBUT0RPOiB3aWxsIEFsdCBzb21lZGF5IG1hcCB0byBPcHRpb24/ICovCisJICAgIGlmICh2YWxpZCkKKwkgICAgeworCQljaGFyX3UJICAgIGl0ZW1fdHh0WzEwXTsKKwkJLyogSW5zZXJ0IHRoZSBtZW51IGl0ZW0gYWZ0ZXIgaWR4LCB3aXRoIGl0cyBjb21tYW5kIGtleS4gKi8KKwkJaXRlbV90eHRbMF0gPSAzOyBpdGVtX3R4dFsxXSA9ICcgJzsgaXRlbV90eHRbMl0gPSAnLyc7CisJCWl0ZW1fdHh0WzNdID0ga2V5OworCQlJbnNlcnRNZW51SXRlbShwYXJlbnQtPnN1Ym1lbnVfaGFuZGxlLCBpdGVtX3R4dCwgaWR4KTsKKwkJLyogU2V0IHRoZSBtb2RpZmllciBrZXlzLiAqLworCQlTZXRNZW51SXRlbU1vZGlmaWVycyhwYXJlbnQtPnN1Ym1lbnVfaGFuZGxlLCBpZHgrMSwgbWFjX21vZHMpOworCQltZW51X2luc2VydGVkID0gMTsKKwkgICAgfQorCX0KKyAgICB9CisgICAgLyogQ2FsbCBJbnNlcnRNZW51SXRlbSBmb2xsb3dlZCBieSBTZXRNZW51SXRlbVRleHQKKyAgICAgKiB0byBhdm9pZCBzcGVjaWFsIGNoYXJhY3RlciByZWNvZ25pdGlvbiBieSBJbnNlcnRNZW51SXRlbQorICAgICAqLworICAgIGlmICghbWVudV9pbnNlcnRlZCkKKwlJbnNlcnRNZW51SXRlbShwYXJlbnQtPnN1Ym1lbnVfaGFuZGxlLCAiXHAgIiwgaWR4KTsgLyogYWZ0ZXJJdGVtICovCisgICAgLyogU2V0IHRoZSBtZW51IGl0ZW0gbmFtZS4gKi8KKyAgICBTZXRNZW51SXRlbVRleHQocGFyZW50LT5zdWJtZW51X2hhbmRsZSwgaWR4KzEsIG5hbWUpOworCisjaWYgMAorICAgIC8qIENhbGxlZCBieSBWaW0gKi8KKyAgICBEcmF3TWVudUJhcigpOworI2VuZGlmCisKKyAgICAvKiBUT0RPOiBDYW4gbmFtZSBiZSBmcmVlZD8gKi8KKyAgICB2aW1fZnJlZShuYW1lKTsKK30KKworICAgIHZvaWQKK2d1aV9tY2hfdG9nZ2xlX3RlYXJvZmZzKGVuYWJsZSkKKyAgICBpbnQJICAgIGVuYWJsZTsKK3sKKyAgICAvKiBubyB0ZWFyb2ZmIG1lbnVzICovCit9CisKKy8qCisgKiBEZXN0cm95IHRoZSBtYWNoaW5lIHNwZWNpZmljIG1lbnUgd2lkZ2V0LgorICovCisgICAgdm9pZAorZ3VpX21jaF9kZXN0cm95X21lbnUobWVudSkKKyAgICB2aW1tZW51X1QJKm1lbnU7Cit7CisgICAgc2hvcnQJaW5kZXggPSBndWlfbWFjX2dldF9tZW51X2l0ZW1faW5kZXggKG1lbnUpOworCisgICAgaWYgKGluZGV4ID4gMCkKKyAgICB7CisgICAgICBpZiAobWVudS0+cGFyZW50KQorICAgICAgeworI2lmZGVmIFVTRV9IRUxQTUVOVQorCWlmIChtZW51LT5wYXJlbnQtPnN1Ym1lbnVfaGFuZGxlICE9IG5pbCkgLypndWkuTWFjT1NIZWxwTWVudSkqLworI2VuZGlmCisJeworCSAgICAvKiBGb3Igbm93IGp1c3QgZG9uJ3QgZGVsZXRlIGhlbHAgbWVudSBpdGVtcy4gKEh1aD8gRGFueSkgKi8KKwkgICAgRGVsZXRlTWVudUl0ZW0gKG1lbnUtPnBhcmVudC0+c3VibWVudV9oYW5kbGUsIGluZGV4KTsKKworCSAgICAvKiBEZWxldGUgdGhlIE1lbnUgaWYgaXQgd2FzIGEgaGllcmFyY2hpY2FsIE1lbnUgKi8KKwkgICAgaWYgKG1lbnUtPnN1Ym1lbnVfaWQgIT0gMCkKKwkgICAgeworCQlEZWxldGVNZW51IChtZW51LT5zdWJtZW51X2lkKTsKKwkJRGlzcG9zZU1lbnUgKG1lbnUtPnN1Ym1lbnVfaGFuZGxlKTsKKwkgICAgfQorCX0KKyNpZmRlZiBVU0VfSEVMUE1FTlUKKyMgaWZkZWYgREVCVUdfTUFDX01FTlUKKwllbHNlCisJeworCSAgICBwcmludGYgKCJnbWRtIDFcbiIpOworCX0KKyMgZW5kaWYKKyNlbmRpZgorICAgICAgfQorI2lmZGVmIERFQlVHX01BQ19NRU5VCisgICAgICBlbHNlCisgICAgICB7CisJcHJpbnRmICgiZ21kbSAyXG4iKTsKKyAgICAgIH0KKyNlbmRpZgorICAgIH0KKyAgICBlbHNlCisgICAgeworCS8qIERvIG5vdCBkZWxldGUgdGhlIEhlbHAgTWVudSAqLworI2lmZGVmIFVTRV9IRUxQTUVOVQorCWlmIChtZW51LT5zdWJtZW51X2lkICE9IGtITUhlbHBNZW51SUQpCisjZW5kaWYKKwl7CisJICAgIERlbGV0ZU1lbnUgKG1lbnUtPnN1Ym1lbnVfaWQpOworCSAgICBEaXNwb3NlTWVudSAobWVudS0+c3VibWVudV9oYW5kbGUpOworCX0KKyAgICB9CisgICAgLyogU2hvdWxkbid0IHRoaXMgYmUgYWxyZWFkeSBkb25lIGJ5IFZpbS4gVE9ETzogQ2hlY2sgKi8KKyAgICBEcmF3TWVudUJhcigpOworfQorCisvKgorICogTWFrZSBhIG1lbnUgZWl0aGVyIGdyZXkgb3Igbm90IGdyZXkuCisgKi8KKyAgICB2b2lkCitndWlfbWNoX21lbnVfZ3JleShtZW51LCBncmV5KQorICAgIHZpbW1lbnVfVAkqbWVudTsKKyAgICBpbnQJCWdyZXk7Cit7CisgICAgLyogVE9ETzogQ2hlY2sgaWYgbWVudSByZWFsbHkgZXhpc3RzICovCisgICAgc2hvcnQgaW5kZXggPSBndWlfbWFjX2dldF9tZW51X2l0ZW1faW5kZXggKG1lbnUpOworLyoKKyAgICBpbmRleCA9IG1lbnUtPmluZGV4OworKi8KKyAgICBpZiAoZ3JleSkKKyAgICB7CisJaWYgKG1lbnUtPmNoaWxkcmVuKQorCSAgICBEaXNhYmxlTWVudUl0ZW0obWVudS0+c3VibWVudV9oYW5kbGUsIGluZGV4KTsKKwlpZiAobWVudS0+cGFyZW50KQorCSAgaWYgKG1lbnUtPnBhcmVudC0+c3VibWVudV9oYW5kbGUpCisJICAgIERpc2FibGVNZW51SXRlbShtZW51LT5wYXJlbnQtPnN1Ym1lbnVfaGFuZGxlLCBpbmRleCk7CisgICAgfQorICAgIGVsc2UKKyAgICB7CisJaWYgKG1lbnUtPmNoaWxkcmVuKQorCSAgICBFbmFibGVNZW51SXRlbShtZW51LT5zdWJtZW51X2hhbmRsZSwgaW5kZXgpOworCWlmIChtZW51LT5wYXJlbnQpCisJICBpZiAobWVudS0+cGFyZW50LT5zdWJtZW51X2hhbmRsZSkKKwkgICAgRW5hYmxlTWVudUl0ZW0obWVudS0+cGFyZW50LT5zdWJtZW51X2hhbmRsZSwgaW5kZXgpOworICAgIH0KK30KKworLyoKKyAqIE1ha2UgbWVudSBpdGVtIGhpZGRlbiBvciBub3QgaGlkZGVuCisgKi8KKyAgICB2b2lkCitndWlfbWNoX21lbnVfaGlkZGVuKG1lbnUsIGhpZGRlbikKKyAgICB2aW1tZW51X1QJKm1lbnU7CisgICAgaW50CQloaWRkZW47Cit7CisgICAgLyogVGhlcmUncyBubyBoaWRkZW4gbW9kZSBvbiBNYWNPUyAqLworICAgIGd1aV9tY2hfbWVudV9ncmV5IChtZW51LCBoaWRkZW4pOworfQorCisKKy8qCisgKiBUaGlzIGlzIGNhbGxlZCBhZnRlciBzZXR0aW5nIGFsbCB0aGUgbWVudXMgdG8gZ3JleS9oaWRkZW4gb3Igbm90LgorICovCisgICAgdm9pZAorZ3VpX21jaF9kcmF3X21lbnViYXIoKQoreworICAgIERyYXdNZW51QmFyKCk7Cit9CisKKworLyoKKyAqIFNjcm9sbGJhciBzdHVmZi4KKyAqLworCisgICAgdm9pZAorZ3VpX21jaF9lbmFibGVfc2Nyb2xsYmFyKHNiLCBmbGFnKQorICAgIHNjcm9sbGJhcl9UCSpzYjsKKyAgICBpbnQJCWZsYWc7Cit7CisgICAgaWYgKGZsYWcpCisJU2hvd0NvbnRyb2woc2ItPmlkKTsKKyAgICBlbHNlCisJSGlkZUNvbnRyb2woc2ItPmlkKTsKKworI2lmZGVmIERFQlVHX01BQ19TQgorICAgIHByaW50ZiAoImVuYl9zYiAoJXgpICV4XG4iLHNiLT5pZCwgZmxhZyk7CisjZW5kaWYKK30KKworICAgIHZvaWQKK2d1aV9tY2hfc2V0X3Njcm9sbGJhcl90aHVtYihzYiwgdmFsLCBzaXplLCBtYXgpCisgICAgc2Nyb2xsYmFyX1QgKnNiOworICAgIGxvbmcJdmFsOworICAgIGxvbmcJc2l6ZTsKKyAgICBsb25nCW1heDsKK3sKKyAgICBTZXRDb250cm9sMzJCaXRNYXhpbXVtIChzYi0+aWQsIG1heCk7CisgICAgU2V0Q29udHJvbDMyQml0TWluaW11bSAoc2ItPmlkLCAwKTsKKyAgICBTZXRDb250cm9sMzJCaXRWYWx1ZSAgIChzYi0+aWQsIHZhbCk7CisjaWZkZWYgREVCVUdfTUFDX1NCCisgICAgcHJpbnRmICgidGh1bWJfc2IgKCV4KSAleCwgJXgsJXhcbiIsc2ItPmlkLCB2YWwsIHNpemUsIG1heCk7CisjZW5kaWYKK30KKworICAgIHZvaWQKK2d1aV9tY2hfc2V0X3Njcm9sbGJhcl9wb3Moc2IsIHgsIHksIHcsIGgpCisgICAgc2Nyb2xsYmFyX1QgKnNiOworICAgIGludAkJeDsKKyAgICBpbnQJCXk7CisgICAgaW50CQl3OworICAgIGludAkJaDsKK3sKKyAgICBndWlfbWNoX3NldF9iZ19jb2xvcihndWkuYmFja19waXhlbCk7CisvKiAgaWYgKGd1aS53aGljaF9zY3JvbGxiYXJzW1NCQVJfTEVGVF0pCisgICAgeworCU1vdmVDb250cm9sIChzYi0+aWQsIHgtMTYsIHkpOworCVNpemVDb250cm9sIChzYi0+aWQsIHcgKyAxLCBoKTsKKyAgICB9CisgICAgZWxzZQorICAgIHsKKwlNb3ZlQ29udHJvbCAoc2ItPmlkLCB4LCB5KTsKKwlTaXplQ29udHJvbCAoc2ItPmlkLCB3ICsgMSwgaCk7CisgICAgfSovCisgICAgaWYgKHNiID09ICZndWkuYm90dG9tX3NiYXIpCisJaCArPSAxOworICAgIGVsc2UKKwl3ICs9IDE7CisKKyAgICBpZiAoZ3VpLndoaWNoX3Njcm9sbGJhcnNbU0JBUl9MRUZUXSkKKwl4IC09IDE1OworCisgICAgTW92ZUNvbnRyb2wgKHNiLT5pZCwgeCwgeSk7CisgICAgU2l6ZUNvbnRyb2wgKHNiLT5pZCwgdywgaCk7CisjaWZkZWYgREVCVUdfTUFDX1NCCisgICAgcHJpbnRmICgic2l6ZV9zYiAoJXgpICV4LCAleCwgJXgsICV4XG4iLHNiLT5pZCwgeCwgeSwgdywgaCk7CisjZW5kaWYKK30KKworICAgIHZvaWQKK2d1aV9tY2hfY3JlYXRlX3Njcm9sbGJhcihzYiwgb3JpZW50KQorICAgIHNjcm9sbGJhcl9UICpzYjsKKyAgICBpbnQJCW9yaWVudDsJLyogU0JBUl9WRVJUIG9yIFNCQVJfSE9SSVogKi8KK3sKKyAgICBSZWN0IGJvdW5kczsKKworICAgIGJvdW5kcy50b3AgPSAtMTY7CisgICAgYm91bmRzLmJvdHRvbSA9IC0xMDsKKyAgICBib3VuZHMucmlnaHQgPSAtMTA7CisgICAgYm91bmRzLmxlZnQgPSAtMTY7CisKKyAgICBzYi0+aWQgPSBOZXdDb250cm9sIChndWkuVmltV2luZG93LAorCQkJICZib3VuZHMsCisJCQkgIlxwU2Nyb2xsQmFyIiwKKwkJCSBUUlVFLAorCQkJIDAsIC8qIGN1cnJlbnQqLworCQkJIDAsIC8qIHRvcCAqLworCQkJIDAsIC8qIGJvdHRvbSAqLworI2lmZGVmIFVTRV9DQVJCT05JWkVECisJCQkga0NvbnRyb2xTY3JvbGxCYXJMaXZlUHJvYywKKyNlbHNlCisJCQkgc2Nyb2xsQmFyUHJvYywKKyNlbmRpZgorCQkJIChsb25nKSBzYi0+aWRlbnQpOworI2lmZGVmIERFQlVHX01BQ19TQgorICAgIHByaW50ZiAoImNyZWF0ZV9zYiAoJXgpICV4XG4iLHNiLT5pZCwgb3JpZW50KTsKKyNlbmRpZgorfQorCisgICAgdm9pZAorZ3VpX21jaF9kZXN0cm95X3Njcm9sbGJhcihzYikKKyAgICBzY3JvbGxiYXJfVCAqc2I7Cit7CisgICAgZ3VpX21jaF9zZXRfYmdfY29sb3IoZ3VpLmJhY2tfcGl4ZWwpOworICAgIERpc3Bvc2VDb250cm9sIChzYi0+aWQpOworI2lmZGVmIERFQlVHX01BQ19TQgorICAgIHByaW50ZiAoImRlc3Rfc2IgKCV4KSBcbiIsc2ItPmlkKTsKKyNlbmRpZgorfQorCisKKy8qCisgKiBDdXJzb3IgYmxpbmsgZnVuY3Rpb25zLgorICoKKyAqIFRoaXMgaXMgYSBzaW1wbGUgc3RhdGUgbWFjaGluZToKKyAqIEJMSU5LX05PTkUJbm90IGJsaW5raW5nIGF0IGFsbAorICogQkxJTktfT0ZGCWJsaW5raW5nLCBjdXJzb3IgaXMgbm90IHNob3duCisgKiBCTElOS19PTiBibGlua2luZywgY3Vyc29yIGlzIHNob3duCisgKi8KKyAgICB2b2lkCitndWlfbWNoX3NldF9ibGlua2luZyhsb25nIHdhaXQsIGxvbmcgb24sIGxvbmcgb2ZmKQoreworICAgIC8qIFRPRE86IFRPRE86IFRPRE86IFRPRE86ICovCisvKiAgICBibGlua193YWl0dGltZSA9IHdhaXQ7CisgICAgYmxpbmtfb250aW1lID0gb247CisgICAgYmxpbmtfb2ZmdGltZSA9IG9mZjsqLworfQorCisvKgorICogU3RvcCB0aGUgY3Vyc29yIGJsaW5raW5nLiAgU2hvdyB0aGUgY3Vyc29yIGlmIGl0IHdhc24ndCBzaG93bi4KKyAqLworICAgIHZvaWQKK2d1aV9tY2hfc3RvcF9ibGluaygpCit7CisgICAgZ3VpX3VwZGF0ZV9jdXJzb3IoVFJVRSwgRkFMU0UpOworICAgIC8qIFRPRE86IFRPRE86IFRPRE86IFRPRE86ICovCisvKiAgICBndWlfdzMyX3JtX2JsaW5rX3RpbWVyKCk7CisgICAgaWYgKGJsaW5rX3N0YXRlID09IEJMSU5LX09GRikKKyAgICBndWlfdXBkYXRlX2N1cnNvcihUUlVFLCBGQUxTRSk7CisgICAgYmxpbmtfc3RhdGUgPSBCTElOS19OT05FOyovCit9CisKKy8qCisgKiBTdGFydCB0aGUgY3Vyc29yIGJsaW5raW5nLiAgSWYgaXQgd2FzIGFscmVhZHkgYmxpbmtpbmcsIHRoaXMgcmVzdGFydHMgdGhlCisgKiB3YWl0aW5nIHRpbWUgYW5kIHNob3dzIHRoZSBjdXJzb3IuCisgKi8KKyAgICB2b2lkCitndWlfbWNoX3N0YXJ0X2JsaW5rKCkKK3sKKyAgICBndWlfdXBkYXRlX2N1cnNvcihUUlVFLCBGQUxTRSk7CisgICAgLyogVE9ETzogVE9ETzogVE9ETzogVE9ETzogKi8KKy8qICAgIGd1aV93MzJfcm1fYmxpbmtfdGltZXIoKTsgKi8KKworICAgIC8qIE9ubHkgc3dpdGNoIGJsaW5raW5nIG9uIGlmIG5vbmUgb2YgdGhlIHRpbWVzIGlzIHplcm8gKi8KKy8qICAgIGlmIChibGlua193YWl0dGltZSAmJiBibGlua19vbnRpbWUgJiYgYmxpbmtfb2ZmdGltZSkKKyAgICB7CisgICAgYmxpbmtfdGltZXIgPSBTZXRUaW1lcihOVUxMLCAwLCAoVUlOVClibGlua193YWl0dGltZSwKKwkJCSAgICAoVElNRVJQUk9DKV9PbkJsaW5rVGltZXIpOworICAgIGJsaW5rX3N0YXRlID0gQkxJTktfT047CisgICAgZ3VpX3VwZGF0ZV9jdXJzb3IoVFJVRSwgRkFMU0UpOworICAgIH0qLworfQorCisvKgorICogUmV0dXJuIHRoZSBSR0IgdmFsdWUgb2YgYSBwaXhlbCBhcyBsb25nLgorICovCisgICAgbG9uZ191CitndWlfbWNoX2dldF9yZ2IoZ3VpY29sb3JfVCBwaXhlbCkKK3sKKyAgICByZXR1cm4gKFJlZChwaXhlbCkgPDwgMTYpICsgKEdyZWVuKHBpeGVsKSA8PCA4KSArIEJsdWUocGl4ZWwpOworfQorCisKKworI2lmZGVmIEZFQVRfQlJPV1NFCisvKgorICogUG9wIG9wZW4gYSBmaWxlIGJyb3dzZXIgYW5kIHJldHVybiB0aGUgZmlsZSBzZWxlY3RlZCwgaW4gYWxsb2NhdGVkIG1lbW9yeSwKKyAqIG9yIE5VTEwgaWYgQ2FuY2VsIGlzIGhpdC4KKyAqICBzYXZpbmcgIC0gVFJVRSBpZiB0aGUgZmlsZSB3aWxsIGJlIHNhdmVkIHRvLCBGQUxTRSBpZiBpdCB3aWxsIGJlIG9wZW5lZC4KKyAqICB0aXRsZSAgIC0gVGl0bGUgbWVzc2FnZSBmb3IgdGhlIGZpbGUgYnJvd3NlciBkaWFsb2cuCisgKiAgZGZsdCAgICAtIERlZmF1bHQgbmFtZSBvZiBmaWxlLgorICogIGV4dCAgICAgLSBEZWZhdWx0IGV4dGVuc2lvbiB0byBiZSBhZGRlZCB0byBmaWxlcyB3aXRob3V0IGV4dGVuc2lvbnMuCisgKiAgaW5pdGRpciAtIGRpcmVjdG9yeSBpbiB3aGljaCB0byBvcGVuIHRoZSBicm93c2VyIChOVUxMID0gY3VycmVudCBkaXIpCisgKiAgZmlsdGVyICAtIEZpbHRlciBmb3IgbWF0Y2hlZCBmaWxlcyB0byBjaG9vc2UgZnJvbS4KKyAqICBIYXMgYSBmb3JtYXQgbGlrZSB0aGlzOgorICogICJDIEZpbGVzICgqLmMpXDAqLmNcMCIKKyAqICAiQWxsIEZpbGVzXDAqLipcMFwwIgorICogIElmIHRoZXNlIHR3byBzdHJpbmdzIHdlcmUgY29uY2F0ZW5hdGVkLCB0aGVuIGEgY2hvaWNlIG9mIHR3byBmaWxlCisgKiAgZmlsdGVycyB3aWxsIGJlIHNlbGVjdGFibGUgdG8gdGhlIHVzZXIuICBUaGVuIG9ubHkgbWF0Y2hpbmcgZmlsZXMgd2lsbAorICogIGJlIHNob3duIGluIHRoZSBicm93c2VyLiAgSWYgTlVMTCwgdGhlIGRlZmF1bHQgYWxsb3dzIGFsbCBmaWxlcy4KKyAqCisgKiAgKk5PVEUqIC0gdGhlIGZpbHRlciBzdHJpbmcgbXVzdCBiZSB0ZXJtaW5hdGVkIHdpdGggVFdPIG51bGxzLgorICovCisgICAgY2hhcl91ICoKK2d1aV9tY2hfYnJvd3NlKAorICAgIGludCBzYXZpbmcsCisgICAgY2hhcl91ICp0aXRsZSwKKyAgICBjaGFyX3UgKmRmbHQsCisgICAgY2hhcl91ICpleHQsCisgICAgY2hhcl91ICppbml0ZGlyLAorICAgIGNoYXJfdSAqZmlsdGVyKQoreworI2lmIGRlZmluZWQgKFVTRV9OQVZJR0FUSU9OX1NFUlZJQ0UpIHx8IGRlZmluZWQgKFVTRV9DQVJCT05JWkVEKQorICAgIC8qIFRPRE86IEFkZCBBbW1vbidzIHNhZmV0eSBjaGVjbCAoRGFueSkgKi8KKyAgICBOYXZSZXBseVJlY29yZAlyZXBseTsKKyAgICBjaGFyX3UJCSpmbmFtZSA9IE5VTEw7CisgICAgY2hhcl91CQkqKmZuYW1lcyA9IE5VTEw7CisgICAgbG9uZwkJbnVtRmlsZXM7CisgICAgTmF2RGlhbG9nT3B0aW9ucwluYXZPcHRpb25zOworICAgIE9TRXJyCQllcnJvcjsKKworICAgIC8qIEdldCBOYXZpZ2F0aW9uIFNlcnZpY2UgRGVmYXVsdHMgdmFsdWUgKi8KKyAgICBOYXZHZXREZWZhdWx0RGlhbG9nT3B0aW9ucyAoJm5hdk9wdGlvbnMpOworCisKKyAgICAvKiBUT0RPOiBJZiB3ZSBnZXQgYSA6YnJvd3NlIGFyZ3MsIHNldCB0aGUgTXVsdGlwbGUgYml0LiAqLworICAgIG5hdk9wdGlvbnMuZGlhbG9nT3B0aW9uRmxhZ3MgPSAga05hdkFsbG93SW52aXNpYmxlRmlsZXMKKwkJCQkgfCAga05hdkRvbnRBdXRvVHJhbnNsYXRlCisJCQkJIHwgIGtOYXZEb250QWRkVHJhbnNsYXRlSXRlbXMKKwkJCSAgICAvKgkgfCAga05hdkFsbG93TXVsdGlwbGVGaWxlcyAqLworCQkJCSB8ICBrTmF2QWxsb3dTdGF0aW9uZXJ5OworCisgICAgKHZvaWQpIEMyUGFzY2FsU3RyaW5nICh0aXRsZSwgICAmbmF2T3B0aW9ucy5tZXNzYWdlKTsKKyAgICAodm9pZCkgQzJQYXNjYWxTdHJpbmcgKGRmbHQsICAgICZuYXZPcHRpb25zLnNhdmVkRmlsZU5hbWUpOworICAgIC8qIENvdWxkIHNldCBjbGllbnROYW1lPworICAgICAqCQkgd2luZG93VGl0bGU/ICh0aGVyZSdzIG5vIHRpdGxlIGJhcj8pCisgICAgICovCisKKyAgICBpZiAoc2F2aW5nKQorICAgIHsKKwkvKiBDaGFuZ2UgZmlyc3QgcGFybSBBRURlc2MgKHR5cGVGU1MpICpkZWZhdWx0TG9jYXRpb24gdG8gbWF0Y2ggZGZsdCAqLworCU5hdlB1dEZpbGUgKE5VTEwsICZyZXBseSwgJm5hdk9wdGlvbnMsIE5VTEwsICdURVhUJywgJ1ZJTSEnLCBOVUxMKTsKKwlpZiAoIXJlcGx5LnZhbGlkUmVjb3JkKQorCSAgICByZXR1cm4gTlVMTDsKKyAgICB9CisgICAgZWxzZQorICAgIHsKKwkvKiBDaGFuZ2UgZmlyc3QgcGFybSBBRURlc2MgKHR5cGVGU1MpICpkZWZhdWx0TG9jYXRpb24gdG8gbWF0Y2ggZGZsdCAqLworCU5hdkdldEZpbGUoTlVMTCwgJnJlcGx5LCAmbmF2T3B0aW9ucywgTlVMTCwgTlVMTCwgTlVMTCwgTlVMTCwgTlVMTCk7CisJaWYgKCFyZXBseS52YWxpZFJlY29yZCkKKwkgICAgcmV0dXJuIE5VTEw7CisgICAgfQorCisgICAgZm5hbWVzID0gbmV3X2ZuYW1lc19mcm9tX0FFRGVzYygmcmVwbHkuc2VsZWN0aW9uLCAmbnVtRmlsZXMsICZlcnJvcik7CisKKyAgICBOYXZEaXNwb3NlUmVwbHkgKCZyZXBseSk7CisKKyAgICBpZiAoZm5hbWVzKQorICAgIHsKKwlmbmFtZSA9IGZuYW1lc1swXTsKKwl2aW1fZnJlZShmbmFtZXMpOworICAgIH0KKworICAgIC8qIFRPRE86IFNob3J0ZW4gdGhlIGZpbGUgbmFtZSBpZiBwb3NzaWJsZSAqLworICAgIHJldHVybiBmbmFtZTsKKyNlbHNlCisgICAgU0ZUeXBlTGlzdAkJZmlsZVR5cGVzOworICAgIFN0YW5kYXJkRmlsZVJlcGx5CXJlcGx5OworICAgIFN0cjI1NQkJUHJvbXB0OworICAgIFN0cjI1NQkJRGVmYXVsdE5hbWU7CisgICAgU3RyMjU1CQlEaXJlY3Rvcnk7CisKKyAgICAvKiBUT0RPOiBzcGxpdCBkZmx0IGluIHBhdGggYW5kIGZpbGVuYW1lICovCisKKyAgICAodm9pZCkgQzJQYXNjYWxTdHJpbmcgKHRpdGxlLCAgICZQcm9tcHQpOworICAgICh2b2lkKSBDMlBhc2NhbFN0cmluZyAoZGZsdCwgICAgJkRlZmF1bHROYW1lKTsKKyAgICAodm9pZCkgQzJQYXNjYWxTdHJpbmcgKGluaXRkaXIsICZEaXJlY3RvcnkpOworCisgICAgaWYgKHNhdmluZykKKyAgICB7CisJLyogVXNlIGEgY3VzdG9uIGZpbHRlciBpbnN0ZWFkIG9mIG5pbCBGQVEgOS00ICovCisJU3RhbmRhcmRQdXRGaWxlIChQcm9tcHQsIERlZmF1bHROYW1lLCAgJnJlcGx5KTsKKwlpZiAoIXJlcGx5LnNmR29vZCkKKwkgICAgcmV0dXJuIE5VTEw7CisgICAgfQorICAgIGVsc2UKKyAgICB7CisJU3RhbmRhcmRHZXRGaWxlIChuaWwsIC0xLCBmaWxlVHlwZXMsICZyZXBseSk7CisJaWYgKCFyZXBseS5zZkdvb2QpCisJICAgIHJldHVybiBOVUxMOworICAgIH0KKworICAgIC8qIFdvcmsgZmluZSBidXQgYXBwZW5kIGEgOiBmb3IgbmV3IGZpbGUgKi8KKyAgICByZXR1cm4gKEZ1bGxQYXRoRnJvbUZTU3BlY19zYXZlIChyZXBseS5zZkZpbGUpKTsKKworICAgIC8qIFNob3J0ZW4gdGhlIGZpbGUgbmFtZSBpZiBwb3NzaWJsZSAqLworLyogICAgbWNoX2Rpcm5hbWUoSU9idWZmLCBJT1NJWkUpOworICAgIHAgPSBzaG9ydGVuX2ZuYW1lKGZpbGVCdWYsIElPYnVmZik7CisgICAgaWYgKHAgPT0gTlVMTCkKKyAgICBwID0gZmlsZUJ1ZjsKKyAgICByZXR1cm4gdmltX3N0cnNhdmUocCk7CisqLworI2VuZGlmCit9CisjZW5kaWYgLyogRkVBVF9CUk9XU0UgKi8KKworI2lmZGVmIEZFQVRfR1VJX0RJQUxPRworLyoKKyAqIFN0dWZmIGZvciBkaWFsb2d1ZXMKKyAqLworCisvKgorICogQ3JlYXRlIGEgZGlhbG9ndWUgZHluYW1pY2FsbHkgZnJvbSB0aGUgcGFyYW1ldGVyIHN0cmluZ3MuCisgKiB0eXBlICAgICAgID0gdHlwZSBvZiBkaWFsb2d1ZSAocXVlc3Rpb24sIGFsZXJ0LCBldGMuKQorICogdGl0bGUgICAgICA9IGRpYWxvZ3VlIHRpdGxlLiBtYXkgYmUgTlVMTCBmb3IgZGVmYXVsdCB0aXRsZS4KKyAqIG1lc3NhZ2UgICAgPSB0ZXh0IHRvIGRpc3BsYXkuIERpYWxvZ3VlIHNpemVzIHRvIGFjY29tbW9kYXRlIGl0LgorICogYnV0dG9ucyAgICA9ICdcbicgc2VwYXJhdGVkIGxpc3Qgb2YgYnV0dG9uIGNhcHRpb25zLCBkZWZhdWx0IGZpcnN0LgorICogZGZsdGJ1dHRvbiA9IG51bWJlciBvZiBkZWZhdWx0IGJ1dHRvbi4KKyAqCisgKiBUaGlzIHJvdXRpbmUgcmV0dXJucyAxIGlmIHRoZSBmaXJzdCBidXR0b24gaXMgcHJlc3NlZCwKKyAqCSAgICAyIGZvciB0aGUgc2Vjb25kLCBldGMuCisgKgorICoJICAgIDAgaW5kaWNhdGVzIEVzYyB3YXMgcHJlc3NlZC4KKyAqCSAgICAtMSBmb3IgdW5leHBlY3RlZCBlcnJvcgorICoKKyAqIElmIHN0dWJiaW5nIG91dCB0aGlzIGZuLCByZXR1cm4gMS4KKyAqLworCit0eXBlZGVmIHN0cnVjdAoreworICAgIHNob3J0ICAgaWR4OworICAgIHNob3J0ICAgd2lkdGg7CS8qIFNpemUgb2YgdGhlIHRleHQgaW4gcGl4ZWwgKi8KKyAgICBSZWN0ICAgIGJveDsKK30gdmdtRGxnSXRtOyAvKiBWaW0gR3VpX01hYy5jIERpYWxvZyBJdGVtICovCisKKyNkZWZpbmUgTW92ZVJlY3RUbyhyLHgseSkgT2Zmc2V0UmVjdChyLHgtci0+bGVmdCx5LXItPnRvcCkKKworICAgIHN0YXRpYyB2b2lkCittYWNNb3ZlRGlhbG9nSXRlbSgKKyAgICBEaWFsb2dSZWYJdGhlRGlhbG9nLAorICAgIHNob3J0CWl0ZW1OdW1iZXIsCisgICAgc2hvcnQJWCwKKyAgICBzaG9ydAlZLAorICAgIFJlY3QJKmluQm94KQoreworI2lmIDAgLyogVVNFX0NBUkJPTklaRUQgKi8KKyAgICAvKiBVbnRlc3RlZCAqLworICAgIE1vdmVEaWFsb2dJdGVtICh0aGVEaWFsb2csIGl0ZW1OdW1iZXIsIFgsIFkpOworICAgIGlmIChpbkJveCAhPSBuaWwpCisJR2V0RGlhbG9nSXRlbSAodGhlRGlhbG9nLCBpdGVtTnVtYmVyLCAmaXRlbVR5cGUsICZpdGVtSGFuZGxlLCBpbkJveCk7CisjZWxzZQorICAgIHNob3J0CWl0ZW1UeXBlOworICAgIEhhbmRsZQlpdGVtSGFuZGxlOworICAgIFJlY3QJbG9jYWxCb3g7CisgICAgUmVjdAkqaXRlbUJveCA9ICZsb2NhbEJveDsKKworICAgIGlmIChpbkJveCAhPSBuaWwpCisJaXRlbUJveCA9IGluQm94OworCisgICAgR2V0RGlhbG9nSXRlbSAodGhlRGlhbG9nLCBpdGVtTnVtYmVyLCAmaXRlbVR5cGUsICZpdGVtSGFuZGxlLCBpdGVtQm94KTsKKyAgICBPZmZzZXRSZWN0IChpdGVtQm94LCAtaXRlbUJveC0+bGVmdCwgLWl0ZW1Cb3gtPnRvcCk7CisgICAgT2Zmc2V0UmVjdCAoaXRlbUJveCwgWCwgWSk7CisgICAgLyogVG8gbW92ZSBhIGNvbnRyb2wgKGxpa2UgYSBidXR0b24pIHdlIG5lZWQgdG8gY2FsbCBib3RoCisgICAgICogTW92ZUNvbnRyb2wgYW5kIFNldERpYWxvZ0l0ZW0uIEZBUSA2LTE4ICovCisgICAgaWYgKDEpIC8qKGl0ZW1UeXBlICYga0NvbnRyb2xEaWFsb2dJdGVtKSAqLworCU1vdmVDb250cm9sICgoQ29udHJvbFJlZikgaXRlbUhhbmRsZSwgWCwgWSk7CisgICAgU2V0RGlhbG9nSXRlbSAodGhlRGlhbG9nLCBpdGVtTnVtYmVyLCBpdGVtVHlwZSwgaXRlbUhhbmRsZSwgaXRlbUJveCk7CisjZW5kaWYKK30KKworICAgIHN0YXRpYyB2b2lkCittYWNTaXplRGlhbG9nSXRlbSgKKyAgICBEaWFsb2dSZWYJdGhlRGlhbG9nLAorICAgIHNob3J0CWl0ZW1OdW1iZXIsCisgICAgc2hvcnQJd2lkdGgsCisgICAgc2hvcnQJaGVpZ2h0KQoreworICAgIHNob3J0CWl0ZW1UeXBlOworICAgIEhhbmRsZQlpdGVtSGFuZGxlOworICAgIFJlY3QJaXRlbUJveDsKKworICAgIEdldERpYWxvZ0l0ZW0gKHRoZURpYWxvZywgaXRlbU51bWJlciwgJml0ZW1UeXBlLCAmaXRlbUhhbmRsZSwgJml0ZW1Cb3gpOworCisgICAgLyogV2hlbiB3aWR0aCBvciBoZWlnaHQgaXMgemVybyBkbyBub3QgY2hhbmdlIGl0ICovCisgICAgaWYgKHdpZHRoICA9PSAwKQorCXdpZHRoICA9IGl0ZW1Cb3gucmlnaHQgIC0gaXRlbUJveC5sZWZ0OworICAgIGlmIChoZWlnaHQgPT0gMCkKKwloZWlnaHQgPSBpdGVtQm94LmJvdHRvbSAtIGl0ZW1Cb3gudG9wOworCisjaWYgMCAvKiBVU0VfQ0FSQk9OSVpFRCAqLworICAgIFNpemVEaWFsb2dJdGVtICh0aGVEaWFsb2csIGl0ZW1OdW1iZXIsIHdpZHRoLCBoZWlnaHQpOyAvKiBVbnRlc3RlZCAqLworI2Vsc2UKKyAgICAvKiBSZXNpemUgdGhlIGJvdW5kaW5nIGJveCAqLworICAgIGl0ZW1Cb3gucmlnaHQgID0gaXRlbUJveC5sZWZ0ICsgd2lkdGg7CisgICAgaXRlbUJveC5ib3R0b20gPSBpdGVtQm94LnRvcCAgKyBoZWlnaHQ7CisKKyAgICAvKiBUbyByZXNpemUgYSBjb250cm9sIChsaWtlIGEgYnV0dG9uKSB3ZSBuZWVkIHRvIGNhbGwgYm90aAorICAgICAqIFNpemVDb250cm9sIGFuZCBTZXREaWFsb2dJdGVtLiAoZGVkdWN0ZWQgZnJvbSBGQVEgNi0xOCkgKi8KKyAgICBpZiAoaXRlbVR5cGUgJiBrQ29udHJvbERpYWxvZ0l0ZW0pCisJU2l6ZUNvbnRyb2wgKChDb250cm9sUmVmKSBpdGVtSGFuZGxlLCB3aWR0aCwgaGVpZ2h0KTsKKworICAgIC8qIENvbmZpZ3VyZSBiYWNrIHRoZSBpdGVtICovCisgICAgU2V0RGlhbG9nSXRlbSAodGhlRGlhbG9nLCBpdGVtTnVtYmVyLCBpdGVtVHlwZSwgaXRlbUhhbmRsZSwgJml0ZW1Cb3gpOworI2VuZGlmCit9CisKKyAgICBzdGF0aWMgdm9pZAorbWFjU2V0RGlhbG9nSXRlbVRleHQoCisgICAgRGlhbG9nUmVmCXRoZURpYWxvZywKKyAgICBzaG9ydAlpdGVtTnVtYmVyLAorICAgIFN0cjI1NQlpdGVtTmFtZSkKK3sKKyAgICBzaG9ydAlpdGVtVHlwZTsKKyAgICBIYW5kbGUJaXRlbUhhbmRsZTsKKyAgICBSZWN0CWl0ZW1Cb3g7CisKKyAgICBHZXREaWFsb2dJdGVtICh0aGVEaWFsb2csIGl0ZW1OdW1iZXIsICZpdGVtVHlwZSwgJml0ZW1IYW5kbGUsICZpdGVtQm94KTsKKworICAgIGlmIChpdGVtVHlwZSAmIGtDb250cm9sRGlhbG9nSXRlbSkKKwlTZXRDb250cm9sVGl0bGUgKChDb250cm9sUmVmKSBpdGVtSGFuZGxlLCBpdGVtTmFtZSk7CisgICAgZWxzZQorCVNldERpYWxvZ0l0ZW1UZXh0IChpdGVtSGFuZGxlLCBpdGVtTmFtZSk7Cit9CisKKyAgICBpbnQKK2d1aV9tY2hfZGlhbG9nKAorICAgIGludAkJdHlwZSwKKyAgICBjaGFyX3UJKnRpdGxlLAorICAgIGNoYXJfdQkqbWVzc2FnZSwKKyAgICBjaGFyX3UJKmJ1dHRvbnMsCisgICAgaW50CQlkZmx0YnV0dG9uLAorICAgIGNoYXJfdQkqdGV4dGZpZWxkKQoreworICAgIEhhbmRsZQlidXR0b25ESVRMOworICAgIEhhbmRsZQlpY29uRElUTDsKKyAgICBIYW5kbGUJaW5wdXRESVRMOworICAgIEhhbmRsZQltZXNzYWdlRElUTDsKKyAgICBIYW5kbGUJaXRlbUhhbmRsZTsKKyAgICBIYW5kbGUJaWNvbkhhbmRsZTsKKyAgICBEaWFsb2dQdHIJdGhlRGlhbG9nOworICAgIGNoYXJfdQlsZW47CisgICAgY2hhcl91CVBhc2NhbFRpdGxlWzI1Nl07CS8qIHBsYWNlIGhvbGRlciBmb3IgdGhlIHRpdGxlICovCisgICAgY2hhcl91CW5hbWVbMjU2XTsKKyAgICBHcmFmUHRyCW9sZFBvcnQ7CisgICAgc2hvcnQJaXRlbUhpdDsKKyAgICBjaGFyX3UJKmJ1dHRvbkNoYXI7CisgICAgUmVjdAlib3g7CisgICAgc2hvcnQJYnV0dG9uOworICAgIHNob3J0CWxhc3RCdXR0b247CisgICAgc2hvcnQJaXRlbVR5cGU7CisgICAgc2hvcnQJdXNlSWNvbjsKKyAgICBzaG9ydAl3aWR0aDsKKyAgICBzaG9ydAl0b3RhbEJ1dHRvbldpZHRoID0gMDsgICAvKiB0aGUgd2lkdGggb2YgYWxsIGJ1dHRvbiB0b2dldGhlciBpbmN1ZGluZyBzcGFjaW5nICovCisgICAgc2hvcnQJd2lkZXN0QnV0dG9uID0gMDsKKyAgICBzaG9ydAlkZmx0QnV0dG9uRWRnZSAgICAgPSAyMDsgIC8qIGd1dCBmZWVsaW5nICovCisgICAgc2hvcnQJZGZsdEVsZW1lbnRTcGFjaW5nID0gMTM7ICAvKiBmcm9tIElNOlYuMi0yOSAqLworICAgIHNob3J0ICAgICAgIGRmbHRJY29uU2lkZVNwYWNlICA9IDIzOyAgLyogZnJvbSBJTTpWLjItMjkgKi8KKyAgICBzaG9ydAltYXhpbXVtV2lkdGggICAgICAgPSA0MDA7IC8qIGd1dCBmZWVsaW5nICovCisgICAgc2hvcnQJbWF4QnV0dG9uV2lkdGgJICAgPSAxNzU7IC8qIGd1dCBmZWVsaW5nICovCisKKyAgICBzaG9ydAl2ZXJ0aWNhbDsKKyAgICBzaG9ydAlkaWFsb2dIZWlnaHQ7CisgICAgc2hvcnQJbWVzc2FnZUxpbmVzID0gMzsKKyAgICBGb250SW5mbwl0ZXh0Rm9udEluZm87CisKKyAgICB2Z21EbGdJdG0gICBpY29uSXRtOworICAgIHZnbURsZ0l0bSAgIG1lc3NhZ2VJdG07CisgICAgdmdtRGxnSXRtICAgaW5wdXRJdG07CisgICAgdmdtRGxnSXRtICAgYnV0dG9uSXRtOworCisgICAgV2luZG93UmVmCXRoZVdpbmRvdzsKKworICAgIC8qIENoZWNrICd2JyBmbGFnIGluICdndWlvcHRpb25zJzogdmVydGljYWwgYnV0dG9uIHBsYWNlbWVudC4gKi8KKyAgICB2ZXJ0aWNhbCA9ICh2aW1fc3RyY2hyKHBfZ28sIEdPX1ZFUlRJQ0FMKSAhPSBOVUxMKTsKKworICAgIC8qIENyZWF0ZSBhIG5ldyBEaWFsb2cgQm94IGZyb20gdGVtcGxhdGUuICovCisgICAgdGhlRGlhbG9nID0gR2V0TmV3RGlhbG9nICgxMjksIG5pbCwgKFdpbmRvd1JlZikgLTEpOworCisgICAgLyogR2V0IHRoZSBXaW5kb3dSZWYgKi8KKyAgICB0aGVXaW5kb3cgPSBHZXREaWFsb2dXaW5kb3codGhlRGlhbG9nKTsKKworICAgIC8qIEhpZGUgdGhlIHdpbmRvdy4KKyAgICAgKiAxLiB0byBhdm9pZCBzZWVpbmcgc2xvdyBkcmF3aW5nCisgICAgICogMi4gdG8gcHJldmVudCBhIHByb2JsZW0gc2VlbiB3aGlsZSBtb3ZpbmcgZGlhbG9nIGl0ZW0KKyAgICAgKiAgICB3aXRoaW4gYSB2aXNpYmxlIHdpbmRvdy4gKG5vbi1DYXJib24gTWFjT1MgOSkKKyAgICAgKiBDb3VsZCBiZSBhdm9pZGVkIGJ5IGNoYW5naW5nIHRoZSByZXNvdXJjZS4KKyAgICAgKi8KKyAgICBIaWRlV2luZG93ICh0aGVXaW5kb3cpOworCisgICAgLyogQ2hhbmdlIHRoZSBncmFwaGljYWwgcG9ydCB0byB0aGUgZGlhbG9nLAorICAgICAqIHNvIHdlIGNhbiBtZWFzdXJlIHRoZSB0ZXh0IHdpdGggdGhlIHByb3BlciBmb250ICovCisgICAgR2V0UG9ydCAoJm9sZFBvcnQpOworI2lmZGVmIFVTRV9DQVJCT05JWkVECisgICAgU2V0UG9ydERpYWxvZ1BvcnQgKHRoZURpYWxvZyk7CisjZWxzZQorICAgIFNldFBvcnQgKHRoZURpYWxvZyk7CisjZW5kaWYKKworICAgIC8qIEdldCB0aGUgaW5mbyBhYm91dCB0aGUgZGVmYXVsdCB0ZXh0LAorICAgICAqIHVzZWQgdG8gY2FsY3VsYXRlIHRoZSBoZWlnaHQgb2YgdGhlIG1lc3NhZ2UKKyAgICAgKiBhbmQgb2YgdGhlICB0ZXh0IGZpZWxkICovCisgICAgR2V0Rm9udEluZm8oJnRleHRGb250SW5mbyk7CisKKyAgICAvKglTZXQgdGhlIGRpYWxvZyB0aXRsZSAqLworICAgIGlmICh0aXRsZSAhPSBOVUxMKQorICAgIHsKKwkodm9pZCkgQzJQYXNjYWxTdHJpbmcgKHRpdGxlLCAmUGFzY2FsVGl0bGUpOworCVNldFdUaXRsZSAodGhlV2luZG93LCBQYXNjYWxUaXRsZSk7CisgICAgfQorCisgICAgLyogQ3JlYXRlcyB0aGUgYnV0dG9ucyBhbmQgYWRkIHRoZW0gdG8gdGhlIERpYWxvZyBCb3guICovCisgICAgYnV0dG9uRElUTCA9IEdldFJlc291cmNlICgnRElUTCcsIDEzMCk7CisgICAgYnV0dG9uQ2hhciA9IGJ1dHRvbnM7CisgICAgYnV0dG9uID0gMDsKKworICAgIGZvciAoOypidXR0b25DaGFyICE9IDA7KQorICAgIHsKKwkvKiBHZXQgdGhlIG5hbWUgb2YgdGhlIGJ1dHRvbiAqLworCWJ1dHRvbisrOworCWxlbiA9IDA7CisJZm9yICg7KCgqYnV0dG9uQ2hhciAhPSBETEdfQlVUVE9OX1NFUCkgJiYgKCpidXR0b25DaGFyICE9IDApICYmIChsZW4gPCAyNTUpKTsgYnV0dG9uQ2hhcisrKQorCXsKKwkgICAgaWYgKCpidXR0b25DaGFyICE9IERMR19IT1RLRVlfQ0hBUikKKwkJbmFtZVsrK2xlbl0gPSAqYnV0dG9uQ2hhcjsKKwl9CisJaWYgKCpidXR0b25DaGFyICE9IDApCisJICBidXR0b25DaGFyKys7CisJbmFtZVswXSA9IGxlbjsKKworCS8qIEFkZCB0aGUgYnV0dG9uICovCisJQXBwZW5kRElUTCAodGhlRGlhbG9nLCBidXR0b25ESVRMLCBvdmVybGF5RElUTCk7IC8qIGFwcGVuZERJVExSaWdodCk7ICovCisKKwkvKiBDaGFuZ2UgdGhlIGJ1dHRvbidzIG5hbWUgKi8KKwltYWNTZXREaWFsb2dJdGVtVGV4dCAodGhlRGlhbG9nLCBidXR0b24sIG5hbWUpOworCisJLyogUmVzaXplIHRoZSBidXR0b24gdG8gZml0IGl0cyBuYW1lICovCisJd2lkdGggPSBTdHJpbmdXaWR0aCAobmFtZSkgKyAyICogZGZsdEJ1dHRvbkVkZ2U7CisJLyogTGltaXRlIHRoZSBzaXplIG9mIGFueSBidXR0b24gdG8gYW4gYWNjZXB0YWJsZSB2YWx1ZS4gKi8KKwkvKiBUT0RPOiBTaG91bGQgYmUgYmFzZWQgb24gdGhlIG1lc3NhZ2Ugd2lkdGggKi8KKwlpZiAod2lkdGggPiBtYXhCdXR0b25XaWR0aCkKKwkgICAgd2lkdGggPSBtYXhCdXR0b25XaWR0aDsKKwltYWNTaXplRGlhbG9nSXRlbSAodGhlRGlhbG9nLCBidXR0b24sIHdpZHRoLCAwKTsKKworCXRvdGFsQnV0dG9uV2lkdGggKz0gd2lkdGg7CisKKwlpZiAod2lkdGggPiB3aWRlc3RCdXR0b24pCisJICAgIHdpZGVzdEJ1dHRvbiA9IHdpZHRoOworICAgIH0KKyAgICBSZWxlYXNlUmVzb3VyY2UgKGJ1dHRvbkRJVEwpOworICAgIGxhc3RCdXR0b24gPSBidXR0b247CisKKyAgICAvKiBBZGQgdGhlIGljb24gdG8gdGhlIERpYWxvZyBCb3guICovCisgICAgaWNvbkl0bS5pZHggPSBsYXN0QnV0dG9uICsgMTsKKyAgICBpY29uRElUTCA9IEdldFJlc291cmNlICgnRElUTCcsIDEzMSk7CisgICAgc3dpdGNoICh0eXBlKQorICAgIHsKKwljYXNlIFZJTV9HRU5FUklDOiAgdXNlSWNvbiA9IGtOb3RlSWNvbjsKKwljYXNlIFZJTV9FUlJPUjogICAgdXNlSWNvbiA9IGtTdG9wSWNvbjsKKwljYXNlIFZJTV9XQVJOSU5HOiAgdXNlSWNvbiA9IGtDYXV0aW9uSWNvbjsKKwljYXNlIFZJTV9JTkZPOiAgICAgdXNlSWNvbiA9IGtOb3RlSWNvbjsKKwljYXNlIFZJTV9RVUVTVElPTjogdXNlSWNvbiA9IGtOb3RlSWNvbjsKKwlkZWZhdWx0OiAgICAgIHVzZUljb24gPSBrU3RvcEljb247CisgICAgfTsKKyAgICBBcHBlbmRESVRMICh0aGVEaWFsb2csIGljb25ESVRMLCBvdmVybGF5RElUTCk7CisgICAgUmVsZWFzZVJlc291cmNlIChpY29uRElUTCk7CisgICAgR2V0RGlhbG9nSXRlbSAodGhlRGlhbG9nLCBpY29uSXRtLmlkeCwgJml0ZW1UeXBlLCAmaXRlbUhhbmRsZSwgJmJveCk7CisgICAgLyogVE9ETzogU2hvdWxkIHRoZSBpdGVtIGJlIGZyZWVkPyAqLworICAgIGljb25IYW5kbGUgPSBHZXRJY29uICh1c2VJY29uKTsKKyAgICBTZXREaWFsb2dJdGVtICh0aGVEaWFsb2csIGljb25JdG0uaWR4LCBpdGVtVHlwZSwgaWNvbkhhbmRsZSwgJmJveCk7CisKKyAgICAvKiBBZGQgdGhlIG1lc3NhZ2UgdG8gdGhlIERpYWxvZyBib3guICovCisgICAgbWVzc2FnZUl0bS5pZHggPSBsYXN0QnV0dG9uICsgMjsKKyAgICBtZXNzYWdlRElUTCA9IEdldFJlc291cmNlICgnRElUTCcsIDEzMik7CisgICAgQXBwZW5kRElUTCAodGhlRGlhbG9nLCBtZXNzYWdlRElUTCwgb3ZlcmxheURJVEwpOworICAgIFJlbGVhc2VSZXNvdXJjZSAobWVzc2FnZURJVEwpOworICAgIEdldERpYWxvZ0l0ZW0gKHRoZURpYWxvZywgbWVzc2FnZUl0bS5pZHgsICZpdGVtVHlwZSwgJml0ZW1IYW5kbGUsICZib3gpOworICAgICh2b2lkKSBDMlBhc2NhbFN0cmluZyAobWVzc2FnZSwgJm5hbWUpOworICAgIFNldERpYWxvZ0l0ZW1UZXh0IChpdGVtSGFuZGxlLCBuYW1lKTsKKyAgICBtZXNzYWdlSXRtLndpZHRoID0gU3RyaW5nV2lkdGggKG5hbWUpOworCisgICAgLyogQWRkIHRoZSBpbnB1dCBib3ggaWYgbmVlZGVkICovCisgICAgaWYgKHRleHRmaWVsZCAhPSBOVUxMKQorICAgIHsKKwkvKiBDaGVhdCBmb3Igbm93IHJldXNlIHRoZSBtZXNzYWdlIGFuZCBjb252ZXQgdG8gdGV4dCBlZGl0ICovCisJaW5wdXRJdG0uaWR4ID0gbGFzdEJ1dHRvbiArIDM7CisJaW5wdXRESVRMID0gR2V0UmVzb3VyY2UgKCdESVRMJywgMTMyKTsKKwlBcHBlbmRESVRMICh0aGVEaWFsb2csIGlucHV0RElUTCwgb3ZlcmxheURJVEwpOworCVJlbGVhc2VSZXNvdXJjZSAoaW5wdXRESVRMKTsKKwlHZXREaWFsb2dJdGVtICh0aGVEaWFsb2csIGlucHV0SXRtLmlkeCwgJml0ZW1UeXBlLCAmaXRlbUhhbmRsZSwgJmJveCk7CisvKgkgIFNldERpYWxvZ0l0ZW0gKHRoZURpYWxvZywgaW5wdXRJdG0uaWR4LCBrRWRpdFRleHREaWFsb2dJdGVtLCBpdGVtSGFuZGxlLCAmYm94KTsqLworCSh2b2lkKSBDMlBhc2NhbFN0cmluZyAodGV4dGZpZWxkLCAmbmFtZSk7CisJU2V0RGlhbG9nSXRlbVRleHQgKGl0ZW1IYW5kbGUsIG5hbWUpOworCWlucHV0SXRtLndpZHRoID0gU3RyaW5nV2lkdGggKG5hbWUpOworICAgIH0KKworICAgIC8qIFNldCB0aGUgPEVOVEVSPiBhbmQgPEVTQz4gYnV0dG9uLiAqLworICAgIFNldERpYWxvZ0RlZmF1bHRJdGVtICh0aGVEaWFsb2csIGRmbHRidXR0b24pOworICAgIFNldERpYWxvZ0NhbmNlbEl0ZW0gKHRoZURpYWxvZywgMCk7CisKKyAgICAvKiBSZXBvc2l0aW9uIGVsZW1lbnQgKi8KKworICAgIC8qIENoZWNrIGlmIHdlIG5lZWQgdG8gZm9yY2UgdmVydGljYWwgKi8KKyAgICBpZiAodG90YWxCdXR0b25XaWR0aCA+IG1heGltdW1XaWR0aCkKKwl2ZXJ0aWNhbCA9IFRSVUU7CisKKyAgICAvKiBQbGFjZSBpY29uICovCisgICAgbWFjTW92ZURpYWxvZ0l0ZW0gKHRoZURpYWxvZywgaWNvbkl0bS5pZHgsIGRmbHRJY29uU2lkZVNwYWNlLCBkZmx0RWxlbWVudFNwYWNpbmcsICZib3gpOworICAgIGljb25JdG0uYm94LnJpZ2h0ID0gYm94LnJpZ2h0OworICAgIGljb25JdG0uYm94LmJvdHRvbSA9IGJveC5ib3R0b207CisKKyAgICAvKiBQbGFjZSBNZXNzYWdlICovCisgICAgbWVzc2FnZUl0bS5ib3gubGVmdCA9IGljb25JdG0uYm94LnJpZ2h0ICsgZGZsdEljb25TaWRlU3BhY2U7CisgICAgbWFjU2l6ZURpYWxvZ0l0ZW0gKHRoZURpYWxvZywgbWVzc2FnZUl0bS5pZHgsIDAsICBtZXNzYWdlTGluZXMgKiAodGV4dEZvbnRJbmZvLmFzY2VudCArIHRleHRGb250SW5mby5kZXNjZW50KSk7CisgICAgbWFjTW92ZURpYWxvZ0l0ZW0gKHRoZURpYWxvZywgbWVzc2FnZUl0bS5pZHgsIG1lc3NhZ2VJdG0uYm94LmxlZnQsIGRmbHRFbGVtZW50U3BhY2luZywgJm1lc3NhZ2VJdG0uYm94KTsKKworICAgIC8qIFBsYWNlIElucHV0ICovCisgICAgaWYgKHRleHRmaWVsZCAhPSBOVUxMKQorICAgIHsKKwlpbnB1dEl0bS5ib3gubGVmdCA9IG1lc3NhZ2VJdG0uYm94LmxlZnQ7CisJaW5wdXRJdG0uYm94LnRvcCAgPSBtZXNzYWdlSXRtLmJveC5ib3R0b20gKyBkZmx0RWxlbWVudFNwYWNpbmc7CisJbWFjU2l6ZURpYWxvZ0l0ZW0gKHRoZURpYWxvZywgaW5wdXRJdG0uaWR4LCAwLCB0ZXh0Rm9udEluZm8uYXNjZW50ICsgdGV4dEZvbnRJbmZvLmRlc2NlbnQpOworCW1hY01vdmVEaWFsb2dJdGVtICh0aGVEaWFsb2csIGlucHV0SXRtLmlkeCwgaW5wdXRJdG0uYm94LmxlZnQsIGlucHV0SXRtLmJveC50b3AsICZpbnB1dEl0bS5ib3gpOworCS8qIENvbnZlcnQgdGhlIHN0YXRpYyB0ZXh0IGludG8gYSB0ZXh0IGVkaXQuCisJICogRm9yIHNvbWUgcmVhc29uIHRoaXMgY2hhbmdlIG5lZWQgdG8gYmUgZG9uZSBsYXN0IChEYW55KSAqLworCUdldERpYWxvZ0l0ZW0gKHRoZURpYWxvZywgaW5wdXRJdG0uaWR4LCAmaXRlbVR5cGUsICZpdGVtSGFuZGxlLCAmaW5wdXRJdG0uYm94KTsKKwlTZXREaWFsb2dJdGVtICh0aGVEaWFsb2csIGlucHV0SXRtLmlkeCwga0VkaXRUZXh0RGlhbG9nSXRlbSwgaXRlbUhhbmRsZSwgJmlucHV0SXRtLmJveCk7CisJU2VsZWN0RGlhbG9nSXRlbVRleHQodGhlRGlhbG9nLCBpbnB1dEl0bS5pZHgsIDAsIDMyNzY3KTsKKyAgICB9CisKKyAgICAvKiBQbGFjZSBCdXR0b24gKi8KKyAgICBpZiAodGV4dGZpZWxkICE9IE5VTEwpCisgICAgeworCWJ1dHRvbkl0bS5ib3gubGVmdCA9IGlucHV0SXRtLmJveC5sZWZ0OworCWJ1dHRvbkl0bS5ib3gudG9wICA9IGlucHV0SXRtLmJveC5ib3R0b20gKyBkZmx0RWxlbWVudFNwYWNpbmc7CisgICAgfQorICAgIGVsc2UKKyAgICB7CisJYnV0dG9uSXRtLmJveC5sZWZ0ID0gbWVzc2FnZUl0bS5ib3gubGVmdDsKKwlidXR0b25JdG0uYm94LnRvcCAgPSBtZXNzYWdlSXRtLmJveC5ib3R0b20gKyBkZmx0RWxlbWVudFNwYWNpbmc7CisgICAgfQorCisgICAgZm9yIChidXR0b249MTsgYnV0dG9uIDw9IGxhc3RCdXR0b247IGJ1dHRvbisrKQorICAgIHsKKworCW1hY01vdmVEaWFsb2dJdGVtICh0aGVEaWFsb2csIGJ1dHRvbiwgYnV0dG9uSXRtLmJveC5sZWZ0LCBidXR0b25JdG0uYm94LnRvcCwgJmJveCk7CisJLyogV2l0aCB2ZXJ0aWNhbCwgaXQncyBiZXR0ZXIgdG8gaGF2ZSBhbGwgYnV0dG9uIHRoZSBzYW1lIGxlbmdodCAqLworCWlmICh2ZXJ0aWNhbCkKKwl7CisJICAgIG1hY1NpemVEaWFsb2dJdGVtICh0aGVEaWFsb2csIGJ1dHRvbiwgd2lkZXN0QnV0dG9uLCAwKTsKKwkgICAgR2V0RGlhbG9nSXRlbSAodGhlRGlhbG9nLCBidXR0b24sICZpdGVtVHlwZSwgJml0ZW1IYW5kbGUsICZib3gpOworCX0KKwkvKiBDYWxjdWxhdGUgcG9zaXRpb24gb2YgbmV4dCBidXR0b24gKi8KKwlpZiAodmVydGljYWwpCisJICAgIGJ1dHRvbkl0bS5ib3gudG9wICA9IGJveC5ib3R0b20gKyBkZmx0RWxlbWVudFNwYWNpbmc7CisJZWxzZQorCSAgICBidXR0b25JdG0uYm94LmxlZnQgID0gYm94LnJpZ2h0ICsgZGZsdEVsZW1lbnRTcGFjaW5nOworICAgIH0KKworICAgIC8qIFJlc2l6ZSB0aGUgZGlhbG9nIGJveCAqLworICAgIGRpYWxvZ0hlaWdodCA9IGJveC5ib3R0b20gKyBkZmx0RWxlbWVudFNwYWNpbmc7CisgICAgU2l6ZVdpbmRvdyh0aGVXaW5kb3csIG1heGltdW1XaWR0aCwgZGlhbG9nSGVpZ2h0LCBUUlVFKTsKKworI2lmZGVmIFVTRV9DQVJCT05JWkVECisgICAgLyogTWFnaWMgcmVzaXplICovCisgICAgQXV0b1NpemVEaWFsb2cgKHRoZURpYWxvZyk7CisgICAgLyogTmVlZCBhIGhvcml6b250YWwgcmVzaXplIGFueXdheSBzbyBub3QgdGhhdCB1c2VmdWwgKi8KKyNlbmRpZgorCisgICAgLyogRGlzcGxheSBpdCAqLworICAgIFNob3dXaW5kb3codGhlV2luZG93KTsKKy8qICBCcmluZ1RvRnJvbnQodGhlV2luZG93KTsgKi8KKyAgICBTZWxlY3RXaW5kb3codGhlV2luZG93KTsKKworLyogIERyYXdEaWFsb2cgKHRoZURpYWxvZyk7ICovCisjaWYgMAorICAgIEdldFBvcnQgKCZvbGRQb3J0KTsKKyNpZmRlZiBVU0VfQ0FSQk9OSVpFRAorICAgIFNldFBvcnREaWFsb2dQb3J0ICh0aGVEaWFsb2cpOworI2Vsc2UKKyAgICBTZXRQb3J0ICh0aGVEaWFsb2cpOworI2VuZGlmCisjZW5kaWYKKworICAgIC8qIEhhbmcgdW50aWwgb25lIG9mIHRoZSBidXR0b24gaXMgaGl0ICovCisgICAgZG8KKyAgICB7CisJTW9kYWxEaWFsb2cgKG5pbCwgJml0ZW1IaXQpOworICAgIH0gd2hpbGUgKChpdGVtSGl0IDwgMSkgfHwgKGl0ZW1IaXQgPiBsYXN0QnV0dG9uKSk7CisKKyAgICAvKiBDb3B5IGJhY2sgdGhlIHRleHQgZW50ZXJlZCBieSB0aGUgdXNlciBpbnRvIHRoZSBwYXJhbSAqLworICAgIGlmICh0ZXh0ZmllbGQgIT0gTlVMTCkKKyAgICB7CisJR2V0RGlhbG9nSXRlbSAodGhlRGlhbG9nLCBpbnB1dEl0bS5pZHgsICZpdGVtVHlwZSwgJml0ZW1IYW5kbGUsICZib3gpOworCUdldERpYWxvZ0l0ZW1UZXh0IChpdGVtSGFuZGxlLCAoY2hhcl91ICopICZuYW1lKTsKKyNpZiBJT1NJWkUgPCAyNTYKKwkvKiBUcnVuY2F0ZSB0aGUgbmFtZSB0byBJT1NJWkUgaWYgbmVlZGVkICovCisJaWYgKG5hbWVbMF0gPiBJT1NJWkUpCisJICAgIG5hbWVbMF0gPSBJT1NJWkUgLSAxOworI2VuZGlmCisJU1RSTkNQWSh0ZXh0ZmllbGQsICZuYW1lWzFdLCBuYW1lWzBdKTsKKwl0ZXh0ZmllbGRbbmFtZVswXV0gPSBOVUw7CisgICAgfQorCisgICAgLyogUmVzdG9yZSB0aGUgb3JpZ2luYWwgZ3JhcGhpY2FsIHBvcnQgKi8KKyAgICBTZXRQb3J0IChvbGRQb3J0KTsKKworICAgIC8qIEdldCByaWRlIG9mIHRoIGVkaWFsb2cgKGZyZWUgbWVtb3J5KSAqLworICAgIERpc3Bvc2VEaWFsb2cgKHRoZURpYWxvZyk7CisKKyAgICByZXR1cm4gaXRlbUhpdDsKKy8qCisgKiBVc2VmdWxsIHRoaW5nIHdoaWNoIGNvdWxkIGJlIHVzZWQKKyAqIFNldERpYWxvZ1RpbWVvdXQoKTogQXV0byBjbGljayBhIGJ1dHRvbiBhZnRlciB0aW1lb3V0CisgKiBTZXREaWFsb2dUcmFja3NDdXJzb3IoKSA6IEdldCB0aGUgSS1iZWFtIGN1cnNvciBvdmVyIGlucHV0IGJveAorICogTW92ZURpYWxvZ0l0ZW0oKToJICAgIFByb2JhYmx5IGJldHRlciB0aGFuIFNldERpYWxvZ0l0ZW0KKyAqIFNpemVEaWFsb2dJdGVtKCk6CQkoYnV0IGlzIGl0IENhcmJvbiBPbmx5PykKKyAqIEF1dG9TaXplRGlhbG9nKCk6CSAgICBNYWdpYyByZXNpemUgb2YgZGlhbG9nIGJhc2VkIG9uIHRleHQgbGVuZ2h0CisgKi8KK30KKyNlbmRpZiAvKiBGRUFUX0RJQUxPR19HVUkgKi8KKworLyoKKyAqIERpc3BsYXkgdGhlIHNhdmVkIGVycm9yIG1lc3NhZ2UocykuCisgKi8KKyNpZmRlZiBVU0VfTUNIX0VSUk1TRworICAgIHZvaWQKK2Rpc3BsYXlfZXJyb3JzKCkKK3sKKyAgICBjaGFyCSpwOworICAgIGNoYXJfdQlwRXJyb3JbMjU2XTsKKworICAgIGlmIChlcnJvcl9nYS5nYV9kYXRhICE9IE5VTEwpCisgICAgeworCS8qIGF2b2lkIHB1dHRpbmcgdXAgYSBtZXNzYWdlIGJveCB3aXRoIGJsYW5rcyBvbmx5ICovCisJZm9yIChwID0gKGNoYXIgKillcnJvcl9nYS5nYV9kYXRhOyAqcDsgKytwKQorCSAgICBpZiAoIWlzc3BhY2UoKnApKQorCSAgICB7CisJCWlmIChTVFJMRU4ocCkgPiAyNTUpCisJCSAgICBwRXJyb3JbMF0gPSAyNTU7CisJCWVsc2UKKwkJICAgIHBFcnJvclswXSA9IFNUUkxFTihwKTsKKworCQlTVFJOQ1BZKCZwRXJyb3JbMV0sIHAsIHBFcnJvclswXSk7CisJCVBhcmFtVGV4dCAocEVycm9yLCBuaWwsIG5pbCwgbmlsKTsKKwkJQWxlcnQgKDEyOCwgbmlsKTsKKwkJYnJlYWs7CisJCS8qIFRPRE86IGhhbmRsZWQgbWVzc2FnZSBsb25nZXIgdGhhbiAyNTYgY2hhcnMKKwkJICoJIHVzZSBhdXRvLXNpemVhYmxlIGFsZXJ0CisJCSAqCSBvciBkaWFsb2cgd2l0aCBzY3JvbGxiYXJzIChUZXh0RWRpdCB6b25lKQorCQkgKi8KKwkgICAgfQorCWdhX2NsZWFyKCZlcnJvcl9nYSk7CisgICAgfQorfQorI2VuZGlmCisKKy8qCisgKiBHZXQgY3VycmVudCB5IG1vdXNlIGNvb3JkaW5hdGUgaW4gdGV4dCB3aW5kb3cuCisgKiBSZXR1cm4gLTEgd2hlbiB1bmtub3duLgorICovCisgICAgaW50CitndWlfbWNoX2dldF9tb3VzZV94KCkKK3sKKyAgICBQb2ludCB3aGVyZTsKKworICAgIEdldE1vdXNlKCZ3aGVyZSk7CisKKyAgICByZXR1cm4gKHdoZXJlLmgpOworfQorCisgICAgaW50CitndWlfbWNoX2dldF9tb3VzZV95KCkKK3sKKyAgICBQb2ludCB3aGVyZTsKKworICAgIEdldE1vdXNlKCZ3aGVyZSk7CisKKyAgICByZXR1cm4gKHdoZXJlLnYpOworfQorCisgICAgdm9pZAorZ3VpX21jaF9zZXRtb3VzZSh4LCB5KQorICAgIGludAkJeDsKKyAgICBpbnQJCXk7Cit7CisgICAgLyogVE9ETyAqLworI2lmIDAKKyAgICAvKiBGcm9tIEZBUSAzLTExICovCisKKyAgICBDdXJzb3JEZXZpY2VQdHIgbXlNb3VzZTsKKyAgICBQb2ludAkgICAgd2hlcmU7CisKKyAgICBpZiAoICAgTkdldFRyYXBBZGRyZXNzIChfQ3Vyc29yRGV2aWNlRGlzcGF0Y2gsIFRvb2xUcmFwKQorCSE9IE5HZXRUcmFwQWRkcmVzcyAoX1VuaW1wbGVtZW50ZWQsICAgVG9vbFRyYXApICkKKyAgICB7CisJLyogTmV3IHdheSAqLworCisJLyoKKwkgKiBHZXQgZmlyc3QgZGV2b2ljZSB3aXRoIG9uZSBidXR0b24uCisJICogVGhpcyB3aWxsIHByb2JhYmx5IGJlIHRoZSBzdGFuZGFkIG1vdXNlCisJICogc3RhcnRhdCBoZWFkIG9mIGN1cnNvciBkZXYgbGlzdAorCSAqCisJICovCisKKwlteU1vdXNlID0gbmlsOworCisJZG8KKwl7CisJICAgIC8qIEdldCB0aGUgbmV4dCBjdXJzb3IgZGV2aWNlICovCisJICAgIEN1cnNvckRldmljZU5leHREZXZpY2UoJm15TW91c2UpOworCX0KKwl3aGlsZSAoIChteU1vdXNlICE9IG5pbCkgJiYgKG15TW91c2UtPmNudEJ1dHRvbnMgIT0gMSkgKTsKKworCUN1cnNvckRldmljZU1vdmVUbyAobXlNb3VzZSwgeCwgeSk7CisgICAgfQorICAgIGVsc2UKKyAgICB7CisJLyogT2xkIHdheSAqLworCXdoZXJlLmggPSB4OworCXdoZXJlLnYgPSB5OworCisJKihQb2ludCAqKVJhd01vdXNlID0gd2hlcmU7CisJKihQb2ludCAqKU1UZW1wICAgID0gd2hlcmU7CisJKihQdHIpICAgIENyc3JOZXcgID0gMHhGRkZGOworICAgIH0KKyNlbmRpZgorfQorCisgICAgdm9pZAorZ3VpX21jaF9zaG93X3BvcHVwbWVudShtZW51KQorICAgIHZpbW1lbnVfVCAqbWVudTsKK3sKKyNpZmRlZiBVU0VfQ1RSTENMSUNLTUVOVQorLyoKKyAqICBDbG9uZSBQb3BVcCB0byB1c2UgbWVudQorICogIENyZWF0ZSBhIG9iamVjdCBkZXNjcmlwdG9yIGZvciB0aGUgY3VycmVudCBzZWxlY3Rpb24KKyAqICBDYWxsIHRoZSBwcm9jZWR1cmUKKyAqLworCisgICAgTWVudUhhbmRsZQlDbnR4TWVudTsKKyAgICBQb2ludAl3aGVyZTsKKyAgICBPU1N0YXR1cwlzdGF0dXM7CisgICAgVUludDMyCUNudHhUeXBlOworICAgIFNJbnQxNglDbnR4TWVudUlEOworICAgIFVJbnQxNglDbnR4TWVudUl0ZW07CisgICAgU3RyMjU1CUhlbHBOYW1lID0gIiI7CisgICAgR3JhZlB0cglzYXZlUG9ydDsKKworICAgIC8qIFNhdmUgQ3VycmVudCBQb3J0OiBPbiBNYWNPUyBYIHdlIHNlZW0gdG8gbG9zZSB0aGUgcG9ydCAqLworICAgIEdldFBvcnQgKCZzYXZlUG9ydCk7IC8qT1NYKi8KKworICAgIEdldE1vdXNlICgmd2hlcmUpOworICAgIExvY2FsVG9HbG9iYWwgKCZ3aGVyZSk7IC8qT1NYKi8KKyAgICBDbnR4TWVudSA9IG1lbnUtPnN1Ym1lbnVfaGFuZGxlOworCisgICAgLyogVE9ETzogR2V0IHRoZSB0ZXh0IHNlbGVjdGlvbiBmcm9tIFZpbSAqLworCisgICAgLyogQ2FsbCB0byBIYW5kbGUgUG9wdXAgKi8KKyAgICBzdGF0dXMgPSBDb250ZXh0dWFsTWVudVNlbGVjdChDbnR4TWVudSwgd2hlcmUsIGZhbHNlLCBrQ01IZWxwSXRlbU5vSGVscCwgSGVscE5hbWUsIE5VTEwsICZDbnR4VHlwZSwgJkNudHhNZW51SUQsICZDbnR4TWVudUl0ZW0pOworCisgICAgaWYgKHN0YXR1cyA9PSBub0VycikKKyAgICB7CisJaWYgKENudHhUeXBlID09IGtDTU1lbnVJdGVtU2VsZWN0ZWQpCisJeworCSAgICAvKiBIYW5kbGUgdGhlIG1lbnUgQ250eE1lbnVJRCwgQ250eE1lbnVJdGVtICovCisJICAgIC8qIFRoZSBzdWJtZW51IGNhbiBiZSBoYW5kbGUgZGlyZWN0bHkgYnkgZ3VpX21hY19oYW5kbGVfbWVudSAqLworCSAgICAvKiBCdXQgd2hhdCBhYm91dCB0aGUgY3VycmVudCBtZW51LCBpcyB0aGUgbWVudSBjaGFuZ2VkIGJ5IENvbnRleHR1YWxNZW51U2VsZWN0ICovCisJICAgIGd1aV9tYWNfaGFuZGxlX21lbnUgKChDbnR4TWVudUlEIDw8IDE2KSArIENudHhNZW51SXRlbSk7CisJfQorCWVsc2UgaWYgKENudHhNZW51SUQgPT0ga0NNU2hvd0hlbHBTZWxlY3RlZCkKKwl7CisJICAgIC8qIFNob3VsZCBjb21lIHVwIHdpdGggdGhlIGhlbHAgKi8KKwl9CisgICAgfQorCisgICAgLyogUmVzdG9yZSBvcmlnaW5hbCBQb3J0ICovCisgICAgU2V0UG9ydCAoc2F2ZVBvcnQpOyAvKk9TWCovCisjZW5kaWYKK30KKworI2lmIGRlZmluZWQoRkVBVF9DV19FRElUT1IpIHx8IGRlZmluZWQoUFJPVE8pCisvKiBUT0RPOiBJcyBpdCBuZWVkIGZvciBNQUNPU19YPyAoRGFueSkgKi8KKyAgICB2b2lkCittY2hfcG9zdF9idWZmZXJfd3JpdGUoYnVmX1QgKmJ1ZikKK3sKKyMgaWZkZWYgVVNFX1NJT1VYCisgICAgcHJpbnRmICgiV3JpdGluZyBCdWYuLi5cbiIpOworIyBlbmRpZgorICAgIEdldEZTU3BlY0Zyb21QYXRoIChidWYtPmJfZmZuYW1lLCAmYnVmLT5iX0ZTU3BlYyk7CisgICAgU2VuZF9LQUhMX01PRF9BRSAoYnVmKTsKK30KKyNlbmRpZgorCisjaWZkZWYgRkVBVF9USVRMRQorLyoKKyAqIFNldCB0aGUgd2luZG93IHRpdGxlIGFuZCBpY29uLgorICogKFRoZSBpY29uIGlzIG5vdCB0YWtlbiBjYXJlIG9mKS4KKyAqLworICAgIHZvaWQKK2d1aV9tY2hfc2V0dGl0bGUodGl0bGUsIGljb24pCisgICAgY2hhcl91ICp0aXRsZTsKKyAgICBjaGFyX3UgKmljb247Cit7CisgICAgLyogVE9ETzogR2V0IHZpbSB0byBtYWtlIHN1cmUgbWF4bGVuIChmcm9tIHBfdGl0bGVsZW4pIGlzIHNtYWxsZXIKKyAgICAgKiAgICAgICB0aGF0IDI1Ni4gRXZlbiBiZXR0ZXIgZ2V0IGl0IHRvIGZpdCBuaWNlbHkgaW4gdGhlIHRpdGxlYmFyLgorICAgICAqLworICAgIGNoYXJfdSAgICpwYXNjYWxUaXRsZTsKKworICAgIGlmICh0aXRsZSA9PSBOVUxMKQkJLyogbm90aGluZyB0byBkbyAqLworCXJldHVybjsKKworICAgIHBhc2NhbFRpdGxlID0gQzJQYXNjYWxfc2F2ZSh0aXRsZSk7CisgICAgaWYgKHBhc2NhbFRpdGxlICE9IE5VTEwpCisgICAgeworCVNldFdUaXRsZShndWkuVmltV2luZG93LCBwYXNjYWxUaXRsZSk7CisJdmltX2ZyZWUocGFzY2FsVGl0bGUpOworICAgIH0KK30KKyNlbmRpZgorCisvKgorICogVHJhbnNmZXJlZCBmcm9tIG9zX21hYy5jIGZvciBNYWNPUyBYIHVzaW5nIG9zX3VuaXguYyBwcmVwIHdvcmsKKyAqLworCisgICAgaW50CitDMlBhc2NhbFN0cmluZyAoQ1N0cmluZywgUGFzY2FsU3RyaW5nKQorICAgIGNoYXJfdSAgKkNTdHJpbmc7CisgICAgU3RyMjU1ICAqUGFzY2FsU3RyaW5nOworeworICAgIGNoYXJfdSAqUGFzY2FsUHRyID0gKGNoYXJfdSAqKSBQYXNjYWxTdHJpbmc7CisgICAgaW50ICAgIGxlbjsKKyAgICBpbnQgICAgaTsKKworICAgIFBhc2NhbFB0clswXSA9IDA7CisgICAgaWYgKENTdHJpbmcgPT0gTlVMTCkKKwlyZXR1cm4gMDsKKworICAgIGxlbiA9IFNUUkxFTihDU3RyaW5nKTsKKyAgICBpZiAobGVuID4gMjU1KQorCWxlbiA9IDI1NTsKKworICAgIGZvciAoaSA9IDA7IGkgPCBsZW47IGkrKykKKwlQYXNjYWxQdHJbaSsxXSA9IENTdHJpbmdbaV07CisKKyAgICBQYXNjYWxQdHJbMF0gPSBsZW47CisKKyAgICByZXR1cm4gMDsKK30KKworICAgIGludAorR2V0RlNTcGVjRnJvbVBhdGggKGZpbGUsIGZpbGVGU1NwZWMpCisgICAgY2hhcl91ICpmaWxlOworICAgIEZTU3BlYyAqZmlsZUZTU3BlYzsKK3sKKyAgICAvKiBGcm9tIEZBUSA4LTEyICovCisgICAgU3RyMjU1ICAgICAgZmlsZVBhc2NhbDsKKyAgICBDSW5mb1BCUmVjCW15Q1BCOworICAgIE9TRXJyCWVycjsKKworICAgICh2b2lkKSBDMlBhc2NhbFN0cmluZyAoZmlsZSwgJmZpbGVQYXNjYWwpOworCisgICAgbXlDUEIuZGlySW5mby5pb05hbWVQdHIgICA9IGZpbGVQYXNjYWw7CisgICAgbXlDUEIuZGlySW5mby5pb1ZSZWZOdW0gICA9IDA7CisgICAgbXlDUEIuZGlySW5mby5pb0ZEaXJJbmRleCA9IDA7CisgICAgbXlDUEIuZGlySW5mby5pb0RyRGlySUQgICA9IDA7CisKKyAgICBlcnI9IFBCR2V0Q2F0SW5mbyAoJm15Q1BCLCBmYWxzZSk7CisKKyAgICAvKiAgICB2UmVmTnVtLCBkaXJJRCwgbmFtZSAqLworICAgIEZTTWFrZUZTU3BlYyAoMCwgMCwgZmlsZVBhc2NhbCwgZmlsZUZTU3BlYyk7CisKKyAgICAvKiBUT0RPOiBVc2UgYW4gZXJyb3IgY29kZSBtZWNoYW5pc20gKi8KKyAgICByZXR1cm4gMDsKK30KKworLyoKKyAqIENvbnZlcnQgYSBGU1NwZWMgdG8gYSBmdWlsbCBwYXRoCisgKi8KKworY2hhcl91ICpGdWxsUGF0aEZyb21GU1NwZWNfc2F2ZSAoRlNTcGVjIGZpbGUpCit7CisgICAgLyoKKyAgICAgKiBUT0RPOiBBZGQgcHJvdGVjdGlvbiBmb3IgMjU2IGNoYXIgbWF4LgorICAgICAqLworCisgICAgQ0luZm9QQlJlYwl0aGVDUEI7CisgICAgY2hhcl91CWZuYW1lWzI1Nl07CisgICAgY2hhcl91CSpmaWxlbmFtZVB0ciA9IGZuYW1lOworICAgIE9TRXJyCWVycm9yOworICAgIGludAkJZm9sZGVyID0gMTsKKyNpZmRlZiBVU0VfVU5JWEZJTEVOQU1FCisgICAgU0ludDE2CWRmbHRWb2xfdlJlZk51bTsKKyAgICBTSW50MzIJZGZsdFZvbF9kaXJJRDsKKyAgICBGU1JlZglyZWZGaWxlOworICAgIE9TU3RhdHVzCXN0YXR1czsKKyAgICBVSW50MzIJcGF0aFNpemUgPSAyNTY7CisgICAgY2hhcl91CXBhdGhuYW1lWzI1Nl07CisgICAgY2hhcl91CSpwYXRoID0gcGF0aG5hbWU7CisjZWxzZQorICAgIFN0cjI1NQlkaXJlY3RvcnlOYW1lOworICAgIGNoYXJfdQl0ZW1wb3JhcnlbMjU1XTsKKyAgICBjaGFyX3UJKnRlbXBvcmFyeVB0ciA9IHRlbXBvcmFyeTsKKyNlbmRpZgorCisjaWZkZWYgVVNFX1VOSVhGSUxFTkFNRQorICAgIC8qIEdldCB0aGUgZGVmYXVsdCB2b2x1bWUgKi8KKyAgICAvKiBUT0RPOiBSZW1vdmUgYXMgdGhpcyBvbmx5IHdvcmsgaWYgVmltIGlzIG9uIHRoZSBCb290IFZvbHVtZSovCisgICAgZXJyb3I9SEdldFZvbCAoIE5VTEwsICZkZmx0Vm9sX3ZSZWZOdW0sICZkZmx0Vm9sX2RpcklEICk7CisKKyAgICBpZiAoZXJyb3IpCisgICAgICByZXR1cm4gTlVMTDsKKyNlbmRpZgorCisgICAgLyogU3RhcnQgZmlsbGluZyBmbmFtZSB3aXRoIGZpbGUubmFtZSAgKi8KKyAgICBTVFJOQ1BZKGZpbGVuYW1lUHRyLCAmZmlsZS5uYW1lWzFdLCBmaWxlLm5hbWVbMF0pOworICAgIGZpbGVuYW1lUHRyW2ZpbGUubmFtZVswXV0gPSAwOyAvKiBOVUxMIHRlcm1pbmF0ZSB0aGUgc3RyaW5nICovCisKKyAgICAvKiBHZXQgdGhlIGluZm8gYWJvdXQgdGhlIGZpbGUgc3BlY2lmaWVkIGluIEZTU3BlYyAqLworICAgIHRoZUNQQi5kaXJJbmZvLmlvRkRpckluZGV4ID0gMDsKKyAgICB0aGVDUEIuZGlySW5mby5pb05hbWVQdHIgICA9IGZpbGUubmFtZTsKKyAgICB0aGVDUEIuZGlySW5mby5pb1ZSZWZOdW0gICA9IGZpbGUudlJlZk51bTsKKyAgLyp0aGVDUEIuaEZpbGVJbmZvLmlvRGlySUQgICA9IDA7Ki8KKyAgICB0aGVDUEIuZGlySW5mby5pb0RyRGlySUQgICA9IGZpbGUucGFySUQ7CisKKyAgICAvKiBBcyBpb0ZEaXJJbmRleCA9IDAsIGdldCB0aGUgaW5mbyBvZiBpb05hbWVQdHIsCisgICAgICAgd2hpY2ggaXMgcmVsYXRpdmUgdG8gaW9WcmVmTnVtLCBpb0RpcklEICovCisgICAgZXJyb3IgPSBQQkdldENhdEluZm8gKCZ0aGVDUEIsIGZhbHNlKTsKKworICAgIC8qIElmIHdlIGFyZSBjYWxsZWQgZm9yIGEgbmV3IGZpbGUgd2UgZXhwZWN0IGZuZkVyciAqLworICAgIGlmICgoZXJyb3IpICYmIChlcnJvciAhPSBmbmZFcnIpKQorICAgICAgcmV0dXJuIE5VTEw7CisKKyAgICAvKiBDaGVjayBpZiBpdCdzIGEgZmlsZSBvciBmb2xkZXIgICAgICAgKi8KKyAgICAvKiBkZWZhdWx0IHRvIGZpbGUgaWYgZmlsZSBkb24ndCBleGlzdCAgKi8KKyAgICBpZiAoKCh0aGVDUEIuaEZpbGVJbmZvLmlvRmxBdHRyaWIgJiBpb0Rpck1hc2spID09IDApIHx8IChlcnJvcikpCisgICAgICBmb2xkZXIgPSAwOyAvKiBJdCdzIG5vdCBhIGZvbGRlciAqLworICAgIGVsc2UKKyAgICAgIGZvbGRlciA9IDE7CisKKyNpZmRlZiBVU0VfVU5JWEZJTEVOQU1FCisgICAgLyoKKyAgICAgKiBUaGUgZnVuY3Rpb24gdXNlZCBoZXJlIGFyZSBhdmFpbGFibGUgaW4gQ2FyYm9uLCBidXQKKyAgICAgKiBkbyBub3RoaW5nIHVuZSBNYWNPUyA4IGFuZCA5CisgICAgICovCisgICAgaWYgKGVycm9yID09IGZuZkVycikKKyAgICB7CisJLyogSWYgdGhlIGZpbGUgdG8gYmUgc2F2ZWQgZG9lcyBub3QgYWxyZWFkeSBleGlzdCwgaXQgaXNuJ3QgcG9zc2libGUKKwkgICB0byBjb252ZXJ0IGl0cyBGU1NwZWMgaW50byBhbiBGU1JlZi4gIEJ1dCB3ZSBjYW4gY29uc3RydWN0IGFuCisJICAgRlNTcGVjIGZvciB0aGUgZmlsZSdzIHBhcmVudCBmb2xkZXIgKHNpbmNlIHdlIGhhdmUgaXRzIHZvbHVtZSBhbmQKKwkgICBkaXJlY3RvcnkgSURzKSwgYW5kIHNpbmNlIHRoYXQgZm9sZGVyIGRvZXMgZXhpc3QsIHdlIGNhbiBjb252ZXJ0CisJICAgdGhhdCBGU1NwZWMgaW50byBhbiBGU1JlZiwgY29udmVydCB0aGUgRlNSZWYgaW4gdHVybiBpbnRvIGEgcGF0aCwKKwkgICBhbmQsIGZpbmFsbHksIGFwcGVuZCB0aGUgZmlsZW5hbWUuICovCisJRlNTcGVjIGRpclNwZWM7CisJRlNSZWYgZGlyUmVmOworCVN0cjI1NSBlbXB0eUZpbGVuYW1lID0gIlxwIjsKKwllcnJvciA9IEZTTWFrZUZTU3BlYyh0aGVDUEIuZGlySW5mby5pb1ZSZWZOdW0sCisJICAgIHRoZUNQQi5kaXJJbmZvLmlvRHJEaXJJRCwgZW1wdHlGaWxlbmFtZSwgJmRpclNwZWMpOworCWlmIChlcnJvcikKKwkgICAgcmV0dXJuIE5VTEw7CisKKwllcnJvciA9IEZTcE1ha2VGU1JlZigmZGlyU3BlYywgJmRpclJlZik7CisJaWYgKGVycm9yKQorCSAgICByZXR1cm4gTlVMTDsKKworCXN0YXR1cyA9IEZTUmVmTWFrZVBhdGgoJmRpclJlZiwgKFVJbnQ4KilwYXRoLCBwYXRoU2l6ZSk7CisJaWYgKHN0YXR1cykKKwkgICAgcmV0dXJuIE5VTEw7CisKKwlTVFJDQVQocGF0aCwgIi8iKTsKKwlTVFJDQVQocGF0aCwgZmlsZW5hbWVQdHIpOworICAgIH0KKyAgICBlbHNlCisgICAgeworCS8qIElmIHRoZSBmaWxlIHRvIGJlIHNhdmVkIGFscmVhZHkgZXhpc3RzLCB3ZSBjYW4gZ2V0IGl0cyBmdWxsIHBhdGgKKwkgICBieSBjb252ZXJ0aW5nIGl0cyBGU1NwZWMgaW50byBhbiBGU1JlZi4gKi8KKwllcnJvcj1GU3BNYWtlRlNSZWYgKCZmaWxlLCAmcmVmRmlsZSk7CisJaWYgKGVycm9yKQorCSAgICByZXR1cm4gTlVMTDsKKworCXN0YXR1cz1GU1JlZk1ha2VQYXRoICgmcmVmRmlsZSwgKFVJbnQ4ICopIHBhdGgsIHBhdGhTaXplKTsKKwlpZiAoc3RhdHVzKQorCSAgICByZXR1cm4gTlVMTDsKKyAgICB9CisKKyAgICAvKiBBZGQgYSBzbGFzaCBhdCB0aGUgZW5kIGlmIG5lZWRlZCAqLworICAgIGlmIChmb2xkZXIpCisJU1RSQ0FUIChwYXRoLCAiLyIpOworCisgICAgcmV0dXJuICh2aW1fc3Ryc2F2ZSAocGF0aCkpOworI2Vsc2UKKyAgICAvKiBUT0RPOiBHZXQgcmlkIG9mIGFsbCBVU0VfVU5JWEZJTEVOQU1FIGJlbG93ICovCisgICAgLyogU2V0IGlvTmFtZVB0ciwgaXQncyB0aGUgc2FtZSBhcmVhIHdoaWNoIGlzIGFsd2F5cyByZXVzZWQuICovCisgICAgdGhlQ1BCLmRpckluZm8uaW9OYW1lUHRyID0gZGlyZWN0b3J5TmFtZTsKKworICAgIC8qIFRyaWNrIGZvciBmaXJzdCBlbnRyeSwgc2V0IGlvRHJQYXJJRCB0byB0aGUgZmlyc3QgdmFsdWUKKyAgICAgKiB3ZSB3YW50IGZvciBpb0RyRGlySUQqLworICAgIHRoZUNQQi5kaXJJbmZvLmlvRHJQYXJJRCA9IGZpbGUucGFySUQ7CisgICAgdGhlQ1BCLmRpckluZm8uaW9EckRpcklEID0gZmlsZS5wYXJJRDsKKworICAgIGlmICgoVFJVRSkgJiYgKGZpbGUucGFySUQgIT0gZnNSdERpcklEIC8qZnNSdFBhcklEKi8gKSkKKyAgICBkbworICAgIHsKKwl0aGVDUEIuZGlySW5mby5pb0ZEaXJJbmRleCA9IC0xOworICAgICAvKiB0aGVDUEIuZGlySW5mby5pb05hbWVQdHIgICA9IGRpcmVjdG9yeU5hbWU7IEFscmVhZHkgZG9uZSBhYm92ZS4gKi8KKwl0aGVDUEIuZGlySW5mby5pb1ZSZWZOdW0gICA9IGZpbGUudlJlZk51bTsKKyAgICAgLyogdGhlQ1BCLmRpckluZm8uaW9EaXJJRCAgICAgPSBpcnJldmVsYW50IHdoZW4gaW9GRGlySW5kZXggPSAtMSAqLworCXRoZUNQQi5kaXJJbmZvLmlvRHJEaXJJRCAgID0gdGhlQ1BCLmRpckluZm8uaW9EclBhcklEOworCisJLyogQXMgaW9GRGlySW5kZXggPSAtMSwgZ2V0IHRoZSBpbmZvIG9mIGlvRHJEaXJJRCwgKi8KKwkvKiAgKmlvTmFtZVB0clswIFRPIDMxXSB3aWxsIGJlIHVwZGF0ZWQJCSAgICovCisJZXJyb3IgPSBQQkdldENhdEluZm8gKCZ0aGVDUEIsZmFsc2UpOworCisJaWYgKGVycm9yKQorCSAgcmV0dXJuIE5VTEw7CisKKwkvKiBQdXQgdGhlIG5ldyBkaXJlY3RvcnlOYW1lIGluIGZyb250IG9mIHRoZSBjdXJyZW50IGZuYW1lICovCisJU1RSQ1BZKHRlbXBvcmFyeVB0ciwgZmlsZW5hbWVQdHIpOworCVNUUk5DUFkoZmlsZW5hbWVQdHIsICZkaXJlY3RvcnlOYW1lWzFdLCBkaXJlY3RvcnlOYW1lWzBdKTsKKwlmaWxlbmFtZVB0cltkaXJlY3RvcnlOYW1lWzBdXSA9IDA7IC8qIE5VTEwgdGVybWluYXRlIHRoZSBzdHJpbmcgKi8KKwlTVFJDQVQoZmlsZW5hbWVQdHIsICI6Iik7CisJU1RSQ0FUKGZpbGVuYW1lUHRyLCB0ZW1wb3JhcnlQdHIpOworICAgIH0KKyNpZiAxIC8qIGRlZiBVU0VfVU5JWEZJTEVOQU1FICovCisgICAgd2hpbGUgKCh0aGVDUEIuZGlySW5mby5pb0RyUGFySUQgIT0gZnNSdERpcklEKSAvKiAmJiAqLworCSAvKiAgKHRoZUNQQi5kaXJJbmZvLmlvRHJEaXJJRCAhPSBmc1J0RGlySUQpKi8pOworI2Vsc2UKKyAgICB3aGlsZSAodGhlQ1BCLmRpckluZm8uaW9EckRpcklEICE9IGZzUnREaXJJRCk7CisjZW5kaWYKKworICAgIC8qIEdldCB0aGUgaW5mb3JtYXRpb24gYWJvdXQgdGhlIHZvbHVtZSBvbiB3aGljaCB0aGUgZmlsZSByZXNpZGUgKi8KKyAgICB0aGVDUEIuZGlySW5mby5pb0ZEaXJJbmRleCA9IC0xOworIC8qIHRoZUNQQi5kaXJJbmZvLmlvTmFtZVB0ciAgID0gZGlyZWN0b3J5TmFtZTsgQWxyZWFkeSBkb25lIGFib3ZlLiAqLworICAgIHRoZUNQQi5kaXJJbmZvLmlvVlJlZk51bSAgID0gZmlsZS52UmVmTnVtOworIC8qIHRoZUNQQi5kaXJJbmZvLmlvRGlySUQgICAgID0gaXJyZXZlbGFudCB3aGVuIGlvRkRpckluZGV4ID0gLTEgKi8KKyAgICB0aGVDUEIuZGlySW5mby5pb0RyRGlySUQgICA9IHRoZUNQQi5kaXJJbmZvLmlvRHJQYXJJRDsKKworICAgIC8qIEFzIGlvRkRpckluZGV4ID0gLTEsIGdldCB0aGUgaW5mbyBvZiBpb0RyRGlySUQsICovCisgICAgLyoJKmlvTmFtZVB0clswIFRPIDMxXSB3aWxsIGJlIHVwZGF0ZWQJICAgICAgICovCisgICAgZXJyb3IgPSBQQkdldENhdEluZm8gKCZ0aGVDUEIsZmFsc2UpOworCisgICAgaWYgKGVycm9yKQorICAgICAgcmV0dXJuIE5VTEw7CisKKyAgICAvKiBGb3IgTWFjT1MgQ2xhc3NpYyBhbHdheXMgYWRkIHRoZSB2b2x1bWUgbmFtZQkgICAgICovCisgICAgLyogRm9yIE1hY09TIFggYWRkIHRoZSB2b2x1bWUgbmFtZSBwcmVjZWRlZCBieSAiVm9sdW1lcyIgKi8KKyAgICAvKgl3aGVuIHdlIGFyZSBub3QgcmVmZXJpbmcgdG8gdGhlIGJvb3Qgdm9sdW1lCSAgICAgKi8KKyNpZmRlZiBVU0VfVU5JWEZJTEVOQU1FCisgICAgaWYgKGZpbGUudlJlZk51bSAhPSBkZmx0Vm9sX3ZSZWZOdW0pCisjZW5kaWYKKyAgICB7CisJLyogQWRkIHRoZSB2b2x1bWUgbmFtZSAqLworCVNUUkNQWSh0ZW1wb3JhcnlQdHIsIGZpbGVuYW1lUHRyKTsKKwlTVFJOQ1BZKGZpbGVuYW1lUHRyLCAmZGlyZWN0b3J5TmFtZVsxXSwgZGlyZWN0b3J5TmFtZVswXSk7CisJZmlsZW5hbWVQdHJbZGlyZWN0b3J5TmFtZVswXV0gPSAwOyAvKiBOVUxMIHRlcm1pbmF0ZSB0aGUgc3RyaW5nICovCisJU1RSQ0FUKGZpbGVuYW1lUHRyLCAiOiIpOworCVNUUkNBVChmaWxlbmFtZVB0ciwgdGVtcG9yYXJ5UHRyKTsKKworI2lmZGVmIFVTRV9VTklYRklMRU5BTUUKKwlTVFJDUFkodGVtcG9yYXJ5UHRyLCBmaWxlbmFtZVB0cik7CisJZmlsZW5hbWVQdHJbMF0gPSAwOyAvKiBOVUxMIHRlcm1pbmF0ZSB0aGUgc3RyaW5nICovCisJU1RSQ0FUKGZpbGVuYW1lUHRyLCAiVm9sdW1lczoiKTsKKwlTVFJDQVQoZmlsZW5hbWVQdHIsIHRlbXBvcmFyeVB0cik7CisjZW5kaWYKKyAgICB9CisKKyAgICAvKiBBcHBlbmQgZmluYWwgcGF0aCBzZXBhcmF0b3IgaWYgaXQncyBhIGZvbGRlciAqLworICAgIGlmIChmb2xkZXIpCisJU1RSQ0FUIChmbmFtZSwgIjoiKTsKKworICAgIC8qIEFzIHdlIHVzZSBVbml4IEZpbGUgTmFtZSBmb3IgTWFjT1MgWCBjb252ZXJ0IGl0ICovCisjaWZkZWYgVVNFX1VOSVhGSUxFTkFNRQorICAgIC8qIE5lZWQgdG8gaW5zZXJ0IGxlYWRpbmcgLyAqLworICAgIC8qIFRPRE86IGdldCB0aGUgYWJvdmUgY29kZSB0byB1c2UgZGlyZWN0bHkgdGhlIC8gKi8KKyAgICBTVFJDUFkoJnRlbXBvcmFyeVB0clsxXSwgZmlsZW5hbWVQdHIpOworICAgIHRlbXBvcmFyeVB0clswXSA9ICcvJzsKKyAgICBTVFJDUFkoZmlsZW5hbWVQdHIsIHRlbXBvcmFyeVB0cik7CisgICAgeworICAgIGNoYXIJKnA7CisgICAgZm9yIChwID0gZm5hbWU7ICpwOyBwKyspCisJaWYgKCpwID09ICc6JykKKwkgICAgKnAgPSAnLyc7CisgICAgfQorI2VuZGlmCisKKyAgICByZXR1cm4gKHZpbV9zdHJzYXZlIChmbmFtZSkpOworI2VuZGlmCit9CisKKyNpZiBkZWZpbmVkKFVTRV9JTV9DT05UUk9MKSB8fCBkZWZpbmVkKFBST1RPKQorLyoKKyAqIElucHV0IE1ldGhvZCBDb250cm9sIGZ1bmN0aW9ucy4KKyAqLworCisvKgorICogTm90aWZ5IGN1cnNvciBwb3NpdGlvbiB0byBJTS4KKyAqLworICAgIHZvaWQKK2ltX3NldF9wb3NpdGlvbihpbnQgcm93LCBpbnQgY29sKQoreworICAgIC8qIFRPRE86IEltcGxlbWVudCBtZSEgKi8KK30KKworLyoKKyAqIFNldCBJTSBzdGF0dXMgb24gKCJhY3RpdmUiIGlzIFRSVUUpIG9yIG9mZiAoImFjdGl2ZSIgaXMgRkFMU0UpLgorICovCisgICAgdm9pZAoraW1fc2V0X2FjdGl2ZShpbnQgYWN0aXZlKQoreworICAgIEtleVNjcmlwdChhY3RpdmUgPyBzbUtleVN5c1NjcmlwdCA6IHNtS2V5Um9tYW4pOworfQorCisvKgorICogR2V0IElNIHN0YXR1cy4gIFdoZW4gSU0gaXMgb24sIHJldHVybiBub3QgMC4gIEVsc2UgcmV0dXJuIDAuCisgKi8KKyAgICBpbnQKK2ltX2dldF9zdGF0dXMoKQoreworICAgIFNJbnQzMiBzY3JpcHQgPSBHZXRTY3JpcHRNYW5hZ2VyVmFyaWFibGUoc21LZXlTY3JpcHQpOworICAgIHJldHVybiAoc2NyaXB0ICE9IHNtUm9tYW4KKwkgICAgJiYgc2NyaXB0ID09IEdldFNjcmlwdE1hbmFnZXJWYXJpYWJsZShzbVN5c1NjcmlwdCkpID8gMSA6IDA7Cit9CisjZW5kaWYgLyogZGVmaW5lZChVU0VfSU1fQ09OVFJPTCkgfHwgZGVmaW5lZChQUk9UTykgKi8K