Ly8gPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PQovLyBCaXRtYXAgY29udmVyc2lvbiByb3V0aW5lcwovLyBUaHJlc2hvbGRpbmcgYW5kIGhhbGZ0b25pbmcgZnVuY3Rpb25zCi8vIERlc2lnbiBhbmQgaW1wbGVtZW50YXRpb24gYnkKLy8gLSBIZXJ26SBEcm9sb24gKGRyb2xvbkBpbmZvbmllLmZyKQovLyAtIERlbm5pcyBMaW0gKGRsa2pAdXNlcnMuc291cmNlZm9yZ2UubmV0KQovLyAtIFRob21hcyBDaG1pZWxld3NraSAoQ2htaWVsZXdza2kuVGhvbWFzQG9jZS5kZSkKLy8KLy8gTWFpbiByZWZlcmVuY2UgOiBVbGljaG5leSwgUi4sIERpZ2l0YWwgSGFsZnRvbmluZywgVGhlIE1JVCBQcmVzcywgQ2FtYnJpZGdlLCBNQSwgMTk4NwovLwovLyBUaGlzIGZpbGUgaXMgcGFydCBvZiBGcmVlSW1hZ2UgMwovLwovLyBDT1ZFUkVEIENPREUgSVMgUFJPVklERUQgVU5ERVIgVEhJUyBMSUNFTlNFIE9OIEFOICJBUyBJUyIgQkFTSVMsIFdJVEhPVVQgV0FSUkFOVFkKLy8gT0YgQU5ZIEtJTkQsIEVJVEhFUiBFWFBSRVNTRUQgT1IgSU1QTElFRCwgSU5DTFVESU5HLCBXSVRIT1VUIExJTUlUQVRJT04sIFdBUlJBTlRJRVMKLy8gVEhBVCBUSEUgQ09WRVJFRCBDT0RFIElTIEZSRUUgT0YgREVGRUNUUywgTUVSQ0hBTlRBQkxFLCBGSVQgRk9SIEEgUEFSVElDVUxBUiBQVVJQT1NFCi8vIE9SIE5PTi1JTkZSSU5HSU5HLiBUSEUgRU5USVJFIFJJU0sgQVMgVE8gVEhFIFFVQUxJVFkgQU5EIFBFUkZPUk1BTkNFIE9GIFRIRSBDT1ZFUkVECi8vIENPREUgSVMgV0lUSCBZT1UuIFNIT1VMRCBBTlkgQ09WRVJFRCBDT0RFIFBST1ZFIERFRkVDVElWRSBJTiBBTlkgUkVTUEVDVCwgWU9VIChOT1QKLy8gVEhFIElOSVRJQUwgREVWRUxPUEVSIE9SIEFOWSBPVEhFUiBDT05UUklCVVRPUikgQVNTVU1FIFRIRSBDT1NUIE9GIEFOWSBORUNFU1NBUlkKLy8gU0VSVklDSU5HLCBSRVBBSVIgT1IgQ09SUkVDVElPTi4gVEhJUyBESVNDTEFJTUVSIE9GIFdBUlJBTlRZIENPTlNUSVRVVEVTIEFOIEVTU0VOVElBTAovLyBQQVJUIE9GIFRISVMgTElDRU5TRS4gTk8gVVNFIE9GIEFOWSBDT1ZFUkVEIENPREUgSVMgQVVUSE9SSVpFRCBIRVJFVU5ERVIgRVhDRVBUIFVOREVSCi8vIFRISVMgRElTQ0xBSU1FUi4KLy8KLy8gVXNlIGF0IHlvdXIgb3duIHJpc2shCi8vID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0KCiNpbmNsdWRlICJGcmVlSW1hZ2UuaCIKI2luY2x1ZGUgIlV0aWxpdGllcy5oIgoKc3RhdGljIGNvbnN0IGludCBXSElURSA9IDI1NTsKc3RhdGljIGNvbnN0IGludCBCTEFDSyA9IDA7CgovLyBGbG95ZCAmIFN0ZWluYmVyZyBlcnJvciBkaWZmdXNpb24gZGl0aGVyaW5nCi8vIFRoaXMgYWxnb3JpdGhtIHVzZSB0aGUgZm9sbG93aW5nIGZpbHRlcgovLyAgICAgICAgICAqICAgNwovLyAgICAgIDMgICA1ICAgMSAgICAgKDEvMTYpCnN0YXRpYyBGSUJJVE1BUCogRmxveWRTdGVpbmJlcmcoRklCSVRNQVAgKmRpYikgewoKI2RlZmluZSBSQU5EKFJOKSAoKChzZWVkID0gMTEwMzUxNTI0NSAqIHNlZWQgKyAxMjM0NSkgPj4gMTIpICUgKFJOKSkKI2RlZmluZSBJTklURVJSKFgsIFkpICgoKGludCkgWCkgLSAoKChpbnQpIFkpID8gV0hJVEUgOiBCTEFDSykgKyAoKFdISVRFLzIpLSgoaW50KVgpKSAvIDIpCgoJaW50IHNlZWQgPSAwOwoJaW50IHgsIHksIHAsIHBpeGVsLCB0aHJlc2hvbGQsIGVycm9yOwoJaW50IHdpZHRoLCBoZWlnaHQsIHBpdGNoOwoJQllURSAqYml0cywgKm5ld19iaXRzOwoJRklCSVRNQVAgKm5ld19kaWIgPSBOVUxMOwoKCS8vIGFsbG9jYXRlIGEgOC1iaXQgRElCCgl3aWR0aCA9IEZyZWVJbWFnZV9HZXRXaWR0aChkaWIpOwoJaGVpZ2h0ID0gRnJlZUltYWdlX0dldEhlaWdodChkaWIpOwoJcGl0Y2ggPSBGcmVlSW1hZ2VfR2V0UGl0Y2goZGliKTsKCW5ld19kaWIgPSBGcmVlSW1hZ2VfQWxsb2NhdGUod2lkdGgsIGhlaWdodCwgOCk7CglpZihOVUxMID09IG5ld19kaWIpIHJldHVybiBOVUxMOwoKCS8vIGFsbG9jYXRlIHNwYWNlIGZvciBlcnJvciBhcnJheXMKCWludCAqbGVyciA9IChpbnQqKW1hbGxvYyAod2lkdGggKiBzaXplb2YoaW50KSk7CglpbnQgKmNlcnIgPSAoaW50KiltYWxsb2MgKHdpZHRoICogc2l6ZW9mKGludCkpOwoJbWVtc2V0KGxlcnIsIDAsIHdpZHRoICogc2l6ZW9mKGludCkpOwoJbWVtc2V0KGNlcnIsIDAsIHdpZHRoICogc2l6ZW9mKGludCkpOwoKCS8vIGxlZnQgYm9yZGVyCgllcnJvciA9IDA7Cglmb3IoeSA9IDA7IHkgPCBoZWlnaHQ7IHkrKykgewoJCWJpdHMgPSBGcmVlSW1hZ2VfR2V0U2NhbkxpbmUoZGliLCB5KTsKCQluZXdfYml0cyA9IEZyZWVJbWFnZV9HZXRTY2FuTGluZShuZXdfZGliLCB5KTsKCgkJdGhyZXNob2xkID0gKFdISVRFIC8gMiArIFJBTkQoMTI5KSAtIDY0KTsKCQlwaXhlbCA9IGJpdHNbMF0gKyBlcnJvcjsKCQlwID0gKHBpeGVsID4gdGhyZXNob2xkKSA/IFdISVRFIDogQkxBQ0s7CgkJZXJyb3IgPSBwaXhlbCAtIHA7CgkJbmV3X2JpdHNbMF0gPSAoQllURSlwOwoJfQoJLy8gcmlnaHQgYm9yZGVyCgllcnJvciA9IDA7Cglmb3IoeSA9IDA7IHkgPCBoZWlnaHQ7IHkrKykgewoJCWJpdHMgPSBGcmVlSW1hZ2VfR2V0U2NhbkxpbmUoZGliLCB5KTsKCQluZXdfYml0cyA9IEZyZWVJbWFnZV9HZXRTY2FuTGluZShuZXdfZGliLCB5KTsKCgkJdGhyZXNob2xkID0gKFdISVRFIC8gMiArIFJBTkQoMTI5KSAtIDY0KTsKCQlwaXhlbCA9IGJpdHNbd2lkdGgtMV0gKyBlcnJvcjsKCQlwID0gKHBpeGVsID4gdGhyZXNob2xkKSA/IFdISVRFIDogQkxBQ0s7CgkJZXJyb3IgPSBwaXhlbCAtIHA7CgkJbmV3X2JpdHNbd2lkdGgtMV0gPSAoQllURSlwOwoJfQoJLy8gdG9wIGJvcmRlcgoJYml0cyA9IEZyZWVJbWFnZV9HZXRCaXRzKGRpYik7CgluZXdfYml0cyA9IEZyZWVJbWFnZV9HZXRCaXRzKG5ld19kaWIpOwoJZXJyb3IgPSAwOwoJZm9yKHggPSAwOyB4IDwgd2lkdGg7IHgrKykgewoJCXRocmVzaG9sZCA9IChXSElURSAvIDIgKyBSQU5EKDEyOSkgLSA2NCk7CgkJcGl4ZWwgPSBiaXRzW3hdICsgZXJyb3I7CgkJcCA9IChwaXhlbCA+IHRocmVzaG9sZCkgPyBXSElURSA6IEJMQUNLOwoJCWVycm9yID0gcGl4ZWwgLSBwOwoJCW5ld19iaXRzW3hdID0gKEJZVEUpcDsKCQlsZXJyW3hdID0gSU5JVEVSUihiaXRzW3hdLCBwKTsKCX0KCgkvLyBpbnRlcmlvciBiaXRzCglmb3IoeSA9IDE7IHkgPCBoZWlnaHQ7IHkrKykgewoJCS8vIHNjYW4gbGVmdCB0byByaWdodAoJCWJpdHMgPSBGcmVlSW1hZ2VfR2V0U2NhbkxpbmUoZGliLCB5KTsKCQluZXdfYml0cyA9IEZyZWVJbWFnZV9HZXRTY2FuTGluZShuZXdfZGliLCB5KTsKCgkgICAgY2VyclswXSA9IElOSVRFUlIoYml0c1swXSwgbmV3X2JpdHNbMF0pOwoJCWZvcih4ID0gMTsgeCA8IHdpZHRoIC0gMTsgeCsrKSB7CgkJCWVycm9yID0gKGxlcnJbeC0xXSArIDUgKiBsZXJyW3hdICsgMyAqIGxlcnJbeCsxXSArIDcgKiBjZXJyW3gtMV0pIC8gMTY7CgkJCXBpeGVsID0gYml0c1t4XSArIGVycm9yOwoJCQlpZihwaXhlbCA+IChXSElURSAvIDIpKSB7CQkKCQkJCW5ld19iaXRzW3hdID0gV0hJVEU7CgkJCQljZXJyW3hdID0gcGl4ZWwgLSBXSElURTsgCgkJCX0gZWxzZSB7CgkJCQluZXdfYml0c1t4XSA9IEJMQUNLOwoJCQkJY2Vyclt4XSA9IHBpeGVsIC0gQkxBQ0s7IAoJCQl9CgkJfQoJCS8vIHNldCBlcnJvcnMgZm9yIGVuZHMgb2YgdGhlIHJvdwoJCWNlcnJbMF0gPSBJTklURVJSIChiaXRzWzBdLCBuZXdfYml0c1swXSk7CgkJY2Vyclt3aWR0aCAtIDFdID0gSU5JVEVSUiAoYml0c1t3aWR0aCAtIDFdLCBuZXdfYml0c1t3aWR0aCAtIDFdKTsKCgkJLy8gc3dhcCBlcnJvciBidWZmZXJzCgkJaW50ICp0ZXJyID0gbGVycjsgbGVyciA9IGNlcnI7IGNlcnIgPSB0ZXJyOwoJfQoKCWZyZWUobGVycik7CglmcmVlKGNlcnIpOwoKCXJldHVybiBuZXdfZGliOwp9CgovLyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ci8vIEJheWVyIG9yZGVyZWQgZGlzcGVyc2VkIGRvdCBkaXRoZXJpbmcKLy8KCi8vIEZ1bmN0aW9uIHRha2VuIGZyb20gIk9yZGVyZWQgRGl0aGVyaW5nLCBTdGVwaGVuIEhhd2xleSwgR3JhcGhpY3MgR2VtcywgQWNhZGVtaWMgUHJlc3MsIDE5OTAiCi8vIFRoaXMgZnVuY3Rpb24gaXMgdXNlZCB0byBnZW5lcmF0ZSBhIEJheWVyIGRpdGhlcmluZyBtYXRyaWNlIHdob3NlIGRpbWVuc2lvbiBhcmUgMl5zaXplIGJ5IDJec2l6ZQovLwpzdGF0aWMgaW50IGRpdGhlcnZhbHVlKGludCB4LCBpbnQgeSwgaW50IHNpemUpIHsKCWludCBkID0gMDsKCS8qCgkgKiBjYWxjdWxhdGUgdGhlIGRpdGhlciB2YWx1ZSBhdCBhIHBhcnRpY3VsYXIKCSAqICh4LCB5KSBvdmVyIHRoZSBzaXplIG9mIHRoZSBtYXRyaXguCgkgKi8KCXdoaWxlIChzaXplLS0+MCkJewoJCS8qIFRoaW5rIG9mIGQgYXMgdGhlIGRlbnNpdHkuIEF0IGV2ZXJ5IGl0ZXJhdGlvbiwKCQkgKiBkIGlzIHNoaWZ0ZWQgbGVmdCBvbmUgYW5kIGEgbmV3IGJpdCBpcyBwdXQgaW4gdGhlCgkJICogbG93IGJpdCBiYXNlZCBvbiB4IGFuZCB5LiBJZiB4IGlzIG9kZCBhbmQgeSBpcyBldmVuLAoJCSAqIG9yIHggaXMgZXZlbiBhbmQgeSBpcyBvZGQsIGEgYml0IGlzIHB1dCBpbi4gVGhpcwoJCSAqIGdlbmVyYXRlcyB0aGUgY2hlY2tlcmJvYXJkIHNlZW4gaW4gZGl0aGVyaW5nLgoJCSAqIFRoaXMgcXVhbnRpdHkgaXMgc2hpZnRlZCBsZWZ0IGFnYWluIGFuZCB0aGUgbG93IGJpdCBvZgoJCSAqIHkgaXMgYWRkZWQgaW4uCgkJICogVGhpcyB3aG9sZSB0aGluZyBpbnRlcmxlYXZlcyBhIGNoZWNrZXJib2FyZCBiaXQgcGF0dGVybgoJCSAqIGFuZCB5J3MgYml0cywgd2hpY2ggaXMgdGhlIHZhbHVlIHlvdSB3YW50LgoJCSAqLwoJCWQgPSAoZCA8PDEgfCAoeCYxIF4geSYxKSk8PDEgfCB5JjE7CgkJeCA+Pj0gMTsKCQl5ID4+PSAxOwoJfQoJcmV0dXJuIGQ7Cn0KCi8vIE9yZGVyZWQgZGl0aGVyaW5nIHdpdGggYSBCYXllciBtYXRyaXggb2Ygc2l6ZSAyXm9yZGVyIGJ5IDJeb3JkZXIKLy8Kc3RhdGljIEZJQklUTUFQKiBPcmRlcmVkRGlzcGVyc2VkRG90KEZJQklUTUFQICpkaWIsIGludCBvcmRlcikgewoJaW50IHgsIHk7CglpbnQgd2lkdGgsIGhlaWdodDsKCUJZVEUgKmJpdHMsICpuZXdfYml0czsKCUZJQklUTUFQICpuZXdfZGliID0gTlVMTDsKCgkvLyBhbGxvY2F0ZSBhIDgtYml0IERJQgoJd2lkdGggPSBGcmVlSW1hZ2VfR2V0V2lkdGgoZGliKTsKCWhlaWdodCA9IEZyZWVJbWFnZV9HZXRIZWlnaHQoZGliKTsKCW5ld19kaWIgPSBGcmVlSW1hZ2VfQWxsb2NhdGUod2lkdGgsIGhlaWdodCwgOCk7CglpZihOVUxMID09IG5ld19kaWIpIHJldHVybiBOVUxMOwoKCS8vIGJ1aWxkIHRoZSBkaXRoZXJpbmcgbWF0cml4CglpbnQgbCA9ICgxIDw8IG9yZGVyKTsJLy8gc3F1YXJlIG9mIGRpdGhlciBtYXRyaXggb3JkZXI7IHRoZSBkaW1lbnNpb25zIG9mIHRoZSBtYXRyaXgKCUJZVEUgKm1hdHJpeCA9IChCWVRFKiltYWxsb2MobCpsICogc2l6ZW9mKEJZVEUpKTsKCWZvcihpbnQgaSA9IDA7IGkgPCBsKmw7IGkrKykgewoJCS8vIGFjY29yZGluZyB0byAiUHVyZHVlIFVuaXZlcnNpdHk6IERpZ2l0YWwgSW1hZ2UgUHJvY2Vzc2luZyBMYWJvcmF0b3J5OiBJbWFnZSBIYWxmdG9uaW5nLCBBcHJpbCAzMHRoLCAyMDA2CgkJbWF0cml4W2ldID0gKEJZVEUpKCAyNTUgKiAoKChkb3VibGUpZGl0aGVydmFsdWUoaSAvIGwsIGkgJSBsLCBvcmRlcikgKyAwLjUpIC8gKGwqbCkpICk7Cgl9CgoJLy8gcGVyZm9ybSB0aGUgZGl0aGVyaW5nCglmb3IoeSA9IDA7IHkgPCBoZWlnaHQ7IHkrKykgewoJCS8vIHNjYW4gbGVmdCB0byByaWdodAoJCWJpdHMgPSBGcmVlSW1hZ2VfR2V0U2NhbkxpbmUoZGliLCB5KTsKCQluZXdfYml0cyA9IEZyZWVJbWFnZV9HZXRTY2FuTGluZShuZXdfZGliLCB5KTsKCQlmb3IoeCA9IDA7IHggPCB3aWR0aDsgeCsrKSB7CgkJCWlmKGJpdHNbeF0gPiBtYXRyaXhbKHggJSBsKSArIGwgKiAoeSAlIGwpXSkgewoJCQkJbmV3X2JpdHNbeF0gPSBXSElURTsKCQkJfSBlbHNlIHsKCQkJCW5ld19iaXRzW3hdID0gQkxBQ0s7CgkJCX0KCQl9Cgl9CgoJZnJlZShtYXRyaXgpOwoKCXJldHVybiBuZXdfZGliOwp9CgovLyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ci8vIE9yZGVyZWQgY2x1c3RlcmVkIGRvdCBkaXRoZXJpbmcKLy8KCi8vIE5CIDogVGhlIHByZWRlZmluZWQgZGl0aGVyIG1hdHJpY2VzIGFyZSB0aGUgc2FtZSBhcyBtYXRyaWNlcyB1c2VkIGluIAovLyB0aGUgTmV0cGJtIHBhY2thZ2UgKGh0dHA6Ly9uZXRwYm0uc291cmNlZm9yZ2UubmV0KSBhbmQgYXJlIGRlZmluZWQgaW4gVWxpY2huZXkncyBib29rLgovLyBTZWUgYWxzbyA6IFRoZSBuZXdzcHJpbnQgd2ViIHNpdGUgYXQgaHR0cDovL3d3dy5jbC5jYW0uYWMudWsvfmFuZDEwMDAvbmV3c3ByaW50LwovLyBmb3IgbW9yZSB0ZWNobmljYWwgaW5mbyBvbiB0aGlzIGRpdGhlcmluZyB0ZWNobmlxdWUKLy8Kc3RhdGljIEZJQklUTUFQKiBPcmRlcmVkQ2x1c3RlcmVkRG90KEZJQklUTUFQICpkaWIsIGludCBvcmRlcikgewoJLy8gT3JkZXItMyBjbHVzdGVyZWQgZGl0aGVyaW5nIG1hdHJpeC4KCWludCBjbHVzdGVyM1tdID0gewoJICA5LDExLDEwLCA4LCA2LCA3LAoJICAxMiwxNywxNiwgNSwgMCwgMSwKCSAgMTMsMTQsMTUsIDQsIDMsIDIsCgkgIDgsIDYsIDcsIDksMTEsMTAsCgkgIDUsIDAsIDEsMTIsMTcsMTYsCgkgIDQsIDMsIDIsMTMsMTQsMTUKCX07CgoJLy8gT3JkZXItNCBjbHVzdGVyZWQgZGl0aGVyaW5nIG1hdHJpeC4gCglpbnQgY2x1c3RlcjRbXSA9IHsKCSAgMTgsMjAsMTksMTYsMTMsMTEsMTIsMTUsCgkgIDI3LDI4LDI5LDIyLCA0LCAzLCAyLCA5LAoJICAyNiwzMSwzMCwyMSwgNSwgMCwgMSwxMCwKCSAgMjMsMjUsMjQsMTcsIDgsIDYsIDcsMTQsCgkgIDEzLDExLDEyLDE1LDE4LDIwLDE5LDE2LAoJICA0LCAzLCAyLCA5LDI3LDI4LDI5LDIyLAoJICA1LCAwLCAxLDEwLDI2LDMxLDMwLDIxLAoJICA4LCA2LCA3LDE0LDIzLDI1LDI0LDE3Cgl9OwoKCS8vIE9yZGVyLTggY2x1c3RlcmVkIGRpdGhlcmluZyBtYXRyaXguIAoJaW50IGNsdXN0ZXI4W10gPSB7CgkgICA2NCwgNjksIDc3LCA4NywgODYsIDc2LCA2OCwgNjcsIDYzLCA1OCwgNTAsIDQwLCA0MSwgNTEsIDU5LCA2MCwKCSAgIDcwLCA5NCwxMDAsMTA5LDEwOCwgOTksIDkzLCA3NSwgNTcsIDMzLCAyNywgMTgsIDE5LCAyOCwgMzQsIDUyLAoJICAgNzgsMTAxLDExNCwxMTYsMTE1LDExMiwgOTgsIDgzLCA0OSwgMjYsIDEzLCAxMSwgMTIsIDE1LCAyOSwgNDQsCgkgICA4OCwxMTAsMTIzLDEyNCwxMjUsMTE4LDEwNywgODUsIDM5LCAxNywgIDQsICAzLCAgMiwgIDksIDIwLCA0MiwKCSAgIDg5LDExMSwxMjIsMTI3LDEyNiwxMTcsMTA2LCA4NCwgMzgsIDE2LCAgNSwgIDAsICAxLCAxMCwgMjEsIDQzLAoJICAgNzksMTAyLDExOSwxMjEsMTIwLDExMywgOTcsIDgyLCA0OCwgMjUsICA4LCAgNiwgIDcsIDE0LCAzMCwgNDUsCgkgICA3MSwgOTUsMTAzLDEwNCwxMDUsIDk2LCA5MiwgNzQsIDU2LCAzMiwgMjQsIDIzLCAyMiwgMzEsIDM1LCA1MywKCSAgIDY1LCA3MiwgODAsIDkwLCA5MSwgODEsIDczLCA2NiwgNjIsIDU1LCA0NywgMzcsIDM2LCA0NiwgNTQsIDYxLAoJICAgNjMsIDU4LCA1MCwgNDAsIDQxLCA1MSwgNTksIDYwLCA2NCwgNjksIDc3LCA4NywgODYsIDc2LCA2OCwgNjcsCgkgICA1NywgMzMsIDI3LCAxOCwgMTksIDI4LCAzNCwgNTIsIDcwLCA5NCwxMDAsMTA5LDEwOCwgOTksIDkzLCA3NSwKCSAgIDQ5LCAyNiwgMTMsIDExLCAxMiwgMTUsIDI5LCA0NCwgNzgsMTAxLDExNCwxMTYsMTE1LDExMiwgOTgsIDgzLAoJICAgMzksIDE3LCAgNCwgIDMsICAyLCAgOSwgMjAsIDQyLCA4OCwxMTAsMTIzLDEyNCwxMjUsMTE4LDEwNywgODUsCgkgICAzOCwgMTYsICA1LCAgMCwgIDEsIDEwLCAyMSwgNDMsIDg5LDExMSwxMjIsMTI3LDEyNiwxMTcsMTA2LCA4NCwKCSAgIDQ4LCAyNSwgIDgsICA2LCAgNywgMTQsIDMwLCA0NSwgNzksMTAyLDExOSwxMjEsMTIwLDExMywgOTcsIDgyLAoJICAgNTYsIDMyLCAyNCwgMjMsIDIyLCAzMSwgMzUsIDUzLCA3MSwgOTUsMTAzLDEwNCwxMDUsIDk2LCA5MiwgNzQsCgkgICA2MiwgNTUsIDQ3LCAzNywgMzYsIDQ2LCA1NCwgNjEsIDY1LCA3MiwgODAsIDkwLCA5MSwgODEsIDczLCA2NgoJfTsKCglpbnQgeCwgeSwgcGl4ZWw7CglpbnQgd2lkdGgsIGhlaWdodDsKCUJZVEUgKmJpdHMsICpuZXdfYml0czsKCUZJQklUTUFQICpuZXdfZGliID0gTlVMTDsKCgkvLyBhbGxvY2F0ZSBhIDgtYml0IERJQgoJd2lkdGggPSBGcmVlSW1hZ2VfR2V0V2lkdGgoZGliKTsKCWhlaWdodCA9IEZyZWVJbWFnZV9HZXRIZWlnaHQoZGliKTsKCW5ld19kaWIgPSBGcmVlSW1hZ2VfQWxsb2NhdGUod2lkdGgsIGhlaWdodCwgOCk7CglpZihOVUxMID09IG5ld19kaWIpIHJldHVybiBOVUxMOwoKCS8vIHNlbGVjdCB0aGUgZGl0aGVyaW5nIG1hdHJpeAoJaW50ICptYXRyaXggPSBOVUxMOwoJc3dpdGNoKG9yZGVyKSB7CgkJY2FzZSAzOgoJCQltYXRyaXggPSAmY2x1c3RlcjNbMF07CgkJCWJyZWFrOwoJCWNhc2UgNDoKCQkJbWF0cml4ID0gJmNsdXN0ZXI0WzBdOwoJCQlicmVhazsKCQljYXNlIDg6CgkJCW1hdHJpeCA9ICZjbHVzdGVyOFswXTsKCQkJYnJlYWs7CgkJZGVmYXVsdDoKCQkJcmV0dXJuIE5VTEw7Cgl9CgoJLy8gc2NhbGUgdGhlIGRpdGhlcmluZyBtYXRyaXgKCWludCBsID0gMiAqIG9yZGVyOwoJaW50IHNjYWxlID0gMjU2IC8gKGwgKiBvcmRlcik7Cglmb3IoeSA9IDA7IHkgPCBsOyB5KyspIHsKCQlmb3IoeCA9IDA7IHggPCBsOyB4KyspIHsKCQkJbWF0cml4W3kqbCArIHhdICo9IHNjYWxlOwoJCX0KCX0KCgkvLyBwZXJmb3JtIHRoZSBkaXRoZXJpbmcKCWZvcih5ID0gMDsgeSA8IGhlaWdodDsgeSsrKSB7CgkJLy8gc2NhbiBsZWZ0IHRvIHJpZ2h0CgkJYml0cyA9IEZyZWVJbWFnZV9HZXRTY2FuTGluZShkaWIsIHkpOwoJCW5ld19iaXRzID0gRnJlZUltYWdlX0dldFNjYW5MaW5lKG5ld19kaWIsIHkpOwoJCWZvcih4ID0gMDsgeCA8IHdpZHRoOyB4KyspIHsKCQkJcGl4ZWwgPSBiaXRzW3hdOwoJCQlpZihwaXhlbCA+PSBtYXRyaXhbKHkgJSBsKSArIGwgKiAoeCAlIGwpXSkgewoJCQkJbmV3X2JpdHNbeF0gPSBXSElURTsKCQkJfSBlbHNlIHsKCQkJCW5ld19iaXRzW3hdID0gQkxBQ0s7CgkJCX0KCQl9Cgl9CgoJcmV0dXJuIG5ld19kaWI7Cn0KCgovLyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ci8vIEhhbGZ0b25pbmcgZnVuY3Rpb24KLy8KRklCSVRNQVAgKiBETExfQ0FMTENPTlYKRnJlZUltYWdlX0RpdGhlcihGSUJJVE1BUCAqZGliLCBGUkVFX0lNQUdFX0RJVEhFUiBhbGdvcml0aG0pIHsKCUZJQklUTUFQICppbnB1dCA9IE5VTEwsICpkaWI4ID0gTlVMTDsKCglpZighRnJlZUltYWdlX0hhc1BpeGVscyhkaWIpKSByZXR1cm4gTlVMTDsKCgljb25zdCB1bnNpZ25lZCBicHAgPSBGcmVlSW1hZ2VfR2V0QlBQKGRpYik7CgoJaWYoYnBwID09IDEpIHsKCQkvLyBKdXN0IGNsb25lIHRoZSBkaWIgYW5kIGFkanVzdCB0aGUgcGFsZXR0ZSBpZiBuZWVkZWQKCQlGSUJJVE1BUCAqbmV3X2RpYiA9IEZyZWVJbWFnZV9DbG9uZShkaWIpOwoJCWlmKE5VTEwgPT0gbmV3X2RpYikgcmV0dXJuIE5VTEw7CgkJaWYoRnJlZUltYWdlX0dldENvbG9yVHlwZShuZXdfZGliKSA9PSBGSUNfUEFMRVRURSkgewoJCQkvLyBCdWlsZCBhIG1vbm9jaHJvbWUgcGFsZXR0ZQoJCQlSR0JRVUFEICpwYWwgPSBGcmVlSW1hZ2VfR2V0UGFsZXR0ZShuZXdfZGliKTsKCQkJcGFsWzBdLnJnYlJlZCA9IHBhbFswXS5yZ2JHcmVlbiA9IHBhbFswXS5yZ2JCbHVlID0gMDsKCQkJcGFsWzFdLnJnYlJlZCA9IHBhbFsxXS5yZ2JHcmVlbiA9IHBhbFsxXS5yZ2JCbHVlID0gMjU1OwoJCX0KCQlyZXR1cm4gbmV3X2RpYjsKCX0KCgkvLyBDb252ZXJ0IHRoZSBpbnB1dCBkaWIgdG8gYSA4LWJpdCBncmV5c2NhbGUgZGliCgkvLwoJc3dpdGNoKGJwcCkgewoJCWNhc2UgODoKCQkJaWYoRnJlZUltYWdlX0dldENvbG9yVHlwZShkaWIpID09IEZJQ19NSU5JU0JMQUNLKSB7CgkJCQlpbnB1dCA9IGRpYjsKCQkJfSBlbHNlIHsKCQkJCWlucHV0ID0gRnJlZUltYWdlX0NvbnZlcnRUb0dyZXlzY2FsZShkaWIpOwoJCQl9IAoJCQlicmVhazsKCQljYXNlIDQ6CgkJY2FzZSAxNjoKCQljYXNlIDI0OgoJCWNhc2UgMzI6CgkJCWlucHV0ID0gRnJlZUltYWdlX0NvbnZlcnRUb0dyZXlzY2FsZShkaWIpOwoJCQlicmVhazsJCQkKCX0KCWlmKE5VTEwgPT0gaW5wdXQpIHJldHVybiBOVUxMOwoKCS8vIEFwcGx5IHRoZSBkaXRoZXJpbmcgYWxnb3JpdGhtCglzd2l0Y2goYWxnb3JpdGhtKSB7CgkJY2FzZSBGSURfRlM6CgkJCWRpYjggPSBGbG95ZFN0ZWluYmVyZyhpbnB1dCk7CgkJCWJyZWFrOwoJCWNhc2UgRklEX0JBWUVSNHg0OgoJCQlkaWI4ID0gT3JkZXJlZERpc3BlcnNlZERvdChpbnB1dCwgMik7CgkJCWJyZWFrOwoJCWNhc2UgRklEX0JBWUVSOHg4OgoJCQlkaWI4ID0gT3JkZXJlZERpc3BlcnNlZERvdChpbnB1dCwgMyk7CgkJCWJyZWFrOwoJCWNhc2UgRklEX0JBWUVSMTZ4MTY6CgkJCWRpYjggPSBPcmRlcmVkRGlzcGVyc2VkRG90KGlucHV0LCA0KTsKCQkJYnJlYWs7CgkJY2FzZSBGSURfQ0xVU1RFUjZ4NjoKCQkJZGliOCA9IE9yZGVyZWRDbHVzdGVyZWREb3QoaW5wdXQsIDMpOwoJCQlicmVhazsKCQljYXNlIEZJRF9DTFVTVEVSOHg4OgoJCQlkaWI4ID0gT3JkZXJlZENsdXN0ZXJlZERvdChpbnB1dCwgNCk7CgkJCWJyZWFrOwoJCWNhc2UgRklEX0NMVVNURVIxNngxNjoKCQkJZGliOCA9IE9yZGVyZWRDbHVzdGVyZWREb3QoaW5wdXQsIDgpOwoJCQlicmVhazsKCX0KCWlmKGlucHV0ICE9IGRpYikgewoJCUZyZWVJbWFnZV9VbmxvYWQoaW5wdXQpOwoJfQoKCS8vIEJ1aWxkIGEgZ3JleXNjYWxlIHBhbGV0dGUgKG5lZWRlZCBieSB0aHJlc2hvbGQpCglSR0JRVUFEICpncmV5X3BhbCA9IEZyZWVJbWFnZV9HZXRQYWxldHRlKGRpYjgpOwoJZm9yKGludCBpID0gMDsgaSA8IDI1NjsgaSsrKSB7CgkJZ3JleV9wYWxbaV0ucmdiUmVkCT0gKEJZVEUpaTsKCQlncmV5X3BhbFtpXS5yZ2JHcmVlbiA9IChCWVRFKWk7CgkJZ3JleV9wYWxbaV0ucmdiQmx1ZQk9IChCWVRFKWk7Cgl9CgoJLy8gQ29udmVydCB0byAxLWJpdAoJRklCSVRNQVAgKm5ld19kaWIgPSBGcmVlSW1hZ2VfVGhyZXNob2xkKGRpYjgsIDEyOCk7CglGcmVlSW1hZ2VfVW5sb2FkKGRpYjgpOwoKCS8vIGNvcHkgbWV0YWRhdGEgZnJvbSBzcmMgdG8gZHN0CglGcmVlSW1hZ2VfQ2xvbmVNZXRhZGF0YShuZXdfZGliLCBkaWIpOwoKCXJldHVybiBuZXdfZGliOwp9CgovLyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ci8vIFRocmVzaG9sZGluZyBmdW5jdGlvbgovLwpGSUJJVE1BUCAqIERMTF9DQUxMQ09OVgpGcmVlSW1hZ2VfVGhyZXNob2xkKEZJQklUTUFQICpkaWIsIEJZVEUgVCkgewoJRklCSVRNQVAgKmRpYjggPSBOVUxMOwoKCWlmKCFGcmVlSW1hZ2VfSGFzUGl4ZWxzKGRpYikpIHJldHVybiBOVUxMOwoKCWNvbnN0IHVuc2lnbmVkIGJwcCA9IEZyZWVJbWFnZV9HZXRCUFAoZGliKTsKCglpZihicHAgPT0gMSkgewoJCS8vIEp1c3QgY2xvbmUgdGhlIGRpYiBhbmQgYWRqdXN0IHRoZSBwYWxldHRlIGlmIG5lZWRlZAoJCUZJQklUTUFQICpuZXdfZGliID0gRnJlZUltYWdlX0Nsb25lKGRpYik7CgkJaWYoTlVMTCA9PSBuZXdfZGliKSByZXR1cm4gTlVMTDsKCQlpZihGcmVlSW1hZ2VfR2V0Q29sb3JUeXBlKG5ld19kaWIpID09IEZJQ19QQUxFVFRFKSB7CgkJCS8vIEJ1aWxkIGEgbW9ub2Nocm9tZSBwYWxldHRlCgkJCVJHQlFVQUQgKnBhbCA9IEZyZWVJbWFnZV9HZXRQYWxldHRlKG5ld19kaWIpOwoJCQlwYWxbMF0ucmdiUmVkID0gcGFsWzBdLnJnYkdyZWVuID0gcGFsWzBdLnJnYkJsdWUgPSAwOwoJCQlwYWxbMV0ucmdiUmVkID0gcGFsWzFdLnJnYkdyZWVuID0gcGFsWzFdLnJnYkJsdWUgPSAyNTU7CgkJfQoJCXJldHVybiBuZXdfZGliOwoJfQoKCS8vIENvbnZlcnQgdGhlIGlucHV0IGRpYiB0byBhIDgtYml0IGdyZXlzY2FsZSBkaWIKCS8vCglzd2l0Y2goYnBwKSB7CgkJY2FzZSA4OgoJCQlpZihGcmVlSW1hZ2VfR2V0Q29sb3JUeXBlKGRpYikgPT0gRklDX01JTklTQkxBQ0spIHsKCQkJCWRpYjggPSBkaWI7CgkJCX0gZWxzZSB7CgkJCQlkaWI4ID0gRnJlZUltYWdlX0NvbnZlcnRUb0dyZXlzY2FsZShkaWIpOwoJCQl9IAoJCQlicmVhazsKCQljYXNlIDQ6CgkJY2FzZSAxNjoKCQljYXNlIDI0OgoJCWNhc2UgMzI6CgkJCWRpYjggPSBGcmVlSW1hZ2VfQ29udmVydFRvR3JleXNjYWxlKGRpYik7CgkJCWJyZWFrOwkJCQoJfQoJaWYoTlVMTCA9PSBkaWI4KSByZXR1cm4gTlVMTDsKCgkvLyBBbGxvY2F0ZSBhIG5ldyAxLWJpdCBESUIKCWludCB3aWR0aCA9IEZyZWVJbWFnZV9HZXRXaWR0aChkaWIpOwoJaW50IGhlaWdodCA9IEZyZWVJbWFnZV9HZXRIZWlnaHQoZGliKTsKCUZJQklUTUFQICpuZXdfZGliID0gRnJlZUltYWdlX0FsbG9jYXRlKHdpZHRoLCBoZWlnaHQsIDEpOwoJaWYoTlVMTCA9PSBuZXdfZGliKSByZXR1cm4gTlVMTDsKCS8vIEJ1aWxkIGEgbW9ub2Nocm9tZSBwYWxldHRlCglSR0JRVUFEICpwYWwgPSBGcmVlSW1hZ2VfR2V0UGFsZXR0ZShuZXdfZGliKTsKCXBhbFswXS5yZ2JSZWQgPSBwYWxbMF0ucmdiR3JlZW4gPSBwYWxbMF0ucmdiQmx1ZSA9IDA7CglwYWxbMV0ucmdiUmVkID0gcGFsWzFdLnJnYkdyZWVuID0gcGFsWzFdLnJnYkJsdWUgPSAyNTU7CgoJLy8gUGVyZm9ybSB0aGUgdGhyZXNob2xkaW5nCgkvLwoJZm9yKGludCB5ID0gMDsgeSA8IGhlaWdodDsgeSsrKSB7CgkJQllURSAqYml0czggPSBGcmVlSW1hZ2VfR2V0U2NhbkxpbmUoZGliOCwgeSk7CgkJQllURSAqYml0czEgPSBGcmVlSW1hZ2VfR2V0U2NhbkxpbmUobmV3X2RpYiwgeSk7CgkJZm9yKGludCB4ID0gMDsgeCA8IHdpZHRoOyB4KyspIHsKCQkJaWYoYml0czhbeF0gPCBUKSB7CgkJCQkvLyBTZXQgYml0KHgsIHkpIHRvIDAKCQkJCWJpdHMxW3ggPj4gM10gJj0gKDB4RkY3RiA+PiAoeCAmIDB4NykpOwoJCQl9IGVsc2UgewoJCQkJLy8gU2V0IGJpdCh4LCB5KSB0byAxCgkJCQliaXRzMVt4ID4+IDNdIHw9ICgweDgwID4+ICh4ICYgMHg3KSk7CgkJCX0KCQl9Cgl9CglpZihkaWI4ICE9IGRpYikgewoJCUZyZWVJbWFnZV9VbmxvYWQoZGliOCk7Cgl9CgoJLy8gY29weSBtZXRhZGF0YSBmcm9tIHNyYyB0byBkc3QKCUZyZWVJbWFnZV9DbG9uZU1ldGFkYXRhKG5ld19kaWIsIGRpYik7CgoJcmV0dXJuIG5ld19kaWI7Cn0KCg==