Ly8gPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PQovLyBCaXRtYXAgY29udmVyc2lvbiByb3V0aW5lcwovLwovLyBEZXNpZ24gYW5kIGltcGxlbWVudGF0aW9uIGJ5Ci8vIC0gRmxvcmlzIHZhbiBkZW4gQmVyZyAoZmx2ZGJlcmdAd3hzLm5sKQovLyAtIEhlcnbpIERyb2xvbiAoZHJvbG9uQGluZm9uaWUuZnIpCi8vIC0gSmFuaSBLYWphbGEgKGphbmlrQHJlbWVkeS5maSkKLy8KLy8gVGhpcyBmaWxlIGlzIHBhcnQgb2YgRnJlZUltYWdlIDMKLy8KLy8gQ09WRVJFRCBDT0RFIElTIFBST1ZJREVEIFVOREVSIFRISVMgTElDRU5TRSBPTiBBTiAiQVMgSVMiIEJBU0lTLCBXSVRIT1VUIFdBUlJBTlRZCi8vIE9GIEFOWSBLSU5ELCBFSVRIRVIgRVhQUkVTU0VEIE9SIElNUExJRUQsIElOQ0xVRElORywgV0lUSE9VVCBMSU1JVEFUSU9OLCBXQVJSQU5USUVTCi8vIFRIQVQgVEhFIENPVkVSRUQgQ09ERSBJUyBGUkVFIE9GIERFRkVDVFMsIE1FUkNIQU5UQUJMRSwgRklUIEZPUiBBIFBBUlRJQ1VMQVIgUFVSUE9TRQovLyBPUiBOT04tSU5GUklOR0lORy4gVEhFIEVOVElSRSBSSVNLIEFTIFRPIFRIRSBRVUFMSVRZIEFORCBQRVJGT1JNQU5DRSBPRiBUSEUgQ09WRVJFRAovLyBDT0RFIElTIFdJVEggWU9VLiBTSE9VTEQgQU5ZIENPVkVSRUQgQ09ERSBQUk9WRSBERUZFQ1RJVkUgSU4gQU5ZIFJFU1BFQ1QsIFlPVSAoTk9UCi8vIFRIRSBJTklUSUFMIERFVkVMT1BFUiBPUiBBTlkgT1RIRVIgQ09OVFJJQlVUT1IpIEFTU1VNRSBUSEUgQ09TVCBPRiBBTlkgTkVDRVNTQVJZCi8vIFNFUlZJQ0lORywgUkVQQUlSIE9SIENPUlJFQ1RJT04uIFRISVMgRElTQ0xBSU1FUiBPRiBXQVJSQU5UWSBDT05TVElUVVRFUyBBTiBFU1NFTlRJQUwKLy8gUEFSVCBPRiBUSElTIExJQ0VOU0UuIE5PIFVTRSBPRiBBTlkgQ09WRVJFRCBDT0RFIElTIEFVVEhPUklaRUQgSEVSRVVOREVSIEVYQ0VQVCBVTkRFUgovLyBUSElTIERJU0NMQUlNRVIuCi8vCi8vIFVzZSBhdCB5b3VyIG93biByaXNrIQovLyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09CgojaW5jbHVkZSAiRnJlZUltYWdlLmgiCiNpbmNsdWRlICJVdGlsaXRpZXMuaCIKCi8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KLy8gIGludGVybmFsIGNvbnZlcnNpb25zIFggdG8gMTYgYml0cyAoNTY1KQovLyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCgp2b2lkIERMTF9DQUxMQ09OVgpGcmVlSW1hZ2VfQ29udmVydExpbmUxVG8xNl81NjUoQllURSAqdGFyZ2V0LCBCWVRFICpzb3VyY2UsIGludCB3aWR0aF9pbl9waXhlbHMsIFJHQlFVQUQgKnBhbGV0dGUpIHsKCVdPUkQgKm5ld19iaXRzID0gKFdPUkQgKil0YXJnZXQ7CgoJZm9yIChpbnQgY29scyA9IDA7IGNvbHMgPCB3aWR0aF9pbl9waXhlbHM7IGNvbHMrKykgewoJCWludCBpbmRleCA9IChzb3VyY2VbY29scyA+PiAzXSAmICgweDgwID4+IChjb2xzICYgMHgwNykpKSAhPSAwID8gMSA6IDA7CgoJCW5ld19iaXRzW2NvbHNdID0gUkdCNTY1KHBhbGV0dGVbaW5kZXhdLnJnYkJsdWUsIHBhbGV0dGVbaW5kZXhdLnJnYkdyZWVuLCBwYWxldHRlW2luZGV4XS5yZ2JSZWQpOwoJfQp9Cgp2b2lkIERMTF9DQUxMQ09OVgpGcmVlSW1hZ2VfQ29udmVydExpbmU0VG8xNl81NjUoQllURSAqdGFyZ2V0LCBCWVRFICpzb3VyY2UsIGludCB3aWR0aF9pbl9waXhlbHMsIFJHQlFVQUQgKnBhbGV0dGUpIHsKCVdPUkQgKm5ld19iaXRzID0gKFdPUkQgKil0YXJnZXQ7CglCT09MIGxvbmliYmxlID0gRkFMU0U7CglpbnQgeCA9IDA7CgoJZm9yIChpbnQgY29scyA9IDA7IGNvbHMgPCB3aWR0aF9pbl9waXhlbHM7IGNvbHMrKykgewoJCVJHQlFVQUQgKmdyYWJfcGFsZXR0ZTsKCgkJaWYgKGxvbmliYmxlKSB7CgkJCWdyYWJfcGFsZXR0ZSA9IHBhbGV0dGUgKyBMT1dOSUJCTEUoc291cmNlW3grK10pOwoJCX0gZWxzZSB7CgkJCWdyYWJfcGFsZXR0ZSA9IHBhbGV0dGUgKyAoSElOSUJCTEUoc291cmNlW3hdKSA+PiA0KTsJCQkJCQkJCQoJCX0KCgkJbmV3X2JpdHNbY29sc10gPSBSR0I1NjUoZ3JhYl9wYWxldHRlLT5yZ2JCbHVlLCBncmFiX3BhbGV0dGUtPnJnYkdyZWVuLCBncmFiX3BhbGV0dGUtPnJnYlJlZCk7CgoJCWxvbmliYmxlID0gIWxvbmliYmxlOwoJfQp9Cgp2b2lkIERMTF9DQUxMQ09OVgpGcmVlSW1hZ2VfQ29udmVydExpbmU4VG8xNl81NjUoQllURSAqdGFyZ2V0LCBCWVRFICpzb3VyY2UsIGludCB3aWR0aF9pbl9waXhlbHMsIFJHQlFVQUQgKnBhbGV0dGUpIHsKCVdPUkQgKm5ld19iaXRzID0gKFdPUkQgKil0YXJnZXQ7CgoJZm9yIChpbnQgY29scyA9IDA7IGNvbHMgPCB3aWR0aF9pbl9waXhlbHM7IGNvbHMrKykgewoJCVJHQlFVQUQgKmdyYWJfcGFsZXR0ZSA9IHBhbGV0dGUgKyBzb3VyY2VbY29sc107CgoJCW5ld19iaXRzW2NvbHNdID0gUkdCNTY1KGdyYWJfcGFsZXR0ZS0+cmdiQmx1ZSwgZ3JhYl9wYWxldHRlLT5yZ2JHcmVlbiwgZ3JhYl9wYWxldHRlLT5yZ2JSZWQpOwoJfQp9Cgp2b2lkIERMTF9DQUxMQ09OVgpGcmVlSW1hZ2VfQ29udmVydExpbmUxNl81NTVfVG8xNl81NjUoQllURSAqdGFyZ2V0LCBCWVRFICpzb3VyY2UsIGludCB3aWR0aF9pbl9waXhlbHMpIHsKCVdPUkQgKnNyY19iaXRzID0gKFdPUkQgKilzb3VyY2U7CglXT1JEICpuZXdfYml0cyA9IChXT1JEICopdGFyZ2V0OwoKCWZvciAoaW50IGNvbHMgPSAwOyBjb2xzIDwgd2lkdGhfaW5fcGl4ZWxzOyBjb2xzKyspIHsKCQluZXdfYml0c1tjb2xzXSA9IFJHQjU2NSgoKChzcmNfYml0c1tjb2xzXSAmIEZJMTZfNTU1X0JMVUVfTUFTSykgPj4gRkkxNl81NTVfQkxVRV9TSElGVCkgKiAweEZGKSAvIDB4MUYsCgkJCSAgICAgICAgICAgICAgICAgICAgKCgoc3JjX2JpdHNbY29sc10gJiBGSTE2XzU1NV9HUkVFTl9NQVNLKSA+PiBGSTE2XzU1NV9HUkVFTl9TSElGVCkgKiAweEZGKSAvIDB4MUYsCgkJCQkJCQkJKCgoc3JjX2JpdHNbY29sc10gJiBGSTE2XzU1NV9SRURfTUFTSykgPj4gRkkxNl81NTVfUkVEX1NISUZUKSAqIDB4RkYpIC8gMHgxRik7Cgl9Cn0KCnZvaWQgRExMX0NBTExDT05WCkZyZWVJbWFnZV9Db252ZXJ0TGluZTI0VG8xNl81NjUoQllURSAqdGFyZ2V0LCBCWVRFICpzb3VyY2UsIGludCB3aWR0aF9pbl9waXhlbHMpIHsKCVdPUkQgKm5ld19iaXRzID0gKFdPUkQgKil0YXJnZXQ7CgoJZm9yIChpbnQgY29scyA9IDA7IGNvbHMgPCB3aWR0aF9pbl9waXhlbHM7IGNvbHMrKykgewoJCW5ld19iaXRzW2NvbHNdID0gUkdCNTY1KHNvdXJjZVtGSV9SR0JBX0JMVUVdLCBzb3VyY2VbRklfUkdCQV9HUkVFTl0sIHNvdXJjZVtGSV9SR0JBX1JFRF0pOwoKCQlzb3VyY2UgKz0gMzsKCX0KfQoKdm9pZCBETExfQ0FMTENPTlYKRnJlZUltYWdlX0NvbnZlcnRMaW5lMzJUbzE2XzU2NShCWVRFICp0YXJnZXQsIEJZVEUgKnNvdXJjZSwgaW50IHdpZHRoX2luX3BpeGVscykgewoJV09SRCAqbmV3X2JpdHMgPSAoV09SRCAqKXRhcmdldDsKCglmb3IgKGludCBjb2xzID0gMDsgY29scyA8IHdpZHRoX2luX3BpeGVsczsgY29scysrKSB7CgkJbmV3X2JpdHNbY29sc10gPSBSR0I1NjUoc291cmNlW0ZJX1JHQkFfQkxVRV0sIHNvdXJjZVtGSV9SR0JBX0dSRUVOXSwgc291cmNlW0ZJX1JHQkFfUkVEXSk7CgoJCXNvdXJjZSArPSA0OwoJfQp9CgovLyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCi8vICAgc21hcnQgY29udmVydCBYIHRvIDE2IGJpdHMgKDU2NSkKLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQoKRklCSVRNQVAgKiBETExfQ0FMTENPTlYKRnJlZUltYWdlX0NvbnZlcnRUbzE2Qml0czU2NShGSUJJVE1BUCAqZGliKSB7CglpZighRnJlZUltYWdlX0hhc1BpeGVscyhkaWIpIHx8IChGcmVlSW1hZ2VfR2V0SW1hZ2VUeXBlKGRpYikgIT0gRklUX0JJVE1BUCkpIHJldHVybiBOVUxMOwoKCWNvbnN0IGludCB3aWR0aCA9IEZyZWVJbWFnZV9HZXRXaWR0aChkaWIpOwoJY29uc3QgaW50IGhlaWdodCA9IEZyZWVJbWFnZV9HZXRIZWlnaHQoZGliKTsKCWNvbnN0IGludCBicHAgPSBGcmVlSW1hZ2VfR2V0QlBQKGRpYik7CgoJaWYoYnBwID09IDE2KSB7CgkJaWYgKChGcmVlSW1hZ2VfR2V0UmVkTWFzayhkaWIpID09IEZJMTZfNTU1X1JFRF9NQVNLKSAmJiAoRnJlZUltYWdlX0dldEdyZWVuTWFzayhkaWIpID09IEZJMTZfNTU1X0dSRUVOX01BU0spICYmIChGcmVlSW1hZ2VfR2V0Qmx1ZU1hc2soZGliKSA9PSBGSTE2XzU1NV9CTFVFX01BU0spKSB7CgkJCS8vIFJHQiA1NTUKCQkJRklCSVRNQVAgKm5ld19kaWIgPSBGcmVlSW1hZ2VfQWxsb2NhdGUod2lkdGgsIGhlaWdodCwgMTYsIEZJMTZfNTY1X1JFRF9NQVNLLCBGSTE2XzU2NV9HUkVFTl9NQVNLLCBGSTE2XzU2NV9CTFVFX01BU0spOwoJCQlpZihuZXdfZGliID09IE5VTEwpIHsKCQkJCXJldHVybiBOVUxMOwoJCQl9CgkJCWZvciAoaW50IHJvd3MgPSAwOyByb3dzIDwgaGVpZ2h0OyByb3dzKyspIHsKCQkJCUZyZWVJbWFnZV9Db252ZXJ0TGluZTE2XzU1NV9UbzE2XzU2NShGcmVlSW1hZ2VfR2V0U2NhbkxpbmUobmV3X2RpYiwgcm93cyksIEZyZWVJbWFnZV9HZXRTY2FuTGluZShkaWIsIHJvd3MpLCB3aWR0aCk7CgkJCX0KCgkJCS8vIGNvcHkgbWV0YWRhdGEgZnJvbSBzcmMgdG8gZHN0CgkJCUZyZWVJbWFnZV9DbG9uZU1ldGFkYXRhKG5ld19kaWIsIGRpYik7CgoJCQlyZXR1cm4gbmV3X2RpYjsKCQl9IGVsc2UgewoJCQkvLyBSR0IgNTY1CgkJCXJldHVybiBGcmVlSW1hZ2VfQ2xvbmUoZGliKTsKCQl9Cgl9CgllbHNlIHsKCQkvLyBvdGhlciBicHAgY2FzZXMgPT4gY29udmVydCB0byBSR0IgNTY1CgkJRklCSVRNQVAgKm5ld19kaWIgPSBGcmVlSW1hZ2VfQWxsb2NhdGUod2lkdGgsIGhlaWdodCwgMTYsIEZJMTZfNTY1X1JFRF9NQVNLLCBGSTE2XzU2NV9HUkVFTl9NQVNLLCBGSTE2XzU2NV9CTFVFX01BU0spOwoJCWlmKG5ld19kaWIgPT0gTlVMTCkgewoJCQlyZXR1cm4gTlVMTDsKCQl9CgoJCS8vIGNvcHkgbWV0YWRhdGEgZnJvbSBzcmMgdG8gZHN0CgkJRnJlZUltYWdlX0Nsb25lTWV0YWRhdGEobmV3X2RpYiwgZGliKTsKCgkJc3dpdGNoIChicHApIHsKCQkJY2FzZSAxIDoKCQkJewoJCQkJZm9yIChpbnQgcm93cyA9IDA7IHJvd3MgPCBoZWlnaHQ7IHJvd3MrKykgewoJCQkJCUZyZWVJbWFnZV9Db252ZXJ0TGluZTFUbzE2XzU2NShGcmVlSW1hZ2VfR2V0U2NhbkxpbmUobmV3X2RpYiwgcm93cyksIEZyZWVJbWFnZV9HZXRTY2FuTGluZShkaWIsIHJvd3MpLCB3aWR0aCwgRnJlZUltYWdlX0dldFBhbGV0dGUoZGliKSk7CgkJCQl9CgoJCQkJcmV0dXJuIG5ld19kaWI7CgkJCX0KCgkJCWNhc2UgNCA6CgkJCXsKCQkJCWZvciAoaW50IHJvd3MgPSAwOyByb3dzIDwgaGVpZ2h0OyByb3dzKyspIHsKCQkJCQlGcmVlSW1hZ2VfQ29udmVydExpbmU0VG8xNl81NjUoRnJlZUltYWdlX0dldFNjYW5MaW5lKG5ld19kaWIsIHJvd3MpLCBGcmVlSW1hZ2VfR2V0U2NhbkxpbmUoZGliLCByb3dzKSwgd2lkdGgsIEZyZWVJbWFnZV9HZXRQYWxldHRlKGRpYikpOwoJCQkJfQoKCQkJCXJldHVybiBuZXdfZGliOwoJCQl9CgoJCQljYXNlIDggOgoJCQl7CgkJCQlmb3IgKGludCByb3dzID0gMDsgcm93cyA8IGhlaWdodDsgcm93cysrKSB7CgkJCQkJRnJlZUltYWdlX0NvbnZlcnRMaW5lOFRvMTZfNTY1KEZyZWVJbWFnZV9HZXRTY2FuTGluZShuZXdfZGliLCByb3dzKSwgRnJlZUltYWdlX0dldFNjYW5MaW5lKGRpYiwgcm93cyksIHdpZHRoLCBGcmVlSW1hZ2VfR2V0UGFsZXR0ZShkaWIpKTsKCQkJCX0KCgkJCQlyZXR1cm4gbmV3X2RpYjsKCQkJfQoKCQkJY2FzZSAyNCA6CgkJCXsKCQkJCWZvciAoaW50IHJvd3MgPSAwOyByb3dzIDwgaGVpZ2h0OyByb3dzKyspIHsKCQkJCQlGcmVlSW1hZ2VfQ29udmVydExpbmUyNFRvMTZfNTY1KEZyZWVJbWFnZV9HZXRTY2FuTGluZShuZXdfZGliLCByb3dzKSwgRnJlZUltYWdlX0dldFNjYW5MaW5lKGRpYiwgcm93cyksIHdpZHRoKTsKCQkJCX0KCgkJCQlyZXR1cm4gbmV3X2RpYjsKCQkJfQoKCQkJY2FzZSAzMiA6CgkJCXsKCQkJCWZvciAoaW50IHJvd3MgPSAwOyByb3dzIDwgaGVpZ2h0OyByb3dzKyspIHsKCQkJCQlGcmVlSW1hZ2VfQ29udmVydExpbmUzMlRvMTZfNTY1KEZyZWVJbWFnZV9HZXRTY2FuTGluZShuZXdfZGliLCByb3dzKSwgRnJlZUltYWdlX0dldFNjYW5MaW5lKGRpYiwgcm93cyksIHdpZHRoKTsKCQkJCX0KCgkJCQlyZXR1cm4gbmV3X2RpYjsKCQkJfQoKCQkJZGVmYXVsdCA6CgkJCQkvLyB1bnJlYWNoYWJsZSBjb2RlIC4uLgoJCQkJRnJlZUltYWdlX1VubG9hZChuZXdfZGliKTsKCQkJCWJyZWFrOwoJCX0KCX0KCglyZXR1cm4gTlVMTDsKfQo=