Ly8tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCi8vIENvcHlyaWdodCAoQykgTWljcm9zb2Z0LiBBbGwgcmlnaHRzIHJlc2VydmVkLgovLyBMaWNlbnNlZCB1bmRlciB0aGUgTUlUIGxpY2Vuc2UuIFNlZSBMSUNFTlNFLnR4dCBmaWxlIGluIHRoZSBwcm9qZWN0IHJvb3QgZm9yIGZ1bGwgbGljZW5zZSBpbmZvcm1hdGlvbi4KLy8tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCgpmdW5jdGlvbiBHZW5lcmF0ZUFycmF5KHNlZWQsIGFycmF5VHlwZSwgYXJyYXlTaXplLCBtaXNzaW5nVmFsdWVQZXJjZW50LCB0eXBlT2ZEZWNsYXJhdGlvbikgewogICAgZm9yICh2YXIgYXJyYXlJbmRleCA9IDA7IGFycmF5SW5kZXggPCBhcnJheVNpemU7IGFycmF5SW5kZXgrKykgewogICAgICAgIGlmIChpc1ZhckFycmF5ICYmIGFycmF5SW5kZXggIT0gMCkge30KICAgIH0KfQpmdW5jdGlvbiB0ZXN0MCgpIHsKICAgIGZ1bmN0aW9uIG1ha2VBcnJheUxlbmd0aCh4KSB7CiAgICAgICAgaWYgKHggPCAxIHx8IHggPiA0Mjk0OTY3Mjk1IHx8IHggIT0geCB8fCBpc05hTih4KSB8fCAhaXNGaW5pdGUoeCkpIHJldHVybiAxMDA7CiAgICAgICAgZWxzZSByZXR1cm4gTWF0aC5mbG9vcih4KSAmIDB4ZmZmZjsKICAgIH07OwoKICAgIGZ1bmN0aW9uIGxlYWYoKSB7CiAgICAgICAgcmV0dXJuIDEwMDsKICAgIH07CiAgICB2YXIgcHJvdG9PYmowID0ge307CiAgICB2YXIgYXJyT2JqMCA9IHt9OwogICAgdmFyIGZ1bmMwID0gZnVuY3Rpb24oKSB7fTsKICAgIHZhciBmdW5jMSA9IGZ1bmN0aW9uKCkgewogICAgICAgIGZ1bmN0aW9uIHYwKCkge30KICAgICAgICB2Mi5wcm90b3R5cGUubWV0aG9kMCA9IGZ1bmN0aW9uKCkgewogICAgICAgICAgICByZXR1cm4gKHRlc3QwLmNhbGxlcik7CiAgICAgICAgfTsKICAgICAgICBzdHJ2YXIzID0gJyp9JyArICdpMScgKyAnbDwnICsgJyphJy5jb25jYXQoYXJ5Wyg4NildKTsKICAgICAgICBmdW5jdGlvbiB2MTEodjEyKSB7fQogICAgICAgIGlmIChzaG91bGRCYWlsb3V0KSB7fQogICAgfTsKICAgIHZhciBmdW5jMiA9IGZ1bmN0aW9uKGFyZ01hdGgwLCBhcmdBcnJPYmoxKSB7fTsKICAgIHZhciBmdW5jMyA9IGZ1bmN0aW9uKGFyZ01hdGgyLCAuLi5hcmdBcnIzKSB7CiAgICAgICAgZnVuY3Rpb24gdjEzKCkgewogICAgICAgICAgICB2YXIgdjE2ID0gewogICAgICAgICAgICAgICAgdG9TdHJpbmc6IGZ1bmN0aW9uKCkgewogICAgICAgICAgICAgICAgICAgIHYxNCA9IDM7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuICJIZWxsbyBXb3JsZCI7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH07CiAgICAgICAgfQogICAgICAgIHYxMygpOwogICAgfTsKICAgIHZhciBmdW5jNCA9IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciB2MTggPSB7fTsKICAgICAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkodjE4LCAidGVzdHZhciIsIHt9KTsKICAgICAgICB2YXIgdjE5ID0gKCgoZyA8IHByb3RvT2JqMC5sZW5ndGgpICYmIChhIDw9IG9iajEubGVuZ3RoKSksIE9iamVjdC5jcmVhdGUoewogICAgICAgICAgICBwcm9wMDogZnVuYzMoKGMgJj0gYyksIGFyeSksCiAgICAgICAgICAgIHByb3AwOiBmdW5jMygoYyAmPSBjKSwgYXJ5KSwKICAgICAgICAgICAgcHJvcDE6ICh0ZXN0MC5jYWxsZXIpCiAgICAgICAgfSksICh0aGlzLnByb3AwID0gZnVuYzIoKHRlc3QwLmNhbGxlciksIGFyck9iajApKSwgZnVuYzAuY2FsbChwcm90b09iajApLCAoKHByb3RvT2JqMC5wcm9wMSA+PSBlKSB8fCAoZCA8PSBjKSkpOwogICAgICAgIGZvciAodmFyIHYyMSBpbiB2MjApIHsgLy8gaW4gb3BlcmF0b3IKICAgICAgICB9CiAgICB9OwogICAgYXJyT2JqMC5tZXRob2QwID0gZnVuYzQ7CiAgICB2YXIgYXJ5ID0gbmV3IEFycmF5KDEwKTsKICAgIHZhciBjID0gLTIxNDc0ODM2NDc7CiAgICB2YXIgZCA9IDI4NjQ0NjMyOTsKICAgIHZhciBlID0gLTgwMDk4MzY2NC45OwogICAgdmFyIGcgPSAtMS4xNTk3NTk3Njk5MzY0MkUrMTg7CiAgICBkbyB7CiAgICAgICAgYXJyT2JqMC5tZXRob2QwLmNhbGwoYXJyT2JqMCk7CiAgICAgICAgaWYgKChvYmoxLm1ldGhvZDAuY2FsbChvYmowKSAqIChmIDw8PSAoKCgodGVzdDAuY2FsbGVyKSA8IChWYXJBcnIwLnVuc2hpZnQoc3RydmFyMSwgKHRlc3QwLmNhbGxlciksIChhbGlhc09mRmxvYXRBcnIwLnBvcCgpKSwgKDU0MTA0NDE4MC4xID8gZiA6IC0xMzIwMDc4MDExKSkpKSB8IChJbnRBcnIwWyg5NSldID8gKChhICogdGhpcy5wcm9wMCArIHByb3RvT2JqMS5sZW5ndGgpICogKCg0MjU1MDYwOTkgKiBwcm90b09iajEucHJvcDEgKyBnKSArIGFyck9iajAubGVuZ3RoKSkgOiAodGVzdDAuY2FsbGVyKSkpICYgKCsrb2JqMC5sZW5ndGgpKSkgKyBWYXJBcnIyWyg3NSldKSkgewogICAgICAgICAgICBpZiAoKCgobmV3IEVycm9yKCdhYmMnKSkgaW5zdGFuY2VvZigodHlwZW9mIFJlZ0V4cCA9PSAnZnVuY3Rpb24nKSA/IFJlZ0V4cCA6IE9iamVjdCkpICE9PSAoKHRlc3QwLmNhbGxlcikgIT0gKGFsaWFzT2ZWYXJBcnIxWygoKCh0eXBlb2YoYikgPT0gJ29iamVjdCcpID49IDAgPyAodHlwZW9mKGIpID09ICdvYmplY3QnKSA6IDApKSAmIDBYRildKSkpKSB7CiAgICAgICAgICAgICAgICBmdW5jdGlvbiBmdW5jNSgpIHt9CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICBmdW5jdGlvbiBmdW5jNihhcmcwKSB7fQogICAgICAgICAgICAgICAgaWYgKChwcm90b09iajAubWV0aG9kMS5jYWxsKG9iajYpICE9ICh0eXBlb2YoaCkgIT0gJ3N0cmluZycpKSkge30KICAgICAgICAgICAgICAgIGZvciAodmFyIF9fbG9vcHZhcjMgPSAwOyBfX2xvb3B2YXIzIDwgMzsgX19sb29wdmFyMysrKSB7fQogICAgICAgICAgICB9CgogICAgICAgICAgICBmdW5jdGlvbiBmdW5jNygpIHt9CiAgICAgICAgfQogICAgfSB3aGlsZSAoKCh+KChuZXcgRXJyb3IoJ2FiYycpKSBpbnN0YW5jZW9mKCh0eXBlb2YgUmVnRXhwID09ICdmdW5jdGlvbicpID8gUmVnRXhwIDogT2JqZWN0KSkpKSAmJiBfX2xvb3B2YXIwIDwgMykKICAgIGlmICgoKChwcm90b09iajEucHJvcDEtLSkgIT0gKCgoVmFyQXJyMC51bnNoaWZ0KCgocGFyc2VJbnQoIi02MCIpIGluc3RhbmNlb2YoKHR5cGVvZiBFdmFsRXJyb3IgPT0gJ2Z1bmN0aW9uJykgPyBFdmFsRXJyb3IgOiBPYmplY3QpKSBpbnN0YW5jZW9mKCh0eXBlb2YgRXJyb3IgPT0gJ2Z1bmN0aW9uJykgPyBFcnJvciA6IE9iamVjdCkpLCAoKytwcm90b09iajEubGVuZ3RoKSwgKCgtMTc3MzU2Mzk0NiAqIDg0ICsgNDI5NDk2NzI5NikgPT0gYXJyT2JqMC5wcm9wMSksIChhcnJPYmowLnByb3AwICU9IGFsaWFzT2ZpMTZbKHByb3RvT2JqMC5wcm9wMCkgJiAyNTVdKSwgKHt9CiAgICAgICAgaW5zdGFuY2VvZigodHlwZW9mIEV2YWxFcnJvciA9PSAnZnVuY3Rpb24nKSA/IEV2YWxFcnJvciA6IE9iamVjdCkpLCAoKCdwcm9wMCcgaW4gYXJyT2JqMCkgKiAoKGQgPyA0NjgwNTU5NzkuMSA6IGgpICsgNzczMTY4MjE4LjEpKSwgKCgncHJvcDAnIGluIGFyck9iajApID8gKC0xLjg1OTY1MDY5MDk0ODU0RSsxOCA+PSAtMjIxKSA6IC0xNDc2NzExMDguOSksICgoLTUyNzgwMDcxNSA/IGYgOiBhcnJPYmowLnByb3AwKSA/IGFsaWFzT2ZJbnRBcnIwWygoKHByb3RvT2JqMC5wcm9wMCA+PSAwID8gcHJvdG9PYmowLnByb3AwIDogMCkpICYgMFhGKV0gOiAoKCdwcm9wMCcgaW4gYXJyT2JqMCkgKiAoKGQgPyA0NjgwNTU5NzkuMSA6IGgpICsgNzczMTY4MjE4LjEpKSksIGFyck9iajAubGVuZ3RoLCBwcm90b09iajAucHJvcDApKSAqIGFsaWFzT2ZGbG9hdEFycjBbKDE4KV0gLSB1aThbKChGbG9hdEFycjJbKDM4KV0gKiAodGVzdDAuY2FsbGVyKSAtIGFsaWFzT2ZJbnRBcnIwWygoKHByb3RvT2JqMC5wcm9wMCA+PSAwID8gcHJvdG9PYmowLnByb3AwIDogMCkpICYgMFhGKV0pKSAmIDI1NV0pICogKGggPj4+PSBmdW5jMCgpKSAtIChwcm90b09iajAucHJvcDEgPj0gcHJvdG9PYmoxLnByb3AwKSkpICE9IChwYXJzZUludCgiLTYwIikgaW5zdGFuY2VvZigodHlwZW9mIEV2YWxFcnJvciA9PSAnZnVuY3Rpb24nKSA/IEV2YWxFcnJvciA6IE9iamVjdCkpKSkgewogICAgICAgIHByb3RvT2JqMSA9IHsKICAgICAgICAgICAgbWV0aG9kMDogZnVuY3Rpb24oKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gZnVuY3Rpb24gdjI1KCkgewogICAgICAgICAgICAgICAgICAgIGZvciAodmFyIF9zdHJ2YXIwIGluIGk4KSB7fQogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9LAogICAgICAgICAgICBtZXRob2QxOiBmdW5jdGlvbigpIHsKICAgICAgICAgICAgICAgIHJldHVybiBmdW5jdGlvbiB2MjYoKSB7fQogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBzd2l0Y2ggKHN0cnZhcjApIHsKICAgICAgICAgICAgY2FzZSAn7kAnICsgJyEkJyArICcoJCcgKyAnJSEnOgogICAgICAgIH0KICAgIH0KfTsKdGVzdDAoKTsK