Iy0qLSBjb2Rpbmc6IElTTy04ODU5LTEgLSotCiMgcHlzcWxpdGUyL3Rlc3QvdHJhbnNhY3Rpb25zLnB5OiB0ZXN0cyB0cmFuc2FjdGlvbnMKIwojIENvcHlyaWdodCAoQykgMjAwNS0yMDA3IEdlcmhhcmQgSORyaW5nIDxnaEBnaGFlcmluZy5kZT4KIwojIFRoaXMgZmlsZSBpcyBwYXJ0IG9mIHB5c3FsaXRlLgojCiMgVGhpcyBzb2Z0d2FyZSBpcyBwcm92aWRlZCAnYXMtaXMnLCB3aXRob3V0IGFueSBleHByZXNzIG9yIGltcGxpZWQKIyB3YXJyYW50eS4gIEluIG5vIGV2ZW50IHdpbGwgdGhlIGF1dGhvcnMgYmUgaGVsZCBsaWFibGUgZm9yIGFueSBkYW1hZ2VzCiMgYXJpc2luZyBmcm9tIHRoZSB1c2Ugb2YgdGhpcyBzb2Z0d2FyZS4KIwojIFBlcm1pc3Npb24gaXMgZ3JhbnRlZCB0byBhbnlvbmUgdG8gdXNlIHRoaXMgc29mdHdhcmUgZm9yIGFueSBwdXJwb3NlLAojIGluY2x1ZGluZyBjb21tZXJjaWFsIGFwcGxpY2F0aW9ucywgYW5kIHRvIGFsdGVyIGl0IGFuZCByZWRpc3RyaWJ1dGUgaXQKIyBmcmVlbHksIHN1YmplY3QgdG8gdGhlIGZvbGxvd2luZyByZXN0cmljdGlvbnM6CiMKIyAxLiBUaGUgb3JpZ2luIG9mIHRoaXMgc29mdHdhcmUgbXVzdCBub3QgYmUgbWlzcmVwcmVzZW50ZWQ7IHlvdSBtdXN0IG5vdAojICAgIGNsYWltIHRoYXQgeW91IHdyb3RlIHRoZSBvcmlnaW5hbCBzb2Z0d2FyZS4gSWYgeW91IHVzZSB0aGlzIHNvZnR3YXJlCiMgICAgaW4gYSBwcm9kdWN0LCBhbiBhY2tub3dsZWRnbWVudCBpbiB0aGUgcHJvZHVjdCBkb2N1bWVudGF0aW9uIHdvdWxkIGJlCiMgICAgYXBwcmVjaWF0ZWQgYnV0IGlzIG5vdCByZXF1aXJlZC4KIyAyLiBBbHRlcmVkIHNvdXJjZSB2ZXJzaW9ucyBtdXN0IGJlIHBsYWlubHkgbWFya2VkIGFzIHN1Y2gsIGFuZCBtdXN0IG5vdCBiZQojICAgIG1pc3JlcHJlc2VudGVkIGFzIGJlaW5nIHRoZSBvcmlnaW5hbCBzb2Z0d2FyZS4KIyAzLiBUaGlzIG5vdGljZSBtYXkgbm90IGJlIHJlbW92ZWQgb3IgYWx0ZXJlZCBmcm9tIGFueSBzb3VyY2UgZGlzdHJpYnV0aW9uLgoKaW1wb3J0IHN5cwppbXBvcnQgb3MsIHVuaXR0ZXN0CmltcG9ydCBzcWxpdGUzIGFzIHNxbGl0ZQoKZGVmIGdldF9kYl9wYXRoKCk6CiAgICByZXR1cm4gInNxbGl0ZV90ZXN0ZGIiCgpjbGFzcyBUcmFuc2FjdGlvblRlc3RzKHVuaXR0ZXN0LlRlc3RDYXNlKToKICAgIGRlZiBzZXRVcChzZWxmKToKICAgICAgICB0cnk6CiAgICAgICAgICAgIG9zLnJlbW92ZShnZXRfZGJfcGF0aCgpKQogICAgICAgIGV4Y2VwdCBPU0Vycm9yOgogICAgICAgICAgICBwYXNzCgogICAgICAgIHNlbGYuY29uMSA9IHNxbGl0ZS5jb25uZWN0KGdldF9kYl9wYXRoKCksIHRpbWVvdXQ9MC4xKQogICAgICAgIHNlbGYuY3VyMSA9IHNlbGYuY29uMS5jdXJzb3IoKQoKICAgICAgICBzZWxmLmNvbjIgPSBzcWxpdGUuY29ubmVjdChnZXRfZGJfcGF0aCgpLCB0aW1lb3V0PTAuMSkKICAgICAgICBzZWxmLmN1cjIgPSBzZWxmLmNvbjIuY3Vyc29yKCkKCiAgICBkZWYgdGVhckRvd24oc2VsZik6CiAgICAgICAgc2VsZi5jdXIxLmNsb3NlKCkKICAgICAgICBzZWxmLmNvbjEuY2xvc2UoKQoKICAgICAgICBzZWxmLmN1cjIuY2xvc2UoKQogICAgICAgIHNlbGYuY29uMi5jbG9zZSgpCgogICAgICAgIHRyeToKICAgICAgICAgICAgb3MudW5saW5rKGdldF9kYl9wYXRoKCkpCiAgICAgICAgZXhjZXB0IE9TRXJyb3I6CiAgICAgICAgICAgIHBhc3MKCiAgICBkZWYgQ2hlY2tETUxkb2VzQXV0b0NvbW1pdEJlZm9yZShzZWxmKToKICAgICAgICBzZWxmLmN1cjEuZXhlY3V0ZSgiY3JlYXRlIHRhYmxlIHRlc3QoaSkiKQogICAgICAgIHNlbGYuY3VyMS5leGVjdXRlKCJpbnNlcnQgaW50byB0ZXN0KGkpIHZhbHVlcyAoNSkiKQogICAgICAgIHNlbGYuY3VyMS5leGVjdXRlKCJjcmVhdGUgdGFibGUgdGVzdDIoaikiKQogICAgICAgIHNlbGYuY3VyMi5leGVjdXRlKCJzZWxlY3QgaSBmcm9tIHRlc3QiKQogICAgICAgIHJlcyA9IHNlbGYuY3VyMi5mZXRjaGFsbCgpCiAgICAgICAgc2VsZi5mYWlsVW5sZXNzRXF1YWwobGVuKHJlcyksIDEpCgogICAgZGVmIENoZWNrSW5zZXJ0U3RhcnRzVHJhbnNhY3Rpb24oc2VsZik6CiAgICAgICAgc2VsZi5jdXIxLmV4ZWN1dGUoImNyZWF0ZSB0YWJsZSB0ZXN0KGkpIikKICAgICAgICBzZWxmLmN1cjEuZXhlY3V0ZSgiaW5zZXJ0IGludG8gdGVzdChpKSB2YWx1ZXMgKDUpIikKICAgICAgICBzZWxmLmN1cjIuZXhlY3V0ZSgic2VsZWN0IGkgZnJvbSB0ZXN0IikKICAgICAgICByZXMgPSBzZWxmLmN1cjIuZmV0Y2hhbGwoKQogICAgICAgIHNlbGYuZmFpbFVubGVzc0VxdWFsKGxlbihyZXMpLCAwKQoKICAgIGRlZiBDaGVja1VwZGF0ZVN0YXJ0c1RyYW5zYWN0aW9uKHNlbGYpOgogICAgICAgIHNlbGYuY3VyMS5leGVjdXRlKCJjcmVhdGUgdGFibGUgdGVzdChpKSIpCiAgICAgICAgc2VsZi5jdXIxLmV4ZWN1dGUoImluc2VydCBpbnRvIHRlc3QoaSkgdmFsdWVzICg1KSIpCiAgICAgICAgc2VsZi5jb24xLmNvbW1pdCgpCiAgICAgICAgc2VsZi5jdXIxLmV4ZWN1dGUoInVwZGF0ZSB0ZXN0IHNldCBpPTYiKQogICAgICAgIHNlbGYuY3VyMi5leGVjdXRlKCJzZWxlY3QgaSBmcm9tIHRlc3QiKQogICAgICAgIHJlcyA9IHNlbGYuY3VyMi5mZXRjaG9uZSgpWzBdCiAgICAgICAgc2VsZi5mYWlsVW5sZXNzRXF1YWwocmVzLCA1KQoKICAgIGRlZiBDaGVja0RlbGV0ZVN0YXJ0c1RyYW5zYWN0aW9uKHNlbGYpOgogICAgICAgIHNlbGYuY3VyMS5leGVjdXRlKCJjcmVhdGUgdGFibGUgdGVzdChpKSIpCiAgICAgICAgc2VsZi5jdXIxLmV4ZWN1dGUoImluc2VydCBpbnRvIHRlc3QoaSkgdmFsdWVzICg1KSIpCiAgICAgICAgc2VsZi5jb24xLmNvbW1pdCgpCiAgICAgICAgc2VsZi5jdXIxLmV4ZWN1dGUoImRlbGV0ZSBmcm9tIHRlc3QiKQogICAgICAgIHNlbGYuY3VyMi5leGVjdXRlKCJzZWxlY3QgaSBmcm9tIHRlc3QiKQogICAgICAgIHJlcyA9IHNlbGYuY3VyMi5mZXRjaGFsbCgpCiAgICAgICAgc2VsZi5mYWlsVW5sZXNzRXF1YWwobGVuKHJlcyksIDEpCgogICAgZGVmIENoZWNrUmVwbGFjZVN0YXJ0c1RyYW5zYWN0aW9uKHNlbGYpOgogICAgICAgIHNlbGYuY3VyMS5leGVjdXRlKCJjcmVhdGUgdGFibGUgdGVzdChpKSIpCiAgICAgICAgc2VsZi5jdXIxLmV4ZWN1dGUoImluc2VydCBpbnRvIHRlc3QoaSkgdmFsdWVzICg1KSIpCiAgICAgICAgc2VsZi5jb24xLmNvbW1pdCgpCiAgICAgICAgc2VsZi5jdXIxLmV4ZWN1dGUoInJlcGxhY2UgaW50byB0ZXN0KGkpIHZhbHVlcyAoNikiKQogICAgICAgIHNlbGYuY3VyMi5leGVjdXRlKCJzZWxlY3QgaSBmcm9tIHRlc3QiKQogICAgICAgIHJlcyA9IHNlbGYuY3VyMi5mZXRjaGFsbCgpCiAgICAgICAgc2VsZi5mYWlsVW5sZXNzRXF1YWwobGVuKHJlcyksIDEpCiAgICAgICAgc2VsZi5mYWlsVW5sZXNzRXF1YWwocmVzWzBdWzBdLCA1KQoKICAgIGRlZiBDaGVja1RvZ2dsZUF1dG9Db21taXQoc2VsZik6CiAgICAgICAgc2VsZi5jdXIxLmV4ZWN1dGUoImNyZWF0ZSB0YWJsZSB0ZXN0KGkpIikKICAgICAgICBzZWxmLmN1cjEuZXhlY3V0ZSgiaW5zZXJ0IGludG8gdGVzdChpKSB2YWx1ZXMgKDUpIikKICAgICAgICBzZWxmLmNvbjEuaXNvbGF0aW9uX2xldmVsID0gTm9uZQogICAgICAgIHNlbGYuZmFpbFVubGVzc0VxdWFsKHNlbGYuY29uMS5pc29sYXRpb25fbGV2ZWwsIE5vbmUpCiAgICAgICAgc2VsZi5jdXIyLmV4ZWN1dGUoInNlbGVjdCBpIGZyb20gdGVzdCIpCiAgICAgICAgcmVzID0gc2VsZi5jdXIyLmZldGNoYWxsKCkKICAgICAgICBzZWxmLmZhaWxVbmxlc3NFcXVhbChsZW4ocmVzKSwgMSkKCiAgICAgICAgc2VsZi5jb24xLmlzb2xhdGlvbl9sZXZlbCA9ICJERUZFUlJFRCIKICAgICAgICBzZWxmLmZhaWxVbmxlc3NFcXVhbChzZWxmLmNvbjEuaXNvbGF0aW9uX2xldmVsICwgIkRFRkVSUkVEIikKICAgICAgICBzZWxmLmN1cjEuZXhlY3V0ZSgiaW5zZXJ0IGludG8gdGVzdChpKSB2YWx1ZXMgKDUpIikKICAgICAgICBzZWxmLmN1cjIuZXhlY3V0ZSgic2VsZWN0IGkgZnJvbSB0ZXN0IikKICAgICAgICByZXMgPSBzZWxmLmN1cjIuZmV0Y2hhbGwoKQogICAgICAgIHNlbGYuZmFpbFVubGVzc0VxdWFsKGxlbihyZXMpLCAxKQoKICAgIGRlZiBDaGVja1JhaXNlVGltZW91dChzZWxmKToKICAgICAgICBpZiBzcWxpdGUuc3FsaXRlX3ZlcnNpb25faW5mbyA8ICgzLCAyLCAyKToKICAgICAgICAgICAgIyBUaGlzIHdpbGwgZmFpbCAoaGFuZykgb24gZWFybGllciB2ZXJzaW9ucyBvZiBzcWxpdGUuCiAgICAgICAgICAgICMgRGV0ZXJtaW5lIGV4YWN0IHZlcnNpb24gaXQgd2FzIGZpeGVkLiAzLjIuMSBoYW5ncy4KICAgICAgICAgICAgcmV0dXJuCiAgICAgICAgc2VsZi5jdXIxLmV4ZWN1dGUoImNyZWF0ZSB0YWJsZSB0ZXN0KGkpIikKICAgICAgICBzZWxmLmN1cjEuZXhlY3V0ZSgiaW5zZXJ0IGludG8gdGVzdChpKSB2YWx1ZXMgKDUpIikKICAgICAgICB0cnk6CiAgICAgICAgICAgIHNlbGYuY3VyMi5leGVjdXRlKCJpbnNlcnQgaW50byB0ZXN0KGkpIHZhbHVlcyAoNSkiKQogICAgICAgICAgICBzZWxmLmZhaWwoInNob3VsZCBoYXZlIHJhaXNlZCBhbiBPcGVyYXRpb25hbEVycm9yIikKICAgICAgICBleGNlcHQgc3FsaXRlLk9wZXJhdGlvbmFsRXJyb3I6CiAgICAgICAgICAgIHBhc3MKICAgICAgICBleGNlcHQ6CiAgICAgICAgICAgIHNlbGYuZmFpbCgic2hvdWxkIGhhdmUgcmFpc2VkIGFuIE9wZXJhdGlvbmFsRXJyb3IiKQoKICAgIGRlZiBDaGVja0xvY2tpbmcoc2VsZik6CiAgICAgICAgIiIiCiAgICAgICAgVGhpcyB0ZXN0cyB0aGUgaW1wcm92ZWQgY29uY3VycmVuY3kgd2l0aCBweXNxbGl0ZSAyLjMuNC4gWW91IG5lZWRlZAogICAgICAgIHRvIHJvbGwgYmFjayBjb24yIGJlZm9yZSB5b3UgY291bGQgY29tbWl0IGNvbjEuCiAgICAgICAgIiIiCiAgICAgICAgaWYgc3FsaXRlLnNxbGl0ZV92ZXJzaW9uX2luZm8gPCAoMywgMiwgMik6CiAgICAgICAgICAgICMgVGhpcyB3aWxsIGZhaWwgKGhhbmcpIG9uIGVhcmxpZXIgdmVyc2lvbnMgb2Ygc3FsaXRlLgogICAgICAgICAgICAjIERldGVybWluZSBleGFjdCB2ZXJzaW9uIGl0IHdhcyBmaXhlZC4gMy4yLjEgaGFuZ3MuCiAgICAgICAgICAgIHJldHVybgogICAgICAgIHNlbGYuY3VyMS5leGVjdXRlKCJjcmVhdGUgdGFibGUgdGVzdChpKSIpCiAgICAgICAgc2VsZi5jdXIxLmV4ZWN1dGUoImluc2VydCBpbnRvIHRlc3QoaSkgdmFsdWVzICg1KSIpCiAgICAgICAgdHJ5OgogICAgICAgICAgICBzZWxmLmN1cjIuZXhlY3V0ZSgiaW5zZXJ0IGludG8gdGVzdChpKSB2YWx1ZXMgKDUpIikKICAgICAgICAgICAgc2VsZi5mYWlsKCJzaG91bGQgaGF2ZSByYWlzZWQgYW4gT3BlcmF0aW9uYWxFcnJvciIpCiAgICAgICAgZXhjZXB0IHNxbGl0ZS5PcGVyYXRpb25hbEVycm9yOgogICAgICAgICAgICBwYXNzCiAgICAgICAgZXhjZXB0OgogICAgICAgICAgICBzZWxmLmZhaWwoInNob3VsZCBoYXZlIHJhaXNlZCBhbiBPcGVyYXRpb25hbEVycm9yIikKICAgICAgICAjIE5PIHNlbGYuY29uMi5yb2xsYmFjaygpIEhFUkUhISEKICAgICAgICBzZWxmLmNvbjEuY29tbWl0KCkKCmNsYXNzIFNwZWNpYWxDb21tYW5kVGVzdHModW5pdHRlc3QuVGVzdENhc2UpOgogICAgZGVmIHNldFVwKHNlbGYpOgogICAgICAgIHNlbGYuY29uID0gc3FsaXRlLmNvbm5lY3QoIjptZW1vcnk6IikKICAgICAgICBzZWxmLmN1ciA9IHNlbGYuY29uLmN1cnNvcigpCgogICAgZGVmIENoZWNrVmFjdXVtKHNlbGYpOgogICAgICAgIHNlbGYuY3VyLmV4ZWN1dGUoImNyZWF0ZSB0YWJsZSB0ZXN0KGkpIikKICAgICAgICBzZWxmLmN1ci5leGVjdXRlKCJpbnNlcnQgaW50byB0ZXN0KGkpIHZhbHVlcyAoNSkiKQogICAgICAgIHNlbGYuY3VyLmV4ZWN1dGUoInZhY3V1bSIpCgogICAgZGVmIENoZWNrRHJvcFRhYmxlKHNlbGYpOgogICAgICAgIHNlbGYuY3VyLmV4ZWN1dGUoImNyZWF0ZSB0YWJsZSB0ZXN0KGkpIikKICAgICAgICBzZWxmLmN1ci5leGVjdXRlKCJpbnNlcnQgaW50byB0ZXN0KGkpIHZhbHVlcyAoNSkiKQogICAgICAgIHNlbGYuY3VyLmV4ZWN1dGUoImRyb3AgdGFibGUgdGVzdCIpCgogICAgZGVmIENoZWNrUHJhZ21hKHNlbGYpOgogICAgICAgIHNlbGYuY3VyLmV4ZWN1dGUoImNyZWF0ZSB0YWJsZSB0ZXN0KGkpIikKICAgICAgICBzZWxmLmN1ci5leGVjdXRlKCJpbnNlcnQgaW50byB0ZXN0KGkpIHZhbHVlcyAoNSkiKQogICAgICAgIHNlbGYuY3VyLmV4ZWN1dGUoInByYWdtYSBjb3VudF9jaGFuZ2VzPTEiKQoKICAgIGRlZiB0ZWFyRG93bihzZWxmKToKICAgICAgICBzZWxmLmN1ci5jbG9zZSgpCiAgICAgICAgc2VsZi5jb24uY2xvc2UoKQoKZGVmIHN1aXRlKCk6CiAgICBkZWZhdWx0X3N1aXRlID0gdW5pdHRlc3QubWFrZVN1aXRlKFRyYW5zYWN0aW9uVGVzdHMsICJDaGVjayIpCiAgICBzcGVjaWFsX2NvbW1hbmRfc3VpdGUgPSB1bml0dGVzdC5tYWtlU3VpdGUoU3BlY2lhbENvbW1hbmRUZXN0cywgIkNoZWNrIikKICAgIHJldHVybiB1bml0dGVzdC5UZXN0U3VpdGUoKGRlZmF1bHRfc3VpdGUsIHNwZWNpYWxfY29tbWFuZF9zdWl0ZSkpCgpkZWYgdGVzdCgpOgogICAgcnVubmVyID0gdW5pdHRlc3QuVGV4dFRlc3RSdW5uZXIoKQogICAgcnVubmVyLnJ1bihzdWl0ZSgpKQoKaWYgX19uYW1lX18gPT0gIl9fbWFpbl9fIjoKICAgIHRlc3QoKQo=