Iy0qLSBjb2Rpbmc6IGlzby04ODU5LTEgLSotCiMgcHlzcWxpdGUyL3Rlc3QvZGJhcGkucHk6IHRlc3RzIGZvciBEQi1BUEkgY29tcGxpYW5jZQojCiMgQ29weXJpZ2h0IChDKSAyMDA0LTIwMTAgR2VyaGFyZCBI5HJpbmcgPGdoQGdoYWVyaW5nLmRlPgojCiMgVGhpcyBmaWxlIGlzIHBhcnQgb2YgcHlzcWxpdGUuCiMKIyBUaGlzIHNvZnR3YXJlIGlzIHByb3ZpZGVkICdhcy1pcycsIHdpdGhvdXQgYW55IGV4cHJlc3Mgb3IgaW1wbGllZAojIHdhcnJhbnR5LiAgSW4gbm8gZXZlbnQgd2lsbCB0aGUgYXV0aG9ycyBiZSBoZWxkIGxpYWJsZSBmb3IgYW55IGRhbWFnZXMKIyBhcmlzaW5nIGZyb20gdGhlIHVzZSBvZiB0aGlzIHNvZnR3YXJlLgojCiMgUGVybWlzc2lvbiBpcyBncmFudGVkIHRvIGFueW9uZSB0byB1c2UgdGhpcyBzb2Z0d2FyZSBmb3IgYW55IHB1cnBvc2UsCiMgaW5jbHVkaW5nIGNvbW1lcmNpYWwgYXBwbGljYXRpb25zLCBhbmQgdG8gYWx0ZXIgaXQgYW5kIHJlZGlzdHJpYnV0ZSBpdAojIGZyZWVseSwgc3ViamVjdCB0byB0aGUgZm9sbG93aW5nIHJlc3RyaWN0aW9uczoKIwojIDEuIFRoZSBvcmlnaW4gb2YgdGhpcyBzb2Z0d2FyZSBtdXN0IG5vdCBiZSBtaXNyZXByZXNlbnRlZDsgeW91IG11c3Qgbm90CiMgICAgY2xhaW0gdGhhdCB5b3Ugd3JvdGUgdGhlIG9yaWdpbmFsIHNvZnR3YXJlLiBJZiB5b3UgdXNlIHRoaXMgc29mdHdhcmUKIyAgICBpbiBhIHByb2R1Y3QsIGFuIGFja25vd2xlZGdtZW50IGluIHRoZSBwcm9kdWN0IGRvY3VtZW50YXRpb24gd291bGQgYmUKIyAgICBhcHByZWNpYXRlZCBidXQgaXMgbm90IHJlcXVpcmVkLgojIDIuIEFsdGVyZWQgc291cmNlIHZlcnNpb25zIG11c3QgYmUgcGxhaW5seSBtYXJrZWQgYXMgc3VjaCwgYW5kIG11c3Qgbm90IGJlCiMgICAgbWlzcmVwcmVzZW50ZWQgYXMgYmVpbmcgdGhlIG9yaWdpbmFsIHNvZnR3YXJlLgojIDMuIFRoaXMgbm90aWNlIG1heSBub3QgYmUgcmVtb3ZlZCBvciBhbHRlcmVkIGZyb20gYW55IHNvdXJjZSBkaXN0cmlidXRpb24uCgppbXBvcnQgdGhyZWFkaW5nCmltcG9ydCB1bml0dGVzdAppbXBvcnQgc3FsaXRlMyBhcyBzcWxpdGUKCmZyb20gdGVzdC5zdXBwb3J0Lm9zX2hlbHBlciBpbXBvcnQgVEVTVEZOLCB1bmxpbmsKCgpjbGFzcyBNb2R1bGVUZXN0cyh1bml0dGVzdC5UZXN0Q2FzZSk6CiAgICBkZWYgQ2hlY2tBUElMZXZlbChzZWxmKToKICAgICAgICBzZWxmLmFzc2VydEVxdWFsKHNxbGl0ZS5hcGlsZXZlbCwgIjIuMCIsCiAgICAgICAgICAgICAgICAgICAgICAgICAiYXBpbGV2ZWwgaXMgJXMsIHNob3VsZCBiZSAyLjAiICUgc3FsaXRlLmFwaWxldmVsKQoKICAgIGRlZiBDaGVja1RocmVhZFNhZmV0eShzZWxmKToKICAgICAgICBzZWxmLmFzc2VydEVxdWFsKHNxbGl0ZS50aHJlYWRzYWZldHksIDEsCiAgICAgICAgICAgICAgICAgICAgICAgICAidGhyZWFkc2FmZXR5IGlzICVkLCBzaG91bGQgYmUgMSIgJSBzcWxpdGUudGhyZWFkc2FmZXR5KQoKICAgIGRlZiBDaGVja1BhcmFtU3R5bGUoc2VsZik6CiAgICAgICAgc2VsZi5hc3NlcnRFcXVhbChzcWxpdGUucGFyYW1zdHlsZSwgInFtYXJrIiwKICAgICAgICAgICAgICAgICAgICAgICAgICJwYXJhbXN0eWxlIGlzICclcycsIHNob3VsZCBiZSAncW1hcmsnIiAlCiAgICAgICAgICAgICAgICAgICAgICAgICBzcWxpdGUucGFyYW1zdHlsZSkKCiAgICBkZWYgQ2hlY2tXYXJuaW5nKHNlbGYpOgogICAgICAgIHNlbGYuYXNzZXJ0VHJ1ZShpc3N1YmNsYXNzKHNxbGl0ZS5XYXJuaW5nLCBFeGNlcHRpb24pLAogICAgICAgICAgICAgICAgICAgICAiV2FybmluZyBpcyBub3QgYSBzdWJjbGFzcyBvZiBFeGNlcHRpb24iKQoKICAgIGRlZiBDaGVja0Vycm9yKHNlbGYpOgogICAgICAgIHNlbGYuYXNzZXJ0VHJ1ZShpc3N1YmNsYXNzKHNxbGl0ZS5FcnJvciwgRXhjZXB0aW9uKSwKICAgICAgICAgICAgICAgICAgICAgICAgIkVycm9yIGlzIG5vdCBhIHN1YmNsYXNzIG9mIEV4Y2VwdGlvbiIpCgogICAgZGVmIENoZWNrSW50ZXJmYWNlRXJyb3Ioc2VsZik6CiAgICAgICAgc2VsZi5hc3NlcnRUcnVlKGlzc3ViY2xhc3Moc3FsaXRlLkludGVyZmFjZUVycm9yLCBzcWxpdGUuRXJyb3IpLAogICAgICAgICAgICAgICAgICAgICAgICAiSW50ZXJmYWNlRXJyb3IgaXMgbm90IGEgc3ViY2xhc3Mgb2YgRXJyb3IiKQoKICAgIGRlZiBDaGVja0RhdGFiYXNlRXJyb3Ioc2VsZik6CiAgICAgICAgc2VsZi5hc3NlcnRUcnVlKGlzc3ViY2xhc3Moc3FsaXRlLkRhdGFiYXNlRXJyb3IsIHNxbGl0ZS5FcnJvciksCiAgICAgICAgICAgICAgICAgICAgICAgICJEYXRhYmFzZUVycm9yIGlzIG5vdCBhIHN1YmNsYXNzIG9mIEVycm9yIikKCiAgICBkZWYgQ2hlY2tEYXRhRXJyb3Ioc2VsZik6CiAgICAgICAgc2VsZi5hc3NlcnRUcnVlKGlzc3ViY2xhc3Moc3FsaXRlLkRhdGFFcnJvciwgc3FsaXRlLkRhdGFiYXNlRXJyb3IpLAogICAgICAgICAgICAgICAgICAgICAgICAiRGF0YUVycm9yIGlzIG5vdCBhIHN1YmNsYXNzIG9mIERhdGFiYXNlRXJyb3IiKQoKICAgIGRlZiBDaGVja09wZXJhdGlvbmFsRXJyb3Ioc2VsZik6CiAgICAgICAgc2VsZi5hc3NlcnRUcnVlKGlzc3ViY2xhc3Moc3FsaXRlLk9wZXJhdGlvbmFsRXJyb3IsIHNxbGl0ZS5EYXRhYmFzZUVycm9yKSwKICAgICAgICAgICAgICAgICAgICAgICAgIk9wZXJhdGlvbmFsRXJyb3IgaXMgbm90IGEgc3ViY2xhc3Mgb2YgRGF0YWJhc2VFcnJvciIpCgogICAgZGVmIENoZWNrSW50ZWdyaXR5RXJyb3Ioc2VsZik6CiAgICAgICAgc2VsZi5hc3NlcnRUcnVlKGlzc3ViY2xhc3Moc3FsaXRlLkludGVncml0eUVycm9yLCBzcWxpdGUuRGF0YWJhc2VFcnJvciksCiAgICAgICAgICAgICAgICAgICAgICAgICJJbnRlZ3JpdHlFcnJvciBpcyBub3QgYSBzdWJjbGFzcyBvZiBEYXRhYmFzZUVycm9yIikKCiAgICBkZWYgQ2hlY2tJbnRlcm5hbEVycm9yKHNlbGYpOgogICAgICAgIHNlbGYuYXNzZXJ0VHJ1ZShpc3N1YmNsYXNzKHNxbGl0ZS5JbnRlcm5hbEVycm9yLCBzcWxpdGUuRGF0YWJhc2VFcnJvciksCiAgICAgICAgICAgICAgICAgICAgICAgICJJbnRlcm5hbEVycm9yIGlzIG5vdCBhIHN1YmNsYXNzIG9mIERhdGFiYXNlRXJyb3IiKQoKICAgIGRlZiBDaGVja1Byb2dyYW1taW5nRXJyb3Ioc2VsZik6CiAgICAgICAgc2VsZi5hc3NlcnRUcnVlKGlzc3ViY2xhc3Moc3FsaXRlLlByb2dyYW1taW5nRXJyb3IsIHNxbGl0ZS5EYXRhYmFzZUVycm9yKSwKICAgICAgICAgICAgICAgICAgICAgICAgIlByb2dyYW1taW5nRXJyb3IgaXMgbm90IGEgc3ViY2xhc3Mgb2YgRGF0YWJhc2VFcnJvciIpCgogICAgZGVmIENoZWNrTm90U3VwcG9ydGVkRXJyb3Ioc2VsZik6CiAgICAgICAgc2VsZi5hc3NlcnRUcnVlKGlzc3ViY2xhc3Moc3FsaXRlLk5vdFN1cHBvcnRlZEVycm9yLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNxbGl0ZS5EYXRhYmFzZUVycm9yKSwKICAgICAgICAgICAgICAgICAgICAgICAgIk5vdFN1cHBvcnRlZEVycm9yIGlzIG5vdCBhIHN1YmNsYXNzIG9mIERhdGFiYXNlRXJyb3IiKQoKY2xhc3MgQ29ubmVjdGlvblRlc3RzKHVuaXR0ZXN0LlRlc3RDYXNlKToKCiAgICBkZWYgc2V0VXAoc2VsZik6CiAgICAgICAgc2VsZi5jeCA9IHNxbGl0ZS5jb25uZWN0KCI6bWVtb3J5OiIpCiAgICAgICAgY3UgPSBzZWxmLmN4LmN1cnNvcigpCiAgICAgICAgY3UuZXhlY3V0ZSgiY3JlYXRlIHRhYmxlIHRlc3QoaWQgaW50ZWdlciBwcmltYXJ5IGtleSwgbmFtZSB0ZXh0KSIpCiAgICAgICAgY3UuZXhlY3V0ZSgiaW5zZXJ0IGludG8gdGVzdChuYW1lKSB2YWx1ZXMgKD8pIiwgKCJmb28iLCkpCgogICAgZGVmIHRlYXJEb3duKHNlbGYpOgogICAgICAgIHNlbGYuY3guY2xvc2UoKQoKICAgIGRlZiBDaGVja0NvbW1pdChzZWxmKToKICAgICAgICBzZWxmLmN4LmNvbW1pdCgpCgogICAgZGVmIENoZWNrQ29tbWl0QWZ0ZXJOb0NoYW5nZXMoc2VsZik6CiAgICAgICAgIiIiCiAgICAgICAgQSBjb21taXQgc2hvdWxkIGFsc28gd29yayB3aGVuIG5vIGNoYW5nZXMgd2VyZSBtYWRlIHRvIHRoZSBkYXRhYmFzZS4KICAgICAgICAiIiIKICAgICAgICBzZWxmLmN4LmNvbW1pdCgpCiAgICAgICAgc2VsZi5jeC5jb21taXQoKQoKICAgIGRlZiBDaGVja1JvbGxiYWNrKHNlbGYpOgogICAgICAgIHNlbGYuY3gucm9sbGJhY2soKQoKICAgIGRlZiBDaGVja1JvbGxiYWNrQWZ0ZXJOb0NoYW5nZXMoc2VsZik6CiAgICAgICAgIiIiCiAgICAgICAgQSByb2xsYmFjayBzaG91bGQgYWxzbyB3b3JrIHdoZW4gbm8gY2hhbmdlcyB3ZXJlIG1hZGUgdG8gdGhlIGRhdGFiYXNlLgogICAgICAgICIiIgogICAgICAgIHNlbGYuY3gucm9sbGJhY2soKQogICAgICAgIHNlbGYuY3gucm9sbGJhY2soKQoKICAgIGRlZiBDaGVja0N1cnNvcihzZWxmKToKICAgICAgICBjdSA9IHNlbGYuY3guY3Vyc29yKCkKCiAgICBkZWYgQ2hlY2tGYWlsZWRPcGVuKHNlbGYpOgogICAgICAgIFlPVV9DQU5OT1RfT1BFTl9USElTID0gIi9mb28vYmFyL2JsYS8yMzUzNC9teWRiLmRiIgogICAgICAgIHdpdGggc2VsZi5hc3NlcnRSYWlzZXMoc3FsaXRlLk9wZXJhdGlvbmFsRXJyb3IpOgogICAgICAgICAgICBjb24gPSBzcWxpdGUuY29ubmVjdChZT1VfQ0FOTk9UX09QRU5fVEhJUykKCiAgICBkZWYgQ2hlY2tDbG9zZShzZWxmKToKICAgICAgICBzZWxmLmN4LmNsb3NlKCkKCiAgICBkZWYgQ2hlY2tFeGNlcHRpb25zKHNlbGYpOgogICAgICAgICMgT3B0aW9uYWwgREItQVBJIGV4dGVuc2lvbi4KICAgICAgICBzZWxmLmFzc2VydEVxdWFsKHNlbGYuY3guV2FybmluZywgc3FsaXRlLldhcm5pbmcpCiAgICAgICAgc2VsZi5hc3NlcnRFcXVhbChzZWxmLmN4LkVycm9yLCBzcWxpdGUuRXJyb3IpCiAgICAgICAgc2VsZi5hc3NlcnRFcXVhbChzZWxmLmN4LkludGVyZmFjZUVycm9yLCBzcWxpdGUuSW50ZXJmYWNlRXJyb3IpCiAgICAgICAgc2VsZi5hc3NlcnRFcXVhbChzZWxmLmN4LkRhdGFiYXNlRXJyb3IsIHNxbGl0ZS5EYXRhYmFzZUVycm9yKQogICAgICAgIHNlbGYuYXNzZXJ0RXF1YWwoc2VsZi5jeC5EYXRhRXJyb3IsIHNxbGl0ZS5EYXRhRXJyb3IpCiAgICAgICAgc2VsZi5hc3NlcnRFcXVhbChzZWxmLmN4Lk9wZXJhdGlvbmFsRXJyb3IsIHNxbGl0ZS5PcGVyYXRpb25hbEVycm9yKQogICAgICAgIHNlbGYuYXNzZXJ0RXF1YWwoc2VsZi5jeC5JbnRlZ3JpdHlFcnJvciwgc3FsaXRlLkludGVncml0eUVycm9yKQogICAgICAgIHNlbGYuYXNzZXJ0RXF1YWwoc2VsZi5jeC5JbnRlcm5hbEVycm9yLCBzcWxpdGUuSW50ZXJuYWxFcnJvcikKICAgICAgICBzZWxmLmFzc2VydEVxdWFsKHNlbGYuY3guUHJvZ3JhbW1pbmdFcnJvciwgc3FsaXRlLlByb2dyYW1taW5nRXJyb3IpCiAgICAgICAgc2VsZi5hc3NlcnRFcXVhbChzZWxmLmN4Lk5vdFN1cHBvcnRlZEVycm9yLCBzcWxpdGUuTm90U3VwcG9ydGVkRXJyb3IpCgogICAgZGVmIENoZWNrSW5UcmFuc2FjdGlvbihzZWxmKToKICAgICAgICAjIENhbid0IHVzZSBkYiBmcm9tIHNldFVwIGJlY2F1c2Ugd2Ugd2FudCB0byB0ZXN0IGluaXRpYWwgc3RhdGUuCiAgICAgICAgY3ggPSBzcWxpdGUuY29ubmVjdCgiOm1lbW9yeToiKQogICAgICAgIGN1ID0gY3guY3Vyc29yKCkKICAgICAgICBzZWxmLmFzc2VydEVxdWFsKGN4LmluX3RyYW5zYWN0aW9uLCBGYWxzZSkKICAgICAgICBjdS5leGVjdXRlKCJjcmVhdGUgdGFibGUgdHJhbnNhY3Rpb250ZXN0KGlkIGludGVnZXIgcHJpbWFyeSBrZXksIG5hbWUgdGV4dCkiKQogICAgICAgIHNlbGYuYXNzZXJ0RXF1YWwoY3guaW5fdHJhbnNhY3Rpb24sIEZhbHNlKQogICAgICAgIGN1LmV4ZWN1dGUoImluc2VydCBpbnRvIHRyYW5zYWN0aW9udGVzdChuYW1lKSB2YWx1ZXMgKD8pIiwgKCJmb28iLCkpCiAgICAgICAgc2VsZi5hc3NlcnRFcXVhbChjeC5pbl90cmFuc2FjdGlvbiwgVHJ1ZSkKICAgICAgICBjdS5leGVjdXRlKCJzZWxlY3QgbmFtZSBmcm9tIHRyYW5zYWN0aW9udGVzdCB3aGVyZSBuYW1lPT8iLCBbImZvbyJdKQogICAgICAgIHJvdyA9IGN1LmZldGNob25lKCkKICAgICAgICBzZWxmLmFzc2VydEVxdWFsKGN4LmluX3RyYW5zYWN0aW9uLCBUcnVlKQogICAgICAgIGN4LmNvbW1pdCgpCiAgICAgICAgc2VsZi5hc3NlcnRFcXVhbChjeC5pbl90cmFuc2FjdGlvbiwgRmFsc2UpCiAgICAgICAgY3UuZXhlY3V0ZSgic2VsZWN0IG5hbWUgZnJvbSB0cmFuc2FjdGlvbnRlc3Qgd2hlcmUgbmFtZT0/IiwgWyJmb28iXSkKICAgICAgICByb3cgPSBjdS5mZXRjaG9uZSgpCiAgICAgICAgc2VsZi5hc3NlcnRFcXVhbChjeC5pbl90cmFuc2FjdGlvbiwgRmFsc2UpCgogICAgZGVmIENoZWNrSW5UcmFuc2FjdGlvblJPKHNlbGYpOgogICAgICAgIHdpdGggc2VsZi5hc3NlcnRSYWlzZXMoQXR0cmlidXRlRXJyb3IpOgogICAgICAgICAgICBzZWxmLmN4LmluX3RyYW5zYWN0aW9uID0gVHJ1ZQoKICAgIGRlZiBDaGVja09wZW5XaXRoUGF0aExpa2VPYmplY3Qoc2VsZik6CiAgICAgICAgIiIiIENoZWNrcyB0aGF0IHdlIGNhbiBzdWNjZXNzZnVsbHkgY29ubmVjdCB0byBhIGRhdGFiYXNlIHVzaW5nIGFuIG9iamVjdCB0aGF0CiAgICAgICAgICAgIGlzIFBhdGhMaWtlLCBpLmUuIGhhcyBfX2ZzcGF0aF9fKCkuICIiIgogICAgICAgIHNlbGYuYWRkQ2xlYW51cCh1bmxpbmssIFRFU1RGTikKICAgICAgICBjbGFzcyBQYXRoOgogICAgICAgICAgICBkZWYgX19mc3BhdGhfXyhzZWxmKToKICAgICAgICAgICAgICAgIHJldHVybiBURVNURk4KICAgICAgICBwYXRoID0gUGF0aCgpCiAgICAgICAgd2l0aCBzcWxpdGUuY29ubmVjdChwYXRoKSBhcyBjeDoKICAgICAgICAgICAgY3guZXhlY3V0ZSgnY3JlYXRlIHRhYmxlIHRlc3QoaWQgaW50ZWdlciknKQoKICAgIGRlZiBDaGVja09wZW5Vcmkoc2VsZik6CiAgICAgICAgaWYgc3FsaXRlLnNxbGl0ZV92ZXJzaW9uX2luZm8gPCAoMywgNywgNyk6CiAgICAgICAgICAgIHdpdGggc2VsZi5hc3NlcnRSYWlzZXMoc3FsaXRlLk5vdFN1cHBvcnRlZEVycm9yKToKICAgICAgICAgICAgICAgIHNxbGl0ZS5jb25uZWN0KCc6bWVtb3J5OicsIHVyaT1UcnVlKQogICAgICAgICAgICByZXR1cm4KICAgICAgICBzZWxmLmFkZENsZWFudXAodW5saW5rLCBURVNURk4pCiAgICAgICAgd2l0aCBzcWxpdGUuY29ubmVjdChURVNURk4pIGFzIGN4OgogICAgICAgICAgICBjeC5leGVjdXRlKCdjcmVhdGUgdGFibGUgdGVzdChpZCBpbnRlZ2VyKScpCiAgICAgICAgd2l0aCBzcWxpdGUuY29ubmVjdCgnZmlsZTonICsgVEVTVEZOLCB1cmk9VHJ1ZSkgYXMgY3g6CiAgICAgICAgICAgIGN4LmV4ZWN1dGUoJ2luc2VydCBpbnRvIHRlc3QoaWQpIHZhbHVlcygwKScpCiAgICAgICAgd2l0aCBzcWxpdGUuY29ubmVjdCgnZmlsZTonICsgVEVTVEZOICsgJz9tb2RlPXJvJywgdXJpPVRydWUpIGFzIGN4OgogICAgICAgICAgICB3aXRoIHNlbGYuYXNzZXJ0UmFpc2VzKHNxbGl0ZS5PcGVyYXRpb25hbEVycm9yKToKICAgICAgICAgICAgICAgIGN4LmV4ZWN1dGUoJ2luc2VydCBpbnRvIHRlc3QoaWQpIHZhbHVlcygxKScpCgogICAgQHVuaXR0ZXN0LnNraXBJZihzcWxpdGUuc3FsaXRlX3ZlcnNpb25faW5mbyA+PSAoMywgMywgMSksCiAgICAgICAgICAgICAgICAgICAgICduZWVkcyBzcWxpdGUgdmVyc2lvbnMgb2xkZXIgdGhhbiAzLjMuMScpCiAgICBkZWYgQ2hlY2tTYW1lVGhyZWFkRXJyb3JPbk9sZFZlcnNpb24oc2VsZik6CiAgICAgICAgd2l0aCBzZWxmLmFzc2VydFJhaXNlcyhzcWxpdGUuTm90U3VwcG9ydGVkRXJyb3IpIGFzIGNtOgogICAgICAgICAgICBzcWxpdGUuY29ubmVjdCgnOm1lbW9yeTonLCBjaGVja19zYW1lX3RocmVhZD1GYWxzZSkKICAgICAgICBzZWxmLmFzc2VydEVxdWFsKHN0cihjbS5leGNlcHRpb24pLCAnc2hhcmVkIGNvbm5lY3Rpb25zIG5vdCBhdmFpbGFibGUnKQoKY2xhc3MgQ3Vyc29yVGVzdHModW5pdHRlc3QuVGVzdENhc2UpOgogICAgZGVmIHNldFVwKHNlbGYpOgogICAgICAgIHNlbGYuY3ggPSBzcWxpdGUuY29ubmVjdCgiOm1lbW9yeToiKQogICAgICAgIHNlbGYuY3UgPSBzZWxmLmN4LmN1cnNvcigpCiAgICAgICAgc2VsZi5jdS5leGVjdXRlKAogICAgICAgICAgICAiY3JlYXRlIHRhYmxlIHRlc3QoaWQgaW50ZWdlciBwcmltYXJ5IGtleSwgbmFtZSB0ZXh0LCAiCiAgICAgICAgICAgICJpbmNvbWUgbnVtYmVyLCB1bmlxdWVfdGVzdCB0ZXh0IHVuaXF1ZSkiCiAgICAgICAgKQogICAgICAgIHNlbGYuY3UuZXhlY3V0ZSgiaW5zZXJ0IGludG8gdGVzdChuYW1lKSB2YWx1ZXMgKD8pIiwgKCJmb28iLCkpCgogICAgZGVmIHRlYXJEb3duKHNlbGYpOgogICAgICAgIHNlbGYuY3UuY2xvc2UoKQogICAgICAgIHNlbGYuY3guY2xvc2UoKQoKICAgIGRlZiBDaGVja0V4ZWN1dGVOb0FyZ3Moc2VsZik6CiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJkZWxldGUgZnJvbSB0ZXN0IikKCiAgICBkZWYgQ2hlY2tFeGVjdXRlSWxsZWdhbFNxbChzZWxmKToKICAgICAgICB3aXRoIHNlbGYuYXNzZXJ0UmFpc2VzKHNxbGl0ZS5PcGVyYXRpb25hbEVycm9yKToKICAgICAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJzZWxlY3QgYXNkZiIpCgogICAgZGVmIENoZWNrRXhlY3V0ZVRvb011Y2hTcWwoc2VsZik6CiAgICAgICAgd2l0aCBzZWxmLmFzc2VydFJhaXNlcyhzcWxpdGUuV2FybmluZyk6CiAgICAgICAgICAgIHNlbGYuY3UuZXhlY3V0ZSgic2VsZWN0IDUrNDsgc2VsZWN0IDQrNSIpCgogICAgZGVmIENoZWNrRXhlY3V0ZVRvb011Y2hTcWwyKHNlbGYpOgogICAgICAgIHNlbGYuY3UuZXhlY3V0ZSgic2VsZWN0IDUrNDsgLS0gZm9vIGJhciIpCgogICAgZGVmIENoZWNrRXhlY3V0ZVRvb011Y2hTcWwzKHNlbGYpOgogICAgICAgIHNlbGYuY3UuZXhlY3V0ZSgiIiIKICAgICAgICAgICAgc2VsZWN0IDUrNDsKCiAgICAgICAgICAgIC8qCiAgICAgICAgICAgIGZvbwogICAgICAgICAgICAqLwogICAgICAgICAgICAiIiIpCgogICAgZGVmIENoZWNrRXhlY3V0ZVdyb25nU3FsQXJnKHNlbGYpOgogICAgICAgIHdpdGggc2VsZi5hc3NlcnRSYWlzZXMoVHlwZUVycm9yKToKICAgICAgICAgICAgc2VsZi5jdS5leGVjdXRlKDQyKQoKICAgIGRlZiBDaGVja0V4ZWN1dGVBcmdJbnQoc2VsZik6CiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJpbnNlcnQgaW50byB0ZXN0KGlkKSB2YWx1ZXMgKD8pIiwgKDQyLCkpCgogICAgZGVmIENoZWNrRXhlY3V0ZUFyZ0Zsb2F0KHNlbGYpOgogICAgICAgIHNlbGYuY3UuZXhlY3V0ZSgiaW5zZXJ0IGludG8gdGVzdChpbmNvbWUpIHZhbHVlcyAoPykiLCAoMjUwMC4zMiwpKQoKICAgIGRlZiBDaGVja0V4ZWN1dGVBcmdTdHJpbmcoc2VsZik6CiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJpbnNlcnQgaW50byB0ZXN0KG5hbWUpIHZhbHVlcyAoPykiLCAoIkh1Z28iLCkpCgogICAgZGVmIENoZWNrRXhlY3V0ZUFyZ1N0cmluZ1dpdGhaZXJvQnl0ZShzZWxmKToKICAgICAgICBzZWxmLmN1LmV4ZWN1dGUoImluc2VydCBpbnRvIHRlc3QobmFtZSkgdmFsdWVzICg/KSIsICgiSHVceDAwZ28iLCkpCgogICAgICAgIHNlbGYuY3UuZXhlY3V0ZSgic2VsZWN0IG5hbWUgZnJvbSB0ZXN0IHdoZXJlIGlkPT8iLCAoc2VsZi5jdS5sYXN0cm93aWQsKSkKICAgICAgICByb3cgPSBzZWxmLmN1LmZldGNob25lKCkKICAgICAgICBzZWxmLmFzc2VydEVxdWFsKHJvd1swXSwgIkh1XHgwMGdvIikKCiAgICBkZWYgQ2hlY2tFeGVjdXRlTm9uSXRlcmFibGUoc2VsZik6CiAgICAgICAgd2l0aCBzZWxmLmFzc2VydFJhaXNlcyhWYWx1ZUVycm9yKSBhcyBjbToKICAgICAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJpbnNlcnQgaW50byB0ZXN0KGlkKSB2YWx1ZXMgKD8pIiwgNDIpCiAgICAgICAgc2VsZi5hc3NlcnRFcXVhbChzdHIoY20uZXhjZXB0aW9uKSwgJ3BhcmFtZXRlcnMgYXJlIG9mIHVuc3VwcG9ydGVkIHR5cGUnKQoKICAgIGRlZiBDaGVja0V4ZWN1dGVXcm9uZ05vT2ZBcmdzMShzZWxmKToKICAgICAgICAjIHRvbyBtYW55IHBhcmFtZXRlcnMKICAgICAgICB3aXRoIHNlbGYuYXNzZXJ0UmFpc2VzKHNxbGl0ZS5Qcm9ncmFtbWluZ0Vycm9yKToKICAgICAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJpbnNlcnQgaW50byB0ZXN0KGlkKSB2YWx1ZXMgKD8pIiwgKDE3LCAiRWdvbiIpKQoKICAgIGRlZiBDaGVja0V4ZWN1dGVXcm9uZ05vT2ZBcmdzMihzZWxmKToKICAgICAgICAjIHRvbyBsaXR0bGUgcGFyYW1ldGVycwogICAgICAgIHdpdGggc2VsZi5hc3NlcnRSYWlzZXMoc3FsaXRlLlByb2dyYW1taW5nRXJyb3IpOgogICAgICAgICAgICBzZWxmLmN1LmV4ZWN1dGUoImluc2VydCBpbnRvIHRlc3QoaWQpIHZhbHVlcyAoPykiKQoKICAgIGRlZiBDaGVja0V4ZWN1dGVXcm9uZ05vT2ZBcmdzMyhzZWxmKToKICAgICAgICAjIG5vIHBhcmFtZXRlcnMsIHBhcmFtZXRlcnMgYXJlIG5lZWRlZAogICAgICAgIHdpdGggc2VsZi5hc3NlcnRSYWlzZXMoc3FsaXRlLlByb2dyYW1taW5nRXJyb3IpOgogICAgICAgICAgICBzZWxmLmN1LmV4ZWN1dGUoImluc2VydCBpbnRvIHRlc3QoaWQpIHZhbHVlcyAoPykiKQoKICAgIGRlZiBDaGVja0V4ZWN1dGVQYXJhbUxpc3Qoc2VsZik6CiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJpbnNlcnQgaW50byB0ZXN0KG5hbWUpIHZhbHVlcyAoJ2ZvbycpIikKICAgICAgICBzZWxmLmN1LmV4ZWN1dGUoInNlbGVjdCBuYW1lIGZyb20gdGVzdCB3aGVyZSBuYW1lPT8iLCBbImZvbyJdKQogICAgICAgIHJvdyA9IHNlbGYuY3UuZmV0Y2hvbmUoKQogICAgICAgIHNlbGYuYXNzZXJ0RXF1YWwocm93WzBdLCAiZm9vIikKCiAgICBkZWYgQ2hlY2tFeGVjdXRlUGFyYW1TZXF1ZW5jZShzZWxmKToKICAgICAgICBjbGFzcyBMKG9iamVjdCk6CiAgICAgICAgICAgIGRlZiBfX2xlbl9fKHNlbGYpOgogICAgICAgICAgICAgICAgcmV0dXJuIDEKICAgICAgICAgICAgZGVmIF9fZ2V0aXRlbV9fKHNlbGYsIHgpOgogICAgICAgICAgICAgICAgYXNzZXJ0IHggPT0gMAogICAgICAgICAgICAgICAgcmV0dXJuICJmb28iCgogICAgICAgIHNlbGYuY3UuZXhlY3V0ZSgiaW5zZXJ0IGludG8gdGVzdChuYW1lKSB2YWx1ZXMgKCdmb28nKSIpCiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJzZWxlY3QgbmFtZSBmcm9tIHRlc3Qgd2hlcmUgbmFtZT0/IiwgTCgpKQogICAgICAgIHJvdyA9IHNlbGYuY3UuZmV0Y2hvbmUoKQogICAgICAgIHNlbGYuYXNzZXJ0RXF1YWwocm93WzBdLCAiZm9vIikKCiAgICBkZWYgQ2hlY2tFeGVjdXRlRGljdE1hcHBpbmcoc2VsZik6CiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJpbnNlcnQgaW50byB0ZXN0KG5hbWUpIHZhbHVlcyAoJ2ZvbycpIikKICAgICAgICBzZWxmLmN1LmV4ZWN1dGUoInNlbGVjdCBuYW1lIGZyb20gdGVzdCB3aGVyZSBuYW1lPTpuYW1lIiwgeyJuYW1lIjogImZvbyJ9KQogICAgICAgIHJvdyA9IHNlbGYuY3UuZmV0Y2hvbmUoKQogICAgICAgIHNlbGYuYXNzZXJ0RXF1YWwocm93WzBdLCAiZm9vIikKCiAgICBkZWYgQ2hlY2tFeGVjdXRlRGljdE1hcHBpbmdfTWFwcGluZyhzZWxmKToKICAgICAgICBjbGFzcyBEKGRpY3QpOgogICAgICAgICAgICBkZWYgX19taXNzaW5nX18oc2VsZiwga2V5KToKICAgICAgICAgICAgICAgIHJldHVybiAiZm9vIgoKICAgICAgICBzZWxmLmN1LmV4ZWN1dGUoImluc2VydCBpbnRvIHRlc3QobmFtZSkgdmFsdWVzICgnZm9vJykiKQogICAgICAgIHNlbGYuY3UuZXhlY3V0ZSgic2VsZWN0IG5hbWUgZnJvbSB0ZXN0IHdoZXJlIG5hbWU9Om5hbWUiLCBEKCkpCiAgICAgICAgcm93ID0gc2VsZi5jdS5mZXRjaG9uZSgpCiAgICAgICAgc2VsZi5hc3NlcnRFcXVhbChyb3dbMF0sICJmb28iKQoKICAgIGRlZiBDaGVja0V4ZWN1dGVEaWN0TWFwcGluZ1Rvb0xpdHRsZUFyZ3Moc2VsZik6CiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJpbnNlcnQgaW50byB0ZXN0KG5hbWUpIHZhbHVlcyAoJ2ZvbycpIikKICAgICAgICB3aXRoIHNlbGYuYXNzZXJ0UmFpc2VzKHNxbGl0ZS5Qcm9ncmFtbWluZ0Vycm9yKToKICAgICAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJzZWxlY3QgbmFtZSBmcm9tIHRlc3Qgd2hlcmUgbmFtZT06bmFtZSBhbmQgaWQ9OmlkIiwgeyJuYW1lIjogImZvbyJ9KQoKICAgIGRlZiBDaGVja0V4ZWN1dGVEaWN0TWFwcGluZ05vQXJncyhzZWxmKToKICAgICAgICBzZWxmLmN1LmV4ZWN1dGUoImluc2VydCBpbnRvIHRlc3QobmFtZSkgdmFsdWVzICgnZm9vJykiKQogICAgICAgIHdpdGggc2VsZi5hc3NlcnRSYWlzZXMoc3FsaXRlLlByb2dyYW1taW5nRXJyb3IpOgogICAgICAgICAgICBzZWxmLmN1LmV4ZWN1dGUoInNlbGVjdCBuYW1lIGZyb20gdGVzdCB3aGVyZSBuYW1lPTpuYW1lIikKCiAgICBkZWYgQ2hlY2tFeGVjdXRlRGljdE1hcHBpbmdVbm5hbWVkKHNlbGYpOgogICAgICAgIHNlbGYuY3UuZXhlY3V0ZSgiaW5zZXJ0IGludG8gdGVzdChuYW1lKSB2YWx1ZXMgKCdmb28nKSIpCiAgICAgICAgd2l0aCBzZWxmLmFzc2VydFJhaXNlcyhzcWxpdGUuUHJvZ3JhbW1pbmdFcnJvcik6CiAgICAgICAgICAgIHNlbGYuY3UuZXhlY3V0ZSgic2VsZWN0IG5hbWUgZnJvbSB0ZXN0IHdoZXJlIG5hbWU9PyIsIHsibmFtZSI6ICJmb28ifSkKCiAgICBkZWYgQ2hlY2tDbG9zZShzZWxmKToKICAgICAgICBzZWxmLmN1LmNsb3NlKCkKCiAgICBkZWYgQ2hlY2tSb3djb3VudEV4ZWN1dGUoc2VsZik6CiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJkZWxldGUgZnJvbSB0ZXN0IikKICAgICAgICBzZWxmLmN1LmV4ZWN1dGUoImluc2VydCBpbnRvIHRlc3QobmFtZSkgdmFsdWVzICgnZm9vJykiKQogICAgICAgIHNlbGYuY3UuZXhlY3V0ZSgiaW5zZXJ0IGludG8gdGVzdChuYW1lKSB2YWx1ZXMgKCdmb28nKSIpCiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJ1cGRhdGUgdGVzdCBzZXQgbmFtZT0nYmFyJyIpCiAgICAgICAgc2VsZi5hc3NlcnRFcXVhbChzZWxmLmN1LnJvd2NvdW50LCAyKQoKICAgIGRlZiBDaGVja1Jvd2NvdW50U2VsZWN0KHNlbGYpOgogICAgICAgICIiIgogICAgICAgIHB5c3FsaXRlIGRvZXMgbm90IGtub3cgdGhlIHJvd2NvdW50IG9mIFNFTEVDVCBzdGF0ZW1lbnRzLCBiZWNhdXNlIHdlCiAgICAgICAgZG9uJ3QgZmV0Y2ggYWxsIHJvd3MgYWZ0ZXIgZXhlY3V0aW5nIHRoZSBzZWxlY3Qgc3RhdGVtZW50LiBUaGUgcm93Y291bnQKICAgICAgICBoYXMgdGh1cyB0byBiZSAtMS4KICAgICAgICAiIiIKICAgICAgICBzZWxmLmN1LmV4ZWN1dGUoInNlbGVjdCA1IHVuaW9uIHNlbGVjdCA2IikKICAgICAgICBzZWxmLmFzc2VydEVxdWFsKHNlbGYuY3Uucm93Y291bnQsIC0xKQoKICAgIGRlZiBDaGVja1Jvd2NvdW50RXhlY3V0ZW1hbnkoc2VsZik6CiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJkZWxldGUgZnJvbSB0ZXN0IikKICAgICAgICBzZWxmLmN1LmV4ZWN1dGVtYW55KCJpbnNlcnQgaW50byB0ZXN0KG5hbWUpIHZhbHVlcyAoPykiLCBbKDEsKSwgKDIsKSwgKDMsKV0pCiAgICAgICAgc2VsZi5hc3NlcnRFcXVhbChzZWxmLmN1LnJvd2NvdW50LCAzKQoKICAgIGRlZiBDaGVja1RvdGFsQ2hhbmdlcyhzZWxmKToKICAgICAgICBzZWxmLmN1LmV4ZWN1dGUoImluc2VydCBpbnRvIHRlc3QobmFtZSkgdmFsdWVzICgnZm9vJykiKQogICAgICAgIHNlbGYuY3UuZXhlY3V0ZSgiaW5zZXJ0IGludG8gdGVzdChuYW1lKSB2YWx1ZXMgKCdmb28nKSIpCiAgICAgICAgc2VsZi5hc3NlcnRMZXNzKDIsIHNlbGYuY3gudG90YWxfY2hhbmdlcywgbXNnPSd0b3RhbCBjaGFuZ2VzIHJlcG9ydGVkIHdyb25nIHZhbHVlJykKCiAgICAjIENoZWNrcyBmb3IgZXhlY3V0ZW1hbnk6CiAgICAjIFNlcXVlbmNlcyBhcmUgcmVxdWlyZWQgYnkgdGhlIERCLUFQSSwgaXRlcmF0b3JzCiAgICAjIGVuaGFuY2VtZW50cyBpbiBweXNxbGl0ZS4KCiAgICBkZWYgQ2hlY2tFeGVjdXRlTWFueVNlcXVlbmNlKHNlbGYpOgogICAgICAgIHNlbGYuY3UuZXhlY3V0ZW1hbnkoImluc2VydCBpbnRvIHRlc3QoaW5jb21lKSB2YWx1ZXMgKD8pIiwgWyh4LCkgZm9yIHggaW4gcmFuZ2UoMTAwLCAxMTApXSkKCiAgICBkZWYgQ2hlY2tFeGVjdXRlTWFueUl0ZXJhdG9yKHNlbGYpOgogICAgICAgIGNsYXNzIE15SXRlcjoKICAgICAgICAgICAgZGVmIF9faW5pdF9fKHNlbGYpOgogICAgICAgICAgICAgICAgc2VsZi52YWx1ZSA9IDUKCiAgICAgICAgICAgIGRlZiBfX25leHRfXyhzZWxmKToKICAgICAgICAgICAgICAgIGlmIHNlbGYudmFsdWUgPT0gMTA6CiAgICAgICAgICAgICAgICAgICAgcmFpc2UgU3RvcEl0ZXJhdGlvbgogICAgICAgICAgICAgICAgZWxzZToKICAgICAgICAgICAgICAgICAgICBzZWxmLnZhbHVlICs9IDEKICAgICAgICAgICAgICAgICAgICByZXR1cm4gKHNlbGYudmFsdWUsKQoKICAgICAgICBzZWxmLmN1LmV4ZWN1dGVtYW55KCJpbnNlcnQgaW50byB0ZXN0KGluY29tZSkgdmFsdWVzICg/KSIsIE15SXRlcigpKQoKICAgIGRlZiBDaGVja0V4ZWN1dGVNYW55R2VuZXJhdG9yKHNlbGYpOgogICAgICAgIGRlZiBteWdlbigpOgogICAgICAgICAgICBmb3IgaSBpbiByYW5nZSg1KToKICAgICAgICAgICAgICAgIHlpZWxkIChpLCkKCiAgICAgICAgc2VsZi5jdS5leGVjdXRlbWFueSgiaW5zZXJ0IGludG8gdGVzdChpbmNvbWUpIHZhbHVlcyAoPykiLCBteWdlbigpKQoKICAgIGRlZiBDaGVja0V4ZWN1dGVNYW55V3JvbmdTcWxBcmcoc2VsZik6CiAgICAgICAgd2l0aCBzZWxmLmFzc2VydFJhaXNlcyhUeXBlRXJyb3IpOgogICAgICAgICAgICBzZWxmLmN1LmV4ZWN1dGVtYW55KDQyLCBbKDMsKV0pCgogICAgZGVmIENoZWNrRXhlY3V0ZU1hbnlTZWxlY3Qoc2VsZik6CiAgICAgICAgd2l0aCBzZWxmLmFzc2VydFJhaXNlcyhzcWxpdGUuUHJvZ3JhbW1pbmdFcnJvcik6CiAgICAgICAgICAgIHNlbGYuY3UuZXhlY3V0ZW1hbnkoInNlbGVjdCA/IiwgWygzLCldKQoKICAgIGRlZiBDaGVja0V4ZWN1dGVNYW55Tm90SXRlcmFibGUoc2VsZik6CiAgICAgICAgd2l0aCBzZWxmLmFzc2VydFJhaXNlcyhUeXBlRXJyb3IpOgogICAgICAgICAgICBzZWxmLmN1LmV4ZWN1dGVtYW55KCJpbnNlcnQgaW50byB0ZXN0KGluY29tZSkgdmFsdWVzICg/KSIsIDQyKQoKICAgIGRlZiBDaGVja0ZldGNoSXRlcihzZWxmKToKICAgICAgICAjIE9wdGlvbmFsIERCLUFQSSBleHRlbnNpb24uCiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJkZWxldGUgZnJvbSB0ZXN0IikKICAgICAgICBzZWxmLmN1LmV4ZWN1dGUoImluc2VydCBpbnRvIHRlc3QoaWQpIHZhbHVlcyAoPykiLCAoNSwpKQogICAgICAgIHNlbGYuY3UuZXhlY3V0ZSgiaW5zZXJ0IGludG8gdGVzdChpZCkgdmFsdWVzICg/KSIsICg2LCkpCiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJzZWxlY3QgaWQgZnJvbSB0ZXN0IG9yZGVyIGJ5IGlkIikKICAgICAgICBsc3QgPSBbXQogICAgICAgIGZvciByb3cgaW4gc2VsZi5jdToKICAgICAgICAgICAgbHN0LmFwcGVuZChyb3dbMF0pCiAgICAgICAgc2VsZi5hc3NlcnRFcXVhbChsc3RbMF0sIDUpCiAgICAgICAgc2VsZi5hc3NlcnRFcXVhbChsc3RbMV0sIDYpCgogICAgZGVmIENoZWNrRmV0Y2hvbmUoc2VsZik6CiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJzZWxlY3QgbmFtZSBmcm9tIHRlc3QiKQogICAgICAgIHJvdyA9IHNlbGYuY3UuZmV0Y2hvbmUoKQogICAgICAgIHNlbGYuYXNzZXJ0RXF1YWwocm93WzBdLCAiZm9vIikKICAgICAgICByb3cgPSBzZWxmLmN1LmZldGNob25lKCkKICAgICAgICBzZWxmLmFzc2VydEVxdWFsKHJvdywgTm9uZSkKCiAgICBkZWYgQ2hlY2tGZXRjaG9uZU5vU3RhdGVtZW50KHNlbGYpOgogICAgICAgIGN1ciA9IHNlbGYuY3guY3Vyc29yKCkKICAgICAgICByb3cgPSBjdXIuZmV0Y2hvbmUoKQogICAgICAgIHNlbGYuYXNzZXJ0RXF1YWwocm93LCBOb25lKQoKICAgIGRlZiBDaGVja0FycmF5U2l6ZShzZWxmKToKICAgICAgICAjIG11c3QgZGVmYXVsdCBvdCAxCiAgICAgICAgc2VsZi5hc3NlcnRFcXVhbChzZWxmLmN1LmFycmF5c2l6ZSwgMSkKCiAgICAgICAgIyBub3cgc2V0IHRvIDIKICAgICAgICBzZWxmLmN1LmFycmF5c2l6ZSA9IDIKCiAgICAgICAgIyBub3cgbWFrZSB0aGUgcXVlcnkgcmV0dXJuIDMgcm93cwogICAgICAgIHNlbGYuY3UuZXhlY3V0ZSgiZGVsZXRlIGZyb20gdGVzdCIpCiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJpbnNlcnQgaW50byB0ZXN0KG5hbWUpIHZhbHVlcyAoJ0EnKSIpCiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJpbnNlcnQgaW50byB0ZXN0KG5hbWUpIHZhbHVlcyAoJ0InKSIpCiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJpbnNlcnQgaW50byB0ZXN0KG5hbWUpIHZhbHVlcyAoJ0MnKSIpCiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJzZWxlY3QgbmFtZSBmcm9tIHRlc3QiKQogICAgICAgIHJlcyA9IHNlbGYuY3UuZmV0Y2htYW55KCkKCiAgICAgICAgc2VsZi5hc3NlcnRFcXVhbChsZW4ocmVzKSwgMikKCiAgICBkZWYgQ2hlY2tGZXRjaG1hbnkoc2VsZik6CiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJzZWxlY3QgbmFtZSBmcm9tIHRlc3QiKQogICAgICAgIHJlcyA9IHNlbGYuY3UuZmV0Y2htYW55KDEwMCkKICAgICAgICBzZWxmLmFzc2VydEVxdWFsKGxlbihyZXMpLCAxKQogICAgICAgIHJlcyA9IHNlbGYuY3UuZmV0Y2htYW55KDEwMCkKICAgICAgICBzZWxmLmFzc2VydEVxdWFsKHJlcywgW10pCgogICAgZGVmIENoZWNrRmV0Y2htYW55S3dBcmcoc2VsZik6CiAgICAgICAgIiIiQ2hlY2tzIGlmIGZldGNobWFueSB3b3JrcyB3aXRoIGtleXdvcmQgYXJndW1lbnRzIiIiCiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJzZWxlY3QgbmFtZSBmcm9tIHRlc3QiKQogICAgICAgIHJlcyA9IHNlbGYuY3UuZmV0Y2htYW55KHNpemU9MTAwKQogICAgICAgIHNlbGYuYXNzZXJ0RXF1YWwobGVuKHJlcyksIDEpCgogICAgZGVmIENoZWNrRmV0Y2hhbGwoc2VsZik6CiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJzZWxlY3QgbmFtZSBmcm9tIHRlc3QiKQogICAgICAgIHJlcyA9IHNlbGYuY3UuZmV0Y2hhbGwoKQogICAgICAgIHNlbGYuYXNzZXJ0RXF1YWwobGVuKHJlcyksIDEpCiAgICAgICAgcmVzID0gc2VsZi5jdS5mZXRjaGFsbCgpCiAgICAgICAgc2VsZi5hc3NlcnRFcXVhbChyZXMsIFtdKQoKICAgIGRlZiBDaGVja1NldGlucHV0c2l6ZXMoc2VsZik6CiAgICAgICAgc2VsZi5jdS5zZXRpbnB1dHNpemVzKFszLCA0LCA1XSkKCiAgICBkZWYgQ2hlY2tTZXRvdXRwdXRzaXplKHNlbGYpOgogICAgICAgIHNlbGYuY3Uuc2V0b3V0cHV0c2l6ZSg1LCAwKQoKICAgIGRlZiBDaGVja1NldG91dHB1dHNpemVOb0NvbHVtbihzZWxmKToKICAgICAgICBzZWxmLmN1LnNldG91dHB1dHNpemUoNDIpCgogICAgZGVmIENoZWNrQ3Vyc29yQ29ubmVjdGlvbihzZWxmKToKICAgICAgICAjIE9wdGlvbmFsIERCLUFQSSBleHRlbnNpb24uCiAgICAgICAgc2VsZi5hc3NlcnRFcXVhbChzZWxmLmN1LmNvbm5lY3Rpb24sIHNlbGYuY3gpCgogICAgZGVmIENoZWNrV3JvbmdDdXJzb3JDYWxsYWJsZShzZWxmKToKICAgICAgICB3aXRoIHNlbGYuYXNzZXJ0UmFpc2VzKFR5cGVFcnJvcik6CiAgICAgICAgICAgIGRlZiBmKCk6IHBhc3MKICAgICAgICAgICAgY3VyID0gc2VsZi5jeC5jdXJzb3IoZikKCiAgICBkZWYgQ2hlY2tDdXJzb3JXcm9uZ0NsYXNzKHNlbGYpOgogICAgICAgIGNsYXNzIEZvbzogcGFzcwogICAgICAgIGZvbyA9IEZvbygpCiAgICAgICAgd2l0aCBzZWxmLmFzc2VydFJhaXNlcyhUeXBlRXJyb3IpOgogICAgICAgICAgICBjdXIgPSBzcWxpdGUuQ3Vyc29yKGZvbykKCiAgICBkZWYgQ2hlY2tMYXN0Um93SURPblJlcGxhY2Uoc2VsZik6CiAgICAgICAgIiIiCiAgICAgICAgSU5TRVJUIE9SIFJFUExBQ0UgYW5kIFJFUExBQ0UgSU5UTyBzaG91bGQgcHJvZHVjZSB0aGUgc2FtZSBiZWhhdmlvci4KICAgICAgICAiIiIKICAgICAgICBzcWwgPSAne30gSU5UTyB0ZXN0KGlkLCB1bmlxdWVfdGVzdCkgVkFMVUVTICg/LCA/KScKICAgICAgICBmb3Igc3RhdGVtZW50IGluICgnSU5TRVJUIE9SIFJFUExBQ0UnLCAnUkVQTEFDRScpOgogICAgICAgICAgICB3aXRoIHNlbGYuc3ViVGVzdChzdGF0ZW1lbnQ9c3RhdGVtZW50KToKICAgICAgICAgICAgICAgIHNlbGYuY3UuZXhlY3V0ZShzcWwuZm9ybWF0KHN0YXRlbWVudCksICgxLCAnZm9vJykpCiAgICAgICAgICAgICAgICBzZWxmLmFzc2VydEVxdWFsKHNlbGYuY3UubGFzdHJvd2lkLCAxKQoKICAgIGRlZiBDaGVja0xhc3RSb3dJRE9uSWdub3JlKHNlbGYpOgogICAgICAgIHNlbGYuY3UuZXhlY3V0ZSgKICAgICAgICAgICAgImluc2VydCBvciBpZ25vcmUgaW50byB0ZXN0KHVuaXF1ZV90ZXN0KSB2YWx1ZXMgKD8pIiwKICAgICAgICAgICAgKCd0ZXN0JywpKQogICAgICAgIHNlbGYuYXNzZXJ0RXF1YWwoc2VsZi5jdS5sYXN0cm93aWQsIDIpCiAgICAgICAgc2VsZi5jdS5leGVjdXRlKAogICAgICAgICAgICAiaW5zZXJ0IG9yIGlnbm9yZSBpbnRvIHRlc3QodW5pcXVlX3Rlc3QpIHZhbHVlcyAoPykiLAogICAgICAgICAgICAoJ3Rlc3QnLCkpCiAgICAgICAgc2VsZi5hc3NlcnRFcXVhbChzZWxmLmN1Lmxhc3Ryb3dpZCwgMikKCiAgICBkZWYgQ2hlY2tMYXN0Um93SURJbnNlcnRPUihzZWxmKToKICAgICAgICByZXN1bHRzID0gW10KICAgICAgICBmb3Igc3RhdGVtZW50IGluICgnRkFJTCcsICdBQk9SVCcsICdST0xMQkFDSycpOgogICAgICAgICAgICBzcWwgPSAnSU5TRVJUIE9SIHt9IElOVE8gdGVzdCh1bmlxdWVfdGVzdCkgVkFMVUVTICg/KScKICAgICAgICAgICAgd2l0aCBzZWxmLnN1YlRlc3Qoc3RhdGVtZW50PSdJTlNFUlQgT1Ige30nLmZvcm1hdChzdGF0ZW1lbnQpKToKICAgICAgICAgICAgICAgIHNlbGYuY3UuZXhlY3V0ZShzcWwuZm9ybWF0KHN0YXRlbWVudCksIChzdGF0ZW1lbnQsKSkKICAgICAgICAgICAgICAgIHJlc3VsdHMuYXBwZW5kKChzdGF0ZW1lbnQsIHNlbGYuY3UubGFzdHJvd2lkKSkKICAgICAgICAgICAgICAgIHdpdGggc2VsZi5hc3NlcnRSYWlzZXMoc3FsaXRlLkludGVncml0eUVycm9yKToKICAgICAgICAgICAgICAgICAgICBzZWxmLmN1LmV4ZWN1dGUoc3FsLmZvcm1hdChzdGF0ZW1lbnQpLCAoc3RhdGVtZW50LCkpCiAgICAgICAgICAgICAgICByZXN1bHRzLmFwcGVuZCgoc3RhdGVtZW50LCBzZWxmLmN1Lmxhc3Ryb3dpZCkpCiAgICAgICAgZXhwZWN0ZWQgPSBbCiAgICAgICAgICAgICgnRkFJTCcsIDIpLCAoJ0ZBSUwnLCAyKSwKICAgICAgICAgICAgKCdBQk9SVCcsIDMpLCAoJ0FCT1JUJywgMyksCiAgICAgICAgICAgICgnUk9MTEJBQ0snLCA0KSwgKCdST0xMQkFDSycsIDQpLAogICAgICAgIF0KICAgICAgICBzZWxmLmFzc2VydEVxdWFsKHJlc3VsdHMsIGV4cGVjdGVkKQoKCmNsYXNzIFRocmVhZFRlc3RzKHVuaXR0ZXN0LlRlc3RDYXNlKToKICAgIGRlZiBzZXRVcChzZWxmKToKICAgICAgICBzZWxmLmNvbiA9IHNxbGl0ZS5jb25uZWN0KCI6bWVtb3J5OiIpCiAgICAgICAgc2VsZi5jdXIgPSBzZWxmLmNvbi5jdXJzb3IoKQogICAgICAgIHNlbGYuY3VyLmV4ZWN1dGUoImNyZWF0ZSB0YWJsZSB0ZXN0KGlkIGludGVnZXIgcHJpbWFyeSBrZXksIG5hbWUgdGV4dCwgYmluIGJpbmFyeSwgcmF0aW8gbnVtYmVyLCB0cyB0aW1lc3RhbXApIikKCiAgICBkZWYgdGVhckRvd24oc2VsZik6CiAgICAgICAgc2VsZi5jdXIuY2xvc2UoKQogICAgICAgIHNlbGYuY29uLmNsb3NlKCkKCiAgICBkZWYgQ2hlY2tDb25DdXJzb3Ioc2VsZik6CiAgICAgICAgZGVmIHJ1bihjb24sIGVycm9ycyk6CiAgICAgICAgICAgIHRyeToKICAgICAgICAgICAgICAgIGN1ciA9IGNvbi5jdXJzb3IoKQogICAgICAgICAgICAgICAgZXJyb3JzLmFwcGVuZCgiZGlkIG5vdCByYWlzZSBQcm9ncmFtbWluZ0Vycm9yIikKICAgICAgICAgICAgICAgIHJldHVybgogICAgICAgICAgICBleGNlcHQgc3FsaXRlLlByb2dyYW1taW5nRXJyb3I6CiAgICAgICAgICAgICAgICByZXR1cm4KICAgICAgICAgICAgZXhjZXB0OgogICAgICAgICAgICAgICAgZXJyb3JzLmFwcGVuZCgicmFpc2VkIHdyb25nIGV4Y2VwdGlvbiIpCgogICAgICAgIGVycm9ycyA9IFtdCiAgICAgICAgdCA9IHRocmVhZGluZy5UaHJlYWQodGFyZ2V0PXJ1biwga3dhcmdzPXsiY29uIjogc2VsZi5jb24sICJlcnJvcnMiOiBlcnJvcnN9KQogICAgICAgIHQuc3RhcnQoKQogICAgICAgIHQuam9pbigpCiAgICAgICAgaWYgbGVuKGVycm9ycykgPiAwOgogICAgICAgICAgICBzZWxmLmZhaWwoIlxuIi5qb2luKGVycm9ycykpCgogICAgZGVmIENoZWNrQ29uQ29tbWl0KHNlbGYpOgogICAgICAgIGRlZiBydW4oY29uLCBlcnJvcnMpOgogICAgICAgICAgICB0cnk6CiAgICAgICAgICAgICAgICBjb24uY29tbWl0KCkKICAgICAgICAgICAgICAgIGVycm9ycy5hcHBlbmQoImRpZCBub3QgcmFpc2UgUHJvZ3JhbW1pbmdFcnJvciIpCiAgICAgICAgICAgICAgICByZXR1cm4KICAgICAgICAgICAgZXhjZXB0IHNxbGl0ZS5Qcm9ncmFtbWluZ0Vycm9yOgogICAgICAgICAgICAgICAgcmV0dXJuCiAgICAgICAgICAgIGV4Y2VwdDoKICAgICAgICAgICAgICAgIGVycm9ycy5hcHBlbmQoInJhaXNlZCB3cm9uZyBleGNlcHRpb24iKQoKICAgICAgICBlcnJvcnMgPSBbXQogICAgICAgIHQgPSB0aHJlYWRpbmcuVGhyZWFkKHRhcmdldD1ydW4sIGt3YXJncz17ImNvbiI6IHNlbGYuY29uLCAiZXJyb3JzIjogZXJyb3JzfSkKICAgICAgICB0LnN0YXJ0KCkKICAgICAgICB0LmpvaW4oKQogICAgICAgIGlmIGxlbihlcnJvcnMpID4gMDoKICAgICAgICAgICAgc2VsZi5mYWlsKCJcbiIuam9pbihlcnJvcnMpKQoKICAgIGRlZiBDaGVja0NvblJvbGxiYWNrKHNlbGYpOgogICAgICAgIGRlZiBydW4oY29uLCBlcnJvcnMpOgogICAgICAgICAgICB0cnk6CiAgICAgICAgICAgICAgICBjb24ucm9sbGJhY2soKQogICAgICAgICAgICAgICAgZXJyb3JzLmFwcGVuZCgiZGlkIG5vdCByYWlzZSBQcm9ncmFtbWluZ0Vycm9yIikKICAgICAgICAgICAgICAgIHJldHVybgogICAgICAgICAgICBleGNlcHQgc3FsaXRlLlByb2dyYW1taW5nRXJyb3I6CiAgICAgICAgICAgICAgICByZXR1cm4KICAgICAgICAgICAgZXhjZXB0OgogICAgICAgICAgICAgICAgZXJyb3JzLmFwcGVuZCgicmFpc2VkIHdyb25nIGV4Y2VwdGlvbiIpCgogICAgICAgIGVycm9ycyA9IFtdCiAgICAgICAgdCA9IHRocmVhZGluZy5UaHJlYWQodGFyZ2V0PXJ1biwga3dhcmdzPXsiY29uIjogc2VsZi5jb24sICJlcnJvcnMiOiBlcnJvcnN9KQogICAgICAgIHQuc3RhcnQoKQogICAgICAgIHQuam9pbigpCiAgICAgICAgaWYgbGVuKGVycm9ycykgPiAwOgogICAgICAgICAgICBzZWxmLmZhaWwoIlxuIi5qb2luKGVycm9ycykpCgogICAgZGVmIENoZWNrQ29uQ2xvc2Uoc2VsZik6CiAgICAgICAgZGVmIHJ1bihjb24sIGVycm9ycyk6CiAgICAgICAgICAgIHRyeToKICAgICAgICAgICAgICAgIGNvbi5jbG9zZSgpCiAgICAgICAgICAgICAgICBlcnJvcnMuYXBwZW5kKCJkaWQgbm90IHJhaXNlIFByb2dyYW1taW5nRXJyb3IiKQogICAgICAgICAgICAgICAgcmV0dXJuCiAgICAgICAgICAgIGV4Y2VwdCBzcWxpdGUuUHJvZ3JhbW1pbmdFcnJvcjoKICAgICAgICAgICAgICAgIHJldHVybgogICAgICAgICAgICBleGNlcHQ6CiAgICAgICAgICAgICAgICBlcnJvcnMuYXBwZW5kKCJyYWlzZWQgd3JvbmcgZXhjZXB0aW9uIikKCiAgICAgICAgZXJyb3JzID0gW10KICAgICAgICB0ID0gdGhyZWFkaW5nLlRocmVhZCh0YXJnZXQ9cnVuLCBrd2FyZ3M9eyJjb24iOiBzZWxmLmNvbiwgImVycm9ycyI6IGVycm9yc30pCiAgICAgICAgdC5zdGFydCgpCiAgICAgICAgdC5qb2luKCkKICAgICAgICBpZiBsZW4oZXJyb3JzKSA+IDA6CiAgICAgICAgICAgIHNlbGYuZmFpbCgiXG4iLmpvaW4oZXJyb3JzKSkKCiAgICBkZWYgQ2hlY2tDdXJJbXBsaWNpdEJlZ2luKHNlbGYpOgogICAgICAgIGRlZiBydW4oY3VyLCBlcnJvcnMpOgogICAgICAgICAgICB0cnk6CiAgICAgICAgICAgICAgICBjdXIuZXhlY3V0ZSgiaW5zZXJ0IGludG8gdGVzdChuYW1lKSB2YWx1ZXMgKCdhJykiKQogICAgICAgICAgICAgICAgZXJyb3JzLmFwcGVuZCgiZGlkIG5vdCByYWlzZSBQcm9ncmFtbWluZ0Vycm9yIikKICAgICAgICAgICAgICAgIHJldHVybgogICAgICAgICAgICBleGNlcHQgc3FsaXRlLlByb2dyYW1taW5nRXJyb3I6CiAgICAgICAgICAgICAgICByZXR1cm4KICAgICAgICAgICAgZXhjZXB0OgogICAgICAgICAgICAgICAgZXJyb3JzLmFwcGVuZCgicmFpc2VkIHdyb25nIGV4Y2VwdGlvbiIpCgogICAgICAgIGVycm9ycyA9IFtdCiAgICAgICAgdCA9IHRocmVhZGluZy5UaHJlYWQodGFyZ2V0PXJ1biwga3dhcmdzPXsiY3VyIjogc2VsZi5jdXIsICJlcnJvcnMiOiBlcnJvcnN9KQogICAgICAgIHQuc3RhcnQoKQogICAgICAgIHQuam9pbigpCiAgICAgICAgaWYgbGVuKGVycm9ycykgPiAwOgogICAgICAgICAgICBzZWxmLmZhaWwoIlxuIi5qb2luKGVycm9ycykpCgogICAgZGVmIENoZWNrQ3VyQ2xvc2Uoc2VsZik6CiAgICAgICAgZGVmIHJ1bihjdXIsIGVycm9ycyk6CiAgICAgICAgICAgIHRyeToKICAgICAgICAgICAgICAgIGN1ci5jbG9zZSgpCiAgICAgICAgICAgICAgICBlcnJvcnMuYXBwZW5kKCJkaWQgbm90IHJhaXNlIFByb2dyYW1taW5nRXJyb3IiKQogICAgICAgICAgICAgICAgcmV0dXJuCiAgICAgICAgICAgIGV4Y2VwdCBzcWxpdGUuUHJvZ3JhbW1pbmdFcnJvcjoKICAgICAgICAgICAgICAgIHJldHVybgogICAgICAgICAgICBleGNlcHQ6CiAgICAgICAgICAgICAgICBlcnJvcnMuYXBwZW5kKCJyYWlzZWQgd3JvbmcgZXhjZXB0aW9uIikKCiAgICAgICAgZXJyb3JzID0gW10KICAgICAgICB0ID0gdGhyZWFkaW5nLlRocmVhZCh0YXJnZXQ9cnVuLCBrd2FyZ3M9eyJjdXIiOiBzZWxmLmN1ciwgImVycm9ycyI6IGVycm9yc30pCiAgICAgICAgdC5zdGFydCgpCiAgICAgICAgdC5qb2luKCkKICAgICAgICBpZiBsZW4oZXJyb3JzKSA+IDA6CiAgICAgICAgICAgIHNlbGYuZmFpbCgiXG4iLmpvaW4oZXJyb3JzKSkKCiAgICBkZWYgQ2hlY2tDdXJFeGVjdXRlKHNlbGYpOgogICAgICAgIGRlZiBydW4oY3VyLCBlcnJvcnMpOgogICAgICAgICAgICB0cnk6CiAgICAgICAgICAgICAgICBjdXIuZXhlY3V0ZSgic2VsZWN0IG5hbWUgZnJvbSB0ZXN0IikKICAgICAgICAgICAgICAgIGVycm9ycy5hcHBlbmQoImRpZCBub3QgcmFpc2UgUHJvZ3JhbW1pbmdFcnJvciIpCiAgICAgICAgICAgICAgICByZXR1cm4KICAgICAgICAgICAgZXhjZXB0IHNxbGl0ZS5Qcm9ncmFtbWluZ0Vycm9yOgogICAgICAgICAgICAgICAgcmV0dXJuCiAgICAgICAgICAgIGV4Y2VwdDoKICAgICAgICAgICAgICAgIGVycm9ycy5hcHBlbmQoInJhaXNlZCB3cm9uZyBleGNlcHRpb24iKQoKICAgICAgICBlcnJvcnMgPSBbXQogICAgICAgIHNlbGYuY3VyLmV4ZWN1dGUoImluc2VydCBpbnRvIHRlc3QobmFtZSkgdmFsdWVzICgnYScpIikKICAgICAgICB0ID0gdGhyZWFkaW5nLlRocmVhZCh0YXJnZXQ9cnVuLCBrd2FyZ3M9eyJjdXIiOiBzZWxmLmN1ciwgImVycm9ycyI6IGVycm9yc30pCiAgICAgICAgdC5zdGFydCgpCiAgICAgICAgdC5qb2luKCkKICAgICAgICBpZiBsZW4oZXJyb3JzKSA+IDA6CiAgICAgICAgICAgIHNlbGYuZmFpbCgiXG4iLmpvaW4oZXJyb3JzKSkKCiAgICBkZWYgQ2hlY2tDdXJJdGVyTmV4dChzZWxmKToKICAgICAgICBkZWYgcnVuKGN1ciwgZXJyb3JzKToKICAgICAgICAgICAgdHJ5OgogICAgICAgICAgICAgICAgcm93ID0gY3VyLmZldGNob25lKCkKICAgICAgICAgICAgICAgIGVycm9ycy5hcHBlbmQoImRpZCBub3QgcmFpc2UgUHJvZ3JhbW1pbmdFcnJvciIpCiAgICAgICAgICAgICAgICByZXR1cm4KICAgICAgICAgICAgZXhjZXB0IHNxbGl0ZS5Qcm9ncmFtbWluZ0Vycm9yOgogICAgICAgICAgICAgICAgcmV0dXJuCiAgICAgICAgICAgIGV4Y2VwdDoKICAgICAgICAgICAgICAgIGVycm9ycy5hcHBlbmQoInJhaXNlZCB3cm9uZyBleGNlcHRpb24iKQoKICAgICAgICBlcnJvcnMgPSBbXQogICAgICAgIHNlbGYuY3VyLmV4ZWN1dGUoImluc2VydCBpbnRvIHRlc3QobmFtZSkgdmFsdWVzICgnYScpIikKICAgICAgICBzZWxmLmN1ci5leGVjdXRlKCJzZWxlY3QgbmFtZSBmcm9tIHRlc3QiKQogICAgICAgIHQgPSB0aHJlYWRpbmcuVGhyZWFkKHRhcmdldD1ydW4sIGt3YXJncz17ImN1ciI6IHNlbGYuY3VyLCAiZXJyb3JzIjogZXJyb3JzfSkKICAgICAgICB0LnN0YXJ0KCkKICAgICAgICB0LmpvaW4oKQogICAgICAgIGlmIGxlbihlcnJvcnMpID4gMDoKICAgICAgICAgICAgc2VsZi5mYWlsKCJcbiIuam9pbihlcnJvcnMpKQoKY2xhc3MgQ29uc3RydWN0b3JUZXN0cyh1bml0dGVzdC5UZXN0Q2FzZSk6CiAgICBkZWYgQ2hlY2tEYXRlKHNlbGYpOgogICAgICAgIGQgPSBzcWxpdGUuRGF0ZSgyMDA0LCAxMCwgMjgpCgogICAgZGVmIENoZWNrVGltZShzZWxmKToKICAgICAgICB0ID0gc3FsaXRlLlRpbWUoMTIsIDM5LCAzNSkKCiAgICBkZWYgQ2hlY2tUaW1lc3RhbXAoc2VsZik6CiAgICAgICAgdHMgPSBzcWxpdGUuVGltZXN0YW1wKDIwMDQsIDEwLCAyOCwgMTIsIDM5LCAzNSkKCiAgICBkZWYgQ2hlY2tEYXRlRnJvbVRpY2tzKHNlbGYpOgogICAgICAgIGQgPSBzcWxpdGUuRGF0ZUZyb21UaWNrcyg0MikKCiAgICBkZWYgQ2hlY2tUaW1lRnJvbVRpY2tzKHNlbGYpOgogICAgICAgIHQgPSBzcWxpdGUuVGltZUZyb21UaWNrcyg0MikKCiAgICBkZWYgQ2hlY2tUaW1lc3RhbXBGcm9tVGlja3Moc2VsZik6CiAgICAgICAgdHMgPSBzcWxpdGUuVGltZXN0YW1wRnJvbVRpY2tzKDQyKQoKICAgIGRlZiBDaGVja0JpbmFyeShzZWxmKToKICAgICAgICBiID0gc3FsaXRlLkJpbmFyeShiIlwwJyIpCgpjbGFzcyBFeHRlbnNpb25UZXN0cyh1bml0dGVzdC5UZXN0Q2FzZSk6CiAgICBkZWYgQ2hlY2tTY3JpcHRTdHJpbmdTcWwoc2VsZik6CiAgICAgICAgY29uID0gc3FsaXRlLmNvbm5lY3QoIjptZW1vcnk6IikKICAgICAgICBjdXIgPSBjb24uY3Vyc29yKCkKICAgICAgICBjdXIuZXhlY3V0ZXNjcmlwdCgiIiIKICAgICAgICAgICAgLS0gYmxhIGJsYQogICAgICAgICAgICAvKiBhIHN0dXBpZCBjb21tZW50ICovCiAgICAgICAgICAgIGNyZWF0ZSB0YWJsZSBhKGkpOwogICAgICAgICAgICBpbnNlcnQgaW50byBhKGkpIHZhbHVlcyAoNSk7CiAgICAgICAgICAgICIiIikKICAgICAgICBjdXIuZXhlY3V0ZSgic2VsZWN0IGkgZnJvbSBhIikKICAgICAgICByZXMgPSBjdXIuZmV0Y2hvbmUoKVswXQogICAgICAgIHNlbGYuYXNzZXJ0RXF1YWwocmVzLCA1KQoKICAgIGRlZiBDaGVja1NjcmlwdFN5bnRheEVycm9yKHNlbGYpOgogICAgICAgIGNvbiA9IHNxbGl0ZS5jb25uZWN0KCI6bWVtb3J5OiIpCiAgICAgICAgY3VyID0gY29uLmN1cnNvcigpCiAgICAgICAgd2l0aCBzZWxmLmFzc2VydFJhaXNlcyhzcWxpdGUuT3BlcmF0aW9uYWxFcnJvcik6CiAgICAgICAgICAgIGN1ci5leGVjdXRlc2NyaXB0KCJjcmVhdGUgdGFibGUgdGVzdCh4KTsgYXNkZjsgY3JlYXRlIHRhYmxlIHRlc3QyKHgpIikKCiAgICBkZWYgQ2hlY2tTY3JpcHRFcnJvck5vcm1hbChzZWxmKToKICAgICAgICBjb24gPSBzcWxpdGUuY29ubmVjdCgiOm1lbW9yeToiKQogICAgICAgIGN1ciA9IGNvbi5jdXJzb3IoKQogICAgICAgIHdpdGggc2VsZi5hc3NlcnRSYWlzZXMoc3FsaXRlLk9wZXJhdGlvbmFsRXJyb3IpOgogICAgICAgICAgICBjdXIuZXhlY3V0ZXNjcmlwdCgiY3JlYXRlIHRhYmxlIHRlc3Qoc2FkZnNhZGZkc2EpOyBzZWxlY3QgZm9vIGZyb20gaHVyejsiKQoKICAgIGRlZiBDaGVja0N1cnNvckV4ZWN1dGVzY3JpcHRBc0J5dGVzKHNlbGYpOgogICAgICAgIGNvbiA9IHNxbGl0ZS5jb25uZWN0KCI6bWVtb3J5OiIpCiAgICAgICAgY3VyID0gY29uLmN1cnNvcigpCiAgICAgICAgd2l0aCBzZWxmLmFzc2VydFJhaXNlcyhWYWx1ZUVycm9yKSBhcyBjbToKICAgICAgICAgICAgY3VyLmV4ZWN1dGVzY3JpcHQoYiJjcmVhdGUgdGFibGUgdGVzdChmb28pOyBpbnNlcnQgaW50byB0ZXN0KGZvbykgdmFsdWVzICg1KTsiKQogICAgICAgIHNlbGYuYXNzZXJ0RXF1YWwoc3RyKGNtLmV4Y2VwdGlvbiksICdzY3JpcHQgYXJndW1lbnQgbXVzdCBiZSB1bmljb2RlLicpCgogICAgZGVmIENoZWNrQ29ubmVjdGlvbkV4ZWN1dGUoc2VsZik6CiAgICAgICAgY29uID0gc3FsaXRlLmNvbm5lY3QoIjptZW1vcnk6IikKICAgICAgICByZXN1bHQgPSBjb24uZXhlY3V0ZSgic2VsZWN0IDUiKS5mZXRjaG9uZSgpWzBdCiAgICAgICAgc2VsZi5hc3NlcnRFcXVhbChyZXN1bHQsIDUsICJCYXNpYyB0ZXN0IG9mIENvbm5lY3Rpb24uZXhlY3V0ZSIpCgogICAgZGVmIENoZWNrQ29ubmVjdGlvbkV4ZWN1dGVtYW55KHNlbGYpOgogICAgICAgIGNvbiA9IHNxbGl0ZS5jb25uZWN0KCI6bWVtb3J5OiIpCiAgICAgICAgY29uLmV4ZWN1dGUoImNyZWF0ZSB0YWJsZSB0ZXN0KGZvbykiKQogICAgICAgIGNvbi5leGVjdXRlbWFueSgiaW5zZXJ0IGludG8gdGVzdChmb28pIHZhbHVlcyAoPykiLCBbKDMsKSwgKDQsKV0pCiAgICAgICAgcmVzdWx0ID0gY29uLmV4ZWN1dGUoInNlbGVjdCBmb28gZnJvbSB0ZXN0IG9yZGVyIGJ5IGZvbyIpLmZldGNoYWxsKCkKICAgICAgICBzZWxmLmFzc2VydEVxdWFsKHJlc3VsdFswXVswXSwgMywgIkJhc2ljIHRlc3Qgb2YgQ29ubmVjdGlvbi5leGVjdXRlbWFueSIpCiAgICAgICAgc2VsZi5hc3NlcnRFcXVhbChyZXN1bHRbMV1bMF0sIDQsICJCYXNpYyB0ZXN0IG9mIENvbm5lY3Rpb24uZXhlY3V0ZW1hbnkiKQoKICAgIGRlZiBDaGVja0Nvbm5lY3Rpb25FeGVjdXRlc2NyaXB0KHNlbGYpOgogICAgICAgIGNvbiA9IHNxbGl0ZS5jb25uZWN0KCI6bWVtb3J5OiIpCiAgICAgICAgY29uLmV4ZWN1dGVzY3JpcHQoImNyZWF0ZSB0YWJsZSB0ZXN0KGZvbyk7IGluc2VydCBpbnRvIHRlc3QoZm9vKSB2YWx1ZXMgKDUpOyIpCiAgICAgICAgcmVzdWx0ID0gY29uLmV4ZWN1dGUoInNlbGVjdCBmb28gZnJvbSB0ZXN0IikuZmV0Y2hvbmUoKVswXQogICAgICAgIHNlbGYuYXNzZXJ0RXF1YWwocmVzdWx0LCA1LCAiQmFzaWMgdGVzdCBvZiBDb25uZWN0aW9uLmV4ZWN1dGVzY3JpcHQiKQoKY2xhc3MgQ2xvc2VkQ29uVGVzdHModW5pdHRlc3QuVGVzdENhc2UpOgogICAgZGVmIENoZWNrQ2xvc2VkQ29uQ3Vyc29yKHNlbGYpOgogICAgICAgIGNvbiA9IHNxbGl0ZS5jb25uZWN0KCI6bWVtb3J5OiIpCiAgICAgICAgY29uLmNsb3NlKCkKICAgICAgICB3aXRoIHNlbGYuYXNzZXJ0UmFpc2VzKHNxbGl0ZS5Qcm9ncmFtbWluZ0Vycm9yKToKICAgICAgICAgICAgY3VyID0gY29uLmN1cnNvcigpCgogICAgZGVmIENoZWNrQ2xvc2VkQ29uQ29tbWl0KHNlbGYpOgogICAgICAgIGNvbiA9IHNxbGl0ZS5jb25uZWN0KCI6bWVtb3J5OiIpCiAgICAgICAgY29uLmNsb3NlKCkKICAgICAgICB3aXRoIHNlbGYuYXNzZXJ0UmFpc2VzKHNxbGl0ZS5Qcm9ncmFtbWluZ0Vycm9yKToKICAgICAgICAgICAgY29uLmNvbW1pdCgpCgogICAgZGVmIENoZWNrQ2xvc2VkQ29uUm9sbGJhY2soc2VsZik6CiAgICAgICAgY29uID0gc3FsaXRlLmNvbm5lY3QoIjptZW1vcnk6IikKICAgICAgICBjb24uY2xvc2UoKQogICAgICAgIHdpdGggc2VsZi5hc3NlcnRSYWlzZXMoc3FsaXRlLlByb2dyYW1taW5nRXJyb3IpOgogICAgICAgICAgICBjb24ucm9sbGJhY2soKQoKICAgIGRlZiBDaGVja0Nsb3NlZEN1ckV4ZWN1dGUoc2VsZik6CiAgICAgICAgY29uID0gc3FsaXRlLmNvbm5lY3QoIjptZW1vcnk6IikKICAgICAgICBjdXIgPSBjb24uY3Vyc29yKCkKICAgICAgICBjb24uY2xvc2UoKQogICAgICAgIHdpdGggc2VsZi5hc3NlcnRSYWlzZXMoc3FsaXRlLlByb2dyYW1taW5nRXJyb3IpOgogICAgICAgICAgICBjdXIuZXhlY3V0ZSgic2VsZWN0IDQiKQoKICAgIGRlZiBDaGVja0Nsb3NlZENyZWF0ZUZ1bmN0aW9uKHNlbGYpOgogICAgICAgIGNvbiA9IHNxbGl0ZS5jb25uZWN0KCI6bWVtb3J5OiIpCiAgICAgICAgY29uLmNsb3NlKCkKICAgICAgICBkZWYgZih4KTogcmV0dXJuIDE3CiAgICAgICAgd2l0aCBzZWxmLmFzc2VydFJhaXNlcyhzcWxpdGUuUHJvZ3JhbW1pbmdFcnJvcik6CiAgICAgICAgICAgIGNvbi5jcmVhdGVfZnVuY3Rpb24oImZvbyIsIDEsIGYpCgogICAgZGVmIENoZWNrQ2xvc2VkQ3JlYXRlQWdncmVnYXRlKHNlbGYpOgogICAgICAgIGNvbiA9IHNxbGl0ZS5jb25uZWN0KCI6bWVtb3J5OiIpCiAgICAgICAgY29uLmNsb3NlKCkKICAgICAgICBjbGFzcyBBZ2c6CiAgICAgICAgICAgIGRlZiBfX2luaXRfXyhzZWxmKToKICAgICAgICAgICAgICAgIHBhc3MKICAgICAgICAgICAgZGVmIHN0ZXAoc2VsZiwgeCk6CiAgICAgICAgICAgICAgICBwYXNzCiAgICAgICAgICAgIGRlZiBmaW5hbGl6ZShzZWxmKToKICAgICAgICAgICAgICAgIHJldHVybiAxNwogICAgICAgIHdpdGggc2VsZi5hc3NlcnRSYWlzZXMoc3FsaXRlLlByb2dyYW1taW5nRXJyb3IpOgogICAgICAgICAgICBjb24uY3JlYXRlX2FnZ3JlZ2F0ZSgiZm9vIiwgMSwgQWdnKQoKICAgIGRlZiBDaGVja0Nsb3NlZFNldEF1dGhvcml6ZXIoc2VsZik6CiAgICAgICAgY29uID0gc3FsaXRlLmNvbm5lY3QoIjptZW1vcnk6IikKICAgICAgICBjb24uY2xvc2UoKQogICAgICAgIGRlZiBhdXRob3JpemVyKCphcmdzKToKICAgICAgICAgICAgcmV0dXJuIHNxbGl0ZS5ERU5ZCiAgICAgICAgd2l0aCBzZWxmLmFzc2VydFJhaXNlcyhzcWxpdGUuUHJvZ3JhbW1pbmdFcnJvcik6CiAgICAgICAgICAgIGNvbi5zZXRfYXV0aG9yaXplcihhdXRob3JpemVyKQoKICAgIGRlZiBDaGVja0Nsb3NlZFNldFByb2dyZXNzQ2FsbGJhY2soc2VsZik6CiAgICAgICAgY29uID0gc3FsaXRlLmNvbm5lY3QoIjptZW1vcnk6IikKICAgICAgICBjb24uY2xvc2UoKQogICAgICAgIGRlZiBwcm9ncmVzcygpOiBwYXNzCiAgICAgICAgd2l0aCBzZWxmLmFzc2VydFJhaXNlcyhzcWxpdGUuUHJvZ3JhbW1pbmdFcnJvcik6CiAgICAgICAgICAgIGNvbi5zZXRfcHJvZ3Jlc3NfaGFuZGxlcihwcm9ncmVzcywgMTAwKQoKICAgIGRlZiBDaGVja0Nsb3NlZENhbGwoc2VsZik6CiAgICAgICAgY29uID0gc3FsaXRlLmNvbm5lY3QoIjptZW1vcnk6IikKICAgICAgICBjb24uY2xvc2UoKQogICAgICAgIHdpdGggc2VsZi5hc3NlcnRSYWlzZXMoc3FsaXRlLlByb2dyYW1taW5nRXJyb3IpOgogICAgICAgICAgICBjb24oKQoKY2xhc3MgQ2xvc2VkQ3VyVGVzdHModW5pdHRlc3QuVGVzdENhc2UpOgogICAgZGVmIENoZWNrQ2xvc2VkKHNlbGYpOgogICAgICAgIGNvbiA9IHNxbGl0ZS5jb25uZWN0KCI6bWVtb3J5OiIpCiAgICAgICAgY3VyID0gY29uLmN1cnNvcigpCiAgICAgICAgY3VyLmNsb3NlKCkKCiAgICAgICAgZm9yIG1ldGhvZF9uYW1lIGluICgiZXhlY3V0ZSIsICJleGVjdXRlbWFueSIsICJleGVjdXRlc2NyaXB0IiwgImZldGNoYWxsIiwgImZldGNobWFueSIsICJmZXRjaG9uZSIpOgogICAgICAgICAgICBpZiBtZXRob2RfbmFtZSBpbiAoImV4ZWN1dGUiLCAiZXhlY3V0ZXNjcmlwdCIpOgogICAgICAgICAgICAgICAgcGFyYW1zID0gKCJzZWxlY3QgNCB1bmlvbiBzZWxlY3QgNSIsKQogICAgICAgICAgICBlbGlmIG1ldGhvZF9uYW1lID09ICJleGVjdXRlbWFueSI6CiAgICAgICAgICAgICAgICBwYXJhbXMgPSAoImluc2VydCBpbnRvIGZvbyhiYXIpIHZhbHVlcyAoPykiLCBbKDMsKSwgKDQsKV0pCiAgICAgICAgICAgIGVsc2U6CiAgICAgICAgICAgICAgICBwYXJhbXMgPSBbXQoKICAgICAgICAgICAgd2l0aCBzZWxmLmFzc2VydFJhaXNlcyhzcWxpdGUuUHJvZ3JhbW1pbmdFcnJvcik6CiAgICAgICAgICAgICAgICBtZXRob2QgPSBnZXRhdHRyKGN1ciwgbWV0aG9kX25hbWUpCiAgICAgICAgICAgICAgICBtZXRob2QoKnBhcmFtcykKCgpjbGFzcyBTcWxpdGVPbkNvbmZsaWN0VGVzdHModW5pdHRlc3QuVGVzdENhc2UpOgogICAgIiIiCiAgICBUZXN0cyBmb3IgU1FMaXRlJ3MgImluc2VydCBvbiBjb25mbGljdCIgZmVhdHVyZS4KCiAgICBTZWUgaHR0cHM6Ly93d3cuc3FsaXRlLm9yZy9sYW5nX2NvbmZsaWN0Lmh0bWwgZm9yIGRldGFpbHMuCiAgICAiIiIKCiAgICBkZWYgc2V0VXAoc2VsZik6CiAgICAgICAgc2VsZi5jeCA9IHNxbGl0ZS5jb25uZWN0KCI6bWVtb3J5OiIpCiAgICAgICAgc2VsZi5jdSA9IHNlbGYuY3guY3Vyc29yKCkKICAgICAgICBzZWxmLmN1LmV4ZWN1dGUoIiIiCiAgICAgICAgICBDUkVBVEUgVEFCTEUgdGVzdCgKICAgICAgICAgICAgaWQgSU5URUdFUiBQUklNQVJZIEtFWSwgbmFtZSBURVhULCB1bmlxdWVfbmFtZSBURVhUIFVOSVFVRQogICAgICAgICAgKTsKICAgICAgICAiIiIpCgogICAgZGVmIHRlYXJEb3duKHNlbGYpOgogICAgICAgIHNlbGYuY3UuY2xvc2UoKQogICAgICAgIHNlbGYuY3guY2xvc2UoKQoKICAgIGRlZiBDaGVja09uQ29uZmxpY3RSb2xsYmFja1dpdGhFeHBsaWNpdFRyYW5zYWN0aW9uKHNlbGYpOgogICAgICAgIHNlbGYuY3guaXNvbGF0aW9uX2xldmVsID0gTm9uZSAgIyBhdXRvY29tbWl0IG1vZGUKICAgICAgICBzZWxmLmN1ID0gc2VsZi5jeC5jdXJzb3IoKQogICAgICAgICMgU3RhcnQgYW4gZXhwbGljaXQgdHJhbnNhY3Rpb24uCiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJCRUdJTiIpCiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJJTlNFUlQgSU5UTyB0ZXN0KG5hbWUpIFZBTFVFUyAoJ2Fib3J0X3Rlc3QnKSIpCiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJJTlNFUlQgT1IgUk9MTEJBQ0sgSU5UTyB0ZXN0KHVuaXF1ZV9uYW1lKSBWQUxVRVMgKCdmb28nKSIpCiAgICAgICAgd2l0aCBzZWxmLmFzc2VydFJhaXNlcyhzcWxpdGUuSW50ZWdyaXR5RXJyb3IpOgogICAgICAgICAgICBzZWxmLmN1LmV4ZWN1dGUoIklOU0VSVCBPUiBST0xMQkFDSyBJTlRPIHRlc3QodW5pcXVlX25hbWUpIFZBTFVFUyAoJ2ZvbycpIikKICAgICAgICAjIFVzZSBjb25uZWN0aW9uIHRvIGNvbW1pdC4KICAgICAgICBzZWxmLmN4LmNvbW1pdCgpCiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJTRUxFQ1QgbmFtZSwgdW5pcXVlX25hbWUgZnJvbSB0ZXN0IikKICAgICAgICAjIFRyYW5zYWN0aW9uIHNob3VsZCBoYXZlIHJvbGxlZCBiYWNrIGFuZCBub3RoaW5nIHNob3VsZCBiZSBpbiB0YWJsZS4KICAgICAgICBzZWxmLmFzc2VydEVxdWFsKHNlbGYuY3UuZmV0Y2hhbGwoKSwgW10pCgogICAgZGVmIENoZWNrT25Db25mbGljdEFib3J0UmFpc2VzV2l0aEV4cGxpY2l0VHJhbnNhY3Rpb25zKHNlbGYpOgogICAgICAgICMgQWJvcnQgY2FuY2VscyB0aGUgY3VycmVudCBzcWwgc3RhdGVtZW50IGJ1dCBkb2Vzbid0IGNoYW5nZSBhbnl0aGluZwogICAgICAgICMgYWJvdXQgdGhlIGN1cnJlbnQgdHJhbnNhY3Rpb24uCiAgICAgICAgc2VsZi5jeC5pc29sYXRpb25fbGV2ZWwgPSBOb25lICAjIGF1dG9jb21taXQgbW9kZQogICAgICAgIHNlbGYuY3UgPSBzZWxmLmN4LmN1cnNvcigpCiAgICAgICAgIyBTdGFydCBhbiBleHBsaWNpdCB0cmFuc2FjdGlvbi4KICAgICAgICBzZWxmLmN1LmV4ZWN1dGUoIkJFR0lOIikKICAgICAgICBzZWxmLmN1LmV4ZWN1dGUoIklOU0VSVCBJTlRPIHRlc3QobmFtZSkgVkFMVUVTICgnYWJvcnRfdGVzdCcpIikKICAgICAgICBzZWxmLmN1LmV4ZWN1dGUoIklOU0VSVCBPUiBBQk9SVCBJTlRPIHRlc3QodW5pcXVlX25hbWUpIFZBTFVFUyAoJ2ZvbycpIikKICAgICAgICB3aXRoIHNlbGYuYXNzZXJ0UmFpc2VzKHNxbGl0ZS5JbnRlZ3JpdHlFcnJvcik6CiAgICAgICAgICAgIHNlbGYuY3UuZXhlY3V0ZSgiSU5TRVJUIE9SIEFCT1JUIElOVE8gdGVzdCh1bmlxdWVfbmFtZSkgVkFMVUVTICgnZm9vJykiKQogICAgICAgIHNlbGYuY3guY29tbWl0KCkKICAgICAgICBzZWxmLmN1LmV4ZWN1dGUoIlNFTEVDVCBuYW1lLCB1bmlxdWVfbmFtZSBGUk9NIHRlc3QiKQogICAgICAgICMgRXhwZWN0IHRoZSBmaXJzdCB0d28gaW5zZXJ0cyB0byB3b3JrLCB0aGlyZCB0byBkbyBub3RoaW5nLgogICAgICAgIHNlbGYuYXNzZXJ0RXF1YWwoc2VsZi5jdS5mZXRjaGFsbCgpLCBbKCdhYm9ydF90ZXN0JywgTm9uZSksIChOb25lLCAnZm9vJywpXSkKCiAgICBkZWYgQ2hlY2tPbkNvbmZsaWN0Um9sbGJhY2tXaXRob3V0VHJhbnNhY3Rpb24oc2VsZik6CiAgICAgICAgIyBTdGFydCBvZiBpbXBsaWNpdCB0cmFuc2FjdGlvbgogICAgICAgIHNlbGYuY3UuZXhlY3V0ZSgiSU5TRVJUIElOVE8gdGVzdChuYW1lKSBWQUxVRVMgKCdhYm9ydF90ZXN0JykiKQogICAgICAgIHNlbGYuY3UuZXhlY3V0ZSgiSU5TRVJUIE9SIFJPTExCQUNLIElOVE8gdGVzdCh1bmlxdWVfbmFtZSkgVkFMVUVTICgnZm9vJykiKQogICAgICAgIHdpdGggc2VsZi5hc3NlcnRSYWlzZXMoc3FsaXRlLkludGVncml0eUVycm9yKToKICAgICAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJJTlNFUlQgT1IgUk9MTEJBQ0sgSU5UTyB0ZXN0KHVuaXF1ZV9uYW1lKSBWQUxVRVMgKCdmb28nKSIpCiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJTRUxFQ1QgbmFtZSwgdW5pcXVlX25hbWUgRlJPTSB0ZXN0IikKICAgICAgICAjIEltcGxpY2l0IHRyYW5zYWN0aW9uIGlzIHJvbGxlZCBiYWNrIG9uIGVycm9yLgogICAgICAgIHNlbGYuYXNzZXJ0RXF1YWwoc2VsZi5jdS5mZXRjaGFsbCgpLCBbXSkKCiAgICBkZWYgQ2hlY2tPbkNvbmZsaWN0QWJvcnRSYWlzZXNXaXRob3V0VHJhbnNhY3Rpb25zKHNlbGYpOgogICAgICAgICMgQWJvcnQgY2FuY2VscyB0aGUgY3VycmVudCBzcWwgc3RhdGVtZW50IGJ1dCBkb2Vzbid0IGNoYW5nZSBhbnl0aGluZwogICAgICAgICMgYWJvdXQgdGhlIGN1cnJlbnQgdHJhbnNhY3Rpb24uCiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJJTlNFUlQgSU5UTyB0ZXN0KG5hbWUpIFZBTFVFUyAoJ2Fib3J0X3Rlc3QnKSIpCiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJJTlNFUlQgT1IgQUJPUlQgSU5UTyB0ZXN0KHVuaXF1ZV9uYW1lKSBWQUxVRVMgKCdmb28nKSIpCiAgICAgICAgd2l0aCBzZWxmLmFzc2VydFJhaXNlcyhzcWxpdGUuSW50ZWdyaXR5RXJyb3IpOgogICAgICAgICAgICBzZWxmLmN1LmV4ZWN1dGUoIklOU0VSVCBPUiBBQk9SVCBJTlRPIHRlc3QodW5pcXVlX25hbWUpIFZBTFVFUyAoJ2ZvbycpIikKICAgICAgICAjIE1ha2Ugc3VyZSBhbGwgb3RoZXIgdmFsdWVzIHdlcmUgaW5zZXJ0ZWQuCiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJTRUxFQ1QgbmFtZSwgdW5pcXVlX25hbWUgRlJPTSB0ZXN0IikKICAgICAgICBzZWxmLmFzc2VydEVxdWFsKHNlbGYuY3UuZmV0Y2hhbGwoKSwgWygnYWJvcnRfdGVzdCcsIE5vbmUpLCAoTm9uZSwgJ2ZvbycsKV0pCgogICAgZGVmIENoZWNrT25Db25mbGljdEZhaWwoc2VsZik6CiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJJTlNFUlQgT1IgRkFJTCBJTlRPIHRlc3QodW5pcXVlX25hbWUpIFZBTFVFUyAoJ2ZvbycpIikKICAgICAgICB3aXRoIHNlbGYuYXNzZXJ0UmFpc2VzKHNxbGl0ZS5JbnRlZ3JpdHlFcnJvcik6CiAgICAgICAgICAgIHNlbGYuY3UuZXhlY3V0ZSgiSU5TRVJUIE9SIEZBSUwgSU5UTyB0ZXN0KHVuaXF1ZV9uYW1lKSBWQUxVRVMgKCdmb28nKSIpCiAgICAgICAgc2VsZi5hc3NlcnRFcXVhbChzZWxmLmN1LmZldGNoYWxsKCksIFtdKQoKICAgIGRlZiBDaGVja09uQ29uZmxpY3RJZ25vcmUoc2VsZik6CiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJJTlNFUlQgT1IgSUdOT1JFIElOVE8gdGVzdCh1bmlxdWVfbmFtZSkgVkFMVUVTICgnZm9vJykiKQogICAgICAgICMgTm90aGluZyBzaG91bGQgaGFwcGVuLgogICAgICAgIHNlbGYuY3UuZXhlY3V0ZSgiSU5TRVJUIE9SIElHTk9SRSBJTlRPIHRlc3QodW5pcXVlX25hbWUpIFZBTFVFUyAoJ2ZvbycpIikKICAgICAgICBzZWxmLmN1LmV4ZWN1dGUoIlNFTEVDVCB1bmlxdWVfbmFtZSBGUk9NIHRlc3QiKQogICAgICAgIHNlbGYuYXNzZXJ0RXF1YWwoc2VsZi5jdS5mZXRjaGFsbCgpLCBbKCdmb28nLCldKQoKICAgIGRlZiBDaGVja09uQ29uZmxpY3RSZXBsYWNlKHNlbGYpOgogICAgICAgIHNlbGYuY3UuZXhlY3V0ZSgiSU5TRVJUIE9SIFJFUExBQ0UgSU5UTyB0ZXN0KG5hbWUsIHVuaXF1ZV9uYW1lKSBWQUxVRVMgKCdEYXRhIScsICdmb28nKSIpCiAgICAgICAgIyBUaGVyZSBzaG91bGRuJ3QgYmUgYW4gSW50ZWdyaXR5RXJyb3IgZXhjZXB0aW9uLgogICAgICAgIHNlbGYuY3UuZXhlY3V0ZSgiSU5TRVJUIE9SIFJFUExBQ0UgSU5UTyB0ZXN0KG5hbWUsIHVuaXF1ZV9uYW1lKSBWQUxVRVMgKCdWZXJ5IGRpZmZlcmVudCBkYXRhIScsICdmb28nKSIpCiAgICAgICAgc2VsZi5jdS5leGVjdXRlKCJTRUxFQ1QgbmFtZSwgdW5pcXVlX25hbWUgRlJPTSB0ZXN0IikKICAgICAgICBzZWxmLmFzc2VydEVxdWFsKHNlbGYuY3UuZmV0Y2hhbGwoKSwgWygnVmVyeSBkaWZmZXJlbnQgZGF0YSEnLCAnZm9vJyldKQoKCmRlZiBzdWl0ZSgpOgogICAgbW9kdWxlX3N1aXRlID0gdW5pdHRlc3QubWFrZVN1aXRlKE1vZHVsZVRlc3RzLCAiQ2hlY2siKQogICAgY29ubmVjdGlvbl9zdWl0ZSA9IHVuaXR0ZXN0Lm1ha2VTdWl0ZShDb25uZWN0aW9uVGVzdHMsICJDaGVjayIpCiAgICBjdXJzb3Jfc3VpdGUgPSB1bml0dGVzdC5tYWtlU3VpdGUoQ3Vyc29yVGVzdHMsICJDaGVjayIpCiAgICB0aHJlYWRfc3VpdGUgPSB1bml0dGVzdC5tYWtlU3VpdGUoVGhyZWFkVGVzdHMsICJDaGVjayIpCiAgICBjb25zdHJ1Y3Rvcl9zdWl0ZSA9IHVuaXR0ZXN0Lm1ha2VTdWl0ZShDb25zdHJ1Y3RvclRlc3RzLCAiQ2hlY2siKQogICAgZXh0X3N1aXRlID0gdW5pdHRlc3QubWFrZVN1aXRlKEV4dGVuc2lvblRlc3RzLCAiQ2hlY2siKQogICAgY2xvc2VkX2Nvbl9zdWl0ZSA9IHVuaXR0ZXN0Lm1ha2VTdWl0ZShDbG9zZWRDb25UZXN0cywgIkNoZWNrIikKICAgIGNsb3NlZF9jdXJfc3VpdGUgPSB1bml0dGVzdC5tYWtlU3VpdGUoQ2xvc2VkQ3VyVGVzdHMsICJDaGVjayIpCiAgICBvbl9jb25mbGljdF9zdWl0ZSA9IHVuaXR0ZXN0Lm1ha2VTdWl0ZShTcWxpdGVPbkNvbmZsaWN0VGVzdHMsICJDaGVjayIpCiAgICByZXR1cm4gdW5pdHRlc3QuVGVzdFN1aXRlKCgKICAgICAgICBtb2R1bGVfc3VpdGUsIGNvbm5lY3Rpb25fc3VpdGUsIGN1cnNvcl9zdWl0ZSwgdGhyZWFkX3N1aXRlLAogICAgICAgIGNvbnN0cnVjdG9yX3N1aXRlLCBleHRfc3VpdGUsIGNsb3NlZF9jb25fc3VpdGUsIGNsb3NlZF9jdXJfc3VpdGUsCiAgICAgICAgb25fY29uZmxpY3Rfc3VpdGUsCiAgICApKQoKZGVmIHRlc3QoKToKICAgIHJ1bm5lciA9IHVuaXR0ZXN0LlRleHRUZXN0UnVubmVyKCkKICAgIHJ1bm5lci5ydW4oc3VpdGUoKSkKCmlmIF9fbmFtZV9fID09ICJfX21haW5fXyI6CiAgICB0ZXN0KCkK