Ly8gPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PQovLyBCaXRtYXAgY29udmVyc2lvbiByb3V0aW5lcwovLwovLyBEZXNpZ24gYW5kIGltcGxlbWVudGF0aW9uIGJ5Ci8vIC0gRmxvcmlzIHZhbiBkZW4gQmVyZyAoZmx2ZGJlcmdAd3hzLm5sKQovLyAtIEhlcnbpIERyb2xvbiAoZHJvbG9uQGluZm9uaWUuZnIpCi8vIC0gSmFuaSBLYWphbGEgKGphbmlrQHJlbWVkeS5maSkKLy8gLSBEZXRsZXYgVmVuZHQgKGRldGxldi52ZW5kdEBicmlsbGl0LmRlKQovLwovLyBUaGlzIGZpbGUgaXMgcGFydCBvZiBGcmVlSW1hZ2UgMwovLwovLyBDT1ZFUkVEIENPREUgSVMgUFJPVklERUQgVU5ERVIgVEhJUyBMSUNFTlNFIE9OIEFOICJBUyBJUyIgQkFTSVMsIFdJVEhPVVQgV0FSUkFOVFkKLy8gT0YgQU5ZIEtJTkQsIEVJVEhFUiBFWFBSRVNTRUQgT1IgSU1QTElFRCwgSU5DTFVESU5HLCBXSVRIT1VUIExJTUlUQVRJT04sIFdBUlJBTlRJRVMKLy8gVEhBVCBUSEUgQ09WRVJFRCBDT0RFIElTIEZSRUUgT0YgREVGRUNUUywgTUVSQ0hBTlRBQkxFLCBGSVQgRk9SIEEgUEFSVElDVUxBUiBQVVJQT1NFCi8vIE9SIE5PTi1JTkZSSU5HSU5HLiBUSEUgRU5USVJFIFJJU0sgQVMgVE8gVEhFIFFVQUxJVFkgQU5EIFBFUkZPUk1BTkNFIE9GIFRIRSBDT1ZFUkVECi8vIENPREUgSVMgV0lUSCBZT1UuIFNIT1VMRCBBTlkgQ09WRVJFRCBDT0RFIFBST1ZFIERFRkVDVElWRSBJTiBBTlkgUkVTUEVDVCwgWU9VIChOT1QKLy8gVEhFIElOSVRJQUwgREVWRUxPUEVSIE9SIEFOWSBPVEhFUiBDT05UUklCVVRPUikgQVNTVU1FIFRIRSBDT1NUIE9GIEFOWSBORUNFU1NBUlkKLy8gU0VSVklDSU5HLCBSRVBBSVIgT1IgQ09SUkVDVElPTi4gVEhJUyBESVNDTEFJTUVSIE9GIFdBUlJBTlRZIENPTlNUSVRVVEVTIEFOIEVTU0VOVElBTAovLyBQQVJUIE9GIFRISVMgTElDRU5TRS4gTk8gVVNFIE9GIEFOWSBDT1ZFUkVEIENPREUgSVMgQVVUSE9SSVpFRCBIRVJFVU5ERVIgRVhDRVBUIFVOREVSCi8vIFRISVMgRElTQ0xBSU1FUi4KLy8KLy8gVXNlIGF0IHlvdXIgb3duIHJpc2shCi8vID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0KCiNpbmNsdWRlICJGcmVlSW1hZ2UuaCIKI2luY2x1ZGUgIlV0aWxpdGllcy5oIgoKLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQovLyAgaW50ZXJuYWwgY29udmVyc2lvbnMgWCB0byAzMiBiaXRzCi8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KCnZvaWQgRExMX0NBTExDT05WCkZyZWVJbWFnZV9Db252ZXJ0TGluZTFUbzMyKEJZVEUgKnRhcmdldCwgQllURSAqc291cmNlLCBpbnQgd2lkdGhfaW5fcGl4ZWxzLCBSR0JRVUFEICpwYWxldHRlKSB7Cglmb3IgKGludCBjb2xzID0gMDsgY29scyA8IHdpZHRoX2luX3BpeGVsczsgY29scysrKSB7CgkJaW50IGluZGV4ID0gKHNvdXJjZVtjb2xzPj4zXSAmICgweDgwID4+IChjb2xzICYgMHgwNykpKSAhPSAwID8gMSA6IDA7CgoJCXRhcmdldFtGSV9SR0JBX0JMVUVdCT0gcGFsZXR0ZVtpbmRleF0ucmdiQmx1ZTsKCQl0YXJnZXRbRklfUkdCQV9HUkVFTl0JPSBwYWxldHRlW2luZGV4XS5yZ2JHcmVlbjsKCQl0YXJnZXRbRklfUkdCQV9SRURdCQk9IHBhbGV0dGVbaW5kZXhdLnJnYlJlZDsKCQl0YXJnZXRbRklfUkdCQV9BTFBIQV0JPSAweEZGOwoJCXRhcmdldCArPSA0OwoJfQkKfQoKdm9pZCBETExfQ0FMTENPTlYKRnJlZUltYWdlX0NvbnZlcnRMaW5lNFRvMzIoQllURSAqdGFyZ2V0LCBCWVRFICpzb3VyY2UsIGludCB3aWR0aF9pbl9waXhlbHMsIFJHQlFVQUQgKnBhbGV0dGUpIHsKCUJPT0wgbG93X25pYmJsZSA9IEZBTFNFOwoJaW50IHggPSAwOwoKCWZvciAoaW50IGNvbHMgPSAwIDsgY29scyA8IHdpZHRoX2luX3BpeGVscyA7ICsrY29scykgewoJCWlmIChsb3dfbmliYmxlKSB7CgkJCXRhcmdldFtGSV9SR0JBX0JMVUVdCT0gcGFsZXR0ZVtMT1dOSUJCTEUoc291cmNlW3hdKV0ucmdiQmx1ZTsKCQkJdGFyZ2V0W0ZJX1JHQkFfR1JFRU5dCT0gcGFsZXR0ZVtMT1dOSUJCTEUoc291cmNlW3hdKV0ucmdiR3JlZW47CgkJCXRhcmdldFtGSV9SR0JBX1JFRF0JCT0gcGFsZXR0ZVtMT1dOSUJCTEUoc291cmNlW3hdKV0ucmdiUmVkOwoKCQkJeCsrOwoJCX0gZWxzZSB7CgkJCXRhcmdldFtGSV9SR0JBX0JMVUVdCT0gcGFsZXR0ZVtISU5JQkJMRShzb3VyY2VbeF0pID4+IDRdLnJnYkJsdWU7CgkJCXRhcmdldFtGSV9SR0JBX0dSRUVOXQk9IHBhbGV0dGVbSElOSUJCTEUoc291cmNlW3hdKSA+PiA0XS5yZ2JHcmVlbjsKCQkJdGFyZ2V0W0ZJX1JHQkFfUkVEXQkJPSBwYWxldHRlW0hJTklCQkxFKHNvdXJjZVt4XSkgPj4gNF0ucmdiUmVkOwoJCX0KCgkJbG93X25pYmJsZSA9ICFsb3dfbmliYmxlOwoKCQl0YXJnZXRbRklfUkdCQV9BTFBIQV0gPSAweEZGOwoJCXRhcmdldCArPSA0OwoJfQp9Cgp2b2lkIERMTF9DQUxMQ09OVgpGcmVlSW1hZ2VfQ29udmVydExpbmU4VG8zMihCWVRFICp0YXJnZXQsIEJZVEUgKnNvdXJjZSwgaW50IHdpZHRoX2luX3BpeGVscywgUkdCUVVBRCAqcGFsZXR0ZSkgewoJZm9yIChpbnQgY29scyA9IDA7IGNvbHMgPCB3aWR0aF9pbl9waXhlbHM7IGNvbHMrKykgewoJCXRhcmdldFtGSV9SR0JBX0JMVUVdCT0gcGFsZXR0ZVtzb3VyY2VbY29sc11dLnJnYkJsdWU7CgkJdGFyZ2V0W0ZJX1JHQkFfR1JFRU5dCT0gcGFsZXR0ZVtzb3VyY2VbY29sc11dLnJnYkdyZWVuOwoJCXRhcmdldFtGSV9SR0JBX1JFRF0JCT0gcGFsZXR0ZVtzb3VyY2VbY29sc11dLnJnYlJlZDsKCQl0YXJnZXRbRklfUkdCQV9BTFBIQV0JPSAweEZGOwoJCXRhcmdldCArPSA0OwoJfQp9Cgp2b2lkIERMTF9DQUxMQ09OVgpGcmVlSW1hZ2VfQ29udmVydExpbmUxNlRvMzJfNTU1KEJZVEUgKnRhcmdldCwgQllURSAqc291cmNlLCBpbnQgd2lkdGhfaW5fcGl4ZWxzKSB7CglXT1JEICpiaXRzID0gKFdPUkQgKilzb3VyY2U7CgoJZm9yIChpbnQgY29scyA9IDA7IGNvbHMgPCB3aWR0aF9pbl9waXhlbHM7IGNvbHMrKykgewoJCXRhcmdldFtGSV9SR0JBX1JFRF0gICA9IChCWVRFKSgoKChiaXRzW2NvbHNdICYgRkkxNl81NTVfUkVEX01BU0spID4+IEZJMTZfNTU1X1JFRF9TSElGVCkgKiAweEZGKSAvIDB4MUYpOwoJCXRhcmdldFtGSV9SR0JBX0dSRUVOXSA9IChCWVRFKSgoKChiaXRzW2NvbHNdICYgRkkxNl81NTVfR1JFRU5fTUFTSykgPj4gRkkxNl81NTVfR1JFRU5fU0hJRlQpICogMHhGRikgLyAweDFGKTsKCQl0YXJnZXRbRklfUkdCQV9CTFVFXSAgPSAoQllURSkoKCgoYml0c1tjb2xzXSAmIEZJMTZfNTU1X0JMVUVfTUFTSykgPj4gRkkxNl81NTVfQkxVRV9TSElGVCkgKiAweEZGKSAvIDB4MUYpOwoJCXRhcmdldFtGSV9SR0JBX0FMUEhBXSA9IDB4RkY7CgkJdGFyZ2V0ICs9IDQ7Cgl9Cn0KCnZvaWQgRExMX0NBTExDT05WCkZyZWVJbWFnZV9Db252ZXJ0TGluZTE2VG8zMl81NjUoQllURSAqdGFyZ2V0LCBCWVRFICpzb3VyY2UsIGludCB3aWR0aF9pbl9waXhlbHMpIHsKCVdPUkQgKmJpdHMgPSAoV09SRCAqKXNvdXJjZTsKCglmb3IgKGludCBjb2xzID0gMDsgY29scyA8IHdpZHRoX2luX3BpeGVsczsgY29scysrKSB7CgkJdGFyZ2V0W0ZJX1JHQkFfUkVEXSAgID0gKEJZVEUpKCgoKGJpdHNbY29sc10gJiBGSTE2XzU2NV9SRURfTUFTSykgPj4gRkkxNl81NjVfUkVEX1NISUZUKSAqIDB4RkYpIC8gMHgxRik7CgkJdGFyZ2V0W0ZJX1JHQkFfR1JFRU5dID0gKEJZVEUpKCgoKGJpdHNbY29sc10gJiBGSTE2XzU2NV9HUkVFTl9NQVNLKSA+PiBGSTE2XzU2NV9HUkVFTl9TSElGVCkgKiAweEZGKSAvIDB4M0YpOwoJCXRhcmdldFtGSV9SR0JBX0JMVUVdICA9IChCWVRFKSgoKChiaXRzW2NvbHNdICYgRkkxNl81NjVfQkxVRV9NQVNLKSA+PiBGSTE2XzU2NV9CTFVFX1NISUZUKSAqIDB4RkYpIC8gMHgxRik7CgkJdGFyZ2V0W0ZJX1JHQkFfQUxQSEFdID0gMHhGRjsKCQl0YXJnZXQgKz0gNDsKCX0KfQovKgp2b2lkIERMTF9DQUxMQ09OVgpGcmVlSW1hZ2VfQ29udmVydExpbmUyNFRvMzIoQllURSAqdGFyZ2V0LCBCWVRFICpzb3VyY2UsIGludCB3aWR0aF9pbl9waXhlbHMpIHsKCWZvciAoaW50IGNvbHMgPSAwOyBjb2xzIDwgd2lkdGhfaW5fcGl4ZWxzOyBjb2xzKyspIHsKCQkqKERXT1JEICopdGFyZ2V0ID0gKCooRFdPUkQgKikgc291cmNlICYgRklfUkdCQV9SR0JfTUFTSykgfCBGSV9SR0JBX0FMUEhBX01BU0s7CgkJdGFyZ2V0ICs9IDQ7CgkJc291cmNlICs9IDM7Cgl9Cn0KKi8KLyoqClRoaXMgdW5vcHRpbWl6ZWQgdmVyc2lvbiBvZiB0aGUgY29udmVyc2lvbiBmdW5jdGlvbiBhdm9pZCBhbiB1bmRldGVybWluZWQgYnVnIHdpdGggVkMrKyBTUDYuIApUaGUgYnVnIG9jY3VycyBpbiByZWxlYXNlIG1vZGUgb25seSwgd2hlbiB0aGUgaW1hZ2UgaGVpZ2h0IGlzIGVxdWFsIHRvIDUzNyAKKHRyeSBlLmcuIGEgc2l6ZSBvZiA0MzJ4NTM3IHRvIHJlcHJvZHVjZSB0aGUgYnVnIHdpdGggdGhlIG9wdGltaXplZCBmdW5jdGlvbikuCiovCnZvaWQgRExMX0NBTExDT05WCkZyZWVJbWFnZV9Db252ZXJ0TGluZTI0VG8zMihCWVRFICp0YXJnZXQsIEJZVEUgKnNvdXJjZSwgaW50IHdpZHRoX2luX3BpeGVscykgewoJZm9yIChpbnQgY29scyA9IDA7IGNvbHMgPCB3aWR0aF9pbl9waXhlbHM7IGNvbHMrKykgewoJCXRhcmdldFtGSV9SR0JBX1JFRF0gICA9IHNvdXJjZVtGSV9SR0JBX1JFRF07CgkJdGFyZ2V0W0ZJX1JHQkFfR1JFRU5dID0gc291cmNlW0ZJX1JHQkFfR1JFRU5dOwoJCXRhcmdldFtGSV9SR0JBX0JMVUVdICA9IHNvdXJjZVtGSV9SR0JBX0JMVUVdOwoJCXRhcmdldFtGSV9SR0JBX0FMUEhBXSA9IDB4RkY7CgkJdGFyZ2V0ICs9IDQ7CgkJc291cmNlICs9IDM7Cgl9Cn0KLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQoKc3RhdGljIHZvaWQgRExMX0NBTExDT05WCk1hcFRyYW5zcGFyZW50VGFibGVUb0FscGhhMShSR0JRVUFEICp0YXJnZXQsIEJZVEUgKnNvdXJjZSwgQllURSAqdGFibGUsIGludCB0cmFuc3BhcmVudF9waXhlbHMsIGludCB3aWR0aF9pbl9waXhlbHMpIHsKCWZvciAoaW50IGNvbHMgPSAwIDsgY29scyA8IHdpZHRoX2luX3BpeGVscyA7IGNvbHMrKykgewoJCWludCBpbmRleCA9IChzb3VyY2VbY29scz4+M10gJiAoMHg4MCA+PiAoY29scyAmIDB4MDcpKSkgIT0gMCA/IDEgOiAwOwoJCXRhcmdldFtjb2xzXS5yZ2JSZXNlcnZlZCA9IChpbmRleCA8IHRyYW5zcGFyZW50X3BpeGVscykgPyB0YWJsZVtpbmRleF0gOiAyNTU7CiAgICB9Cn0KCnN0YXRpYyB2b2lkIERMTF9DQUxMQ09OVgpNYXBUcmFuc3BhcmVudFRhYmxlVG9BbHBoYTQoUkdCUVVBRCAqdGFyZ2V0LCBCWVRFICpzb3VyY2UsIEJZVEUgKnRhYmxlLCBpbnQgdHJhbnNwYXJlbnRfcGl4ZWxzLCBpbnQgd2lkdGhfaW5fcGl4ZWxzKSB7CiAgICBCT09MIGxvd19uaWJibGUgPSBGQUxTRTsKICAgIGludCB4ID0gMDsKCiAgICBmb3IgKGludCBjb2xzID0gMCA7IGNvbHMgPCB3aWR0aF9pbl9waXhlbHMgOyArK2NvbHMpIHsKICAgICAgICBpbnQgaW5kZXg7CiAgICAgICAgaWYgKGxvd19uaWJibGUpIHsKICAgICAgICAgICAgaW5kZXggPSBMT1dOSUJCTEUoc291cmNlW3hdKTsKICAgICAgICAgICAgeCsrOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIGluZGV4ID0gSElOSUJCTEUoc291cmNlW3hdKSA+PiA0OwogICAgICAgIH0KICAgICAgICB0YXJnZXRbY29sc10ucmdiUmVzZXJ2ZWQgPSAoaW5kZXggPCB0cmFuc3BhcmVudF9waXhlbHMpID8gdGFibGVbaW5kZXhdIDogMjU1OwogICAgICAgIGxvd19uaWJibGUgPSAhbG93X25pYmJsZTsKICAgIH0KfQoKc3RhdGljIHZvaWQgRExMX0NBTExDT05WCk1hcFRyYW5zcGFyZW50VGFibGVUb0FscGhhOChSR0JRVUFEICp0YXJnZXQsIEJZVEUgKnNvdXJjZSwgQllURSAqdGFibGUsIGludCB0cmFuc3BhcmVudF9waXhlbHMsIGludCB3aWR0aF9pbl9waXhlbHMpIHsKICAgIGZvciAoaW50IGNvbHMgPSAwOyBjb2xzIDwgd2lkdGhfaW5fcGl4ZWxzOyBjb2xzKyspIHsKCQl0YXJnZXRbY29sc10ucmdiUmVzZXJ2ZWQgPSAoc291cmNlW2NvbHNdIDwgdHJhbnNwYXJlbnRfcGl4ZWxzKSA/IHRhYmxlW3NvdXJjZVtjb2xzXV0gOiAyNTU7Cgl9Cn0gCgovLyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCgpGSUJJVE1BUCAqIERMTF9DQUxMQ09OVgpGcmVlSW1hZ2VfQ29udmVydFRvMzJCaXRzKEZJQklUTUFQICpkaWIpIHsKCWlmKCFkaWIpIHJldHVybiBOVUxMOwoKCWNvbnN0IGludCBicHAgPSBGcmVlSW1hZ2VfR2V0QlBQKGRpYik7Cgljb25zdCBGUkVFX0lNQUdFX1RZUEUgaW1hZ2VfdHlwZSA9IEZyZWVJbWFnZV9HZXRJbWFnZVR5cGUoZGliKTsKCQoJaWYoKGltYWdlX3R5cGUgIT0gRklUX0JJVE1BUCkgJiYgKGltYWdlX3R5cGUgIT0gRklUX1JHQjE2KSAmJiAoaW1hZ2VfdHlwZSAhPSBGSVRfUkdCQTE2KSkgewoJCXJldHVybiBOVUxMOwoJfQoJCgljb25zdCBpbnQgd2lkdGggPSBGcmVlSW1hZ2VfR2V0V2lkdGgoZGliKTsKCWNvbnN0IGludCBoZWlnaHQgPSBGcmVlSW1hZ2VfR2V0SGVpZ2h0KGRpYik7CgoJaWYoaW1hZ2VfdHlwZSA9PSBGSVRfQklUTUFQKSB7CgoJCWlmKGJwcCA9PSAzMikgewoJCQlyZXR1cm4gRnJlZUltYWdlX0Nsb25lKGRpYik7CgkJfQoKCQlGSUJJVE1BUCAqbmV3X2RpYiA9IEZyZWVJbWFnZV9BbGxvY2F0ZSh3aWR0aCwgaGVpZ2h0LCAzMiwgRklfUkdCQV9SRURfTUFTSywgRklfUkdCQV9HUkVFTl9NQVNLLCBGSV9SR0JBX0JMVUVfTUFTSyk7CgkJaWYobmV3X2RpYiA9PSBOVUxMKSB7CgkJCXJldHVybiBOVUxMOwoJCX0KCgkJLy8gY29weSBtZXRhZGF0YSBmcm9tIHNyYyB0byBkc3QKCQlGcmVlSW1hZ2VfQ2xvbmVNZXRhZGF0YShuZXdfZGliLCBkaWIpOwoKCQlzd2l0Y2goYnBwKSB7CgkJCWNhc2UgMToKCQkJewoJCQkJZm9yIChpbnQgcm93cyA9IDA7IHJvd3MgPCBoZWlnaHQ7IHJvd3MrKykgewoJCQkJCUZyZWVJbWFnZV9Db252ZXJ0TGluZTFUbzMyKEZyZWVJbWFnZV9HZXRTY2FuTGluZShuZXdfZGliLCByb3dzKSwgRnJlZUltYWdlX0dldFNjYW5MaW5lKGRpYiwgcm93cyksIHdpZHRoLCBGcmVlSW1hZ2VfR2V0UGFsZXR0ZShkaWIpKTsKCQkJCQkKCQkJCQlpZiAoRnJlZUltYWdlX0lzVHJhbnNwYXJlbnQoZGliKSkgewoJCQkJCQlNYXBUcmFuc3BhcmVudFRhYmxlVG9BbHBoYTEoKFJHQlFVQUQgKilGcmVlSW1hZ2VfR2V0U2NhbkxpbmUobmV3X2RpYiwgcm93cyksIEZyZWVJbWFnZV9HZXRTY2FuTGluZShkaWIsIHJvd3MpLCBGcmVlSW1hZ2VfR2V0VHJhbnNwYXJlbmN5VGFibGUoZGliKSwgRnJlZUltYWdlX0dldFRyYW5zcGFyZW5jeUNvdW50KGRpYiksIHdpZHRoKTsKCQkJCQl9CgkJCQl9CgoJCQkJcmV0dXJuIG5ld19kaWI7CgkJCX0KCgkJCWNhc2UgNDoKCQkJewoJCQkJZm9yIChpbnQgcm93cyA9IDA7IHJvd3MgPCBoZWlnaHQ7IHJvd3MrKykgewoJCQkJCUZyZWVJbWFnZV9Db252ZXJ0TGluZTRUbzMyKEZyZWVJbWFnZV9HZXRTY2FuTGluZShuZXdfZGliLCByb3dzKSwgRnJlZUltYWdlX0dldFNjYW5MaW5lKGRpYiwgcm93cyksIHdpZHRoLCBGcmVlSW1hZ2VfR2V0UGFsZXR0ZShkaWIpKTsKCQkJCgkJCQkJaWYgKEZyZWVJbWFnZV9Jc1RyYW5zcGFyZW50KGRpYikpIHsKCQkJCQkJTWFwVHJhbnNwYXJlbnRUYWJsZVRvQWxwaGE0KChSR0JRVUFEICopRnJlZUltYWdlX0dldFNjYW5MaW5lKG5ld19kaWIsIHJvd3MpLCBGcmVlSW1hZ2VfR2V0U2NhbkxpbmUoZGliLCByb3dzKSwgRnJlZUltYWdlX0dldFRyYW5zcGFyZW5jeVRhYmxlKGRpYiksIEZyZWVJbWFnZV9HZXRUcmFuc3BhcmVuY3lDb3VudChkaWIpLCB3aWR0aCk7CgkJCQkJfQoJCQkJfQoKCQkJCXJldHVybiBuZXdfZGliOwoJCQl9CgkJCQkKCQkJY2FzZSA4OgoJCQl7CgkJCQlmb3IgKGludCByb3dzID0gMDsgcm93cyA8IGhlaWdodDsgcm93cysrKSB7CgkJCQkJRnJlZUltYWdlX0NvbnZlcnRMaW5lOFRvMzIoRnJlZUltYWdlX0dldFNjYW5MaW5lKG5ld19kaWIsIHJvd3MpLCBGcmVlSW1hZ2VfR2V0U2NhbkxpbmUoZGliLCByb3dzKSwgd2lkdGgsIEZyZWVJbWFnZV9HZXRQYWxldHRlKGRpYikpOwoKCQkJCQlpZiAoRnJlZUltYWdlX0lzVHJhbnNwYXJlbnQoZGliKSkgewoJCQkJCQlNYXBUcmFuc3BhcmVudFRhYmxlVG9BbHBoYTgoKFJHQlFVQUQgKilGcmVlSW1hZ2VfR2V0U2NhbkxpbmUobmV3X2RpYiwgcm93cyksIEZyZWVJbWFnZV9HZXRTY2FuTGluZShkaWIsIHJvd3MpLCBGcmVlSW1hZ2VfR2V0VHJhbnNwYXJlbmN5VGFibGUoZGliKSwgRnJlZUltYWdlX0dldFRyYW5zcGFyZW5jeUNvdW50KGRpYiksIHdpZHRoKTsKCQkJCQl9CgkJCQl9CgoJCQkJcmV0dXJuIG5ld19kaWI7CgkJCX0KCgkJCWNhc2UgMTY6CgkJCXsKCQkJCWZvciAoaW50IHJvd3MgPSAwOyByb3dzIDwgaGVpZ2h0OyByb3dzKyspIHsKCQkJCQlpZiAoKEZyZWVJbWFnZV9HZXRSZWRNYXNrKGRpYikgPT0gRkkxNl81NjVfUkVEX01BU0spICYmIChGcmVlSW1hZ2VfR2V0R3JlZW5NYXNrKGRpYikgPT0gRkkxNl81NjVfR1JFRU5fTUFTSykgJiYgKEZyZWVJbWFnZV9HZXRCbHVlTWFzayhkaWIpID09IEZJMTZfNTY1X0JMVUVfTUFTSykpIHsKCQkJCQkJRnJlZUltYWdlX0NvbnZlcnRMaW5lMTZUbzMyXzU2NShGcmVlSW1hZ2VfR2V0U2NhbkxpbmUobmV3X2RpYiwgcm93cyksIEZyZWVJbWFnZV9HZXRTY2FuTGluZShkaWIsIHJvd3MpLCB3aWR0aCk7CgkJCQkJfSBlbHNlIHsKCQkJCQkJLy8gaW5jbHVkZXMgY2FzZSB3aGVyZSBhbGwgdGhlIG1hc2tzIGFyZSAwCgkJCQkJCUZyZWVJbWFnZV9Db252ZXJ0TGluZTE2VG8zMl81NTUoRnJlZUltYWdlX0dldFNjYW5MaW5lKG5ld19kaWIsIHJvd3MpLCBGcmVlSW1hZ2VfR2V0U2NhbkxpbmUoZGliLCByb3dzKSwgd2lkdGgpOwoJCQkJCX0KCQkJCX0KCgkJCQlyZXR1cm4gbmV3X2RpYjsKCQkJfQoKCQkJY2FzZSAyNDoKCQkJewoJCQkJZm9yIChpbnQgcm93cyA9IDA7IHJvd3MgPCBoZWlnaHQ7IHJvd3MrKykgewoJCQkJCUZyZWVJbWFnZV9Db252ZXJ0TGluZTI0VG8zMihGcmVlSW1hZ2VfR2V0U2NhbkxpbmUobmV3X2RpYiwgcm93cyksIEZyZWVJbWFnZV9HZXRTY2FuTGluZShkaWIsIHJvd3MpLCB3aWR0aCk7CgkJCQl9CgoJCQkJcmV0dXJuIG5ld19kaWI7CgkJCX0KCQl9CgoJfSBlbHNlIGlmKGltYWdlX3R5cGUgPT0gRklUX1JHQjE2KSB7CgkJRklCSVRNQVAgKm5ld19kaWIgPSBGcmVlSW1hZ2VfQWxsb2NhdGUod2lkdGgsIGhlaWdodCwgMzIsIEZJX1JHQkFfUkVEX01BU0ssIEZJX1JHQkFfR1JFRU5fTUFTSywgRklfUkdCQV9CTFVFX01BU0spOwoJCWlmKG5ld19kaWIgPT0gTlVMTCkgewoJCQlyZXR1cm4gTlVMTDsKCQl9CgoJCS8vIGNvcHkgbWV0YWRhdGEgZnJvbSBzcmMgdG8gZHN0CgkJRnJlZUltYWdlX0Nsb25lTWV0YWRhdGEobmV3X2RpYiwgZGliKTsKCgkJY29uc3QgdW5zaWduZWQgc3JjX3BpdGNoID0gRnJlZUltYWdlX0dldFBpdGNoKGRpYik7CgkJY29uc3QgdW5zaWduZWQgZHN0X3BpdGNoID0gRnJlZUltYWdlX0dldFBpdGNoKG5ld19kaWIpOwoJCWNvbnN0IEJZVEUgKnNyY19iaXRzID0gRnJlZUltYWdlX0dldEJpdHMoZGliKTsKCQlCWVRFICpkc3RfYml0cyA9IEZyZWVJbWFnZV9HZXRCaXRzKG5ld19kaWIpOwoJCWZvciAoaW50IHJvd3MgPSAwOyByb3dzIDwgaGVpZ2h0OyByb3dzKyspIHsKCQkJY29uc3QgRklSR0IxNiAqc3JjX3BpeGVsID0gKEZJUkdCMTYqKXNyY19iaXRzOwoJCQlSR0JRVUFEICpkc3RfcGl4ZWwgPSAoUkdCUVVBRCopZHN0X2JpdHM7CgkJCWZvcihpbnQgY29scyA9IDA7IGNvbHMgPCB3aWR0aDsgY29scysrKSB7CgkJCQlkc3RfcGl4ZWxbY29sc10ucmdiUmVkCQk9IChCWVRFKShzcmNfcGl4ZWxbY29sc10ucmVkICAgPj4gOCk7CgkJCQlkc3RfcGl4ZWxbY29sc10ucmdiR3JlZW4JPSAoQllURSkoc3JjX3BpeGVsW2NvbHNdLmdyZWVuID4+IDgpOwoJCQkJZHN0X3BpeGVsW2NvbHNdLnJnYkJsdWUJCT0gKEJZVEUpKHNyY19waXhlbFtjb2xzXS5ibHVlICA+PiA4KTsKCQkJCWRzdF9waXhlbFtjb2xzXS5yZ2JSZXNlcnZlZCA9IChCWVRFKTB4RkY7CgkJCX0KCQkJc3JjX2JpdHMgKz0gc3JjX3BpdGNoOwoJCQlkc3RfYml0cyArPSBkc3RfcGl0Y2g7CgkJfQoKCQlyZXR1cm4gbmV3X2RpYjsKCgl9IGVsc2UgaWYoaW1hZ2VfdHlwZSA9PSBGSVRfUkdCQTE2KSB7CgkJRklCSVRNQVAgKm5ld19kaWIgPSBGcmVlSW1hZ2VfQWxsb2NhdGUod2lkdGgsIGhlaWdodCwgMzIsIEZJX1JHQkFfUkVEX01BU0ssIEZJX1JHQkFfR1JFRU5fTUFTSywgRklfUkdCQV9CTFVFX01BU0spOwoJCWlmKG5ld19kaWIgPT0gTlVMTCkgewoJCQlyZXR1cm4gTlVMTDsKCQl9CgoJCS8vIGNvcHkgbWV0YWRhdGEgZnJvbSBzcmMgdG8gZHN0CgkJRnJlZUltYWdlX0Nsb25lTWV0YWRhdGEobmV3X2RpYiwgZGliKTsKCgkJY29uc3QgdW5zaWduZWQgc3JjX3BpdGNoID0gRnJlZUltYWdlX0dldFBpdGNoKGRpYik7CgkJY29uc3QgdW5zaWduZWQgZHN0X3BpdGNoID0gRnJlZUltYWdlX0dldFBpdGNoKG5ld19kaWIpOwoJCWNvbnN0IEJZVEUgKnNyY19iaXRzID0gRnJlZUltYWdlX0dldEJpdHMoZGliKTsKCQlCWVRFICpkc3RfYml0cyA9IEZyZWVJbWFnZV9HZXRCaXRzKG5ld19kaWIpOwoJCWZvciAoaW50IHJvd3MgPSAwOyByb3dzIDwgaGVpZ2h0OyByb3dzKyspIHsKCQkJY29uc3QgRklSR0JBMTYgKnNyY19waXhlbCA9IChGSVJHQkExNiopc3JjX2JpdHM7CgkJCVJHQlFVQUQgKmRzdF9waXhlbCA9IChSR0JRVUFEKilkc3RfYml0czsKCQkJZm9yKGludCBjb2xzID0gMDsgY29scyA8IHdpZHRoOyBjb2xzKyspIHsKCQkJCWRzdF9waXhlbFtjb2xzXS5yZ2JSZWQJCT0gKEJZVEUpKHNyY19waXhlbFtjb2xzXS5yZWQgICA+PiA4KTsKCQkJCWRzdF9waXhlbFtjb2xzXS5yZ2JHcmVlbgk9IChCWVRFKShzcmNfcGl4ZWxbY29sc10uZ3JlZW4gPj4gOCk7CgkJCQlkc3RfcGl4ZWxbY29sc10ucmdiQmx1ZQkJPSAoQllURSkoc3JjX3BpeGVsW2NvbHNdLmJsdWUgID4+IDgpOwoJCQkJZHN0X3BpeGVsW2NvbHNdLnJnYlJlc2VydmVkID0gKEJZVEUpKHNyY19waXhlbFtjb2xzXS5hbHBoYSA+PiA4KTsKCQkJfQoJCQlzcmNfYml0cyArPSBzcmNfcGl0Y2g7CgkJCWRzdF9iaXRzICs9IGRzdF9waXRjaDsKCQl9CQkKCgkJcmV0dXJuIG5ld19kaWI7Cgl9CgkKCXJldHVybiBOVUxMOwp9Cg==