1 line
68 KiB
Python
1 line
68 KiB
Python
IyBDb3B5cmlnaHQgKEMpIDIwMjQgQ2V0bWl4IE/DnAojIExpY2Vuc2UgQUdQTC0zLjAgb3IgbGF0ZXIgKGh0dHA6Ly93d3cuZ251Lm9yZy9saWNlbnNlcy9hZ3BsKS4KaW1wb3J0IGFzdAppbXBvcnQgYmFzZTY0CmltcG9ydCBoZWFwcQppbXBvcnQgbG9nZ2luZwppbXBvcnQgeG1sLmV0cmVlLkVsZW1lbnRUcmVlIGFzIEVUCmZyb20gY29sbGVjdGlvbnMgaW1wb3J0IGRlZmF1bHRkaWN0Cgpmcm9tIG9kb28gaW1wb3J0IF8sIGFwaSwgZmllbGRzLCBtb2RlbHMKZnJvbSBvZG9vLmV4Y2VwdGlvbnMgaW1wb3J0IFZhbGlkYXRpb25FcnJvcgoKZnJvbSAudG9vbHMgaW1wb3J0IGdlbmVyYXRlX3JhbmRvbV9pZCwgaXNfdmFsaWRfdXJsCgpfbG9nZ2VyID0gbG9nZ2luZy5nZXRMb2dnZXIoX19uYW1lX18pCgoKIyBNYXhpbXVtIG51bWJlciBvZiByZXRyaWVzIHRvIGdlbmVyYXRlIGEgdW5pcXVlIGpldCBuYW1lCiMgVXNlZCB0byBwcmV2ZW50IGluZmluaXRlIGxvb3AKTUFYX0pFVF9OQU1FX1JFVFJJRVMgPSA1MAoKCmNsYXNzIEN4VG93ZXJKZXRUZW1wbGF0ZShtb2RlbHMuTW9kZWwpOgogICAgIiIiSmV0IFRlbXBsYXRlcyBhcmUgdGVtcGxhdGVzIHRvIGNyZWF0ZSBhbmQgbWFuYWdlIGpldHMiIiIKCiAgICBfbmFtZSA9ICJjeC50b3dlci5qZXQudGVtcGxhdGUiCiAgICBfZGVzY3JpcHRpb24gPSAiQ2V0bWl4IFRvd2VyIEpldCBUZW1wbGF0ZSIKICAgIF9pbmhlcml0ID0gWwogICAgICAgICJjeC50b3dlci5yZWZlcmVuY2UubWl4aW4iLAogICAgICAgICJjeC50b3dlci5hY2Nlc3MubWl4aW4iLAogICAgICAgICJjeC50b3dlci5hY2Nlc3Mucm9sZS5taXhpbiIsCiAgICAgICAgImN4LnRvd2VyLnZhcmlhYmxlLm1peGluIiwKICAgICAgICAibWFpbC50aHJlYWQiLAogICAgICAgICJjeC50b3dlci50YWcubWl4aW4iLAogICAgXQogICAgX29yZGVyID0gIm5hbWUgYXNjIgogICAgX21haWxfcG9zdF9hY2Nlc3MgPSAicmVhZCIKCiAgICBhY3RpdmUgPSBmaWVsZHMuQm9vbGVhbihkZWZhdWx0PVRydWUpCiAgICBpY29uID0gZmllbGRzLkltYWdlKAogICAgICAgIHN0cmluZz0iSWNvbiBpbWFnZSIsCiAgICAgICAgbWF4X3dpZHRoPTEyOCwKICAgICAgICBtYXhfaGVpZ2h0PTEyOCwKICAgICAgICBoZWxwPSJJY29uIG9mIHRoZSByZWxhdGVkIHByb2R1Y3QgdG8gbWFrZSBuYXZpZ2F0aW9uIGVhc2llci4gIgogICAgICAgICJFLmcuIERvY2tlciBsb2dvIGZvciB0aGUgRG9ja2VyIGpldCB0ZW1wbGF0ZS4iLAogICAgKQogICAgbm90ZSA9IGZpZWxkcy5UZXh0KCkKCiAgICAjIC0tLS0gQWNjZXNzLiBBZGQgcmVsYXRpb24gZm9yIG1peGluIGZpZWxkcwogICAgdXNlcl9pZHMgPSBmaWVsZHMuTWFueTJtYW55KAogICAgICAgIHJlbGF0aW9uPSJjeF90b3dlcl9qZXRfdGVtcGxhdGVfdXNlcl9yZWwiLAogICAgKQogICAgbWFuYWdlcl9pZHMgPSBmaWVsZHMuTWFueTJtYW55KAogICAgICAgIHJlbGF0aW9uPSJjeF90b3dlcl9qZXRfdGVtcGxhdGVfbWFuYWdlcl9yZWwiLAogICAgKQoKICAgICMgSmV0cwogICAgamV0X2lkcyA9IGZpZWxkcy5PbmUybWFueSgKICAgICAgICBjb21vZGVsX25hbWU9ImN4LnRvd2VyLmpldCIsCiAgICAgICAgaW52ZXJzZV9uYW1lPSJqZXRfdGVtcGxhdGVfaWQiLAogICAgICAgIHN0cmluZz0iSmV0cyIsCiAgICAgICAgY29weT1GYWxzZSwKICAgICkKICAgIGpldF9jb3VudCA9IGZpZWxkcy5JbnRlZ2VyKGNvbXB1dGU9Il9jb21wdXRlX2pldF9jb3VudCIsIHN0b3JlPUZhbHNlKQoKICAgICMgU2VydmVycwogICAgc2VydmVyX2lkcyA9IGZpZWxkcy5NYW55Mm1hbnkoCiAgICAgICAgY29tb2RlbF9uYW1lPSJjeC50b3dlci5zZXJ2ZXIiLAogICAgICAgIHJlbGF0aW9uPSJjeF90b3dlcl9qZXRfdGVtcGxhdGVfc2VydmVyX3JlbCIsCiAgICAgICAgY29sdW1uMT0iamV0X3RlbXBsYXRlX2lkIiwKICAgICAgICBjb2x1bW4yPSJzZXJ2ZXJfaWQiLAogICAgICAgIHN0cmluZz0iSW5zdGFsbGVkIG9uIFNlcnZlcnMiLAogICAgICAgIHJlYWRvbmx5PVRydWUsCiAgICAgICAgaGVscD0iVGhlc2Ugc2VydmVycyBoYXZlIHRoaXMgamV0IHRlbXBsYXRlIGluc3RhbGxlZCIsCiAgICAgICAgY29weT1GYWxzZSwKICAgICkKICAgIGxpbWl0X3Blcl9zZXJ2ZXIgPSBmaWVsZHMuSW50ZWdlcigKICAgICAgICBzdHJpbmc9IkxpbWl0IHBlciBTZXJ2ZXIiLAogICAgICAgIGhlbHA9Ik1heGltdW0gbnVtYmVyIG9mIEpldHMgdGhhdCBjYW4gYmUgbGF1bmNoZWQgb24gYSBzZXJ2ZXIuICIKICAgICAgICAiU2V0IHRvIDAgZm9yIG5vIGxpbWl0LiIsCiAgICApCiAgICBmaWxlX2lkcyA9IGZpZWxkcy5PbmUybWFueSgKICAgICAgICBjb21vZGVsX25hbWU9ImN4LnRvd2VyLmZpbGUiLAogICAgICAgIGludmVyc2VfbmFtZT0iamV0X3RlbXBsYXRlX2lkIiwKICAgICAgICBzdHJpbmc9IkZpbGVzIiwKICAgICAgICBoZWxwPSJGaWxlcyBvZiB0aGlzIGpldCB0ZW1wbGF0ZSIsCiAgICAgICAgY29weT1GYWxzZSwKICAgICkKCiAgICAjIFdpemFyZHMKICAgIHNob3dfaW5fY3JlYXRlX3dpemFyZCA9IGZpZWxkcy5Cb29sZWFuKAogICAgICAgIHN0cmluZz0iU2hvdyBpbiBXaXphcmQiLAogICAgICAgIGhlbHA9IklmIGVuYWJsZWQsIHRoZSB0ZW1wbGF0ZSB3aWxsIGJlIHNob3duICIKICAgICAgICAiaW4gdGhlIHdpemFyZCB0byBjcmVhdGUgYSBuZXcgamV0IiwKICAgICkKCiAgICAjIEZsaWdodCBQbGFucwogICAgcGxhbl9pbnN0YWxsX2lkID0gZmllbGRzLk1hbnkyb25lKAogICAgICAgIGNvbW9kZWxfbmFtZT0iY3gudG93ZXIucGxhbiIsCiAgICAgICAgc3RyaW5nPSJJbnN0YWxsYXRpb24gRmxpZ2h0IFBsYW4iLAogICAgICAgIGhlbHA9IkZsaWdodCBwbGFuIHVzZWQgdG8gaW5zdGFsbCB0aGUgdGVtcGxhdGUgZnJvbSBhIHNlcnZlciIsCiAgICApCiAgICBwbGFuX3VuaW5zdGFsbF9pZCA9IGZpZWxkcy5NYW55Mm9uZSgKICAgICAgICBjb21vZGVsX25hbWU9ImN4LnRvd2VyLnBsYW4iLAogICAgICAgIHN0cmluZz0iVW5pbnN0YWxsYXRpb24gRmxpZ2h0IFBsYW4iLAogICAgICAgIGhlbHA9IkZsaWdodCBwbGFuIHVzZWQgdG8gdW5pbnN0YWxsIHRoZSB0ZW1wbGF0ZSBmcm9tIGEgc2VydmVyIiwKICAgICkKICAgIHBsYW5fY2xvbmVfc2FtZV9zZXJ2ZXJfaWQgPSBmaWVsZHMuTWFueTJvbmUoCiAgICAgICAgY29tb2RlbF9uYW1lPSJjeC50b3dlci5wbGFuIiwKICAgICAgICBoZWxwPSJGbGlnaHQgcGxhbiB1c2VkIHRvIGNsb25lIHRoZSBqZXQgb24gdGhlIHNhbWUgc2VydmVyIiwKICAgICkKICAgIHBsYW5fY2xvbmVfZGlmZmVyZW50X3NlcnZlcl9pZCA9IGZpZWxkcy5NYW55Mm9uZSgKICAgICAgICBjb21vZGVsX25hbWU9ImN4LnRvd2VyLnBsYW4iLAogICAgICAgIGhlbHA9IkZsaWdodCBwbGFuIHVzZWQgdG8gY2xvbmUgdGhlIGpldCB0byBhIGRpZmZlcmVudCBzZXJ2ZXIiLAogICAgKQoKICAgICMgTG9ncwogICAgY29tbWFuZF9sb2dfaWRzID0gZmllbGRzLk9uZTJtYW55KAogICAgICAgIGNvbW9kZWxfbmFtZT0iY3gudG93ZXIuY29tbWFuZC5sb2ciLAogICAgICAgIGludmVyc2VfbmFtZT0iamV0X3RlbXBsYXRlX2lkIiwKICAgICAgICBjb3B5PUZhbHNlLAogICAgKQogICAgcGxhbl9sb2dfaWRzID0gZmllbGRzLk9uZTJtYW55KAogICAgICAgIGNvbW9kZWxfbmFtZT0iY3gudG93ZXIucGxhbi5sb2ciLAogICAgICAgIGludmVyc2VfbmFtZT0iamV0X3RlbXBsYXRlX2lkIiwKICAgICAgICBjb3B5PUZhbHNlLAogICAgKQoKICAgICMgU2VydmVyIGxvZ3MKICAgIHNlcnZlcl9sb2dfaWRzID0gZmllbGRzLk9uZTJtYW55KAogICAgICAgIGNvbW9kZWxfbmFtZT0iY3gudG93ZXIuc2VydmVyLmxvZyIsCiAgICAgICAgaW52ZXJzZV9uYW1lPSJqZXRfdGVtcGxhdGVfaWQiLAogICAgICAgIGNvcHk9VHJ1ZSwKICAgICkKICAgICMgU2NoZWR1bGVkIFRhc2tzCiAgICBzY2hlZHVsZWRfdGFza19pZHMgPSBmaWVsZHMuTWFueTJtYW55KAogICAgICAgIGNvbW9kZWxfbmFtZT0iY3gudG93ZXIuc2NoZWR1bGVkLnRhc2siLAogICAgICAgIHJlbGF0aW9uPSJjeF90b3dlcl9qZXRfdGVtcGxhdGVfc2NoZWR1bGVkX3Rhc2tfcmVsIiwKICAgICAgICBjb2x1bW4xPSJqZXRfdGVtcGxhdGVfaWQiLAogICAgICAgIGNvbHVtbjI9InNjaGVkdWxlZF90YXNrX2lkIiwKICAgICAgICBzdHJpbmc9IlNjaGVkdWxlZCBUYXNrcyIsCiAgICAgICAgY29weT1UcnVlLAogICAgKQoKICAgICMgQ29uZmlndXJhdGlvbiB2YXJpYWJsZXMKICAgIHZhcmlhYmxlX3ZhbHVlX2lkcyA9IGZpZWxkcy5PbmUybWFueSgKICAgICAgICBpbnZlcnNlX25hbWU9ImpldF90ZW1wbGF0ZV9pZCIsCiAgICAgICAgY29weT1UcnVlLAogICAgKQoKICAgICMgQWN0aW9ucwogICAgYWN0aW9uX2lkcyA9IGZpZWxkcy5PbmUybWFueSgKICAgICAgICBjb21vZGVsX25hbWU9ImN4LnRvd2VyLmpldC5hY3Rpb24iLAogICAgICAgIGludmVyc2VfbmFtZT0iamV0X3RlbXBsYXRlX2lkIiwKICAgICAgICBzdHJpbmc9IkxpZmVjeWNsZSBBY3Rpb25zIiwKICAgICAgICBjb3B5PVRydWUsCiAgICApCiAgICBhY3Rpb25fY3JlYXRlX2lkID0gZmllbGRzLk1hbnkyb25lKAogICAgICAgIGNvbW9kZWxfbmFtZT0iY3gudG93ZXIuamV0LmFjdGlvbiIsCiAgICAgICAgc3RyaW5nPSJDcmVhdGUgSmV0IiwKICAgICAgICBoZWxwPSJUaGUgYWN0aW9uIGlzIHVzZWQgdG8gY3JlYXRlIGEgbmV3IEpldCIsCiAgICAgICAgY29tcHV0ZT0iX2NvbXB1dGVfYm9yZGVyX2FjdGlvbnMiLAogICAgICAgIHJlYWRvbmx5PUZhbHNlLAogICAgICAgIHN0b3JlPVRydWUsCiAgICAgICAgZG9tYWluPSJbKCdzdGF0ZV9mcm9tX2lkJywgJz0nLCBGYWxzZSksICIKICAgICAgICAiKCdzdGF0ZV90b19pZCcsICchPScsIEZhbHNlKSwiCiAgICAgICAgIiAoJ2pldF90ZW1wbGF0ZV9pZCcsICc9JywgaWQpXSIsCiAgICAgICAgY29weT1GYWxzZSwKICAgICkKICAgIGFjdGlvbl9kZXN0cm95X2lkID0gZmllbGRzLk1hbnkyb25lKAogICAgICAgIGNvbW9kZWxfbmFtZT0iY3gudG93ZXIuamV0LmFjdGlvbiIsCiAgICAgICAgc3RyaW5nPSJEZXN0cm95IEpldCIsCiAgICAgICAgY29tcHV0ZT0iX2NvbXB1dGVfYm9yZGVyX2FjdGlvbnMiLAogICAgICAgIHJlYWRvbmx5PUZhbHNlLAogICAgICAgIHN0b3JlPVRydWUsCiAgICAgICAgaGVscD0iVGhlIGFjdGlvbiBpcyB1c2VkIHRvIGRlc3Ryb3kgYSBKZXQiLAogICAgICAgIGRvbWFpbj0iWygnc3RhdGVfdG9faWQnLCAnPScsIEZhbHNlKSwgKCdqZXRfdGVtcGxhdGVfaWQnLCAnPScsIGlkKV0iLAogICAgICAgIGNvcHk9RmFsc2UsCiAgICApCgogICAgIyBEZXBlbmRlbmNpZXMKICAgIHRlbXBsYXRlX3JlcXVpcmVzX2lkcyA9IGZpZWxkcy5PbmUybWFueSgKICAgICAgICBjb21vZGVsX25hbWU9ImN4LnRvd2VyLmpldC50ZW1wbGF0ZS5kZXBlbmRlbmN5IiwKICAgICAgICBpbnZlcnNlX25hbWU9InRlbXBsYXRlX2lkIiwKICAgICAgICBzdHJpbmc9IlJlcXVpcmVzIiwKICAgICAgICBoZWxwPSJEZWZpbmUgb3RoZXIgdGVtcGxhdGVzIHRoYXQgbXVzdCBiZSBpbiBzcGVjaWZpYyIKICAgICAgICAiIHN0YXRlcyBmb3IgdGhpcyB0ZW1wbGF0ZSB0byBmdW5jdGlvbiIsCiAgICAgICAgY29weT1UcnVlLAogICAgICAgIGdyb3Vwcz0iY2V0bWl4X3Rvd2VyX3NlcnZlci5ncm91cF9tYW5hZ2VyIiwKICAgICkKICAgIHRlbXBsYXRlX3JlcXVpcmVkX2J5X2lkcyA9IGZpZWxkcy5PbmUybWFueSgKICAgICAgICBjb21vZGVsX25hbWU9ImN4LnRvd2VyLmpldC50ZW1wbGF0ZS5kZXBlbmRlbmN5IiwKICAgICAgICBpbnZlcnNlX25hbWU9InRlbXBsYXRlX3JlcXVpcmVkX2lkIiwKICAgICAgICBzdHJpbmc9IlJlcXVpcmVkIGJ5IiwKICAgICAgICBoZWxwPSJEZWZpbmUgb3RoZXIgdGVtcGxhdGVzIHRoYXQgcmVxdWlyZSB0aGlzIHRlbXBsYXRlIgogICAgICAgICIgdG8gYmUgaW4gYSBzcGVjaWZpYyIKICAgICAgICAiIHN0YXRlIHRvIGZ1bmN0aW9uIiwKICAgICAgICBncm91cHM9ImNldG1peF90b3dlcl9zZXJ2ZXIuZ3JvdXBfbWFuYWdlciIsCiAgICApCgogICAgIyBJbnN0YWxsYXRpb24KICAgIGluc3RhbGxfaWRzID0gZmllbGRzLk9uZTJtYW55KAogICAgICAgIGNvbW9kZWxfbmFtZT0iY3gudG93ZXIuamV0LnRlbXBsYXRlLmluc3RhbGwubGluZSIsCiAgICAgICAgaW52ZXJzZV9uYW1lPSJqZXRfdGVtcGxhdGVfaWQiLAogICAgICAgIHN0cmluZz0iSW5zdGFsbGF0aW9ucyIsCiAgICAgICAgaGVscD0iSW5zdGFsbGF0aW9ucyBvZiB0aGUgdGVtcGxhdGUiLAogICAgICAgIGF1dG9fam9pbj1UcnVlLAogICAgICAgIGNvcHk9RmFsc2UsCiAgICAgICAgZ3JvdXBzPSJjZXRtaXhfdG93ZXJfc2VydmVyLmdyb3VwX21hbmFnZXIiLAogICAgICAgIHJlYWRvbmx5PVRydWUsCiAgICApCgogICAgIyBXYXlwb2ludHMKICAgIHdheXBvaW50X3RlbXBsYXRlX2lkcyA9IGZpZWxkcy5PbmUybWFueSgKICAgICAgICBjb21vZGVsX25hbWU9ImN4LnRvd2VyLmpldC53YXlwb2ludC50ZW1wbGF0ZSIsCiAgICAgICAgaW52ZXJzZV9uYW1lPSJqZXRfdGVtcGxhdGVfaWQiLAogICAgICAgIHN0cmluZz0iV2F5cG9pbnRzIiwKICAgICAgICBoZWxwPSJXYXlwb2ludHMgb2YgdGhlIHRlbXBsYXRlIiwKICAgICAgICBjb3B5PVRydWUsCiAgICApCgogICAgIyBEZXBlbmRlbmN5IEdyYXBoCiAgICAjIE9kb28gYmxvY2tzIFNWRyBpbWFnZXMgaW4gZmllbGRzLkJpbmFyeSwKICAgICMgc28gd2UgdXNlIGZpZWxkcy5DaGFyIHRvIHN0b3JlIHRoZSBTVkcgY29udGVudAogICAgIyBodHRwczovL2dpdGh1Yi5jb20vb2Rvby9vZG9vL2Jsb2IvYzI3ZDk3OGFkZTliY2JlYTA1NjkzM2Q4ZmI4YjVhOTI0ZTk4M2JkZS9vZG9vL2ZpZWxkcy5weSNMMjMyMQogICAgZGVwZW5kZW5jeV9ncmFwaF9zdmcgPSBmaWVsZHMuQ2hhcigKICAgICAgICBjb21wdXRlPSJfY29tcHV0ZV9kZXBlbmRlbmN5X2dyYXBoX3N2ZyIsCiAgICAgICAgc3RvcmU9VHJ1ZSwKICAgICAgICByZWN1cnNpdmU9VHJ1ZSwKICAgICAgICBjb3B5PUZhbHNlLAogICAgICAgIGhlbHA9IlNWRyBpbWFnZSBjb250ZW50IG9mIHRoZSBkZXBlbmRlbmN5IGdyYXBoIG9mIHRoZSB0ZW1wbGF0ZSIsCiAgICApCiAgICBkZXBlbmRlbmN5X2dyYXBoX2ltYWdlID0gZmllbGRzLkJpbmFyeSgKICAgICAgICBzdHJpbmc9IkRlcGVuZGVuY3kgR3JhcGgiLAogICAgICAgIGNvbXB1dGU9Il9jb21wdXRlX2RlcGVuZGVuY3lfZ3JhcGhfaW1hZ2UiLAogICAgICAgIGNvbXB1dGVfc3Vkbz1UcnVlLAogICAgICAgIGhlbHA9IlNWRyBpbWFnZSBvZiB0aGUgZGVwZW5kZW5jeSBncmFwaCBvZiB0aGUgdGVtcGxhdGUiLAogICAgKQoKICAgICMgKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKwogICAgIyAgIENvbXB1dGUgZnVuY3Rpb25zCiAgICAjICsrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysKCiAgICBAYXBpLmRlcGVuZHMoImpldF9pZHMiKQogICAgZGVmIF9jb21wdXRlX2pldF9jb3VudChzZWxmKToKICAgICAgICAiIiJDb21wdXRlIHRoZSBudW1iZXIgb2YgamV0cyBmb3IgZWFjaCB0ZW1wbGF0ZS4iIiIKICAgICAgICBmb3IgdGVtcGxhdGUgaW4gc2VsZjoKICAgICAgICAgICAgdGVtcGxhdGUuamV0X2NvdW50ID0gbGVuKHRlbXBsYXRlLmpldF9pZHMpCgogICAgQGFwaS5kZXBlbmRzKAogICAgICAgICJhY3Rpb25faWRzIiwKICAgICAgICAiYWN0aW9uX2lkcy5zdGF0ZV9mcm9tX2lkIiwKICAgICAgICAiYWN0aW9uX2lkcy5zdGF0ZV90b19pZCIsCiAgICAgICAgImFjdGlvbl9pZHMucHJpb3JpdHkiLAogICAgKQogICAgZGVmIF9jb21wdXRlX2JvcmRlcl9hY3Rpb25zKHNlbGYpOgogICAgICAgICIiIkNvbXB1dGUgdGhlICdDcmVhdGUgSmV0JyBhbmQgJ0Rlc3Ryb3kgSmV0JyBhY3Rpb25zIiIiCiAgICAgICAgZm9yIHRlbXBsYXRlIGluIHNlbGY6CiAgICAgICAgICAgICMgSWYgbm8gaW5pdGlhbCBzdGF0ZSwgYWRkIHRoZSBvbmUgYXV0b21hdGljYWxseQogICAgICAgICAgICBpZiBub3QgdGVtcGxhdGUuYWN0aW9uX2NyZWF0ZV9pZDoKICAgICAgICAgICAgICAgICMgSGFzIG5vIGluaXRpYWwgc3RhdGUgYW5kIGhhcyBhIGZpbmFsIHN0YXRlCiAgICAgICAgICAgICAgICBzdWl0YWJsZV9hY3Rpb25zID0gdGVtcGxhdGUuYWN0aW9uX2lkcy5maWx0ZXJlZCgKICAgICAgICAgICAgICAgICAgICBsYW1iZGEgYTogbm90IGEuc3RhdGVfZnJvbV9pZCBhbmQgYS5zdGF0ZV90b19pZAogICAgICAgICAgICAgICAgKS5zb3J0ZWQoInByaW9yaXR5IikKICAgICAgICAgICAgICAgICMgVGFrZSB0aGUgZmlyc3Qgb25lIChsb3dlc3QgcHJpb3JpdHkgPSBoaWdoZXN0IHByaW9yaXR5KQogICAgICAgICAgICAgICAgaWYgc3VpdGFibGVfYWN0aW9uczoKICAgICAgICAgICAgICAgICAgICB0ZW1wbGF0ZS5hY3Rpb25fY3JlYXRlX2lkID0gc3VpdGFibGVfYWN0aW9uc1swXQoKICAgICAgICAgICAgIyBJZiAiQ3JlYXRlIiBhY3Rpb24gaGFzIGFuIGluaXRpYWwgc3RhdGUKICAgICAgICAgICAgIyBvciBkb2VzIG5vdCBoYXZlIGEgZmluYWwgc3RhdGUKICAgICAgICAgICAgIyBpdCBjYW5ub3QgYmUgdXNlZCB0byBjcmVhdGUgYSBuZXcgSmV0CiAgICAgICAgICAgIGVsaWYgKAogICAgICAgICAgICAgICAgdGVtcGxhdGUuYWN0aW9uX2NyZWF0ZV9pZC5zdGF0ZV9mcm9tX2lkCiAgICAgICAgICAgICAgICBvciBub3QgdGVtcGxhdGUuYWN0aW9uX2NyZWF0ZV9pZC5zdGF0ZV90b19pZAogICAgICAgICAgICApOgogICAgICAgICAgICAgICAgdGVtcGxhdGUuYWN0aW9uX2NyZWF0ZV9pZCA9IEZhbHNlCgogICAgICAgICAgICBpZiBub3QgdGVtcGxhdGUuYWN0aW9uX2Rlc3Ryb3lfaWQ6CiAgICAgICAgICAgICAgICAjIEhhcyBubyBmaW5hbCBzdGF0ZQogICAgICAgICAgICAgICAgc3VpdGFibGVfYWN0aW9ucyA9IHRlbXBsYXRlLmFjdGlvbl9pZHMuZmlsdGVyZWQoCiAgICAgICAgICAgICAgICAgICAgbGFtYmRhIGE6IG5vdCBhLnN0YXRlX3RvX2lkCiAgICAgICAgICAgICAgICApLnNvcnRlZCgicHJpb3JpdHkiKQogICAgICAgICAgICAgICAgIyBUYWtlIHRoZSBmaXJzdCBvbmUgKGxvd2VzdCBwcmlvcml0eSA9IGhpZ2hlc3QgcHJpb3JpdHkpCiAgICAgICAgICAgICAgICBpZiBzdWl0YWJsZV9hY3Rpb25zOgogICAgICAgICAgICAgICAgICAgIHRlbXBsYXRlLmFjdGlvbl9kZXN0cm95X2lkID0gc3VpdGFibGVfYWN0aW9uc1swXQoKICAgICAgICAgICAgIyBJZiAiRGVzdHJveSIgYWN0aW9uIGhhcyBhIGZpbmFsIHN0YXRlCiAgICAgICAgICAgICMgaXQgY2Fubm90IGJlIHVzZWQgdG8gZGVzdHJveSBhIEpldAogICAgICAgICAgICBlbGlmIHRlbXBsYXRlLmFjdGlvbl9kZXN0cm95X2lkLnN0YXRlX3RvX2lkOgogICAgICAgICAgICAgICAgdGVtcGxhdGUuYWN0aW9uX2Rlc3Ryb3lfaWQgPSBGYWxzZQoKICAgIEBhcGkuZGVwZW5kcygKICAgICAgICAidGVtcGxhdGVfcmVxdWlyZXNfaWRzIiwKICAgICAgICAidGVtcGxhdGVfcmVxdWlyZXNfaWRzLnN0YXRlX3JlcXVpcmVkX2lkIiwKICAgICAgICAidGVtcGxhdGVfcmVxdWlyZXNfaWRzLnRlbXBsYXRlX3JlcXVpcmVkX2lkLmRlcGVuZGVuY3lfZ3JhcGhfaW1hZ2UiLAogICAgKQogICAgZGVmIF9jb21wdXRlX2RlcGVuZGVuY3lfZ3JhcGhfc3ZnKHNlbGYpOgogICAgICAgICIiIkNvbXB1dGUgZGVwZW5kZW5jeSBncmFwaCBpbWFnZSB1c2luZyBTVkcgZ2VuZXJhdGlvbiIiIgogICAgICAgIGZvciB0ZW1wbGF0ZSBpbiBzZWxmOgogICAgICAgICAgICB0cnk6CiAgICAgICAgICAgICAgICBncmFwaF9kYXRhID0gdGVtcGxhdGUuX2J1aWxkX2RlcGVuZGVuY3lfZ3JhcGgoKQogICAgICAgICAgICAgICAgc3ZnX2NvbnRlbnQgPSB0ZW1wbGF0ZS5fZ2VuZXJhdGVfc3ZnX2dyYXBoKGdyYXBoX2RhdGEpCiAgICAgICAgICAgICAgICB0ZW1wbGF0ZS5kZXBlbmRlbmN5X2dyYXBoX3N2ZyA9IHN2Z19jb250ZW50CiAgICAgICAgICAgIGV4Y2VwdCBFeGNlcHRpb24gYXMgZToKICAgICAgICAgICAgICAgIF9sb2dnZXIuZXJyb3IoCiAgICAgICAgICAgICAgICAgICAgZiJFcnJvciBnZW5lcmF0aW5nIGRlcGVuZGVuY3kgZ3JhcGggIgogICAgICAgICAgICAgICAgICAgIGYiZm9yIHRlbXBsYXRlIHt0ZW1wbGF0ZS5uYW1lfToge2V9IgogICAgICAgICAgICAgICAgKQogICAgICAgICAgICAgICAgdGVtcGxhdGUuZGVwZW5kZW5jeV9ncmFwaF9zdmcgPSBGYWxzZQoKICAgIEBhcGkuZGVwZW5kcygiZGVwZW5kZW5jeV9ncmFwaF9zdmciKQogICAgZGVmIF9jb21wdXRlX2RlcGVuZGVuY3lfZ3JhcGhfaW1hZ2Uoc2VsZik6CiAgICAgICAgZm9yIHRlbXBsYXRlIGluIHNlbGY6CiAgICAgICAgICAgIHRlbXBsYXRlLmRlcGVuZGVuY3lfZ3JhcGhfaW1hZ2UgPSB0ZW1wbGF0ZS5kZXBlbmRlbmN5X2dyYXBoX3N2ZwoKICAgICMgKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKwogICAgIyAgIE9STSBtZXRob2RzCiAgICAjICsrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysKICAgIGRlZiB1bmxpbmsoc2VsZik6CiAgICAgICAgIiIiCiAgICAgICAgVW5saW5rIGFsbCByZWxhdGVkIGZpbGVzCiAgICAgICAgIiIiCgogICAgICAgICMgRG9uJ3QgYWxsb3cgdG8gdW5saW5rIGEgdGVtcGxhdGUgaWYgaXQgaGFzIGFueSBqZXRzCiAgICAgICAgIyBvciBpcyBpbnN0YWxsZWQgb24gYW55IHNlcnZlcgogICAgICAgIHRlbXBsYXRlc193aXRoX2pldHMgPSBzZWxmLmZpbHRlcmVkKGxhbWJkYSB0OiB0LmpldF9pZHMpCiAgICAgICAgaWYgdGVtcGxhdGVzX3dpdGhfamV0czoKICAgICAgICAgICAgcmFpc2UgVmFsaWRhdGlvbkVycm9yKAogICAgICAgICAgICAgICAgXygKICAgICAgICAgICAgICAgICAgICAiRm9sbG93aW5nIHRlbXBsYXRlcyBjYW5ub3QgYmUgZGVsZXRlZCAiCiAgICAgICAgICAgICAgICAgICAgImFzIHRoZXkgc3RpbGwgaGF2ZSBqZXRzOiAlcyIsCiAgICAgICAgICAgICAgICAgICAgdGVtcGxhdGVzX3dpdGhfamV0cy5tYXBwZWQoImRpc3BsYXlfbmFtZSIpLAogICAgICAgICAgICAgICAgKQogICAgICAgICAgICApCiAgICAgICAgdGVtcGxhdGVzX3dpdGhfaW5zdGFsbGVkX3NlcnZlcnMgPSBzZWxmLmZpbHRlcmVkKGxhbWJkYSB0OiB0LnNlcnZlcl9pZHMpCiAgICAgICAgaWYgdGVtcGxhdGVzX3dpdGhfaW5zdGFsbGVkX3NlcnZlcnM6CiAgICAgICAgICAgIHJhaXNlIFZhbGlkYXRpb25FcnJvcigKICAgICAgICAgICAgICAgIF8oCiAgICAgICAgICAgICAgICAgICAgIkZvbGxvd2luZyB0ZW1wbGF0ZXMgY2Fubm90IGJlIGRlbGV0ZWQgIgogICAgICAgICAgICAgICAgICAgICJhcyB0aGV5IGFyZSBpbnN0YWxsZWQgb24gc2VydmVyczogJXMiLAogICAgICAgICAgICAgICAgICAgICIsIi5qb2luKHRlbXBsYXRlc193aXRoX2luc3RhbGxlZF9zZXJ2ZXJzLm1hcHBlZCgiZGlzcGxheV9uYW1lIikpLAogICAgICAgICAgICAgICAgKQogICAgICAgICAgICApCgogICAgICAgIGZpbGVzID0gc2VsZi5maWxlX2lkcwogICAgICAgIHJlcyA9IHN1cGVyKCkudW5saW5rKCkKCiAgICAgICAgIyBVbmxpbmsgZmlsZXMgb25seSBhZnRlciB0aGUgcmVjb3JkcyBhcmUgZGVsZXRlZAogICAgICAgICMgVGhpcyBpcyBkb25lIHRvIGF2b2lkIGRlbGV0aW5nIHRoZSBmaWxlcyB3aGlsZQogICAgICAgICMgdGhlICd1bmxpbmsnIG1ldGhvZCBmYWlscyBkdWUgdG8gc29tZSByZWFzb24uCiAgICAgICAgaWYgZmlsZXM6CiAgICAgICAgICAgIGZpbGVzLnVubGluaygpCiAgICAgICAgcmV0dXJuIHJlcwoKICAgICMgKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKwogICAgIyAgIE9kb28gQWN0aW9ucwogICAgIyArKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrCgogICAgZGVmIGFjdGlvbl9pbnN0YWxsX29uX3NlcnZlcnMoc2VsZik6CiAgICAgICAgIiIiQWN0aW9uIHRvIGluc3RhbGwgdGhlIEpldCBUZW1wbGF0ZSBvbiB0aGUgc2VsZWN0ZWQgc2VydmVycy4iIiIKICAgICAgICBzZWxmLmVuc3VyZV9vbmUoKQogICAgICAgICMgT3BlbiB0aGUgd2l6YXJkIHRvIGluc3RhbGwgdGhlIHRlbXBsYXRlIG9uIHRoZSBzZWxlY3RlZCBzZXJ2ZXJzCiAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgInR5cGUiOiAiaXIuYWN0aW9ucy5hY3Rfd2luZG93IiwKICAgICAgICAgICAgIm5hbWUiOiBfKCJJbnN0YWxsIG9uIFNlcnZlcnMiKSwKICAgICAgICAgICAgInJlc19tb2RlbCI6ICJjeC50b3dlci5qZXQudGVtcGxhdGUuaW5zdGFsbC53aXoiLAogICAgICAgICAgICAidmlld19tb2RlIjogImZvcm0iLAogICAgICAgICAgICAidGFyZ2V0IjogIm5ldyIsCiAgICAgICAgICAgICJjb250ZXh0IjogewogICAgICAgICAgICAgICAgImRlZmF1bHRfamV0X3RlbXBsYXRlX2lkIjogc2VsZi5pZCwKICAgICAgICAgICAgfSwKICAgICAgICB9CgogICAgZGVmIGFjdGlvbl91bmluc3RhbGxfZnJvbV9zZXJ2ZXIoc2VsZiwgc2VydmVyPU5vbmUpOgogICAgICAgICIiIkFjdGlvbiB0byB1bmluc3RhbGwgdGhlIEpldCBUZW1wbGF0ZSBmcm9tIHRoZSBzZWxlY3RlZCBzZXJ2ZXJzLiIiIgogICAgICAgIHNlbGYuZW5zdXJlX29uZSgpCiAgICAgICAgIyBPcGVuIHRoZSB3aXphcmQgdG8gdW5pbnN0YWxsIHRoZSB0ZW1wbGF0ZSBmcm9tIHRoZSBzZWxlY3RlZCBzZXJ2ZXJzCiAgICAgICAgaWYgbm90IHNlcnZlcjoKICAgICAgICAgICAgc2VydmVyX2lkID0gc2VsZi5lbnYuY29udGV4dC5nZXQoInNlcnZlcl9pZCIpCiAgICAgICAgICAgIHNlcnZlciA9IHNlbGYuZW52WyJjeC50b3dlci5zZXJ2ZXIiXS5icm93c2Uoc2VydmVyX2lkKQogICAgICAgIGlmIG5vdCBzZXJ2ZXI6CiAgICAgICAgICAgIHJhaXNlIFZhbGlkYXRpb25FcnJvcihfKCJObyBzZXJ2ZXIgc2VsZWN0ZWQiKSkKICAgICAgICByZXR1cm4gc2VsZi51bmluc3RhbGxfZnJvbV9zZXJ2ZXJzKHNlcnZlcnM9c2VydmVyKQoKICAgIGRlZiBhY3Rpb25fb3Blbl9jb21tYW5kX2xvZ3Moc2VsZik6CiAgICAgICAgIiIiCiAgICAgICAgT3BlbiBjdXJyZW50IHNlcnZlciBjb21tYW5kIGxvZyByZWNvcmRzCiAgICAgICAgIiIiCiAgICAgICAgc2VsZi5lbnN1cmVfb25lKCkKICAgICAgICBhY3Rpb24gPSBzZWxmLmVudlsiaXIuYWN0aW9ucy5hY3Rpb25zIl0uX2Zvcl94bWxfaWQoCiAgICAgICAgICAgICJjZXRtaXhfdG93ZXJfc2VydmVyLmFjdGlvbl9jeF90b3dlcl9jb21tYW5kX2xvZyIKICAgICAgICApCiAgICAgICAgYWN0aW9uWyJkb21haW4iXSA9IFsoImpldF90ZW1wbGF0ZV9pZCIsICI9Iiwgc2VsZi5pZCldICAjIHB5bGludDogZGlzYWJsZT1uby1tZW1iZXIKICAgICAgICByZXR1cm4gYWN0aW9uCgogICAgZGVmIGFjdGlvbl9vcGVuX3BsYW5fbG9ncyhzZWxmKToKICAgICAgICAiIiIKICAgICAgICBPcGVuIGN1cnJlbnQgc2VydmVyIGZsaWdodHBsYW4gbG9nIHJlY29yZHMKICAgICAgICAiIiIKICAgICAgICBzZWxmLmVuc3VyZV9vbmUoKQogICAgICAgIGFjdGlvbiA9IHNlbGYuZW52WyJpci5hY3Rpb25zLmFjdGlvbnMiXS5fZm9yX3htbF9pZCgKICAgICAgICAgICAgImNldG1peF90b3dlcl9zZXJ2ZXIuYWN0aW9uX2N4X3Rvd2VyX3BsYW5fbG9nIgogICAgICAgICkKICAgICAgICBhY3Rpb25bImRvbWFpbiJdID0gWygiamV0X3RlbXBsYXRlX2lkIiwgIj0iLCBzZWxmLmlkKV0gICMgcHlsaW50OiBkaXNhYmxlPW5vLW1lbWJlcgogICAgICAgIHJldHVybiBhY3Rpb24KCiAgICBkZWYgYWN0aW9uX29wZW5fZmlsZXMoc2VsZik6CiAgICAgICAgIiIiCiAgICAgICAgT3BlbiBmaWxlcyBvZiB0aGUgY3VycmVudCBzZXJ2ZXIKICAgICAgICAiIiIKICAgICAgICBzZWxmLmVuc3VyZV9vbmUoKQogICAgICAgIGFjdGlvbiA9IHNlbGYuZW52WyJpci5hY3Rpb25zLmFjdGlvbnMiXS5fZm9yX3htbF9pZCgKICAgICAgICAgICAgImNldG1peF90b3dlcl9zZXJ2ZXIuY3hfdG93ZXJfZmlsZV9hY3Rpb24iCiAgICAgICAgKQogICAgICAgIGFjdGlvblsiZG9tYWluIl0gPSBbKCJqZXRfdGVtcGxhdGVfaWQiLCAiPSIsIHNlbGYuaWQpXSAgIyBweWxpbnQ6IGRpc2FibGU9bm8tbWVtYmVyCgogICAgICAgIGNvbnRleHQgPSBzZWxmLl9jb250ZXh0LmNvcHkoKQogICAgICAgIGlmICJjb250ZXh0IiBpbiBhY3Rpb24gYW5kIGlzaW5zdGFuY2UoKGFjdGlvblsiY29udGV4dCJdKSwgc3RyKToKICAgICAgICAgICAgY29udGV4dC51cGRhdGUoYXN0LmxpdGVyYWxfZXZhbChhY3Rpb25bImNvbnRleHQiXSkpCiAgICAgICAgZWxzZToKICAgICAgICAgICAgY29udGV4dC51cGRhdGUoYWN0aW9uLmdldCgiY29udGV4dCIsIHt9KSkKCiAgICAgICAgY29udGV4dC51cGRhdGUoCiAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgICJkZWZhdWx0X2pldF90ZW1wbGF0ZV9pZCI6IHNlbGYuaWQsICAjIHB5bGludDogZGlzYWJsZT1uby1tZW1iZXIKICAgICAgICAgICAgICAgICJzZWFyY2hfZGVmYXVsdF9ncm91cF9ieV9qZXRfaWQiOiAxLAogICAgICAgICAgICB9CiAgICAgICAgKQogICAgICAgIGFjdGlvblsiY29udGV4dCJdID0gY29udGV4dAogICAgICAgIHJldHVybiBhY3Rpb24KCiAgICBkZWYgYWN0aW9uX29wZW5famV0cyhzZWxmKToKICAgICAgICAiIiIKICAgICAgICBPcGVuIGpldHMgb2YgdGhlIGN1cnJlbnQgamV0IHRlbXBsYXRlCiAgICAgICAgIiIiCiAgICAgICAgc2VsZi5lbnN1cmVfb25lKCkKICAgICAgICBhY3Rpb24gPSBzZWxmLmVudlsiaXIuYWN0aW9ucy5hY3Rpb25zIl0uX2Zvcl94bWxfaWQoCiAgICAgICAgICAgICJjZXRtaXhfdG93ZXJfc2VydmVyLmN4X3Rvd2VyX2pldF9hY3Rpb24iCiAgICAgICAgKQogICAgICAgIGNvbnRleHQgPSBzZWxmLl9jb250ZXh0LmNvcHkoKQogICAgICAgIGlmICJjb250ZXh0IiBpbiBhY3Rpb24gYW5kIGlzaW5zdGFuY2UoKGFjdGlvblsiY29udGV4dCJdKSwgc3RyKToKICAgICAgICAgICAgY29udGV4dC51cGRhdGUoYXN0LmxpdGVyYWxfZXZhbChhY3Rpb25bImNvbnRleHQiXSkpCiAgICAgICAgZWxzZToKICAgICAgICAgICAgY29udGV4dC51cGRhdGUoYWN0aW9uLmdldCgiY29udGV4dCIsIHt9KSkKCiAgICAgICAgY29udGV4dC51cGRhdGUoCiAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgICJkZWZhdWx0X2pldF90ZW1wbGF0ZV9pZCI6IHNlbGYuaWQsICAjIHB5bGludDogZGlzYWJsZT1uby1tZW1iZXIKICAgICAgICAgICAgICAgICJncm91cF9ieSI6ICJzZXJ2ZXJfaWQiLAogICAgICAgICAgICB9CiAgICAgICAgKQogICAgICAgIGFjdGlvblsiZG9tYWluIl0gPSBbKCJqZXRfdGVtcGxhdGVfaWQiLCAiPSIsIHNlbGYuaWQpXSAgIyBweWxpbnQ6IGRpc2FibGU9bm8tbWVtYmVyCiAgICAgICAgYWN0aW9uWyJjb250ZXh0Il0gPSBjb250ZXh0CiAgICAgICAgcmV0dXJuIGFjdGlvbgoKICAgIGRlZiBhY3Rpb25fbmV3X2pldChzZWxmKToKICAgICAgICAiIiIKICAgICAgICBSZXR1cm5zIHdpemFyZCBhY3Rpb24gdG8gbGF1bmNoIGEgamV0CiAgICAgICAgIiIiCiAgICAgICAgY29udGV4dCA9IHNlbGYuZW52LmNvbnRleHQuY29weSgpCiAgICAgICAgY29udGV4dC51cGRhdGUoCiAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgICJkZWZhdWx0X2pldF90ZW1wbGF0ZV9pZCI6IHNlbGYuaWQKICAgICAgICAgICAgICAgIGlmIHNlbGYuc2hvd19pbl9jcmVhdGVfd2l6YXJkCiAgICAgICAgICAgICAgICBlbHNlIEZhbHNlLAogICAgICAgICAgICB9CiAgICAgICAgKQogICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICJ0eXBlIjogImlyLmFjdGlvbnMuYWN0X3dpbmRvdyIsCiAgICAgICAgICAgICJuYW1lIjogXygiTGF1bmNoIE5ldyBKZXQiKSwKICAgICAgICAgICAgInJlc19tb2RlbCI6ICJjeC50b3dlci5qZXQuY3JlYXRlLndpemFyZCIsCiAgICAgICAgICAgICJ2aWV3X21vZGUiOiAiZm9ybSIsCiAgICAgICAgICAgICJ0YXJnZXQiOiAibmV3IiwKICAgICAgICAgICAgImNvbnRleHQiOiBjb250ZXh0LAogICAgICAgIH0KCiAgICAjICsrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysKICAgICMgIEdlbmVyYWwgZnVuY3Rpb25zCiAgICAjICsrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysKCiAgICBkZWYgZ2V0X3ZhcmlhYmxlX3ZhbHVlKHNlbGYsIHZhcmlhYmxlX3JlZmVyZW5jZSwgbm9fZmFsbGJhY2s9RmFsc2UpOgogICAgICAgICIiIgogICAgICAgIFJldHVybiB0aGUgdmFsdWUgb2YgYSB2YXJpYWJsZSBmb3IgdGhlIGN1cnJlbnQgamV0LgogICAgICAgIE5COiB0aGlzIGZ1bmN0aW9uIGZvbGxvd3MgdGhlIHZhbHVlIGFwcGxpY2F0aW9uIG9yZGVyLgogICAgICAgIEpldCBUZW1wbGF0ZS0+U2VydmVyLT5HbG9iYWwKICAgICAgICBBcmdzOgogICAgICAgICAgICB2YXJpYWJsZV9yZWZlcmVuY2UgKENoYXIpOiBUaGUgcmVmZXJlbmNlIG9mIHRoZSB2YXJpYWJsZQogICAgICAgICAgICAgICAgdG8gZ2V0IHRoZSB2YWx1ZSBmb3IKICAgICAgICAgICAgbm9fZmFsbGJhY2sgKGJvb2wpOiBJZiBUcnVlLCB3aWxsIHJldHVybiBjdXJyZW50IHJlY29yZCB2YWx1ZQogICAgICAgICAgICAgICAgd2l0aG91dCBjaGVja2luZyBmYWxsYmFjayB2YWx1ZXMuCgoKICAgICAgICBSZXR1cm5zOgogICAgICAgICAgICBzdHI6IFRoZSB2YWx1ZSBvZiB0aGUgdmFyaWFibGUgZm9yIHRoZSBjdXJyZW50IHJlY29yZCBvciBOb25lCiAgICAgICAgIiIiCiAgICAgICAgc2VsZi5lbnN1cmVfb25lKCkKICAgICAgICBpZiBub19mYWxsYmFjazoKICAgICAgICAgICAgcmV0dXJuIHN1cGVyKCkuZ2V0X3ZhcmlhYmxlX3ZhbHVlKHZhcmlhYmxlX3JlZmVyZW5jZSwgbm9fZmFsbGJhY2spCiAgICAgICAgdmFyaWFibGUgPSBzZWxmLmVudlsiY3gudG93ZXIudmFyaWFibGUiXS5nZXRfYnlfcmVmZXJlbmNlKHZhcmlhYmxlX3JlZmVyZW5jZSkKICAgICAgICBpZiBub3QgdmFyaWFibGU6CiAgICAgICAgICAgIHJldHVybiBOb25lCiAgICAgICAgdmFsdWVzID0gdmFyaWFibGUuX2dldF92YXJpYWJsZV92YWx1ZXNfYnlfcmVmZXJlbmNlcygKICAgICAgICAgICAgdmFyaWFibGVfcmVmZXJlbmNlcz1bdmFyaWFibGVfcmVmZXJlbmNlXSwgamV0X3RlbXBsYXRlPXNlbGYKICAgICAgICApCiAgICAgICAgcmV0dXJuIHZhbHVlc1t2YXJpYWJsZV9yZWZlcmVuY2VdCgogICAgIyArKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrCiAgICAjICAgVGVtcGxhdGUgQWN0aW9ucwogICAgIyArKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrCgogICAgZGVmIF9nZXRfYWN0aW9uX3BhdGgoc2VsZiwgc3RhdGVfZnJvbT1Ob25lLCBzdGF0ZV90bz1Ob25lKToKICAgICAgICAiIiJSZXR1cm4gdGhlIG9yZGVyIG9mIGFjdGlvbnMgdGhhdCBsZWFkIGZyb20gb25lIHN0YXRlIHRvIGFub3RoZXIuCiAgICAgICAgSWYgdGhlIGluaXRpYWwgc3RhdGUgaXMgbm90IHByb3ZpZGVkLCBtdXN0IHN0YXJ0IHdpdGggIkNyZWF0ZSBBY3Rpb24iLgogICAgICAgIElmIHRoZSBmaW5hbCBzdGF0ZSBpcyBub3QgcHJvdmlkZWQsIG11c3QgZW5kIHdpdGggIkRlc3Ryb3kgQWN0aW9uIi4KCiAgICAgICAgQXJnczoKICAgICAgICAgICAgc3RhdGVfZnJvbSAoY3gudG93ZXIuamV0LnN0YXRlKCkpOiBTdGF0ZSB0byBzdGFydCBmcm9tCiAgICAgICAgICAgIHN0YXRlX3RvIChjeC50b3dlci5qZXQuc3RhdGUoKSk6IFN0YXRlIHRvIGVuZCBhdAoKICAgICAgICBSZXR1cm5zOgogICAgICAgICAgICBsaXN0OiBMaXN0IG9mIGFjdGlvbnMgdGhhdCBsZWFkIGZyb20gb25lIHN0YXRlIHRvIGFub3RoZXIKICAgICAgICAiIiIKICAgICAgICBzZWxmLmVuc3VyZV9vbmUoKQoKICAgICAgICBvcmlnaW5hbF9zdGF0ZV90byA9IHN0YXRlX3RvCiAgICAgICAgcGF0aCA9IFtdCgogICAgICAgIGNyZWF0ZV9hY3Rpb24gPSBzZWxmLmFjdGlvbl9jcmVhdGVfaWQgaWYgc2VsZi5hY3Rpb25fY3JlYXRlX2lkIGVsc2UgRmFsc2UKICAgICAgICBkZXN0cm95X2FjdGlvbiA9IHNlbGYuYWN0aW9uX2Rlc3Ryb3lfaWQgaWYgc2VsZi5hY3Rpb25fZGVzdHJveV9pZCBlbHNlIEZhbHNlCgogICAgICAgIGlmIG5vdCBzdGF0ZV9mcm9tOgogICAgICAgICAgICBpZiBub3QgY3JlYXRlX2FjdGlvbjoKICAgICAgICAgICAgICAgIHJldHVybiBbXQogICAgICAgICAgICBwYXRoLmFwcGVuZChjcmVhdGVfYWN0aW9uKQogICAgICAgICAgICBzdGF0ZV9mcm9tID0gY3JlYXRlX2FjdGlvbi5zdGF0ZV90b19pZAoKICAgICAgICBpZiBub3Qgc3RhdGVfdG86CiAgICAgICAgICAgIGlmIG5vdCBkZXN0cm95X2FjdGlvbjoKICAgICAgICAgICAgICAgIHJldHVybiBbXQogICAgICAgICAgICBzdGF0ZV90byA9IGRlc3Ryb3lfYWN0aW9uLnN0YXRlX2Zyb21faWQKCiAgICAgICAgaWYgc3RhdGVfZnJvbSA9PSBzdGF0ZV90bzoKICAgICAgICAgICAgaWYgbm90IG9yaWdpbmFsX3N0YXRlX3RvIGFuZCBkZXN0cm95X2FjdGlvbjoKICAgICAgICAgICAgICAgIHJldHVybiBwYXRoICsgW2Rlc3Ryb3lfYWN0aW9uXQogICAgICAgICAgICByZXR1cm4gcGF0aAoKICAgICAgICBhZGphY2VuY3kgPSBzZWxmLl9nZXRfYWN0aW9uX2FkamFjZW5jeSgpCiAgICAgICAgc3RhdGVfcGF0aCA9IHNlbGYuX2ZpbmRfYWN0aW9uX3BhdGhfYmZzKHN0YXRlX2Zyb20sIHN0YXRlX3RvLCBhZGphY2VuY3kpCiAgICAgICAgaWYgc3RhdGVfcGF0aCBpcyBub3QgTm9uZToKICAgICAgICAgICAgcmVzdWx0X3BhdGggPSBwYXRoICsgc3RhdGVfcGF0aAogICAgICAgICAgICBpZiBub3Qgb3JpZ2luYWxfc3RhdGVfdG8gYW5kIGRlc3Ryb3lfYWN0aW9uOgogICAgICAgICAgICAgICAgcmVzdWx0X3BhdGguYXBwZW5kKGRlc3Ryb3lfYWN0aW9uKQogICAgICAgICAgICByZXR1cm4gcmVzdWx0X3BhdGgKCiAgICAgICAgaWYgKAogICAgICAgICAgICBub3Qgb3JpZ2luYWxfc3RhdGVfdG8KICAgICAgICAgICAgYW5kIGRlc3Ryb3lfYWN0aW9uCiAgICAgICAgICAgIGFuZCBzdGF0ZV9mcm9tID09IGRlc3Ryb3lfYWN0aW9uLnN0YXRlX2Zyb21faWQKICAgICAgICApOgogICAgICAgICAgICByZXR1cm4gcGF0aCArIFtkZXN0cm95X2FjdGlvbl0KCiAgICAgICAgcmV0dXJuIFtdCgogICAgZGVmIF9nZXRfYWN0aW9uX2FkamFjZW5jeShzZWxmKToKICAgICAgICAiIiJCdWlsZCBhZGphY2VuY3kgbGlzdCBmb3Igc3RhdGUgdHJhbnNpdGlvbnMuIiIiCiAgICAgICAgYWRqYWNlbmN5ID0ge30KICAgICAgICBmb3IgYWN0aW9uIGluIHNlbGYuYWN0aW9uX2lkczoKICAgICAgICAgICAgaWYgYWN0aW9uLnN0YXRlX2Zyb21faWQgYW5kIGFjdGlvbi5zdGF0ZV90b19pZDoKICAgICAgICAgICAgICAgIGlmIGFjdGlvbi5zdGF0ZV9mcm9tX2lkIG5vdCBpbiBhZGphY2VuY3k6CiAgICAgICAgICAgICAgICAgICAgYWRqYWNlbmN5W2FjdGlvbi5zdGF0ZV9mcm9tX2lkXSA9IFtdCiAgICAgICAgICAgICAgICBhZGphY2VuY3lbYWN0aW9uLnN0YXRlX2Zyb21faWRdLmFwcGVuZCgoYWN0aW9uLnN0YXRlX3RvX2lkLCBhY3Rpb24pKQogICAgICAgIHJldHVybiBhZGphY2VuY3kKCiAgICBkZWYgX2ZpbmRfYWN0aW9uX3BhdGhfYmZzKHNlbGYsIHN0YXRlX2Zyb20sIHN0YXRlX3RvLCBhZGphY2VuY3kpOgogICAgICAgICIiIkZpbmQgdGhlIHNob3J0ZXN0IHBhdGggb2YgYWN0aW9ucyBmcm9tIHN0YXRlX2Zyb20gdG8gc3RhdGVfdG8KICAgICAgICB1c2luZyBCRlMuCgogICAgICAgIEFyZ3M6CiAgICAgICAgICAgIHN0YXRlX2Zyb20gKGN4LnRvd2VyLmpldC5zdGF0ZSgpKTogU3RhdGUgdG8gc3RhcnQgZnJvbQogICAgICAgICAgICBzdGF0ZV90byAoY3gudG93ZXIuamV0LnN0YXRlKCkpOiBTdGF0ZSB0byBlbmQgYXQKICAgICAgICAgICAgYWRqYWNlbmN5IChkaWN0KTogQWRqYWNlbmN5IGxpc3QgZm9yIHN0YXRlIHRyYW5zaXRpb25zCiAgICAgICAgIiIiCiAgICAgICAgcXVldWUgPSBbKHN0YXRlX2Zyb20sIFtdKV0KICAgICAgICB2aXNpdGVkID0ge3N0YXRlX2Zyb219CiAgICAgICAgd2hpbGUgcXVldWU6CiAgICAgICAgICAgIGN1cnJlbnRfc3RhdGUsIHN0YXRlX3BhdGggPSBxdWV1ZS5wb3AoMCkKICAgICAgICAgICAgaWYgY3VycmVudF9zdGF0ZSBub3QgaW4gYWRqYWNlbmN5OgogICAgICAgICAgICAgICAgY29udGludWUKICAgICAgICAgICAgZm9yIG5leHRfc3RhdGUsIGFjdGlvbiBpbiBhZGphY2VuY3lbY3VycmVudF9zdGF0ZV06CiAgICAgICAgICAgICAgICBpZiBuZXh0X3N0YXRlID09IHN0YXRlX3RvOgogICAgICAgICAgICAgICAgICAgIHJldHVybiBzdGF0ZV9wYXRoICsgW2FjdGlvbl0KICAgICAgICAgICAgICAgIGlmIG5leHRfc3RhdGUgbm90IGluIHZpc2l0ZWQ6CiAgICAgICAgICAgICAgICAgICAgdmlzaXRlZC5hZGQobmV4dF9zdGF0ZSkKICAgICAgICAgICAgICAgICAgICBxdWV1ZS5hcHBlbmQoKG5leHRfc3RhdGUsIHN0YXRlX3BhdGggKyBbYWN0aW9uXSkpCiAgICAgICAgcmV0dXJuIE5vbmUKCiAgICAjICsrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysKICAgICMgICBJbnN0YWxsL1VuaW5zdGFsbAogICAgIyArKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrCgogICAgZGVmIF9pc19pbnN0YWxsYXRpb25fbmVlZGVkKHNlbGYsIHNlcnZlcik6CiAgICAgICAgIiIiQ2hlY2sgaWYgaW5zdGFsbGF0aW9uIGlzIG5lZWRlZCBmb3IgdGhlIGdpdmVuIHNlcnZlci4KCiAgICAgICAgQXJnczoKICAgICAgICAgICAgc2VydmVyOiBTZXJ2ZXIgdG8gY2hlY2sKCiAgICAgICAgUmV0dXJuczoKICAgICAgICAgICAgYm9vbDogRmFsc2UgaWYgc2VydmVyIGlzIGFscmVhZHkgaW5zdGFsbGVkIG9yIGJlaW5nIGluc3RhbGxlZCwKICAgICAgICAgICAgICAgIFRydWUgb3RoZXJ3aXNlCiAgICAgICAgIiIiCiAgICAgICAgIyBDaGVjayBpZiB0ZW1wbGF0ZSBpcyBhbHJlYWR5IGluc3RhbGxlZCBvbiB0aGUgc2VydmVyCiAgICAgICAgaWYgc2VydmVyLmlkIGluIHNlbGYuc2VydmVyX2lkcy5pZHM6CiAgICAgICAgICAgIHJldHVybiBGYWxzZQoKICAgICAgICAjIENoZWNrIGlmIHRlbXBsYXRlIGlzIGFscmVhZHkgYmVpbmcgaW5zdGFsbGVkIG9uIHRoZSBzZXJ2ZXIKICAgICAgICBpZiAoCiAgICAgICAgICAgIHNlcnZlci5pZAogICAgICAgICAgICBpbiBzZWxmLmluc3RhbGxfaWRzLmZpbHRlcmVkKAogICAgICAgICAgICAgICAgbGFtYmRhIGluc3RhbGw6IGluc3RhbGwuamV0X3RlbXBsYXRlX2luc3RhbGxfaWQuc3RhdGUgPT0gInByb2Nlc3NpbmciCiAgICAgICAgICAgICkuc2VydmVyX2lkLmlkcwogICAgICAgICk6CiAgICAgICAgICAgIHJldHVybiBGYWxzZQoKICAgICAgICByZXR1cm4gVHJ1ZQoKICAgIGRlZiBpbnN0YWxsX29uX3NlcnZlcnMoc2VsZiwgc2VydmVycyk6CiAgICAgICAgIiIiSW5zdGFsbCB0aGUgSmV0IFRlbXBsYXRlIG9uIHRoZSBzZWxlY3RlZCBzZXJ2ZXJzLgoKICAgICAgICBBcmdzOgogICAgICAgICAgICBzZXJ2ZXJzIChjeC50b3dlci5zZXJ2ZXIoKSk6IFNlcnZlcnMgdG8gaW5zdGFsbCB0aGUgSmV0IFRlbXBsYXRlIG9uCiAgICAgICAgIiIiCiAgICAgICAgc2VsZi5lbnN1cmVfb25lKCkKCiAgICAgICAgdGVtcGxhdGVfaW5zdGFsbF9vYmogPSBzZWxmLmVudlsiY3gudG93ZXIuamV0LnRlbXBsYXRlLmluc3RhbGwiXQogICAgICAgIG5vdyA9IGZpZWxkcy5EYXRldGltZS5ub3coKQogICAgICAgIGNvbnRleHRfdGltZXN0YW1wID0gZmllbGRzLkRhdGV0aW1lLnRvX3N0cmluZyhub3cpCgogICAgICAgIGZvciBzZXJ2ZXIgaW4gc2VydmVyczoKICAgICAgICAgICAgIyBDaGVjayBpZiBpbnN0YWxsYXRpb24gaXMgbmVlZGVkIGZvciB0aGlzIHNlcnZlcgogICAgICAgICAgICBpZiBub3Qgc2VsZi5faXNfaW5zdGFsbGF0aW9uX25lZWRlZChzZXJ2ZXIpOgogICAgICAgICAgICAgICAgX2xvZ2dlci5pbmZvKAogICAgICAgICAgICAgICAgICAgICJUZW1wbGF0ZSAnJXMnIGlzIGFscmVhZHkgaW5zdGFsbGVkIG9yIGJlaW5nIGluc3RhbGxlZCIKICAgICAgICAgICAgICAgICAgICAiIG9uIHRoZSBzZXJ2ZXIgJyVzJyIsCiAgICAgICAgICAgICAgICAgICAgc2VsZi5uYW1lLCAgIyBweWxpbnQ6IGRpc2FibGU9bm8tbWVtYmVyCiAgICAgICAgICAgICAgICAgICAgc2VydmVyLm5hbWUsCiAgICAgICAgICAgICAgICApCiAgICAgICAgICAgICAgICAjIE5vdGlmeSB0aGUgdXNlcgogICAgICAgICAgICAgICAgc2VsZi5lbnYudXNlci5ub3RpZnlfaW5mbygKICAgICAgICAgICAgICAgICAgICB0aXRsZT1zZWxmLm5hbWUsICAjIHB5bGludDogZGlzYWJsZT1uby1tZW1iZXIKICAgICAgICAgICAgICAgICAgICBtZXNzYWdlPV8oCiAgICAgICAgICAgICAgICAgICAgICAgICIlKHRpbWVzdGFtcClzPGJyLz5UZW1wbGF0ZSBpcyBhbHJlYWR5IGluc3RhbGxlZCAiCiAgICAgICAgICAgICAgICAgICAgICAgICJvciBiZWluZyBpbnN0YWxsZWQiCiAgICAgICAgICAgICAgICAgICAgICAgICIgb24gdGhlIHNlcnZlciAnJShzZXJ2ZXJfbmFtZSlzJyIsCiAgICAgICAgICAgICAgICAgICAgICAgIHRpbWVzdGFtcD1jb250ZXh0X3RpbWVzdGFtcCwKICAgICAgICAgICAgICAgICAgICAgICAgc2VydmVyX25hbWU9c2VydmVyLm5hbWUsCiAgICAgICAgICAgICAgICAgICAgKSwKICAgICAgICAgICAgICAgICkKICAgICAgICAgICAgICAgIGNvbnRpbnVlCgogICAgICAgICAgICB0ZW1wbGF0ZV9pbnN0YWxsX29iai5pbnN0YWxsKAogICAgICAgICAgICAgICAgdGVtcGxhdGU9c2VsZiwKICAgICAgICAgICAgICAgIHNlcnZlcj1zZXJ2ZXIsCiAgICAgICAgICAgICkKCiAgICAgICAgIyBSZWZyZXNoIHRoZSBmcm9udGVuZCB2aWV3cwogICAgICAgIHNlbGYuZW52LnVzZXIucmVsb2FkX3ZpZXdzKG1vZGVsPSJjeC50b3dlci5qZXQudGVtcGxhdGUiLCByZWNfaWRzPVtzZWxmLmlkXSkKCiAgICBkZWYgdW5pbnN0YWxsX2Zyb21fc2VydmVycyhzZWxmLCBzZXJ2ZXJzLCByYWlzZV9pZl9ub3RfcG9zc2libGU9VHJ1ZSk6CiAgICAgICAgIiIiVW5pbnN0YWxsIHRoZSBKZXQgVGVtcGxhdGUgZnJvbSB0aGUgc2VsZWN0ZWQgc2VydmVycy4KCiAgICAgICAgQXJnczoKICAgICAgICAgICAgc2VydmVycyAoY3gudG93ZXIuc2VydmVyKCkpOiBTZXJ2ZXJzIHRvIHVuaW5zdGFsbCB0aGUgSmV0IFRlbXBsYXRlIGZyb20KICAgICAgICAgICAgcmFpc2VfaWZfbm90X3Bvc3NpYmxlIChib29sKToKICAgICAgICAgICAgSWYgVHJ1ZSwgd2lsbCByYWlzZSBhbiBlcnJvciBpZiB0aGUgdW5pbnN0YWxsYXRpb24gaXMgbm90IHBvc3NpYmxlLgogICAgICAgICIiIgogICAgICAgIHNlbGYuZW5zdXJlX29uZSgpCiAgICAgICAgdGVtcGxhdGVfaW5zdGFsbF9vYmogPSBzZWxmLmVudlsiY3gudG93ZXIuamV0LnRlbXBsYXRlLmluc3RhbGwiXQoKICAgICAgICBmb3Igc2VydmVyIGluIHNlcnZlcnM6CiAgICAgICAgICAgICMgQ2hlY2sgaWYgaW5zdGFsbGF0aW9uIGlzIHBvc3NpYmxlIGZvciB0aGlzIHNlcnZlcgogICAgICAgICAgICB3YXJuaW5nX21lc3NhZ2UgPSBOb25lCiAgICAgICAgICAgICMgVGVtcGxhdGUgaXMgbm90IGluc3RhbGxlZCBvbiB0aGUgc2VydmVyCiAgICAgICAgICAgIGlmIHNlcnZlci5pZCBub3QgaW4gc2VsZi5zZXJ2ZXJfaWRzLmlkczoKICAgICAgICAgICAgICAgIHdhcm5pbmdfbWVzc2FnZSA9IF8oCiAgICAgICAgICAgICAgICAgICAgIlRlbXBsYXRlICclKHRlbXBsYXRlX25hbWUpcycgaXMgbm90IGluc3RhbGxlZCAiCiAgICAgICAgICAgICAgICAgICAgIm9uIHRoZSBzZXJ2ZXIgJyUoc2VydmVyX25hbWUpcyciLAogICAgICAgICAgICAgICAgICAgIHRlbXBsYXRlX25hbWU9c2VsZi5uYW1lLCAgIyBweWxpbnQ6IGRpc2FibGU9bm8tbWVtYmVyCiAgICAgICAgICAgICAgICAgICAgc2VydmVyX25hbWU9c2VydmVyLm5hbWUsCiAgICAgICAgICAgICAgICApCiAgICAgICAgICAgICMgVGhlcmUgYXJlIHN0aWxsIGpldHMgb24gdGhlIHNlcnZlcgogICAgICAgICAgICBlbGlmIHNlcnZlci5qZXRfaWRzLmZpbHRlcmVkKGxhbWJkYSBqZXQ6IGpldC5qZXRfdGVtcGxhdGVfaWQgPT0gc2VsZik6CiAgICAgICAgICAgICAgICB3YXJuaW5nX21lc3NhZ2UgPSBfKAogICAgICAgICAgICAgICAgICAgICJUaGVyZSBhcmUgc3RpbGwgamV0cyBvZiB0ZW1wbGF0ZSAnJSh0ZW1wbGF0ZV9uYW1lKXMnICIKICAgICAgICAgICAgICAgICAgICAib24gdGhlIHNlcnZlciAnJShzZXJ2ZXJfbmFtZSlzJyIsCiAgICAgICAgICAgICAgICAgICAgdGVtcGxhdGVfbmFtZT1zZWxmLm5hbWUsICAjIHB5bGludDogZGlzYWJsZT1uby1tZW1iZXIKICAgICAgICAgICAgICAgICAgICBzZXJ2ZXJfbmFtZT1zZXJ2ZXIubmFtZSwKICAgICAgICAgICAgICAgICkKICAgICAgICAgICAgIyBUaGVyZSBhcmUgb3RoZXIgdGVtcGxhdGVzIHRoYXQgZGVwZW5kIG9uIHRoaXMgdGVtcGxhdGUKICAgICAgICAgICAgIyBpbnN0YWxsZWQgb24gdGhlIHNlcnZlcgogICAgICAgICAgICBlbGlmIHNlcnZlci5qZXRfdGVtcGxhdGVfaWRzLmZpbHRlcmVkKAogICAgICAgICAgICAgICAgbGFtYmRhIHRlbXBsYXRlOiB0ZW1wbGF0ZS50ZW1wbGF0ZV9yZXF1aXJlc19pZHMuZmlsdGVyZWQoCiAgICAgICAgICAgICAgICAgICAgbGFtYmRhIGRlcGVuZGVuY3k6IGRlcGVuZGVuY3kudGVtcGxhdGVfcmVxdWlyZWRfaWQgPT0gc2VsZgogICAgICAgICAgICAgICAgKQogICAgICAgICAgICApOgogICAgICAgICAgICAgICAgd2FybmluZ19tZXNzYWdlID0gXygKICAgICAgICAgICAgICAgICAgICAiVGhlcmUgYXJlIG90aGVyIHRlbXBsYXRlcyB0aGF0IGRlcGVuZCAiCiAgICAgICAgICAgICAgICAgICAgIm9uIHRlbXBsYXRlICclKHRlbXBsYXRlX25hbWUpcycgIgogICAgICAgICAgICAgICAgICAgICJ0aGF0IGFyZSBpbnN0YWxsZWQgb24gdGhlIHNlcnZlciAnJShzZXJ2ZXJfbmFtZSlzJyIsCiAgICAgICAgICAgICAgICAgICAgdGVtcGxhdGVfbmFtZT1zZWxmLm5hbWUsICAjIHB5bGludDogZGlzYWJsZT1uby1tZW1iZXIKICAgICAgICAgICAgICAgICAgICBzZXJ2ZXJfbmFtZT1zZXJ2ZXIubmFtZSwKICAgICAgICAgICAgICAgICkKCiAgICAgICAgICAgIGlmIHdhcm5pbmdfbWVzc2FnZToKICAgICAgICAgICAgICAgIGlmIHJhaXNlX2lmX25vdF9wb3NzaWJsZToKICAgICAgICAgICAgICAgICAgICByYWlzZSBWYWxpZGF0aW9uRXJyb3Iod2FybmluZ19tZXNzYWdlKQogICAgICAgICAgICAgICAgc2VsZi5lbnYudXNlci5ub3RpZnlfd2FybmluZygKICAgICAgICAgICAgICAgICAgICBtZXNzYWdlPXdhcm5pbmdfbWVzc2FnZSwKICAgICAgICAgICAgICAgICAgICB0aXRsZT1zZWxmLm5hbWUsICAjIHB5bGludDogZGlzYWJsZT1uby1tZW1iZXIKICAgICAgICAgICAgICAgICkKICAgICAgICAgICAgICAgIGNvbnRpbnVlCgogICAgICAgICAgICB0ZW1wbGF0ZV9pbnN0YWxsX29iai51bmluc3RhbGwoCiAgICAgICAgICAgICAgICB0ZW1wbGF0ZT1zZWxmLAogICAgICAgICAgICAgICAgc2VydmVyPXNlcnZlciwKICAgICAgICAgICAgKQoKICAgIGRlZiBfZ2V0X3N5c3RlbV92YXJpYWJsZV92YWx1ZShzZWxmLCB2YXJpYWJsZV9yZWZlcmVuY2UpOgogICAgICAgICIiIlJldHVybiB0aGUgamV0IHRlbXBsYXRlIHZhcmlhYmxlIHZhbHVlcwoKICAgICAgICBBcmdzOgogICAgICAgICAgICB2YXJpYWJsZV9yZWZlcmVuY2UgKENoYXIpOiB2YXJpYWJsZSB2YWx1ZQoKICAgICAgICBSZXR1cm5zOgogICAgICAgICAgICBkaWN0KCk6IHBvcHVsYXRlcyBgdG93ZXJgIHZhcmlhYmxlIHdpdGggd2l0aCB2YWx1ZXMuCiAgICAgICAgICAgICAgICB7CiAgICAgICAgICAgICAgICAgICAgJ2pldF90ZW1wbGF0ZSc6IHsuLmpldCB0ZW1wbGF0ZSB2YWxzLi59LAogICAgICAgICAgICAgICAgfS4KICAgICAgICAiIiIKCiAgICAgICAgIyBUaGlzIHdvcmtzIGZvciBhIHNpbmdsZSByZWNvcmQgb25seSEKICAgICAgICBzZWxmLmVuc3VyZV9vbmUoKQoKICAgICAgICB2YXJpYWJsZV92YWx1ZSA9IHt9CiAgICAgICAgaWYgdmFyaWFibGVfcmVmZXJlbmNlID09ICJ0b3dlciI6CiAgICAgICAgICAgIHZhcmlhYmxlX3ZhbHVlLnVwZGF0ZSgKICAgICAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgICAgICAiamV0X3RlbXBsYXRlIjogewogICAgICAgICAgICAgICAgICAgICAgICAibmFtZSI6IHNlbGYubmFtZSwgICMgcHlsaW50OiBkaXNhYmxlPW5vLW1lbWJlcgogICAgICAgICAgICAgICAgICAgICAgICAicmVmZXJlbmNlIjogc2VsZi5yZWZlcmVuY2UsICAjIHB5bGludDogZGlzYWJsZT1uby1tZW1iZXIKICAgICAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICAgICAgfQogICAgICAgICAgICApCiAgICAgICAgcmV0dXJuIHZhcmlhYmxlX3ZhbHVlCgogICAgIyArKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrCiAgICAjICAgSmV0IGNyZWF0aW9uCiAgICAjICsrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysKCiAgICBkZWYgY3JlYXRlX2pldChzZWxmLCBzZXJ2ZXIsIG5hbWU9Tm9uZSwgc3RhdGU9Tm9uZSwgKiprd2FyZ3MpOgogICAgICAgICIiIgogICAgICAgIENyZWF0ZSBhIG5ldyBqZXQgZnJvbSB0aGlzIHRlbXBsYXRlIG9uIHRoZSBnaXZlbiBzZXJ2ZXIuCgogICAgICAgIEFyZ3M6CiAgICAgICAgICAgIHNlcnZlciAoY3gudG93ZXIuc2VydmVyKCkpOiBUaGUgc2VydmVyIHRvIHVzZQogICAgICAgICAgICBuYW1lIChzdHIpOiBUaGUgbmFtZSBvZiB0aGUgamV0LgogICAgICAgICAgICAgICAgSWYgbm90IHByb3ZpZGVkLCBhIHJhbmRvbSBuYW1lIHdpbGwgYmUgZ2VuZXJhdGVkLgogICAgICAgICAgICAgICAgRGVmYXVsdHMgdG8gTm9uZS4KICAgICAgICAgICAgc3RhdGUgKGN4LnRvd2VyLmpldC5zdGF0ZSgpKTogVGhlIHN0YXRlIHRvIHNldCB0aGUgamV0IHRvLgogICAgICAgICAgICAgICAgSWYgbm90IHByb3ZpZGVkLCB0aGUgamV0IHdpbGwgYmUgY3JlYXRlZCBpbiB0aGUgaW5pdGlhbCBzdGF0ZS4KICAgICAgICAgICAgICAgIERlZmF1bHRzIHRvIE5vbmUuCiAgICAgICAgS3dhcmdzOgogICAgICAgICAgICBmaWVsZCB2YWx1ZXMgdG8gcG9wdWxhdGUgaW4gdGhlIG5ldyBqZXQgcmVjb3JkLgogICAgICAgICAgICBOQjogY29uZmlndXJhdGlvbiB2YXJpYWJsZXMgYXJlIHByb3ZpZGVkIGFzIGZvbGxvd3M6CiAgICAgICAgICAgIHZhcmlhYmxlX3ZhbHVlcyAoZGljdCk6IEN1c3RvbSBjb25maWd1cmF0aW9uIHZhcmlhYmxlcwogICAgICAgICAgICAgICAgaW4gdGhlIGZvcm1hdCBvZiBge3ZhcmlhYmxlX3JlZmVyZW5jZTogdmFyaWFibGVfdmFsdWV9YAogICAgICAgICAgICAgICAgZWcgYHsnb2Rvb192ZXJzaW9uJzogJzE2LjAnfWAKICAgICAgICBSZXR1cm5zOgogICAgICAgICAgICBjeC50b3dlci5qZXQoKTogVGhlIG5ldyBqZXQgb3IgRmFsc2UgaWYgdGhlIGNyZWF0aW9uIGhhcyBmYWlsZWQKICAgICAgICAiIiIKICAgICAgICBzZWxmLmVuc3VyZV9vbmUoKQoKICAgICAgICAjIENoZWNrIGlmIHRoZSBqZXQgY3JlYXRpb24gaXMgYWxsb3dlZCBvbiB0aGUgZ2l2ZW4gc2VydmVyCiAgICAgICAgaWYgbm90IHNlbGYuX2FsbG93X2pldF9jcmVhdGlvbihzZXJ2ZXIpOgogICAgICAgICAgICByZXR1cm4gRmFsc2UKCiAgICAgICAgIyBQcmVwYXJlIHRoZSBqZXQgdmFsdWVzCiAgICAgICAgdmFscyA9IHNlbGYuX3ByZXBhcmVfamV0X3ZhbHVlcyhzZXJ2ZXIsIG5hbWUsICoqa3dhcmdzKQoKICAgICAgICAjIENyZWF0ZSBhIG5ldyBqZXQKICAgICAgICBqZXQgPSBzZWxmLmVudlsiY3gudG93ZXIuamV0Il0uY3JlYXRlKHZhbHMpCgogICAgICAgICMgU2V0IHRoZSBzdGF0ZSBvZiB0aGUgamV0CiAgICAgICAgaWYgc3RhdGU6CiAgICAgICAgICAgIGpldC5fYnJpbmdfdG9fc3RhdGUoc3RhdGUpCgogICAgICAgIHJldHVybiBqZXQKCiAgICBkZWYgX3ByZXBhcmVfamV0X3ZhbHVlcyhzZWxmLCBzZXJ2ZXIsIG5hbWU9Tm9uZSwgKiprd2FyZ3MpOgogICAgICAgICIiIgogICAgICAgIFByZXBhcmUgdGhlIGpldCB2YWx1ZXMgdG8gY3JlYXRlIGEgbmV3IGpldCBiYXNlZAogICAgICAgIG9uIHRoZSBnaXZlbiBzZXJ2ZXIgYW5kIHRlbXBsYXRlLgoKICAgICAgICBBcmdzOgogICAgICAgICAgICBzZXJ2ZXIgKGN4LnRvd2VyLnNlcnZlcigpKTogVGhlIHNlcnZlciB0byBjcmVhdGUgdGhlIGpldCBvbgogICAgICAgICAgICAqKmt3YXJnczogQWRkaXRpb25hbCB2YWx1ZXMgdG8gdXBkYXRlIGluIHRoZSBmaW5hbCBqZXQgcmVjb3JkLgogICAgICAgICIiIgogICAgICAgIHNlbGYuZW5zdXJlX29uZSgpCgogICAgICAgICMgQ2hlY2sgaWYgdGhlIFVSTCBpcyB2YWxpZAogICAgICAgIHVybCA9IGt3YXJncy5wb3AoInVybCIsIE5vbmUpCiAgICAgICAgaWYgdXJsIGFuZCBub3QgaXNfdmFsaWRfdXJsKHVybCwgbm9fc2NoZW1lX2NoZWNrPVRydWUpOgogICAgICAgICAgICByYWlzZSBWYWxpZGF0aW9uRXJyb3IoCiAgICAgICAgICAgICAgICBfKAogICAgICAgICAgICAgICAgICAgICJJbnZhbGlkIFVSTDogJyUodXJsKXMnLiBVUkwgbXVzdCBjb250YWluIGEgcHJvdG9jb2wgYW5kICIKICAgICAgICAgICAgICAgICAgICAiYSBwcm9wZXIgZG9tYWluIG9yIElQLCBlZyAnaHR0cHM6Ly9teV90b3dlcl9qZXQuZXhhbXBsZS5jb20nIiwKICAgICAgICAgICAgICAgICAgICB1cmw9dXJsLAogICAgICAgICAgICAgICAgKQogICAgICAgICAgICApCgogICAgICAgICMgSWYgbm8gbmFtZSBpcyBwcm92aWRlZCwgZ2VuZXJhdGUgYSByYW5kb20gb25lCiAgICAgICAgaWYgbm90IG5hbWU6CiAgICAgICAgICAgIG5hbWUgPSBzZWxmLl9nZW5lcmF0ZV9qZXRfbmFtZSgpCgogICAgICAgICMgQ2hlY2sgaWYgdGhlIHNhbWUgbmFtZSBhbHJlYWR5IGV4aXN0cyBvbiB0aGUgc2VydmVyCiAgICAgICAgIyBLZWVwIGdlbmVyYXRpbmcgYSBuZXcgbmFtZSB1bnRpbCBhIHVuaXF1ZSBvbmUgaXMgZm91bmQKICAgICAgICBqZXRfb2JqID0gc2VsZi5lbnZbImN4LnRvd2VyLmpldCJdCiAgICAgICAgIyBQcmUtZmV0Y2ggZXhpc3RpbmcgbmFtZXMgZm9yIHRoaXMgc2VydmVyCiAgICAgICAgZXhpc3RpbmdfbmFtZXMgPSBzZXQoCiAgICAgICAgICAgIGpldF9vYmouc2VhcmNoKFsoInNlcnZlcl9pZCIsICI9Iiwgc2VydmVyLmlkKV0pLm1hcHBlZCgibmFtZSIpCiAgICAgICAgKQoKICAgICAgICBmb3IgX2F0dGVtcHQgaW4gcmFuZ2UoTUFYX0pFVF9OQU1FX1JFVFJJRVMpOgogICAgICAgICAgICBpZiBuYW1lIG5vdCBpbiBleGlzdGluZ19uYW1lczoKICAgICAgICAgICAgICAgIGJyZWFrCiAgICAgICAgICAgIG5hbWUgPSBzZWxmLl9nZW5lcmF0ZV9qZXRfbmFtZSgpCiAgICAgICAgZWxzZToKICAgICAgICAgICAgIyBMb29wIGV4aGF1c3RlZCB3aXRob3V0IGZpbmRpbmcgdW5pcXVlIG5hbWUKICAgICAgICAgICAgcmFpc2UgVmFsaWRhdGlvbkVycm9yKAogICAgICAgICAgICAgICAgXygKICAgICAgICAgICAgICAgICAgICAiRmFpbGVkIHRvIGdlbmVyYXRlIHVuaXF1ZSBqZXQgbmFtZSBhZnRlciAlKGF0dGVtcHRzKWQgYXR0ZW1wdHMiLAogICAgICAgICAgICAgICAgICAgIGF0dGVtcHRzPU1BWF9KRVRfTkFNRV9SRVRSSUVTLAogICAgICAgICAgICAgICAgKQogICAgICAgICAgICApCgogICAgICAgICMgUHJlcGFyZSB0aGUgSmV0IHZhbHVlcwogICAgICAgIHZhbHMgPSB7CiAgICAgICAgICAgICJuYW1lIjogbmFtZSwKICAgICAgICAgICAgImpldF90ZW1wbGF0ZV9pZCI6IHNlbGYuaWQsICAjIHB5bGludDogZGlzYWJsZT1uby1tZW1iZXIKICAgICAgICAgICAgInNlcnZlcl9pZCI6IHNlcnZlci5pZCwKICAgICAgICAgICAgInVybCI6IHVybCwKICAgICAgICB9CgogICAgICAgICMgUGFyc2Ugc3BlY2lmaWMgZmllbGRzIGZyb20ga3dhcmdzCiAgICAgICAgaWYga3dhcmdzOgogICAgICAgICAgICAjIFBhcnNlIGNvbmZpZ3VyYXRpb24gdmFyaWFibGVzCiAgICAgICAgICAgIGNvbmZpZ3VyYXRpb25fdmFyaWFibGVzID0ga3dhcmdzLnBvcCgidmFyaWFibGVfdmFsdWVzIiwge30pCiAgICAgICAgICAgIGlmIGNvbmZpZ3VyYXRpb25fdmFyaWFibGVzOgogICAgICAgICAgICAgICAgdmFyaWFibGVfb2JqID0gc2VsZi5lbnZbImN4LnRvd2VyLnZhcmlhYmxlIl0KICAgICAgICAgICAgICAgIHZhcmlhYmxlX3ZhbHVlcyA9IFtdCiAgICAgICAgICAgICAgICBmb3IgKAogICAgICAgICAgICAgICAgICAgIHZhcmlhYmxlX3JlZmVyZW5jZSwKICAgICAgICAgICAgICAgICAgICB2YXJpYWJsZV92YWx1ZSwKICAgICAgICAgICAgICAgICkgaW4gY29uZmlndXJhdGlvbl92YXJpYWJsZXMuaXRlbXMoKToKICAgICAgICAgICAgICAgICAgICB2YXJpYWJsZSA9IHZhcmlhYmxlX29iai5nZXRfYnlfcmVmZXJlbmNlKHZhcmlhYmxlX3JlZmVyZW5jZSkKICAgICAgICAgICAgICAgICAgICBpZiB2YXJpYWJsZToKICAgICAgICAgICAgICAgICAgICAgICAgdmFyaWFibGVfdmFsdWVzLmFwcGVuZCgKICAgICAgICAgICAgICAgICAgICAgICAgICAgICgKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAwLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIDAsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAidmFyaWFibGVfaWQiOiB2YXJpYWJsZS5pZCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgInZhbHVlX2NoYXIiOiB2YXJpYWJsZV92YWx1ZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgKQogICAgICAgICAgICAgICAgICAgICAgICApCiAgICAgICAgICAgICAgICAgICAgICAgIGNvbnRpbnVlCiAgICAgICAgICAgICAgICAgICAgX2xvZ2dlci53YXJuaW5nKAogICAgICAgICAgICAgICAgICAgICAgICAiVmFyaWFibGUgcmVmZXJlbmNlICclcycgbm90IGZvdW5kIHdoaWxlIGNyZWF0aW5nIGpldCAnJXMnIiwKICAgICAgICAgICAgICAgICAgICAgICAgdmFyaWFibGVfcmVmZXJlbmNlLAogICAgICAgICAgICAgICAgICAgICAgICBzZWxmLm5hbWUsICAjIHB5bGludDogZGlzYWJsZT1uby1tZW1iZXIKICAgICAgICAgICAgICAgICAgICApCgogICAgICAgICAgICAgICAgaWYgdmFyaWFibGVfdmFsdWVzOgogICAgICAgICAgICAgICAgICAgIHZhbHMudXBkYXRlKAogICAgICAgICAgICAgICAgICAgICAgICB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAidmFyaWFibGVfdmFsdWVfaWRzIjogdmFyaWFibGVfdmFsdWVzLAogICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgKQoKICAgICAgICAjIFBvcHVsYXRlIHRoZSBhbGxvd2VkIGZpZWxkcwogICAgICAgIGZvciBmaWVsZCBpbiBzZWxmLl9hbGxvd2VkX2pldF9maWVsZHMoKToKICAgICAgICAgICAgaWYgZmllbGQgaW4ga3dhcmdzOgogICAgICAgICAgICAgICAgdmFsc1tmaWVsZF0gPSBrd2FyZ3MucG9wKGZpZWxkKQoKICAgICAgICByZXR1cm4gdmFscwoKICAgIGRlZiBfYWxsb3dlZF9qZXRfZmllbGRzKHNlbGYpOgogICAgICAgICIiIlJldHVybiB0aGUgYWxsb3dlZCBmaWVsZHMgZm9yIHRoZSBqZXQgY3JlYXRpb24iIiIKICAgICAgICBzZWxmLmVuc3VyZV9vbmUoKQogICAgICAgIHJldHVybiBbCiAgICAgICAgICAgICJuYW1lIiwKICAgICAgICAgICAgInJlZmVyZW5jZSIsCiAgICAgICAgICAgICJzZXF1ZW5jZSIsCiAgICAgICAgICAgICJ0YWdfaWRzIiwKICAgICAgICAgICAgInBhcnRuZXJfaWQiLAogICAgICAgICAgICAiamV0X2Nsb25lZF9mcm9tX2lkIiwKICAgICAgICAgICAgInNjaGVkdWxlZF90YXNrX2lkcyIsCiAgICAgICAgICAgICJzZXJ2ZXJfbG9nX2lkcyIsCiAgICAgICAgXQoKICAgIGRlZiBfYWxsb3dfamV0X2NyZWF0aW9uKHNlbGYsIHNlcnZlcik6CiAgICAgICAgIiIiCiAgICAgICAgQ2hlY2sgaWYgdGhlIGpldCBjcmVhdGlvbiBpcyBhbGxvd2VkIG9uIHRoZSBnaXZlbiBzZXJ2ZXIuCiAgICAgICAgVGhpcyBmdW5jdGlvbiBjYW4gYmUgZXh0ZW5kZWQgdG8gY2hlY2sgZm9yIG90aGVyIGNvbmRpdGlvbnMuCiAgICAgICAgRWcgaWYgamV0IGNhcGFjaXR5IGlzIHJlYWNoZWQgZm9yIHRoZSBzZXJ2ZXIuCiAgICAgICAgT3Igc2VydmVyIHRlbXBsYXRlIGhhcyBhIGNlcnRhaW4gbGltaXQgb24gdGhlIG51bWJlciBvZiBqZXRzIHBlciBzZXJ2ZXIuCgogICAgICAgIEFyZ3M6CiAgICAgICAgICAgIHNlcnZlciAoY3gudG93ZXIuc2VydmVyKCkpOiBUaGUgc2VydmVyIHRvIGNoZWNrCgogICAgICAgIFJldHVybnM6CiAgICAgICAgICAgIGJvb2w6IFRydWUgaWYgdGhlIGpldCBjcmVhdGlvbiBpcyBhbGxvd2VkLCBGYWxzZSBvdGhlcndpc2UKICAgICAgICAiIiIKICAgICAgICBzZWxmLmVuc3VyZV9vbmUoKQogICAgICAgIHJldHVybiBUcnVlCgogICAgZGVmIF9nZW5lcmF0ZV9qZXRfbmFtZShzZWxmKToKICAgICAgICAiIiJHZW5lcmF0ZSBhIHVuaXF1ZSBuYW1lIGZvciBhIGpldCIiIgogICAgICAgIHNlbGYuZW5zdXJlX29uZSgpCiAgICAgICAgcmV0dXJuICgKICAgICAgICAgICAgZiJ7c2VsZi5uYW1lfSAiCiAgICAgICAgICAgIGYiW3tnZW5lcmF0ZV9yYW5kb21faWQoc2VjdGlvbnM9MiwgcG9wdWxhdGlvbj00LCBzZXBhcmF0b3I9Jy0nKX1dIgogICAgICAgICkKCiAgICAjICsrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysKICAgICMgICBEZXBlbmRlbmN5IEdyYXBoCiAgICAjICsrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysKCiAgICBkZWYgX2J1aWxkX2RlcGVuZGVuY3lfZ3JhcGgoc2VsZik6CiAgICAgICAgIiIiQnVpbGQgYSBkZXBlbmRlbmN5IGdyYXBoIG9mIGFsbCB0ZW1wbGF0ZXMgdGhpcyB0ZW1wbGF0ZSBkZXBlbmRzIG9uCgogICAgICAgIFJldHVybnM6CiAgICAgICAgICAgIGRpY3Q6IEEgZGljdGlvbmFyeSByZXByZXNlbnRpbmcgdGhlIGRlcGVuZGVuY3kgZ3JhcGggd2hlcmU6CiAgICAgICAgICAgICAgICAtIEtleXMgYXJlIHRlbXBsYXRlIElEcwogICAgICAgICAgICAgICAgLSBWYWx1ZXMgYXJlIGRpY3Rpb25hcmllcyBjb250YWluaW5nIHRlbXBsYXRlIGluZm8KICAgICAgICAgICAgICAgICAgICBhbmQgZGVwZW5kZW5jaWVzCiAgICAgICAgIiIiCiAgICAgICAgc2VsZi5lbnN1cmVfb25lKCkKCiAgICAgICAgZ3JhcGggPSB7fQogICAgICAgIHZpc2l0ZWQgPSBzZXQoKQoKICAgICAgICAjIFVzZSBhIHN0YWNrIHRvIHByb2Nlc3MgdGVtcGxhdGVzIGl0ZXJhdGl2ZWx5IGluc3RlYWQgb2YgcmVjdXJzaW9uCiAgICAgICAgc3RhY2sgPSBbc2VsZl0KCiAgICAgICAgd2hpbGUgc3RhY2s6CiAgICAgICAgICAgIHRlbXBsYXRlID0gc3RhY2sucG9wKCkKCiAgICAgICAgICAgICMgU2tpcCBpZiBhbHJlYWR5IHZpc2l0ZWQKICAgICAgICAgICAgaWYgdGVtcGxhdGUuaWQgaW4gdmlzaXRlZDoKICAgICAgICAgICAgICAgIGNvbnRpbnVlCgogICAgICAgICAgICAjIE1hcmsgYXMgdmlzaXRlZAogICAgICAgICAgICB2aXNpdGVkLmFkZCh0ZW1wbGF0ZS5pZCkKCiAgICAgICAgICAgICMgQWRkIGN1cnJlbnQgdGVtcGxhdGUgdG8gZ3JhcGgKICAgICAgICAgICAgZ3JhcGhbdGVtcGxhdGUuaWRdID0gewogICAgICAgICAgICAgICAgInRlbXBsYXRlIjogdGVtcGxhdGUsCiAgICAgICAgICAgICAgICAibmFtZSI6IHRlbXBsYXRlLm5hbWUsCiAgICAgICAgICAgICAgICAicmVmZXJlbmNlIjogdGVtcGxhdGUucmVmZXJlbmNlLAogICAgICAgICAgICAgICAgImRlcGVuZGVuY2llcyI6IFtdLAogICAgICAgICAgICAgICAgImxldmVsIjogMCwgICMgV2lsbCBiZSBjYWxjdWxhdGVkIGxhdGVyCiAgICAgICAgICAgIH0KCiAgICAgICAgICAgICMgQWRkIGRlcGVuZGVuY2llcwogICAgICAgICAgICBmb3IgZGVwZW5kZW5jeSBpbiB0ZW1wbGF0ZS50ZW1wbGF0ZV9yZXF1aXJlc19pZHM6CiAgICAgICAgICAgICAgICByZXF1aXJlZF90ZW1wbGF0ZSA9IGRlcGVuZGVuY3kudGVtcGxhdGVfcmVxdWlyZWRfaWQKCiAgICAgICAgICAgICAgICAjIEFkZCBkZXBlbmRlbmN5IGluZm8KICAgICAgICAgICAgICAgIGRlcF9pbmZvID0gewogICAgICAgICAgICAgICAgICAgICJ0ZW1wbGF0ZV9pZCI6IHJlcXVpcmVkX3RlbXBsYXRlLmlkLAogICAgICAgICAgICAgICAgICAgICJ0ZW1wbGF0ZV9uYW1lIjogcmVxdWlyZWRfdGVtcGxhdGUubmFtZSwKICAgICAgICAgICAgICAgICAgICAidGVtcGxhdGVfcmVmZXJlbmNlIjogcmVxdWlyZWRfdGVtcGxhdGUucmVmZXJlbmNlLAogICAgICAgICAgICAgICAgICAgICJyZXF1aXJlZF9zdGF0ZV9pZCI6IGRlcGVuZGVuY3kuc3RhdGVfcmVxdWlyZWRfaWQuaWQKICAgICAgICAgICAgICAgICAgICBpZiBkZXBlbmRlbmN5LnN0YXRlX3JlcXVpcmVkX2lkCiAgICAgICAgICAgICAgICAgICAgZWxzZSBOb25lLAogICAgICAgICAgICAgICAgICAgICJyZXF1aXJlZF9zdGF0ZV9uYW1lIjogZGVwZW5kZW5jeS5zdGF0ZV9yZXF1aXJlZF9pZC5uYW1lCiAgICAgICAgICAgICAgICAgICAgaWYgZGVwZW5kZW5jeS5zdGF0ZV9yZXF1aXJlZF9pZAogICAgICAgICAgICAgICAgICAgIGVsc2UgTm9uZSwKICAgICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgICBncmFwaFt0ZW1wbGF0ZS5pZF1bImRlcGVuZGVuY2llcyJdLmFwcGVuZChkZXBfaW5mbykKCiAgICAgICAgICAgICAgICAjIEFkZCByZXF1aXJlZCB0ZW1wbGF0ZSB0byBzdGFjayBpZiBub3QgeWV0IHZpc2l0ZWQKICAgICAgICAgICAgICAgIGlmIHJlcXVpcmVkX3RlbXBsYXRlLmlkIG5vdCBpbiB2aXNpdGVkOgogICAgICAgICAgICAgICAgICAgIHN0YWNrLmFwcGVuZChyZXF1aXJlZF90ZW1wbGF0ZSkKCiAgICAgICAgIyBDYWxjdWxhdGUgZGVwZW5kZW5jeSBsZXZlbHMgKGRpc3RhbmNlIGZyb20gcm9vdCB0ZW1wbGF0ZSkKICAgICAgICBzZWxmLl9jYWxjdWxhdGVfZGVwZW5kZW5jeV9sZXZlbHMoZ3JhcGgpCgogICAgICAgIHJldHVybiBncmFwaAoKICAgIGRlZiBfY2FsY3VsYXRlX2RlcGVuZGVuY3lfbGV2ZWxzKHNlbGYsIGdyYXBoKToKICAgICAgICAiIiJDYWxjdWxhdGUgdGhlIGRlcGVuZGVuY3kgbGV2ZWwgZm9yIGVhY2ggdGVtcGxhdGUgaW4gdGhlIGdyYXBoCgogICAgICAgIEFyZ3M6CiAgICAgICAgICAgIGdyYXBoIChkaWN0KTogVGhlIGRlcGVuZGVuY3kgZ3JhcGggdG8gdXBkYXRlIHdpdGggbGV2ZWxzCiAgICAgICAgIiIiCiAgICAgICAgIyBTdGFydCB3aXRoIHRoZSByb290IHRlbXBsYXRlIChjdXJyZW50IHRlbXBsYXRlKSBhdCBsZXZlbCAwCiAgICAgICAgcXVldWUgPSBbKHNlbGYuaWQsIDApXQogICAgICAgIGxldmVscyA9IHtzZWxmLmlkOiAwfQoKICAgICAgICB3aGlsZSBxdWV1ZToKICAgICAgICAgICAgdGVtcGxhdGVfaWQsIGxldmVsID0gcXVldWUucG9wKDApCgogICAgICAgICAgICBpZiB0ZW1wbGF0ZV9pZCBub3QgaW4gZ3JhcGg6CiAgICAgICAgICAgICAgICBjb250aW51ZQoKICAgICAgICAgICAgIyBVcGRhdGUgdGhlIGxldmVsIGluIHRoZSBncmFwaAogICAgICAgICAgICBncmFwaFt0ZW1wbGF0ZV9pZF1bImxldmVsIl0gPSBsZXZlbAoKICAgICAgICAgICAgIyBQcm9jZXNzIGRlcGVuZGVuY2llcwogICAgICAgICAgICBmb3IgZGVwIGluIGdyYXBoW3RlbXBsYXRlX2lkXVsiZGVwZW5kZW5jaWVzIl06CiAgICAgICAgICAgICAgICBkZXBfdGVtcGxhdGVfaWQgPSBkZXBbInRlbXBsYXRlX2lkIl0KICAgICAgICAgICAgICAgIG5ld19sZXZlbCA9IGxldmVsICsgMQoKICAgICAgICAgICAgICAgICMgT25seSB1cGRhdGUgaWYgd2UgaGF2ZW4ndCBzZWVuIHRoaXMgdGVtcGxhdGUKICAgICAgICAgICAgICAgICMgb3IgZm91bmQgYSBzaG9ydGVyIHBhdGgKICAgICAgICAgICAgICAgIGlmIGRlcF90ZW1wbGF0ZV9pZCBub3QgaW4gbGV2ZWxzIG9yIGxldmVsc1tkZXBfdGVtcGxhdGVfaWRdID4gbmV3X2xldmVsOgogICAgICAgICAgICAgICAgICAgIGxldmVsc1tkZXBfdGVtcGxhdGVfaWRdID0gbmV3X2xldmVsCiAgICAgICAgICAgICAgICAgICAgcXVldWUuYXBwZW5kKChkZXBfdGVtcGxhdGVfaWQsIG5ld19sZXZlbCkpCgogICAgZGVmIF90b3BvbG9naWNhbF9zb3J0X2RlcGVuZGVuY3lfZ3JhcGgoc2VsZiwgZ3JhcGgpOgogICAgICAgICIiIlRvcG9sb2dpY2FsIG9yZGVyOiBwcmVyZXF1aXNpdGUgdGVtcGxhdGVzIGJlZm9yZSBkZXBlbmRlbnRzLgoKICAgICAgICBGb3IgZWFjaCBlZGdlIGBgcmVxdWlyZWQgLT4gZGVwZW5kZW50YGAgKGBgZGVwZW5kZW50YGAgbGlzdHMgYGByZXF1aXJlZGBgCiAgICAgICAgaW4gYGB0ZW1wbGF0ZV9yZXF1aXJlc19pZHNgYCksIGBgcmVxdWlyZWRgYCBhcHBlYXJzIGVhcmxpZXIgaW4gdGhlIHJlc3VsdC4KCiAgICAgICAgVGllLWJyZWFrOiBzbWFsbGVzdCB0ZW1wbGF0ZSBpZCBmaXJzdCAoZGV0ZXJtaW5pc3RpYykuCgogICAgICAgIEFyZ3M6CiAgICAgICAgICAgIGdyYXBoIChkaWN0KTogT3V0cHV0IG9mIDptZXRoOmBfYnVpbGRfZGVwZW5kZW5jeV9ncmFwaGAuCgogICAgICAgIFJldHVybnM6CiAgICAgICAgICAgIGxpc3Q6IFRlbXBsYXRlIGlkcyBpbiB0b3BvbG9naWNhbCBvcmRlciwgb3IgZW1wdHkgbGlzdCBpZiB0aGUgZ3JhcGgKICAgICAgICAgICAgICAgIGhhcyBhIGN5Y2xlLgogICAgICAgICIiIgogICAgICAgIGFkaiA9IGRlZmF1bHRkaWN0KGxpc3QpCiAgICAgICAgaW5kZWdyZWUgPSB7dGlkOiAwIGZvciB0aWQgaW4gZ3JhcGh9CgogICAgICAgIGZvciB0aWQgaW4gZ3JhcGg6CiAgICAgICAgICAgIGZvciBkZXAgaW4gZ3JhcGhbdGlkXVsiZGVwZW5kZW5jaWVzIl06CiAgICAgICAgICAgICAgICBkZXBfaWQgPSBkZXBbInRlbXBsYXRlX2lkIl0KICAgICAgICAgICAgICAgIGlmIGRlcF9pZCBub3QgaW4gZ3JhcGg6CiAgICAgICAgICAgICAgICAgICAgY29udGludWUKICAgICAgICAgICAgICAgIGFkaltkZXBfaWRdLmFwcGVuZCh0aWQpCiAgICAgICAgICAgICAgICBpbmRlZ3JlZVt0aWRdICs9IDEKCiAgICAgICAgaGVhcCA9IFt0aWQgZm9yIHRpZCBpbiBncmFwaCBpZiBpbmRlZ3JlZVt0aWRdID09IDBdCiAgICAgICAgaGVhcHEuaGVhcGlmeShoZWFwKQoKICAgICAgICB0b3BvID0gW10KICAgICAgICB3aGlsZSBoZWFwOgogICAgICAgICAgICBub2RlID0gaGVhcHEuaGVhcHBvcChoZWFwKQogICAgICAgICAgICB0b3BvLmFwcGVuZChub2RlKQogICAgICAgICAgICBmb3Igc3VjYyBpbiBzb3J0ZWQoYWRqW25vZGVdKToKICAgICAgICAgICAgICAgIGluZGVncmVlW3N1Y2NdIC09IDEKICAgICAgICAgICAgICAgIGlmIGluZGVncmVlW3N1Y2NdID09IDA6CiAgICAgICAgICAgICAgICAgICAgaGVhcHEuaGVhcHB1c2goaGVhcCwgc3VjYykKCiAgICAgICAgaWYgbGVuKHRvcG8pICE9IGxlbihncmFwaCk6CiAgICAgICAgICAgIHJldHVybiBbXQoKICAgICAgICByZXR1cm4gdG9wbwoKICAgIGRlZiBfZ2V0X2FsbF9kZXBlbmRlbmNpZXNfbGV2ZWxfZmFsbGJhY2soc2VsZiwgZ3JhcGgpOgogICAgICAgICIiIkZhbGxiYWNrIG9yZGVyIHdoZW4gdGhlIGRlcGVuZGVuY3kgZ3JhcGggaGFzIGEgY3ljbGU6IHNvcnQgYnkgbGV2ZWwuIiIiCiAgICAgICAgZGVwZW5kZW5jaWVzX3dpdGhfbGV2ZWxzID0gW10KICAgICAgICBmb3IgdGVtcGxhdGVfaWQsIGluZm8gaW4gZ3JhcGguaXRlbXMoKToKICAgICAgICAgICAgaWYgdGVtcGxhdGVfaWQgIT0gc2VsZi5pZDoKICAgICAgICAgICAgICAgIGRlcGVuZGVuY2llc193aXRoX2xldmVscy5hcHBlbmQoKGluZm9bInRlbXBsYXRlIl0sIGluZm9bImxldmVsIl0pKQoKICAgICAgICBkZXBlbmRlbmNpZXNfd2l0aF9sZXZlbHMuc29ydChrZXk9bGFtYmRhIHg6IHhbMV0pCiAgICAgICAgcmV0dXJuIFt0IGZvciB0LCBfbGV2ZWwgaW4gZGVwZW5kZW5jaWVzX3dpdGhfbGV2ZWxzXQoKICAgIGRlZiBfZ2V0X2FsbF9kZXBlbmRlbmNpZXMoc2VsZik6CiAgICAgICAgIiIiR2V0IGFsbCB0ZW1wbGF0ZXMgdGhhdCB0aGlzIHRlbXBsYXRlIGRlcGVuZHMgb24gKGRpcmVjdGx5IG9yIGluZGlyZWN0bHkpLgoKICAgICAgICBPcmRlciBpcyAqKnJldmVyc2UgdG9wb2xvZ2ljYWwqKgogICAgICAgIChzZWUgOm1ldGg6YF90b3BvbG9naWNhbF9zb3J0X2RlcGVuZGVuY3lfZ3JhcGhgKToKICAgICAgICBgYGN4LnRvd2VyLmpldC50ZW1wbGF0ZS5pbnN0YWxsYGAgYXNzaWducyBpbmNyZWFzaW5nIGBgb3JkZXJgYCBhbmQgcnVucwogICAgICAgIHRhc2tzIHdpdGggaGlnaGVzdCBgYG9yZGVyYGAgZmlyc3QsIHNvIHByZXJlcXVpc2l0ZXMgbXVzdCBhcHBlYXIgKipsYXRlcioqCiAgICAgICAgaW4gdGhpcyBsaXN0IHRoYW4gdGVtcGxhdGVzIHRoYXQgZGVwZW5kIG9uIHRoZW0uCgogICAgICAgIFJldHVybnM6CiAgICAgICAgICAgIGxpc3Q6IGBgY3gudG93ZXIuamV0LnRlbXBsYXRlYGAgcmVjb3JkcyBleGNsdWRpbmcgYGBzZWxmYGAuCiAgICAgICAgIiIiCiAgICAgICAgc2VsZi5lbnN1cmVfb25lKCkKICAgICAgICBncmFwaCA9IHNlbGYuX2J1aWxkX2RlcGVuZGVuY3lfZ3JhcGgoKQoKICAgICAgICB0b3BvX29yZGVyID0gc2VsZi5fdG9wb2xvZ2ljYWxfc29ydF9kZXBlbmRlbmN5X2dyYXBoKGdyYXBoKQogICAgICAgIGlmIG5vdCB0b3BvX29yZGVyOgogICAgICAgICAgICBfbG9nZ2VyLndhcm5pbmcoCiAgICAgICAgICAgICAgICAiRGVwZW5kZW5jeSBjeWNsZSBvciBpbnZhbGlkIGdyYXBoIGZvciB0ZW1wbGF0ZSAlczsgIgogICAgICAgICAgICAgICAgInVzaW5nIGxldmVsLWJhc2VkIGRlcGVuZGVuY3kgb3JkZXIiLAogICAgICAgICAgICAgICAgc2VsZi5uYW1lLAogICAgICAgICAgICApCiAgICAgICAgICAgIHJldHVybiBzZWxmLl9nZXRfYWxsX2RlcGVuZGVuY2llc19sZXZlbF9mYWxsYmFjayhncmFwaCkKCiAgICAgICAgZGVwZW5kZW5jaWVzID0gW10KICAgICAgICBmb3IgdGlkIGluIHJldmVyc2VkKHRvcG9fb3JkZXIpOgogICAgICAgICAgICBpZiB0aWQgPT0gc2VsZi5pZDoKICAgICAgICAgICAgICAgIGNvbnRpbnVlCiAgICAgICAgICAgIGRlcGVuZGVuY2llcy5hcHBlbmQoZ3JhcGhbdGlkXVsidGVtcGxhdGUiXSkKCiAgICAgICAgcmV0dXJuIGRlcGVuZGVuY2llcwoKICAgIGRlZiBfY2hlY2tfZGVwZW5kZW5jeV9zYXRpc2ZhY3Rpb24oc2VsZiwgc2VydmVyKToKICAgICAgICAiIiJDaGVjayBpZiBhbGwgZGVwZW5kYW50IHRlbXBsYXRlcyBhcmUgaW5zdGFsbGVkIG9uIHRoZSBzZXJ2ZXIuCgogICAgICAgIEFyZ3M6CiAgICAgICAgICAgIHNlcnZlciAoY3gudG93ZXIuc2VydmVyKCkpOiBTZXJ2ZXIgdG8gY2hlY2sgZGVwZW5kZW5jaWVzIGZvcgoKICAgICAgICBSZXR1cm5zOgogICAgICAgICAgICBsaXN0OiBUZW1wbGF0ZXMgdGhhdCBhcmUgbm90IGluc3RhbGxlZCBvbiB0aGUgc2VydmVyCiAgICAgICAgIiIiCiAgICAgICAgZGVwZW5kZW5jaWVzID0gc2VsZi5fZ2V0X2FsbF9kZXBlbmRlbmNpZXMoKQoKICAgICAgICBtaXNzaW5nX3RlbXBsYXRlcyA9IFtdCgogICAgICAgIGZvciBkZXBlbmRlbmN5IGluIGRlcGVuZGVuY2llczoKICAgICAgICAgICAgaWYgc2VydmVyIGFuZCBzZXJ2ZXIuaWQgbm90IGluIGRlcGVuZGVuY3kuc2VydmVyX2lkcy5pZHM6CiAgICAgICAgICAgICAgICBtaXNzaW5nX3RlbXBsYXRlcy5hcHBlbmQoZGVwZW5kZW5jeSkKCiAgICAgICAgcmV0dXJuIG1pc3NpbmdfdGVtcGxhdGVzCgogICAgZGVmIF9nZXRfYWxsX2RlcGVuZF9vbl90aGlzKHNlbGYpOgogICAgICAgICIiIkdldCBhbGwgdGVtcGxhdGVzIHRoYXQgZGVwZW5kIG9uIHRoaXMgdGVtcGxhdGUgKGRpcmVjdGx5IG9yIGluZGlyZWN0bHkpCgogICAgICAgIFJldHVybnM6CiAgICAgICAgICAgIHJlY29yZHNldDogQWxsIHRlbXBsYXRlcyB0aGF0IGRlcGVuZCBvbiB0aGlzIHRlbXBsYXRlCiAgICAgICAgIiIiCiAgICAgICAgc2VsZi5lbnN1cmVfb25lKCkKCiAgICAgICAgIyBGaW5kIGFsbCB0ZW1wbGF0ZXMgdGhhdCBoYXZlIHRoaXMgdGVtcGxhdGUgYXMgYSBkZXBlbmRlbmN5CiAgICAgICAgZGVwZW5kZW50X3RlbXBsYXRlcyA9IHNldCgpCgogICAgICAgICMgU3RhcnQgd2l0aCBkaXJlY3QgZGVwZW5kZW50cwogICAgICAgIGRpcmVjdF9kZXBlbmRlbnRzID0gc2VsZi5lbnZbImN4LnRvd2VyLmpldC50ZW1wbGF0ZSJdLnNlYXJjaCgKICAgICAgICAgICAgWygidGVtcGxhdGVfcmVxdWlyZXNfaWRzLnRlbXBsYXRlX3JlcXVpcmVkX2lkIiwgIj0iLCBzZWxmLmlkKV0KICAgICAgICApCgogICAgICAgICMgVXNlIGEgcXVldWUgdG8gZmluZCBpbmRpcmVjdCBkZXBlbmRlbnRzCiAgICAgICAgcXVldWUgPSBsaXN0KGRpcmVjdF9kZXBlbmRlbnRzKQogICAgICAgIHByb2Nlc3NlZCA9IHNldCgpCgogICAgICAgIHdoaWxlIHF1ZXVlOgogICAgICAgICAgICBjdXJyZW50X3RlbXBsYXRlID0gcXVldWUucG9wKDApCgogICAgICAgICAgICBpZiBjdXJyZW50X3RlbXBsYXRlLmlkIGluIHByb2Nlc3NlZDoKICAgICAgICAgICAgICAgIGNvbnRpbnVlCgogICAgICAgICAgICBwcm9jZXNzZWQuYWRkKGN1cnJlbnRfdGVtcGxhdGUuaWQpCiAgICAgICAgICAgIGRlcGVuZGVudF90ZW1wbGF0ZXMuYWRkKGN1cnJlbnRfdGVtcGxhdGUuaWQpCgogICAgICAgICAgICAjIEZpbmQgdGVtcGxhdGVzIHRoYXQgZGVwZW5kIG9uIHRoZSBjdXJyZW50IHRlbXBsYXRlCiAgICAgICAgICAgIG5leHRfbGV2ZWxfZGVwZW5kZW50cyA9IHNlbGYuZW52WyJjeC50b3dlci5qZXQudGVtcGxhdGUiXS5zZWFyY2goCiAgICAgICAgICAgICAgICBbCiAgICAgICAgICAgICAgICAgICAgKAogICAgICAgICAgICAgICAgICAgICAgICAidGVtcGxhdGVfcmVxdWlyZXNfaWRzLnRlbXBsYXRlX3JlcXVpcmVkX2lkIiwKICAgICAgICAgICAgICAgICAgICAgICAgIj0iLAogICAgICAgICAgICAgICAgICAgICAgICBjdXJyZW50X3RlbXBsYXRlLmlkLAogICAgICAgICAgICAgICAgICAgICkKICAgICAgICAgICAgICAgIF0KICAgICAgICAgICAgKQoKICAgICAgICAgICAgZm9yIHRlbXBsYXRlIGluIG5leHRfbGV2ZWxfZGVwZW5kZW50czoKICAgICAgICAgICAgICAgIGlmIHRlbXBsYXRlLmlkIG5vdCBpbiBwcm9jZXNzZWQ6CiAgICAgICAgICAgICAgICAgICAgcXVldWUuYXBwZW5kKHRlbXBsYXRlKQoKICAgICAgICByZXR1cm4gc2VsZi5lbnZbImN4LnRvd2VyLmpldC50ZW1wbGF0ZSJdLmJyb3dzZShsaXN0KGRlcGVuZGVudF90ZW1wbGF0ZXMpKQoKICAgICMgKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKwogICAgIyAgIFNWRyBHcmFwaCBHZW5lcmF0aW9uCiAgICAjICsrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysKCiAgICBkZWYgX2dlbmVyYXRlX3N2Z19ncmFwaChzZWxmLCBncmFwaF9kYXRhKToKICAgICAgICAiIiJHZW5lcmF0ZSBTVkcgZGVwZW5kZW5jeSBncmFwaAoKICAgICAgICBBcmdzOgogICAgICAgICAgICBncmFwaF9kYXRhIChkaWN0KTogRGljdGlvbmFyeSBjb250YWluaW5nIHRlbXBsYXRlIGRlcGVuZGVuY3kgaW5mb3JtYXRpb24KCiAgICAgICAgUmV0dXJuczoKICAgICAgICAgICAgYnl0ZXM6IEJhc2U2NCBlbmNvZGVkIFNWRyBjb250ZW50CiAgICAgICAgIiIiCiAgICAgICAgd2lkdGgsIGhlaWdodCA9IDgwMCwgNjAwCgogICAgICAgICMgQ3JlYXRlIFNWRyByb290CiAgICAgICAgc3ZnID0gRVQuRWxlbWVudCgKICAgICAgICAgICAgInN2ZyIsCiAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgICJ3aWR0aCI6IHN0cih3aWR0aCksCiAgICAgICAgICAgICAgICAiaGVpZ2h0Ijogc3RyKGhlaWdodCksCiAgICAgICAgICAgICAgICAieG1sbnMiOiAiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciLAogICAgICAgICAgICAgICAgInZpZXdCb3giOiBmIjAgMCB7d2lkdGh9IHtoZWlnaHR9IiwKICAgICAgICAgICAgfSwKICAgICAgICApCgogICAgICAgICMgQWRkIHN0eWxlcwogICAgICAgIHN0eWxlID0gRVQuU3ViRWxlbWVudChzdmcsICJzdHlsZSIpCiAgICAgICAgc3R5bGUudGV4dCA9ICIiIgogICAgICAgICAgICAubm9kZSB7IHN0cm9rZTogIzMzMzsgc3Ryb2tlLXdpZHRoOiAyOyB9CiAgICAgICAgICAgIC5lZGdlIHsgc3Ryb2tlOiAjNjY2OyBzdHJva2Utd2lkdGg6IDI7IG1hcmtlci1lbmQ6IHVybCgjYXJyb3doZWFkKTsgfQogICAgICAgICAgICAudGV4dCB7IGZvbnQtZmFtaWx5OiBBcmlhbDsgZm9udC1zaXplOiAxNHB4OyB0ZXh0LWFuY2hvcjogbWlkZGxlOyBmb250LXdlaWdodDogYm9sZDsgfQogICAgICAgICAgICAuZWRnZS1sYWJlbCB7IGZvbnQtZmFtaWx5OiBBcmlhbDsgZm9udC1zaXplOiAxMnB4OyB0ZXh0LWFuY2hvcjogbWlkZGxlOyBmaWxsOiAjNDQ0OyB9CiAgICAgICAgICAgIC5yb290LW5vZGUgeyBmaWxsOiBsaWdodGJsdWU7IH0KICAgICAgICAgICAgLmRpcmVjdC1kZXAgeyBmaWxsOiBsaWdodGdyZWVuOyB9CiAgICAgICAgICAgIC5pbmRpcmVjdC1kZXAgeyBmaWxsOiBsaWdodHllbGxvdzsgfQogICAgICAgICIiIiAgIyBub3FhOiBFNTAxCgogICAgICAgICMgQWRkIGFycm93IG1hcmtlcgogICAgICAgIGRlZnMgPSBFVC5TdWJFbGVtZW50KHN2ZywgImRlZnMiKQogICAgICAgIG1hcmtlciA9IEVULlN1YkVsZW1lbnQoCiAgICAgICAgICAgIGRlZnMsCiAgICAgICAgICAgICJtYXJrZXIiLAogICAgICAgICAgICB7CiAgICAgICAgICAgICAgICAiaWQiOiAiYXJyb3doZWFkIiwKICAgICAgICAgICAgICAgICJtYXJrZXJXaWR0aCI6ICIxMCIsCiAgICAgICAgICAgICAgICAibWFya2VySGVpZ2h0IjogIjciLAogICAgICAgICAgICAgICAgInJlZlgiOiAiOSIsCiAgICAgICAgICAgICAgICAicmVmWSI6ICIzLjUiLAogICAgICAgICAgICAgICAgIm9yaWVudCI6ICJhdXRvIiwKICAgICAgICAgICAgfSwKICAgICAgICApCiAgICAgICAgRVQuU3ViRWxlbWVudChtYXJrZXIsICJwb2x5Z29uIiwgeyJwb2ludHMiOiAiMCAwLCAxMCAzLjUsIDAgNyIsICJmaWxsIjogIiM2NjYifSkKCiAgICAgICAgaWYgbm90IGdyYXBoX2RhdGEgb3IgbGVuKGdyYXBoX2RhdGEpIDw9IDE6CiAgICAgICAgICAgICMgU2luZ2xlIG5vZGUKICAgICAgICAgICAgc2VsZi5fYWRkX3NpbmdsZV9ub2RlX3N2ZyhzdmcsIHdpZHRoLCBoZWlnaHQpCiAgICAgICAgZWxzZToKICAgICAgICAgICAgIyBNdWx0aXBsZSBub2RlcyAtIGFycmFuZ2UgaW4gbGV2ZWxzCiAgICAgICAgICAgIHNlbGYuX2FkZF9tdWx0aV9ub2RlX3N2ZyhzdmcsIGdyYXBoX2RhdGEsIHdpZHRoLCBoZWlnaHQpCgogICAgICAgICMgQ29udmVydCB0byBzdHJpbmcgYW5kIHRoZW4gdG8gYmFzZTY0CiAgICAgICAgc3ZnX3N0cmluZyA9IEVULnRvc3RyaW5nKHN2ZywgZW5jb2Rpbmc9InVuaWNvZGUiKQogICAgICAgIHJldHVybiBiYXNlNjQuYjY0ZW5jb2RlKHN2Z19zdHJpbmcuZW5jb2RlKCJ1dGYtOCIpKQoKICAgIGRlZiBfYWRkX3NpbmdsZV9ub2RlX3N2ZyhzZWxmLCBzdmcsIHdpZHRoLCBoZWlnaHQpOgogICAgICAgICIiIkFkZCBhIHNpbmdsZSBub2RlIHRvIHRoZSBTVkcgZm9yIHRlbXBsYXRlcyB3aXRoIG5vIGRlcGVuZGVuY2llcwoKICAgICAgICBBcmdzOgogICAgICAgICAgICBzdmcgKHhtbC5ldHJlZS5FbGVtZW50VHJlZS5FbGVtZW50KTogU1ZHIHJvb3QgZWxlbWVudAogICAgICAgICAgICB3aWR0aCAoaW50KTogU1ZHIHdpZHRoCiAgICAgICAgICAgIGhlaWdodCAoaW50KTogU1ZHIGhlaWdodAogICAgICAgICIiIgogICAgICAgIG5vZGVfd2lkdGgsIG5vZGVfaGVpZ2h0ID0gMjAwLCA2MAogICAgICAgIHggPSB3aWR0aCAvLyAyIC0gbm9kZV93aWR0aCAvLyAyCiAgICAgICAgeSA9IGhlaWdodCAvLyAyIC0gbm9kZV9oZWlnaHQgLy8gMgoKICAgICAgICAjIERyYXcgbm9kZSByZWN0YW5nbGUKICAgICAgICBFVC5TdWJFbGVtZW50KAogICAgICAgICAgICBzdmcsCiAgICAgICAgICAgICJyZWN0IiwKICAgICAgICAgICAgewogICAgICAgICAgICAgICAgIngiOiBzdHIoeCksCiAgICAgICAgICAgICAgICAieSI6IHN0cih5KSwKICAgICAgICAgICAgICAgICJ3aWR0aCI6IHN0cihub2RlX3dpZHRoKSwKICAgICAgICAgICAgICAgICJoZWlnaHQiOiBzdHIobm9kZV9oZWlnaHQpLAogICAgICAgICAgICAgICAgImNsYXNzIjogIm5vZGUgcm9vdC1ub2RlIiwKICAgICAgICAgICAgICAgICJyeCI6ICIxMCIsICAjIFJvdW5kZWQgY29ybmVycwogICAgICAgICAgICB9LAogICAgICAgICkKCiAgICAgICAgIyBBZGQgdGV4dAogICAgICAgIEVULlN1YkVsZW1lbnQoCiAgICAgICAgICAgIHN2ZywKICAgICAgICAgICAgInRleHQiLAogICAgICAgICAgICB7IngiOiBzdHIod2lkdGggLy8gMiksICJ5Ijogc3RyKGhlaWdodCAvLyAyICsgNSksICJjbGFzcyI6ICJ0ZXh0In0sCiAgICAgICAgKS50ZXh0ID0gc2VsZi5uYW1lCgogICAgZGVmIF9hZGRfbXVsdGlfbm9kZV9zdmcoc2VsZiwgc3ZnLCBncmFwaF9kYXRhLCB3aWR0aCwgaGVpZ2h0KToKICAgICAgICAiIiJBZGQgbXVsdGlwbGUgbm9kZXMgYW5kIGVkZ2VzIHRvIHRoZSBTVkcgZm9yIGNvbXBsZXggZGVwZW5kZW5jeSBncmFwaHMKCiAgICAgICAgQXJnczoKICAgICAgICAgICAgc3ZnICh4bWwuZXRyZWUuRWxlbWVudFRyZWUuRWxlbWVudCk6IFNWRyByb290IGVsZW1lbnQKICAgICAgICAgICAgZ3JhcGhfZGF0YSAoZGljdCk6IERpY3Rpb25hcnkgY29udGFpbmluZyB0ZW1wbGF0ZSBkZXBlbmRlbmN5IGluZm9ybWF0aW9uCiAgICAgICAgICAgIHdpZHRoIChpbnQpOiBTVkcgd2lkdGgKICAgICAgICAgICAgaGVpZ2h0IChpbnQpOiBTVkcgaGVpZ2h0CiAgICAgICAgIiIiCiAgICAgICAgIyBHcm91cCB0ZW1wbGF0ZXMgYnkgbGV2ZWwKICAgICAgICBsZXZlbHMgPSB7fQogICAgICAgIGZvciB0ZW1wbGF0ZV9pZCwgaW5mbyBpbiBncmFwaF9kYXRhLml0ZW1zKCk6CiAgICAgICAgICAgIGxldmVsID0gaW5mb1sibGV2ZWwiXQogICAgICAgICAgICBpZiBsZXZlbCBub3QgaW4gbGV2ZWxzOgogICAgICAgICAgICAgICAgbGV2ZWxzW2xldmVsXSA9IFtdCiAgICAgICAgICAgIGxldmVsc1tsZXZlbF0uYXBwZW5kKCh0ZW1wbGF0ZV9pZCwgaW5mbykpCgogICAgICAgIHBvc2l0aW9ucyA9IHt9CiAgICAgICAgbm9kZV93aWR0aCA9IDE4MAogICAgICAgIG5vZGVfaGVpZ2h0ID0gNjAKICAgICAgICBsZXZlbF9oZWlnaHQgPSAxMjAKICAgICAgICBtYXJnaW4gPSA1MAoKICAgICAgICAjIENhbGN1bGF0ZSBwb3NpdGlvbnMgZm9yIGVhY2ggbm9kZQogICAgICAgIGZvciBsZXZlbCwgbm9kZXMgaW4gbGV2ZWxzLml0ZW1zKCk6CiAgICAgICAgICAgIHkgPSBtYXJnaW4gKyBsZXZlbCAqIGxldmVsX2hlaWdodAogICAgICAgICAgICBhdmFpbGFibGVfd2lkdGggPSB3aWR0aCAtIDIgKiBtYXJnaW4KCiAgICAgICAgICAgIGlmIGxlbihub2RlcykgPT0gMToKICAgICAgICAgICAgICAgICMgQ2VudGVyIHNpbmdsZSBub2RlCiAgICAgICAgICAgICAgICB4ID0gd2lkdGggLy8gMgogICAgICAgICAgICAgICAgcG9zaXRpb25zW25vZGVzWzBdWzBdXSA9ICh4LCB5KQogICAgICAgICAgICBlbHNlOgogICAgICAgICAgICAgICAgIyBEaXN0cmlidXRlIG11bHRpcGxlIG5vZGVzCiAgICAgICAgICAgICAgICBzcGFjaW5nID0gYXZhaWxhYmxlX3dpZHRoIC8gbGVuKG5vZGVzKQogICAgICAgICAgICAgICAgZm9yIGksIG5vZGVfdHVwbGUgaW4gZW51bWVyYXRlKG5vZGVzKToKICAgICAgICAgICAgICAgICAgICB0ZW1wbGF0ZV9pZCA9IG5vZGVfdHVwbGVbMF0gICMgRXh0cmFjdCB0ZW1wbGF0ZV9pZCBmcm9tIHR1cGxlCiAgICAgICAgICAgICAgICAgICAgeCA9IG1hcmdpbiArIHNwYWNpbmcgKiAoaSArIDAuNSkKICAgICAgICAgICAgICAgICAgICBwb3NpdGlvbnNbdGVtcGxhdGVfaWRdID0gKHgsIHkpCgogICAgICAgICMgRHJhdyBlZGdlcyBmaXJzdCAoc28gdGhleSBhcHBlYXIgYmVoaW5kIG5vZGVzKQogICAgICAgIHNlbGYuX2RyYXdfc3ZnX2VkZ2VzKHN2ZywgZ3JhcGhfZGF0YSwgcG9zaXRpb25zLCBub2RlX2hlaWdodCkKCiAgICAgICAgIyBEcmF3IG5vZGVzCiAgICAgICAgc2VsZi5fZHJhd19zdmdfbm9kZXMoc3ZnLCBncmFwaF9kYXRhLCBwb3NpdGlvbnMsIG5vZGVfd2lkdGgsIG5vZGVfaGVpZ2h0KQoKICAgIGRlZiBfZHJhd19zdmdfZWRnZXMoc2VsZiwgc3ZnLCBncmFwaF9kYXRhLCBwb3NpdGlvbnMsIG5vZGVfaGVpZ2h0KToKICAgICAgICAiIiJEcmF3IGVkZ2VzIGJldHdlZW4gbm9kZXMgaW4gdGhlIFNWRwoKICAgICAgICBBcmdzOgogICAgICAgICAgICBzdmcgKHhtbC5ldHJlZS5FbGVtZW50VHJlZS5FbGVtZW50KTogU1ZHIHJvb3QgZWxlbWVudAogICAgICAgICAgICBncmFwaF9kYXRhIChkaWN0KTogRGljdGlvbmFyeSBjb250YWluaW5nIHRlbXBsYXRlIGRlcGVuZGVuY3kgaW5mb3JtYXRpb24KICAgICAgICAgICAgcG9zaXRpb25zIChkaWN0KTogRGljdGlvbmFyeSBtYXBwaW5nIHRlbXBsYXRlIElEcyB0byAoeCwgeSkgcG9zaXRpb25zCiAgICAgICAgICAgIG5vZGVfaGVpZ2h0IChpbnQpOiBIZWlnaHQgb2Ygbm9kZXMgZm9yIGVkZ2UgcG9zaXRpb25pbmcKICAgICAgICAiIiIKICAgICAgICBmb3IgdGVtcGxhdGVfaWQsIGluZm8gaW4gZ3JhcGhfZGF0YS5pdGVtcygpOgogICAgICAgICAgICBpZiB0ZW1wbGF0ZV9pZCBpbiBwb3NpdGlvbnM6CiAgICAgICAgICAgICAgICB4MSwgeTEgPSBwb3NpdGlvbnNbdGVtcGxhdGVfaWRdCgogICAgICAgICAgICAgICAgZm9yIGRlcCBpbiBpbmZvWyJkZXBlbmRlbmNpZXMiXToKICAgICAgICAgICAgICAgICAgICBkZXBfaWQgPSBkZXBbInRlbXBsYXRlX2lkIl0KICAgICAgICAgICAgICAgICAgICBpZiBkZXBfaWQgaW4gcG9zaXRpb25zOgogICAgICAgICAgICAgICAgICAgICAgICB4MiwgeTIgPSBwb3NpdGlvbnNbZGVwX2lkXQoKICAgICAgICAgICAgICAgICAgICAgICAgIyBEcmF3IGVkZ2UgbGluZQogICAgICAgICAgICAgICAgICAgICAgICBFVC5TdWJFbGVtZW50KAogICAgICAgICAgICAgICAgICAgICAgICAgICAgc3ZnLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgImxpbmUiLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICJ4MSI6IHN0cih4MSksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgInkxIjogc3RyKHkxICsgbm9kZV9oZWlnaHQgLy8gMiksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIngyIjogc3RyKHgyKSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAieTIiOiBzdHIoeTIgLSBub2RlX2hlaWdodCAvLyAyKSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAiY2xhc3MiOiAiZWRnZSIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICAgICAgICAgICAgICApCgogICAgICAgICAgICAgICAgICAgICAgICAjIEFkZCBlZGdlIGxhYmVsIGlmIHRoZXJlJ3MgYSByZXF1aXJlZCBzdGF0ZQogICAgICAgICAgICAgICAgICAgICAgICBpZiBkZXBbInJlcXVpcmVkX3N0YXRlX25hbWUiXToKICAgICAgICAgICAgICAgICAgICAgICAgICAgIG1pZF94ID0gKHgxICsgeDIpIC8gMgogICAgICAgICAgICAgICAgICAgICAgICAgICAgbWlkX3kgPSAoeTEgKyB5MikgLyAyCgogICAgICAgICAgICAgICAgICAgICAgICAgICAgIyBCYWNrZ3JvdW5kIHJlY3RhbmdsZSBmb3IgbGFiZWwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGxhYmVsX3RleHQgPSBkZXBbInJlcXVpcmVkX3N0YXRlX25hbWUiXQogICAgICAgICAgICAgICAgICAgICAgICAgICAgbGFiZWxfd2lkdGggPSBsZW4obGFiZWxfdGV4dCkgKiA4ICsgMTAKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGxhYmVsX2hlaWdodCA9IDIwCgogICAgICAgICAgICAgICAgICAgICAgICAgICAgRVQuU3ViRWxlbWVudCgKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzdmcsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgInJlY3QiLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIngiOiBzdHIobWlkX3ggLSBsYWJlbF93aWR0aCAvLyAyKSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgInkiOiBzdHIobWlkX3kgLSBsYWJlbF9oZWlnaHQgLy8gMiksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICJ3aWR0aCI6IHN0cihsYWJlbF93aWR0aCksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICJoZWlnaHQiOiBzdHIobGFiZWxfaGVpZ2h0KSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgImZpbGwiOiAid2hpdGUiLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAic3Ryb2tlIjogIiNjY2MiLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAicngiOiAiMyIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICkKCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBFVC5TdWJFbGVtZW50KAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHN2ZywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAidGV4dCIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAieCI6IHN0cihtaWRfeCksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICJ5Ijogc3RyKG1pZF95ICsgNCksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICJjbGFzcyI6ICJlZGdlLWxhYmVsIiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgKS50ZXh0ID0gbGFiZWxfdGV4dAoKICAgIGRlZiBfZHJhd19zdmdfbm9kZXMoc2VsZiwgc3ZnLCBncmFwaF9kYXRhLCBwb3NpdGlvbnMsIG5vZGVfd2lkdGgsIG5vZGVfaGVpZ2h0KToKICAgICAgICAiIiJEcmF3IG5vZGVzIGluIHRoZSBTVkcKCiAgICAgICAgQXJnczoKICAgICAgICAgICAgc3ZnICh4bWwuZXRyZWUuRWxlbWVudFRyZWUuRWxlbWVudCk6IFNWRyByb290IGVsZW1lbnQKICAgICAgICAgICAgZ3JhcGhfZGF0YSAoZGljdCk6IERpY3Rpb25hcnkgY29udGFpbmluZyB0ZW1wbGF0ZSBkZXBlbmRlbmN5IGluZm9ybWF0aW9uCiAgICAgICAgICAgIHBvc2l0aW9ucyAoZGljdCk6IERpY3Rpb25hcnkgbWFwcGluZyB0ZW1wbGF0ZSBJRHMgdG8gKHgsIHkpIHBvc2l0aW9ucwogICAgICAgICAgICBub2RlX3dpZHRoIChpbnQpOiBXaWR0aCBvZiBub2RlcwogICAgICAgICAgICBub2RlX2hlaWdodCAoaW50KTogSGVpZ2h0IG9mIG5vZGVzCiAgICAgICAgIiIiCiAgICAgICAgZm9yIHRlbXBsYXRlX2lkLCBpbmZvIGluIGdyYXBoX2RhdGEuaXRlbXMoKToKICAgICAgICAgICAgaWYgdGVtcGxhdGVfaWQgaW4gcG9zaXRpb25zOgogICAgICAgICAgICAgICAgeCwgeSA9IHBvc2l0aW9uc1t0ZW1wbGF0ZV9pZF0KICAgICAgICAgICAgICAgIHRlbXBsYXRlX29iaiA9IGluZm9bInRlbXBsYXRlIl0KCiAgICAgICAgICAgICAgICAjIERldGVybWluZSBub2RlIGNsYXNzIGJhc2VkIG9uIGxldmVsCiAgICAgICAgICAgICAgICBpZiBpbmZvWyJsZXZlbCJdID09IDA6CiAgICAgICAgICAgICAgICAgICAgbm9kZV9jbGFzcyA9ICJub2RlIHJvb3Qtbm9kZSIKICAgICAgICAgICAgICAgIGVsaWYgaW5mb1sibGV2ZWwiXSA9PSAxOgogICAgICAgICAgICAgICAgICAgIG5vZGVfY2xhc3MgPSAibm9kZSBkaXJlY3QtZGVwIgogICAgICAgICAgICAgICAgZWxzZToKICAgICAgICAgICAgICAgICAgICBub2RlX2NsYXNzID0gIm5vZGUgaW5kaXJlY3QtZGVwIgoKICAgICAgICAgICAgICAgICMgRHJhdyBub2RlIHJlY3RhbmdsZQogICAgICAgICAgICAgICAgRVQuU3ViRWxlbWVudCgKICAgICAgICAgICAgICAgICAgICBzdmcsCiAgICAgICAgICAgICAgICAgICAgInJlY3QiLAogICAgICAgICAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgICAgICAgICAgIngiOiBzdHIoeCAtIG5vZGVfd2lkdGggLy8gMiksCiAgICAgICAgICAgICAgICAgICAgICAgICJ5Ijogc3RyKHkgLSBub2RlX2hlaWdodCAvLyAyKSwKICAgICAgICAgICAgICAgICAgICAgICAgIndpZHRoIjogc3RyKG5vZGVfd2lkdGgpLAogICAgICAgICAgICAgICAgICAgICAgICAiaGVpZ2h0Ijogc3RyKG5vZGVfaGVpZ2h0KSwKICAgICAgICAgICAgICAgICAgICAgICAgImNsYXNzIjogbm9kZV9jbGFzcywKICAgICAgICAgICAgICAgICAgICAgICAgInJ4IjogIjEwIiwgICMgUm91bmRlZCBjb3JuZXJzCiAgICAgICAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgICAgICkKCiAgICAgICAgICAgICAgICAjIEFkZCB0ZXh0ICh0cnVuY2F0ZSBpZiB0b28gbG9uZykKICAgICAgICAgICAgICAgIGRpc3BsYXlfbmFtZSA9IHRlbXBsYXRlX29iai5uYW1lCiAgICAgICAgICAgICAgICBpZiBsZW4oZGlzcGxheV9uYW1lKSA+IDIwOgogICAgICAgICAgICAgICAgICAgIGRpc3BsYXlfbmFtZSA9IGRpc3BsYXlfbmFtZVs6MTddICsgIi4uLiIKCiAgICAgICAgICAgICAgICBFVC5TdWJFbGVtZW50KAogICAgICAgICAgICAgICAgICAgIHN2ZywgInRleHQiLCB7IngiOiBzdHIoeCksICJ5Ijogc3RyKHkgKyA1KSwgImNsYXNzIjogInRleHQifQogICAgICAgICAgICAgICAgKS50ZXh0ID0gZGlzcGxheV9uYW1lCgogICAgIyArKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrCiAgICAjICAgQWNjZXNzIHJvbGUgbWl4aW4gZnVuY3Rpb25zCiAgICAjICsrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysKICAgIGRlZiBfZ2V0X3Bvc3RfY3JlYXRlX2ZpZWxkcyhzZWxmKToKICAgICAgICAiIiIKICAgICAgICBBZGQgZmllbGRzIHRoYXQgc2hvdWxkIGJlIHBvcHVsYXRlZCBhZnRlciBqZXQgdGVtcGxhdGUgY3JlYXRpb24KICAgICAgICAiIiIKICAgICAgICByZXMgPSBzdXBlcigpLl9nZXRfcG9zdF9jcmVhdGVfZmllbGRzKCkKICAgICAgICByZXR1cm4gcmVzICsgWyJ2YXJpYWJsZV92YWx1ZV9pZHMiLCAic2VydmVyX2xvZ19pZHMiXQo= |