OneTimeAuthentificationLink
10.1.1
Rother OSS GmbH
https://rother-oss.com/
GNU GENERAL PUBLIC LICENSE Version 3, 29 June 2007
Update to OTOBO 10.1.
Automatically creates customer users and gives them access via one time authentification tokens.
10.0.x
2022-09-22 06:25:18
opms
IyAtLQojIE9UT0JPIGlzIGEgd2ViLWJhc2VkIHRpY2tldGluZyBzeXN0ZW0gZm9yIHNlcnZpY2Ugb3JnYW5pc2F0aW9ucy4KIyAtLQojIENvcHlyaWdodCAoQykgMjAwMS0yMDIwIE9UUlMgQUcsIGh0dHBzOi8vb3Rycy5jb20vCiMgQ29weXJpZ2h0IChDKSAyMDE5LTIwMjIgUm90aGVyIE9TUyBHbWJILCBodHRwczovL290b2JvLmRlLwojIC0tCiMgJG9yaWdpbjogb3RvYm8gLSBlODk0YWVmNjEwMjA4ZmRjNDAxYTRkZjgxNGNhNTk2NTgyOTJmYmJhIC0gS2VybmVsL1N5c3RlbS9DdXN0b21lckF1dGgucG0KIyAtLQojIFRoaXMgcHJvZ3JhbSBpcyBmcmVlIHNvZnR3YXJlOiB5b3UgY2FuIHJlZGlzdHJpYnV0ZSBpdCBhbmQvb3IgbW9kaWZ5IGl0IHVuZGVyCiMgdGhlIHRlcm1zIG9mIHRoZSBHTlUgR2VuZXJhbCBQdWJsaWMgTGljZW5zZSBhcyBwdWJsaXNoZWQgYnkgdGhlIEZyZWUgU29mdHdhcmUKIyBGb3VuZGF0aW9uLCBlaXRoZXIgdmVyc2lvbiAzIG9mIHRoZSBMaWNlbnNlLCBvciAoYXQgeW91ciBvcHRpb24pIGFueSBsYXRlciB2ZXJzaW9uLgojIFRoaXMgcHJvZ3JhbSBpcyBkaXN0cmlidXRlZCBpbiB0aGUgaG9wZSB0aGF0IGl0IHdpbGwgYmUgdXNlZnVsLCBidXQgV0lUSE9VVAojIEFOWSBXQVJSQU5UWTsgd2l0aG91dCBldmVuIHRoZSBpbXBsaWVkIHdhcnJhbnR5IG9mIE1FUkNIQU5UQUJJTElUWSBvciBGSVRORVNTCiMgRk9SIEEgUEFSVElDVUxBUiBQVVJQT1NFLiBTZWUgdGhlIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlIGZvciBtb3JlIGRldGFpbHMuCiMgWW91IHNob3VsZCBoYXZlIHJlY2VpdmVkIGEgY29weSBvZiB0aGUgR05VIEdlbmVyYWwgUHVibGljIExpY2Vuc2UKIyBhbG9uZyB3aXRoIHRoaXMgcHJvZ3JhbS4gSWYgbm90LCBzZWUgPGh0dHBzOi8vd3d3LmdudS5vcmcvbGljZW5zZXMvPi4KIyAtLQoKcGFja2FnZSBLZXJuZWw6OlN5c3RlbTo6Q3VzdG9tZXJBdXRoOwoKdXNlIHN0cmljdDsKdXNlIHdhcm5pbmdzOwoKdXNlIEtlcm5lbDo6TGFuZ3VhZ2UgcXcoVHJhbnNsYXRhYmxlKTsKCm91ciBAT2JqZWN0RGVwZW5kZW5jaWVzID0gKAogICAgJ0tlcm5lbDo6Q29uZmlnJywKICAgICdLZXJuZWw6OlN5c3RlbTo6Q3VzdG9tZXJVc2VyJywKICAgICdLZXJuZWw6OlN5c3RlbTo6RGF0ZVRpbWUnLAogICAgJ0tlcm5lbDo6U3lzdGVtOjpMb2cnLAogICAgJ0tlcm5lbDo6U3lzdGVtOjpNYWluJywKICAgICdLZXJuZWw6OlN5c3RlbTo6U3lzdGVtTWFpbnRlbmFuY2UnLAopOwoKPWhlYWQxIE5BTUUKCktlcm5lbDo6U3lzdGVtOjpDdXN0b21lckF1dGggLSBjdXN0b21lciBhdXRoZW50aWNhdGlvbiBtb2R1bGUuCgo9aGVhZDEgREVTQ1JJUFRJT04KClRoZSBhdXRoZW50aWNhdGlvbiBtb2R1bGUgZm9yIHRoZSBjdXN0b21lciBpbnRlcmZhY2UuCgo9aGVhZDEgUFVCTElDIElOVEVSRkFDRQoKPWhlYWQyIG5ldygpCgpEb24ndCB1c2UgdGhlIGNvbnN0cnVjdG9yIGRpcmVjdGx5LCB1c2UgdGhlIE9iamVjdE1hbmFnZXIgaW5zdGVhZDoKCiAgICBteSAkQ3VzdG9tZXJBdXRoT2JqZWN0ID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkN1c3RvbWVyQXV0aCcpOwoKPWN1dAoKc3ViIG5ldyB7CiAgICBteSAoICRUeXBlLCAlUGFyYW0gKSA9IEBfOwoKICAgICMgYWxsb2NhdGUgbmV3IGhhc2ggZm9yIG9iamVjdAogICAgbXkgJFNlbGYgPSB7fTsKICAgIGJsZXNzKCAkU2VsZiwgJFR5cGUgKTsKCiAgICAjIGdldCBuZWVkZWQgb2JqZWN0cwogICAgbXkgJE1haW5PYmplY3QgICA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpNYWluJyk7CiAgICBteSAkQ29uZmlnT2JqZWN0ID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpDb25maWcnKTsKCiAgICAjIGxvYWQgYXV0aCBtb2R1bGVzCiAgICBDT1VOVDoKICAgIGZvciBteSAkQ291bnQgKCAnJywgMSAuLiAxMCApIHsKCiAgICAgICAgbXkgJEdlbmVyaWNNb2R1bGUgPSAkQ29uZmlnT2JqZWN0LT5HZXQoIkN1c3RvbWVyOjpBdXRoTW9kdWxlJENvdW50Iik7CgogICAgICAgIG5leHQgQ09VTlQgaWYgISRHZW5lcmljTW9kdWxlOwoKICAgICAgICBpZiAoICEkTWFpbk9iamVjdC0+UmVxdWlyZSgkR2VuZXJpY01vZHVsZSkgKSB7CiAgICAgICAgICAgICRNYWluT2JqZWN0LT5EaWUoIkNhbid0IGxvYWQgYmFja2VuZCBtb2R1bGUgJEdlbmVyaWNNb2R1bGUhICRAIik7CiAgICAgICAgfQoKICAgICAgICAkU2VsZi0+eyJBdXRoQmFja2VuZCRDb3VudCJ9ID0gJEdlbmVyaWNNb2R1bGUtPm5ldyggJXskU2VsZn0sIENvdW50ID0+ICRDb3VudCApOwogICAgfQoKICAgICMgbG9hZCAyZmFjdG9yIGF1dGggbW9kdWxlcwogICAgQ09VTlQ6CiAgICBmb3IgbXkgJENvdW50ICggJycsIDEgLi4gMTAgKSB7CgogICAgICAgIG15ICRHZW5lcmljTW9kdWxlID0gJENvbmZpZ09iamVjdC0+R2V0KCJDdXN0b21lcjo6QXV0aFR3b0ZhY3Rvck1vZHVsZSRDb3VudCIpOwoKICAgICAgICBuZXh0IENPVU5UIGlmICEkR2VuZXJpY01vZHVsZTsKCiAgICAgICAgaWYgKCAhJE1haW5PYmplY3QtPlJlcXVpcmUoJEdlbmVyaWNNb2R1bGUpICkgewogICAgICAgICAgICAkTWFpbk9iamVjdC0+RGllKCJDYW4ndCBsb2FkIGJhY2tlbmQgbW9kdWxlICRHZW5lcmljTW9kdWxlISAkQCIpOwogICAgICAgIH0KCiAgICAgICAgJFNlbGYtPnsiQXV0aFR3b0ZhY3RvckJhY2tlbmQkQ291bnQifSA9ICRHZW5lcmljTW9kdWxlLT5uZXcoICV7JFNlbGZ9LCBDb3VudCA9PiAkQ291bnQgKTsKICAgIH0KCiAgICAjIEluaXRpYWxpemUgbGFzdCBlcnJvciBtZXNzYWdlCiAgICAkU2VsZi0+e0xhc3RFcnJvck1lc3NhZ2V9ID0gJyc7CgogICAgcmV0dXJuICRTZWxmOwp9Cgo9aGVhZDIgR2V0T3B0aW9uKCkKCkdldCBtb2R1bGUgb3B0aW9ucy4gQ3VycmVudGx5IHRoZXJlIGlzIGp1c3Qgb25lIG9wdGlvbiwgIlByZUF1dGgiLgoKICAgIGlmICggJEF1dGhPYmplY3QtPkdldE9wdGlvbiggV2hhdCA9PiAnUHJlQXV0aCcgKSApIHsKICAgICAgICBwcmludCAiTm8gbG9naW4gc2NyZWVuIGlzIG5lZWRlZC4gQXV0aGVudGljYXRpb24gaXMgYmFzZWQgb24gc29tZSBvdGhlciBvcHRpb25zLiBFLiBnLiAkRU5We1JFTU9URV9VU0VSfVxuIjsKICAgIH0KCj1jdXQKCnN1YiBHZXRPcHRpb24gewogICAgbXkgKCAkU2VsZiwgJVBhcmFtICkgPSBAXzsKCiAgICByZXR1cm4gJFNlbGYtPntBdXRoQmFja2VuZH0tPkdldE9wdGlvbiglUGFyYW0pOwp9CgojIFJvdGhlciBPU1MgLyBPbmVUaW1lQXV0aGVudGljYXRpb25MaW5rCj1oZWFkMiBFeHRlbmRlZFBhcmFtTmFtZXMoKQoKR2V0IG5hbWVzIG9mIGV4dGVuZGVkIHBhcmFtcyB3aGljaCBwcm92aWRlIGF1dGhlbnRpZmljYXRpb24gaW5mb3JtYXRpb24KCiAgICBteSBAUGFyYW1OYW1lcyA9ICRBdXRoT2JqZWN0LT5FeHRlbmRlZFBhcmFtTmFtZXMoKTsKCj1jdXQKCnN1YiBFeHRlbmRlZFBhcmFtTmFtZXMgewogICAgbXkgKCAkU2VsZiwgJVBhcmFtICkgPSBAXzsKCiAgICBteSAlTmFtZXM7CiAgICBDT1VOVDoKICAgIGZvciAoICcnLCAxIC4uIDEwICkgewogICAgICAgIG5leHQgQ09VTlQgaWYgISRTZWxmLT57IkF1dGhCYWNrZW5kJF8ifTsKICAgICAgICBuZXh0IENPVU5UIGlmICEkU2VsZi0+eyJBdXRoQmFja2VuZCRfIn0tPmNhbignRXh0ZW5kZWRQYXJhbU5hbWVzJyk7CgogICAgICAgIGZvciBteSAkRXh0TmFtZSAoICRTZWxmLT57IkF1dGhCYWNrZW5kJF8ifS0+RXh0ZW5kZWRQYXJhbU5hbWVzKCkgKSB7CiAgICAgICAgICAgICROYW1lc3skRXh0TmFtZX0gPSAxOwogICAgICAgIH0KICAgIH0KCiAgICByZXR1cm4gKCBrZXlzICVOYW1lcyApOwp9CiMgRU8gT25lVGltZUF1dGhlbnRpY2F0aW9uTGluawoKPWhlYWQyIEF1dGgoKQoKVGhlIGF1dGhlbnRpY2F0aW9uIGZ1bmN0aW9uLgoKICAgIGlmICggJEF1dGhPYmplY3QtPkF1dGgoIFVzZXIgPT4gJFVzZXIsIFB3ID0+ICRQdyApICkgewogICAgICAgIHByaW50ICJBdXRoIG9rIVxuIjsKICAgIH0KICAgIGVsc2UgewogICAgICAgIHByaW50ICJBdXRoIGludmFsaWQhXG4iOwogICAgfQoKPWN1dAoKc3ViIEF1dGggewogICAgbXkgKCAkU2VsZiwgJVBhcmFtICkgPSBAXzsKCiAgICAjIGdldCBjdXN0b21lciB1c2VyIG9iamVjdAogICAgbXkgJEN1c3RvbWVyVXNlck9iamVjdCA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpDdXN0b21lclVzZXInKTsKICAgIG15ICRDb25maWdPYmplY3QgICAgICAgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OkNvbmZpZycpOwoKICAgICMgdXNlIGFsbCAxMSBhdXRoIGJhY2tlbmRzIGFuZCByZXR1cm4gb24gZmlyc3QgdHJ1ZQogICAgbXkgJFVzZXI7CiAgICBDT1VOVDoKICAgIGZvciBteSAkQ291bnQgKCAnJywgMSAuLiAxMCApIHsKCiAgICAgICAgIyBuZXh0IG9uIG5vIGNvbmZpZyBzZXR0aW5nCiAgICAgICAgbmV4dCBDT1VOVCBpZiAhJFNlbGYtPnsiQXV0aEJhY2tlbmQkQ291bnQifTsKCiAgICAgICAgIyBjaGVjayBhdXRoIGJhY2tlbmQKICAgICAgICAkVXNlciA9ICRTZWxmLT57IkF1dGhCYWNrZW5kJENvdW50In0tPkF1dGgoJVBhcmFtKTsKCiMgUm90aGVyIE9TUyAvIE9uZVRpbWVBdXRoZW50aWNhdGlvbkxpbmsKICAgICAgICBpZiAoIHJlZiAkVXNlciAmJiByZWYgJFVzZXIgZXEgJ0hBU0gnICYmICRVc2VyLT57RXJyb3J9ICkgewogICAgICAgICAgICAkU2VsZi0+e0xhc3RFcnJvck1lc3NhZ2V9ID0gJFVzZXItPntFcnJvcn07CiAgICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiMgRU8gT25lVGltZUF1dGhlbnRpY2F0aW9uTGluawoKICAgICAgICAjIG5leHQgb24gbm8gc3VjY2VzcwogICAgICAgIG5leHQgQ09VTlQgaWYgISRVc2VyOwoKICAgICAgICAjIGNoZWNrIDJmYWN0b3IgYXV0aCBiYWNrZW5kcwogICAgICAgIG15ICRUd29GYWN0b3JBdXRoOwogICAgICAgIFRXT0ZBQ1RPUlNPVVJDRToKICAgICAgICBmb3IgbXkgJENvdW50ICggJycsIDEgLi4gMTAgKSB7CgogICAgICAgICAgICAjIHJldHVybiBvbiBubyBjb25maWcgc2V0dGluZwogICAgICAgICAgICBuZXh0IFRXT0ZBQ1RPUlNPVVJDRSBpZiAhJFNlbGYtPnsiQXV0aFR3b0ZhY3RvckJhY2tlbmQkQ291bnQifTsKCiAgICAgICAgICAgICMgMmZhY3RvciBiYWNrZW5kCiAgICAgICAgICAgIG15ICRBdXRoT2sgPSAkU2VsZi0+eyJBdXRoVHdvRmFjdG9yQmFja2VuZCRDb3VudCJ9LT5BdXRoKAogICAgICAgICAgICAgICAgVHdvRmFjdG9yVG9rZW4gPT4gJFBhcmFte1R3b0ZhY3RvclRva2VufSwKICAgICAgICAgICAgICAgIFVzZXIgICAgICAgICAgID0+ICRVc2VyLAogICAgICAgICAgICApOwogICAgICAgICAgICAkVHdvRmFjdG9yQXV0aCA9ICRBdXRoT2sgPyAncGFzc2VkJyA6ICdmYWlsZWQnOwoKICAgICAgICAgICAgbGFzdCBUV09GQUNUT1JTT1VSQ0UgaWYgJEF1dGhPazsKICAgICAgICB9CgogICAgICAgICMgaWYgYXQgbGVhc3Qgb25lIDJmYWN0b3IgYXV0aCBiYWNrZW5kIHdhcyBjaGVja2VkIGJ1dCBub25lIHdhcyBzdWNjZXNzZnVsLAogICAgICAgICMgaXQgY291bnRzIGFzIGEgZmFpbGVkIGxvZ2luCiAgICAgICAgaWYgKCAkVHdvRmFjdG9yQXV0aCAmJiAkVHdvRmFjdG9yQXV0aCBuZSAncGFzc2VkJyApIHsKICAgICAgICAgICAgJFVzZXIgPSB1bmRlZjsKICAgICAgICAgICAgbGFzdCBDT1VOVDsKICAgICAgICB9CgogICAgICAgICMgcmVtZW1iZXIgYXV0aCBiYWNrZW5kCiAgICAgICAgaWYgKCRVc2VyKSB7CiAgICAgICAgICAgICRDdXN0b21lclVzZXJPYmplY3QtPlNldFByZWZlcmVuY2VzKAogICAgICAgICAgICAgICAgS2V5ICAgID0+ICdVc2VyQXV0aEJhY2tlbmQnLAogICAgICAgICAgICAgICAgVmFsdWUgID0+ICRDb3VudCwKICAgICAgICAgICAgICAgIFVzZXJJRCA9PiAkVXNlciwKICAgICAgICAgICAgKTsKCiAgICAgICAgICAgIGxhc3QgQ09VTlQ7CiAgICAgICAgfQogICAgfQoKICAgICMgY2hlY2sgaWYgcmVjb3JkIGV4aXN0cwogICAgaWYgKCAhJFVzZXIgKSB7CiAgICAgICAgbXkgJUN1c3RvbWVyRGF0YSA9ICRDdXN0b21lclVzZXJPYmplY3QtPkN1c3RvbWVyVXNlckRhdGFHZXQoIFVzZXIgPT4gJFBhcmFte1VzZXJ9ICk7CiAgICAgICAgaWYgKCVDdXN0b21lckRhdGEpIHsKICAgICAgICAgICAgbXkgJENvdW50ID0gJEN1c3RvbWVyRGF0YXtVc2VyTG9naW5GYWlsZWR9IHx8IDA7CiAgICAgICAgICAgICRDb3VudCsrOwogICAgICAgICAgICAkQ3VzdG9tZXJVc2VyT2JqZWN0LT5TZXRQcmVmZXJlbmNlcygKICAgICAgICAgICAgICAgIEtleSAgICA9PiAnVXNlckxvZ2luRmFpbGVkJywKICAgICAgICAgICAgICAgIFZhbHVlICA9PiAkQ291bnQsCiAgICAgICAgICAgICAgICBVc2VySUQgPT4gJEN1c3RvbWVyRGF0YXtVc2VyTG9naW59LAogICAgICAgICAgICApOwogICAgICAgIH0KICAgICAgICByZXR1cm47CiAgICB9CgogICAgIyBjaGVjayBpZiB1c2VyIGlzIHZhbGlkCiAgICBteSAlQ3VzdG9tZXJEYXRhID0gJEN1c3RvbWVyVXNlck9iamVjdC0+Q3VzdG9tZXJVc2VyRGF0YUdldCggVXNlciA9PiAkVXNlciApOwogICAgaWYgKCBkZWZpbmVkICRDdXN0b21lckRhdGF7VmFsaWRJRH0gJiYgJEN1c3RvbWVyRGF0YXtWYWxpZElEfSBuZSAxICkgewogICAgICAgICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpMb2cnKS0+TG9nKAogICAgICAgICAgICBQcmlvcml0eSA9PiAnbm90aWNlJywKICAgICAgICAgICAgTWVzc2FnZSAgPT4gIkN1c3RvbWVyVXNlcjogJyRVc2VyJyBpcyBzZXQgdG8gaW52YWxpZCwgY2FuJ3QgbG9naW4hIiwKICAgICAgICApOwogICAgICAgIHJldHVybjsKICAgIH0KCiAgICByZXR1cm4gJFVzZXIgaWYgISVDdXN0b21lckRhdGE7CgogICAgIyByZXNldCBmYWlsZWQgbG9naW5zCiAgICAkQ3VzdG9tZXJVc2VyT2JqZWN0LT5TZXRQcmVmZXJlbmNlcygKICAgICAgICBLZXkgICAgPT4gJ1VzZXJMb2dpbkZhaWxlZCcsCiAgICAgICAgVmFsdWUgID0+IDAsCiAgICAgICAgVXNlcklEID0+ICRDdXN0b21lckRhdGF7VXNlckxvZ2lufSwKICAgICk7CgogICAgIyBvbiBzeXN0ZW0gbWFpbnRlbmFuY2UgY3VzdG9tZXJzCiAgICAjIHNob3VsZG4ndCBiZSBhbGxvd2VkIGdldCBpbnRvIHRoZSBzeXN0ZW0KICAgIG15ICRBY3RpdmVNYWludGVuYW5jZSA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpTeXN0ZW1NYWludGVuYW5jZScpLT5TeXN0ZW1NYWludGVuYW5jZUlzQWN0aXZlKCk7CgogICAgIyBjaGVjayBpZiBzeXN0ZW0gbWFpbnRlbmFuY2UgaXMgYWN0aXZlCiAgICBpZiAoJEFjdGl2ZU1haW50ZW5hbmNlKSB7CgogICAgICAgICRTZWxmLT57TGFzdEVycm9yTWVzc2FnZX0gPQogICAgICAgICAgICAkQ29uZmlnT2JqZWN0LT5HZXQoJ1N5c3RlbU1haW50ZW5hbmNlOjpJc0FjdGl2ZURlZmF1bHRMb2dpbkVycm9yTWVzc2FnZScpCiAgICAgICAgICAgIHx8IFRyYW5zbGF0YWJsZSgiSXQgaXMgY3VycmVudGx5IG5vdCBwb3NzaWJsZSB0byBsb2dpbiBkdWUgdG8gYSBzY2hlZHVsZWQgc3lzdGVtIG1haW50ZW5hbmNlLiIpOwoKICAgICAgICByZXR1cm47CiAgICB9CgogICAgIyBsYXN0IGxvZ2luIHByZWZlcmVuY2VzIHVwZGF0ZQogICAgbXkgJERhdGVUaW1lT2JqZWN0ID0gJEtlcm5lbDo6T00tPkNyZWF0ZSgnS2VybmVsOjpTeXN0ZW06OkRhdGVUaW1lJyk7CgogICAgJEN1c3RvbWVyVXNlck9iamVjdC0+U2V0UHJlZmVyZW5jZXMoCiAgICAgICAgS2V5ICAgID0+ICdVc2VyTGFzdExvZ2luJywKICAgICAgICBWYWx1ZSAgPT4gJERhdGVUaW1lT2JqZWN0LT5Ub0Vwb2NoKCksCiAgICAgICAgVXNlcklEID0+ICRDdXN0b21lckRhdGF7VXNlckxvZ2lufSwKICAgICk7CgogICAgcmV0dXJuICRVc2VyOwp9Cgo9aGVhZDIgUHJlQXV0aCgpCgpDYWxsIHRoZSBQcmVBdXRoIG1ldGhvZCBvZiB0aGUgQXV0aEJhY2tlbmQKCiAgICBteSAkUHJlQXV0aEluZm8gPSAkQXV0aE9iamVjdC0+UHJlQXV0aCgKICAgICAgICBSZXF1ZXN0ZWRVUkwgPT4gJFJlcXVlc3RlZFVSTCwKICAgICk7Cgo9Y3V0CgpzdWIgUHJlQXV0aCB7CiAgICBteSAoICRTZWxmLCAlUGFyYW0gKSA9IEBfOwoKICAgIHJldHVybiBpZiAhJFNlbGYtPntBdXRoQmFja2VuZH0tPmNhbignUHJlQXV0aCcpOwoKICAgIHJldHVybiAkU2VsZi0+e0F1dGhCYWNrZW5kfS0+UHJlQXV0aCglUGFyYW0pOwp9Cgo9aGVhZDIgUG9zdEF1dGgoKQoKQ2FsbCB0aGUgUG9zdEF1dGggbWV0aG9kIG9mIHRoZSBBdXRoQmFja2VuZAoKICAgIG15ICRQb3N0QXV0aEluZm8gPSAkQXV0aE9iamVjdC0+UG9zdEF1dGgoKTsKCj1jdXQKCnN1YiBQb3N0QXV0aCB7CiAgICBteSAoICRTZWxmLCAlUGFyYW0gKSA9IEBfOwoKICAgIHJldHVybiBpZiAhJFNlbGYtPntBdXRoQmFja2VuZH0tPmNhbignUG9zdEF1dGgnKTsKCiAgICByZXR1cm4gJFNlbGYtPntBdXRoQmFja2VuZH0tPlBvc3RBdXRoKCVQYXJhbSk7Cn0KCj1oZWFkMiBMb2dvdXQoKQoKQ2FsbCB0aGUgTG9nb3V0IG1ldGhvZCBvZiB0aGUgQXV0aEJhY2tlbmQKCiAgICBteSAkTG9nb3V0SW5mbyA9ICRBdXRoT2JqZWN0LT5Mb2dvdXQoKTsKCj1jdXQKCnN1YiBMb2dvdXQgewogICAgbXkgKCAkU2VsZiwgJVBhcmFtICkgPSBAXzsKCiAgICByZXR1cm4gaWYgISRTZWxmLT57QXV0aEJhY2tlbmR9LT5jYW4oJ0xvZ291dCcpOwoKICAgIHJldHVybiAkU2VsZi0+e0F1dGhCYWNrZW5kfS0+TG9nb3V0KCVQYXJhbSk7Cn0KCj1oZWFkMiBHZXRMYXN0RXJyb3JNZXNzYWdlKCkKClJldHJpZXZlICRTZWxmLT57TGFzdEVycm9yTWVzc2FnZX0gY29udGVudC4KCiAgICBteSAkQXV0aEVycm9yTWVzc2FnZSA9ICRBdXRoT2JqZWN0LT5HZXRMYXN0RXJyb3JNZXNzYWdlKCk7CgogICAgUmVzdWx0OgoKICAgICAgICAkQXV0aEVycm9yTWVzc2FnZSA9ICJBbiBlcnJvciBzdHJpbmcgbWVzc2FnZS4iOwoKPWN1dAoKc3ViIEdldExhc3RFcnJvck1lc3NhZ2UgewogICAgbXkgKCAkU2VsZiwgJVBhcmFtICkgPSBAXzsKCiAgICByZXR1cm4gJFNlbGYtPntMYXN0RXJyb3JNZXNzYWdlfTsKfQoKMTsK
IyAtLQojIE9UT0JPIGlzIGEgd2ViLWJhc2VkIHRpY2tldGluZyBzeXN0ZW0gZm9yIHNlcnZpY2Ugb3JnYW5pc2F0aW9ucy4KIyAtLQojIENvcHlyaWdodCAoQykgMjAwMS0yMDIwIE9UUlMgQUcsIGh0dHBzOi8vb3Rycy5jb20vCiMgQ29weXJpZ2h0IChDKSAyMDE5LTIwMjIgUm90aGVyIE9TUyBHbWJILCBodHRwczovL290b2JvLmRlLwojIC0tCiMgJG9yaWdpbjogb3RvYm8gLSBlODk0YWVmNjEwMjA4ZmRjNDAxYTRkZjgxNGNhNTk2NTgyOTJmYmJhIC0gS2VybmVsL1N5c3RlbS9UZW1wbGF0ZUdlbmVyYXRvci5wbQojIC0tCiMgVGhpcyBwcm9ncmFtIGlzIGZyZWUgc29mdHdhcmU6IHlvdSBjYW4gcmVkaXN0cmlidXRlIGl0IGFuZC9vciBtb2RpZnkgaXQgdW5kZXIKIyB0aGUgdGVybXMgb2YgdGhlIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlIGFzIHB1Ymxpc2hlZCBieSB0aGUgRnJlZSBTb2Z0d2FyZQojIEZvdW5kYXRpb24sIGVpdGhlciB2ZXJzaW9uIDMgb2YgdGhlIExpY2Vuc2UsIG9yIChhdCB5b3VyIG9wdGlvbikgYW55IGxhdGVyIHZlcnNpb24uCiMgVGhpcyBwcm9ncmFtIGlzIGRpc3RyaWJ1dGVkIGluIHRoZSBob3BlIHRoYXQgaXQgd2lsbCBiZSB1c2VmdWwsIGJ1dCBXSVRIT1VUCiMgQU5ZIFdBUlJBTlRZOyB3aXRob3V0IGV2ZW4gdGhlIGltcGxpZWQgd2FycmFudHkgb2YgTUVSQ0hBTlRBQklMSVRZIG9yIEZJVE5FU1MKIyBGT1IgQSBQQVJUSUNVTEFSIFBVUlBPU0UuIFNlZSB0aGUgR05VIEdlbmVyYWwgUHVibGljIExpY2Vuc2UgZm9yIG1vcmUgZGV0YWlscy4KIyBZb3Ugc2hvdWxkIGhhdmUgcmVjZWl2ZWQgYSBjb3B5IG9mIHRoZSBHTlUgR2VuZXJhbCBQdWJsaWMgTGljZW5zZQojIGFsb25nIHdpdGggdGhpcyBwcm9ncmFtLiBJZiBub3QsIHNlZSA8aHR0cHM6Ly93d3cuZ251Lm9yZy9saWNlbnNlcy8+LgojIC0tCgpwYWNrYWdlIEtlcm5lbDo6U3lzdGVtOjpUZW1wbGF0ZUdlbmVyYXRvcjsKIyMgbm9maWx0ZXIoVGlkeUFsbDo6UGx1Z2luOjpPVE9CTzo6UGVybDo6TGF5b3V0T2JqZWN0KQoKdXNlIHN0cmljdDsKdXNlIHdhcm5pbmdzOwoKdXNlIEtlcm5lbDo6TGFuZ3VhZ2U7Cgp1c2UgS2VybmVsOjpTeXN0ZW06OlZhcmlhYmxlQ2hlY2sgcXcoOmFsbCk7CgpvdXIgQE9iamVjdERlcGVuZGVuY2llcyA9ICgKICAgICdLZXJuZWw6OkNvbmZpZycsCiAgICAnS2VybmVsOjpTeXN0ZW06OkF1dG9SZXNwb25zZScsCiAgICAnS2VybmVsOjpTeXN0ZW06OkNvbW11bmljYXRpb25DaGFubmVsJywKICAgICdLZXJuZWw6OlN5c3RlbTo6Q3VzdG9tZXJVc2VyJywKICAgICdLZXJuZWw6OlN5c3RlbTo6RHluYW1pY0ZpZWxkJywKICAgICdLZXJuZWw6OlN5c3RlbTo6RHluYW1pY0ZpZWxkOjpCYWNrZW5kJywKICAgICdLZXJuZWw6OlN5c3RlbTo6RW5jb2RlJywKICAgICdLZXJuZWw6OlN5c3RlbTo6SFRNTFV0aWxzJywKICAgICdLZXJuZWw6OlN5c3RlbTo6TG9nJywKICAgICdLZXJuZWw6OlN5c3RlbTo6UXVldWUnLAogICAgJ0tlcm5lbDo6U3lzdGVtOjpTYWx1dGF0aW9uJywKICAgICdLZXJuZWw6OlN5c3RlbTo6U2lnbmF0dXJlJywKICAgICdLZXJuZWw6OlN5c3RlbTo6U3RhbmRhcmRUZW1wbGF0ZScsCiAgICAnS2VybmVsOjpTeXN0ZW06OlN5c3RlbUFkZHJlc3MnLAogICAgJ0tlcm5lbDo6U3lzdGVtOjpUaWNrZXQnLAogICAgJ0tlcm5lbDo6U3lzdGVtOjpUaWNrZXQ6OkFydGljbGUnLAogICAgJ0tlcm5lbDo6U3lzdGVtOjpVc2VyJywKICAgICdLZXJuZWw6Ok91dHB1dDo6SFRNTDo6TGF5b3V0JywKICAgICdLZXJuZWw6OlN5c3RlbTo6RGF0ZVRpbWUnLAopOwoKPWhlYWQxIE5BTUUKCktlcm5lbDo6U3lzdGVtOjpUZW1wbGF0ZUdlbmVyYXRvciAtIHNpZ25hdHVyZSBsaWIKCj1oZWFkMSBERVNDUklQVElPTgoKQWxsIHNpZ25hdHVyZSBmdW5jdGlvbnMuCgo9aGVhZDEgUFVCTElDIElOVEVSRkFDRQoKPWhlYWQyIG5ldygpCgpEb24ndCB1c2UgdGhlIGNvbnN0cnVjdG9yIGRpcmVjdGx5LCB1c2UgdGhlIE9iamVjdE1hbmFnZXIgaW5zdGVhZDoKCiAgICBteSAkVGVtcGxhdGVHZW5lcmF0b3JPYmplY3QgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6VGVtcGxhdGVHZW5lcmF0b3InKTsKCj1jdXQKCnN1YiBuZXcgewogICAgbXkgKCAkVHlwZSwgJVBhcmFtICkgPSBAXzsKCiAgICAjIGFsbG9jYXRlIG5ldyBoYXNoIGZvciBvYmplY3QKICAgIG15ICRTZWxmID0ge307CiAgICBibGVzcyggJFNlbGYsICRUeXBlICk7CgogICAgJFNlbGYtPntSaWNoVGV4dH0gPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OkNvbmZpZycpLT5HZXQoJ0Zyb250ZW5kOjpSaWNoVGV4dCcpOwoKICAgIHJldHVybiAkU2VsZjsKfQoKPWhlYWQyIFNhbHV0YXRpb24oKQoKZ2VuZXJhdGUgc2FsdXRhdGlvbgoKICAgIG15ICRTYWx1dGF0aW9uID0gJFRlbXBsYXRlR2VuZXJhdG9yT2JqZWN0LT5TYWx1dGF0aW9uKAogICAgICAgIFRpY2tldElEID0+IDEyMywKICAgICAgICBVc2VySUQgICA9PiAxMjMsCiAgICAgICAgRGF0YSAgICAgPT4gJEFydGljbGVIYXNoUmVmLAogICAgKTsKCnJldHVybnMKICAgIFRleHQKICAgIENvbnRlbnRUeXBlCgo9Y3V0CgpzdWIgU2FsdXRhdGlvbiB7CiAgICBteSAoICRTZWxmLCAlUGFyYW0gKSA9IEBfOwoKICAgICMgY2hlY2sgbmVlZGVkIHN0dWZmCiAgICBmb3IgKHF3KFRpY2tldElEIERhdGEgVXNlcklEKSkgewogICAgICAgIGlmICggISRQYXJhbXskX30gKSB7CiAgICAgICAgICAgICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpMb2cnKS0+TG9nKAogICAgICAgICAgICAgICAgUHJpb3JpdHkgPT4gJ2Vycm9yJywKICAgICAgICAgICAgICAgIE1lc3NhZ2UgID0+ICJOZWVkICRfISIKICAgICAgICAgICAgKTsKICAgICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgIH0KCiAgICAjIEdldCB0aWNrZXQuCiAgICBteSAlVGlja2V0ID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OlRpY2tldCcpLT5UaWNrZXRHZXQoCiAgICAgICAgVGlja2V0SUQgICAgICA9PiAkUGFyYW17VGlja2V0SUR9LAogICAgICAgIER5bmFtaWNGaWVsZHMgPT4gMSwKICAgICk7CgogICAgIyBHZXQgcXVldWUuCiAgICBteSAlUXVldWUgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6UXVldWUnKS0+UXVldWVHZXQoCiAgICAgICAgSUQgPT4gJFRpY2tldHtRdWV1ZUlEfSwKICAgICk7CgogICAgIyBHZXQgc2FsdXRhdGlvbi4KICAgIG15ICVTYWx1dGF0aW9uID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OlNhbHV0YXRpb24nKS0+U2FsdXRhdGlvbkdldCgKICAgICAgICBJRCA9PiAkUXVldWV7U2FsdXRhdGlvbklEfSwKICAgICk7CgogICAgIyBkbyB0ZXh0L3BsYWluIHRvIHRleHQvaHRtbCBjb252ZXJ0CiAgICBpZiAoICRTZWxmLT57UmljaFRleHR9ICYmICRTYWx1dGF0aW9ue0NvbnRlbnRUeXBlfSA9fiAvdGV4dFwvcGxhaW4vaSApIHsKICAgICAgICAkU2FsdXRhdGlvbntDb250ZW50VHlwZX0gPSAndGV4dC9odG1sJzsKICAgICAgICAkU2FsdXRhdGlvbntUZXh0fSAgICAgICAgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6SFRNTFV0aWxzJyktPlRvSFRNTCgKICAgICAgICAgICAgU3RyaW5nID0+ICRTYWx1dGF0aW9ue1RleHR9LAogICAgICAgICk7CiAgICB9CgogICAgIyBkbyB0ZXh0L2h0bWwgdG8gdGV4dC9wbGFpbiBjb252ZXJ0CiAgICBpZiAoICEkU2VsZi0+e1JpY2hUZXh0fSAmJiAkU2FsdXRhdGlvbntDb250ZW50VHlwZX0gPX4gL3RleHRcL2h0bWwvaSApIHsKICAgICAgICAkU2FsdXRhdGlvbntDb250ZW50VHlwZX0gPSAndGV4dC9wbGFpbic7CiAgICAgICAgJFNhbHV0YXRpb257VGV4dH0gICAgICAgID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkhUTUxVdGlscycpLT5Ub0FzY2lpKAogICAgICAgICAgICBTdHJpbmcgPT4gJFNhbHV0YXRpb257VGV4dH0sCiAgICAgICAgKTsKICAgIH0KCiAgICAjIGdldCBsaXN0IHVuc3VwcG9ydGVkIHRhZ3MgZm9yIHN0YW5kYXJkIHRlbXBsYXRlCiAgICBteSBATGlzdE9mVW5TdXBwb3J0ZWRUYWcgPSBxdyhPVE9CT19BR0VOVF9TVUJKRUNUIE9UT0JPX0FHRU5UX0JPRFkgT1RPQk9fQ1VTVE9NRVJfQk9EWSBPVE9CT19DVVNUT01FUl9TVUJKRUNUKTsKCiAgICBteSAkU2FsdXRhdGlvblRleHQgPSAkU2VsZi0+X1JlbW92ZVVuU3VwcG9ydGVkVGFnKAogICAgICAgIFRleHQgICAgICAgICAgICAgICAgID0+ICRTYWx1dGF0aW9ue1RleHR9IHx8ICcnLAogICAgICAgIExpc3RPZlVuU3VwcG9ydGVkVGFnID0+IFxATGlzdE9mVW5TdXBwb3J0ZWRUYWcsCiAgICApOwoKICAgICMgcmVwbGFjZSBwbGFjZSBob2xkZXIgc3R1ZmYKICAgICRTYWx1dGF0aW9uVGV4dCA9ICRTZWxmLT5fUmVwbGFjZSgKICAgICAgICBSaWNoVGV4dCAgID0+ICRTZWxmLT57UmljaFRleHR9LAogICAgICAgIFRleHQgICAgICAgPT4gJFNhbHV0YXRpb25UZXh0LAogICAgICAgIFRpY2tldERhdGEgPT4gXCVUaWNrZXQsCiAgICAgICAgRGF0YSAgICAgICA9PiAkUGFyYW17RGF0YX0sCiAgICAgICAgVXNlcklEICAgICA9PiAkUGFyYW17VXNlcklEfSwKICAgICk7CgogICAgIyBhZGQgdXJscwogICAgaWYgKCAkU2VsZi0+e1JpY2hUZXh0fSApIHsKICAgICAgICAkU2FsdXRhdGlvblRleHQgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6SFRNTFV0aWxzJyktPkxpbmtRdW90ZSgKICAgICAgICAgICAgU3RyaW5nID0+ICRTYWx1dGF0aW9uVGV4dCwKICAgICAgICApOwogICAgfQoKICAgIHJldHVybiAkU2FsdXRhdGlvblRleHQ7Cn0KCj1oZWFkMiBTaWduYXR1cmUoKQoKZ2VuZXJhdGUgc2FsdXRhdGlvbgoKICAgIG15ICRTaWduYXR1cmUgPSAkVGVtcGxhdGVHZW5lcmF0b3JPYmplY3QtPlNpZ25hdHVyZSgKICAgICAgICBUaWNrZXRJRCA9PiAxMjMsCiAgICAgICAgVXNlcklEICAgPT4gMTIzLAogICAgICAgIERhdGEgICAgID0+ICRBcnRpY2xlSGFzaFJlZiwKICAgICk7CgpvcgoKICAgIG15ICRTaWduYXR1cmUgPSAkVGVtcGxhdGVHZW5lcmF0b3JPYmplY3QtPlNpZ25hdHVyZSgKICAgICAgICBRdWV1ZUlEID0+IDEyMywKICAgICAgICBVc2VySUQgID0+IDEyMywKICAgICAgICBEYXRhICAgID0+ICRBcnRpY2xlSGFzaFJlZiwKICAgICk7CgpyZXR1cm5zCiAgICBUZXh0CiAgICBDb250ZW50VHlwZQoKPWN1dAoKc3ViIFNpZ25hdHVyZSB7CiAgICBteSAoICRTZWxmLCAlUGFyYW0gKSA9IEBfOwoKICAgICMgY2hlY2sgbmVlZGVkIHN0dWZmCiAgICBmb3IgKHF3KERhdGEgVXNlcklEKSkgewogICAgICAgIGlmICggISRQYXJhbXskX30gKSB7CiAgICAgICAgICAgICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpMb2cnKS0+TG9nKAogICAgICAgICAgICAgICAgUHJpb3JpdHkgPT4gJ2Vycm9yJywKICAgICAgICAgICAgICAgIE1lc3NhZ2UgID0+ICJOZWVkICRfISIKICAgICAgICAgICAgKTsKICAgICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgIH0KCiAgICAjIG5lZWQgdGlja2V0IGlkIG9yIHF1ZXVlIGlkCiAgICBpZiAoICEkUGFyYW17VGlja2V0SUR9ICYmICEkUGFyYW17UXVldWVJRH0gKSB7CiAgICAgICAgJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkxvZycpLT5Mb2coCiAgICAgICAgICAgIFByaW9yaXR5ID0+ICdlcnJvcicsCiAgICAgICAgICAgIE1lc3NhZ2UgID0+ICdOZWVkIFRpY2tldElEIG9yIFF1ZXVlSUQhJwogICAgICAgICk7CiAgICAgICAgcmV0dXJuOwogICAgfQoKICAgICMgR2V0IHRpY2tldCBkYXRhLgogICAgbXkgJVRpY2tldDsKICAgIGlmICggJFBhcmFte1RpY2tldElEfSApIHsKICAgICAgICAlVGlja2V0ID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OlRpY2tldCcpLT5UaWNrZXRHZXQoCiAgICAgICAgICAgIFRpY2tldElEICAgICAgPT4gJFBhcmFte1RpY2tldElEfSwKICAgICAgICAgICAgRHluYW1pY0ZpZWxkcyA9PiAxLAogICAgICAgICk7CiAgICB9CgogICAgIyBHZXQgcXVldWUuCiAgICBteSAlUXVldWUgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6UXVldWUnKS0+UXVldWVHZXQoCiAgICAgICAgSUQgPT4gJFRpY2tldHtRdWV1ZUlEfSB8fCAkUGFyYW17UXVldWVJRH0sCiAgICApOwoKICAgICMgR2V0IHNpZ25hdHVyZS4KICAgIG15ICVTaWduYXR1cmUgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6U2lnbmF0dXJlJyktPlNpZ25hdHVyZUdldCgKICAgICAgICBJRCA9PiAkUXVldWV7U2lnbmF0dXJlSUR9LAogICAgKTsKCiAgICAjIGRvIHRleHQvcGxhaW4gdG8gdGV4dC9odG1sIGNvbnZlcnQKICAgIGlmICggJFNlbGYtPntSaWNoVGV4dH0gJiYgJFNpZ25hdHVyZXtDb250ZW50VHlwZX0gPX4gL3RleHRcL3BsYWluL2kgKSB7CiAgICAgICAgJFNpZ25hdHVyZXtDb250ZW50VHlwZX0gPSAndGV4dC9odG1sJzsKICAgICAgICAkU2lnbmF0dXJle1RleHR9ICAgICAgICA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpIVE1MVXRpbHMnKS0+VG9IVE1MKAogICAgICAgICAgICBTdHJpbmcgPT4gJFNpZ25hdHVyZXtUZXh0fSwKICAgICAgICApOwogICAgfQoKICAgICMgZG8gdGV4dC9odG1sIHRvIHRleHQvcGxhaW4gY29udmVydAogICAgaWYgKCAhJFNlbGYtPntSaWNoVGV4dH0gJiYgJFNpZ25hdHVyZXtDb250ZW50VHlwZX0gPX4gL3RleHRcL2h0bWwvaSApIHsKICAgICAgICAkU2lnbmF0dXJle0NvbnRlbnRUeXBlfSA9ICd0ZXh0L3BsYWluJzsKICAgICAgICAkU2lnbmF0dXJle1RleHR9ICAgICAgICA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpIVE1MVXRpbHMnKS0+VG9Bc2NpaSgKICAgICAgICAgICAgU3RyaW5nID0+ICRTaWduYXR1cmV7VGV4dH0sCiAgICAgICAgKTsKICAgIH0KCiAgICAjIGdldCBsaXN0IHVuc3VwcG9ydGVkIHRhZ3MgZm9yIHN0YW5kYXJkIHRlbXBsYXRlCiAgICBteSBATGlzdE9mVW5TdXBwb3J0ZWRUYWcgPSBxdyhPVE9CT19BR0VOVF9TVUJKRUNUIE9UT0JPX0FHRU5UX0JPRFkgT1RPQk9fQ1VTVE9NRVJfQk9EWSBPVE9CT19DVVNUT01FUl9TVUJKRUNUKTsKCiAgICBteSAkU2lnbmF0dXJlVGV4dCA9ICRTZWxmLT5fUmVtb3ZlVW5TdXBwb3J0ZWRUYWcoCiAgICAgICAgVGV4dCAgICAgICAgICAgICAgICAgPT4gJFNpZ25hdHVyZXtUZXh0fSB8fCAnJywKICAgICAgICBMaXN0T2ZVblN1cHBvcnRlZFRhZyA9PiBcQExpc3RPZlVuU3VwcG9ydGVkVGFnLAogICAgKTsKCiAgICAjIHJlcGxhY2UgcGxhY2UgaG9sZGVyIHN0dWZmCiAgICAkU2lnbmF0dXJlVGV4dCA9ICRTZWxmLT5fUmVwbGFjZSgKICAgICAgICBSaWNoVGV4dCAgID0+ICRTZWxmLT57UmljaFRleHR9LAogICAgICAgIFRleHQgICAgICAgPT4gJFNpZ25hdHVyZVRleHQsCiAgICAgICAgVGlja2V0RGF0YSA9PiBcJVRpY2tldCwKICAgICAgICBEYXRhICAgICAgID0+ICRQYXJhbXtEYXRhfSwKICAgICAgICBRdWV1ZUlEICAgID0+ICRQYXJhbXtRdWV1ZUlEfSwKICAgICAgICBVc2VySUQgICAgID0+ICRQYXJhbXtVc2VySUR9LAogICAgKTsKCiAgICAjIGFkZCB1cmxzCiAgICBpZiAoICRTZWxmLT57UmljaFRleHR9ICkgewogICAgICAgICRTaWduYXR1cmVUZXh0ID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkhUTUxVdGlscycpLT5MaW5rUXVvdGUoCiAgICAgICAgICAgIFN0cmluZyA9PiAkU2lnbmF0dXJlVGV4dCwKICAgICAgICApOwogICAgfQoKICAgIHJldHVybiAkU2lnbmF0dXJlVGV4dDsKfQoKPWhlYWQyIFNlbmRlcigpCgpnZW5lcmF0ZSBzZW5kZXIgYWRkcmVzcyAoRlJPTSBzdHJpbmcpIGZvciBlbWFpbHMKCiAgICBteSAkU2VuZGVyID0gJFRlbXBsYXRlR2VuZXJhdG9yT2JqZWN0LT5TZW5kZXIoCiAgICAgICAgUXVldWVJRCAgICA9PiAxMjMsCiAgICAgICAgVXNlcklEICAgICA9PiAxMjMsCiAgICApOwoKcmV0dXJuczoKCiAgICBKb2huIERvZSBhdCBTdXBlciBTdXBwb3J0IDxzZXJ2aWNlQGV4YW1wbGUuY29tPgoKYW5kIGl0IHJldHVybnMgdGhlIHF1b3RlZCByZWFsIG5hbWUgaWYgbmVjZXNzYXJ5CgogICAgIkpvaG4gRG9lLCBTdXBwb3J0IiA8c2VydmljZUBleGFtcGxlLnRsZD4KCj1jdXQKCnN1YiBTZW5kZXIgewogICAgbXkgKCAkU2VsZiwgJVBhcmFtICkgPSBAXzsKCiAgICAjIGNoZWNrIG5lZWRlZCBzdHVmZgogICAgZm9yIChxdyggVXNlcklEIFF1ZXVlSUQpKSB7CiAgICAgICAgaWYgKCAhJFBhcmFteyRffSApIHsKICAgICAgICAgICAgJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkxvZycpLT5Mb2coCiAgICAgICAgICAgICAgICBQcmlvcml0eSA9PiAnZXJyb3InLAogICAgICAgICAgICAgICAgTWVzc2FnZSAgPT4gIk5lZWQgJF8hIgogICAgICAgICAgICApOwogICAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgfQoKICAgICMgZ2V0IHNlbmRlciBhdHRyaWJ1dGVzCiAgICBteSAlQWRkcmVzcyA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpRdWV1ZScpLT5HZXRTeXN0ZW1BZGRyZXNzKAogICAgICAgIFF1ZXVlSUQgPT4gJFBhcmFte1F1ZXVlSUR9LAogICAgKTsKCiAgICAjIGdldCBjb25maWcgb2JqZWN0CiAgICBteSAkQ29uZmlnT2JqZWN0ID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpDb25maWcnKTsKCiAgICAjIGNoZWNrIGNvbmZpZyBmb3IgYWdlbnQgcmVhbCBuYW1lCiAgICBteSAkVXNlQWdlbnRSZWFsTmFtZSA9ICRDb25maWdPYmplY3QtPkdldCgnVGlja2V0OjpEZWZpbmVFbWFpbEZyb20nKTsKICAgIGlmICggJFVzZUFnZW50UmVhbE5hbWUgJiYgJFVzZUFnZW50UmVhbE5hbWUgPX4gL14oQWdlbnROYW1lfEFnZW50TmFtZVN5c3RlbUFkZHJlc3NOYW1lKSQvICkgewoKICAgICAgICAjIGdldCBkYXRhIGZyb20gY3VycmVudCBhZ2VudAogICAgICAgIG15ICVVc2VyRGF0YSA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpVc2VyJyktPkdldFVzZXJEYXRhKAogICAgICAgICAgICBVc2VySUQgICAgICAgID0+ICRQYXJhbXtVc2VySUR9LAogICAgICAgICAgICBOb091dE9mT2ZmaWNlID0+IDEsCiAgICAgICAgKTsKCiAgICAgICAgIyBzZXQgcmVhbCBuYW1lIHdpdGggdXNlciBuYW1lCiAgICAgICAgaWYgKCAkVXNlQWdlbnRSZWFsTmFtZSBlcSAnQWdlbnROYW1lJyApIHsKCiAgICAgICAgICAgICMgY2hlY2sgZm9yIHVzZXIgZGF0YQogICAgICAgICAgICBpZiAoICRVc2VyRGF0YXtVc2VyRnVsbG5hbWV9ICkgewoKICAgICAgICAgICAgICAgICMgcmV3cml0ZSBSZWFsTmFtZQogICAgICAgICAgICAgICAgJEFkZHJlc3N7UmVhbE5hbWV9ID0gIiRVc2VyRGF0YXtVc2VyRnVsbG5hbWV9IjsKICAgICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgIyBzZXQgcmVhbCBuYW1lIHdpdGggdXNlciBuYW1lCiAgICAgICAgaWYgKCAkVXNlQWdlbnRSZWFsTmFtZSBlcSAnQWdlbnROYW1lU3lzdGVtQWRkcmVzc05hbWUnICkgewoKICAgICAgICAgICAgIyBjaGVjayBmb3IgdXNlciBkYXRhCiAgICAgICAgICAgIGlmICggJFVzZXJEYXRhe1VzZXJGdWxsbmFtZX0gKSB7CgogICAgICAgICAgICAgICAgIyByZXdyaXRlIFJlYWxOYW1lCiAgICAgICAgICAgICAgICBteSAkU2VwYXJhdG9yID0gJyAnIC4gJENvbmZpZ09iamVjdC0+R2V0KCdUaWNrZXQ6OkRlZmluZUVtYWlsRnJvbVNlcGFyYXRvcicpCiAgICAgICAgICAgICAgICAgICAgfHwgJyc7CiAgICAgICAgICAgICAgICAkQWRkcmVzc3tSZWFsTmFtZX0gPSAkVXNlckRhdGF7VXNlckZ1bGxuYW1lfSAuICRTZXBhcmF0b3IgLiAnICcgLiAkQWRkcmVzc3tSZWFsTmFtZX07CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICB9CgogICAgIyBwcmVwYXJlIHJlYWxuYW1lIHF1b3RlCiAgICBpZiAoICRBZGRyZXNze1JlYWxOYW1lfSA9fiAvKFsuXXwsfEB8XCh8XCl8OikvICYmICRBZGRyZXNze1JlYWxOYW1lfSAhfiAvXigifCcpLyApIHsKICAgICAgICAkQWRkcmVzc3tSZWFsTmFtZX0gPX4gcy8iLy9nOyAgICAjIHJlbW92ZSBhbnkgcXVvdGVzIHRoYXQgYXJlIGFscmVhZHkgcHJlc2VudAogICAgICAgICRBZGRyZXNze1JlYWxOYW1lfSA9ICciJyAuICRBZGRyZXNze1JlYWxOYW1lfSAuICciJzsKICAgIH0KICAgIG15ICRTZW5kZXIgPSAiJEFkZHJlc3N7UmVhbE5hbWV9IDwkQWRkcmVzc3tFbWFpbH0+IjsKCiAgICByZXR1cm4gJFNlbmRlcjsKfQoKPWhlYWQyIFRlbXBsYXRlKCkKCmdlbmVyYXRlIHRlbXBsYXRlCgogICAgbXkgJFRlbXBsYXRlID0gJFRlbXBsYXRlR2VuZXJhdG9yT2JqZWN0LT5UZW1wbGF0ZSgKICAgICAgICBUZW1wbGF0ZUlEID0+IDEyMwogICAgICAgIFRpY2tldElEICAgPT4gMTIzLCAgICAgICAgICAgICAgICAgICMgT3B0aW9uYWwKICAgICAgICBEYXRhICAgICAgID0+ICRBcnRpY2xlSGFzaFJlZiwgICAgICAjIE9wdGlvbmFsCiAgICAgICAgVXNlcklEICAgICA9PiAxMjMsCiAgICApOwoKUmV0dXJuczoKCiAgICAkVGVtcGxhdGUgPT4gICdTb21lIHRleHQnOwoKPWN1dAoKc3ViIFRlbXBsYXRlIHsKICAgIG15ICggJFNlbGYsICVQYXJhbSApID0gQF87CgogICAgIyBjaGVjayBuZWVkZWQgc3R1ZmYKICAgIGZvciAocXcoVGVtcGxhdGVJRCBVc2VySUQpKSB7CiAgICAgICAgaWYgKCAhJFBhcmFteyRffSApIHsKICAgICAgICAgICAgJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkxvZycpLT5Mb2coCiAgICAgICAgICAgICAgICBQcmlvcml0eSA9PiAnZXJyb3InLAogICAgICAgICAgICAgICAgTWVzc2FnZSAgPT4gIk5lZWQgJF8hIgogICAgICAgICAgICApOwogICAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgfQoKICAgIG15ICVUZW1wbGF0ZSA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpTdGFuZGFyZFRlbXBsYXRlJyktPlN0YW5kYXJkVGVtcGxhdGVHZXQoCiAgICAgICAgSUQgPT4gJFBhcmFte1RlbXBsYXRlSUR9LAogICAgKTsKCiAgICAjIGRvIHRleHQvcGxhaW4gdG8gdGV4dC9odG1sIGNvbnZlcnQKICAgIGlmICgKICAgICAgICAkU2VsZi0+e1JpY2hUZXh0fQogICAgICAgICYmICRUZW1wbGF0ZXtDb250ZW50VHlwZX0gPX4gL3RleHRcL3BsYWluL2kKICAgICAgICAmJiAkVGVtcGxhdGV7VGVtcGxhdGV9CiAgICAgICAgKQogICAgewogICAgICAgICRUZW1wbGF0ZXtDb250ZW50VHlwZX0gPSAndGV4dC9odG1sJzsKICAgICAgICAkVGVtcGxhdGV7VGVtcGxhdGV9ICAgID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkhUTUxVdGlscycpLT5Ub0hUTUwoCiAgICAgICAgICAgIFN0cmluZyA9PiAkVGVtcGxhdGV7VGVtcGxhdGV9LAogICAgICAgICk7CiAgICB9CgogICAgIyBkbyB0ZXh0L2h0bWwgdG8gdGV4dC9wbGFpbiBjb252ZXJ0CiAgICBpZiAoCiAgICAgICAgISRTZWxmLT57UmljaFRleHR9CiAgICAgICAgJiYgJFRlbXBsYXRle0NvbnRlbnRUeXBlfSA9fiAvdGV4dFwvaHRtbC9pCiAgICAgICAgJiYgJFRlbXBsYXRle1RlbXBsYXRlfQogICAgICAgICkKICAgIHsKICAgICAgICAkVGVtcGxhdGV7Q29udGVudFR5cGV9ID0gJ3RleHQvcGxhaW4nOwogICAgICAgICRUZW1wbGF0ZXtUZW1wbGF0ZX0gICAgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6SFRNTFV0aWxzJyktPlRvQXNjaWkoCiAgICAgICAgICAgIFN0cmluZyA9PiAkVGVtcGxhdGV7VGVtcGxhdGV9LAogICAgICAgICk7CiAgICB9CgogICAgIyBHZXQgdXNlciBsYW5ndWFnZS4KICAgIG15ICRMYW5ndWFnZTsKICAgIG15ICVUaWNrZXQ7CiAgICBpZiAoIGRlZmluZWQgJFBhcmFte1RpY2tldElEfSApIHsKCiAgICAgICAgIyBHZXQgdGlja2V0IGRhdGEuCiAgICAgICAgJVRpY2tldCA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpUaWNrZXQnKS0+VGlja2V0R2V0KAogICAgICAgICAgICBUaWNrZXRJRCAgICAgID0+ICRQYXJhbXtUaWNrZXRJRH0sCiAgICAgICAgICAgIER5bmFtaWNGaWVsZHMgPT4gMSwKICAgICAgICApOwoKICAgICAgICAjIEdldCByZWNpcGllbnQuCiAgICAgICAgbXkgJVVzZXIgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6Q3VzdG9tZXJVc2VyJyktPkN1c3RvbWVyVXNlckRhdGFHZXQoCiAgICAgICAgICAgIFVzZXIgPT4gJFRpY2tldHtDdXN0b21lclVzZXJJRH0sCiAgICAgICAgKTsKICAgICAgICAkTGFuZ3VhZ2UgPSAkVXNlcntVc2VyTGFuZ3VhZ2V9OwogICAgfQoKICAgICMgSWYgdGVtcGxhdGUgdHlwZSBpcyAnQ3JlYXRlJyBhbmQgdGhlcmUgaXMgY3VzdG9tZXIgdXNlciBpbmZvcm1hdGlvbiwgdHJlYXQgaXQgYXMgYSB0aWNrZXQgcGFyYW0gaW4gb3JkZXIgdG8KICAgICMgY29ycmVjdGx5IHJlcGxhY2UgY3VzdG9tZXIgdXNlciB0YWdzLiBTZWUgYnVnIzE0NDU1LgogICAgaWYgKCAkVGVtcGxhdGV7VGVtcGxhdGVUeXBlfSBlcSAnQ3JlYXRlJyAmJiAkUGFyYW17Q3VzdG9tZXJVc2VySUR9ICkgewogICAgICAgICRUaWNrZXR7Q3VzdG9tZXJVc2VySUR9ID0gJFBhcmFte0N1c3RvbWVyVXNlcklEfTsKICAgIH0KCiAgICAjIGlmIGN1c3RvbWVyIGxhbmd1YWdlIGlzIG5vdCBkZWZpbmVkLCBzZXQgZGVmYXVsdCBsYW5ndWFnZQogICAgJExhbmd1YWdlIC8vPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OkNvbmZpZycpLT5HZXQoJ0RlZmF1bHRMYW5ndWFnZScpIHx8ICdlbic7CgogICAgIyBnZXQgbGlzdCB1bnN1cHBvcnRlZCB0YWdzIGZvciBzdGFuZGFyZCB0ZW1wbGF0ZQogICAgbXkgQExpc3RPZlVuU3VwcG9ydGVkVGFnID0gcXcoT1RPQk9fQUdFTlRfU1VCSkVDVCBPVE9CT19BR0VOVF9CT0RZIE9UT0JPX0NVU1RPTUVSX0JPRFkgT1RPQk9fQ1VTVE9NRVJfU1VCSkVDVCk7CgogICAgbXkgJVN1cHBvcnRlZFR5cGVzID0gKAogICAgICAgIEFuc3dlciAgPT4gMSwKICAgICAgICBGb3J3YXJkID0+IDEsCiAgICAgICAgTm90ZSAgICA9PiAxLAogICAgKTsKCiAgICBteSAkVGVtcGxhdGVUZXh0ID0gJFRlbXBsYXRle1RlbXBsYXRlfSB8fCAnJzsKICAgIG15ICRUZW1wbGF0ZVR5cGUgPSAkVGVtcGxhdGV7VGVtcGxhdGVUeXBlfTsKCiAgICAjIFJlbW92ZSB1bnN1cHBvcnRlZCB0YWdzIG9ubHkgZm9yIHNvbWUgdGVtcGxhdGUgdHlwZXMuCiAgICBpZiAoICEkU3VwcG9ydGVkVHlwZXN7ICRUZW1wbGF0ZXtUZW1wbGF0ZVR5cGV9IH0gKSB7CiAgICAgICAgJFRlbXBsYXRlVGV4dCA9ICRTZWxmLT5fUmVtb3ZlVW5TdXBwb3J0ZWRUYWcoCiAgICAgICAgICAgIFRleHQgICAgICAgICAgICAgICAgID0+ICRUZW1wbGF0ZXtUZW1wbGF0ZX0gfHwgJycsCiAgICAgICAgICAgIExpc3RPZlVuU3VwcG9ydGVkVGFnID0+IFxATGlzdE9mVW5TdXBwb3J0ZWRUYWcsCiAgICAgICAgKTsKCiAgICAgICAgIyBSZXNldCB0ZW1wbGF0ZSB0eXBlIGZvciB1bnN1cHBvcnRlZCB0YWcuCiAgICAgICAgJFRlbXBsYXRlVHlwZSA9ICcnOwogICAgfQoKICAgICMgcmVwbGFjZSBwbGFjZSBob2xkZXIgc3R1ZmYKICAgICRUZW1wbGF0ZVRleHQgPSAkU2VsZi0+X1JlcGxhY2UoCiAgICAgICAgUmljaFRleHQgICA9PiAkU2VsZi0+e1JpY2hUZXh0fSwKICAgICAgICBUZXh0ICAgICAgID0+ICRUZW1wbGF0ZVRleHQgfHwgJycsCiAgICAgICAgVGlja2V0RGF0YSA9PiBcJVRpY2tldCwKICAgICAgICBEYXRhICAgICAgID0+ICRQYXJhbXtEYXRhfSB8fCB7fSwKICAgICAgICBVc2VySUQgICAgID0+ICRQYXJhbXtVc2VySUR9LAogICAgICAgIExhbmd1YWdlICAgPT4gJExhbmd1YWdlLAogICAgICAgIFRlbXBsYXRlICAgPT4gJFRlbXBsYXRlVHlwZSwKICAgICk7CgogICAgaWYgKCAkU2VsZi0+e1JpY2hUZXh0fSApIHsKICAgICAgICAkVGVtcGxhdGVUZXh0ID1+IHMvJmx0Oy88L2c7CiAgICAgICAgJFRlbXBsYXRlVGV4dCA9fiBzLyZndDsvPi9nOwogICAgICAgICRUZW1wbGF0ZVRleHQgPX4gcy8mcXVvdDsvIi9nOwogICAgICAgICRUZW1wbGF0ZVRleHQgPX4gcy8mYXBvczsvJy9nOwogICAgICAgICRUZW1wbGF0ZVRleHQgPX4gcy8mbmJzcDsvIC9nOwogICAgfQoKICAgIHJldHVybiAkVGVtcGxhdGVUZXh0Owp9Cgo9aGVhZDIgR2VuZXJpY0FnZW50QXJ0aWNsZSgpCgpnZW5lcmF0ZSBpbnRlcm5hbCBvciBleHRlcm5hbCBub3RlcwoKICAgIG15ICRHZW5lcmljQWdlbnRBcnRpY2xlID0gJFRlbXBsYXRlR2VuZXJhdG9yT2JqZWN0LT5HZW5lcmljQWdlbnRBcnRpY2xlKAogICAgICAgIE5vdGlmaWNhdGlvbiAgICA9PiAkTm90aWZpY2F0aW9uRGF0YUhhc2hSZWYsCiAgICAgICAgVGlja2V0SUQgICAgICAgID0+IDEyMywKICAgICAgICBVc2VySUQgICAgICAgICAgPT4gMTIzLAogICAgICAgIERhdGEgICAgICAgICAgICA9PiAkQXJ0aWNsZUhhc2hSZWYsICAgICAgICAgICAgICMgT3B0aW9uYWwKICAgICk7Cgo9Y3V0CgpzdWIgR2VuZXJpY0FnZW50QXJ0aWNsZSB7CiAgICBteSAoICRTZWxmLCAlUGFyYW0gKSA9IEBfOwoKICAgICMgY2hlY2sgbmVlZGVkIHN0dWZmCiAgICBmb3IgKHF3KFRpY2tldElEIE5vdGlmaWNhdGlvbiBVc2VySUQpKSB7CiAgICAgICAgaWYgKCAhJFBhcmFteyRffSApIHsKICAgICAgICAgICAgJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkxvZycpLT5Mb2coCiAgICAgICAgICAgICAgICBQcmlvcml0eSA9PiAnZXJyb3InLAogICAgICAgICAgICAgICAgTWVzc2FnZSAgPT4gIk5lZWQgJF8hIgogICAgICAgICAgICApOwogICAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgfQoKICAgIG15ICVUZW1wbGF0ZSA9ICV7ICRQYXJhbXtOb3RpZmljYXRpb259IH07CgogICAgIyBnZXQgdGlja2V0IG9iamVjdAogICAgbXkgJFRpY2tldE9iamVjdCA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpUaWNrZXQnKTsKCiAgICAjIEdldCB0aWNrZXQgZGF0YS4KICAgIG15ICVUaWNrZXQgPSAkVGlja2V0T2JqZWN0LT5UaWNrZXRHZXQoCiAgICAgICAgVGlja2V0SUQgICAgICA9PiAkUGFyYW17VGlja2V0SUR9LAogICAgICAgIER5bmFtaWNGaWVsZHMgPT4gMSwKICAgICk7CgogICAgIyBkbyB0ZXh0L3BsYWluIHRvIHRleHQvaHRtbCBjb252ZXJ0CiAgICBpZiAoCiAgICAgICAgJFNlbGYtPntSaWNoVGV4dH0KICAgICAgICAmJiAkVGVtcGxhdGV7Q29udGVudFR5cGV9ID1+IC90ZXh0XC9wbGFpbi9pCiAgICAgICAgJiYgJFRlbXBsYXRle0JvZHl9CiAgICAgICAgKQogICAgewogICAgICAgICRUZW1wbGF0ZXtDb250ZW50VHlwZX0gPSAndGV4dC9odG1sJzsKICAgICAgICAkVGVtcGxhdGV7Qm9keX0gICAgICAgID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkhUTUxVdGlscycpLT5Ub0hUTUwoCiAgICAgICAgICAgIFN0cmluZyA9PiAkVGVtcGxhdGV7Qm9keX0sCiAgICAgICAgKTsKICAgIH0KCiAgICAjIGRvIHRleHQvaHRtbCB0byB0ZXh0L3BsYWluIGNvbnZlcnQKICAgIGlmICgKICAgICAgICAhJFNlbGYtPntSaWNoVGV4dH0KICAgICAgICAmJiAkVGVtcGxhdGV7Q29udGVudFR5cGV9ID1+IC90ZXh0XC9odG1sL2kKICAgICAgICAmJiAkVGVtcGxhdGV7Qm9keX0KICAgICAgICApCiAgICB7CiAgICAgICAgJFRlbXBsYXRle0NvbnRlbnRUeXBlfSA9ICd0ZXh0L3BsYWluJzsKICAgICAgICAkVGVtcGxhdGV7Qm9keX0gICAgICAgID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkhUTUxVdGlscycpLT5Ub0FzY2lpKAogICAgICAgICAgICBTdHJpbmcgPT4gJFRlbXBsYXRle0JvZHl9LAogICAgICAgICk7CiAgICB9CgogICAgIyByZXBsYWNlIHBsYWNlIGhvbGRlciBzdHVmZgogICAgJFRlbXBsYXRle0JvZHl9ID0gJFNlbGYtPl9SZXBsYWNlKAogICAgICAgIFJpY2hUZXh0ICAgPT4gJFNlbGYtPntSaWNoVGV4dH0sCiAgICAgICAgVGV4dCAgICAgICA9PiAkVGVtcGxhdGV7Qm9keX0sCiAgICAgICAgUmVjaXBpZW50ICA9PiAkUGFyYW17UmVjaXBpZW50fSwKICAgICAgICBEYXRhICAgICAgID0+ICRQYXJhbXtEYXRhfSB8fCB7fSwKICAgICAgICBUaWNrZXREYXRhID0+IFwlVGlja2V0LAogICAgICAgIFVzZXJJRCAgICAgPT4gJFBhcmFte1VzZXJJRH0sCiAgICApOwogICAgJFRlbXBsYXRle1N1YmplY3R9ID0gJFNlbGYtPl9SZXBsYWNlKAogICAgICAgIFJpY2hUZXh0ICAgPT4gMCwKICAgICAgICBUZXh0ICAgICAgID0+ICRUZW1wbGF0ZXtTdWJqZWN0fSwKICAgICAgICBSZWNpcGllbnQgID0+ICRQYXJhbXtSZWNpcGllbnR9LAogICAgICAgIERhdGEgICAgICAgPT4gJFBhcmFte0RhdGF9IHx8IHt9LAogICAgICAgIFRpY2tldERhdGEgPT4gXCVUaWNrZXQsCiAgICAgICAgVXNlcklEICAgICA9PiAkUGFyYW17VXNlcklEfSwKICAgICk7CgogICAgJFRlbXBsYXRle1N1YmplY3R9ID0gJFRpY2tldE9iamVjdC0+VGlja2V0U3ViamVjdEJ1aWxkKAogICAgICAgIFRpY2tldE51bWJlciA9PiAkVGlja2V0e1RpY2tldE51bWJlcn0sCiAgICAgICAgU3ViamVjdCAgICAgID0+ICRUZW1wbGF0ZXtTdWJqZWN0fSB8fCAnJywKICAgICAgICBUeXBlICAgICAgICAgPT4gJ05ldycsCiAgICApOwoKICAgICMgYWRkIFVSTHMgYW5kIHZlcmlmeSB0byBiZSBmdWxsIEhUTUwgZG9jdW1lbnQKICAgIGlmICggJFNlbGYtPntSaWNoVGV4dH0gKSB7CgogICAgICAgICRUZW1wbGF0ZXtCb2R5fSA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpIVE1MVXRpbHMnKS0+TGlua1F1b3RlKAogICAgICAgICAgICBTdHJpbmcgPT4gJFRlbXBsYXRle0JvZHl9LAogICAgICAgICk7CiAgICB9CgogICAgcmV0dXJuICVUZW1wbGF0ZTsKfQoKPWhlYWQyIEF0dHJpYnV0ZXMoKQoKZ2VuZXJhdGUgYXR0cmlidXRlcwoKICAgIG15ICVBdHRyaWJ1dGVzID0gJFRlbXBsYXRlR2VuZXJhdG9yT2JqZWN0LT5BdHRyaWJ1dGVzKAogICAgICAgIFRpY2tldElEICAgPT4gMTIzLAogICAgICAgIEFydGljbGVJRCAgPT4gMTIzLAogICAgICAgIFJlc3BvbnNlSUQgPT4gMTIzCiAgICAgICAgVXNlcklEICAgICA9PiAxMjMsCiAgICAgICAgQWN0aW9uICAgICA9PiAnRm9yd2FyZCcsICMgUG9zc2libGUgdmFsdWVzIGFyZSBSZXBseSBhbmQgRm9yd2FyZCwgUmVwbHkgaXMgZGVmYXVsdC4KICAgICk7CgpyZXR1cm5zCiAgICBTdGFuZGFyZFJlc3BvbnNlCiAgICBTYWx1dGF0aW9uCiAgICBTaWduYXR1cmUKCj1jdXQKCnN1YiBBdHRyaWJ1dGVzIHsKICAgIG15ICggJFNlbGYsICVQYXJhbSApID0gQF87CgogICAgIyBjaGVjayBuZWVkZWQgc3R1ZmYKICAgIGZvciAocXcoVGlja2V0SUQgRGF0YSBVc2VySUQpKSB7CiAgICAgICAgaWYgKCAhJFBhcmFteyRffSApIHsKICAgICAgICAgICAgJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkxvZycpLT5Mb2coCiAgICAgICAgICAgICAgICBQcmlvcml0eSA9PiAnZXJyb3InLAogICAgICAgICAgICAgICAgTWVzc2FnZSAgPT4gIk5lZWQgJF8hIgogICAgICAgICAgICApOwogICAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgfQoKICAgICMgZ2V0IHRpY2tldCBvYmplY3QKICAgIG15ICRUaWNrZXRPYmplY3QgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6VGlja2V0Jyk7CgogICAgIyBnZXQgcXVldWUKICAgIG15ICVUaWNrZXQgPSAkVGlja2V0T2JqZWN0LT5UaWNrZXRHZXQoCiAgICAgICAgVGlja2V0SUQgICAgICA9PiAkUGFyYW17VGlja2V0SUR9LAogICAgICAgIER5bmFtaWNGaWVsZHMgPT4gMCwKICAgICk7CgogICAgIyBwcmVwYXJlIHN1YmplY3QgLi4uCiAgICAkUGFyYW17RGF0YX0tPntTdWJqZWN0fSA9ICRUaWNrZXRPYmplY3QtPlRpY2tldFN1YmplY3RCdWlsZCgKICAgICAgICBUaWNrZXROdW1iZXIgPT4gJFRpY2tldHtUaWNrZXROdW1iZXJ9LAogICAgICAgIFN1YmplY3QgICAgICA9PiAkUGFyYW17RGF0YX0tPntTdWJqZWN0fSB8fCAnJywKICAgICAgICBBY3Rpb24gICAgICAgPT4gJFBhcmFte0FjdGlvbn0gICAgICAgICAgfHwgJycsCiAgICApOwoKICAgICMgZ2V0IHNlbmRlciBhZGRyZXNzCiAgICAkUGFyYW17RGF0YX0tPntGcm9tfSA9ICRTZWxmLT5TZW5kZXIoCiAgICAgICAgUXVldWVJRCA9PiAkVGlja2V0e1F1ZXVlSUR9LAogICAgICAgIFVzZXJJRCAgPT4gJFBhcmFte1VzZXJJRH0sCiAgICApOwoKICAgIHJldHVybiAleyAkUGFyYW17RGF0YX0gfTsKfQoKPWhlYWQyIEF1dG9SZXNwb25zZSgpCgpnZW5lcmF0ZSByZXNwb25zZQoKQXV0b1Jlc3BvbnNlCiAgICBUaWNrZXRJRAogICAgICAgIE93bmVyCiAgICAgICAgUmVzcG9uc2libGUKICAgICAgICBDVVNUT01FUl9EQVRBCiAgICBBcnRpY2xlSUQKICAgICAgICBDVVNUT01FUl9TVUJKRUNUCiAgICAgICAgQ1VTVE9NRVJfRU1BSUwKICAgIFVzZXJJRAoKICAgIFRvCiAgICBDYwogICAgQmNjCiAgICBTdWJqZWN0CiAgICBCb2R5CiAgICBDb250ZW50VHlwZQoKICAgIG15ICVBdXRvUmVzcG9uc2UgPSAkVGVtcGxhdGVHZW5lcmF0b3JPYmplY3QtPkF1dG9SZXNwb25zZSgKICAgICAgICBUaWNrZXRJRCAgICAgICAgID0+IDEyMywKICAgICAgICBPcmlnSGVhZGVyICAgICAgID0+IHt9LAogICAgICAgIEF1dG9SZXNwb25zZVR5cGUgPT4gJ2F1dG8gcmVwbHknLAogICAgICAgIFVzZXJJRCAgICAgICAgICAgPT4gMTIzLAogICAgKTsKCj1jdXQKCnN1YiBBdXRvUmVzcG9uc2UgewogICAgbXkgKCAkU2VsZiwgJVBhcmFtICkgPSBAXzsKCiAgICAjIGNoZWNrIG5lZWRlZCBzdHVmZgogICAgZm9yIChxdyhUaWNrZXRJRCBBdXRvUmVzcG9uc2VUeXBlIE9yaWdIZWFkZXIgVXNlcklEKSkgewogICAgICAgIGlmICggISRQYXJhbXskX30gKSB7CiAgICAgICAgICAgICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpMb2cnKS0+TG9nKAogICAgICAgICAgICAgICAgUHJpb3JpdHkgPT4gJ2Vycm9yJywKICAgICAgICAgICAgICAgIE1lc3NhZ2UgID0+ICJOZWVkICRfISIKICAgICAgICAgICAgKTsKICAgICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgIH0KCiAgICAjIGdldCB0aWNrZXQgb2JqZWN0CiAgICBteSAkVGlja2V0T2JqZWN0ID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OlRpY2tldCcpOwoKICAgICMgR2V0IHRpY2tldCBkYXRhLgogICAgbXkgJVRpY2tldCA9ICRUaWNrZXRPYmplY3QtPlRpY2tldEdldCgKICAgICAgICBUaWNrZXRJRCAgICAgID0+ICRQYXJhbXtUaWNrZXRJRH0sCiAgICAgICAgRHluYW1pY0ZpZWxkcyA9PiAxLAogICAgKTsKCiAgICAjIGdldCBhdXRvIGRlZmF1bHQgcmVzcG9uc2VzCiAgICBteSAlQXV0b1Jlc3BvbnNlID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkF1dG9SZXNwb25zZScpLT5BdXRvUmVzcG9uc2VHZXRCeVR5cGVRdWV1ZUlEKAogICAgICAgIFF1ZXVlSUQgPT4gJFRpY2tldHtRdWV1ZUlEfSwKICAgICAgICBUeXBlICAgID0+ICRQYXJhbXtBdXRvUmVzcG9uc2VUeXBlfSwKICAgICk7CgogICAgcmV0dXJuIGlmICElQXV0b1Jlc3BvbnNlOwoKICAgICMgZ2V0IG9sZCBhcnRpY2xlIGZvciBxdW90aW5nCiAgICBteSAkQXJ0aWNsZU9iamVjdCA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpUaWNrZXQ6OkFydGljbGUnKTsKICAgIG15IEBBcnRpY2xlTGlzdCAgID0gJEFydGljbGVPYmplY3QtPkFydGljbGVMaXN0KAogICAgICAgIFRpY2tldElEICAgPT4gJFBhcmFte1RpY2tldElEfSwKICAgICAgICBTZW5kZXJUeXBlID0+ICdjdXN0b21lcicsCiAgICAgICAgT25seUxhc3QgICA9PiAxLAogICAgKTsKCiAgICBpZiAoICFAQXJ0aWNsZUxpc3QgKSB7CiAgICAgICAgQEFydGljbGVMaXN0ID0gJEFydGljbGVPYmplY3QtPkFydGljbGVMaXN0KAogICAgICAgICAgICBUaWNrZXRJRCAgICAgICAgICAgICA9PiAkUGFyYW17VGlja2V0SUR9LAogICAgICAgICAgICBJc1Zpc2libGVGb3JDdXN0b21lciA9PiAxLAogICAgICAgICAgICBPbmx5TGFzdCAgICAgICAgICAgICA9PiAxLAogICAgICAgICk7CiAgICB9CgogICAgaWYgKEBBcnRpY2xlTGlzdCkgewogICAgICAgIG15ICVBcnRpY2xlID0gJEFydGljbGVPYmplY3QtPkJhY2tlbmRGb3JBcnRpY2xlKCAleyAkQXJ0aWNsZUxpc3RbMF0gfSApLT5BcnRpY2xlR2V0KCAleyAkQXJ0aWNsZUxpc3RbMF0gfSApOwoKICAgICAgICBmb3IgKHF3KEZyb20gVG8gQ2MgU3ViamVjdCBCb2R5KSkgewogICAgICAgICAgICBpZiAoICEkUGFyYW17T3JpZ0hlYWRlcn0tPnskX30gKSB7CiAgICAgICAgICAgICAgICAkUGFyYW17T3JpZ0hlYWRlcn0tPnskX30gPSAkQXJ0aWNsZXskX30gfHwgJyc7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgY2hvbXAgJFBhcmFte09yaWdIZWFkZXJ9LT57JF99OwogICAgICAgIH0KICAgIH0KCiAgICAjIGZvcm1hdCBib2R5IChvbmx5IGlmIGxvbmdlciB0aGFuIDg2IGNoYXJzKQogICAgaWYgKCAkUGFyYW17T3JpZ0hlYWRlcn0tPntCb2R5fSApIHsKICAgICAgICBpZiAoIGxlbmd0aCAkUGFyYW17T3JpZ0hlYWRlcn0tPntCb2R5fSA+IDg2ICkgewogICAgICAgICAgICBteSBATGluZXMgPSBzcGxpdCAvXG4vLCAkUGFyYW17T3JpZ0hlYWRlcn0tPntCb2R5fTsKICAgICAgICAgICAgTElORToKICAgICAgICAgICAgZm9yIG15ICRMaW5lIChATGluZXMpIHsKICAgICAgICAgICAgICAgIG15ICRMaW5lV3JhcHBlZCA9ICRMaW5lID1+IHMvKF4+Lit8Lns0LDg2fSkoPzpcc3xceikvJDFcbi9nbTsKCiAgICAgICAgICAgICAgICBuZXh0IExJTkUgaWYgJExpbmVXcmFwcGVkOwoKICAgICAgICAgICAgICAgICMgaWYgdGhlIHJlZ2V4IGRvZXMgbm90IG1hdGNoIHRoZW4gd2UgbmVlZAogICAgICAgICAgICAgICAgIyB0byBhZGQgdGhlIG1pc3NpbmcgbmV3IGxpbmUgb2YgdGhlIHNwbGl0CiAgICAgICAgICAgICAgICAjIGVsc2Ugd2Ugd2lsbCBsb3NlIGUuZy4gZW1wdHkgbGluZXMgb2YgdGhlIGJvZHkuCiAgICAgICAgICAgICAgICAjIChidWcjMTA2NzkpCiAgICAgICAgICAgICAgICAkTGluZSAuPSAiXG4iOwogICAgICAgICAgICB9CiAgICAgICAgICAgICRQYXJhbXtPcmlnSGVhZGVyfS0+e0JvZHl9ID0gam9pbiAnJywgQExpbmVzOwogICAgICAgIH0KICAgIH0KCiAgICAjIGZpbGwgdXAgcmVxdWlyZWQgYXR0cmlidXRlcwogICAgZm9yIChxdyhTdWJqZWN0IEJvZHkpKSB7CiAgICAgICAgaWYgKCAhJFBhcmFte09yaWdIZWFkZXJ9LT57JF99ICkgewogICAgICAgICAgICAkUGFyYW17T3JpZ0hlYWRlcn0tPnskX30gPSAiTm8gJF8iOwogICAgICAgIH0KICAgIH0KCiAgICAjIGdldCByZWNpcGllbnQKICAgIG15ICVVc2VyID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkN1c3RvbWVyVXNlcicpLT5DdXN0b21lclVzZXJEYXRhR2V0KAogICAgICAgIFVzZXIgPT4gJFRpY2tldHtDdXN0b21lclVzZXJJRH0sCiAgICApOwoKICAgICMgZ2V0IHVzZXIgbGFuZ3VhZ2UKICAgIG15ICRMYW5ndWFnZSA9ICRVc2Vye1VzZXJMYW5ndWFnZX0gfHwgJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpDb25maWcnKS0+R2V0KCdEZWZhdWx0TGFuZ3VhZ2UnKSB8fCAnZW4nOwoKICAgICMgZG8gdGV4dC9wbGFpbiB0byB0ZXh0L2h0bWwgY29udmVydAogICAgaWYgKCAkU2VsZi0+e1JpY2hUZXh0fSAmJiAkQXV0b1Jlc3BvbnNle0NvbnRlbnRUeXBlfSA9fiAvdGV4dFwvcGxhaW4vaSApIHsKICAgICAgICAkQXV0b1Jlc3BvbnNle0NvbnRlbnRUeXBlfSA9ICd0ZXh0L2h0bWwnOwogICAgICAgICRBdXRvUmVzcG9uc2V7VGV4dH0gICAgICAgID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkhUTUxVdGlscycpLT5Ub0hUTUwoCiAgICAgICAgICAgIFN0cmluZyA9PiAkQXV0b1Jlc3BvbnNle1RleHR9LAogICAgICAgICk7CiAgICB9CgogICAgIyBkbyB0ZXh0L2h0bWwgdG8gdGV4dC9wbGFpbiBjb252ZXJ0CiAgICBpZiAoICEkU2VsZi0+e1JpY2hUZXh0fSAmJiAkQXV0b1Jlc3BvbnNle0NvbnRlbnRUeXBlfSA9fiAvdGV4dFwvaHRtbC9pICkgewogICAgICAgICRBdXRvUmVzcG9uc2V7Q29udGVudFR5cGV9ID0gJ3RleHQvcGxhaW4nOwogICAgICAgICRBdXRvUmVzcG9uc2V7VGV4dH0gICAgICAgID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkhUTUxVdGlscycpLT5Ub0FzY2lpKAogICAgICAgICAgICBTdHJpbmcgPT4gJEF1dG9SZXNwb25zZXtUZXh0fSwKICAgICAgICApOwogICAgfQoKICAgICMgcmVwbGFjZSBwbGFjZSBob2xkZXIgc3R1ZmYKICAgICRBdXRvUmVzcG9uc2V7VGV4dH0gPSAkU2VsZi0+X1JlcGxhY2UoCiAgICAgICAgUmljaFRleHQgPT4gJFNlbGYtPntSaWNoVGV4dH0sCiAgICAgICAgVGV4dCAgICAgPT4gJEF1dG9SZXNwb25zZXtUZXh0fSwKICAgICAgICBEYXRhICAgICA9PiB7CiAgICAgICAgICAgICV7ICRQYXJhbXtPcmlnSGVhZGVyfSB9LAogICAgICAgICAgICBGcm9tID0+ICRQYXJhbXtPcmlnSGVhZGVyfS0+e1RvfSwKICAgICAgICAgICAgVG8gICA9PiAkUGFyYW17T3JpZ0hlYWRlcn0tPntGcm9tfSwKICAgICAgICB9LAogICAgICAgIFRpY2tldERhdGEgICAgICA9PiBcJVRpY2tldCwKICAgICAgICBVc2VySUQgICAgICAgICAgPT4gJFBhcmFte1VzZXJJRH0sCiAgICAgICAgTGFuZ3VhZ2UgICAgICAgID0+ICRMYW5ndWFnZSwKICAgICAgICBBZGRUaW1lem9uZUluZm8gPT4gewogICAgICAgICAgICBBdXRvUmVzcG9uc2UgPT4gMSwKICAgICAgICB9LAogICAgKTsKICAgICRBdXRvUmVzcG9uc2V7U3ViamVjdH0gPSAkU2VsZi0+X1JlcGxhY2UoCiAgICAgICAgUmljaFRleHQgPT4gMCwKICAgICAgICBUZXh0ICAgICA9PiAkQXV0b1Jlc3BvbnNle1N1YmplY3R9LAogICAgICAgIERhdGEgICAgID0+IHsKICAgICAgICAgICAgJXsgJFBhcmFte09yaWdIZWFkZXJ9IH0sCiAgICAgICAgICAgIEZyb20gPT4gJFBhcmFte09yaWdIZWFkZXJ9LT57VG99LAogICAgICAgICAgICBUbyAgID0+ICRQYXJhbXtPcmlnSGVhZGVyfS0+e0Zyb219LAogICAgICAgIH0sCiAgICAgICAgVGlja2V0RGF0YSAgICAgID0+IFwlVGlja2V0LAogICAgICAgIFVzZXJJRCAgICAgICAgICA9PiAkUGFyYW17VXNlcklEfSwKICAgICAgICBMYW5ndWFnZSAgICAgICAgPT4gJExhbmd1YWdlLAogICAgICAgIEFkZFRpbWV6b25lSW5mbyA9PiB7CiAgICAgICAgICAgIEF1dG9SZXNwb25zZSA9PiAxLAogICAgICAgIH0sCiAgICApOwoKICAgICRBdXRvUmVzcG9uc2V7U3ViamVjdH0gPSAkVGlja2V0T2JqZWN0LT5UaWNrZXRTdWJqZWN0QnVpbGQoCiAgICAgICAgVGlja2V0TnVtYmVyID0+ICRUaWNrZXR7VGlja2V0TnVtYmVyfSwKICAgICAgICBTdWJqZWN0ICAgICAgPT4gJEF1dG9SZXNwb25zZXtTdWJqZWN0fSwKICAgICAgICBUeXBlICAgICAgICAgPT4gJ05ldycsCiAgICAgICAgTm9DbGVhbnVwICAgID0+IDEsCiAgICApOwoKICAgICMgZ2V0IHNlbmRlciBhdHRyaWJ1dGVzIGJhc2VkIG9uIGF1dG8gcmVzcG9uc2UgdHlwZQogICAgaWYgKCAkQXV0b1Jlc3BvbnNle1N5c3RlbUFkZHJlc3NJRH0gKSB7CgogICAgICAgIG15ICVBZGRyZXNzID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OlN5c3RlbUFkZHJlc3MnKS0+U3lzdGVtQWRkcmVzc0dldCgKICAgICAgICAgICAgSUQgPT4gJEF1dG9SZXNwb25zZXtTeXN0ZW1BZGRyZXNzSUR9LAogICAgICAgICk7CgogICAgICAgICRBdXRvUmVzcG9uc2V7U2VuZGVyQWRkcmVzc30gID0gJEFkZHJlc3N7TmFtZX07CiAgICAgICAgJEF1dG9SZXNwb25zZXtTZW5kZXJSZWFsbmFtZX0gPSAkQWRkcmVzc3tSZWFsbmFtZX07CiAgICB9CgogICAgIyBnZXQgc2VuZGVyIGF0dHJpYnV0ZXMgYmFzZWQgb24gcXVldWUKICAgIGVsc2UgewoKICAgICAgICBteSAlQWRkcmVzcyA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpRdWV1ZScpLT5HZXRTeXN0ZW1BZGRyZXNzKAogICAgICAgICAgICBRdWV1ZUlEID0+ICRUaWNrZXR7UXVldWVJRH0sCiAgICAgICAgKTsKCiAgICAgICAgJEF1dG9SZXNwb25zZXtTZW5kZXJBZGRyZXNzfSAgPSAkQWRkcmVzc3tFbWFpbH07CiAgICAgICAgJEF1dG9SZXNwb25zZXtTZW5kZXJSZWFsbmFtZX0gPSAkQWRkcmVzc3tSZWFsTmFtZX07CiAgICB9CgogICAgIyBhZGQgdXJscyBhbmQgdmVyaWZ5IHRvIGJlIGZ1bGwgaHRtbCBkb2N1bWVudAogICAgaWYgKCAkU2VsZi0+e1JpY2hUZXh0fSApIHsKCiAgICAgICAgJEF1dG9SZXNwb25zZXtUZXh0fSA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpIVE1MVXRpbHMnKS0+TGlua1F1b3RlKAogICAgICAgICAgICBTdHJpbmcgPT4gJEF1dG9SZXNwb25zZXtUZXh0fSwKICAgICAgICApOwoKICAgICAgICAkQXV0b1Jlc3BvbnNle1RleHR9ID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkhUTUxVdGlscycpLT5Eb2N1bWVudENvbXBsZXRlKAogICAgICAgICAgICBDaGFyc2V0ID0+ICd1dGYtOCcsCiAgICAgICAgICAgIFN0cmluZyAgPT4gJEF1dG9SZXNwb25zZXtUZXh0fSwKICAgICAgICApOwogICAgfQoKICAgIHJldHVybiAlQXV0b1Jlc3BvbnNlOwp9Cgo9aGVhZDIgTm90aWZpY2F0aW9uRXZlbnQoKQoKcmVwbGFjZSBhbGwgT1RPQk8gc21hcnQgdGFncyBpbiB0aGUgbm90aWZpY2F0aW9uIGJvZHkgYW5kIHN1YmplY3QKCiAgICBteSAlTm90aWZpY2F0aW9uRXZlbnQgPSAkVGVtcGxhdGVHZW5lcmF0b3JPYmplY3QtPk5vdGlmaWNhdGlvbkV2ZW50KAogICAgICAgIFRpY2tldERhdGEgICAgICAgICAgICA9PiAkVGlja2V0RGF0YUhhc2hSZWYsCiAgICAgICAgUmVjaXBpZW50ICAgICAgICAgICAgID0+ICRVc2VyRGF0YUhhc2hSZWYsICAgICAgICAgICMgQWdlbnQgb3IgQ3VzdG9tZXIgZGF0YSBnZXQgcmVzdWx0CiAgICAgICAgTm90aWZpY2F0aW9uICAgICAgICAgID0+ICROb3RpZmljYXRpb25EYXRhSGFzaFJlZiwKICAgICAgICBDdXN0b21lck1lc3NhZ2VQYXJhbXMgPT4gJEFydGljbGVIYXNoUmVmLCAgICAgICAgICAgIyBvcHRpb25hbAogICAgICAgIFVzZXJJRCAgICAgICAgICAgICAgICA9PiAxMjMsCiAgICApOwoKPWN1dAoKc3ViIE5vdGlmaWNhdGlvbkV2ZW50IHsKICAgIG15ICggJFNlbGYsICVQYXJhbSApID0gQF87CgogICAgIyBjaGVjayBuZWVkZWQgc3R1ZmYKICAgIGZvciBteSAkTmVlZGVkIChxdyhUaWNrZXREYXRhIE5vdGlmaWNhdGlvbiBSZWNpcGllbnQgVXNlcklEKSkgewogICAgICAgIGlmICggISRQYXJhbXskTmVlZGVkfSApIHsKICAgICAgICAgICAgJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkxvZycpLT5Mb2coCiAgICAgICAgICAgICAgICBQcmlvcml0eSA9PiAnZXJyb3InLAogICAgICAgICAgICAgICAgTWVzc2FnZSAgPT4gIk5lZWQgJE5lZWRlZCEiLAogICAgICAgICAgICApOwogICAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgfQoKICAgIGlmICggIUlzSGFzaFJlZldpdGhEYXRhKCAkUGFyYW17Tm90aWZpY2F0aW9ufSApICkgewogICAgICAgICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpMb2cnKS0+TG9nKAogICAgICAgICAgICBQcmlvcml0eSA9PiAnZXJyb3InLAogICAgICAgICAgICBNZXNzYWdlICA9PiAiTm90aWZpY2F0aW9uIGlzIGludmFsaWQhIiwKICAgICAgICApOwogICAgICAgIHJldHVybjsKICAgIH0KCiAgICBteSAlTm90aWZpY2F0aW9uID0gJXsgJFBhcmFte05vdGlmaWNhdGlvbn0gfTsKCiAgICAjIGV4Y2hhbmdpbmcgb3JpZ2luYWwgcmVmZXJlbmNlIHByZXZlbnQgaXQgdG8gZ3JvdyB1cAogICAgaWYgKCByZWYgJFBhcmFte0N1c3RvbWVyTWVzc2FnZVBhcmFtc30gJiYgcmVmICRQYXJhbXtDdXN0b21lck1lc3NhZ2VQYXJhbXN9IGVxICdIQVNIJyApIHsKICAgICAgICBteSAlTG9jYWxDdXN0b21lck1lc3NhZ2VQYXJhbXMgPSAleyAkUGFyYW17Q3VzdG9tZXJNZXNzYWdlUGFyYW1zfSB9OwogICAgICAgICRQYXJhbXtDdXN0b21lck1lc3NhZ2VQYXJhbXN9ID0gXCVMb2NhbEN1c3RvbWVyTWVzc2FnZVBhcmFtczsKICAgIH0KCiAgICBteSAkQXJ0aWNsZU9iamVjdCA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpUaWNrZXQ6OkFydGljbGUnKTsKCiAgICAjIEdldCBsYXN0IGFydGljbGUgZnJvbSBjdXN0b21lci4KICAgIG15IEBDdXN0b21lckFydGljbGVzID0gJEFydGljbGVPYmplY3QtPkFydGljbGVMaXN0KAogICAgICAgIFRpY2tldElEICAgPT4gJFBhcmFte1RpY2tldERhdGF9LT57VGlja2V0SUR9LAogICAgICAgIFNlbmRlclR5cGUgPT4gJ2N1c3RvbWVyJywKICAgICAgICBPbmx5TGFzdCAgID0+IDEsCiAgICApOwoKICAgIG15ICVDdXN0b21lckFydGljbGU7CgogICAgQVJUSUNMRToKICAgIGZvciBteSAkQXJ0aWNsZSAoQEN1c3RvbWVyQXJ0aWNsZXMpIHsKICAgICAgICBuZXh0IEFSVElDTEUgaWYgISRBcnRpY2xlLT57QXJ0aWNsZUlEfTsKCiAgICAgICAgJUN1c3RvbWVyQXJ0aWNsZSA9ICRBcnRpY2xlT2JqZWN0LT5CYWNrZW5kRm9yQXJ0aWNsZSggJXskQXJ0aWNsZX0gKS0+QXJ0aWNsZUdldCgKICAgICAgICAgICAgJXskQXJ0aWNsZX0sCiAgICAgICAgICAgIER5bmFtaWNGaWVsZHMgPT4gMCwKICAgICAgICApOwogICAgfQoKICAgICMgR2V0IGxhc3QgYXJ0aWNsZSBmcm9tIGFnZW50LgogICAgbXkgQEFnZW50QXJ0aWNsZXMgPSAkQXJ0aWNsZU9iamVjdC0+QXJ0aWNsZUxpc3QoCiAgICAgICAgVGlja2V0SUQgICA9PiAkUGFyYW17VGlja2V0RGF0YX0tPntUaWNrZXRJRH0sCiAgICAgICAgU2VuZGVyVHlwZSA9PiAnYWdlbnQnLAogICAgICAgIE9ubHlMYXN0ICAgPT4gMSwKICAgICk7CgogICAgbXkgJUFnZW50QXJ0aWNsZTsKCiAgICBBR0VOVEFSVElDTEU6CiAgICBmb3IgbXkgJEFydGljbGUgKEBBZ2VudEFydGljbGVzKSB7CiAgICAgICAgbmV4dCBBR0VOVEFSVElDTEUgaWYgISRBcnRpY2xlLT57QXJ0aWNsZUlEfTsKCiAgICAgICAgJUFnZW50QXJ0aWNsZSA9ICRBcnRpY2xlT2JqZWN0LT5CYWNrZW5kRm9yQXJ0aWNsZSggJXskQXJ0aWNsZX0gKS0+QXJ0aWNsZUdldCgKICAgICAgICAgICAgJXskQXJ0aWNsZX0sCiAgICAgICAgICAgIER5bmFtaWNGaWVsZHMgPT4gMCwKICAgICAgICApOwoKICAgICAgICAjIEluY2x1ZGUgdGhlIHRyYW5zbWlzc2lvbiBzdGF0dXMsIGlmIGFydGljbGUgaXMgYW4gZW1haWwuCiAgICAgICAgbXkgJUNvbW11bmljYXRpb25DaGFubmVsID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkNvbW11bmljYXRpb25DaGFubmVsJyktPkNoYW5uZWxHZXQoCiAgICAgICAgICAgIENoYW5uZWxJRCA9PiAkQXJ0aWNsZS0+e0NvbW11bmljYXRpb25DaGFubmVsSUR9LAogICAgICAgICk7CiAgICAgICAgaWYgKCAkQ29tbXVuaWNhdGlvbkNoYW5uZWx7Q2hhbm5lbE5hbWV9IGVxICdFbWFpbCcgKSB7CiAgICAgICAgICAgIG15ICRUcmFuc21pc3Npb25TdGF0dXMgPSAkQXJ0aWNsZU9iamVjdC0+QmFja2VuZEZvckFydGljbGUoICV7JEFydGljbGV9ICktPkFydGljbGVUcmFuc21pc3Npb25TdGF0dXMoCiAgICAgICAgICAgICAgICBBcnRpY2xlSUQgPT4gJEFydGljbGUtPntBcnRpY2xlSUR9LAogICAgICAgICAgICApOwogICAgICAgICAgICBpZiAoICRUcmFuc21pc3Npb25TdGF0dXMgJiYgJFRyYW5zbWlzc2lvblN0YXR1cy0+e01lc3NhZ2V9ICkgewogICAgICAgICAgICAgICAgJEFnZW50QXJ0aWNsZXtUcmFuc21pc3Npb25TdGF0dXNNZXNzYWdlfSA9ICRUcmFuc21pc3Npb25TdGF0dXMtPntNZXNzYWdlfTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgIH0KCiAgICBteSAkTGF5b3V0T2JqZWN0ID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpPdXRwdXQ6OkhUTUw6OkxheW91dCcpOwoKICAgIEFSVElDTEU6CiAgICBmb3IgbXkgJEFydGljbGVEYXRhICggXCVDdXN0b21lckFydGljbGUsIFwlQWdlbnRBcnRpY2xlICkgewogICAgICAgIG5leHQgQVJUSUNMRSBpZiAhJEFydGljbGVEYXRhLT57VGlja2V0SUR9OwogICAgICAgIG5leHQgQVJUSUNMRSBpZiAhJEFydGljbGVEYXRhLT57QXJ0aWNsZUlEfTsKCiAgICAgICAgIyBHZXQgYXJ0aWNsZSBwcmV2aWV3IGluIHBsYWluIHRleHQgYW5kIHN0b3JlIGl0IGFzIEJvZHkga2V5LgogICAgICAgICRBcnRpY2xlRGF0YS0+e0JvZHl9ID0gJExheW91dE9iamVjdC0+QXJ0aWNsZVByZXZpZXcoCiAgICAgICAgICAgIFRpY2tldElEICAgPT4gJEFydGljbGVEYXRhLT57VGlja2V0SUR9LAogICAgICAgICAgICBBcnRpY2xlSUQgID0+ICRBcnRpY2xlRGF0YS0+e0FydGljbGVJRH0sCiAgICAgICAgICAgIFJlc3VsdFR5cGUgPT4gJ3BsYWluJywKICAgICAgICAgICAgVXNlcklEICAgICA9PiAkUGFyYW17VXNlcklEfSwKICAgICAgICApOwoKICAgICAgICAjIGdldCBhY2NvdW50ZWQgdGltZQogICAgICAgIG15ICRBY2NvdW50ZWRUaW1lID0gJEFydGljbGVPYmplY3QtPkFydGljbGVBY2NvdW50ZWRUaW1lR2V0KAogICAgICAgICAgICBBcnRpY2xlSUQgPT4gJEFydGljbGVEYXRhLT57QXJ0aWNsZUlEfSwKICAgICAgICApOwoKICAgICAgICAjIHNldCB0aGUgYWNjb3VudGVkIHRpbWUgYXMgcGFydCBvZiB0aGUgYXJ0aWNsZXMgaW5mb3JtYXRpb24KICAgICAgICAkQXJ0aWNsZURhdGEtPntUaW1lVW5pdH0gPSAkQWNjb3VudGVkVGltZTsKICAgIH0KCiAgICAjIFBvcHVsYXRlIHRoZSBoYXNoICdDdXN0b21lck1lc3NhZ2VQYXJhbXMnIHdpdGggYWxsIHRoZSBjdXN0b21lci1hcnRpY2xlIGRhdGEKICAgICMgYW5kIG92ZXJ3cml0ZSBpdCB3aXRoICdDdXN0b21lck1lc3NhZ2VQYXJhbXMnIHBhc3NlZCBpbiB0aGUgUGFyYW1zIChidWcgIzEzMzI1KS4KICAgICRQYXJhbXtDdXN0b21lck1lc3NhZ2VQYXJhbXN9ID0gewogICAgICAgICVDdXN0b21lckFydGljbGUsCiAgICAgICAgJXsgJFBhcmFte0N1c3RvbWVyTWVzc2FnZVBhcmFtc30gfHwge30gfSwKICAgIH07CgogICAgIyBnZXQgc3lzdGVtIGRlZmF1bHQgbGFuZ3VhZ2UKICAgIG15ICREZWZhdWx0TGFuZ3VhZ2UgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OkNvbmZpZycpLT5HZXQoJ0RlZmF1bHRMYW5ndWFnZScpIHx8ICdlbic7CgogICAgbXkgJExhbmd1YWdlcyA9IFsgJFBhcmFte1JlY2lwaWVudH0tPntVc2VyTGFuZ3VhZ2V9LCAkRGVmYXVsdExhbmd1YWdlLCAnZW4nIF07CgogICAgbXkgJExhbmd1YWdlOwogICAgTEFOR1VBR0U6CiAgICBmb3IgbXkgJEl0ZW0gKCBAeyRMYW5ndWFnZXN9ICkgewogICAgICAgIG5leHQgTEFOR1VBR0UgaWYgISRJdGVtOwogICAgICAgIG5leHQgTEFOR1VBR0UgaWYgISROb3RpZmljYXRpb257TWVzc2FnZX0tPnskSXRlbX07CgogICAgICAgICMgc2V0IGxhbmd1YWdlCiAgICAgICAgJExhbmd1YWdlID0gJEl0ZW07CiAgICAgICAgbGFzdCBMQU5HVUFHRTsKICAgIH0KCiAgICAjIGlmIG5vIGxhbmd1YWdlLCB0aGVuIHRha2UgdGhlIGZpcnN0IG9uZSBhdmFpbGFibGUKICAgIGlmICggISRMYW5ndWFnZSApIHsKICAgICAgICBteSBATm90aWZpY2F0aW9uTGFuZ3VhZ2VzID0gc29ydCBrZXlzICV7ICROb3RpZmljYXRpb257TWVzc2FnZX0gfTsKICAgICAgICAkTGFuZ3VhZ2UgPSAkTm90aWZpY2F0aW9uTGFuZ3VhZ2VzWzBdOwogICAgfQoKICAgICMgY29weSB0aGUgY29ycmVjdCBsYW5ndWFnZSBtZXNzYWdlIGF0dHJpYnV0ZXMgdG8gYSBmbGF0IHN0cnVjdHVyZQogICAgZm9yIG15ICRBdHRyaWJ1dGUgKHF3KFN1YmplY3QgQm9keSBDb250ZW50VHlwZSkpIHsKICAgICAgICAkTm90aWZpY2F0aW9ueyRBdHRyaWJ1dGV9ID0gJE5vdGlmaWNhdGlvbntNZXNzYWdlfS0+eyRMYW5ndWFnZX0tPnskQXR0cmlidXRlfTsKICAgIH0KCiAgICAjIEdldCBjdXN0b21lciBhcnRpY2xlIGZpZWxkcy4KICAgIG15ICVDdXN0b21lckFydGljbGVGaWVsZHM7CgogICAgaWYgKCVDdXN0b21lckFydGljbGUpIHsKICAgICAgICAlQ3VzdG9tZXJBcnRpY2xlRmllbGRzID0gJExheW91dE9iamVjdC0+QXJ0aWNsZUZpZWxkcygKICAgICAgICAgICAgVGlja2V0SUQgID0+ICRDdXN0b21lckFydGljbGV7VGlja2V0SUR9LAogICAgICAgICAgICBBcnRpY2xlSUQgPT4gJEN1c3RvbWVyQXJ0aWNsZXtBcnRpY2xlSUR9LAogICAgICAgICAgICBVc2VySUQgICAgPT4gJFBhcmFte1VzZXJJRH0sCiAgICAgICAgKTsKICAgIH0KCiAgICBBUlRJQ0xFX0ZJRUxEOgogICAgZm9yIG15ICRBcnRpY2xlRmllbGQgKCBzb3J0IGtleXMgJUN1c3RvbWVyQXJ0aWNsZUZpZWxkcyApIHsKICAgICAgICBuZXh0IEFSVElDTEVfRklFTEQgaWYgIWRlZmluZWQgJEN1c3RvbWVyQXJ0aWNsZUZpZWxkc3skQXJ0aWNsZUZpZWxkfS0+e1ZhbHVlfTsKCiAgICAgICAgaWYgKCAhZGVmaW5lZCAkUGFyYW17Q3VzdG9tZXJNZXNzYWdlUGFyYW1zfS0+eyRBcnRpY2xlRmllbGR9ICkgewogICAgICAgICAgICAkUGFyYW17Q3VzdG9tZXJNZXNzYWdlUGFyYW1zfS0+eyRBcnRpY2xlRmllbGR9ID0gJEN1c3RvbWVyQXJ0aWNsZUZpZWxkc3skQXJ0aWNsZUZpZWxkfS0+e1ZhbHVlfTsKICAgICAgICB9CiAgICAgICAgY2hvbXAgJFBhcmFte0N1c3RvbWVyTWVzc2FnZVBhcmFtc30tPnskQXJ0aWNsZUZpZWxkfTsKICAgIH0KCiAgICAjIGZvcm1hdCBib2R5IChvbmx5IGlmIGxvbmdlciB0aGUgODYgY2hhcnMpCiAgICBpZiAoICRQYXJhbXtDdXN0b21lck1lc3NhZ2VQYXJhbXN9LT57Qm9keX0gKSB7CiAgICAgICAgaWYgKCBsZW5ndGggJFBhcmFte0N1c3RvbWVyTWVzc2FnZVBhcmFtc30tPntCb2R5fSA+IDg2ICkgewogICAgICAgICAgICBteSBATGluZXMgPSBzcGxpdCAvXG4vLCAkUGFyYW17Q3VzdG9tZXJNZXNzYWdlUGFyYW1zfS0+e0JvZHl9OwogICAgICAgICAgICBMSU5FOgogICAgICAgICAgICBmb3IgbXkgJExpbmUgKEBMaW5lcykgewogICAgICAgICAgICAgICAgbXkgJExpbmVXcmFwcGVkID0gJExpbmUgPX4gcy8oXj4uK3wuezQsODZ9KSg/OlxzfFx6KS8kMVxuL2dtOwoKICAgICAgICAgICAgICAgIG5leHQgTElORSBpZiAkTGluZVdyYXBwZWQ7CgogICAgICAgICAgICAgICAgIyBpZiB0aGUgcmVnZXggZG9lcyBub3QgbWF0Y2ggdGhlbiB3ZSBuZWVkCiAgICAgICAgICAgICAgICAjIHRvIGFkZCB0aGUgbWlzc2luZyBuZXcgbGluZSBvZiB0aGUgc3BsaXQKICAgICAgICAgICAgICAgICMgZWxzZSB3ZSB3aWxsIGxvc2UgZS5nLiBlbXB0eSBsaW5lcyBvZiB0aGUgYm9keS4KICAgICAgICAgICAgICAgICMgKGJ1ZyMxMDY3OSkKICAgICAgICAgICAgICAgICRMaW5lIC49ICJcbiI7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgJFBhcmFte0N1c3RvbWVyTWVzc2FnZVBhcmFtc30tPntCb2R5fSA9IGpvaW4gJycsIEBMaW5lczsKICAgICAgICB9CiAgICB9CgogICAgIyBmaWxsIHVwIHJlcXVpcmVkIGF0dHJpYnV0ZXMKICAgIGZvciBteSAkVGV4dCAocXcoU3ViamVjdCBCb2R5KSkgewogICAgICAgIGlmICggISRQYXJhbXtDdXN0b21lck1lc3NhZ2VQYXJhbXN9LT57JFRleHR9ICkgewoKICAgICAgICAgICAgIyBTZXQgdG8gbGFzdCBjdXN0b21lciBhcnRpY2xlIGF0dHJpYnV0ZSBpZiBpdCBpcyBlbXB0eSBzdHJpbmcuCiAgICAgICAgICAgICMgRm9yIGV4YW1wbGUsIGlmIEJvZHkgaXMgZW1wdHkgc3RyaW5nIChub3QgdW5kZWYhKSwgaXQgaXMgbWF5YmUgc2VudCBmcm9tIE5vdGlmaWNhdGlvbk93bmVyVXBkYXRlIGV2ZW50CiAgICAgICAgICAgICMgYW5kIG92ZXJyaWRlcyBsYXN0IGN1c3RvbWVyIGFydGljbGUgYm9keSAoaW4gJUN1c3RvbWVyQXJ0aWNsZSkgYWJvdmUgLSBzZWUgYnVnIzE0Njc4LgogICAgICAgICAgICAkUGFyYW17Q3VzdG9tZXJNZXNzYWdlUGFyYW1zfS0+eyRUZXh0fSA9ICRDdXN0b21lckFydGljbGV7JFRleHR9IHx8ICJObyAkVGV4dCI7CiAgICAgICAgfQogICAgfQoKICAgIG15ICRTdGFydCA9ICc8JzsKICAgIG15ICRFbmQgICA9ICc+JzsKICAgIGlmICggJE5vdGlmaWNhdGlvbntDb250ZW50VHlwZX0gPX4gbXt0ZXh0XC9odG1sfSApIHsKICAgICAgICAkU3RhcnQgPSAnJmx0Oyc7CiAgICAgICAgJEVuZCAgID0gJyZndDsnOwogICAgfQoKICAgICMgcmVwbGFjZSA8T1RPQk9fQ1VTVE9NRVJfREFUQV8qPiB0YWdzIGVhcmx5IGZyb20gQ3VzdG9tZXJNZXNzYWdlUGFyYW1zLCB0aGUgcmVzdHMgd2lsbCBiZSByZXBsYWNlZAogICAgIyBieSB0aWNrZXQgY3VzdG9tZXIgdXNlcgogICAgS0VZOgogICAgZm9yIG15ICRLZXkgKCBzb3J0IGtleXMgJXsgJFBhcmFte0N1c3RvbWVyTWVzc2FnZVBhcmFtc30gfHwge30gfSApIHsKCiAgICAgICAgbmV4dCBLRVkgaWYgISRQYXJhbXtDdXN0b21lck1lc3NhZ2VQYXJhbXN9LT57JEtleX07CgogICAgICAgICROb3RpZmljYXRpb257Qm9keX0gICAgPX4gcy8ke1N0YXJ0fU9UT0JPX0NVU1RPTUVSX0RBVEFfJEtleSR7RW5kfS8kUGFyYW17Q3VzdG9tZXJNZXNzYWdlUGFyYW1zfS0+eyRLZXl9L2dpOwogICAgICAgICROb3RpZmljYXRpb257U3ViamVjdH0gPX4gcy88T1RPQk9fQ1VTVE9NRVJfREFUQV8kS2V5Pi8kUGFyYW17Q3VzdG9tZXJNZXNzYWdlUGFyYW1zfS0+eyRLZXl9eyRLZXl9L2dpOwogICAgfQoKICAgICMgZG8gdGV4dC9wbGFpbiB0byB0ZXh0L2h0bWwgY29udmVydAogICAgaWYgKCAkU2VsZi0+e1JpY2hUZXh0fSAmJiAkTm90aWZpY2F0aW9ue0NvbnRlbnRUeXBlfSA9fiAvdGV4dFwvcGxhaW4vaSApIHsKICAgICAgICAkTm90aWZpY2F0aW9ue0NvbnRlbnRUeXBlfSA9ICd0ZXh0L2h0bWwnOwogICAgICAgICROb3RpZmljYXRpb257Qm9keX0gICAgICAgID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkhUTUxVdGlscycpLT5Ub0hUTUwoCiAgICAgICAgICAgIFN0cmluZyA9PiAkTm90aWZpY2F0aW9ue0JvZHl9LAogICAgICAgICk7CiAgICB9CgogICAgIyBkbyB0ZXh0L2h0bWwgdG8gdGV4dC9wbGFpbiBjb252ZXJ0CiAgICBpZiAoICEkU2VsZi0+e1JpY2hUZXh0fSAmJiAkTm90aWZpY2F0aW9ue0NvbnRlbnRUeXBlfSA9fiAvdGV4dFwvaHRtbC9pICkgewogICAgICAgICROb3RpZmljYXRpb257Q29udGVudFR5cGV9ID0gJ3RleHQvcGxhaW4nOwogICAgICAgICROb3RpZmljYXRpb257Qm9keX0gICAgICAgID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkhUTUxVdGlscycpLT5Ub0FzY2lpKAogICAgICAgICAgICBTdHJpbmcgPT4gJE5vdGlmaWNhdGlvbntCb2R5fSwKICAgICAgICApOwogICAgfQoKICAgICMgZ2V0IG5vdGlmeSB0ZXh0cwogICAgZm9yIG15ICRUZXh0IChxdyhTdWJqZWN0IEJvZHkpKSB7CiAgICAgICAgaWYgKCAhJE5vdGlmaWNhdGlvbnskVGV4dH0gKSB7CiAgICAgICAgICAgICROb3RpZmljYXRpb257JFRleHR9ID0gIk5vIE5vdGlmaWNhdGlvbiAkVGV4dCBmb3IgJFBhcmFte1R5cGV9IGZvdW5kISI7CiAgICAgICAgfQogICAgfQoKICAgICMgcmVwbGFjZSBwbGFjZSBob2xkZXIgc3R1ZmYKICAgICROb3RpZmljYXRpb257Qm9keX0gPSAkU2VsZi0+X1JlcGxhY2UoCiAgICAgICAgUmljaFRleHQgICAgICAgID0+ICRTZWxmLT57UmljaFRleHR9LAogICAgICAgIFRleHQgICAgICAgICAgICA9PiAkTm90aWZpY2F0aW9ue0JvZHl9LAogICAgICAgIFJlY2lwaWVudCAgICAgICA9PiAkUGFyYW17UmVjaXBpZW50fSwKICAgICAgICBEYXRhICAgICAgICAgICAgPT4gJFBhcmFte0N1c3RvbWVyTWVzc2FnZVBhcmFtc30sCiAgICAgICAgRGF0YUFnZW50ICAgICAgID0+IFwlQWdlbnRBcnRpY2xlLAogICAgICAgIFRpY2tldERhdGEgICAgICA9PiAkUGFyYW17VGlja2V0RGF0YX0sCiAgICAgICAgVXNlcklEICAgICAgICAgID0+ICRQYXJhbXtVc2VySUR9LAogICAgICAgIExhbmd1YWdlICAgICAgICA9PiAkTGFuZ3VhZ2UsCiAgICAgICAgQWRkVGltZXpvbmVJbmZvID0+IHsKICAgICAgICAgICAgTm90aWZpY2F0aW9uRXZlbnQgPT4gMSwKICAgICAgICB9LAogICAgKTsKCiAgICAkTm90aWZpY2F0aW9ue1N1YmplY3R9ID0gJFNlbGYtPl9SZXBsYWNlKAogICAgICAgIFJpY2hUZXh0ICAgICAgICA9PiAwLAogICAgICAgIFRleHQgICAgICAgICAgICA9PiAkTm90aWZpY2F0aW9ue1N1YmplY3R9LAogICAgICAgIFJlY2lwaWVudCAgICAgICA9PiAkUGFyYW17UmVjaXBpZW50fSwKICAgICAgICBEYXRhICAgICAgICAgICAgPT4gJFBhcmFte0N1c3RvbWVyTWVzc2FnZVBhcmFtc30sCiAgICAgICAgRGF0YUFnZW50ICAgICAgID0+IFwlQWdlbnRBcnRpY2xlLAogICAgICAgIFRpY2tldERhdGEgICAgICA9PiAkUGFyYW17VGlja2V0RGF0YX0sCiAgICAgICAgVXNlcklEICAgICAgICAgID0+ICRQYXJhbXtVc2VySUR9LAogICAgICAgIExhbmd1YWdlICAgICAgICA9PiAkTGFuZ3VhZ2UsCiAgICAgICAgQWRkVGltZXpvbmVJbmZvID0+IHsKICAgICAgICAgICAgTm90aWZpY2F0aW9uRXZlbnQgPT4gMSwKICAgICAgICB9LAogICAgKTsKCiAgICAjIEtlZXAgdGhlICJvcmlnaW5hbCIgKHVubW9kaWZpZWQpIHN1YmplY3QgYW5kIGJvZHkgZm9yIGxhdGVyIHVzZS4KICAgICROb3RpZmljYXRpb257T3JpZ2luYWxTdWJqZWN0fSA9ICROb3RpZmljYXRpb257U3ViamVjdH07CiAgICAkTm90aWZpY2F0aW9ue09yaWdpbmFsQm9keX0gICAgPSAkTm90aWZpY2F0aW9ue0JvZHl9OwoKICAgICROb3RpZmljYXRpb257U3ViamVjdH0gPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6VGlja2V0JyktPlRpY2tldFN1YmplY3RCdWlsZCgKICAgICAgICBUaWNrZXROdW1iZXIgPT4gJFBhcmFte1RpY2tldERhdGF9LT57VGlja2V0TnVtYmVyfSwKICAgICAgICBTdWJqZWN0ICAgICAgPT4gJE5vdGlmaWNhdGlvbntTdWJqZWN0fSB8fCAnJywKICAgICAgICBUeXBlICAgICAgICAgPT4gJ05ldycsCiAgICApOwoKICAgICMgYWRkIFVSTHMgYW5kIHZlcmlmeSB0byBiZSBmdWxsIEhUTUwgZG9jdW1lbnQKICAgIGlmICggJFNlbGYtPntSaWNoVGV4dH0gKSB7CgogICAgICAgICROb3RpZmljYXRpb257Qm9keX0gPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6SFRNTFV0aWxzJyktPkxpbmtRdW90ZSgKICAgICAgICAgICAgU3RyaW5nID0+ICROb3RpZmljYXRpb257Qm9keX0sCiAgICAgICAgKTsKICAgIH0KCiAgICByZXR1cm4gJU5vdGlmaWNhdGlvbjsKfQoKPWJlZ2luIEludGVybmFsOgoKPWN1dAoKc3ViIF9SZXBsYWNlIHsKICAgIG15ICggJFNlbGYsICVQYXJhbSApID0gQF87CgogICAgIyBjaGVjayBuZWVkZWQgc3R1ZmYKICAgIGZvciAocXcoVGV4dCBSaWNoVGV4dCBEYXRhIFVzZXJJRCkpIHsKICAgICAgICBpZiAoICFkZWZpbmVkICRQYXJhbXskX30gKSB7CiAgICAgICAgICAgICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpMb2cnKS0+TG9nKAogICAgICAgICAgICAgICAgUHJpb3JpdHkgPT4gJ2Vycm9yJywKICAgICAgICAgICAgICAgIE1lc3NhZ2UgID0+ICJOZWVkICRfISIKICAgICAgICAgICAgKTsKICAgICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgIH0KCiAgICAjIGNoZWNrIGZvciBtYWlsdG8gbGlua3MKICAgICMgc2luY2UgdGhlIHN1YmplY3QgYW5kIGJvZHkgb2YgdGhvc2UgbWFpbHRvIGxpbmtzIGFyZQogICAgIyB1cmkgZXNjYXBlZCB3ZSBoYXZlIHRvIHVyaSB1bmVzY2FwZSB0aGVtLCByZXBsYWNlCiAgICAjIHBvc3NpYmxlIHBsYWNlaG9sZGVycyBhbmQgdGhlbiByZS11cmkgZXNjYXBlIHRoZW0KICAgICRQYXJhbXtUZXh0fSA9fiBzewogICAgICAgIChocmVmPSJtYWlsdG86W15cP10rXD8pKFteIl0rIikKICAgIH0KICAgIHsKICAgICAgICBteSAkTWFpbFRvSHJlZiAgICAgICAgPSAkMTsKICAgICAgICBteSAkTWFpbFRvSHJlZkNvbnRlbnQgPSAkMjsKCiAgICAgICAgJE1haWxUb0hyZWZDb250ZW50ID1+IHN7CiAgICAgICAgICAgICgoPzpzdWJqZWN0fGJvZHkpPSkoLis/KSgifCYpCiAgICAgICAgfQogICAgICAgIHsKICAgICAgICAgICAgbXkgJFN1YmplY3RPckJvZHlQcmVmaXggID0gJDE7CiAgICAgICAgICAgIG15ICRTdWJqZWN0T3JCb2R5Q29udGVudCA9ICQyOwogICAgICAgICAgICBteSAkU3ViamVjdE9yQm9keVN1ZmZpeCAgPSAkMzsKCiAgICAgICAgICAgIG15ICRTdWJqZWN0T3JCb2R5Q29udGVudFVuZXNjYXBlZCA9IFVSSTo6RXNjYXBlOjp1cmlfdW5lc2NhcGUgJFN1YmplY3RPckJvZHlDb250ZW50OwoKICAgICAgICAgICAgbXkgJFN1YmplY3RPckJvZHlDb250ZW50UmVwbGFjZWQgPSAkU2VsZi0+X1JlcGxhY2UoCiAgICAgICAgICAgICAgICAlUGFyYW0sCiAgICAgICAgICAgICAgICBUZXh0ICAgICA9PiAkU3ViamVjdE9yQm9keUNvbnRlbnRVbmVzY2FwZWQsCiAgICAgICAgICAgICAgICBSaWNoVGV4dCA9PiAwLAogICAgICAgICAgICApOwoKICAgICAgICAgICAgbXkgJFN1YmplY3RPckJvZHlDb250ZW50RXNjYXBlZCA9IFVSSTo6RXNjYXBlOjp1cmlfZXNjYXBlX3V0ZjggJFN1YmplY3RPckJvZHlDb250ZW50UmVwbGFjZWQ7CgogICAgICAgICAgICAkU3ViamVjdE9yQm9keVByZWZpeCAuICRTdWJqZWN0T3JCb2R5Q29udGVudEVzY2FwZWQgLiAkU3ViamVjdE9yQm9keVN1ZmZpeDsKICAgICAgICB9ZWd4OwoKICAgICAgICAkTWFpbFRvSHJlZiAuICRNYWlsVG9IcmVmQ29udGVudDsKICAgIH1lZ3g7CgogICAgbXkgJFN0YXJ0ID0gJzwnOwogICAgbXkgJEVuZCAgID0gJz4nOwogICAgaWYgKCAkUGFyYW17UmljaFRleHR9ICkgewogICAgICAgICRTdGFydCA9ICcmbHQ7JzsKICAgICAgICAkRW5kICAgPSAnJmd0Oyc7CiAgICAgICAgJFBhcmFte1RleHR9ID1+IHMvKFxufFxyKS8vZzsKICAgIH0KCiAgICBteSAlVGlja2V0OwogICAgaWYgKCAkUGFyYW17VGlja2V0RGF0YX0gKSB7CiAgICAgICAgJVRpY2tldCA9ICV7ICRQYXJhbXtUaWNrZXREYXRhfSB9OwogICAgfQoKICAgIG15ICRDdXN0b21lclVzZXJPYmplY3QgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6Q3VzdG9tZXJVc2VyJyk7CgogICAgIyBEZXRlcm1pbmUgcmVjaXBpZW50J3MgdGltZXpvbmUgaWYgbmVlZGVkLgogICAgbXkgJFJlY2lwaWVudFRpbWVab25lOwogICAgaWYgKCAkUGFyYW17QWRkVGltZXpvbmVJbmZvfSApIHsKICAgICAgICAkUmVjaXBpZW50VGltZVpvbmUgPSAkS2VybmVsOjpPTS0+Q3JlYXRlKCdLZXJuZWw6OlN5c3RlbTo6RGF0ZVRpbWUnKS0+T1RPQk9UaW1lWm9uZUdldCgpOwoKICAgICAgICBteSAlQ3VzdG9tZXJVc2VyOwogICAgICAgIGlmICggSXNIYXNoUmVmV2l0aERhdGEoIFwlVGlja2V0ICkgJiYgJFRpY2tldHtDdXN0b21lclVzZXJJRH0gKSB7CiAgICAgICAgICAgICVDdXN0b21lclVzZXIgPSAkQ3VzdG9tZXJVc2VyT2JqZWN0LT5DdXN0b21lclVzZXJEYXRhR2V0KCBVc2VyID0+ICRUaWNrZXR7Q3VzdG9tZXJVc2VySUR9ICk7CiAgICAgICAgfQoKICAgICAgICBteSAlVXNlclByZWZlcmVuY2VzOwoKICAgICAgICBpZiAoICRQYXJhbXtBZGRUaW1lem9uZUluZm99LT57Tm90aWZpY2F0aW9uRXZlbnR9ICYmICRQYXJhbXtSZWNpcGllbnR9LT57VHlwZX0gZXEgJ0FnZW50JyApIHsKICAgICAgICAgICAgJVVzZXJQcmVmZXJlbmNlcyA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpVc2VyJyktPkdldFByZWZlcmVuY2VzKAogICAgICAgICAgICAgICAgVXNlcklEID0+ICRQYXJhbXtSZWNpcGllbnR9LT57VXNlcklEfSwKICAgICAgICAgICAgKTsKICAgICAgICB9CiAgICAgICAgZWxzaWYgKAogICAgICAgICAgICAkUGFyYW17QWRkVGltZXpvbmVJbmZvfS0+e05vdGlmaWNhdGlvbkV2ZW50fQogICAgICAgICAgICAmJiAkUGFyYW17UmVjaXBpZW50fS0+e1R5cGV9IGVxICdDdXN0b21lcicKICAgICAgICAgICAgJiYgJFBhcmFte1JlY2lwaWVudH0tPntVc2VySUR9CiAgICAgICAgICAgICkKICAgICAgICB7CiAgICAgICAgICAgICVVc2VyUHJlZmVyZW5jZXMgPSAkQ3VzdG9tZXJVc2VyT2JqZWN0LT5HZXRQcmVmZXJlbmNlcygKICAgICAgICAgICAgICAgIFVzZXJJRCA9PiAkUGFyYW17UmVjaXBpZW50fS0+e1VzZXJJRH0sCiAgICAgICAgICAgICk7CiAgICAgICAgfQogICAgICAgIGVsc2lmICgKICAgICAgICAgICAgJFBhcmFte0FkZFRpbWV6b25lSW5mb30tPntBdXRvUmVzcG9uc2V9CiAgICAgICAgICAgICYmICRUaWNrZXR7Q3VzdG9tZXJVc2VySUR9CiAgICAgICAgICAgICYmIElzSGFzaFJlZldpdGhEYXRhKCBcJUN1c3RvbWVyVXNlciApCiAgICAgICAgICAgICkKICAgICAgICB7CiAgICAgICAgICAgICVVc2VyUHJlZmVyZW5jZXMgPSAkQ3VzdG9tZXJVc2VyT2JqZWN0LT5HZXRQcmVmZXJlbmNlcygKICAgICAgICAgICAgICAgIFVzZXJJRCA9PiAkVGlja2V0e0N1c3RvbWVyVXNlcklEfSwKICAgICAgICAgICAgKTsKICAgICAgICB9CgogICAgICAgIGlmICggJFVzZXJQcmVmZXJlbmNlc3tVc2VyVGltZVpvbmV9ICkgewogICAgICAgICAgICAkUmVjaXBpZW50VGltZVpvbmUgPSAkVXNlclByZWZlcmVuY2Vze1VzZXJUaW1lWm9uZX07CiAgICAgICAgfQogICAgfQoKICAgICMgUmVwbGFjZSBVbml4IHRpbWUgZm9ybWF0IHRhZ3MuCiAgICAjIElmIGxhbmd1YWdlIGlzIGRlZmluZWQsIHRoZXkgd2lsbCBiZSBjb252ZXJ0ZWQgaW50byBhIGNvcnJlY3QgZm9ybWF0IGluIGJlbG93IElGIHN0YXRlbWVudC4KICAgIGZvciBteSAkVW5peEZvcm1hdFRpbWUgKAogICAgICAgIHF3KFJlYWxUaWxsVGltZU5vdFVzZWQgRXNjYWxhdGlvblJlc3BvbnNlVGltZSBFc2NhbGF0aW9uVXBkYXRlVGltZSBFc2NhbGF0aW9uU29sdXRpb25UaW1lKQogICAgICAgICkKICAgIHsKICAgICAgICBpZiAoICRUaWNrZXR7JFVuaXhGb3JtYXRUaW1lfSApIHsKICAgICAgICAgICAgJFRpY2tldHskVW5peEZvcm1hdFRpbWV9ID0gJEtlcm5lbDo6T00tPkNyZWF0ZSgKICAgICAgICAgICAgICAgICdLZXJuZWw6OlN5c3RlbTo6RGF0ZVRpbWUnLAogICAgICAgICAgICAgICAgT2JqZWN0UGFyYW1zID0+IHsKICAgICAgICAgICAgICAgICAgICBFcG9jaCA9PiAkVGlja2V0eyRVbml4Rm9ybWF0VGltZX0sCiAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICApLT5Ub1N0cmluZygpOwogICAgICAgIH0KICAgIH0KCiAgICAjIHRyYW5zbGF0ZSB0aWNrZXQgdmFsdWVzIGlmIG5lZWRlZAogICAgaWYgKCAkUGFyYW17TGFuZ3VhZ2V9ICkgewoKICAgICAgICBteSAkTGFuZ3VhZ2VPYmplY3QgPSBLZXJuZWw6Okxhbmd1YWdlLT5uZXcoCiAgICAgICAgICAgIFVzZXJMYW5ndWFnZSA9PiAkUGFyYW17TGFuZ3VhZ2V9LAogICAgICAgICk7CgogICAgICAgICMgVHJhbnNsYXRlIHRoZSBkaWZmZXJlbnQgdmFsdWVzLgogICAgICAgIGZvciBteSAkRmllbGQgKHF3KFR5cGUgU3RhdGUgU3RhdGVUeXBlIExvY2sgUHJpb3JpdHkpKSB7CiAgICAgICAgICAgICRUaWNrZXR7JEZpZWxkfSA9ICRMYW5ndWFnZU9iamVjdC0+VHJhbnNsYXRlKCAkVGlja2V0eyRGaWVsZH0gKTsKICAgICAgICB9CgogICAgICAgICMgVHJhbnNmb3JtIHRoZSBkYXRlIHZhbHVlcyBmcm9tIHRoZSB0aWNrZXQgZGF0YSAoYnV0IG5vdCB0aGUgZHluYW1pYyBmaWVsZCB2YWx1ZXMpLgogICAgICAgIEFUVFJJQlVURToKICAgICAgICBmb3IgbXkgJEF0dHJpYnV0ZSAoIHNvcnQga2V5cyAlVGlja2V0ICkgewogICAgICAgICAgICBuZXh0IEFUVFJJQlVURSBpZiAkQXR0cmlidXRlID1+IG17IFxBIER5bmFtaWNGaWVsZF8gfXhtczsKICAgICAgICAgICAgbmV4dCBBVFRSSUJVVEUgaWYgISRUaWNrZXR7JEF0dHJpYnV0ZX07CgogICAgICAgICAgICBpZiAoICRUaWNrZXR7JEF0dHJpYnV0ZX0gPX4gbXtcQShcZFxkXGRcZCktKFxkXGQpLShcZFxkKVxzKFxkXGQpOihcZFxkKTooXGRcZClcen14aSApIHsKCiAgICAgICAgICAgICAgICAjIENoYW5nZSB0aW1lIHRvIHJlY2lwaWVudCdzIHRpbWV6b25lIGlmIG5lZWRlZAogICAgICAgICAgICAgICAgIyBhbmQgbGF0ZXIgYXBwZW5kIHRpbWV6b25lIGluZm9ybWF0aW9uLgogICAgICAgICAgICAgICAgIyBGb3IgbW9yZSBpbmZvcm1hdGlvbiwKICAgICAgICAgICAgICAgICMgc2VlIGJ1ZyMxMzg2NSAoaHR0cHM6Ly9idWdzLm90cnMub3JnL3Nob3dfYnVnLmNnaT9pZD0xMzg2NSkKICAgICAgICAgICAgICAgICMgYW5kIGJ1ZyMxNDI3MCAoaHR0cHM6Ly9idWdzLm90cnMub3JnL3Nob3dfYnVnLmNnaT9pZD0xNDI3MCkuCiAgICAgICAgICAgICAgICBpZiAoJFJlY2lwaWVudFRpbWVab25lKSB7CiAgICAgICAgICAgICAgICAgICAgbXkgJERhdGVUaW1lT2JqZWN0ID0gJEtlcm5lbDo6T00tPkNyZWF0ZSgKICAgICAgICAgICAgICAgICAgICAgICAgJ0tlcm5lbDo6U3lzdGVtOjpEYXRlVGltZScsCiAgICAgICAgICAgICAgICAgICAgICAgIE9iamVjdFBhcmFtcyA9PiB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBTdHJpbmcgPT4gJFRpY2tldHskQXR0cmlidXRlfSwKICAgICAgICAgICAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgICAgICAgICApOwogICAgICAgICAgICAgICAgICAgICREYXRlVGltZU9iamVjdC0+VG9UaW1lWm9uZSggVGltZVpvbmUgPT4gJFJlY2lwaWVudFRpbWVab25lICk7CiAgICAgICAgICAgICAgICAgICAgJFRpY2tldHskQXR0cmlidXRlfSA9ICREYXRlVGltZU9iamVjdC0+VG9TdHJpbmcoKTsKICAgICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgICAkVGlja2V0eyRBdHRyaWJ1dGV9ID0gJExhbmd1YWdlT2JqZWN0LT5Gb3JtYXRUaW1lU3RyaW5nKAogICAgICAgICAgICAgICAgICAgICRUaWNrZXR7JEF0dHJpYnV0ZX0sCiAgICAgICAgICAgICAgICAgICAgJ0RhdGVGb3JtYXQnLAogICAgICAgICAgICAgICAgICAgICdOb1NlY29uZHMnLAogICAgICAgICAgICAgICAgKTsKCiAgICAgICAgICAgICAgICAjIEFwcGVuZCB0aW1lem9uZSBpbmZvcm1hdGlvbiBpZiBuZWVkZWQuCiAgICAgICAgICAgICAgICBpZiAoJFJlY2lwaWVudFRpbWVab25lKSB7CiAgICAgICAgICAgICAgICAgICAgJFRpY2tldHskQXR0cmlidXRlfSAuPSAiICgkUmVjaXBpZW50VGltZVpvbmUpIjsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgbXkgJExvY2FsTGF5b3V0T2JqZWN0ID0gS2VybmVsOjpPdXRwdXQ6OkhUTUw6OkxheW91dC0+bmV3KAogICAgICAgICAgICBMYW5nID0+ICRQYXJhbXtMYW5ndWFnZX0sCiAgICAgICAgKTsKCiAgICAgICAgIyBDb252ZXJ0IHRhZ3MgaW4gc2Vjb25kcyB0byBtb3JlIHJlYWRhYmxlIGFwcHJvcHJpYXRlIGZvcm1hdCBpZiBsYW5ndWFnZSBpcyBkZWZpbmVkLgogICAgICAgIGZvciBteSAkVGltZUluU2Vjb25kcyAoCiAgICAgICAgICAgIHF3KFVudGlsVGltZSBFc2NhbGF0aW9uVGltZVdvcmtpbmdUaW1lIEVzY2FsYXRpb25UaW1lIEZpcnN0UmVzcG9uc2VUaW1lV29ya2luZ1RpbWUgRmlyc3RSZXNwb25zZVRpbWUgVXBkYXRlVGltZVdvcmtpbmdUaW1lCiAgICAgICAgICAgIFVwZGF0ZVRpbWUgU29sdXRpb25UaW1lV29ya2luZ1RpbWUgU29sdXRpb25UaW1lKQogICAgICAgICAgICApCiAgICAgICAgewogICAgICAgICAgICBpZiAoICRUaWNrZXR7JFRpbWVJblNlY29uZHN9ICkgewogICAgICAgICAgICAgICAgJFRpY2tldHskVGltZUluU2Vjb25kc30gPSAkTG9jYWxMYXlvdXRPYmplY3QtPkN1c3RvbWVyQWdlKAogICAgICAgICAgICAgICAgICAgIEFnZSAgID0+ICRUaWNrZXR7JFRpbWVJblNlY29uZHN9LAogICAgICAgICAgICAgICAgICAgIFNwYWNlID0+ICcgJwogICAgICAgICAgICAgICAgKTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgIH0KCiAgICBteSAlUXVldWU7CiAgICBpZiAoICRQYXJhbXtRdWV1ZUlEfSApIHsKICAgICAgICAlUXVldWUgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6UXVldWUnKS0+UXVldWVHZXQoCiAgICAgICAgICAgIElEID0+ICRQYXJhbXtRdWV1ZUlEfSwKICAgICAgICApOwogICAgfQoKICAgIG15ICRDb25maWdPYmplY3QgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OkNvbmZpZycpOwoKICAgICMgUmVwbGFjZSBjb25maWcgb3B0aW9ucy4KICAgIG15ICRUYWcgPSAkU3RhcnQgLiAnT1RPQk9fQ09ORklHXyc7CiAgICAkUGFyYW17VGV4dH0gPX4gc3skVGFnKC4rPykkRW5kfXsKICAgICAgICBteSAkS2V5ICAgPSAkMTsKICAgICAgICBteSAkVmFsdWUgPSAkQ29uZmlnT2JqZWN0LT5HZXQoJEtleSkgLy8gJyc7CgogICAgICAgICMgTWFzayBzZW5zaXRpdmUgY29uZmlnIG9wdGlvbnMuCiAgICAgICAgbXkgJFJlcGxhY2UgPSAkU2VsZi0+X01hc2tTZW5zaXRpdmVWYWx1ZSgKICAgICAgICAgICAgS2V5ICAgICAgPT4gJEtleSwKICAgICAgICAgICAgVmFsdWUgICAgPT4gJFZhbHVlLAogICAgICAgICAgICBJc0NvbmZpZyA9PiAxLAogICAgICAgICk7CgogICAgICAgICRSZXBsYWNlOwogICAgfWVneDsKCiAgICAjIGNsZWFudXAKICAgICRQYXJhbXtUZXh0fSA9fiBzLyRUYWcuKz8kRW5kLy0vZ2k7CgogICAgbXkgJVJlY2lwaWVudCA9ICV7ICRQYXJhbXtSZWNpcGllbnR9IHx8IHt9IH07CgogICAgIyBnZXQgdXNlciBvYmplY3QKICAgIG15ICRVc2VyT2JqZWN0ID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OlVzZXInKTsKCiAgICBpZiAoICElUmVjaXBpZW50ICYmICRQYXJhbXtSZWNpcGllbnRJRH0gKSB7CgogICAgICAgICVSZWNpcGllbnQgPSAkVXNlck9iamVjdC0+R2V0VXNlckRhdGEoCiAgICAgICAgICAgIFVzZXJJRCAgICAgICAgPT4gJFBhcmFte1JlY2lwaWVudElEfSwKICAgICAgICAgICAgTm9PdXRPZk9mZmljZSA9PiAxLAogICAgICAgICk7CiAgICB9CgogICAgbXkgJEhhc2hHbG9iYWxSZXBsYWNlID0gc3ViIHsKICAgICAgICBteSAoICRUYWcsICVIICkgPSBAXzsKCiAgICAgICAgIyBHZW5lcmF0ZSBvbmUgc2luZ2xlIG1hdGNoaW5nIHN0cmluZyBmb3IgYWxsIGtleXMgdG8gc2F2ZSBwZXJmb3JtYW5jZS4KICAgICAgICBteSAkS2V5cyA9IGpvaW4gJ3wnLCBtYXAge3F1b3RlbWV0YX0gZ3JlcCB7IGRlZmluZWQgJEh7JF99IH0ga2V5cyAlSDsKCiAgICAgICAgIyBTZXQgYWxsIGtleXMgYXMgbG93ZXJjYXNlIHRvIGJlIGFibGUgdG8gbWF0Y2ggY2FzZSBpbnNlbnNpdGl2ZSwKICAgICAgICAjICAgZS4gZy4gPE9UT0JPX0NVU1RPTUVSX0Zyb20+IGFuZCA8T1RPQk9fQ1VTVE9NRVJfRlJPTT4uCiAgICAgICAgIyAgIEFsc28gbWFzayBhbnkgdmFsdWVzIGNvbnRhaW5pbmcgc2Vuc2l0aXZlIGRhdGEuCiAgICAgICAgJUggPSBtYXAgewogICAgICAgICAgICBsYyAkXyA9PiAkU2VsZi0+X01hc2tTZW5zaXRpdmVWYWx1ZSgKICAgICAgICAgICAgICAgIEtleSAgID0+ICRfLAogICAgICAgICAgICAgICAgVmFsdWUgPT4gJEh7JF99LAogICAgICAgICAgICApCiAgICAgICAgfSBzb3J0IGtleXMgJUg7CgogICAgICAgICMgSWYgdGFnIGlzICdPVE9CT19DVVNUT01FUl8nIGFkZCB0aGUgYm9keSBhbGlhcyAnZW1haWwvbm90ZScgdG8gYmUgcmVwbGFjZWQuCiAgICAgICAgaWYgKCAkVGFnID1+IG0vT1RPQk9fKENVU1RPTUVSfEFHRU5UKV8vICkgewogICAgICAgICAgICBLRVk6CiAgICAgICAgICAgIGZvciBteSAkS2V5IChxdyggZW1haWwgbm90ZSApKSB7CiAgICAgICAgICAgICAgICBteSAkVmFsdWUgPSAkSHskS2V5fTsKICAgICAgICAgICAgICAgIG5leHQgS0VZIGlmIGRlZmluZWQoJFZhbHVlKTsKCiAgICAgICAgICAgICAgICAkSHskS2V5fSA9ICRIeydib2R5J307CiAgICAgICAgICAgICAgICAkS2V5cyAuPSAnfCcgLiB1Y2ZpcnN0ICRLZXk7CiAgICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgICRQYXJhbXtUZXh0fSA9fiBzLyg/OiRUYWcpKCRLZXlzKSRFbmQvJEh7IGxjICQxIH0vaWVnOwogICAgfTsKCiAgICAjIGdldCByZWNpcGllbnQgZGF0YSBhbmQgcmVwbGFjZSBpdCB3aXRoIDxPVE9CT18uLi4KICAgICRUYWcgPSAkU3RhcnQgLiAnT1RPQk9fJzsKCiAgICAjIGluY2x1ZGUgbW9yZSByZWFkYWJsZSB0YWcgPE9UT0JPX05PVElGSUNBVElPTl9SRUNJUElFTlQKICAgIG15ICRSZWNpcGllbnRUYWcgPSAkU3RhcnQgLiAnT1RPQk9fTk9USUZJQ0FUSU9OX1JFQ0lQSUVOVF8nOwoKICAgIGlmICglUmVjaXBpZW50KSB7CgogICAgICAgICMgSFRNTCBxdW90aW5nIG9mIGNvbnRlbnQKICAgICAgICBpZiAoICRQYXJhbXtSaWNoVGV4dH0gKSB7CiAgICAgICAgICAgIEFUVFJJQlVURToKICAgICAgICAgICAgZm9yIG15ICRBdHRyaWJ1dGUgKCBzb3J0IGtleXMgJVJlY2lwaWVudCApIHsKICAgICAgICAgICAgICAgIG5leHQgQVRUUklCVVRFIGlmICEkUmVjaXBpZW50eyRBdHRyaWJ1dGV9OwogICAgICAgICAgICAgICAgJFJlY2lwaWVudHskQXR0cmlidXRlfSA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpIVE1MVXRpbHMnKS0+VG9IVE1MKAogICAgICAgICAgICAgICAgICAgIFN0cmluZyA9PiAkUmVjaXBpZW50eyRBdHRyaWJ1dGV9LAogICAgICAgICAgICAgICAgKTsKICAgICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgJEhhc2hHbG9iYWxSZXBsYWNlLT4oICIkVGFnfCRSZWNpcGllbnRUYWciLCAlUmVjaXBpZW50ICk7CiAgICB9CgogICAgIyBjbGVhbnVwCiAgICAkUGFyYW17VGV4dH0gPX4gcy8kUmVjaXBpZW50VGFnLis/JEVuZC8tL2dpOwoKICAgICMgZ2V0IG93bmVyIGRhdGEgYW5kIHJlcGxhY2UgaXQgd2l0aCA8T1RPQk9fT1dORVJfLi4uCiAgICAkVGFnID0gJFN0YXJ0IC4gJ09UT0JPX09XTkVSXyc7CgogICAgIyBpbmNsdWRlIG1vcmUgcmVhZGFibGUgdmVyc2lvbiA8T1RPQk9fVElDS0VUX09XTkVSCiAgICBteSAkT3duZXJUYWcgPSAkU3RhcnQgLiAnT1RPQk9fVElDS0VUX09XTkVSXyc7CgogICAgaWYgKCAkVGlja2V0e093bmVySUR9ICkgewoKICAgICAgICBteSAlT3duZXIgPSAkVXNlck9iamVjdC0+R2V0VXNlckRhdGEoCiAgICAgICAgICAgIFVzZXJJRCAgICAgICAgPT4gJFRpY2tldHtPd25lcklEfSwKICAgICAgICAgICAgTm9PdXRPZk9mZmljZSA9PiAxLAogICAgICAgICk7CgogICAgICAgICMgaHRtbCBxdW90aW5nIG9mIGNvbnRlbnQKICAgICAgICBpZiAoICRQYXJhbXtSaWNoVGV4dH0gKSB7CgogICAgICAgICAgICBBVFRSSUJVVEU6CiAgICAgICAgICAgIGZvciBteSAkQXR0cmlidXRlICggc29ydCBrZXlzICVPd25lciApIHsKICAgICAgICAgICAgICAgIG5leHQgQVRUUklCVVRFIGlmICEkT3duZXJ7JEF0dHJpYnV0ZX07CiAgICAgICAgICAgICAgICAkT3duZXJ7JEF0dHJpYnV0ZX0gPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6SFRNTFV0aWxzJyktPlRvSFRNTCgKICAgICAgICAgICAgICAgICAgICBTdHJpbmcgPT4gJE93bmVyeyRBdHRyaWJ1dGV9LAogICAgICAgICAgICAgICAgKTsKICAgICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgJEhhc2hHbG9iYWxSZXBsYWNlLT4oICIkVGFnfCRPd25lclRhZyIsICVPd25lciApOwogICAgfQoKICAgICMgY2xlYW51cAogICAgJFBhcmFte1RleHR9ID1+IHMvJFRhZy4rPyRFbmQvLS9naTsKICAgICRQYXJhbXtUZXh0fSA9fiBzLyRPd25lclRhZy4rPyRFbmQvLS9naTsKCiAgICAjIGdldCBvd25lciBkYXRhIGFuZCByZXBsYWNlIGl0IHdpdGggPE9UT0JPX1JFU1BPTlNJQkxFXy4uLgogICAgJFRhZyA9ICRTdGFydCAuICdPVE9CT19SRVNQT05TSUJMRV8nOwoKICAgICMgaW5jbHVkZSBtb3JlIHJlYWRhYmxlIHZlcnNpb24gPE9UT0JPX1RJQ0tFVF9SRVNQT05TSUJMRQogICAgbXkgJFJlc3BvbnNpYmxlVGFnID0gJFN0YXJ0IC4gJ09UT0JPX1RJQ0tFVF9SRVNQT05TSUJMRV8nOwoKICAgIGlmICggJFRpY2tldHtSZXNwb25zaWJsZUlEfSApIHsKICAgICAgICBteSAlUmVzcG9uc2libGUgPSAkVXNlck9iamVjdC0+R2V0VXNlckRhdGEoCiAgICAgICAgICAgIFVzZXJJRCAgICAgICAgPT4gJFRpY2tldHtSZXNwb25zaWJsZUlEfSwKICAgICAgICAgICAgTm9PdXRPZk9mZmljZSA9PiAxLAogICAgICAgICk7CgogICAgICAgICMgSFRNTCBxdW90aW5nIG9mIGNvbnRlbnQKICAgICAgICBpZiAoICRQYXJhbXtSaWNoVGV4dH0gKSB7CgogICAgICAgICAgICBBVFRSSUJVVEU6CiAgICAgICAgICAgIGZvciBteSAkQXR0cmlidXRlICggc29ydCBrZXlzICVSZXNwb25zaWJsZSApIHsKICAgICAgICAgICAgICAgIG5leHQgQVRUUklCVVRFIGlmICEkUmVzcG9uc2libGV7JEF0dHJpYnV0ZX07CiAgICAgICAgICAgICAgICAkUmVzcG9uc2libGV7JEF0dHJpYnV0ZX0gPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6SFRNTFV0aWxzJyktPlRvSFRNTCgKICAgICAgICAgICAgICAgICAgICBTdHJpbmcgPT4gJFJlc3BvbnNpYmxleyRBdHRyaWJ1dGV9LAogICAgICAgICAgICAgICAgKTsKICAgICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgJEhhc2hHbG9iYWxSZXBsYWNlLT4oICIkVGFnfCRSZXNwb25zaWJsZVRhZyIsICVSZXNwb25zaWJsZSApOwogICAgfQoKICAgICMgY2xlYW51cAogICAgJFBhcmFte1RleHR9ID1+IHMvJFRhZy4rPyRFbmQvLS9naTsKICAgICRQYXJhbXtUZXh0fSA9fiBzLyRSZXNwb25zaWJsZVRhZy4rPyRFbmQvLS9naTsKCiAgICAkVGFnID0gJFN0YXJ0IC4gJ09UT0JPX0FnZW50Xyc7CiAgICBteSAkVGFnMiAgICAgICAgPSAkU3RhcnQgLiAnT1RPQk9fQ1VSUkVOVF8nOwogICAgbXkgJUN1cnJlbnRVc2VyID0gJFVzZXJPYmplY3QtPkdldFVzZXJEYXRhKAogICAgICAgIFVzZXJJRCAgICAgICAgPT4gJFBhcmFte1VzZXJJRH0sCiAgICAgICAgTm9PdXRPZk9mZmljZSA9PiAxLAogICAgKTsKCiAgICAjIEhUTUwgcXVvdGluZyBvZiBjb250ZW50CiAgICBpZiAoICRQYXJhbXtSaWNoVGV4dH0gKSB7CgogICAgICAgIEFUVFJJQlVURToKICAgICAgICBmb3IgbXkgJEF0dHJpYnV0ZSAoIHNvcnQga2V5cyAlQ3VycmVudFVzZXIgKSB7CiAgICAgICAgICAgIG5leHQgQVRUUklCVVRFIGlmICEkQ3VycmVudFVzZXJ7JEF0dHJpYnV0ZX07CiAgICAgICAgICAgICRDdXJyZW50VXNlcnskQXR0cmlidXRlfSA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpIVE1MVXRpbHMnKS0+VG9IVE1MKAogICAgICAgICAgICAgICAgU3RyaW5nID0+ICRDdXJyZW50VXNlcnskQXR0cmlidXRlfSwKICAgICAgICAgICAgKTsKICAgICAgICB9CiAgICB9CgogICAgJEhhc2hHbG9iYWxSZXBsYWNlLT4oICIkVGFnfCRUYWcyIiwgJUN1cnJlbnRVc2VyICk7CgogICAgIyByZXBsYWNlIG90aGVyIG5lZWRlZCBzdHVmZgogICAgJFBhcmFte1RleHR9ID1+IHMvJFN0YXJ0IE9UT0JPX0ZJUlNUX05BTUUgJEVuZC8kQ3VycmVudFVzZXJ7VXNlckZpcnN0bmFtZX0vZ3htczsKICAgICRQYXJhbXtUZXh0fSA9fiBzLyRTdGFydCBPVE9CT19MQVNUX05BTUUgJEVuZC8kQ3VycmVudFVzZXJ7VXNlckxhc3RuYW1lfS9neG1zOwoKICAgICMgY2xlYW51cAogICAgJFBhcmFte1RleHR9ID1+IHMvJFRhZzIuKz8kRW5kLy0vZ2k7CgojIFJvdGhlciBPU1MgLyBPbmVUaW1lQXV0aGVudGljYXRpb25MaW5rCiAgICAjIFJlcGxhY2UgY29uZmlnIG9wdGlvbnMuCiAgICAkVGFnID0gJFN0YXJ0IC4gJ09UT0JPX09UQUN1c3RvbWVyVGlja2V0TGluayc7CiAgICAkUGFyYW17VGV4dH0gPX4gc3skVGFnJEVuZH17CiAgICAgICAgbXkgJFJlcGxhY2UgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6Q3VzdG9tZXJBdXRoOjpPbmVUaW1lQXV0aExpbmsnKS0+VGlja2V0TGluaygKICAgICAgICAgICAgVGlja2V0TnVtYmVyID0+ICRUaWNrZXR7VGlja2V0TnVtYmVyfSwKICAgICAgICAgICAgVXNlciAgICAgICAgID0+ICRUaWNrZXR7Q3VzdG9tZXJVc2VySUR9LAogICAgICAgICk7CgogICAgICAgICRSZXBsYWNlOwogICAgfWVneDsKIyBFTyBPbmVUaW1lQXV0aGVudGljYXRpb25MaW5rCgogICAgIyB0aWNrZXQgZGF0YQogICAgJFRhZyA9ICRTdGFydCAuICdPVE9CT19USUNLRVRfJzsKCiAgICAjIGh0bWwgcXVvdGluZyBvZiBjb250ZW50CiAgICBpZiAoICRQYXJhbXtSaWNoVGV4dH0gKSB7CgogICAgICAgIEFUVFJJQlVURToKICAgICAgICBmb3IgbXkgJEF0dHJpYnV0ZSAoIHNvcnQga2V5cyAlVGlja2V0ICkgewogICAgICAgICAgICBuZXh0IEFUVFJJQlVURSBpZiAhJFRpY2tldHskQXR0cmlidXRlfTsKICAgICAgICAgICAgJFRpY2tldHskQXR0cmlidXRlfSA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpIVE1MVXRpbHMnKS0+VG9IVE1MKAogICAgICAgICAgICAgICAgU3RyaW5nID0+ICRUaWNrZXR7JEF0dHJpYnV0ZX0sCiAgICAgICAgICAgICk7CiAgICAgICAgfQogICAgfQoKICAgICMgRHJvcGRvd24sIENoZWNrYm94IGFuZCBNdWx0aXBsZVNlbGVjdCBEeW5hbWljRmllbGRzLCBjYW4gc3RvcmUgdmFsdWVzIChrZXlzKSB0aGF0IGFyZQogICAgIyBkaWZmZXJlbnQgZnJvbSB0aGUgdGhlIHZhbHVlcyB0byBkaXNwbGF5CiAgICAjIDxPVE9CT19USUNLRVRfRHluYW1pY0ZpZWxkX05hbWVYPiByZXR1cm5zIHRoZSBzdG9yZWQga2V5CiAgICAjIDxPVE9CT19USUNLRVRfRHluYW1pY0ZpZWxkX05hbWVYX1ZhbHVlPiByZXR1cm5zIHRoZSBkaXNwbGF5IHZhbHVlCgogICAgbXkgJUR5bmFtaWNGaWVsZHM7CgogICAgIyBGb3Igc3lzdGVtcyB3aXRoIG1hbnkgRHluYW1pYyBmaWVsZHMgd2UgZG8gbm90IHdhbnQgdG8gbG9hZCB0aGVtIGFsbCB1bmxlc3MgbmVlZGVkCiAgICAjIEZpbmQgd2hhdCBEeW5hbWljIEZpZWxkIFZhbHVlcyBhcmUgcmVxdWVzdGVkCiAgICB3aGlsZSAoICRQYXJhbXtUZXh0fSA9fiBtLyRUYWcgRHluYW1pY0ZpZWxkXyhcUys/KShfVmFsdWUpPyAkRW5kL2dpeG1zICkgewogICAgICAgICREeW5hbWljRmllbGRzeyQxfSA9IDE7CiAgICB9CgogICAgIyB0byBzdG9yZSBhbGwgdGhlIHJlcXVpcmVkIER5bmFtaWNGaWVsZCBkaXNwbGF5IHZhbHVlcwogICAgbXkgJUR5bmFtaWNGaWVsZERpc3BsYXlWYWx1ZXM7CgogICAgIyBnZXQgZHluYW1pYyBmaWVsZCBvYmplY3RzCiAgICBteSAkRHluYW1pY0ZpZWxkT2JqZWN0ICAgICAgICA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpEeW5hbWljRmllbGQnKTsKICAgIG15ICREeW5hbWljRmllbGRCYWNrZW5kT2JqZWN0ID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkR5bmFtaWNGaWVsZDo6QmFja2VuZCcpOwoKICAgICMgZ2V0IHRoZSBkeW5hbWljIGZpZWxkcyBmb3IgdGlja2V0IG9iamVjdAogICAgbXkgJER5bmFtaWNGaWVsZExpc3QgPSAkRHluYW1pY0ZpZWxkT2JqZWN0LT5EeW5hbWljRmllbGRMaXN0R2V0KAogICAgICAgIFZhbGlkICAgICAgPT4gMSwKICAgICAgICBPYmplY3RUeXBlID0+IFsnVGlja2V0J10sCiAgICApIHx8IFtdOwoKICAgICMgY3ljbGUgdGhyb3VnaCB0aGUgYWN0aXZhdGVkIER5bmFtaWMgRmllbGRzIGZvciB0aGlzIHNjcmVlbgogICAgRFlOQU1JQ0ZJRUxEOgogICAgZm9yIG15ICREeW5hbWljRmllbGRDb25maWcgKCBAeyREeW5hbWljRmllbGRMaXN0fSApIHsKCiAgICAgICAgbmV4dCBEWU5BTUlDRklFTEQgaWYgIUlzSGFzaFJlZldpdGhEYXRhKCREeW5hbWljRmllbGRDb25maWcpOwoKICAgICAgICAjIHdlIG9ubHkgbG9hZCB0aGUgb25lcyByZXF1ZXN0ZWQKICAgICAgICBuZXh0IERZTkFNSUNGSUVMRCBpZiAhJER5bmFtaWNGaWVsZHN7ICREeW5hbWljRmllbGRDb25maWctPntOYW1lfSB9OwoKICAgICAgICBteSAkTGFuZ3VhZ2VPYmplY3Q7CgogICAgICAgICMgdHJhbnNsYXRlIHZhbHVlcyBpZiBuZWVkZWQKICAgICAgICBpZiAoICRQYXJhbXtMYW5ndWFnZX0gKSB7CiAgICAgICAgICAgICRMYW5ndWFnZU9iamVjdCA9IEtlcm5lbDo6TGFuZ3VhZ2UtPm5ldygKICAgICAgICAgICAgICAgIFVzZXJMYW5ndWFnZSA9PiAkUGFyYW17TGFuZ3VhZ2V9LAogICAgICAgICAgICApOwogICAgICAgIH0KCiAgICAgICAgbXkgJERhdGVUaW1lT2JqZWN0OwoKICAgICAgICAjIENoYW5nZSBEYXRlVGltZSBERiB2YWx1ZSBmb3IgdGlja2V0IGlmIG5lZWRlZC4KICAgICAgICBpZiAoCiAgICAgICAgICAgIGRlZmluZWQgJFRpY2tldHsgJ0R5bmFtaWNGaWVsZF8nIC4gJER5bmFtaWNGaWVsZENvbmZpZy0+e05hbWV9IH0KICAgICAgICAgICAgJiYgJER5bmFtaWNGaWVsZENvbmZpZy0+e0ZpZWxkVHlwZX0gZXEgJ0RhdGVUaW1lJwogICAgICAgICAgICAmJiAkUmVjaXBpZW50VGltZVpvbmUKICAgICAgICAgICAgKQogICAgICAgIHsKICAgICAgICAgICAgJERhdGVUaW1lT2JqZWN0ID0gJEtlcm5lbDo6T00tPkNyZWF0ZSgKICAgICAgICAgICAgICAgICdLZXJuZWw6OlN5c3RlbTo6RGF0ZVRpbWUnLAogICAgICAgICAgICAgICAgT2JqZWN0UGFyYW1zID0+IHsKICAgICAgICAgICAgICAgICAgICBTdHJpbmcgPT4gJFRpY2tldHsgJ0R5bmFtaWNGaWVsZF8nIC4gJER5bmFtaWNGaWVsZENvbmZpZy0+e05hbWV9IH0sCiAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICApOwogICAgICAgICAgICAkRGF0ZVRpbWVPYmplY3QtPlRvVGltZVpvbmUoIFRpbWVab25lID0+ICRSZWNpcGllbnRUaW1lWm9uZSApOwogICAgICAgICAgICAkVGlja2V0eyAnRHluYW1pY0ZpZWxkXycgLiAkRHluYW1pY0ZpZWxkQ29uZmlnLT57TmFtZX0gfSA9ICREYXRlVGltZU9iamVjdC0+VG9TdHJpbmcoKTsKICAgICAgICB9CgogICAgICAgICMgZ2V0IHRoZSBkaXNwbGF5IHZhbHVlIGZvciBlYWNoIGR5bmFtaWMgZmllbGQKICAgICAgICBteSAkRGlzcGxheVZhbHVlID0gJER5bmFtaWNGaWVsZEJhY2tlbmRPYmplY3QtPlZhbHVlTG9va3VwKAogICAgICAgICAgICBEeW5hbWljRmllbGRDb25maWcgPT4gJER5bmFtaWNGaWVsZENvbmZpZywKICAgICAgICAgICAgS2V5ICAgICAgICAgICAgICAgID0+ICRUaWNrZXR7ICdEeW5hbWljRmllbGRfJyAuICREeW5hbWljRmllbGRDb25maWctPntOYW1lfSB9LAogICAgICAgICAgICBMYW5ndWFnZU9iamVjdCAgICAgPT4gJExhbmd1YWdlT2JqZWN0LAogICAgICAgICk7CgogICAgICAgICMgZ2V0IHRoZSByZWFkYWJsZSB2YWx1ZSAodmFsdWUpIGZvciBlYWNoIGR5bmFtaWMgZmllbGQKICAgICAgICBteSAkRGlzcGxheVZhbHVlU3RyZyA9ICREeW5hbWljRmllbGRCYWNrZW5kT2JqZWN0LT5SZWFkYWJsZVZhbHVlUmVuZGVyKAogICAgICAgICAgICBEeW5hbWljRmllbGRDb25maWcgPT4gJER5bmFtaWNGaWVsZENvbmZpZywKICAgICAgICAgICAgVmFsdWUgICAgICAgICAgICAgID0+ICREaXNwbGF5VmFsdWUsCiAgICAgICAgKTsKCiAgICAgICAgIyBmaWxsIHRoZSBEeW5hbWljRmllbHNEaXNwbGF5VmFsdWVzCiAgICAgICAgaWYgKCREaXNwbGF5VmFsdWVTdHJnKSB7CiAgICAgICAgICAgICREeW5hbWljRmllbGREaXNwbGF5VmFsdWVzeyAnRHluYW1pY0ZpZWxkXycgLiAkRHluYW1pY0ZpZWxkQ29uZmlnLT57TmFtZX0gLiAnX1ZhbHVlJyB9ID0gJERpc3BsYXlWYWx1ZVN0cmctPntWYWx1ZX07CgogICAgICAgICAgICAjIEFkZCB0aW1lem9uZSBpbmZvIGlmIG5lZWRlZC4KICAgICAgICAgICAgaWYgKAogICAgICAgICAgICAgICAgZGVmaW5lZCAkVGlja2V0eyAnRHluYW1pY0ZpZWxkXycgLiAkRHluYW1pY0ZpZWxkQ29uZmlnLT57TmFtZX0gfQogICAgICAgICAgICAgICAgJiYgbGVuZ3RoICRUaWNrZXR7ICdEeW5hbWljRmllbGRfJyAuICREeW5hbWljRmllbGRDb25maWctPntOYW1lfSB9CiAgICAgICAgICAgICAgICAmJiAkRHluYW1pY0ZpZWxkQ29uZmlnLT57RmllbGRUeXBlfSBlcSAnRGF0ZVRpbWUnCiAgICAgICAgICAgICAgICAmJiAkUmVjaXBpZW50VGltZVpvbmUKICAgICAgICAgICAgICAgICkKICAgICAgICAgICAgewogICAgICAgICAgICAgICAgJER5bmFtaWNGaWVsZERpc3BsYXlWYWx1ZXN7ICdEeW5hbWljRmllbGRfJyAuICREeW5hbWljRmllbGRDb25maWctPntOYW1lfSAuICdfVmFsdWUnIH0KICAgICAgICAgICAgICAgICAgICAuPSAiICgkUmVjaXBpZW50VGltZVpvbmUpIjsKICAgICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgIyBnZXQgdGhlIHJlYWRhYmxlIHZhbHVlIChrZXkpIGZvciBlYWNoIGR5bmFtaWMgZmllbGQKICAgICAgICBteSAkVmFsdWVTdHJnID0gJER5bmFtaWNGaWVsZEJhY2tlbmRPYmplY3QtPlJlYWRhYmxlVmFsdWVSZW5kZXIoCiAgICAgICAgICAgIER5bmFtaWNGaWVsZENvbmZpZyA9PiAkRHluYW1pY0ZpZWxkQ29uZmlnLAogICAgICAgICAgICBWYWx1ZSAgICAgICAgICAgICAgPT4gJFRpY2tldHsgJ0R5bmFtaWNGaWVsZF8nIC4gJER5bmFtaWNGaWVsZENvbmZpZy0+e05hbWV9IH0sCiAgICAgICAgKTsKCiAgICAgICAgIyByZXBsYWNlIHRpY2tldCBjb250ZW50IHdpdGggdGhlIHZhbHVlIGZyb20gUmVhZGFibGVWYWx1ZVJlbmRlciAoaWYgYW55KQogICAgICAgIGlmICggSXNIYXNoUmVmV2l0aERhdGEoJFZhbHVlU3RyZykgKSB7CiAgICAgICAgICAgICRUaWNrZXR7ICdEeW5hbWljRmllbGRfJyAuICREeW5hbWljRmllbGRDb25maWctPntOYW1lfSB9ID0gJFZhbHVlU3RyZy0+e1ZhbHVlfTsKCiAgICAgICAgICAgICMgQWRkIHRpbWV6b25lIGluZm8gaWYgbmVlZGVkLgogICAgICAgICAgICBpZiAoCiAgICAgICAgICAgICAgICBkZWZpbmVkICRUaWNrZXR7ICdEeW5hbWljRmllbGRfJyAuICREeW5hbWljRmllbGRDb25maWctPntOYW1lfSB9CiAgICAgICAgICAgICAgICAmJiBsZW5ndGggJFRpY2tldHsgJ0R5bmFtaWNGaWVsZF8nIC4gJER5bmFtaWNGaWVsZENvbmZpZy0+e05hbWV9IH0KICAgICAgICAgICAgICAgICYmICREeW5hbWljRmllbGRDb25maWctPntGaWVsZFR5cGV9IGVxICdEYXRlVGltZScKICAgICAgICAgICAgICAgICYmICRSZWNpcGllbnRUaW1lWm9uZQogICAgICAgICAgICAgICAgKQogICAgICAgICAgICB7CiAgICAgICAgICAgICAgICAkVGlja2V0eyAnRHluYW1pY0ZpZWxkXycgLiAkRHluYW1pY0ZpZWxkQ29uZmlnLT57TmFtZX0gfSAuPSAiICgkUmVjaXBpZW50VGltZVpvbmUpIjsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgIH0KCiAgICAjIHJlcGxhY2UgaXQKICAgICRIYXNoR2xvYmFsUmVwbGFjZS0+KCAkVGFnLCAlVGlja2V0LCAlRHluYW1pY0ZpZWxkRGlzcGxheVZhbHVlcyApOwoKICAgICMgQ09NUEFUCiAgICAkUGFyYW17VGV4dH0gPX4gcy8kU3RhcnQgT1RPQk9fVElDS0VUX0lEICRFbmQvJFRpY2tldHtUaWNrZXRJRH0vZ2l4bXM7CiAgICAkUGFyYW17VGV4dH0gPX4gcy8kU3RhcnQgT1RPQk9fVElDS0VUX05VTUJFUiAkRW5kLyRUaWNrZXR7VGlja2V0TnVtYmVyfS9naXhtczsKICAgIGlmICggJFRpY2tldHtUaWNrZXRJRH0gKSB7CiAgICAgICAgJFBhcmFte1RleHR9ID1+IHMvJFN0YXJ0IE9UT0JPX1FVRVVFICRFbmQvJFRpY2tldHtRdWV1ZX0vZ2l4bXM7CiAgICB9CiAgICBpZiAoICRQYXJhbXtRdWV1ZUlEfSApIHsKICAgICAgICAkUGFyYW17VGV4dH0gPX4gcy8kU3RhcnQgT1RPQk9fVElDS0VUX1FVRVVFICRFbmQvJFF1ZXVle05hbWV9L2dpeG1zOwogICAgfQoKICAgICMgY2xlYW51cAogICAgJFBhcmFte1RleHR9ID1+IHMvJFRhZy4rPyRFbmQvLS9naTsKCiAgICAjIEZvbGxvdy11cCBmb3IgYnVnIzEwODI1LgogICAgIyBTZXQgZGF0YSBmb3IgcmVwbGFjaW5nIG9mIHNwZWNpZmljIHRhZ3MgaW4gVGVtcGxhdGVzOgogICAgIyAtIE9UT0JPX0FHRU5UX1NVQkpFQ1QsIE9UT0JPX0FHRU5UX0JPRFkgLSBzdWJqZWN0L2JvZHkgb2YgdGhlIENVUlJFTlQvTEFURVNUIGFnZW50IGFydGljbGUKICAgICMgLSBPVE9CT19DVVNUT01FUl9TVUJKRUNULCBPVE9CT19DVVNUT01FUl9CT0RZIC0gc3ViamVjdC9ib2R5IG9mIHRoZSBDVVJSRU5UL0xBVEVTVCBjdXN0b21lciBhcnRpY2xlCiAgICAjIC0gT1RPQk9fQUdFTlRfU1VCSkVDVFtuXSAgICAtIGZpcnN0IG4gY2hhcmFjdGVycyBvZiB0aGUgc3ViamVjdCBvZiB0aGUgQ1VSUkVOVC9MQVRFU1QgYWdlbnQgYXJ0aWNsZQogICAgIyAtIE9UT0JPX0FHRU5UX0JPRFlbbl0gICAgICAgLSBmaXJzdCBuIGxpbmVzIG9mIHRoZSBib2R5IG9mIHRoZSBDVVJSRU5UL0xBVEVTVCBhZ2VudCBhcnRpY2xlCiAgICAjIC0gT1RPQk9fQ1VTVE9NRVJfU1VCSkVDVFtuXSAtIGZpcnN0IG4gY2hhcmFjdGVycyBvZiB0aGUgc3ViamVjdCBvZiB0aGUgQ1VSUkVOVC9MQVRFU1QgY3VzdG9tZXIgYXJ0aWNsZQogICAgIyAtIE9UT0JPX0NVU1RPTUVSX0JPRFlbbl0gICAgLSBmaXJzdCBuIGxpbmVzIG9mIHRoZSBib2R5IG9mIHRoZSBDVVJSRU5UL0xBVEVTVCBjdXN0b21lciBhcnRpY2xlCiAgICAjCiAgICAjIEZvciBOb3RlIHRlbXBsYXRlIHdlIG5lZWQgdGhlIGxhc3QgYXJ0aWNsZS4KICAgICMgRm9yIEFuc3dlciwgJFBhcmFte0RhdGF9IGhhcyBzZWxlY3RlZCBvciBsYXN0IGFydGljbGUgZGF0YSwgZGVwZW5kcyB3aGV0aGVyIEFydGljbGVJRCBpcyBzZW50IG9yIG5vdC4KICAgICMgRm9yIEZvcndhcmQsICRQYXJhbXtEYXRhfSBoYXMgdGhlIGZvbGxvd2luZyBhcnRpY2xlIGRhdGE6CiAgICAjIC0gaWYgQXJ0aWNsZUlEIGlzIHNlbnQsIGRhdGEgaXMgZnJvbSBzZWxlY3RlZCBhcnRpY2xlLgogICAgIyAtIGlmIEFydGljbGVJRCBpcyBub3Qgc2VudCwgZGF0YSBpcyBmcm9tIGxhc3QgY3VzdG9tZXIvYWdlbnQvYW55IGFydGljbGUuCiAgICBpZiAoICRQYXJhbXtUZW1wbGF0ZX0gJiYgJFRpY2tldHtUaWNrZXRJRH0gKSB7CiAgICAgICAgbXkgJEFydGljbGVPYmplY3QgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6VGlja2V0OjpBcnRpY2xlJyk7CgogICAgICAgIGlmICggJFBhcmFte1RlbXBsYXRlfSBlcSAnTm90ZScgKSB7CgogICAgICAgICAgICAjIEdldCBsYXN0IGFydGljbGUgZnJvbSBhZ2VudC4KICAgICAgICAgICAgbXkgQEFnZW50QXJ0aWNsZXMgPSAkQXJ0aWNsZU9iamVjdC0+QXJ0aWNsZUxpc3QoCiAgICAgICAgICAgICAgICBUaWNrZXRJRCAgID0+ICRQYXJhbXtUaWNrZXREYXRhfS0+e1RpY2tldElEfSwKICAgICAgICAgICAgICAgIFNlbmRlclR5cGUgPT4gJ2FnZW50JywKICAgICAgICAgICAgICAgIE9ubHlMYXN0ICAgPT4gMSwKICAgICAgICAgICAgKTsKCiAgICAgICAgICAgIG15ICVBZ2VudEFydGljbGUgPSAkQXJ0aWNsZU9iamVjdC0+QmFja2VuZEZvckFydGljbGUoICV7ICRBZ2VudEFydGljbGVzWzBdIH0gKS0+QXJ0aWNsZUdldCgKICAgICAgICAgICAgICAgICV7ICRBZ2VudEFydGljbGVzWzBdIH0sCiAgICAgICAgICAgICAgICBEeW5hbWljRmllbGRzID0+IDAsCiAgICAgICAgICAgICk7CgogICAgICAgICAgICAjIEdldCBsYXN0IGFydGljbGUgZnJvbSBjdXN0b21lci4KICAgICAgICAgICAgbXkgQEN1c3RvbWVyQXJ0aWNsZXMgPSAkQXJ0aWNsZU9iamVjdC0+QXJ0aWNsZUxpc3QoCiAgICAgICAgICAgICAgICBUaWNrZXRJRCAgID0+ICRQYXJhbXtUaWNrZXREYXRhfS0+e1RpY2tldElEfSwKICAgICAgICAgICAgICAgIFNlbmRlclR5cGUgPT4gJ2N1c3RvbWVyJywKICAgICAgICAgICAgICAgIE9ubHlMYXN0ICAgPT4gMSwKICAgICAgICAgICAgKTsKCiAgICAgICAgICAgIG15ICVDdXN0b21lckFydGljbGUgPSAkQXJ0aWNsZU9iamVjdC0+QmFja2VuZEZvckFydGljbGUoICV7ICRDdXN0b21lckFydGljbGVzWzBdIH0gKS0+QXJ0aWNsZUdldCgKICAgICAgICAgICAgICAgICV7ICRDdXN0b21lckFydGljbGVzWzBdIH0sCiAgICAgICAgICAgICAgICBEeW5hbWljRmllbGRzID0+IDAsCiAgICAgICAgICAgICk7CgogICAgICAgICAgICAkUGFyYW17RGF0YUFnZW50fS0+e1N1YmplY3R9ID0gJEFnZW50QXJ0aWNsZXtTdWJqZWN0fTsKICAgICAgICAgICAgJFBhcmFte0RhdGFBZ2VudH0tPntCb2R5fSAgICA9ICRBZ2VudEFydGljbGV7Qm9keX07CiAgICAgICAgICAgICRQYXJhbXtEYXRhfS0+e1N1YmplY3R9ICAgICAgPSAkQ3VzdG9tZXJBcnRpY2xle1N1YmplY3R9OwogICAgICAgICAgICAkUGFyYW17RGF0YX0tPntCb2R5fSAgICAgICAgID0gJEN1c3RvbWVyQXJ0aWNsZXtCb2R5fTsKICAgICAgICB9CiAgICAgICAgZWxzaWYgKCAkUGFyYW17VGVtcGxhdGV9IGVxICdBbnN3ZXInIHx8ICRQYXJhbXtUZW1wbGF0ZX0gZXEgJ0ZvcndhcmQnICkgewoKICAgICAgICAgICAgIyBJZiAkUGFyYW17RGF0YX0gaGFzIGFnZW50IGFydGljbGUgZGF0YSwgd2Ugd2lsbCBzZXQgc3ViamVjdCBhbmQgYm9keSBpbiAkUGFyYW17RGF0YUFnZW50fQogICAgICAgICAgICAjIHRvIHZhbHVlcyBmcm9tICRQYXJhbXtEYXRhfSBpbiBvcmRlciB0byByaWdodCByZXBsYWNpbmcgb2YgT1RPQk9fQUdFTlRfU1VCSkVDVC9CT0RZIHRhZ3MuCiAgICAgICAgICAgIGlmICggJFBhcmFte0RhdGF9LT57U2VuZGVyVHlwZX0gJiYgJFBhcmFte0RhdGF9LT57U2VuZGVyVHlwZX0gZXEgJ2FnZW50JyApIHsKICAgICAgICAgICAgICAgICRQYXJhbXtEYXRhQWdlbnR9LT57U3ViamVjdH0gPSAkUGFyYW17RGF0YX0tPntTdWJqZWN0fTsKICAgICAgICAgICAgICAgICRQYXJhbXtEYXRhQWdlbnR9LT57Qm9keX0gICAgPSAkUGFyYW17RGF0YX0tPntCb2R5fTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgIH0KCiAgICAjIGdldCBjdXN0b21lciBhbmQgYWdlbnQgcGFyYW1zIGFuZCByZXBsYWNlIGl0IHdpdGggPE9UT0JPX0NVU1RPTUVSXy4uLiBvciA8T1RPQk9fQUdFTlRfLi4uCiAgICBteSAlQXJ0aWNsZURhdGEgPSAoCiAgICAgICAgJ09UT0JPX0NVU1RPTUVSXycgPT4gJFBhcmFte0RhdGF9ICAgICAgfHwge30sCiAgICAgICAgJ09UT0JPX0FHRU5UXycgICAgPT4gJFBhcmFte0RhdGFBZ2VudH0gfHwge30sCiAgICApOwoKICAgICMgdXNlIGEgbGlzdCB0byBnZXQgY3VzdG9tZXIgZmlyc3QKICAgIGZvciBteSAkRGF0YVR5cGUgKHF3KE9UT0JPX0NVU1RPTUVSXyBPVE9CT19BR0VOVF8pKSB7CiAgICAgICAgbXkgJURhdGEgPSAleyAkQXJ0aWNsZURhdGF7JERhdGFUeXBlfSB9OwoKICAgICAgICAjIEhUTUwgcXVvdGluZyBvZiBjb250ZW50CiAgICAgICAgaWYgKCAkUGFyYW17UmljaFRleHR9ICkgewoKICAgICAgICAgICAgQVRUUklCVVRFOgogICAgICAgICAgICBmb3IgbXkgJEF0dHJpYnV0ZSAoIHNvcnQga2V5cyAlRGF0YSApIHsKICAgICAgICAgICAgICAgIG5leHQgQVRUUklCVVRFIGlmICEkRGF0YXskQXR0cmlidXRlfTsKCiAgICAgICAgICAgICAgICAkRGF0YXskQXR0cmlidXRlfSA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpIVE1MVXRpbHMnKS0+VG9IVE1MKAogICAgICAgICAgICAgICAgICAgIFN0cmluZyA9PiAkRGF0YXskQXR0cmlidXRlfSwKICAgICAgICAgICAgICAgICk7CiAgICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIGlmICglRGF0YSkgewoKICAgICAgICAgICAgIyByZXBsYWNlIDxPVE9CT19DVVNUT01FUl8qPiBhbmQgPE9UT0JPX0FHRU5UXyo+IHRhZ3MKICAgICAgICAgICAgJFRhZyA9ICRTdGFydCAuICREYXRhVHlwZTsKICAgICAgICAgICAgJEhhc2hHbG9iYWxSZXBsYWNlLT4oICRUYWcsICVEYXRhICk7CgogICAgICAgICAgICAjIHByZXBhcmUgYm9keSAoaW5zZXJ0IG9sZCBlbWFpbCkgPE9UT0JPX0NVU1RPTUVSX0VNQUlMW25dPiwgPE9UT0JPX0NVU1RPTUVSX05PVEVbbl0+CiAgICAgICAgICAgICMgICA8T1RPQk9fQ1VTVE9NRVJfQk9EWVtuXT4sIDxPVE9CT19BR0VOVF9FTUFJTFtuXT4uLi4sIDxPVE9CT19DT01NRU5UPgoKICAgICAgICAgICAgIyBDaGFuZ2VkIHRoaXMgdG8gYSAnd2hpbGUnIHRvIGFsbG93IHRoZSBzYW1lIGtleS90YWcgbXVsdGlwbGUgdGltZXMgYW5kIGRpZmZlcmVudCBudW1iZXIgb2YgbGluZXMuCiAgICAgICAgICAgIHdoaWxlICgKICAgICAgICAgICAgICAgICRQYXJhbXtUZXh0fSA9fiAvJFN0YXJ0KD86JERhdGFUeXBlKEVNQUlMfE5PVEV8Qk9EWSlcWyguKz8pXF0pJEVuZC8KICAgICAgICAgICAgICAgIHx8CiAgICAgICAgICAgICAgICAkUGFyYW17VGV4dH0gPX4gLyRTdGFydCg/Ok9UT0JPX0NPTU1FTlQoXFsoLis/KVxdKT8pJEVuZC8KICAgICAgICAgICAgICAgICkKICAgICAgICAgICAgewoKICAgICAgICAgICAgICAgIG15ICRMaW5lICAgICAgID0gJDIgfHwgMjUwMDsKICAgICAgICAgICAgICAgIG15ICROZXdPbGRCb2R5ID0gJyc7CiAgICAgICAgICAgICAgICBteSBAQm9keSAgICAgICA9IHNwbGl0KCAvXG4vLCAkRGF0YXtCb2R5fSApOwoKICAgICAgICAgICAgICAgIGZvciBteSAkQ291bnRlciAoIDAgLi4gJExpbmUgLSAxICkgewoKICAgICAgICAgICAgICAgICAgICAjIDIwMDItMDYtMTQgcGF0Y2ggb2YgUGFibG8gUnVpeiBHYXJjaWEKICAgICAgICAgICAgICAgICAgICAjIGh0dHA6Ly9saXN0cy5vdG9iby5vcmcvcGlwZXJtYWlsL2Rldi8yMDAyLUp1bmUvMDAwMDEyLmh0bWwKICAgICAgICAgICAgICAgICAgICBpZiAoICQjQm9keSA+PSAkQ291bnRlciApIHsKCiAgICAgICAgICAgICAgICAgICAgICAgICMgYWRkIG5vIHF1b3RlIGNoYXIsIGRvIGl0IGxhdGVyIGJ5IHVzaW5nIERvY3VtZW50Q2xlYW51cCgpCiAgICAgICAgICAgICAgICAgICAgICAgIGlmICggJFBhcmFte1JpY2hUZXh0fSApIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICROZXdPbGRCb2R5IC49ICRCb2R5WyRDb3VudGVyXTsKICAgICAgICAgICAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICAgICAgICAgICAgIyBhZGQgIj4gIiBhcyBxdW90ZSBjaGFyCiAgICAgICAgICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgJE5ld09sZEJvZHkgLj0gIj4gJEJvZHlbJENvdW50ZXJdIjsKICAgICAgICAgICAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICAgICAgICAgICAgIyBhZGQgbmV3IGxpbmUKICAgICAgICAgICAgICAgICAgICAgICAgaWYgKCAkQ291bnRlciA8ICggJExpbmUgLSAxICkgKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAkTmV3T2xkQm9keSAuPSAiXG4iOwogICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgICRDb3VudGVyKys7CiAgICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgICAgY2hvbXAgJE5ld09sZEJvZHk7CgogICAgICAgICAgICAgICAgIyBIVE1MIHF1b3Rpbmcgb2YgY29udGVudAogICAgICAgICAgICAgICAgaWYgKCAkUGFyYW17UmljaFRleHR9ICYmICROZXdPbGRCb2R5ICkgewoKICAgICAgICAgICAgICAgICAgICAjIHJlbW92ZSB0cmFpbGluZyBuZXcgbGluZXMKICAgICAgICAgICAgICAgICAgICBmb3IgKCAxIC4uIDEwICkgewogICAgICAgICAgICAgICAgICAgICAgICAkTmV3T2xkQm9keSA9fiBzLyg8YnJcLz4pXHN7MCwyMH0kLy9nczsKICAgICAgICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgICAgICAgICMgYWRkIHF1b3RlCiAgICAgICAgICAgICAgICAgICAgJE5ld09sZEJvZHkgPSAiPGJsb2NrcXVvdGUgdHlwZT1cImNpdGVcIj4kTmV3T2xkQm9keTwvYmxvY2txdW90ZT4iOwogICAgICAgICAgICAgICAgICAgICROZXdPbGRCb2R5ID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkhUTUxVdGlscycpLT5Eb2N1bWVudENsZWFudXAoCiAgICAgICAgICAgICAgICAgICAgICAgIFN0cmluZyA9PiAkTmV3T2xkQm9keSwKICAgICAgICAgICAgICAgICAgICApOwogICAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICAgICMgcmVwbGFjZSB0YWcKICAgICAgICAgICAgICAgICRQYXJhbXtUZXh0fQogICAgICAgICAgICAgICAgICAgID1+IHMvJFN0YXJ0KD86KD86JERhdGFUeXBlKEVNQUlMfE5PVEV8Qk9EWSlcWyguKz8pXF18KD86T1RPQk9fQ09NTUVOVChcWyguKz8pXF0pPykpKSRFbmQvJE5ld09sZEJvZHkvOwogICAgICAgICAgICB9CgogICAgICAgICAgICAjIHJlcGxhY2UgPE9UT0JPX0NVU1RPTUVSX1NVQkpFQ1RbXT4gIGFuZCAgPE9UT0JPX0FHRU5UX1NVQkpFQ1RbXT4gdGFncwogICAgICAgICAgICAkVGFnID0gIiRTdGFydCREYXRhVHlwZSIgLiAnU1VCSkVDVCc7CiAgICAgICAgICAgIGlmICggJFBhcmFte1RleHR9ID1+IC8kVGFnXFsoLis/KVxdJEVuZC9nICkgewoKICAgICAgICAgICAgICAgIG15ICRTdWJqZWN0Q2hhciA9ICQxOwogICAgICAgICAgICAgICAgbXkgJFN1YmplY3QgICAgID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OlRpY2tldCcpLT5UaWNrZXRTdWJqZWN0Q2xlYW4oCiAgICAgICAgICAgICAgICAgICAgVGlja2V0TnVtYmVyID0+ICRUaWNrZXR7VGlja2V0TnVtYmVyfSwKICAgICAgICAgICAgICAgICAgICBTdWJqZWN0ICAgICAgPT4gJERhdGF7U3ViamVjdH0sCiAgICAgICAgICAgICAgICApOwoKICAgICAgICAgICAgICAgICRTdWJqZWN0ID1+IHMvXigueyRTdWJqZWN0Q2hhcn0pLiokLyQxIFsuLi5dLzsKICAgICAgICAgICAgICAgICRQYXJhbXtUZXh0fSA9fiBzLyRUYWdcWy4rP1xdJEVuZC8kU3ViamVjdC9nOwogICAgICAgICAgICB9CgogICAgICAgICAgICBpZiAoICREYXRhVHlwZSBlcSAnT1RPQk9fQ1VTVE9NRVJfJyApIHsKCiAgICAgICAgICAgICAgICAjIEdldCA8T1RPQk9fRU1BSUxfREFURVtdPiBmcm9tIGJvZHkgYW5kIHJlcGxhY2Ugd2l0aCByZWNlaXZlZCBkYXRlLgogICAgICAgICAgICAgICAgIyBUaGlzIHRhZyB3aWxsIGJlIGFibGUgdG8gdXNlIHdpdGggc3VwcG9ydGVkIE9UT0JPIHRpbWUgem9uZXMKICAgICAgICAgICAgICAgICMgICAoIGUuZy4gPE9UT0JPX0VNQUlMX0RBVEVbRXVyb3BlL0Jlcmxpbl0+LCA8T1RPQk9fRU1BSUxfREFURVtBc2lhL1Rva3lvXT4sCiAgICAgICAgICAgICAgICAjICAgPE9UT0JPX0VNQUlMX0RBVEVbQW1lcmljYS9EZW52ZXJdPiAsIC4uLikuCiAgICAgICAgICAgICAgICAjIElmIHlvdSB1c2UgdGFnIHdpdGhvdXQgdGltZSBpbiBzaW1wbGUgZm9ybWF0IGFzIDxPVE9CT19FTUFJTF9EQVRFPiwKICAgICAgICAgICAgICAgICMgIHRpbWUgd2lsbCBiZSB0cmFuc2Zvcm1lZCBpbnRvIE9UT0JPIFN5c3RlbVRpbWVab25lLgogICAgICAgICAgICAgICAgJFRhZyA9ICRTdGFydCAuICdPVE9CT19FTUFJTF9EQVRFJzsKCiAgICAgICAgICAgICAgICBteSAkRGF0ZVRpbWVPYmplY3QgPSAkS2VybmVsOjpPTS0+Q3JlYXRlKCdLZXJuZWw6OlN5c3RlbTo6RGF0ZVRpbWUnKTsKICAgICAgICAgICAgICAgIG15ICRTeXN0ZW1UaW1lWm9uZSA9ICREYXRlVGltZU9iamVjdC0+T1RPQk9UaW1lWm9uZUdldCgpOwogICAgICAgICAgICAgICAgd2hpbGUgKCAkUGFyYW17VGV4dH0gPX4gLyRUYWdcWyguKz8pXF0kRW5kL2cgKSB7CiAgICAgICAgICAgICAgICAgICAgbXkgJFRpbWVab25lICAgICAgPSAkMTsKICAgICAgICAgICAgICAgICAgICBteSAkVGltZVpvbmVWYWxpZCA9ICREYXRlVGltZU9iamVjdC0+SXNUaW1lWm9uZVZhbGlkKCBUaW1lWm9uZSA9PiAkVGltZVpvbmUgKTsKICAgICAgICAgICAgICAgICAgICBpZiAoJFRpbWVab25lVmFsaWQpIHsKICAgICAgICAgICAgICAgICAgICAgICAgJERhdGVUaW1lT2JqZWN0LT5Ub1RpbWVab25lKCBUaW1lWm9uZSA9PiAkVGltZVpvbmUgKTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgICAgICRUaW1lWm9uZSA9ICRTeXN0ZW1UaW1lWm9uZTsKICAgICAgICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgICAgICAgIG15ICRFbWFpbERhdGUgPSAkRGF0ZVRpbWVPYmplY3QtPkZvcm1hdCggRm9ybWF0ID0+ICclQSwgJUIgJWUsICVZIGF0ICVUICcgKTsKICAgICAgICAgICAgICAgICAgICAkRW1haWxEYXRlIC49ICIoJFRpbWVab25lKSI7CiAgICAgICAgICAgICAgICAgICAgJFBhcmFte1RleHR9ID1+IHMvJFRhZ1xbJDFcXSRFbmQvJEVtYWlsRGF0ZS9nOwogICAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICAgIGlmICggJFBhcmFte1RleHR9ID1+IC8kVGFnJEVuZC9nICkgewogICAgICAgICAgICAgICAgICAgIG15ICRUaW1lWm9uZSA9ICRTeXN0ZW1UaW1lWm9uZTsKICAgICAgICAgICAgICAgICAgICAkRGF0ZVRpbWVPYmplY3QtPlRvVGltZVpvbmUoIFRpbWVab25lID0+ICRUaW1lWm9uZSApOwoKICAgICAgICAgICAgICAgICAgICBteSAkRW1haWxEYXRlID0gJERhdGVUaW1lT2JqZWN0LT5Gb3JtYXQoIEZvcm1hdCA9PiAnJUEsICVCICVlLCAlWSBhdCAlVCAnICk7CiAgICAgICAgICAgICAgICAgICAgJEVtYWlsRGF0ZSAuPSAiKCRUaW1lWm9uZSkiOwogICAgICAgICAgICAgICAgICAgICRQYXJhbXtUZXh0fSA9fiBzLyRUYWckRW5kLyRFbWFpbERhdGUvZzsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgaWYgKCAkRGF0YVR5cGUgZXEgJ09UT0JPX0NVU1RPTUVSXycgKSB7CgogICAgICAgICAgICAjIGdldCBhbmQgcHJlcGFyZSByZWFsbmFtZQogICAgICAgICAgICAkVGFnID0gJFN0YXJ0IC4gJ09UT0JPX0NVU1RPTUVSX1JFQUxOQU1FJzsKICAgICAgICAgICAgaWYgKCAkUGFyYW17VGV4dH0gPX4gLyRUYWckRW5kL2kgKSB7CgogICAgICAgICAgICAgICAgbXkgJEZyb207CgogICAgICAgICAgICAgICAgaWYgKCAkVGlja2V0e0N1c3RvbWVyVXNlcklEfSApIHsKCiAgICAgICAgICAgICAgICAgICAgJEZyb20gPSAkQ3VzdG9tZXJVc2VyT2JqZWN0LT5DdXN0b21lck5hbWUoCiAgICAgICAgICAgICAgICAgICAgICAgIFVzZXJMb2dpbiA9PiAkVGlja2V0e0N1c3RvbWVyVXNlcklEfQogICAgICAgICAgICAgICAgICAgICk7CiAgICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgICAgIyB0cnkgdG8gZ2V0IHRoZSByZWFsIG5hbWUgZGlyZWN0bHkgZnJvbSB0aGUgZGF0YQogICAgICAgICAgICAgICAgJEZyb20gLy89ICRSZWNpcGllbnR7UmVhbG5hbWV9OwoKICAgICAgICAgICAgICAgICMgZ2V0IHJlYWwgbmFtZSBiYXNlZCBvbiByZXBseS10bwogICAgICAgICAgICAgICAgaWYgKCAhJEZyb20gJiYgJERhdGF7UmVwbHlUb30gKSB7CgogICAgICAgICAgICAgICAgICAgICRGcm9tID0gJERhdGF7UmVwbHlUb307CgogICAgICAgICAgICAgICAgICAgICMgcmVtb3ZlIGVtYWlsIGFkZHJlc3NlcwogICAgICAgICAgICAgICAgICAgICRGcm9tID1+IHMvJmx0Oy4qJmd0O3w8Lio+fFwoLipcKXxcInwmcXVvdDt8O3wsLy9nOwoKICAgICAgICAgICAgICAgICAgICAjIHJlbW92ZSBsZWFkaW5nL3RyYWlsaW5nIHNwYWNlcwogICAgICAgICAgICAgICAgICAgICRGcm9tID1+IHMvXlxzKy8vZzsKICAgICAgICAgICAgICAgICAgICAkRnJvbSA9fiBzL1xzKyQvL2c7CiAgICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgICAgIyBnZW5lcmF0ZSByZWFsIG5hbWUgYmFzZWQgb24gc2VuZGVyIGxpbmUKICAgICAgICAgICAgICAgIGlmICggISRGcm9tICkgewogICAgICAgICAgICAgICAgICAgICRGcm9tID0gJERhdGF7VG99IHx8ICcnOwoKICAgICAgICAgICAgICAgICAgICAjIHJlbW92ZSBlbWFpbCBhZGRyZXNzZXMKICAgICAgICAgICAgICAgICAgICAkRnJvbSA9fiBzLyZsdDsuKiZndDt8PC4qPnxcKC4qXCl8XCJ8JnF1b3Q7fDt8LC8vZzsKCiAgICAgICAgICAgICAgICAgICAgIyByZW1vdmUgbGVhZGluZy90cmFpbGluZyBzcGFjZXMKICAgICAgICAgICAgICAgICAgICAkRnJvbSA9fiBzL15ccysvL2c7CiAgICAgICAgICAgICAgICAgICAgJEZyb20gPX4gcy9ccyskLy9nOwogICAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICAgICMgcmVwbGFjZSA8T1RPQk9fQ1VTVE9NRVJfUkVBTE5BTUU+IHdpdGggZnJvbQogICAgICAgICAgICAgICAgJFBhcmFte1RleHR9ID1+IHMvJFRhZyRFbmQvJEZyb20vZzsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgIH0KCiAgICAjIGdldCBjdXN0b21lciBkYXRhIGFuZCByZXBsYWNlIGl0IHdpdGggPE9UT0JPX0NVU1RPTUVSX0RBVEFfLi4uCiAgICAkVGFnICA9ICRTdGFydCAuICdPVE9CT19DVVNUT01FUl8nOwogICAgJFRhZzIgPSAkU3RhcnQgLiAnT1RPQk9fQ1VTVE9NRVJfREFUQV8nOwoKICAgIGlmICggJFRpY2tldHtDdXN0b21lclVzZXJJRH0gfHwgJFBhcmFte0RhdGF9LT57Q3VzdG9tZXJVc2VySUR9ICkgewoKICAgICAgICBteSAkQ3VzdG9tZXJVc2VySUQgPSAkUGFyYW17RGF0YX0tPntDdXN0b21lclVzZXJJRH0gfHwgJFRpY2tldHtDdXN0b21lclVzZXJJRH07CgogICAgICAgIG15ICVDdXN0b21lclVzZXIgPSAkQ3VzdG9tZXJVc2VyT2JqZWN0LT5DdXN0b21lclVzZXJEYXRhR2V0KAogICAgICAgICAgICBVc2VyID0+ICRDdXN0b21lclVzZXJJRCwKICAgICAgICApOwoKICAgICAgICAjIEhUTUwgcXVvdGluZyBvZiBjb250ZW50CiAgICAgICAgaWYgKCAkUGFyYW17UmljaFRleHR9ICkgewoKICAgICAgICAgICAgQVRUUklCVVRFOgogICAgICAgICAgICBmb3IgbXkgJEF0dHJpYnV0ZSAoIHNvcnQga2V5cyAlQ3VzdG9tZXJVc2VyICkgewogICAgICAgICAgICAgICAgbmV4dCBBVFRSSUJVVEUgaWYgISRDdXN0b21lclVzZXJ7JEF0dHJpYnV0ZX07CiAgICAgICAgICAgICAgICAkQ3VzdG9tZXJVc2VyeyRBdHRyaWJ1dGV9ID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkhUTUxVdGlscycpLT5Ub0hUTUwoCiAgICAgICAgICAgICAgICAgICAgU3RyaW5nID0+ICRDdXN0b21lclVzZXJ7JEF0dHJpYnV0ZX0sCiAgICAgICAgICAgICAgICApOwogICAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAjIHJlcGxhY2UgaXQKICAgICAgICAkSGFzaEdsb2JhbFJlcGxhY2UtPiggIiRUYWd8JFRhZzIiLCAlQ3VzdG9tZXJVc2VyICk7CiAgICB9CgogICAgIyBjbGVhbnVwIGFsbCBub3QgbmVlZGVkIDxPVE9CT19DVVNUT01FUl9EQVRBXyB0YWdzCiAgICAkUGFyYW17VGV4dH0gPX4gcy8oPzokVGFnfCRUYWcyKS4rPyRFbmQvLS9naTsKCiAgICAjIGNsZWFudXAgYWxsIG5vdCBuZWVkZWQgPE9UT0JPX0FHRU5UXyB0YWdzCiAgICAkVGFnID0gJFN0YXJ0IC4gJ09UT0JPX0FHRU5UXyc7CiAgICAkUGFyYW17VGV4dH0gPX4gcy8kVGFnLis/JEVuZC8tL2dpOwoKICAgIHJldHVybiAkUGFyYW17VGV4dH07Cn0KCj1oZWFkMiBfUmVtb3ZlVW5TdXBwb3J0ZWRUYWcoKQoKY2xlYW51cCBhbGwgbm90IHN1cHBvcnRlZCB0YWdzCgogICAgbXkgJFRleHQgPSAkVGVtcGxhdGVHZW5lcmF0b3JPYmplY3QtPl9SZW1vdmVVblN1cHBvcnRlZFRhZygKICAgICAgICBUZXh0ID0+ICRTb21lVGV4dFdpdGhUYWdzLAogICAgICAgIExpc3RPZlVuU3VwcG9ydGVkVGFnID0+IFxATGlzdE9mVW5TdXBwb3J0ZWRUYWcsCiAgICApOwoKPWN1dAoKc3ViIF9SZW1vdmVVblN1cHBvcnRlZFRhZyB7CgogICAgbXkgKCAkU2VsZiwgJVBhcmFtICkgPSBAXzsKCiAgICAjIGNoZWNrIG5lZWRlZCBzdHVmZgogICAgZm9yIG15ICRJdGVtIChxdyhUZXh0IExpc3RPZlVuU3VwcG9ydGVkVGFnKSkgewogICAgICAgIGlmICggIWRlZmluZWQgJFBhcmFteyRJdGVtfSApIHsKICAgICAgICAgICAgJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkxvZycpLT5Mb2coCiAgICAgICAgICAgICAgICBQcmlvcml0eSA9PiAnZXJyb3InLAogICAgICAgICAgICAgICAgTWVzc2FnZSAgPT4gIk5lZWQgJEl0ZW0hIgogICAgICAgICAgICApOwogICAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgfQoKICAgIG15ICRTdGFydCA9ICc8JzsKICAgIG15ICRFbmQgICA9ICc+JzsKICAgIGlmICggJFNlbGYtPntSaWNoVGV4dH0gKSB7CiAgICAgICAgJFN0YXJ0ID0gJyZsdDsnOwogICAgICAgICRFbmQgICA9ICcmZ3Q7JzsKICAgICAgICAkUGFyYW17VGV4dH0gPX4gcy8oXG58XHIpLy9nOwogICAgfQoKICAgICMgQ2xlYW51cCBhbGwgbm90IHN1cHBvcnRlZCB0YWdzIHdpdGggYW5kIHdpdGhvdXQgbnVtYmVyLCBlLmcuIE9UT0JPX0NVU1RPTUVSX0JPRFkgYW5kIE9UT0JPX0NVU1RPTUVSX0JPRFlbbl0uCiAgICAjIFNlZSBodHRwczovL2J1Z3Mub3Rycy5vcmcvc2hvd19idWcuY2dpP2lkPTE0MzY5IGFuZCBodHRwczovL2J1Z3Mub3Rycy5vcmcvc2hvd19idWcuY2dpP2lkPTEwODI1LgogICAgbXkgJE5vdFN1cHBvcnRlZFRhZyA9ICRTdGFydCAuICIoPzoiIC4gam9pbiggInwiLCBAeyAkUGFyYW17TGlzdE9mVW5TdXBwb3J0ZWRUYWd9IH0gKSAuICIpKFxcWy4qP1xcXSk/IiAuICRFbmQ7CiAgICAkUGFyYW17VGV4dH0gPX4gcy8kTm90U3VwcG9ydGVkVGFnLy0vZ2k7CgogICAgcmV0dXJuICRQYXJhbXtUZXh0fTsKCn0KCj1oZWFkMiBfTWFza1NlbnNpdGl2ZVZhbHVlKCkKCk1hc2sgc2Vuc2l0aXZlIHZhbHVlLCBpLmUuIGEgcGFzc3dvcmQsIGEgc2VjdXJpdHkgdG9rZW4sIGV0Yy4KCiAgICBteSAkTWFza2VkVmFsdWUgPSAkU2VsZi0+X01hc2tTZW5zaXRpdmVWYWx1ZSgKICAgICAgICBLZXkgICAgICA9PiAnRGF0YWJhc2VQYXNzd29yZCcsICMgKHJlcXVpcmVkKSBOYW1lIG9mIHRoZSBmaWVsZC9rZXkuCiAgICAgICAgVmFsdWUgICAgPT4gJ3NlY3JldHZhbHVlJywgICAgICAjIChvcHRpb25hbCkgVmFsdWUgdG8gcG90ZW50aWFsbHkgbWFzay4KICAgICAgICBJc0NvbmZpZyA9PiAxLCAgICAgICAgICAgICAgICAgICMgKG9wdGlvbmFsKSBXaGV0aGVyIHRoZSB2YWx1ZSBpcyBhIGNvbmZpZyBvcHRpb24sIGRlZmF1bHQ6IDAuCiAgICApOwoKUmV0dXJucyBtYXNrZWQgdmFsdWUsIGluIGNhc2UgdGhlIGtleSBpcyBtYXRjaGVkOgoKICAgJE1hc2tlZFZhbHVlID0gJ3h4eCc7Cgo9Y3V0CgpzdWIgX01hc2tTZW5zaXRpdmVWYWx1ZSB7CiAgICBteSAoICRTZWxmLCAlUGFyYW0gKSA9IEBfOwoKICAgIHJldHVybiAnJyBpZiAhJFBhcmFte0tleX0gfHwgIWRlZmluZWQgJFBhcmFte1ZhbHVlfTsKCiAgICAjIFNraXAgbWFza2luZyBzZW5zaXRpdmUgdmFsdWVzIGZvciBEeW5hbWljIEZpZWxkcy4KICAgIHJldHVybiAkUGFyYW17VmFsdWV9IGlmICRQYXJhbXtLZXl9ID1+IHFyeyBkeW5hbWljZmllbGQgfXhpOwoKICAgICMgTWF0Y2ggZ2VuZXJhbCBrZXkgbmFtZXMsIGkuZS4gZnJvbSB0aGUgdXNlciBwcmVmZXJlbmNlcy4KICAgIG15ICRNYXRjaCA9IHFyeyBjb25maWd8c2VjcmV0fHBhc3N3fHVzZXJwd3xhdXRofHRva2VuIH14aTsKCiAgICAjIE1hdGNoIGZvcmJpZGRlbiBjb25maWcga2V5cy4KICAgIGlmICggJFBhcmFte0lzQ29uZmlnfSApIHsKICAgICAgICAkTWF0Y2ggPSBxcnsgKD86cGFzc3dvcmR8cHcpIFxkKiAkIH1zbXhpOwogICAgfQoKICAgIHJldHVybiAkUGFyYW17VmFsdWV9IGlmICRQYXJhbXtLZXl9ICF+ICRNYXRjaDsKCiAgICByZXR1cm4gJ3h4eCc7Cn0KCj1lbmQgSW50ZXJuYWw6Cgo9Y3V0CgoxOwo=
IyAtLQojIE9UT0JPIGlzIGEgd2ViLWJhc2VkIHRpY2tldGluZyBzeXN0ZW0gZm9yIHNlcnZpY2Ugb3JnYW5pc2F0aW9ucy4KIyAtLQojIENvcHlyaWdodCAoQykgMjAwMS0yMDIwIE9UUlMgQUcsIGh0dHBzOi8vb3Rycy5jb20vCiMgQ29weXJpZ2h0IChDKSAyMDE5LTIwMjIgUm90aGVyIE9TUyBHbWJILCBodHRwczovL290b2JvLmRlLwojIC0tCiMgJG9yaWdpbjogb3RvYm8gLSAxMDFkMDk0NTVkOGIyNTdhYWEwZmE5OWE1NmRjNTE4OGU5MDU4MGY1IC0gS2VybmVsL1N5c3RlbS9XZWIvSW50ZXJmYWNlQ3VzdG9tZXIucG0KIyAtLQojIFRoaXMgcHJvZ3JhbSBpcyBmcmVlIHNvZnR3YXJlOiB5b3UgY2FuIHJlZGlzdHJpYnV0ZSBpdCBhbmQvb3IgbW9kaWZ5IGl0IHVuZGVyCiMgdGhlIHRlcm1zIG9mIHRoZSBHTlUgR2VuZXJhbCBQdWJsaWMgTGljZW5zZSBhcyBwdWJsaXNoZWQgYnkgdGhlIEZyZWUgU29mdHdhcmUKIyBGb3VuZGF0aW9uLCBlaXRoZXIgdmVyc2lvbiAzIG9mIHRoZSBMaWNlbnNlLCBvciAoYXQgeW91ciBvcHRpb24pIGFueSBsYXRlciB2ZXJzaW9uLgojIFRoaXMgcHJvZ3JhbSBpcyBkaXN0cmlidXRlZCBpbiB0aGUgaG9wZSB0aGF0IGl0IHdpbGwgYmUgdXNlZnVsLCBidXQgV0lUSE9VVAojIEFOWSBXQVJSQU5UWTsgd2l0aG91dCBldmVuIHRoZSBpbXBsaWVkIHdhcnJhbnR5IG9mIE1FUkNIQU5UQUJJTElUWSBvciBGSVRORVNTCiMgRk9SIEEgUEFSVElDVUxBUiBQVVJQT1NFLiBTZWUgdGhlIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlIGZvciBtb3JlIGRldGFpbHMuCiMgWW91IHNob3VsZCBoYXZlIHJlY2VpdmVkIGEgY29weSBvZiB0aGUgR05VIEdlbmVyYWwgUHVibGljIExpY2Vuc2UKIyBhbG9uZyB3aXRoIHRoaXMgcHJvZ3JhbS4gSWYgbm90LCBzZWUgPGh0dHBzOi8vd3d3LmdudS5vcmcvbGljZW5zZXMvPi4KIyAtLQoKcGFja2FnZSBLZXJuZWw6OlN5c3RlbTo6V2ViOjpJbnRlcmZhY2VDdXN0b21lcjsKCnVzZSB2NS4yNDsKdXNlIHN0cmljdDsKdXNlIHdhcm5pbmdzOwp1c2UgbmFtZXNwYWNlOjphdXRvY2xlYW47CnVzZSB1dGY4OwoKIyBjb3JlIG1vZHVsZXMKdXNlIFRpbWU6OkhpUmVzIHF3KCk7CgojIENQQU4gbW9kdWxlcwoKIyBPVE9CTyBtb2R1bGVzCnVzZSBLZXJuZWw6OlN5c3RlbTo6VmFyaWFibGVDaGVjayBxdyhJc0FycmF5UmVmV2l0aERhdGEgSXNIYXNoUmVmV2l0aERhdGEpOwp1c2UgS2VybmVsOjpMYW5ndWFnZSBxdyhUcmFuc2xhdGFibGUpOwp1c2UgS2VybmVsOjpTeXN0ZW06OkRhdGVUaW1lOwoKb3VyIEBPYmplY3REZXBlbmRlbmNpZXMgPSAoCiAgICAnS2VybmVsOjpDb25maWcnLAogICAgJ0tlcm5lbDo6T3V0cHV0OjpIVE1MOjpMYXlvdXQnLAogICAgJ0tlcm5lbDo6U3lzdGVtOjpBdXRoU2Vzc2lvbicsCiAgICAnS2VybmVsOjpTeXN0ZW06OkNhY2hlJywKICAgICdLZXJuZWw6OlN5c3RlbTo6Q3VzdG9tZXJBdXRoJywKICAgICdLZXJuZWw6OlN5c3RlbTo6Q3VzdG9tZXJHcm91cCcsCiAgICAnS2VybmVsOjpTeXN0ZW06OkN1c3RvbWVyVXNlcicsCiAgICAnS2VybmVsOjpTeXN0ZW06OkRCJywKICAgICdLZXJuZWw6OlN5c3RlbTo6RW1haWwnLAogICAgJ0tlcm5lbDo6U3lzdGVtOjpMb2cnLAogICAgJ0tlcm5lbDo6U3lzdGVtOjpNYWluJywKICAgICdLZXJuZWw6OlN5c3RlbTo6U2NoZWR1bGVyJywKICAgICdLZXJuZWw6OlN5c3RlbTo6RGF0ZVRpbWUnLAogICAgJ0tlcm5lbDo6U3lzdGVtOjpXZWI6OlJlcXVlc3QnLAogICAgJ0tlcm5lbDo6U3lzdGVtOjpXZWI6OlJlc3BvbnNlJywKICAgICdLZXJuZWw6OlN5c3RlbTo6VmFsaWQnLAopOwoKPWhlYWQxIE5BTUUKCktlcm5lbDo6U3lzdGVtOjpXZWI6OkludGVyZmFjZUN1c3RvbWVyIC0gdGhlIGN1c3RvbWVyIHdlYiBpbnRlcmZhY2UKCj1oZWFkMSBTWU5PUFNJUwoKICAgIHVzZSBLZXJuZWw6OlN5c3RlbTo6V2ViOjpJbnRlcmZhY2VDdXN0b21lcjsKCiAgICAjIGEgUGxhY2sgcmVxdWVzdCBoYW5kbGVyCiAgICBteSAkQXBwID0gc3ViIHsKICAgICAgICBteSAkRW52ID0gc2hpZnQ7CgogICAgICAgIG15ICRJbnRlcmZhY2UgPSBLZXJuZWw6OlN5c3RlbTo6V2ViOjpJbnRlcmZhY2VDdXN0b21lci0+bmV3KAogICAgICAgICAgICAjIERlYnVnID0+IDEKICAgICAgICAgICAgUFNHSUVudiAgICA9PiAkRW52LAogICAgICAgICk7CgogICAgICAgICMgZ2VuZXJhdGUgY29udGVudCAoYWN0dWFsbHkgaGVhZGVycyBhcmUgZ2VuZXJhdGVkIGFzIGEgc2lkZSBlZmZlY3QpCiAgICAgICAgbXkgJENvbnRlbnQgPSAkSW50ZXJmYWNlLT5Db250ZW50KCk7CgogICAgICAgICMgYXNzdW1pbmcgYWxsIHdlbnQgd2VsbCBhbmQgSFRNTCB3YXMgZ2VuZXJhdGVkCiAgICAgICAgcmV0dXJuIFsKICAgICAgICAgICAgJzIwMCcsCiAgICAgICAgICAgIFsgJ0NvbnRlbnQtVHlwZScgPT4gJ3RleHQvaHRtbCcgXSwKICAgICAgICAgICAgJENvbnRlbnQKICAgICAgICBdOwogICAgfTsKCj1oZWFkMSBERVNDUklQVElPTgoKVGhpcyBtb2R1bGUgZ2VuZXJhdGVzIHRoZSBIVFRQIHJlc3BvbnNlIGZvciBGPGN1c3RvbWVyLnBsPi4KVGhpcyBjbGFzcyBpcyBtZWFudCB0byBiZSB1c2VkIHdpdGhpbiBhIFBsYWNrIHJlcXVlc3QgaGFuZGxlci4KU2VlIEY8YmluL3BzZ2ktYmluL290b2JvLnBzZ2k+IGZvciB0aGUgcmVhbCBsaXZlIHVzYWdlLgoKPWhlYWQxIFBVQkxJQyBJTlRFUkZBQ0UKCj1oZWFkMiBuZXcoKQoKY3JlYXRlIHRoZSB3ZWIgaW50ZXJmYWNlIG9iamVjdCBmb3IgRjxjdXN0b21lci5wbD4uCgo9Y3V0CgpzdWIgbmV3IHsKICAgIG15ICggJFR5cGUsICVQYXJhbSApID0gQF87CgogICAgIyBzdGFydCB3aXRoIGFuIGVtcHR5IGhhc2ggZm9yIHRoZSBuZXcgb2JqZWN0CiAgICBteSAkU2VsZiA9IGJsZXNzIHt9LCAkVHlwZTsKCiAgICAjIHNldCBkZWJ1ZyBsZXZlbAogICAgJFNlbGYtPntEZWJ1Z30gPSAkUGFyYW17RGVidWd9IHx8IDA7CgogICAgIyBwZXJmb3JtYW5jZSBsb2cgYmFzZWQgb24gaGlnaCByZXNvbHV0aW9uIHRpbWVzdGFtcHMKICAgICRTZWxmLT57UGVyZm9ybWFuY2VMb2dTdGFydH0gPSBUaW1lOjpIaVJlczo6dGltZSgpOwoKICAgICMgcmVnaXN0ZXIgb2JqZWN0IHBhcmFtcwogICAgJEtlcm5lbDo6T00tPk9iamVjdFBhcmFtQWRkKAogICAgICAgICdLZXJuZWw6OlN5c3RlbTo6TG9nJyA9PiB7CiAgICAgICAgICAgIExvZ1ByZWZpeCA9PiAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OkNvbmZpZycpLT5HZXQoJ0NHSUxvZ1ByZWZpeCcpIHx8ICdDdXN0b21lcicsCiAgICAgICAgfSwKICAgICAgICAnS2VybmVsOjpTeXN0ZW06OldlYjo6UmVxdWVzdCcgPT4gewogICAgICAgICAgICBQU0dJRW52ID0+ICRQYXJhbXtQU0dJRW52fSB8fCAwLAogICAgICAgIH0sCiAgICApOwoKICAgICMgZGVidWcgaW5mbwogICAgaWYgKCAkU2VsZi0+e0RlYnVnfSApIHsKICAgICAgICAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6TG9nJyktPkxvZygKICAgICAgICAgICAgUHJpb3JpdHkgPT4gJ2RlYnVnJywKICAgICAgICAgICAgTWVzc2FnZSAgPT4gJ0dsb2JhbCBoYW5kbGUgc3RhcnRlZC4uLicsCiAgICAgICAgKTsKICAgIH0KCiAgICByZXR1cm4gJFNlbGY7Cn0KCj1oZWFkMiBDb250ZW50KCkKCmV4ZWN1dGUgdGhlIG9iamVjdC4KU2V0IGhlYWRlcnMgaW4gS2VybmVsczo6U3lzdGVtOjpXZWI6OlJlcXVlc3Qgc2luZ2xldG9uIGFzIHNpZGUgZWZmZWN0LgoKICAgIG15ICRDb250ZW50ID0gJEludGVyZmFjZS0+Q29udGVudCgpOwoKPWN1dAoKc3ViIENvbnRlbnQgeyAgICAjIyBubyBjcml0aWMgcXcoU3Vicm91dGluZXM6OlJlcXVpcmVGaW5hbFJldHVybikKICAgIG15ICRTZWxmID0gc2hpZnQ7CgogICAgbXkgJENvbmZpZ09iamVjdCA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6Q29uZmlnJyk7CiAgICBteSAkUGFyYW1PYmplY3QgID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OldlYjo6UmVxdWVzdCcpOwoKICAgICMgQ2hlY2sgaWYgaHR0cHMgZm9yY2luZyBpcyBhY3RpdmUsIGFuZCByZWRpcmVjdCBpZiBuZWVkZWQuCiAgICBpZiAoICRDb25maWdPYmplY3QtPkdldCgnSFRUUFNGb3JjZVJlZGlyZWN0JykgKSB7CgogICAgICAgICMgQWxsb3cgSFRUUFMgdG8gYmUgJ29uJyBpbiBhIGNhc2UgaW5zZW5zaXRpdmUgd2F5LgogICAgICAgICMgSW4gT1RPQk8gMTAuMC4xIGl0IGhhZCB0byBiZSBsb3dlcmNhc2UgJ29uJy4KICAgICAgICBteSAkSFRUUFMgPSAkUGFyYW1PYmplY3QtPkhUVFBTKCdIVFRQUycpIC8vICcnOwogICAgICAgIGlmICggbGMgJEhUVFBTIG5lICdvbicgKSB7CiAgICAgICAgICAgIG15ICRIb3N0ICAgICAgICAgPSAkUGFyYW1PYmplY3QtPkhUVFAoJ0hPU1QnKSB8fCAkQ29uZmlnT2JqZWN0LT5HZXQoJ0ZRRE4nKTsKICAgICAgICAgICAgbXkgJFJlcXVlc3RVUkkgICA9ICRQYXJhbU9iamVjdC0+UmVxdWVzdFVSSSgpOwogICAgICAgICAgICBteSAkTGF5b3V0T2JqZWN0ID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpPdXRwdXQ6OkhUTUw6OkxheW91dCcpOwoKICAgICAgICAgICAgJExheW91dE9iamVjdC0+UmVkaXJlY3QoIEV4dFVSTCA9PiAiaHR0cHM6Ly8kSG9zdCRSZXF1ZXN0VVJJIiApOyAgICAjIHRocm93IGEgS2VybmVsOjpTeXN0ZW06OldlYjo6RXhjZXB0aW9uIGV4Y2VwdGlvbgogICAgICAgIH0KICAgIH0KCiAgICAjIGdldCBjb21tb24gZnJhbWV3b3JrIHBhcmFtcwogICAgbXkgJVBhcmFtOwogICAgJFBhcmFte1Nlc3Npb25OYW1lfSA9ICRDb25maWdPYmplY3QtPkdldCgnQ3VzdG9tZXJQYW5lbFNlc3Npb25OYW1lJykgICAgICAgICB8fCAnQ1NJRCc7CiAgICAkUGFyYW17U2Vzc2lvbklEfSAgID0gJFBhcmFtT2JqZWN0LT5HZXRQYXJhbSggUGFyYW0gPT4gJFBhcmFte1Nlc3Npb25OYW1lfSApIHx8ICcnOwoKICAgICMgZHJvcCBvbGQgc2Vzc2lvbiBpZCAoaWYgZXhpc3RzKQogICAgbXkgJFF1ZXJ5U3RyaW5nID0gJFBhcmFtT2JqZWN0LT5RdWVyeVN0cmluZygpIHx8ICcnOwogICAgJFF1ZXJ5U3RyaW5nID1+IHMvKFw/fCZ8O3wpJFBhcmFte1Nlc3Npb25OYW1lfSg9Jnw9O3w9Lis/Jnw9Lis/JCkvOy9nOwoKICAgICMgZGVmaW5lIGZyYW1ld29yayBwYXJhbXMKICAgIHsKICAgICAgICBteSAlRnJhbWV3b3JrUGFyYW1zID0gKAogICAgICAgICAgICBMYW5nICAgICAgICAgPT4gJycsCiAgICAgICAgICAgIEFjdGlvbiAgICAgICA9PiAnJywKICAgICAgICAgICAgU3ViYWN0aW9uICAgID0+ICcnLAogICAgICAgICAgICBSZXF1ZXN0ZWRVUkwgPT4gJFF1ZXJ5U3RyaW5nLAogICAgICAgICk7CiAgICAgICAgZm9yIG15ICRLZXkgKCBzb3J0IGtleXMgJUZyYW1ld29ya1BhcmFtcyApIHsKICAgICAgICAgICAgJFBhcmFteyRLZXl9ID0gJFBhcmFtT2JqZWN0LT5HZXRQYXJhbSggUGFyYW0gPT4gJEtleSApIHx8ICRGcmFtZXdvcmtQYXJhbXN7JEtleX07CiAgICAgICAgfQogICAgfQoKICAgICMgdmFsaWRhdGUgbGFuZ3VhZ2UKICAgIGlmICggJFBhcmFte0xhbmd9ICYmICRQYXJhbXtMYW5nfSAhfiBte1xBW2Etel17Mn0oPzpfW0EtWl17Mn0pP1x6fXhtcyApIHsKICAgICAgICBkZWxldGUgJFBhcmFte0xhbmd9OwogICAgfQoKICAgICMgQ2hlY2sgaWYgdGhlIGJyb3dzZXIgc2VuZHMgdGhlIFNlc3Npb25JRCBjb29raWUgYW5kIHNldCB0aGUgU2Vzc2lvbklELWNvb2tpZQogICAgIyBhcyBTZXNzaW9uSUQhIEdFVCBvciBQT1NUIFNlc3Npb25JRCBoYXZlIHRoZSBsb3dlc3QgcHJpb3JpdHkuCiAgICBpZiAoICRDb25maWdPYmplY3QtPkdldCgnU2Vzc2lvblVzZUNvb2tpZScpICkgewogICAgICAgICRQYXJhbXtTZXNzaW9uSURDb29raWV9ID0gJFBhcmFtT2JqZWN0LT5HZXRDb29raWUoIEtleSA9PiAkUGFyYW17U2Vzc2lvbk5hbWV9ICk7CiAgICAgICAgaWYgKCAkUGFyYW17U2Vzc2lvbklEQ29va2llfSApIHsKICAgICAgICAgICAgJFBhcmFte1Nlc3Npb25JRH0gPSAkUGFyYW17U2Vzc2lvbklEQ29va2llfTsKICAgICAgICB9CiAgICB9CgogICAgJEtlcm5lbDo6T00tPk9iamVjdFBhcmFtQWRkKAogICAgICAgICdLZXJuZWw6Ok91dHB1dDo6SFRNTDo6TGF5b3V0JyA9PiB7CiAgICAgICAgICAgIExhbmcgPT4gJFBhcmFte0xhbmd9LAogICAgICAgIH0sCiAgICAgICAgJ0tlcm5lbDo6TGFuZ3VhZ2UnID0+IHsKICAgICAgICAgICAgVXNlckxhbmd1YWdlID0+ICRQYXJhbXtMYW5nfQogICAgICAgIH0sCiAgICApOwoKICAgICMgUmVzdHJpY3QgQ29va2llIHRvIEhUVFBTIGlmIGl0IGlzIHVzZWQuCiAgICBteSAkQ29va2llU2VjdXJlQXR0cmlidXRlID0gJENvbmZpZ09iamVjdC0+R2V0KCdIdHRwVHlwZScpIGVxICdodHRwcycgPyAxIDogdW5kZWY7CgogICAgbXkgJERCQ2FuQ29ubmVjdCA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpEQicpLT5Db25uZWN0KCk7CgogICAgaWYgKCAhJERCQ2FuQ29ubmVjdCB8fCAkUGFyYW1PYmplY3QtPkVycm9yKCkgKSB7CiAgICAgICAgbXkgJExheW91dE9iamVjdCA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6T3V0cHV0OjpIVE1MOjpMYXlvdXQnKTsKICAgICAgICBpZiAoICEkREJDYW5Db25uZWN0ICkgewogICAgICAgICAgICAkTGF5b3V0T2JqZWN0LT5DdXN0b21lckZhdGFsRXJyb3IoCiAgICAgICAgICAgICAgICBDb21tZW50ID0+IFRyYW5zbGF0YWJsZSgnUGxlYXNlIGNvbnRhY3QgdGhlIGFkbWluaXN0cmF0b3IuJyksCiAgICAgICAgICAgICk7ICAgICMgdGhyb3dzIGEgS2VybmVsOjpTeXN0ZW06OldlYjo6RXhjZXB0aW9uCiAgICAgICAgfQogICAgICAgIGlmICggJFBhcmFtT2JqZWN0LT5FcnJvcigpICkgewogICAgICAgICAgICAkTGF5b3V0T2JqZWN0LT5DdXN0b21lckZhdGFsRXJyb3IoCiAgICAgICAgICAgICAgICBNZXNzYWdlID0+ICRQYXJhbU9iamVjdC0+RXJyb3IoKSwKICAgICAgICAgICAgICAgIENvbW1lbnQgPT4gVHJhbnNsYXRhYmxlKCdQbGVhc2UgY29udGFjdCB0aGUgYWRtaW5pc3RyYXRvci4nKSwKICAgICAgICAgICAgKTsgICAgIyB0aHJvd3MgYSBLZXJuZWw6OlN5c3RlbTo6V2ViOjpFeGNlcHRpb24KICAgICAgICB9CiAgICB9CgogICAgIyBnZXQgY29tbW9uIGFwcGxpY2F0aW9uIGFuZCBhZGQtb24gYXBwbGljYXRpb24gcGFyYW1zCiAgICBteSAlQ29tbW9uT2JqZWN0UGFyYW0gPSAleyAkQ29uZmlnT2JqZWN0LT5HZXQoJ0N1c3RvbWVyRnJvbnRlbmQ6OkNvbW1vblBhcmFtJykgfTsKICAgIGZvciBteSAkS2V5ICggc29ydCBrZXlzICVDb21tb25PYmplY3RQYXJhbSApIHsKICAgICAgICAkUGFyYW17JEtleX0gPSAkUGFyYW1PYmplY3QtPkdldFBhcmFtKCBQYXJhbSA9PiAkS2V5ICkgfHwgJENvbW1vbk9iamVjdFBhcmFteyRLZXl9OwogICAgfQoKICAgICMgc2VjdXJpdHkgY2hlY2sgQWN0aW9uIFBhcmFtIChyZXBsYWNlIG5vbi13b3JkIGNoYXJzKQogICAgJFBhcmFte0FjdGlvbn0gPX4gcy9cVy8vZzsKCiAgICBteSAkU2Vzc2lvbk9iamVjdCA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpBdXRoU2Vzc2lvbicpOwogICAgbXkgJFVzZXJPYmplY3QgICAgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6Q3VzdG9tZXJVc2VyJyk7CgogICAgIyBjaGVjayByZXF1ZXN0IHR5cGUKICAgIGlmICggJFBhcmFte0FjdGlvbn0gZXEgJ1ByZUxvZ2luJyApIHsKICAgICAgICBteSAkTGF5b3V0T2JqZWN0ID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpPdXRwdXQ6OkhUTUw6OkxheW91dCcpOwogICAgICAgICRQYXJhbXtSZXF1ZXN0ZWRVUkx9IHx8PSAnQWN0aW9uPUN1c3RvbWVyRGFzaGJvYXJkJzsKCiAgICAgICAgIyBsb2dpbiBzY3JlZW4KICAgICAgICByZXR1cm4gJExheW91dE9iamVjdC0+Q3VzdG9tZXJMb2dpbigKICAgICAgICAgICAgVGl0bGUgPT4gJ0xvZ2luJywKICAgICAgICAgICAgTW9kZSAgPT4gJ1ByZUxvZ2luJywKICAgICAgICAgICAgJVBhcmFtLAogICAgICAgICk7CiAgICB9CiAgICBlbHNpZiAoICRQYXJhbXtBY3Rpb259IGVxICdMb2dpbicgKSB7CgogICAgICAgICMgZ2V0IHBhcmFtcwogICAgICAgIG15ICRQb3N0VXNlciA9ICRQYXJhbU9iamVjdC0+R2V0UGFyYW0oIFBhcmFtID0+ICdVc2VyJyApIHx8ICcnOwoKICAgICAgICBteSAkUHJldmVudEJydXRlRm9yY2VDb25maWcgPSAkQ29uZmlnT2JqZWN0LT5HZXQoJ1NpbXBsZUJydXRlRm9yY2VQcm90ZWN0aW9uOjpHZW5lcmFsU2V0dGluZ3MnKTsKCiAgICAgICAgIyBpZiBzaW1wbGVicnV0ZWZvcmNlY29uZmlnIGlzIHZhbGlkCiAgICAgICAgaWYgKCAkUHJldmVudEJydXRlRm9yY2VDb25maWcgJiYgJFBvc3RVc2VyICkgewoKICAgICAgICAgICAgIyBjaGVjayBpZiB0aGUgbG9naW4gaXMgYmFubmVkCiAgICAgICAgICAgIG15ICRDYWNoZU9iamVjdCAgID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkNhY2hlJyk7CiAgICAgICAgICAgIG15ICRDaGVja0hhc2hVc2VyID0gJENhY2hlT2JqZWN0LT5HZXQoCiAgICAgICAgICAgICAgICBUeXBlID0+ICdCYW5uZWRMb2dpbnNDdXN0b21lcicsCiAgICAgICAgICAgICAgICBLZXkgID0+ICRQb3N0VXNlciwKICAgICAgICAgICAgKTsKCiAgICAgICAgICAgICMgY2hlY2sgaWYgQ2FjaGUgQ2hlY2tIYXNoVXNlciBleGlzdHMKICAgICAgICAgICAgaWYgKCRDaGVja0hhc2hVc2VyKSB7CiAgICAgICAgICAgICAgICBteSAlQmFuU3RhdHVzID0gJFNlbGYtPl9DaGVja0FuZFJlbW92ZUZyb21CYW5uZWRMaXN0KAogICAgICAgICAgICAgICAgICAgIFBvc3RVc2VyICAgICAgICAgICAgICAgID0+ICRQb3N0VXNlciwKICAgICAgICAgICAgICAgICAgICBQcmV2ZW50QnJ1dGVGb3JjZUNvbmZpZyA9PiAkUHJldmVudEJydXRlRm9yY2VDb25maWcsCiAgICAgICAgICAgICAgICApOwoKICAgICAgICAgICAgICAgIGlmICggJEJhblN0YXR1c3tCYW5uZWR9ICkgewoKICAgICAgICAgICAgICAgICAgICAjIG91dHB1dCBlcnJvciBtZXNzYWdlCiAgICAgICAgICAgICAgICAgICAgbXkgJExheW91dE9iamVjdCA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6T3V0cHV0OjpIVE1MOjpMYXlvdXQnKTsKCiAgICAgICAgICAgICAgICAgICAgcmV0dXJuICRMYXlvdXRPYmplY3QtPkN1c3RvbWVyTG9naW4oCiAgICAgICAgICAgICAgICAgICAgICAgICVQYXJhbSwKICAgICAgICAgICAgICAgICAgICAgICAgVGl0bGUgICA9PiAnTG9naW4nLAogICAgICAgICAgICAgICAgICAgICAgICBNZXNzYWdlID0+ICRMYXlvdXRPYmplY3QtPntMYW5ndWFnZU9iamVjdH0tPlRyYW5zbGF0ZSgKICAgICAgICAgICAgICAgICAgICAgICAgICAgICdUb28gbWFueSBmYWlsZWQgbG9naW4gYXR0ZW1wdHMsIHBsZWFzZSByZXRyeSBpbiAlcyBzLicsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAkQmFuU3RhdHVze1Jlc2lkdWFsVGltZX0KICAgICAgICAgICAgICAgICAgICAgICAgKSwKICAgICAgICAgICAgICAgICAgICAgICAgTG9naW5GYWlsZWQgPT4gMSwKICAgICAgICAgICAgICAgICAgICAgICAgTWVzc2FnZVR5cGUgPT4gJ0Vycm9yJywKICAgICAgICAgICAgICAgICAgICAgICAgVXNlciAgICAgICAgPT4gJFBvc3RVc2VyLAogICAgICAgICAgICAgICAgICAgICk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIG15ICRQb3N0UHcgPSAkUGFyYW1PYmplY3QtPkdldFBhcmFtKAogICAgICAgICAgICBQYXJhbSA9PiAnUGFzc3dvcmQnLAogICAgICAgICAgICBSYXcgICA9PiAxCiAgICAgICAgKSB8fCAnJzsKICAgICAgICBteSAkUG9zdFR3b0ZhY3RvclRva2VuID0gJFBhcmFtT2JqZWN0LT5HZXRQYXJhbSgKICAgICAgICAgICAgUGFyYW0gPT4gJ1R3b0ZhY3RvclRva2VuJywKICAgICAgICAgICAgUmF3ICAgPT4gMQogICAgICAgICkgfHwgJyc7CgogICAgICAgICMgY3JlYXRlIEF1dGhPYmplY3QKICAgICAgICBteSAkQXV0aE9iamVjdCA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpDdXN0b21lckF1dGgnKTsKCiMgUm90aGVyIE9TUyAvIE9uZVRpbWVBdXRoZW50aWNhdGlvbkxpbmsKICAgICAgICBteSAlRXh0ZW5kZWRBdXRoUGFyYW1zOwogICAgICAgIGZvciBteSAkTmFtZSAoICRBdXRoT2JqZWN0LT5FeHRlbmRlZFBhcmFtTmFtZXMoKSApIHsKICAgICAgICAgICAgJEV4dGVuZGVkQXV0aFBhcmFtc3skTmFtZX0gPSAkUGFyYW1PYmplY3QtPkdldFBhcmFtKAogICAgICAgICAgICAgICAgUGFyYW0gPT4gJE5hbWUsCiAgICAgICAgICAgICAgICBSYXcgICA9PiAxCiAgICAgICAgICAgICkgfHwgJyc7CiAgICAgICAgfQojIEVPIE9uZVRpbWVBdXRoZW50aWNhdGlvbkxpbmsKCiAgICAgICAgIyBjaGVjayBzdWJtaXR0ZWQgZGF0YQogICAgICAgIG15ICRVc2VyID0gJEF1dGhPYmplY3QtPkF1dGgoCiAgICAgICAgICAgIFVzZXIgICAgICAgICAgID0+ICRQb3N0VXNlciwKICAgICAgICAgICAgUHcgICAgICAgICAgICAgPT4gJFBvc3RQdywKICAgICAgICAgICAgVHdvRmFjdG9yVG9rZW4gPT4gJFBvc3RUd29GYWN0b3JUb2tlbiwKIyBSb3RoZXIgT1NTIC8gT25lVGltZUF1dGhlbnRpY2F0aW9uTGluawogICAgICAgICAgICAlRXh0ZW5kZWRBdXRoUGFyYW1zLAojIEVPIE9uZVRpbWVBdXRoZW50aWNhdGlvbkxpbmsKICAgICAgICApOwoKICAgICAgICAjIGFkZGl0aW9uYWwgdGFza3MgLyBpbmZvCiAgICAgICAgbXkgJFBvc3RBdXRoID0gJEF1dGhPYmplY3QtPlBvc3RBdXRoKCk7CgogICAgICAgIGlmICgkUG9zdEF1dGgpIHsKICAgICAgICAgICAgJFBhcmFte1JlcXVlc3RlZFVSTH0gPSAkUG9zdEF1dGgtPntSZXF1ZXN0ZWRVUkx9IC8vICRQYXJhbXtSZXF1ZXN0ZWRVUkx9OwogICAgICAgIH0KCiAgICAgICAgIyBsb2dpbiBpcyBpbnZhbGlkCiAgICAgICAgaWYgKCAhJFVzZXIgKSB7CgogICAgICAgICAgICBteSAkRXhwaXJlcyA9ICcrJyAuICRDb25maWdPYmplY3QtPkdldCgnU2Vzc2lvbk1heFRpbWUnKSAuICdzJzsKICAgICAgICAgICAgaWYgKCAhJENvbmZpZ09iamVjdC0+R2V0KCdTZXNzaW9uVXNlQ29va2llQWZ0ZXJCcm93c2VyQ2xvc2UnKSApIHsKICAgICAgICAgICAgICAgICRFeHBpcmVzID0gJyc7CiAgICAgICAgICAgIH0KCiAgICAgICAgICAgICMgdGVudGF0aXZlbHkgc2V0IGFuIHVzZWxlc3MgY29va2llLCBmb3IgY2hlY2tpbmcgY29va2llIHN1cHBvcnQKICAgICAgICAgICAgbXkgJExheW91dE9iamVjdCA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6T3V0cHV0OjpIVE1MOjpMYXlvdXQnKTsKICAgICAgICAgICAgJExheW91dE9iamVjdC0+U2V0Q29va2llKAogICAgICAgICAgICAgICAgS2V5ICAgICAgPT4gJ09UT0JPQnJvd3Nlckhhc0Nvb2tpZScsCiAgICAgICAgICAgICAgICBWYWx1ZSAgICA9PiAxLAogICAgICAgICAgICAgICAgRXhwaXJlcyAgPT4gJEV4cGlyZXMsCiAgICAgICAgICAgICAgICBQYXRoICAgICA9PiAkQ29uZmlnT2JqZWN0LT5HZXQoJ1NjcmlwdEFsaWFzJyksCiAgICAgICAgICAgICAgICBTZWN1cmUgICA9PiAkQ29va2llU2VjdXJlQXR0cmlidXRlLAogICAgICAgICAgICAgICAgSFRUUE9ubHkgPT4gMSwKICAgICAgICAgICAgKTsKCiAgICAgICAgICAgICMgcmVkaXJlY3QgdG8gYWx0ZXJuYXRlIGxvZ2luCiAgICAgICAgICAgIGlmICggJENvbmZpZ09iamVjdC0+R2V0KCdDdXN0b21lclBhbmVsTG9naW5VUkwnKSApIHsKICAgICAgICAgICAgICAgICRQYXJhbXtSZXF1ZXN0ZWRVUkx9ID0gJExheW91dE9iamVjdC0+TGlua0VuY29kZSggJFBhcmFte1JlcXVlc3RlZFVSTH0gKTsKCiAgICAgICAgICAgICAgICAjIHRocm93IGEgS2VybmVsOjpTeXN0ZW06OldlYjo6RXhjZXB0aW9uIHRoYXQgcmVkaXJlY3RzCiAgICAgICAgICAgICAgICAkTGF5b3V0T2JqZWN0LT5SZWRpcmVjdCgKICAgICAgICAgICAgICAgICAgICBFeHRVUkwgPT4gJENvbmZpZ09iamVjdC0+R2V0KCdDdXN0b21lclBhbmVsTG9naW5VUkwnKSAuICI/UmVhc29uPUxvZ2luRmFpbGVkJlJlcXVlc3RlZFVSTD0kUGFyYW17UmVxdWVzdGVkVVJMfSIsCiAgICAgICAgICAgICAgICApOwogICAgICAgICAgICB9CgojIFJvdGhlciBPU1MgLyBPbmVUaW1lQXV0aGVudGljYXRpb25MaW5rCiMgICAgICAgICAgICBpZiAoJFByZXZlbnRCcnV0ZUZvcmNlQ29uZmlnKSB7CiAgICAgICAgICAgIGlmICggJFBvc3RVc2VyICYmICRQcmV2ZW50QnJ1dGVGb3JjZUNvbmZpZyApIHsKIyBFTyBPbmVUaW1lQXV0aGVudGljYXRpb25MaW5rCgogICAgICAgICAgICAgICAgIyBwcmV2ZW50IGJydXRlIGZvcmNlCiAgICAgICAgICAgICAgICBteSAkQmFubmVkID0gJFNlbGYtPl9TdG9yZUZhaWxlZExvZ2lucygKICAgICAgICAgICAgICAgICAgICBQb3N0VXNlciAgICAgICAgICAgICAgICA9PiAkUG9zdFVzZXIsCiAgICAgICAgICAgICAgICAgICAgUHJldmVudEJydXRlRm9yY2VDb25maWcgPT4gJFByZXZlbnRCcnV0ZUZvcmNlQ29uZmlnLAogICAgICAgICAgICAgICAgKTsKCiAgICAgICAgICAgICAgICBpZiAoJEJhbm5lZCkgewogICAgICAgICAgICAgICAgICAgIHJldHVybiAkTGF5b3V0T2JqZWN0LT5DdXN0b21lckxvZ2luKAogICAgICAgICAgICAgICAgICAgICAgICAlUGFyYW0sCiAgICAgICAgICAgICAgICAgICAgICAgIFRpdGxlICAgPT4gJ0xvZ2luJywKICAgICAgICAgICAgICAgICAgICAgICAgTWVzc2FnZSA9PiAkTGF5b3V0T2JqZWN0LT57TGFuZ3VhZ2VPYmplY3R9LT5UcmFuc2xhdGUoCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAnVG9vIG1hbnkgZmFpbGVkIGxvZ2luIGF0dGVtcHRzLCBwbGVhc2UgcmV0cnkgaW4gJXMgcy4nLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgJFByZXZlbnRCcnV0ZUZvcmNlQ29uZmlnLT57QmFuRHVyYXRpb259CiAgICAgICAgICAgICAgICAgICAgICAgICksCiAgICAgICAgICAgICAgICAgICAgICAgIExvZ2luRmFpbGVkID0+IDEsCiAgICAgICAgICAgICAgICAgICAgICAgIE1lc3NhZ2VUeXBlID0+ICdFcnJvcicsCiAgICAgICAgICAgICAgICAgICAgICAgIFVzZXIgICAgICAgID0+ICRQb3N0VXNlciwKICAgICAgICAgICAgICAgICAgICApOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CgogICAgICAgICAgICAjIHNob3cgbm9ybWFsIGxvZ2luCiAgICAgICAgICAgIHJldHVybiAkTGF5b3V0T2JqZWN0LT5DdXN0b21lckxvZ2luKAogICAgICAgICAgICAgICAgVGl0bGUgICA9PiAnTG9naW4nLAogICAgICAgICAgICAgICAgTWVzc2FnZSA9PiAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6TG9nJyktPkdldExvZ0VudHJ5KAogICAgICAgICAgICAgICAgICAgIFR5cGUgPT4gJ0luZm8nLAogICAgICAgICAgICAgICAgICAgIFdoYXQgPT4gJ01lc3NhZ2UnLAogICAgICAgICAgICAgICAgICAgICkKICAgICAgICAgICAgICAgICAgICB8fCAkQXV0aE9iamVjdC0+R2V0TGFzdEVycm9yTWVzc2FnZSgpCiAgICAgICAgICAgICAgICAgICAgfHwgVHJhbnNsYXRhYmxlKCdMb2dpbiBmYWlsZWQhIFlvdXIgdXNlciBuYW1lIG9yIHBhc3N3b3JkIHdhcyBlbnRlcmVkIGluY29ycmVjdGx5LicpLAogICAgICAgICAgICAgICAgTG9naW5GYWlsZWQgPT4gMSwKICAgICAgICAgICAgICAgIFVzZXIgICAgICAgID0+ICRQb3N0VXNlciwKICAgICAgICAgICAgICAgICVQYXJhbSwKICAgICAgICAgICAgKTsKICAgICAgICB9CgogICAgICAgICMgbG9naW4gaXMgc3VjY2Vzc2Z1bAogICAgICAgIG15ICVVc2VyRGF0YSA9ICRVc2VyT2JqZWN0LT5DdXN0b21lclVzZXJEYXRhR2V0KAogICAgICAgICAgICBVc2VyICA9PiAkVXNlciwKICAgICAgICAgICAgVmFsaWQgPT4gMSwKICAgICAgICApOwoKICAgICAgICAjIGNoZWNrIGlmIHRoZSBicm93c2VyIHN1cHBvcnRzIGNvb2tpZXMKICAgICAgICBpZiAoICRQYXJhbU9iamVjdC0+R2V0Q29va2llKCBLZXkgPT4gJ09UT0JPQnJvd3Nlckhhc0Nvb2tpZScgKSApIHsKICAgICAgICAgICAgJEtlcm5lbDo6T00tPk9iamVjdFBhcmFtQWRkKAogICAgICAgICAgICAgICAgJ0tlcm5lbDo6T3V0cHV0OjpIVE1MOjpMYXlvdXQnID0+IHsKICAgICAgICAgICAgICAgICAgICBCcm93c2VySGFzQ29va2llID0+IDEsCiAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICApOwogICAgICAgIH0KCiAgICAgICAgIyBjaGVjayBuZWVkZWQgZGF0YQogICAgICAgIGlmICggISRVc2VyRGF0YXtVc2VySUR9IHx8ICEkVXNlckRhdGF7VXNlckxvZ2lufSApIHsKCiAgICAgICAgICAgIG15ICRMYXlvdXRPYmplY3QgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6Ok91dHB1dDo6SFRNTDo6TGF5b3V0Jyk7CgogICAgICAgICAgICAjIHJlZGlyZWN0IHRvIGFsdGVybmF0ZSBsb2dpbgogICAgICAgICAgICBpZiAoICRDb25maWdPYmplY3QtPkdldCgnQ3VzdG9tZXJQYW5lbExvZ2luVVJMJykgKSB7CgogICAgICAgICAgICAgICAgIyB0aHJvdyBhIEtlcm5lbDo6U3lzdGVtOjpXZWI6OkV4Y2VwdGlvbiB0aGF0IHJlZGlyZWN0cwogICAgICAgICAgICAgICAgJExheW91dE9iamVjdC0+UmVkaXJlY3QoCiAgICAgICAgICAgICAgICAgICAgRXh0VVJMID0+ICRDb25maWdPYmplY3QtPkdldCgnQ3VzdG9tZXJQYW5lbExvZ2luVVJMJykgLiAnP1JlYXNvbj1TeXN0ZW1FcnJvcicsCiAgICAgICAgICAgICAgICApOwogICAgICAgICAgICB9CgogICAgICAgICAgICAjIHNob3cgbmVlZCB1c2VyIGRhdGEgZXJyb3IgbWVzc2FnZQogICAgICAgICAgICByZXR1cm4gJExheW91dE9iamVjdC0+Q3VzdG9tZXJMb2dpbigKICAgICAgICAgICAgICAgIFRpdGxlICAgPT4gJ0Vycm9yJywKICAgICAgICAgICAgICAgIE1lc3NhZ2UgPT4KICAgICAgICAgICAgICAgICAgICBUcmFuc2xhdGFibGUoCiAgICAgICAgICAgICAgICAgICAgICAgICdBdXRoZW50aWNhdGlvbiBzdWNjZWVkZWQsIGJ1dCBubyBjdXN0b21lciByZWNvcmQgaXMgZm91bmQgaW4gdGhlIGN1c3RvbWVyIGJhY2tlbmQuIFBsZWFzZSBjb250YWN0IHRoZSBhZG1pbmlzdHJhdG9yLicKICAgICAgICAgICAgICAgICAgICApLAogICAgICAgICAgICAgICAgJVBhcmFtLAogICAgICAgICAgICApOwogICAgICAgIH0KCiAgICAgICAgIyBjcmVhdGUgZGF0ZXRpbWUgb2JqZWN0CiAgICAgICAgbXkgJFNlc3Npb25EVE9iamVjdCA9ICRLZXJuZWw6Ok9NLT5DcmVhdGUoJ0tlcm5lbDo6U3lzdGVtOjpEYXRlVGltZScpOwoKICAgICAgICAjIFJlbW92ZSBjZXJ0YWluIHVzZXIgYXR0cmlidXRlcyB0aGF0IGFyZSBub3QgbmVlZGVkIHRvIGJlIHN0b3JlZCBpbiB0aGUgc2Vzc2lvbi4KICAgICAgICAjICAgLSBTTUlNRSBDZXJ0aWZpY2F0ZSBjb3VsZCBiZSBpbiBiaW5hcnkgZm9ybWF0LCBpZiBzZXNzaW9uIGJhY2tlbmQgaW4gREIgKGRlZmF1bHQpCiAgICAgICAgIyAgIGl0IHdvbnQgYmUgcG9zc2libGUgdG8gYmUgc2F2ZWQgaW4gY2VydGFpbiBkYXRhYmFzZXMgKHNlZSBidWcjMTQ0MDUpLgogICAgICAgIG15ICVVc2VyU2Vzc2lvbkRhdGEgPSAlVXNlckRhdGE7CiAgICAgICAgZGVsZXRlICRVc2VyU2Vzc2lvbkRhdGF7VXNlclNNSU1FQ2VydGlmaWNhdGV9OwoKICAgICAgICAjIGNyZWF0ZSBuZXcgc2Vzc2lvbiBpZAogICAgICAgIG15ICROZXdTZXNzaW9uSUQgPSAkU2Vzc2lvbk9iamVjdC0+Q3JlYXRlU2Vzc2lvbklEKAogICAgICAgICAgICAlVXNlclNlc3Npb25EYXRhLAogICAgICAgICAgICBVc2VyTGFzdFJlcXVlc3QgPT4gJFNlc3Npb25EVE9iamVjdC0+VG9FcG9jaCgpLAogICAgICAgICAgICBVc2VyVHlwZSAgICAgICAgPT4gJ0N1c3RvbWVyJywKICAgICAgICAgICAgU2Vzc2lvblNvdXJjZSAgID0+ICdDdXN0b21lckludGVyZmFjZScsCiAgICAgICAgKTsKCiAgICAgICAgIyBzaG93IGVycm9yIG1lc3NhZ2UgaWYgbm8gc2Vzc2lvbiBpZCBoYXMgYmVlbiBjcmVhdGVkCiAgICAgICAgaWYgKCAhJE5ld1Nlc3Npb25JRCApIHsKCiAgICAgICAgICAgICMgZ2V0IGVycm9yIG1lc3NhZ2UKICAgICAgICAgICAgbXkgJEVycm9yID0gJFNlc3Npb25PYmplY3QtPlNlc3Npb25JREVycm9yTWVzc2FnZSgpIHx8ICcnOwoKICAgICAgICAgICAgIyBvdXRwdXQgZXJyb3IgbWVzc2FnZQogICAgICAgICAgICBteSAkTGF5b3V0T2JqZWN0ID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpPdXRwdXQ6OkhUTUw6OkxheW91dCcpOwoKICAgICAgICAgICAgcmV0dXJuICRMYXlvdXRPYmplY3QtPkN1c3RvbWVyTG9naW4oCiAgICAgICAgICAgICAgICBUaXRsZSAgID0+ICdMb2dpbicsCiAgICAgICAgICAgICAgICBNZXNzYWdlID0+ICRFcnJvciwKICAgICAgICAgICAgICAgICVQYXJhbSwKICAgICAgICAgICAgKTsKICAgICAgICB9CgogICAgICAgICMgZXhlY3V0aW9uIGluIDIwIHNlY29uZHMKICAgICAgICBteSAkRXhlY3V0aW9uVGltZU9iaiA9ICRTZXNzaW9uRFRPYmplY3QtPkNsb25lKCk7CiAgICAgICAgJEV4ZWN1dGlvblRpbWVPYmotPkFkZCggU2Vjb25kcyA9PiAyMCApOwogICAgICAgIG15ICRFeGVjdXRpb25UaW1lID0gJEV4ZWN1dGlvblRpbWVPYmotPlRvU3RyaW5nKCk7CgogICAgICAgICMgYWRkIGEgYXN5bmNocm9ub3VzIGV4ZWN1dG9yIHNjaGVkdWxlciB0YXNrIHRvIGNvdW50IHRoZSBjb25jdXJyZW50IHVzZXIKICAgICAgICAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6U2NoZWR1bGVyJyktPlRhc2tBZGQoCiAgICAgICAgICAgIEV4ZWN1dGlvblRpbWUgICAgICAgICAgICA9PiAkRXhlY3V0aW9uVGltZSwKICAgICAgICAgICAgVHlwZSAgICAgICAgICAgICAgICAgICAgID0+ICdBc3luY2hyb25vdXNFeGVjdXRvcicsCiAgICAgICAgICAgIE5hbWUgICAgICAgICAgICAgICAgICAgICA9PiAnUGx1Z2luQXN5bmNocm9ub3VzOjpDb25jdXJyZW50VXNlcicsCiAgICAgICAgICAgIE1heGltdW1QYXJhbGxlbEluc3RhbmNlcyA9PiAxLAogICAgICAgICAgICBEYXRhICAgICAgICAgICAgICAgICAgICAgPT4gewogICAgICAgICAgICAgICAgT2JqZWN0ICAgPT4gJ0tlcm5lbDo6U3lzdGVtOjpTdXBwb3J0RGF0YUNvbGxlY3Rvcjo6UGx1Z2luQXN5bmNocm9ub3VzOjpPVE9CTzo6Q29uY3VycmVudFVzZXJzJywKICAgICAgICAgICAgICAgIEZ1bmN0aW9uID0+ICdSdW5Bc3luY2hyb25vdXMnLAogICAgICAgICAgICB9LAogICAgICAgICk7CgogICAgICAgIG15ICRVc2VyVGltZVpvbmUgPSAkU2VsZi0+X1VzZXJUaW1lWm9uZUdldCglVXNlckRhdGEpOwoKICAgICAgICAkU2Vzc2lvbk9iamVjdC0+VXBkYXRlU2Vzc2lvbklEKAogICAgICAgICAgICBTZXNzaW9uSUQgPT4gJE5ld1Nlc3Npb25JRCwKICAgICAgICAgICAgS2V5ICAgICAgID0+ICdVc2VyVGltZVpvbmUnLAogICAgICAgICAgICBWYWx1ZSAgICAgPT4gJFVzZXJUaW1lWm9uZSwKICAgICAgICApOwoKICAgICAgICAjIGNoZWNrIGlmIHRoZSB0aW1lIHpvbmUgb2Zmc2V0IHJlcG9ydGVkIGJ5IHRoZSB1c2VyJ3MgYnJvd3NlciBkaWZmZXJzIGZyb20gdGhhdAogICAgICAgICMgb2YgdGhlIE9UT0JPIHVzZXIncyB0aW1lIHpvbmUgb2Zmc2V0CiAgICAgICAgbXkgJERhdGVUaW1lT2JqZWN0ID0gJEtlcm5lbDo6T00tPkNyZWF0ZSgKICAgICAgICAgICAgJ0tlcm5lbDo6U3lzdGVtOjpEYXRlVGltZScsCiAgICAgICAgICAgIE9iamVjdFBhcmFtcyA9PiB7CiAgICAgICAgICAgICAgICBUaW1lWm9uZSA9PiAkVXNlclRpbWVab25lLAogICAgICAgICAgICB9LAogICAgICAgICk7CiAgICAgICAgbXkgJE9UT0JPVXNlclRpbWVab25lT2Zmc2V0ID0gJERhdGVUaW1lT2JqZWN0LT5Gb3JtYXQoIEZvcm1hdCA9PiAnJXtvZmZzZXR9JyApIC8gNjA7CiAgICAgICAgbXkgJEJyb3dzZXJUaW1lWm9uZU9mZnNldCAgID0gKCAkUGFyYW1PYmplY3QtPkdldFBhcmFtKCBQYXJhbSA9PiAnVGltZVpvbmVPZmZzZXQnICkgfHwgMCApICogLTE7CgogICAgICAgICMgVGltZVpvbmVPZmZzZXREaWZmZXJlbmNlIGNvbnRhaW5zIHRoZSBkaWZmZXJlbmNlIG9mIHRoZSB0aW1lIHpvbmUgb2Zmc2V0IGJldHdlZW4KICAgICAgICAjIHRoZSB1c2VyJ3MgT1RPQk8gdGltZSB6b25lIHNldHRpbmcgYW5kIHRoZSBvbmUgcmVwb3J0ZWQgYnkgdGhlIHVzZXIncyBicm93c2VyLgogICAgICAgICMgSWYgdGhlcmUgaXMgYSBkaWZmZXJlbmNlIGl0IGNhbiBiZSBldmFsdWF0ZWQgbGF0ZXIgdG8gZS4gZy4gc2hvdyBhIG1lc3NhZ2UKICAgICAgICAjIGZvciB0aGUgdXNlciB0byBjaGVjayBoaXMgT1RPQk8gdGltZSB6b25lIHNldHRpbmcuCiAgICAgICAgbXkgJFVzZXJUaW1lWm9uZU9mZnNldERpZmZlcmVuY2UgPSBhYnMoICRPVE9CT1VzZXJUaW1lWm9uZU9mZnNldCAtICRCcm93c2VyVGltZVpvbmVPZmZzZXQgKTsKICAgICAgICAkU2Vzc2lvbk9iamVjdC0+VXBkYXRlU2Vzc2lvbklEKAogICAgICAgICAgICBTZXNzaW9uSUQgPT4gJE5ld1Nlc3Npb25JRCwKICAgICAgICAgICAgS2V5ICAgICAgID0+ICdVc2VyVGltZVpvbmVPZmZzZXREaWZmZXJlbmNlJywKICAgICAgICAgICAgVmFsdWUgICAgID0+ICRVc2VyVGltZVpvbmVPZmZzZXREaWZmZXJlbmNlLAogICAgICAgICk7CgogICAgICAgICMgY3JlYXRlIGEgbmV3IExheW91dE9iamVjdCB3aXRoIFNlc3Npb25JRENvb2tpZQogICAgICAgIG15ICRFeHBpcmVzID0gJysnIC4gJENvbmZpZ09iamVjdC0+R2V0KCdTZXNzaW9uTWF4VGltZScpIC4gJ3MnOwogICAgICAgIGlmICggISRDb25maWdPYmplY3QtPkdldCgnU2Vzc2lvblVzZUNvb2tpZUFmdGVyQnJvd3NlckNsb3NlJykgKSB7CiAgICAgICAgICAgICRFeHBpcmVzID0gJyc7CiAgICAgICAgfQoKICAgICAgICAkS2VybmVsOjpPTS0+T2JqZWN0UGFyYW1BZGQoCiAgICAgICAgICAgICdLZXJuZWw6Ok91dHB1dDo6SFRNTDo6TGF5b3V0JyA9PiB7CiAgICAgICAgICAgICAgICBTZXRDb29raWVzID0+IHsKICAgICAgICAgICAgICAgICAgICBTZXNzaW9uSURDb29raWUgPT4gJFBhcmFtT2JqZWN0LT5TZXRDb29raWUoCiAgICAgICAgICAgICAgICAgICAgICAgIEtleSAgICAgID0+ICRQYXJhbXtTZXNzaW9uTmFtZX0sCiAgICAgICAgICAgICAgICAgICAgICAgIFZhbHVlICAgID0+ICROZXdTZXNzaW9uSUQsCiAgICAgICAgICAgICAgICAgICAgICAgIEV4cGlyZXMgID0+ICRFeHBpcmVzLAogICAgICAgICAgICAgICAgICAgICAgICBQYXRoICAgICA9PiAkQ29uZmlnT2JqZWN0LT5HZXQoJ1NjcmlwdEFsaWFzJyksCiAgICAgICAgICAgICAgICAgICAgICAgIFNlY3VyZSAgID0+ICRDb29raWVTZWN1cmVBdHRyaWJ1dGUsCiAgICAgICAgICAgICAgICAgICAgICAgIEhUVFBPbmx5ID0+IDEsCiAgICAgICAgICAgICAgICAgICAgKSwKCiAgICAgICAgICAgICAgICAgICAgIyBkZWxldGUgdGhlIE9UT0JPQnJvd3Nlckhhc0Nvb2tpZSBjb29raWUKICAgICAgICAgICAgICAgICAgICBPVE9CT0Jyb3dzZXJIYXNDb29raWUgPT4gJFBhcmFtT2JqZWN0LT5TZXRDb29raWUoCiAgICAgICAgICAgICAgICAgICAgICAgIEtleSAgICAgID0+ICdPVE9CT0Jyb3dzZXJIYXNDb29raWUnLAogICAgICAgICAgICAgICAgICAgICAgICBWYWx1ZSAgICA9PiAnJywKICAgICAgICAgICAgICAgICAgICAgICAgRXhwaXJlcyAgPT4gJy0xeScsCiAgICAgICAgICAgICAgICAgICAgICAgIFBhdGggICAgID0+ICRDb25maWdPYmplY3QtPkdldCgnU2NyaXB0QWxpYXMnKSwKICAgICAgICAgICAgICAgICAgICAgICAgU2VjdXJlICAgPT4gJENvb2tpZVNlY3VyZUF0dHJpYnV0ZSwKICAgICAgICAgICAgICAgICAgICAgICAgSFRUUE9ubHkgPT4gMSwKICAgICAgICAgICAgICAgICAgICApLAogICAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgICAgIFNlc3Npb25JRCAgID0+ICROZXdTZXNzaW9uSUQsCiAgICAgICAgICAgICAgICBTZXNzaW9uTmFtZSA9PiAkUGFyYW17U2Vzc2lvbk5hbWV9LAogICAgICAgICAgICB9LAogICAgICAgICk7CgogICAgICAgICMgcmVkaXJlY3Qgd2l0aCBuZXcgc2Vzc2lvbiBpZCBhbmQgb2xkIHBhcmFtcwogICAgICAgICMgcHJlcGFyZSBvbGQgcmVkaXJlY3QgVVJMIC0tIGRvIG5vdCByZWRpcmVjdCB0byBMb2dpbiBvciBMb2dvdXQgKGxvb3ApIQogICAgICAgIGlmICggJFBhcmFte1JlcXVlc3RlZFVSTH0gPX4gL0FjdGlvbj0oTG9nb3V0fExvZ2lufExvc3RQYXNzd29yZHxQcmVMb2dpbikvICkgewogICAgICAgICAgICAkUGFyYW17UmVxdWVzdGVkVVJMfSA9ICcnOwogICAgICAgIH0KCiAgICAgICAgIyByZWRpcmVjdCB3aXRoIG5ldyBzZXNzaW9uIGlkCiAgICAgICAgbXkgJExheW91dE9iamVjdCA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6T3V0cHV0OjpIVE1MOjpMYXlvdXQnKTsKCiAgICAgICAgJExheW91dE9iamVjdC0+UmVkaXJlY3QoCiAgICAgICAgICAgIE9QICAgID0+ICRQYXJhbXtSZXF1ZXN0ZWRVUkx9LAogICAgICAgICAgICBMb2dpbiA9PiAxLAogICAgICAgICk7ICAgICMgdGhyb3dzIGEgS2VybmVsOjpTeXN0ZW06OldlYjo6RXhjZXB0aW9uCiAgICB9CgogICAgIyBsb2dvdXQKICAgIGVsc2lmICggJFBhcmFte0FjdGlvbn0gZXEgJ0xvZ291dCcgKSB7CgogICAgICAgICMgY2hlY2sgc2Vzc2lvbiBpZAogICAgICAgIGlmICggISRTZXNzaW9uT2JqZWN0LT5DaGVja1Nlc3Npb25JRCggU2Vzc2lvbklEID0+ICRQYXJhbXtTZXNzaW9uSUR9ICkgKSB7CgogICAgICAgICAgICAjIG5ldyBsYXlvdXQgb2JqZWN0CiAgICAgICAgICAgIG15ICRMYXlvdXRPYmplY3QgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6Ok91dHB1dDo6SFRNTDo6TGF5b3V0Jyk7CgogICAgICAgICAgICAjIHJlZGlyZWN0IHRvIGFsdGVybmF0ZSBsb2dpbgogICAgICAgICAgICBpZiAoICRDb25maWdPYmplY3QtPkdldCgnQ3VzdG9tZXJQYW5lbExvZ2luVVJMJykgKSB7CiAgICAgICAgICAgICAgICAkUGFyYW17UmVxdWVzdGVkVVJMfSA9ICRMYXlvdXRPYmplY3QtPkxpbmtFbmNvZGUoICRQYXJhbXtSZXF1ZXN0ZWRVUkx9ICk7CgogICAgICAgICAgICAgICAgJExheW91dE9iamVjdC0+UmVkaXJlY3QoCiAgICAgICAgICAgICAgICAgICAgRXh0VVJMID0+ICRDb25maWdPYmplY3QtPkdldCgnQ3VzdG9tZXJQYW5lbExvZ2luVVJMJykKICAgICAgICAgICAgICAgICAgICAgICAgLiAiP1JlYXNvbj1JbnZhbGlkU2Vzc2lvbklEO1JlcXVlc3RlZFVSTD0kUGFyYW17UmVxdWVzdGVkVVJMfSIsCiAgICAgICAgICAgICAgICApOyAgICAjIHRocm93cyBhIEtlcm5lbDo6U3lzdGVtOjpXZWI6OkV4Y2VwdGlvbgogICAgICAgICAgICB9CgogICAgICAgICAgICAjIHNob3cgbG9naW4gc2NyZWVuCiAgICAgICAgICAgIHJldHVybiAkTGF5b3V0T2JqZWN0LT5DdXN0b21lckxvZ2luKAogICAgICAgICAgICAgICAgVGl0bGUgICA9PiAnTG9nb3V0JywKICAgICAgICAgICAgICAgIE1lc3NhZ2UgPT4gVHJhbnNsYXRhYmxlKCdTZXNzaW9uIGludmFsaWQuIFBsZWFzZSBsb2cgaW4gYWdhaW4uJyksCiAgICAgICAgICAgICAgICAlUGFyYW0sCiAgICAgICAgICAgICk7CiAgICAgICAgfQoKICAgICAgICAjIGdldCBzZXNzaW9uIGRhdGEKICAgICAgICBteSAlVXNlckRhdGEgPSAkU2Vzc2lvbk9iamVjdC0+R2V0U2Vzc2lvbklERGF0YSgKICAgICAgICAgICAgU2Vzc2lvbklEID0+ICRQYXJhbXtTZXNzaW9uSUR9LAogICAgICAgICk7CgogICAgICAgICRVc2VyRGF0YXtVc2VyVGltZVpvbmV9ID0gJFNlbGYtPl9Vc2VyVGltZVpvbmVHZXQoJVVzZXJEYXRhKTsKCiAgICAgICAgIyBjcmVhdGUgYSBuZXcgTGF5b3V0T2JqZWN0IHdpdGggJyVQYXJhbScgYW5kICclVXNlckRhdGEnCiAgICAgICAgJEtlcm5lbDo6T00tPk9iamVjdFBhcmFtQWRkKAogICAgICAgICAgICAnS2VybmVsOjpPdXRwdXQ6OkhUTUw6OkxheW91dCcgPT4gewogICAgICAgICAgICAgICAgU2V0Q29va2llcyA9PiB7CgogICAgICAgICAgICAgICAgICAgICMgZGVsZXRlIHRoZSBPVE9CTyBzZXNzaW9uIGNvb2tpZQogICAgICAgICAgICAgICAgICAgIFNlc3Npb25JRENvb2tpZSA9PiAkUGFyYW1PYmplY3QtPlNldENvb2tpZSgKICAgICAgICAgICAgICAgICAgICAgICAgS2V5ICAgICAgPT4gJFBhcmFte1Nlc3Npb25OYW1lfSwKICAgICAgICAgICAgICAgICAgICAgICAgVmFsdWUgICAgPT4gJycsCiAgICAgICAgICAgICAgICAgICAgICAgIEV4cGlyZXMgID0+ICctMXknLAogICAgICAgICAgICAgICAgICAgICAgICBQYXRoICAgICA9PiAkQ29uZmlnT2JqZWN0LT5HZXQoJ1NjcmlwdEFsaWFzJyksCiAgICAgICAgICAgICAgICAgICAgICAgIFNlY3VyZSAgID0+ICRDb29raWVTZWN1cmVBdHRyaWJ1dGUsCiAgICAgICAgICAgICAgICAgICAgICAgIEhUVFBPbmx5ID0+IDEsCiAgICAgICAgICAgICAgICAgICAgKSwKICAgICAgICAgICAgICAgIH0sCiAgICAgICAgICAgICAgICAlUGFyYW0sCiAgICAgICAgICAgICAgICAlVXNlckRhdGEsCiAgICAgICAgICAgIH0sCiAgICAgICAgKTsKCiAgICAgICAgJEtlcm5lbDo6T00tPk9iamVjdHNEaXNjYXJkKCBPYmplY3RzID0+IFsnS2VybmVsOjpPdXRwdXQ6OkhUTUw6OkxheW91dCddICk7CiAgICAgICAgbXkgJExheW91dE9iamVjdCA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6T3V0cHV0OjpIVE1MOjpMYXlvdXQnKTsKCiAgICAgICAgIyByZW1vdmUgc2Vzc2lvbiBpZAogICAgICAgIGlmICggISRTZXNzaW9uT2JqZWN0LT5SZW1vdmVTZXNzaW9uSUQoIFNlc3Npb25JRCA9PiAkUGFyYW17U2Vzc2lvbklEfSApICkgewogICAgICAgICAgICAkTGF5b3V0T2JqZWN0LT5DdXN0b21lckZhdGFsRXJyb3IoCiAgICAgICAgICAgICAgICBDb21tZW50ID0+IFRyYW5zbGF0YWJsZSgnUGxlYXNlIGNvbnRhY3QgdGhlIGFkbWluaXN0cmF0b3IuJykKICAgICAgICAgICAgKTsgICAgIyB0aHJvd3MgYSBLZXJuZWw6OlN5c3RlbTo6V2ViOjpFeGNlcHRpb24KICAgICAgICB9CgogICAgICAgICMgcmVkaXJlY3QgdG8gYWx0ZXJuYXRlIGxvZ2luCiAgICAgICAgaWYgKCAkQ29uZmlnT2JqZWN0LT5HZXQoJ0N1c3RvbWVyUGFuZWxMb2dvdXRVUkwnKSApIHsKICAgICAgICAgICAgJExheW91dE9iamVjdC0+UmVkaXJlY3QoCiAgICAgICAgICAgICAgICBFeHRVUkwgPT4gJENvbmZpZ09iamVjdC0+R2V0KCdDdXN0b21lclBhbmVsTG9nb3V0VVJMJyksCiAgICAgICAgICAgICk7ICAgICMgdGhyb3dzIGEgS2VybmVsOjpTeXN0ZW06OldlYjo6RXhjZXB0aW9uCiAgICAgICAgfQoKICAgICAgICAjIHRyeSBhdXRoIG1vZHVsZSBzcGVjaWZpYyBsb2dvdXQKICAgICAgICBteSAkTG9nb3V0SW5mbyA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpDdXN0b21lckF1dGgnKS0+TG9nb3V0KCk7CiAgICAgICAgaWYgKCAkTG9nb3V0SW5mbyAmJiAkTG9nb3V0SW5mby0+e0xvZ291dFVSTH0gKSB7CiAgICAgICAgICAgICRMYXlvdXRPYmplY3QtPlJlZGlyZWN0KAogICAgICAgICAgICAgICAgRXh0VVJMID0+ICRMb2dvdXRJbmZvLT57TG9nb3V0VVJMfSwKICAgICAgICAgICAgKTsgICAgIyB0aHJvd3MgYSBLZXJuZWw6OlN5c3RlbTo6V2ViOjpFeGNlcHRpb24KICAgICAgICB9CgogICAgICAgICMgc2hvdyBsb2dvdXQgc2NyZWVuCiAgICAgICAgcmV0dXJuICRMYXlvdXRPYmplY3QtPkN1c3RvbWVyTG9naW4oCiAgICAgICAgICAgIFRpdGxlICAgICAgID0+ICdMb2dvdXQnLAogICAgICAgICAgICBNZXNzYWdlICAgICA9PiAkTGF5b3V0T2JqZWN0LT57TGFuZ3VhZ2VPYmplY3R9LT5UcmFuc2xhdGUoJ0xvZ291dCBzdWNjZXNzZnVsLicpLAogICAgICAgICAgICBNZXNzYWdlVHlwZSA9PiAnU3VjY2VzcycsCiAgICAgICAgICAgICVQYXJhbSwKICAgICAgICApOwogICAgfQoKICAgICMgbG9zdCBwYXNzd29yZAogICAgZWxzaWYgKCAkUGFyYW17QWN0aW9ufSBlcSAnQ3VzdG9tZXJMb3N0UGFzc3dvcmQnICkgewoKICAgICAgICBteSAkTGF5b3V0T2JqZWN0ID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpPdXRwdXQ6OkhUTUw6OkxheW91dCcpOwoKICAgICAgICAjIGNoZWNrIGZlYXR1cmUKICAgICAgICBpZiAoICEkQ29uZmlnT2JqZWN0LT5HZXQoJ0N1c3RvbWVyUGFuZWxMb3N0UGFzc3dvcmQnKSApIHsKCiAgICAgICAgICAgICMgc2hvdyBub3JtYWwgbG9naW4KICAgICAgICAgICAgcmV0dXJuICRMYXlvdXRPYmplY3QtPkN1c3RvbWVyTG9naW4oCiAgICAgICAgICAgICAgICBUaXRsZSAgID0+ICdMb2dpbicsCiAgICAgICAgICAgICAgICBNZXNzYWdlID0+IFRyYW5zbGF0YWJsZSgnRmVhdHVyZSBub3QgYWN0aXZlIScpLAogICAgICAgICAgICApOwogICAgICAgIH0KCiAgICAgICAgIyBnZXQgcGFyYW1zCiAgICAgICAgbXkgJFVzZXIgID0gJFBhcmFtT2JqZWN0LT5HZXRQYXJhbSggUGFyYW0gPT4gJ1VzZXInICkgIHx8ICcnOwogICAgICAgIG15ICRUb2tlbiA9ICRQYXJhbU9iamVjdC0+R2V0UGFyYW0oIFBhcmFtID0+ICdUb2tlbicgKSB8fCAnJzsKCiAgICAgICAgIyBnZXQgdXNlciBsb2dpbiBieSB0b2tlbgogICAgICAgIGlmICggISRVc2VyICYmICRUb2tlbiApIHsKCiAgICAgICAgICAgICMgUHJldmVudCBleHRyYWN0aW5nIHBhc3N3b3JkIHJlc2V0IHRva2VuIGNoYXJhY3Rlci1ieS1jaGFyYWN0ZXIgdmlhIHdpbGRjYXJkIGluamVjdGlvbgogICAgICAgICAgICAjIFRoZSB3aWxkIGNhcmQgY2hhcmFjdGVycyAiJSIgYW5kICJfIiBjb3VsZCBiZSB1c2VkIHRvIG1hdGNoIGFyYml0cmFyeSBjaGFyYWN0ZXIuCiAgICAgICAgICAgIGlmICggJFRva2VuICF+IG17XEEgKD86IFthLXpBLVpdIHwgXGQgKSsgXHp9eG1zICkgewoKICAgICAgICAgICAgICAgICMgU2VjdXJpdHk6IHByZXRlbmQgdGhhdCBwYXNzd29yZCByZXNldCBpbnN0cnVjdGlvbnMgd2VyZSBhY3R1YWxseSBzZW50IHRvCiAgICAgICAgICAgICAgICAjICAgbWFrZSBzdXJlIHRoYXQgdXNlcnMgY2Fubm90IGZpbmQgb3V0IHZhbGlkIHVzZXJuYW1lcyBieQogICAgICAgICAgICAgICAgIyAgIGp1c3QgdHJ5aW5nIGFuZCBjaGVja2luZyB0aGUgcmVzdWx0IG1lc3NhZ2UuCiAgICAgICAgICAgICAgICByZXR1cm4gJExheW91dE9iamVjdC0+TG9naW4oCiAgICAgICAgICAgICAgICAgICAgVGl0bGUgICAgICAgPT4gJ0xvZ2luJywKICAgICAgICAgICAgICAgICAgICBNZXNzYWdlICAgICA9PiBUcmFuc2xhdGFibGUoJ1NlbnQgcGFzc3dvcmQgcmVzZXQgaW5zdHJ1Y3Rpb25zLiBQbGVhc2UgY2hlY2sgeW91ciBlbWFpbC4nKSwKICAgICAgICAgICAgICAgICAgICBNZXNzYWdlVHlwZSA9PiAnU3VjY2VzcycsCiAgICAgICAgICAgICAgICAgICAgJVBhcmFtLAogICAgICAgICAgICAgICAgKTsKICAgICAgICAgICAgfQoKICAgICAgICAgICAgbXkgJVVzZXJMaXN0ID0gJFVzZXJPYmplY3QtPlNlYXJjaFByZWZlcmVuY2VzKAogICAgICAgICAgICAgICAgS2V5ICAgPT4gJ1VzZXJUb2tlbicsCiAgICAgICAgICAgICAgICBWYWx1ZSA9PiAkVG9rZW4sCiAgICAgICAgICAgICk7CiAgICAgICAgICAgIFVTRVJfSUQ6CiAgICAgICAgICAgIGZvciBteSAkVXNlcklEICggc29ydCBrZXlzICVVc2VyTGlzdCApIHsKICAgICAgICAgICAgICAgIG15ICVVc2VyRGF0YSA9ICRVc2VyT2JqZWN0LT5DdXN0b21lclVzZXJEYXRhR2V0KAogICAgICAgICAgICAgICAgICAgIFVzZXIgID0+ICRVc2VySUQsCiAgICAgICAgICAgICAgICAgICAgVmFsaWQgPT4gMSwKICAgICAgICAgICAgICAgICk7CiAgICAgICAgICAgICAgICBpZiAoJVVzZXJEYXRhKSB7CiAgICAgICAgICAgICAgICAgICAgJFVzZXIgPSAkVXNlckRhdGF7VXNlckxvZ2lufTsKCiAgICAgICAgICAgICAgICAgICAgbGFzdCBVU0VSX0lEOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAjIGdldCB1c2VyIGRhdGEKICAgICAgICBteSAlVXNlckRhdGEgPSAkVXNlck9iamVjdC0+Q3VzdG9tZXJVc2VyRGF0YUdldCgKICAgICAgICAgICAgVXNlciA9PiAkVXNlciwKICAgICAgICApOwoKICAgICAgICAjIHZlcmlmeSBjdXN0b21lciB1c2VyIGlzIHZhbGlkIHdoZW4gcmVxdWVzdGluZyBwYXNzd29yZCByZXNldAogICAgICAgIG15IEBWYWxpZElEcyAgICA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpWYWxpZCcpLT5WYWxpZElEc0dldCgpOwogICAgICAgIG15ICRVc2VySXNWYWxpZCA9IGdyZXAgeyAkVXNlckRhdGF7VmFsaWRJRH0gJiYgJFVzZXJEYXRhe1ZhbGlkSUR9ID09ICRfIH0gQFZhbGlkSURzOwogICAgICAgIGlmICggISRVc2VyRGF0YXtVc2VySUR9IHx8ICEkVXNlcklzVmFsaWQgKSB7CgogICAgICAgICAgICAjIFNlY3VyaXR5OiBwcmV0ZW5kIHRoYXQgcGFzc3dvcmQgcmVzZXQgaW5zdHJ1Y3Rpb25zIHdlcmUgYWN0dWFsbHkgc2VudCB0bwogICAgICAgICAgICAjICAgbWFrZSBzdXJlIHRoYXQgdXNlcnMgY2Fubm90IGZpbmQgb3V0IHZhbGlkIHVzZXJuYW1lcyBieQogICAgICAgICAgICAjICAganVzdCB0cnlpbmcgYW5kIGNoZWNraW5nIHRoZSByZXN1bHQgbWVzc2FnZS4KICAgICAgICAgICAgcmV0dXJuICRMYXlvdXRPYmplY3QtPkN1c3RvbWVyTG9naW4oCiAgICAgICAgICAgICAgICBUaXRsZSAgICAgICA9PiAnTG9naW4nLAogICAgICAgICAgICAgICAgTWVzc2FnZSAgICAgPT4gVHJhbnNsYXRhYmxlKCdTZW50IHBhc3N3b3JkIHJlc2V0IGluc3RydWN0aW9ucy4gUGxlYXNlIGNoZWNrIHlvdXIgZW1haWwuJyksCiAgICAgICAgICAgICAgICBNZXNzYWdlVHlwZSA9PiAnU3VjY2VzcycsCiAgICAgICAgICAgICk7CiAgICAgICAgfQoKICAgICAgICAjIGNyZWF0ZSBlbWFpbCBvYmplY3QKICAgICAgICBteSAkRW1haWxPYmplY3QgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6RW1haWwnKTsKCiAgICAgICAgIyBzZW5kIHBhc3N3b3JkIHJlc2V0IHRva2VuCiAgICAgICAgaWYgKCAhJFRva2VuICkgewoKICAgICAgICAgICAgIyBnZW5lcmF0ZSB0b2tlbgogICAgICAgICAgICAkVXNlckRhdGF7VG9rZW59ID0gJFVzZXJPYmplY3QtPlRva2VuR2VuZXJhdGUoCiAgICAgICAgICAgICAgICBVc2VySUQgPT4gJFVzZXJEYXRhe1VzZXJJRH0sCiAgICAgICAgICAgICk7CgogICAgICAgICAgICAjIHNlbmQgdG9rZW4gbm90aWZ5IGVtYWlsIHdpdGggbGluawogICAgICAgICAgICBteSAkQm9keSA9ICRDb25maWdPYmplY3QtPkdldCgnQ3VzdG9tZXJQYW5lbEJvZHlMb3N0UGFzc3dvcmRUb2tlbicpCiAgICAgICAgICAgICAgICB8fCAnRVJST1I6IEN1c3RvbWVyUGFuZWxCb2R5TG9zdFBhc3N3b3JkVG9rZW4gaXMgbWlzc2luZyEnOwogICAgICAgICAgICBteSAkU3ViamVjdCA9ICRDb25maWdPYmplY3QtPkdldCgnQ3VzdG9tZXJQYW5lbFN1YmplY3RMb3N0UGFzc3dvcmRUb2tlbicpCiAgICAgICAgICAgICAgICB8fCAnRVJST1I6IEN1c3RvbWVyUGFuZWxTdWJqZWN0TG9zdFBhc3N3b3JkVG9rZW4gaXMgbWlzc2luZyEnOwogICAgICAgICAgICBmb3IgKCBzb3J0IGtleXMgJVVzZXJEYXRhICkgewogICAgICAgICAgICAgICAgJEJvZHkgPX4gcy88T1RPQk9fJF8+LyRVc2VyRGF0YXskX30vZ2k7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgbXkgJFNlbnQgPSAkRW1haWxPYmplY3QtPlNlbmQoCiAgICAgICAgICAgICAgICBUbyAgICAgICA9PiAkVXNlckRhdGF7VXNlckVtYWlsfSwKICAgICAgICAgICAgICAgIFN1YmplY3QgID0+ICRTdWJqZWN0LAogICAgICAgICAgICAgICAgQ2hhcnNldCAgPT4gJExheW91dE9iamVjdC0+e1VzZXJDaGFyc2V0fSwKICAgICAgICAgICAgICAgIE1pbWVUeXBlID0+ICd0ZXh0L3BsYWluJywKICAgICAgICAgICAgICAgIEJvZHkgICAgID0+ICRCb2R5CiAgICAgICAgICAgICk7CiAgICAgICAgICAgIGlmICggISRTZW50LT57U3VjY2Vzc30gKSB7CiAgICAgICAgICAgICAgICAkTGF5b3V0T2JqZWN0LT5GYXRhbEVycm9yKAogICAgICAgICAgICAgICAgICAgIENvbW1lbnQgPT4gVHJhbnNsYXRhYmxlKCdQbGVhc2UgY29udGFjdCB0aGUgYWRtaW5pc3RyYXRvci4nKSwKICAgICAgICAgICAgICAgICk7ICAgICMgdGhyb3dzIGEgS2VybmVsOjpTeXN0ZW06OldlYjo6RXhjZXB0aW9uCiAgICAgICAgICAgIH0KCiAgICAgICAgICAgIHJldHVybiAkTGF5b3V0T2JqZWN0LT5DdXN0b21lckxvZ2luKAogICAgICAgICAgICAgICAgVGl0bGUgICAgICAgPT4gJ0xvZ2luJywKICAgICAgICAgICAgICAgIE1lc3NhZ2UgICAgID0+IFRyYW5zbGF0YWJsZSgnU2VudCBwYXNzd29yZCByZXNldCBpbnN0cnVjdGlvbnMuIFBsZWFzZSBjaGVjayB5b3VyIGVtYWlsLicpLAogICAgICAgICAgICAgICAgTWVzc2FnZVR5cGUgPT4gJ1N1Y2Nlc3MnLAogICAgICAgICAgICAgICAgJVBhcmFtLAogICAgICAgICAgICApOwogICAgICAgIH0KCiAgICAgICAgIyByZXNldCBwYXNzd29yZAogICAgICAgICMgY2hlY2sgaWYgdG9rZW4gaXMgdmFsaWQKICAgICAgICBteSAkVG9rZW5WYWxpZCA9ICRVc2VyT2JqZWN0LT5Ub2tlbkNoZWNrKAogICAgICAgICAgICBUb2tlbiAgPT4gJFRva2VuLAogICAgICAgICAgICBVc2VySUQgPT4gJFVzZXJEYXRhe1VzZXJJRH0sCiAgICAgICAgKTsKCiAgICAgICAgaWYgKCAhJFRva2VuVmFsaWQgKSB7CiAgICAgICAgICAgIHJldHVybiAkTGF5b3V0T2JqZWN0LT5DdXN0b21lckxvZ2luKAogICAgICAgICAgICAgICAgVGl0bGUgICA9PiAnTG9naW4nLAogICAgICAgICAgICAgICAgTWVzc2FnZSA9PiBUcmFuc2xhdGFibGUoJ0ludmFsaWQgVG9rZW4hJyksCiAgICAgICAgICAgICAgICAlUGFyYW0sCiAgICAgICAgICAgICk7CiAgICAgICAgfQoKICAgICAgICAjIGdldCBuZXcgcGFzc3dvcmQKICAgICAgICAkVXNlckRhdGF7TmV3UFd9ID0gJFVzZXJPYmplY3QtPkdlbmVyYXRlUmFuZG9tUGFzc3dvcmQoKTsKCiAgICAgICAgIyB1cGRhdGUgbmV3IHBhc3N3b3JkCiAgICAgICAgbXkgJFN1Y2Nlc3MgPSAkVXNlck9iamVjdC0+U2V0UGFzc3dvcmQoCiAgICAgICAgICAgIFVzZXJMb2dpbiA9PiAkVXNlciwKICAgICAgICAgICAgUFcgICAgICAgID0+ICRVc2VyRGF0YXtOZXdQV30KICAgICAgICApOwoKICAgICAgICBpZiAoICEkU3VjY2VzcyApIHsKICAgICAgICAgICAgcmV0dXJuICRMYXlvdXRPYmplY3QtPkN1c3RvbWVyTG9naW4oCiAgICAgICAgICAgICAgICBUaXRsZSAgID0+ICdMb2dpbicsCiAgICAgICAgICAgICAgICBNZXNzYWdlID0+IFRyYW5zbGF0YWJsZSgnUmVzZXQgcGFzc3dvcmQgdW5zdWNjZXNzZnVsLiBQbGVhc2UgY29udGFjdCB0aGUgYWRtaW5pc3RyYXRvci4nKSwKICAgICAgICAgICAgICAgIFVzZXIgICAgPT4gJFVzZXIsCiAgICAgICAgICAgICk7CiAgICAgICAgfQoKICAgICAgICAjIHNlbmQgbm90aWZ5IGVtYWlsCiAgICAgICAgbXkgJEJvZHkgPSAkQ29uZmlnT2JqZWN0LT5HZXQoJ0N1c3RvbWVyUGFuZWxCb2R5TG9zdFBhc3N3b3JkJykKICAgICAgICAgICAgfHwgJ05ldyBQYXNzd29yZCBpczogPE9UT0JPX05FV1BXPic7CiAgICAgICAgbXkgJFN1YmplY3QgPSAkQ29uZmlnT2JqZWN0LT5HZXQoJ0N1c3RvbWVyUGFuZWxTdWJqZWN0TG9zdFBhc3N3b3JkJykKICAgICAgICAgICAgfHwgJ05ldyBQYXNzd29yZCEnOwogICAgICAgIGZvciAoIHNvcnQga2V5cyAlVXNlckRhdGEgKSB7CiAgICAgICAgICAgICRCb2R5ID1+IHMvPE9UT0JPXyRfPi8kVXNlckRhdGF7JF99L2dpOwogICAgICAgIH0KICAgICAgICBteSAkU2VudCA9ICRFbWFpbE9iamVjdC0+U2VuZCgKICAgICAgICAgICAgVG8gICAgICAgPT4gJFVzZXJEYXRhe1VzZXJFbWFpbH0sCiAgICAgICAgICAgIFN1YmplY3QgID0+ICRTdWJqZWN0LAogICAgICAgICAgICBDaGFyc2V0ICA9PiAkTGF5b3V0T2JqZWN0LT57VXNlckNoYXJzZXR9LAogICAgICAgICAgICBNaW1lVHlwZSA9PiAndGV4dC9wbGFpbicsCiAgICAgICAgICAgIEJvZHkgICAgID0+ICRCb2R5CiAgICAgICAgKTsKCiAgICAgICAgaWYgKCAhJFNlbnQtPntTdWNjZXNzfSApIHsKICAgICAgICAgICAgJExheW91dE9iamVjdC0+Q3VzdG9tZXJGYXRhbEVycm9yKAogICAgICAgICAgICAgICAgQ29tbWVudCA9PiBUcmFuc2xhdGFibGUoJ1BsZWFzZSBjb250YWN0IHRoZSBhZG1pbmlzdHJhdG9yLicpLAogICAgICAgICAgICApOyAgICAjIHRocm93cyBhIEtlcm5lbDo6U3lzdGVtOjpXZWI6OkV4Y2VwdGlvbgogICAgICAgIH0KICAgICAgICBteSAkTWVzc2FnZSA9ICRMYXlvdXRPYmplY3QtPntMYW5ndWFnZU9iamVjdH0tPlRyYW5zbGF0ZSgKICAgICAgICAgICAgJ1NlbnQgbmV3IHBhc3N3b3JkIHRvICVzLiBQbGVhc2UgY2hlY2sgeW91ciBlbWFpbC4nLAogICAgICAgICAgICAkVXNlckRhdGF7VXNlckVtYWlsfSwKICAgICAgICApOwoKICAgICAgICByZXR1cm4gJExheW91dE9iamVjdC0+Q3VzdG9tZXJMb2dpbigKICAgICAgICAgICAgVGl0bGUgICAgICAgPT4gJ0xvZ2luJywKICAgICAgICAgICAgTWVzc2FnZSAgICAgPT4gJE1lc3NhZ2UsCiAgICAgICAgICAgIFVzZXIgICAgICAgID0+ICRVc2VyLAogICAgICAgICAgICBNZXNzYWdlVHlwZSA9PiAnU3VjY2VzcycsCiAgICAgICAgKTsKICAgIH0KCiAgICAjIGNyZWF0ZSBuZXcgY3VzdG9tZXIgYWNjb3VudAogICAgZWxzaWYgKCAkUGFyYW17QWN0aW9ufSBlcSAnQ3VzdG9tZXJDcmVhdGVBY2NvdW50JyApIHsKCiAgICAgICAgIyBuZXcgbGF5b3V0IG9iamVjdAogICAgICAgIG15ICRMYXlvdXRPYmplY3QgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6Ok91dHB1dDo6SFRNTDo6TGF5b3V0Jyk7CgogICAgICAgICMgY2hlY2sgZmVhdHVyZQogICAgICAgIGlmICggISRDb25maWdPYmplY3QtPkdldCgnQ3VzdG9tZXJQYW5lbENyZWF0ZUFjY291bnQnKSApIHsKCiAgICAgICAgICAgICMgc2hvdyBub3JtYWwgbG9naW4KICAgICAgICAgICAgcmV0dXJuICRMYXlvdXRPYmplY3QtPkN1c3RvbWVyTG9naW4oCiAgICAgICAgICAgICAgICBUaXRsZSAgID0+ICdMb2dpbicsCiAgICAgICAgICAgICAgICBNZXNzYWdlID0+IFRyYW5zbGF0YWJsZSgnRmVhdHVyZSBub3QgYWN0aXZlIScpLAogICAgICAgICAgICApOwogICAgICAgIH0KCiAgICAgICAgIyBnZXQgcGFyYW1zCiAgICAgICAgbXkgJUdldFBhcmFtczsKICAgICAgICBmb3IgbXkgJEVudHJ5ICggQHsgJENvbmZpZ09iamVjdC0+R2V0KCdDdXN0b21lclVzZXInKS0+e01hcH0gfSApIHsKICAgICAgICAgICAgJEdldFBhcmFtc3sgJEVudHJ5LT5bMF0gfSA9ICRQYXJhbU9iamVjdC0+R2V0UGFyYW0oIFBhcmFtID0+ICRFbnRyeS0+WzFdICkKICAgICAgICAgICAgICAgIHx8ICcnOwogICAgICAgIH0KICAgICAgICAkR2V0UGFyYW1ze1ZhbGlkSUR9ID0gMTsKCiAgICAgICAgIyBjaGVjayBuZWVkZWQgcGFyYW1zCiAgICAgICAgaWYgKCAhJEdldFBhcmFtc3tVc2VyQ3VzdG9tZXJJRH0gKSB7CiAgICAgICAgICAgICRHZXRQYXJhbXN7VXNlckN1c3RvbWVySUR9ID0gJEdldFBhcmFtc3tVc2VyRW1haWx9OwogICAgICAgIH0KICAgICAgICBpZiAoICEkR2V0UGFyYW1ze1VzZXJMb2dpbn0gKSB7CiAgICAgICAgICAgICRHZXRQYXJhbXN7VXNlckxvZ2lufSA9ICRHZXRQYXJhbXN7VXNlckVtYWlsfTsKICAgICAgICB9CgogICAgICAgICMgZ2V0IG5ldyBwYXNzd29yZAogICAgICAgICRHZXRQYXJhbXN7VXNlclBhc3N3b3JkfSA9ICRVc2VyT2JqZWN0LT5HZW5lcmF0ZVJhbmRvbVBhc3N3b3JkKCk7CgogICAgICAgICMgZ2V0IHVzZXIgZGF0YQogICAgICAgIG15ICVVc2VyRGF0YSA9ICRVc2VyT2JqZWN0LT5DdXN0b21lclVzZXJEYXRhR2V0KCBVc2VyID0+ICRHZXRQYXJhbXN7VXNlckxvZ2lufSApOwogICAgICAgIGlmICggJFVzZXJEYXRhe1VzZXJJRH0gfHwgISRHZXRQYXJhbXN7VXNlckxvZ2lufSApIHsKCiAgICAgICAgICAgICMgc2VuZCBkYXRhIHRvIEpTCiAgICAgICAgICAgICRMYXlvdXRPYmplY3QtPkFkZEpTRGF0YSgKICAgICAgICAgICAgICAgIEtleSAgID0+ICdTaWdudXBFcnJvcicsCiAgICAgICAgICAgICAgICBWYWx1ZSA9PiAxLAogICAgICAgICAgICApOwoKICAgICAgICAgICAgcmV0dXJuICRMYXlvdXRPYmplY3QtPkN1c3RvbWVyTG9naW4oCiAgICAgICAgICAgICAgICBUaXRsZSAgICAgICAgID0+ICdMb2dpbicsCiAgICAgICAgICAgICAgICBNZXNzYWdlICAgICAgID0+IFRyYW5zbGF0YWJsZSgnVGhpcyBlLW1haWwgYWRkcmVzcyBhbHJlYWR5IGV4aXN0cy4gUGxlYXNlIGxvZyBpbiBvciByZXNldCB5b3VyIHBhc3N3b3JkLicpLAogICAgICAgICAgICAgICAgVXNlclRpdGxlICAgICA9PiAkR2V0UGFyYW1ze1VzZXJUaXRsZX0sCiAgICAgICAgICAgICAgICBVc2VyRmlyc3RuYW1lID0+ICRHZXRQYXJhbXN7VXNlckZpcnN0bmFtZX0sCiAgICAgICAgICAgICAgICBVc2VyTGFzdG5hbWUgID0+ICRHZXRQYXJhbXN7VXNlckxhc3RuYW1lfSwKICAgICAgICAgICAgICAgIFVzZXJFbWFpbCAgICAgPT4gJEdldFBhcmFtc3tVc2VyRW1haWx9LAogICAgICAgICAgICApOwogICAgICAgIH0KCiAgICAgICAgIyBjaGVjayBmb3IgbWFpbCBhZGRyZXNzIHJlc3RyaWN0aW9ucwogICAgICAgIG15IEBXaGl0ZWxpc3QgPSBAewogICAgICAgICAgICAkQ29uZmlnT2JqZWN0LT5HZXQoJ0N1c3RvbWVyUGFuZWxDcmVhdGVBY2NvdW50OjpNYWlsUmVzdHJpY3Rpb25zOjpXaGl0ZWxpc3QnKSAvLyBbXQogICAgICAgIH07CiAgICAgICAgbXkgQEJsYWNrbGlzdCA9IEB7CiAgICAgICAgICAgICRDb25maWdPYmplY3QtPkdldCgnQ3VzdG9tZXJQYW5lbENyZWF0ZUFjY291bnQ6Ok1haWxSZXN0cmljdGlvbnM6OkJsYWNrbGlzdCcpIC8vIFtdCiAgICAgICAgfTsKCiAgICAgICAgbXkgJFdoaXRlbGlzdE1hdGNoZWQ7CiAgICAgICAgZm9yIG15ICRXaGl0ZWxpc3RFbnRyeSAoQFdoaXRlbGlzdCkgewogICAgICAgICAgICBteSAkUmVnZXggPSBldmFsIHtxci8kV2hpdGVsaXN0RW50cnkvaX07CiAgICAgICAgICAgIGlmICgkQCkgewogICAgICAgICAgICAgICAgJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkxvZycpLT5Mb2coCiAgICAgICAgICAgICAgICAgICAgUHJpb3JpdHkgPT4gJ2Vycm9yJywKICAgICAgICAgICAgICAgICAgICBNZXNzYWdlICA9PgogICAgICAgICAgICAgICAgICAgICAgICAkTGF5b3V0T2JqZWN0LT57TGFuZ3VhZ2VPYmplY3R9LT5UcmFuc2xhdGUoCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAnVGhlIGN1c3RvbWVyIHBhbmVsIG1haWwgYWRkcmVzcyB3aGl0ZWxpc3QgY29udGFpbnMgdGhlIGludmFsaWQgcmVndWxhciBleHByZXNzaW9uICRXaGl0ZWxpc3RFbnRyeSwgcGxlYXNlIGNoZWNrIGFuZCBjb3JyZWN0IGl0LicKICAgICAgICAgICAgICAgICAgICAgICAgKSwKICAgICAgICAgICAgICAgICk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzaWYgKCAkR2V0UGFyYW1ze1VzZXJFbWFpbH0gPX4gJFJlZ2V4ICkgewogICAgICAgICAgICAgICAgJFdoaXRlbGlzdE1hdGNoZWQrKzsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBteSAkQmxhY2tsaXN0TWF0Y2hlZDsKICAgICAgICBmb3IgbXkgJEJsYWNrbGlzdEVudHJ5IChAQmxhY2tsaXN0KSB7CiAgICAgICAgICAgIG15ICRSZWdleCA9IGV2YWwge3FyLyRCbGFja2xpc3RFbnRyeS9pfTsKICAgICAgICAgICAgaWYgKCRAKSB7CiAgICAgICAgICAgICAgICAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6TG9nJyktPkxvZygKICAgICAgICAgICAgICAgICAgICBQcmlvcml0eSA9PiAnZXJyb3InLAogICAgICAgICAgICAgICAgICAgIE1lc3NhZ2UgID0+CiAgICAgICAgICAgICAgICAgICAgICAgICRMYXlvdXRPYmplY3QtPntMYW5ndWFnZU9iamVjdH0tPlRyYW5zbGF0ZSgKICAgICAgICAgICAgICAgICAgICAgICAgICAgICdUaGUgY3VzdG9tZXIgcGFuZWwgbWFpbCBhZGRyZXNzIGJsYWNrbGlzdCBjb250YWlucyB0aGUgaW52YWxpZCByZWd1bGFyIGV4cHJlc3Npb24gJEJsYWNrbGlzdEVudHJ5LCBwbGVhc2UgY2hlY2sgYW5kIGNvcnJlY3QgaXQuJwogICAgICAgICAgICAgICAgICAgICAgICApLAogICAgICAgICAgICAgICAgKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNpZiAoICRHZXRQYXJhbXN7VXNlckVtYWlsfSA9fiAkUmVnZXggKSB7CiAgICAgICAgICAgICAgICAkQmxhY2tsaXN0TWF0Y2hlZCsrOwogICAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICBpZiAoICggQFdoaXRlbGlzdCAmJiAhJFdoaXRlbGlzdE1hdGNoZWQgKSB8fCAoIEBCbGFja2xpc3QgJiYgJEJsYWNrbGlzdE1hdGNoZWQgKSApIHsKCiAgICAgICAgICAgICMgc2VuZCBkYXRhIHRvIEpTCiAgICAgICAgICAgICRMYXlvdXRPYmplY3QtPkFkZEpTRGF0YSgKICAgICAgICAgICAgICAgIEtleSAgID0+ICdTaWdudXBFcnJvcicsCiAgICAgICAgICAgICAgICBWYWx1ZSA9PiAxLAogICAgICAgICAgICApOwoKICAgICAgICAgICAgcmV0dXJuICRMYXlvdXRPYmplY3QtPkN1c3RvbWVyTG9naW4oCiAgICAgICAgICAgICAgICBUaXRsZSAgICAgICAgID0+ICdMb2dpbicsCiAgICAgICAgICAgICAgICBNZXNzYWdlICAgICAgID0+IFRyYW5zbGF0YWJsZSgnVGhpcyBlbWFpbCBhZGRyZXNzIGlzIG5vdCBhbGxvd2VkIHRvIHJlZ2lzdGVyLiBQbGVhc2UgY29udGFjdCBzdXBwb3J0IHN0YWZmLicpLAogICAgICAgICAgICAgICAgVXNlclRpdGxlICAgICA9PiAkR2V0UGFyYW1ze1VzZXJUaXRsZX0sCiAgICAgICAgICAgICAgICBVc2VyRmlyc3RuYW1lID0+ICRHZXRQYXJhbXN7VXNlckZpcnN0bmFtZX0sCiAgICAgICAgICAgICAgICBVc2VyTGFzdG5hbWUgID0+ICRHZXRQYXJhbXN7VXNlckxhc3RuYW1lfSwKICAgICAgICAgICAgICAgIFVzZXJFbWFpbCAgICAgPT4gJEdldFBhcmFtc3tVc2VyRW1haWx9LAogICAgICAgICAgICApOwogICAgICAgIH0KCiAgICAgICAgIyBjcmVhdGUgYWNjb3VudAogICAgICAgIG15ICREYXRlVGltZU9iamVjdCA9ICRLZXJuZWw6Ok9NLT5DcmVhdGUoJ0tlcm5lbDo6U3lzdGVtOjpEYXRlVGltZScpOwoKICAgICAgICBteSAkTm93ID0gJERhdGVUaW1lT2JqZWN0LT5Ub1N0cmluZygpOwoKICAgICAgICBteSAkQWRkID0gJFVzZXJPYmplY3QtPkN1c3RvbWVyVXNlckFkZCgKICAgICAgICAgICAgJUdldFBhcmFtcywKICAgICAgICAgICAgQ29tbWVudCA9PiAkTGF5b3V0T2JqZWN0LT57TGFuZ3VhZ2VPYmplY3R9LT5UcmFuc2xhdGUoICdBZGRlZCB2aWEgQ3VzdG9tZXIgUGFuZWwgKCVzKScsICROb3cgKSwKICAgICAgICAgICAgVmFsaWRJRCA9PiAxLAogICAgICAgICAgICBVc2VySUQgID0+ICRDb25maWdPYmplY3QtPkdldCgnQ3VzdG9tZXJQYW5lbFVzZXJJRCcpLAogICAgICAgICk7CiAgICAgICAgaWYgKCAhJEFkZCApIHsKCiAgICAgICAgICAgICMgc2VuZCBkYXRhIHRvIEpTCiAgICAgICAgICAgICRMYXlvdXRPYmplY3QtPkFkZEpTRGF0YSgKICAgICAgICAgICAgICAgIEtleSAgID0+ICdTaWdudXBFcnJvcicsCiAgICAgICAgICAgICAgICBWYWx1ZSA9PiAxLAogICAgICAgICAgICApOwoKICAgICAgICAgICAgcmV0dXJuICRMYXlvdXRPYmplY3QtPkN1c3RvbWVyTG9naW4oCiAgICAgICAgICAgICAgICBUaXRsZSAgICAgICAgID0+ICdMb2dpbicsCiAgICAgICAgICAgICAgICBNZXNzYWdlICAgICAgID0+IFRyYW5zbGF0YWJsZSgnQ3VzdG9tZXIgdXNlciBjYW5cJ3QgYmUgYWRkZWQhJyksCiAgICAgICAgICAgICAgICBVc2VyVGl0bGUgICAgID0+ICRHZXRQYXJhbXN7VXNlclRpdGxlfSwKICAgICAgICAgICAgICAgIFVzZXJGaXJzdG5hbWUgPT4gJEdldFBhcmFtc3tVc2VyRmlyc3RuYW1lfSwKICAgICAgICAgICAgICAgIFVzZXJMYXN0bmFtZSAgPT4gJEdldFBhcmFtc3tVc2VyTGFzdG5hbWV9LAogICAgICAgICAgICAgICAgVXNlckVtYWlsICAgICA9PiAkR2V0UGFyYW1ze1VzZXJFbWFpbH0sCiAgICAgICAgICAgICk7CiAgICAgICAgfQoKICAgICAgICAjIHNlbmQgbm90aWZ5IGVtYWlsCiAgICAgICAgbXkgJEVtYWlsT2JqZWN0ID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkVtYWlsJyk7CiAgICAgICAgbXkgJEJvZHkgICAgICAgID0gJENvbmZpZ09iamVjdC0+R2V0KCdDdXN0b21lclBhbmVsQm9keU5ld0FjY291bnQnKQogICAgICAgICAgICB8fCAnTm8gQ29uZmlnIE9wdGlvbiBmb3VuZCEnOwogICAgICAgIG15ICRTdWJqZWN0ID0gJENvbmZpZ09iamVjdC0+R2V0KCdDdXN0b21lclBhbmVsU3ViamVjdE5ld0FjY291bnQnKQogICAgICAgICAgICB8fCAnTmV3IE9UT0JPIEFjY291bnQhJzsKICAgICAgICBmb3IgKCBzb3J0IGtleXMgJUdldFBhcmFtcyApIHsKICAgICAgICAgICAgJEJvZHkgPX4gcy88T1RPQk9fJF8+LyRHZXRQYXJhbXN7JF99L2dpOwogICAgICAgIH0KCiAgICAgICAgIyBzZW5kIGFjY291bnQgaW5mbwogICAgICAgIG15ICRTZW50ID0gJEVtYWlsT2JqZWN0LT5TZW5kKAogICAgICAgICAgICBUbyAgICAgICA9PiAkR2V0UGFyYW1ze1VzZXJFbWFpbH0sCiAgICAgICAgICAgIFN1YmplY3QgID0+ICRTdWJqZWN0LAogICAgICAgICAgICBDaGFyc2V0ICA9PiAkTGF5b3V0T2JqZWN0LT57VXNlckNoYXJzZXR9LAogICAgICAgICAgICBNaW1lVHlwZSA9PiAndGV4dC9wbGFpbicsCiAgICAgICAgICAgIEJvZHkgICAgID0+ICRCb2R5CiAgICAgICAgKTsKICAgICAgICBpZiAoICEkU2VudC0+e1N1Y2Nlc3N9ICkgewogICAgICAgICAgICByZXR1cm4gam9pbiAnJywKICAgICAgICAgICAgICAgICRMYXlvdXRPYmplY3QtPkN1c3RvbWVySGVhZGVyKAogICAgICAgICAgICAgICAgICAgIEFyZWEgID0+ICdDb3JlJywKICAgICAgICAgICAgICAgICAgICBUaXRsZSA9PiAnRXJyb3InCiAgICAgICAgICAgICAgICApLAogICAgICAgICAgICAgICAgJExheW91dE9iamVjdC0+Q3VzdG9tZXJXYXJuaW5nKAogICAgICAgICAgICAgICAgICAgIENvbW1lbnQgPT4gVHJhbnNsYXRhYmxlKCdDYW5cJ3Qgc2VuZCBhY2NvdW50IGluZm8hJykKICAgICAgICAgICAgICAgICksCiAgICAgICAgICAgICAgICAkTGF5b3V0T2JqZWN0LT5DdXN0b21lckZvb3RlcigpOwogICAgICAgIH0KCiAgICAgICAgIyBzaG93IHNlbnQgYWNjb3VudCBpbmZvCiAgICAgICAgaWYgKCAkQ29uZmlnT2JqZWN0LT5HZXQoJ0N1c3RvbWVyUGFuZWxMb2dpblVSTCcpICkgewoKICAgICAgICAgICAgIyByZWRpcmVjdCB0byBhbHRlcm5hdGUgbG9naW4KICAgICAgICAgICAgJFBhcmFte1JlcXVlc3RlZFVSTH0gPSAkTGF5b3V0T2JqZWN0LT5MaW5rRW5jb2RlKCAkUGFyYW17UmVxdWVzdGVkVVJMfSApOwoKICAgICAgICAgICAgJExheW91dE9iamVjdC0+UmVkaXJlY3QoCiAgICAgICAgICAgICAgICBFeHRVUkwgPT4gJENvbmZpZ09iamVjdC0+R2V0KCdDdXN0b21lclBhbmVsTG9naW5VUkwnKQogICAgICAgICAgICAgICAgICAgIC4gIj9SZXF1ZXN0ZWRVUkw9JFBhcmFte1JlcXVlc3RlZFVSTH07VXNlcj0kR2V0UGFyYW1ze1VzZXJMb2dpbn07IgogICAgICAgICAgICAgICAgICAgIC4gIkVtYWlsPSRHZXRQYXJhbXN7VXNlckVtYWlsfTtSZWFzb249TmV3QWNjb3VudENyZWF0ZWQiLAogICAgICAgICAgICApOyAgICAjIHRocm93cyBhIEtlcm5lbDo6U3lzdGVtOjpXZWI6OkV4Y2VwdGlvbgogICAgICAgIH0KCiAgICAgICAgbXkgJEFjY291bnRDcmVhdGVkTWVzc2FnZSA9ICRMYXlvdXRPYmplY3QtPntMYW5ndWFnZU9iamVjdH0tPlRyYW5zbGF0ZSgKICAgICAgICAgICAgJ05ldyBhY2NvdW50IGNyZWF0ZWQuIFNlbnQgbG9naW4gaW5mb3JtYXRpb24gdG8gJXMuIFBsZWFzZSBjaGVjayB5b3VyIGVtYWlsLicsCiAgICAgICAgICAgICRHZXRQYXJhbXN7VXNlckVtYWlsfSwKICAgICAgICApOwoKICAgICAgICAjIGxvZ2luIHNjcmVlbgogICAgICAgIHJldHVybiAkTGF5b3V0T2JqZWN0LT5DdXN0b21lckxvZ2luKAogICAgICAgICAgICBUaXRsZSAgICAgICA9PiAnTG9naW4nLAogICAgICAgICAgICBNZXNzYWdlICAgICA9PiAkQWNjb3VudENyZWF0ZWRNZXNzYWdlLAogICAgICAgICAgICBVc2VyICAgICAgICA9PiAkR2V0UGFyYW1ze1VzZXJMb2dpbn0sCiAgICAgICAgICAgIE1lc3NhZ2VUeXBlID0+ICdTdWNjZXNzJywKICAgICAgICApOwogICAgfQoKICAgICMgc2hvdyBsb2dpbiBzaXRlCiAgICBlbHNpZiAoICEkUGFyYW17U2Vzc2lvbklEfSApIHsKCiAgICAgICAgIyBjcmVhdGUgQXV0aE9iamVjdAogICAgICAgIG15ICRBdXRoT2JqZWN0ICAgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6Q3VzdG9tZXJBdXRoJyk7CiAgICAgICAgbXkgJExheW91dE9iamVjdCA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6T3V0cHV0OjpIVE1MOjpMYXlvdXQnKTsKICAgICAgICBpZiAoICRBdXRoT2JqZWN0LT5HZXRPcHRpb24oIFdoYXQgPT4gJ1ByZUF1dGgnICkgKSB7CgogICAgICAgICAgICAjIGF1dG9tYXRpYyBsb2dpbgogICAgICAgICAgICAkUGFyYW17UmVxdWVzdGVkVVJMfSA9ICRMYXlvdXRPYmplY3QtPkxpbmtFbmNvZGUoICRQYXJhbXtSZXF1ZXN0ZWRVUkx9ICk7CgogICAgICAgICAgICBteSAkUHJlQXV0aCA9ICRBdXRoT2JqZWN0LT5QcmVBdXRoKAogICAgICAgICAgICAgICAgUmVxdWVzdGVkVVJMID0+ICRQYXJhbXtSZXF1ZXN0ZWRVUkx9LAogICAgICAgICAgICApOwoKICAgICAgICAgICAgaWYgKCAkUHJlQXV0aCAmJiAkUHJlQXV0aC0+e1JlZGlyZWN0VVJMfSApIHsKICAgICAgICAgICAgICAgICRMYXlvdXRPYmplY3QtPlJlZGlyZWN0KAogICAgICAgICAgICAgICAgICAgIEV4dFVSTCA9PiAkUHJlQXV0aC0+e1JlZGlyZWN0VVJMfSwKICAgICAgICAgICAgICAgICk7ICAgICMgdGhyb3dzIGEgS2VybmVsOjpTeXN0ZW06OldlYjo6RXhjZXB0aW9uCiAgICAgICAgICAgIH0KCiAgICAgICAgICAgICRMYXlvdXRPYmplY3QtPlJlZGlyZWN0KAogICAgICAgICAgICAgICAgT1AgPT4gIkFjdGlvbj1QcmVMb2dpbiZSZXF1ZXN0ZWRVUkw9JFBhcmFte1JlcXVlc3RlZFVSTH0iLAogICAgICAgICAgICApOyAgICAgICAgIyB0aHJvd3MgYSBLZXJuZWw6OlN5c3RlbTo6V2ViOjpFeGNlcHRpb24KICAgICAgICB9CiAgICAgICAgZWxzaWYgKCAkQ29uZmlnT2JqZWN0LT5HZXQoJ0N1c3RvbWVyUGFuZWxMb2dpblVSTCcpICkgewoKICAgICAgICAgICAgIyByZWRpcmVjdCB0byBhbHRlcm5hdGUgbG9naW4KICAgICAgICAgICAgJFBhcmFte1JlcXVlc3RlZFVSTH0gPSAkTGF5b3V0T2JqZWN0LT5MaW5rRW5jb2RlKCAkUGFyYW17UmVxdWVzdGVkVVJMfSApOwoKICAgICAgICAgICAgJExheW91dE9iamVjdC0+UmVkaXJlY3QoCiAgICAgICAgICAgICAgICBFeHRVUkwgPT4gJENvbmZpZ09iamVjdC0+R2V0KCdDdXN0b21lclBhbmVsTG9naW5VUkwnKQogICAgICAgICAgICAgICAgICAgIC4gIj9SZXF1ZXN0ZWRVUkw9JFBhcmFte1JlcXVlc3RlZFVSTH0iLAogICAgICAgICAgICApOyAgICAgICAgIyB0aHJvd3MgYSBLZXJuZWw6OlN5c3RlbTo6V2ViOjpFeGNlcHRpb24KICAgICAgICB9CgojIFJvdGhlciBPU1MgLyBPbmVUaW1lQXV0aGVudGljYXRpb25MaW5rCiAgICAgICAgbXkgJUV4dGVuZGVkQXV0aFBhcmFtczsKICAgICAgICBmb3IgbXkgJE5hbWUgKCAkQXV0aE9iamVjdC0+RXh0ZW5kZWRQYXJhbU5hbWVzKCkgKSB7CiAgICAgICAgICAgIG15ICRFeHRQYXJhbSA9ICRQYXJhbU9iamVjdC0+R2V0UGFyYW0oCiAgICAgICAgICAgICAgICBQYXJhbSA9PiAkTmFtZSwKICAgICAgICAgICAgICAgIFJhdyAgID0+IDEKICAgICAgICAgICAgKTsKICAgICAgICAgICAgaWYgKCBkZWZpbmVkICRFeHRQYXJhbSApIHsKICAgICAgICAgICAgICAgICRFeHRlbmRlZEF1dGhQYXJhbXN7JE5hbWV9ID0gJEV4dFBhcmFtOwogICAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAjIHJlZGlyZWN0IGRpcmVjdGx5IHRvIExvZ2luIGlmIG5lY2Vzc2FyeSBwYXJhbWV0ZXJzIGFyZSBwcmVzZW50CiAgICAgICAgaWYgKCAlRXh0ZW5kZWRBdXRoUGFyYW1zICkgewogICAgICAgICAgICBteSAkTG9naW5TdHJpbmcgPSAnQWN0aW9uPUxvZ2luJzsKICAgICAgICAgICAgZm9yIG15ICRLZXkgKCBrZXlzICVFeHRlbmRlZEF1dGhQYXJhbXMgKSB7CiAgICAgICAgICAgICAgICAkTG9naW5TdHJpbmcgLj0gIjskS2V5PSRFeHRlbmRlZEF1dGhQYXJhbXN7JEtleX0iOwogICAgICAgICAgICB9CgogICAgICAgICAgICAkUGFyYW17UmVxdWVzdGVkVVJMfSA9ICRMYXlvdXRPYmplY3QtPkxpbmtFbmNvZGUoICRQYXJhbXtSZXF1ZXN0ZWRVUkx9ICk7CiAgICAgICAgICAgIHByaW50ICRMYXlvdXRPYmplY3QtPlJlZGlyZWN0KAogICAgICAgICAgICAgICAgT1AgPT4gIiRMb2dpblN0cmluZztSZXF1ZXN0ZWRVUkw9JFBhcmFte1JlcXVlc3RlZFVSTH0iLAogICAgICAgICAgICApOwogICAgICAgIH0KIyBFTyBPbmVUaW1lQXV0aGVudGljYXRpb25MaW5rCgogICAgICAgICMgbG9naW4gc2NyZWVuCiAgICAgICAgcmV0dXJuICRMYXlvdXRPYmplY3QtPkN1c3RvbWVyTG9naW4oCiAgICAgICAgICAgIFRpdGxlID0+ICdMb2dpbicsCiAgICAgICAgICAgICVQYXJhbSwKICAgICAgICApOwogICAgfQoKICAgICMgcnVuIG1vZHVsZXMgaWYgYSB2ZXJzaW9uIHZhbHVlIGV4aXN0cwogICAgZWxzaWYgKCAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6TWFpbicpLT5SZXF1aXJlKCJLZXJuZWw6Ok1vZHVsZXM6OiRQYXJhbXtBY3Rpb259IikgKSB7CgogICAgICAgICMgY2hlY2sgc2Vzc2lvbiBpZAogICAgICAgIGlmICggISRTZXNzaW9uT2JqZWN0LT5DaGVja1Nlc3Npb25JRCggU2Vzc2lvbklEID0+ICRQYXJhbXtTZXNzaW9uSUR9ICkgKSB7CgogICAgICAgICAgICAjIGNyZWF0ZSBuZXcgTGF5b3V0T2JqZWN0IHdpdGggbmV3ICclUGFyYW0nCiAgICAgICAgICAgICRLZXJuZWw6Ok9NLT5PYmplY3RQYXJhbUFkZCgKICAgICAgICAgICAgICAgICdLZXJuZWw6Ok91dHB1dDo6SFRNTDo6TGF5b3V0JyA9PiB7CiAgICAgICAgICAgICAgICAgICAgU2V0Q29va2llcyA9PiB7CgogICAgICAgICAgICAgICAgICAgICAgICAjIGRlbGV0ZSB0aGUgT1RPQk8gc2Vzc2lvbiBjb29raWUKICAgICAgICAgICAgICAgICAgICAgICAgU2Vzc2lvbklEQ29va2llID0+ICRQYXJhbU9iamVjdC0+U2V0Q29va2llKAogICAgICAgICAgICAgICAgICAgICAgICAgICAgS2V5ICAgICAgPT4gJFBhcmFte1Nlc3Npb25OYW1lfSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIFZhbHVlICAgID0+ICcnLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgRXhwaXJlcyAgPT4gJy0xeScsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBQYXRoICAgICA9PiAkQ29uZmlnT2JqZWN0LT5HZXQoJ1NjcmlwdEFsaWFzJyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBTZWN1cmUgICA9PiAkQ29va2llU2VjdXJlQXR0cmlidXRlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgSFRUUE9ubHkgPT4gMSwKICAgICAgICAgICAgICAgICAgICAgICAgKSwKICAgICAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICAgICAgICAgICVQYXJhbSwKICAgICAgICAgICAgICAgIH0sCiAgICAgICAgICAgICk7CgogICAgICAgICAgICAjIGlmIHRoZSB3cm9uZyBzY2hlbWUgaXMgdXNlZCwgZGVsZXRlIGFsc28gdGhlICJvdGhlciIgY29va2llIC0gaXNzdWUgIzI1MQogICAgICAgICAgICBteSAoJFJlcXVlc3RTY2hlbWUpID0gc3BsaXQgJy8nLCAkUGFyYW1PYmplY3QtPlNlcnZlclByb3RvY29sLCAyOwogICAgICAgICAgICBpZiAoICRSZXF1ZXN0U2NoZW1lIG5lICRDb25maWdPYmplY3QtPkdldCgnSHR0cFR5cGUnKSApIHsKICAgICAgICAgICAgICAgICRLZXJuZWw6Ok9NLT5PYmplY3RQYXJhbUFkZCgKICAgICAgICAgICAgICAgICAgICAnS2VybmVsOjpPdXRwdXQ6OkhUTUw6OkxheW91dCcgPT4gewogICAgICAgICAgICAgICAgICAgICAgICBTZXRDb29raWVzID0+IHsKCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAjIGRlbGV0ZSB0aGUgT1RPQk8gc2Vzc2lvbiBjb29raWUKICAgICAgICAgICAgICAgICAgICAgICAgICAgIFNlc3Npb25JRENvb2tpZWh0dHAgPT4gJFBhcmFtT2JqZWN0LT5TZXRDb29raWUoCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgS2V5ICAgICAgPT4gJFBhcmFte1Nlc3Npb25OYW1lfSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBWYWx1ZSAgICA9PiAnJywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBFeHBpcmVzICA9PiAnLTF5JywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBQYXRoICAgICA9PiAkQ29uZmlnT2JqZWN0LT5HZXQoJ1NjcmlwdEFsaWFzJyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgU2VjdXJlICAgPT4gJycsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgSFRUUE9ubHkgPT4gMSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICksCgogICAgICAgICAgICAgICAgICAgICAgICAgICAgIyBkZWxldGUgdGhlIE9UT0JPIHNlc3Npb24gY29va2llCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBTZXNzaW9uSURDb29raWVodHRwcyA9PiAkUGFyYW1PYmplY3QtPlNldENvb2tpZSgKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBLZXkgICAgICA9PiAkUGFyYW17U2Vzc2lvbk5hbWV9LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFZhbHVlICAgID0+ICcnLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEV4cGlyZXMgID0+ICctMXknLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFBhdGggICAgID0+ICRDb25maWdPYmplY3QtPkdldCgnU2NyaXB0QWxpYXMnKSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBTZWN1cmUgICA9PiAxLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEhUVFBPbmx5ID0+IDEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICApLAogICAgICAgICAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICAgICAgICAgICAgICAlUGFyYW0sCiAgICAgICAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgICAgICk7CiAgICAgICAgICAgIH0KCiAgICAgICAgICAgICRLZXJuZWw6Ok9NLT5PYmplY3RzRGlzY2FyZCggT2JqZWN0cyA9PiBbJ0tlcm5lbDo6T3V0cHV0OjpIVE1MOjpMYXlvdXQnXSApOwogICAgICAgICAgICBteSAkTGF5b3V0T2JqZWN0ID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpPdXRwdXQ6OkhUTUw6OkxheW91dCcpOwoKICAgICAgICAgICAgIyBjcmVhdGUgQXV0aE9iamVjdAogICAgICAgICAgICBteSAkQXV0aE9iamVjdCA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpDdXN0b21lckF1dGgnKTsKICAgICAgICAgICAgaWYgKCAkQXV0aE9iamVjdC0+R2V0T3B0aW9uKCBXaGF0ID0+ICdQcmVBdXRoJyApICkgewoKICAgICAgICAgICAgICAgICMgYXV0b21hdGljIHJlLWxvZ2luCiAgICAgICAgICAgICAgICAkUGFyYW17UmVxdWVzdGVkVVJMfSA9ICRMYXlvdXRPYmplY3QtPkxpbmtFbmNvZGUoICRQYXJhbXtSZXF1ZXN0ZWRVUkx9ICk7CgogICAgICAgICAgICAgICAgbXkgJFByZUF1dGggPSAkQXV0aE9iamVjdC0+UHJlQXV0aCgKICAgICAgICAgICAgICAgICAgICBSZXF1ZXN0ZWRVUkwgPT4gJFBhcmFte1JlcXVlc3RlZFVSTH0sCiAgICAgICAgICAgICAgICApOwoKICAgICAgICAgICAgICAgIGlmICggJFByZUF1dGggJiYgJFByZUF1dGgtPntSZWRpcmVjdFVSTH0gKSB7CiAgICAgICAgICAgICAgICAgICAgJExheW91dE9iamVjdC0+UmVkaXJlY3QoCiAgICAgICAgICAgICAgICAgICAgICAgIEV4dFVSTCA9PiAkUHJlQXV0aC0+e1JlZGlyZWN0VVJMfSwKICAgICAgICAgICAgICAgICAgICApOyAgICAjIHRocm93cyBhIEtlcm5lbDo6U3lzdGVtOjpXZWI6OkV4Y2VwdGlvbgogICAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICAgICRMYXlvdXRPYmplY3QtPlJlZGlyZWN0KAogICAgICAgICAgICAgICAgICAgIE9QID0+ICI/QWN0aW9uPVByZUxvZ2luJlJlcXVlc3RlZFVSTD0kUGFyYW17UmVxdWVzdGVkVVJMfSIsCiAgICAgICAgICAgICAgICApOyAgICAgICAgIyB0aHJvd3MgYSBLZXJuZWw6OlN5c3RlbTo6V2ViOjpFeGNlcHRpb24KICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNpZiAoICRDb25maWdPYmplY3QtPkdldCgnQ3VzdG9tZXJQYW5lbExvZ2luVVJMJykgKSB7CgogICAgICAgICAgICAgICAgIyByZWRpcmVjdCB0byBhbHRlcm5hdGUgbG9naW4KICAgICAgICAgICAgICAgICRQYXJhbXtSZXF1ZXN0ZWRVUkx9ID0gJExheW91dE9iamVjdC0+TGlua0VuY29kZSggJFBhcmFte1JlcXVlc3RlZFVSTH0gKTsKCiAgICAgICAgICAgICAgICAkTGF5b3V0T2JqZWN0LT5SZWRpcmVjdCgKICAgICAgICAgICAgICAgICAgICBFeHRVUkwgPT4gJENvbmZpZ09iamVjdC0+R2V0KCdDdXN0b21lclBhbmVsTG9naW5VUkwnKQogICAgICAgICAgICAgICAgICAgICAgICAuICI/UmVhc29uPUludmFsaWRTZXNzaW9uSUQmUmVxdWVzdGVkVVJMPSRQYXJhbXtSZXF1ZXN0ZWRVUkx9IiwKICAgICAgICAgICAgICAgICk7ICAgICAgICAjIHRocm93cyBhIEtlcm5lbDo6U3lzdGVtOjpXZWI6OkV4Y2VwdGlvbgogICAgICAgICAgICB9CgogICAgICAgICAgICAjIHNob3cgbG9naW4KICAgICAgICAgICAgcmV0dXJuICRMYXlvdXRPYmplY3QtPkN1c3RvbWVyTG9naW4oCiAgICAgICAgICAgICAgICBUaXRsZSAgID0+ICdMb2dpbicsCiAgICAgICAgICAgICAgICBNZXNzYWdlID0+CiAgICAgICAgICAgICAgICAgICAgJExheW91dE9iamVjdC0+e0xhbmd1YWdlT2JqZWN0fS0+VHJhbnNsYXRlKCAkU2Vzc2lvbk9iamVjdC0+U2Vzc2lvbklERXJyb3JNZXNzYWdlKCkgKSwKICAgICAgICAgICAgICAgICVQYXJhbSwKICAgICAgICAgICAgKTsKICAgICAgICB9CgogICAgICAgICMgZ2V0IHNlc3Npb24gZGF0YQogICAgICAgIG15ICVVc2VyRGF0YSA9ICRTZXNzaW9uT2JqZWN0LT5HZXRTZXNzaW9uSUREYXRhKAogICAgICAgICAgICBTZXNzaW9uSUQgPT4gJFBhcmFte1Nlc3Npb25JRH0sCiAgICAgICAgKTsKCiAgICAgICAgJFVzZXJEYXRhe1VzZXJUaW1lWm9uZX0gPSAkU2VsZi0+X1VzZXJUaW1lWm9uZUdldCglVXNlckRhdGEpOwoKICAgICAgICAjIGNoZWNrIG5lZWRlZCBkYXRhCiAgICAgICAgaWYgKCAhJFVzZXJEYXRhe1VzZXJJRH0gfHwgISRVc2VyRGF0YXtVc2VyTG9naW59IHx8ICRVc2VyRGF0YXtVc2VyVHlwZX0gbmUgJ0N1c3RvbWVyJyApIHsKCiAgICAgICAgICAgIG15ICRMYXlvdXRPYmplY3QgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6Ok91dHB1dDo6SFRNTDo6TGF5b3V0Jyk7CgogICAgICAgICAgICAjIHJlZGlyZWN0IHRvIGFsdGVybmF0ZSBsb2dpbgogICAgICAgICAgICBpZiAoICRDb25maWdPYmplY3QtPkdldCgnQ3VzdG9tZXJQYW5lbExvZ2luVVJMJykgKSB7CiAgICAgICAgICAgICAgICAkTGF5b3V0T2JqZWN0LT5SZWRpcmVjdCgKICAgICAgICAgICAgICAgICAgICBFeHRVUkwgPT4gJENvbmZpZ09iamVjdC0+R2V0KCdDdXN0b21lclBhbmVsTG9naW5VUkwnKSAuICc/UmVhc29uPVN5c3RlbUVycm9yJywKICAgICAgICAgICAgICAgICk7ICAgICMgdGhyb3dzIGEgS2VybmVsOjpTeXN0ZW06OldlYjo6RXhjZXB0aW9uCiAgICAgICAgICAgIH0KCiAgICAgICAgICAgICMgc2hvdyBsb2dpbiBzY3JlZW4KICAgICAgICAgICAgcmV0dXJuICRMYXlvdXRPYmplY3QtPkN1c3RvbWVyTG9naW4oCiAgICAgICAgICAgICAgICBUaXRsZSAgID0+ICdFcnJvcicsCiAgICAgICAgICAgICAgICBNZXNzYWdlID0+IFRyYW5zbGF0YWJsZSgnRXJyb3I6IGludmFsaWQgc2Vzc2lvbi4nKSwKICAgICAgICAgICAgICAgICVQYXJhbSwKICAgICAgICAgICAgKTsKICAgICAgICB9CgogICAgICAgICMgY2hlY2sgbW9kdWxlIHJlZ2lzdHJ5CiAgICAgICAgbXkgJE1vZHVsZVJlZyA9ICRDb25maWdPYmplY3QtPkdldCgnQ3VzdG9tZXJGcm9udGVuZDo6TW9kdWxlJyktPnsgJFBhcmFte0FjdGlvbn0gfTsKICAgICAgICBpZiAoICEkTW9kdWxlUmVnICkgewoKICAgICAgICAgICAgbXkgJExheW91dE9iamVjdCA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6T3V0cHV0OjpIVE1MOjpMYXlvdXQnKTsKCiAgICAgICAgICAgICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpMb2cnKS0+TG9nKAogICAgICAgICAgICAgICAgUHJpb3JpdHkgPT4gJ2Vycm9yJywKICAgICAgICAgICAgICAgIE1lc3NhZ2UgID0+CiAgICAgICAgICAgICAgICAgICAgIk1vZHVsZSBLZXJuZWw6Ok1vZHVsZXM6OiRQYXJhbXtBY3Rpb259IG5vdCByZWdpc3RlcmVkIGluIEtlcm5lbC9Db25maWcucG0hIiwKICAgICAgICAgICAgKTsKCiAgICAgICAgICAgICRMYXlvdXRPYmplY3QtPkN1c3RvbWVyRmF0YWxFcnJvcigKICAgICAgICAgICAgICAgIENvbW1lbnQgPT4gVHJhbnNsYXRhYmxlKCdQbGVhc2UgY29udGFjdCB0aGUgYWRtaW5pc3RyYXRvci4nKSwKICAgICAgICAgICAgKTsgICAgIyB0aHJvd3MgYSBLZXJuZWw6OlN5c3RlbTo6V2ViOjpFeGNlcHRpb24KICAgICAgICB9CgogICAgICAgICMgbW9kdWxlIHBlcm1pc3Npb24gY2hlY2sgZm9yIGFjdGlvbgogICAgICAgIGlmICgKICAgICAgICAgICAgcmVmICRNb2R1bGVSZWctPntHcm91cFJvfSBlcSAnQVJSQVknCiAgICAgICAgICAgICYmICFzY2FsYXIgQHsgJE1vZHVsZVJlZy0+e0dyb3VwUm99IH0KICAgICAgICAgICAgJiYgcmVmICRNb2R1bGVSZWctPntHcm91cH0gZXEgJ0FSUkFZJwogICAgICAgICAgICAmJiAhc2NhbGFyIEB7ICRNb2R1bGVSZWctPntHcm91cH0gfQogICAgICAgICAgICApCiAgICAgICAgewogICAgICAgICAgICAkUGFyYW17QWNjZXNzUm99ID0gMTsKICAgICAgICAgICAgJFBhcmFte0FjY2Vzc1J3fSA9IDE7CiAgICAgICAgfQogICAgICAgIGVsc2UgewoKICAgICAgICAgICAgKCAkUGFyYW17QWNjZXNzUm99LCAkUGFyYW17QWNjZXNzUnd9ICkgPSAkU2VsZi0+X0NoZWNrTW9kdWxlUGVybWlzc2lvbigKICAgICAgICAgICAgICAgIE1vZHVsZVJlZyA9PiAkTW9kdWxlUmVnLAogICAgICAgICAgICAgICAgJVVzZXJEYXRhLAogICAgICAgICAgICApOwoKICAgICAgICAgICAgaWYgKCAhJFBhcmFte0FjY2Vzc1JvfSApIHsKCiAgICAgICAgICAgICAgICAjIG5ldyBsYXlvdXQgb2JqZWN0CiAgICAgICAgICAgICAgICBteSAkTGF5b3V0T2JqZWN0ID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpPdXRwdXQ6OkhUTUw6OkxheW91dCcpOwogICAgICAgICAgICAgICAgJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkxvZycpLT5Mb2coCiAgICAgICAgICAgICAgICAgICAgUHJpb3JpdHkgPT4gJ2Vycm9yJywKICAgICAgICAgICAgICAgICAgICBNZXNzYWdlICA9PiAnTm8gUGVybWlzc2lvbiB0byB1c2UgdGhpcyBmcm9udGVuZCBhY3Rpb24gbW9kdWxlIScKICAgICAgICAgICAgICAgICk7CgogICAgICAgICAgICAgICAgJExheW91dE9iamVjdC0+Q3VzdG9tZXJGYXRhbEVycm9yKAogICAgICAgICAgICAgICAgICAgIENvbW1lbnQgPT4gVHJhbnNsYXRhYmxlKCdQbGVhc2UgY29udGFjdCB0aGUgYWRtaW5pc3RyYXRvci4nKSwKICAgICAgICAgICAgICAgICk7ICAgICMgdGhyb3dzIGEgS2VybmVsOjpTeXN0ZW06OldlYjo6RXhjZXB0aW9uCiAgICAgICAgICAgIH0KCiAgICAgICAgfQoKICAgICAgICBteSAkTmF2aWdhdGlvbkNvbmZpZyA9ICRDb25maWdPYmplY3QtPkdldCgnQ3VzdG9tZXJGcm9udGVuZDo6TmF2aWdhdGlvbicpLT57ICRQYXJhbXtBY3Rpb259IH07CgogICAgICAgICMgbW9kdWxlIHBlcm1pc3Npb24gY2hlY2sgZm9yIHN1Ym1lbnUgaXRlbQogICAgICAgIGlmICggSXNIYXNoUmVmV2l0aERhdGEoJE5hdmlnYXRpb25Db25maWcpICkgewoKICAgICAgICAgICAgS0VZOgogICAgICAgICAgICBmb3IgbXkgJEtleSAoIHNvcnQga2V5cyAleyROYXZpZ2F0aW9uQ29uZmlnfSApIHsKICAgICAgICAgICAgICAgIG5leHQgS0VZIGlmICRLZXkgICAgICAgICAgICAgICAgICF+IG0vXlxkKy9pOwogICAgICAgICAgICAgICAgbmV4dCBLRVkgaWYgJFBhcmFte1JlcXVlc3RlZFVSTH0gIX4gbS9TdWJhY3Rpb24vaTsKCiAgICAgICAgICAgICAgICBteSBATW9kdWxlTmF2aWdhdGlvbkNvbmZpZ3M7CgogICAgICAgICAgICAgICAgIyBGSVhNRTogU3VwcG9ydCBib3RoIG9sZCAoSEFTSCkgYW5kIG5ldyAoQVJSQVkgb2YgSEFTSCkgbmF2aWdhdGlvbiBjb25maWd1cmF0aW9ucywgZm9yIHJlYXNvbnMgb2YKICAgICAgICAgICAgICAgICMgICBiYWNrd2FyZHMgY29tcGF0aWJpbGl0eS4gT25jZSB3ZSBhcmUgc3VyZSBldmVyeXRoaW5nIGhhcyBiZWVuIG1pZ3JhdGVkIGNvcnJlY3RseSwgc3VwcG9ydCBmb3IKICAgICAgICAgICAgICAgICMgICBIQVNILW9ubHkgY29uZmlndXJhdGlvbiBjYW4gYmUgZHJvcHBlZCBpbiBmdXR1cmUgbWFqb3IgcmVsZWFzZS4KICAgICAgICAgICAgICAgIGlmICggSXNIYXNoUmVmV2l0aERhdGEoICROYXZpZ2F0aW9uQ29uZmlnLT57JEtleX0gKSApIHsKICAgICAgICAgICAgICAgICAgICBwdXNoIEBNb2R1bGVOYXZpZ2F0aW9uQ29uZmlncywgJE5hdmlnYXRpb25Db25maWctPnskS2V5fTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2lmICggSXNBcnJheVJlZldpdGhEYXRhKCAkTmF2aWdhdGlvbkNvbmZpZy0+eyRLZXl9ICkgKSB7CiAgICAgICAgICAgICAgICAgICAgcHVzaCBATW9kdWxlTmF2aWdhdGlvbkNvbmZpZ3MsIEB7ICROYXZpZ2F0aW9uQ29uZmlnLT57JEtleX0gfTsKICAgICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgICAjIFNraXAgaW5jb21wYXRpYmxlIGNvbmZpZ3VyYXRpb24uCiAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICBuZXh0IEtFWTsKICAgICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgICBJVEVNOgogICAgICAgICAgICAgICAgZm9yIG15ICRJdGVtIChATW9kdWxlTmF2aWdhdGlvbkNvbmZpZ3MpIHsKICAgICAgICAgICAgICAgICAgICBpZiAoCiAgICAgICAgICAgICAgICAgICAgICAgICRJdGVtLT57TGlua30gIX4gbS9TdWJhY3Rpb249L2kKICAgICAgICAgICAgICAgICAgICAgICAgfHwgJEl0ZW0tPntMaW5rfSAhfiBtLyRQYXJhbXtTdWJhY3Rpb259L2kKICAgICAgICAgICAgICAgICAgICAgICAgKQogICAgICAgICAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgICAgICAgICAgbmV4dCBJVEVNOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAkUGFyYW17QWNjZXNzUm99ID0gMDsKICAgICAgICAgICAgICAgICAgICAkUGFyYW17QWNjZXNzUnd9ID0gMDsKCiAgICAgICAgICAgICAgICAgICAgIyBtb2R1bGUgcGVybWlzc2lvbiBjaGVjayBmb3Igc3VibWVudSBpdGVtCiAgICAgICAgICAgICAgICAgICAgaWYgKAogICAgICAgICAgICAgICAgICAgICAgICByZWYgJEl0ZW0tPntHcm91cFJvfSBlcSAnQVJSQVknCiAgICAgICAgICAgICAgICAgICAgICAgICYmICFzY2FsYXIgQHsgJEl0ZW0tPntHcm91cFJvfSB9CiAgICAgICAgICAgICAgICAgICAgICAgICYmIHJlZiAkSXRlbS0+e0dyb3VwfSBlcSAnQVJSQVknCiAgICAgICAgICAgICAgICAgICAgICAgICYmICFzY2FsYXIgQHsgJEl0ZW0tPntHcm91cH0gfQogICAgICAgICAgICAgICAgICAgICAgICApCiAgICAgICAgICAgICAgICAgICAgewogICAgICAgICAgICAgICAgICAgICAgICAkUGFyYW17QWNjZXNzUm99ID0gMTsKICAgICAgICAgICAgICAgICAgICAgICAgJFBhcmFte0FjY2Vzc1J3fSA9IDE7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGVsc2UgewoKICAgICAgICAgICAgICAgICAgICAgICAgKCAkUGFyYW17QWNjZXNzUm99LCAkUGFyYW17QWNjZXNzUnd9ICkgPSAkU2VsZi0+X0NoZWNrTW9kdWxlUGVybWlzc2lvbigKICAgICAgICAgICAgICAgICAgICAgICAgICAgIE1vZHVsZVJlZyA9PiAkSXRlbSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICVVc2VyRGF0YSwKICAgICAgICAgICAgICAgICAgICAgICAgKTsKCiAgICAgICAgICAgICAgICAgICAgICAgIGlmICggISRQYXJhbXtBY2Nlc3NSb30gKSB7CgogICAgICAgICAgICAgICAgICAgICAgICAgICAgIyBuZXcgbGF5b3V0IG9iamVjdAogICAgICAgICAgICAgICAgICAgICAgICAgICAgbXkgJExheW91dE9iamVjdCA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6T3V0cHV0OjpIVE1MOjpMYXlvdXQnKTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpMb2cnKS0+TG9nKAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFByaW9yaXR5ID0+ICdlcnJvcicsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgTWVzc2FnZSAgPT4gJ05vIFBlcm1pc3Npb24gdG8gdXNlIHRoaXMgZnJvbnRlbmQgc3ViYWN0aW9uIG1vZHVsZSEnCiAgICAgICAgICAgICAgICAgICAgICAgICAgICApOwoKICAgICAgICAgICAgICAgICAgICAgICAgICAgICRMYXlvdXRPYmplY3QtPkN1c3RvbWVyRmF0YWxFcnJvcigKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBDb21tZW50ID0+IFRyYW5zbGF0YWJsZSgnUGxlYXNlIGNvbnRhY3QgdGhlIGFkbWluaXN0cmF0b3IuJykKICAgICAgICAgICAgICAgICAgICAgICAgICAgICk7ICAgICMgdGhyb3dzIGEgS2VybmVsOjpTeXN0ZW06OldlYjo6RXhjZXB0aW9uCiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgICMgY3JlYXRlIG5ldyBMYXlvdXRPYmplY3Qgd2l0aCBuZXcgJyVQYXJhbScgYW5kICclVXNlckRhdGEnCiAgICAgICAgJEtlcm5lbDo6T00tPk9iamVjdFBhcmFtQWRkKAogICAgICAgICAgICAnS2VybmVsOjpPdXRwdXQ6OkhUTUw6OkxheW91dCcgPT4gewogICAgICAgICAgICAgICAgJVBhcmFtLAogICAgICAgICAgICAgICAgJVVzZXJEYXRhLAogICAgICAgICAgICAgICAgTW9kdWxlUmVnID0+ICRNb2R1bGVSZWcsCiAgICAgICAgICAgIH0sCiAgICAgICAgKTsKCiAgICAgICAgJEtlcm5lbDo6T00tPk9iamVjdHNEaXNjYXJkKCBPYmplY3RzID0+IFsnS2VybmVsOjpPdXRwdXQ6OkhUTUw6OkxheW91dCddICk7CgogICAgICAgICMgdXBkYXRlIGxhc3QgcmVxdWVzdCB0aW1lCiAgICAgICAgaWYgKAogICAgICAgICAgICAhJFBhcmFtT2JqZWN0LT5Jc0FKQVhSZXF1ZXN0KCkKICAgICAgICAgICAgfHwgJFBhcmFte0FjdGlvbn0gZXEgJ0N1c3RvbWVyVmlkZW9DaGF0JwogICAgICAgICAgICApCiAgICAgICAgewogICAgICAgICAgICBteSAkRGF0ZVRpbWVPYmplY3QgPSAkS2VybmVsOjpPTS0+Q3JlYXRlKCdLZXJuZWw6OlN5c3RlbTo6RGF0ZVRpbWUnKTsKCiAgICAgICAgICAgICRTZXNzaW9uT2JqZWN0LT5VcGRhdGVTZXNzaW9uSUQoCiAgICAgICAgICAgICAgICBTZXNzaW9uSUQgPT4gJFBhcmFte1Nlc3Npb25JRH0sCiAgICAgICAgICAgICAgICBLZXkgICAgICAgPT4gJ1VzZXJMYXN0UmVxdWVzdCcsCiAgICAgICAgICAgICAgICBWYWx1ZSAgICAgPT4gJERhdGVUaW1lT2JqZWN0LT5Ub0Vwb2NoKCksCiAgICAgICAgICAgICk7CiAgICAgICAgfQoKICAgICAgICAjIHByZSBhcHBsaWNhdGlvbiBtb2R1bGUKICAgICAgICBteSAkUHJlTW9kdWxlID0gJENvbmZpZ09iamVjdC0+R2V0KCdDdXN0b21lclBhbmVsUHJlQXBwbGljYXRpb25Nb2R1bGUnKTsKICAgICAgICBpZiAoICRQYXJhbXtBY3Rpb259IG5lICdDdXN0b21lckdlbmVyaWNDb250ZW50JyAmJiAkUHJlTW9kdWxlICkgewogICAgICAgICAgICBteSAlUHJlTW9kdWxlTGlzdDsKICAgICAgICAgICAgaWYgKCByZWYgJFByZU1vZHVsZSBlcSAnSEFTSCcgKSB7CiAgICAgICAgICAgICAgICAlUHJlTW9kdWxlTGlzdCA9ICV7JFByZU1vZHVsZX07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAkUHJlTW9kdWxlTGlzdHtJbml0fSA9ICRQcmVNb2R1bGU7CiAgICAgICAgICAgIH0KCiAgICAgICAgICAgIE1PRFVMRToKICAgICAgICAgICAgZm9yIG15ICRQcmVNb2R1bGVLZXkgKCBzb3J0IGtleXMgJVByZU1vZHVsZUxpc3QgKSB7CiAgICAgICAgICAgICAgICBteSAkUHJlTW9kdWxlID0gJFByZU1vZHVsZUxpc3R7JFByZU1vZHVsZUtleX07CiAgICAgICAgICAgICAgICBuZXh0IE1PRFVMRSBpZiAhJFByZU1vZHVsZTsKICAgICAgICAgICAgICAgIG5leHQgTU9EVUxFIGlmICEkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6TWFpbicpLT5SZXF1aXJlKCRQcmVNb2R1bGUpOwoKICAgICAgICAgICAgICAgICMgZGVidWcgaW5mbwogICAgICAgICAgICAgICAgaWYgKCAkU2VsZi0+e0RlYnVnfSApIHsKICAgICAgICAgICAgICAgICAgICAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6TG9nJyktPkxvZygKICAgICAgICAgICAgICAgICAgICAgICAgUHJpb3JpdHkgPT4gJ2RlYnVnJywKICAgICAgICAgICAgICAgICAgICAgICAgTWVzc2FnZSAgPT4gIkN1c3RvbWVyUGFuZWxQcmVBcHBsaWNhdGlvbiBtb2R1bGUgJFByZU1vZHVsZSBpcyB1c2VkLiIsCiAgICAgICAgICAgICAgICAgICAgKTsKICAgICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgICBteSAkTGF5b3V0T2JqZWN0ID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpPdXRwdXQ6OkhUTUw6OkxheW91dCcpOwoKICAgICAgICAgICAgICAgICMgdXNlIG1vZHVsZQogICAgICAgICAgICAgICAgbXkgJFByZU1vZHVsZU9iamVjdCA9ICRQcmVNb2R1bGUtPm5ldygKICAgICAgICAgICAgICAgICAgICAlUGFyYW0sCiAgICAgICAgICAgICAgICAgICAgJVVzZXJEYXRhLAoKICAgICAgICAgICAgICAgICk7CiAgICAgICAgICAgICAgICBteSAkT3V0cHV0ID0gJFByZU1vZHVsZU9iamVjdC0+UHJlUnVuKCk7CgogICAgICAgICAgICAgICAgcmV0dXJuICRPdXRwdXQgaWYgJE91dHB1dDsKICAgICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgIyBkZWJ1ZyBpbmZvCiAgICAgICAgaWYgKCAkU2VsZi0+e0RlYnVnfSApIHsKICAgICAgICAgICAgJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkxvZycpLT5Mb2coCiAgICAgICAgICAgICAgICBQcmlvcml0eSA9PiAnZGVidWcnLAogICAgICAgICAgICAgICAgTWVzc2FnZSAgPT4gJ0tlcm5lbDo6TW9kdWxlczo6JyAuICRQYXJhbXtBY3Rpb259IC4gJy0+bmV3JywKICAgICAgICAgICAgKTsKICAgICAgICB9CgogICAgICAgIG15ICRGcm9udGVuZE9iamVjdCA9ICggJ0tlcm5lbDo6TW9kdWxlczo6JyAuICRQYXJhbXtBY3Rpb259ICktPm5ldygKICAgICAgICAgICAgJVBhcmFtLAogICAgICAgICAgICAlVXNlckRhdGEsCiAgICAgICAgICAgIE1vZHVsZVJlZyA9PiAkTW9kdWxlUmVnLAogICAgICAgICAgICBEZWJ1ZyAgICAgPT4gJFNlbGYtPntEZWJ1Z30sCiAgICAgICAgKTsKCiAgICAgICAgIyBkZWJ1ZyBpbmZvCiAgICAgICAgaWYgKCAkU2VsZi0+e0RlYnVnfSApIHsKICAgICAgICAgICAgJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkxvZycpLT5Mb2coCiAgICAgICAgICAgICAgICBQcmlvcml0eSA9PiAnZGVidWcnLAogICAgICAgICAgICAgICAgTWVzc2FnZSAgPT4gJ0tlcm5lbDo6TW9kdWxlczo6JyAuICRQYXJhbXtBY3Rpb259IC4gJy0+cnVuJywKICAgICAgICAgICAgKTsKICAgICAgICB9CgogICAgICAgICMgLT5SdW4gJEFjdGlvbiB3aXRoICRGcm9udGVuZE9iamVjdAogICAgICAgIG15ICRPdXRwdXQgPSAkRnJvbnRlbmRPYmplY3QtPlJ1bigpOwoKICAgICAgICAjIGxvZyByZXF1ZXN0IHRpbWUgZm9yIEFkbWluUGVyZm9ybWFuY2VMb2cKICAgICAgICBpZiAoICRDb25maWdPYmplY3QtPkdldCgnUGVyZm9ybWFuY2VMb2cnKSApIHsKICAgICAgICAgICAgbXkgJEZpbGUgPSAkQ29uZmlnT2JqZWN0LT5HZXQoJ1BlcmZvcm1hbmNlTG9nOjpGaWxlJyk7CgogICAgICAgICAgICAjIFdyaXRlIHRvIFBlcmZvcm1hbmNlTG9nIGZpbGUgb25seSBpZiBpdCBpcyBzbWFsbGVyIHRoYW4gc2l6ZSBsaW1pdCAoc2VlIGJ1ZyMxNDc0NykuCiAgICAgICAgICAgIGlmICggLXMgJEZpbGUgPCAoIDEwMjQgKiAxMDI0ICogJENvbmZpZ09iamVjdC0+R2V0KCdQZXJmb3JtYW5jZUxvZzo6RmlsZU1heCcpICkgKSB7CiAgICAgICAgICAgICAgICBpZiAoIG9wZW4gbXkgJE91dCwgJz4+JywgJEZpbGUgKSB7ICAgICMjIG5vIGNyaXRpYyBxdyhPVE9CTzo6UHJvaGliaXRPcGVuKQoKICAgICAgICAgICAgICAgICAgICAjIGEgZmFsbGJhY2sgZm9yIHRoZSBxdWVyeSBzdHJpbmcgd2hlbiB0aGUgYWN0aW9uIGlzIG1pc3NpbmcKICAgICAgICAgICAgICAgICAgICBpZiAoICggISRRdWVyeVN0cmluZyAmJiAkUGFyYW17QWN0aW9ufSApIHx8ICRRdWVyeVN0cmluZyAhfiAvQWN0aW9uPS8gKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICRRdWVyeVN0cmluZyA9ICdBY3Rpb249JyAuICRQYXJhbXtBY3Rpb259IC4gJztTdWJhY3Rpb249JyAuICRQYXJhbXtTdWJhY3Rpb259OwogICAgICAgICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgICAgICAgbXkgJE5vdyA9IFRpbWU6OkhpUmVzOjp0aW1lKCk7CiAgICAgICAgICAgICAgICAgICAgcHJpbnQgJE91dCBqb2luICc6OicsCiAgICAgICAgICAgICAgICAgICAgICAgICROb3csCiAgICAgICAgICAgICAgICAgICAgICAgICdDdXN0b21lcicsCiAgICAgICAgICAgICAgICAgICAgICAgICggJE5vdyAtICRTZWxmLT57UGVyZm9ybWFuY2VMb2dTdGFydH0gKSwKICAgICAgICAgICAgICAgICAgICAgICAgJFVzZXJEYXRhe1VzZXJMb2dpbn0sICAgICMgbm90IHVzZWQgaW4gdGhlIEFkbWluUGVyZm9ybWFuY2VMb2cgZnJvbnRlbmQKICAgICAgICAgICAgICAgICAgICAgICAgIiRRdWVyeVN0cmluZ1xuIjsKICAgICAgICAgICAgICAgICAgICBjbG9zZSAkT3V0OwoKICAgICAgICAgICAgICAgICAgICAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6TG9nJyktPkxvZygKICAgICAgICAgICAgICAgICAgICAgICAgUHJpb3JpdHkgPT4gJ2RlYnVnJywKICAgICAgICAgICAgICAgICAgICAgICAgTWVzc2FnZSAgPT4gJ1Jlc3BvbnNlOjpDdXN0b21lcjogJwogICAgICAgICAgICAgICAgICAgICAgICAgICAgLiAoICROb3cgLSAkU2VsZi0+e1BlcmZvcm1hbmNlTG9nU3RhcnR9ICkKICAgICAgICAgICAgICAgICAgICAgICAgICAgIC4gInMgdGFrZW4gKFVSTDokUXVlcnlTdHJpbmc6JFVzZXJEYXRhe1VzZXJMb2dpbn0pIiwKICAgICAgICAgICAgICAgICAgICApOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkxvZycpLT5Mb2coCiAgICAgICAgICAgICAgICAgICAgICAgIFByaW9yaXR5ID0+ICdlcnJvcicsCiAgICAgICAgICAgICAgICAgICAgICAgIE1lc3NhZ2UgID0+ICJDYW4ndCB3cml0ZSAkRmlsZTogJCEiLAogICAgICAgICAgICAgICAgICAgICk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6TG9nJyktPkxvZygKICAgICAgICAgICAgICAgICAgICBQcmlvcml0eSA9PiAnZXJyb3InLAogICAgICAgICAgICAgICAgICAgIE1lc3NhZ2UgID0+ICJQZXJmb3JtYW5jZUxvZyBmaWxlICckRmlsZScgaXMgdG9vIGxhcmdlLCB5b3UgbmVlZCB0byByZXNldCBpdCBpbiBQZXJmb3JtYW5jZUxvZyBwYWdlISIsCiAgICAgICAgICAgICAgICApOwogICAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICByZXR1cm4gJE91dHB1dDsKICAgIH0KCiAgICAjIHRocm93cyBhIEtlcm5lbDo6U3lzdGVtOjpXZWI6OkV4Y2VwdGlvbgogICAgbXkgJURhdGEgPSAkU2Vzc2lvbk9iamVjdC0+R2V0U2Vzc2lvbklERGF0YSgKICAgICAgICBTZXNzaW9uSUQgPT4gJFBhcmFte1Nlc3Npb25JRH0sCiAgICApOwogICAgJERhdGF7VXNlclRpbWVab25lfSA9ICRTZWxmLT5fVXNlclRpbWVab25lR2V0KCVEYXRhKTsKICAgICRLZXJuZWw6Ok9NLT5PYmplY3RQYXJhbUFkZCgKICAgICAgICAnS2VybmVsOjpPdXRwdXQ6OkhUTUw6OkxheW91dCcgPT4gewogICAgICAgICAgICAlUGFyYW0sCiAgICAgICAgICAgICVEYXRhLAogICAgICAgIH0sCiAgICApOwoKICAgIG15ICRMYXlvdXRPYmplY3QgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6Ok91dHB1dDo6SFRNTDo6TGF5b3V0Jyk7CgogICAgJExheW91dE9iamVjdC0+Q3VzdG9tZXJGYXRhbEVycm9yKAogICAgICAgIENvbW1lbnQgPT4gVHJhbnNsYXRhYmxlKCdQbGVhc2UgY29udGFjdCB0aGUgYWRtaW5pc3RyYXRvci4nKSwKICAgICk7Cn0KCj1oZWFkMiBSZXNwb25zZSgpCgpHZW5lcmF0ZSBhIFBTR0kgUmVzcG9uc2Ugb2JqZWN0IGZyb20gdGhlIGNvbnRlbnQgZ2VuZXJhdGVkIGJ5IEM8Q29udGVudCgpPi4KCiAgICBteSAkUmVzcG9uc2UgPSAkSW50ZXJmYWNlLT5SZXNwb25zZSgpOwoKPWN1dAoKc3ViIFJlc3BvbnNlIHsKICAgIG15ICgkU2VsZikgPSBAXzsKCiAgICAjIE5vdGUgdGhhdCB0aGUgbGF5b3V0IG9iamVjdCBtdXN0bid0IGJlIGNyZWF0ZWQgYmVmb3JlIGNhbGxpbmcgQ29udGVudCgpLgogICAgIyBUaGlzIGlzIGJlY2F1c2UgQ29udGVudCgpIG1pZ2h0IHdhbnQgdG8gc2V0IG9iamVjdCBwYXJhbXMgYmVmb3JlIHRoZSBpbml0aWFsIGNyZWF0aW9ucy4KICAgICMgQSBub3RhYmxlIGV4YW1wbGUgaXMgdGhlIFNldENvb2tpZXMgcGFyYW1ldGVyLgogICAgbXkgJENvbnRlbnQgPSAkU2VsZi0+Q29udGVudCgpOwoKICAgICMgVGhlIGZpbHRlcmVkIGNvbnRlbnQgaXMgYSBzdHJpbmcsIHJlZ2FyZGxlc3Mgb2Ygd2hldGhlciB0aGUgb3JpZ2luYWwgY29udGVudCBpcwogICAgIyBhIHN0cmluZywgYW4gYXJyYXkgcmVmZXJlbmNlLCBvciBhIGZpbGUgaGFuZGxlLgogICAgbXkgJExheW91dE9iamVjdCA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6T3V0cHV0OjpIVE1MOjpMYXlvdXQnKTsKICAgICRDb250ZW50ID0gJExheW91dE9iamVjdC0+QXBwbHlPdXRwdXRGaWx0ZXJzKCBPdXRwdXQgPT4gJENvbnRlbnQgKTsKCiAgICAjIFRoZSBIVFRQIGhlYWRlcnMgb2YgdGhlIE9UT0JPIHdlYiByZXNwb25zZSBvYmplY3QgYWxyZWFkeSBoYXZlIGJlZW4gc2V0IHVwLgogICAgIyBFbmhhbmNlIGl0IHdpdGggdGhlIEhUVFAgc3RhdHVzIGNvZGUgYW5kIHRoZSBjb250ZW50LgogICAgcmV0dXJuICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpXZWI6OlJlc3BvbnNlJyktPkZpbmFsaXplKCBDb250ZW50ID0+ICRDb250ZW50ICk7Cn0KCj1iZWdpbiBJbnRlcm5hbDoKCj1oZWFkMiBfU3RvcmVGYWlsZWRMb2dpbnMoKQoKPWN1dAoKc3ViIF9TdG9yZUZhaWxlZExvZ2lucyB7CiAgICBteSAoICRTZWxmLCAlUGFyYW0gKSA9IEBfOwogICAgbXkgJEN1cnJlbnRUaW1lT2JqZWN0ICAgPSAkS2VybmVsOjpPTS0+Q3JlYXRlKCdLZXJuZWw6OlN5c3RlbTo6RGF0ZVRpbWUnKTsKICAgIG15ICRDdXJyZW50TmV3VGltZVN0YW1wID0gJEN1cnJlbnRUaW1lT2JqZWN0LT5Ub1N0cmluZygpOwogICAgbXkgJENhY2hlT2JqZWN0ICAgICAgICAgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6Q2FjaGUnKTsKICAgIG15ICRDaGVja0hhc2ggICAgICAgICAgID0gJENhY2hlT2JqZWN0LT5HZXQoCiAgICAgICAgVHlwZSA9PiAnRmFpbGVkTG9naW5zQ3VzdG9tZXInLAogICAgICAgIEtleSAgPT4gJFBhcmFte1Bvc3RVc2VyfSwKICAgICk7CgogICAgaWYgKCAhJENoZWNrSGFzaCApIHsKICAgICAgICAkQ2FjaGVPYmplY3QtPlNldCgKICAgICAgICAgICAgVHlwZSAgPT4gJ0ZhaWxlZExvZ2luc0N1c3RvbWVyJywKICAgICAgICAgICAgS2V5ICAgPT4gJFBhcmFte1Bvc3RVc2VyfSwKICAgICAgICAgICAgVmFsdWUgPT4gWyRDdXJyZW50TmV3VGltZVN0YW1wXSwKICAgICAgICAgICAgVFRMICAgPT4gJFBhcmFte1ByZXZlbnRCcnV0ZUZvcmNlQ29uZmlnfXtLZWVwQ2FjaGVEdXJhdGlvbn0sCiAgICAgICAgKTsKCiAgICAgICAgcmV0dXJuIDA7CiAgICB9CgogICAgbXkgQExvZ2luVHJ5QXJyYXkgPSBAeyRDaGVja0hhc2h9OwoKICAgICMgZGVsZXRlIGV4cGlyZWQgY2FjaGUgZW50cmllcwogICAgTE9HSU46CiAgICBmb3IgbXkgJExvZ2luVGltZSAoIEB7JENoZWNrSGFzaH0gKSB7CiAgICAgICAgbXkgJExvZ2luVGltZU9iamVjdCA9ICRLZXJuZWw6Ok9NLT5DcmVhdGUoCiAgICAgICAgICAgICdLZXJuZWw6OlN5c3RlbTo6RGF0ZVRpbWUnLAogICAgICAgICAgICBPYmplY3RQYXJhbXMgPT4gewogICAgICAgICAgICAgICAgU3RyaW5nID0+ICRMb2dpblRpbWUsCiAgICAgICAgICAgIH0sCiAgICAgICAgKTsKICAgICAgICBteSAkT2Zmc2V0ID0gJEN1cnJlbnRUaW1lT2JqZWN0LT5EZWx0YSgKICAgICAgICAgICAgRGF0ZVRpbWVPYmplY3QgPT4gJExvZ2luVGltZU9iamVjdCwKICAgICAgICApOwoKICAgICAgICBpZiAoICRPZmZzZXQtPntBYnNvbHV0ZVNlY29uZHN9ID4gJFBhcmFte1ByZXZlbnRCcnV0ZUZvcmNlQ29uZmlnfS0+e0tlZXBDYWNoZUR1cmF0aW9ufSApIHsKICAgICAgICAgICAgc2hpZnQgQExvZ2luVHJ5QXJyYXk7CiAgICAgICAgfQogICAgICAgIGVsc2UgewogICAgICAgICAgICBsYXN0IExPR0lOOwogICAgICAgIH0KICAgIH0KCiAgICAjIGFkZCBuZXcgZmFpbGVkIGxvZ2luIHRvIGNhY2hlCiAgICBwdXNoIEBMb2dpblRyeUFycmF5LCAkQ3VycmVudE5ld1RpbWVTdGFtcDsKICAgICRDYWNoZU9iamVjdC0+U2V0KAogICAgICAgIFR5cGUgID0+ICdGYWlsZWRMb2dpbnNDdXN0b21lcicsCiAgICAgICAgS2V5ICAgPT4gJFBhcmFte1Bvc3RVc2VyfSwKICAgICAgICBWYWx1ZSA9PiBcQExvZ2luVHJ5QXJyYXksCiAgICAgICAgVFRMICAgPT4gJFBhcmFte1ByZXZlbnRCcnV0ZUZvcmNlQ29uZmlnfXtLZWVwQ2FjaGVEdXJhdGlvbn0sCiAgICApOwoKICAgIGlmICggc2NhbGFyIEBMb2dpblRyeUFycmF5ID49ICRQYXJhbXtQcmV2ZW50QnJ1dGVGb3JjZUNvbmZpZ317TWF4QXR0ZW1wdH0gKSB7CiAgICAgICAgJENhY2hlT2JqZWN0LT5TZXQoCiAgICAgICAgICAgIFR5cGUgID0+ICdCYW5uZWRMb2dpbnNDdXN0b21lcicsCiAgICAgICAgICAgIEtleSAgID0+ICRQYXJhbXtQb3N0VXNlcn0sCiAgICAgICAgICAgIFZhbHVlID0+ICRDdXJyZW50TmV3VGltZVN0YW1wLAogICAgICAgICAgICBUVEwgICA9PiAkUGFyYW17UHJldmVudEJydXRlRm9yY2VDb25maWd9e0JhbkR1cmF0aW9ufSwKICAgICAgICApOwogICAgICAgIHJldHVybiAxOwogICAgfQoKICAgIHJldHVybiAwOwp9CgpzdWIgX0NoZWNrQW5kUmVtb3ZlRnJvbUJhbm5lZExpc3QgewogICAgbXkgKCAkU2VsZiwgJVBhcmFtICkgPSBAXzsKCiAgICAjIGdldCBjYWNoZQogICAgbXkgJENhY2hlT2JqZWN0ID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkNhY2hlJyk7CgogICAgbXkgJEJhblRpbWUgPSAkQ2FjaGVPYmplY3QtPkdldCgKICAgICAgICBUeXBlID0+ICdCYW5uZWRMb2dpbnNDdXN0b21lcicsCiAgICAgICAgS2V5ICA9PiAkUGFyYW17UG9zdFVzZXJ9LAogICAgKTsKCiAgICBpZiAoICEkQmFuVGltZSApIHsKICAgICAgICByZXR1cm4gKAogICAgICAgICAgICBCYW5uZWQgPT4gMCwKICAgICAgICApOwogICAgfQoKICAgICMgY2FsY3VsYXRlIGVsYXBzZWQgdGltZQogICAgbXkgJEN1clRpbWVPYmplY3QgPSAkS2VybmVsOjpPTS0+Q3JlYXRlKCdLZXJuZWw6OlN5c3RlbTo6RGF0ZVRpbWUnKTsKICAgIG15ICRCYW5UaW1lT2JqZWN0ID0gJEtlcm5lbDo6T00tPkNyZWF0ZSgKICAgICAgICAnS2VybmVsOjpTeXN0ZW06OkRhdGVUaW1lJywKICAgICAgICBPYmplY3RQYXJhbXMgPT4gewogICAgICAgICAgICBTdHJpbmcgPT4gJEJhblRpbWUsCiAgICAgICAgfSwKICAgICk7CiAgICBteSAkT2Zmc2V0ID0gJEN1clRpbWVPYmplY3QtPkRlbHRhKAogICAgICAgIERhdGVUaW1lT2JqZWN0ID0+ICRCYW5UaW1lT2JqZWN0LAogICAgKTsKCiAgICAjIGlmIHRoZSBiYW4gZHVyYXRpb24gaGFzIGJlZW4gc3VycGFzc2VkLCBkZWxldGUgdGhlIGNhY2hlIGVudHJ5CiAgICBpZiAoICRPZmZzZXQtPntBYnNvbHV0ZVNlY29uZHN9ID4gJFBhcmFte1ByZXZlbnRCcnV0ZUZvcmNlQ29uZmlnfXtCYW5EdXJhdGlvbn0gKSB7CiAgICAgICAgJENhY2hlT2JqZWN0LT5EZWxldGUoCiAgICAgICAgICAgIFR5cGUgPT4gJ0Jhbm5lZExvZ2luc0N1c3RvbWVyJywKICAgICAgICAgICAgS2V5ICA9PiAkUGFyYW17UG9zdFVzZXJ9LAogICAgICAgICk7CiAgICAgICAgcmV0dXJuICgKICAgICAgICAgICAgQmFubmVkID0+IDAsCiAgICAgICAgKTsKICAgIH0KCiAgICByZXR1cm4gKAogICAgICAgIEJhbm5lZCAgICAgICA9PiAxLAogICAgICAgIFJlc2lkdWFsVGltZSA9PiAkUGFyYW17UHJldmVudEJydXRlRm9yY2VDb25maWd9e0JhbkR1cmF0aW9ufSAtICRPZmZzZXQtPntBYnNvbHV0ZVNlY29uZHN9LAogICAgKTsKfQoKPWhlYWQyIF9DaGVja01vZHVsZVBlcm1pc3Npb24oKQoKbW9kdWxlIHBlcm1pc3Npb24gY2hlY2sKCiAgICAoJEFjY2Vzc1JvLCAkQWNjZXNzUncgPSAkQXV0b1Jlc3BvbnNlT2JqZWN0LT5fQ2hlY2tNb2R1bGVQZXJtaXNzaW9uKAogICAgICAgIE1vZHVsZVJlZyA9PiAkTW9kdWxlUmVnLAogICAgICAgICVVc2VyRGF0YSwKICAgICk7Cgo9Y3V0CgpzdWIgX0NoZWNrTW9kdWxlUGVybWlzc2lvbiB7CiAgICBteSAoICRTZWxmLCAlUGFyYW0gKSA9IEBfOwoKICAgIG15ICRBY2Nlc3NSbyA9IDA7CiAgICBteSAkQWNjZXNzUncgPSAwOwoKICAgIFBFUk1JU1NJT046CiAgICBmb3IgbXkgJFBlcm1pc3Npb24gKHF3KEdyb3VwUm8gR3JvdXApKSB7CiAgICAgICAgbXkgJEFjY2Vzc09rID0gMDsKICAgICAgICBteSAkR3JvdXAgICAgPSAkUGFyYW17TW9kdWxlUmVnfS0+eyRQZXJtaXNzaW9ufTsKCiAgICAgICAgbmV4dCBQRVJNSVNTSU9OIGlmICEkR3JvdXA7CgogICAgICAgIG15ICRHcm91cE9iamVjdCA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpDdXN0b21lckdyb3VwJyk7CgogICAgICAgIGlmICggSXNBcnJheVJlZldpdGhEYXRhKCRHcm91cCkgKSB7CiAgICAgICAgICAgIEdST1VQOgogICAgICAgICAgICBmb3IgbXkgJEl0ZW0gKCBAeyRHcm91cH0gKSB7CiAgICAgICAgICAgICAgICBuZXh0IEdST1VQIGlmICEkSXRlbTsKICAgICAgICAgICAgICAgIG5leHQgR1JPVVAgaWYgISRHcm91cE9iamVjdC0+UGVybWlzc2lvbkNoZWNrKAogICAgICAgICAgICAgICAgICAgIFVzZXJJRCAgICA9PiAkUGFyYW17VXNlcklEfSwKICAgICAgICAgICAgICAgICAgICBHcm91cE5hbWUgPT4gJEl0ZW0sCiAgICAgICAgICAgICAgICAgICAgVHlwZSAgICAgID0+ICRQZXJtaXNzaW9uIGVxICdHcm91cFJvJyA/ICdybycgOiAncncnLAogICAgICAgICAgICAgICAgKTsKCiAgICAgICAgICAgICAgICAkQWNjZXNzT2sgPSAxOwogICAgICAgICAgICAgICAgbGFzdCBHUk9VUDsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBlbHNlIHsKICAgICAgICAgICAgbXkgJEhhc1Blcm1pc3Npb24gPSAkR3JvdXBPYmplY3QtPlBlcm1pc3Npb25DaGVjaygKICAgICAgICAgICAgICAgIFVzZXJJRCAgICA9PiAkUGFyYW17VXNlcklEfSwKICAgICAgICAgICAgICAgIEdyb3VwTmFtZSA9PiAkR3JvdXAsCiAgICAgICAgICAgICAgICBUeXBlICAgICAgPT4gJFBlcm1pc3Npb24gZXEgJ0dyb3VwUm8nID8gJ3JvJyA6ICdydycsCiAgICAgICAgICAgICk7CiAgICAgICAgICAgIGlmICgkSGFzUGVybWlzc2lvbikgewogICAgICAgICAgICAgICAgJEFjY2Vzc09rID0gMTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBpZiAoICRQZXJtaXNzaW9uIGVxICdHcm91cCcgJiYgJEFjY2Vzc09rICkgewogICAgICAgICAgICAkQWNjZXNzUm8gPSAxOwogICAgICAgICAgICAkQWNjZXNzUncgPSAxOwogICAgICAgIH0KICAgICAgICBlbHNpZiAoICRQZXJtaXNzaW9uIGVxICdHcm91cFJvJyAmJiAkQWNjZXNzT2sgKSB7CiAgICAgICAgICAgICRBY2Nlc3NSbyA9IDE7CiAgICAgICAgfQogICAgfQoKICAgIHJldHVybiAoICRBY2Nlc3NSbywgJEFjY2Vzc1J3ICk7Cn0KCj1oZWFkMiBfVXNlclRpbWVab25lR2V0KCkKCkdldCB0aW1lIHpvbmUgZm9yIHRoZSBjdXJyZW50IHVzZXIuIFRoaXMgZnVuY3Rpb24gd2lsbCB2YWxpZGF0ZSBwYXNzZWQgdGltZSB6b25lIHBhcmFtZXRlciBhbmQgcmV0dXJuIGRlZmF1bHQgdXNlciB0aW1lCnpvbmUgaWYgaXQncyBub3QgdmFsaWQuCgogICAgbXkgJFVzZXJUaW1lWm9uZSA9ICRTZWxmLT5fVXNlclRpbWVab25lR2V0KAogICAgICAgIFVzZXJUaW1lWm9uZSA9PiAnRXVyb3BlL0JlcmxpbicsCiAgICApOwoKPWN1dAoKc3ViIF9Vc2VyVGltZVpvbmVHZXQgewogICAgbXkgKCAkU2VsZiwgJVBhcmFtICkgPSBAXzsKCiAgICBteSAkVXNlclRpbWVab25lOwoKICAgICMgUmV0dXJuIHBhc3NlZCB0aW1lIHpvbmUgb25seSBpZiBpdCdzIHZhbGlkLiBJdCBjYW4gaGFwcGVuIHRoYXQgdXNlciBwcmVmZXJlbmNlcyBvciBzZXNzaW9uIHN0b3JlIGFuIG9sZC1zdHlsZQogICAgIyAgIG9mZnNldCB3aGljaCBpcyBub3QgdmFsaWQgYW55bW9yZS4gSW4gdGhpcyBjYXNlLCByZXR1cm4gdGhlIGRlZmF1bHQgdmFsdWUuCiAgICAjICAgUGxlYXNlIHNlZSBidWcjMTMzNzQgZm9yIG1vcmUgaW5mb3JtYXRpb24uCiAgICBpZiAoCiAgICAgICAgJFBhcmFte1VzZXJUaW1lWm9uZX0KICAgICAgICAmJiBLZXJuZWw6OlN5c3RlbTo6RGF0ZVRpbWUtPklzVGltZVpvbmVWYWxpZCggVGltZVpvbmUgPT4gJFBhcmFte1VzZXJUaW1lWm9uZX0gKQogICAgICAgICkKICAgIHsKICAgICAgICAkVXNlclRpbWVab25lID0gJFBhcmFte1VzZXJUaW1lWm9uZX07CiAgICB9CgogICAgJFVzZXJUaW1lWm9uZSB8fD0gS2VybmVsOjpTeXN0ZW06OkRhdGVUaW1lLT5Vc2VyRGVmYXVsdFRpbWVab25lR2V0KCk7CgogICAgcmV0dXJuICRVc2VyVGltZVpvbmU7Cn0KCj1lbmQgSW50ZXJuYWw6Cgo9Y3V0CgoxOwo=
PD94bWwgdmVyc2lvbj0iMS4wIiBlbmNvZGluZz0idXRmLTgiID8+CjxvdG9ib19jb25maWcgdmVyc2lvbj0iMi4wIiBpbml0PSJBcHBsaWNhdGlvbiI+CiAgICA8U2V0dGluZyBOYW1lPSJPbmVUaW1lQXV0aDo6Q3VzdG9tZXJFcnJvck1lc3NhZ2VSZWZyZXNoRmFpbGVkIiBSZXF1aXJlZD0iMCIgVmFsaWQ9IjEiPgogICAgICAgIDxEZXNjcmlwdGlvbiBUcmFuc2xhdGFibGU9IjEiPlRoZSBtZXNzYWdlIHdoaWNoIHdpbGwgYmUgc2VudCB0byB0aGUgY3VzdG9tZXIgaWYgYSBsaW5rIGNvdWxkIG5vdCBiZSBnZW5lcmF0ZWQuPC9EZXNjcmlwdGlvbj4KICAgICAgICA8TmF2aWdhdGlvbj5Db3JlOjpBdXRoOjpDdXN0b21lcjwvTmF2aWdhdGlvbj4KICAgICAgICA8VmFsdWU+CiAgICAgICAgICAgIDxJdGVtIFZhbHVlVHlwZT0iU3RyaW5nIiBWYWx1ZVJlZ2V4PSIiPkxpbmsga29ubnRlIG5pY2h0IGVyemV1Z3Qgd2VyZGVuLCBiaXR0ZSBzZW5kZW4gU2llIGVpbmUgZW1haWwgYW4gc3VwcG9ydEB3ZS5jb20uPC9JdGVtPgogICAgICAgIDwvVmFsdWU+CiAgICA8L1NldHRpbmc+CiAgICA8U2V0dGluZyBOYW1lPSJPbmVUaW1lQXV0aDo6Q3VzdG9tZXJFcnJvck1lc3NhZ2VMaW5rRXhwaXJlZCIgUmVxdWlyZWQ9IjAiIFZhbGlkPSIxIj4KICAgICAgICA8RGVzY3JpcHRpb24gVHJhbnNsYXRhYmxlPSIxIj5UaGUgbWVzc2FnZSB3aGljaCB0aGUgY3VzdG9tZXIgdXNlciB3aWxsIHNlZSBpZiBoZSB1c2VzIGFuIGludmFsaWQgdG9rZW4uPC9EZXNjcmlwdGlvbj4KICAgICAgICA8TmF2aWdhdGlvbj5Db3JlOjpBdXRoOjpDdXN0b21lcjwvTmF2aWdhdGlvbj4KICAgICAgICA8VmFsdWU+CiAgICAgICAgICAgIDxJdGVtIFZhbHVlVHlwZT0iU3RyaW5nIiBWYWx1ZVJlZ2V4PSIiPklociBMaW5rIHZlcndlaXN0IGF1ZiBrZWluIG5vY2ggZ8O8bHRpZ2VzIFRpY2tldC48L0l0ZW0+CiAgICAgICAgPC9WYWx1ZT4KICAgIDwvU2V0dGluZz4KICAgIDxTZXR0aW5nIE5hbWU9Ik9uZVRpbWVBdXRoOjpDdXN0b21lckVycm9yTWVzc2FnZVdyb25nTGluayIgUmVxdWlyZWQ9IjAiIFZhbGlkPSIxIj4KICAgICAgICA8RGVzY3JpcHRpb24gVHJhbnNsYXRhYmxlPSIxIj5UaGUgbWVzc2FnZSB3aGljaCB0aGUgY3VzdG9tZXIgdXNlciB3aWxsIHNlZSBpZiBoZSB1c2VzIGFuIG9sZCB0b2tlbiB3aXRoIGFuIGFjdGl2ZSBvbmUgYWxyZWFkeSBiZWluZyBwcmVzZW50LjwvRGVzY3JpcHRpb24+CiAgICAgICAgPE5hdmlnYXRpb24+Q29yZTo6QXV0aDo6Q3VzdG9tZXI8L05hdmlnYXRpb24+CiAgICAgICAgPFZhbHVlPgogICAgICAgICAgICA8SXRlbSBWYWx1ZVR5cGU9IlN0cmluZyIgVmFsdWVSZWdleD0iIj5BdXMgU2ljaGVyaGVpdHNncsO8bmRlbiBtw7xzc2VuIFNpZSBkZW4gbmV1ZXN0ZW4gSWhuZW4genVnZXNhbmR0ZW4gTGluayBudXR6ZW4gdW0gYXVmIGRpZXNlcyBUaWNrZXQgenV6dWdyZWlmZW4uPC9JdGVtPgogICAgICAgIDwvVmFsdWU+CiAgICA8L1NldHRpbmc+CiAgICA8U2V0dGluZyBOYW1lPSJPbmVUaW1lQXV0aDo6Q3VzdG9tZXJFcnJvck1lc3NhZ2VOZXdMaW5rIiBSZXF1aXJlZD0iMCIgVmFsaWQ9IjEiPgogICAgICAgIDxEZXNjcmlwdGlvbiBUcmFuc2xhdGFibGU9IjEiPlRoZSBtZXNzYWdlIHdoaWNoIHRoZSBjdXN0b21lciB1c2VyIHdpbGwgc2VlIGlmIGEgbmV3IG9uZSBpcyBzZW50IHRvIGhpcyBlbWFpbCBhZGRyZXNzLjwvRGVzY3JpcHRpb24+CiAgICAgICAgPE5hdmlnYXRpb24+Q29yZTo6QXV0aDo6Q3VzdG9tZXI8L05hdmlnYXRpb24+CiAgICAgICAgPFZhbHVlPgogICAgICAgICAgICA8SXRlbSBWYWx1ZVR5cGU9IlN0cmluZyIgVmFsdWVSZWdleD0iIj5JaHJlIFNlc3Npb24gaXN0IGxlaWRlciBhYmdlbGF1ZmVuIC0gZWluIG5ldWVyIExpbmsgd3VyZGUgYW4gSWhyZSBFbWFpbC1BZHJlc3NlIGdlc2VuZGV0LjwvSXRlbT4KICAgICAgICA8L1ZhbHVlPgogICAgPC9TZXR0aW5nPgogICAgPFNldHRpbmcgTmFtZT0iT25lVGltZUF1dGg6OkFjY2Vzc0RheXNBZnRlckNsb3NlIiBSZXF1aXJlZD0iMCIgVmFsaWQ9IjEiPgogICAgICAgIDxEZXNjcmlwdGlvbiBUcmFuc2xhdGFibGU9IjEiPlRoZSBudW1iZXIgb2YgZGF5cyBjdXN0b21lciB1c2VycyBjYW4gdXNlIGRpcmVjdCBsaW5rcyB0byBvcGVuIHRpY2tldHMgYWZ0ZXIgdGhleSBhcmUgY2xvc2VkLjwvRGVzY3JpcHRpb24+CiAgICAgICAgPE5hdmlnYXRpb24+Q29yZTo6QXV0aDo6Q3VzdG9tZXI8L05hdmlnYXRpb24+CiAgICAgICAgPFZhbHVlPgogICAgICAgICAgICA8SXRlbSBWYWx1ZVR5cGU9IlN0cmluZyIgVmFsdWVSZWdleD0iXlxkKiQiPjE0PC9JdGVtPgogICAgICAgIDwvVmFsdWU+CiAgICA8L1NldHRpbmc+CiAgICA8U2V0dGluZyBOYW1lPSJPbmVUaW1lQXV0aDo6VG9rZW5SZWZyZXNoTm90aWZpY2F0aW9uSUQiIFJlcXVpcmVkPSIwIiBWYWxpZD0iMCI+CiAgICAgICAgPERlc2NyaXB0aW9uIFRyYW5zbGF0YWJsZT0iMSI+U2VuZCB0aGUgdGV4dCBvZiBhIG5vdGlmaWNhdGlvbiB0byB0aGUgY3VzdG9tZXIgdXNlciBpZiBoZSByZWZyZXNocyBoaXMgdG9rZW4uPC9EZXNjcmlwdGlvbj4KICAgICAgICA8TmF2aWdhdGlvbj5Db3JlOjpBdXRoOjpDdXN0b21lcjwvTmF2aWdhdGlvbj4KICAgICAgICA8VmFsdWU+CiAgICAgICAgICAgIDxJdGVtIFZhbHVlVHlwZT0iU3RyaW5nIiBWYWx1ZVJlZ2V4PSJeXGQqJCI+MDwvSXRlbT4KICAgICAgICA8L1ZhbHVlPgogICAgPC9TZXR0aW5nPgogICAgPFNldHRpbmcgTmFtZT0iUG9zdE1hc3Rlcjo6UHJlRmlsdGVyTW9kdWxlIyMjMDAwLUNyZWF0ZUN1c3RvbWVyVXNlciIgUmVxdWlyZWQ9IjAiIFZhbGlkPSIwIj4KICAgICAgICA8RGVzY3JpcHRpb24gVHJhbnNsYXRhYmxlPSIxIj5DcmVhdGUgYSBDdXN0b21lclVzZXIgaW4gYSBzcGVjaWZpYyBiYWNrZW5kIGlmIG5vbmUgZXhpc3RzIGZvciB0aGUgc2VuZGVyIGVtYWlsLiBDdXN0b21lckhlYWRlclNwb29mUHJvdGVjdGlvbiBzZXRzIChhbmQgcG9zc2libHkgb3ZlcndyaXRlcykgdGhlIFgtT1RPQk8tQ3VzdG9tZXIgaGVhZGVyIGlmIGEgY3VzdG9tZXIgdXNlciBleGlzdHMgZm9yIGFuIGVtYWlsIGFkZHJlc3MgdG8gcHJldmVudCBzcG9vZmluZy4gQ3VzdG9tZXJVc2VyQmFja2VuZCBkZWZpbmVzIHRoZSBiYWNrZW5kIGluIHdoaWNoIHRoZSBDdXN0b21lclVzZXIgd2lsbCBiZSBjcmVhdGVkLCBpZiBTZXRDaGVja0JveE5hbWUgaXMgc2V0IHRvIHRoZSBuYW1lIG9mIGEgZHluYW1pYyBmaWVsZCBvZiB0aGUgdHlwZSBjaGVja2JveCwgaXQgd2lsbCBiZSBzZXQgdG8gY2hlY2tlZCBmb3IgdGlja2V0cyBjcmVhdGVkIGJ5IGN1c3RvbWVyIHVzZXJzIGZyb20gdGhpcyBiYWNrZW5kLjwvRGVzY3JpcHRpb24+CiAgICAgICAgPE5hdmlnYXRpb24+Q29yZTo6RW1haWw6OlBvc3RNYXN0ZXI8L05hdmlnYXRpb24+CiAgICAgICAgPFZhbHVlPgogICAgICAgICAgICA8SGFzaD4KICAgICAgICAgICAgICAgIDxJdGVtIEtleT0iTW9kdWxlIj5LZXJuZWw6OlN5c3RlbTo6UG9zdE1hc3Rlcjo6RmlsdGVyOjpDcmVhdGVOZXdDdXN0b21lclVzZXI8L0l0ZW0+CiAgICAgICAgICAgICAgICA8SXRlbSBLZXk9IkN1c3RvbWVySGVhZGVyU3Bvb2ZQcm90ZWN0aW9uIj4xPC9JdGVtPgogICAgICAgICAgICAgICAgPEl0ZW0gS2V5PSJDdXN0b21lclVzZXJCYWNrZW5kIj48L0l0ZW0+CiAgICAgICAgICAgICAgICA8SXRlbSBLZXk9IlNldENoZWNrQm94TmFtZSI+PC9JdGVtPgogICAgICAgICAgICA8L0hhc2g+CiAgICAgICAgPC9WYWx1ZT4KICAgIDwvU2V0dGluZz4KICAgIDxTZXR0aW5nIE5hbWU9IkRhZW1vbjo6U2NoZWR1bGVyQ3JvblRhc2tNYW5hZ2VyOjpUYXNrIyMjRGVsZXRlRXhwaXJlZE9UQVRva2VucyIgUmVxdWlyZWQ9IjAiIFZhbGlkPSIxIiBDb25maWdMZXZlbD0iMTAwIj4KICAgICAgICA8RGVzY3JpcHRpb24gVHJhbnNsYXRhYmxlPSIxIj5EZWxldGVzIE9UQSBUb2tlbnMgb2YgY2xvc2VkIHRpY2tldHMuPC9EZXNjcmlwdGlvbj4KICAgICAgICA8TmF2aWdhdGlvbj5EYWVtb246OlNjaGVkdWxlckNyb25UYXNrTWFuYWdlcjo6VGFzazwvTmF2aWdhdGlvbj4KICAgICAgICA8VmFsdWU+CiAgICAgICAgICAgIDxIYXNoPgogICAgICAgICAgICAgICAgPEl0ZW0gS2V5PSJUYXNrTmFtZSI+RGVsZXRlRXhwaXJlZE9UQVRva2VuczwvSXRlbT4KICAgICAgICAgICAgICAgIDxJdGVtIEtleT0iU2NoZWR1bGUiPjAgNCAqICogKjwvSXRlbT4KICAgICAgICAgICAgICAgIDxJdGVtIEtleT0iTW9kdWxlIj5LZXJuZWw6OlN5c3RlbTo6Q3VzdG9tZXJBdXRoOjpPbmVUaW1lQXV0aExpbms8L0l0ZW0+CiAgICAgICAgICAgICAgICA8SXRlbSBLZXk9IkZ1bmN0aW9uIj5EZWFjdGl2YXRlQ2xvc2VkVGlja2V0czwvSXRlbT4KICAgICAgICAgICAgICAgIDxJdGVtIEtleT0iTWF4aW11bVBhcmFsbGVsSW5zdGFuY2VzIj4xPC9JdGVtPgogICAgICAgICAgICAgICAgPEl0ZW0gS2V5PSJQYXJhbXMiPgogICAgICAgICAgICAgICAgICAgIDxBcnJheT4KICAgICAgICAgICAgICAgICAgICA8L0FycmF5PgogICAgICAgICAgICAgICAgPC9JdGVtPgogICAgICAgICAgICA8L0hhc2g+CiAgICAgICAgPC9WYWx1ZT4KICAgIDwvU2V0dGluZz4KPC9vdG9ib19jb25maWc+Cg==
IyAtLQojIE9UT0JPIGlzIGEgd2ViLWJhc2VkIHRpY2tldGluZyBzeXN0ZW0gZm9yIHNlcnZpY2Ugb3JnYW5pc2F0aW9ucy4KIyAtLQojIENvcHlyaWdodCAoQykgMjAwMS0yMDIwIE9UUlMgQUcsIGh0dHBzOi8vb3Rycy5jb20vCiMgQ29weXJpZ2h0IChDKSAyMDE5LTIwMjEgUm90aGVyIE9TUyBHbWJILCBodHRwczovL290b2JvLmRlLwojIC0tCiMgVGhpcyBwcm9ncmFtIGlzIGZyZWUgc29mdHdhcmU6IHlvdSBjYW4gcmVkaXN0cmlidXRlIGl0IGFuZC9vciBtb2RpZnkgaXQgdW5kZXIKIyB0aGUgdGVybXMgb2YgdGhlIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlIGFzIHB1Ymxpc2hlZCBieSB0aGUgRnJlZSBTb2Z0d2FyZQojIEZvdW5kYXRpb24sIGVpdGhlciB2ZXJzaW9uIDMgb2YgdGhlIExpY2Vuc2UsIG9yIChhdCB5b3VyIG9wdGlvbikgYW55IGxhdGVyIHZlcnNpb24uCiMgVGhpcyBwcm9ncmFtIGlzIGRpc3RyaWJ1dGVkIGluIHRoZSBob3BlIHRoYXQgaXQgd2lsbCBiZSB1c2VmdWwsIGJ1dCBXSVRIT1VUCiMgQU5ZIFdBUlJBTlRZOyB3aXRob3V0IGV2ZW4gdGhlIGltcGxpZWQgd2FycmFudHkgb2YgTUVSQ0hBTlRBQklMSVRZIG9yIEZJVE5FU1MKIyBGT1IgQSBQQVJUSUNVTEFSIFBVUlBPU0UuIFNlZSB0aGUgR05VIEdlbmVyYWwgUHVibGljIExpY2Vuc2UgZm9yIG1vcmUgZGV0YWlscy4KIyBZb3Ugc2hvdWxkIGhhdmUgcmVjZWl2ZWQgYSBjb3B5IG9mIHRoZSBHTlUgR2VuZXJhbCBQdWJsaWMgTGljZW5zZQojIGFsb25nIHdpdGggdGhpcyBwcm9ncmFtLiBJZiBub3QsIHNlZSA8aHR0cHM6Ly93d3cuZ251Lm9yZy9saWNlbnNlcy8+LgojIC0tCgpwYWNrYWdlIEtlcm5lbDo6U3lzdGVtOjpDb25zb2xlOjpDb21tYW5kOjpNYWludDo6Q3VzdG9tZXJBdXRoOjpEZWxldGVFeHBpcmVkT1RBVG9rZW5zOwoKdXNlIHN0cmljdDsKdXNlIHdhcm5pbmdzOwoKdXNlIHBhcmVudCBxdyhLZXJuZWw6OlN5c3RlbTo6Q29uc29sZTo6QmFzZUNvbW1hbmQpOwoKdXNlIEtlcm5lbDo6U3lzdGVtOjpWYXJpYWJsZUNoZWNrIHF3KDphbGwpOwoKb3VyIEBPYmplY3REZXBlbmRlbmNpZXMgPSAoCiAgICAnS2VybmVsOjpTeXN0ZW06OkN1c3RvbWVyQXV0aDo6T25lVGltZUF1dGhMaW5rJywKKTsKCnN1YiBDb25maWd1cmUgewogICAgbXkgKCAkU2VsZiwgJVBhcmFtICkgPSBAXzsKCiAgICAkU2VsZi0+RGVzY3JpcHRpb24oJ0RlbGV0ZXMgZXhwaXJlZCBPbmVUaW1lQXV0aGVudGlmaWNhdGlvblRva2Vucy4nKTsKCiAgICByZXR1cm47Cn0KCnN1YiBQcmVSdW4gewogICAgbXkgKCAkU2VsZiwgJVBhcmFtICkgPSBAXzsKCiAgICByZXR1cm47Cn0KCnN1YiBSdW4gewogICAgbXkgKCAkU2VsZiwgJVBhcmFtICkgPSBAXzsKCiAgICBteSAkU3VjY2VzcyA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpDdXN0b21lckF1dGg6Ok9uZVRpbWVBdXRoTGluaycpLT5EZWFjdGl2YXRlQ2xvc2VkVGlja2V0cygpOwoKICAgIGlmICgkU3VjY2VzcykgewogICAgICAgICRTZWxmLT5QcmludCgiPGdyZWVuPkRvbmUuPC9ncmVlbj5cblxuIik7CiAgICAgICAgcmV0dXJuICRTZWxmLT5FeGl0Q29kZU9rKCk7CiAgICB9CgogICAgJFNlbGYtPlByaW50RXJyb3IoIkZhaWxlZC5cblxuIik7CiAgICByZXR1cm4gJFNlbGYtPkV4aXRDb2RlRXJyb3IoKTsKfQoKMTsK
IyAtLQojIE9UT0JPIGlzIGEgd2ViLWJhc2VkIHRpY2tldGluZyBzeXN0ZW0gZm9yIHNlcnZpY2Ugb3JnYW5pc2F0aW9ucy4KIyAtLQojIENvcHlyaWdodCAoQykgMjAwMS0yMDIwIE9UUlMgQUcsIGh0dHBzOi8vb3Rycy5jb20vCiMgQ29weXJpZ2h0IChDKSAyMDE5LTIwMjEgUm90aGVyIE9TUyBHbWJILCBodHRwczovL290b2JvLmRlLwojIC0tCiMgVGhpcyBwcm9ncmFtIGlzIGZyZWUgc29mdHdhcmU6IHlvdSBjYW4gcmVkaXN0cmlidXRlIGl0IGFuZC9vciBtb2RpZnkgaXQgdW5kZXIKIyB0aGUgdGVybXMgb2YgdGhlIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlIGFzIHB1Ymxpc2hlZCBieSB0aGUgRnJlZSBTb2Z0d2FyZQojIEZvdW5kYXRpb24sIGVpdGhlciB2ZXJzaW9uIDMgb2YgdGhlIExpY2Vuc2UsIG9yIChhdCB5b3VyIG9wdGlvbikgYW55IGxhdGVyIHZlcnNpb24uCiMgVGhpcyBwcm9ncmFtIGlzIGRpc3RyaWJ1dGVkIGluIHRoZSBob3BlIHRoYXQgaXQgd2lsbCBiZSB1c2VmdWwsIGJ1dCBXSVRIT1VUCiMgQU5ZIFdBUlJBTlRZOyB3aXRob3V0IGV2ZW4gdGhlIGltcGxpZWQgd2FycmFudHkgb2YgTUVSQ0hBTlRBQklMSVRZIG9yIEZJVE5FU1MKIyBGT1IgQSBQQVJUSUNVTEFSIFBVUlBPU0UuIFNlZSB0aGUgR05VIEdlbmVyYWwgUHVibGljIExpY2Vuc2UgZm9yIG1vcmUgZGV0YWlscy4KIyBZb3Ugc2hvdWxkIGhhdmUgcmVjZWl2ZWQgYSBjb3B5IG9mIHRoZSBHTlUgR2VuZXJhbCBQdWJsaWMgTGljZW5zZQojIGFsb25nIHdpdGggdGhpcyBwcm9ncmFtLiBJZiBub3QsIHNlZSA8aHR0cHM6Ly93d3cuZ251Lm9yZy9saWNlbnNlcy8+LgojIC0tCgpwYWNrYWdlIEtlcm5lbDo6U3lzdGVtOjpDdXN0b21lckF1dGg6Ok9uZVRpbWVBdXRoTGluazsKCnVzZSBzdHJpY3Q7CnVzZSB3YXJuaW5nczsKdXNlIHV0Zjg7CgpvdXIgQE9iamVjdERlcGVuZGVuY2llcyA9ICgKICAgICdLZXJuZWw6OkNvbmZpZycsCiAgICAnS2VybmVsOjpTeXN0ZW06OkN1c3RvbWVyVXNlcicsCiAgICAnS2VybmVsOjpTeXN0ZW06OkRCJywKICAgICdLZXJuZWw6OlN5c3RlbTo6TG9nJywKKTsKCnN1YiBuZXcgewogICAgbXkgKCAkVHlwZSwgJVBhcmFtICkgPSBAXzsKCiAgICAjIGFsbG9jYXRlIG5ldyBoYXNoIGZvciBvYmplY3QKICAgIG15ICRTZWxmID0ge307CiAgICBibGVzcyggJFNlbGYsICRUeXBlICk7CgogICAgIyBnZXQgZGF0YWJhc2Ugb2JqZWN0CiAgICAkU2VsZi0+e0RCT2JqZWN0fSA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpEQicpOwogICAgCiAgICAkU2VsZi0+e1RhYmxlfSA9ICdvdGFfdG9rZW5zJzsKCiAgICByZXR1cm4gJFNlbGY7Cn0KCnN1YiBHZXRPcHRpb24gewogICAgbXkgKCAkU2VsZiwgJVBhcmFtICkgPSBAXzsKCiAgICAjIGNoZWNrIG5lZWRlZCBzdHVmZgogICAgaWYgKCAhJFBhcmFte1doYXR9ICkgewogICAgICAgICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpMb2cnKS0+TG9nKAogICAgICAgICAgICBQcmlvcml0eSA9PiAnZXJyb3InLAogICAgICAgICAgICBNZXNzYWdlICA9PiAiTmVlZCBXaGF0ISIKICAgICAgICApOwogICAgICAgIHJldHVybjsKICAgIH0KCiAgICAjIG1vZHVsZSBvcHRpb25zCiAgICBteSAlT3B0aW9uID0gKAogICAgICAgIFByZUF1dGggPT4gMCwKICAgICk7CgogICAgIyByZXR1cm4gb3B0aW9uCiAgICByZXR1cm4gJE9wdGlvbnsgJFBhcmFte1doYXR9IH07Cn0KCnN1YiBFeHRlbmRlZFBhcmFtTmFtZXMgewogICAgbXkgKCAkU2VsZiwgJVBhcmFtICkgPSBAXzsKICAgIAogICAgcmV0dXJuIHF3L09UQVRva2VuLzsKfQoKc3ViIEF1dGggewogICAgbXkgKCAkU2VsZiwgJVBhcmFtICkgPSBAXzsKCiAgICAjIGNoZWNrIG5lZWRlZCBzdHVmZgogICAgaWYgKCAhJFBhcmFte09UQVRva2VufSApIHsKICAgICAgICAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6TG9nJyktPkxvZygKICAgICAgICAgICAgUHJpb3JpdHkgPT4gJ2RlYnVnJywKICAgICAgICAgICAgTWVzc2FnZSAgPT4gIk5vIFRva2VuIHByb3ZpZGVkISIKICAgICAgICApOwogICAgICAgIHJldHVybjsKICAgIH0KCiAgICAkU2VsZi0+e0RCT2JqZWN0fS0+UHJlcGFyZSgKICAgICAgICBTUUwgPT4gIlNFTEVDVCB1c2VkLHVzZXIsdGlja2V0X251bWJlciBGUk9NICRTZWxmLT57VGFibGV9IFdIRVJFIHRva2VuID0gPyIsCiAgICAgICAgQmluZCA9PiBbIFwkUGFyYW17T1RBVG9rZW59IF0sCiAgICApOwoKICAgIG15IEBSb3cgPSAgJFNlbGYtPntEQk9iamVjdH0tPkZldGNocm93QXJyYXkoKTsKICAgIG15ICggJFVzZWQsICRVc2VyLCAkVGlja2V0TnVtYmVyICkgPSAoIDAgKTsKCiAgICBpZiAoIEBSb3cgKSB7CiAgICAgICAgKCAkVXNlZCwgJFVzZXIsICRUaWNrZXROdW1iZXIgKSA9IEBSb3c7CiAgICB9CgogICAgaWYgKCAhJFVzZWQgfHwgISRVc2VyICkgewogICAgICAgIHJldHVybiB7CiAgICAgICAgICAgIEVycm9yID0+ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6Q29uZmlnJyktPkdldCgnT25lVGltZUF1dGg6OkN1c3RvbWVyRXJyb3JNZXNzYWdlTGlua0V4cGlyZWQnKSB8fCAnSWhyIExpbmsgdmVyd2Vpc3QgYXVmIGtlaW4gbm9jaCBnw7xsdGlnZXMgVGlja2V0LicsCiAgICAgICAgfQogICAgfQoKICAgIG15ICRDdXN0b21lclVzZXJPYmplY3QgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6Q3VzdG9tZXJVc2VyJyk7CgogICAgIyBzZW5kIG91dCBuZXcgZW1haWwgaWYgdGhlIHRpY2tldCBpcyBzdGlsbCBjb25zaWRlcmVkIGFjdGl2ZSBidXQgbm8gY3VycmVudCBsaW5rIGV4aXN0cwogICAgaWYgKCAkVXNlZCA9PSAxICkgewogICAgICAgICMgc3RvcmUgZmFpbGVkIGxvZ2luIGNvdW50CiAgICAgICAgbXkgJUN1c3RvbWVyRGF0YSA9ICRDdXN0b21lclVzZXJPYmplY3QtPkN1c3RvbWVyVXNlckRhdGFHZXQoIFVzZXIgPT4gJFBhcmFte1VzZXJ9ICk7CiAgICAgICAgaWYgKCVDdXN0b21lckRhdGEpIHsKICAgICAgICAgICAgbXkgJENvdW50ID0gJEN1c3RvbWVyRGF0YXtVc2VyTG9naW5GYWlsZWR9IHx8IDA7CiAgICAgICAgICAgICRDb3VudCsrOwogICAgICAgICAgICAkQ3VzdG9tZXJVc2VyT2JqZWN0LT5TZXRQcmVmZXJlbmNlcygKICAgICAgICAgICAgICAgIEtleSAgICA9PiAnVXNlckxvZ2luRmFpbGVkJywKICAgICAgICAgICAgICAgIFZhbHVlICA9PiAkQ291bnQsCiAgICAgICAgICAgICAgICBVc2VySUQgPT4gJEN1c3RvbWVyRGF0YXtVc2VyTG9naW59LAogICAgICAgICAgICApOwogICAgICAgIH0KCiAgICAgICAgIyBjaGVjayB3aGV0aGVyIGFjdGl2ZSBsb2dpbiBsaW5rIHN0aWxsIGV4aXN0cwogICAgICAgICRTZWxmLT57REJPYmplY3R9LT5QcmVwYXJlKAogICAgICAgICAgICBTUUwgPT4gIlNFTEVDVCB1c2VyIEZST00gJFNlbGYtPntUYWJsZX0gV0hFUkUgdGlja2V0X251bWJlciA9ID8gQU5EIHVzZWQgPSA/IiwKICAgICAgICAgICAgQmluZCA9PiBbIFwkVGlja2V0TnVtYmVyLCBcMiBdLAogICAgICAgICk7CgogICAgICAgIGlmICggJFNlbGYtPntEQk9iamVjdH0tPkZldGNocm93QXJyYXkoKSApIHsKICAgICAgICAgICAgJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkxvZycpLT5Mb2coCiAgICAgICAgICAgICAgICBQcmlvcml0eSA9PiAnZGVidWcnLAogICAgICAgICAgICAgICAgTWVzc2FnZSAgPT4gIkN1c3RvbWVyVXNlciAnJFVzZXInIHRyaWVkIHRvIGxvZyBpbiB3aXRoIGFuIG9sZCB0b2tlbi4gTmV3IHRva2VuIGV4aXN0cyAtIG5vdGhpbmcgdG8gZG8uIgogICAgICAgICAgICApOwoKICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgIEVycm9yID0+ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6Q29uZmlnJyktPkdldCgnT25lVGltZUF1dGg6OkN1c3RvbWVyRXJyb3JNZXNzYWdlV3JvbmdMaW5rJykgfHwgJ0F1cyBTaWNoZXJoZWl0c2dyw7xuZGVuIG3DvHNzZW4gU2llIGRlbiBuZXVlc3RlbiBJaG5lbiB6dWdlc2FuZHRlbiBMaW5rIG51dHplbiB1bSBhdWYgZGllc2VzIFRpY2tldCB6dXp1Z3JlaWZlbi4nLAogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIGVsc2UgewogICAgICAgICAgICAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6TG9nJyktPkxvZygKICAgICAgICAgICAgICAgIFByaW9yaXR5ID0+ICdkZWJ1ZycsCiAgICAgICAgICAgICAgICBNZXNzYWdlICA9PiAiQ3VzdG9tZXJVc2VyICckVXNlcicgdHJpZWQgdG8gbG9nIGluIHdpdGggYW4gb2xkIHRva2VuLiBObyBhY3RpdmUgdG9rZW4gbGVmdCAtIHNlbmRpbmcgYSBuZXcgb25lIHZpYSBtYWlsLiIKICAgICAgICAgICAgKTsKCiAgICAgICAgICAgICRTZWxmLT5TZW5kTmV3VG9rZW4oCiAgICAgICAgICAgICAgICBVc2VyICAgICAgICAgPT4gJFVzZXIsCiAgICAgICAgICAgICAgICBUaWNrZXROdW1iZXIgPT4gJFRpY2tldE51bWJlciwKICAgICAgICAgICAgKTsKCiAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgICBFcnJvciA9PiAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OkNvbmZpZycpLT5HZXQoJ09uZVRpbWVBdXRoOjpDdXN0b21lckVycm9yTWVzc2FnZU5ld0xpbmsnKSB8fCAnSWhyZSBTZXNzaW9uIGlzdCBsZWlkZXIgYWJnZWxhdWZlbiAtIGVpbiBuZXVlciBMaW5rIHd1cmRlIGFuIElocmUgRW1haWwtQWRyZXNzZSBnZXNlbmRldC4nLAogICAgICAgICAgICB9CiAgICAgICAgfQogICAgfQogICAgZWxzaWYgKCAkVXNlZCA9PSAyICkgewogICAgICAgICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpMb2cnKS0+TG9nKAogICAgICAgICAgICBQcmlvcml0eSA9PiAnZGVidWcnLAogICAgICAgICAgICBNZXNzYWdlICA9PiAiQ3VzdG9tZXJVc2VyICckVXNlcicgbG9nZ2VkIGluIHZpYSB0b2tlbi4iCiAgICAgICAgKTsKCiAgICAgICAgJFNlbGYtPkRlYWN0aXZhdGVUaWNrZXRUb2tlbnMoCiAgICAgICAgICAgIFRpY2tldE51bWJlciA9PiAkVGlja2V0TnVtYmVyLAogICAgICAgICk7CgogICAgICAgIHJldHVybiAkVXNlcjsKICAgIH0KCiAgICByZXR1cm47Cn0KCnN1YiBHZW5lcmF0ZVRva2VuIHsKICAgIG15ICggJFNlbGYsICVQYXJhbSApID0gQF87CgogICAgIyBjaGVjayBuZWVkZWQgc3R1ZmYKICAgIGZvciBteSAkTmVlZGVkICggcXcvVXNlciBUaWNrZXROdW1iZXIvICkgewogICAgICAgIGlmICggISRQYXJhbXskTmVlZGVkfSApIHsKICAgICAgICAgICAgJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkxvZycpLT5Mb2coCiAgICAgICAgICAgICAgICBQcmlvcml0eSA9PiAnZXJyb3InLAogICAgICAgICAgICAgICAgTWVzc2FnZSAgPT4gIk5lZWQgJE5lZWRlZCEiCiAgICAgICAgICAgICk7CiAgICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICB9CgogICAgIyBkZWFjdGl2YXRlIGFsbCBvdGhlciB0b2tlbnMgZm9yIHRoaXMgdGlja2V0CiAgICAkU2VsZi0+RGVhY3RpdmF0ZVRpY2tldFRva2VucygKICAgICAgICBUaWNrZXROdW1iZXIgPT4gJFBhcmFte1RpY2tldE51bWJlcn0sCiAgICApOwoKICAgIG15ICRPVEFUb2tlbkxlbmd0aCA9IDI0OwogICAgbXkgJFJhbmRvbVN0cmluZzsKCiAgICBteSAkVHJ5ID0gMTsKICAgIHdoaWxlICggJFRyeSApIHsKICAgICAgICAkUmFuZG9tU3RyaW5nID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06Ok1haW4nKS0+R2VuZXJhdGVSYW5kb21TdHJpbmcoCiAgICAgICAgICAgIExlbmd0aCA9PiAkT1RBVG9rZW5MZW5ndGgsCiAgICAgICAgKTsKCiAgICAgICAgIyBjaGVjayB3aGV0aGVyIHRoZSBzdHJpbmcgYWxyZWFkeSBleGlzdHMKICAgICAgICAkU2VsZi0+e0RCT2JqZWN0fS0+UHJlcGFyZSgKICAgICAgICAgICAgU1FMID0+ICJTRUxFQ1QgdXNlciBGUk9NICRTZWxmLT57VGFibGV9IFdIRVJFIHRva2VuID0gPyIsCiAgICAgICAgICAgIEJpbmQgPT4gWyBcJFBhcmFte09UQVRva2VufSBdLAogICAgICAgICk7CgogICAgICAgIGlmICggJFNlbGYtPntEQk9iamVjdH0tPkZldGNocm93QXJyYXkoKSApIHsKICAgICAgICAgICAgJFRyeSsrOwogICAgICAgIH0KICAgICAgICBlbHNlIHsKICAgICAgICAgICAgJFRyeSA9IDA7CiAgICAgICAgfQoKICAgICAgICBpZiAoICRUcnkgPiA1ICkgewogICAgICAgICAgICAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6TG9nJyktPkxvZygKICAgICAgICAgICAgICAgIFByaW9yaXR5ID0+ICdlcnJvcicsCiAgICAgICAgICAgICAgICBNZXNzYWdlICA9PiAiQ291bGQgbm90IGdlbmVyYXRlIGEgdW5pcXVlIHJhbmRvbSBzdHJpbmcgYWZ0ZXIgZml2ZSByZXRyaWVzIC0gc29tZXRoaW5nIGlzIG5vdCByaWdodCEiCiAgICAgICAgICAgICk7CiAgICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICB9CgogICAgcmV0dXJuIGlmICEkU2VsZi0+e0RCT2JqZWN0fS0+RG8oCiAgICAgICAgU1FMID0+ICJJTlNFUlQgSU5UTyAkU2VsZi0+e1RhYmxlfSAoIHRva2VuLCB0aWNrZXRfbnVtYmVyLCB1c2VkLCB1c2VyLCBjcmVhdGVfdGltZSwgY2hhbmdlX3RpbWUgKQogICAgICAgICAgICBWQUxVRVMgKCA/LCA/LCA/LCA/LCBjdXJyZW50X3RpbWVzdGFtcCwgY3VycmVudF90aW1lc3RhbXAgKSIsCiAgICAgICAgQmluZCA9PiBbIFwkUmFuZG9tU3RyaW5nLCBcJFBhcmFte1RpY2tldE51bWJlcn0sIFwyLCBcJFBhcmFte1VzZXJ9IF0sCiAgICApOwogICAgCiAgICByZXR1cm4gJFJhbmRvbVN0cmluZzsKfQoKc3ViIERlYWN0aXZhdGVUaWNrZXRUb2tlbnMgewogICAgbXkgKCAkU2VsZiwgJVBhcmFtICkgPSBAXzsKCiAgICAjIGNoZWNrIG5lZWRlZCBzdHVmZgogICAgZm9yIG15ICROZWVkZWQgKCBxdy9UaWNrZXROdW1iZXIvICkgewogICAgICAgIGlmICggISRQYXJhbXskTmVlZGVkfSApIHsKICAgICAgICAgICAgJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkxvZycpLT5Mb2coCiAgICAgICAgICAgICAgICBQcmlvcml0eSA9PiAnZXJyb3InLAogICAgICAgICAgICAgICAgTWVzc2FnZSAgPT4gIk5lZWQgJE5lZWRlZCEiCiAgICAgICAgICAgICk7CiAgICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICB9CgogICAgcmV0dXJuIGlmICEkU2VsZi0+e0RCT2JqZWN0fS0+RG8oCiAgICAgICAgU1FMID0+ICJVUERBVEUgJFNlbGYtPntUYWJsZX0gU0VUIHVzZWQgPSAxLCBjaGFuZ2VfdGltZSA9IGN1cnJlbnRfdGltZXN0YW1wIFdIRVJFIHRpY2tldF9udW1iZXIgPSA/IEFORCB1c2VkID0gMiIsCiAgICAgICAgQmluZCA9PiBbIFwkUGFyYW17VGlja2V0TnVtYmVyfSBdLAogICAgKTsKCiAgICByZXR1cm4gMTsKfQoKc3ViIERlbGV0ZVRpY2tldFRva2VucyB7CiAgICBteSAoICRTZWxmLCAlUGFyYW0gKSA9IEBfOwoKICAgICMgY2hlY2sgbmVlZGVkIHN0dWZmCiAgICBmb3IgbXkgJE5lZWRlZCAoIHF3L1RpY2tldE51bWJlci8gKSB7CiAgICAgICAgaWYgKCAhJFBhcmFteyROZWVkZWR9ICkgewogICAgICAgICAgICAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6TG9nJyktPkxvZygKICAgICAgICAgICAgICAgIFByaW9yaXR5ID0+ICdlcnJvcicsCiAgICAgICAgICAgICAgICBNZXNzYWdlICA9PiAiTmVlZCAkTmVlZGVkISIKICAgICAgICAgICAgKTsKICAgICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgIH0KCiAgICByZXR1cm4gaWYgISRTZWxmLT57REJPYmplY3R9LT5EbygKICAgICAgICBTUUwgPT4gIkRFTEVURSBGUk9NICRTZWxmLT57VGFibGV9IFdIRVJFIHRpY2tldF9udW1iZXIgPSA/IiwKICAgICAgICBCaW5kID0+IFsgXCRQYXJhbXtUaWNrZXROdW1iZXJ9IF0sCiAgICApOwoKICAgIHJldHVybiAxOwp9CgpzdWIgVGlja2V0TGluayB7CiAgICBteSAoICRTZWxmLCAlUGFyYW0gKSA9IEBfOwoKICAgIG15ICRDb25maWdPYmplY3QgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OkNvbmZpZycpOwoKICAgICMgY2hlY2sgbmVlZGVkIHN0dWZmCiAgICBmb3IgbXkgJE5lZWRlZCAoIHF3L1RpY2tldE51bWJlciBVc2VyLyApIHsKICAgICAgICBpZiAoICEkUGFyYW17JE5lZWRlZH0gKSB7CiAgICAgICAgICAgICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpMb2cnKS0+TG9nKAogICAgICAgICAgICAgICAgUHJpb3JpdHkgPT4gJ2Vycm9yJywKICAgICAgICAgICAgICAgIE1lc3NhZ2UgID0+ICJOZWVkICROZWVkZWQhIgogICAgICAgICAgICApOwoKICAgICAgICAgICAgcmV0dXJuICRDb25maWdPYmplY3QtPkdldCgnT25lVGltZUF1dGg6OkN1c3RvbWVyRXJyb3JNZXNzYWdlUmVmcmVzaEZhaWxlZCcpIC8vICdMaW5rIGNvdWxkIG5vdCBiZSBnZW5lcmF0ZWQsIHBsZWFzZSBjb250YWN0IHVzIGRpcmVjdGx5ISc7CiAgICAgICAgfQogICAgfQoKICAgIG15ICRUaWNrZXRMaW5rID0gJENvbmZpZ09iamVjdC0+R2V0KCdIdHRwVHlwZScpIC4gJzovLycgLiAkQ29uZmlnT2JqZWN0LT5HZXQoJ0ZRRE4nKSAuICcvb3RvYm8vY3VzdG9tZXIucGwnOwogICAgJFRpY2tldExpbmsgLj0gIj9BY3Rpb249Q3VzdG9tZXJUaWNrZXRab29tO1RpY2tldE51bWJlcj0kUGFyYW17VGlja2V0TnVtYmVyfSI7CgogICAgIyBjaGVjayBpZiB0aGUgdXNlciBhbHJlYWR5IGhhcyBhIHBhc3Nzd29yZCAtIHRoZW4gbm8gZGlyZWN0IGxpbmsgaXMgbmVlZGVkCiAgICBteSAlVXNlciA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpDdXN0b21lclVzZXInKS0+Q3VzdG9tZXJVc2VyRGF0YUdldCgKICAgICAgICBVc2VyID0+ICRQYXJhbXtVc2VyfSwKICAgICk7CgogICAgdW5sZXNzICggJFVzZXJ7VXNlclBhc3N3b3JkfSApIHsKICAgICAgICAjIGdlbmVyYXRlIHRva2VuCiAgICAgICAgbXkgJFRva2VuID0gJFNlbGYtPkdlbmVyYXRlVG9rZW4oCiAgICAgICAgICAgICVQYXJhbSwKICAgICAgICApOwoKICAgICAgICBpZiAoICEkVG9rZW4gKSB7CiAgICAgICAgICAgICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpMb2cnKS0+TG9nKAogICAgICAgICAgICAgICAgUHJpb3JpdHkgPT4gJ2Vycm9yJywKICAgICAgICAgICAgICAgIE1lc3NhZ2UgID0+ICJFcnJvciBpbiB0b2tlbiBnZW5lcmF0aW9uISIKICAgICAgICAgICAgKTsKCiAgICAgICAgICAgIHJldHVybiAkQ29uZmlnT2JqZWN0LT5HZXQoJ09uZVRpbWVBdXRoOjpDdXN0b21lckVycm9yTWVzc2FnZScpIC8vICdMaW5rIGNvdWxkIG5vdCBiZSBnZW5lcmF0ZWQsIHBsZWFzZSBjb250YWN0IHVzIGRpcmVjdGx5ISc7CiAgICAgICAgfQoKICAgICAgICAkVGlja2V0TGluayAuPSAiO09UQVRva2VuPSRUb2tlbiI7CiAgICB9CgogICAgcmV0dXJuICI8YSBocmVmPSckVGlja2V0TGluaycgdGFyZ2V0PSdfYmxhbmsnPiRUaWNrZXRMaW5rPC9hPiI7Cn0KCnN1YiBEZWFjdGl2YXRlQ2xvc2VkVGlja2V0cyB7CiAgICBteSAoICRTZWxmLCAlUGFyYW0gKSA9IEBfOwoKICAgIG15ICRDb25maWdPYmplY3QgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OkNvbmZpZycpOwogICAgbXkgJFRpY2tldE9iamVjdCA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpUaWNrZXQnKTsKCiAgICAjIGdldCB0aGUgY29tcGFyZSB0aW1lIGlmIGEgZGVsYXkgaXMgZ2l2ZW4KICAgIG15ICREZWxheSAgICAgICA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6Q29uZmlnJyktPkdldCgnT25lVGltZUF1dGg6OkFjY2Vzc0RheXNBZnRlckNsb3NlJykgfHwgMDsKICAgIG15ICRTdGlsbE9LVGltZSA9ICRLZXJuZWw6Ok9NLT5DcmVhdGUoJ0tlcm5lbDo6U3lzdGVtOjpEYXRlVGltZScpLT5Ub0Vwb2NoKCkgLSAyNCo2MCo2MCokRGVsYXk7CgogICAgJFNlbGYtPntEQk9iamVjdH0tPlByZXBhcmUoCiAgICAgICAgU1FMID0+ICJTRUxFQ1QgRElTVElOQ1QodGlja2V0X251bWJlcikgRlJPTSAkU2VsZi0+e1RhYmxlfSIsCiAgICApOwogICAgCiAgICBteSBAVGlja2V0TnVtYmVyczsKICAgIHdoaWxlICggbXkgQFJvdyA9ICRTZWxmLT57REJPYmplY3R9LT5GZXRjaHJvd0FycmF5KCkgKSB7CiAgICAgICAgcHVzaCBAVGlja2V0TnVtYmVycywgJFJvd1swXTsKICAgIH0KICAgIAogICAgVElDS0VUOgogICAgZm9yIG15ICRUTiAoIEBUaWNrZXROdW1iZXJzICkgewogICAgICAgIG15ICRUaWNrZXRJRCA9ICRUaWNrZXRPYmplY3QtPlRpY2tldElETG9va3VwKAogICAgICAgICAgICBUaWNrZXROdW1iZXIgPT4gJFROLAogICAgICAgICk7CgogICAgICAgIG15ICVUaWNrZXQgPSAkVGlja2V0T2JqZWN0LT5UaWNrZXRHZXQoCiAgICAgICAgICAgIFRpY2tldElEID0+ICRUaWNrZXRJRCwKICAgICAgICApOwoKICAgICAgICAjIHJlbW92ZSBvbGQgdG9rZW5zCiAgICAgICAgaWYgKCAkVGlja2V0e1N0YXRlVHlwZX0gZXEgJ2Nsb3NlZCcgfHwgJFRpY2tldHtTdGF0ZVR5cGV9IGVxICdyZW1vdmVkJyB8fCAkVGlja2V0e1N0YXRlVHlwZX0gZXEgJ21lcmdlZCcgKSB7CiAgICAgICAgICAgIGlmICggJERlbGF5ICkgewogICAgICAgICAgICAgICAgbXkgJExhc3RDaGFuZ2VkVGltZSA9ICRLZXJuZWw6Ok9NLT5DcmVhdGUoCiAgICAgICAgICAgICAgICAgICAgJ0tlcm5lbDo6U3lzdGVtOjpEYXRlVGltZScsCiAgICAgICAgICAgICAgICAgICAgT2JqZWN0UGFyYW1zID0+IHsKICAgICAgICAgICAgICAgICAgICAgICAgU3RyaW5nICAgPT4gJFRpY2tldHtDaGFuZ2VkfSwKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICApLT5Ub0Vwb2NoKCk7CgogICAgICAgICAgICAgICAgbmV4dCBUSUNLRVQgaWYgJExhc3RDaGFuZ2VkVGltZSA+ICRTdGlsbE9LVGltZTsKICAgICAgICAgICAgfQoKICAgICAgICAgICAgJFNlbGYtPkRlbGV0ZVRpY2tldFRva2VucygKICAgICAgICAgICAgICAgIFRpY2tldE51bWJlciA9PiAkVE4sCiAgICAgICAgICAgICk7IAogICAgICAgIH0KICAgIH0KCiAgICByZXR1cm4gMTsKfQoKc3ViIFNlbmROZXdUb2tlbiB7CiAgICBteSAoICRTZWxmLCAlUGFyYW0gKSA9IEBfOwoKICAgICMgY2hlY2sgbmVlZGVkIHN0dWZmCiAgICBmb3IgbXkgJE5lZWRlZCAoIHF3L1RpY2tldE51bWJlciBVc2VyLyApIHsKICAgICAgICBpZiAoICEkUGFyYW17JE5lZWRlZH0gKSB7CiAgICAgICAgICAgICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpMb2cnKS0+TG9nKAogICAgICAgICAgICAgICAgUHJpb3JpdHkgPT4gJ2Vycm9yJywKICAgICAgICAgICAgICAgIE1lc3NhZ2UgID0+ICJOZWVkICROZWVkZWQhIgogICAgICAgICAgICApOwoKICAgICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgIH0KCiAgICBteSAkQ29uZmlnT2JqZWN0ICAgICAgID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpDb25maWcnKTsKICAgIG15ICRDdXN0b21lclVzZXJPYmplY3QgPSAkS2VybmVsOjpPTS0+R2V0KCdLZXJuZWw6OlN5c3RlbTo6Q3VzdG9tZXJVc2VyJyk7CiAgICBteSAkVGlja2V0T2JqZWN0ICAgICAgID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OlRpY2tldCcpOwoKICAgIG15ICRUaWNrZXRJRCA9ICRUaWNrZXRPYmplY3QtPlRpY2tldElETG9va3VwKAogICAgICAgIFRpY2tldE51bWJlciA9PiAkUGFyYW17VGlja2V0TnVtYmVyfSwKICAgICk7CiAgICBteSAlVGlja2V0ID0gJFRpY2tldE9iamVjdC0+VGlja2V0R2V0KAogICAgICAgIFRpY2tldElEID0+ICRUaWNrZXRJRCwKICAgICk7CiAgICBteSAlVXNlciA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpDdXN0b21lclVzZXInKS0+Q3VzdG9tZXJVc2VyRGF0YUdldCgKICAgICAgICBVc2VyID0+ICRQYXJhbXtVc2VyfSwKICAgICk7CgogICAgbXkgJFRlbXBsYXRlR2VuZXJhdG9yID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OlRlbXBsYXRlR2VuZXJhdG9yJyk7CiAgICBteSAkU2VuZGVyICAgICAgICAgICAgPSAkVGVtcGxhdGVHZW5lcmF0b3ItPlNlbmRlcigKICAgICAgICBRdWV1ZUlEID0+ICRUaWNrZXR7UXVldWVJRH0sCiAgICAgICAgVXNlcklEICA9PiAxLAogICAgKTsKCiAgICBteSAkTm90aWZpY2F0aW9uSUQgPSAkQ29uZmlnT2JqZWN0LT5HZXQoJ09uZVRpbWVBdXRoOjpUb2tlblJlZnJlc2hOb3RpZmljYXRpb25JRCcpOwoKICAgIG15ICggJEJvZHksICRTdWJqZWN0ICk7CgogICAgaWYgKCAkTm90aWZpY2F0aW9uSUQgKSB7CiAgICAgICAgbXkgJU5vdGlmaWNhdGlvbiA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpOb3RpZmljYXRpb25FdmVudCcpLT5Ob3RpZmljYXRpb25HZXQoCiAgICAgICAgICAgIElEID0+ICROb3RpZmljYXRpb25JRCwKICAgICAgICApOwoKICAgICAgICBteSAlTGFuZ3VhZ2VzID0gbWFwIHsgJF8gPT4gJF8gfSBAeyAkTm90aWZpY2F0aW9ue0RhdGF9e0xhbmd1YWdlSUR9IH07CiAgICAgICAgbXkgJExhbmd1YWdlICA9ICRMYW5ndWFnZXN7ZGV9IHx8ICRMYW5ndWFnZXN7ZW59IHx8ICROb3RpZmljYXRpb257RGF0YX17TGFuZ3VhZ2VJRH1bMF07CgogICAgICAgICMgcmVwbGFjZSBwbGFjZSBob2xkZXIgc3R1ZmYKICAgICAgICAkQm9keSA9ICRUZW1wbGF0ZUdlbmVyYXRvci0+X1JlcGxhY2UoCiAgICAgICAgICAgIFJpY2hUZXh0ICAgICAgICA9PiAkQ29uZmlnT2JqZWN0LT5HZXQoJ0Zyb250ZW5kOjpSaWNoVGV4dCcpLAogICAgICAgICAgICBUZXh0ICAgICAgICAgICAgPT4gJE5vdGlmaWNhdGlvbntNZXNzYWdlfXskTGFuZ3VhZ2V9e0JvZHl9LAogICAgICAgICAgICBEYXRhICAgICAgICAgICAgPT4ge30sCiAgICAgICAgICAgIFRpY2tldERhdGEgICAgICA9PiBcJVRpY2tldCwKICAgICAgICAgICAgVXNlcklEICAgICAgICAgID0+IDEsCiAgICAgICAgKTsKCiAgICAgICAgJFN1YmplY3QgPSAkVGVtcGxhdGVHZW5lcmF0b3ItPl9SZXBsYWNlKAogICAgICAgICAgICBSaWNoVGV4dCAgICAgICAgPT4gMCwKICAgICAgICAgICAgVGV4dCAgICAgICAgICAgID0+ICROb3RpZmljYXRpb257TWVzc2FnZX17JExhbmd1YWdlfXtTdWJqZWN0fSwKICAgICAgICAgICAgRGF0YSAgICAgICAgICAgID0+IHt9LAogICAgICAgICAgICBUaWNrZXREYXRhICAgICAgPT4gXCVUaWNrZXQsCiAgICAgICAgICAgIFVzZXJJRCAgICAgICAgICA9PiAxLAogICAgICAgICk7CiAgICB9CgogICAgZWxzZSB7CiAgICAgICAgbXkgJFRpY2tldExpbmsgPSAkU2VsZi0+VGlja2V0TGluayggJVBhcmFtICk7CgogICAgICAgICRTdWJqZWN0ID0gIk5ldWVyIEF1dGhlbnRpZml6aWVydW5nc2xpbmsgZsO8ciBUaWNrZXQjJFRpY2tldHtUaWNrZXROdW1iZXJ9IjsKICAgICAgICAkQm9keSAgICA9ICJHdXRlbiBUYWc8YnIvPklociBha3R1ZWxsZXIgTGluayB1bSBhdWYgVGlja2V0IyRUaWNrZXR7VGlja2V0TnVtYmVyfSB6dWdyZWlmZW4genUga8O2bm5lbiBsYXV0ZXQ6PGJyLz4kVGlja2V0TGluayI7CiAgICB9CgoKICAgIG15ICRFbWFpbE9iamVjdCA9ICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpFbWFpbCcpOwogICAgbXkgJFNlbnQgPSAkRW1haWxPYmplY3QtPlNlbmQoCiAgICAgICAgRnJvbSAgICAgPT4gJFNlbmRlciwKICAgICAgICBUbyAgICAgICA9PiAkVXNlcntVc2VyRW1haWx9LAogICAgICAgIFN1YmplY3QgID0+ICRTdWJqZWN0LAogICAgICAgIENoYXJzZXQgID0+ICd1dGYtOCcsCiAgICAgICAgTWltZVR5cGUgPT4gJ3RleHQvaHRtbCcsCiAgICAgICAgQm9keSAgICAgPT4gJEJvZHksCiAgICApOwoKICAgIGlmICggISRTZW50ICkgewogICAgICAgICRLZXJuZWw6Ok9NLT5HZXQoJ0tlcm5lbDo6U3lzdGVtOjpMb2cnKS0+TG9nKAogICAgICAgICAgICBQcmlvcml0eSA9PiAnZXJyb3InLAogICAgICAgICAgICBNZXNzYWdlICA9PiAiQ291bGQgbm90IHNlbmQgbmV3IHRva2VuIHRvICRQYXJhbXtVc2VyfSBmb3IgVGlja2V0IyRQYXJhbXtUaWNrZXROdW1iZXJ9ISIKICAgICAgICApOwoKICAgICAgICByZXR1cm47CiAgICB9CgogICAgcmV0dXJuIDE7Cn0KCjE7Cg==
IyAtLQojIE9UT0JPIGlzIGEgd2ViLWJhc2VkIHRpY2tldGluZyBzeXN0ZW0gZm9yIHNlcnZpY2Ugb3JnYW5pc2F0aW9ucy4KIyAtLQojIENvcHlyaWdodCAoQykgMjAwMS0yMDIwIE9UUlMgQUcsIGh0dHBzOi8vb3Rycy5jb20vCiMgQ29weXJpZ2h0IChDKSAyMDE5LTIwMjEgUm90aGVyIE9TUyBHbWJILCBodHRwczovL290b2JvLmRlLwojIC0tCiMgVGhpcyBwcm9ncmFtIGlzIGZyZWUgc29mdHdhcmU6IHlvdSBjYW4gcmVkaXN0cmlidXRlIGl0IGFuZC9vciBtb2RpZnkgaXQgdW5kZXIKIyB0aGUgdGVybXMgb2YgdGhlIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlIGFzIHB1Ymxpc2hlZCBieSB0aGUgRnJlZSBTb2Z0d2FyZQojIEZvdW5kYXRpb24sIGVpdGhlciB2ZXJzaW9uIDMgb2YgdGhlIExpY2Vuc2UsIG9yIChhdCB5b3VyIG9wdGlvbikgYW55IGxhdGVyIHZlcnNpb24uCiMgVGhpcyBwcm9ncmFtIGlzIGRpc3RyaWJ1dGVkIGluIHRoZSBob3BlIHRoYXQgaXQgd2lsbCBiZSB1c2VmdWwsIGJ1dCBXSVRIT1VUCiMgQU5ZIFdBUlJBTlRZOyB3aXRob3V0IGV2ZW4gdGhlIGltcGxpZWQgd2FycmFudHkgb2YgTUVSQ0hBTlRBQklMSVRZIG9yIEZJVE5FU1MKIyBGT1IgQSBQQVJUSUNVTEFSIFBVUlBPU0UuIFNlZSB0aGUgR05VIEdlbmVyYWwgUHVibGljIExpY2Vuc2UgZm9yIG1vcmUgZGV0YWlscy4KIyBZb3Ugc2hvdWxkIGhhdmUgcmVjZWl2ZWQgYSBjb3B5IG9mIHRoZSBHTlUgR2VuZXJhbCBQdWJsaWMgTGljZW5zZQojIGFsb25nIHdpdGggdGhpcyBwcm9ncmFtLiBJZiBub3QsIHNlZSA8aHR0cHM6Ly93d3cuZ251Lm9yZy9saWNlbnNlcy8+LgojIC0tCgpwYWNrYWdlIEtlcm5lbDo6U3lzdGVtOjpQb3N0TWFzdGVyOjpGaWx0ZXI6OkNyZWF0ZU5ld0N1c3RvbWVyVXNlcjsKCnVzZSBzdHJpY3Q7CnVzZSB3YXJuaW5nczsKCnVzZSBLZXJuZWw6OlN5c3RlbTo6VmFyaWFibGVDaGVjayBxdyg6YWxsKTsKCm91ciBAT2JqZWN0RGVwZW5kZW5jaWVzID0gKAogICAgJ0tlcm5lbDo6U3lzdGVtOjpDdXN0b21lclVzZXInLAogICAgJ0tlcm5lbDo6U3lzdGVtOjpMb2cnLAopOwoKc3ViIG5ldyB7CiAgICBteSAoICRUeXBlLCAlUGFyYW0gKSA9IEBfOwoKICAgICMgYWxsb2NhdGUgbmV3IGhhc2ggZm9yIG9iamVjdAogICAgbXkgJFNlbGYgPSB7fTsKICAgIGJsZXNzKCAkU2VsZiwgJFR5cGUgKTsKCiAgICAjIGdldCBwYXJzZXIgb2JqZWN0CiAgICAkU2VsZi0+e1BhcnNlck9iamVjdH0gPSAkUGFyYW17UGFyc2VyT2JqZWN0fSB8fCBkaWUgIkdvdCBubyBQYXJzZXJPYmplY3QhIjsKCiAgICAjIEdldCBjb21tdW5pY2F0aW9uIGxvZyBvYmplY3QuCiAgICAkU2VsZi0+e0NvbW11bmljYXRpb25Mb2dPYmplY3R9ID0gJFBhcmFte0NvbW11bmljYXRpb25Mb2dPYmplY3R9IHx8IGRpZSAiR290IG5vIENvbW11bmljYXRpb25Mb2dPYmplY3QhIjsKCiAgICByZXR1cm4gJFNlbGY7Cn0KCnN1YiBSdW4gewogICAgbXkgKCAkU2VsZiwgJVBhcmFtICkgPSBAXzsKCiAgICAjIG9ubHkgbmVlZGVkIGZvciBuZXcgdGlja2V0cwogICAgcmV0dXJuIDEgaWYgJFBhcmFte1RpY2tldElEfTsKCiAgICAjIGNoZWNrIG5lZWRlZCBzdHVmZgogICAgZm9yIChxdyhHZXRQYXJhbSBKb2JDb25maWcpKSB7CiAgICAgICAgaWYgKCAhJFBhcmFteyRffSApIHsKICAgICAgICAgICAgJFNlbGYtPntDb21tdW5pY2F0aW9uTG9nT2JqZWN0fS0+T2JqZWN0TG9nKAogICAgICAgICAgICAgICAgT2JqZWN0TG9nVHlwZSA9PiAnTWVzc2FnZScsCiAgICAgICAgICAgICAgICBQcmlvcml0eSAgICAgID0+ICdFcnJvcicsCiAgICAgICAgICAgICAgICBLZXkgICAgICAgICAgID0+ICdLZXJuZWw6OlN5c3RlbTo6UG9zdE1hc3Rlcjo6RmlsdGVyOjpDcmVhdGVOZXdDdXN0b21lclVzZXInLAogICAgICAgICAgICAgICAgVmFsdWUgICAgICAgICA9PiAiTmVlZCAkXyEiLAogICAgICAgICAgICApOwogICAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgfQoKICAgIG15IEBFbWFpbEFkZHJlc3NPbkZpZWxkID0gJFNlbGYtPntQYXJzZXJPYmplY3R9LT5TcGxpdEFkZHJlc3NMaW5lKAogICAgICAgIExpbmUgPT4gJFNlbGYtPntQYXJzZXJPYmplY3R9LT5HZXRQYXJhbSggV0hBVCA9PiAnRnJvbScgKSwKICAgICk7CgogICAgbXkgJEluY29taW5nTWFpbEFkZHJlc3M7CgogICAgZm9yIG15ICRFbWFpbEFkZHJlc3MgKEBFbWFpbEFkZHJlc3NPbkZpZWxkKSB7CiAgICAgICAgJEluY29taW5nTWFpbEFkZHJlc3MgPSAkU2VsZi0+e1BhcnNlck9iamVjdH0tPkdldEVtYWlsQWRkcmVzcygKICAgICAgICAgICAgRW1haWwgPT4gJEVtYWlsQWRkcmVzcywKICAgICAgICApOwogICAgfQoKICAgIHJldHVybiAxIGlmICEkSW5jb21pbmdNYWlsQWRkcmVzczsKCiAgICBteSAkQ3VzdG9tZXJVc2VyT2JqZWN0ID0gJEtlcm5lbDo6T00tPkdldCgnS2VybmVsOjpTeXN0ZW06OkN1c3RvbWVyVXNlcicpOwoKICAgIG15ICVMaXN0ID0gJEN1c3RvbWVyVXNlck9iamVjdC0+Q3VzdG9tZXJTZWFyY2goCiAgICAgICAgUG9zdE1hc3RlclNlYXJjaCA9PiBsYyggJEluY29taW5nTWFpbEFkZHJlc3MgKSwKICAgICAgICBWYWxpZCAgICAgICAgICAgID0+IDAsCiAgICApOwoKICAgICMgdXNlciBhbHJlYWR5IGV4aXN0cwogICAgaWYgKCAlTGlzdCApIHsKCiAgICAgICAgIyByZXR1cm4gaWYgbm8gWC1PVE9CTy1DdXN0b21lclVzZXIgc3Bvb2ZpbmcgaXMgcG9zc2libGUvZGFuZ2Vyb3VzCiAgICAgICAgcmV0dXJuIDEgaWYgISRQYXJhbXtKb2JDb25maWd9e0N1c3RvbWVySGVhZGVyU3Bvb2ZQcm90ZWN0aW9ufSAmJiAhJFBhcmFte0pvYkNvbmZpZ317U2V0Q2hlY2tCb3hOYW1lfTsKCiAgICAgICAgbXkgJUN1c3RvbWVyRGF0YTsKICAgICAgICBMT0dJTjoKICAgICAgICBmb3IgbXkgJFVzZXJMb2dpbiAoIHNvcnQga2V5cyAlTGlzdCApIHsKICAgICAgICAgICAgbXkgJUN1c3RvbWVyVXNlciA9ICRDdXN0b21lclVzZXJPYmplY3QtPkN1c3RvbWVyVXNlckRhdGFHZXQoCiAgICAgICAgICAgICAgICBVc2VyID0+ICRVc2VyTG9naW4sCiAgICAgICAgICAgICk7CiAgICAgICAgICAgIAogICAgICAgICAgICBpZiAoICRDdXN0b21lclVzZXJ7VmFsaWRJRH0gPT0gMSApIHsKICAgICAgICAgICAgICAgICVDdXN0b21lckRhdGEgPSAlQ3VzdG9tZXJVc2VyOwogICAgICAgICAgICAgICAgbGFzdCBMT0dJTjsKICAgICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgIyBpZiB1c2VyIGV4aXN0cyBidXQgaXMgbm90IHZhbGlkLCBkbyBub3RoaW5nCiAgICAgICAgcmV0dXJuIDEgaWYgISVDdXN0b21lckRhdGE7CgogICAgICAgIGlmICggJFBhcmFte0pvYkNvbmZpZ317U2V0Q2hlY2tCb3hOYW1lfSAmJiAkQ3VzdG9tZXJEYXRhe1NvdXJjZX0gZXEgKCAkUGFyYW17Sm9iQ29uZmlnfXtDdXN0b21lclVzZXJCYWNrZW5kfSB8fCAnQ3VzdG9tZXJVc2VyJyApICkgewogICAgICAgICAgICAkUGFyYW17R2V0UGFyYW19eyAnWC1PVE9CTy1EeW5hbWljRmllbGQtJyAuICRQYXJhbXtKb2JDb25maWd9e1NldENoZWNrQm94TmFtZX0gfSA9IDE7CiAgICAgICAgfQoKICAgICAgICByZXR1cm4gMSBpZiAhJFBhcmFte0pvYkNvbmZpZ317Q3VzdG9tZXJIZWFkZXJTcG9vZlByb3RlY3Rpb259OwoKICAgICAgICAjIHRha2UgQ3VzdG9tZXJJRCBmcm9tIGN1c3RvbWVyIGJhY2tlbmQgbG9va3VwIG9yIGZyb20gZnJvbSBmaWVsZAogICAgICAgIGlmICggJEN1c3RvbWVyRGF0YXtVc2VyTG9naW59ICkgewogICAgICAgICAgICAkUGFyYW17R2V0UGFyYW19eydYLU9UT0JPLUN1c3RvbWVyVXNlcid9ID0gJEN1c3RvbWVyRGF0YXtVc2VyTG9naW59OwoKICAgICAgICAgICAgIyBub3RpY2UgdGhhdCBVc2VyTG9naW4gaXMgZnJvbSBjdXN0b21lciBzb3VyY2UgYmFja2VuZAogICAgICAgICAgICAkU2VsZi0+e0NvbW11bmljYXRpb25Mb2dPYmplY3R9LT5PYmplY3RMb2coCiAgICAgICAgICAgICAgICBPYmplY3RMb2dUeXBlID0+ICdNZXNzYWdlJywKICAgICAgICAgICAgICAgIFByaW9yaXR5ICAgICAgPT4gJ05vdGljZScsCiAgICAgICAgICAgICAgICBLZXkgICAgICAgICAgID0+ICdLZXJuZWw6OlN5c3RlbTo6UG9zdE1hc3Rlcjo6RmlsdGVyOjpDcmVhdGVOZXdDdXN0b21lclVzZXInLAogICAgICAgICAgICAgICAgVmFsdWUgICAgICAgICA9PiAiVGFrZSBVc2VyTG9naW4gKCRDdXN0b21lckRhdGF7VXNlckxvZ2lufSkgZnJvbSAiCiAgICAgICAgICAgICAgICAgICAgLiAiY3VzdG9tZXIgc291cmNlIGJhY2tlbmQgYmFzZWQgb24gKCRJbmNvbWluZ01haWxBZGRyZXNzKS4iLAogICAgICAgICAgICApOwogICAgICAgIH0KICAgICAgICBpZiAoICRDdXN0b21lckRhdGF7VXNlckN1c3RvbWVySUR9ICkgewogICAgICAgICAgICAkUGFyYW17R2V0UGFyYW19eydYLU9UT0JPLUN1c3RvbWVyTm8nfSA9ICRDdXN0b21lckRhdGF7VXNlckN1c3RvbWVySUR9OwoKICAgICAgICAgICAgIyBub3RpY2UgdGhhdCBVc2VyQ3VzdG9tZXJJRCBpcyBmcm9tIGN1c3RvbWVyIHNvdXJjZSBiYWNrZW5kCiAgICAgICAgICAgICRTZWxmLT57Q29tbXVuaWNhdGlvbkxvZ09iamVjdH0tPk9iamVjdExvZygKICAgICAgICAgICAgICAgIE9iamVjdExvZ1R5cGUgPT4gJ01lc3NhZ2UnLAogICAgICAgICAgICAgICAgUHJpb3JpdHkgICAgICA9PiAnTm90aWNlJywKICAgICAgICAgICAgICAgIEtleSAgICAgICAgICAgPT4gJ0tlcm5lbDo6U3lzdGVtOjpQb3N0TWFzdGVyOjpGaWx0ZXI6OkNyZWF0ZU5ld0N1c3RvbWVyVXNlcicsCiAgICAgICAgICAgICAgICBWYWx1ZSAgICAgICAgID0+ICJUYWtlIFVzZXJDdXN0b21lcklEICgkQ3VzdG9tZXJEYXRhe1VzZXJDdXN0b21lcklEfSkiCiAgICAgICAgICAgICAgICAgICAgLiAiIGZyb20gY3VzdG9tZXIgc291cmNlIGJhY2tlbmQgYmFzZWQgb24gKCRJbmNvbWluZ01haWxBZGRyZXNzKS4iLAogICAgICAgICAgICApOwogICAgICAgIH0KICAgIH0KCiAgICAjIHVzZXIgZG9lcyBub3QgeWV0IGV4aXN0IC0gY3JlYXRlIGl0IQogICAgZWxzZSB7CiAgICAgICAgbXkgJFVzZXJMb2dpbiA9IGxjKCAkSW5jb21pbmdNYWlsQWRkcmVzcyApOwogICAgICAgIAogICAgICAgIG15ICRTdWNjZXNzID0gJEN1c3RvbWVyVXNlck9iamVjdC0+Q3VzdG9tZXJVc2VyQWRkKAogICAgICAgICAgICBTb3VyY2UgICAgICAgICA9PiAkUGFyYW17Sm9iQ29uZmlnfXtDdXN0b21lclVzZXJCYWNrZW5kfSB8fCAnQ3VzdG9tZXJVc2VyJywKICAgICAgICAgICAgVXNlckZpcnN0bmFtZSAgPT4gJyAnLAogICAgICAgICAgICBVc2VyTGFzdG5hbWUgICA9PiAnICcsCiAgICAgICAgICAgIFVzZXJDdXN0b21lcklEID0+ICRVc2VyTG9naW4sCiAgICAgICAgICAgIFVzZXJMb2dpbiAgICAgID0+ICRVc2VyTG9naW4sCiAgICAgICAgICAgIFVzZXJFbWFpbCAgICAgID0+ICRVc2VyTG9naW4sCiAgICAgICAgICAgIFZhbGlkSUQgICAgICAgID0+IDEsCiAgICAgICAgICAgIFVzZXJJRCAgICAgICAgID0+IDEsCiAgICAgICAgKTsKCiAgICAgICAgaWYgKCAkU3VjY2VzcyApIHsKICAgICAgICAgICAgIyBub3RpY2UgdGhhdCBVc2VyTG9naW4gaXMgZnJvbSBjdXN0b21lciBzb3VyY2UgYmFja2VuZAogICAgICAgICAgICAkU2VsZi0+e0NvbW11bmljYXRpb25Mb2dPYmplY3R9LT5PYmplY3RMb2coCiAgICAgICAgICAgICAgICBPYmplY3RMb2dUeXBlID0+ICdNZXNzYWdlJywKICAgICAgICAgICAgICAgIFByaW9yaXR5ICAgICAgPT4gJ05vdGljZScsCiAgICAgICAgICAgICAgICBLZXkgICAgICAgICAgID0+ICdLZXJuZWw6OlN5c3RlbTo6UG9zdE1hc3Rlcjo6RmlsdGVyOjpDcmVhdGVOZXdDdXN0b21lclVzZXInLAogICAgICAgICAgICAgICAgVmFsdWUgICAgICAgICA9PiAiQ3JlYXRlIGFuZCBzZXQgbmV3IFVzZXJMb2dpbiAoJFVzZXJMb2dpbikuIiwKICAgICAgICAgICAgKTsKCiAgICAgICAgICAgICRQYXJhbXtHZXRQYXJhbX17J1gtT1RPQk8tQ3VzdG9tZXJVc2VyJ30gPSAkVXNlckxvZ2luOwogICAgICAgICAgICAkUGFyYW17R2V0UGFyYW19eydYLU9UT0JPLUN1c3RvbWVyTm8nfSAgID0gJFVzZXJMb2dpbjsKCiAgICAgICAgICAgIGlmICggJFBhcmFte0pvYkNvbmZpZ317U2V0Q2hlY2tCb3hOYW1lfSApIHsKICAgICAgICAgICAgICAgICRQYXJhbXtHZXRQYXJhbX17ICdYLU9UT0JPLUR5bmFtaWNGaWVsZC0nIC4gJFBhcmFte0pvYkNvbmZpZ317U2V0Q2hlY2tCb3hOYW1lfSB9ID0gMTsKICAgICAgICAgICAgfQoKICAgICAgICAgICAgIyBzZXQgcHJlZmVyZW5jZXMKICAgICAgICAgICAgJEN1c3RvbWVyVXNlck9iamVjdC0+U2V0UHJlZmVyZW5jZXMoCiAgICAgICAgICAgICAgICBVc2VySUQgPT4gJFVzZXJMb2dpbiwKICAgICAgICAgICAgICAgIEtleSAgICA9PiAnVXNlclRpbWVab25lJywKICAgICAgICAgICAgICAgIFZhbHVlICA9PiAnRXVyb3BlL0JlcmxpbicsCiAgICAgICAgICAgICk7CiAgICAgICAgICAgICRDdXN0b21lclVzZXJPYmplY3QtPlNldFByZWZlcmVuY2VzKAogICAgICAgICAgICAgICAgVXNlcklEID0+ICRVc2VyTG9naW4sCiAgICAgICAgICAgICAgICBLZXkgICAgPT4gJ1VzZXJTaG93VGlja2V0cycsCiAgICAgICAgICAgICAgICBWYWx1ZSAgPT4gJzI1JywKICAgICAgICAgICAgKTsKICAgICAgICAgICAgJEN1c3RvbWVyVXNlck9iamVjdC0+U2V0UHJlZmVyZW5jZXMoCiAgICAgICAgICAgICAgICBVc2VySUQgPT4gJFVzZXJMb2dpbiwKICAgICAgICAgICAgICAgIEtleSAgICA9PiAnVXNlclJlZnJlc2hUaW1lJywKICAgICAgICAgICAgICAgIFZhbHVlICA9PiAnMCcsCiAgICAgICAgICAgICk7CiAgICAgICAgfQogICAgfQoKICAgIHJldHVybiAxOwp9CgoxOwo=