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b3Zlcm5lZCBieSBhIEJTRC1zdHlsZSBsaWNlbnNlIHRoYXQgY2FuIGJlCiAqIGZvdW5kIGluIHRoZSBMSUNFTlNFIGZpbGUuICovCgpodG1sLCBib2R5IHsKICAtd2Via2l0LXVzZXItc2VsZWN0OiBub25lOwogIGZvbnQtZmFtaWx5OiBzYW5zLXNlcmlmOwogIGhlaWdodDogMTAwJTsKICBtYXJnaW46IDA7CiAgb3ZlcmZsb3c6IGhpZGRlbjsKICB0ZXh0LWFsaWduOiBjZW50ZXI7CiAgd2lkdGg6IDEwMCU7Cn0KCmgxIHsKICBkaXNwbGF5OiBub25lOwogIGZvbnQtc2l6ZTogMTBwdDsKICBmb250LXdlaWdodDogbm9ybWFsOwogIHBhZGRpbmc6IDBwdCAxMHB0Owp9CgpwIHsKICBmb250LXNpemU6IDhwdDsKICBwYWRkaW5nOiAwcHQgMTRwdDsKfQoKI3QgewogIGJhY2tncm91bmQtY29sb3I6ICNmN2Y3Zjc7CiAgY29sb3I6ICM2NDY0NjQ7Cn0KCiNvdXRlciB7CiAgYWxpZ24taXRlbXM6IGNlbnRlcjsKICBib3gtc2l6aW5nOiBib3JkZXItYm94OwogIGRpc3BsYXk6IGZsZXg7CiAgaGVpZ2h0OiAxMDAlOwogIGp1c3RpZnktY29udGVudDogY2VudGVyOwogIHBvc2l0aW9uOiBhYnNvbHV0ZTsKICB3aWR0aDogMTAwJTsKICBmbGV4LWRpcmVjdGlvbjogY29sdW1uOwp9CgouaWNvbiB7CiAgbWF4LWhlaWdodDogMTAwJTsKICBtYXgtd2lkdGg6IDEwMCU7CiAgb3BhY2l0eTogLjM7Cn0KCkBtZWRpYSAob3JpZW50YXRpb246IGxhbmRzY2FwZSkgYW5kIChtaW4taGVpZ2h0OiAyZW0pIGFuZCAobWluLXdpZHRoOiAxNGVtKSB7CiAgI291dGVyIHsKICAgIGZsZXgtZGlyZWN0aW9uOiByb3c7CiAgfQogIC5pY29uIHsKICAgIG1heC1oZWlnaHQ6IDEwMCU7CiAgICBtYXgtd2lkdGg6IDUwJTsKICB9CiAgaDEgewogICAgZGlzcGxheTogYmxvY2s7CiAgfQp9CgpAbWVkaWEgKG1pbi1oZWlnaHQ6IDdlbSkgYW5kIChtaW4td2lkdGg6IDZlbSkgewogICNvdXRlciB7CiAgICBmbGV4LWRpcmVjdGlvbjogY29sdW1uOwogIH0KICAuaWNvbiB7CiAgICBtYXgtaGVpZ2h0OiA1MCU7CiAgICBtYXgtd2lkdGg6IDEwMCU7CiAgfQogIGgxIHsKICAgIGRpc3BsYXk6IGJsb2NrOwogIH0KfQo8L3N0eWxlPgogIDwvaGVhZD4KICA8Ym9keSBpZD0idCIgb25sb2FkPSJub3RpZnlEaWRGaW5pc2hMb2FkaW5nKCk7Ij4KICAgIDxkaXYgaTE4bi12YWx1ZXM9InRpdGxlOm5hbWUiIGlkPSJvdXRlciI+CiAgICAgIDxpbWcgY2xhc3M9Imljb24iCiAgICAgICAgICAgc3JjPSJkYXRhOmltYWdlL3N2Zyt4bWw7YmFzZTY0LFBITjJaeUI0Yld4dWN6MGlhSFIwY0RvdkwzZDNkeTUzTXk1dmNtY3ZNakF3TUM5emRtY2lJSGRwWkhSb1BTSTBPSEI0SWlCb1pXbG5hSFE5SWpRNGNIZ2lJSFpwWlhkQ2IzZzlJakFnTUNBME9DQTBPQ0lnWm1sc2JEMGlJell5TmpJMk1pSStDaUFnSUNBOGNHRjBhQ0JrUFNKTk1DQXdhRFE0ZGpRNFNEQjZJaUJtYVd4c1BTSnViMjVsSWk4K0NpQWdJQ0E4Y0dGMGFDQmtQU0pOTkRFZ01qSm9MVE4yTFRoak1DMHlMakl4TFRFdU56a3ROQzAwTFRSb0xUaFdOMk13TFRJdU56WXRNaTR5TkMwMUxUVXROWE10TlNBeUxqSTBMVFVnTlhZelNEaGpMVEl1TWpFZ01DMHpMams0SURFdU56a3RNeTQ1T0NBMGJDMHVNREVnTnk0MlNEZGpNaTQ1T0NBd0lEVXVOQ0F5TGpReUlEVXVOQ0ExTGpSVE9TNDVPQ0F6TWk0MElEY2dNekl1TkVnMExqQXhURFFnTkRCak1DQXlMakl4SURFdU56a2dOQ0EwSURSb055NDJkaTB6WXpBdE1pNDVPQ0F5TGpReUxUVXVOQ0ExTGpRdE5TNDBJREl1T1RnZ01DQTFMalFnTWk0ME1pQTFMalFnTlM0MGRqTklNelJqTWk0eU1TQXdJRFF0TVM0M09TQTBMVFIyTFRob00yTXlMamMySURBZ05TMHlMakkwSURVdE5YTXRNaTR5TkMwMUxUVXROWG9pTHo0S1BDOXpkbWMrQ2c9PSI+CiAgICAgIDxoMSBpZD0ibWVzc2FnZSI+JGkxOG57bWVzc2FnZX08L2gxPgogICAgPC9kaXY+CiAgPC9ib2R5Pgo8L2h0bWw+CjwhZG9jdHlwZSBodG1sPgo8aHRtbD4KICA8aGVhZD4KICAgIDxtZXRhIGNoYXJzZXQ9InV0Zi04Ij4KICAgIDxtZXRhIG5hbWU9InZpZXdwb3J0IiBjb250ZW50PSJ3aWR0aD1kZXZpY2Utd2lkdGgsIHVzZXItc2NhbGFibGU9bm8iPgogICAgPHN0eWxlPi8qIENvcHlyaWdodCAoYykgMjAxMiBUaGUgQ2hyb21pdW0gQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICogVXNlIG9mIHRoaXMgc291cmNlIGNvZGUgaXMgZ292ZXJuZWQgYnkgYSBCU0Qtc3R5bGUgbGljZW5zZSB0aGF0IGNhbiBiZQogKiBmb3VuZCBpbiB0aGUgTElDRU5TRSBmaWxlLiAqLwoKaHRtbCwgYm9keSB7CiAgLXdlYmtpdC11c2VyLXNlbGVjdDogbm9uZTsKICBmb250LWZhbWlseTogc2Fucy1zZXJpZjsKICBoZWlnaHQ6IDEwMCU7CiAgbWFyZ2luOiAwOwogIG92ZXJmbG93OiBoaWRkZW47CiAgdGV4dC1hbGlnbjogY2VudGVyOwogIHdpZHRoOiAxMDAlOwp9CgpoMSB7CiAgZGlzcGxheTogbm9uZTsKICBmb250LXNpemU6IDEwcHQ7CiAgZm9udC13ZWlnaHQ6IG5vcm1hbDsKICBwYWRkaW5nOiAwcHQgMTBwdDsKfQoKcCB7CiAgZm9udC1zaXplOiA4cHQ7CiAgcGFkZGluZzogMHB0IDE0cHQ7Cn0KCiN0IHsKICBiYWNrZ3JvdW5kLWNvbG9yOiAjZjdmN2Y3OwogIGNvbG9yOiAjNjQ2NDY0Owp9Cgojb3V0ZXIgewogIGFsaWduLWl0ZW1zOiBjZW50ZXI7CiAgYm94LXNpemluZzogYm9yZGVyLWJveDsKICBkaXNwbGF5OiBmbGV4OwogIGhlaWdodDogMTAwJTsKICBqdXN0aWZ5LWNvbnRlbnQ6IGNlbnRlcjsKICBwb3NpdGlvbjogYWJzb2x1dGU7CiAgd2lkdGg6IDEwMCU7CiAgZmxleC1kaXJlY3Rpb246IGNvbHVtbjsKfQoKLmljb24gewogIG1heC1oZWlnaHQ6IDEwMCU7CiAgbWF4LXdpZHRoOiAxMDAlOwogIG9wYWNpdHk6IC4zOwp9CgpAbWVkaWEgKG9yaWVudGF0aW9uOiBsYW5kc2NhcGUpIGFuZCAobWluLWhlaWdodDogMmVtKSBhbmQgKG1pbi13aWR0aDogMTRlbSkgewogICNvdXRlciB7CiAgICBmbGV4LWRpcmVjdGlvbjogcm93OwogIH0KICAuaWNvbiB7CiAgICBtYXgtaGVpZ2h0OiAxMDAlOwogICAgbWF4LXdpZHRoOiA1MCU7CiAgfQogIGgxIHsKICAgIGRpc3BsYXk6IGJsb2NrOwogIH0KfQoKQG1lZGlhIChtaW4taGVpZ2h0OiA3ZW0pIGFuZCAobWluLXdpZHRoOiA2ZW0pIHsKICAjb3V0ZXIgewogICAgZmxleC1kaXJlY3Rpb246IGNvbHVtbjsKICB9CiAgLmljb24gewogICAgbWF4LWhlaWdodDogNTAlOwogICAgbWF4LXdpZHRoOiAxMDAlOwogIH0KICBoMSB7CiAgICBkaXNwbGF5OiBibG9jazsKICB9Cn0KPC9zdHlsZT4KICA8L2hlYWQ+CiAgPGJvZHkgaWQ9InQiIG9uTG9hZD0iaW5zZXJ0TGluaygpIj4KICAgIDxkaXYgaTE4bi12YWx1ZXM9InRpdGxlOm5hbWUiIGlkPSJvdXRlciI+CiAgICAgIDxpbWcgY2xhc3M9Imljb24iCiAgICAgICAgICAgc3JjPSJkYXRhOmltYWdlL3N2Zyt4bWw7YmFzZTY0LFBITjJaeUI0Yld4dWN6MGlhSFIwY0RvdkwzZDNkeTUzTXk1dmNtY3ZNakF3TUM5emRtY2lJSGRwWkhSb1BTSTBPSEI0SWlCb1pXbG5hSFE5SWpRNGNIZ2lJSFpwWlhkQ2IzZzlJakFnTUNBME9DQTBPQ0lnWm1sc2JEMGlJell5TmpJMk1pSStDaUFnSUNBOGNHRjBhQ0JrUFNKTk1DQXdhRFE0ZGpRNFNEQjZJaUJtYVd4c1BTSnViMjVsSWk4K0NpQWdJQ0E4Y0dGMGFDQmtQU0pOTkRFZ01qSm9MVE4yTFRoak1DMHlMakl4TFRFdU56a3ROQzAwTFRSb0xUaFdOMk13TFRJdU56WXRNaTR5TkMwMUxUVXROWE10TlNBeUxqSTBMVFVnTlhZelNEaGpMVEl1TWpFZ01DMHpMams0SURFdU56a3RNeTQ1T0NBMGJDMHVNREVnTnk0MlNEZGpNaTQ1T0NBd0lEVXVOQ0F5TGpReUlEVXVOQ0ExTGpSVE9TNDVPQ0F6TWk0MElEY2dNekl1TkVnMExqQXhURFFnTkRCak1DQXlMakl4SURFdU56a2dOQ0EwSURSb055NDJkaTB6WXpBdE1pNDVPQ0F5TGpReUxUVXVOQ0ExTGpRdE5TNDBJREl1T1RnZ01DQTFMalFnTWk0ME1pQTFMalFnTlM0MGRqTklNelJqTWk0eU1TQXdJRFF0TVM0M09TQTBMVFIyTFRob00yTXlMamMySURBZ05TMHlMakkwSURVdE5YTXRNaTR5TkMwMUxUVXROWG9pTHo0S1BDOXpkbWMrQ2c9PSI+CiAgICAgIDxoMSBpZD0ibWVzc2FnZSI+JGkxOG57bWVzc2FnZX08L2gxPgogICAgPC9kaXY+CiAgPC9ib2R5Pgo8L2h0bWw+CjwhZG9jdHlwZSBodG1sPgo8aHRtbD4KICA8aGVhZD4KICAgIDxtZXRhIGNoYXJzZXQ9InV0Zi04Ij4KICAgIDxtZXRhIG5hbWU9InZpZXdwb3J0IiBjb250ZW50PSJ3aWR0aD1kZXZpY2Utd2lkdGgsIHVzZXItc2NhbGFibGU9bm8iPgogICAgPHN0eWxlPgogICAgICBodG1sLAogICAgICBib2R5IHsKICAgICAgICBoZWlnaHQ6IDEwMCU7CiAgICAgICAgd2lkdGg6IDEwMCU7CiAgICAgIH0KCiAgICAgIGJvZHkgewogICAgICAgIGJhY2tncm91bmQtY29sb3I6ICNmNWY1ZjU7ICAvKiBnb29nbGUtZ3JleS0xMDAgKi8KICAgICAgICBtYXJnaW46IDA7CiAgICAgIH0KCiAgICAgIHN2ZyB7CiAgICAgICAgaGVpZ2h0OiA0MHB4OwogICAgICAgIHdpZHRoOiA0MHB4OwogICAgICB9CgogICAgICBwYXRoIHsKICAgICAgICBmaWxsOiAjYmRiZGJkOyAgLyogZ29vZ2xlLWdyZXktNDAwICovCiAgICAgIH0KCiAgICAgICNpY29uLWNvbnRhaW5lciB7CiAgICAgICAgYWxpZ24taXRlbXM6IGNlbnRlcjsKICAgICAgICBkaXNwbGF5OiBmbGV4OwogICAgICAgIGhlaWdodDogMTAwJTsKICAgICAgICBqdXN0aWZ5LWNvbnRlbnQ6IGNlbnRlcjsKICAgICAgICB3aWR0aDogMTAwJTsKICAgICAgfQoKICAgICAgI2Zvb3RlciB7CiAgICAgICAgYWxpZ24taXRlbXM6IGNlbnRlcjsKICAgICAgICBiYWNrZ3JvdW5kLWNvbG9yOiAjNDI4NWY0OyAgLyogZ29vZ2xlLWJsdWUtNTAwICovCiAgICAgICAgYm9yZGVyLXJhZGl1czogMnB4OwogICAgICAgIGJvdHRvbTogMDsKICAgICAgICBjb2xvcjogd2hpdGU7CiAgICAgICAgZGlzcGxheTogZmxleDsKICAgICAgICBmb250LXNpemU6IDE0cHg7CiAgICAgICAganVzdGlmeS1jb250ZW50OiBzcGFjZS1iZXR3ZWVuOwogICAgICAgIGxlZnQ6IDA7CiAgICAgICAgbWF4LWhlaWdodDogNTJweDsKICAgICAgICBtaW4taGVpZ2h0OiAyMHB4OwogICAgICAgIHBhZGRpbmc6IDE0cHggMjRweDsKICAgICAgICBwb3NpdGlvbjogYWJzb2x1dGU7CiAgICAgICAgcmlnaHQ6IDA7CiAgICAgIH0KCiAgICAgIHAsCiAgICAgIGEgewogICAgICAgIGxpbmUtaGVpZ2h0OiAyMHB4OwogICAgICB9CgogICAgICBwIHsKICAgICAgICBmb250LWZhbWlseTogUm9ib3RvOwogICAgICAgIG1hcmdpbjogMDsKICAgICAgfQoKICAgICAgYSB7CiAgICAgICAgZm9udC1mYW1pbHk6IFJvYm90byBNZWRpdW07CiAgICAgICAgbWFyZ2luLWxlZnQ6IDQ4cHg7CiAgICAgICAgdGV4dC10cmFuc2Zvcm06IHVwcGVyY2FzZTsKICAgICAgfQoKICAgICAgYTpsaW5rLAogICAgICBhOnZpc2l0ZWQgewogICAgICAgIGNvbG9yOiB3aGl0ZTsKICAgICAgICB0ZXh0LWRlY29yYXRpb246IG5vbmU7CiAgICAgIH0KCiAgICA8L3N0eWxlPgogIDwvaGVhZD4KICA8Ym9keT4KICAgIDxkaXYgaWQ9Imljb24tY29udGFpbmVyIj4KICAgICAgPCEtLSBNYXRlcmlhbCBEZXNpZ24gUERGIGljb24gLS0+CiAgICAgIDxzdmcgdmlld2JveD0iMCAwIDI0IDI0Ij4KICAgICAgICA8cGF0aCBkPSJNNyAxMS41aDF2LTFIN3Yxek0xOSAzSDVjLTEuMSAwLTIgLjktMiAydjE0YzAgMS4xLjkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWNWMwLTEuMS0uOS0yLTItMnptLTkuNSA4LjVjMCAuODMtLjY3IDEuNS0xLjUgMS41SDd2Mkg1LjVWOUg4Yy44MyAwIDEuNS42NyAxLjUgMS41djF6bTEwLTFIMTd2MWgxLjVWMTNIMTd2MmgtMS41VjloNHYxLjV6bS01IDNjMCAuODMtLjY3IDEuNS0xLjUgMS41aC0yLjVWOUgxM2MuODMgMCAxLjUuNjcgMS41IDEuNXYzem0tMi41IDBoMXYtM2gtMXYzeiI+PC9wYXRoPgogICAgICA8L3N2Zz4KICAgIDwvZGl2PgogICAgPGRpdiBpZD0iZm9vdGVyIiBpMThuLXZhbHVlcz0idGl0bGU6bmFtZSI+CiAgICAgIDxwPiRpMThue2ZpbGVOYW1lfTwvcD4KICAgICAgPGEgaHJlZj0iIyIgb25jbGljaz0icGx1Z2luLm9wZW5QREYoKSI+VmlldyBQREY8L2E+CiAgICA8L2Rpdj4KICA8L2JvZHk+CjwvaHRtbD4KPCFkb2N0eXBlIGh0bWw+CjxodG1sPgo8aGVhZD4KICA8bWV0YSBjaGFyc2V0PSJ1dGYtOCI+CiAgPG1ldGEgbmFtZT0idmlld3BvcnQiIGNvbnRlbnQ9IndpZHRoPWRldmljZS13aWR0aCwgdXNlci1zY2FsYWJsZT1ubyI+CiAgPHNjcmlwdD4KICAgIGZ1bmN0aW9uIHNldE1lc3NhZ2UobXNnKSB7CiAgICAgIGRvY3VtZW50LmdldEVsZW1lbnRCeUlkKCdtZXNzYWdlJykudGV4dENvbnRlbnQgPSBtc2c7CiAgICB9CiAgICBmdW5jdGlvbiBub3RpZnlEaWRGaW5pc2hMb2FkaW5nKCkgewogICAgICBpZiAocGx1Z2luLmRpZEZpbmlzaExvYWRpbmcpCiAgICAgICAgcGx1Z2luLmRpZEZpbmlzaExvYWRpbmcoKTsKCiAgICAgIGlmIChwbHVnaW4uZGlkRmluaXNoSWNvblJlcG9zaXRpb25Gb3JUZXN0aW5nKQogICAgICAgIHBsdWdpbi5kaWRGaW5pc2hJY29uUmVwb3NpdGlvbkZvclRlc3RpbmcoKTsKICAgIH0KICA8L3NjcmlwdD4KICA8c3R5bGU+LyogQ29weXJpZ2h0IChjKSAyMDEyIFRoZSBDaHJvbWl1bSBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogKiBVc2Ugb2YgdGhpcyBzb3VyY2UgY29kZSBpcyBnb3Zlcm5lZCBieSBhIEJTRC1zdHlsZSBsaWNlbnNlIHRoYXQgY2FuIGJlCiAqIGZvdW5kIGluIHRoZSBMSUNFTlNFIGZpbGUuICovCgpodG1sLCBib2R5IHsKICAtd2Via2l0LXVzZXItc2VsZWN0OiBub25lOwogIGZvbnQtZmFtaWx5OiBzYW5zLXNlcmlmOwogIGhlaWdodDogMTAwJTsKICBtYXJnaW46IDA7CiAgb3ZlcmZsb3c6IGhpZGRlbjsKICB0ZXh0LWFsaWduOiBjZW50ZXI7CiAgd2lkdGg6IDEwMCU7Cn0KCmgxIHsKICBkaXNwbGF5OiBub25lOwogIGZvbnQtc2l6ZTogMTBwdDsKICBmb250LXdlaWdodDogbm9ybWFsOwogIHBhZGRpbmc6IDBwdCAxMHB0Owp9CgpwIHsKICBmb250LXNpemU6IDhwdDsKICBwYWRkaW5nOiAwcHQgMTRwdDsKfQoKI3QgewogIGJhY2tncm91bmQtY29sb3I6ICNmN2Y3Zjc7CiAgY29sb3I6ICM2NDY0NjQ7Cn0KCiNvdXRlciB7CiAgYWxpZ24taXRlbXM6IGNlbnRlcjsKICBib3gtc2l6aW5nOiBib3JkZXItYm94OwogIGRpc3BsYXk6IGZsZXg7CiAgaGVpZ2h0OiAxMDAlOwogIGp1c3RpZnktY29udGVudDogY2VudGVyOwogIHBvc2l0aW9uOiBhYnNvbHV0ZTsKICB3aWR0aDogMTAwJTsKICBmbGV4LWRpcmVjdGlvbjogY29sdW1uOwp9CgouaWNvbiB7CiAgbWF4LWhlaWdodDogMTAwJTsKICBtYXgtd2lkdGg6IDEwMCU7CiAgb3BhY2l0eTogLjM7Cn0KCkBtZWRpYSAob3JpZW50YXRpb246IGxhbmRzY2FwZSkgYW5kIChtaW4taGVpZ2h0OiAyZW0pIGFuZCAobWluLXdpZHRoOiAxNGVtKSB7CiAgI291dGVyIHsKICAgIGZsZXgtZGlyZWN0aW9uOiByb3c7CiAgfQogIC5pY29uIHsKICAgIG1heC1oZWlnaHQ6IDEwMCU7CiAgICBtYXgtd2lkdGg6IDUwJTsKICB9CiAgaDEgewogICAgZGlzcGxheTogYmxvY2s7CiAgfQp9CgpAbWVkaWEgKG1pbi1oZWlnaHQ6IDdlbSkgYW5kIChtaW4td2lkdGg6IDZlbSkgewogICNvdXRlciB7CiAgICBmbGV4LWRpcmVjdGlvbjogY29sdW1uOwogIH0KICAuaWNvbiB7CiAgICBtYXgtaGVpZ2h0OiA1MCU7CiAgICBtYXgtd2lkdGg6IDEwMCU7CiAgfQogIGgxIHsKICAgIGRpc3BsYXk6IGJsb2NrOwogIH0KfQo8L3N0eWxlPgogIDxzdHlsZT4KICAjb3V0ZXIgewogICAgY3Vyc29yOiBwb2ludGVyOwogIH0KICA8L3N0eWxlPgo8L2hlYWQ+Cjxib2R5IGlkPSJ0IiBvbmxvYWQ9Im5vdGlmeURpZEZpbmlzaExvYWRpbmcoKTsiPgogIDxkaXYgaTE4bi12YWx1ZXM9InRpdGxlOm5hbWUiIGlkPSJvdXRlciI+CiAgICA8aW1nIGNsYXNzPSJpY29uIgogICAgICAgICBzcmM9ImRhdGE6aW1hZ2Uvc3ZnK3htbDtiYXNlNjQsUEhOMlp5QjRiV3h1Y3owaWFIUjBjRG92TDNkM2R5NTNNeTV2Y21jdk1qQXdNQzl6ZG1jaUlIZHBaSFJvUFNJME9IQjRJaUJvWldsbmFIUTlJalE0Y0hnaUlIWnBaWGRDYjNnOUlqQWdNQ0EwT0NBME9DSWdabWxzYkQwaUl6WXlOakkyTWlJK0NpQWdJQ0E4Y0dGMGFDQmtQU0pOTUNBd2FEUTRkalE0U0RCNklpQm1hV3hzUFNKdWIyNWxJaTgrQ2lBZ0lDQThjR0YwYUNCa1BTSk5OREVnTWpKb0xUTjJMVGhqTUMweUxqSXhMVEV1TnprdE5DMDBMVFJvTFRoV04yTXdMVEl1TnpZdE1pNHlOQzAxTFRVdE5YTXROU0F5TGpJMExUVWdOWFl6U0RoakxUSXVNakVnTUMwekxqazRJREV1TnprdE15NDVPQ0EwYkMwdU1ERWdOeTQyU0Rkak1pNDVPQ0F3SURVdU5DQXlMalF5SURVdU5DQTFMalJUT1M0NU9DQXpNaTQwSURjZ016SXVORWcwTGpBeFREUWdOREJqTUNBeUxqSXhJREV1TnprZ05DQTBJRFJvTnk0MmRpMHpZekF0TWk0NU9DQXlMalF5TFRVdU5DQTFMalF0TlM0MElESXVPVGdnTUNBMUxqUWdNaTQwTWlBMUxqUWdOUzQwZGpOSU16UmpNaTR5TVNBd0lEUXRNUzQzT1NBMExUUjJMVGhvTTJNeUxqYzJJREFnTlMweUxqSTBJRFV0TlhNdE1pNHlOQzAxTFRVdE5Yb2lMejRLUEM5emRtYytDZz09Ij4KICAgIDxoMSBpZD0ibWVzc2FnZSI+JGkxOG57bWVzc2FnZX08L2gxPgogIDwvZGl2PgogIDxzY3JpcHQ+CiAgICB3aW5kb3cub25rZXlkb3duID0gZnVuY3Rpb24oZSkgewogICAgICBpZiAoZS5rZXkgPT0gJ0VudGVyJyB8fCBlLmtleSA9PSAnICcpIHsKICAgICAgICBwbHVnaW4uc2hvd1Blcm1pc3Npb25CdWJibGUoKTsKICAgICAgICBlLnByZXZlbnREZWZhdWx0KCk7CiAgICAgIH0KICAgIH07CgogICAgZG9jdW1lbnQuZ2V0RWxlbWVudEJ5SWQoJ291dGVyJykub25jbGljayA9IGZ1bmN0aW9uKCkgewogICAgICBwbHVnaW4uc2hvd1Blcm1pc3Npb25CdWJibGUoKTsKICAgIH07CiAgPC9zY3JpcHQ+CjwvYm9keT4KPC9odG1sPgo8IWRvY3R5cGUgaHRtbD4KPGh0bWw+CjxoZWFkPgo8bWV0YSBjaGFyc2V0PSJ1dGYtOCI+CjxtZXRhIG5hbWU9InZpZXdwb3J0IiBjb250ZW50PSJ3aWR0aD1kZXZpY2Utd2lkdGgsIHVzZXItc2NhbGFibGU9bm8iPgo8c2NyaXB0PgogIHdpbmRvdy5vbmxvYWQgPSBmdW5jdGlvbigpIHsKICAgIGlmIChwbHVnaW4uZGlkRmluaXNoTG9hZGluZykKICAgICAgcGx1Z2luLmRpZEZpbmlzaExvYWRpbmcoKTsKICB9OwoKICB3aW5kb3cub25rZXlkb3duID0gZnVuY3Rpb24oZSkgewogICAgaWYgKGUua2V5ID09ICdFbnRlcicgfHwgZS5rZXkgPT0gJyAnKSB7CiAgICAgIHBsdWdpbi5sb2FkKCk7CiAgICAgIGUucHJldmVudERlZmF1bHQoKTsKICAgIH0KICB9Owo8L3NjcmlwdD4KPHN0eWxlPi8qIENvcHlyaWdodCAoYykgMjAxMiBUaGUgQ2hyb21pdW0gQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICogVXNlIG9mIHRoaXMgc291cmNlIGNvZGUgaXMgZ292ZXJuZWQgYnkgYSBCU0Qtc3R5bGUgbGljZW5zZSB0aGF0IGNhbiBiZQogKiBmb3VuZCBpbiB0aGUgTElDRU5TRSBmaWxlLiAqLwoKaHRtbCwgYm9keSB7CiAgLXdlYmtpdC11c2VyLXNlbGVjdDogbm9uZTsKICBmb250LWZhbWlseTogc2Fucy1zZXJpZjsKICBoZWlnaHQ6IDEwMCU7CiAgbWFyZ2luOiAwOwogIG92ZXJmbG93OiBoaWRkZW47CiAgdGV4dC1hbGlnbjogY2VudGVyOwogIHdpZHRoOiAxMDAlOwp9CgpoMSB7CiAgZGlzcGxheTogbm9uZTsKICBmb250LXNpemU6IDEwcHQ7CiAgZm9udC13ZWlnaHQ6IG5vcm1hbDsKICBwYWRkaW5nOiAwcHQgMTBwdDsKfQoKcCB7CiAgZm9udC1zaXplOiA4cHQ7CiAgcGFkZGluZzogMHB0IDE0cHQ7Cn0KCiN0IHsKICBiYWNrZ3JvdW5kLWNvbG9yOiAjZjdmN2Y3OwogIGNvbG9yOiAjNjQ2NDY0Owp9Cgojb3V0ZXIgewogIGFsaWduLWl0ZW1zOiBjZW50ZXI7CiAgYm94LXNpemluZzogYm9yZGVyLWJveDsKICBkaXNwbGF5OiBmbGV4OwogIGhlaWdodDogMTAwJTsKICBqdXN0aWZ5LWNvbnRlbnQ6IGNlbnRlcjsKICBwb3NpdGlvbjogYWJzb2x1dGU7CiAgd2lkdGg6IDEwMCU7CiAgZmxleC1kaXJlY3Rpb246IGNvbHVtbjsKfQoKLmljb24gewogIG1heC1oZWlnaHQ6IDEwMCU7CiAgbWF4LXdpZHRoOiAxMDAlOwogIG9wYWNpdHk6IC4zOwp9CgpAbWVkaWEgKG9yaWVudGF0aW9uOiBsYW5kc2NhcGUpIGFuZCAobWluLWhlaWdodDogMmVtKSBhbmQgKG1pbi13aWR0aDogMTRlbSkgewogICNvdXRlciB7CiAgICBmbGV4LWRpcmVjdGlvbjogcm93OwogIH0KICAuaWNvbiB7CiAgICBtYXgtaGVpZ2h0OiAxMDAlOwogICAgbWF4LXdpZHRoOiA1MCU7CiAgfQogIGgxIHsKICAgIGRpc3BsYXk6IGJsb2NrOwogIH0KfQoKQG1lZGlhIChtaW4taGVpZ2h0OiA3ZW0pIGFuZCAobWluLXdpZHRoOiA2ZW0pIHsKICAjb3V0ZXIgewogICAgZmxleC1kaXJlY3Rpb246IGNvbHVtbjsKICB9CiAgLmljb24gewogICAgbWF4LWhlaWdodDogNTAlOwogICAgbWF4LXdpZHRoOiAxMDAlOwogIH0KICBoMSB7CiAgICBkaXNwbGF5OiBibG9jazsKICB9Cn0KPC9zdHlsZT4KPHN0eWxlPgojb3V0ZXIgewogIGJvcmRlcjogbm9uZTsKICBmbGV4LWRpcmVjdGlvbjogcm93OwogIGN1cnNvcjogcG9pbnRlcjsKfQoKI3NoaWVsZGluZyB7CiAgYmFja2dyb3VuZC1jb2xvcjogcmdiYSgwLCAwLCAwLCAwLjUpOwogIGhlaWdodDogMTAwJTsKICBsZWZ0OiAwcHg7CiAgcG9zaXRpb246IGFic29sdXRlOwogIHRvcDogMHB4OwogIHdpZHRoOiAxMDAlOwogIHotaW5kZXg6IDI7Cn0KCiNwbHVnaW4taWNvbiB7CiAgb3BhY2l0eTogMC44OwogIG1heC1oZWlnaHQ6IDEwMCU7CiAgbWF4LXdpZHRoOiAxMDAlOwogIG1pbi13aWR0aDogMDsKICBtaW4taGVpZ2h0OiAwOwp9CgojcGx1Z2luLWljb246aG92ZXIgewogIG9wYWNpdHk6IDAuOTU7Cn0KCiNwb3N0ZXIgewogIGhlaWdodDogMTAwJTsKICBvYmplY3QtZml0OiBjb250YWluOwogIHdpZHRoOiAxMDAlOwogIHotaW5kZXg6IDE7Cn0KCiNpbm5lci1jb250YWluZXIgewogIGFsaWduLWl0ZW1zOiBjZW50ZXI7CiAgZGlzcGxheTogZmxleDsKICBoZWlnaHQ6IDEwMCU7CiAganVzdGlmeS1jb250ZW50OiBjZW50ZXI7CiAgbGVmdDogMHB4OwogIG1heC1oZWlnaHQ6IDEwMCU7CiAgbWF4LXdpZHRoOiAxMDAlOwogIHBvc2l0aW9uOiBhYnNvbHV0ZTsKICB0b3A6IDBweDsKICB3aWR0aDogMTAwJTsKICB6LWluZGV4OiAyOwp9Cjwvc3R5bGU+CjxiYXNlIGkxOG4tdmFsdWVzPSJocmVmOmJhc2V1cmwiPgo8L2hlYWQ+Cgo8Ym9keT4KICA8ZGl2IGkxOG4tdmFsdWVzPSJ0aXRsZTpuYW1lIiBpZD0ib3V0ZXIiPgogICAgPGltZyBpZD0icG9zdGVyIiBpMThuLXZhbHVlcz0ic3Jjc2V0OnBvc3RlciI+CiAgICA8ZGl2IGlkPSJzaGllbGRpbmciPjwvZGl2PgogICAgPGRpdiBpZD0iaW5uZXItY29udGFpbmVyIgogICAgICAgICBpMThuLXZhbHVlcz0iLnN0eWxlLndpZHRoOnZpc2libGVXaWR0aDsuc3R5bGUuaGVpZ2h0OnZpc2libGVIZWlnaHQiPgogICAgICA8aW1nIGlkPSJwbHVnaW4taWNvbiIgc3JjPSJkYXRhOmltYWdlL3BuZztiYXNlNjQsaVZCT1J3MEtHZ29BQUFBTlNVaEVVZ0FBQURJQUFBQXlDQVlBQUFBZVA0aXhBQUFBQVhOU1IwSUFyczRjNlFBQUE4ZEpSRUZVYUFYZFdzOXZFa0VVWmt2WlFsb054Sm9ZNDBreEpzRE5vOUdEaWYrQmY0Q0hwakVtSlBvUGVNY2UxRjQwOGRZalFlUEJneWN2M3ZSRzRHQk1QUkVQTFNscENVV2dnTiszbmNWbDZQSnJaNWE2azB4MloyZm52ZS9iZWZQbXpjd2FJYlZwR2VMQ3lFc2lHNUw0UHNvOWtidTRua2oxQ3lzU2FBUTV0cm01dVY2cFZCNGVIeCsvYnJWYW4zdTkzczkrdjE5RmJvbGM1VFBXOFIyK3l6WnNLMlRJcFBGWWY2TFM2UGIyOXJYOS9mME5nUHNJc0Eza1dWT0RiU21Ec2lnVDJUZENaamFidlZ5djE1OEQ5ZUdzeU1lOGYwaVpsQTB5SnJLMkZFNG1reGVyMWVvVG1NanZNWUE4VlZFMmRWQVhtSEM4S1UxbVBwOVBkanFkNzU1UXp0Q1l1cWdUTEpUMVRyUllMTjdUMlF0dS9LaVR1a0dHWThkVGl1M3Q3VDJDb3FhYk1oK2VONGtCTE9qZDVrcFJRY0lIckpOVkNESXo5NHpKTG9YNFJmYUV6SzRwekd6cU1SUG1JRnZFbUpDUnkyVmlFZzVnc2plajIvUFRPOGxnSjVXSlRiam1zZVBGcEErZkpHelI5Y1FJRnE0bVpuQldQWThtSlg4NFloUVJ3Sm5oVEZTRUhYSzdtY3JOWnZNZEdqQlExSnFJRmIweTRzVU1CbTNRN0RsMktwVktkNWp4MVhhMU1nRldFV2dPOVVxRUVhZ0t4U1NCTDdXU3krV3VJcko5cjBLbW13eGloaTR1SXdZcEprSnh0elpUUHhkRTdJWFZhcTFXZTRiR1dreU5tTUhBbXZHcE1JUUZ6cXBwbWc4R3ROVGNjQ1hZU0NRU2I4cmw4bjJRK2FWRzdEOHB4RXpzOXBObHJ0YW0vdVFUWG5UMGlDMmYxNGd1VXlOMnlPY1NPN1RDcGVjRWZGTlh1eENoSHZZK1RlMHBoQ2t6TldJbkI4dVd3K0h3TFdyU25HeFRlNnZTMUFUMkpZdElKQks1b1ptRVUveWZUQ2J6Yld0cjYyNjczZjdnckpqblhtQzN4dm9hdXBxN0hVclNHTk9TY2FveXRTb0VyMWxNY0hOQjF1SkRXWldwV2RodElqN2cxcXZDY2x0UVVVZStwRmZWaUhSK3hCaTgyRVk4SG4rQmU5ZG9kcVRsOEFOaXQxd2l4MFp0dUU1N2lmUEtGY3pNT3lEeEN0cm1KUkVTMlB2c2tSNFdLN3VZSlpQYTRaOHFpTUloM0U2bFVqdUdZVnozcXBQWXlZSGQyK3QydXorOENweWlQWFZ4UW55Y1RxZS9xQ0JCblFLN1JhUjdjSER3ZFFvZ1hsNXhtdEpMQ0pyYmxHUVFBanQzOXEyZ2NSMjJOczhtTk1mWFVEcGpIcUVwNlZxZk5NU08vb0NmempCZWFXemwvR29qWVR6b25Cd2RIWDBhMFBKK284MlVuTkFFNXFIRG9zQXNkVWswRUpzUEpCS1k3U0NTQ2NRR0hZbUVnckpsU2k3QjJNUW1FNlJBSEN1Y1VvRVhDOEpCajAwbUVFZHZOcGxBSEliYVpNeENvWERUendNZzZsSjlQRzJUQ2NRUEF6WVpYdi83WHppY1pBTHhVNDFNNkZ6ODVqUjAydU5FT09jOU56TjRkTXoxT2JNc1g5dVBaMzhCdndadzZ6OTJQSTRBQUFBQVNVVk9SSzVDWUlJPSIgLz4KICAgIDwvZGl2PgogIDwvZGl2PgogIDxzY3JpcHQ+CiAgICBkb2N1bWVudC5nZXRFbGVtZW50QnlJZCgncG9zdGVyJykub25lcnJvciA9IGZ1bmN0aW9uKCkgewogICAgICB0aGlzLmhpZGRlbiA9IHRydWU7CiAgICB9OwoKICAgIGRvY3VtZW50LmdldEVsZW1lbnRCeUlkKCdvdXRlcicpLm9uY2xpY2sgPSBmdW5jdGlvbigpIHsKICAgICAgcGx1Z2luLmxvYWQoKTsKICAgIH07CgogICAgd2luZG93LnJlc2l6ZVBvc3RlciA9IGZ1bmN0aW9uKG1hcmdpbkxlZnQsIG1hcmdpblRvcCwgd2lkdGgsIGhlaWdodCkgewogICAgICB2YXIgY29udGFpbmVyID0gZG9jdW1lbnQuZ2V0RWxlbWVudEJ5SWQoJ2lubmVyLWNvbnRhaW5lcicpOwogICAgICBjb250YWluZXIuc3R5bGUubWFyZ2luTGVmdCA9IG1hcmdpbkxlZnQ7CiAgICAgIGNvbnRhaW5lci5zdHlsZS5tYXJnaW5Ub3AgPSBtYXJnaW5Ub3A7CiAgICAgIGNvbnRhaW5lci5zdHlsZS53aWR0aCA9IHdpZHRoOwogICAgICBjb250YWluZXIuc3R5bGUuaGVpZ2h0ID0gaGVpZ2h0OwoKICAgICAgaWYgKHBsdWdpbi5kaWRGaW5pc2hJY29uUmVwb3NpdGlvbkZvclRlc3RpbmcpIHsKICAgICAgICAvLyBEZWZlciB1bnRpbCByZWZsb3cgY29tcGxldGUuCiAgICAgICAgd2luZG93LnNldFRpbWVvdXQoZnVuY3Rpb24oKSB7CiAgICAgICAgICBwbHVnaW4uZGlkRmluaXNoSWNvblJlcG9zaXRpb25Gb3JUZXN0aW5nKCk7CiAgICAgICAgfSk7CiAgICAgIH0KICAgIH07CiAgPC9zY3JpcHQ+CjwvYm9keT4KPC9odG1sPgovLyBDb3B5cmlnaHQgKGMpIDIwMTIgVGhlIENocm9taXVtIEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCi8vIFVzZSBvZiB0aGlzIHNvdXJjZSBjb2RlIGlzIGdvdmVybmVkIGJ5IGEgQlNELXN0eWxlIGxpY2Vuc2UgdGhhdCBjYW4gYmUKLy8gZm91bmQgaW4gdGhlIExJQ0VOU0UgZmlsZS4KCi8vIEN1c3RvbSBiaW5kaW5nIGZvciB0aGUgYXBwIEFQSS4KCnZhciBhcHBOYXRpdmVzID0gcmVxdWlyZU5hdGl2ZSgnYXBwJyk7CnZhciBwcm9jZXNzID0gcmVxdWlyZU5hdGl2ZSgncHJvY2VzcycpOwp2YXIgZXh0ZW5zaW9uSWQgPSBwcm9jZXNzLkdldEV4dGVuc2lvbklkKCk7CnZhciBsb2dBY3Rpdml0eSA9IHJlcXVpcmVOYXRpdmUoJ2FjdGl2aXR5TG9nZ2VyJyk7CgpmdW5jdGlvbiB3cmFwRm9yTG9nZ2luZyhmdW4pIHsKICBpZiAoIWV4dGVuc2lvbklkKQogICAgcmV0dXJuIGZ1bjsgIC8vIG5vdGhpbmcgaW50ZXJlc3RpbmcgdG8gbG9nIHdpdGhvdXQgYW4gZXh0ZW5zaW9uCgogIHJldHVybiBmdW5jdGlvbigpIHsKICAgIC8vIFRPRE8oYXRhbHkpOiBXZSBuZWVkIHRvIG1ha2Ugc3VyZSB3ZSB1c2UgdGhlIHJpZ2h0IHByb3RvdHlwZSBmb3IKICAgIC8vIGZ1bi5hcHBseS4gQXJyYXkgc2xpY2UgY2FuIGVpdGhlciBiZSByZXdyaXR0ZW4gb3Igc2ltaWxhcmx5IGRlZmluZWQuCiAgICBsb2dBY3Rpdml0eS5Mb2dBUElDYWxsKGV4dGVuc2lvbklkLCAiYXBwLiIgKyBmdW4ubmFtZSwKICAgICAgICAkQXJyYXkuc2xpY2UoYXJndW1lbnRzKSk7CiAgICByZXR1cm4gJEZ1bmN0aW9uLmFwcGx5KGZ1biwgdGhpcywgYXJndW1lbnRzKTsKICB9Owp9CgovLyBUaGlzIGJlY29tZXMgY2hyb21lLmFwcAp2YXIgYXBwID0gewogIGdldElzSW5zdGFsbGVkOiB3cmFwRm9yTG9nZ2luZyhhcHBOYXRpdmVzLkdldElzSW5zdGFsbGVkKSwKICBnZXREZXRhaWxzOiB3cmFwRm9yTG9nZ2luZyhhcHBOYXRpdmVzLkdldERldGFpbHMpLAogIHJ1bm5pbmdTdGF0ZTogd3JhcEZvckxvZ2dpbmcoYXBwTmF0aXZlcy5HZXRSdW5uaW5nU3RhdGUpCn07CgovLyBUcmlja3k7ICJnZXRJc0luc3RhbGxlZCIgaXMgYWN0dWFsbHkgZXhwb3NlZCBhcyB0aGUgZ2V0dGVyICJpc0luc3RhbGxlZCIsCi8vIGJ1dCB3ZSBkb24ndCBoYXZlIGEgd2F5IHRvIGV4cHJlc3MgdGhpcyBpbiB0aGUgc2NoZW1hIEpTT04gKG5vciBpcyBpdAovLyB3b3J0aCBpdCBmb3IgdGhpcyBvbmUgc3BlY2lhbCBjYXNlKS4KLy8KLy8gU28sIGRlZmluZSBpdCBtYW51YWxseSwgYW5kIGxldCB0aGUgZ2V0SXNJbnN0YWxsZWQgZnVuY3Rpb24gYWN0IGFzIGl0cwovLyBkb2N1bWVudGF0aW9uLgp2YXIgaXNJbnN0YWxsZWQgPSB3cmFwRm9yTG9nZ2luZyhhcHBOYXRpdmVzLkdldElzSW5zdGFsbGVkKTsKJE9iamVjdC5kZWZpbmVQcm9wZXJ0eSgKICAgIGFwcCwgJ2lzSW5zdGFsbGVkJywKICAgIHsKICAgICAgX19wcm90b19fOiBudWxsLAogICAgICBjb25maWd1cmFibGU6IHRydWUsCiAgICAgIGVudW1lcmFibGU6IHRydWUsCiAgICAgIGdldDogZnVuY3Rpb24oKSB7IHJldHVybiBpc0luc3RhbGxlZCgpOyB9LAogICAgfSk7CgovLyBDYWxsZWQgYnkgYXBwX2JpbmRpbmdzLmNjLgpmdW5jdGlvbiBvbkluc3RhbGxTdGF0ZVJlc3BvbnNlKHN0YXRlLCBjYWxsYmFja0lkKSB7CiAgdmFyIGNhbGxiYWNrID0gY2FsbGJhY2tzW2NhbGxiYWNrSWRdOwogIGRlbGV0ZSBjYWxsYmFja3NbY2FsbGJhY2tJZF07CiAgaWYgKHR5cGVvZiBjYWxsYmFjayA9PSAnZnVuY3Rpb24nKSB7CiAgICB0cnkgewogICAgICBjYWxsYmFjayhzdGF0ZSk7CiAgICB9IGNhdGNoIChlKSB7CiAgICAgIGNvbnNvbGUuZXJyb3IoJ0V4Y2VwdGlvbiBpbiBjaHJvbWUuYXBwLmluc3RhbGxTdGF0ZSByZXNwb25zZSBoYW5kbGVyOiAnICsKICAgICAgICAgICAgICAgICAgICBlLnN0YWNrKTsKICAgIH0KICB9Cn0KCi8vIFRPRE8oa2FsbWFuKTogbW92ZSB0aGlzIHN0dWZmIHRvIGl0cyBvd24gY3VzdG9tIGJpbmRpbmdzLgp2YXIgY2FsbGJhY2tzID0geyBfX3Byb3RvX186IG51bGwgfTsKdmFyIG5leHRDYWxsYmFja0lkID0gMTsKCmZ1bmN0aW9uIGdldEluc3RhbGxTdGF0ZShjYWxsYmFjaykgewogIHZhciBjYWxsYmFja0lkID0gbmV4dENhbGxiYWNrSWQrKzsKICBjYWxsYmFja3NbY2FsbGJhY2tJZF0gPSBjYWxsYmFjazsKICBhcHBOYXRpdmVzLkdldEluc3RhbGxTdGF0ZShjYWxsYmFja0lkKTsKfQoKJE9iamVjdC5kZWZpbmVQcm9wZXJ0eSgKICAgIGFwcCwgJ2luc3RhbGxTdGF0ZScsCiAgICB7CiAgICAgIF9fcHJvdG9fXzogbnVsbCwKICAgICAgY29uZmlndXJhYmxlOiB0cnVlLAogICAgICBlbnVtZXJhYmxlOiB0cnVlLAogICAgICB2YWx1ZTogd3JhcEZvckxvZ2dpbmcoZ2V0SW5zdGFsbFN0YXRlKSwKICAgICAgd3JpdGFibGU6IHRydWUsCiAgICB9KTsKCmV4cG9ydHMuJHNldCgnYmluZGluZycsIGFwcCk7CmV4cG9ydHMuJHNldCgnb25JbnN0YWxsU3RhdGVSZXNwb25zZScsIG9uSW5zdGFsbFN0YXRlUmVzcG9uc2UpOwovLyBDb3B5cmlnaHQgMjAxNCBUaGUgQ2hyb21pdW0gQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KLy8gVXNlIG9mIHRoaXMgc291cmNlIGNvZGUgaXMgZ292ZXJuZWQgYnkgYSBCU0Qtc3R5bGUgbGljZW5zZSB0aGF0IGNhbiBiZQovLyBmb3VuZCBpbiB0aGUgTElDRU5TRSBmaWxlLgoKLy8gQ3VzdG9tIGJpbmRpbmdzIGZvciB0aGUgYXV0b21hdGlvbiBBUEkuCnZhciBBdXRvbWF0aW9uTm9kZSA9IHJlcXVpcmUoJ2F1dG9tYXRpb25Ob2RlJykuQXV0b21hdGlvbk5vZGU7CnZhciBBdXRvbWF0aW9uUm9vdE5vZGUgPSByZXF1aXJlKCdhdXRvbWF0aW9uTm9kZScpLkF1dG9tYXRpb25Sb290Tm9kZTsKdmFyIGF1dG9tYXRpb24gPSBhcGlCcmlkZ2UgfHwgcmVxdWlyZSgnYmluZGluZycpLkJpbmRpbmcuY3JlYXRlKCdhdXRvbWF0aW9uJyk7CnZhciBhdXRvbWF0aW9uSW50ZXJuYWwgPQogICAgZ2V0SW50ZXJuYWxBcGkgPwogICAgICAgIGdldEludGVybmFsQXBpKCdhdXRvbWF0aW9uSW50ZXJuYWwnKSA6CiAgICAgICAgcmVxdWlyZSgnYmluZGluZycpLkJpbmRpbmcuY3JlYXRlKCdhdXRvbWF0aW9uSW50ZXJuYWwnKS5nZW5lcmF0ZSgpOwp2YXIgZXhjZXB0aW9uSGFuZGxlciA9IHJlcXVpcmUoJ3VuY2F1Z2h0X2V4Y2VwdGlvbl9oYW5kbGVyJyk7CnZhciBsb2dnaW5nID0gcmVxdWlyZU5hdGl2ZSgnbG9nZ2luZycpOwp2YXIgbmF0aXZlQXV0b21hdGlvbkludGVybmFsID0gcmVxdWlyZU5hdGl2ZSgnYXV0b21hdGlvbkludGVybmFsJyk7CnZhciBEZXN0cm95QWNjZXNzaWJpbGl0eVRyZWUgPQogICAgbmF0aXZlQXV0b21hdGlvbkludGVybmFsLkRlc3Ryb3lBY2Nlc3NpYmlsaXR5VHJlZTsKdmFyIEdldEludEF0dHJpYnV0ZSA9IG5hdGl2ZUF1dG9tYXRpb25JbnRlcm5hbC5HZXRJbnRBdHRyaWJ1dGU7CnZhciBTdGFydENhY2hpbmdBY2Nlc3NpYmlsaXR5VHJlZXMgPQogICAgbmF0aXZlQXV0b21hdGlvbkludGVybmFsLlN0YXJ0Q2FjaGluZ0FjY2Vzc2liaWxpdHlUcmVlczsKdmFyIEFkZFRyZWVDaGFuZ2VPYnNlcnZlciA9IG5hdGl2ZUF1dG9tYXRpb25JbnRlcm5hbC5BZGRUcmVlQ2hhbmdlT2JzZXJ2ZXI7CnZhciBSZW1vdmVUcmVlQ2hhbmdlT2JzZXJ2ZXIgPQogICAgbmF0aXZlQXV0b21hdGlvbkludGVybmFsLlJlbW92ZVRyZWVDaGFuZ2VPYnNlcnZlcjsKdmFyIEdldEZvY3VzTmF0aXZlID0gbmF0aXZlQXV0b21hdGlvbkludGVybmFsLkdldEZvY3VzOwoKdmFyIGpzTGFzdEVycm9yID0gYmluZGluZ1V0aWwgPyB1bmRlZmluZWQgOiByZXF1aXJlKCdsYXN0RXJyb3InKTsKZnVuY3Rpb24gaGFzTGFzdEVycm9yKCkgewogIHJldHVybiBiaW5kaW5nVXRpbCA/CiAgICAgIGJpbmRpbmdVdGlsLmhhc0xhc3RFcnJvcigpIDoganNMYXN0RXJyb3IuaGFzRXJyb3IoY2hyb21lKTsKfQoKLyoqCiAqIEEgbmFtZXNwYWNlIHRvIGV4cG9ydCB1dGlsaXR5IGZ1bmN0aW9ucyB0byBvdGhlciBmaWxlcyBpbiBhdXRvbWF0aW9uLgogKi8Kd2luZG93LmF1dG9tYXRpb25VdGlsID0gZnVuY3Rpb24oKSB7fTsKCi8vIFRPRE8oYWJveGhhbGwpOiBMb29rIGludG8gdXNpbmcgV2Vha01hcAp2YXIgaWRUb0NhbGxiYWNrID0ge307Cgp2YXIgREVTS1RPUF9UUkVFX0lEID0gMDsKCmF1dG9tYXRpb25VdGlsLnN0b3JlVHJlZUNhbGxiYWNrID0gZnVuY3Rpb24oaWQsIGNhbGxiYWNrKSB7CiAgaWYgKCFjYWxsYmFjaykKICAgIHJldHVybjsKCiAgdmFyIHRhcmdldFRyZWUgPSBBdXRvbWF0aW9uUm9vdE5vZGUuZ2V0KGlkKTsKICBpZiAoIXRhcmdldFRyZWUpIHsKICAgIC8vIElmIHdlIGhhdmVuJ3QgY2FjaGVkIHRoZSB0cmVlLCBob2xkIHRoZSBjYWxsYmFjayB1bnRpbCB0aGUgdHJlZSBpcwogICAgLy8gcG9wdWxhdGVkIGJ5IHRoZSBpbml0aWFsIG9uQWNjZXNzaWJpbGl0eUV2ZW50IGNhbGwuCiAgICBpZiAoaWQgaW4gaWRUb0NhbGxiYWNrKQogICAgICBpZFRvQ2FsbGJhY2tbaWRdLnB1c2goY2FsbGJhY2spOwogICAgZWxzZQogICAgICBpZFRvQ2FsbGJhY2tbaWRdID0gW2NhbGxiYWNrXTsKICB9IGVsc2UgewogICAgY2FsbGJhY2sodGFyZ2V0VHJlZSk7CiAgfQp9OwoKLyoqCiAqIEdsb2JhbCBsaXN0IG9mIHRyZWUgY2hhbmdlIG9ic2VydmVycy4KICogQHR5cGUge09iamVjdDxudW1iZXIsIFRyZWVDaGFuZ2VPYnNlcnZlcj59CiAqLwphdXRvbWF0aW9uVXRpbC50cmVlQ2hhbmdlT2JzZXJ2ZXJNYXAgPSB7fTsKCi8qKgogKiBUaGUgaWQgb2YgdGhlIG5leHQgdHJlZSBjaGFuZ2Ugb2JzZXJ2ZXIuCiAqIEB0eXBlIHtudW1iZXJ9CiAqLwphdXRvbWF0aW9uVXRpbC5uZXh0VHJlZUNoYW5nZU9ic2VydmVySWQgPSAxOwoKLyoqCiAqIEB0eXBlIHtBdXRvbWF0aW9uTm9kZX0gVGhlIGN1cnJlbnQgZm9jdXNlZCBub2RlLiBUaGlzIGlzIG9ubHkgdXBkYXRlZAogKiAgIHdoZW4gY2FsbGluZyBhdXRvbWF0aW9uVXRpbC51cGRhdGVGb2N1c2VkTm9kZS4KICovCmF1dG9tYXRpb25VdGlsLmZvY3VzZWROb2RlID0gbnVsbDsKCi8qKgogKiBHZXRzIHRoZSBjdXJyZW50bHkgZm9jdXNlZCBBdXRvbWF0aW9uTm9kZS4KICogQHJldHVybiB7QXV0b21hdGlvbk5vZGV9CiAqLwphdXRvbWF0aW9uVXRpbC5nZXRGb2N1cyA9IGZ1bmN0aW9uKCkgewogIHZhciBmb2N1c2VkTm9kZUluZm8gPSBHZXRGb2N1c05hdGl2ZShERVNLVE9QX1RSRUVfSUQpOwogIGlmICghZm9jdXNlZE5vZGVJbmZvKQogICAgcmV0dXJuIG51bGw7CiAgdmFyIHRyZWUgPSBBdXRvbWF0aW9uUm9vdE5vZGUuZ2V0T3JDcmVhdGUoZm9jdXNlZE5vZGVJbmZvLnRyZWVJZCk7CiAgaWYgKHRyZWUpCiAgICByZXR1cm4gcHJpdmF0ZXModHJlZSkuaW1wbC5nZXQoZm9jdXNlZE5vZGVJbmZvLm5vZGVJZCk7Cn07CgovKioKICogVXBkYXRlIGF1dG9tYXRpb25VdGlsLmZvY3VzZWROb2RlIHRvIGJlIHRoZSBub2RlIHRoYXQgY3VycmVudGx5IGhhcyBmb2N1cy4KICovCmF1dG9tYXRpb25VdGlsLnVwZGF0ZUZvY3VzZWROb2RlID0gZnVuY3Rpb24oKSB7CiAgYXV0b21hdGlvblV0aWwuZm9jdXNlZE5vZGUgPSBhdXRvbWF0aW9uVXRpbC5nZXRGb2N1cygpOwp9OwoKLyoqCiAqIFVwZGF0ZXMgdGhlIGZvY3VzIG9uIGJsdXIuCiAqLwphdXRvbWF0aW9uVXRpbC51cGRhdGVGb2N1c2VkTm9kZU9uQmx1ciA9IGZ1bmN0aW9uKCkgewogIHZhciBmb2N1cyA9IGF1dG9tYXRpb25VdGlsLmdldEZvY3VzKCk7CiAgYXV0b21hdGlvblV0aWwuZm9jdXNlZE5vZGUgPSBmb2N1cyA/IGZvY3VzLnJvb3QgOiBudWxsOwp9OwoKYXV0b21hdGlvbi5yZWdpc3RlckN1c3RvbUhvb2soZnVuY3Rpb24oYmluZGluZ3NBUEkpIHsKICB2YXIgYXBpRnVuY3Rpb25zID0gYmluZGluZ3NBUEkuYXBpRnVuY3Rpb25zOwoKICAvLyBUT0RPKGFib3hoYWxsLCBkdHNlbmcpOiBNYWtlIHRoaXMgcmV0dXJuIHRoZSBzcGVjZWQgQXV0b21hdGlvblJvb3ROb2RlIG9iai4KICBhcGlGdW5jdGlvbnMuc2V0SGFuZGxlUmVxdWVzdCgnZ2V0VHJlZScsIGZ1bmN0aW9uIGdldFRyZWUodGFiSUQsIGNhbGxiYWNrKSB7CiAgICBTdGFydENhY2hpbmdBY2Nlc3NpYmlsaXR5VHJlZXMoKTsKCiAgICAvLyBlbmFibGVUYWIoKSBlbnN1cmVzIHRoZSByZW5kZXJlciBmb3IgdGhlIGFjdGl2ZSBvciBzcGVjaWZpZWQgdGFiIGhhcwogICAgLy8gYWNjZXNzaWJpbGl0eSBlbmFibGVkLCBhbmQgZmV0Y2hlcyBpdHMgYXggdHJlZSBpZCB0byB1c2UgYXMKICAgIC8vIGEga2V5IGluIHRoZSBpZFRvQXV0b21hdGlvblJvb3ROb2RlIG1hcC4gVGhlIGNhbGxiYWNrIHRvCiAgICAvLyBlbmFibGVUYWIgaXMgYm91bmQgdG8gdGhlIGNhbGxiYWNrIHBhc3NlZCBpbiB0byBnZXRUcmVlKCksIHNvIHRoYXQgb25jZQogICAgLy8gdGhlIHRyZWUgaXMgYXZhaWxhYmxlIChlaXRoZXIgZHVlIHRvIGhhdmluZyBiZWVuIGNhY2hlZCBlYXJsaWVyLCBvciBhZnRlcgogICAgLy8gYW4gYWNjZXNzaWJpbGl0eSBldmVudCBvY2N1cnMgd2hpY2ggY2F1c2VzIHRoZSB0cmVlIHRvIGJlIHBvcHVsYXRlZCksIHRoZQogICAgLy8gY2FsbGJhY2sgY2FuIGJlIGNhbGxlZC4KICAgIHZhciBwYXJhbXMgPSB7IHRhYklEOiB0YWJJRCB9OwogICAgYXV0b21hdGlvbkludGVybmFsLmVuYWJsZVRhYihwYXJhbXMsCiAgICAgICAgZnVuY3Rpb24gb25FbmFibGUoaWQpIHsKICAgICAgICAgIGlmIChoYXNMYXN0RXJyb3IoKSkgewogICAgICAgICAgICBjYWxsYmFjaygpOwogICAgICAgICAgICByZXR1cm47CiAgICAgICAgICB9CiAgICAgICAgICBhdXRvbWF0aW9uVXRpbC5zdG9yZVRyZWVDYWxsYmFjayhpZCwgY2FsbGJhY2spOwogICAgICAgIH0pOwogIH0pOwoKICB2YXIgZGVza3RvcFRyZWUgPSBudWxsOwogIGFwaUZ1bmN0aW9ucy5zZXRIYW5kbGVSZXF1ZXN0KCdnZXREZXNrdG9wJywgZnVuY3Rpb24oY2FsbGJhY2spIHsKICAgIFN0YXJ0Q2FjaGluZ0FjY2Vzc2liaWxpdHlUcmVlcygpOwogICAgZGVza3RvcFRyZWUgPSBBdXRvbWF0aW9uUm9vdE5vZGUuZ2V0KERFU0tUT1BfVFJFRV9JRCk7CiAgICBpZiAoIWRlc2t0b3BUcmVlKSB7CiAgICAgIGlmIChERVNLVE9QX1RSRUVfSUQgaW4gaWRUb0NhbGxiYWNrKQogICAgICAgIGlkVG9DYWxsYmFja1tERVNLVE9QX1RSRUVfSURdLnB1c2goY2FsbGJhY2spOwogICAgICBlbHNlCiAgICAgICAgaWRUb0NhbGxiYWNrW0RFU0tUT1BfVFJFRV9JRF0gPSBbY2FsbGJhY2tdOwoKICAgICAgLy8gVE9ETyhkdHNlbmcpOiBEaXNhYmxlIGRlc2t0b3AgdHJlZSBvbmNlIGRlc2t0b3Agb2JqZWN0IGdvZXMgb3V0IG9mCiAgICAgIC8vIHNjb3BlLgogICAgICBhdXRvbWF0aW9uSW50ZXJuYWwuZW5hYmxlRGVza3RvcChmdW5jdGlvbigpIHsKICAgICAgICBpZiAoaGFzTGFzdEVycm9yKCkpIHsKICAgICAgICAgIEF1dG9tYXRpb25Sb290Tm9kZS5kZXN0cm95KERFU0tUT1BfVFJFRV9JRCk7CiAgICAgICAgICBjYWxsYmFjaygpOwogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgfSk7CiAgICB9IGVsc2UgewogICAgICBjYWxsYmFjayhkZXNrdG9wVHJlZSk7CiAgICB9CiAgfSk7CgogIGFwaUZ1bmN0aW9ucy5zZXRIYW5kbGVSZXF1ZXN0KCdnZXRGb2N1cycsIGZ1bmN0aW9uKGNhbGxiYWNrKSB7CiAgICBjYWxsYmFjayhhdXRvbWF0aW9uVXRpbC5nZXRGb2N1cygpKTsKICB9KTsKCiAgZnVuY3Rpb24gcmVtb3ZlVHJlZUNoYW5nZU9ic2VydmVyKG9ic2VydmVyKSB7CiAgICBmb3IgKHZhciBpZCBpbiBhdXRvbWF0aW9uVXRpbC50cmVlQ2hhbmdlT2JzZXJ2ZXJNYXApIHsKICAgICAgaWYgKGF1dG9tYXRpb25VdGlsLnRyZWVDaGFuZ2VPYnNlcnZlck1hcFtpZF0gPT0gb2JzZXJ2ZXIpIHsKICAgICAgICBSZW1vdmVUcmVlQ2hhbmdlT2JzZXJ2ZXIoaWQpOwogICAgICAgIGRlbGV0ZSBhdXRvbWF0aW9uVXRpbC50cmVlQ2hhbmdlT2JzZXJ2ZXJNYXBbaWRdOwogICAgICAgIHJldHVybjsKICAgICAgfQogICAgfQogIH0KICBhcGlGdW5jdGlvbnMuc2V0SGFuZGxlUmVxdWVzdCgncmVtb3ZlVHJlZUNoYW5nZU9ic2VydmVyJywgZnVuY3Rpb24ob2JzZXJ2ZXIpIHsKICAgIHJlbW92ZVRyZWVDaGFuZ2VPYnNlcnZlcihvYnNlcnZlcik7CiAgfSk7CgogIGZ1bmN0aW9uIGFkZFRyZWVDaGFuZ2VPYnNlcnZlcihmaWx0ZXIsIG9ic2VydmVyKSB7CiAgICByZW1vdmVUcmVlQ2hhbmdlT2JzZXJ2ZXIob2JzZXJ2ZXIpOwogICAgdmFyIGlkID0gYXV0b21hdGlvblV0aWwubmV4dFRyZWVDaGFuZ2VPYnNlcnZlcklkKys7CiAgICBBZGRUcmVlQ2hhbmdlT2JzZXJ2ZXIoaWQsIGZpbHRlcik7CiAgICBhdXRvbWF0aW9uVXRpbC50cmVlQ2hhbmdlT2JzZXJ2ZXJNYXBbaWRdID0gb2JzZXJ2ZXI7CiAgfQogIGFwaUZ1bmN0aW9ucy5zZXRIYW5kbGVSZXF1ZXN0KCdhZGRUcmVlQ2hhbmdlT2JzZXJ2ZXInLAogICAgICBmdW5jdGlvbihmaWx0ZXIsIG9ic2VydmVyKSB7CiAgICBhZGRUcmVlQ2hhbmdlT2JzZXJ2ZXIoZmlsdGVyLCBvYnNlcnZlcik7CiAgfSk7CgogIGFwaUZ1bmN0aW9ucy5zZXRIYW5kbGVSZXF1ZXN0KCdzZXREb2N1bWVudFNlbGVjdGlvbicsIGZ1bmN0aW9uKHBhcmFtcykgewogICAgdmFyIGFuY2hvck5vZGVJbXBsID0gcHJpdmF0ZXMocGFyYW1zLmFuY2hvck9iamVjdCkuaW1wbDsKICAgIHZhciBmb2N1c05vZGVJbXBsID0gcHJpdmF0ZXMocGFyYW1zLmZvY3VzT2JqZWN0KS5pbXBsOwogICAgaWYgKGFuY2hvck5vZGVJbXBsLnRyZWVJRCAhPT0gZm9jdXNOb2RlSW1wbC50cmVlSUQpCiAgICAgIHRocm93IG5ldyBFcnJvcignU2VsZWN0aW9uIGFuY2hvciBhbmQgZm9jdXMgbXVzdCBiZSBpbiB0aGUgc2FtZSB0cmVlLicpOwogICAgaWYgKGFuY2hvck5vZGVJbXBsLnRyZWVJRCA9PT0gREVTS1RPUF9UUkVFX0lEKSB7CiAgICAgIHRocm93IG5ldyBFcnJvcignVXNlIEF1dG9tYXRpb25Ob2RlLnNldFNlbGVjdGlvbiB0byBzZXQgdGhlIHNlbGVjdGlvbiAnICsKICAgICAgICAgICdpbiB0aGUgZGVza3RvcCB0cmVlLicpOwogICAgfQogICAgYXV0b21hdGlvbkludGVybmFsLnBlcmZvcm1BY3Rpb24oeyB0cmVlSUQ6IGFuY2hvck5vZGVJbXBsLnRyZWVJRCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgYXV0b21hdGlvbk5vZGVJRDogYW5jaG9yTm9kZUltcGwuaWQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGFjdGlvblR5cGU6ICdzZXRTZWxlY3Rpb24nfSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHsgZm9jdXNOb2RlSUQ6IGZvY3VzTm9kZUltcGwuaWQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGFuY2hvck9mZnNldDogcGFyYW1zLmFuY2hvck9mZnNldCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZm9jdXNPZmZzZXQ6IHBhcmFtcy5mb2N1c09mZnNldCB9KTsKICB9KTsKCn0pOwoKYXV0b21hdGlvbkludGVybmFsLm9uQ2hpbGRUcmVlSUQuYWRkTGlzdGVuZXIoZnVuY3Rpb24odHJlZUlELAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBub2RlSUQpIHsKICB2YXIgdHJlZSA9IEF1dG9tYXRpb25Sb290Tm9kZS5nZXRPckNyZWF0ZSh0cmVlSUQpOwogIGlmICghdHJlZSkKICAgIHJldHVybjsKCiAgdmFyIG5vZGUgPSBwcml2YXRlcyh0cmVlKS5pbXBsLmdldChub2RlSUQpOwogIGlmICghbm9kZSkKICAgIHJldHVybjsKCiAgLy8gQSBXZWJWaWV3IGluIHRoZSBkZXNrdG9wIHRyZWUgaGFzIGEgZGlmZmVyZW50IEFYIHRyZWUgYXMgaXRzIGNoaWxkLgogIC8vIFdoZW4gd2UgZW5jb3VudGVyIGEgV2ViVmlldyB3aXRoIGEgY2hpbGQgQVggdHJlZSBpZCB0aGF0IHdlIGRvbid0CiAgLy8gY3VycmVudGx5IGhhdmUgY2FjaGVkLCBleHBsaWNpdGx5IHJlcXVlc3QgdGhhdCBBWCB0cmVlIGZyb20gdGhlCiAgLy8gYnJvd3NlciBwcm9jZXNzIGFuZCBzZXQgdXAgYSBjYWxsYmFjayB3aGVuIGl0IGxvYWRzIHRvIGF0dGFjaCB0aGF0CiAgLy8gdHJlZSBhcyBhIGNoaWxkIG9mIHRoaXMgbm9kZSBhbmQgZmlyZSBhcHByb3ByaWF0ZSBldmVudHMuCiAgdmFyIGNoaWxkVHJlZUlEID0gR2V0SW50QXR0cmlidXRlKHRyZWVJRCwgbm9kZUlELCAnY2hpbGRUcmVlSWQnKTsKICBpZiAoIWNoaWxkVHJlZUlEKQogICAgcmV0dXJuOwoKICB2YXIgc3Vicm9vdCA9IEF1dG9tYXRpb25Sb290Tm9kZS5nZXQoY2hpbGRUcmVlSUQpOwogIGlmICghc3Vicm9vdCB8fCBzdWJyb290LnJvbGUgPT0gJ3Vua25vd24nKSB7CiAgICBhdXRvbWF0aW9uVXRpbC5zdG9yZVRyZWVDYWxsYmFjayhjaGlsZFRyZWVJRCwgZnVuY3Rpb24ocm9vdCkgewogICAgICAvLyBSZXR1cm4gZWFybHkgaWYgdGhlIHJvb3QgaGFzIGFscmVhZHkgYmVlbiBhdHRhY2hlZC4KICAgICAgaWYgKHJvb3QucGFyZW50KQogICAgICAgIHJldHVybjsKCiAgICAgIHByaXZhdGVzKHJvb3QpLmltcGwuc2V0SG9zdE5vZGUobm9kZSk7CgogICAgICBpZiAocm9vdC5kb2NMb2FkZWQpIHsKICAgICAgICBwcml2YXRlcyhyb290KS5pbXBsLmRpc3BhdGNoRXZlbnQoJ2xvYWRDb21wbGV0ZScsICdwYWdlJyk7CiAgICAgIH0KCiAgICAgIHByaXZhdGVzKG5vZGUpLmltcGwuZGlzcGF0Y2hFdmVudCgnY2hpbGRyZW5DaGFuZ2VkJywgJ25vbmUnKTsKICAgIH0pOwoKICAgIGF1dG9tYXRpb25JbnRlcm5hbC5lbmFibGVGcmFtZShjaGlsZFRyZWVJRCk7CiAgfSBlbHNlIHsKICAgIHByaXZhdGVzKHN1YnJvb3QpLmltcGwuc2V0SG9zdE5vZGUobm9kZSk7CiAgfQp9KTsKCmF1dG9tYXRpb25JbnRlcm5hbC5vblRyZWVDaGFuZ2UuYWRkTGlzdGVuZXIoZnVuY3Rpb24ob2JzZXJ2ZXJJRCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB0cmVlSUQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgbm9kZUlELAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNoYW5nZVR5cGUpIHsKICB2YXIgdHJlZSA9IEF1dG9tYXRpb25Sb290Tm9kZS5nZXRPckNyZWF0ZSh0cmVlSUQpOwogIGlmICghdHJlZSkKICAgIHJldHVybjsKCiAgdmFyIG5vZGUgPSBwcml2YXRlcyh0cmVlKS5pbXBsLmdldChub2RlSUQpOwogIGlmICghbm9kZSkKICAgIHJldHVybjsKCiAgdmFyIG9ic2VydmVyID0gYXV0b21hdGlvblV0aWwudHJlZUNoYW5nZU9ic2VydmVyTWFwW29ic2VydmVySURdOwogIGlmICghb2JzZXJ2ZXIpCiAgICByZXR1cm47CgogIHRyeSB7CiAgICBvYnNlcnZlcih7dGFyZ2V0OiBub2RlLCB0eXBlOiBjaGFuZ2VUeXBlfSk7CiAgfSBjYXRjaCAoZSkgewogICAgZXhjZXB0aW9uSGFuZGxlci5oYW5kbGUoJ0Vycm9yIGluIHRyZWUgY2hhbmdlIG9ic2VydmVyIGZvciAnICsKICAgICAgICB0cmVlQ2hhbmdlLnR5cGUsIGUpOwogIH0KfSk7CgphdXRvbWF0aW9uSW50ZXJuYWwub25Ob2Rlc1JlbW92ZWQuYWRkTGlzdGVuZXIoZnVuY3Rpb24odHJlZUlELCBub2RlSURzKSB7CiAgdmFyIHRyZWUgPSBBdXRvbWF0aW9uUm9vdE5vZGUuZ2V0T3JDcmVhdGUodHJlZUlEKTsKICBpZiAoIXRyZWUpCiAgICByZXR1cm47CgogIGZvciAodmFyIGkgPSAwOyBpIDwgbm9kZUlEcy5sZW5ndGg7IGkrKykgewogICAgcHJpdmF0ZXModHJlZSkuaW1wbC5yZW1vdmUobm9kZUlEc1tpXSk7CiAgfQp9KTsKCi8qKgogKiBEaXNwYXRjaCBhY2Nlc3NpYmlsaXR5IGV2ZW50cyBmaXJlZCBvbiBpbmRpdmlkdWFsIG5vZGVzIHRvIGl0cwogKiBjb3JyZXNwb25kaW5nIEF1dG9tYXRpb25Ob2RlLiBIYW5kbGUgZm9jdXMgZXZlbnRzIHNwZWNpYWxseQogKiAoc2VlIGJlbG93KS4KICovCmF1dG9tYXRpb25JbnRlcm5hbC5vbkFjY2Vzc2liaWxpdHlFdmVudC5hZGRMaXN0ZW5lcihmdW5jdGlvbihldmVudFBhcmFtcykgewogIHZhciBpZCA9IGV2ZW50UGFyYW1zLnRyZWVJRDsKICB2YXIgdGFyZ2V0VHJlZSA9IEF1dG9tYXRpb25Sb290Tm9kZS5nZXRPckNyZWF0ZShpZCk7CiAgaWYgKGV2ZW50UGFyYW1zLmV2ZW50VHlwZSA9PSAnYmx1cicpIHsKICAgIC8vIFdvcmsgYXJvdW5kIGFuIGlzc3VlIHdoZXJlIENocm9tZSBzZW5kcyB1cyAnYmx1cicgZXZlbnRzIG9uIHRoZQogICAgLy8gcm9vdCBub2RlIHdoZW4gbm90aGluZyBoYXMgZm9jdXMsIHdlIG5lZWQgdG8gdHJlYXQgdGhvc2UgYXMgZm9jdXMKICAgIC8vIGV2ZW50cyBidXQgb3RoZXJ3aXNlIG5vdCBoYW5kbGUgYmx1ciBldmVudHMgc3BlY2lhbGx5LgogICAgdmFyIG5vZGUgPSBwcml2YXRlcyh0YXJnZXRUcmVlKS5pbXBsLmdldChldmVudFBhcmFtcy50YXJnZXRJRCk7CiAgICBpZiAobm9kZSA9PSBub2RlLnJvb3QpCiAgICAgIGF1dG9tYXRpb25VdGlsLnVwZGF0ZUZvY3VzZWROb2RlT25CbHVyKCk7CiAgfSBlbHNlIGlmIChldmVudFBhcmFtcy5ldmVudFR5cGUgPT0gJ21lZGlhU3RhcnRlZFBsYXlpbmcnIHx8CiAgICAgIGV2ZW50UGFyYW1zLmV2ZW50VHlwZSA9PSAnbWVkaWFTdG9wcGVkUGxheWluZycpIHsKICAgIC8vIFRoZXNlIGV2ZW50cyBhcmUgZ2xvYmFsIHRvIHRoZSB0cmVlLgogICAgZXZlbnRQYXJhbXMudGFyZ2V0SUQgPSBwcml2YXRlcyh0YXJnZXRUcmVlKS5pbXBsLmlkOwogIH0gZWxzZSB7CiAgICB2YXIgcHJldmlvdXNGb2N1c2VkTm9kZSA9IGF1dG9tYXRpb25VdGlsLmZvY3VzZWROb2RlOwogICAgYXV0b21hdGlvblV0aWwudXBkYXRlRm9jdXNlZE5vZGUoKTsKCiAgICAvLyBGaXJlIGZvY3VzIGV2ZW50cyBpZiBuZWNlc3NhcnkuCiAgICBpZiAoYXV0b21hdGlvblV0aWwuZm9jdXNlZE5vZGUgJiYKICAgICAgICBhdXRvbWF0aW9uVXRpbC5mb2N1c2VkTm9kZSAhPSBwcmV2aW91c0ZvY3VzZWROb2RlKSB7CiAgICAgIHZhciBldmVudFBhcmFtc0NvcHkgPSB7fTsKICAgICAgZm9yICh2YXIga2V5IGluIGV2ZW50UGFyYW1zKQogICAgICAgIGV2ZW50UGFyYW1zQ29weVtrZXldID0gZXZlbnRQYXJhbXNba2V5XTsKICAgICAgZXZlbnRQYXJhbXNDb3B5WydldmVudFR5cGUnXSA9ICdmb2N1cyc7CiAgICAgIGV2ZW50UGFyYW1zQ29weVsndHJlZUlEJ10gPQogICAgICAgICAgcHJpdmF0ZXMoYXV0b21hdGlvblV0aWwuZm9jdXNlZE5vZGUucm9vdCkuaW1wbC50cmVlSUQ7CiAgICAgIGV2ZW50UGFyYW1zQ29weVsndGFyZ2V0SUQnXSA9CiAgICAgICAgICBwcml2YXRlcyhhdXRvbWF0aW9uVXRpbC5mb2N1c2VkTm9kZSkuaW1wbC5pZDsKICAgICAgcHJpdmF0ZXMoYXV0b21hdGlvblV0aWwuZm9jdXNlZE5vZGUucm9vdCkKICAgICAgICAgIC5pbXBsLm9uQWNjZXNzaWJpbGl0eUV2ZW50KGV2ZW50UGFyYW1zQ29weSk7CiAgICB9CiAgfQoKICAvLyBOb3RlIHRoYXQgZm9jdXMgdHlwZSBldmVudHMgaGF2ZSBhbHJlYWR5IGJlZW4gaGFuZGxlZCBhYm92ZSBpZiB0aGVyZSB3YXMgYQogIC8vIGZvY3VzZWQgbm9kZS4gQWxsIG90aGVyIGV2ZW50cywgZXZlbiBub24tZm9jdXMgZXZlbnRzIHRoYXQgdHJpZ2dlcmVkIGEKICAvLyBmb2N1cyBkaXNwYXRjaCwgc3RpbGwgbmVlZCB0byBoYXZlIHRoZWlyIG9yaWdpbmFsIGV2ZW50IGZpcmVkLgogIGlmICgoIWF1dG9tYXRpb25VdGlsLmZvY3VzZWROb2RlIHx8IGV2ZW50UGFyYW1zLmV2ZW50VHlwZSAhPSAnZm9jdXMnKSAmJgogICAgICAhcHJpdmF0ZXModGFyZ2V0VHJlZSkuaW1wbC5vbkFjY2Vzc2liaWxpdHlFdmVudChldmVudFBhcmFtcykpCiAgICByZXR1cm47CgogIC8vIElmIHdlJ3JlIG5vdCB3YWl0aW5nIG9uIGEgY2FsbGJhY2sgdG8gZ2V0VHJlZSgpLCB3ZSBjYW4gZWFybHkgb3V0IGhlcmUuCiAgaWYgKCEoaWQgaW4gaWRUb0NhbGxiYWNrKSkKICAgIHJldHVybjsKCiAgLy8gV2UgdXN1YWxseSBnZXQgYSAncGxhY2Vob2xkZXInIHRyZWUgZmlyc3QsIHdoaWNoIGRvZXNuJ3QgaGF2ZSBhbnkgdXJsCiAgLy8gYXR0cmlidXRlIG9yIGNoaWxkIG5vZGVzLiBJZiB3ZSd2ZSBnb3QgdGhhdCwgd2FpdCBmb3IgdGhlIGZ1bGwgdHJlZSBiZWZvcmUKICAvLyBjYWxsaW5nIHRoZSBjYWxsYmFjay4KICAvLyBUT0RPKGRtYXp6b25pKTogRG9uJ3Qgc2VuZCBkb3duIHBsYWNlaG9sZGVyIChjcmJ1Zy5jb20vMzk3NTUzKQogIGlmIChpZCAhPSBERVNLVE9QX1RSRUVfSUQgJiYgIXRhcmdldFRyZWUudXJsICYmCiAgICAgIHRhcmdldFRyZWUuY2hpbGRyZW4ubGVuZ3RoID09IDApCiAgICByZXR1cm47CgogIC8vIElmIHRoZSB0cmVlIHdhc24ndCBhdmFpbGFibGUgd2hlbiBnZXRUcmVlKCkgd2FzIGNhbGxlZCwgdGhlIGNhbGxiYWNrIHdpbGwKICAvLyBoYXZlIGJlZW4gY2FjaGVkIGluIGlkVG9DYWxsYmFjaywgc28gY2FsbCBhbmQgZGVsZXRlIGl0IG5vdyB0aGF0IHdlCiAgLy8gaGF2ZSB0aGUgY29tcGxldGUgdHJlZS4KICBmb3IgKHZhciBpID0gMDsgaSA8IGlkVG9DYWxsYmFja1tpZF0ubGVuZ3RoOyBpKyspIHsKICAgIHZhciBjYWxsYmFjayA9IGlkVG9DYWxsYmFja1tpZF1baV07CiAgICBjYWxsYmFjayh0YXJnZXRUcmVlKTsKICB9CiAgZGVsZXRlIGlkVG9DYWxsYmFja1tpZF07Cn0pOwoKYXV0b21hdGlvbkludGVybmFsLm9uQWNjZXNzaWJpbGl0eVRyZWVEZXN0cm95ZWQuYWRkTGlzdGVuZXIoZnVuY3Rpb24oaWQpIHsKICAvLyBEZXN0cm95IHRoZSBBdXRvbWF0aW9uUm9vdE5vZGUuCiAgdmFyIHRhcmdldFRyZWUgPSBBdXRvbWF0aW9uUm9vdE5vZGUuZ2V0KGlkKTsKICBpZiAodGFyZ2V0VHJlZSkgewogICAgcHJpdmF0ZXModGFyZ2V0VHJlZSkuaW1wbC5kZXN0cm95KCk7CiAgICBBdXRvbWF0aW9uUm9vdE5vZGUuZGVzdHJveShpZCk7CiAgfSBlbHNlIHsKICAgIGxvZ2dpbmcuV0FSTklORygnbm8gdGFyZ2V0VHJlZSB0byBkZXN0cm95Jyk7CiAgfQoKICAvLyBEZXN0cm95IHRoZSBuYXRpdmUgY2FjaGUgb2YgdGhlIGFjY2Vzc2liaWxpdHkgdHJlZS4KICBEZXN0cm95QWNjZXNzaWJpbGl0eVRyZWUoaWQpOwp9KTsKCmF1dG9tYXRpb25JbnRlcm5hbC5vbkFjY2Vzc2liaWxpdHlUcmVlU2VyaWFsaXphdGlvbkVycm9yLmFkZExpc3RlbmVyKAogICAgZnVuY3Rpb24oaWQpIHsKICBhdXRvbWF0aW9uSW50ZXJuYWwuZW5hYmxlRnJhbWUoaWQpOwp9KTsKCmF1dG9tYXRpb25JbnRlcm5hbC5vbkFjdGlvblJlc3VsdC5hZGRMaXN0ZW5lcigKICAgIGZ1bmN0aW9uKHRyZWVJRCwgcmVxdWVzdElELCByZXN1bHQpIHsKICB2YXIgdGFyZ2V0VHJlZSA9IEF1dG9tYXRpb25Sb290Tm9kZS5nZXQodHJlZUlEKTsKICBpZiAoIXRhcmdldFRyZWUpCiAgICByZXR1cm47CgogIHByaXZhdGVzKHRhcmdldFRyZWUpLmltcGwub25BY3Rpb25SZXN1bHQocmVxdWVzdElELCByZXN1bHQpOwogICAgfSk7CgppZiAoIWFwaUJyaWRnZSkKICBleHBvcnRzLiRzZXQoJ2JpbmRpbmcnLCBhdXRvbWF0aW9uLmdlbmVyYXRlKCkpOwovLyBDb3B5cmlnaHQgMjAxNCBUaGUgQ2hyb21pdW0gQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KLy8gVXNlIG9mIHRoaXMgc291cmNlIGNvZGUgaXMgZ292ZXJuZWQgYnkgYSBCU0Qtc3R5bGUgbGljZW5zZSB0aGF0IGNhbiBiZQovLyBmb3VuZCBpbiB0aGUgTElDRU5TRSBmaWxlLgoKdmFyIHV0aWxzID0gcmVxdWlyZSgndXRpbHMnKTsKCmZ1bmN0aW9uIEF1dG9tYXRpb25FdmVudEltcGwodHlwZSwgdGFyZ2V0LCBldmVudEZyb20pIHsKICB0aGlzLnByb3BhZ2F0aW9uU3RvcHBlZCA9IGZhbHNlOwogIHRoaXMudHlwZSA9IHR5cGU7CiAgdGhpcy50YXJnZXQgPSB0YXJnZXQ7CiAgdGhpcy5ldmVudFBoYXNlID0gRXZlbnQuTk9ORTsKICB0aGlzLmV2ZW50RnJvbSA9IGV2ZW50RnJvbTsKfQoKQXV0b21hdGlvbkV2ZW50SW1wbC5wcm90b3R5cGUgPSB7CiAgX19wcm90b19fOiBudWxsLAogIHN0b3BQcm9wYWdhdGlvbjogZnVuY3Rpb24oKSB7CiAgICB0aGlzLnByb3BhZ2F0aW9uU3RvcHBlZCA9IHRydWU7CiAgfSwKfTsKCmZ1bmN0aW9uIEF1dG9tYXRpb25FdmVudCgpIHsKICBwcml2YXRlcyhBdXRvbWF0aW9uRXZlbnQpLmNvbnN0cnVjdFByaXZhdGUodGhpcywgYXJndW1lbnRzKTsKfQp1dGlscy5leHBvc2UoQXV0b21hdGlvbkV2ZW50LCBBdXRvbWF0aW9uRXZlbnRJbXBsLCB7CiAgZnVuY3Rpb25zOiBbCiAgICAnc3RvcFByb3BhZ2F0aW9uJywKICBdLAogIHJlYWRvbmx5OiBbCiAgICAndHlwZScsCiAgICAndGFyZ2V0JywKICAgICdldmVudFBoYXNlJywKICAgICdldmVudEZyb20nLAogIF0sCn0pOwoKZXhwb3J0cy4kc2V0KCdBdXRvbWF0aW9uRXZlbnQnLCBBdXRvbWF0aW9uRXZlbnQpOwovLyBDb3B5cmlnaHQgMjAxNCBUaGUgQ2hyb21pdW0gQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KLy8gVXNlIG9mIHRoaXMgc291cmNlIGNvZGUgaXMgZ292ZXJuZWQgYnkgYSBCU0Qtc3R5bGUgbGljZW5zZSB0aGF0IGNhbiBiZQovLyBmb3VuZCBpbiB0aGUgTElDRU5TRSBmaWxlLgoKdmFyIEF1dG9tYXRpb25FdmVudCA9IHJlcXVpcmUoJ2F1dG9tYXRpb25FdmVudCcpLkF1dG9tYXRpb25FdmVudDsKdmFyIGF1dG9tYXRpb25JbnRlcm5hbCA9CiAgICBnZXRJbnRlcm5hbEFwaSA/CiAgICAgICAgZ2V0SW50ZXJuYWxBcGkoJ2F1dG9tYXRpb25JbnRlcm5hbCcpIDoKICAgICAgICByZXF1aXJlKCdiaW5kaW5nJykuQmluZGluZy5jcmVhdGUoJ2F1dG9tYXRpb25JbnRlcm5hbCcpLmdlbmVyYXRlKCk7CnZhciBleGNlcHRpb25IYW5kbGVyID0gcmVxdWlyZSgndW5jYXVnaHRfZXhjZXB0aW9uX2hhbmRsZXInKTsKCnZhciBuYXRpdmVzID0gcmVxdWlyZU5hdGl2ZSgnYXV0b21hdGlvbkludGVybmFsJyk7Cgp2YXIgSXNJbnRlcmFjdFBlcm1pdHRlZCA9IG5hdGl2ZXMuSXNJbnRlcmFjdFBlcm1pdHRlZDsKCi8qKgogKiBAcGFyYW0ge251bWJlcn0gYXhUcmVlSUQgVGhlIGlkIG9mIHRoZSBhY2Nlc3NpYmlsaXR5IHRyZWUuCiAqIEByZXR1cm4gez9udW1iZXJ9IFRoZSBpZCBvZiB0aGUgcm9vdCBub2RlLgogKi8KdmFyIEdldFJvb3RJRCA9IG5hdGl2ZXMuR2V0Um9vdElEOwoKLyoqCiAqIEBwYXJhbSB7bnVtYmVyfSBheFRyZWVJRCBUaGUgaWQgb2YgdGhlIGFjY2Vzc2liaWxpdHkgdHJlZS4KICogQHJldHVybiB7P3N0cmluZ30gVGhlIHRpdGxlIG9mIHRoZSBkb2N1bWVudC4KICovCnZhciBHZXREb2NUaXRsZSA9IG5hdGl2ZXMuR2V0RG9jVGl0bGU7CgovKioKICogQHBhcmFtIHtudW1iZXJ9IGF4VHJlZUlEIFRoZSBpZCBvZiB0aGUgYWNjZXNzaWJpbGl0eSB0cmVlLgogKiBAcmV0dXJuIHs/c3RyaW5nfSBUaGUgdXJsIG9mIHRoZSBkb2N1bWVudC4KICovCnZhciBHZXREb2NVUkwgPSBuYXRpdmVzLkdldERvY1VSTDsKCi8qKgogKiBAcGFyYW0ge251bWJlcn0gYXhUcmVlSUQgVGhlIGlkIG9mIHRoZSBhY2Nlc3NpYmlsaXR5IHRyZWUuCiAqIEByZXR1cm4gez9ib29sZWFufSBUcnVlIGlmIHRoZSBkb2N1bWVudCBoYXMgZmluaXNoZWQgbG9hZGluZy4KICovCnZhciBHZXREb2NMb2FkZWQgPSBuYXRpdmVzLkdldERvY0xvYWRlZDsKCi8qKgogKiBAcGFyYW0ge251bWJlcn0gYXhUcmVlSUQgVGhlIGlkIG9mIHRoZSBhY2Nlc3NpYmlsaXR5IHRyZWUuCiAqIEByZXR1cm4gez9udW1iZXJ9IFRoZSBsb2FkaW5nIHByb2dyZXNzLCBmcm9tIDAuMCB0byAxLjAgKGZ1bGx5IGxvYWRlZCkuCiAqLwp2YXIgR2V0RG9jTG9hZGluZ1Byb2dyZXNzID0KICAgIG5hdGl2ZXMuR2V0RG9jTG9hZGluZ1Byb2dyZXNzOwoKLyoqCiAqIEBwYXJhbSB7bnVtYmVyfSBheFRyZWVJRCBUaGUgaWQgb2YgdGhlIGFjY2Vzc2liaWxpdHkgdHJlZS4KICogQHJldHVybiB7P251bWJlcn0gVGhlIElEIG9mIHRoZSBzZWxlY3Rpb24gYW5jaG9yIG9iamVjdC4KICovCnZhciBHZXRBbmNob3JPYmplY3RJRCA9IG5hdGl2ZXMuR2V0QW5jaG9yT2JqZWN0SUQ7CgovKioKICogQHBhcmFtIHtudW1iZXJ9IGF4VHJlZUlEIFRoZSBpZCBvZiB0aGUgYWNjZXNzaWJpbGl0eSB0cmVlLgogKiBAcmV0dXJuIHs/bnVtYmVyfSBUaGUgc2VsZWN0aW9uIGFuY2hvciBvZmZzZXQuCiAqLwp2YXIgR2V0QW5jaG9yT2Zmc2V0ID0gbmF0aXZlcy5HZXRBbmNob3JPZmZzZXQ7CgovKioKICogQHBhcmFtIHtudW1iZXJ9IGF4VHJlZUlEIFRoZSBpZCBvZiB0aGUgYWNjZXNzaWJpbGl0eSB0cmVlLgogKiBAcmV0dXJuIHs/c3RyaW5nfSBUaGUgc2VsZWN0aW9uIGFuY2hvciBhZmZpbml0eS4KICovCnZhciBHZXRBbmNob3JBZmZpbml0eSA9IG5hdGl2ZXMuR2V0QW5jaG9yQWZmaW5pdHk7CgovKioKICogQHBhcmFtIHtudW1iZXJ9IGF4VHJlZUlEIFRoZSBpZCBvZiB0aGUgYWNjZXNzaWJpbGl0eSB0cmVlLgogKiBAcmV0dXJuIHs/bnVtYmVyfSBUaGUgSUQgb2YgdGhlIHNlbGVjdGlvbiBmb2N1cyBvYmplY3QuCiAqLwp2YXIgR2V0Rm9jdXNPYmplY3RJRCA9IG5hdGl2ZXMuR2V0Rm9jdXNPYmplY3RJRDsKCi8qKgogKiBAcGFyYW0ge251bWJlcn0gYXhUcmVlSUQgVGhlIGlkIG9mIHRoZSBhY2Nlc3NpYmlsaXR5IHRyZWUuCiAqIEByZXR1cm4gez9udW1iZXJ9IFRoZSBzZWxlY3Rpb24gZm9jdXMgb2Zmc2V0LgogKi8KdmFyIEdldEZvY3VzT2Zmc2V0ID0gbmF0aXZlcy5HZXRGb2N1c09mZnNldDsKCi8qKgogKiBAcGFyYW0ge251bWJlcn0gYXhUcmVlSUQgVGhlIGlkIG9mIHRoZSBhY2Nlc3NpYmlsaXR5IHRyZWUuCiAqIEByZXR1cm4gez9zdHJpbmd9IFRoZSBzZWxlY3Rpb24gZm9jdXMgYWZmaW5pdHkuCiAqLwp2YXIgR2V0Rm9jdXNBZmZpbml0eSA9IG5hdGl2ZXMuR2V0Rm9jdXNBZmZpbml0eTsKCi8qKgogKiBAcGFyYW0ge251bWJlcn0gYXhUcmVlSUQgVGhlIGlkIG9mIHRoZSBhY2Nlc3NpYmlsaXR5IHRyZWUuCiAqIEBwYXJhbSB7bnVtYmVyfSBub2RlSUQgVGhlIGlkIG9mIGEgbm9kZS4KICogQHJldHVybiB7P251bWJlcn0gVGhlIGlkIG9mIHRoZSBub2RlJ3MgcGFyZW50LCBvciB1bmRlZmluZWQgaWYgaXQncyB0aGUKICogICAgcm9vdCBvZiBpdHMgdHJlZSBvciBpZiB0aGUgdHJlZSBvciBub2RlIHdhc24ndCBmb3VuZC4KICovCnZhciBHZXRQYXJlbnRJRCA9IG5hdGl2ZXMuR2V0UGFyZW50SUQ7CgovKioKICogQHBhcmFtIHtudW1iZXJ9IGF4VHJlZUlEIFRoZSBpZCBvZiB0aGUgYWNjZXNzaWJpbGl0eSB0cmVlLgogKiBAcGFyYW0ge251bWJlcn0gbm9kZUlEIFRoZSBpZCBvZiBhIG5vZGUuCiAqIEByZXR1cm4gez9udW1iZXJ9IFRoZSBudW1iZXIgb2YgY2hpbGRyZW4gb2YgdGhlIG5vZGUsIG9yIHVuZGVmaW5lZCBpZgogKiAgICAgdGhlIHRyZWUgb3Igbm9kZSB3YXNuJ3QgZm91bmQuCiAqLwp2YXIgR2V0Q2hpbGRDb3VudCA9IG5hdGl2ZXMuR2V0Q2hpbGRDb3VudDsKCi8qKgogKiBAcGFyYW0ge251bWJlcn0gYXhUcmVlSUQgVGhlIGlkIG9mIHRoZSBhY2Nlc3NpYmlsaXR5IHRyZWUuCiAqIEBwYXJhbSB7bnVtYmVyfSBub2RlSUQgVGhlIGlkIG9mIGEgbm9kZS4KICogQHBhcmFtIHtudW1iZXJ9IGNoaWxkSW5kZXggQW4gaW5kZXggb2YgYSBjaGlsZCBvZiB0aGlzIG5vZGUuCiAqIEByZXR1cm4gez9udW1iZXJ9IFRoZSBpZCBvZiB0aGUgY2hpbGQgYXQgdGhlIGdpdmVuIGluZGV4LCBvciB1bmRlZmluZWQKICogICAgIGlmIHRoZSB0cmVlIG9yIG5vZGUgb3IgY2hpbGQgYXQgdGhhdCBpbmRleCB3YXNuJ3QgZm91bmQuCiAqLwp2YXIgR2V0Q2hpbGRJREF0SW5kZXggPSBuYXRpdmVzLkdldENoaWxkSURBdEluZGV4OwoKLyoqCiAqIEBwYXJhbSB7bnVtYmVyfSBheFRyZWVJRCBUaGUgaWQgb2YgdGhlIGFjY2Vzc2liaWxpdHkgdHJlZS4KICogQHBhcmFtIHtudW1iZXJ9IG5vZGVJRCBUaGUgaWQgb2YgYSBub2RlLgogKiBAcmV0dXJuIHs/bnVtYmVyfSBUaGUgaWRzIG9mIHRoZSBjaGlsZHJlbiBvZiB0aGUgbm9kZSwgb3IgdW5kZWZpbmVkCiAqICAgICBpZiB0aGUgdHJlZSBvciBub2RlIHdhc24ndCBmb3VuZC4KICovCnZhciBHZXRDaGlsZElkcyA9IG5hdGl2ZXMuR2V0Q2hpbGRJRHM7CgovKioKICogQHBhcmFtIHtudW1iZXJ9IGF4VHJlZUlEIFRoZSBpZCBvZiB0aGUgYWNjZXNzaWJpbGl0eSB0cmVlLgogKiBAcGFyYW0ge251bWJlcn0gbm9kZUlEIFRoZSBpZCBvZiBhIG5vZGUuCiAqIEByZXR1cm4gez9PYmplY3R9IEFuIG9iamVjdCBtYXBwaW5nIGh0bWwgYXR0cmlidXRlcyB0byB2YWx1ZXMuCiAqLwp2YXIgR2V0SHRtbEF0dHJpYnV0ZXMgPSBuYXRpdmVzLkdldEh0bWxBdHRyaWJ1dGVzOwoKLyoqCiAqIEBwYXJhbSB7bnVtYmVyfSBheFRyZWVJRCBUaGUgaWQgb2YgdGhlIGFjY2Vzc2liaWxpdHkgdHJlZS4KICogQHBhcmFtIHtudW1iZXJ9IG5vZGVJRCBUaGUgaWQgb2YgYSBub2RlLgogKiBAcmV0dXJuIHs/bnVtYmVyfSBUaGUgaW5kZXggb2YgdGhpcyBub2RlIGluIGl0cyBwYXJlbnQsIG9yIHVuZGVmaW5lZCBpZgogKiAgICAgdGhlIHRyZWUgb3Igbm9kZSBvciBub2RlIHBhcmVudCB3YXNuJ3QgZm91bmQuCiAqLwp2YXIgR2V0SW5kZXhJblBhcmVudCA9IG5hdGl2ZXMuR2V0SW5kZXhJblBhcmVudDsKCi8qKgogKiBAcGFyYW0ge251bWJlcn0gYXhUcmVlSUQgVGhlIGlkIG9mIHRoZSBhY2Nlc3NpYmlsaXR5IHRyZWUuCiAqIEBwYXJhbSB7bnVtYmVyfSBub2RlSUQgVGhlIGlkIG9mIGEgbm9kZS4KICogQHJldHVybiB7P09iamVjdH0gQW4gb2JqZWN0IHdpdGggYSBzdHJpbmcga2V5IGZvciBldmVyeSBzdGF0ZSBmbGFnIHNldCwKICogICAgIG9yIHVuZGVmaW5lZCBpZiB0aGUgdHJlZSBvciBub2RlIG9yIG5vZGUgcGFyZW50IHdhc24ndCBmb3VuZC4KICovCnZhciBHZXRTdGF0ZSA9IG5hdGl2ZXMuR2V0U3RhdGU7CgovKioKICogQHBhcmFtIHtudW1iZXJ9IGF4VHJlZUlEIFRoZSBpZCBvZiB0aGUgYWNjZXNzaWJpbGl0eSB0cmVlLgogKiBAcGFyYW0ge251bWJlcn0gbm9kZUlEIFRoZSBpZCBvZiBhIG5vZGUuCiAqIEByZXR1cm4ge3N0cmluZ30gVGhlIHJlc3RyaWN0aW9uLCBvbmUgb2YKICogImRpc2FibGVkIiwgInJlYWRPbmx5IiBvciB1bmRlZmluZWQgaWYgZW5hYmxlZCBvciBvdGhlciBvYmplY3Qgbm90IGRpc2FibGVkCiAqLwp2YXIgR2V0UmVzdHJpY3Rpb24gPSBuYXRpdmVzLkdldFJlc3RyaWN0aW9uOwoKLyoqCiAqIEBwYXJhbSB7bnVtYmVyfSBheFRyZWVJRCBUaGUgaWQgb2YgdGhlIGFjY2Vzc2liaWxpdHkgdHJlZS4KICogQHBhcmFtIHtudW1iZXJ9IG5vZGVJRCBUaGUgaWQgb2YgYSBub2RlLgogKiBAcmV0dXJuIHtzdHJpbmd9IFRoZSBjaGVja2VkIHN0YXRlLCBhcyB1bmRlZmluZWQsICJ0cnVlIiwgImZhbHNlIiBvciAibWl4ZWQiLgogKi8KdmFyIEdldENoZWNrZWQgPSBuYXRpdmVzLkdldENoZWNrZWQ7CgovKioKICogQHBhcmFtIHtudW1iZXJ9IGF4VHJlZUlEIFRoZSBpZCBvZiB0aGUgYWNjZXNzaWJpbGl0eSB0cmVlLgogKiBAcGFyYW0ge251bWJlcn0gbm9kZUlEIFRoZSBpZCBvZiBhIG5vZGUuCiAqIEByZXR1cm4ge3N0cmluZ30gVGhlIHJvbGUgb2YgdGhlIG5vZGUsIG9yIHVuZGVmaW5lZCBpZiB0aGUgdHJlZSBvcgogKiAgICAgbm9kZSB3YXNuJ3QgZm91bmQuCiAqLwp2YXIgR2V0Um9sZSA9IG5hdGl2ZXMuR2V0Um9sZTsKCi8qKgogKiBAcGFyYW0ge251bWJlcn0gYXhUcmVlSUQgVGhlIGlkIG9mIHRoZSBhY2Nlc3NpYmlsaXR5IHRyZWUuCiAqIEBwYXJhbSB7bnVtYmVyfSBub2RlSUQgVGhlIGlkIG9mIGEgbm9kZS4KICogQHJldHVybiB7P2F1dG9tYXRpb24uUmVjdH0gVGhlIGxvY2F0aW9uIG9mIHRoZSBub2RlLCBvciB1bmRlZmluZWQgaWYKICogICAgIHRoZSB0cmVlIG9yIG5vZGUgd2Fzbid0IGZvdW5kLgogKi8KdmFyIEdldExvY2F0aW9uID0gbmF0aXZlcy5HZXRMb2NhdGlvbjsKCi8qKgogKiBAcGFyYW0ge251bWJlcn0gYXhUcmVlSUQgVGhlIGlkIG9mIHRoZSBhY2Nlc3NpYmlsaXR5IHRyZWUuCiAqIEBwYXJhbSB7bnVtYmVyfSBub2RlSUQgVGhlIGlkIG9mIGEgbm9kZS4KICogQHBhcmFtIHtudW1iZXJ9IHN0YXJ0SW5kZXggVGhlIHN0YXJ0IGluZGV4IG9mIHRoZSByYW5nZS4KICogQHBhcmFtIHtudW1iZXJ9IGVuZEluZGV4IFRoZSBlbmQgaW5kZXggb2YgdGhlIHJhbmdlLgogKiBAcmV0dXJuIHs/YXV0b21hdGlvbi5SZWN0fSBUaGUgYm91bmRpbmcgYm94IG9mIHRoZSBzdWJyYW5nZSBvZiB0aGlzIG5vZGUsCiAqICAgICBvciB0aGUgbG9jYXRpb24gaWYgdGhlcmUgYXJlIG5vIHN1YnJhbmdlcywgb3IgdW5kZWZpbmVkIGlmCiAqICAgICB0aGUgdHJlZSBvciBub2RlIHdhc24ndCBmb3VuZC4KICovCnZhciBHZXRCb3VuZHNGb3JSYW5nZSA9IG5hdGl2ZXMuR2V0Qm91bmRzRm9yUmFuZ2U7CgovKioKICogQHBhcmFtIHtudW1iZXJ9IGF4VHJlZUlEIFRoZSBpZCBvZiB0aGUgYWNjZXNzaWJpbGl0eSB0cmVlLgogKiBAcGFyYW0ge251bWJlcn0gbm9kZUlEIFRoZSBpZCBvZiBhIG5vZGUuCiAqIEByZXR1cm4gez9hdXRvbWF0aW9uLlJlY3R9IFRoZSB1bmNsaXBwZWQgbG9jYXRpb24gb2YgdGhlIG5vZGUsIG9yCiAqIHVuZGVmaW5lZCBpZiB0aGUgdHJlZSBvciBub2RlIHdhc24ndCBmb3VuZC4KICovCnZhciBHZXRVbmNsaXBwZWRMb2NhdGlvbiA9IG5hdGl2ZXMuR2V0VW5jbGlwcGVkTG9jYXRpb247CgovKioKICogQHBhcmFtIHtudW1iZXJ9IGF4VHJlZUlEIFRoZSBpZCBvZiB0aGUgYWNjZXNzaWJpbGl0eSB0cmVlLgogKiBAcGFyYW0ge251bWJlcn0gbm9kZUlEIFRoZSBpZCBvZiBhIG5vZGUuCiAqIEByZXR1cm4geyFBcnJheS48bnVtYmVyPn0gVGhlIHRleHQgb2Zmc2V0IHdoZXJlIGVhY2ggbGluZSBzdGFydHMsIG9yIGFuIGVtcHR5CiAqICAgICBhcnJheSBpZiB0aGlzIG5vZGUgaGFzIG5vIHRleHQgY29udGVudCwgb3IgdW5kZWZpbmVkIGlmIHRoZSB0cmVlIG9yIG5vZGUKICogICAgIHdhcyBub3QgZm91bmQuCiAqLwp2YXIgR2V0TGluZVN0YXJ0T2Zmc2V0cyA9IHJlcXVpcmVOYXRpdmUoCiAgICAnYXV0b21hdGlvbkludGVybmFsJykuR2V0TGluZVN0YXJ0T2Zmc2V0czsKCi8qKgogKiBAcGFyYW0ge251bWJlcn0gYXhUcmVlSUQgVGhlIGlkIG9mIHRoZSBhY2Nlc3NpYmlsaXR5IHRyZWUuCiAqIEBwYXJhbSB7bnVtYmVyfSBub2RlSUQgVGhlIGlkIG9mIGEgbm9kZS4KICogQHBhcmFtIHtzdHJpbmd9IGF0dHIgVGhlIG5hbWUgb2YgYSBzdHJpbmcgYXR0cmlidXRlLgogKiBAcmV0dXJuIHs/c3RyaW5nfSBUaGUgdmFsdWUgb2YgdGhpcyBhdHRyaWJ1dGUsIG9yIHVuZGVmaW5lZCBpZiB0aGUgdHJlZSwKICogICAgIG5vZGUsIG9yIGF0dHJpYnV0ZSB3YXNuJ3QgZm91bmQuCiAqLwp2YXIgR2V0U3RyaW5nQXR0cmlidXRlID0gbmF0aXZlcy5HZXRTdHJpbmdBdHRyaWJ1dGU7CgovKioKICogQHBhcmFtIHtudW1iZXJ9IGF4VHJlZUlEIFRoZSBpZCBvZiB0aGUgYWNjZXNzaWJpbGl0eSB0cmVlLgogKiBAcGFyYW0ge251bWJlcn0gbm9kZUlEIFRoZSBpZCBvZiBhIG5vZGUuCiAqIEBwYXJhbSB7c3RyaW5nfSBhdHRyIFRoZSBuYW1lIG9mIGFuIGF0dHJpYnV0ZS4KICogQHJldHVybiB7P2Jvb2xlYW59IFRoZSB2YWx1ZSBvZiB0aGlzIGF0dHJpYnV0ZSwgb3IgdW5kZWZpbmVkIGlmIHRoZSB0cmVlLAogKiAgICAgbm9kZSwgb3IgYXR0cmlidXRlIHdhc24ndCBmb3VuZC4KICovCnZhciBHZXRCb29sQXR0cmlidXRlID0gbmF0aXZlcy5HZXRCb29sQXR0cmlidXRlOwoKLyoqCiAqIEBwYXJhbSB7bnVtYmVyfSBheFRyZWVJRCBUaGUgaWQgb2YgdGhlIGFjY2Vzc2liaWxpdHkgdHJlZS4KICogQHBhcmFtIHtudW1iZXJ9IG5vZGVJRCBUaGUgaWQgb2YgYSBub2RlLgogKiBAcGFyYW0ge3N0cmluZ30gYXR0ciBUaGUgbmFtZSBvZiBhbiBhdHRyaWJ1dGUuCiAqIEByZXR1cm4gez9udW1iZXJ9IFRoZSB2YWx1ZSBvZiB0aGlzIGF0dHJpYnV0ZSwgb3IgdW5kZWZpbmVkIGlmIHRoZSB0cmVlLAogKiAgICAgbm9kZSwgb3IgYXR0cmlidXRlIHdhc24ndCBmb3VuZC4KICovCnZhciBHZXRJbnRBdHRyaWJ1dGUgPSBuYXRpdmVzLkdldEludEF0dHJpYnV0ZTsKCi8qKgogKiBAcGFyYW0ge251bWJlcn0gYXhUcmVlSUQgVGhlIGlkIG9mIHRoZSBhY2Nlc3NpYmlsaXR5IHRyZWUuCiAqIEBwYXJhbSB7bnVtYmVyfSBub2RlSUQgVGhlIGlkIG9mIGEgbm9kZS4KICogQHBhcmFtIHtzdHJpbmd9IGF0dHIgVGhlIG5hbWUgb2YgYW4gYXR0cmlidXRlLgogKiBAcmV0dXJuIHs/bnVtYmVyfSBUaGUgdmFsdWUgb2YgdGhpcyBhdHRyaWJ1dGUsIG9yIHVuZGVmaW5lZCBpZiB0aGUgdHJlZSwKICogICAgIG5vZGUsIG9yIGF0dHJpYnV0ZSB3YXNuJ3QgZm91bmQuCiAqLwp2YXIgR2V0RmxvYXRBdHRyaWJ1dGUgPSBuYXRpdmVzLkdldEZsb2F0QXR0cmlidXRlOwoKLyoqCiAqIEBwYXJhbSB7bnVtYmVyfSBheFRyZWVJRCBUaGUgaWQgb2YgdGhlIGFjY2Vzc2liaWxpdHkgdHJlZS4KICogQHBhcmFtIHtudW1iZXJ9IG5vZGVJRCBUaGUgaWQgb2YgYSBub2RlLgogKiBAcGFyYW0ge3N0cmluZ30gYXR0ciBUaGUgbmFtZSBvZiBhbiBhdHRyaWJ1dGUuCiAqIEByZXR1cm4gez9BcnJheS48bnVtYmVyPn0gVGhlIHZhbHVlIG9mIHRoaXMgYXR0cmlidXRlLCBvciB1bmRlZmluZWQKICogICAgIGlmIHRoZSB0cmVlLCBub2RlLCBvciBhdHRyaWJ1dGUgd2Fzbid0IGZvdW5kLgogKi8KdmFyIEdldEludExpc3RBdHRyaWJ1dGUgPQogICAgbmF0aXZlcy5HZXRJbnRMaXN0QXR0cmlidXRlOwoKLyoqCiAqIEBwYXJhbSB7bnVtYmVyfSBheFRyZWVJRCBUaGUgaWQgb2YgdGhlIGFjY2Vzc2liaWxpdHkgdHJlZS4KICogQHBhcmFtIHtudW1iZXJ9IG5vZGVJRCBUaGUgaWQgb2YgYSBub2RlLgogKiBAcGFyYW0ge3N0cmluZ30gYXR0ciBUaGUgbmFtZSBvZiBhbiBIVE1MIGF0dHJpYnV0ZS4KICogQHJldHVybiB7P3N0cmluZ30gVGhlIHZhbHVlIG9mIHRoaXMgYXR0cmlidXRlLCBvciB1bmRlZmluZWQgaWYgdGhlIHRyZWUsCiAqICAgICBub2RlLCBvciBhdHRyaWJ1dGUgd2Fzbid0IGZvdW5kLgogKi8KdmFyIEdldEh0bWxBdHRyaWJ1dGUgPSBuYXRpdmVzLkdldEh0bWxBdHRyaWJ1dGU7CgovKioKICogQHBhcmFtIHtudW1iZXJ9IGF4VHJlZUlEIFRoZSBpZCBvZiB0aGUgYWNjZXNzaWJpbGl0eSB0cmVlLgogKiBAcGFyYW0ge251bWJlcn0gbm9kZUlEIFRoZSBpZCBvZiBhIG5vZGUuCiAqIEByZXR1cm4ge2F1dG9tYXRpb24uTmFtZUZyb21UeXBlfSBUaGUgc291cmNlIG9mIHRoZSBub2RlJ3MgbmFtZS4KICovCnZhciBHZXROYW1lRnJvbSA9IG5hdGl2ZXMuR2V0TmFtZUZyb207CgovKioKICogQHBhcmFtIHtudW1iZXJ9IGF4VHJlZUlEIFRoZSBpZCBvZiB0aGUgYWNjZXNzaWJpbGl0eSB0cmVlLgogKiBAcGFyYW0ge251bWJlcn0gbm9kZUlEIFRoZSBpZCBvZiBhIG5vZGUuCiAqIEByZXR1cm4ge2Jvb2xlYW59CiAqLwp2YXIgR2V0Qm9sZCA9IG5hdGl2ZXMuR2V0Qm9sZDsKCi8qKgogKiBAcGFyYW0ge251bWJlcn0gYXhUcmVlSUQgVGhlIGlkIG9mIHRoZSBhY2Nlc3NpYmlsaXR5IHRyZWUuCiAqIEBwYXJhbSB7bnVtYmVyfSBub2RlSUQgVGhlIGlkIG9mIGEgbm9kZS4KICogQHJldHVybiB7Ym9vbGVhbn0KICovCnZhciBHZXRJdGFsaWMgPSBuYXRpdmVzLkdldEl0YWxpYzsKCi8qKgogKiBAcGFyYW0ge251bWJlcn0gYXhUcmVlSUQgVGhlIGlkIG9mIHRoZSBhY2Nlc3NpYmlsaXR5IHRyZWUuCiAqIEBwYXJhbSB7bnVtYmVyfSBub2RlSUQgVGhlIGlkIG9mIGEgbm9kZS4KICogQHJldHVybiB7Ym9vbGVhbn0KICovCnZhciBHZXRVbmRlcmxpbmUgPSBuYXRpdmVzLkdldFVuZGVybGluZTsKCi8qKgogKiBAcGFyYW0ge251bWJlcn0gYXhUcmVlSUQgVGhlIGlkIG9mIHRoZSBhY2Nlc3NpYmlsaXR5IHRyZWUuCiAqIEBwYXJhbSB7bnVtYmVyfSBub2RlSUQgVGhlIGlkIG9mIGEgbm9kZS4KICogQHJldHVybiB7Ym9vbGVhbn0KICovCnZhciBHZXRMaW5lVGhyb3VnaCA9IG5hdGl2ZXMuR2V0TGluZVRocm91Z2g7CgovKioKICogQHBhcmFtIHtudW1iZXJ9IGF4VHJlZUlEIFRoZSBpZCBvZiB0aGUgYWNjZXNzaWJpbGl0eSB0cmVlLgogKiBAcGFyYW0ge251bWJlcn0gbm9kZUlEIFRoZSBpZCBvZiBhIG5vZGUuCiAqIEByZXR1cm4gez9BcnJheS48YXV0b21hdGlvbi5DdXN0b21BY3Rpb24+fSBMaXN0IG9mIGN1c3RvbSBhY3Rpb25zIG9mIHRoZQogKiAgICAgbm9kZS4KICovCnZhciBHZXRDdXN0b21BY3Rpb25zID0gbmF0aXZlcy5HZXRDdXN0b21BY3Rpb25zOwoKdmFyIGxvZ2dpbmcgPSByZXF1aXJlTmF0aXZlKCdsb2dnaW5nJyk7CnZhciB1dGlscyA9IHJlcXVpcmUoJ3V0aWxzJyk7CgovKioKICogQSBzaW5nbGUgbm9kZSBpbiB0aGUgQXV0b21hdGlvbiB0cmVlLgogKiBAcGFyYW0ge0F1dG9tYXRpb25Sb290Tm9kZUltcGx9IHJvb3QgVGhlIHJvb3Qgb2YgdGhlIHRyZWUuCiAqIEBjb25zdHJ1Y3RvcgogKi8KZnVuY3Rpb24gQXV0b21hdGlvbk5vZGVJbXBsKHJvb3QpIHsKICB0aGlzLnJvb3RJbXBsID0gcm9vdDsKICB0aGlzLmhvc3ROb2RlXyA9IG51bGw7CiAgdGhpcy5saXN0ZW5lcnMgPSB7X19wcm90b19fOiBudWxsfTsKfQoKQXV0b21hdGlvbk5vZGVJbXBsLnByb3RvdHlwZSA9IHsKICBfX3Byb3RvX186IG51bGwsCiAgdHJlZUlEOiAtMSwKICBpZDogLTEsCiAgaXNSb290Tm9kZTogZmFsc2UsCgogIGRldGFjaDogZnVuY3Rpb24oKSB7CiAgICB0aGlzLnJvb3RJbXBsID0gbnVsbDsKICAgIHRoaXMuaG9zdE5vZGVfID0gbnVsbDsKICAgIHRoaXMubGlzdGVuZXJzID0ge19fcHJvdG9fXzogbnVsbH07CiAgfSwKCiAgZ2V0IHJvb3QoKSB7CiAgICByZXR1cm4gdGhpcy5yb290SW1wbCAmJiB0aGlzLnJvb3RJbXBsLndyYXBwZXI7CiAgfSwKCiAgZ2V0IHBhcmVudCgpIHsKICAgIGlmICghdGhpcy5yb290SW1wbCkKICAgICAgcmV0dXJuIHVuZGVmaW5lZDsKICAgIGlmICh0aGlzLmhvc3ROb2RlXykKICAgICAgcmV0dXJuIHRoaXMuaG9zdE5vZGVfOwogICAgdmFyIHBhcmVudElEID0gR2V0UGFyZW50SUQodGhpcy50cmVlSUQsIHRoaXMuaWQpOwogICAgcmV0dXJuIHRoaXMucm9vdEltcGwuZ2V0KHBhcmVudElEKTsKICB9LAoKICBnZXQgaHRtbEF0dHJpYnV0ZXMoKSB7CiAgICByZXR1cm4gR2V0SHRtbEF0dHJpYnV0ZXModGhpcy50cmVlSUQsIHRoaXMuaWQpIHx8IHt9OwogIH0sCgogIGdldCBzdGF0ZSgpIHsKICAgIHJldHVybiBHZXRTdGF0ZSh0aGlzLnRyZWVJRCwgdGhpcy5pZCkgfHwge307CiAgfSwKCiAgZ2V0IHJvbGUoKSB7CiAgICByZXR1cm4gR2V0Um9sZSh0aGlzLnRyZWVJRCwgdGhpcy5pZCk7CiAgfSwKCiAgZ2V0IHJlc3RyaWN0aW9uKCkgewogICAgcmV0dXJuIEdldFJlc3RyaWN0aW9uKHRoaXMudHJlZUlELCB0aGlzLmlkKTsKICB9LAoKICBnZXQgY2hlY2tlZCgpIHsKICAgIHJldHVybiBHZXRDaGVja2VkKHRoaXMudHJlZUlELCB0aGlzLmlkKTsKICB9LAoKICBnZXQgbG9jYXRpb24oKSB7CiAgICByZXR1cm4gR2V0TG9jYXRpb24odGhpcy50cmVlSUQsIHRoaXMuaWQpOwogIH0sCgogIGJvdW5kc0ZvclJhbmdlOiBmdW5jdGlvbihzdGFydEluZGV4LCBlbmRJbmRleCkgewogICAgcmV0dXJuIEdldEJvdW5kc0ZvclJhbmdlKHRoaXMudHJlZUlELCB0aGlzLmlkLCBzdGFydEluZGV4LCBlbmRJbmRleCk7CiAgfSwKCiAgZ2V0IHVuY2xpcHBlZExvY2F0aW9uKCkgewogICAgdmFyIHJlc3VsdCA9IEdldFVuY2xpcHBlZExvY2F0aW9uKHRoaXMudHJlZUlELCB0aGlzLmlkKTsKICAgIGlmIChyZXN1bHQgPT09IHVuZGVmaW5lZCkKICAgICAgcmVzdWx0ID0gR2V0TG9jYXRpb24odGhpcy50cmVlSUQsIHRoaXMuaWQpOwogICAgcmV0dXJuIHJlc3VsdDsKICB9LAoKICBnZXQgaW5kZXhJblBhcmVudCgpIHsKICAgIHJldHVybiBHZXRJbmRleEluUGFyZW50KHRoaXMudHJlZUlELCB0aGlzLmlkKTsKICB9LAoKICBnZXQgbGluZVN0YXJ0T2Zmc2V0cygpIHsKICAgIHJldHVybiBHZXRMaW5lU3RhcnRPZmZzZXRzKHRoaXMudHJlZUlELCB0aGlzLmlkKTsKICB9LAoKICBnZXQgY2hpbGRUcmVlKCkgewogICAgdmFyIGNoaWxkVHJlZUlEID0gR2V0SW50QXR0cmlidXRlKHRoaXMudHJlZUlELCB0aGlzLmlkLCAnY2hpbGRUcmVlSWQnKTsKICAgIGlmIChjaGlsZFRyZWVJRCkKICAgICAgcmV0dXJuIEF1dG9tYXRpb25Sb290Tm9kZUltcGwuZ2V0KGNoaWxkVHJlZUlEKTsKICB9LAoKICBnZXQgZmlyc3RDaGlsZCgpIHsKICAgIGlmICghdGhpcy5yb290SW1wbCkKICAgICAgcmV0dXJuIHVuZGVmaW5lZDsKICAgIGlmICh0aGlzLmNoaWxkVHJlZSkKICAgICAgcmV0dXJuIHRoaXMuY2hpbGRUcmVlOwogICAgaWYgKCFHZXRDaGlsZENvdW50KHRoaXMudHJlZUlELCB0aGlzLmlkKSkKICAgICAgcmV0dXJuIHVuZGVmaW5lZDsKICAgIHZhciBmaXJzdENoaWxkSUQgPSBHZXRDaGlsZElEQXRJbmRleCh0aGlzLnRyZWVJRCwgdGhpcy5pZCwgMCk7CiAgICByZXR1cm4gdGhpcy5yb290SW1wbC5nZXQoZmlyc3RDaGlsZElEKTsKICB9LAoKICBnZXQgbGFzdENoaWxkKCkgewogICAgaWYgKCF0aGlzLnJvb3RJbXBsKQogICAgICByZXR1cm4gdW5kZWZpbmVkOwogICAgaWYgKHRoaXMuY2hpbGRUcmVlKQogICAgICByZXR1cm4gdGhpcy5jaGlsZFRyZWU7CiAgICB2YXIgY291bnQgPSBHZXRDaGlsZENvdW50KHRoaXMudHJlZUlELCB0aGlzLmlkKTsKICAgIGlmICghY291bnQpCiAgICAgIHJldHVybiB1bmRlZmluZWQ7CiAgICB2YXIgbGFzdENoaWxkSUQgPSBHZXRDaGlsZElEQXRJbmRleCh0aGlzLnRyZWVJRCwgdGhpcy5pZCwgY291bnQgLSAxKTsKICAgIHJldHVybiB0aGlzLnJvb3RJbXBsLmdldChsYXN0Q2hpbGRJRCk7CiAgfSwKCiAgZ2V0IGNoaWxkcmVuKCkgewogICAgaWYgKCF0aGlzLnJvb3RJbXBsKQogICAgICByZXR1cm4gW107CgogICAgaWYgKHRoaXMuY2hpbGRUcmVlKQogICAgICByZXR1cm4gW3RoaXMuY2hpbGRUcmVlXTsKCiAgICB2YXIgY2hpbGRyZW4gPSBbXTsKICAgIHZhciBjaGlsZElkcyA9IEdldENoaWxkSWRzKHRoaXMudHJlZUlELCB0aGlzLmlkKTsKICAgIGZvciAodmFyIGkgPSAwOyBpIDwgY2hpbGRJZHMubGVuZ3RoOyArK2kpIHsKICAgICAgdmFyIGNoaWxkSUQgPSBjaGlsZElkc1tpXTsKICAgICAgdmFyIGNoaWxkID0gdGhpcy5yb290SW1wbC5nZXQoY2hpbGRJRCk7CiAgICAgICRBcnJheS5wdXNoKGNoaWxkcmVuLCBjaGlsZCk7CiAgICB9CiAgICByZXR1cm4gY2hpbGRyZW47CiAgfSwKCiAgZ2V0IHByZXZpb3VzU2libGluZygpIHsKICAgIHZhciBwYXJlbnQgPSB0aGlzLnBhcmVudDsKICAgIGlmICghcGFyZW50KQogICAgICByZXR1cm4gdW5kZWZpbmVkOwogICAgcGFyZW50ID0gcHJpdmF0ZXMocGFyZW50KS5pbXBsOwogICAgdmFyIGluZGV4SW5QYXJlbnQgPSBHZXRJbmRleEluUGFyZW50KHRoaXMudHJlZUlELCB0aGlzLmlkKTsKICAgIHJldHVybiB0aGlzLnJvb3RJbXBsLmdldCgKICAgICAgICBHZXRDaGlsZElEQXRJbmRleChwYXJlbnQudHJlZUlELCBwYXJlbnQuaWQsIGluZGV4SW5QYXJlbnQgLSAxKSk7CiAgfSwKCiAgZ2V0IG5leHRTaWJsaW5nKCkgewogICAgdmFyIHBhcmVudCA9IHRoaXMucGFyZW50OwogICAgaWYgKCFwYXJlbnQpCiAgICAgIHJldHVybiB1bmRlZmluZWQ7CiAgICBwYXJlbnQgPSBwcml2YXRlcyhwYXJlbnQpLmltcGw7CiAgICB2YXIgaW5kZXhJblBhcmVudCA9IEdldEluZGV4SW5QYXJlbnQodGhpcy50cmVlSUQsIHRoaXMuaWQpOwogICAgcmV0dXJuIHRoaXMucm9vdEltcGwuZ2V0KAogICAgICAgIEdldENoaWxkSURBdEluZGV4KHBhcmVudC50cmVlSUQsIHBhcmVudC5pZCwgaW5kZXhJblBhcmVudCArIDEpKTsKICB9LAoKICBnZXQgbmFtZUZyb20oKSB7CiAgICByZXR1cm4gR2V0TmFtZUZyb20odGhpcy50cmVlSUQsIHRoaXMuaWQpOwogIH0sCgogIGdldCBib2xkKCkgewogICAgcmV0dXJuIEdldEJvbGQodGhpcy50cmVlSUQsIHRoaXMuaWQpOwogIH0sCgogIGdldCBpdGFsaWMoKSB7CiAgICByZXR1cm4gR2V0SXRhbGljKHRoaXMudHJlZUlELCB0aGlzLmlkKTsKICB9LAoKICBnZXQgdW5kZXJsaW5lKCkgewogICAgcmV0dXJuIEdldFVuZGVybGluZSh0aGlzLnRyZWVJRCwgdGhpcy5pZCk7CiAgfSwKCiAgZ2V0IGxpbmVUaHJvdWdoKCkgewogICAgcmV0dXJuIEdldExpbmVUaHJvdWdoKHRoaXMudHJlZUlELCB0aGlzLmlkKTsKICB9LAoKICBnZXQgY3VzdG9tQWN0aW9ucygpIHsKICAgIHJldHVybiBHZXRDdXN0b21BY3Rpb25zKHRoaXMudHJlZUlELCB0aGlzLmlkKTsKICB9LAoKICBkb0RlZmF1bHQ6IGZ1bmN0aW9uKCkgewogICAgdGhpcy5wZXJmb3JtQWN0aW9uXygnZG9EZWZhdWx0Jyk7CiAgfSwKCiAgZm9jdXM6IGZ1bmN0aW9uKCkgewogICAgdGhpcy5wZXJmb3JtQWN0aW9uXygnZm9jdXMnKTsKICB9LAoKICBnZXRJbWFnZURhdGE6IGZ1bmN0aW9uKG1heFdpZHRoLCBtYXhIZWlnaHQpIHsKICAgIHRoaXMucGVyZm9ybUFjdGlvbl8oJ2dldEltYWdlRGF0YScsCiAgICAgICAgICAgICAgICAgICAgICAgIHsgbWF4V2lkdGg6IG1heFdpZHRoLAogICAgICAgICAgICAgICAgICAgICAgICAgIG1heEhlaWdodDogbWF4SGVpZ2h0IH0pOwogIH0sCgogIGhpdFRlc3Q6IGZ1bmN0aW9uKHgsIHksIGV2ZW50VG9GaXJlKSB7CiAgICB0aGlzLmhpdFRlc3RJbnRlcm5hbCh4LCB5LCBldmVudFRvRmlyZSk7CiAgfSwKCiAgaGl0VGVzdFdpdGhSZXBseTogZnVuY3Rpb24oeCwgeSwgb3B0X2NhbGxiYWNrKSB7CiAgICB0aGlzLmhpdFRlc3RJbnRlcm5hbCh4LCB5LCAnaGl0VGVzdFJlc3VsdCcsIG9wdF9jYWxsYmFjayk7CiAgfSwKCiAgaGl0VGVzdEludGVybmFsOiBmdW5jdGlvbih4LCB5LCBldmVudFRvRmlyZSwgb3B0X2NhbGxiYWNrKSB7CiAgICAvLyBDb252ZXJ0IGZyb20gZ2xvYmFsIHRvIHRyZWUtcmVsYXRpdmUgY29vcmRpbmF0ZXMuCiAgICB2YXIgbG9jYXRpb24gPSBHZXRMb2NhdGlvbih0aGlzLnRyZWVJRCwgR2V0Um9vdElEKHRoaXMudHJlZUlEKSk7CiAgICB0aGlzLnBlcmZvcm1BY3Rpb25fKCdoaXRUZXN0JywKICAgICAgICAgICAgICAgICAgICAgICAgeyB4OiBNYXRoLmZsb29yKHggLSBsb2NhdGlvbi5sZWZ0KSwKICAgICAgICAgICAgICAgICAgICAgICAgICB5OiBNYXRoLmZsb29yKHkgLSBsb2NhdGlvbi50b3ApLAogICAgICAgICAgICAgICAgICAgICAgICAgIGV2ZW50VG9GaXJlOiBldmVudFRvRmlyZSB9LAogICAgICAgICAgICAgICAgICAgICAgICBvcHRfY2FsbGJhY2spOwogIH0sCgogIG1ha2VWaXNpYmxlOiBmdW5jdGlvbigpIHsKICAgIHRoaXMucGVyZm9ybUFjdGlvbl8oJ21ha2VWaXNpYmxlJyk7CiAgfSwKCiAgcGVyZm9ybUN1c3RvbUFjdGlvbjogZnVuY3Rpb24oY3VzdG9tQWN0aW9uSWQpIHsKICAgIHRoaXMucGVyZm9ybUFjdGlvbl8oJ2N1c3RvbUFjdGlvbicsIHsgY3VzdG9tQWN0aW9uSUQ6IGN1c3RvbUFjdGlvbklkIH0pOwogIH0sCgogIHJlc3VtZU1lZGlhOiBmdW5jdGlvbigpIHsKICAgIHRoaXMucGVyZm9ybUFjdGlvbl8oJ3Jlc3VtZU1lZGlhJyk7CiAgfSwKCiAgc2Nyb2xsQmFja3dhcmQ6IGZ1bmN0aW9uKG9wdF9jYWxsYmFjaykgewogICAgdGhpcy5wZXJmb3JtQWN0aW9uXygnc2Nyb2xsQmFja3dhcmQnLCB7fSwgb3B0X2NhbGxiYWNrKTsKICB9LAoKICBzY3JvbGxGb3J3YXJkOiBmdW5jdGlvbihvcHRfY2FsbGJhY2spIHsKICAgIHRoaXMucGVyZm9ybUFjdGlvbl8oJ3Njcm9sbEZvcndhcmQnLCB7fSwgb3B0X2NhbGxiYWNrKTsKICB9LAoKICBzY3JvbGxVcDogZnVuY3Rpb24ob3B0X2NhbGxiYWNrKSB7CiAgICB0aGlzLnBlcmZvcm1BY3Rpb25fKCdzY3JvbGxVcCcsIHt9LCBvcHRfY2FsbGJhY2spOwogIH0sCgogIHNjcm9sbERvd246IGZ1bmN0aW9uKG9wdF9jYWxsYmFjaykgewogICAgdGhpcy5wZXJmb3JtQWN0aW9uXygnc2Nyb2xsRG93bicsIHt9LCBvcHRfY2FsbGJhY2spOwogIH0sCgogIHNjcm9sbExlZnQ6IGZ1bmN0aW9uKG9wdF9jYWxsYmFjaykgewogICAgdGhpcy5wZXJmb3JtQWN0aW9uXygnc2Nyb2xsTGVmdCcsIHt9LCBvcHRfY2FsbGJhY2spOwogIH0sCgogIHNjcm9sbFJpZ2h0OiBmdW5jdGlvbihvcHRfY2FsbGJhY2spIHsKICAgIHRoaXMucGVyZm9ybUFjdGlvbl8oJ3Njcm9sbFJpZ2h0Jywge30sIG9wdF9jYWxsYmFjayk7CiAgfSwKCiAgc2V0U2VsZWN0aW9uOiBmdW5jdGlvbihzdGFydEluZGV4LCBlbmRJbmRleCkgewogICAgaWYgKHRoaXMuc3RhdGUuZWRpdGFibGUpIHsKICAgICAgdGhpcy5wZXJmb3JtQWN0aW9uXygnc2V0U2VsZWN0aW9uJywKICAgICAgICAgICAgICAgICAgICAgICAgICB7IGZvY3VzTm9kZUlEOiB0aGlzLmlkLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgYW5jaG9yT2Zmc2V0OiBzdGFydEluZGV4LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgZm9jdXNPZmZzZXQ6IGVuZEluZGV4IH0pOwogICAgfQogIH0sCgogIHNldFNlcXVlbnRpYWxGb2N1c05hdmlnYXRpb25TdGFydGluZ1BvaW50OiBmdW5jdGlvbigpIHsKICAgIHRoaXMucGVyZm9ybUFjdGlvbl8oJ3NldFNlcXVlbnRpYWxGb2N1c05hdmlnYXRpb25TdGFydGluZ1BvaW50Jyk7CiAgfSwKCiAgc2hvd0NvbnRleHRNZW51OiBmdW5jdGlvbigpIHsKICAgIHRoaXMucGVyZm9ybUFjdGlvbl8oJ3Nob3dDb250ZXh0TWVudScpOwogIH0sCgogIHN0YXJ0RHVja2luZ01lZGlhOiBmdW5jdGlvbigpIHsKICAgIHRoaXMucGVyZm9ybUFjdGlvbl8oJ3N0YXJ0RHVja2luZ01lZGlhJyk7CiAgfSwKCiAgc3RvcER1Y2tpbmdNZWRpYTogZnVuY3Rpb24oKSB7CiAgICB0aGlzLnBlcmZvcm1BY3Rpb25fKCdzdG9wRHVja2luZ01lZGlhJyk7CiAgfSwKCiAgc3VzcGVuZE1lZGlhOiBmdW5jdGlvbigpIHsKICAgIHRoaXMucGVyZm9ybUFjdGlvbl8oJ3N1c3BlbmRNZWRpYScpOwogIH0sCgogIGRvbVF1ZXJ5U2VsZWN0b3I6IGZ1bmN0aW9uKHNlbGVjdG9yLCBjYWxsYmFjaykgewogICAgaWYgKCF0aGlzLnJvb3RJbXBsKQogICAgICBjYWxsYmFjaygpOwogICAgYXV0b21hdGlvbkludGVybmFsLnF1ZXJ5U2VsZWN0b3IoCiAgICAgIHsgdHJlZUlEOiB0aGlzLnJvb3RJbXBsLnRyZWVJRCwKICAgICAgICBhdXRvbWF0aW9uTm9kZUlEOiB0aGlzLmlkLAogICAgICAgIHNlbGVjdG9yOiBzZWxlY3RvciB9LAogICAgICAkRnVuY3Rpb24uYmluZCh0aGlzLmRvbVF1ZXJ5U2VsZWN0b3JDYWxsYmFja18sIHRoaXMsIGNhbGxiYWNrKSk7CiAgfSwKCiAgZmluZDogZnVuY3Rpb24ocGFyYW1zKSB7CiAgICByZXR1cm4gdGhpcy5maW5kSW50ZXJuYWxfKHBhcmFtcyk7CiAgfSwKCiAgZmluZEFsbDogZnVuY3Rpb24ocGFyYW1zKSB7CiAgICByZXR1cm4gdGhpcy5maW5kSW50ZXJuYWxfKHBhcmFtcywgW10pOwogIH0sCgogIG1hdGNoZXM6IGZ1bmN0aW9uKHBhcmFtcykgewogICAgcmV0dXJuIHRoaXMubWF0Y2hJbnRlcm5hbF8ocGFyYW1zKTsKICB9LAoKICBhZGRFdmVudExpc3RlbmVyOiBmdW5jdGlvbihldmVudFR5cGUsIGNhbGxiYWNrLCBjYXB0dXJlKSB7CiAgICB0aGlzLnJlbW92ZUV2ZW50TGlzdGVuZXIoZXZlbnRUeXBlLCBjYWxsYmFjayk7CiAgICBpZiAoIXRoaXMubGlzdGVuZXJzW2V2ZW50VHlwZV0pCiAgICAgIHRoaXMubGlzdGVuZXJzW2V2ZW50VHlwZV0gPSBbXTsKICAgICRBcnJheS5wdXNoKHRoaXMubGlzdGVuZXJzW2V2ZW50VHlwZV0sIHsKICAgICAgX19wcm90b19fOiBudWxsLAogICAgICBjYWxsYmFjazogY2FsbGJhY2ssCiAgICAgIGNhcHR1cmU6ICEhY2FwdHVyZSwKICAgIH0pOwogIH0sCgogIC8vIFRPRE8oZHRzZW5nL2Fib3hoYWxsKTogQ2hlY2sgdGhpcyBpbXBsIGFnYWluc3Qgc3BlYy4KICByZW1vdmVFdmVudExpc3RlbmVyOiBmdW5jdGlvbihldmVudFR5cGUsIGNhbGxiYWNrKSB7CiAgICBpZiAodGhpcy5saXN0ZW5lcnNbZXZlbnRUeXBlXSkgewogICAgICB2YXIgbGlzdGVuZXJzID0gdGhpcy5saXN0ZW5lcnNbZXZlbnRUeXBlXTsKICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCBsaXN0ZW5lcnMubGVuZ3RoOyBpKyspIHsKICAgICAgICBpZiAoY2FsbGJhY2sgPT09IGxpc3RlbmVyc1tpXS5jYWxsYmFjaykKICAgICAgICAgICRBcnJheS5zcGxpY2UobGlzdGVuZXJzLCBpLCAxKTsKICAgICAgfQogICAgfQogIH0sCgogIHRvSlNPTjogZnVuY3Rpb24oKSB7CiAgICByZXR1cm4geyB0cmVlSUQ6IHRoaXMudHJlZUlELAogICAgICAgICAgICAgaWQ6IHRoaXMuaWQsCiAgICAgICAgICAgICByb2xlOiB0aGlzLnJvbGUsCiAgICAgICAgICAgICBhdHRyaWJ1dGVzOiB0aGlzLmF0dHJpYnV0ZXMgfTsKICB9LAoKICBkaXNwYXRjaEV2ZW50OiBmdW5jdGlvbihldmVudFR5cGUsIGV2ZW50RnJvbSwgbW91c2VYLCBtb3VzZVkpIHsKICAgIHZhciBwYXRoID0gW107CiAgICB2YXIgcGFyZW50ID0gdGhpcy5wYXJlbnQ7CiAgICB3aGlsZSAocGFyZW50KSB7CiAgICAgICRBcnJheS5wdXNoKHBhdGgsIHBhcmVudCk7CiAgICAgIHBhcmVudCA9IHBhcmVudC5wYXJlbnQ7CiAgICB9CiAgICB2YXIgZXZlbnQgPSBuZXcgQXV0b21hdGlvbkV2ZW50KGV2ZW50VHlwZSwgdGhpcy53cmFwcGVyLCBldmVudEZyb20pOwogICAgZXZlbnQubW91c2VYID0gbW91c2VYOwogICAgZXZlbnQubW91c2VZID0gbW91c2VZOwoKICAgIC8vIERpc3BhdGNoIHRoZSBldmVudCB0aHJvdWdoIHRoZSBwcm9wYWdhdGlvbiBwYXRoIGluIHRocmVlIHBoYXNlczoKICAgIC8vIC0gY2FwdHVyaW5nOiBzdGFydGluZyBmcm9tIHRoZSByb290IGFuZCBnb2luZyBkb3duIHRvIHRoZSB0YXJnZXQncyBwYXJlbnQKICAgIC8vIC0gdGFyZ2V0aW5nOiBkaXNwYXRjaGluZyB0aGUgZXZlbnQgb24gdGhlIHRhcmdldCBpdHNlbGYKICAgIC8vIC0gYnViYmxpbmc6IHN0YXJ0aW5nIGZyb20gdGhlIHRhcmdldCdzIHBhcmVudCwgZ29pbmcgYmFjayB1cCB0byB0aGUgcm9vdC4KICAgIC8vIEF0IGFueSBzdGFnZSwgYSBsaXN0ZW5lciBtYXkgY2FsbCBzdG9wUHJvcGFnYXRpb24oKSBvbiB0aGUgZXZlbnQsIHdoaWNoCiAgICAvLyB3aWxsIGltbWVkaWF0ZWx5IHN0b3AgZXZlbnQgcHJvcGFnYXRpb24gdGhyb3VnaCB0aGlzIHBhdGguCiAgICBpZiAodGhpcy5kaXNwYXRjaEV2ZW50QXRDYXB0dXJpbmdfKGV2ZW50LCBwYXRoKSkgewogICAgICBpZiAodGhpcy5kaXNwYXRjaEV2ZW50QXRUYXJnZXRpbmdfKGV2ZW50LCBwYXRoKSkKICAgICAgICB0aGlzLmRpc3BhdGNoRXZlbnRBdEJ1YmJsaW5nXyhldmVudCwgcGF0aCk7CiAgICB9CiAgfSwKCiAgdG9TdHJpbmc6IGZ1bmN0aW9uKCkgewogICAgdmFyIHBhcmVudElEID0gR2V0UGFyZW50SUQodGhpcy50cmVlSUQsIHRoaXMuaWQpOwogICAgdmFyIGNoaWxkVHJlZUlEID0gR2V0SW50QXR0cmlidXRlKHRoaXMudHJlZUlELCB0aGlzLmlkLCAnY2hpbGRUcmVlSWQnKTsKICAgIHZhciBjb3VudCA9IEdldENoaWxkQ291bnQodGhpcy50cmVlSUQsIHRoaXMuaWQpOwogICAgdmFyIGNoaWxkSURzID0gW107CiAgICBmb3IgKHZhciBpID0gMDsgaSA8IGNvdW50OyArK2kpIHsKICAgICAgdmFyIGNoaWxkSUQgPSBHZXRDaGlsZElEQXRJbmRleCh0aGlzLnRyZWVJRCwgdGhpcy5pZCwgaSk7CiAgICAgICRBcnJheS5wdXNoKGNoaWxkSURzLCBjaGlsZElEKTsKICAgIH0KCiAgICB2YXIgcmVzdWx0ID0gJ25vZGUgaWQ9JyArIHRoaXMuaWQgKwogICAgICAgICcgcm9sZT0nICsgdGhpcy5yb2xlICsKICAgICAgICAnIHN0YXRlPScgKyAkSlNPTi5zdHJpbmdpZnkodGhpcy5zdGF0ZSkgKwogICAgICAgICcgcGFyZW50SUQ9JyArIHBhcmVudElEICsKICAgICAgICAnIGNoaWxkSWRzPScgKyAkSlNPTi5zdHJpbmdpZnkoY2hpbGRJRHMpOwogICAgaWYgKHRoaXMuaG9zdE5vZGVfKSB7CiAgICAgIHZhciBob3N0Tm9kZUltcGwgPSBwcml2YXRlcyh0aGlzLmhvc3ROb2RlXykuaW1wbDsKICAgICAgcmVzdWx0ICs9ICcgaG9zdCB0cmVlSUQ9JyArIGhvc3ROb2RlSW1wbC50cmVlSUQgKwogICAgICAgICAgJyBob3N0IG5vZGVJRD0nICsgaG9zdE5vZGVJbXBsLmlkOwogICAgfQogICAgaWYgKGNoaWxkVHJlZUlEKQogICAgICByZXN1bHQgKz0gJyBjaGlsZFRyZWVJRD0nICsgY2hpbGRUcmVlSUQ7CiAgICByZXR1cm4gcmVzdWx0OwogIH0sCgogIGRpc3BhdGNoRXZlbnRBdENhcHR1cmluZ186IGZ1bmN0aW9uKGV2ZW50LCBwYXRoKSB7CiAgICBwcml2YXRlcyhldmVudCkuaW1wbC5ldmVudFBoYXNlID0gRXZlbnQuQ0FQVFVSSU5HX1BIQVNFOwogICAgZm9yICh2YXIgaSA9IHBhdGgubGVuZ3RoIC0gMTsgaSA+PSAwOyBpLS0pIHsKICAgICAgdGhpcy5maXJlRXZlbnRMaXN0ZW5lcnNfKHBhdGhbaV0sIGV2ZW50KTsKICAgICAgaWYgKHByaXZhdGVzKGV2ZW50KS5pbXBsLnByb3BhZ2F0aW9uU3RvcHBlZCkKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICB9CiAgICByZXR1cm4gdHJ1ZTsKICB9LAoKICBkaXNwYXRjaEV2ZW50QXRUYXJnZXRpbmdfOiBmdW5jdGlvbihldmVudCkgewogICAgcHJpdmF0ZXMoZXZlbnQpLmltcGwuZXZlbnRQaGFzZSA9IEV2ZW50LkFUX1RBUkdFVDsKICAgIHRoaXMuZmlyZUV2ZW50TGlzdGVuZXJzXyh0aGlzLndyYXBwZXIsIGV2ZW50KTsKICAgIHJldHVybiAhcHJpdmF0ZXMoZXZlbnQpLmltcGwucHJvcGFnYXRpb25TdG9wcGVkOwogIH0sCgogIGRpc3BhdGNoRXZlbnRBdEJ1YmJsaW5nXzogZnVuY3Rpb24oZXZlbnQsIHBhdGgpIHsKICAgIHByaXZhdGVzKGV2ZW50KS5pbXBsLmV2ZW50UGhhc2UgPSBFdmVudC5CVUJCTElOR19QSEFTRTsKICAgIGZvciAodmFyIGkgPSAwOyBpIDwgcGF0aC5sZW5ndGg7IGkrKykgewogICAgICB0aGlzLmZpcmVFdmVudExpc3RlbmVyc18ocGF0aFtpXSwgZXZlbnQpOwogICAgICBpZiAocHJpdmF0ZXMoZXZlbnQpLmltcGwucHJvcGFnYXRpb25TdG9wcGVkKQogICAgICAgIHJldHVybiBmYWxzZTsKICAgIH0KICAgIHJldHVybiB0cnVlOwogIH0sCgogIGZpcmVFdmVudExpc3RlbmVyc186IGZ1bmN0aW9uKG5vZGUsIGV2ZW50KSB7CiAgICB2YXIgbm9kZUltcGwgPSBwcml2YXRlcyhub2RlKS5pbXBsOwogICAgaWYgKCFub2RlSW1wbC5yb290SW1wbCkKICAgICAgcmV0dXJuOwoKICAgIHZhciBsaXN0ZW5lcnMgPSBub2RlSW1wbC5saXN0ZW5lcnNbZXZlbnQudHlwZV07CiAgICBpZiAoIWxpc3RlbmVycykKICAgICAgcmV0dXJuOwogICAgdmFyIGV2ZW50UGhhc2UgPSBldmVudC5ldmVudFBoYXNlOwogICAgZm9yICh2YXIgaSA9IDA7IGkgPCBsaXN0ZW5lcnMubGVuZ3RoOyBpKyspIHsKICAgICAgaWYgKGV2ZW50UGhhc2UgPT0gRXZlbnQuQ0FQVFVSSU5HX1BIQVNFICYmICFsaXN0ZW5lcnNbaV0uY2FwdHVyZSkKICAgICAgICBjb250aW51ZTsKICAgICAgaWYgKGV2ZW50UGhhc2UgPT0gRXZlbnQuQlVCQkxJTkdfUEhBU0UgJiYgbGlzdGVuZXJzW2ldLmNhcHR1cmUpCiAgICAgICAgY29udGludWU7CgogICAgICB0cnkgewogICAgICAgIGxpc3RlbmVyc1tpXS5jYWxsYmFjayhldmVudCk7CiAgICAgIH0gY2F0Y2ggKGUpIHsKICAgICAgICBleGNlcHRpb25IYW5kbGVyLmhhbmRsZSgnRXJyb3IgaW4gZXZlbnQgaGFuZGxlciBmb3IgJyArIGV2ZW50LnR5cGUgKwogICAgICAgICAgICAnIGR1cmluZyBwaGFzZSAnICsgZXZlbnRQaGFzZSwgZSk7CiAgICAgIH0KICAgIH0KICB9LAoKICBwZXJmb3JtQWN0aW9uXzogZnVuY3Rpb24oYWN0aW9uVHlwZSwgb3B0X2FyZ3MsIG9wdF9jYWxsYmFjaykgewogICAgaWYgKCF0aGlzLnJvb3RJbXBsKQogICAgICByZXR1cm47CgogICAgLy8gTm90IHlldCBpbml0aWFsaXplZC4KICAgIGlmICh0aGlzLnJvb3RJbXBsLnRyZWVJRCA9PT0gdW5kZWZpbmVkIHx8CiAgICAgICAgdGhpcy5pZCA9PT0gdW5kZWZpbmVkKSB7CiAgICAgIHJldHVybjsKICAgIH0KCiAgICAvLyBDaGVjayBwZXJtaXNzaW9ucy4KICAgIGlmICghSXNJbnRlcmFjdFBlcm1pdHRlZCgpKSB7CiAgICAgIHRocm93IG5ldyBFcnJvcihhY3Rpb25UeXBlICsgJyByZXF1aXJlcyB7ImRlc2t0b3AiOiB0cnVlfSBvcicgKwogICAgICAgICAgJyB7ImludGVyYWN0IjogdHJ1ZX0gaW4gdGhlICJhdXRvbWF0aW9uIiBtYW5pZmVzdCBrZXkuJyk7CiAgICB9CiAgICB2YXIgcmVxdWVzdElEID0gLTE7CiAgICBpZiAob3B0X2NhbGxiYWNrKSB7CiAgICAgIHJlcXVlc3RJRCA9IHRoaXMucm9vdEltcGwuYWRkQWN0aW9uUmVzdWx0Q2FsbGJhY2sob3B0X2NhbGxiYWNrKTsKICAgIH0KCiAgICBhdXRvbWF0aW9uSW50ZXJuYWwucGVyZm9ybUFjdGlvbih7IHRyZWVJRDogdGhpcy5yb290SW1wbC50cmVlSUQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGF1dG9tYXRpb25Ob2RlSUQ6IHRoaXMuaWQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGFjdGlvblR5cGU6IGFjdGlvblR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJlcXVlc3RJRDogcmVxdWVzdElEfSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIG9wdF9hcmdzIHx8IHt9KTsKICB9LAoKICBkb21RdWVyeVNlbGVjdG9yQ2FsbGJhY2tfOiBmdW5jdGlvbih1c2VyQ2FsbGJhY2ssIHJlc3VsdEF1dG9tYXRpb25Ob2RlSUQpIHsKICAgIC8vIHJlc3VsdEF1dG9tYXRpb25Ob2RlSUQgY291bGQgYmUgemVybyBvciB1bmRlZmluZWQgb3IgKHVubGlrZWx5KSBudWxsOwogICAgLy8gdGhleSBhbGwgYW1vdW50IHRvIHRoZSBzYW1lIHRoaW5nIGhlcmUsIHdoaWNoIGlzIHRoYXQgbm8gbm9kZSB3YXMKICAgIC8vIHJldHVybmVkLgogICAgaWYgKCFyZXN1bHRBdXRvbWF0aW9uTm9kZUlEIHx8ICF0aGlzLnJvb3RJbXBsKSB7CiAgICAgIHVzZXJDYWxsYmFjayhudWxsKTsKICAgICAgcmV0dXJuOwogICAgfQogICAgdmFyIHJlc3VsdE5vZGUgPSB0aGlzLnJvb3RJbXBsLmdldChyZXN1bHRBdXRvbWF0aW9uTm9kZUlEKTsKICAgIGlmICghcmVzdWx0Tm9kZSkgewogICAgICBsb2dnaW5nLldBUk5JTkcoJ1F1ZXJ5IHNlbGVjdG9yIHJlc3VsdCBub3QgaW4gdHJlZTogJyArCiAgICAgICAgICAgICAgICAgICAgICByZXN1bHRBdXRvbWF0aW9uTm9kZUlEKTsKICAgICAgdXNlckNhbGxiYWNrKG51bGwpOwogICAgfQogICAgdXNlckNhbGxiYWNrKHJlc3VsdE5vZGUpOwogIH0sCgogIGZpbmRJbnRlcm5hbF86IGZ1bmN0aW9uKHBhcmFtcywgb3B0X3Jlc3VsdHMpIHsKICAgIHZhciByZXN1bHQgPSBudWxsOwogICAgdGhpcy5mb3JBbGxEZXNjZW5kYW50c18oZnVuY3Rpb24obm9kZSkgewogICAgICBpZiAocHJpdmF0ZXMobm9kZSkuaW1wbC5tYXRjaEludGVybmFsXyhwYXJhbXMpKSB7CiAgICAgICAgaWYgKG9wdF9yZXN1bHRzKQogICAgICAgICAgJEFycmF5LnB1c2gob3B0X3Jlc3VsdHMsIG5vZGUpOwogICAgICAgIGVsc2UKICAgICAgICAgIHJlc3VsdCA9IG5vZGU7CiAgICAgICAgcmV0dXJuICFvcHRfcmVzdWx0czsKICAgICAgfQogICAgfSk7CiAgICBpZiAob3B0X3Jlc3VsdHMpCiAgICAgIHJldHVybiBvcHRfcmVzdWx0czsKICAgIHJldHVybiByZXN1bHQ7CiAgfSwKCiAgLyoqCiAgICogRXhlY3V0ZXMgYSBjbG9zdXJlIGZvciBhbGwgb2YgdGhpcyBub2RlJ3MgZGVzY2VuZGFudHMsIGluIHByZS1vcmRlci4KICAgKiBFYXJseS1vdXRzIGlmIHRoZSBjbG9zdXJlIHJldHVybnMgdHJ1ZS4KICAgKiBAcGFyYW0ge0Z1bmN0aW9uKEF1dG9tYXRpb25Ob2RlKTpib29sZWFufSBjbG9zdXJlIENsb3N1cmUgdG8gYmUgZXhlY3V0ZWQKICAgKiAgICAgZm9yIGVhY2ggbm9kZS4gUmV0dXJuIHRydWUgdG8gZWFybHktb3V0IHRoZSB0cmF2ZXJzYWwuCiAgICovCiAgZm9yQWxsRGVzY2VuZGFudHNfOiBmdW5jdGlvbihjbG9zdXJlKSB7CiAgICB2YXIgc3RhY2sgPSAkQXJyYXkucmV2ZXJzZSh0aGlzLndyYXBwZXIuY2hpbGRyZW4pOwogICAgd2hpbGUgKHN0YWNrLmxlbmd0aCA+IDApIHsKICAgICAgdmFyIG5vZGUgPSAkQXJyYXkucG9wKHN0YWNrKTsKICAgICAgaWYgKGNsb3N1cmUobm9kZSkpCiAgICAgICAgcmV0dXJuOwoKICAgICAgdmFyIGNoaWxkcmVuID0gbm9kZS5jaGlsZHJlbjsKICAgICAgZm9yICh2YXIgaSA9IGNoaWxkcmVuLmxlbmd0aCAtIDE7IGkgPj0gMDsgaS0tKQogICAgICAgICRBcnJheS5wdXNoKHN0YWNrLCBjaGlsZHJlbltpXSk7CiAgICB9CiAgfSwKCiAgbWF0Y2hJbnRlcm5hbF86IGZ1bmN0aW9uKHBhcmFtcykgewogICAgaWYgKCRPYmplY3Qua2V5cyhwYXJhbXMpLmxlbmd0aCA9PT0gMCkKICAgICAgcmV0dXJuIGZhbHNlOwoKICAgIGlmICgncm9sZScgaW4gcGFyYW1zICYmIHRoaXMucm9sZSAhPSBwYXJhbXMucm9sZSkKICAgICAgICByZXR1cm4gZmFsc2U7CgogICAgaWYgKCdzdGF0ZScgaW4gcGFyYW1zKSB7CiAgICAgIGZvciAodmFyIHN0YXRlIGluIHBhcmFtcy5zdGF0ZSkgewogICAgICAgIGlmIChwYXJhbXMuc3RhdGVbc3RhdGVdICE9IChzdGF0ZSBpbiB0aGlzLnN0YXRlKSkKICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgfQogICAgfQogICAgaWYgKCdhdHRyaWJ1dGVzJyBpbiBwYXJhbXMpIHsKICAgICAgZm9yICh2YXIgYXR0cmlidXRlIGluIHBhcmFtcy5hdHRyaWJ1dGVzKSB7CiAgICAgICAgdmFyIGF0dHJWYWx1ZSA9IHBhcmFtcy5hdHRyaWJ1dGVzW2F0dHJpYnV0ZV07CiAgICAgICAgaWYgKHR5cGVvZiBhdHRyVmFsdWUgIT0gJ29iamVjdCcpIHsKICAgICAgICAgIGlmICh0aGlzW2F0dHJpYnV0ZV0gIT09IGF0dHJWYWx1ZSkKICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgIH0gZWxzZSBpZiAoYXR0clZhbHVlIGluc3RhbmNlb2YgJFJlZ0V4cC5zZWxmKSB7CiAgICAgICAgICBpZiAodHlwZW9mIHRoaXNbYXR0cmlidXRlXSAhPSAnc3RyaW5nJykKICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgICAgaWYgKCFhdHRyVmFsdWUudGVzdCh0aGlzW2F0dHJpYnV0ZV0pKQogICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIC8vIFRPRE8oYWJveGhhbGwpOiBoYW5kbGUgaW50bGlzdCBjYXNlLgogICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgIH0KICAgICAgfQogICAgfQogICAgcmV0dXJuIHRydWU7CiAgfQp9OwoKdmFyIHN0cmluZ0F0dHJpYnV0ZXMgPSBbCiAgICAnYWNjZXNzS2V5JywKICAgICdhcmlhSW52YWxpZFZhbHVlJywKICAgICdhdXRvQ29tcGxldGUnLAogICAgJ2NsYXNzTmFtZScsCiAgICAnY29udGFpbmVyTGl2ZVJlbGV2YW50JywKICAgICdjb250YWluZXJMaXZlU3RhdHVzJywKICAgICdkZXNjcmlwdGlvbicsCiAgICAnZGlzcGxheScsCiAgICAnaHRtbFRhZycsCiAgICAnaW1hZ2VEYXRhVXJsJywKICAgICdsYW5ndWFnZScsCiAgICAnbGl2ZVJlbGV2YW50JywKICAgICdsaXZlU3RhdHVzJywKICAgICduYW1lJywKICAgICdwbGFjZWhvbGRlcicsCiAgICAncm9sZURlc2NyaXB0aW9uJywKICAgICd0ZXh0SW5wdXRUeXBlJywKICAgICd1cmwnLAogICAgJ3ZhbHVlJ107Cgp2YXIgYm9vbEF0dHJpYnV0ZXMgPSBbCiAgICAnYnVzeScsCiAgICAnY2xpY2thYmxlJywKICAgICdjb250YWluZXJMaXZlQXRvbWljJywKICAgICdjb250YWluZXJMaXZlQnVzeScsCiAgICAnbGl2ZUF0b21pYycsCiAgICAnc2Nyb2xsYWJsZScKXTsKCnZhciBpbnRBdHRyaWJ1dGVzID0gWwogICAgJ2JhY2tncm91bmRDb2xvcicsCiAgICAnY29sb3InLAogICAgJ2NvbG9yVmFsdWUnLAogICAgJ2hpZXJhcmNoaWNhbExldmVsJywKICAgICdwb3NJblNldCcsCiAgICAnc2Nyb2xsWCcsCiAgICAnc2Nyb2xsWE1heCcsCiAgICAnc2Nyb2xsWE1pbicsCiAgICAnc2Nyb2xsWScsCiAgICAnc2Nyb2xsWU1heCcsCiAgICAnc2Nyb2xsWU1pbicsCiAgICAnc2V0U2l6ZScsCiAgICAndGFibGVDZWxsQ29sdW1uSW5kZXgnLAogICAgJ2FyaWFDZWxsQ29sdW1uSW5kZXgnLAogICAgJ3RhYmxlQ2VsbENvbHVtblNwYW4nLAogICAgJ3RhYmxlQ2VsbFJvd0luZGV4JywKICAgICdhcmlhQ2VsbFJvd0luZGV4JywKICAgICd0YWJsZUNlbGxSb3dTcGFuJywKICAgICd0YWJsZUNvbHVtbkNvdW50JywKICAgICdhcmlhQ29sdW1uQ291bnQnLAogICAgJ3RhYmxlQ29sdW1uSW5kZXgnLAogICAgJ3RhYmxlUm93Q291bnQnLAogICAgJ2FyaWFSb3dDb3VudCcsCiAgICAndGFibGVSb3dJbmRleCcsCiAgICAndGV4dFNlbEVuZCcsCiAgICAndGV4dFNlbFN0YXJ0J107Cgp2YXIgbm9kZVJlZkF0dHJpYnV0ZXMgPSBbCiAgICBbJ2FjdGl2ZWRlc2NlbmRhbnRJZCcsICdhY3RpdmVEZXNjZW5kYW50J10sCiAgICBbJ2luUGFnZUxpbmtUYXJnZXRJZCcsICdpblBhZ2VMaW5rVGFyZ2V0J10sCiAgICBbJ25leHRGb2N1c0lkJywgJ25leHRGb2N1cyddLAogICAgWyduZXh0T25MaW5lSWQnLCAnbmV4dE9uTGluZSddLAogICAgWydwcmV2aW91c0ZvY3VzSWQnLCAncHJldmlvdXNGb2N1cyddLAogICAgWydwcmV2aW91c09uTGluZUlkJywgJ3ByZXZpb3VzT25MaW5lJ10sCiAgICBbJ3RhYmxlQ29sdW1uSGVhZGVySWQnLCAndGFibGVDb2x1bW5IZWFkZXInXSwKICAgIFsndGFibGVIZWFkZXJJZCcsICd0YWJsZUhlYWRlciddLAogICAgWyd0YWJsZVJvd0hlYWRlcklkJywgJ3RhYmxlUm93SGVhZGVyJ11dOwoKdmFyIGludExpc3RBdHRyaWJ1dGVzID0gWwogICAgJ2xpbmVCcmVha3MnLAogICAgJ21hcmtlckVuZHMnLAogICAgJ21hcmtlclN0YXJ0cycsCiAgICAnbWFya2VyVHlwZXMnLAogICAgJ3dvcmRFbmRzJywKICAgICd3b3JkU3RhcnRzJ107Cgp2YXIgbm9kZVJlZkxpc3RBdHRyaWJ1dGVzID0gWwogICAgWydjb250cm9sc0lkcycsICdjb250cm9scyddLAogICAgWydkZXNjcmliZWRieUlkcycsICdkZXNjcmliZWRCeSddLAogICAgWydmbG93dG9JZHMnLCAnZmxvd1RvJ10sCiAgICBbJ2xhYmVsbGVkYnlJZHMnLCAnbGFiZWxsZWRCeSddXTsKCnZhciBmbG9hdEF0dHJpYnV0ZXMgPSBbCiAgICAndmFsdWVGb3JSYW5nZScsCiAgICAnbWluVmFsdWVGb3JSYW5nZScsCiAgICAnbWF4VmFsdWVGb3JSYW5nZSddOwoKdmFyIGh0bWxBdHRyaWJ1dGVzID0gWwogICAgWyd0eXBlJywgJ2lucHV0VHlwZSddXTsKCnZhciBwdWJsaWNBdHRyaWJ1dGVzID0gW107CgokQXJyYXkuZm9yRWFjaChzdHJpbmdBdHRyaWJ1dGVzLCBmdW5jdGlvbihhdHRyaWJ1dGVOYW1lKSB7CiAgJEFycmF5LnB1c2gocHVibGljQXR0cmlidXRlcywgYXR0cmlidXRlTmFtZSk7CiAgJE9iamVjdC5kZWZpbmVQcm9wZXJ0eShBdXRvbWF0aW9uTm9kZUltcGwucHJvdG90eXBlLCBhdHRyaWJ1dGVOYW1lLCB7CiAgICBfX3Byb3RvX186IG51bGwsCiAgICBnZXQ6IGZ1bmN0aW9uKCkgewogICAgICByZXR1cm4gR2V0U3RyaW5nQXR0cmlidXRlKHRoaXMudHJlZUlELCB0aGlzLmlkLCBhdHRyaWJ1dGVOYW1lKTsKICAgIH0KICB9KTsKfSk7CgokQXJyYXkuZm9yRWFjaChib29sQXR0cmlidXRlcywgZnVuY3Rpb24oYXR0cmlidXRlTmFtZSkgewogICRBcnJheS5wdXNoKHB1YmxpY0F0dHJpYnV0ZXMsIGF0dHJpYnV0ZU5hbWUpOwogICRPYmplY3QuZGVmaW5lUHJvcGVydHkoQXV0b21hdGlvbk5vZGVJbXBsLnByb3RvdHlwZSwgYXR0cmlidXRlTmFtZSwgewogICAgX19wcm90b19fOiBudWxsLAogICAgZ2V0OiBmdW5jdGlvbigpIHsKICAgICAgcmV0dXJuIEdldEJvb2xBdHRyaWJ1dGUodGhpcy50cmVlSUQsIHRoaXMuaWQsIGF0dHJpYnV0ZU5hbWUpOwogICAgfQogIH0pOwp9KTsKCiRBcnJheS5mb3JFYWNoKGludEF0dHJpYnV0ZXMsIGZ1bmN0aW9uKGF0dHJpYnV0ZU5hbWUpIHsKICAkQXJyYXkucHVzaChwdWJsaWNBdHRyaWJ1dGVzLCBhdHRyaWJ1dGVOYW1lKTsKICAkT2JqZWN0LmRlZmluZVByb3BlcnR5KEF1dG9tYXRpb25Ob2RlSW1wbC5wcm90b3R5cGUsIGF0dHJpYnV0ZU5hbWUsIHsKICAgIF9fcHJvdG9fXzogbnVsbCwKICAgIGdldDogZnVuY3Rpb24oKSB7CiAgICAgIHJldHVybiBHZXRJbnRBdHRyaWJ1dGUodGhpcy50cmVlSUQsIHRoaXMuaWQsIGF0dHJpYnV0ZU5hbWUpOwogICAgfQogIH0pOwp9KTsKCiRBcnJheS5mb3JFYWNoKG5vZGVSZWZBdHRyaWJ1dGVzLCBmdW5jdGlvbihwYXJhbXMpIHsKICB2YXIgc3JjQXR0cmlidXRlTmFtZSA9IHBhcmFtc1swXTsKICB2YXIgZHN0QXR0cmlidXRlTmFtZSA9IHBhcmFtc1sxXTsKICAkQXJyYXkucHVzaChwdWJsaWNBdHRyaWJ1dGVzLCBkc3RBdHRyaWJ1dGVOYW1lKTsKICAkT2JqZWN0LmRlZmluZVByb3BlcnR5KEF1dG9tYXRpb25Ob2RlSW1wbC5wcm90b3R5cGUsIGRzdEF0dHJpYnV0ZU5hbWUsIHsKICAgIF9fcHJvdG9fXzogbnVsbCwKICAgIGdldDogZnVuY3Rpb24oKSB7CiAgICAgIHZhciBpZCA9IEdldEludEF0dHJpYnV0ZSh0aGlzLnRyZWVJRCwgdGhpcy5pZCwgc3JjQXR0cmlidXRlTmFtZSk7CiAgICAgIGlmIChpZCAmJiB0aGlzLnJvb3RJbXBsKQogICAgICAgIHJldHVybiB0aGlzLnJvb3RJbXBsLmdldChpZCk7CiAgICAgIGVsc2UKICAgICAgICByZXR1cm4gdW5kZWZpbmVkOwogICAgfQogIH0pOwp9KTsKCiRBcnJheS5mb3JFYWNoKGludExpc3RBdHRyaWJ1dGVzLCBmdW5jdGlvbihhdHRyaWJ1dGVOYW1lKSB7CiAgJEFycmF5LnB1c2gocHVibGljQXR0cmlidXRlcywgYXR0cmlidXRlTmFtZSk7CiAgJE9iamVjdC5kZWZpbmVQcm9wZXJ0eShBdXRvbWF0aW9uTm9kZUltcGwucHJvdG90eXBlLCBhdHRyaWJ1dGVOYW1lLCB7CiAgICBfX3Byb3RvX186IG51bGwsCiAgICBnZXQ6IGZ1bmN0aW9uKCkgewogICAgICByZXR1cm4gR2V0SW50TGlzdEF0dHJpYnV0ZSh0aGlzLnRyZWVJRCwgdGhpcy5pZCwgYXR0cmlidXRlTmFtZSk7CiAgICB9CiAgfSk7Cn0pOwoKJEFycmF5LmZvckVhY2gobm9kZVJlZkxpc3RBdHRyaWJ1dGVzLCBmdW5jdGlvbihwYXJhbXMpIHsKICB2YXIgc3JjQXR0cmlidXRlTmFtZSA9IHBhcmFtc1swXTsKICB2YXIgZHN0QXR0cmlidXRlTmFtZSA9IHBhcmFtc1sxXTsKICAkQXJyYXkucHVzaChwdWJsaWNBdHRyaWJ1dGVzLCBkc3RBdHRyaWJ1dGVOYW1lKTsKICAkT2JqZWN0LmRlZmluZVByb3BlcnR5KEF1dG9tYXRpb25Ob2RlSW1wbC5wcm90b3R5cGUsIGRzdEF0dHJpYnV0ZU5hbWUsIHsKICAgIF9fcHJvdG9fXzogbnVsbCwKICAgIGdldDogZnVuY3Rpb24oKSB7CiAgICAgIHZhciBpZHMgPSBHZXRJbnRMaXN0QXR0cmlidXRlKHRoaXMudHJlZUlELCB0aGlzLmlkLCBzcmNBdHRyaWJ1dGVOYW1lKTsKICAgICAgaWYgKCFpZHMgfHwgIXRoaXMucm9vdEltcGwpCiAgICAgICAgcmV0dXJuIHVuZGVmaW5lZDsKICAgICAgdmFyIHJlc3VsdCA9IFtdOwogICAgICBmb3IgKHZhciBpID0gMDsgaSA8IGlkcy5sZW5ndGg7ICsraSkgewogICAgICAgIHZhciBub2RlID0gdGhpcy5yb290SW1wbC5nZXQoaWRzW2ldKTsKICAgICAgICBpZiAobm9kZSkKICAgICAgICAgICRBcnJheS5wdXNoKHJlc3VsdCwgbm9kZSk7CiAgICAgIH0KICAgICAgcmV0dXJuIHJlc3VsdDsKICAgIH0KICB9KTsKfSk7CgokQXJyYXkuZm9yRWFjaChmbG9hdEF0dHJpYnV0ZXMsIGZ1bmN0aW9uKGF0dHJpYnV0ZU5hbWUpIHsKICAkQXJyYXkucHVzaChwdWJsaWNBdHRyaWJ1dGVzLCBhdHRyaWJ1dGVOYW1lKTsKICAkT2JqZWN0LmRlZmluZVByb3BlcnR5KEF1dG9tYXRpb25Ob2RlSW1wbC5wcm90b3R5cGUsIGF0dHJpYnV0ZU5hbWUsIHsKICAgIF9fcHJvdG9fXzogbnVsbCwKICAgIGdldDogZnVuY3Rpb24oKSB7CiAgICAgIHJldHVybiBHZXRGbG9hdEF0dHJpYnV0ZSh0aGlzLnRyZWVJRCwgdGhpcy5pZCwgYXR0cmlidXRlTmFtZSk7CiAgICB9CiAgfSk7Cn0pOwoKJEFycmF5LmZvckVhY2goaHRtbEF0dHJpYnV0ZXMsIGZ1bmN0aW9uKHBhcmFtcykgewogIHZhciBzcmNBdHRyaWJ1dGVOYW1lID0gcGFyYW1zWzBdOwogIHZhciBkc3RBdHRyaWJ1dGVOYW1lID0gcGFyYW1zWzFdOwogICRBcnJheS5wdXNoKHB1YmxpY0F0dHJpYnV0ZXMsIGRzdEF0dHJpYnV0ZU5hbWUpOwogICRPYmplY3QuZGVmaW5lUHJvcGVydHkoQXV0b21hdGlvbk5vZGVJbXBsLnByb3RvdHlwZSwgZHN0QXR0cmlidXRlTmFtZSwgewogICAgX19wcm90b19fOiBudWxsLAogICAgZ2V0OiBmdW5jdGlvbigpIHsKICAgICAgcmV0dXJuIEdldEh0bWxBdHRyaWJ1dGUodGhpcy50cmVlSUQsIHRoaXMuaWQsIHNyY0F0dHJpYnV0ZU5hbWUpOwogICAgfQogIH0pOwp9KTsKCi8qKgogKiBBdXRvbWF0aW9uUm9vdE5vZGUuCiAqCiAqIEFuIEF1dG9tYXRpb25Sb290Tm9kZSBpcyB0aGUgamF2YXNjcmlwdCBlbmQgb2YgYW4gQVhUcmVlIGxpdmluZyBpbiB0aGUKICogYnJvd3Nlci4gQXV0b21hdGlvblJvb3ROb2RlIGhhbmRsZXMgdW5zZXJpYWxpemluZyBpbmNyZW1lbnRhbCB1cGRhdGVzIGZyb20KICogdGhlIHNvdXJjZSBBWFRyZWUuIEVhY2ggdXBkYXRlIGNvbnRhaW5zIG5vZGUgZGF0YSB0aGF0IGZvcm0gYSBjb21wbGV0ZSB0cmVlCiAqIGFmdGVyIGFwcGx5aW5nIHRoZSB1cGRhdGUuCiAqCiAqIEEgYnJpZWYgbm90ZSBhYm91dCBpZHMgdXNlZCB0aHJvdWdoIHRoaXMgY2xhc3MuIFRoZSBzb3VyY2UgQVhUcmVlIGFzc2lnbnMKICogdW5pcXVlIGlkcyBwZXIgbm9kZSBhbmQgd2UgdXNlIHRoZXNlIGlkcyB0byBidWlsZCBhIGhhc2ggdG8gdGhlIGFjdHVhbAogKiBBdXRvbWF0aW9uTm9kZSBvYmplY3QuCiAqIFRodXMsIHRyZWUgdHJhdmVyc2FscyBhbW91bnQgdG8gYSBsb29rdXAgaW4gb3VyIGhhc2guCiAqCiAqIFRoZSB0cmVlIGl0c2VsZiBpcyBpZGVudGlmaWVkIGJ5IHRoZSBhY2Nlc3NpYmlsaXR5IHRyZWUgaWQgb2YgdGhlCiAqIHJlbmRlcmVyIHdpZGdldCBob3N0LgogKiBAY29uc3RydWN0b3IKICovCmZ1bmN0aW9uIEF1dG9tYXRpb25Sb290Tm9kZUltcGwodHJlZUlEKSB7CiAgJEZ1bmN0aW9uLmNhbGwoQXV0b21hdGlvbk5vZGVJbXBsLCB0aGlzLCB0aGlzKTsKICB0aGlzLnRyZWVJRCA9IHRyZWVJRDsKICB0aGlzLmF4Tm9kZURhdGFDYWNoZV8gPSB7X19wcm90b19fOiBudWxsfTsKICB0aGlzLmFjdGlvblJlcXVlc3RJRFRvQ2FsbGJhY2tfID0ge19fcHJvdG9fXzogbnVsbH07Cn0KCnV0aWxzLmRlZmluZVByb3BlcnR5KEF1dG9tYXRpb25Sb290Tm9kZUltcGwsICdpZFRvQXV0b21hdGlvblJvb3ROb2RlXycsCiAgICB7X19wcm90b19fOiBudWxsfSk7Cgp1dGlscy5kZWZpbmVQcm9wZXJ0eShBdXRvbWF0aW9uUm9vdE5vZGVJbXBsLCAnZ2V0JywgZnVuY3Rpb24odHJlZUlEKSB7CiAgdmFyIHJlc3VsdCA9IEF1dG9tYXRpb25Sb290Tm9kZUltcGwuaWRUb0F1dG9tYXRpb25Sb290Tm9kZV9bdHJlZUlEXTsKICByZXR1cm4gcmVzdWx0IHx8IHVuZGVmaW5lZDsKfSk7Cgp1dGlscy5kZWZpbmVQcm9wZXJ0eShBdXRvbWF0aW9uUm9vdE5vZGVJbXBsLCAnZ2V0T3JDcmVhdGUnLCBmdW5jdGlvbih0cmVlSUQpIHsKICBpZiAoQXV0b21hdGlvblJvb3ROb2RlSW1wbC5pZFRvQXV0b21hdGlvblJvb3ROb2RlX1t0cmVlSURdKQogICAgcmV0dXJuIEF1dG9tYXRpb25Sb290Tm9kZUltcGwuaWRUb0F1dG9tYXRpb25Sb290Tm9kZV9bdHJlZUlEXTsKICB2YXIgcmVzdWx0ID0gbmV3IEF1dG9tYXRpb25Sb290Tm9kZSh0cmVlSUQpOwogIEF1dG9tYXRpb25Sb290Tm9kZUltcGwuaWRUb0F1dG9tYXRpb25Sb290Tm9kZV9bdHJlZUlEXSA9IHJlc3VsdDsKICByZXR1cm4gcmVzdWx0Owp9KTsKCnV0aWxzLmRlZmluZVByb3BlcnR5KEF1dG9tYXRpb25Sb290Tm9kZUltcGwsICdkZXN0cm95JywgZnVuY3Rpb24odHJlZUlEKSB7CiAgZGVsZXRlIEF1dG9tYXRpb25Sb290Tm9kZUltcGwuaWRUb0F1dG9tYXRpb25Sb290Tm9kZV9bdHJlZUlEXTsKfSk7CgpBdXRvbWF0aW9uUm9vdE5vZGVJbXBsLnByb3RvdHlwZSA9IHsKICBfX3Byb3RvX186IEF1dG9tYXRpb25Ob2RlSW1wbC5wcm90b3R5cGUsCgogIC8qKgogICAqIEB0eXBlIHtib29sZWFufQogICAqLwogIGlzUm9vdE5vZGU6IHRydWUsCgogIC8qKgogICAqIEB0eXBlIHtudW1iZXJ9CiAgICovCiAgdHJlZUlEOiAtMSwKCiAgLyoqCiAgICogVGhlIHBhcmVudCBvZiB0aGlzIG5vZGUgZnJvbSBhIGRpZmZlcmVudCB0cmVlLgogICAqIEB0eXBlIHs/QXV0b21hdGlvbk5vZGV9CiAgICogQHByaXZhdGUKICAgKi8KICBob3N0Tm9kZV86IG51bGwsCgogIC8qKgogICAqIEEgbWFwIGZyb20gaWQgdG8gQXV0b21hdGlvbk5vZGUuCiAgICogQHR5cGUge09iamVjdC48bnVtYmVyLCBBdXRvbWF0aW9uTm9kZT59CiAgICogQHByaXZhdGUKICAgKi8KICBheE5vZGVEYXRhQ2FjaGVfOiBudWxsLAoKICBhY3Rpb25SZXF1ZXN0Q291bnRlcl86IDAsCgogIGFjdGlvblJlcXVlc3RJRFRvQ2FsbGJhY2tfOiBudWxsLAoKICBnZXQgaWQoKSB7CiAgICB2YXIgcmVzdWx0ID0gR2V0Um9vdElEKHRoaXMudHJlZUlEKTsKCiAgICAvLyBEb24ndCByZXR1cm4gdW5kZWZpbmVkLCBiZWNhdXNlIHRoZSBpZCBpcyBvZnRlbiBwYXNzZWQgZGlyZWN0bHkKICAgIC8vIGFzIGFuIGFyZ3VtZW50IHRvIGEgbmF0aXZlIGJpbmRpbmcgdGhhdCBleHBlY3RzIG9ubHkgYSB2YWxpZCBudW1iZXIuCiAgICBpZiAocmVzdWx0ID09PSB1bmRlZmluZWQpCiAgICAgIHJldHVybiAtMTsKCiAgICByZXR1cm4gcmVzdWx0OwogIH0sCgogIGdldCBjaHJvbWVDaGFubmVsKCkgewogICAgcmV0dXJuIEdldFN0cmluZ0F0dHJpYnV0ZSh0aGlzLnRyZWVJRCwgdGhpcy5pZCwgJ2Nocm9tZUNoYW5uZWwnKTsKICB9LAoKICBnZXQgZG9jVXJsKCkgewogICAgcmV0dXJuIEdldERvY1VSTCh0aGlzLnRyZWVJRCk7CiAgfSwKCiAgZ2V0IGRvY1RpdGxlKCkgewogICAgcmV0dXJuIEdldERvY1RpdGxlKHRoaXMudHJlZUlEKTsKICB9LAoKICBnZXQgZG9jTG9hZGVkKCkgewogICAgcmV0dXJuIEdldERvY0xvYWRlZCh0aGlzLnRyZWVJRCk7CiAgfSwKCiAgZ2V0IGRvY0xvYWRpbmdQcm9ncmVzcygpIHsKICAgIHJldHVybiBHZXREb2NMb2FkaW5nUHJvZ3Jlc3ModGhpcy50cmVlSUQpOwogIH0sCgogIGdldCBhbmNob3JPYmplY3QoKSB7CiAgICB2YXIgaWQgPSBHZXRBbmNob3JPYmplY3RJRCh0aGlzLnRyZWVJRCk7CiAgICBpZiAoaWQgJiYgaWQgIT0gLTEpCiAgICAgIHJldHVybiB0aGlzLmdldChpZCk7CiAgICBlbHNlCiAgICAgIHJldHVybiB1bmRlZmluZWQ7CiAgfSwKCiAgZ2V0IGFuY2hvck9mZnNldCgpIHsKICAgIHZhciBpZCA9IEdldEFuY2hvck9iamVjdElEKHRoaXMudHJlZUlEKTsKICAgIGlmIChpZCAmJiBpZCAhPSAtMSkKICAgICAgcmV0dXJuIEdldEFuY2hvck9mZnNldCh0aGlzLnRyZWVJRCk7CiAgfSwKCiAgZ2V0IGFuY2hvckFmZmluaXR5KCkgewogICAgdmFyIGlkID0gR2V0QW5jaG9yT2JqZWN0SUQodGhpcy50cmVlSUQpOwogICAgaWYgKGlkICYmIGlkICE9IC0xKQogICAgICByZXR1cm4gR2V0QW5jaG9yQWZmaW5pdHkodGhpcy50cmVlSUQpOwogIH0sCgogIGdldCBmb2N1c09iamVjdCgpIHsKICAgIHZhciBpZCA9IEdldEZvY3VzT2JqZWN0SUQodGhpcy50cmVlSUQpOwogICAgaWYgKGlkICYmIGlkICE9IC0xKQogICAgICByZXR1cm4gdGhpcy5nZXQoaWQpOwogICAgZWxzZQogICAgICByZXR1cm4gdW5kZWZpbmVkOwogIH0sCgogIGdldCBmb2N1c09mZnNldCgpIHsKICAgIHZhciBpZCA9IEdldEZvY3VzT2JqZWN0SUQodGhpcy50cmVlSUQpOwogICAgaWYgKGlkICYmIGlkICE9IC0xKQogICAgICByZXR1cm4gR2V0Rm9jdXNPZmZzZXQodGhpcy50cmVlSUQpOwogIH0sCgogIGdldCBmb2N1c0FmZmluaXR5KCkgewogICAgdmFyIGlkID0gR2V0Rm9jdXNPYmplY3RJRCh0aGlzLnRyZWVJRCk7CiAgICBpZiAoaWQgJiYgaWQgIT0gLTEpCiAgICAgIHJldHVybiBHZXRGb2N1c0FmZmluaXR5KHRoaXMudHJlZUlEKTsKICB9LAoKICBnZXQ6IGZ1bmN0aW9uKGlkKSB7CiAgICBpZiAoaWQgPT0gdW5kZWZpbmVkKQogICAgICByZXR1cm4gdW5kZWZpbmVkOwoKICAgIGlmIChpZCA9PSB0aGlzLmlkKQogICAgICByZXR1cm4gdGhpcy53cmFwcGVyOwoKICAgIHZhciBvYmogPSB0aGlzLmF4Tm9kZURhdGFDYWNoZV9baWRdOwogICAgaWYgKG9iaikKICAgICAgcmV0dXJuIG9iajsKCiAgICBvYmogPSBuZXcgQXV0b21hdGlvbk5vZGUodGhpcyk7CiAgICBwcml2YXRlcyhvYmopLmltcGwudHJlZUlEID0gdGhpcy50cmVlSUQ7CiAgICBwcml2YXRlcyhvYmopLmltcGwuaWQgPSBpZDsKICAgIHRoaXMuYXhOb2RlRGF0YUNhY2hlX1tpZF0gPSBvYmo7CgogICAgcmV0dXJuIG9iajsKICB9LAoKICByZW1vdmU6IGZ1bmN0aW9uKGlkKSB7CiAgICBpZiAodGhpcy5heE5vZGVEYXRhQ2FjaGVfW2lkXSkKICAgICAgcHJpdmF0ZXModGhpcy5heE5vZGVEYXRhQ2FjaGVfW2lkXSkuaW1wbC5kZXRhY2goKTsKICAgIGRlbGV0ZSB0aGlzLmF4Tm9kZURhdGFDYWNoZV9baWRdOwogIH0sCgogIGRlc3Ryb3k6IGZ1bmN0aW9uKCkgewogICAgdGhpcy5kaXNwYXRjaEV2ZW50KCdkZXN0cm95ZWQnLCAnbm9uZScpOwogICAgZm9yICh2YXIgaWQgaW4gdGhpcy5heE5vZGVEYXRhQ2FjaGVfKQogICAgICB0aGlzLnJlbW92ZShpZCk7CiAgICB0aGlzLmRldGFjaCgpOwogIH0sCgogIHNldEhvc3ROb2RlKGhvc3ROb2RlKSB7CiAgICB0aGlzLmhvc3ROb2RlXyA9IGhvc3ROb2RlOwogIH0sCgogIG9uQWNjZXNzaWJpbGl0eUV2ZW50OiBmdW5jdGlvbihldmVudFBhcmFtcykgewogICAgdmFyIHRhcmdldE5vZGUgPSB0aGlzLmdldChldmVudFBhcmFtcy50YXJnZXRJRCk7CiAgICBpZiAodGFyZ2V0Tm9kZSkgewogICAgICB2YXIgdGFyZ2V0Tm9kZUltcGwgPSBwcml2YXRlcyh0YXJnZXROb2RlKS5pbXBsOwogICAgICB0YXJnZXROb2RlSW1wbC5kaXNwYXRjaEV2ZW50KAogICAgICAgICAgZXZlbnRQYXJhbXMuZXZlbnRUeXBlLCBldmVudFBhcmFtcy5ldmVudEZyb20sCiAgICAgICAgICBldmVudFBhcmFtcy5tb3VzZVgsIGV2ZW50UGFyYW1zLm1vdXNlWSk7CgogICAgICBpZiAoZXZlbnRQYXJhbXMuYWN0aW9uUmVxdWVzdElEICE9IC0xKSB7CiAgICAgICAgdGhpcy5vbkFjdGlvblJlc3VsdChldmVudFBhcmFtcy5hY3Rpb25SZXF1ZXN0SUQsIHRhcmdldE5vZGUpOwogICAgICB9CiAgICB9IGVsc2UgewogICAgICBsb2dnaW5nLldBUk5JTkcoJ0dvdCAnICsgZXZlbnRQYXJhbXMuZXZlbnRUeXBlICsKICAgICAgICAgICAgICAgICAgICAgICcgZXZlbnQgb24gdW5rbm93biBub2RlOiAnICsgZXZlbnRQYXJhbXMudGFyZ2V0SUQgKwogICAgICAgICAgICAgICAgICAgICAgJzsgdGhpczogJyArIHRoaXMuaWQpOwogICAgfQogICAgcmV0dXJuIHRydWU7CiAgfSwKCiAgYWRkQWN0aW9uUmVzdWx0Q2FsbGJhY2s6IGZ1bmN0aW9uKGNhbGxiYWNrKSB7CiAgICB0aGlzLmFjdGlvblJlcXVlc3RJRFRvQ2FsbGJhY2tfWysrdGhpcy5hY3Rpb25SZXF1ZXN0Q291bnRlcl9dID0gY2FsbGJhY2s7CiAgICByZXR1cm4gdGhpcy5hY3Rpb25SZXF1ZXN0Q291bnRlcl87CiAgfSwKCiAgb25BY3Rpb25SZXN1bHQ6IGZ1bmN0aW9uKHJlcXVlc3RJRCwgcmVzdWx0KSB7CiAgICBpZiAocmVxdWVzdElEIGluIHRoaXMuYWN0aW9uUmVxdWVzdElEVG9DYWxsYmFja18pIHsKICAgICAgdGhpcy5hY3Rpb25SZXF1ZXN0SURUb0NhbGxiYWNrX1tyZXF1ZXN0SURdKHJlc3VsdCk7CiAgICAgIGRlbGV0ZSB0aGlzLmFjdGlvblJlcXVlc3RJRFRvQ2FsbGJhY2tfW3JlcXVlc3RJRF07CiAgICB9CiAgfSwKCiAgdG9TdHJpbmc6IGZ1bmN0aW9uKCkgewogICAgZnVuY3Rpb24gdG9TdHJpbmdJbnRlcm5hbChub2RlSW1wbCwgaW5kZW50KSB7CiAgICAgIGlmICghbm9kZUltcGwpCiAgICAgICAgcmV0dXJuICcnOwogICAgICB2YXIgb3V0cHV0ID0gJyc7CiAgICAgIGlmIChub2RlSW1wbC5pc1Jvb3ROb2RlKQogICAgICAgIG91dHB1dCArPSBpbmRlbnQgKyAndHJlZSBpZD0nICsgbm9kZUltcGwudHJlZUlEICsgJ1xuJzsKICAgICAgb3V0cHV0ICs9IGluZGVudCArCiAgICAgICAgJEZ1bmN0aW9uLmNhbGwoQXV0b21hdGlvbk5vZGVJbXBsLnByb3RvdHlwZS50b1N0cmluZywgbm9kZUltcGwpICsgJ1xuJzsKICAgICAgaW5kZW50ICs9ICcgICc7CiAgICAgIHZhciBjaGlsZHJlbiA9IG5vZGVJbXBsLmNoaWxkcmVuOwogICAgICBmb3IgKHZhciBpID0gMDsgaSA8IGNoaWxkcmVuLmxlbmd0aDsgKytpKQogICAgICAgIG91dHB1dCArPSB0b1N0cmluZ0ludGVybmFsKHByaXZhdGVzKGNoaWxkcmVuW2ldKS5pbXBsLCBpbmRlbnQpOwogICAgICByZXR1cm4gb3V0cHV0OwogICAgfQogICAgcmV0dXJuIHRvU3RyaW5nSW50ZXJuYWwodGhpcywgJycpOwogIH0sCn07CgpmdW5jdGlvbiBBdXRvbWF0aW9uTm9kZSgpIHsKICBwcml2YXRlcyhBdXRvbWF0aW9uTm9kZSkuY29uc3RydWN0UHJpdmF0ZSh0aGlzLCBhcmd1bWVudHMpOwp9CnV0aWxzLmV4cG9zZShBdXRvbWF0aW9uTm9kZSwgQXV0b21hdGlvbk5vZGVJbXBsLCB7CiAgZnVuY3Rpb25zOiBbCiAgICAnZG9EZWZhdWx0JywKICAgICdmaW5kJywKICAgICdmaW5kQWxsJywKICAgICdmb2N1cycsCiAgICAnZ2V0SW1hZ2VEYXRhJywKICAgICdoaXRUZXN0JywKICAgICdoaXRUZXN0V2l0aFJlcGx5JywKICAgICdtYWtlVmlzaWJsZScsCiAgICAnbWF0Y2hlcycsCiAgICAncGVyZm9ybUN1c3RvbUFjdGlvbicsCiAgICAncmVzdW1lTWVkaWEnLAogICAgJ3Njcm9sbEJhY2t3YXJkJywKICAgICdzY3JvbGxGb3J3YXJkJywKICAgICdzY3JvbGxVcCcsCiAgICAnc2Nyb2xsRG93bicsCiAgICAnc2Nyb2xsTGVmdCcsCiAgICAnc2Nyb2xsUmlnaHQnLAogICAgJ3NldFNlbGVjdGlvbicsCiAgICAnc2V0U2VxdWVudGlhbEZvY3VzTmF2aWdhdGlvblN0YXJ0aW5nUG9pbnQnLAogICAgJ3Nob3dDb250ZXh0TWVudScsCiAgICAnc3RhcnREdWNraW5nTWVkaWEnLAogICAgJ3N0b3BEdWNraW5nTWVkaWEnLAogICAgJ3N1c3BlbmRNZWRpYScsCiAgICAnYWRkRXZlbnRMaXN0ZW5lcicsCiAgICAncmVtb3ZlRXZlbnRMaXN0ZW5lcicsCiAgICAnZG9tUXVlcnlTZWxlY3RvcicsCiAgICAndG9TdHJpbmcnLAogICAgJ2JvdW5kc0ZvclJhbmdlJywKICBdLAogIHJlYWRvbmx5OiAkQXJyYXkuY29uY2F0KHB1YmxpY0F0dHJpYnV0ZXMsIFsKICAgICAgJ3BhcmVudCcsCiAgICAgICdmaXJzdENoaWxkJywKICAgICAgJ2xhc3RDaGlsZCcsCiAgICAgICdjaGlsZHJlbicsCiAgICAgICdwcmV2aW91c1NpYmxpbmcnLAogICAgICAnbmV4dFNpYmxpbmcnLAogICAgICAnaXNSb290Tm9kZScsCiAgICAgICdyb2xlJywKICAgICAgJ2NoZWNrZWQnLAogICAgICAncmVzdHJpY3Rpb24nLAogICAgICAnc3RhdGUnLAogICAgICAnbG9jYXRpb24nLAogICAgICAnaW5kZXhJblBhcmVudCcsCiAgICAgICdsaW5lU3RhcnRPZmZzZXRzJywKICAgICAgJ3Jvb3QnLAogICAgICAnaHRtbEF0dHJpYnV0ZXMnLAogICAgICAnbmFtZUZyb20nLAogICAgICAnYm9sZCcsCiAgICAgICdpdGFsaWMnLAogICAgICAndW5kZXJsaW5lJywKICAgICAgJ2xpbmVUaHJvdWdoJywKICAgICAgJ2N1c3RvbUFjdGlvbnMnLAogICAgICAndW5jbGlwcGVkTG9jYXRpb24nLAogIF0pLAp9KTsKCmZ1bmN0aW9uIEF1dG9tYXRpb25Sb290Tm9kZSgpIHsKICBwcml2YXRlcyhBdXRvbWF0aW9uUm9vdE5vZGUpLmNvbnN0cnVjdFByaXZhdGUodGhpcywgYXJndW1lbnRzKTsKfQp1dGlscy5leHBvc2UoQXV0b21hdGlvblJvb3ROb2RlLCBBdXRvbWF0aW9uUm9vdE5vZGVJbXBsLCB7CiAgc3VwZXJjbGFzczogQXV0b21hdGlvbk5vZGUsCiAgcmVhZG9ubHk6IFsKICAgICdjaHJvbWVDaGFubmVsJywKICAgICdkb2NUaXRsZScsCiAgICAnZG9jVXJsJywKICAgICdkb2NMb2FkZWQnLAogICAgJ2RvY0xvYWRpbmdQcm9ncmVzcycsCiAgICAnYW5jaG9yT2JqZWN0JywKICAgICdhbmNob3JPZmZzZXQnLAogICAgJ2FuY2hvckFmZmluaXR5JywKICAgICdmb2N1c09iamVjdCcsCiAgICAnZm9jdXNPZmZzZXQnLAogICAgJ2ZvY3VzQWZmaW5pdHknLAogIF0sCn0pOwoKdXRpbHMuZGVmaW5lUHJvcGVydHkoQXV0b21hdGlvblJvb3ROb2RlLCAnZ2V0JywgZnVuY3Rpb24odHJlZUlEKSB7CiAgcmV0dXJuIEF1dG9tYXRpb25Sb290Tm9kZUltcGwuZ2V0KHRyZWVJRCk7Cn0pOwoKdXRpbHMuZGVmaW5lUHJvcGVydHkoQXV0b21hdGlvblJvb3ROb2RlLCAnZ2V0T3JDcmVhdGUnLCBmdW5jdGlvbih0cmVlSUQpIHsKICByZXR1cm4gQXV0b21hdGlvblJvb3ROb2RlSW1wbC5nZXRPckNyZWF0ZSh0cmVlSUQpOwp9KTsKCnV0aWxzLmRlZmluZVByb3BlcnR5KEF1dG9tYXRpb25Sb290Tm9kZSwgJ2Rlc3Ryb3knLCBmdW5jdGlvbih0cmVlSUQpIHsKICBBdXRvbWF0aW9uUm9vdE5vZGVJbXBsLmRlc3Ryb3kodHJlZUlEKTsKfSk7CgpleHBvcnRzLiRzZXQoJ0F1dG9tYXRpb25Ob2RlJywgQXV0b21hdGlvbk5vZGUpOwpleHBvcnRzLiRzZXQoJ0F1dG9tYXRpb25Sb290Tm9kZScsIEF1dG9tYXRpb25Sb290Tm9kZSk7Ci8vIENvcHlyaWdodCAoYykgMjAxMiBUaGUgQ2hyb21pdW0gQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KLy8gVXNlIG9mIHRoaXMgc291cmNlIGNvZGUgaXMgZ292ZXJuZWQgYnkgYSBCU0Qtc3R5bGUgbGljZW5zZSB0aGF0IGNhbiBiZQovLyBmb3VuZCBpbiB0aGUgTElDRU5TRSBmaWxlLgoKLy8gQ3VzdG9tIGJpbmRpbmcgZm9yIHRoZSBicm93c2VyQWN0aW9uIEFQSS4KCnZhciBiaW5kaW5nID0gYXBpQnJpZGdlIHx8IHJlcXVpcmUoJ2JpbmRpbmcnKS5CaW5kaW5nLmNyZWF0ZSgnYnJvd3NlckFjdGlvbicpOwoKdmFyIHNldEljb24gPSByZXF1aXJlKCdzZXRJY29uJykuc2V0SWNvbjsKdmFyIGdldEV4dGVuc2lvblZpZXdzID0gcmVxdWlyZU5hdGl2ZSgncnVudGltZScpLkdldEV4dGVuc2lvblZpZXdzOwp2YXIgc2VuZFJlcXVlc3QgPSBiaW5kaW5nVXRpbCA/CiAgICAkRnVuY3Rpb24uYmluZChiaW5kaW5nVXRpbC5zZW5kUmVxdWVzdCwgYmluZGluZ1V0aWwpIDoKICAgIHJlcXVpcmUoJ3NlbmRSZXF1ZXN0Jykuc2VuZFJlcXVlc3Q7Cgp2YXIganNMYXN0RXJyb3IgPSBiaW5kaW5nVXRpbCA/IHVuZGVmaW5lZCA6IHJlcXVpcmUoJ2xhc3RFcnJvcicpOwpmdW5jdGlvbiBoYXNMYXN0RXJyb3IoKSB7CiAgcmV0dXJuIGJpbmRpbmdVdGlsID8KICAgICAgYmluZGluZ1V0aWwuaGFzTGFzdEVycm9yKCkgOiBqc0xhc3RFcnJvci5oYXNFcnJvcihjaHJvbWUpOwp9CgpiaW5kaW5nLnJlZ2lzdGVyQ3VzdG9tSG9vayhmdW5jdGlvbihiaW5kaW5nc0FQSSkgewogIHZhciBhcGlGdW5jdGlvbnMgPSBiaW5kaW5nc0FQSS5hcGlGdW5jdGlvbnM7CgogIGFwaUZ1bmN0aW9ucy5zZXRIYW5kbGVSZXF1ZXN0KCdzZXRJY29uJywgZnVuY3Rpb24oZGV0YWlscywgY2FsbGJhY2spIHsKICAgIHNldEljb24oZGV0YWlscywgZnVuY3Rpb24oYXJncykgewogICAgICBzZW5kUmVxdWVzdCgnYnJvd3NlckFjdGlvbi5zZXRJY29uJywKICAgICAgICAgICAgICAgICAgW2FyZ3MsIGNhbGxiYWNrXSwKICAgICAgICAgICAgICAgICAgYXBpQnJpZGdlID8gdW5kZWZpbmVkIDogdGhpcy5kZWZpbml0aW9uLnBhcmFtZXRlcnMsCiAgICAgICAgICAgICAgICAgIHVuZGVmaW5lZCk7CiAgICB9LmJpbmQodGhpcykpOwogIH0pOwoKICBhcGlGdW5jdGlvbnMuc2V0Q3VzdG9tQ2FsbGJhY2soJ29wZW5Qb3B1cCcsCiAgICAgIGZ1bmN0aW9uKG5hbWUsIHJlcXVlc3QsIGNhbGxiYWNrLCByZXNwb25zZSkgewogICAgaWYgKCFjYWxsYmFjaykKICAgICAgcmV0dXJuOwoKICAgIGlmIChoYXNMYXN0RXJyb3IoKSkgewogICAgICBjYWxsYmFjaygpOwogICAgfSBlbHNlIHsKICAgICAgdmFyIHZpZXdzID0gZ2V0RXh0ZW5zaW9uVmlld3MoLTEsIC0xLCAnUE9QVVAnKTsKICAgICAgY2FsbGJhY2sodmlld3MubGVuZ3RoID4gMCA/IHZpZXdzWzBdIDogbnVsbCk7CiAgICB9CiAgfSk7Cn0pOwoKaWYgKCFhcGlCcmlkZ2UpCiAgZXhwb3J0cy4kc2V0KCdiaW5kaW5nJywgYmluZGluZy5nZW5lcmF0ZSgpKTsKLy8gQ29weXJpZ2h0IDIwMTMgVGhlIENocm9taXVtIEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCi8vIFVzZSBvZiB0aGlzIHNvdXJjZSBjb2RlIGlzIGdvdmVybmVkIGJ5IGEgQlNELXN0eWxlIGxpY2Vuc2UgdGhhdCBjYW4gYmUKLy8gZm91bmQgaW4gdGhlIExJQ0VOU0UgZmlsZS4KCi8vIEN1c3RvbSBiaW5kaW5nIGZvciB0aGUgQ2FzdCBTdHJlYW1pbmcgUnRwU3RyZWFtIEFQSS4KCnZhciBiaW5kaW5nID0gYXBpQnJpZGdlIHx8CiAgICAgICAgICAgICAgcmVxdWlyZSgnYmluZGluZycpLkJpbmRpbmcuY3JlYXRlKCdjYXN0LnN0cmVhbWluZy5ydHBTdHJlYW0nKTsKdmFyIG5hdGl2ZXMgPSByZXF1aXJlTmF0aXZlKCdjYXN0X3N0cmVhbWluZ19uYXRpdmVzJyk7CgpiaW5kaW5nLnJlZ2lzdGVyQ3VzdG9tSG9vayhmdW5jdGlvbihiaW5kaW5nc0FQSSwgZXh0ZW5zaW9uSWQpIHsKICB2YXIgYXBpRnVuY3Rpb25zID0gYmluZGluZ3NBUEkuYXBpRnVuY3Rpb25zOwoKICBhcGlGdW5jdGlvbnMuc2V0SGFuZGxlUmVxdWVzdCgnZGVzdHJveScsCiAgICAgIGZ1bmN0aW9uKHRyYW5zcG9ydElkKSB7CiAgICAgICAgbmF0aXZlcy5EZXN0cm95Q2FzdFJ0cFN0cmVhbSh0cmFuc3BvcnRJZCk7CiAgfSk7CiAgYXBpRnVuY3Rpb25zLnNldEhhbmRsZVJlcXVlc3QoJ2dldFN1cHBvcnRlZFBhcmFtcycsCiAgICAgIGZ1bmN0aW9uKHRyYW5zcG9ydElkKSB7CiAgICAgICAgcmV0dXJuIG5hdGl2ZXMuR2V0U3VwcG9ydGVkUGFyYW1zQ2FzdFJ0cFN0cmVhbSh0cmFuc3BvcnRJZCk7CiAgfSk7CiAgYXBpRnVuY3Rpb25zLnNldEhhbmRsZVJlcXVlc3QoJ3N0YXJ0JywKICAgICAgZnVuY3Rpb24odHJhbnNwb3J0SWQsIHBhcmFtcykgewogICAgICAgIG5hdGl2ZXMuU3RhcnRDYXN0UnRwU3RyZWFtKHRyYW5zcG9ydElkLCBwYXJhbXMpOwogIH0pOwogIGFwaUZ1bmN0aW9ucy5zZXRIYW5kbGVSZXF1ZXN0KCdzdG9wJywKICAgICAgZnVuY3Rpb24odHJhbnNwb3J0SWQpIHsKICAgICAgICBuYXRpdmVzLlN0b3BDYXN0UnRwU3RyZWFtKHRyYW5zcG9ydElkKTsKICB9KTsKICBhcGlGdW5jdGlvbnMuc2V0SGFuZGxlUmVxdWVzdCgndG9nZ2xlTG9nZ2luZycsCiAgICAgIGZ1bmN0aW9uKHRyYW5zcG9ydElkLCBlbmFibGUpIHsKICAgICAgICBuYXRpdmVzLlRvZ2dsZUxvZ2dpbmcodHJhbnNwb3J0SWQsIGVuYWJsZSk7CiAgfSk7CiAgYXBpRnVuY3Rpb25zLnNldEhhbmRsZVJlcXVlc3QoJ2dldFJhd0V2ZW50cycsCiAgICAgIGZ1bmN0aW9uKHRyYW5zcG9ydElkLCBleHRyYURhdGEsIGNhbGxiYWNrKSB7CiAgICAgICAgbmF0aXZlcy5HZXRSYXdFdmVudHModHJhbnNwb3J0SWQsIGV4dHJhRGF0YSwgY2FsbGJhY2spOwogIH0pOwogIGFwaUZ1bmN0aW9ucy5zZXRIYW5kbGVSZXF1ZXN0KCdnZXRTdGF0cycsCiAgICAgIGZ1bmN0aW9uKHRyYW5zcG9ydElkLCBjYWxsYmFjaykgewogICAgICAgIG5hdGl2ZXMuR2V0U3RhdHModHJhbnNwb3J0SWQsIGNhbGxiYWNrKTsKICB9KTsKfSk7CgppZiAoIWFwaUJyaWRnZSkKICBleHBvcnRzLiRzZXQoJ2JpbmRpbmcnLCBiaW5kaW5nLmdlbmVyYXRlKCkpOwovLyBDb3B5cmlnaHQgMjAxMyBUaGUgQ2hyb21pdW0gQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KLy8gVXNlIG9mIHRoaXMgc291cmNlIGNvZGUgaXMgZ292ZXJuZWQgYnkgYSBCU0Qtc3R5bGUgbGljZW5zZSB0aGF0IGNhbiBiZQovLyBmb3VuZCBpbiB0aGUgTElDRU5TRSBmaWxlLgoKLy8gQ3VzdG9tIGJpbmRpbmcgZm9yIHRoZSBDYXN0IFN0cmVhbWluZyBTZXNzaW9uIEFQSS4KCnZhciBiaW5kaW5nID0gYXBpQnJpZGdlIHx8CiAgICAgICAgICAgICAgcmVxdWlyZSgnYmluZGluZycpLkJpbmRpbmcuY3JlYXRlKCdjYXN0LnN0cmVhbWluZy5zZXNzaW9uJyk7CnZhciBuYXRpdmVzID0gcmVxdWlyZU5hdGl2ZSgnY2FzdF9zdHJlYW1pbmdfbmF0aXZlcycpOwoKYmluZGluZy5yZWdpc3RlckN1c3RvbUhvb2soZnVuY3Rpb24oYmluZGluZ3NBUEksIGV4dGVuc2lvbklkKSB7CiAgdmFyIGFwaUZ1bmN0aW9ucyA9IGJpbmRpbmdzQVBJLmFwaUZ1bmN0aW9uczsKICBhcGlGdW5jdGlvbnMuc2V0SGFuZGxlUmVxdWVzdCgnY3JlYXRlJywKICAgICAgZnVuY3Rpb24oYXVkaW9UcmFjaywgdmlkZW9UcmFjaywgY2FsbGJhY2spIHsKICAgICAgICBuYXRpdmVzLkNyZWF0ZVNlc3Npb24oYXVkaW9UcmFjaywgdmlkZW9UcmFjaywgY2FsbGJhY2spOwogIH0pOwp9KTsKCmlmICghYXBpQnJpZGdlKQogIGV4cG9ydHMuJHNldCgnYmluZGluZycsIGJpbmRpbmcuZ2VuZXJhdGUoKSk7Ci8vIENvcHlyaWdodCAyMDEzIFRoZSBDaHJvbWl1bSBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgovLyBVc2Ugb2YgdGhpcyBzb3VyY2UgY29kZSBpcyBnb3Zlcm5lZCBieSBhIEJTRC1zdHlsZSBsaWNlbnNlIHRoYXQgY2FuIGJlCi8vIGZvdW5kIGluIHRoZSBMSUNFTlNFIGZpbGUuCgovLyBDdXN0b20gYmluZGluZyBmb3IgdGhlIENhc3QgU3RyZWFtaW5nIFVkcFRyYW5zcG9ydCBBUEkuCgp2YXIgYmluZGluZyA9IGFwaUJyaWRnZSB8fAogICAgICAgICAgICAgIHJlcXVpcmUoJ2JpbmRpbmcnKS5CaW5kaW5nLmNyZWF0ZSgnY2FzdC5zdHJlYW1pbmcudWRwVHJhbnNwb3J0Jyk7CnZhciBuYXRpdmVzID0gcmVxdWlyZU5hdGl2ZSgnY2FzdF9zdHJlYW1pbmdfbmF0aXZlcycpOwoKYmluZGluZy5yZWdpc3RlckN1c3RvbUhvb2soZnVuY3Rpb24oYmluZGluZ3NBUEksIGV4dGVuc2lvbklkKSB7CiAgdmFyIGFwaUZ1bmN0aW9ucyA9IGJpbmRpbmdzQVBJLmFwaUZ1bmN0aW9uczsKCiAgYXBpRnVuY3Rpb25zLnNldEhhbmRsZVJlcXVlc3QoJ2Rlc3Ryb3knLCBmdW5jdGlvbih0cmFuc3BvcnRJZCkgewogICAgbmF0aXZlcy5EZXN0cm95Q2FzdFVkcFRyYW5zcG9ydCh0cmFuc3BvcnRJZCk7CiAgfSk7CiAgYXBpRnVuY3Rpb25zLnNldEhhbmRsZVJlcXVlc3QoJ3NldERlc3RpbmF0aW9uJywKICAgIGZ1bmN0aW9uKHRyYW5zcG9ydElkLCBkZXN0aW5hdGlvbikgewogICAgICBuYXRpdmVzLlNldERlc3RpbmF0aW9uQ2FzdFVkcFRyYW5zcG9ydCh0cmFuc3BvcnRJZCwgZGVzdGluYXRpb24pOwogIH0pOwogIGFwaUZ1bmN0aW9ucy5zZXRIYW5kbGVSZXF1ZXN0KCdzZXRPcHRpb25zJywKICAgIGZ1bmN0aW9uKHRyYW5zcG9ydElkLCBvcHRpb25zKSB7CiAgICAgIG5hdGl2ZXMuU2V0T3B0aW9uc0Nhc3RVZHBUcmFuc3BvcnQodHJhbnNwb3J0SWQsIG9wdGlvbnMpOwogIH0pOwp9KTsKCmlmICghYXBpQnJpZGdlKQogIGV4cG9ydHMuJHNldCgnYmluZGluZycsIGJpbmRpbmcuZ2VuZXJhdGUoKSk7Ci8vIENvcHlyaWdodCAyMDEzIFRoZSBDaHJvbWl1bSBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgovLyBVc2Ugb2YgdGhpcyBzb3VyY2UgY29kZSBpcyBnb3Zlcm5lZCBieSBhIEJTRC1zdHlsZSBsaWNlbnNlIHRoYXQgY2FuIGJlCi8vIGZvdW5kIGluIHRoZSBMSUNFTlNFIGZpbGUuCgovLyBDdXN0b20gYmluZGluZyBmb3IgdGhlIENhc3QgU3RyZWFtaW5nIFNlc3Npb24gQVBJLgoKdmFyIGJpbmRpbmcgPQogICAgYXBpQnJpZGdlIHx8CiAgICByZXF1aXJlKCdiaW5kaW5nJykuQmluZGluZy5jcmVhdGUoJ2Nhc3Quc3RyZWFtaW5nLnJlY2VpdmVyU2Vzc2lvbicpOwp2YXIgbmF0aXZlcyA9IHJlcXVpcmVOYXRpdmUoJ2Nhc3Rfc3RyZWFtaW5nX25hdGl2ZXMnKTsKCmJpbmRpbmcucmVnaXN0ZXJDdXN0b21Ib29rKGZ1bmN0aW9uKGJpbmRpbmdzQVBJLCBleHRlbnNpb25JZCkgewogIHZhciBhcGlGdW5jdGlvbnMgPSBiaW5kaW5nc0FQSS5hcGlGdW5jdGlvbnM7CiAgYXBpRnVuY3Rpb25zLnNldEhhbmRsZVJlcXVlc3QoCiAgICAgICdjcmVhdGVBbmRCaW5kJywKICAgICAgZnVuY3Rpb24oYXAsIHZwLCBsb2NhbCwgd2VpZGd0aCwgaGVpZ2h0LCBmciwgdXJsLCBjYiwgb3ApIHsKICAgICAgICBuYXRpdmVzLlN0YXJ0Q2FzdFJ0cFJlY2VpdmVyKAogICAgICAgICAgICBhcCwgdnAsIGxvY2FsLCB3ZWlkZ3RoLCBoZWlnaHQsIGZyLCB1cmwsIGNiLCBvcCk7CiAgfSk7Cn0pOwoKaWYgKCFhcGlCcmlkZ2UpCiAgZXhwb3J0cy4kc2V0KCdiaW5kaW5nJywgYmluZGluZy5nZW5lcmF0ZSgpKTsKLy8gQ29weXJpZ2h0IChjKSAyMDEyIFRoZSBDaHJvbWl1bSBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgovLyBVc2Ugb2YgdGhpcyBzb3VyY2UgY29kZSBpcyBnb3Zlcm5lZCBieSBhIEJTRC1zdHlsZSBsaWNlbnNlIHRoYXQgY2FuIGJlCi8vIGZvdW5kIGluIHRoZSBMSUNFTlNFIGZpbGUuCgp2YXIgRXZlbnQgPSByZXF1aXJlKCdldmVudF9iaW5kaW5ncycpLkV2ZW50Owp2YXIgc2VuZFJlcXVlc3QgPSByZXF1aXJlKCdzZW5kUmVxdWVzdCcpLnNlbmRSZXF1ZXN0Owp2YXIgdmFsaWRhdGUgPSByZXF1aXJlKCdzY2hlbWFVdGlscycpLnZhbGlkYXRlOwoKZnVuY3Rpb24gZXh0ZW5kU2NoZW1hKHNjaGVtYSkgewogIHZhciBleHRlbmRlZFNjaGVtYSA9ICRBcnJheS5zbGljZShzY2hlbWEpOwogICRBcnJheS51bnNoaWZ0KGV4dGVuZGVkU2NoZW1hLCB7J3R5cGUnOiAnc3RyaW5nJ30pOwogIHJldHVybiBleHRlbmRlZFNjaGVtYTsKfQoKLy8gVE9ETyhkZXZsaW4pOiBNYXliZSBmaW5kIGEgd2F5IHRvIGNvbWJpbmUgdGhpcyBhbmQgQ29udGVudFNldHRpbmcuCmZ1bmN0aW9uIENocm9tZVNldHRpbmcocHJlZktleSwgdmFsdWVTY2hlbWEsIHNjaGVtYSkgewogIHZhciBnZXRGdW5jdGlvblBhcmFtZXRlcnMgPSBmdW5jdGlvbihuYW1lKSB7CiAgICB2YXIgZiA9ICRBcnJheS5maWx0ZXIoCiAgICAgICAgICAgICAgICBzY2hlbWEuZnVuY3Rpb25zLCBmdW5jdGlvbihmKSB7IHJldHVybiBmLm5hbWUgPT09IG5hbWU7IH0pWzBdOwogICAgcmV0dXJuIGYucGFyYW1ldGVyczsKICB9OwogIHRoaXMuZ2V0ID0gZnVuY3Rpb24oZGV0YWlscywgY2FsbGJhY2spIHsKICAgIHZhciBnZXRTY2hlbWEgPSBnZXRGdW5jdGlvblBhcmFtZXRlcnMoJ2dldCcpOwogICAgdmFsaWRhdGUoW2RldGFpbHMsIGNhbGxiYWNrXSwgZ2V0U2NoZW1hKTsKICAgIHJldHVybiBzZW5kUmVxdWVzdCgndHlwZXMuQ2hyb21lU2V0dGluZy5nZXQnLAogICAgICAgICAgICAgICAgICAgICAgIFtwcmVmS2V5LCBkZXRhaWxzLCBjYWxsYmFja10sCiAgICAgICAgICAgICAgICAgICAgICAgZXh0ZW5kU2NoZW1hKGdldFNjaGVtYSkpOwogIH07CiAgdGhpcy5zZXQgPSBmdW5jdGlvbihkZXRhaWxzLCBjYWxsYmFjaykgewogICAgLy8gVGhlIHNldCBzY2hlbWEgaW5jbHVkZWQgaW4gdGhlIFNjaGVtYSBvYmplY3QgaXMgZ2VuZXJpYywgc2luY2UgaXQgdmFyaWVzCiAgICAvLyBwZXItc2V0dGluZy4gSG93ZXZlciwgdGhpcyBpcyBvbmx5IGV2ZXIgZm9yIGEgc2luZ2xlIHNldHRpbmcsIHNvIHdlIGNhbgogICAgLy8gZW5mb3JjZSB0aGUgdHlwZXMgbW9yZSB0aG9yb3VnaGx5LgogICAgdmFyIHJhd1NldFNjaGVtYSA9IGdldEZ1bmN0aW9uUGFyYW1ldGVycygnc2V0Jyk7CiAgICB2YXIgcmF3U2V0dGluZ1BhcmFtID0gcmF3U2V0U2NoZW1hWzBdOwogICAgdmFyIHByb3BzID0gJE9iamVjdC5hc3NpZ24oe30sIHJhd1NldHRpbmdQYXJhbS5wcm9wZXJ0aWVzKTsKICAgIHByb3BzLnZhbHVlID0gdmFsdWVTY2hlbWE7CiAgICB2YXIgbW9kU2V0dGluZ1BhcmFtID0gewogICAgICBuYW1lOiByYXdTZXR0aW5nUGFyYW0ubmFtZSwKICAgICAgdHlwZTogcmF3U2V0dGluZ1BhcmFtLnR5cGUsCiAgICAgIHByb3BlcnRpZXM6IHByb3BzLAogICAgfTsKICAgIHZhciBtb2RTZXRTY2hlbWEgPSAkQXJyYXkuc2xpY2UocmF3U2V0U2NoZW1hKTsKICAgIG1vZFNldFNjaGVtYVswXSA9IG1vZFNldHRpbmdQYXJhbTsKICAgIHZhbGlkYXRlKFtkZXRhaWxzLCBjYWxsYmFja10sIG1vZFNldFNjaGVtYSk7CiAgICByZXR1cm4gc2VuZFJlcXVlc3QoJ3R5cGVzLkNocm9tZVNldHRpbmcuc2V0JywKICAgICAgICAgICAgICAgICAgICAgICBbcHJlZktleSwgZGV0YWlscywgY2FsbGJhY2tdLAogICAgICAgICAgICAgICAgICAgICAgIGV4dGVuZFNjaGVtYShtb2RTZXRTY2hlbWEpKTsKICB9OwogIHRoaXMuY2xlYXIgPSBmdW5jdGlvbihkZXRhaWxzLCBjYWxsYmFjaykgewogICAgdmFyIGNsZWFyU2NoZW1hID0gZ2V0RnVuY3Rpb25QYXJhbWV0ZXJzKCdjbGVhcicpOwogICAgdmFsaWRhdGUoW2RldGFpbHMsIGNhbGxiYWNrXSwgY2xlYXJTY2hlbWEpOwogICAgcmV0dXJuIHNlbmRSZXF1ZXN0KCd0eXBlcy5DaHJvbWVTZXR0aW5nLmNsZWFyJywKICAgICAgICAgICAgICAgICAgICAgICBbcHJlZktleSwgZGV0YWlscywgY2FsbGJhY2tdLAogICAgICAgICAgICAgICAgICAgICAgIGV4dGVuZFNjaGVtYShjbGVhclNjaGVtYSkpOwogIH07CiAgdGhpcy5vbkNoYW5nZSA9IG5ldyBFdmVudCgndHlwZXMuQ2hyb21lU2V0dGluZy4nICsgcHJlZktleSArICcub25DaGFuZ2UnKTsKfTsKCmV4cG9ydHMuJHNldCgnQ2hyb21lU2V0dGluZycsIENocm9tZVNldHRpbmcpOwovLyBDb3B5cmlnaHQgMjAxNCBUaGUgQ2hyb21pdW0gQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KLy8gVXNlIG9mIHRoaXMgc291cmNlIGNvZGUgaXMgZ292ZXJuZWQgYnkgYSBCU0Qtc3R5bGUgbGljZW5zZSB0aGF0IGNhbiBiZQovLyBmb3VuZCBpbiB0aGUgTElDRU5TRSBmaWxlLgoKdmFyIGJpbmRpbmcgPSBhcGlCcmlkZ2UgfHwKICAgICAgICAgICAgICByZXF1aXJlKCdiaW5kaW5nJykuQmluZGluZy5jcmVhdGUoJ2Nocm9tZVdlYlZpZXdJbnRlcm5hbCcpOwp2YXIgY29udGV4dE1lbnVzSGFuZGxlcnMgPSByZXF1aXJlKCdjb250ZXh0TWVudXNIYW5kbGVycycpOwoKYmluZGluZy5yZWdpc3RlckN1c3RvbUhvb2soZnVuY3Rpb24oYmluZGluZ3NBUEkpIHsKICB2YXIgYXBpRnVuY3Rpb25zID0gYmluZGluZ3NBUEkuYXBpRnVuY3Rpb25zOwoKICB2YXIgaGFuZGxlcnMgPSBjb250ZXh0TWVudXNIYW5kbGVycy5jcmVhdGUodHJ1ZSAvKiBpc1dlYnZpZXcgKi8pOwoKICBhcGlGdW5jdGlvbnMuc2V0SGFuZGxlUmVxdWVzdCgKICAgICAgJ2NvbnRleHRNZW51c0NyZWF0ZScsIGhhbmRsZXJzLnJlcXVlc3RIYW5kbGVycy5jcmVhdGUpOwoKICBhcGlGdW5jdGlvbnMuc2V0SGFuZGxlUmVxdWVzdCgKICAgICAgJ2NvbnRleHRNZW51c1VwZGF0ZScsIGhhbmRsZXJzLnJlcXVlc3RIYW5kbGVycy51cGRhdGUpOwoKICBhcGlGdW5jdGlvbnMuc2V0SGFuZGxlUmVxdWVzdCgKICAgICAgJ2NvbnRleHRNZW51c1JlbW92ZScsIGhhbmRsZXJzLnJlcXVlc3RIYW5kbGVycy5yZW1vdmUpOwoKICBhcGlGdW5jdGlvbnMuc2V0SGFuZGxlUmVxdWVzdCgKICAgICAgJ2NvbnRleHRNZW51c1JlbW92ZUFsbCcsIGhhbmRsZXJzLnJlcXVlc3RIYW5kbGVycy5yZW1vdmVBbGwpOwp9KTsKCmlmICghYXBpQnJpZGdlKQogIGV4cG9ydHMuJHNldCgnQ2hyb21lV2ViVmlldycsIGJpbmRpbmcuZ2VuZXJhdGUoKSk7Ci8vIENvcHlyaWdodCAyMDE0IFRoZSBDaHJvbWl1bSBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgovLyBVc2Ugb2YgdGhpcyBzb3VyY2UgY29kZSBpcyBnb3Zlcm5lZCBieSBhIEJTRC1zdHlsZSBsaWNlbnNlIHRoYXQgY2FuIGJlCi8vIGZvdW5kIGluIHRoZSBMSUNFTlNFIGZpbGUuCgovLyBUaGlzIG1vZHVsZSBpbXBsZW1lbnRzIGNocm9tZS1zcGVjaWZpYyA8d2Vidmlldz4gQVBJLgovLyBTZWUgd2ViX3ZpZXdfYXBpX21ldGhvZHMuanMgZm9yIGRldGFpbHMuCgp2YXIgQ2hyb21lV2ViVmlldyA9IGdldEludGVybmFsQXBpID8KICAgIGdldEludGVybmFsQXBpKCdjaHJvbWVXZWJWaWV3SW50ZXJuYWwnKSA6CiAgICByZXF1aXJlKCdjaHJvbWVXZWJWaWV3SW50ZXJuYWwnKS5DaHJvbWVXZWJWaWV3Owp2YXIgQ2hyb21lV2ViVmlld1NjaGVtYSA9CiAgICByZXF1aXJlTmF0aXZlKCdzY2hlbWFfcmVnaXN0cnknKS5HZXRTY2hlbWEoJ2Nocm9tZVdlYlZpZXdJbnRlcm5hbCcpOwp2YXIgQ3JlYXRlRXZlbnQgPSByZXF1aXJlKCdndWVzdFZpZXdFdmVudHMnKS5DcmVhdGVFdmVudDsKdmFyIEd1ZXN0Vmlld0ludGVybmFsTmF0aXZlcyA9IHJlcXVpcmVOYXRpdmUoJ2d1ZXN0X3ZpZXdfaW50ZXJuYWwnKTsKdmFyIGlkR2VuZXJhdG9yTmF0aXZlcyA9IHJlcXVpcmVOYXRpdmUoJ2lkX2dlbmVyYXRvcicpOwp2YXIgdXRpbHMgPSByZXF1aXJlKCd1dGlscycpOwp2YXIgV2ViVmlld0ltcGwgPSByZXF1aXJlKCd3ZWJWaWV3JykuV2ViVmlld0ltcGw7CgovLyBUaGlzIGlzIHRoZSBvbmx5ICJ3ZWJWaWV3SW50ZXJuYWwub25DbGlja2VkIiBuYW1lZCBldmVudCBmb3IgdGhpcyByZW5kZXJlci4KLy8KLy8gU2luY2Ugd2UgbmVlZCBhbiBldmVudCBwZXIgPHdlYnZpZXc+LCB3ZSBkZWZpbmUgZXZlbnRzIHdpdGggc3VmZml4Ci8vIChzdWJFdmVudE5hbWUpIGluIGVhY2ggb2YgdGhlIDx3ZWJ2aWV3Pi4gQmVoaW5kIHRoZSBzY2VuZXMsIHRoaXMgZXZlbnQgaXMKLy8gcmVnaXN0ZXJlZCBhcyBhIENvbnRleHRNZW51c0V2ZW50LCB3aXRoIGZpbHRlciBzZXQgdG8gdGhlIHdlYnZpZXcncwovLyB8dmlld0luc3RhbmNlSWR8LiBBbnkgdGltZSBhIENvbnRleHRNZW51c0V2ZW50IGlzIGRpc3BhdGNoZWQsIHdlIHJlLWRpc3BhdGNoCi8vIGl0IHRvIHRoZSBzdWJFdmVudCdzIGxpc3RlbmVycy4gVGhpcyB3YXkKLy8gPHdlYnZpZXc+LmNvbnRleHRNZW51cy5vbkNsaWNrZWQgYmVoYXZlIGFzIGEgcmVndWxhciBjaHJvbWUgRXZlbnQgdHlwZS4KdmFyIENvbnRleHRNZW51c0V2ZW50ID0gQ3JlYXRlRXZlbnQoJ2Nocm9tZVdlYlZpZXdJbnRlcm5hbC5vbkNsaWNrZWQnKTsKLy8gU2VlIGNvbW1lbnQgYWJvdmUuCnZhciBDb250ZXh0TWVudXNIYW5kbGVyRXZlbnQgPQogICAgQ3JlYXRlRXZlbnQoJ2Nocm9tZVdlYlZpZXdJbnRlcm5hbC5vbkNvbnRleHRNZW51U2hvdycpOwoKdmFyIGpzRXZlbnQ7CmZ1bmN0aW9uIGNyZWF0ZUN1c3RvbUV2ZW50KG5hbWUsIHNjaGVtYSwgb3B0aW9ucywgd2Vidmlld0lkKSB7CiAgaWYgKGJpbmRpbmdVdGlsKQogICAgcmV0dXJuIGJpbmRpbmdVdGlsLmNyZWF0ZUN1c3RvbUV2ZW50KG5hbWUsIHVuZGVmaW5lZCwgZmFsc2UsIGZhbHNlKTsKICBpZiAoIWpzRXZlbnQpCiAgICBqc0V2ZW50ID0gcmVxdWlyZSgnZXZlbnRfYmluZGluZ3MnKS5FdmVudDsKICByZXR1cm4gbmV3IGpzRXZlbnQobmFtZSwgc2NoZW1hLCBvcHRpb25zLCB3ZWJ2aWV3SWQpOwp9CgovLyBUaGlzIGV2ZW50IGlzIGV4cG9zZWQgYXMgPHdlYnZpZXc+LmNvbnRleHRNZW51cy5vbkNsaWNrZWQuCmZ1bmN0aW9uIGNyZWF0ZUNvbnRleHRNZW51c09uQ2xpY2tlZEV2ZW50KHdlYlZpZXdJbnN0YW5jZUlkLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBvcHRfZXZlbnROYW1lLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBvcHRfYXJnU2NoZW1hcywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgb3B0X2V2ZW50T3B0aW9ucykgewogIHZhciBzdWJFdmVudE5hbWUgPSBHZXRVbmlxdWVTdWJFdmVudE5hbWUob3B0X2V2ZW50TmFtZSk7CiAgdmFyIG5ld0V2ZW50ID0gY3JlYXRlQ3VzdG9tRXZlbnQoc3ViRXZlbnROYW1lLCBvcHRfYXJnU2NoZW1hcywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBvcHRfZXZlbnRPcHRpb25zLCB3ZWJWaWV3SW5zdGFuY2VJZCk7CgogIHZhciB2aWV3ID0gR3Vlc3RWaWV3SW50ZXJuYWxOYXRpdmVzLkdldFZpZXdGcm9tSUQod2ViVmlld0luc3RhbmNlSWQpOwogIGlmICh2aWV3KSB7CiAgICB2aWV3LmV2ZW50cy5hZGRTY29wZWRMaXN0ZW5lcigKICAgICAgICBDb250ZXh0TWVudXNFdmVudCwKICAgICAgICAkRnVuY3Rpb24uYmluZChmdW5jdGlvbigpIHsKICAgICAgICAgIC8vIFJlLWRpc3BhdGNoIHRvIHN1YkV2ZW50J3MgbGlzdGVuZXJzLgogICAgICAgICAgJEZ1bmN0aW9uLmFwcGx5KG5ld0V2ZW50LmRpc3BhdGNoLCBuZXdFdmVudCwgJEFycmF5LnNsaWNlKGFyZ3VtZW50cykpOwogICAgICAgIH0sIG5ld0V2ZW50KSwKICAgICAgICB7aW5zdGFuY2VJZDogd2ViVmlld0luc3RhbmNlSWR9KTsKICB9CiAgcmV0dXJuIG5ld0V2ZW50Owp9CgovLyBUaGlzIGV2ZW50IGlzIGV4cG9zZWQgYXMgPHdlYnZpZXc+LmNvbnRleHRNZW51cy5vblNob3cuCmZ1bmN0aW9uIGNyZWF0ZUNvbnRleHRNZW51c09uQ29udGV4dE1lbnVFdmVudCh3ZWJWaWV3SW5zdGFuY2VJZCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIG9wdF9ldmVudE5hbWUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBvcHRfYXJnU2NoZW1hcywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIG9wdF9ldmVudE9wdGlvbnMpIHsKICB2YXIgc3ViRXZlbnROYW1lID0gR2V0VW5pcXVlU3ViRXZlbnROYW1lKG9wdF9ldmVudE5hbWUpOwogIHZhciBuZXdFdmVudCA9IGNyZWF0ZUN1c3RvbUV2ZW50KHN1YkV2ZW50TmFtZSwgb3B0X2FyZ1NjaGVtYXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgb3B0X2V2ZW50T3B0aW9ucywgd2ViVmlld0luc3RhbmNlSWQpOwoKICB2YXIgdmlldyA9IEd1ZXN0Vmlld0ludGVybmFsTmF0aXZlcy5HZXRWaWV3RnJvbUlEKHdlYlZpZXdJbnN0YW5jZUlkKTsKICBpZiAodmlldykgewogICAgdmlldy5ldmVudHMuYWRkU2NvcGVkTGlzdGVuZXIoCiAgICAgICAgQ29udGV4dE1lbnVzSGFuZGxlckV2ZW50LAogICAgICAgICRGdW5jdGlvbi5iaW5kKGZ1bmN0aW9uKGUpIHsKICAgICAgICAgIHZhciBkZWZhdWx0UHJldmVudGVkID0gZmFsc2U7CiAgICAgICAgICB2YXIgZXZlbnQgPSB7CiAgICAgICAgICAgIHByZXZlbnREZWZhdWx0OiBmdW5jdGlvbigpIHsgZGVmYXVsdFByZXZlbnRlZCA9IHRydWU7IH0KICAgICAgICAgIH07CgogICAgICAgICAgLy8gUmUtZGlzcGF0Y2ggdG8gc3ViRXZlbnQncyBsaXN0ZW5lcnMuCiAgICAgICAgICAkRnVuY3Rpb24uYXBwbHkobmV3RXZlbnQuZGlzcGF0Y2gsIG5ld0V2ZW50LCBbZXZlbnRdKTsKCiAgICAgICAgICBpZiAoIWRlZmF1bHRQcmV2ZW50ZWQpIHsKICAgICAgICAgIC8vIFRPRE8obGF6eWJveSk6IFJlbW92ZSB8aXRlbXN8IHBhcmFtZXRlciBjb21wbGV0ZWx5IGZyb20KICAgICAgICAgIC8vIENocm9tZVdlYlZpZXcuc2hvd0NvbnRleHRNZW51IGFzIHdlIGRvbid0IGRvIGFueXRoaW5nIHVzZWZ1bCB3aXRoCiAgICAgICAgICAvLyBpdCBjdXJyZW50bHkuCiAgICAgICAgICB2YXIgaXRlbXMgPSBbXTsKICAgICAgICAgIHZhciBndWVzdEluc3RhbmNlSWQgPSBHdWVzdFZpZXdJbnRlcm5hbE5hdGl2ZXMuCiAgICAgICAgICAgICAgR2V0Vmlld0Zyb21JRCh3ZWJWaWV3SW5zdGFuY2VJZCkuZ3Vlc3QuZ2V0SWQoKTsKICAgICAgICAgIENocm9tZVdlYlZpZXcuc2hvd0NvbnRleHRNZW51KGd1ZXN0SW5zdGFuY2VJZCwgZS5yZXF1ZXN0SWQsIGl0ZW1zKTsKICAgICAgICB9CiAgICAgIH0sIG5ld0V2ZW50KSwKICAgICAge2luc3RhbmNlSWQ6IHdlYlZpZXdJbnN0YW5jZUlkfSk7CiAgfQoKICByZXR1cm4gbmV3RXZlbnQ7Cn0KCi8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCi8vIFdlYlZpZXdDb250ZXh0TWVudXNJbXBsIG9iamVjdC4KCi8vIEFuIGluc3RhbmNlIG9mIHRoaXMgY2xhc3MgaXMgZXhwb3NlZCBhcyA8d2Vidmlldz4uY29udGV4dE1lbnVzLgpmdW5jdGlvbiBXZWJWaWV3Q29udGV4dE1lbnVzSW1wbCh2aWV3SW5zdGFuY2VJZCkgewogIHRoaXMudmlld0luc3RhbmNlSWRfID0gdmlld0luc3RhbmNlSWQ7Cn0KJE9iamVjdC5zZXRQcm90b3R5cGVPZihXZWJWaWV3Q29udGV4dE1lbnVzSW1wbC5wcm90b3R5cGUsIG51bGwpOwoKV2ViVmlld0NvbnRleHRNZW51c0ltcGwucHJvdG90eXBlLmNyZWF0ZSA9IGZ1bmN0aW9uKCkgewogIHZhciBhcmdzID0gJEFycmF5LmNvbmNhdChbdGhpcy52aWV3SW5zdGFuY2VJZF9dLCAkQXJyYXkuc2xpY2UoYXJndW1lbnRzKSk7CiAgcmV0dXJuICRGdW5jdGlvbi5hcHBseShDaHJvbWVXZWJWaWV3LmNvbnRleHRNZW51c0NyZWF0ZSwgbnVsbCwgYXJncyk7Cn07CgpXZWJWaWV3Q29udGV4dE1lbnVzSW1wbC5wcm90b3R5cGUucmVtb3ZlID0gZnVuY3Rpb24oKSB7CiAgdmFyIGFyZ3MgPSAkQXJyYXkuY29uY2F0KFt0aGlzLnZpZXdJbnN0YW5jZUlkX10sICRBcnJheS5zbGljZShhcmd1bWVudHMpKTsKICByZXR1cm4gJEZ1bmN0aW9uLmFwcGx5KENocm9tZVdlYlZpZXcuY29udGV4dE1lbnVzUmVtb3ZlLCBudWxsLCBhcmdzKTsKfTsKCldlYlZpZXdDb250ZXh0TWVudXNJbXBsLnByb3RvdHlwZS5yZW1vdmVBbGwgPSBmdW5jdGlvbigpIHsKICB2YXIgYXJncyA9ICRBcnJheS5jb25jYXQoW3RoaXMudmlld0luc3RhbmNlSWRfXSwgJEFycmF5LnNsaWNlKGFyZ3VtZW50cykpOwogIHJldHVybiAkRnVuY3Rpb24uYXBwbHkoQ2hyb21lV2ViVmlldy5jb250ZXh0TWVudXNSZW1vdmVBbGwsIG51bGwsIGFyZ3MpOwp9OwoKV2ViVmlld0NvbnRleHRNZW51c0ltcGwucHJvdG90eXBlLnVwZGF0ZSA9IGZ1bmN0aW9uKCkgewogIHZhciBhcmdzID0gJEFycmF5LmNvbmNhdChbdGhpcy52aWV3SW5zdGFuY2VJZF9dLCAkQXJyYXkuc2xpY2UoYXJndW1lbnRzKSk7CiAgcmV0dXJuICRGdW5jdGlvbi5hcHBseShDaHJvbWVXZWJWaWV3LmNvbnRleHRNZW51c1VwZGF0ZSwgbnVsbCwgYXJncyk7Cn07CgpmdW5jdGlvbiBXZWJWaWV3Q29udGV4dE1lbnVzKCkgewogIHByaXZhdGVzKFdlYlZpZXdDb250ZXh0TWVudXMpLmNvbnN0cnVjdFByaXZhdGUodGhpcywgYXJndW1lbnRzKTsKfQp1dGlscy5leHBvc2UoV2ViVmlld0NvbnRleHRNZW51cywgV2ViVmlld0NvbnRleHRNZW51c0ltcGwsIHsKICBmdW5jdGlvbnM6IFsKICAgICdjcmVhdGUnLAogICAgJ3JlbW92ZScsCiAgICAncmVtb3ZlQWxsJywKICAgICd1cGRhdGUnLAogIF0sCn0pOwoKLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KCldlYlZpZXdJbXBsLnByb3RvdHlwZS5tYXliZVNldHVwQ29udGV4dE1lbnVzID0gZnVuY3Rpb24oKSB7CiAgaWYgKCF0aGlzLmNvbnRleHRNZW51c09uQ29udGV4dE1lbnVFdmVudF8pIHsKICAgIHZhciBldmVudE5hbWUgPSAnY2hyb21lV2ViVmlld0ludGVybmFsLm9uQ29udGV4dE1lbnVTaG93JzsKICAgIHZhciBldmVudFNjaGVtYSA9CiAgICAgICAgdXRpbHMubG9va3VwKENocm9tZVdlYlZpZXdTY2hlbWEuZXZlbnRzLCAnbmFtZScsICdvblNob3cnKTsKICAgIHZhciBldmVudE9wdGlvbnMgPSB7c3VwcG9ydHNMaXN0ZW5lcnM6IHRydWUsIHN1cHBvcnRzTGF6eUxpc3RlbmVyczogZmFsc2V9OwogICAgdGhpcy5jb250ZXh0TWVudXNPbkNvbnRleHRNZW51RXZlbnRfID0gY3JlYXRlQ29udGV4dE1lbnVzT25Db250ZXh0TWVudUV2ZW50KAogICAgICAgIHRoaXMudmlld0luc3RhbmNlSWQsIGV2ZW50TmFtZSwgZXZlbnRTY2hlbWEsIGV2ZW50T3B0aW9ucyk7CiAgfQoKICB2YXIgY3JlYXRlQ29udGV4dE1lbnVzID0gJEZ1bmN0aW9uLmJpbmQoZnVuY3Rpb24oKSB7CiAgICByZXR1cm4gdGhpcy53ZWFrV3JhcHBlcihmdW5jdGlvbigpIHsKICAgICAgaWYgKHRoaXMuY29udGV4dE1lbnVzXykgewogICAgICAgIHJldHVybiB0aGlzLmNvbnRleHRNZW51c187CiAgICAgIH0KCiAgICAgIHRoaXMuY29udGV4dE1lbnVzXyA9IG5ldyBXZWJWaWV3Q29udGV4dE1lbnVzKHRoaXMudmlld0luc3RhbmNlSWQpOwoKICAgICAgLy8gRGVmaW5lICdvbkNsaWNrZWQnIGV2ZW50IHByb3BlcnR5IG9uIHx0aGlzLmNvbnRleHRNZW51c198LgogICAgICB2YXIgZ2V0T25DbGlja2VkRXZlbnQgPSAkRnVuY3Rpb24uYmluZChmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gdGhpcy53ZWFrV3JhcHBlcihmdW5jdGlvbigpIHsKICAgICAgICAgIGlmICghdGhpcy5jb250ZXh0TWVudXNPbkNsaWNrZWRFdmVudF8pIHsKICAgICAgICAgICAgdmFyIGV2ZW50TmFtZSA9ICdjaHJvbWVXZWJWaWV3SW50ZXJuYWwub25DbGlja2VkJzsKICAgICAgICAgICAgdmFyIGV2ZW50U2NoZW1hID0KICAgICAgICAgICAgICAgIHV0aWxzLmxvb2t1cChDaHJvbWVXZWJWaWV3U2NoZW1hLmV2ZW50cywgJ25hbWUnLCAnb25DbGlja2VkJyk7CiAgICAgICAgICAgIHZhciBldmVudE9wdGlvbnMgPQogICAgICAgICAgICAgICAge3N1cHBvcnRzTGlzdGVuZXJzOiB0cnVlLCBzdXBwb3J0c0xhenlMaXN0ZW5lcnM6IGZhbHNlfTsKICAgICAgICAgICAgdmFyIG9uQ2xpY2tlZEV2ZW50ID0gY3JlYXRlQ29udGV4dE1lbnVzT25DbGlja2VkRXZlbnQoCiAgICAgICAgICAgICAgICB0aGlzLnZpZXdJbnN0YW5jZUlkLCBldmVudE5hbWUsIGV2ZW50U2NoZW1hLCBldmVudE9wdGlvbnMpOwogICAgICAgICAgICB0aGlzLmNvbnRleHRNZW51c09uQ2xpY2tlZEV2ZW50XyA9IG9uQ2xpY2tlZEV2ZW50OwogICAgICAgICAgICByZXR1cm4gb25DbGlja2VkRXZlbnQ7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gdGhpcy5jb250ZXh0TWVudXNPbkNsaWNrZWRFdmVudF87CiAgICAgICAgfSk7CiAgICAgIH0sIHRoaXMpOwogICAgICAkT2JqZWN0LmRlZmluZVByb3BlcnR5KAogICAgICAgICAgdGhpcy5jb250ZXh0TWVudXNfLAogICAgICAgICAgJ29uQ2xpY2tlZCcsCiAgICAgICAgICB7Z2V0OiBnZXRPbkNsaWNrZWRFdmVudCgpLCBlbnVtZXJhYmxlOiB0cnVlfSk7CiAgICAgICRPYmplY3QuZGVmaW5lUHJvcGVydHkoCiAgICAgICAgICB0aGlzLmNvbnRleHRNZW51c18sCiAgICAgICAgICAnb25TaG93JywKICAgICAgICAgIHsKICAgICAgICAgICAgZ2V0OiB0aGlzLndlYWtXcmFwcGVyKGZ1bmN0aW9uKCkgewogICAgICAgICAgICAgIHJldHVybiB0aGlzLmNvbnRleHRNZW51c09uQ29udGV4dE1lbnVFdmVudF87CiAgICAgICAgICAgIH0pLAogICAgICAgICAgICBlbnVtZXJhYmxlOiB0cnVlCiAgICAgICAgICB9KTsKICAgICAgcmV0dXJuIHRoaXMuY29udGV4dE1lbnVzXzsKICAgIH0pOwogIH0sIHRoaXMpOwoKICAvLyBFeHBvc2UgPHdlYnZpZXc+LmNvbnRleHRNZW51cyBvYmplY3QuCiAgJE9iamVjdC5kZWZpbmVQcm9wZXJ0eSgKICAgICAgdGhpcy5lbGVtZW50LAogICAgICAnY29udGV4dE1lbnVzJywKICAgICAgewogICAgICAgIGdldDogY3JlYXRlQ29udGV4dE1lbnVzKCksCiAgICAgICAgZW51bWVyYWJsZTogdHJ1ZQogICAgICB9KTsKfTsKCmZ1bmN0aW9uIEdldFVuaXF1ZVN1YkV2ZW50TmFtZShldmVudE5hbWUpIHsKICByZXR1cm4gZXZlbnROYW1lICsgJy8nICsgaWRHZW5lcmF0b3JOYXRpdmVzLkdldE5leHRJZCgpOwp9Ci8vIENvcHlyaWdodCAoYykgMjAxMiBUaGUgQ2hyb21pdW0gQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KLy8gVXNlIG9mIHRoaXMgc291cmNlIGNvZGUgaXMgZ292ZXJuZWQgYnkgYSBCU0Qtc3R5bGUgbGljZW5zZSB0aGF0IGNhbiBiZQovLyBmb3VuZCBpbiB0aGUgTElDRU5TRSBmaWxlLgoKLy8gQ3VzdG9tIGJpbmRpbmcgZm9yIHRoZSBjb250ZW50U2V0dGluZ3MgQVBJLgoKdmFyIHNlbmRSZXF1ZXN0ID0gcmVxdWlyZSgnc2VuZFJlcXVlc3QnKS5zZW5kUmVxdWVzdDsKdmFyIHZhbGlkYXRlID0gcmVxdWlyZSgnc2NoZW1hVXRpbHMnKS52YWxpZGF0ZTsKCi8vIFNvbWUgY29udGVudCB0eXBlcyBoYXZlIGJlZW4gcmVtb3ZlZCBhbmQgbm8gbG9uZ2VyIGNvcnJlc3BvbmQgdG8gYSByZWFsCi8vIGNvbnRlbnQgc2V0dGluZy4gSW5zdGVhZCwgdGhlc2UgYWx3YXlzIHJldHVybiBhIGZpeGVkIGR1bW15IHZhbHVlLCBhbmQgaXNzdWUKLy8gYSB3YXJuaW5nIHdoZW4gYWNjZXNzZWQuIFRoaXMgbWFwcyB0aGUgY29udGVudCB0eXBlIG5hbWUgdG8gdGhlIGR1bW15IHZhbHVlLgp2YXIgREVQUkVDQVRFRF9DT05URU5UX1RZUEVTID0gewogIF9fcHJvdG9fXzogbnVsbCwKCiAgZnVsbHNjcmVlbjogJ2FsbG93JywKICBtb3VzZWxvY2s6ICdhbGxvdycsCn07CgpmdW5jdGlvbiBleHRlbmRTY2hlbWEoc2NoZW1hKSB7CiAgdmFyIGV4dGVuZGVkU2NoZW1hID0gJEFycmF5LnNsaWNlKHNjaGVtYSk7CiAgJEFycmF5LnVuc2hpZnQoZXh0ZW5kZWRTY2hlbWEsIHsndHlwZSc6ICdzdHJpbmcnfSk7CiAgcmV0dXJuIGV4dGVuZGVkU2NoZW1hOwp9CgpmdW5jdGlvbiBDb250ZW50U2V0dGluZyhjb250ZW50VHlwZSwgc2V0dGluZ1NjaGVtYSwgc2NoZW1hKSB7CiAgdmFyIGdldEZ1bmN0aW9uUGFyYW1ldGVycyA9IGZ1bmN0aW9uKG5hbWUpIHsKICAgIHZhciBmID0gJEFycmF5LmZpbHRlcigKICAgICAgICAgICAgICAgIHNjaGVtYS5mdW5jdGlvbnMsIGZ1bmN0aW9uKGYpIHsgcmV0dXJuIGYubmFtZSA9PT0gbmFtZTsgfSlbMF07CiAgICByZXR1cm4gZi5wYXJhbWV0ZXJzOwogIH07CiAgdGhpcy5nZXQgPSBmdW5jdGlvbihkZXRhaWxzLCBjYWxsYmFjaykgewogICAgdmFyIGdldFNjaGVtYSA9IGdldEZ1bmN0aW9uUGFyYW1ldGVycygnZ2V0Jyk7CiAgICB2YWxpZGF0ZShbZGV0YWlscywgY2FsbGJhY2tdLCBnZXRTY2hlbWEpOwoKICAgIHZhciBkdW1teVNldHRpbmcgPSBERVBSRUNBVEVEX0NPTlRFTlRfVFlQRVNbY29udGVudFR5cGVdOwogICAgaWYgKGR1bW15U2V0dGluZyAhPT0gdW5kZWZpbmVkKSB7CiAgICAgIGNvbnNvbGUud2FybignY29udGVudFNldHRpbmdzLicgKyBjb250ZW50VHlwZSArICcgaXMgZGVwcmVjYXRlZDsgaXQgd2lsbCAnCiAgICAgICAgICAgICAgICAgICArICdhbHdheXMgcmV0dXJuIFwnJyArIGR1bW15U2V0dGluZyArICdcJy4nKTsKICAgICAgJEZ1bmN0aW9uLmFwcGx5KGNhbGxiYWNrLCB1bmRlZmluZWQsIFt7c2V0dGluZzogZHVtbXlTZXR0aW5nfV0pOwogICAgICByZXR1cm47CiAgICB9CgogICAgcmV0dXJuIHNlbmRSZXF1ZXN0KCdjb250ZW50U2V0dGluZ3MuZ2V0JywKICAgICAgICAgICAgICAgICAgICAgICBbY29udGVudFR5cGUsIGRldGFpbHMsIGNhbGxiYWNrXSwKICAgICAgICAgICAgICAgICAgICAgICBleHRlbmRTY2hlbWEoZ2V0U2NoZW1hKSk7CiAgfTsKCiAgdGhpcy5zZXQgPSBmdW5jdGlvbihkZXRhaWxzLCBjYWxsYmFjaykgewogICAgLy8gV2UgY2hlY2sgaWYgdGhlIHNldHRpbmcgaXMgZGVwcmVjYXRlZCBmaXJzdCwgc2luY2UgdGhlIHZhbGlkYXRpb24gd2lsbAogICAgLy8gZmFpbCBmb3IgZGVwcmVjYXRlZCB0eXBlcy4KICAgIGlmICgkT2JqZWN0Lmhhc093blByb3BlcnR5KERFUFJFQ0FURURfQ09OVEVOVF9UWVBFUywgY29udGVudFR5cGUpKSB7CiAgICAgIGNvbnNvbGUud2FybignY29udGVudFNldHRpbmdzLicgKyBjb250ZW50VHlwZSArICcgaXMgZGVwcmVjYXRlZDsgc2V0dGluZyAnCiAgICAgICAgICAgICAgICAgICArICdpdCBoYXMgbm8gZWZmZWN0LicpOwogICAgICAkRnVuY3Rpb24uYXBwbHkoY2FsbGJhY2ssIHVuZGVmaW5lZCwgW10pOwogICAgICByZXR1cm47CiAgICB9CgogICAgLy8gVGhlIHNldCBzY2hlbWEgaW5jbHVkZWQgaW4gdGhlIFNjaGVtYSBvYmplY3QgaXMgZ2VuZXJpYywgc2luY2UgaXQgdmFyaWVzCiAgICAvLyBwZXItc2V0dGluZy4gSG93ZXZlciwgdGhpcyBpcyBvbmx5IGV2ZXIgZm9yIGEgc2luZ2xlIHNldHRpbmcsIHNvIHdlIGNhbgogICAgLy8gZW5mb3JjZSB0aGUgdHlwZXMgbW9yZSB0aG9yb3VnaGx5LgogICAgdmFyIHJhd1NldFNjaGVtYSA9IGdldEZ1bmN0aW9uUGFyYW1ldGVycygnc2V0Jyk7CiAgICB2YXIgcmF3U2V0dGluZ1BhcmFtID0gcmF3U2V0U2NoZW1hWzBdOwogICAgdmFyIHByb3BzID0gJE9iamVjdC5hc3NpZ24oe30sIHJhd1NldHRpbmdQYXJhbS5wcm9wZXJ0aWVzKTsKICAgIHByb3BzLnNldHRpbmcgPSBzZXR0aW5nU2NoZW1hOwogICAgdmFyIG1vZFNldHRpbmdQYXJhbSA9IHsKICAgICAgbmFtZTogcmF3U2V0dGluZ1BhcmFtLm5hbWUsCiAgICAgIHR5cGU6IHJhd1NldHRpbmdQYXJhbS50eXBlLAogICAgICBwcm9wZXJ0aWVzOiBwcm9wcywKICAgIH07CiAgICB2YXIgbW9kU2V0U2NoZW1hID0gJEFycmF5LnNsaWNlKHJhd1NldFNjaGVtYSk7CiAgICBtb2RTZXRTY2hlbWFbMF0gPSBtb2RTZXR0aW5nUGFyYW07CiAgICB2YWxpZGF0ZShbZGV0YWlscywgY2FsbGJhY2tdLCBtb2RTZXRTY2hlbWEpOwoKICAgIHJldHVybiBzZW5kUmVxdWVzdCgnY29udGVudFNldHRpbmdzLnNldCcsCiAgICAgICAgICAgICAgICAgICAgICAgW2NvbnRlbnRUeXBlLCBkZXRhaWxzLCBjYWxsYmFja10sCiAgICAgICAgICAgICAgICAgICAgICAgZXh0ZW5kU2NoZW1hKG1vZFNldFNjaGVtYSkpOwogIH07CgogIHRoaXMuY2xlYXIgPSBmdW5jdGlvbihkZXRhaWxzLCBjYWxsYmFjaykgewogICAgdmFyIGNsZWFyU2NoZW1hID0gZ2V0RnVuY3Rpb25QYXJhbWV0ZXJzKCdjbGVhcicpOwogICAgdmFsaWRhdGUoW2RldGFpbHMsIGNhbGxiYWNrXSwgY2xlYXJTY2hlbWEpOwoKICAgIGlmICgkT2JqZWN0Lmhhc093blByb3BlcnR5KERFUFJFQ0FURURfQ09OVEVOVF9UWVBFUywgY29udGVudFR5cGUpKSB7CiAgICAgIGNvbnNvbGUud2FybignY29udGVudFNldHRpbmdzLicgKyBjb250ZW50VHlwZSArICcgaXMgZGVwcmVjYXRlZDsgJwogICAgICAgICAgICAgICAgICAgKyAnY2xlYXJpbmcgaXQgaGFzIG5vIGVmZmVjdC4nKTsKICAgICAgJEZ1bmN0aW9uLmFwcGx5KGNhbGxiYWNrLCB1bmRlZmluZWQsIFtdKTsKICAgICAgcmV0dXJuOwogICAgfQoKICAgIHJldHVybiBzZW5kUmVxdWVzdCgnY29udGVudFNldHRpbmdzLmNsZWFyJywKICAgICAgICAgICAgICAgICAgICAgICBbY29udGVudFR5cGUsIGRldGFpbHMsIGNhbGxiYWNrXSwKICAgICAgICAgICAgICAgICAgICAgICBleHRlbmRTY2hlbWEoY2xlYXJTY2hlbWEpKTsKICB9OwoKICB0aGlzLmdldFJlc291cmNlSWRlbnRpZmllcnMgPSBmdW5jdGlvbihjYWxsYmFjaykgewogICAgdmFyIHNjaGVtYSA9IGdldEZ1bmN0aW9uUGFyYW1ldGVycygnZ2V0UmVzb3VyY2VJZGVudGlmaWVycycpOwogICAgdmFsaWRhdGUoW2NhbGxiYWNrXSwgc2NoZW1hKTsKCiAgICBpZiAoJE9iamVjdC5oYXNPd25Qcm9wZXJ0eShERVBSRUNBVEVEX0NPTlRFTlRfVFlQRVMsIGNvbnRlbnRUeXBlKSkgewogICAgICAkRnVuY3Rpb24uYXBwbHkoY2FsbGJhY2ssIHVuZGVmaW5lZCwgW10pOwogICAgICByZXR1cm47CiAgICB9CgogICAgcmV0dXJuIHNlbmRSZXF1ZXN0KAogICAgICAgICdjb250ZW50U2V0dGluZ3MuZ2V0UmVzb3VyY2VJZGVudGlmaWVycycsCiAgICAgICAgW2NvbnRlbnRUeXBlLCBjYWxsYmFja10sCiAgICAgICAgZXh0ZW5kU2NoZW1hKHNjaGVtYSkpOwogIH07Cn0KCmV4cG9ydHMuJHNldCgnQ29udGVudFNldHRpbmcnLCBDb250ZW50U2V0dGluZyk7Ci8vIENvcHlyaWdodCAoYykgMjAxMiBUaGUgQ2hyb21pdW0gQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KLy8gVXNlIG9mIHRoaXMgc291cmNlIGNvZGUgaXMgZ292ZXJuZWQgYnkgYSBCU0Qtc3R5bGUgbGljZW5zZSB0aGF0IGNhbiBiZQovLyBmb3VuZCBpbiB0aGUgTElDRU5TRSBmaWxlLgoKLy8gQ3VzdG9tIGJpbmRpbmcgZm9yIHRoZSBkZWNsYXJhdGl2ZUNvbnRlbnQgQVBJLgoKdmFyIGJpbmRpbmcgPQogICAgYXBpQnJpZGdlIHx8IHJlcXVpcmUoJ2JpbmRpbmcnKS5CaW5kaW5nLmNyZWF0ZSgnZGVjbGFyYXRpdmVDb250ZW50Jyk7CgppZiAoIWFwaUJyaWRnZSkgewogIHZhciB1dGlscyA9IHJlcXVpcmUoJ3V0aWxzJyk7CiAgdmFyIHZhbGlkYXRlID0gcmVxdWlyZSgnc2NoZW1hVXRpbHMnKS52YWxpZGF0ZTsKICB2YXIgY2Fub25pY2FsaXplQ29tcG91bmRTZWxlY3RvciA9CiAgICAgIHJlcXVpcmVOYXRpdmUoJ2Nzc19uYXRpdmVzJykuQ2Fub25pY2FsaXplQ29tcG91bmRTZWxlY3RvcjsKfQoKdmFyIHNldEljb24gPSByZXF1aXJlKCdzZXRJY29uJykuc2V0SWNvbjsKCmJpbmRpbmcucmVnaXN0ZXJDdXN0b21Ib29rKGZ1bmN0aW9uKGFwaSkgewogIHZhciBkZWNsYXJhdGl2ZUNvbnRlbnQgPSBhcGkuY29tcGlsZWRBcGk7CgogIGlmIChhcGlCcmlkZ2UpIHsKICAgIC8vIFZhbGlkYXRpb24gZm9yIG1vc3QgdHlwZXMgaXMgZG9uZSBpbiB0aGUgbmF0aXZlIEMrKyB3aXRoIG5hdGl2ZSBiaW5kaW5ncywKICAgIC8vIGJ1dCBzZXRJY29uIGlzIGZ1bm55IChhbmQgc2FkbHkgYnJva2VuKS4gSWRlYWxseSwgd2UgY2FuIG1vdmUgdGhpcwogICAgLy8gdmFsaWRhdGlvbiBlbnRpcmVseSBpbnRvIHRoZSBuYXRpdmUgY29kZSwgYW5kIHRoaXMgd2hvbGUgZmlsZSBjYW4gZ28KICAgIC8vIGF3YXkuCiAgICB2YXIgbmF0aXZlU2V0SWNvbiA9IGRlY2xhcmF0aXZlQ29udGVudC5TZXRJY29uOwogICAgZGVjbGFyYXRpdmVDb250ZW50LlNldEljb24gPSBmdW5jdGlvbihwYXJhbWV0ZXJzKSB7CiAgICAgIC8vIFRPRE8oZGV2bGluKTogVGhpcyBpcyB2ZXJ5LCB2ZXJ5IHdyb25nLiBzZXRJY29uKCkgaXMgcG90ZW50aWFsbHkKICAgICAgLy8gYXN5bmNocm9ub3VzIChpbiB0aGUgY2FzZSBvZiBhIHBhdGggYmVpbmcgc3BlY2lmaWVkKSwgd2hpY2ggbWVhbnMgdGhpcwogICAgICAvLyBiZWNvbWVzIGFuICJhc3luY2hyb25vdXMgY29uc3RydWN0b3IiLiBFcnJvcnMgY2FuIGJlIHRocm93biAqYWZ0ZXIqIHRoZQogICAgICAvLyBgbmV3IGRlY2xhcmF0aXZlQ29udGVudC5TZXRJY29uKC4uLilgIGNhbGwsIGFuZCBpbiB0aGUgYXN5bmMgY2FzZXMsCiAgICAgIC8vIHRoaXMgd291bGRuJ3Qgd29yayB3aGVuIHdlIGltbWVkaWF0ZWx5IGFkZCB0aGUgYWN0aW9uIHZpYSBhbiBBUEkgY2FsbAogICAgICAvLyAoZS5nLiwKICAgICAgLy8gICBjaHJvbWUuZGVjbGFyYXRpdmVDb250ZW50Lm9uUGFnZUNoYW5nZS5hZGRSdWxlcygKICAgICAgLy8gICAgICAgW3tjb25kaXRpb25zOiAuLi4sIGFjdGlvbnM6IFsgbmV3IFNldEljb24oLi4uKSBdfV0pOwogICAgICAvLyApLiBTb21lIG9mIHRoaXMgaXMgdHJhY2tlZCBpbiBodHRwOi8vY3JidWcuY29tLzQxNTMxNS4KICAgICAgc2V0SWNvbihwYXJhbWV0ZXJzLCAkRnVuY3Rpb24uYmluZChmdW5jdGlvbihkYXRhKSB7CiAgICAgICAgLy8gRmFrZSBjYWxsaW5nIHRoZSBvcmlnaW5hbCBmdW5jdGlvbiBhcyBhIGNvbnN0cnVjdG9yLgogICAgICAgICRPYmplY3Quc2V0UHJvdG90eXBlT2YodGhpcywgbmF0aXZlU2V0SWNvbi5wcm90b3R5cGUpOwogICAgICAgICRGdW5jdGlvbi5hcHBseShuYXRpdmVTZXRJY29uLCB0aGlzLCBbZGF0YV0pOwogICAgICB9LCB0aGlzKSk7CiAgICB9OwogICAgcmV0dXJuOwogIH0KCiAgLy8gUmV0dXJucyB0aGUgc2NoZW1hIGRlZmluaXRpb24gb2YgdHlwZSB8dHlwZUlkfCBkZWZpbmVkIGluIHxuYW1lc3BhY2V8LgogIGZ1bmN0aW9uIGdldFNjaGVtYSh0eXBlSWQpIHsKICAgIHJldHVybiB1dGlscy5sb29rdXAoYXBpLnNjaGVtYS50eXBlcywKICAgICAgICAgICAgICAgICAgICAgICAgJ2lkJywKICAgICAgICAgICAgICAgICAgICAgICAgJ2RlY2xhcmF0aXZlQ29udGVudC4nICsgdHlwZUlkKTsKICB9CgogIC8vIEhlbHBlciBmdW5jdGlvbiBmb3IgdGhlIGNvbnN0cnVjdG9yIG9mIGNvbmNyZXRlIGRhdGF0eXBlcyBvZiB0aGUKICAvLyBkZWNsYXJhdGl2ZSBjb250ZW50IEFQSS4KICAvLyBNYWtlcyBzdXJlIHRoYXQgfHRoaXN8IGNvbnRhaW5zIHRoZSB1bmlvbiBvZiBwYXJhbWV0ZXJzIGFuZAogIC8vIHsnaW5zdGFuY2VUeXBlJzogJ2RlY2xhcmF0aXZlQ29udGVudC4nICsgdHlwZUlkfSBhbmQgdmFsaWRhdGVzIHRoZQogIC8vIGdlbmVyYXRlZCB1bmlvbiBkaWN0aW9uYXJ5IGFnYWluc3QgdGhlIHNjaGVtYSBmb3IgfHR5cGVJZHwuCiAgZnVuY3Rpb24gc2V0dXBJbnN0YW5jZShpbnN0YW5jZSwgcGFyYW1ldGVycywgdHlwZUlkKSB7CiAgICBmb3IgKHZhciBrZXkgaW4gcGFyYW1ldGVycykgewogICAgICBpZiAoJE9iamVjdC5oYXNPd25Qcm9wZXJ0eShwYXJhbWV0ZXJzLCBrZXkpKSB7CiAgICAgICAgaW5zdGFuY2Vba2V5XSA9IHBhcmFtZXRlcnNba2V5XTsKICAgICAgfQogICAgfQogICAgaW5zdGFuY2UuaW5zdGFuY2VUeXBlID0gJ2RlY2xhcmF0aXZlQ29udGVudC4nICsgdHlwZUlkOwogICAgdmFyIHNjaGVtYSA9IGdldFNjaGVtYSh0eXBlSWQpOwogICAgdmFsaWRhdGUoW2luc3RhbmNlXSwgW3NjaGVtYV0pOwogIH0KCiAgZnVuY3Rpb24gY2Fub25pY2FsaXplQ3NzU2VsZWN0b3JzKHNlbGVjdG9ycykgewogICAgZm9yICh2YXIgaSA9IDA7IGkgPCBzZWxlY3RvcnMubGVuZ3RoOyBpKyspIHsKICAgICAgdmFyIGNhbm9uaWNhbGl6ZWRTZWxlY3RvciA9IGNhbm9uaWNhbGl6ZUNvbXBvdW5kU2VsZWN0b3Ioc2VsZWN0b3JzW2ldKTsKICAgICAgaWYgKGNhbm9uaWNhbGl6ZWRTZWxlY3RvciA9PSAnJykgewogICAgICAgIHRocm93IG5ldyBFcnJvcigKICAgICAgICAgICAgJ0VsZW1lbnQgb2YgXCdjc3NcJyBhcnJheSBtdXN0IGJlIGEgJyArCiAgICAgICAgICAgICdsaXN0IG9mIHZhbGlkIGNvbXBvdW5kIHNlbGVjdG9yczogJyArCiAgICAgICAgICAgIHNlbGVjdG9yc1tpXSk7CiAgICAgIH0KICAgICAgc2VsZWN0b3JzW2ldID0gY2Fub25pY2FsaXplZFNlbGVjdG9yOwogICAgfQogIH0KCiAgLy8gU2V0dXAgYWxsIGRhdGEgdHlwZXMgZm9yIHRoZSBkZWNsYXJhdGl2ZSBjb250ZW50IEFQSS4KICBkZWNsYXJhdGl2ZUNvbnRlbnQuUGFnZVN0YXRlTWF0Y2hlciA9IGZ1bmN0aW9uKHBhcmFtZXRlcnMpIHsKICAgIHNldHVwSW5zdGFuY2UodGhpcywgcGFyYW1ldGVycywgJ1BhZ2VTdGF0ZU1hdGNoZXInKTsKICAgIGlmICgkT2JqZWN0Lmhhc093blByb3BlcnR5KHRoaXMsICdjc3MnKSkgewogICAgICBjYW5vbmljYWxpemVDc3NTZWxlY3RvcnModGhpcy5jc3MpOwogICAgfQogIH07CiAgZGVjbGFyYXRpdmVDb250ZW50LlNob3dQYWdlQWN0aW9uID0gZnVuY3Rpb24ocGFyYW1ldGVycykgewogICAgc2V0dXBJbnN0YW5jZSh0aGlzLCBwYXJhbWV0ZXJzLCAnU2hvd1BhZ2VBY3Rpb24nKTsKICB9OwogIGRlY2xhcmF0aXZlQ29udGVudC5SZXF1ZXN0Q29udGVudFNjcmlwdCA9IGZ1bmN0aW9uKHBhcmFtZXRlcnMpIHsKICAgIHNldHVwSW5zdGFuY2UodGhpcywgcGFyYW1ldGVycywgJ1JlcXVlc3RDb250ZW50U2NyaXB0Jyk7CiAgfTsKICAvLyBUT0RPKHJvY2tvdCk6IERvIG5vdCBleHBvc2UgdGhpcyBpbiBNMzkgc3RhYmxlLiBNYWtpbmcgdGhpcyByZXN0cmljdGlvbgogIC8vIHBvc3NpYmxlIHdpbGwgdGFrZSBzb21lIGV4dHJhIHdvcmsuIFNlZSBodHRwOi8vY3JidWcuY29tLzQxNTMxNQogIC8vIE5vdGU6IFNlZSBhbHNvIHRoZSBTZXRJY29uIHdyYXBwZXIgYWJvdmUgZm9yIG1vcmUgaXNzdWVzLgogIGRlY2xhcmF0aXZlQ29udGVudC5TZXRJY29uID0gZnVuY3Rpb24ocGFyYW1ldGVycykgewogICAgc2V0SWNvbihwYXJhbWV0ZXJzLCAkRnVuY3Rpb24uYmluZChmdW5jdGlvbihkYXRhKSB7CiAgICAgIHNldHVwSW5zdGFuY2UodGhpcywgZGF0YSwgJ1NldEljb24nKTsKICAgIH0sIHRoaXMpKTsKICB9Owp9KTsKCmlmICghYXBpQnJpZGdlKQogIGV4cG9ydHMuJHNldCgnYmluZGluZycsIGJpbmRpbmcuZ2VuZXJhdGUoKSk7Ci8vIENvcHlyaWdodCAyMDEzIFRoZSBDaHJvbWl1bSBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgovLyBVc2Ugb2YgdGhpcyBzb3VyY2UgY29kZSBpcyBnb3Zlcm5lZCBieSBhIEJTRC1zdHlsZSBsaWNlbnNlIHRoYXQgY2FuIGJlCi8vIGZvdW5kIGluIHRoZSBMSUNFTlNFIGZpbGUuCgovLyBDdXN0b20gYmluZGluZyBmb3IgdGhlIGRlc2t0b3BDYXB0dXJlIEFQSS4KCnZhciBiaW5kaW5nID0gYXBpQnJpZGdlIHx8IHJlcXVpcmUoJ2JpbmRpbmcnKS5CaW5kaW5nLmNyZWF0ZSgnZGVza3RvcENhcHR1cmUnKTsKdmFyIHNlbmRSZXF1ZXN0ID0gYmluZGluZ1V0aWwgPwogICAgJEZ1bmN0aW9uLmJpbmQoYmluZGluZ1V0aWwuc2VuZFJlcXVlc3QsIGJpbmRpbmdVdGlsKSA6CiAgICByZXF1aXJlKCdzZW5kUmVxdWVzdCcpLnNlbmRSZXF1ZXN0Owp2YXIgaWRHZW5lcmF0b3IgPSByZXF1aXJlTmF0aXZlKCdpZF9nZW5lcmF0b3InKTsKCmJpbmRpbmcucmVnaXN0ZXJDdXN0b21Ib29rKGZ1bmN0aW9uKGJpbmRpbmdzQVBJKSB7CiAgdmFyIGFwaUZ1bmN0aW9ucyA9IGJpbmRpbmdzQVBJLmFwaUZ1bmN0aW9uczsKCiAgdmFyIHBlbmRpbmdSZXF1ZXN0cyA9IHt9OwoKICBmdW5jdGlvbiBvblJlcXVlc3RSZXN1bHQoaWQsIHJlc3VsdCwgb3B0aW9ucykgewogICAgaWYgKGlkIGluIHBlbmRpbmdSZXF1ZXN0cykgewogICAgICB2YXIgY2FsbGJhY2sgPSBwZW5kaW5nUmVxdWVzdHNbaWRdOwogICAgICBkZWxldGUgcGVuZGluZ1JlcXVlc3RzW2lkXTsKICAgICAgY2FsbGJhY2socmVzdWx0LCBvcHRpb25zKTsKICAgIH0KICB9CgogIGFwaUZ1bmN0aW9ucy5zZXRIYW5kbGVSZXF1ZXN0KCdjaG9vc2VEZXNrdG9wTWVkaWEnLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGZ1bmN0aW9uKHNvdXJjZXMsIHRhcmdldF90YWIsIGNhbGxiYWNrKSB7CiAgICAvLyB8dGFyZ2V0X3RhYnwgaXMgYW4gb3B0aW9uYWwgcGFyYW1ldGVyLgogICAgaWYgKGNhbGxiYWNrID09PSB1bmRlZmluZWQpIHsKICAgICAgY2FsbGJhY2sgPSB0YXJnZXRfdGFiOwogICAgICB0YXJnZXRfdGFiID0gdW5kZWZpbmVkOwogICAgfQogICAgdmFyIGlkID0gaWRHZW5lcmF0b3IuR2V0TmV4dElkKCk7CiAgICBwZW5kaW5nUmVxdWVzdHNbaWRdID0gY2FsbGJhY2s7CiAgICBzZW5kUmVxdWVzdCgnZGVza3RvcENhcHR1cmUuY2hvb3NlRGVza3RvcE1lZGlhJywKICAgICAgICAgICAgICAgIFtpZCwgc291cmNlcywgdGFyZ2V0X3RhYiwKICAgICAgICAgICAgICAgICAkRnVuY3Rpb24uYmluZChvblJlcXVlc3RSZXN1bHQsIG51bGwsIGlkKV0sCiAgICAgICAgICAgICAgICBhcGlCcmlkZ2UgPyB1bmRlZmluZWQgOiB0aGlzLmRlZmluaXRpb24ucGFyYW1ldGVycywKICAgICAgICAgICAgICAgIHVuZGVmaW5lZCk7CiAgICByZXR1cm4gaWQ7CiAgfSk7CgogIGFwaUZ1bmN0aW9ucy5zZXRIYW5kbGVSZXF1ZXN0KCdjYW5jZWxDaG9vc2VEZXNrdG9wTWVkaWEnLCBmdW5jdGlvbihpZCkgewogICAgaWYgKGlkIGluIHBlbmRpbmdSZXF1ZXN0cykgewogICAgICBkZWxldGUgcGVuZGluZ1JlcXVlc3RzW2lkXTsKICAgICAgc2VuZFJlcXVlc3QoJ2Rlc2t0b3BDYXB0dXJlLmNhbmNlbENob29zZURlc2t0b3BNZWRpYScsCiAgICAgICAgICAgICAgICAgIFtpZF0sIGFwaUJyaWRnZSA/IHVuZGVmaW5lZCA6IHRoaXMuZGVmaW5pdGlvbi5wYXJhbWV0ZXJzLAogICAgICAgICAgICAgICAgICB1bmRlZmluZWQpOwogICAgfQogIH0pOwp9KTsKCmlmICghYXBpQnJpZGdlKQogIGV4cG9ydHMuJHNldCgnYmluZGluZycsIGJpbmRpbmcuZ2VuZXJhdGUoKSk7Ci8vIENvcHlyaWdodCAyMDE0IFRoZSBDaHJvbWl1bSBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgovLyBVc2Ugb2YgdGhpcyBzb3VyY2UgY29kZSBpcyBnb3Zlcm5lZCBieSBhIEJTRC1zdHlsZSBsaWNlbnNlIHRoYXQgY2FuIGJlCi8vIGZvdW5kIGluIHRoZSBMSUNFTlNFIGZpbGUuCgovLyBDdXN0b20gYmluZGluZyBmb3IgdGhlIGRldmVsb3BlclByaXZhdGUgQVBJLgoKdmFyIGJpbmRpbmcgPQogICAgYXBpQnJpZGdlIHx8IHJlcXVpcmUoJ2JpbmRpbmcnKS5CaW5kaW5nLmNyZWF0ZSgnZGV2ZWxvcGVyUHJpdmF0ZScpOwoKYmluZGluZy5yZWdpc3RlckN1c3RvbUhvb2soZnVuY3Rpb24oYmluZGluZ3NBUEkpIHsKICB2YXIgYXBpRnVuY3Rpb25zID0gYmluZGluZ3NBUEkuYXBpRnVuY3Rpb25zOwoKICAvLyBDb252ZXJ0cyB0aGUgYXJndW1lbnQgb2YgfGZ1bmN0aW9uTmFtZXwgZnJvbSBEaXJlY3RvcnlFbnRyeSB0byBVUkwuCiAgZnVuY3Rpb24gYmluZEZpbGVTeXN0ZW1GdW5jdGlvbihmdW5jdGlvbk5hbWUpIHsKICAgIGFwaUZ1bmN0aW9ucy5zZXRVcGRhdGVBcmd1bWVudHNQb3N0VmFsaWRhdGUoCiAgICAgICAgZnVuY3Rpb25OYW1lLCBmdW5jdGlvbihkaXJlY3RvcnlFbnRyeSwgY2FsbGJhY2spIHsKICAgICAgICAgIHZhciBmaWxlU3lzdGVtTmFtZSA9IGRpcmVjdG9yeUVudHJ5LmZpbGVzeXN0ZW0ubmFtZTsKICAgICAgICAgIHZhciByZWxhdGl2ZVBhdGggPSAkU3RyaW5nLnNsaWNlKGRpcmVjdG9yeUVudHJ5LmZ1bGxQYXRoLCAxKTsKICAgICAgICAgIHZhciB1cmwgPSBkaXJlY3RvcnlFbnRyeS50b1VSTCgpOwogICAgICAgICAgcmV0dXJuIFtmaWxlU3lzdGVtTmFtZSwgcmVsYXRpdmVQYXRoLCB1cmwsIGNhbGxiYWNrXTsKICAgIH0pOwogIH0KCiAgYmluZEZpbGVTeXN0ZW1GdW5jdGlvbignbG9hZERpcmVjdG9yeScpOwoKICAvLyBkZXZlbG9wZXJQcml2YXRlLmVuYWJsZSBpcyB0aGUgc2FtZSBhcyBjaHJvbWUubWFuYWdlbWVudC5zZXRFbmFibGVkLgogIC8vIFRPRE8oZGV2bGluKTogTWlncmF0ZSBjYWxsZXJzIG9mZiBkZXZlbG9wZXJQcml2YXRlLmVuYWJsZS4KICBiaW5kaW5nc0FQSS5jb21waWxlZEFwaS5lbmFibGUgPSBjaHJvbWUubWFuYWdlbWVudC5zZXRFbmFibGVkOwoKICBhcGlGdW5jdGlvbnMuc2V0SGFuZGxlUmVxdWVzdCgnYWxsb3dGaWxlQWNjZXNzJywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBmdW5jdGlvbihpZCwgYWxsb3csIGNhbGxiYWNrKSB7CiAgICBjaHJvbWUuZGV2ZWxvcGVyUHJpdmF0ZS51cGRhdGVFeHRlbnNpb25Db25maWd1cmF0aW9uKAogICAgICAgIHtleHRlbnNpb25JZDogaWQsIGZpbGVBY2Nlc3M6IGFsbG93fSwgY2FsbGJhY2spOwogIH0pOwoKICBhcGlGdW5jdGlvbnMuc2V0SGFuZGxlUmVxdWVzdCgnYWxsb3dJbmNvZ25pdG8nLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGZ1bmN0aW9uKGlkLCBhbGxvdywgY2FsbGJhY2spIHsKICAgIGNocm9tZS5kZXZlbG9wZXJQcml2YXRlLnVwZGF0ZUV4dGVuc2lvbkNvbmZpZ3VyYXRpb24oCiAgICAgICAge2V4dGVuc2lvbklkOiBpZCwgaW5jb2duaXRvQWNjZXNzOiBhbGxvd30sIGNhbGxiYWNrKTsKICB9KTsKCiAgYXBpRnVuY3Rpb25zLnNldEhhbmRsZVJlcXVlc3QoJ2luc3BlY3QnLCBmdW5jdGlvbihvcHRpb25zLCBjYWxsYmFjaykgewogICAgdmFyIHJlbmRlclZpZXdJZCA9IG9wdGlvbnMucmVuZGVyX3ZpZXdfaWQ7CiAgICBpZiAodHlwZW9mIHJlbmRlclZpZXdJZCA9PSAnc3RyaW5nJykgewogICAgICByZW5kZXJWaWV3SWQgPSBwYXJzZUludChyZW5kZXJWaWV3SWQpOwogICAgICBpZiAoaXNOYU4ocmVuZGVyVmlld0lkKSkKICAgICAgICB0aHJvdyBuZXcgRXJyb3IoJ0ludmFsaWQgdmFsdWUgZm9yIHJlbmRlcl92aWV3X2lkJyk7CiAgICB9CiAgICB2YXIgcmVuZGVyUHJvY2Vzc0lkID0gb3B0aW9ucy5yZW5kZXJfcHJvY2Vzc19pZDsKICAgIGlmICh0eXBlb2YgcmVuZGVyUHJvY2Vzc0lkID09ICdzdHJpbmcnKSB7CiAgICAgIHJlbmRlclByb2Nlc3NJZCA9IHBhcnNlSW50KHJlbmRlclByb2Nlc3NJZCk7CiAgICAgIGlmIChpc05hTihyZW5kZXJQcm9jZXNzSWQpKQogICAgICAgIHRocm93IG5ldyBFcnJvcignSW52YWxpZCB2YWx1ZSBmb3IgcmVuZGVyX3Byb2Nlc3NfaWQnKTsKICAgIH0KICAgIGNocm9tZS5kZXZlbG9wZXJQcml2YXRlLm9wZW5EZXZUb29scyh7CiAgICAgICAgZXh0ZW5zaW9uSWQ6IG9wdGlvbnMuZXh0ZW5zaW9uX2lkLAogICAgICAgIHJlbmRlclByb2Nlc3NJZDogcmVuZGVyUHJvY2Vzc0lkLAogICAgICAgIHJlbmRlclZpZXdJZDogcmVuZGVyVmlld0lkLAogICAgICAgIGluY29nbml0bzogb3B0aW9ucy5pbmNvZ25pdG8KICAgIH0sIGNhbGxiYWNrKTsKICB9KTsKfSk7CgppZiAoIWFwaUJyaWRnZSkKICBleHBvcnRzLiRzZXQoJ2JpbmRpbmcnLCBiaW5kaW5nLmdlbmVyYXRlKCkpOwovLyBDb3B5cmlnaHQgKGMpIDIwMTMgVGhlIENocm9taXVtIEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCi8vIFVzZSBvZiB0aGlzIHNvdXJjZSBjb2RlIGlzIGdvdmVybmVkIGJ5IGEgQlNELXN0eWxlIGxpY2Vuc2UgdGhhdCBjYW4gYmUKLy8gZm91bmQgaW4gdGhlIExJQ0VOU0UgZmlsZS4KCi8vIEN1c3RvbSBiaW5kaW5ncyBmb3IgdGhlIGRvd25sb2FkcyBBUEkuCgp2YXIgYmluZGluZyA9IGFwaUJyaWRnZSB8fCByZXF1aXJlKCdiaW5kaW5nJykuQmluZGluZy5jcmVhdGUoJ2Rvd25sb2FkcycpOwp2YXIgZG93bmxvYWRzSW50ZXJuYWwgPQogICAgZ2V0SW50ZXJuYWxBcGkgPwogICAgICAgIGdldEludGVybmFsQXBpKCdkb3dubG9hZHNJbnRlcm5hbCcpIDoKICAgICAgICByZXF1aXJlKCdiaW5kaW5nJykuQmluZGluZy5jcmVhdGUoJ2Rvd25sb2Fkc0ludGVybmFsJykuZ2VuZXJhdGUoKTsKdmFyIHJlZ2lzdGVyQXJndW1lbnRNYXNzYWdlciA9IGJpbmRpbmdVdGlsID8KICAgICRGdW5jdGlvbi5iaW5kKGJpbmRpbmdVdGlsLnJlZ2lzdGVyRXZlbnRBcmd1bWVudE1hc3NhZ2VyLCBiaW5kaW5nVXRpbCkgOgogICAgcmVxdWlyZSgnZXZlbnRfYmluZGluZ3MnKS5yZWdpc3RlckFyZ3VtZW50TWFzc2FnZXI7CgpyZWdpc3RlckFyZ3VtZW50TWFzc2FnZXIoJ2Rvd25sb2Fkcy5vbkRldGVybWluaW5nRmlsZW5hbWUnLAogICAgICAgICAgICAgICAgICAgICAgICAgZnVuY3Rpb24oYXJncywgZGlzcGF0Y2gpIHsKICB2YXIgZG93bmxvYWRJdGVtID0gYXJnc1swXTsKICAvLyBDb3B5IHRoZSBpZCBzbyB0aGF0IGV4dGVuc2lvbnMgY2FuJ3QgY2hhbmdlIGl0LgogIHZhciBkb3dubG9hZElkID0gZG93bmxvYWRJdGVtLmlkOwogIHZhciBzdWdnZXN0YWJsZSA9IHRydWU7CiAgZnVuY3Rpb24gaXNWYWxpZFJlc3VsdChyZXN1bHQpIHsKICAgIGlmIChyZXN1bHQgPT09IHVuZGVmaW5lZCkKICAgICAgcmV0dXJuIGZhbHNlOwogICAgaWYgKHR5cGVvZihyZXN1bHQpICE9ICdvYmplY3QnKSB7CiAgICAgIGNvbnNvbGUuZXJyb3IoJ0Vycm9yOiBJbnZvY2F0aW9uIG9mIGZvcm0gc3VnZ2VzdCgnICsgdHlwZW9mKHJlc3VsdCkgKwogICAgICAgICAgICAgICAgICAgICcpIGRvZXNuXCd0IG1hdGNoIGRlZmluaXRpb24gc3VnZ2VzdCh7ZmlsZW5hbWU6IHN0cmluZywgJyArCiAgICAgICAgICAgICAgICAgICAgJ2NvbmZsaWN0QWN0aW9uOiBzdHJpbmd9KScpOwogICAgICByZXR1cm4gZmFsc2U7CiAgICB9IGVsc2UgaWYgKCh0eXBlb2YocmVzdWx0LmZpbGVuYW1lKSAhPSAnc3RyaW5nJykgfHwKICAgICAgICAgICAgICAgKHJlc3VsdC5maWxlbmFtZS5sZW5ndGggPT0gMCkpIHsKICAgICAgY29uc29sZS5lcnJvcignRXJyb3I6ICJmaWxlbmFtZSIgcGFyYW1ldGVyIHRvIHN1Z2dlc3QoKSBtdXN0IGJlIGEgJyArCiAgICAgICAgICAgICAgICAgICAgJ25vbi1lbXB0eSBzdHJpbmcnKTsKICAgICAgcmV0dXJuIGZhbHNlOwogICAgfSBlbHNlIGlmIChbdW5kZWZpbmVkLCAndW5pcXVpZnknLCAnb3ZlcndyaXRlJywgJ3Byb21wdCddLmluZGV4T2YoCiAgICAgICAgICAgICAgICAgcmVzdWx0LmNvbmZsaWN0QWN0aW9uKSA8IDApIHsKICAgICAgY29uc29sZS5lcnJvcignRXJyb3I6ICJjb25mbGljdEFjdGlvbiIgcGFyYW1ldGVyIHRvIHN1Z2dlc3QoKSBtdXN0IGJlICcgKwogICAgICAgICAgICAgICAgICAgICdvbmUgb2YgdW5kZWZpbmVkLCAidW5pcXVpZnkiLCAib3ZlcndyaXRlIiwgInByb21wdCInKTsKICAgICAgcmV0dXJuIGZhbHNlOwogICAgfQogICAgcmV0dXJuIHRydWU7CiAgfQogIGZ1bmN0aW9uIHN1Z2dlc3RDYWxsYmFjayhyZXN1bHQpIHsKICAgIGlmICghc3VnZ2VzdGFibGUpIHsKICAgICAgY29uc29sZS5lcnJvcignc3VnZ2VzdENhbGxiYWNrIG1heSBub3QgYmUgY2FsbGVkIG1vcmUgdGhhbiBvbmNlLicpOwogICAgICByZXR1cm47CiAgICB9CiAgICBzdWdnZXN0YWJsZSA9IGZhbHNlOwogICAgaWYgKGlzVmFsaWRSZXN1bHQocmVzdWx0KSkgewogICAgICBkb3dubG9hZHNJbnRlcm5hbC5kZXRlcm1pbmVGaWxlbmFtZSgKICAgICAgICAgIGRvd25sb2FkSWQsIHJlc3VsdC5maWxlbmFtZSwgcmVzdWx0LmNvbmZsaWN0QWN0aW9uIHx8ICIiKTsKICAgIH0gZWxzZSB7CiAgICAgIGRvd25sb2Fkc0ludGVybmFsLmRldGVybWluZUZpbGVuYW1lKGRvd25sb2FkSWQsICIiLCAiIik7CiAgICB9CiAgfQogIHRyeSB7CiAgICB2YXIgcmVzdWx0cyA9IGRpc3BhdGNoKFtkb3dubG9hZEl0ZW0sIHN1Z2dlc3RDYWxsYmFja10pOwogICAgdmFyIGFzeW5jID0gKHJlc3VsdHMgJiYKICAgICAgICAgICAgICAgICByZXN1bHRzLnJlc3VsdHMgJiYKICAgICAgICAgICAgICAgICAocmVzdWx0cy5yZXN1bHRzLmxlbmd0aCAhPSAwKSAmJgogICAgICAgICAgICAgICAgIChyZXN1bHRzLnJlc3VsdHNbMF0gPT09IHRydWUpKTsKICAgIGlmIChzdWdnZXN0YWJsZSAmJiAhYXN5bmMpCiAgICAgIHN1Z2dlc3RDYWxsYmFjaygpOwogIH0gY2F0Y2ggKGUpIHsKICAgIHN1Z2dlc3RDYWxsYmFjaygpOwogICAgdGhyb3cgZTsKICB9Cn0pOwoKaWYgKCFhcGlCcmlkZ2UpCiAgZXhwb3J0cy4kc2V0KCdiaW5kaW5nJywgYmluZGluZy5nZW5lcmF0ZSgpKTsKLy8gQ29weXJpZ2h0IDIwMTcgVGhlIENocm9taXVtIEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCi8vIFVzZSBvZiB0aGlzIHNvdXJjZSBjb2RlIGlzIGdvdmVybmVkIGJ5IGEgQlNELXN0eWxlIGxpY2Vuc2UgdGhhdCBjYW4gYmUKLy8gZm91bmQgaW4gdGhlIExJQ0VOU0UgZmlsZS4KCnZhciBFdmVudCA9IHJlcXVpcmUoJ2V2ZW50X2JpbmRpbmdzJykuRXZlbnQ7CgovLyBUaGUgRWFzeVVubG9ja1Byb3hpbWl0eVJlcXVpcmVkIG9iamVjdCBpcyBqdXN0IGEgc3R1YiB0aGF0IGhhcyBhbiBvbkNoYW5nZQovLyBldmVudCwgd2hpY2ggaXMgbmV2ZXIgdHJpZ2dlcmVkLgovLyBUT0RPKGRldmxpbik6IFJlbW92ZSB0aGlzIG9uY2UgdGhlIHByZWZlcmVuY2VzUHJpdmF0ZSBBUEkgaXMgZnVsbHkgcmVtb3ZlZC4KLy8gaHR0cHM6Ly9jcmJ1Zy5jb20vNTkzMTY2CmZ1bmN0aW9uIEVhc3lVbmxvY2tQcm94aW1pdHlSZXF1aXJlZChwcmVmS2V5LCB2YWx1ZVNjaGVtYSwgc2NoZW1hKSB7CiAgLy8gTm90ZTogdGVjaG5pY2FsbHksIGV4dGVuc2lvbnMgY291bGQgaW50ZXJjZXB0IHRoaXMgdGhyb3VnaCBhIHNldHRlciBvbgogIC8vIE9iamVjdC5wcm90b3R5cGUoKS4gV2UgZG9uJ3QgcmVhbGx5IGNhcmUsIGJlY2F1c2UgYSkgdGhpcyBpcyBvbmx5IGZvciBhCiAgLy8gcHJpdmF0ZSBBUEksIHNvIHdlIHNob3VsZG4ndCBoYXZlIHRvIHdvcnJ5IGFib3V0IHVudHJ1c3RlZCBjb2RlLCBhbmQgYikKICAvLyB0aGlzIGlzIGFuIGFub255bW91cyBldmVudCwgd2hpY2ggZXhwb3NlcyBubyBhdHRhY2sgc3VyZmFjZSBhbmQgd2lsbCBiZQogIC8vIGV4cG9zZWQgdG8gdGhlIGV4dGVuc2lvbiBhbnl3YXkuCiAgdGhpcy5vbkNoYW5nZSA9IG5ldyBFdmVudCgpOwp9OwoKZXhwb3J0cy4kc2V0KCdFYXN5VW5sb2NrUHJveGltaXR5UmVxdWlyZWQnLCBFYXN5VW5sb2NrUHJveGltaXR5UmVxdWlyZWQpOwovLyBDb3B5cmlnaHQgMjAxMyBUaGUgQ2hyb21pdW0gQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KLy8gVXNlIG9mIHRoaXMgc291cmNlIGNvZGUgaXMgZ292ZXJuZWQgYnkgYSBCU0Qtc3R5bGUgbGljZW5zZSB0aGF0IGNhbiBiZQovLyBmb3VuZCBpbiB0aGUgTElDRU5TRSBmaWxlLgoKLy8gQ3VzdG9tIGJpbmRpbmdzIGZvciB0aGUgZmVlZGJhY2tQcml2YXRlIEFQSS4KCnZhciBiaW5kaW5nID0gYXBpQnJpZGdlIHx8IHJlcXVpcmUoJ2JpbmRpbmcnKS5CaW5kaW5nLmNyZWF0ZSgnZmVlZGJhY2tQcml2YXRlJyk7Cgp2YXIgYmxvYk5hdGl2ZXMgPSByZXF1aXJlTmF0aXZlKCdibG9iX25hdGl2ZXMnKTsKCmJpbmRpbmcucmVnaXN0ZXJDdXN0b21Ib29rKGZ1bmN0aW9uKGJpbmRpbmdzQVBJKSB7CiAgdmFyIGFwaUZ1bmN0aW9ucyA9IGJpbmRpbmdzQVBJLmFwaUZ1bmN0aW9uczsKICBhcGlGdW5jdGlvbnMuc2V0VXBkYXRlQXJndW1lbnRzUG9zdFZhbGlkYXRlKAogICAgICAic2VuZEZlZWRiYWNrIiwgZnVuY3Rpb24oZmVlZGJhY2tJbmZvLCBjYWxsYmFjaykgewogICAgdmFyIGF0dGFjaGVkRmlsZUJsb2JVdWlkID0gJyc7CiAgICB2YXIgc2NyZWVuc2hvdEJsb2JVdWlkID0gJyc7CgogICAgaWYgKGZlZWRiYWNrSW5mby5hdHRhY2hlZEZpbGUpCiAgICAgIGF0dGFjaGVkRmlsZUJsb2JVdWlkID0KICAgICAgICAgIGJsb2JOYXRpdmVzLkdldEJsb2JVdWlkKGZlZWRiYWNrSW5mby5hdHRhY2hlZEZpbGUuZGF0YSk7CiAgICBpZiAoZmVlZGJhY2tJbmZvLnNjcmVlbnNob3QpCiAgICAgIHNjcmVlbnNob3RCbG9iVXVpZCA9CiAgICAgICAgICBibG9iTmF0aXZlcy5HZXRCbG9iVXVpZChmZWVkYmFja0luZm8uc2NyZWVuc2hvdCk7CgogICAgZmVlZGJhY2tJbmZvLmF0dGFjaGVkRmlsZUJsb2JVdWlkID0gYXR0YWNoZWRGaWxlQmxvYlV1aWQ7CiAgICBmZWVkYmFja0luZm8uc2NyZWVuc2hvdEJsb2JVdWlkID0gc2NyZWVuc2hvdEJsb2JVdWlkOwoKICAgIHJldHVybiBbZmVlZGJhY2tJbmZvLCBjYWxsYmFja107CiAgfSk7Cn0pOwoKaWYgKCFhcGlCcmlkZ2UpCiAgZXhwb3J0cy4kc2V0KCdiaW5kaW5nJywgYmluZGluZy5nZW5lcmF0ZSgpKTsKLy8gQ29weXJpZ2h0IDIwMTMgVGhlIENocm9taXVtIEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCi8vIFVzZSBvZiB0aGlzIHNvdXJjZSBjb2RlIGlzIGdvdmVybmVkIGJ5IGEgQlNELXN0eWxlIGxpY2Vuc2UgdGhhdCBjYW4gYmUKLy8gZm91bmQgaW4gdGhlIExJQ0VOU0UgZmlsZS4KCi8vIEN1c3RvbSBiaW5kaW5nIGZvciB0aGUgR0NNIEFQSS4KCnZhciBiaW5kaW5nID0gYXBpQnJpZGdlIHx8IHJlcXVpcmUoJ2JpbmRpbmcnKS5CaW5kaW5nLmNyZWF0ZSgnZ2NtJyk7CnZhciBmb3JFYWNoID0gcmVxdWlyZSgndXRpbHMnKS5mb3JFYWNoOwoKYmluZGluZy5yZWdpc3RlckN1c3RvbUhvb2soZnVuY3Rpb24oYmluZGluZ3NBUEkpIHsKICB2YXIgYXBpRnVuY3Rpb25zID0gYmluZGluZ3NBUEkuYXBpRnVuY3Rpb25zOwogIHZhciBnY20gPSBiaW5kaW5nc0FQSS5jb21waWxlZEFwaTsKCiAgYXBpRnVuY3Rpb25zLnNldFVwZGF0ZUFyZ3VtZW50c1Bvc3RWYWxpZGF0ZSgKICAgICdzZW5kJywgZnVuY3Rpb24obWVzc2FnZSwgY2FsbGJhY2spIHsKICAgICAgLy8gVmFsaWRhdGUgbWVzc2FnZS5kYXRhLgogICAgICB2YXIgcGF5bG9hZFNpemUgPSAwOwogICAgICBmb3JFYWNoKG1lc3NhZ2UuZGF0YSwgZnVuY3Rpb24ocHJvcGVydHksIHZhbHVlKSB7CiAgICAgICAgaWYgKHByb3BlcnR5Lmxlbmd0aCA9PSAwKQogICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJPbmUgb2YgZGF0YSBrZXlzIGlzIGVtcHR5LiIpOwoKICAgICAgICB2YXIgbG93ZXJDYXNlZFByb3BlcnR5ID0gcHJvcGVydHkudG9Mb3dlckNhc2UoKTsKICAgICAgICAvLyBJc3N1ZSBhbiBlcnJvciBmb3IgZm9yYmlkZGVuIHByZWZpeGVzIG9mIHByb3BlcnR5IG5hbWVzLgogICAgICAgIGlmIChsb3dlckNhc2VkUHJvcGVydHkuc3RhcnRzV2l0aCgiZ29vZy4iKSB8fAogICAgICAgICAgICBsb3dlckNhc2VkUHJvcGVydHkuc3RhcnRzV2l0aCgiZ29vZ2xlIikgfHwKICAgICAgICAgICAgcHJvcGVydHkuc3RhcnRzV2l0aCgiY29sbGFwc2Vfa2V5IikpIHsKICAgICAgICAgIHRocm93IG5ldyBFcnJvcigiSW52YWxpZCBkYXRhIGtleTogIiArIHByb3BlcnR5KTsKICAgICAgICB9CgogICAgICAgIHBheWxvYWRTaXplICs9IHByb3BlcnR5Lmxlbmd0aCArIHZhbHVlLmxlbmd0aDsKICAgICAgfSk7CgogICAgICBpZiAocGF5bG9hZFNpemUgPiBnY20uTUFYX01FU1NBR0VfU0laRSkKICAgICAgICB0aHJvdyBuZXcgRXJyb3IoIlBheWxvYWQgZXhjZWVkZWQgYWxsb3dlZCBzaXplIGxpbWl0LiBQYXlsb2FkIHNpemUgaXM6ICIKICAgICAgICAgICAgKyBwYXlsb2FkU2l6ZSk7CgogICAgICBpZiAocGF5bG9hZFNpemUgPT0gMCkKICAgICAgICB0aHJvdyBuZXcgRXJyb3IoIk5vIGRhdGEgdG8gc2VuZC4iKTsKCiAgICAgIHJldHVybiBhcmd1bWVudHM7CiAgICB9KTsKfSk7CgppZiAoIWFwaUJyaWRnZSkKICBleHBvcnRzLiRzZXQoJ2JpbmRpbmcnLCBiaW5kaW5nLmdlbmVyYXRlKCkpOwovLyBDb3B5cmlnaHQgMjAxMyBUaGUgQ2hyb21pdW0gQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KLy8gVXNlIG9mIHRoaXMgc291cmNlIGNvZGUgaXMgZ292ZXJuZWQgYnkgYSBCU0Qtc3R5bGUgbGljZW5zZSB0aGF0IGNhbiBiZQovLyBmb3VuZCBpbiB0aGUgTElDRU5TRSBmaWxlLgoKLy8gQ3VzdG9tIGJpbmRpbmcgZm9yIHRoZSBJZGVudGl0eSBBUEkuCgp2YXIgYmluZGluZyA9IGFwaUJyaWRnZSB8fCByZXF1aXJlKCdiaW5kaW5nJykuQmluZGluZy5jcmVhdGUoJ2lkZW50aXR5Jyk7CgpiaW5kaW5nLnJlZ2lzdGVyQ3VzdG9tSG9vayhmdW5jdGlvbihiaW5kaW5nLCBpZCwgY29udGV4dFR5cGUpIHsKICB2YXIgYXBpRnVuY3Rpb25zID0gYmluZGluZy5hcGlGdW5jdGlvbnM7CgogIGFwaUZ1bmN0aW9ucy5zZXRIYW5kbGVSZXF1ZXN0KCdnZXRSZWRpcmVjdFVSTCcsIGZ1bmN0aW9uKHBhdGgpIHsKICAgIGlmIChwYXRoID09PSBudWxsIHx8IHBhdGggPT09IHVuZGVmaW5lZCkKICAgICAgcGF0aCA9ICcvJzsKICAgIGVsc2UKICAgICAgcGF0aCA9IFN0cmluZyhwYXRoKTsKICAgIGlmIChwYXRoWzBdICE9ICcvJykKICAgICAgcGF0aCA9ICcvJyArIHBhdGg7CiAgICByZXR1cm4gJ2h0dHBzOi8vJyArIGlkICsgJy5jaHJvbWl1bWFwcC5vcmcnICsgcGF0aDsKICB9KTsKfSk7CgppZiAoIWFwaUJyaWRnZSkKICBleHBvcnRzLiRzZXQoJ2JpbmRpbmcnLCBiaW5kaW5nLmdlbmVyYXRlKCkpOwovLyBDb3B5cmlnaHQgMjAxMyBUaGUgQ2hyb21pdW0gQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KLy8gVXNlIG9mIHRoaXMgc291cmNlIGNvZGUgaXMgZ292ZXJuZWQgYnkgYSBCU0Qtc3R5bGUgbGljZW5zZSB0aGF0IGNhbiBiZQovLyBmb3VuZCBpbiB0aGUgTElDRU5TRSBmaWxlLgoKLy8gQ3VzdG9tIGJpbmRpbmcgZm9yIHRoZSBpbWFnZSB3cml0ZXIgcHJpdmF0ZSBBUEkuCgp2YXIgYmluZGluZyA9CiAgICBhcGlCcmlkZ2UgfHwgcmVxdWlyZSgnYmluZGluZycpLkJpbmRpbmcuY3JlYXRlKCdpbWFnZVdyaXRlclByaXZhdGUnKTsKCmJpbmRpbmcucmVnaXN0ZXJDdXN0b21Ib29rKGZ1bmN0aW9uKGJpbmRpbmdzQVBJKSB7CiAgdmFyIGFwaUZ1bmN0aW9ucyA9IGJpbmRpbmdzQVBJLmFwaUZ1bmN0aW9uczsKCiAgYXBpRnVuY3Rpb25zLnNldFVwZGF0ZUFyZ3VtZW50c1Bvc3RWYWxpZGF0ZSgKICAgICAgJ3dyaXRlRnJvbUZpbGUnLCBmdW5jdGlvbihkZXZpY2UsIGZpbGVFbnRyeSwgb3B0aW9ucywgY2FsbGJhY2spIHsKICAgIHZhciBmaWxlU3lzdGVtTmFtZSA9IGZpbGVFbnRyeS5maWxlc3lzdGVtLm5hbWU7CiAgICB2YXIgcmVsYXRpdmVQYXRoID0gJFN0cmluZy5zbGljZShmaWxlRW50cnkuZnVsbFBhdGgsIDEpOwogICAgcmV0dXJuIFtkZXZpY2UsIGZpbGVTeXN0ZW1OYW1lLCByZWxhdGl2ZVBhdGgsIGNhbGxiYWNrXTsKICB9KTsKfSk7CgppZiAoIWFwaUJyaWRnZSkKICBleHBvcnRzLiRzZXQoJ2JpbmRpbmcnLCBiaW5kaW5nLmdlbmVyYXRlKCkpOwovLyBDb3B5cmlnaHQgKGMpIDIwMTIgVGhlIENocm9taXVtIEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCi8vIFVzZSBvZiB0aGlzIHNvdXJjZSBjb2RlIGlzIGdvdmVybmVkIGJ5IGEgQlNELXN0eWxlIGxpY2Vuc2UgdGhhdCBjYW4gYmUKLy8gZm91bmQgaW4gdGhlIExJQ0VOU0UgZmlsZS4KCi8vIEN1c3RvbSBiaW5kaW5nIGZvciB0aGUgaW5wdXQgaW1lIEFQSS4gT25seSBpbmplY3RlZCBpbnRvIHRoZQovLyB2OCBjb250ZXh0cyBmb3IgZXh0ZW5zaW9ucyB3aGljaCBoYXZlIHBlcm1pc3Npb24gZm9yIHRoZSBBUEkuCgp2YXIgYmluZGluZyA9IGFwaUJyaWRnZSB8fCByZXF1aXJlKCdiaW5kaW5nJykuQmluZGluZy5jcmVhdGUoJ2lucHV0LmltZScpOwp2YXIgYXBwV2luZG93TmF0aXZlcyA9IHJlcXVpcmVOYXRpdmUoJ2FwcF93aW5kb3dfbmF0aXZlcycpOwp2YXIgcmVnaXN0ZXJBcmd1bWVudE1hc3NhZ2VyID0gYmluZGluZ1V0aWwgPwogICAgJEZ1bmN0aW9uLmJpbmQoYmluZGluZ1V0aWwucmVnaXN0ZXJFdmVudEFyZ3VtZW50TWFzc2FnZXIsIGJpbmRpbmdVdGlsKSA6CiAgICByZXF1aXJlKCdldmVudF9iaW5kaW5ncycpLnJlZ2lzdGVyQXJndW1lbnRNYXNzYWdlcjsKCi8vIFRPRE8oY3JidWcuY29tLzczMzgyNSk6IFRoZXNlIGJpbmRpbmdzIGhhdmUgc29tZSBpc3N1ZXMuCgp2YXIgaW5wdXRJbWU7CnJlZ2lzdGVyQXJndW1lbnRNYXNzYWdlcignaW5wdXQuaW1lLm9uS2V5RXZlbnQnLAogICAgICAgICAgICAgICAgICAgICAgICAgZnVuY3Rpb24oYXJncywgZGlzcGF0Y2gpIHsKICB2YXIga2V5RGF0YSA9IGFyZ3NbMV07CiAgdmFyIHJlc3VsdCA9IGZhbHNlOwogIHRyeSB7CiAgICAvLyBkaXNwYXRjaCgpIGlzIHdlaXJkIC0gaXQgcmV0dXJucyBhbiBvYmplY3Qge3Jlc3VsdHM6IGFycmF5PHJlc3VsdHM+fSBpZmYKICAgIC8vIHRoZXJlIGlzIGF0IGxlYXN0IG9uZSByZXN1bHQgdmFsdWUgdGhhdCAhPT0gdW5kZWZpbmVkLiBTaW5jZSBvbktleUV2ZW50CiAgICAvLyBoYXMgYSBtYXhpbXVtIG9mIG9uZSBsaXN0ZW5lciwgd2Uga25vdyB0aGF0IGFueSByZXN1bHQgd2UgZmluZCBpcyB0aGUgb25lCiAgICAvLyB3ZSdyZSBpbnRlcmVzdGVkIGluLgogICAgdmFyIGRpc3BhdGNoUmVzdWx0ID0gZGlzcGF0Y2goYXJncyk7CiAgICBpZiAoZGlzcGF0Y2hSZXN1bHQgJiYgZGlzcGF0Y2hSZXN1bHQucmVzdWx0cykKICAgICAgcmVzdWx0ID0gZGlzcGF0Y2hSZXN1bHQucmVzdWx0c1swXTsKICB9IGNhdGNoIChlKSB7CiAgICBjb25zb2xlLmVycm9yKCdFcnJvciBpbiBldmVudCBoYW5kbGVyIGZvciBvbktleUV2ZW50OiAnICsgZS5zdGFjayk7CiAgfQogIGlmICghaW5wdXRJbWUub25LZXlFdmVudC5hc3luYykKICAgIGlucHV0SW1lLmtleUV2ZW50SGFuZGxlZChrZXlEYXRhLnJlcXVlc3RJZCwgcmVzdWx0KTsKfSk7CgpiaW5kaW5nLnJlZ2lzdGVyQ3VzdG9tSG9vayhmdW5jdGlvbihhcGkpIHsKIGlucHV0SW1lID0gYXBpLmNvbXBpbGVkQXBpOwoKICB2YXIgb3JpZ2luYWxBZGRMaXN0ZW5lciA9IGlucHV0SW1lLm9uS2V5RXZlbnQuYWRkTGlzdGVuZXI7CiAgaW5wdXRJbWUub25LZXlFdmVudC5hZGRMaXN0ZW5lciA9IGZ1bmN0aW9uKGNiLCBvcHRfZXh0cmFJbmZvKSB7CiAgICBpbnB1dEltZS5vbktleUV2ZW50LmFzeW5jID0gZmFsc2U7CiAgICBpZiAob3B0X2V4dHJhSW5mbyBpbnN0YW5jZW9mIEFycmF5KSB7CiAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgb3B0X2V4dHJhSW5mby5sZW5ndGg7ICsraSkgewogICAgICAgIGlmIChvcHRfZXh0cmFJbmZvW2ldID09ICdhc3luYycpIHsKICAgICAgICAgIGlucHV0SW1lLm9uS2V5RXZlbnQuYXN5bmMgPSB0cnVlOwogICAgICAgIH0KICAgICAgfQogICAgfQogICAgJEZ1bmN0aW9uLmNhbGwob3JpZ2luYWxBZGRMaXN0ZW5lciwgdGhpcywgY2IpOwogIH07CgogIGFwaS5hcGlGdW5jdGlvbnMuc2V0Q3VzdG9tQ2FsbGJhY2soJ2NyZWF0ZVdpbmRvdycsCiAgICAgIGZ1bmN0aW9uKG5hbWUsIHJlcXVlc3QsIGNhbGxiYWNrLCB3aW5kb3dQYXJhbXMpIHsKICAgIGlmICghY2FsbGJhY2spIHsKICAgICAgcmV0dXJuOwogICAgfQogICAgdmFyIHZpZXc7CiAgICBpZiAod2luZG93UGFyYW1zICYmIHdpbmRvd1BhcmFtcy5mcmFtZUlkKSB7CiAgICAgIHZpZXcgPSBhcHBXaW5kb3dOYXRpdmVzLkdldEZyYW1lKAogICAgICAgICAgd2luZG93UGFyYW1zLmZyYW1lSWQsIGZhbHNlIC8qIG5vdGlmeUJyb3dzZXIgKi8pOwogICAgICB2aWV3LmlkID0gd2luZG93UGFyYW1zLmZyYW1lSWQ7CiAgICB9CiAgICBjYWxsYmFjayh2aWV3KTsKICB9KTsKfSk7CgppZiAoIWFwaUJyaWRnZSkKICBleHBvcnRzLiRzZXQoJ2JpbmRpbmcnLCBiaW5kaW5nLmdlbmVyYXRlKCkpOwovLyBDb3B5cmlnaHQgKGMpIDIwMTIgVGhlIENocm9taXVtIEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCi8vIFVzZSBvZiB0aGlzIHNvdXJjZSBjb2RlIGlzIGdvdmVybmVkIGJ5IGEgQlNELXN0eWxlIGxpY2Vuc2UgdGhhdCBjYW4gYmUKLy8gZm91bmQgaW4gdGhlIExJQ0VOU0UgZmlsZS4KCi8vIEN1c3RvbSBiaW5kaW5nIGZvciB0aGUgTWVkaWEgR2FsbGVyeSBBUEkuCgp2YXIgYmluZGluZyA9IGFwaUJyaWRnZSB8fCByZXF1aXJlKCdiaW5kaW5nJykuQmluZGluZy5jcmVhdGUoJ21lZGlhR2FsbGVyaWVzJyk7CnZhciBibG9iTmF0aXZlcyA9IHJlcXVpcmVOYXRpdmUoJ2Jsb2JfbmF0aXZlcycpOwp2YXIgbWVkaWFHYWxsZXJpZXNOYXRpdmVzID0gcmVxdWlyZU5hdGl2ZSgnbWVkaWFHYWxsZXJpZXMnKTsKdmFyIHNlbmRSZXF1ZXN0ID0gYmluZGluZ1V0aWwgPwogICAgJEZ1bmN0aW9uLmJpbmQoYmluZGluZ1V0aWwuc2VuZFJlcXVlc3QsIGJpbmRpbmdVdGlsKSA6CiAgICByZXF1aXJlKCdzZW5kUmVxdWVzdCcpLnNlbmRSZXF1ZXN0OwoKdmFyIGJsb2JzQXdhaXRpbmdNZXRhZGF0YSA9IHt9Owp2YXIgbWVkaWFHYWxsZXJpZXNNZXRhZGF0YSA9IHt9OwoKZnVuY3Rpb24gY3JlYXRlRmlsZVN5c3RlbU9iamVjdHNBbmRVcGRhdGVNZXRhZGF0YShyZXNwb25zZSkgewogIHZhciByZXN1bHQgPSBbXTsKICBtZWRpYUdhbGxlcmllc01ldGFkYXRhID0ge307ICAvLyBDbGVhciBhbnkgcHJldmlvdXMgbWV0YWRhdGEuCiAgaWYgKHJlc3BvbnNlKSB7CiAgICBmb3IgKHZhciBpID0gMDsgaSA8IHJlc3BvbnNlLmxlbmd0aDsgaSsrKSB7CiAgICAgIHZhciBmaWxlc3lzdGVtID0gbWVkaWFHYWxsZXJpZXNOYXRpdmVzLkdldE1lZGlhRmlsZVN5c3RlbU9iamVjdCgKICAgICAgICAgIHJlc3BvbnNlW2ldLmZzaWQpOwogICAgICAkQXJyYXkucHVzaChyZXN1bHQsIGZpbGVzeXN0ZW0pOwogICAgICB2YXIgbWV0YWRhdGEgPSByZXNwb25zZVtpXTsKICAgICAgZGVsZXRlIG1ldGFkYXRhLmZzaWQ7CiAgICAgIG1lZGlhR2FsbGVyaWVzTWV0YWRhdGFbZmlsZXN5c3RlbS5uYW1lXSA9IG1ldGFkYXRhOwogICAgfQogIH0KICByZXR1cm4gcmVzdWx0Owp9CgpiaW5kaW5nLnJlZ2lzdGVyQ3VzdG9tSG9vayhmdW5jdGlvbihiaW5kaW5nc0FQSSwgZXh0ZW5zaW9uSWQpIHsKICB2YXIgYXBpRnVuY3Rpb25zID0gYmluZGluZ3NBUEkuYXBpRnVuY3Rpb25zOwoKICAvLyBnZXRNZWRpYUZpbGVTeXN0ZW1zIGFuZCBhZGRVc2VyU2VsZWN0ZWRGb2xkZXIgdXNlIGEgY3VzdG9tIGNhbGxiYWNrIHNvIHRoYXQKICAvLyB0aGV5IGNhbiBpbnN0YW50aWF0ZSBhbmQgcmV0dXJuIGFuIGFycmF5IG9mIGZpbGUgc3lzdGVtIG9iamVjdHMuCiAgYXBpRnVuY3Rpb25zLnNldEN1c3RvbUNhbGxiYWNrKCdnZXRNZWRpYUZpbGVTeXN0ZW1zJywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZnVuY3Rpb24obmFtZSwgcmVxdWVzdCwgY2FsbGJhY2ssIHJlc3BvbnNlKSB7CiAgICB2YXIgcmVzdWx0ID0gY3JlYXRlRmlsZVN5c3RlbU9iamVjdHNBbmRVcGRhdGVNZXRhZGF0YShyZXNwb25zZSk7CiAgICBpZiAoY2FsbGJhY2spCiAgICAgIGNhbGxiYWNrKHJlc3VsdCk7CiAgfSk7CgogIGFwaUZ1bmN0aW9ucy5zZXRDdXN0b21DYWxsYmFjaygnYWRkVXNlclNlbGVjdGVkRm9sZGVyJywKICAgICAgZnVuY3Rpb24obmFtZSwgcmVxdWVzdCwgY2FsbGJhY2ssIHJlc3BvbnNlKSB7CiAgICB2YXIgZmlsZVN5c3RlbXMgPSBbXTsKICAgIHZhciBzZWxlY3RlZEZpbGVTeXN0ZW1OYW1lID0gIiI7CiAgICBpZiAocmVzcG9uc2UgJiYgJ21lZGlhRmlsZVN5c3RlbXMnIGluIHJlc3BvbnNlICYmCiAgICAgICAgJ3NlbGVjdGVkRmlsZVN5c3RlbUluZGV4JyBpbiByZXNwb25zZSkgewogICAgICBmaWxlU3lzdGVtcyA9IGNyZWF0ZUZpbGVTeXN0ZW1PYmplY3RzQW5kVXBkYXRlTWV0YWRhdGEoCiAgICAgICAgICByZXNwb25zZVsnbWVkaWFGaWxlU3lzdGVtcyddKTsKICAgICAgdmFyIHNlbGVjdGVkRmlsZVN5c3RlbUluZGV4ID0gcmVzcG9uc2VbJ3NlbGVjdGVkRmlsZVN5c3RlbUluZGV4J107CiAgICAgIGlmIChzZWxlY3RlZEZpbGVTeXN0ZW1JbmRleCA+PSAwKSB7CiAgICAgICAgc2VsZWN0ZWRGaWxlU3lzdGVtTmFtZSA9IGZpbGVTeXN0ZW1zW3NlbGVjdGVkRmlsZVN5c3RlbUluZGV4XS5uYW1lOwogICAgICB9CiAgICB9CiAgICBpZiAoY2FsbGJhY2spCiAgICAgIGNhbGxiYWNrKGZpbGVTeXN0ZW1zLCBzZWxlY3RlZEZpbGVTeXN0ZW1OYW1lKTsKICB9KTsKCiAgYXBpRnVuY3Rpb25zLnNldEhhbmRsZVJlcXVlc3QoJ2dldE1lZGlhRmlsZVN5c3RlbU1ldGFkYXRhJywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBmdW5jdGlvbihmaWxlc3lzdGVtKSB7CiAgICBpZiAoZmlsZXN5c3RlbSAmJiBmaWxlc3lzdGVtLm5hbWUgJiYKICAgICAgICBmaWxlc3lzdGVtLm5hbWUgaW4gbWVkaWFHYWxsZXJpZXNNZXRhZGF0YSkgewogICAgICByZXR1cm4gbWVkaWFHYWxsZXJpZXNNZXRhZGF0YVtmaWxlc3lzdGVtLm5hbWVdOwogICAgfQogICAgcmV0dXJuIHsKICAgICAgJ25hbWUnOiAnJywKICAgICAgJ2dhbGxlcnlJZCc6ICcnLAogICAgICAnaXNSZW1vdmFibGUnOiBmYWxzZSwKICAgICAgJ2lzTWVkaWFEZXZpY2UnOiBmYWxzZSwKICAgICAgJ2lzQXZhaWxhYmxlJzogZmFsc2UsCiAgICB9OwogIH0pOwoKICBmdW5jdGlvbiBnZXRNZXRhZGF0YUNhbGxiYWNrKHV1aWQsIG5hbWUsIHJlcXVlc3QsIGNhbGxiYWNrLCByZXNwb25zZSkgewogICAgaWYgKHJlc3BvbnNlICYmIHJlc3BvbnNlLmF0dGFjaGVkSW1hZ2VzQmxvYkluZm8pIHsKICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCByZXNwb25zZS5hdHRhY2hlZEltYWdlc0Jsb2JJbmZvLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgdmFyIGJsb2JJbmZvID0gcmVzcG9uc2UuYXR0YWNoZWRJbWFnZXNCbG9iSW5mb1tpXTsKICAgICAgICB2YXIgYmxvYiA9IGJsb2JOYXRpdmVzLlRha2VCcm93c2VyUHJvY2Vzc0Jsb2IoCiAgICAgICAgICAgIGJsb2JJbmZvLmJsb2JVVUlELCBibG9iSW5mby50eXBlLCBibG9iSW5mby5zaXplKTsKICAgICAgICByZXNwb25zZS5tZXRhZGF0YS5hdHRhY2hlZEltYWdlcy5wdXNoKGJsb2IpOwogICAgICB9CiAgICB9CgogICAgaWYgKGNhbGxiYWNrKQogICAgICBjYWxsYmFjayhyZXNwb25zZSA/IHJlc3BvbnNlLm1ldGFkYXRhIDogbnVsbCk7CgogICAgZGVsZXRlIGJsb2JzQXdhaXRpbmdNZXRhZGF0YVt1dWlkXTsKICB9CgogIGFwaUZ1bmN0aW9ucy5zZXRIYW5kbGVSZXF1ZXN0KCdnZXRNZXRhZGF0YScsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZnVuY3Rpb24obWVkaWFGaWxlLCBvcHRpb25zLCBjYWxsYmFjaykgewogICAgdmFyIGJsb2JVdWlkID0gYmxvYk5hdGl2ZXMuR2V0QmxvYlV1aWQobWVkaWFGaWxlKQogICAgLy8gU3RvcmUgdGhlIGJsb2IgaW4gYSBnbG9iYWwgb2JqZWN0IHRvIGtlZXAgaXRzIHJlZmNvdW50IG5vbnplcm8gLS0gdGhpcwogICAgLy8gcHJldmVudHMgdGhlIG9iamVjdCBmcm9tIGJlaW5nIGdhcmJhZ2UgY29sbGVjdGVkIGJlZm9yZSBhbnkgbWV0YWRhdGEKICAgIC8vIHBhcnNpbmcgZ2V0cyB0byBvY2N1ciAoc2VlIGNyYnVnLmNvbS80MTU3OTIpLgogICAgYmxvYnNBd2FpdGluZ01ldGFkYXRhW2Jsb2JVdWlkXSA9IG1lZGlhRmlsZTsKCiAgICB2YXIgb3B0QXJncyA9IHsKICAgICAgX19wcm90b19fOiBudWxsLAogICAgICBjdXN0b21DYWxsYmFjazogJEZ1bmN0aW9uLmJpbmQoZ2V0TWV0YWRhdGFDYWxsYmFjaywgbnVsbCwgYmxvYlV1aWQpLAogICAgfTsKCiAgICBzZW5kUmVxdWVzdCgnbWVkaWFHYWxsZXJpZXMuZ2V0TWV0YWRhdGEnLCBbYmxvYlV1aWQsIG9wdGlvbnMsIGNhbGxiYWNrXSwKICAgICAgICAgICAgICAgIGJpbmRpbmdVdGlsID8gdW5kZWZpbmVkIDogdGhpcy5kZWZpbml0aW9uLnBhcmFtZXRlcnMsIG9wdEFyZ3MpOwogIH0pOwp9KTsKCmlmICghYXBpQnJpZGdlKQogIGV4cG9ydHMuJHNldCgnYmluZGluZycsIGJpbmRpbmcuZ2VuZXJhdGUoKSk7Ci8vIENvcHlyaWdodCAyMDEzIFRoZSBDaHJvbWl1bSBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgovLyBVc2Ugb2YgdGhpcyBzb3VyY2UgY29kZSBpcyBnb3Zlcm5lZCBieSBhIEJTRC1zdHlsZSBsaWNlbnNlIHRoYXQgY2FuIGJlCi8vIGZvdW5kIGluIHRoZSBMSUNFTlNFIGZpbGUuCgovLyBDdXN0b20gYmluZGluZ3MgZm9yIHRoZSBub3RpZmljYXRpb25zIEFQSS4KLy8KdmFyIGJpbmRpbmcgPSBhcGlCcmlkZ2UgfHwgcmVxdWlyZSgnYmluZGluZycpLkJpbmRpbmcuY3JlYXRlKCdub3RpZmljYXRpb25zJyk7Cgp2YXIgc2VuZFJlcXVlc3QgPSBiaW5kaW5nVXRpbCA/CiAgICAkRnVuY3Rpb24uYmluZChiaW5kaW5nVXRpbC5zZW5kUmVxdWVzdCwgYmluZGluZ1V0aWwpIDoKICAgIHJlcXVpcmUoJ3NlbmRSZXF1ZXN0Jykuc2VuZFJlcXVlc3Q7CnZhciBleGNlcHRpb25IYW5kbGVyID0gcmVxdWlyZSgndW5jYXVnaHRfZXhjZXB0aW9uX2hhbmRsZXInKTsKdmFyIGltYWdlVXRpbCA9IHJlcXVpcmUoJ2ltYWdlVXRpbCcpOwp2YXIgbm90aWZpY2F0aW9uc1ByaXZhdGUgPSByZXF1aXJlTmF0aXZlKCdub3RpZmljYXRpb25zX3ByaXZhdGUnKTsKCnZhciBqc0xhc3RFcnJvciA9IGJpbmRpbmdVdGlsID8gdW5kZWZpbmVkIDogcmVxdWlyZSgnbGFzdEVycm9yJyk7CmZ1bmN0aW9uIHJ1bkNhbGxiYWNrV2l0aExhc3RFcnJvcihuYW1lLCBtZXNzYWdlLCBzdGFjaywgY2FsbGJhY2ssIGFyZ3MpIHsKICBpZiAoYmluZGluZ1V0aWwpIHsKICAgIGJpbmRpbmdVdGlsLnJ1bkNhbGxiYWNrV2l0aExhc3RFcnJvcihtZXNzYWdlLCBmdW5jdGlvbigpIHsKICAgICAgJEZ1bmN0aW9uLmFwcGx5KGNhbGxiYWNrLCBudWxsLCBhcmdzKTsKICAgIH0pOwogIH0gZWxzZSB7CiAgICBqc0xhc3RFcnJvci5ydW4obmFtZSwgbWVzc2FnZSwgc3RhY2ssIGNhbGxiYWNrLCBhcmdzKTsKICB9Cn0KCmZ1bmN0aW9uIGltYWdlRGF0YVNldHRlcihjb250ZXh0LCBrZXkpIHsKICB2YXIgZiA9IGZ1bmN0aW9uKHZhbCkgewogICAgdGhpc1trZXldID0gdmFsOwogIH07CiAgcmV0dXJuICRGdW5jdGlvbi5iaW5kKGYsIGNvbnRleHQpOwp9CgovLyBBIFVSTCBTcGVjIGlzIGFuIG9iamVjdCB3aXRoIHRoZSBmb2xsb3dpbmcga2V5czoKLy8gIHBhdGg6IFRoZSByZXNvdXJjZSB0byBiZSBkb3dubG9hZGVkLgovLyAgd2lkdGg6IChvcHRpb25hbCkgVGhlIG1heGltdW0gd2lkdGggb2YgdGhlIGltYWdlIHRvIGJlIGRvd25sb2FkZWQgaW4gZGV2aWNlCi8vICAgICAgICAgcGl4ZWxzLgovLyAgaGVpZ2h0OiAob3B0aW9uYWwpIFRoZSBtYXhpbXVtIGhlaWdodCBvZiB0aGUgaW1hZ2UgdG8gYmUgZG93bmxvYWRlZCBpbgovLyAgICAgICAgICBkZXZpY2UgcGl4ZWxzLgovLyAgY2FsbGJhY2s6IEEgZnVuY3Rpb24gdG8gYmUgY2FsbGVkIHdoZW4gdGhlIFVSTCBpcyBjb21wbGV0ZS4gSXQKLy8gICAgc2hvdWxkIGFjY2VwdCBhbiBJbWFnZURhdGEgb2JqZWN0IGFuZCBzZXQgdGhlIGFwcHJvcHJpYXRlCi8vICAgIGZpZWxkIGluIHxub3RpZmljYXRpb25EZXRhaWxzfC4KZnVuY3Rpb24gZ2V0VXJsU3BlY3MoaW1hZ2VTaXplcywgbm90aWZpY2F0aW9uRGV0YWlscykgewogIHZhciB1cmxTcGVjcyA9IFtdOwoKICAvLyB8aWNvblVybHwgbWlnaHQgYmUgb3B0aW9uYWwgZm9yIG5vdGlmaWNhdGlvbiB1cGRhdGVzLgogIGlmIChub3RpZmljYXRpb25EZXRhaWxzLmljb25VcmwpIHsKICAgICRBcnJheS5wdXNoKHVybFNwZWNzLCB7CiAgICAgIHBhdGg6IG5vdGlmaWNhdGlvbkRldGFpbHMuaWNvblVybCwKICAgICAgd2lkdGg6IGltYWdlU2l6ZXMuaWNvbi53aWR0aCAqIGltYWdlU2l6ZXMuc2NhbGVGYWN0b3IsCiAgICAgIGhlaWdodDogaW1hZ2VTaXplcy5pY29uLmhlaWdodCAqIGltYWdlU2l6ZXMuc2NhbGVGYWN0b3IsCiAgICAgIGNhbGxiYWNrOiBpbWFnZURhdGFTZXR0ZXIobm90aWZpY2F0aW9uRGV0YWlscywgJ2ljb25CaXRtYXAnKQogICAgfSk7CiAgfQoKICAvLyB8YXBwSWNvbk1hc2tVcmx8IGlzIG9wdGlvbmFsLgogIGlmIChub3RpZmljYXRpb25EZXRhaWxzLmFwcEljb25NYXNrVXJsKSB7CiAgICAkQXJyYXkucHVzaCh1cmxTcGVjcywgewogICAgICBwYXRoOiBub3RpZmljYXRpb25EZXRhaWxzLmFwcEljb25NYXNrVXJsLAogICAgICB3aWR0aDogaW1hZ2VTaXplcy5hcHBJY29uTWFzay53aWR0aCAqIGltYWdlU2l6ZXMuc2NhbGVGYWN0b3IsCiAgICAgIGhlaWdodDogaW1hZ2VTaXplcy5hcHBJY29uTWFzay5oZWlnaHQgKiBpbWFnZVNpemVzLnNjYWxlRmFjdG9yLAogICAgICBjYWxsYmFjazogaW1hZ2VEYXRhU2V0dGVyKG5vdGlmaWNhdGlvbkRldGFpbHMsICdhcHBJY29uTWFza0JpdG1hcCcpCiAgICB9KTsKICB9CgogIC8vIHxpbWFnZVVybHwgaXMgb3B0aW9uYWwuCiAgaWYgKG5vdGlmaWNhdGlvbkRldGFpbHMuaW1hZ2VVcmwpIHsKICAgICRBcnJheS5wdXNoKHVybFNwZWNzLCB7CiAgICAgIHBhdGg6IG5vdGlmaWNhdGlvbkRldGFpbHMuaW1hZ2VVcmwsCiAgICAgIHdpZHRoOiBpbWFnZVNpemVzLmltYWdlLndpZHRoICogaW1hZ2VTaXplcy5zY2FsZUZhY3RvciwKICAgICAgaGVpZ2h0OiBpbWFnZVNpemVzLmltYWdlLmhlaWdodCAqIGltYWdlU2l6ZXMuc2NhbGVGYWN0b3IsCiAgICAgIGNhbGxiYWNrOiBpbWFnZURhdGFTZXR0ZXIobm90aWZpY2F0aW9uRGV0YWlscywgJ2ltYWdlQml0bWFwJykKICAgIH0pOwogIH0KCiAgLy8gRWFjaCBidXR0b24gaGFzIGFuIG9wdGlvbmFsIGljb24uCiAgdmFyIGJ1dHRvbkxpc3QgPSBub3RpZmljYXRpb25EZXRhaWxzLmJ1dHRvbnM7CiAgaWYgKGJ1dHRvbkxpc3QgJiYgdHlwZW9mIGJ1dHRvbkxpc3QubGVuZ3RoID09PSAnbnVtYmVyJykgewogICAgdmFyIG51bUJ1dHRvbnMgPSBidXR0b25MaXN0Lmxlbmd0aDsKICAgIGZvciAodmFyIGkgPSAwOyBpIDwgbnVtQnV0dG9uczsgaSsrKSB7CiAgICAgIGlmIChidXR0b25MaXN0W2ldLmljb25VcmwpIHsKICAgICAgICAkQXJyYXkucHVzaCh1cmxTcGVjcywgewogICAgICAgICAgcGF0aDogYnV0dG9uTGlzdFtpXS5pY29uVXJsLAogICAgICAgICAgd2lkdGg6IGltYWdlU2l6ZXMuYnV0dG9uSWNvbi53aWR0aCAqIGltYWdlU2l6ZXMuc2NhbGVGYWN0b3IsCiAgICAgICAgICBoZWlnaHQ6IGltYWdlU2l6ZXMuYnV0dG9uSWNvbi5oZWlnaHQgKiBpbWFnZVNpemVzLnNjYWxlRmFjdG9yLAogICAgICAgICAgY2FsbGJhY2s6IGltYWdlRGF0YVNldHRlcihidXR0b25MaXN0W2ldLCAnaWNvbkJpdG1hcCcpCiAgICAgICAgfSk7CiAgICAgIH0KICAgIH0KICB9CgogIHJldHVybiB1cmxTcGVjczsKfQoKZnVuY3Rpb24gcmVwbGFjZU5vdGlmaWNhdGlvbk9wdGlvblVSTHMobm90aWZpY2F0aW9uX2RldGFpbHMsIGNhbGxiYWNrKSB7CiAgdmFyIGltYWdlU2l6ZXMgPSBub3RpZmljYXRpb25zUHJpdmF0ZS5HZXROb3RpZmljYXRpb25JbWFnZVNpemVzKCk7CiAgdmFyIHVybF9zcGVjcyA9IGdldFVybFNwZWNzKGltYWdlU2l6ZXMsIG5vdGlmaWNhdGlvbl9kZXRhaWxzKTsKICBpZiAoIXVybF9zcGVjcy5sZW5ndGgpIHsKICAgIGNhbGxiYWNrKHRydWUpOwogICAgcmV0dXJuOwogIH0KCiAgdmFyIGVycm9ycyA9IDA7CgogIGltYWdlVXRpbC5sb2FkQWxsSW1hZ2VzKHVybF9zcGVjcywgewogICAgb25lcnJvcjogZnVuY3Rpb24oaW5kZXgpIHsKICAgICAgZXJyb3JzKys7CiAgICB9LAogICAgb25jb21wbGV0ZTogZnVuY3Rpb24oaW1hZ2VEYXRhKSB7CiAgICAgIGlmIChlcnJvcnMgPiAwKSB7CiAgICAgICAgY2FsbGJhY2soZmFsc2UpOwogICAgICAgIHJldHVybjsKICAgICAgfQogICAgICBmb3IgKHZhciBpbmRleCA9IDA7IGluZGV4IDwgdXJsX3NwZWNzLmxlbmd0aDsgaW5kZXgrKykgewogICAgICAgIHZhciB1cmxfc3BlYyA9IHVybF9zcGVjc1tpbmRleF07CiAgICAgICAgdXJsX3NwZWMuY2FsbGJhY2soaW1hZ2VEYXRhW2luZGV4XSk7CiAgICAgIH0KICAgICAgY2FsbGJhY2sodHJ1ZSk7CiAgICB9CiAgfSk7Cn0KCmZ1bmN0aW9uIGdlbkhhbmRsZShuYW1lLCBmYWlsdXJlX2Z1bmN0aW9uKSB7CiAgcmV0dXJuIGZ1bmN0aW9uKGlkLCBpbnB1dF9ub3RpZmljYXRpb25fZGV0YWlscywgY2FsbGJhY2spIHsKICAgIC8vIFRPRE8oZGV3aXR0aik6IFJlbW92ZSB0aGlzIGhhY2suIFRoaXMgaXMgdXNlZCBhcyBhIHdheSB0byBkZWVwCiAgICAvLyBjb3B5IGEgY29tcGxleCBKU09OIG9iamVjdC4KICAgIHZhciBub3RpZmljYXRpb25fZGV0YWlscyA9ICRKU09OLnBhcnNlKAogICAgICAgICRKU09OLnN0cmluZ2lmeShpbnB1dF9ub3RpZmljYXRpb25fZGV0YWlscykpOwogICAgdmFyIHRoYXQgPSB0aGlzOwogICAgdmFyIHN0YWNrID0gZXhjZXB0aW9uSGFuZGxlci5nZXRFeHRlbnNpb25TdGFja1RyYWNlKCk7CiAgICByZXBsYWNlTm90aWZpY2F0aW9uT3B0aW9uVVJMcyhub3RpZmljYXRpb25fZGV0YWlscywgZnVuY3Rpb24oc3VjY2VzcykgewogICAgICBpZiAoc3VjY2VzcykgewogICAgICAgIHNlbmRSZXF1ZXN0KAogICAgICAgICAgICBuYW1lLCBbaWQsIG5vdGlmaWNhdGlvbl9kZXRhaWxzLCBjYWxsYmFja10sCiAgICAgICAgICAgIGJpbmRpbmdVdGlsID8gdW5kZWZpbmVkIDogdGhhdC5kZWZpbml0aW9uLnBhcmFtZXRlcnMsCiAgICAgICAgICAgIGJpbmRpbmdVdGlsID8gdW5kZWZpbmVkIDoge19fcHJvdG9fXzogbnVsbCwgc3RhY2s6IHN0YWNrfSk7CiAgICAgICAgcmV0dXJuOwogICAgICB9CiAgICAgIHJ1bkNhbGxiYWNrV2l0aExhc3RFcnJvcigKICAgICAgICAgIG5hbWUsICdVbmFibGUgdG8gZG93bmxvYWQgYWxsIHNwZWNpZmllZCBpbWFnZXMuJywKICAgICAgICAgIHN0YWNrLCBmYWlsdXJlX2Z1bmN0aW9uLCBbY2FsbGJhY2sgfHwgZnVuY3Rpb24oKSB7fSwgaWRdKTsKICAgIH0pOwogIH07Cn0KCnZhciBoYW5kbGVDcmVhdGUgPSBnZW5IYW5kbGUoJ25vdGlmaWNhdGlvbnMuY3JlYXRlJywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICBmdW5jdGlvbihjYWxsYmFjaywgaWQpIHsgY2FsbGJhY2soaWQpOyB9KTsKdmFyIGhhbmRsZVVwZGF0ZSA9IGdlbkhhbmRsZSgnbm90aWZpY2F0aW9ucy51cGRhdGUnLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgIGZ1bmN0aW9uKGNhbGxiYWNrLCBpZCkgeyBjYWxsYmFjayhmYWxzZSk7IH0pOwoKdmFyIG5vdGlmaWNhdGlvbnNDdXN0b21Ib29rID0gZnVuY3Rpb24oYmluZGluZ3NBUEksIGV4dGVuc2lvbklkKSB7CiAgdmFyIGFwaUZ1bmN0aW9ucyA9IGJpbmRpbmdzQVBJLmFwaUZ1bmN0aW9uczsKICBhcGlGdW5jdGlvbnMuc2V0SGFuZGxlUmVxdWVzdCgnY3JlYXRlJywgaGFuZGxlQ3JlYXRlKTsKICBhcGlGdW5jdGlvbnMuc2V0SGFuZGxlUmVxdWVzdCgndXBkYXRlJywgaGFuZGxlVXBkYXRlKTsKfTsKCmJpbmRpbmcucmVnaXN0ZXJDdXN0b21Ib29rKG5vdGlmaWNhdGlvbnNDdXN0b21Ib29rKTsKCmlmICghYXBpQnJpZGdlKQogIGV4cG9ydHMuJHNldCgnYmluZGluZycsIGJpbmRpbmcuZ2VuZXJhdGUoKSk7Ci8vIENvcHlyaWdodCAoYykgMjAxMiBUaGUgQ2hyb21pdW0gQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KLy8gVXNlIG9mIHRoaXMgc291cmNlIGNvZGUgaXMgZ292ZXJuZWQgYnkgYSBCU0Qtc3R5bGUgbGljZW5zZSB0aGF0IGNhbiBiZQovLyBmb3VuZCBpbiB0aGUgTElDRU5TRSBmaWxlLgoKLy8gQ3VzdG9tIGJpbmRpbmcgZm9yIHRoZSBvbW5pYm94IEFQSS4gT25seSBpbmplY3RlZCBpbnRvIHRoZSB2OCBjb250ZXh0cwovLyBmb3IgZXh0ZW5zaW9ucyB3aGljaCBoYXZlIHBlcm1pc3Npb24gZm9yIHRoZSBvbW5pYm94IEFQSS4KCnZhciBiaW5kaW5nID0gYXBpQnJpZGdlIHx8IHJlcXVpcmUoJ2JpbmRpbmcnKS5CaW5kaW5nLmNyZWF0ZSgnb21uaWJveCcpOwoKdmFyIHJlZ2lzdGVyQXJndW1lbnRNYXNzYWdlciA9IGJpbmRpbmdVdGlsID8KICAgICRGdW5jdGlvbi5iaW5kKGJpbmRpbmdVdGlsLnJlZ2lzdGVyRXZlbnRBcmd1bWVudE1hc3NhZ2VyLCBiaW5kaW5nVXRpbCkgOgogICAgcmVxdWlyZSgnZXZlbnRfYmluZGluZ3MnKS5yZWdpc3RlckFyZ3VtZW50TWFzc2FnZXI7Cgp2YXIgc2VuZFJlcXVlc3QgPSBiaW5kaW5nVXRpbCA/CiAgICAkRnVuY3Rpb24uYmluZChiaW5kaW5nVXRpbC5zZW5kUmVxdWVzdCwgYmluZGluZ1V0aWwpIDoKICAgIHJlcXVpcmUoJ3NlbmRSZXF1ZXN0Jykuc2VuZFJlcXVlc3Q7CgovLyBSZW1vdmUgaW52YWxpZCBjaGFyYWN0ZXJzIGZyb20gfHRleHR8IHNvIHRoYXQgaXQgaXMgc3VpdGFibGUgdG8gdXNlCi8vIGZvciB8QXV0b2NvbXBsZXRlTWF0Y2g6OmNvbnRlbnRzfC4KZnVuY3Rpb24gc2FuaXRpemVTdHJpbmcodGV4dCwgc2hvdWxkVHJpbSkgewogIC8vIE5PVEU6IFRoaXMgbG9naWMgbWlycm9ycyB8QXV0b2NvbXBsZXRlTWF0Y2g6OlNhbml0aXplU3RyaW5nKCl8LgogIC8vIDB4MjAyOCA9IGxpbmUgc2VwYXJhdG9yOyAweDIwMjkgPSBwYXJhZ3JhcGggc2VwYXJhdG9yLgogIHZhciBrUmVtb3ZlQ2hhcnMgPSAvKFxyfFxufFx0fFx1MjAyOHxcdTIwMjkpL2dtOwogIGlmIChzaG91bGRUcmltKQogICAgdGV4dCA9IHRleHQudHJpbUxlZnQoKTsKICByZXR1cm4gdGV4dC5yZXBsYWNlKGtSZW1vdmVDaGFycywgJycpOwp9CgovLyBQYXJzZXMgdGhlIHhtbCBzeW50YXggc3VwcG9ydGVkIGJ5IG9tbmlib3ggc3VnZ2VzdGlvbiByZXN1bHRzLiBSZXR1cm5zIGFuCi8vIG9iamVjdCB3aXRoIHR3byBwcm9wZXJ0aWVzOiAnZGVzY3JpcHRpb24nLCB3aGljaCBpcyBqdXN0IHRoZSB0ZXh0IGNvbnRlbnQsCi8vIGFuZCAnZGVzY3JpcHRpb25TdHlsZXMnLCB3aGljaCBpcyBhbiBhcnJheSBvZiBzdHlsZSBvYmplY3RzIGluIGEgZm9ybWF0Ci8vIHVuZGVyc3Rvb2QgYnkgdGhlIEMrKyBiYWNrZW5kLgpmdW5jdGlvbiBwYXJzZU9tbmlib3hEZXNjcmlwdGlvbihpbnB1dCkgewogIHZhciBkb21QYXJzZXIgPSBuZXcgRE9NUGFyc2VyKCk7CgogIC8vIFRoZSBYTUwgcGFyc2VyIHJlcXVpcmVzIGEgc2luZ2xlIHRvcC1sZXZlbCBlbGVtZW50LCBidXQgd2Ugd2FudCB0bwogIC8vIHN1cHBvcnQgdGhpbmdzIGxpa2UgJ2hlbGxvLCA8bWF0Y2g+d29ybGQ8L21hdGNoPiEnLiBTbyB3ZSB3cmFwIHRoZQogIC8vIHByb3ZpZGVkIHRleHQgaW4gZ2VuZXJhdGVkIHJvb3QgbGV2ZWwgZWxlbWVudC4KICB2YXIgcm9vdCA9IGRvbVBhcnNlci5wYXJzZUZyb21TdHJpbmcoCiAgICAgICc8ZnJhZ21lbnQ+JyArIGlucHV0ICsgJzwvZnJhZ21lbnQ+JywgJ3RleHQveG1sJyk7CgogIC8vIERPTVBhcnNlciBoYXMgYSB0ZXJyaWJsZSBlcnJvciByZXBvcnRpbmcgZmFjaWxpdHkuIEVycm9ycyBjb21lIG91dCBuZXN0ZWQKICAvLyBpbnNpZGUgdGhlIHJldHVybmVkIGRvY3VtZW50LgogIHZhciBlcnJvciA9IHJvb3QucXVlcnlTZWxlY3RvcigncGFyc2VyZXJyb3IgZGl2Jyk7CiAgaWYgKGVycm9yKSB7CiAgICB0aHJvdyBuZXcgRXJyb3IoZXJyb3IudGV4dENvbnRlbnQpOwogIH0KCiAgLy8gT3RoZXJ3aXNlLCBpdCdzIHZhbGlkLCBzbyBidWlsZCB1cCB0aGUgcmVzdWx0LgogIHZhciByZXN1bHQgPSB7CiAgICBkZXNjcmlwdGlvbjogJycsCiAgICBkZXNjcmlwdGlvblN0eWxlczogW10KICB9OwoKICAvLyBSZWN1cnNpdmVseSB3YWxrIHRoZSB0cmVlLgogIGZ1bmN0aW9uIHdhbGsobm9kZSkgewogICAgZm9yICh2YXIgaSA9IDAsIGNoaWxkOyBjaGlsZCA9IG5vZGUuY2hpbGROb2Rlc1tpXTsgaSsrKSB7CiAgICAgIC8vIEFwcGVuZCB0ZXh0IG5vZGVzIHRvIG91ciBkZXNjcmlwdGlvbi4KICAgICAgaWYgKGNoaWxkLm5vZGVUeXBlID09IE5vZGUuVEVYVF9OT0RFKSB7CiAgICAgICAgdmFyIHNob3VsZFRyaW0gPSByZXN1bHQuZGVzY3JpcHRpb24ubGVuZ3RoID09IDA7CiAgICAgICAgcmVzdWx0LmRlc2NyaXB0aW9uICs9IHNhbml0aXplU3RyaW5nKGNoaWxkLm5vZGVWYWx1ZSwgc2hvdWxkVHJpbSk7CiAgICAgICAgY29udGludWU7CiAgICAgIH0KCiAgICAgIC8vIFByb2Nlc3MgYW5kIGRlc2NlbmQgaW50byBhIHN1YnNldCBvZiByZWNvZ25pemVkIHRhZ3MuCiAgICAgIGlmIChjaGlsZC5ub2RlVHlwZSA9PSBOb2RlLkVMRU1FTlRfTk9ERSAmJgogICAgICAgICAgKGNoaWxkLm5vZGVOYW1lID09ICdkaW0nIHx8IGNoaWxkLm5vZGVOYW1lID09ICdtYXRjaCcgfHwKICAgICAgICAgICBjaGlsZC5ub2RlTmFtZSA9PSAndXJsJykpIHsKICAgICAgICB2YXIgc3R5bGUgPSB7CiAgICAgICAgICAndHlwZSc6IGNoaWxkLm5vZGVOYW1lLAogICAgICAgICAgJ29mZnNldCc6IHJlc3VsdC5kZXNjcmlwdGlvbi5sZW5ndGgKICAgICAgICB9OwogICAgICAgICRBcnJheS5wdXNoKHJlc3VsdC5kZXNjcmlwdGlvblN0eWxlcywgc3R5bGUpOwogICAgICAgIHdhbGsoY2hpbGQpOwogICAgICAgIHN0eWxlLmxlbmd0aCA9IHJlc3VsdC5kZXNjcmlwdGlvbi5sZW5ndGggLSBzdHlsZS5vZmZzZXQ7CiAgICAgICAgY29udGludWU7CiAgICAgIH0KCiAgICAgIC8vIERlc2NlbmQgaW50byBhbGwgb3RoZXIgbm9kZXMsIGV2ZW4gaWYgdGhleSBhcmUgdW5yZWNvZ25pemVkLCBmb3IKICAgICAgLy8gZm9yd2FyZCBjb21wYXQuCiAgICAgIHdhbGsoY2hpbGQpOwogICAgfQogIH07CiAgd2Fsayhyb290KTsKCiAgcmV0dXJuIHJlc3VsdDsKfQoKYmluZGluZy5yZWdpc3RlckN1c3RvbUhvb2soZnVuY3Rpb24oYmluZGluZ3NBUEkpIHsKICB2YXIgYXBpRnVuY3Rpb25zID0gYmluZGluZ3NBUEkuYXBpRnVuY3Rpb25zOwoKICBhcGlGdW5jdGlvbnMuc2V0VXBkYXRlQXJndW1lbnRzUHJlVmFsaWRhdGUoJ3NldERlZmF1bHRTdWdnZXN0aW9uJywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZnVuY3Rpb24oc3VnZ2VzdFJlc3VsdCkgewogICAgaWYgKHN1Z2dlc3RSZXN1bHQuY29udGVudCAhPSB1bmRlZmluZWQpIHsgIC8vIG51bGwsIGV0Yy4KICAgICAgdGhyb3cgbmV3IEVycm9yKAogICAgICAgICAgJ3NldERlZmF1bHRTdWdnZXN0aW9uIGNhbm5vdCBjb250YWluIHRoZSAiY29udGVudCIgZmllbGQnKTsKICAgIH0KICAgIHJldHVybiBbc3VnZ2VzdFJlc3VsdF07CiAgfSk7CgogIGFwaUZ1bmN0aW9ucy5zZXRIYW5kbGVSZXF1ZXN0KCdzZXREZWZhdWx0U3VnZ2VzdGlvbicsIGZ1bmN0aW9uKGRldGFpbHMpIHsKICAgIHZhciBwYXJzZVJlc3VsdCA9IHBhcnNlT21uaWJveERlc2NyaXB0aW9uKGRldGFpbHMuZGVzY3JpcHRpb24pOwogICAgc2VuZFJlcXVlc3QoJ29tbmlib3guc2V0RGVmYXVsdFN1Z2dlc3Rpb24nLCBbcGFyc2VSZXN1bHRdLAogICAgICAgICAgICAgICAgYmluZGluZ1V0aWwgPyB1bmRlZmluZWQgOiB0aGlzLmRlZmluaXRpb24ucGFyYW1ldGVycywKICAgICAgICAgICAgICAgIHVuZGVmaW5lZCk7CiAgfSk7CgogIGFwaUZ1bmN0aW9ucy5zZXRVcGRhdGVBcmd1bWVudHNQb3N0VmFsaWRhdGUoCiAgICAgICdzZW5kU3VnZ2VzdGlvbnMnLCBmdW5jdGlvbihyZXF1ZXN0SWQsIHVzZXJTdWdnZXN0aW9ucykgewogICAgdmFyIHN1Z2dlc3Rpb25zID0gW107CiAgICBmb3IgKHZhciBpID0gMDsgaSA8IHVzZXJTdWdnZXN0aW9ucy5sZW5ndGg7IGkrKykgewogICAgICB2YXIgcGFyc2VSZXN1bHQgPSBwYXJzZU9tbmlib3hEZXNjcmlwdGlvbigKICAgICAgICAgIHVzZXJTdWdnZXN0aW9uc1tpXS5kZXNjcmlwdGlvbik7CiAgICAgIHBhcnNlUmVzdWx0LmNvbnRlbnQgPSB1c2VyU3VnZ2VzdGlvbnNbaV0uY29udGVudDsKICAgICAgcGFyc2VSZXN1bHQuZGVsZXRhYmxlID0gdXNlclN1Z2dlc3Rpb25zW2ldLmRlbGV0YWJsZTsKICAgICAgJEFycmF5LnB1c2goc3VnZ2VzdGlvbnMsIHBhcnNlUmVzdWx0KTsKICAgIH0KICAgIHJldHVybiBbcmVxdWVzdElkLCBzdWdnZXN0aW9uc107CiAgfSk7Cn0pOwoKcmVnaXN0ZXJBcmd1bWVudE1hc3NhZ2VyKCdvbW5pYm94Lm9uSW5wdXRDaGFuZ2VkJywgZnVuY3Rpb24oYXJncywgZGlzcGF0Y2gpIHsKICB2YXIgdGV4dCA9IGFyZ3NbMF07CiAgdmFyIHJlcXVlc3RJZCA9IGFyZ3NbMV07CiAgdmFyIHN1Z2dlc3RDYWxsYmFjayA9IGZ1bmN0aW9uKHN1Z2dlc3Rpb25zKSB7CiAgICBjaHJvbWUub21uaWJveC5zZW5kU3VnZ2VzdGlvbnMocmVxdWVzdElkLCBzdWdnZXN0aW9ucyk7CiAgfTsKICBkaXNwYXRjaChbdGV4dCwgc3VnZ2VzdENhbGxiYWNrXSk7Cn0pOwoKaWYgKCFhcGlCcmlkZ2UpCiAgZXhwb3J0cy4kc2V0KCdiaW5kaW5nJywgYmluZGluZy5nZW5lcmF0ZSgpKTsKLy8gQ29weXJpZ2h0IChjKSAyMDEyIFRoZSBDaHJvbWl1bSBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgovLyBVc2Ugb2YgdGhpcyBzb3VyY2UgY29kZSBpcyBnb3Zlcm5lZCBieSBhIEJTRC1zdHlsZSBsaWNlbnNlIHRoYXQgY2FuIGJlCi8vIGZvdW5kIGluIHRoZSBMSUNFTlNFIGZpbGUuCgovLyBDdXN0b20gYmluZGluZyBmb3IgdGhlIHBhZ2VBY3Rpb24gQVBJLgoKdmFyIGJpbmRpbmcgPSBhcGlCcmlkZ2UgfHwgcmVxdWlyZSgnYmluZGluZycpLkJpbmRpbmcuY3JlYXRlKCdwYWdlQWN0aW9uJyk7CnZhciBzZXRJY29uID0gcmVxdWlyZSgnc2V0SWNvbicpLnNldEljb247CnZhciBzZW5kUmVxdWVzdCA9IGJpbmRpbmdVdGlsID8KICAgICRGdW5jdGlvbi5iaW5kKGJpbmRpbmdVdGlsLnNlbmRSZXF1ZXN0LCBiaW5kaW5nVXRpbCkgOgogICAgcmVxdWlyZSgnc2VuZFJlcXVlc3QnKS5zZW5kUmVxdWVzdDsKCmJpbmRpbmcucmVnaXN0ZXJDdXN0b21Ib29rKGZ1bmN0aW9uKGJpbmRpbmdzQVBJKSB7CiAgdmFyIGFwaUZ1bmN0aW9ucyA9IGJpbmRpbmdzQVBJLmFwaUZ1bmN0aW9uczsKCiAgYXBpRnVuY3Rpb25zLnNldEhhbmRsZVJlcXVlc3QoJ3NldEljb24nLCBmdW5jdGlvbihkZXRhaWxzLCBjYWxsYmFjaykgewogICAgc2V0SWNvbihkZXRhaWxzLCAkRnVuY3Rpb24uYmluZChmdW5jdGlvbihhcmdzKSB7CiAgICAgIHNlbmRSZXF1ZXN0KCdwYWdlQWN0aW9uLnNldEljb24nLCBbYXJncywgY2FsbGJhY2tdLAogICAgICAgICAgICAgICAgICBiaW5kaW5nVXRpbCA/IHVuZGVmaW5lZCA6IHRoaXMuZGVmaW5pdGlvbi5wYXJhbWV0ZXJzLAogICAgICAgICAgICAgICAgICB1bmRlZmluZWQpOwogICAgfSwgdGhpcykpOwogIH0pOwp9KTsKCmlmICghYXBpQnJpZGdlKQogIGV4cG9ydHMuJHNldCgnYmluZGluZycsIGJpbmRpbmcuZ2VuZXJhdGUoKSk7Ci8vIENvcHlyaWdodCAoYykgMjAxMiBUaGUgQ2hyb21pdW0gQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KLy8gVXNlIG9mIHRoaXMgc291cmNlIGNvZGUgaXMgZ292ZXJuZWQgYnkgYSBCU0Qtc3R5bGUgbGljZW5zZSB0aGF0IGNhbiBiZQovLyBmb3VuZCBpbiB0aGUgTElDRU5TRSBmaWxlLgoKLy8gQ3VzdG9tIGJpbmRpbmcgZm9yIHRoZSBwYWdlQ2FwdHVyZSBBUEkuCgp2YXIgYmluZGluZyA9IGFwaUJyaWRnZSB8fCByZXF1aXJlKCdiaW5kaW5nJykuQmluZGluZy5jcmVhdGUoJ3BhZ2VDYXB0dXJlJyk7Cgp2YXIgaGFuZGxlVW5jYXVnaHRFeGNlcHRpb24gPSByZXF1aXJlKCd1bmNhdWdodF9leGNlcHRpb25faGFuZGxlcicpLmhhbmRsZTsKdmFyIHBhZ2VDYXB0dXJlTmF0aXZlcyA9IHJlcXVpcmVOYXRpdmUoJ3BhZ2VfY2FwdHVyZScpOwp2YXIgQ3JlYXRlQmxvYiA9IHBhZ2VDYXB0dXJlTmF0aXZlcy5DcmVhdGVCbG9iOwp2YXIgU2VuZFJlc3BvbnNlQWNrID0gcGFnZUNhcHR1cmVOYXRpdmVzLlNlbmRSZXNwb25zZUFjazsKCmJpbmRpbmcucmVnaXN0ZXJDdXN0b21Ib29rKGZ1bmN0aW9uKGJpbmRpbmdzQVBJKSB7CiAgdmFyIGFwaUZ1bmN0aW9ucyA9IGJpbmRpbmdzQVBJLmFwaUZ1bmN0aW9uczsKCiAgYXBpRnVuY3Rpb25zLnNldEN1c3RvbUNhbGxiYWNrKCdzYXZlQXNNSFRNTCcsCiAgICAgIGZ1bmN0aW9uKG5hbWUsIHJlcXVlc3QsIGNhbGxiYWNrLCByZXNwb25zZSkgewogICAgaWYgKHJlc3BvbnNlKQogICAgICByZXNwb25zZSA9IENyZWF0ZUJsb2IocmVzcG9uc2UubWh0bWxGaWxlUGF0aCwgcmVzcG9uc2UubWh0bWxGaWxlTGVuZ3RoKTsKCiAgICB0cnkgewogICAgICBjYWxsYmFjayhyZXNwb25zZSk7CiAgICB9IGNhdGNoIChlKSB7CiAgICAgIGhhbmRsZVVuY2F1Z2h0RXhjZXB0aW9uKAogICAgICAgICAgJ0Vycm9yIGluIGNocm9tZS5wYWdlQ2FwdHVyZS5zYXZlQXNNSFRNTCBjYWxsYmFjaycsIGUsIHJlcXVlc3Quc3RhY2spOwogICAgfSBmaW5hbGx5IHsKICAgICAgLy8gTm90aWZ5IHRoZSBicm93c2VyLiBOb3cgdGhhdCB0aGUgYmxvYiBpcyByZWZlcmVuY2VkIGZyb20gSmF2YVNjcmlwdCwKICAgICAgLy8gdGhlIGJyb3dzZXIgY2FuIGRyb3AgaXRzIHJlZmVyZW5jZSB0byBpdC4KICAgICAgU2VuZFJlc3BvbnNlQWNrKHJlcXVlc3QuaWQpOwogICAgfQogIH0pOwp9KTsKCmlmICghYXBpQnJpZGdlKQogIGV4cG9ydHMuJHNldCgnYmluZGluZycsIGJpbmRpbmcuZ2VuZXJhdGUoKSk7Ci8vIENvcHlyaWdodCAoYykgMjAxMiBUaGUgQ2hyb21pdW0gQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KLy8gVXNlIG9mIHRoaXMgc291cmNlIGNvZGUgaXMgZ292ZXJuZWQgYnkgYSBCU0Qtc3R5bGUgbGljZW5zZSB0aGF0IGNhbiBiZQovLyBmb3VuZCBpbiB0aGUgTElDRU5TRSBmaWxlLgoKLy8gQ3VzdG9tIGJpbmRpbmcgZm9yIHRoZSBzeW5jRmlsZVN5c3RlbSBBUEkuCgp2YXIgYmluZGluZyA9CiAgICBhcGlCcmlkZ2UgfHwgcmVxdWlyZSgnYmluZGluZycpLkJpbmRpbmcuY3JlYXRlKCdzeW5jRmlsZVN5c3RlbScpOwoKdmFyIHJlZ2lzdGVyQXJndW1lbnRNYXNzYWdlciA9IGJpbmRpbmdVdGlsID8KICAgICRGdW5jdGlvbi5iaW5kKGJpbmRpbmdVdGlsLnJlZ2lzdGVyRXZlbnRBcmd1bWVudE1hc3NhZ2VyLCBiaW5kaW5nVXRpbCkgOgogICAgcmVxdWlyZSgnZXZlbnRfYmluZGluZ3MnKS5yZWdpc3RlckFyZ3VtZW50TWFzc2FnZXI7Cgp2YXIgZmlsZVN5c3RlbU5hdGl2ZXMgPSByZXF1aXJlTmF0aXZlKCdmaWxlX3N5c3RlbV9uYXRpdmVzJyk7CnZhciBzeW5jRmlsZVN5c3RlbU5hdGl2ZXMgPSByZXF1aXJlTmF0aXZlKCdzeW5jX2ZpbGVfc3lzdGVtJyk7CgpiaW5kaW5nLnJlZ2lzdGVyQ3VzdG9tSG9vayhmdW5jdGlvbihiaW5kaW5nc0FQSSkgewogIHZhciBhcGlGdW5jdGlvbnMgPSBiaW5kaW5nc0FQSS5hcGlGdW5jdGlvbnM7CgogIC8vIEZ1bmN0aW9ucyB3aGljaCB0YWtlIGluIGFuIFtpbnN0YW5jZU9mPUZpbGVFbnRyeV0uCiAgZnVuY3Rpb24gYmluZEZpbGVFbnRyeUZ1bmN0aW9uKGZ1bmN0aW9uTmFtZSkgewogICAgYXBpRnVuY3Rpb25zLnNldFVwZGF0ZUFyZ3VtZW50c1Bvc3RWYWxpZGF0ZSgKICAgICAgICBmdW5jdGlvbk5hbWUsIGZ1bmN0aW9uKGVudHJ5LCBjYWxsYmFjaykgewogICAgICB2YXIgZmlsZVN5c3RlbVVybCA9IGVudHJ5LnRvVVJMKCk7CiAgICAgIHJldHVybiBbZmlsZVN5c3RlbVVybCwgY2FsbGJhY2tdOwogICAgfSk7CiAgfQogICRBcnJheS5mb3JFYWNoKFsnZ2V0RmlsZVN0YXR1cyddLCBiaW5kRmlsZUVudHJ5RnVuY3Rpb24pOwoKICAvLyBGdW5jdGlvbnMgd2hpY2ggdGFrZSBpbiBhIEZpbGVFbnRyeSBhcnJheS4KICBmdW5jdGlvbiBiaW5kRmlsZUVudHJ5QXJyYXlGdW5jdGlvbihmdW5jdGlvbk5hbWUpIHsKICAgIGFwaUZ1bmN0aW9ucy5zZXRVcGRhdGVBcmd1bWVudHNQb3N0VmFsaWRhdGUoCiAgICAgICAgZnVuY3Rpb25OYW1lLCBmdW5jdGlvbihlbnRyaWVzLCBjYWxsYmFjaykgewogICAgICB2YXIgZmlsZVN5c3RlbVVybEFycmF5ID0gW107CiAgICAgIGZvciAodmFyIGk9MDsgaSA8IGVudHJpZXMubGVuZ3RoOyBpKyspIHsKICAgICAgICAkQXJyYXkucHVzaChmaWxlU3lzdGVtVXJsQXJyYXksIGVudHJpZXNbaV0udG9VUkwoKSk7CiAgICAgIH0KICAgICAgcmV0dXJuIFtmaWxlU3lzdGVtVXJsQXJyYXksIGNhbGxiYWNrXTsKICAgIH0pOwogIH0KICAkQXJyYXkuZm9yRWFjaChbJ2dldEZpbGVTdGF0dXNlcyddLCBiaW5kRmlsZUVudHJ5QXJyYXlGdW5jdGlvbik7CgogIC8vIEZ1bmN0aW9ucyB3aGljaCB0YWtlIGluIGFuIFtpbnN0YW5jZU9mPURPTUZpbGVTeXN0ZW1dLgogIGZ1bmN0aW9uIGJpbmRGaWxlU3lzdGVtRnVuY3Rpb24oZnVuY3Rpb25OYW1lKSB7CiAgICBhcGlGdW5jdGlvbnMuc2V0VXBkYXRlQXJndW1lbnRzUG9zdFZhbGlkYXRlKAogICAgICAgIGZ1bmN0aW9uTmFtZSwgZnVuY3Rpb24oZmlsZXN5c3RlbSwgY2FsbGJhY2spIHsKICAgICAgdmFyIGZpbGVTeXN0ZW1VcmwgPSBmaWxlc3lzdGVtLnJvb3QudG9VUkwoKTsKICAgICAgcmV0dXJuIFtmaWxlU3lzdGVtVXJsLCBjYWxsYmFja107CiAgICB9KTsKICB9CiAgJEFycmF5LmZvckVhY2goWydnZXRVc2FnZUFuZFF1b3RhJ10sIGJpbmRGaWxlU3lzdGVtRnVuY3Rpb24pOwoKICAvLyBGdW5jdGlvbnMgd2hpY2ggcmV0dXJuIGFuIFtpbnN0YW5jZU9mPURPTUZpbGVTeXN0ZW1dLgogIGFwaUZ1bmN0aW9ucy5zZXRDdXN0b21DYWxsYmFjaygncmVxdWVzdEZpbGVTeXN0ZW0nLAogICAgICBmdW5jdGlvbihuYW1lLCByZXF1ZXN0LCBjYWxsYmFjaywgcmVzcG9uc2UpIHsKICAgIHZhciByZXN1bHQgPSBudWxsOwogICAgaWYgKHJlc3BvbnNlKSB7CiAgICAgIHJlc3VsdCA9IHN5bmNGaWxlU3lzdGVtTmF0aXZlcy5HZXRTeW5jRmlsZVN5c3RlbU9iamVjdCgKICAgICAgICAgIHJlc3BvbnNlLm5hbWUsIHJlc3BvbnNlLnJvb3QpOwogICAgfQogICAgaWYgKGNhbGxiYWNrKQogICAgICBjYWxsYmFjayhyZXN1bHQpOwogIH0pOwoKICAvLyBGdW5jdGlvbnMgd2hpY2ggcmV0dXJuIGFuIGFycmF5IG9mIEZpbGVTdGF0dXNJbmZvIG9iamVjdAogIC8vIHdoaWNoIGhhcyBbaW5zdGFuY2VPZj1GaWxlRW50cnldLgogIGFwaUZ1bmN0aW9ucy5zZXRDdXN0b21DYWxsYmFjaygnZ2V0RmlsZVN0YXR1c2VzJywKICAgICAgZnVuY3Rpb24obmFtZSwgcmVxdWVzdCwgY2FsbGJhY2ssIHJlc3BvbnNlKSB7CiAgICB2YXIgcmVzdWx0cyA9IFtdOwogICAgaWYgKHJlc3BvbnNlKSB7CiAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgcmVzcG9uc2UubGVuZ3RoOyBpKyspIHsKICAgICAgICB2YXIgcmVzdWx0ID0ge307CiAgICAgICAgdmFyIGVudHJ5ID0gcmVzcG9uc2VbaV0uZW50cnk7CiAgICAgICAgcmVzdWx0LmZpbGVFbnRyeSA9IGZpbGVTeXN0ZW1OYXRpdmVzLkdldEZpbGVFbnRyeSgKICAgICAgICAgICAgZW50cnkuZmlsZVN5c3RlbVR5cGUsCiAgICAgICAgICAgIGVudHJ5LmZpbGVTeXN0ZW1OYW1lLAogICAgICAgICAgICBlbnRyeS5yb290VXJsLAogICAgICAgICAgICBlbnRyeS5maWxlUGF0aCwKICAgICAgICAgICAgZW50cnkuaXNEaXJlY3RvcnkpOwogICAgICAgIHJlc3VsdC5zdGF0dXMgPSByZXNwb25zZVtpXS5zdGF0dXM7CiAgICAgICAgcmVzdWx0LmVycm9yID0gcmVzcG9uc2VbaV0uZXJyb3I7CiAgICAgICAgJEFycmF5LnB1c2gocmVzdWx0cywgcmVzdWx0KTsKICAgICAgfQogICAgfQogICAgaWYgKGNhbGxiYWNrKQogICAgICBjYWxsYmFjayhyZXN1bHRzKTsKICB9KTsKfSk7CgpyZWdpc3RlckFyZ3VtZW50TWFzc2FnZXIoJ3N5bmNGaWxlU3lzdGVtLm9uRmlsZVN0YXR1c0NoYW5nZWQnLAogICAgICAgICAgICAgICAgICAgICAgICAgZnVuY3Rpb24oYXJncywgZGlzcGF0Y2gpIHsKICAvLyBNYWtlIEZpbGVFbnRyeSBvYmplY3QgdXNpbmcgYWxsIHRoZSBiYXNlIHN0cmluZyBmaWVsZHMuCiAgdmFyIGZpbGVFbnRyeSA9IGZpbGVTeXN0ZW1OYXRpdmVzLkdldEZpbGVFbnRyeSgKICAgICAgYXJnc1swXS5maWxlU3lzdGVtVHlwZSwKICAgICAgYXJnc1swXS5maWxlU3lzdGVtTmFtZSwKICAgICAgYXJnc1swXS5yb290VXJsLAogICAgICBhcmdzWzBdLmZpbGVQYXRoLAogICAgICBhcmdzWzBdLmlzRGlyZWN0b3J5KTsKCiAgLy8gQ29tYmluZSBpbnRvIGEgc2luZ2xlIGRpY3Rpb25hcnkuCiAgdmFyIGZpbGVJbmZvID0gbmV3IE9iamVjdCgpOwogIGZpbGVJbmZvLmZpbGVFbnRyeSA9IGZpbGVFbnRyeTsKICBmaWxlSW5mby5zdGF0dXMgPSBhcmdzWzFdOwogIGlmIChmaWxlSW5mby5zdGF0dXMgPT0gInN5bmNlZCIpIHsKICAgIGZpbGVJbmZvLmFjdGlvbiA9IGFyZ3NbMl07CiAgICBmaWxlSW5mby5kaXJlY3Rpb24gPSBhcmdzWzNdOwogIH0KICBkaXNwYXRjaChbZmlsZUluZm9dKTsKfSk7CgppZiAoIWFwaUJyaWRnZSkKICBleHBvcnRzLiRzZXQoJ2JpbmRpbmcnLCBiaW5kaW5nLmdlbmVyYXRlKCkpOwovLyBDb3B5cmlnaHQgKGMpIDIwMTIgVGhlIENocm9taXVtIEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCi8vIFVzZSBvZiB0aGlzIHNvdXJjZSBjb2RlIGlzIGdvdmVybmVkIGJ5IGEgQlNELXN0eWxlIGxpY2Vuc2UgdGhhdCBjYW4gYmUKLy8gZm91bmQgaW4gdGhlIExJQ0VOU0UgZmlsZS4KCi8vIEN1c3RvbSBiaW5kaW5nIGZvciB0aGUgc3lzdGVtSW5kaWNhdG9yIEFQSS4KLy8gVE9ETyhkZXdpdHRqKSBSZWZhY3RvciBjdXN0b20gYmluZGluZyB0byByZWR1Y2UgcmVkdW5kYW5jeSBiZXR3ZWVuIHRoZQovLyBleHRlbnNpb24gYWN0aW9uIEFQSXMuCgp2YXIgYmluZGluZyA9CiAgICBhcGlCcmlkZ2UgfHwgcmVxdWlyZSgnYmluZGluZycpLkJpbmRpbmcuY3JlYXRlKCdzeXN0ZW1JbmRpY2F0b3InKTsKCnZhciBzZXRJY29uID0gcmVxdWlyZSgnc2V0SWNvbicpLnNldEljb247CnZhciBzZW5kUmVxdWVzdCA9IGJpbmRpbmdVdGlsID8KICAgICRGdW5jdGlvbi5iaW5kKGJpbmRpbmdVdGlsLnNlbmRSZXF1ZXN0LCBiaW5kaW5nVXRpbCkgOgogICAgcmVxdWlyZSgnc2VuZFJlcXVlc3QnKS5zZW5kUmVxdWVzdDsKCmJpbmRpbmcucmVnaXN0ZXJDdXN0b21Ib29rKGZ1bmN0aW9uKGJpbmRpbmdzQVBJKSB7CiAgdmFyIGFwaUZ1bmN0aW9ucyA9IGJpbmRpbmdzQVBJLmFwaUZ1bmN0aW9uczsKCiAgYXBpRnVuY3Rpb25zLnNldEhhbmRsZVJlcXVlc3QoJ3NldEljb24nLCBmdW5jdGlvbihkZXRhaWxzLCBjYWxsYmFjaykgewogICAgc2V0SWNvbihkZXRhaWxzLCAkRnVuY3Rpb24uYmluZChmdW5jdGlvbihhcmdzKSB7CiAgICAgIHNlbmRSZXF1ZXN0KCdzeXN0ZW1JbmRpY2F0b3Iuc2V0SWNvbicsIFthcmdzLCBjYWxsYmFja10sCiAgICAgICAgICAgICAgICAgIGJpbmRpbmdVdGlsID8gdW5kZWZpbmVkIDogdGhpcy5kZWZpbml0aW9uLnBhcmFtZXRlcnMsCiAgICAgICAgICAgICAgICAgIHVuZGVmaW5lZCk7CiAgICB9LCB0aGlzKSk7CiAgfSk7Cn0pOwoKaWYgKCFhcGlCcmlkZ2UpCiAgZXhwb3J0cy4kc2V0KCdiaW5kaW5nJywgYmluZGluZy5nZW5lcmF0ZSgpKTsKLy8gQ29weXJpZ2h0IChjKSAyMDEyIFRoZSBDaHJvbWl1bSBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgovLyBVc2Ugb2YgdGhpcyBzb3VyY2UgY29kZSBpcyBnb3Zlcm5lZCBieSBhIEJTRC1zdHlsZSBsaWNlbnNlIHRoYXQgY2FuIGJlCi8vIGZvdW5kIGluIHRoZSBMSUNFTlNFIGZpbGUuCgovLyBDdXN0b20gYmluZGluZyBmb3IgdGhlIFRhYiBDYXB0dXJlIEFQSS4KCnZhciBiaW5kaW5nID0gYXBpQnJpZGdlIHx8IHJlcXVpcmUoJ2JpbmRpbmcnKS5CaW5kaW5nLmNyZWF0ZSgndGFiQ2FwdHVyZScpOwoKdmFyIGpzTGFzdEVycm9yID0gYmluZGluZ1V0aWwgPyB1bmRlZmluZWQgOiByZXF1aXJlKCdsYXN0RXJyb3InKTsKZnVuY3Rpb24gcnVuQ2FsbGJhY2tXaXRoTGFzdEVycm9yKG5hbWUsIG1lc3NhZ2UsIHN0YWNrLCBjYWxsYmFjaywgYXJncykgewogIGlmIChiaW5kaW5nVXRpbCkgewogICAgYmluZGluZ1V0aWwucnVuQ2FsbGJhY2tXaXRoTGFzdEVycm9yKG1lc3NhZ2UsIGZ1bmN0aW9uKCkgewogICAgICAkRnVuY3Rpb24uYXBwbHkoY2FsbGJhY2ssIG51bGwsIGFyZ3MpOwogICAgfSk7CiAgfSBlbHNlIHsKICAgIGpzTGFzdEVycm9yLnJ1bihuYW1lLCBtZXNzYWdlLCBzdGFjaywgY2FsbGJhY2ssIGFyZ3MpOwogIH0KfQoKYmluZGluZy5yZWdpc3RlckN1c3RvbUhvb2soZnVuY3Rpb24oYmluZGluZ3NBUEksIGV4dGVuc2lvbklkKSB7CiAgdmFyIGFwaUZ1bmN0aW9ucyA9IGJpbmRpbmdzQVBJLmFwaUZ1bmN0aW9uczsKCiAgZnVuY3Rpb24gcHJveHlUb0dldFVzZXJNZWRpYShuYW1lLCByZXF1ZXN0LCBjYWxsYmFjaywgcmVzcG9uc2UpIHsKICAgIGlmICghY2FsbGJhY2spCiAgICAgIHJldHVybjsKCiAgICBpZiAoIXJlc3BvbnNlKSB7CiAgICAgIC8vIFdoZW4gdGhlIHJlc3BvbnNlIGlzIG1pc3NpbmcsIHJ1bnRpbWUubGFzdEVycm9yIGhhcyBhbHJlYWR5IGJlZW4gc2V0LgogICAgICAvLyBTZWUgY2hyb21lL2Jyb3dzZXIvZXh0ZW5zaW9ucy9hcGkvdGFiX2NhcHR1cmUvdGFiX2NhcHR1cmVfYXBpLmNjLgogICAgICBjYWxsYmFjayhudWxsKTsKICAgICAgcmV0dXJuOwogICAgfQoKICAgIC8vIENvbnZlbmllbmNlIGZ1bmN0aW9uIGZvciBwcm9jZXNzaW5nIHdlYmtpdEdldFVzZXJNZWRpYSgpIGVycm9yIG9iamVjdHMgdG8KICAgIC8vIHByb3ZpZGUgcnVudGltZS5sYXN0RXJyb3IgbWVzc2FnZXMgZm9yIHRoZSB0YWIgY2FwdHVyZSBBUEkuCiAgICBmdW5jdGlvbiBnZXRFcnJvck1lc3NhZ2UoZXJyb3IsIGZhbGxiYWNrTWVzc2FnZSkgewogICAgICBpZiAoIWVycm9yIHx8ICh0eXBlb2YgZXJyb3IubWVzc2FnZSAhPSAnc3RyaW5nJykpCiAgICAgICAgcmV0dXJuIGZhbGxiYWNrTWVzc2FnZTsKICAgICAgcmV0dXJuIGVycm9yLm1lc3NhZ2UucmVwbGFjZSgvKG5hdmlnYXRvclwuKT8od2Via2l0KT9HZXRVc2VyTWVkaWEvZ2ksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgbmFtZSk7CiAgICB9CgogICAgdmFyIG9wdGlvbnMgPSB7fTsKICAgIGlmIChyZXNwb25zZS5hdWRpb0NvbnN0cmFpbnRzKQogICAgICBvcHRpb25zLmF1ZGlvID0gcmVzcG9uc2UuYXVkaW9Db25zdHJhaW50czsKICAgIGlmIChyZXNwb25zZS52aWRlb0NvbnN0cmFpbnRzKQogICAgICBvcHRpb25zLnZpZGVvID0gcmVzcG9uc2UudmlkZW9Db25zdHJhaW50czsKICAgIHRyeSB7CiAgICAgIG5hdmlnYXRvci53ZWJraXRHZXRVc2VyTWVkaWEoCiAgICAgICAgICBvcHRpb25zLAogICAgICAgICAgZnVuY3Rpb24gb25TdWNjZXNzKG1lZGlhX3N0cmVhbSkgewogICAgICAgICAgICBjYWxsYmFjayhtZWRpYV9zdHJlYW0pOwogICAgICAgICAgfSwKICAgICAgICAgIGZ1bmN0aW9uIG9uRXJyb3IoZXJyb3IpIHsKICAgICAgICAgICAgcnVuQ2FsbGJhY2tXaXRoTGFzdEVycm9yKAogICAgICAgICAgICAgICAgbmFtZSwKICAgICAgICAgICAgICAgIGdldEVycm9yTWVzc2FnZShlcnJvciwgIkZhaWxlZCB0byBzdGFydCBNZWRpYVN0cmVhbS4iKSwKICAgICAgICAgICAgICAgIHJlcXVlc3Quc3RhY2ssCiAgICAgICAgICAgICAgICBmdW5jdGlvbigpIHsgY2FsbGJhY2sobnVsbCk7IH0pOwogICAgICAgICAgfSk7CiAgICB9IGNhdGNoIChlcnJvcikgewogICAgICBydW5DYWxsYmFja1dpdGhMYXN0RXJyb3IoCiAgICAgICAgICBuYW1lLCBnZXRFcnJvck1lc3NhZ2UoZXJyb3IsICJJbnZhbGlkIGFyZ3VtZW50KHMpLiIpLCByZXF1ZXN0LnN0YWNrLAogICAgICAgICAgZnVuY3Rpb24oKSB7IGNhbGxiYWNrKG51bGwpOyB9KTsKICAgIH0KICB9CgogIGFwaUZ1bmN0aW9ucy5zZXRDdXN0b21DYWxsYmFjaygnY2FwdHVyZScsIHByb3h5VG9HZXRVc2VyTWVkaWEpOwogIGFwaUZ1bmN0aW9ucy5zZXRDdXN0b21DYWxsYmFjaygnY2FwdHVyZU9mZnNjcmVlblRhYicsIHByb3h5VG9HZXRVc2VyTWVkaWEpOwp9KTsKCmlmICghYXBpQnJpZGdlKQogIGV4cG9ydHMuJHNldCgnYmluZGluZycsIGJpbmRpbmcuZ2VuZXJhdGUoKSk7Ci8vIENvcHlyaWdodCAoYykgMjAxMiBUaGUgQ2hyb21pdW0gQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KLy8gVXNlIG9mIHRoaXMgc291cmNlIGNvZGUgaXMgZ292ZXJuZWQgYnkgYSBCU0Qtc3R5bGUgbGljZW5zZSB0aGF0IGNhbiBiZQovLyBmb3VuZCBpbiB0aGUgTElDRU5TRSBmaWxlLgoKLy8gQ3VzdG9tIGJpbmRpbmcgZm9yIHRoZSB0YWJzIEFQSS4KCnZhciBiaW5kaW5nID0gYXBpQnJpZGdlIHx8IHJlcXVpcmUoJ2JpbmRpbmcnKS5CaW5kaW5nLmNyZWF0ZSgndGFicycpOwoKdmFyIG1lc3NhZ2luZyA9IHJlcXVpcmUoJ21lc3NhZ2luZycpOwp2YXIgT3BlbkNoYW5uZWxUb1RhYiA9IHJlcXVpcmVOYXRpdmUoJ21lc3NhZ2luZ19uYXRpdmVzJykuT3BlbkNoYW5uZWxUb1RhYjsKdmFyIHNlbmRSZXF1ZXN0SXNEaXNhYmxlZCA9IHJlcXVpcmVOYXRpdmUoJ3Byb2Nlc3MnKS5Jc1NlbmRSZXF1ZXN0RGlzYWJsZWQoKTsKdmFyIGZvckVhY2ggPSByZXF1aXJlKCd1dGlscycpLmZvckVhY2g7CgpiaW5kaW5nLnJlZ2lzdGVyQ3VzdG9tSG9vayhmdW5jdGlvbihiaW5kaW5nc0FQSSwgZXh0ZW5zaW9uSWQpIHsKICB2YXIgYXBpRnVuY3Rpb25zID0gYmluZGluZ3NBUEkuYXBpRnVuY3Rpb25zOwogIHZhciB0YWJzID0gYmluZGluZ3NBUEkuY29tcGlsZWRBcGk7CgogIGFwaUZ1bmN0aW9ucy5zZXRIYW5kbGVSZXF1ZXN0KCdjb25uZWN0JywgZnVuY3Rpb24odGFiSWQsIGNvbm5lY3RJbmZvKSB7CiAgICB2YXIgbmFtZSA9ICcnOwogICAgdmFyIGZyYW1lSWQgPSAtMTsKICAgIGlmIChjb25uZWN0SW5mbykgewogICAgICBuYW1lID0gY29ubmVjdEluZm8ubmFtZSB8fCBuYW1lOwogICAgICBmcmFtZUlkID0gY29ubmVjdEluZm8uZnJhbWVJZDsKICAgICAgaWYgKHR5cGVvZiBmcmFtZUlkID09ICd1bmRlZmluZWQnIHx8IGZyYW1lSWQgPCAwKQogICAgICAgIGZyYW1lSWQgPSAtMTsKICAgIH0KICAgIHZhciBwb3J0SWQgPSBPcGVuQ2hhbm5lbFRvVGFiKHRhYklkLCBmcmFtZUlkLCBleHRlbnNpb25JZCwgbmFtZSk7CiAgICByZXR1cm4gbWVzc2FnaW5nLmNyZWF0ZVBvcnQocG9ydElkLCBuYW1lKTsKICB9KTsKCiAgYXBpRnVuY3Rpb25zLnNldEhhbmRsZVJlcXVlc3QoJ3NlbmRSZXF1ZXN0JywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBmdW5jdGlvbih0YWJJZCwgcmVxdWVzdCwgcmVzcG9uc2VDYWxsYmFjaykgewogICAgaWYgKHNlbmRSZXF1ZXN0SXNEaXNhYmxlZCkKICAgICAgdGhyb3cgbmV3IEVycm9yKHNlbmRSZXF1ZXN0SXNEaXNhYmxlZCk7CiAgICB2YXIgcG9ydCA9IHRhYnMuY29ubmVjdCh0YWJJZCwge25hbWU6IG1lc3NhZ2luZy5rUmVxdWVzdENoYW5uZWx9KTsKICAgIG1lc3NhZ2luZy5zZW5kTWVzc2FnZUltcGwocG9ydCwgcmVxdWVzdCwgcmVzcG9uc2VDYWxsYmFjayk7CiAgfSk7CgogIGFwaUZ1bmN0aW9ucy5zZXRIYW5kbGVSZXF1ZXN0KCdzZW5kTWVzc2FnZScsCiAgICAgIGZ1bmN0aW9uKHRhYklkLCBtZXNzYWdlLCBvcHRpb25zLCByZXNwb25zZUNhbGxiYWNrKSB7CiAgICB2YXIgY29ubmVjdEluZm8gPSB7CiAgICAgIG5hbWU6IG1lc3NhZ2luZy5rTWVzc2FnZUNoYW5uZWwKICAgIH07CiAgICBpZiAob3B0aW9ucykgewogICAgICBmb3JFYWNoKG9wdGlvbnMsIGZ1bmN0aW9uKGssIHYpIHsKICAgICAgICBjb25uZWN0SW5mb1trXSA9IHY7CiAgICAgIH0pOwogICAgfQoKICAgIHZhciBwb3J0ID0gdGFicy5jb25uZWN0KHRhYklkLCBjb25uZWN0SW5mbyk7CiAgICBtZXNzYWdpbmcuc2VuZE1lc3NhZ2VJbXBsKHBvcnQsIG1lc3NhZ2UsIHJlc3BvbnNlQ2FsbGJhY2spOwogIH0pOwp9KTsKCmlmICghYXBpQnJpZGdlKQogIGV4cG9ydHMuJHNldCgnYmluZGluZycsIGJpbmRpbmcuZ2VuZXJhdGUoKSk7Ci8vIENvcHlyaWdodCAoYykgMjAxMiBUaGUgQ2hyb21pdW0gQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KLy8gVXNlIG9mIHRoaXMgc291cmNlIGNvZGUgaXMgZ292ZXJuZWQgYnkgYSBCU0Qtc3R5bGUgbGljZW5zZSB0aGF0IGNhbiBiZQovLyBmb3VuZCBpbiB0aGUgTElDRU5TRSBmaWxlLgoKLy8gQ3VzdG9tIGJpbmRpbmcgZm9yIHRoZSB0dHMgQVBJLgoKdmFyIGJpbmRpbmcgPSBhcGlCcmlkZ2UgfHwgcmVxdWlyZSgnYmluZGluZycpLkJpbmRpbmcuY3JlYXRlKCd0dHMnKTsKCnZhciBpZEdlbmVyYXRvciA9IHJlcXVpcmVOYXRpdmUoJ2lkX2dlbmVyYXRvcicpOwp2YXIgc2VuZFJlcXVlc3QgPSBiaW5kaW5nVXRpbCA/CiAgICAkRnVuY3Rpb24uYmluZChiaW5kaW5nVXRpbC5zZW5kUmVxdWVzdCwgYmluZGluZ1V0aWwpIDoKICAgIHJlcXVpcmUoJ3NlbmRSZXF1ZXN0Jykuc2VuZFJlcXVlc3Q7CnZhciBsYXp5QkcgPSByZXF1aXJlTmF0aXZlKCdsYXp5X2JhY2tncm91bmRfcGFnZScpOwoKYmluZGluZy5yZWdpc3RlckN1c3RvbUhvb2soZnVuY3Rpb24oYXBpKSB7CiAgdmFyIGFwaUZ1bmN0aW9ucyA9IGFwaS5hcGlGdW5jdGlvbnM7CiAgdmFyIHR0cyA9IGFwaS5jb21waWxlZEFwaTsKICB2YXIgaGFuZGxlcnMgPSB7fTsKCiAgZnVuY3Rpb24gdHRzRXZlbnRMaXN0ZW5lcihldmVudCkgewogICAgdmFyIGV2ZW50SGFuZGxlciA9IGhhbmRsZXJzW2V2ZW50LnNyY0lkXTsKICAgIGlmIChldmVudEhhbmRsZXIpIHsKICAgICAgZXZlbnRIYW5kbGVyKHsKICAgICAgICAgICAgICAgICAgICAgdHlwZTogZXZlbnQudHlwZSwKICAgICAgICAgICAgICAgICAgICAgY2hhckluZGV4OiBldmVudC5jaGFySW5kZXgsCiAgICAgICAgICAgICAgICAgICAgIGVycm9yTWVzc2FnZTogZXZlbnQuZXJyb3JNZXNzYWdlCiAgICAgICAgICAgICAgICAgICB9KTsKICAgICAgaWYgKGV2ZW50LmlzRmluYWxFdmVudCkgewogICAgICAgIGRlbGV0ZSBoYW5kbGVyc1tldmVudC5zcmNJZF07CiAgICAgICAgLy8gQmFsYW5jZWQgaW4gJ3NwZWFrJyBoYW5kbGVyLgogICAgICAgIGxhenlCRy5EZWNyZW1lbnRLZWVwYWxpdmVDb3VudCgpOwogICAgICB9CiAgICB9CiAgfQoKICAvLyBUaGlzIGZpbGUgd2lsbCBnZXQgcnVuIGlmIGFuIGV4dGVuc2lvbiBuZWVkcyB0aGUgdHRzRW5naW5lIHBlcm1pc3Npb24sIGJ1dAogIC8vIGl0IGRvZXNuJ3QgbmVjZXNzYXJpbHkgaGF2ZSB0aGUgdHRzIHBlcm1pc3Npb24uIElmIGl0IGRvZXNuJ3QsIHRyeWluZyB0bwogIC8vIGFkZCBhIGxpc3RlbmVyIHRvIGNocm9tZS50dHMub25FdmVudCB3aWxsIGZhaWwuCiAgLy8gU2VlIGh0dHA6Ly9jcmJ1Zy5jb20vMTIyNDc0LgogIHRyeSB7CiAgICB0dHMub25FdmVudC5hZGRMaXN0ZW5lcih0dHNFdmVudExpc3RlbmVyKTsKICB9IGNhdGNoIChlKSB7fQoKICBhcGlGdW5jdGlvbnMuc2V0SGFuZGxlUmVxdWVzdCgnc3BlYWsnLCBmdW5jdGlvbigpIHsKICAgIHZhciBhcmdzID0gJEFycmF5LmZyb20oYXJndW1lbnRzKTsKICAgIGlmIChhcmdzLmxlbmd0aCA+IDEgJiYgYXJnc1sxXSAmJiBhcmdzWzFdLm9uRXZlbnQpIHsKICAgICAgdmFyIGlkID0gaWRHZW5lcmF0b3IuR2V0TmV4dElkKCk7CiAgICAgIGFyZ3NbMV0uc3JjSWQgPSBpZDsKICAgICAgaGFuZGxlcnNbaWRdID0gYXJnc1sxXS5vbkV2ZW50OwogICAgICAvLyBLZWVwIHRoZSBwYWdlIGFsaXZlIHVudGlsIHRoZSBldmVudCBmaW5pc2hlcy4KICAgICAgLy8gQmFsYW5jZWQgaW4gZXZlbnRIYW5kbGVyLgogICAgICBsYXp5QkcuSW5jcmVtZW50S2VlcGFsaXZlQ291bnQoKTsKICAgIH0KICAgIHNlbmRSZXF1ZXN0KCd0dHMuc3BlYWsnLCBhcmdzLAogICAgICAgICAgICAgICAgYmluZGluZ1V0aWwgPyB1bmRlZmluZWQgOiB0aGlzLmRlZmluaXRpb24ucGFyYW1ldGVycywKICAgICAgICAgICAgICAgIHVuZGVmaW5lZCk7CiAgICByZXR1cm4gaWQ7CiAgfSk7Cn0pOwoKaWYgKCFhcGlCcmlkZ2UpCiAgZXhwb3J0cy4kc2V0KCdiaW5kaW5nJywgYmluZGluZy5nZW5lcmF0ZSgpKTsKLy8gQ29weXJpZ2h0IChjKSAyMDEyIFRoZSBDaHJvbWl1bSBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgovLyBVc2Ugb2YgdGhpcyBzb3VyY2UgY29kZSBpcyBnb3Zlcm5lZCBieSBhIEJTRC1zdHlsZSBsaWNlbnNlIHRoYXQgY2FuIGJlCi8vIGZvdW5kIGluIHRoZSBMSUNFTlNFIGZpbGUuCgovLyBDdXN0b20gYmluZGluZyBmb3IgdGhlIHR0c0VuZ2luZSBBUEkuCgp2YXIgYmluZGluZyA9IGFwaUJyaWRnZSB8fCByZXF1aXJlKCdiaW5kaW5nJykuQmluZGluZy5jcmVhdGUoJ3R0c0VuZ2luZScpOwp2YXIgcmVnaXN0ZXJBcmd1bWVudE1hc3NhZ2VyID0gYmluZGluZ1V0aWwgPwogICAgJEZ1bmN0aW9uLmJpbmQoYmluZGluZ1V0aWwucmVnaXN0ZXJFdmVudEFyZ3VtZW50TWFzc2FnZXIsIGJpbmRpbmdVdGlsKSA6CiAgICByZXF1aXJlKCdldmVudF9iaW5kaW5ncycpLnJlZ2lzdGVyQXJndW1lbnRNYXNzYWdlcjsKCnJlZ2lzdGVyQXJndW1lbnRNYXNzYWdlcigndHRzRW5naW5lLm9uU3BlYWsnLCBmdW5jdGlvbihhcmdzLCBkaXNwYXRjaCkgewogIHZhciB0ZXh0ID0gYXJnc1swXTsKICB2YXIgb3B0aW9ucyA9IGFyZ3NbMV07CiAgdmFyIHJlcXVlc3RJZCA9IGFyZ3NbMl07CiAgdmFyIHNlbmRUdHNFdmVudCA9IGZ1bmN0aW9uKGV2ZW50KSB7CiAgICBjaHJvbWUudHRzRW5naW5lLnNlbmRUdHNFdmVudChyZXF1ZXN0SWQsIGV2ZW50KTsKICB9OwogIGRpc3BhdGNoKFt0ZXh0LCBvcHRpb25zLCBzZW5kVHRzRXZlbnRdKTsKfSk7CgppZiAoIWFwaUJyaWRnZSkKICBleHBvcnRzLiRzZXQoJ2JpbmRpbmcnLCBiaW5kaW5nLmdlbmVyYXRlKCkpOwovLyBDb3B5cmlnaHQgMjAxNSBUaGUgQ2hyb21pdW0gQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KLy8gVXNlIG9mIHRoaXMgc291cmNlIGNvZGUgaXMgZ292ZXJuZWQgYnkgYSBCU0Qtc3R5bGUgbGljZW5zZSB0aGF0IGNhbiBiZQovLyBmb3VuZCBpbiB0aGUgTElDRU5TRSBmaWxlLgoKLy8gQ3VzdG9tIGJpbmRpbmcgZm9yIHRoZSB3ZWJydGNEZXNrdG9wQ2FwdHVyZVByaXZhdGUgQVBJLgoKdmFyIGJpbmRpbmcgPSBhcGlCcmlkZ2UgfHwKICAgICAgICAgICAgICByZXF1aXJlKCdiaW5kaW5nJykuQmluZGluZy5jcmVhdGUoJ3dlYnJ0Y0Rlc2t0b3BDYXB0dXJlUHJpdmF0ZScpOwp2YXIgc2VuZFJlcXVlc3QgPSBiaW5kaW5nVXRpbCA/CiAgICAkRnVuY3Rpb24uYmluZChiaW5kaW5nVXRpbC5zZW5kUmVxdWVzdCwgYmluZGluZ1V0aWwpIDoKICAgIHJlcXVpcmUoJ3NlbmRSZXF1ZXN0Jykuc2VuZFJlcXVlc3Q7CnZhciBpZEdlbmVyYXRvciA9IHJlcXVpcmVOYXRpdmUoJ2lkX2dlbmVyYXRvcicpOwoKYmluZGluZy5yZWdpc3RlckN1c3RvbUhvb2soZnVuY3Rpb24oYmluZGluZ3NBUEkpIHsKICB2YXIgYXBpRnVuY3Rpb25zID0gYmluZGluZ3NBUEkuYXBpRnVuY3Rpb25zOwoKICB2YXIgcGVuZGluZ1JlcXVlc3RzID0ge307CgogIGZ1bmN0aW9uIG9uUmVxdWVzdFJlc3VsdChpZCwgcmVzdWx0KSB7CiAgICBpZiAoaWQgaW4gcGVuZGluZ1JlcXVlc3RzKSB7CiAgICAgIHZhciBjYWxsYmFjayA9IHBlbmRpbmdSZXF1ZXN0c1tpZF07CiAgICAgIGRlbGV0ZSBwZW5kaW5nUmVxdWVzdHNbaWRdOwogICAgICBjYWxsYmFjayhyZXN1bHQpOwogICAgfQogIH0KCiAgYXBpRnVuY3Rpb25zLnNldEhhbmRsZVJlcXVlc3QoJ2Nob29zZURlc2t0b3BNZWRpYScsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZnVuY3Rpb24oc291cmNlcywgcmVxdWVzdCwgY2FsbGJhY2spIHsKICAgIHZhciBpZCA9IGlkR2VuZXJhdG9yLkdldE5leHRJZCgpOwogICAgcGVuZGluZ1JlcXVlc3RzW2lkXSA9IGNhbGxiYWNrOwogICAgc2VuZFJlcXVlc3QoJ3dlYnJ0Y0Rlc2t0b3BDYXB0dXJlUHJpdmF0ZS5jaG9vc2VEZXNrdG9wTWVkaWEnLAogICAgICAgICAgICAgICAgW2lkLCBzb3VyY2VzLCByZXF1ZXN0LAogICAgICAgICAgICAgICAgICRGdW5jdGlvbi5iaW5kKG9uUmVxdWVzdFJlc3VsdCwgbnVsbCwgaWQpXSwKICAgICAgICAgICAgICAgIGJpbmRpbmdVdGlsID8gdW5kZWZpbmVkIDogdGhpcy5kZWZpbml0aW9uLnBhcmFtZXRlcnMsCiAgICAgICAgICAgICAgICB1bmRlZmluZWQpOwogICAgcmV0dXJuIGlkOwogIH0pOwoKICBhcGlGdW5jdGlvbnMuc2V0SGFuZGxlUmVxdWVzdCgnY2FuY2VsQ2hvb3NlRGVza3RvcE1lZGlhJywgZnVuY3Rpb24oaWQpIHsKICAgIGlmIChpZCBpbiBwZW5kaW5nUmVxdWVzdHMpIHsKICAgICAgZGVsZXRlIHBlbmRpbmdSZXF1ZXN0c1tpZF07CiAgICAgIHNlbmRSZXF1ZXN0KCd3ZWJydGNEZXNrdG9wQ2FwdHVyZVByaXZhdGUuY2FuY2VsQ2hvb3NlRGVza3RvcE1lZGlhJywgW2lkXSwKICAgICAgICAgICAgICAgICAgYmluZGluZ1V0aWwgPyB1bmRlZmluZWQgOiB0aGlzLmRlZmluaXRpb24ucGFyYW1ldGVycywKICAgICAgICAgICAgICAgICAgdW5kZWZpbmVkKTsKICAgIH0KICB9KTsKfSk7CgppZiAoIWFwaUJyaWRnZSkKICBleHBvcnRzLiRzZXQoJ2JpbmRpbmcnLCBiaW5kaW5nLmdlbmVyYXRlKCkpOwovLyBDb3B5cmlnaHQgMjAxNyBUaGUgQ2hyb21pdW0gQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KLy8gVXNlIG9mIHRoaXMgc291cmNlIGNvZGUgaXMgZ292ZXJuZWQgYnkgYSBCU0Qtc3R5bGUgbGljZW5zZSB0aGF0IGNhbiBiZQovLyBmb3VuZCBpbiB0aGUgTElDRU5TRSBmaWxlLgoKLy8gQ3VzdG9tIGJpbmRpbmcgZm9yIHRoZSB3ZWJydGNMb2dnaW5nUHJpdmF0ZSBBUEkuCgp2YXIgYmluZGluZyA9IGFwaUJyaWRnZSB8fAogICAgICAgICAgICAgIHJlcXVpcmUoJ2JpbmRpbmcnKS5CaW5kaW5nLmNyZWF0ZSgnd2VicnRjTG9nZ2luZ1ByaXZhdGUnKTsKCnZhciBnZXRCaW5kRGlyZWN0b3J5RW50cnlDYWxsYmFjayA9CiAgICByZXF1aXJlKCdmaWxlRW50cnlCaW5kaW5nVXRpbCcpLmdldEJpbmREaXJlY3RvcnlFbnRyeUNhbGxiYWNrOwoKYmluZGluZy5yZWdpc3RlckN1c3RvbUhvb2soZnVuY3Rpb24oYmluZGluZywgaWQsIGNvbnRleHRUeXBlKSB7CiAgdmFyIGFwaUZ1bmN0aW9ucyA9IGJpbmRpbmcuYXBpRnVuY3Rpb25zOwogIGFwaUZ1bmN0aW9ucy5zZXRDdXN0b21DYWxsYmFjaygnZ2V0TG9nc0RpcmVjdG9yeScsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGdldEJpbmREaXJlY3RvcnlFbnRyeUNhbGxiYWNrKCkpOwp9KTsKCmlmICghYXBpQnJpZGdlKQogIGV4cG9ydHMuJHNldCgnYmluZGluZycsIGJpbmRpbmcuZ2VuZXJhdGUoKSk7Ci8vIENvcHlyaWdodCAoYykgMjAxMiBUaGUgQ2hyb21pdW0gQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KLy8gVXNlIG9mIHRoaXMgc291cmNlIGNvZGUgaXMgZ292ZXJuZWQgYnkgYSBCU0Qtc3R5bGUgbGljZW5zZSB0aGF0IGNhbiBiZQovLyBmb3VuZCBpbiB0aGUgTElDRU5TRSBmaWxlLgoKLy8gQ3VzdG9tIGJpbmRpbmcgZm9yIHRoZSB3ZWJzdG9yZSBBUEkuCgp2YXIgd2Vic3RvcmVOYXRpdmVzID0gcmVxdWlyZU5hdGl2ZSgnd2Vic3RvcmUnKTsKCnZhciBvbkluc3RhbGxTdGFnZUNoYW5nZWQ7CnZhciBvbkRvd25sb2FkUHJvZ3Jlc3M7CgpmdW5jdGlvbiBJbnN0YWxsZXIoKSB7CiAgdGhpcy5fcGVuZGluZ0luc3RhbGwgPSBudWxsOwp9CgpJbnN0YWxsZXIucHJvdG90eXBlLmluc3RhbGwgPSBmdW5jdGlvbih1cmwsIG9uU3VjY2Vzcywgb25GYWlsdXJlKSB7CiAgaWYgKHRoaXMuX3BlbmRpbmdJbnN0YWxsKQogICAgdGhyb3cgbmV3IEVycm9yKCdBIENocm9tZSBXZWIgU3RvcmUgaW5zdGFsbGF0aW9uIGlzIGFscmVhZHkgcGVuZGluZy4nKTsKCiAgLy8gV2l0aCBuYXRpdmUgYmluZGluZ3MsIHRoZXNlIGNhbGxzIGdvIHRocm91Z2ggYXJndW1lbnQgdmFsaWRhdGlvbiwgd2hpY2gKICAvLyBzZXRzIG9wdGlvbmFsL21pc3NpbmcgYXJndW1lbnRzIHRvIG51bGwuIFRoZSBuYXRpdmUgd2Vic3RvcmUgYmluZGluZ3MKICAvLyBleHBlY3QgZWl0aGVyIHByZXNlbnQgb3IgdW5kZWZpbmVkLCBzbyB0cmFuc2Zvcm0gbnVsbCB0byB1bmRlZmluZWQuCiAgaWYgKHVybCA9PT0gbnVsbCkKICAgIHVybCA9IHVuZGVmaW5lZDsKICBpZiAob25TdWNjZXNzID09PSBudWxsKQogICAgb25TdWNjZXNzID0gdW5kZWZpbmVkOwogIGlmIChvbkZhaWx1cmUgPT09IG51bGwpCiAgICBvbkZhaWx1cmUgPSB1bmRlZmluZWQ7CgogIGlmICh1cmwgIT09IHVuZGVmaW5lZCAmJiB0eXBlb2YgdXJsICE9PSAnc3RyaW5nJykgewogICAgdGhyb3cgbmV3IEVycm9yKAogICAgICAgICdUaGUgQ2hyb21lIFdlYiBTdG9yZSBpdGVtIGxpbmsgVVJMIHBhcmFtZXRlciBtdXN0IGJlIGEgc3RyaW5nLicpOwogIH0KICBpZiAob25TdWNjZXNzICE9PSB1bmRlZmluZWQgJiYgdHlwZW9mIG9uU3VjY2VzcyAhPT0gJ2Z1bmN0aW9uJykgewogICAgdGhyb3cgbmV3IEVycm9yKCdUaGUgc3VjY2VzcyBjYWxsYmFjayBwYXJhbWV0ZXIgbXVzdCBiZSBhIGZ1bmN0aW9uLicpOwogIH0KICBpZiAob25GYWlsdXJlICE9PSB1bmRlZmluZWQgJiYgdHlwZW9mIG9uRmFpbHVyZSAhPT0gJ2Z1bmN0aW9uJykgewogICAgdGhyb3cgbmV3IEVycm9yKCdUaGUgZmFpbHVyZSBjYWxsYmFjayBwYXJhbWV0ZXIgbXVzdCBiZSBhIGZ1bmN0aW9uLicpOwogIH0KCiAgLy8gU2luY2Ugd2UgY2FsbCBJbnN0YWxsKCkgd2l0aCBhIGJvb2wgZm9yIGlmIHdlIGhhdmUgbGlzdGVuZXJzLCBsaXN0ZW5lcnMKICAvLyBtdXN0IGJlIHNldCBwcmlvciB0byB0aGUgaW5saW5lIGluc3RhbGxhdGlvbiBzdGFydGluZyAodGhpcyBpcyBhbHNvCiAgLy8gbm90ZWQgaW4gdGhlIEV2ZW50IGRvY3VtZW50YXRpb24gaW4KICAvLyBjaHJvbWUvY29tbW9uL2V4dGVuc2lvbnMvYXBpL3dlYnN0b3JlLmpzb24pLgogIHZhciBpbnN0YWxsSWQgPSB3ZWJzdG9yZU5hdGl2ZXMuSW5zdGFsbCgKICAgICAgb25JbnN0YWxsU3RhZ2VDaGFuZ2VkLmhhc0xpc3RlbmVycygpLAogICAgICBvbkRvd25sb2FkUHJvZ3Jlc3MuaGFzTGlzdGVuZXJzKCksCiAgICAgIHVybCwKICAgICAgb25TdWNjZXNzLAogICAgICBvbkZhaWx1cmUpOwogIGlmIChpbnN0YWxsSWQgIT09IHVuZGVmaW5lZCkgewogICAgdGhpcy5fcGVuZGluZ0luc3RhbGwgPSB7CiAgICAgIGluc3RhbGxJZDogaW5zdGFsbElkLAogICAgICBvblN1Y2Nlc3M6IG9uU3VjY2VzcywKICAgICAgb25GYWlsdXJlOiBvbkZhaWx1cmUKICAgIH07CiAgfQp9OwoKSW5zdGFsbGVyLnByb3RvdHlwZS5vbkluc3RhbGxSZXNwb25zZSA9CiAgICBmdW5jdGlvbihpbnN0YWxsSWQsIHN1Y2Nlc3MsIGVycm9yLCByZXN1bHRDb2RlKSB7CiAgdmFyIHBlbmRpbmdJbnN0YWxsID0gdGhpcy5fcGVuZGluZ0luc3RhbGw7CiAgaWYgKCFwZW5kaW5nSW5zdGFsbCB8fCBwZW5kaW5nSW5zdGFsbC5pbnN0YWxsSWQgIT0gaW5zdGFsbElkKSB7CiAgICAvLyBUT0RPKGthbG1hbik6IHNob3VsZCB0aGlzIGJlIGFuIGVycm9yPwogICAgcmV0dXJuOwogIH0KCiAgdHJ5IHsKICAgIGlmIChzdWNjZXNzICYmIHBlbmRpbmdJbnN0YWxsLm9uU3VjY2VzcykKICAgICAgcGVuZGluZ0luc3RhbGwub25TdWNjZXNzKCk7CiAgICBlbHNlIGlmICghc3VjY2VzcyAmJiBwZW5kaW5nSW5zdGFsbC5vbkZhaWx1cmUpCiAgICAgIHBlbmRpbmdJbnN0YWxsLm9uRmFpbHVyZShlcnJvciwgcmVzdWx0Q29kZSk7CiAgfSBjYXRjaCAoZSkgewogICAgY29uc29sZS5lcnJvcignRXhjZXB0aW9uIGluIGNocm9tZS53ZWJzdG9yZS5pbnN0YWxsIHJlc3BvbnNlIGhhbmRsZXI6ICcgKwogICAgICAgICAgICAgICAgICBlLnN0YWNrKTsKICB9IGZpbmFsbHkgewogICAgdGhpcy5fcGVuZGluZ0luc3RhbGwgPSBudWxsOwogIH0KfTsKCkluc3RhbGxlci5wcm90b3R5cGUub25JbnN0YWxsU3RhZ2VDaGFuZ2VkID0gZnVuY3Rpb24oaW5zdGFsbFN0YWdlKSB7CiAgb25JbnN0YWxsU3RhZ2VDaGFuZ2VkLmRpc3BhdGNoKGluc3RhbGxTdGFnZSk7Cn07CgpJbnN0YWxsZXIucHJvdG90eXBlLm9uRG93bmxvYWRQcm9ncmVzcyA9IGZ1bmN0aW9uKHByb2dyZXNzKSB7CiAgb25Eb3dubG9hZFByb2dyZXNzLmRpc3BhdGNoKHByb2dyZXNzKTsKfTsKCnZhciBpbnN0YWxsZXIgPSBuZXcgSW5zdGFsbGVyKCk7CgoKaWYgKGFwaUJyaWRnZSkgewogIGFwaUJyaWRnZS5yZWdpc3RlckN1c3RvbUhvb2soZnVuY3Rpb24oYXBpKSB7CiAgICBhcGkuYXBpRnVuY3Rpb25zLnNldEhhbmRsZVJlcXVlc3QoJ2luc3RhbGwnLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGZ1bmN0aW9uKHVybCwgb25TdWNjZXNzLCBvbkZhaWx1cmUpIHsKICAgICAgaW5zdGFsbGVyLmluc3RhbGwodXJsLCBvblN1Y2Nlc3MsIG9uRmFpbHVyZSk7CiAgICB9KTsKCiAgICBvbkluc3RhbGxTdGFnZUNoYW5nZWQgPSBhcGkuY29tcGlsZWRBcGkub25JbnN0YWxsU3RhZ2VDaGFuZ2VkOwogICAgb25Eb3dubG9hZFByb2dyZXNzID0gYXBpLmNvbXBpbGVkQXBpLm9uRG93bmxvYWRQcm9ncmVzczsKICB9KTsKfSBlbHNlIHsKICB2YXIgRXZlbnQgPSByZXF1aXJlKCdldmVudF9iaW5kaW5ncycpLkV2ZW50OwogIG9uSW5zdGFsbFN0YWdlQ2hhbmdlZCA9CiAgICAgIG5ldyBFdmVudChudWxsLCBbe25hbWU6ICdzdGFnZScsIHR5cGU6ICdzdHJpbmcnfV0sIHt1bm1hbmFnZWQ6IHRydWV9KTsKICBvbkRvd25sb2FkUHJvZ3Jlc3MgPQogICAgICBuZXcgRXZlbnQobnVsbCwgW3tuYW1lOiAncHJvZ3Jlc3MnLCB0eXBlOiAnbnVtYmVyJ31dLCB7dW5tYW5hZ2VkOiB0cnVlfSk7CgogIHZhciBjaHJvbWVXZWJzdG9yZSA9IHsKICAgIGluc3RhbGw6IGZ1bmN0aW9uICh1cmwsIG9uU3VjY2Vzcywgb25GYWlsdXJlKSB7CiAgICAgIGluc3RhbGxlci5pbnN0YWxsKHVybCwgb25TdWNjZXNzLCBvbkZhaWx1cmUpOwogICAgfSwKICAgIG9uSW5zdGFsbFN0YWdlQ2hhbmdlZDogb25JbnN0YWxsU3RhZ2VDaGFuZ2VkLAogICAgb25Eb3dubG9hZFByb2dyZXNzOiBvbkRvd25sb2FkUHJvZ3Jlc3MsCiAgfTsKICBleHBvcnRzLiRzZXQoJ2JpbmRpbmcnLCBjaHJvbWVXZWJzdG9yZSk7Cn0KCi8vIENhbGxlZCBieSB3ZWJzdG9yZV9iaW5kaW5ncy5jYy4KZXhwb3J0cy4kc2V0KCdvbkluc3RhbGxSZXNwb25zZScsCiAgICAgICAgICAgICAkRnVuY3Rpb24uYmluZChJbnN0YWxsZXIucHJvdG90eXBlLm9uSW5zdGFsbFJlc3BvbnNlLCBpbnN0YWxsZXIpKTsKZXhwb3J0cy4kc2V0KCdvbkluc3RhbGxTdGFnZUNoYW5nZWQnLAogICAgICAgICAgICAgJEZ1bmN0aW9uLmJpbmQoSW5zdGFsbGVyLnByb3RvdHlwZS5vbkluc3RhbGxTdGFnZUNoYW5nZWQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBpbnN0YWxsZXIpKTsKZXhwb3J0cy4kc2V0KCdvbkRvd25sb2FkUHJvZ3Jlc3MnLAogICAgICAgICAgICAgJEZ1bmN0aW9uLmJpbmQoSW5zdGFsbGVyLnByb3RvdHlwZS5vbkRvd25sb2FkUHJvZ3Jlc3MsIGluc3RhbGxlcikpOwovLyBDb3B5cmlnaHQgMjAxNCBUaGUgQ2hyb21pdW0gQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KLy8gVXNlIG9mIHRoaXMgc291cmNlIGNvZGUgaXMgZ292ZXJuZWQgYnkgYSBCU0Qtc3R5bGUgbGljZW5zZSB0aGF0IGNhbiBiZQovLyBmb3VuZCBpbiB0aGUgTElDRU5TRSBmaWxlLgoKJ3VzZSBzdHJpY3QnOwoKKGZ1bmN0aW9uKCkgewogIHZhciBtb2pvbUlkID0gJ2Nocm9tZS9jb21tb24vbWVkaWFfcm91dGVyL21vam8vbWVkaWFfY29udHJvbGxlci5tb2pvbSc7CiAgaWYgKG1vam8uaW50ZXJuYWwuaXNNb2pvbUxvYWRlZChtb2pvbUlkKSkgewogICAgY29uc29sZS53YXJuKCdUaGUgZm9sbG93aW5nIG1vam9tIGlzIGxvYWRlZCBtdWx0aXBsZSB0aW1lczogJyArIG1vam9tSWQpOwogICAgcmV0dXJuOwogIH0KICBtb2pvLmludGVybmFsLm1hcmtNb2pvbUxvYWRlZChtb2pvbUlkKTsKICB2YXIgYmluZGluZ3MgPSBtb2pvOwogIHZhciBhc3NvY2lhdGVkQmluZGluZ3MgPSBtb2pvOwogIHZhciBjb2RlYyA9IG1vam8uaW50ZXJuYWw7CiAgdmFyIHZhbGlkYXRvciA9IG1vam8uaW50ZXJuYWw7CgogIHZhciBleHBvcnRzID0gbW9qby5pbnRlcm5hbC5leHBvc2VOYW1lc3BhY2UoJ21lZGlhUm91dGVyLm1vam9tJyk7CiAgdmFyIG1lZGlhX3N0YXR1cyQgPQogICAgICBtb2pvLmludGVybmFsLmV4cG9zZU5hbWVzcGFjZSgnbWVkaWFSb3V0ZXIubW9qb20nKTsKICBpZiAobW9qby5jb25maWcuYXV0b0xvYWRNb2pvbURlcHMpIHsKICAgIG1vam8uaW50ZXJuYWwubG9hZE1vam9tSWZOZWNlc3NhcnkoCiAgICAgICAgJ2Nocm9tZS9jb21tb24vbWVkaWFfcm91dGVyL21vam8vbWVkaWFfc3RhdHVzLm1vam9tJywgJ21lZGlhX3N0YXR1cy5tb2pvbS5qcycpOwogIH0KICB2YXIgdGltZSQgPQogICAgICBtb2pvLmludGVybmFsLmV4cG9zZU5hbWVzcGFjZSgnbW9qby5jb21tb24ubW9qb20nKTsKICBpZiAobW9qby5jb25maWcuYXV0b0xvYWRNb2pvbURlcHMpIHsKICAgIG1vam8uaW50ZXJuYWwubG9hZE1vam9tSWZOZWNlc3NhcnkoCiAgICAgICAgJ21vam8vY29tbW9uL3RpbWUubW9qb20nLCAnLi4vLi4vLi4vLi4vbW9qby9jb21tb24vdGltZS5tb2pvbS5qcycpOwogIH0KCgoKICBmdW5jdGlvbiBNZWRpYUNvbnRyb2xsZXJfUGxheV9QYXJhbXModmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBNZWRpYUNvbnRyb2xsZXJfUGxheV9QYXJhbXMucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICB9OwogIE1lZGlhQ29udHJvbGxlcl9QbGF5X1BhcmFtcy5wcm90b3R5cGUuaW5pdEZpZWxkc18gPSBmdW5jdGlvbihmaWVsZHMpIHsKICAgIGZvcih2YXIgZmllbGQgaW4gZmllbGRzKSB7CiAgICAgICAgaWYgKHRoaXMuaGFzT3duUHJvcGVydHkoZmllbGQpKQogICAgICAgICAgdGhpc1tmaWVsZF0gPSBmaWVsZHNbZmllbGRdOwogICAgfQogIH07CgogIE1lZGlhQ29udHJvbGxlcl9QbGF5X1BhcmFtcy52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiA4fQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIE1lZGlhQ29udHJvbGxlcl9QbGF5X1BhcmFtcy5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMDsKCiAgTWVkaWFDb250cm9sbGVyX1BsYXlfUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1lZGlhQ29udHJvbGxlcl9QbGF5X1BhcmFtcygpOwogICAgdmFyIG51bWJlck9mQnl0ZXMgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhciB2ZXJzaW9uID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICByZXR1cm4gdmFsOwogIH07CgogIE1lZGlhQ29udHJvbGxlcl9QbGF5X1BhcmFtcy5lbmNvZGUgPSBmdW5jdGlvbihlbmNvZGVyLCB2YWwpIHsKICAgIHZhciBwYWNrZWQ7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKE1lZGlhQ29udHJvbGxlcl9QbGF5X1BhcmFtcy5lbmNvZGVkU2l6ZSk7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKDApOwogIH07CiAgZnVuY3Rpb24gTWVkaWFDb250cm9sbGVyX1BhdXNlX1BhcmFtcyh2YWx1ZXMpIHsKICAgIHRoaXMuaW5pdERlZmF1bHRzXygpOwogICAgdGhpcy5pbml0RmllbGRzXyh2YWx1ZXMpOwogIH0KCgogIE1lZGlhQ29udHJvbGxlcl9QYXVzZV9QYXJhbXMucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICB9OwogIE1lZGlhQ29udHJvbGxlcl9QYXVzZV9QYXJhbXMucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNZWRpYUNvbnRyb2xsZXJfUGF1c2VfUGFyYW1zLnZhbGlkYXRlID0gZnVuY3Rpb24obWVzc2FnZVZhbGlkYXRvciwgb2Zmc2V0KSB7CiAgICB2YXIgZXJyOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdEhlYWRlcihvZmZzZXQsIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHZhciBrVmVyc2lvblNpemVzID0gWwogICAgICB7dmVyc2lvbjogMCwgbnVtQnl0ZXM6IDh9CiAgICBdOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFZlcnNpb24ob2Zmc2V0LCBrVmVyc2lvblNpemVzKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgfTsKCiAgTWVkaWFDb250cm9sbGVyX1BhdXNlX1BhcmFtcy5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMDsKCiAgTWVkaWFDb250cm9sbGVyX1BhdXNlX1BhcmFtcy5kZWNvZGUgPSBmdW5jdGlvbihkZWNvZGVyKSB7CiAgICB2YXIgcGFja2VkOwogICAgdmFyIHZhbCA9IG5ldyBNZWRpYUNvbnRyb2xsZXJfUGF1c2VfUGFyYW1zKCk7CiAgICB2YXIgbnVtYmVyT2ZCeXRlcyA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFyIHZlcnNpb24gPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHJldHVybiB2YWw7CiAgfTsKCiAgTWVkaWFDb250cm9sbGVyX1BhdXNlX1BhcmFtcy5lbmNvZGUgPSBmdW5jdGlvbihlbmNvZGVyLCB2YWwpIHsKICAgIHZhciBwYWNrZWQ7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKE1lZGlhQ29udHJvbGxlcl9QYXVzZV9QYXJhbXMuZW5jb2RlZFNpemUpOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMigwKTsKICB9OwogIGZ1bmN0aW9uIE1lZGlhQ29udHJvbGxlcl9TZXRNdXRlX1BhcmFtcyh2YWx1ZXMpIHsKICAgIHRoaXMuaW5pdERlZmF1bHRzXygpOwogICAgdGhpcy5pbml0RmllbGRzXyh2YWx1ZXMpOwogIH0KCgogIE1lZGlhQ29udHJvbGxlcl9TZXRNdXRlX1BhcmFtcy5wcm90b3R5cGUuaW5pdERlZmF1bHRzXyA9IGZ1bmN0aW9uKCkgewogICAgdGhpcy5tdXRlID0gZmFsc2U7CiAgfTsKICBNZWRpYUNvbnRyb2xsZXJfU2V0TXV0ZV9QYXJhbXMucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNZWRpYUNvbnRyb2xsZXJfU2V0TXV0ZV9QYXJhbXMudmFsaWRhdGUgPSBmdW5jdGlvbihtZXNzYWdlVmFsaWRhdG9yLCBvZmZzZXQpIHsKICAgIHZhciBlcnI7CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0SGVhZGVyKG9mZnNldCwgY29kZWMua1N0cnVjdEhlYWRlclNpemUpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgdmFyIGtWZXJzaW9uU2l6ZXMgPSBbCiAgICAgIHt2ZXJzaW9uOiAwLCBudW1CeXRlczogMTZ9CiAgICBdOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFZlcnNpb24ob2Zmc2V0LCBrVmVyc2lvblNpemVzKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIE1lZGlhQ29udHJvbGxlcl9TZXRNdXRlX1BhcmFtcy5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgODsKCiAgTWVkaWFDb250cm9sbGVyX1NldE11dGVfUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1lZGlhQ29udHJvbGxlcl9TZXRNdXRlX1BhcmFtcygpOwogICAgdmFyIG51bWJlck9mQnl0ZXMgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhciB2ZXJzaW9uID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICBwYWNrZWQgPSBkZWNvZGVyLnJlYWRVaW50OCgpOwogICAgdmFsLm11dGUgPSAocGFja2VkID4+IDApICYgMSA/IHRydWUgOiBmYWxzZTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIHJldHVybiB2YWw7CiAgfTsKCiAgTWVkaWFDb250cm9sbGVyX1NldE11dGVfUGFyYW1zLmVuY29kZSA9IGZ1bmN0aW9uKGVuY29kZXIsIHZhbCkgewogICAgdmFyIHBhY2tlZDsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoTWVkaWFDb250cm9sbGVyX1NldE11dGVfUGFyYW1zLmVuY29kZWRTaXplKTsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoMCk7CiAgICBwYWNrZWQgPSAwOwogICAgcGFja2VkIHw9ICh2YWwubXV0ZSAmIDEpIDw8IDAKICAgIGVuY29kZXIud3JpdGVVaW50OChwYWNrZWQpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogIH07CiAgZnVuY3Rpb24gTWVkaWFDb250cm9sbGVyX1NldFZvbHVtZV9QYXJhbXModmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBNZWRpYUNvbnRyb2xsZXJfU2V0Vm9sdW1lX1BhcmFtcy5wcm90b3R5cGUuaW5pdERlZmF1bHRzXyA9IGZ1bmN0aW9uKCkgewogICAgdGhpcy52b2x1bWUgPSAwOwogIH07CiAgTWVkaWFDb250cm9sbGVyX1NldFZvbHVtZV9QYXJhbXMucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNZWRpYUNvbnRyb2xsZXJfU2V0Vm9sdW1lX1BhcmFtcy52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiAxNn0KICAgIF07CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0VmVyc2lvbihvZmZzZXQsIGtWZXJzaW9uU2l6ZXMpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgfTsKCiAgTWVkaWFDb250cm9sbGVyX1NldFZvbHVtZV9QYXJhbXMuZW5jb2RlZFNpemUgPSBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDg7CgogIE1lZGlhQ29udHJvbGxlcl9TZXRWb2x1bWVfUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1lZGlhQ29udHJvbGxlcl9TZXRWb2x1bWVfUGFyYW1zKCk7CiAgICB2YXIgbnVtYmVyT2ZCeXRlcyA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFyIHZlcnNpb24gPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhbC52b2x1bWUgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5GbG9hdCk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICByZXR1cm4gdmFsOwogIH07CgogIE1lZGlhQ29udHJvbGxlcl9TZXRWb2x1bWVfUGFyYW1zLmVuY29kZSA9IGZ1bmN0aW9uKGVuY29kZXIsIHZhbCkgewogICAgdmFyIHBhY2tlZDsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoTWVkaWFDb250cm9sbGVyX1NldFZvbHVtZV9QYXJhbXMuZW5jb2RlZFNpemUpOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMigwKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLkZsb2F0LCB2YWwudm9sdW1lKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICB9OwogIGZ1bmN0aW9uIE1lZGlhQ29udHJvbGxlcl9TZWVrX1BhcmFtcyh2YWx1ZXMpIHsKICAgIHRoaXMuaW5pdERlZmF1bHRzXygpOwogICAgdGhpcy5pbml0RmllbGRzXyh2YWx1ZXMpOwogIH0KCgogIE1lZGlhQ29udHJvbGxlcl9TZWVrX1BhcmFtcy5wcm90b3R5cGUuaW5pdERlZmF1bHRzXyA9IGZ1bmN0aW9uKCkgewogICAgdGhpcy50aW1lID0gbnVsbDsKICB9OwogIE1lZGlhQ29udHJvbGxlcl9TZWVrX1BhcmFtcy5wcm90b3R5cGUuaW5pdEZpZWxkc18gPSBmdW5jdGlvbihmaWVsZHMpIHsKICAgIGZvcih2YXIgZmllbGQgaW4gZmllbGRzKSB7CiAgICAgICAgaWYgKHRoaXMuaGFzT3duUHJvcGVydHkoZmllbGQpKQogICAgICAgICAgdGhpc1tmaWVsZF0gPSBmaWVsZHNbZmllbGRdOwogICAgfQogIH07CgogIE1lZGlhQ29udHJvbGxlcl9TZWVrX1BhcmFtcy52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiAxNn0KICAgIF07CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0VmVyc2lvbihvZmZzZXQsIGtWZXJzaW9uU2l6ZXMpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhQ29udHJvbGxlcl9TZWVrX1BhcmFtcy50aW1lCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0UG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDAsIHRpbWUkLlRpbWVEZWx0YSwgZmFsc2UpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKICB9OwoKICBNZWRpYUNvbnRyb2xsZXJfU2Vla19QYXJhbXMuZW5jb2RlZFNpemUgPSBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDg7CgogIE1lZGlhQ29udHJvbGxlcl9TZWVrX1BhcmFtcy5kZWNvZGUgPSBmdW5jdGlvbihkZWNvZGVyKSB7CiAgICB2YXIgcGFja2VkOwogICAgdmFyIHZhbCA9IG5ldyBNZWRpYUNvbnRyb2xsZXJfU2Vla19QYXJhbXMoKTsKICAgIHZhciBudW1iZXJPZkJ5dGVzID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YXIgdmVyc2lvbiA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFsLnRpbWUgPSBkZWNvZGVyLmRlY29kZVN0cnVjdFBvaW50ZXIodGltZSQuVGltZURlbHRhKTsKICAgIHJldHVybiB2YWw7CiAgfTsKCiAgTWVkaWFDb250cm9sbGVyX1NlZWtfUGFyYW1zLmVuY29kZSA9IGZ1bmN0aW9uKGVuY29kZXIsIHZhbCkgewogICAgdmFyIHBhY2tlZDsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoTWVkaWFDb250cm9sbGVyX1NlZWtfUGFyYW1zLmVuY29kZWRTaXplKTsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoMCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdFBvaW50ZXIodGltZSQuVGltZURlbHRhLCB2YWwudGltZSk7CiAgfTsKICBmdW5jdGlvbiBNZWRpYUNvbnRyb2xsZXJfQ29ubmVjdEhhbmdvdXRzTWVkaWFSb3V0ZUNvbnRyb2xsZXJfUGFyYW1zKHZhbHVlcykgewogICAgdGhpcy5pbml0RGVmYXVsdHNfKCk7CiAgICB0aGlzLmluaXRGaWVsZHNfKHZhbHVlcyk7CiAgfQoKCiAgTWVkaWFDb250cm9sbGVyX0Nvbm5lY3RIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyX1BhcmFtcy5wcm90b3R5cGUuaW5pdERlZmF1bHRzXyA9IGZ1bmN0aW9uKCkgewogICAgdGhpcy5jb250cm9sbGVyUmVxdWVzdCA9IG5ldyBiaW5kaW5ncy5JbnRlcmZhY2VSZXF1ZXN0KCk7CiAgfTsKICBNZWRpYUNvbnRyb2xsZXJfQ29ubmVjdEhhbmdvdXRzTWVkaWFSb3V0ZUNvbnRyb2xsZXJfUGFyYW1zLnByb3RvdHlwZS5pbml0RmllbGRzXyA9IGZ1bmN0aW9uKGZpZWxkcykgewogICAgZm9yKHZhciBmaWVsZCBpbiBmaWVsZHMpIHsKICAgICAgICBpZiAodGhpcy5oYXNPd25Qcm9wZXJ0eShmaWVsZCkpCiAgICAgICAgICB0aGlzW2ZpZWxkXSA9IGZpZWxkc1tmaWVsZF07CiAgICB9CiAgfTsKCiAgTWVkaWFDb250cm9sbGVyX0Nvbm5lY3RIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyX1BhcmFtcy52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiAxNn0KICAgIF07CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0VmVyc2lvbihvZmZzZXQsIGtWZXJzaW9uU2l6ZXMpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhQ29udHJvbGxlcl9Db25uZWN0SGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlcl9QYXJhbXMuY29udHJvbGxlclJlcXVlc3QKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVJbnRlcmZhY2VSZXF1ZXN0KG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMCwgZmFsc2UpCiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIE1lZGlhQ29udHJvbGxlcl9Db25uZWN0SGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlcl9QYXJhbXMuZW5jb2RlZFNpemUgPSBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDg7CgogIE1lZGlhQ29udHJvbGxlcl9Db25uZWN0SGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlcl9QYXJhbXMuZGVjb2RlID0gZnVuY3Rpb24oZGVjb2RlcikgewogICAgdmFyIHBhY2tlZDsKICAgIHZhciB2YWwgPSBuZXcgTWVkaWFDb250cm9sbGVyX0Nvbm5lY3RIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyX1BhcmFtcygpOwogICAgdmFyIG51bWJlck9mQnl0ZXMgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhciB2ZXJzaW9uID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YWwuY29udHJvbGxlclJlcXVlc3QgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5JbnRlcmZhY2VSZXF1ZXN0KTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIHJldHVybiB2YWw7CiAgfTsKCiAgTWVkaWFDb250cm9sbGVyX0Nvbm5lY3RIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyX1BhcmFtcy5lbmNvZGUgPSBmdW5jdGlvbihlbmNvZGVyLCB2YWwpIHsKICAgIHZhciBwYWNrZWQ7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKE1lZGlhQ29udHJvbGxlcl9Db25uZWN0SGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlcl9QYXJhbXMuZW5jb2RlZFNpemUpOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMigwKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLkludGVyZmFjZVJlcXVlc3QsIHZhbC5jb250cm9sbGVyUmVxdWVzdCk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgfTsKICBmdW5jdGlvbiBIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyX1NldExvY2FsUHJlc2VudF9QYXJhbXModmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyX1NldExvY2FsUHJlc2VudF9QYXJhbXMucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMubG9jYWxQcmVzZW50ID0gZmFsc2U7CiAgfTsKICBIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyX1NldExvY2FsUHJlc2VudF9QYXJhbXMucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyX1NldExvY2FsUHJlc2VudF9QYXJhbXMudmFsaWRhdGUgPSBmdW5jdGlvbihtZXNzYWdlVmFsaWRhdG9yLCBvZmZzZXQpIHsKICAgIHZhciBlcnI7CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0SGVhZGVyKG9mZnNldCwgY29kZWMua1N0cnVjdEhlYWRlclNpemUpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgdmFyIGtWZXJzaW9uU2l6ZXMgPSBbCiAgICAgIHt2ZXJzaW9uOiAwLCBudW1CeXRlczogMTZ9CiAgICBdOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFZlcnNpb24ob2Zmc2V0LCBrVmVyc2lvblNpemVzKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIEhhbmdvdXRzTWVkaWFSb3V0ZUNvbnRyb2xsZXJfU2V0TG9jYWxQcmVzZW50X1BhcmFtcy5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgODsKCiAgSGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlcl9TZXRMb2NhbFByZXNlbnRfUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IEhhbmdvdXRzTWVkaWFSb3V0ZUNvbnRyb2xsZXJfU2V0TG9jYWxQcmVzZW50X1BhcmFtcygpOwogICAgdmFyIG51bWJlck9mQnl0ZXMgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhciB2ZXJzaW9uID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICBwYWNrZWQgPSBkZWNvZGVyLnJlYWRVaW50OCgpOwogICAgdmFsLmxvY2FsUHJlc2VudCA9IChwYWNrZWQgPj4gMCkgJiAxID8gdHJ1ZSA6IGZhbHNlOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyX1NldExvY2FsUHJlc2VudF9QYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyX1NldExvY2FsUHJlc2VudF9QYXJhbXMuZW5jb2RlZFNpemUpOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMigwKTsKICAgIHBhY2tlZCA9IDA7CiAgICBwYWNrZWQgfD0gKHZhbC5sb2NhbFByZXNlbnQgJiAxKSA8PCAwCiAgICBlbmNvZGVyLndyaXRlVWludDgocGFja2VkKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICB9OwogIHZhciBrTWVkaWFDb250cm9sbGVyX1BsYXlfTmFtZSA9IDgzMDYxOTk2MjsKICB2YXIga01lZGlhQ29udHJvbGxlcl9QYXVzZV9OYW1lID0gMzE4Mzg5MzMxOwogIHZhciBrTWVkaWFDb250cm9sbGVyX1NldE11dGVfTmFtZSA9IDg2OTE0MDQ3MjsKICB2YXIga01lZGlhQ29udHJvbGxlcl9TZXRWb2x1bWVfTmFtZSA9IDEwMzM3MTIwNzsKICB2YXIga01lZGlhQ29udHJvbGxlcl9TZWVrX05hbWUgPSAxMjU4MzI4NzE0OwogIHZhciBrTWVkaWFDb250cm9sbGVyX0Nvbm5lY3RIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyX05hbWUgPSAyMDg3NDAzODYyOwoKICBmdW5jdGlvbiBNZWRpYUNvbnRyb2xsZXJQdHIoaGFuZGxlT3JQdHJJbmZvKSB7CiAgICB0aGlzLnB0ciA9IG5ldyBiaW5kaW5ncy5JbnRlcmZhY2VQdHJDb250cm9sbGVyKE1lZGlhQ29udHJvbGxlciwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaGFuZGxlT3JQdHJJbmZvKTsKICB9CgogIGZ1bmN0aW9uIE1lZGlhQ29udHJvbGxlckFzc29jaWF0ZWRQdHIoYXNzb2NpYXRlZEludGVyZmFjZVB0ckluZm8pIHsKICAgIHRoaXMucHRyID0gbmV3IGFzc29jaWF0ZWRCaW5kaW5ncy5Bc3NvY2lhdGVkSW50ZXJmYWNlUHRyQ29udHJvbGxlcigKICAgICAgICBNZWRpYUNvbnRyb2xsZXIsIGFzc29jaWF0ZWRJbnRlcmZhY2VQdHJJbmZvKTsKICB9CgogIE1lZGlhQ29udHJvbGxlckFzc29jaWF0ZWRQdHIucHJvdG90eXBlID0KICAgICAgT2JqZWN0LmNyZWF0ZShNZWRpYUNvbnRyb2xsZXJQdHIucHJvdG90eXBlKTsKICBNZWRpYUNvbnRyb2xsZXJBc3NvY2lhdGVkUHRyLnByb3RvdHlwZS5jb25zdHJ1Y3RvciA9CiAgICAgIE1lZGlhQ29udHJvbGxlckFzc29jaWF0ZWRQdHI7CgogIGZ1bmN0aW9uIE1lZGlhQ29udHJvbGxlclByb3h5KHJlY2VpdmVyKSB7CiAgICB0aGlzLnJlY2VpdmVyXyA9IHJlY2VpdmVyOwogIH0KICBNZWRpYUNvbnRyb2xsZXJQdHIucHJvdG90eXBlLnBsYXkgPSBmdW5jdGlvbigpIHsKICAgIHJldHVybiBNZWRpYUNvbnRyb2xsZXJQcm94eS5wcm90b3R5cGUucGxheQogICAgICAgIC5hcHBseSh0aGlzLnB0ci5nZXRQcm94eSgpLCBhcmd1bWVudHMpOwogIH07CgogIE1lZGlhQ29udHJvbGxlclByb3h5LnByb3RvdHlwZS5wbGF5ID0gZnVuY3Rpb24oKSB7CiAgICB2YXIgcGFyYW1zID0gbmV3IE1lZGlhQ29udHJvbGxlcl9QbGF5X1BhcmFtcygpOwogICAgdmFyIGJ1aWxkZXIgPSBuZXcgY29kZWMuTWVzc2FnZVYwQnVpbGRlcigKICAgICAgICBrTWVkaWFDb250cm9sbGVyX1BsYXlfTmFtZSwKICAgICAgICBjb2RlYy5hbGlnbihNZWRpYUNvbnRyb2xsZXJfUGxheV9QYXJhbXMuZW5jb2RlZFNpemUpKTsKICAgIGJ1aWxkZXIuZW5jb2RlU3RydWN0KE1lZGlhQ29udHJvbGxlcl9QbGF5X1BhcmFtcywgcGFyYW1zKTsKICAgIHZhciBtZXNzYWdlID0gYnVpbGRlci5maW5pc2goKTsKICAgIHRoaXMucmVjZWl2ZXJfLmFjY2VwdChtZXNzYWdlKTsKICB9OwogIE1lZGlhQ29udHJvbGxlclB0ci5wcm90b3R5cGUucGF1c2UgPSBmdW5jdGlvbigpIHsKICAgIHJldHVybiBNZWRpYUNvbnRyb2xsZXJQcm94eS5wcm90b3R5cGUucGF1c2UKICAgICAgICAuYXBwbHkodGhpcy5wdHIuZ2V0UHJveHkoKSwgYXJndW1lbnRzKTsKICB9OwoKICBNZWRpYUNvbnRyb2xsZXJQcm94eS5wcm90b3R5cGUucGF1c2UgPSBmdW5jdGlvbigpIHsKICAgIHZhciBwYXJhbXMgPSBuZXcgTWVkaWFDb250cm9sbGVyX1BhdXNlX1BhcmFtcygpOwogICAgdmFyIGJ1aWxkZXIgPSBuZXcgY29kZWMuTWVzc2FnZVYwQnVpbGRlcigKICAgICAgICBrTWVkaWFDb250cm9sbGVyX1BhdXNlX05hbWUsCiAgICAgICAgY29kZWMuYWxpZ24oTWVkaWFDb250cm9sbGVyX1BhdXNlX1BhcmFtcy5lbmNvZGVkU2l6ZSkpOwogICAgYnVpbGRlci5lbmNvZGVTdHJ1Y3QoTWVkaWFDb250cm9sbGVyX1BhdXNlX1BhcmFtcywgcGFyYW1zKTsKICAgIHZhciBtZXNzYWdlID0gYnVpbGRlci5maW5pc2goKTsKICAgIHRoaXMucmVjZWl2ZXJfLmFjY2VwdChtZXNzYWdlKTsKICB9OwogIE1lZGlhQ29udHJvbGxlclB0ci5wcm90b3R5cGUuc2V0TXV0ZSA9IGZ1bmN0aW9uKCkgewogICAgcmV0dXJuIE1lZGlhQ29udHJvbGxlclByb3h5LnByb3RvdHlwZS5zZXRNdXRlCiAgICAgICAgLmFwcGx5KHRoaXMucHRyLmdldFByb3h5KCksIGFyZ3VtZW50cyk7CiAgfTsKCiAgTWVkaWFDb250cm9sbGVyUHJveHkucHJvdG90eXBlLnNldE11dGUgPSBmdW5jdGlvbihtdXRlKSB7CiAgICB2YXIgcGFyYW1zID0gbmV3IE1lZGlhQ29udHJvbGxlcl9TZXRNdXRlX1BhcmFtcygpOwogICAgcGFyYW1zLm11dGUgPSBtdXRlOwogICAgdmFyIGJ1aWxkZXIgPSBuZXcgY29kZWMuTWVzc2FnZVYwQnVpbGRlcigKICAgICAgICBrTWVkaWFDb250cm9sbGVyX1NldE11dGVfTmFtZSwKICAgICAgICBjb2RlYy5hbGlnbihNZWRpYUNvbnRyb2xsZXJfU2V0TXV0ZV9QYXJhbXMuZW5jb2RlZFNpemUpKTsKICAgIGJ1aWxkZXIuZW5jb2RlU3RydWN0KE1lZGlhQ29udHJvbGxlcl9TZXRNdXRlX1BhcmFtcywgcGFyYW1zKTsKICAgIHZhciBtZXNzYWdlID0gYnVpbGRlci5maW5pc2goKTsKICAgIHRoaXMucmVjZWl2ZXJfLmFjY2VwdChtZXNzYWdlKTsKICB9OwogIE1lZGlhQ29udHJvbGxlclB0ci5wcm90b3R5cGUuc2V0Vm9sdW1lID0gZnVuY3Rpb24oKSB7CiAgICByZXR1cm4gTWVkaWFDb250cm9sbGVyUHJveHkucHJvdG90eXBlLnNldFZvbHVtZQogICAgICAgIC5hcHBseSh0aGlzLnB0ci5nZXRQcm94eSgpLCBhcmd1bWVudHMpOwogIH07CgogIE1lZGlhQ29udHJvbGxlclByb3h5LnByb3RvdHlwZS5zZXRWb2x1bWUgPSBmdW5jdGlvbih2b2x1bWUpIHsKICAgIHZhciBwYXJhbXMgPSBuZXcgTWVkaWFDb250cm9sbGVyX1NldFZvbHVtZV9QYXJhbXMoKTsKICAgIHBhcmFtcy52b2x1bWUgPSB2b2x1bWU7CiAgICB2YXIgYnVpbGRlciA9IG5ldyBjb2RlYy5NZXNzYWdlVjBCdWlsZGVyKAogICAgICAgIGtNZWRpYUNvbnRyb2xsZXJfU2V0Vm9sdW1lX05hbWUsCiAgICAgICAgY29kZWMuYWxpZ24oTWVkaWFDb250cm9sbGVyX1NldFZvbHVtZV9QYXJhbXMuZW5jb2RlZFNpemUpKTsKICAgIGJ1aWxkZXIuZW5jb2RlU3RydWN0KE1lZGlhQ29udHJvbGxlcl9TZXRWb2x1bWVfUGFyYW1zLCBwYXJhbXMpOwogICAgdmFyIG1lc3NhZ2UgPSBidWlsZGVyLmZpbmlzaCgpOwogICAgdGhpcy5yZWNlaXZlcl8uYWNjZXB0KG1lc3NhZ2UpOwogIH07CiAgTWVkaWFDb250cm9sbGVyUHRyLnByb3RvdHlwZS5zZWVrID0gZnVuY3Rpb24oKSB7CiAgICByZXR1cm4gTWVkaWFDb250cm9sbGVyUHJveHkucHJvdG90eXBlLnNlZWsKICAgICAgICAuYXBwbHkodGhpcy5wdHIuZ2V0UHJveHkoKSwgYXJndW1lbnRzKTsKICB9OwoKICBNZWRpYUNvbnRyb2xsZXJQcm94eS5wcm90b3R5cGUuc2VlayA9IGZ1bmN0aW9uKHRpbWUpIHsKICAgIHZhciBwYXJhbXMgPSBuZXcgTWVkaWFDb250cm9sbGVyX1NlZWtfUGFyYW1zKCk7CiAgICBwYXJhbXMudGltZSA9IHRpbWU7CiAgICB2YXIgYnVpbGRlciA9IG5ldyBjb2RlYy5NZXNzYWdlVjBCdWlsZGVyKAogICAgICAgIGtNZWRpYUNvbnRyb2xsZXJfU2Vla19OYW1lLAogICAgICAgIGNvZGVjLmFsaWduKE1lZGlhQ29udHJvbGxlcl9TZWVrX1BhcmFtcy5lbmNvZGVkU2l6ZSkpOwogICAgYnVpbGRlci5lbmNvZGVTdHJ1Y3QoTWVkaWFDb250cm9sbGVyX1NlZWtfUGFyYW1zLCBwYXJhbXMpOwogICAgdmFyIG1lc3NhZ2UgPSBidWlsZGVyLmZpbmlzaCgpOwogICAgdGhpcy5yZWNlaXZlcl8uYWNjZXB0KG1lc3NhZ2UpOwogIH07CiAgTWVkaWFDb250cm9sbGVyUHRyLnByb3RvdHlwZS5jb25uZWN0SGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlciA9IGZ1bmN0aW9uKCkgewogICAgcmV0dXJuIE1lZGlhQ29udHJvbGxlclByb3h5LnByb3RvdHlwZS5jb25uZWN0SGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlcgogICAgICAgIC5hcHBseSh0aGlzLnB0ci5nZXRQcm94eSgpLCBhcmd1bWVudHMpOwogIH07CgogIE1lZGlhQ29udHJvbGxlclByb3h5LnByb3RvdHlwZS5jb25uZWN0SGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlciA9IGZ1bmN0aW9uKGNvbnRyb2xsZXJSZXF1ZXN0KSB7CiAgICB2YXIgcGFyYW1zID0gbmV3IE1lZGlhQ29udHJvbGxlcl9Db25uZWN0SGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlcl9QYXJhbXMoKTsKICAgIHBhcmFtcy5jb250cm9sbGVyUmVxdWVzdCA9IGNvbnRyb2xsZXJSZXF1ZXN0OwogICAgdmFyIGJ1aWxkZXIgPSBuZXcgY29kZWMuTWVzc2FnZVYwQnVpbGRlcigKICAgICAgICBrTWVkaWFDb250cm9sbGVyX0Nvbm5lY3RIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyX05hbWUsCiAgICAgICAgY29kZWMuYWxpZ24oTWVkaWFDb250cm9sbGVyX0Nvbm5lY3RIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyX1BhcmFtcy5lbmNvZGVkU2l6ZSkpOwogICAgYnVpbGRlci5lbmNvZGVTdHJ1Y3QoTWVkaWFDb250cm9sbGVyX0Nvbm5lY3RIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyX1BhcmFtcywgcGFyYW1zKTsKICAgIHZhciBtZXNzYWdlID0gYnVpbGRlci5maW5pc2goKTsKICAgIHRoaXMucmVjZWl2ZXJfLmFjY2VwdChtZXNzYWdlKTsKICB9OwoKICBmdW5jdGlvbiBNZWRpYUNvbnRyb2xsZXJTdHViKGRlbGVnYXRlKSB7CiAgICB0aGlzLmRlbGVnYXRlXyA9IGRlbGVnYXRlOwogIH0KICBNZWRpYUNvbnRyb2xsZXJTdHViLnByb3RvdHlwZS5wbGF5ID0gZnVuY3Rpb24oKSB7CiAgICByZXR1cm4gdGhpcy5kZWxlZ2F0ZV8gJiYgdGhpcy5kZWxlZ2F0ZV8ucGxheSAmJiB0aGlzLmRlbGVnYXRlXy5wbGF5KCk7CiAgfQogIE1lZGlhQ29udHJvbGxlclN0dWIucHJvdG90eXBlLnBhdXNlID0gZnVuY3Rpb24oKSB7CiAgICByZXR1cm4gdGhpcy5kZWxlZ2F0ZV8gJiYgdGhpcy5kZWxlZ2F0ZV8ucGF1c2UgJiYgdGhpcy5kZWxlZ2F0ZV8ucGF1c2UoKTsKICB9CiAgTWVkaWFDb250cm9sbGVyU3R1Yi5wcm90b3R5cGUuc2V0TXV0ZSA9IGZ1bmN0aW9uKG11dGUpIHsKICAgIHJldHVybiB0aGlzLmRlbGVnYXRlXyAmJiB0aGlzLmRlbGVnYXRlXy5zZXRNdXRlICYmIHRoaXMuZGVsZWdhdGVfLnNldE11dGUobXV0ZSk7CiAgfQogIE1lZGlhQ29udHJvbGxlclN0dWIucHJvdG90eXBlLnNldFZvbHVtZSA9IGZ1bmN0aW9uKHZvbHVtZSkgewogICAgcmV0dXJuIHRoaXMuZGVsZWdhdGVfICYmIHRoaXMuZGVsZWdhdGVfLnNldFZvbHVtZSAmJiB0aGlzLmRlbGVnYXRlXy5zZXRWb2x1bWUodm9sdW1lKTsKICB9CiAgTWVkaWFDb250cm9sbGVyU3R1Yi5wcm90b3R5cGUuc2VlayA9IGZ1bmN0aW9uKHRpbWUpIHsKICAgIHJldHVybiB0aGlzLmRlbGVnYXRlXyAmJiB0aGlzLmRlbGVnYXRlXy5zZWVrICYmIHRoaXMuZGVsZWdhdGVfLnNlZWsodGltZSk7CiAgfQogIE1lZGlhQ29udHJvbGxlclN0dWIucHJvdG90eXBlLmNvbm5lY3RIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyID0gZnVuY3Rpb24oY29udHJvbGxlclJlcXVlc3QpIHsKICAgIHJldHVybiB0aGlzLmRlbGVnYXRlXyAmJiB0aGlzLmRlbGVnYXRlXy5jb25uZWN0SGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlciAmJiB0aGlzLmRlbGVnYXRlXy5jb25uZWN0SGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlcihjb250cm9sbGVyUmVxdWVzdCk7CiAgfQoKICBNZWRpYUNvbnRyb2xsZXJTdHViLnByb3RvdHlwZS5hY2NlcHQgPSBmdW5jdGlvbihtZXNzYWdlKSB7CiAgICB2YXIgcmVhZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VSZWFkZXIobWVzc2FnZSk7CiAgICBzd2l0Y2ggKHJlYWRlci5tZXNzYWdlTmFtZSkgewogICAgY2FzZSBrTWVkaWFDb250cm9sbGVyX1BsYXlfTmFtZToKICAgICAgdmFyIHBhcmFtcyA9IHJlYWRlci5kZWNvZGVTdHJ1Y3QoTWVkaWFDb250cm9sbGVyX1BsYXlfUGFyYW1zKTsKICAgICAgdGhpcy5wbGF5KCk7CiAgICAgIHJldHVybiB0cnVlOwogICAgY2FzZSBrTWVkaWFDb250cm9sbGVyX1BhdXNlX05hbWU6CiAgICAgIHZhciBwYXJhbXMgPSByZWFkZXIuZGVjb2RlU3RydWN0KE1lZGlhQ29udHJvbGxlcl9QYXVzZV9QYXJhbXMpOwogICAgICB0aGlzLnBhdXNlKCk7CiAgICAgIHJldHVybiB0cnVlOwogICAgY2FzZSBrTWVkaWFDb250cm9sbGVyX1NldE11dGVfTmFtZToKICAgICAgdmFyIHBhcmFtcyA9IHJlYWRlci5kZWNvZGVTdHJ1Y3QoTWVkaWFDb250cm9sbGVyX1NldE11dGVfUGFyYW1zKTsKICAgICAgdGhpcy5zZXRNdXRlKHBhcmFtcy5tdXRlKTsKICAgICAgcmV0dXJuIHRydWU7CiAgICBjYXNlIGtNZWRpYUNvbnRyb2xsZXJfU2V0Vm9sdW1lX05hbWU6CiAgICAgIHZhciBwYXJhbXMgPSByZWFkZXIuZGVjb2RlU3RydWN0KE1lZGlhQ29udHJvbGxlcl9TZXRWb2x1bWVfUGFyYW1zKTsKICAgICAgdGhpcy5zZXRWb2x1bWUocGFyYW1zLnZvbHVtZSk7CiAgICAgIHJldHVybiB0cnVlOwogICAgY2FzZSBrTWVkaWFDb250cm9sbGVyX1NlZWtfTmFtZToKICAgICAgdmFyIHBhcmFtcyA9IHJlYWRlci5kZWNvZGVTdHJ1Y3QoTWVkaWFDb250cm9sbGVyX1NlZWtfUGFyYW1zKTsKICAgICAgdGhpcy5zZWVrKHBhcmFtcy50aW1lKTsKICAgICAgcmV0dXJuIHRydWU7CiAgICBjYXNlIGtNZWRpYUNvbnRyb2xsZXJfQ29ubmVjdEhhbmdvdXRzTWVkaWFSb3V0ZUNvbnRyb2xsZXJfTmFtZToKICAgICAgdmFyIHBhcmFtcyA9IHJlYWRlci5kZWNvZGVTdHJ1Y3QoTWVkaWFDb250cm9sbGVyX0Nvbm5lY3RIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyX1BhcmFtcyk7CiAgICAgIHRoaXMuY29ubmVjdEhhbmdvdXRzTWVkaWFSb3V0ZUNvbnRyb2xsZXIocGFyYW1zLmNvbnRyb2xsZXJSZXF1ZXN0KTsKICAgICAgcmV0dXJuIHRydWU7CiAgICBkZWZhdWx0OgogICAgICByZXR1cm4gZmFsc2U7CiAgICB9CiAgfTsKCiAgTWVkaWFDb250cm9sbGVyU3R1Yi5wcm90b3R5cGUuYWNjZXB0V2l0aFJlc3BvbmRlciA9CiAgICAgIGZ1bmN0aW9uKG1lc3NhZ2UsIHJlc3BvbmRlcikgewogICAgdmFyIHJlYWRlciA9IG5ldyBjb2RlYy5NZXNzYWdlUmVhZGVyKG1lc3NhZ2UpOwogICAgc3dpdGNoIChyZWFkZXIubWVzc2FnZU5hbWUpIHsKICAgIGRlZmF1bHQ6CiAgICAgIHJldHVybiBmYWxzZTsKICAgIH0KICB9OwoKICBmdW5jdGlvbiB2YWxpZGF0ZU1lZGlhQ29udHJvbGxlclJlcXVlc3QobWVzc2FnZVZhbGlkYXRvcikgewogICAgdmFyIG1lc3NhZ2UgPSBtZXNzYWdlVmFsaWRhdG9yLm1lc3NhZ2U7CiAgICB2YXIgcGFyYW1zQ2xhc3MgPSBudWxsOwogICAgc3dpdGNoIChtZXNzYWdlLmdldE5hbWUoKSkgewogICAgICBjYXNlIGtNZWRpYUNvbnRyb2xsZXJfUGxheV9OYW1lOgogICAgICAgIGlmICghbWVzc2FnZS5leHBlY3RzUmVzcG9uc2UoKSAmJiAhbWVzc2FnZS5pc1Jlc3BvbnNlKCkpCiAgICAgICAgICBwYXJhbXNDbGFzcyA9IE1lZGlhQ29udHJvbGxlcl9QbGF5X1BhcmFtczsKICAgICAgYnJlYWs7CiAgICAgIGNhc2Uga01lZGlhQ29udHJvbGxlcl9QYXVzZV9OYW1lOgogICAgICAgIGlmICghbWVzc2FnZS5leHBlY3RzUmVzcG9uc2UoKSAmJiAhbWVzc2FnZS5pc1Jlc3BvbnNlKCkpCiAgICAgICAgICBwYXJhbXNDbGFzcyA9IE1lZGlhQ29udHJvbGxlcl9QYXVzZV9QYXJhbXM7CiAgICAgIGJyZWFrOwogICAgICBjYXNlIGtNZWRpYUNvbnRyb2xsZXJfU2V0TXV0ZV9OYW1lOgogICAgICAgIGlmICghbWVzc2FnZS5leHBlY3RzUmVzcG9uc2UoKSAmJiAhbWVzc2FnZS5pc1Jlc3BvbnNlKCkpCiAgICAgICAgICBwYXJhbXNDbGFzcyA9IE1lZGlhQ29udHJvbGxlcl9TZXRNdXRlX1BhcmFtczsKICAgICAgYnJlYWs7CiAgICAgIGNhc2Uga01lZGlhQ29udHJvbGxlcl9TZXRWb2x1bWVfTmFtZToKICAgICAgICBpZiAoIW1lc3NhZ2UuZXhwZWN0c1Jlc3BvbnNlKCkgJiYgIW1lc3NhZ2UuaXNSZXNwb25zZSgpKQogICAgICAgICAgcGFyYW1zQ2xhc3MgPSBNZWRpYUNvbnRyb2xsZXJfU2V0Vm9sdW1lX1BhcmFtczsKICAgICAgYnJlYWs7CiAgICAgIGNhc2Uga01lZGlhQ29udHJvbGxlcl9TZWVrX05hbWU6CiAgICAgICAgaWYgKCFtZXNzYWdlLmV4cGVjdHNSZXNwb25zZSgpICYmICFtZXNzYWdlLmlzUmVzcG9uc2UoKSkKICAgICAgICAgIHBhcmFtc0NsYXNzID0gTWVkaWFDb250cm9sbGVyX1NlZWtfUGFyYW1zOwogICAgICBicmVhazsKICAgICAgY2FzZSBrTWVkaWFDb250cm9sbGVyX0Nvbm5lY3RIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyX05hbWU6CiAgICAgICAgaWYgKCFtZXNzYWdlLmV4cGVjdHNSZXNwb25zZSgpICYmICFtZXNzYWdlLmlzUmVzcG9uc2UoKSkKICAgICAgICAgIHBhcmFtc0NsYXNzID0gTWVkaWFDb250cm9sbGVyX0Nvbm5lY3RIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyX1BhcmFtczsKICAgICAgYnJlYWs7CiAgICB9CiAgICBpZiAocGFyYW1zQ2xhc3MgPT09IG51bGwpCiAgICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgICByZXR1cm4gcGFyYW1zQ2xhc3MudmFsaWRhdGUobWVzc2FnZVZhbGlkYXRvciwgbWVzc2FnZVZhbGlkYXRvci5tZXNzYWdlLmdldEhlYWRlck51bUJ5dGVzKCkpOwogIH0KCiAgZnVuY3Rpb24gdmFsaWRhdGVNZWRpYUNvbnRyb2xsZXJSZXNwb25zZShtZXNzYWdlVmFsaWRhdG9yKSB7CiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH0KCiAgdmFyIE1lZGlhQ29udHJvbGxlciA9IHsKICAgIG5hbWU6ICdtZWRpYV9yb3V0ZXI6Om1vam9tOjpNZWRpYUNvbnRyb2xsZXInLAogICAga1ZlcnNpb246IDAsCiAgICBwdHJDbGFzczogTWVkaWFDb250cm9sbGVyUHRyLAogICAgcHJveHlDbGFzczogTWVkaWFDb250cm9sbGVyUHJveHksCiAgICBzdHViQ2xhc3M6IE1lZGlhQ29udHJvbGxlclN0dWIsCiAgICB2YWxpZGF0ZVJlcXVlc3Q6IHZhbGlkYXRlTWVkaWFDb250cm9sbGVyUmVxdWVzdCwKICAgIHZhbGlkYXRlUmVzcG9uc2U6IG51bGwsCiAgfTsKICBNZWRpYUNvbnRyb2xsZXJTdHViLnByb3RvdHlwZS52YWxpZGF0b3IgPSB2YWxpZGF0ZU1lZGlhQ29udHJvbGxlclJlcXVlc3Q7CiAgTWVkaWFDb250cm9sbGVyUHJveHkucHJvdG90eXBlLnZhbGlkYXRvciA9IG51bGw7CiAgdmFyIGtIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyX1NldExvY2FsUHJlc2VudF9OYW1lID0gMTEwMjg5MDU5ODsKCiAgZnVuY3Rpb24gSGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlclB0cihoYW5kbGVPclB0ckluZm8pIHsKICAgIHRoaXMucHRyID0gbmV3IGJpbmRpbmdzLkludGVyZmFjZVB0ckNvbnRyb2xsZXIoSGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlciwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaGFuZGxlT3JQdHJJbmZvKTsKICB9CgogIGZ1bmN0aW9uIEhhbmdvdXRzTWVkaWFSb3V0ZUNvbnRyb2xsZXJBc3NvY2lhdGVkUHRyKGFzc29jaWF0ZWRJbnRlcmZhY2VQdHJJbmZvKSB7CiAgICB0aGlzLnB0ciA9IG5ldyBhc3NvY2lhdGVkQmluZGluZ3MuQXNzb2NpYXRlZEludGVyZmFjZVB0ckNvbnRyb2xsZXIoCiAgICAgICAgSGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlciwgYXNzb2NpYXRlZEludGVyZmFjZVB0ckluZm8pOwogIH0KCiAgSGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlckFzc29jaWF0ZWRQdHIucHJvdG90eXBlID0KICAgICAgT2JqZWN0LmNyZWF0ZShIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyUHRyLnByb3RvdHlwZSk7CiAgSGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlckFzc29jaWF0ZWRQdHIucHJvdG90eXBlLmNvbnN0cnVjdG9yID0KICAgICAgSGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlckFzc29jaWF0ZWRQdHI7CgogIGZ1bmN0aW9uIEhhbmdvdXRzTWVkaWFSb3V0ZUNvbnRyb2xsZXJQcm94eShyZWNlaXZlcikgewogICAgdGhpcy5yZWNlaXZlcl8gPSByZWNlaXZlcjsKICB9CiAgSGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlclB0ci5wcm90b3R5cGUuc2V0TG9jYWxQcmVzZW50ID0gZnVuY3Rpb24oKSB7CiAgICByZXR1cm4gSGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlclByb3h5LnByb3RvdHlwZS5zZXRMb2NhbFByZXNlbnQKICAgICAgICAuYXBwbHkodGhpcy5wdHIuZ2V0UHJveHkoKSwgYXJndW1lbnRzKTsKICB9OwoKICBIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyUHJveHkucHJvdG90eXBlLnNldExvY2FsUHJlc2VudCA9IGZ1bmN0aW9uKGxvY2FsUHJlc2VudCkgewogICAgdmFyIHBhcmFtcyA9IG5ldyBIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyX1NldExvY2FsUHJlc2VudF9QYXJhbXMoKTsKICAgIHBhcmFtcy5sb2NhbFByZXNlbnQgPSBsb2NhbFByZXNlbnQ7CiAgICB2YXIgYnVpbGRlciA9IG5ldyBjb2RlYy5NZXNzYWdlVjBCdWlsZGVyKAogICAgICAgIGtIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyX1NldExvY2FsUHJlc2VudF9OYW1lLAogICAgICAgIGNvZGVjLmFsaWduKEhhbmdvdXRzTWVkaWFSb3V0ZUNvbnRyb2xsZXJfU2V0TG9jYWxQcmVzZW50X1BhcmFtcy5lbmNvZGVkU2l6ZSkpOwogICAgYnVpbGRlci5lbmNvZGVTdHJ1Y3QoSGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlcl9TZXRMb2NhbFByZXNlbnRfUGFyYW1zLCBwYXJhbXMpOwogICAgdmFyIG1lc3NhZ2UgPSBidWlsZGVyLmZpbmlzaCgpOwogICAgdGhpcy5yZWNlaXZlcl8uYWNjZXB0KG1lc3NhZ2UpOwogIH07CgogIGZ1bmN0aW9uIEhhbmdvdXRzTWVkaWFSb3V0ZUNvbnRyb2xsZXJTdHViKGRlbGVnYXRlKSB7CiAgICB0aGlzLmRlbGVnYXRlXyA9IGRlbGVnYXRlOwogIH0KICBIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyU3R1Yi5wcm90b3R5cGUuc2V0TG9jYWxQcmVzZW50ID0gZnVuY3Rpb24obG9jYWxQcmVzZW50KSB7CiAgICByZXR1cm4gdGhpcy5kZWxlZ2F0ZV8gJiYgdGhpcy5kZWxlZ2F0ZV8uc2V0TG9jYWxQcmVzZW50ICYmIHRoaXMuZGVsZWdhdGVfLnNldExvY2FsUHJlc2VudChsb2NhbFByZXNlbnQpOwogIH0KCiAgSGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlclN0dWIucHJvdG90eXBlLmFjY2VwdCA9IGZ1bmN0aW9uKG1lc3NhZ2UpIHsKICAgIHZhciByZWFkZXIgPSBuZXcgY29kZWMuTWVzc2FnZVJlYWRlcihtZXNzYWdlKTsKICAgIHN3aXRjaCAocmVhZGVyLm1lc3NhZ2VOYW1lKSB7CiAgICBjYXNlIGtIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyX1NldExvY2FsUHJlc2VudF9OYW1lOgogICAgICB2YXIgcGFyYW1zID0gcmVhZGVyLmRlY29kZVN0cnVjdChIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyX1NldExvY2FsUHJlc2VudF9QYXJhbXMpOwogICAgICB0aGlzLnNldExvY2FsUHJlc2VudChwYXJhbXMubG9jYWxQcmVzZW50KTsKICAgICAgcmV0dXJuIHRydWU7CiAgICBkZWZhdWx0OgogICAgICByZXR1cm4gZmFsc2U7CiAgICB9CiAgfTsKCiAgSGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlclN0dWIucHJvdG90eXBlLmFjY2VwdFdpdGhSZXNwb25kZXIgPQogICAgICBmdW5jdGlvbihtZXNzYWdlLCByZXNwb25kZXIpIHsKICAgIHZhciByZWFkZXIgPSBuZXcgY29kZWMuTWVzc2FnZVJlYWRlcihtZXNzYWdlKTsKICAgIHN3aXRjaCAocmVhZGVyLm1lc3NhZ2VOYW1lKSB7CiAgICBkZWZhdWx0OgogICAgICByZXR1cm4gZmFsc2U7CiAgICB9CiAgfTsKCiAgZnVuY3Rpb24gdmFsaWRhdGVIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyUmVxdWVzdChtZXNzYWdlVmFsaWRhdG9yKSB7CiAgICB2YXIgbWVzc2FnZSA9IG1lc3NhZ2VWYWxpZGF0b3IubWVzc2FnZTsKICAgIHZhciBwYXJhbXNDbGFzcyA9IG51bGw7CiAgICBzd2l0Y2ggKG1lc3NhZ2UuZ2V0TmFtZSgpKSB7CiAgICAgIGNhc2Uga0hhbmdvdXRzTWVkaWFSb3V0ZUNvbnRyb2xsZXJfU2V0TG9jYWxQcmVzZW50X05hbWU6CiAgICAgICAgaWYgKCFtZXNzYWdlLmV4cGVjdHNSZXNwb25zZSgpICYmICFtZXNzYWdlLmlzUmVzcG9uc2UoKSkKICAgICAgICAgIHBhcmFtc0NsYXNzID0gSGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlcl9TZXRMb2NhbFByZXNlbnRfUGFyYW1zOwogICAgICBicmVhazsKICAgIH0KICAgIGlmIChwYXJhbXNDbGFzcyA9PT0gbnVsbCkKICAgICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKICAgIHJldHVybiBwYXJhbXNDbGFzcy52YWxpZGF0ZShtZXNzYWdlVmFsaWRhdG9yLCBtZXNzYWdlVmFsaWRhdG9yLm1lc3NhZ2UuZ2V0SGVhZGVyTnVtQnl0ZXMoKSk7CiAgfQoKICBmdW5jdGlvbiB2YWxpZGF0ZUhhbmdvdXRzTWVkaWFSb3V0ZUNvbnRyb2xsZXJSZXNwb25zZShtZXNzYWdlVmFsaWRhdG9yKSB7CiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH0KCiAgdmFyIEhhbmdvdXRzTWVkaWFSb3V0ZUNvbnRyb2xsZXIgPSB7CiAgICBuYW1lOiAnbWVkaWFfcm91dGVyOjptb2pvbTo6SGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlcicsCiAgICBrVmVyc2lvbjogMCwKICAgIHB0ckNsYXNzOiBIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyUHRyLAogICAgcHJveHlDbGFzczogSGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlclByb3h5LAogICAgc3R1YkNsYXNzOiBIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyU3R1YiwKICAgIHZhbGlkYXRlUmVxdWVzdDogdmFsaWRhdGVIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyUmVxdWVzdCwKICAgIHZhbGlkYXRlUmVzcG9uc2U6IG51bGwsCiAgfTsKICBIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyU3R1Yi5wcm90b3R5cGUudmFsaWRhdG9yID0gdmFsaWRhdGVIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyUmVxdWVzdDsKICBIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyUHJveHkucHJvdG90eXBlLnZhbGlkYXRvciA9IG51bGw7CiAgZXhwb3J0cy5NZWRpYUNvbnRyb2xsZXIgPSBNZWRpYUNvbnRyb2xsZXI7CiAgZXhwb3J0cy5NZWRpYUNvbnRyb2xsZXJQdHIgPSBNZWRpYUNvbnRyb2xsZXJQdHI7CiAgZXhwb3J0cy5NZWRpYUNvbnRyb2xsZXJBc3NvY2lhdGVkUHRyID0gTWVkaWFDb250cm9sbGVyQXNzb2NpYXRlZFB0cjsKICBleHBvcnRzLkhhbmdvdXRzTWVkaWFSb3V0ZUNvbnRyb2xsZXIgPSBIYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyOwogIGV4cG9ydHMuSGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlclB0ciA9IEhhbmdvdXRzTWVkaWFSb3V0ZUNvbnRyb2xsZXJQdHI7CiAgZXhwb3J0cy5IYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyQXNzb2NpYXRlZFB0ciA9IEhhbmdvdXRzTWVkaWFSb3V0ZUNvbnRyb2xsZXJBc3NvY2lhdGVkUHRyOwp9KSgpOy8vIENvcHlyaWdodCAyMDE0IFRoZSBDaHJvbWl1bSBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgovLyBVc2Ugb2YgdGhpcyBzb3VyY2UgY29kZSBpcyBnb3Zlcm5lZCBieSBhIEJTRC1zdHlsZSBsaWNlbnNlIHRoYXQgY2FuIGJlCi8vIGZvdW5kIGluIHRoZSBMSUNFTlNFIGZpbGUuCgondXNlIHN0cmljdCc7CgooZnVuY3Rpb24oKSB7CiAgdmFyIG1vam9tSWQgPSAnY2hyb21lL2NvbW1vbi9tZWRpYV9yb3V0ZXIvbW9qby9tZWRpYV9yb3V0ZXIubW9qb20nOwogIGlmIChtb2pvLmludGVybmFsLmlzTW9qb21Mb2FkZWQobW9qb21JZCkpIHsKICAgIGNvbnNvbGUud2FybignVGhlIGZvbGxvd2luZyBtb2pvbSBpcyBsb2FkZWQgbXVsdGlwbGUgdGltZXM6ICcgKyBtb2pvbUlkKTsKICAgIHJldHVybjsKICB9CiAgbW9qby5pbnRlcm5hbC5tYXJrTW9qb21Mb2FkZWQobW9qb21JZCk7CiAgdmFyIGJpbmRpbmdzID0gbW9qbzsKICB2YXIgYXNzb2NpYXRlZEJpbmRpbmdzID0gbW9qbzsKICB2YXIgY29kZWMgPSBtb2pvLmludGVybmFsOwogIHZhciB2YWxpZGF0b3IgPSBtb2pvLmludGVybmFsOwoKICB2YXIgZXhwb3J0cyA9IG1vam8uaW50ZXJuYWwuZXhwb3NlTmFtZXNwYWNlKCdtZWRpYVJvdXRlci5tb2pvbScpOwogIHZhciBtZWRpYV9jb250cm9sbGVyJCA9CiAgICAgIG1vam8uaW50ZXJuYWwuZXhwb3NlTmFtZXNwYWNlKCdtZWRpYVJvdXRlci5tb2pvbScpOwogIGlmIChtb2pvLmNvbmZpZy5hdXRvTG9hZE1vam9tRGVwcykgewogICAgbW9qby5pbnRlcm5hbC5sb2FkTW9qb21JZk5lY2Vzc2FyeSgKICAgICAgICAnY2hyb21lL2NvbW1vbi9tZWRpYV9yb3V0ZXIvbW9qby9tZWRpYV9jb250cm9sbGVyLm1vam9tJywgJ21lZGlhX2NvbnRyb2xsZXIubW9qb20uanMnKTsKICB9CiAgdmFyIG1lZGlhX3N0YXR1cyQgPQogICAgICBtb2pvLmludGVybmFsLmV4cG9zZU5hbWVzcGFjZSgnbWVkaWFSb3V0ZXIubW9qb20nKTsKICBpZiAobW9qby5jb25maWcuYXV0b0xvYWRNb2pvbURlcHMpIHsKICAgIG1vam8uaW50ZXJuYWwubG9hZE1vam9tSWZOZWNlc3NhcnkoCiAgICAgICAgJ2Nocm9tZS9jb21tb24vbWVkaWFfcm91dGVyL21vam8vbWVkaWFfc3RhdHVzLm1vam9tJywgJ21lZGlhX3N0YXR1cy5tb2pvbS5qcycpOwogIH0KICB2YXIgbWlycm9yX3NlcnZpY2VfcmVtb3RpbmckID0KICAgICAgbW9qby5pbnRlcm5hbC5leHBvc2VOYW1lc3BhY2UoJ21lZGlhLm1vam9tJyk7CiAgaWYgKG1vam8uY29uZmlnLmF1dG9Mb2FkTW9qb21EZXBzKSB7CiAgICBtb2pvLmludGVybmFsLmxvYWRNb2pvbUlmTmVjZXNzYXJ5KAogICAgICAgICdtZWRpYS9tb2pvL2ludGVyZmFjZXMvbWlycm9yX3NlcnZpY2VfcmVtb3RpbmcubW9qb20nLCAnLi4vLi4vLi4vLi4vbWVkaWEvbW9qby9pbnRlcmZhY2VzL21pcnJvcl9zZXJ2aWNlX3JlbW90aW5nLm1vam9tLmpzJyk7CiAgfQogIHZhciB0aW1lJCA9CiAgICAgIG1vam8uaW50ZXJuYWwuZXhwb3NlTmFtZXNwYWNlKCdtb2pvLmNvbW1vbi5tb2pvbScpOwogIGlmIChtb2pvLmNvbmZpZy5hdXRvTG9hZE1vam9tRGVwcykgewogICAgbW9qby5pbnRlcm5hbC5sb2FkTW9qb21JZk5lY2Vzc2FyeSgKICAgICAgICAnbW9qby9jb21tb24vdGltZS5tb2pvbScsICcuLi8uLi8uLi8uLi9tb2pvL2NvbW1vbi90aW1lLm1vam9tLmpzJyk7CiAgfQogIHZhciBpcF9hZGRyZXNzJCA9CiAgICAgIG1vam8uaW50ZXJuYWwuZXhwb3NlTmFtZXNwYWNlKCduZXQuaW50ZXJmYWNlcycpOwogIGlmIChtb2pvLmNvbmZpZy5hdXRvTG9hZE1vam9tRGVwcykgewogICAgbW9qby5pbnRlcm5hbC5sb2FkTW9qb21JZk5lY2Vzc2FyeSgKICAgICAgICAnbmV0L2ludGVyZmFjZXMvaXBfYWRkcmVzcy5tb2pvbScsICcuLi8uLi8uLi8uLi9uZXQvaW50ZXJmYWNlcy9pcF9hZGRyZXNzLm1vam9tLmpzJyk7CiAgfQogIHZhciBpcF9lbmRwb2ludCQgPQogICAgICBtb2pvLmludGVybmFsLmV4cG9zZU5hbWVzcGFjZSgnbmV0LmludGVyZmFjZXMnKTsKICBpZiAobW9qby5jb25maWcuYXV0b0xvYWRNb2pvbURlcHMpIHsKICAgIG1vam8uaW50ZXJuYWwubG9hZE1vam9tSWZOZWNlc3NhcnkoCiAgICAgICAgJ25ldC9pbnRlcmZhY2VzL2lwX2VuZHBvaW50Lm1vam9tJywgJy4uLy4uLy4uLy4uL25ldC9pbnRlcmZhY2VzL2lwX2VuZHBvaW50Lm1vam9tLmpzJyk7CiAgfQogIHZhciBvcmlnaW4kID0KICAgICAgbW9qby5pbnRlcm5hbC5leHBvc2VOYW1lc3BhY2UoJ3VybC5tb2pvbScpOwogIGlmIChtb2pvLmNvbmZpZy5hdXRvTG9hZE1vam9tRGVwcykgewogICAgbW9qby5pbnRlcm5hbC5sb2FkTW9qb21JZk5lY2Vzc2FyeSgKICAgICAgICAndXJsL21vam8vb3JpZ2luLm1vam9tJywgJy4uLy4uLy4uLy4uL3VybC9tb2pvL29yaWdpbi5tb2pvbS5qcycpOwogIH0KICB2YXIgdXJsJCA9CiAgICAgIG1vam8uaW50ZXJuYWwuZXhwb3NlTmFtZXNwYWNlKCd1cmwubW9qb20nKTsKICBpZiAobW9qby5jb25maWcuYXV0b0xvYWRNb2pvbURlcHMpIHsKICAgIG1vam8uaW50ZXJuYWwubG9hZE1vam9tSWZOZWNlc3NhcnkoCiAgICAgICAgJ3VybC9tb2pvL3VybC5tb2pvbScsICcuLi8uLi8uLi8uLi91cmwvbW9qby91cmwubW9qb20uanMnKTsKICB9CgoKICB2YXIgU2lua0ljb25UeXBlID0ge307CiAgU2lua0ljb25UeXBlLkNBU1QgPSAwOwogIFNpbmtJY29uVHlwZS5DQVNUX0FVRElPX0dST1VQID0gU2lua0ljb25UeXBlLkNBU1QgKyAxOwogIFNpbmtJY29uVHlwZS5DQVNUX0FVRElPID0gU2lua0ljb25UeXBlLkNBU1RfQVVESU9fR1JPVVAgKyAxOwogIFNpbmtJY29uVHlwZS5NRUVUSU5HID0gU2lua0ljb25UeXBlLkNBU1RfQVVESU8gKyAxOwogIFNpbmtJY29uVHlwZS5IQU5HT1VUID0gU2lua0ljb25UeXBlLk1FRVRJTkcgKyAxOwogIFNpbmtJY29uVHlwZS5FRFVDQVRJT04gPSBTaW5rSWNvblR5cGUuSEFOR09VVCArIDE7CiAgU2lua0ljb25UeXBlLldJUkVEX0RJU1BMQVkgPSBTaW5rSWNvblR5cGUuRURVQ0FUSU9OICsgMTsKICBTaW5rSWNvblR5cGUuR0VORVJJQyA9IFNpbmtJY29uVHlwZS5XSVJFRF9ESVNQTEFZICsgMTsKCiAgU2lua0ljb25UeXBlLmlzS25vd25FbnVtVmFsdWUgPSBmdW5jdGlvbih2YWx1ZSkgewogICAgc3dpdGNoICh2YWx1ZSkgewogICAgY2FzZSAwOgogICAgY2FzZSAxOgogICAgY2FzZSAyOgogICAgY2FzZSAzOgogICAgY2FzZSA0OgogICAgY2FzZSA1OgogICAgY2FzZSA2OgogICAgY2FzZSA3OgogICAgICByZXR1cm4gdHJ1ZTsKICAgIH0KICAgIHJldHVybiBmYWxzZTsKICB9OwoKICBTaW5rSWNvblR5cGUudmFsaWRhdGUgPSBmdW5jdGlvbihlbnVtVmFsdWUpIHsKICAgIHZhciBpc0V4dGVuc2libGUgPSBmYWxzZTsKICAgIGlmIChpc0V4dGVuc2libGUgfHwgdGhpcy5pc0tub3duRW51bVZhbHVlKGVudW1WYWx1ZSkpCiAgICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuVU5LTk9XTl9FTlVNX1ZBTFVFOwogIH07CiAgdmFyIFJvdXRlQ29udHJvbGxlclR5cGUgPSB7fTsKICBSb3V0ZUNvbnRyb2xsZXJUeXBlLmtOb25lID0gMDsKICBSb3V0ZUNvbnRyb2xsZXJUeXBlLmtHZW5lcmljID0gUm91dGVDb250cm9sbGVyVHlwZS5rTm9uZSArIDE7CiAgUm91dGVDb250cm9sbGVyVHlwZS5rSGFuZ291dHMgPSBSb3V0ZUNvbnRyb2xsZXJUeXBlLmtHZW5lcmljICsgMTsKICBSb3V0ZUNvbnRyb2xsZXJUeXBlLmtNaXJyb3JpbmcgPSBSb3V0ZUNvbnRyb2xsZXJUeXBlLmtIYW5nb3V0cyArIDE7CgogIFJvdXRlQ29udHJvbGxlclR5cGUuaXNLbm93bkVudW1WYWx1ZSA9IGZ1bmN0aW9uKHZhbHVlKSB7CiAgICBzd2l0Y2ggKHZhbHVlKSB7CiAgICBjYXNlIDA6CiAgICBjYXNlIDE6CiAgICBjYXNlIDI6CiAgICBjYXNlIDM6CiAgICAgIHJldHVybiB0cnVlOwogICAgfQogICAgcmV0dXJuIGZhbHNlOwogIH07CgogIFJvdXRlQ29udHJvbGxlclR5cGUudmFsaWRhdGUgPSBmdW5jdGlvbihlbnVtVmFsdWUpIHsKICAgIHZhciBpc0V4dGVuc2libGUgPSBmYWxzZTsKICAgIGlmIChpc0V4dGVuc2libGUgfHwgdGhpcy5pc0tub3duRW51bVZhbHVlKGVudW1WYWx1ZSkpCiAgICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuVU5LTk9XTl9FTlVNX1ZBTFVFOwogIH07CiAgdmFyIFJvdXRlUmVxdWVzdFJlc3VsdENvZGUgPSB7fTsKICBSb3V0ZVJlcXVlc3RSZXN1bHRDb2RlLlVOS05PV05fRVJST1IgPSAwOwogIFJvdXRlUmVxdWVzdFJlc3VsdENvZGUuT0sgPSBSb3V0ZVJlcXVlc3RSZXN1bHRDb2RlLlVOS05PV05fRVJST1IgKyAxOwogIFJvdXRlUmVxdWVzdFJlc3VsdENvZGUuVElNRURfT1VUID0gUm91dGVSZXF1ZXN0UmVzdWx0Q29kZS5PSyArIDE7CiAgUm91dGVSZXF1ZXN0UmVzdWx0Q29kZS5ST1VURV9OT1RfRk9VTkQgPSBSb3V0ZVJlcXVlc3RSZXN1bHRDb2RlLlRJTUVEX09VVCArIDE7CiAgUm91dGVSZXF1ZXN0UmVzdWx0Q29kZS5TSU5LX05PVF9GT1VORCA9IFJvdXRlUmVxdWVzdFJlc3VsdENvZGUuUk9VVEVfTk9UX0ZPVU5EICsgMTsKICBSb3V0ZVJlcXVlc3RSZXN1bHRDb2RlLklOVkFMSURfT1JJR0lOID0gUm91dGVSZXF1ZXN0UmVzdWx0Q29kZS5TSU5LX05PVF9GT1VORCArIDE7CiAgUm91dGVSZXF1ZXN0UmVzdWx0Q29kZS5JTkNPR05JVE9fTUlTTUFUQ0ggPSBSb3V0ZVJlcXVlc3RSZXN1bHRDb2RlLklOVkFMSURfT1JJR0lOICsgMTsKICBSb3V0ZVJlcXVlc3RSZXN1bHRDb2RlLk5PX1NVUFBPUlRFRF9QUk9WSURFUiA9IFJvdXRlUmVxdWVzdFJlc3VsdENvZGUuSU5DT0dOSVRPX01JU01BVENIICsgMTsKICBSb3V0ZVJlcXVlc3RSZXN1bHRDb2RlLkNBTkNFTExFRCA9IFJvdXRlUmVxdWVzdFJlc3VsdENvZGUuTk9fU1VQUE9SVEVEX1BST1ZJREVSICsgMTsKCiAgUm91dGVSZXF1ZXN0UmVzdWx0Q29kZS5pc0tub3duRW51bVZhbHVlID0gZnVuY3Rpb24odmFsdWUpIHsKICAgIHN3aXRjaCAodmFsdWUpIHsKICAgIGNhc2UgMDoKICAgIGNhc2UgMToKICAgIGNhc2UgMjoKICAgIGNhc2UgMzoKICAgIGNhc2UgNDoKICAgIGNhc2UgNToKICAgIGNhc2UgNjoKICAgIGNhc2UgNzoKICAgIGNhc2UgODoKICAgICAgcmV0dXJuIHRydWU7CiAgICB9CiAgICByZXR1cm4gZmFsc2U7CiAgfTsKCiAgUm91dGVSZXF1ZXN0UmVzdWx0Q29kZS52YWxpZGF0ZSA9IGZ1bmN0aW9uKGVudW1WYWx1ZSkgewogICAgdmFyIGlzRXh0ZW5zaWJsZSA9IGZhbHNlOwogICAgaWYgKGlzRXh0ZW5zaWJsZSB8fCB0aGlzLmlzS25vd25FbnVtVmFsdWUoZW51bVZhbHVlKSkKICAgICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5VTktOT1dOX0VOVU1fVkFMVUU7CiAgfTsKCiAgZnVuY3Rpb24gTWVkaWFTaW5rKHZhbHVlcykgewogICAgdGhpcy5pbml0RGVmYXVsdHNfKCk7CiAgICB0aGlzLmluaXRGaWVsZHNfKHZhbHVlcyk7CiAgfQoKCiAgTWVkaWFTaW5rLnByb3RvdHlwZS5pbml0RGVmYXVsdHNfID0gZnVuY3Rpb24oKSB7CiAgICB0aGlzLnNpbmtJZCA9IG51bGw7CiAgICB0aGlzLm5hbWUgPSBudWxsOwogICAgdGhpcy5kZXNjcmlwdGlvbiA9IG51bGw7CiAgICB0aGlzLmRvbWFpbiA9IG51bGw7CiAgICB0aGlzLmljb25UeXBlID0gMDsKICAgIHRoaXMucHJvdmlkZXJJZCA9IDA7CiAgICB0aGlzLmV4dHJhRGF0YSA9IG51bGw7CiAgfTsKICBNZWRpYVNpbmsucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNZWRpYVNpbmsudmFsaWRhdGUgPSBmdW5jdGlvbihtZXNzYWdlVmFsaWRhdG9yLCBvZmZzZXQpIHsKICAgIHZhciBlcnI7CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0SGVhZGVyKG9mZnNldCwgY29kZWMua1N0cnVjdEhlYWRlclNpemUpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgdmFyIGtWZXJzaW9uU2l6ZXMgPSBbCiAgICAgIHt2ZXJzaW9uOiAwLCBudW1CeXRlczogNjR9CiAgICBdOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFZlcnNpb24ob2Zmc2V0LCBrVmVyc2lvblNpemVzKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBNZWRpYVNpbmsuc2lua0lkCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDAsIGZhbHNlKQogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhU2luay5uYW1lCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDgsIGZhbHNlKQogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhU2luay5kZXNjcmlwdGlvbgogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cmluZ1BvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAxNiwgdHJ1ZSkKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBNZWRpYVNpbmsuZG9tYWluCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDI0LCB0cnVlKQogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhU2luay5pY29uVHlwZQogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZUVudW0ob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAzMiwgU2lua0ljb25UeXBlKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBNZWRpYVNpbmsucHJvdmlkZXJJZAogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZUVudW0ob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAzNiwgTWVkaWFSb3V0ZVByb3ZpZGVyLklkKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBNZWRpYVNpbmsuZXh0cmFEYXRhCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlVW5pb24ob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA0MCwgTWVkaWFTaW5rRXh0cmFEYXRhLCB0cnVlKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgfTsKCiAgTWVkaWFTaW5rLmVuY29kZWRTaXplID0gY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA1NjsKCiAgTWVkaWFTaW5rLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1lZGlhU2luaygpOwogICAgdmFyIG51bWJlck9mQnl0ZXMgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhciB2ZXJzaW9uID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YWwuc2lua0lkID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nKTsKICAgIHZhbC5uYW1lID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nKTsKICAgIHZhbC5kZXNjcmlwdGlvbiA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLk51bGxhYmxlU3RyaW5nKTsKICAgIHZhbC5kb21haW4gPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5OdWxsYWJsZVN0cmluZyk7CiAgICB2YWwuaWNvblR5cGUgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5JbnQzMik7CiAgICB2YWwucHJvdmlkZXJJZCA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLkludDMyKTsKICAgIHZhbC5leHRyYURhdGEgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChNZWRpYVNpbmtFeHRyYURhdGEpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBNZWRpYVNpbmsuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNZWRpYVNpbmsuZW5jb2RlZFNpemUpOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMigwKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLlN0cmluZywgdmFsLnNpbmtJZCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5TdHJpbmcsIHZhbC5uYW1lKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLk51bGxhYmxlU3RyaW5nLCB2YWwuZGVzY3JpcHRpb24pOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuTnVsbGFibGVTdHJpbmcsIHZhbC5kb21haW4pOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuSW50MzIsIHZhbC5pY29uVHlwZSk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5JbnQzMiwgdmFsLnByb3ZpZGVySWQpOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoTWVkaWFTaW5rRXh0cmFEYXRhLCB2YWwuZXh0cmFEYXRhKTsKICB9OwogIGZ1bmN0aW9uIERpYWxNZWRpYVNpbmsodmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBEaWFsTWVkaWFTaW5rLnByb3RvdHlwZS5pbml0RGVmYXVsdHNfID0gZnVuY3Rpb24oKSB7CiAgICB0aGlzLmlwQWRkcmVzcyA9IG51bGw7CiAgICB0aGlzLm1vZGVsTmFtZSA9IG51bGw7CiAgICB0aGlzLmFwcFVybCA9IG51bGw7CiAgfTsKICBEaWFsTWVkaWFTaW5rLnByb3RvdHlwZS5pbml0RmllbGRzXyA9IGZ1bmN0aW9uKGZpZWxkcykgewogICAgZm9yKHZhciBmaWVsZCBpbiBmaWVsZHMpIHsKICAgICAgICBpZiAodGhpcy5oYXNPd25Qcm9wZXJ0eShmaWVsZCkpCiAgICAgICAgICB0aGlzW2ZpZWxkXSA9IGZpZWxkc1tmaWVsZF07CiAgICB9CiAgfTsKCiAgRGlhbE1lZGlhU2luay52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiAzMn0KICAgIF07CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0VmVyc2lvbihvZmZzZXQsIGtWZXJzaW9uU2l6ZXMpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIERpYWxNZWRpYVNpbmsuaXBBZGRyZXNzCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0UG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDAsIGlwX2FkZHJlc3MkLklQQWRkcmVzcywgZmFsc2UpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIERpYWxNZWRpYVNpbmsubW9kZWxOYW1lCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDgsIGZhbHNlKQogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIERpYWxNZWRpYVNpbmsuYXBwVXJsCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0UG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDE2LCB1cmwkLlVybCwgZmFsc2UpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKICB9OwoKICBEaWFsTWVkaWFTaW5rLmVuY29kZWRTaXplID0gY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAyNDsKCiAgRGlhbE1lZGlhU2luay5kZWNvZGUgPSBmdW5jdGlvbihkZWNvZGVyKSB7CiAgICB2YXIgcGFja2VkOwogICAgdmFyIHZhbCA9IG5ldyBEaWFsTWVkaWFTaW5rKCk7CiAgICB2YXIgbnVtYmVyT2ZCeXRlcyA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFyIHZlcnNpb24gPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhbC5pcEFkZHJlc3MgPSBkZWNvZGVyLmRlY29kZVN0cnVjdFBvaW50ZXIoaXBfYWRkcmVzcyQuSVBBZGRyZXNzKTsKICAgIHZhbC5tb2RlbE5hbWUgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5TdHJpbmcpOwogICAgdmFsLmFwcFVybCA9IGRlY29kZXIuZGVjb2RlU3RydWN0UG9pbnRlcih1cmwkLlVybCk7CiAgICByZXR1cm4gdmFsOwogIH07CgogIERpYWxNZWRpYVNpbmsuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihEaWFsTWVkaWFTaW5rLmVuY29kZWRTaXplKTsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoMCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdFBvaW50ZXIoaXBfYWRkcmVzcyQuSVBBZGRyZXNzLCB2YWwuaXBBZGRyZXNzKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLlN0cmluZywgdmFsLm1vZGVsTmFtZSk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdFBvaW50ZXIodXJsJC5VcmwsIHZhbC5hcHBVcmwpOwogIH07CiAgZnVuY3Rpb24gQ2FzdE1lZGlhU2luayh2YWx1ZXMpIHsKICAgIHRoaXMuaW5pdERlZmF1bHRzXygpOwogICAgdGhpcy5pbml0RmllbGRzXyh2YWx1ZXMpOwogIH0KCgogIENhc3RNZWRpYVNpbmsucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMuaXBFbmRwb2ludCA9IG51bGw7CiAgICB0aGlzLm1vZGVsTmFtZSA9IG51bGw7CiAgICB0aGlzLmNhcGFiaWxpdGllcyA9IDA7CiAgICB0aGlzLmNhc3RDaGFubmVsSWQgPSAwOwogIH07CiAgQ2FzdE1lZGlhU2luay5wcm90b3R5cGUuaW5pdEZpZWxkc18gPSBmdW5jdGlvbihmaWVsZHMpIHsKICAgIGZvcih2YXIgZmllbGQgaW4gZmllbGRzKSB7CiAgICAgICAgaWYgKHRoaXMuaGFzT3duUHJvcGVydHkoZmllbGQpKQogICAgICAgICAgdGhpc1tmaWVsZF0gPSBmaWVsZHNbZmllbGRdOwogICAgfQogIH07CgogIENhc3RNZWRpYVNpbmsudmFsaWRhdGUgPSBmdW5jdGlvbihtZXNzYWdlVmFsaWRhdG9yLCBvZmZzZXQpIHsKICAgIHZhciBlcnI7CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0SGVhZGVyKG9mZnNldCwgY29kZWMua1N0cnVjdEhlYWRlclNpemUpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgdmFyIGtWZXJzaW9uU2l6ZXMgPSBbCiAgICAgIHt2ZXJzaW9uOiAwLCBudW1CeXRlczogMzJ9CiAgICBdOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFZlcnNpb24ob2Zmc2V0LCBrVmVyc2lvblNpemVzKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBDYXN0TWVkaWFTaW5rLmlwRW5kcG9pbnQKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RQb2ludGVyKG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMCwgaXBfZW5kcG9pbnQkLklQRW5kUG9pbnQsIGZhbHNlKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBDYXN0TWVkaWFTaW5rLm1vZGVsTmFtZQogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cmluZ1BvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA4LCBmYWxzZSkKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKICB9OwoKICBDYXN0TWVkaWFTaW5rLmVuY29kZWRTaXplID0gY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAyNDsKCiAgQ2FzdE1lZGlhU2luay5kZWNvZGUgPSBmdW5jdGlvbihkZWNvZGVyKSB7CiAgICB2YXIgcGFja2VkOwogICAgdmFyIHZhbCA9IG5ldyBDYXN0TWVkaWFTaW5rKCk7CiAgICB2YXIgbnVtYmVyT2ZCeXRlcyA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFyIHZlcnNpb24gPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhbC5pcEVuZHBvaW50ID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3RQb2ludGVyKGlwX2VuZHBvaW50JC5JUEVuZFBvaW50KTsKICAgIHZhbC5tb2RlbE5hbWUgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5TdHJpbmcpOwogICAgdmFsLmNhcGFiaWxpdGllcyA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLlVpbnQ4KTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIHZhbC5jYXN0Q2hhbm5lbElkID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuSW50MzIpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBDYXN0TWVkaWFTaW5rLmVuY29kZSA9IGZ1bmN0aW9uKGVuY29kZXIsIHZhbCkgewogICAgdmFyIHBhY2tlZDsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoQ2FzdE1lZGlhU2luay5lbmNvZGVkU2l6ZSk7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKDApOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3RQb2ludGVyKGlwX2VuZHBvaW50JC5JUEVuZFBvaW50LCB2YWwuaXBFbmRwb2ludCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5TdHJpbmcsIHZhbC5tb2RlbE5hbWUpOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuVWludDgsIHZhbC5jYXBhYmlsaXRpZXMpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuSW50MzIsIHZhbC5jYXN0Q2hhbm5lbElkKTsKICB9OwogIGZ1bmN0aW9uIE1lZGlhUm91dGUodmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBNZWRpYVJvdXRlLnByb3RvdHlwZS5pbml0RGVmYXVsdHNfID0gZnVuY3Rpb24oKSB7CiAgICB0aGlzLm1lZGlhUm91dGVJZCA9IG51bGw7CiAgICB0aGlzLnByZXNlbnRhdGlvbklkID0gbnVsbDsKICAgIHRoaXMubWVkaWFTb3VyY2UgPSBudWxsOwogICAgdGhpcy5tZWRpYVNpbmtJZCA9IG51bGw7CiAgICB0aGlzLmRlc2NyaXB0aW9uID0gbnVsbDsKICAgIHRoaXMuaXNMb2NhbCA9IGZhbHNlOwogICAgdGhpcy5mb3JEaXNwbGF5ID0gZmFsc2U7CiAgICB0aGlzLmlzSW5jb2duaXRvID0gZmFsc2U7CiAgICB0aGlzLmlzTG9jYWxQcmVzZW50YXRpb24gPSBmYWxzZTsKICAgIHRoaXMuY29udHJvbGxlclR5cGUgPSAwOwogIH07CiAgTWVkaWFSb3V0ZS5wcm90b3R5cGUuaW5pdEZpZWxkc18gPSBmdW5jdGlvbihmaWVsZHMpIHsKICAgIGZvcih2YXIgZmllbGQgaW4gZmllbGRzKSB7CiAgICAgICAgaWYgKHRoaXMuaGFzT3duUHJvcGVydHkoZmllbGQpKQogICAgICAgICAgdGhpc1tmaWVsZF0gPSBmaWVsZHNbZmllbGRdOwogICAgfQogIH07CgogIE1lZGlhUm91dGUudmFsaWRhdGUgPSBmdW5jdGlvbihtZXNzYWdlVmFsaWRhdG9yLCBvZmZzZXQpIHsKICAgIHZhciBlcnI7CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0SGVhZGVyKG9mZnNldCwgY29kZWMua1N0cnVjdEhlYWRlclNpemUpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgdmFyIGtWZXJzaW9uU2l6ZXMgPSBbCiAgICAgIHt2ZXJzaW9uOiAwLCBudW1CeXRlczogNTZ9CiAgICBdOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFZlcnNpb24ob2Zmc2V0LCBrVmVyc2lvblNpemVzKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBNZWRpYVJvdXRlLm1lZGlhUm91dGVJZAogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cmluZ1BvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAwLCBmYWxzZSkKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBNZWRpYVJvdXRlLnByZXNlbnRhdGlvbklkCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDgsIGZhbHNlKQogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhUm91dGUubWVkaWFTb3VyY2UKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJpbmdQb2ludGVyKG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMTYsIHRydWUpCiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZS5tZWRpYVNpbmtJZAogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cmluZ1BvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAyNCwgZmFsc2UpCiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZS5kZXNjcmlwdGlvbgogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cmluZ1BvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAzMiwgZmFsc2UpCiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhUm91dGUuY29udHJvbGxlclR5cGUKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVFbnVtKG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgNDQsIFJvdXRlQ29udHJvbGxlclR5cGUpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKCgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKICB9OwoKICBNZWRpYVJvdXRlLmVuY29kZWRTaXplID0gY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA0ODsKCiAgTWVkaWFSb3V0ZS5kZWNvZGUgPSBmdW5jdGlvbihkZWNvZGVyKSB7CiAgICB2YXIgcGFja2VkOwogICAgdmFyIHZhbCA9IG5ldyBNZWRpYVJvdXRlKCk7CiAgICB2YXIgbnVtYmVyT2ZCeXRlcyA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFyIHZlcnNpb24gPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhbC5tZWRpYVJvdXRlSWQgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5TdHJpbmcpOwogICAgdmFsLnByZXNlbnRhdGlvbklkID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nKTsKICAgIHZhbC5tZWRpYVNvdXJjZSA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLk51bGxhYmxlU3RyaW5nKTsKICAgIHZhbC5tZWRpYVNpbmtJZCA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLlN0cmluZyk7CiAgICB2YWwuZGVzY3JpcHRpb24gPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5TdHJpbmcpOwogICAgcGFja2VkID0gZGVjb2Rlci5yZWFkVWludDgoKTsKICAgIHZhbC5pc0xvY2FsID0gKHBhY2tlZCA+PiAwKSAmIDEgPyB0cnVlIDogZmFsc2U7CiAgICB2YWwuZm9yRGlzcGxheSA9IChwYWNrZWQgPj4gMSkgJiAxID8gdHJ1ZSA6IGZhbHNlOwogICAgdmFsLmlzSW5jb2duaXRvID0gKHBhY2tlZCA+PiAyKSAmIDEgPyB0cnVlIDogZmFsc2U7CiAgICB2YWwuaXNMb2NhbFByZXNlbnRhdGlvbiA9IChwYWNrZWQgPj4gMykgJiAxID8gdHJ1ZSA6IGZhbHNlOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgdmFsLmNvbnRyb2xsZXJUeXBlID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuSW50MzIpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBNZWRpYVJvdXRlLmVuY29kZSA9IGZ1bmN0aW9uKGVuY29kZXIsIHZhbCkgewogICAgdmFyIHBhY2tlZDsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoTWVkaWFSb3V0ZS5lbmNvZGVkU2l6ZSk7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKDApOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nLCB2YWwubWVkaWFSb3V0ZUlkKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLlN0cmluZywgdmFsLnByZXNlbnRhdGlvbklkKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLk51bGxhYmxlU3RyaW5nLCB2YWwubWVkaWFTb3VyY2UpOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nLCB2YWwubWVkaWFTaW5rSWQpOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nLCB2YWwuZGVzY3JpcHRpb24pOwogICAgcGFja2VkID0gMDsKICAgIHBhY2tlZCB8PSAodmFsLmlzTG9jYWwgJiAxKSA8PCAwCiAgICBwYWNrZWQgfD0gKHZhbC5mb3JEaXNwbGF5ICYgMSkgPDwgMQogICAgcGFja2VkIHw9ICh2YWwuaXNJbmNvZ25pdG8gJiAxKSA8PCAyCiAgICBwYWNrZWQgfD0gKHZhbC5pc0xvY2FsUHJlc2VudGF0aW9uICYgMSkgPDwgMwogICAgZW5jb2Rlci53cml0ZVVpbnQ4KHBhY2tlZCk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5JbnQzMiwgdmFsLmNvbnRyb2xsZXJUeXBlKTsKICB9OwogIGZ1bmN0aW9uIElzc3VlKHZhbHVlcykgewogICAgdGhpcy5pbml0RGVmYXVsdHNfKCk7CiAgICB0aGlzLmluaXRGaWVsZHNfKHZhbHVlcyk7CiAgfQoKICBJc3N1ZS5TZXZlcml0eSA9IHt9OwogIElzc3VlLlNldmVyaXR5LkZBVEFMID0gMDsKICBJc3N1ZS5TZXZlcml0eS5XQVJOSU5HID0gSXNzdWUuU2V2ZXJpdHkuRkFUQUwgKyAxOwogIElzc3VlLlNldmVyaXR5Lk5PVElGSUNBVElPTiA9IElzc3VlLlNldmVyaXR5LldBUk5JTkcgKyAxOwoKICBJc3N1ZS5TZXZlcml0eS5pc0tub3duRW51bVZhbHVlID0gZnVuY3Rpb24odmFsdWUpIHsKICAgIHN3aXRjaCAodmFsdWUpIHsKICAgIGNhc2UgMDoKICAgIGNhc2UgMToKICAgIGNhc2UgMjoKICAgICAgcmV0dXJuIHRydWU7CiAgICB9CiAgICByZXR1cm4gZmFsc2U7CiAgfTsKCiAgSXNzdWUuU2V2ZXJpdHkudmFsaWRhdGUgPSBmdW5jdGlvbihlbnVtVmFsdWUpIHsKICAgIHZhciBpc0V4dGVuc2libGUgPSBmYWxzZTsKICAgIGlmIChpc0V4dGVuc2libGUgfHwgdGhpcy5pc0tub3duRW51bVZhbHVlKGVudW1WYWx1ZSkpCiAgICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuVU5LTk9XTl9FTlVNX1ZBTFVFOwogIH07CiAgSXNzdWUuQWN0aW9uVHlwZSA9IHt9OwogIElzc3VlLkFjdGlvblR5cGUuRElTTUlTUyA9IDA7CiAgSXNzdWUuQWN0aW9uVHlwZS5MRUFSTl9NT1JFID0gSXNzdWUuQWN0aW9uVHlwZS5ESVNNSVNTICsgMTsKCiAgSXNzdWUuQWN0aW9uVHlwZS5pc0tub3duRW51bVZhbHVlID0gZnVuY3Rpb24odmFsdWUpIHsKICAgIHN3aXRjaCAodmFsdWUpIHsKICAgIGNhc2UgMDoKICAgIGNhc2UgMToKICAgICAgcmV0dXJuIHRydWU7CiAgICB9CiAgICByZXR1cm4gZmFsc2U7CiAgfTsKCiAgSXNzdWUuQWN0aW9uVHlwZS52YWxpZGF0ZSA9IGZ1bmN0aW9uKGVudW1WYWx1ZSkgewogICAgdmFyIGlzRXh0ZW5zaWJsZSA9IGZhbHNlOwogICAgaWYgKGlzRXh0ZW5zaWJsZSB8fCB0aGlzLmlzS25vd25FbnVtVmFsdWUoZW51bVZhbHVlKSkKICAgICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5VTktOT1dOX0VOVU1fVkFMVUU7CiAgfTsKCiAgSXNzdWUucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMucm91dGVJZCA9IG51bGw7CiAgICB0aGlzLnNldmVyaXR5ID0gMDsKICAgIHRoaXMuaXNCbG9ja2luZyA9IGZhbHNlOwogICAgdGhpcy50aXRsZSA9IG51bGw7CiAgICB0aGlzLm1lc3NhZ2UgPSBudWxsOwogICAgdGhpcy5kZWZhdWx0QWN0aW9uID0gMDsKICAgIHRoaXMuaGVscFBhZ2VJZCA9IDA7CiAgICB0aGlzLnNlY29uZGFyeUFjdGlvbnMgPSBudWxsOwogIH07CiAgSXNzdWUucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBJc3N1ZS52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiA1Nn0KICAgIF07CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0VmVyc2lvbihvZmZzZXQsIGtWZXJzaW9uU2l6ZXMpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIElzc3VlLnJvdXRlSWQKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJpbmdQb2ludGVyKG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMCwgdHJ1ZSkKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBJc3N1ZS5zZXZlcml0eQogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZUVudW0ob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA4LCBJc3N1ZS5TZXZlcml0eSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgoKICAgIC8vIHZhbGlkYXRlIElzc3VlLnRpdGxlCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDE2LCBmYWxzZSkKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBJc3N1ZS5tZXNzYWdlCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDI0LCB0cnVlKQogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIElzc3VlLmRlZmF1bHRBY3Rpb24KICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVFbnVtKG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMzIsIElzc3VlLkFjdGlvblR5cGUpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIElzc3VlLnNlY29uZGFyeUFjdGlvbnMKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVBcnJheVBvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA0MCwgNCwgbmV3IGNvZGVjLkVudW0oSXNzdWUuQWN0aW9uVHlwZSksIGZhbHNlLCBbMF0sIDApOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgfTsKCiAgSXNzdWUuZW5jb2RlZFNpemUgPSBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDQ4OwoKICBJc3N1ZS5kZWNvZGUgPSBmdW5jdGlvbihkZWNvZGVyKSB7CiAgICB2YXIgcGFja2VkOwogICAgdmFyIHZhbCA9IG5ldyBJc3N1ZSgpOwogICAgdmFyIG51bWJlck9mQnl0ZXMgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhciB2ZXJzaW9uID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YWwucm91dGVJZCA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLk51bGxhYmxlU3RyaW5nKTsKICAgIHZhbC5zZXZlcml0eSA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLkludDMyKTsKICAgIHBhY2tlZCA9IGRlY29kZXIucmVhZFVpbnQ4KCk7CiAgICB2YWwuaXNCbG9ja2luZyA9IChwYWNrZWQgPj4gMCkgJiAxID8gdHJ1ZSA6IGZhbHNlOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgdmFsLnRpdGxlID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nKTsKICAgIHZhbC5tZXNzYWdlID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuTnVsbGFibGVTdHJpbmcpOwogICAgdmFsLmRlZmF1bHRBY3Rpb24gPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5JbnQzMik7CiAgICB2YWwuaGVscFBhZ2VJZCA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLkludDMyKTsKICAgIHZhbC5zZWNvbmRhcnlBY3Rpb25zID0gZGVjb2Rlci5kZWNvZGVBcnJheVBvaW50ZXIobmV3IGNvZGVjLkVudW0oSXNzdWUuQWN0aW9uVHlwZSkpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBJc3N1ZS5lbmNvZGUgPSBmdW5jdGlvbihlbmNvZGVyLCB2YWwpIHsKICAgIHZhciBwYWNrZWQ7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKElzc3VlLmVuY29kZWRTaXplKTsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoMCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5OdWxsYWJsZVN0cmluZywgdmFsLnJvdXRlSWQpOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuSW50MzIsIHZhbC5zZXZlcml0eSk7CiAgICBwYWNrZWQgPSAwOwogICAgcGFja2VkIHw9ICh2YWwuaXNCbG9ja2luZyAmIDEpIDw8IDAKICAgIGVuY29kZXIud3JpdGVVaW50OChwYWNrZWQpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nLCB2YWwudGl0bGUpOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuTnVsbGFibGVTdHJpbmcsIHZhbC5tZXNzYWdlKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLkludDMyLCB2YWwuZGVmYXVsdEFjdGlvbik7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5JbnQzMiwgdmFsLmhlbHBQYWdlSWQpOwogICAgZW5jb2Rlci5lbmNvZGVBcnJheVBvaW50ZXIobmV3IGNvZGVjLkVudW0oSXNzdWUuQWN0aW9uVHlwZSksIHZhbC5zZWNvbmRhcnlBY3Rpb25zKTsKICB9OwogIGZ1bmN0aW9uIFJvdXRlTWVzc2FnZSh2YWx1ZXMpIHsKICAgIHRoaXMuaW5pdERlZmF1bHRzXygpOwogICAgdGhpcy5pbml0RmllbGRzXyh2YWx1ZXMpOwogIH0KCiAgUm91dGVNZXNzYWdlLlR5cGUgPSB7fTsKICBSb3V0ZU1lc3NhZ2UuVHlwZS5URVhUID0gMDsKICBSb3V0ZU1lc3NhZ2UuVHlwZS5CSU5BUlkgPSBSb3V0ZU1lc3NhZ2UuVHlwZS5URVhUICsgMTsKCiAgUm91dGVNZXNzYWdlLlR5cGUuaXNLbm93bkVudW1WYWx1ZSA9IGZ1bmN0aW9uKHZhbHVlKSB7CiAgICBzd2l0Y2ggKHZhbHVlKSB7CiAgICBjYXNlIDA6CiAgICBjYXNlIDE6CiAgICAgIHJldHVybiB0cnVlOwogICAgfQogICAgcmV0dXJuIGZhbHNlOwogIH07CgogIFJvdXRlTWVzc2FnZS5UeXBlLnZhbGlkYXRlID0gZnVuY3Rpb24oZW51bVZhbHVlKSB7CiAgICB2YXIgaXNFeHRlbnNpYmxlID0gZmFsc2U7CiAgICBpZiAoaXNFeHRlbnNpYmxlIHx8IHRoaXMuaXNLbm93bkVudW1WYWx1ZShlbnVtVmFsdWUpKQogICAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLlVOS05PV05fRU5VTV9WQUxVRTsKICB9OwoKICBSb3V0ZU1lc3NhZ2UucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMudHlwZSA9IDA7CiAgICB0aGlzLm1lc3NhZ2UgPSBudWxsOwogICAgdGhpcy5kYXRhID0gbnVsbDsKICB9OwogIFJvdXRlTWVzc2FnZS5wcm90b3R5cGUuaW5pdEZpZWxkc18gPSBmdW5jdGlvbihmaWVsZHMpIHsKICAgIGZvcih2YXIgZmllbGQgaW4gZmllbGRzKSB7CiAgICAgICAgaWYgKHRoaXMuaGFzT3duUHJvcGVydHkoZmllbGQpKQogICAgICAgICAgdGhpc1tmaWVsZF0gPSBmaWVsZHNbZmllbGRdOwogICAgfQogIH07CgogIFJvdXRlTWVzc2FnZS52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiAzMn0KICAgIF07CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0VmVyc2lvbihvZmZzZXQsIGtWZXJzaW9uU2l6ZXMpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIFJvdXRlTWVzc2FnZS50eXBlCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlRW51bShvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDAsIFJvdXRlTWVzc2FnZS5UeXBlKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBSb3V0ZU1lc3NhZ2UubWVzc2FnZQogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cmluZ1BvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA4LCB0cnVlKQogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIFJvdXRlTWVzc2FnZS5kYXRhCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlQXJyYXlQb2ludGVyKG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMTYsIDEsIGNvZGVjLlVpbnQ4LCB0cnVlLCBbMF0sIDApOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKICB9OwoKICBSb3V0ZU1lc3NhZ2UuZW5jb2RlZFNpemUgPSBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDI0OwoKICBSb3V0ZU1lc3NhZ2UuZGVjb2RlID0gZnVuY3Rpb24oZGVjb2RlcikgewogICAgdmFyIHBhY2tlZDsKICAgIHZhciB2YWwgPSBuZXcgUm91dGVNZXNzYWdlKCk7CiAgICB2YXIgbnVtYmVyT2ZCeXRlcyA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFyIHZlcnNpb24gPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhbC50eXBlID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuSW50MzIpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgdmFsLm1lc3NhZ2UgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5OdWxsYWJsZVN0cmluZyk7CiAgICB2YWwuZGF0YSA9IGRlY29kZXIuZGVjb2RlQXJyYXlQb2ludGVyKGNvZGVjLlVpbnQ4KTsKICAgIHJldHVybiB2YWw7CiAgfTsKCiAgUm91dGVNZXNzYWdlLmVuY29kZSA9IGZ1bmN0aW9uKGVuY29kZXIsIHZhbCkgewogICAgdmFyIHBhY2tlZDsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoUm91dGVNZXNzYWdlLmVuY29kZWRTaXplKTsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoMCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5JbnQzMiwgdmFsLnR5cGUpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuTnVsbGFibGVTdHJpbmcsIHZhbC5tZXNzYWdlKTsKICAgIGVuY29kZXIuZW5jb2RlQXJyYXlQb2ludGVyKGNvZGVjLlVpbnQ4LCB2YWwuZGF0YSk7CiAgfTsKICBmdW5jdGlvbiBTaW5rU2VhcmNoQ3JpdGVyaWEodmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBTaW5rU2VhcmNoQ3JpdGVyaWEucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMuaW5wdXQgPSBudWxsOwogICAgdGhpcy5kb21haW4gPSBudWxsOwogIH07CiAgU2lua1NlYXJjaENyaXRlcmlhLnByb3RvdHlwZS5pbml0RmllbGRzXyA9IGZ1bmN0aW9uKGZpZWxkcykgewogICAgZm9yKHZhciBmaWVsZCBpbiBmaWVsZHMpIHsKICAgICAgICBpZiAodGhpcy5oYXNPd25Qcm9wZXJ0eShmaWVsZCkpCiAgICAgICAgICB0aGlzW2ZpZWxkXSA9IGZpZWxkc1tmaWVsZF07CiAgICB9CiAgfTsKCiAgU2lua1NlYXJjaENyaXRlcmlhLnZhbGlkYXRlID0gZnVuY3Rpb24obWVzc2FnZVZhbGlkYXRvciwgb2Zmc2V0KSB7CiAgICB2YXIgZXJyOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdEhlYWRlcihvZmZzZXQsIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHZhciBrVmVyc2lvblNpemVzID0gWwogICAgICB7dmVyc2lvbjogMCwgbnVtQnl0ZXM6IDI0fQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgU2lua1NlYXJjaENyaXRlcmlhLmlucHV0CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDAsIGZhbHNlKQogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIFNpbmtTZWFyY2hDcml0ZXJpYS5kb21haW4KICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJpbmdQb2ludGVyKG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgOCwgZmFsc2UpCiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIFNpbmtTZWFyY2hDcml0ZXJpYS5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMTY7CgogIFNpbmtTZWFyY2hDcml0ZXJpYS5kZWNvZGUgPSBmdW5jdGlvbihkZWNvZGVyKSB7CiAgICB2YXIgcGFja2VkOwogICAgdmFyIHZhbCA9IG5ldyBTaW5rU2VhcmNoQ3JpdGVyaWEoKTsKICAgIHZhciBudW1iZXJPZkJ5dGVzID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YXIgdmVyc2lvbiA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFsLmlucHV0ID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nKTsKICAgIHZhbC5kb21haW4gPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5TdHJpbmcpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBTaW5rU2VhcmNoQ3JpdGVyaWEuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihTaW5rU2VhcmNoQ3JpdGVyaWEuZW5jb2RlZFNpemUpOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMigwKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLlN0cmluZywgdmFsLmlucHV0KTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLlN0cmluZywgdmFsLmRvbWFpbik7CiAgfTsKICBmdW5jdGlvbiBNZWRpYVJvdXRlUHJvdmlkZXJDb25maWcodmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBNZWRpYVJvdXRlUHJvdmlkZXJDb25maWcucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMuZW5hYmxlRGlhbERpc2NvdmVyeSA9IGZhbHNlOwogICAgdGhpcy5lbmFibGVDYXN0RGlzY292ZXJ5ID0gZmFsc2U7CiAgfTsKICBNZWRpYVJvdXRlUHJvdmlkZXJDb25maWcucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJDb25maWcudmFsaWRhdGUgPSBmdW5jdGlvbihtZXNzYWdlVmFsaWRhdG9yLCBvZmZzZXQpIHsKICAgIHZhciBlcnI7CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0SGVhZGVyKG9mZnNldCwgY29kZWMua1N0cnVjdEhlYWRlclNpemUpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgdmFyIGtWZXJzaW9uU2l6ZXMgPSBbCiAgICAgIHt2ZXJzaW9uOiAwLCBudW1CeXRlczogMTZ9CiAgICBdOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFZlcnNpb24ob2Zmc2V0LCBrVmVyc2lvblNpemVzKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJDb25maWcuZW5jb2RlZFNpemUgPSBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDg7CgogIE1lZGlhUm91dGVQcm92aWRlckNvbmZpZy5kZWNvZGUgPSBmdW5jdGlvbihkZWNvZGVyKSB7CiAgICB2YXIgcGFja2VkOwogICAgdmFyIHZhbCA9IG5ldyBNZWRpYVJvdXRlUHJvdmlkZXJDb25maWcoKTsKICAgIHZhciBudW1iZXJPZkJ5dGVzID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YXIgdmVyc2lvbiA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgcGFja2VkID0gZGVjb2Rlci5yZWFkVWludDgoKTsKICAgIHZhbC5lbmFibGVEaWFsRGlzY292ZXJ5ID0gKHBhY2tlZCA+PiAwKSAmIDEgPyB0cnVlIDogZmFsc2U7CiAgICB2YWwuZW5hYmxlQ2FzdERpc2NvdmVyeSA9IChwYWNrZWQgPj4gMSkgJiAxID8gdHJ1ZSA6IGZhbHNlOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJDb25maWcuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNZWRpYVJvdXRlUHJvdmlkZXJDb25maWcuZW5jb2RlZFNpemUpOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMigwKTsKICAgIHBhY2tlZCA9IDA7CiAgICBwYWNrZWQgfD0gKHZhbC5lbmFibGVEaWFsRGlzY292ZXJ5ICYgMSkgPDwgMAogICAgcGFja2VkIHw9ICh2YWwuZW5hYmxlQ2FzdERpc2NvdmVyeSAmIDEpIDw8IDEKICAgIGVuY29kZXIud3JpdGVVaW50OChwYWNrZWQpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogIH07CiAgZnVuY3Rpb24gTWVkaWFSb3V0ZVByb3ZpZGVyX0NyZWF0ZVJvdXRlX1BhcmFtcyh2YWx1ZXMpIHsKICAgIHRoaXMuaW5pdERlZmF1bHRzXygpOwogICAgdGhpcy5pbml0RmllbGRzXyh2YWx1ZXMpOwogIH0KCgogIE1lZGlhUm91dGVQcm92aWRlcl9DcmVhdGVSb3V0ZV9QYXJhbXMucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMubWVkaWFTb3VyY2UgPSBudWxsOwogICAgdGhpcy5zaW5rSWQgPSBudWxsOwogICAgdGhpcy5vcmlnaW5hbFByZXNlbnRhdGlvbklkID0gbnVsbDsKICAgIHRoaXMub3JpZ2luID0gbnVsbDsKICAgIHRoaXMudGFiSWQgPSAwOwogICAgdGhpcy5pbmNvZ25pdG8gPSBmYWxzZTsKICAgIHRoaXMudGltZW91dCA9IG51bGw7CiAgfTsKICBNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlUm91dGVfUGFyYW1zLnByb3RvdHlwZS5pbml0RmllbGRzXyA9IGZ1bmN0aW9uKGZpZWxkcykgewogICAgZm9yKHZhciBmaWVsZCBpbiBmaWVsZHMpIHsKICAgICAgICBpZiAodGhpcy5oYXNPd25Qcm9wZXJ0eShmaWVsZCkpCiAgICAgICAgICB0aGlzW2ZpZWxkXSA9IGZpZWxkc1tmaWVsZF07CiAgICB9CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX0NyZWF0ZVJvdXRlX1BhcmFtcy52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiA1Nn0KICAgIF07CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0VmVyc2lvbihvZmZzZXQsIGtWZXJzaW9uU2l6ZXMpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhUm91dGVQcm92aWRlcl9DcmVhdGVSb3V0ZV9QYXJhbXMubWVkaWFTb3VyY2UKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJpbmdQb2ludGVyKG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMCwgZmFsc2UpCiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZVByb3ZpZGVyX0NyZWF0ZVJvdXRlX1BhcmFtcy5zaW5rSWQKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJpbmdQb2ludGVyKG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgOCwgZmFsc2UpCiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZVByb3ZpZGVyX0NyZWF0ZVJvdXRlX1BhcmFtcy5vcmlnaW5hbFByZXNlbnRhdGlvbklkCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDE2LCBmYWxzZSkKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlUm91dGVfUGFyYW1zLm9yaWdpbgogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFBvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAyNCwgb3JpZ2luJC5PcmlnaW4sIGZhbHNlKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZVByb3ZpZGVyX0NyZWF0ZVJvdXRlX1BhcmFtcy50aW1lb3V0CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0UG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDQwLCB0aW1lJC5UaW1lRGVsdGEsIGZhbHNlKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIE1lZGlhUm91dGVQcm92aWRlcl9DcmVhdGVSb3V0ZV9QYXJhbXMuZW5jb2RlZFNpemUgPSBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDQ4OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlUm91dGVfUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1lZGlhUm91dGVQcm92aWRlcl9DcmVhdGVSb3V0ZV9QYXJhbXMoKTsKICAgIHZhciBudW1iZXJPZkJ5dGVzID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YXIgdmVyc2lvbiA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFsLm1lZGlhU291cmNlID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nKTsKICAgIHZhbC5zaW5rSWQgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5TdHJpbmcpOwogICAgdmFsLm9yaWdpbmFsUHJlc2VudGF0aW9uSWQgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5TdHJpbmcpOwogICAgdmFsLm9yaWdpbiA9IGRlY29kZXIuZGVjb2RlU3RydWN0UG9pbnRlcihvcmlnaW4kLk9yaWdpbik7CiAgICB2YWwudGFiSWQgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5JbnQzMik7CiAgICBwYWNrZWQgPSBkZWNvZGVyLnJlYWRVaW50OCgpOwogICAgdmFsLmluY29nbml0byA9IChwYWNrZWQgPj4gMCkgJiAxID8gdHJ1ZSA6IGZhbHNlOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgdmFsLnRpbWVvdXQgPSBkZWNvZGVyLmRlY29kZVN0cnVjdFBvaW50ZXIodGltZSQuVGltZURlbHRhKTsKICAgIHJldHVybiB2YWw7CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX0NyZWF0ZVJvdXRlX1BhcmFtcy5lbmNvZGUgPSBmdW5jdGlvbihlbmNvZGVyLCB2YWwpIHsKICAgIHZhciBwYWNrZWQ7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKE1lZGlhUm91dGVQcm92aWRlcl9DcmVhdGVSb3V0ZV9QYXJhbXMuZW5jb2RlZFNpemUpOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMigwKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLlN0cmluZywgdmFsLm1lZGlhU291cmNlKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLlN0cmluZywgdmFsLnNpbmtJZCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5TdHJpbmcsIHZhbC5vcmlnaW5hbFByZXNlbnRhdGlvbklkKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0UG9pbnRlcihvcmlnaW4kLk9yaWdpbiwgdmFsLm9yaWdpbik7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5JbnQzMiwgdmFsLnRhYklkKTsKICAgIHBhY2tlZCA9IDA7CiAgICBwYWNrZWQgfD0gKHZhbC5pbmNvZ25pdG8gJiAxKSA8PCAwCiAgICBlbmNvZGVyLndyaXRlVWludDgocGFja2VkKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0UG9pbnRlcih0aW1lJC5UaW1lRGVsdGEsIHZhbC50aW1lb3V0KTsKICB9OwogIGZ1bmN0aW9uIE1lZGlhUm91dGVQcm92aWRlcl9DcmVhdGVSb3V0ZV9SZXNwb25zZVBhcmFtcyh2YWx1ZXMpIHsKICAgIHRoaXMuaW5pdERlZmF1bHRzXygpOwogICAgdGhpcy5pbml0RmllbGRzXyh2YWx1ZXMpOwogIH0KCgogIE1lZGlhUm91dGVQcm92aWRlcl9DcmVhdGVSb3V0ZV9SZXNwb25zZVBhcmFtcy5wcm90b3R5cGUuaW5pdERlZmF1bHRzXyA9IGZ1bmN0aW9uKCkgewogICAgdGhpcy5yb3V0ZSA9IG51bGw7CiAgICB0aGlzLmVycm9yVGV4dCA9IG51bGw7CiAgICB0aGlzLnJlc3VsdENvZGUgPSAwOwogIH07CiAgTWVkaWFSb3V0ZVByb3ZpZGVyX0NyZWF0ZVJvdXRlX1Jlc3BvbnNlUGFyYW1zLnByb3RvdHlwZS5pbml0RmllbGRzXyA9IGZ1bmN0aW9uKGZpZWxkcykgewogICAgZm9yKHZhciBmaWVsZCBpbiBmaWVsZHMpIHsKICAgICAgICBpZiAodGhpcy5oYXNPd25Qcm9wZXJ0eShmaWVsZCkpCiAgICAgICAgICB0aGlzW2ZpZWxkXSA9IGZpZWxkc1tmaWVsZF07CiAgICB9CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX0NyZWF0ZVJvdXRlX1Jlc3BvbnNlUGFyYW1zLnZhbGlkYXRlID0gZnVuY3Rpb24obWVzc2FnZVZhbGlkYXRvciwgb2Zmc2V0KSB7CiAgICB2YXIgZXJyOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdEhlYWRlcihvZmZzZXQsIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHZhciBrVmVyc2lvblNpemVzID0gWwogICAgICB7dmVyc2lvbjogMCwgbnVtQnl0ZXM6IDMyfQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZVByb3ZpZGVyX0NyZWF0ZVJvdXRlX1Jlc3BvbnNlUGFyYW1zLnJvdXRlCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0UG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDAsIE1lZGlhUm91dGUsIHRydWUpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhUm91dGVQcm92aWRlcl9DcmVhdGVSb3V0ZV9SZXNwb25zZVBhcmFtcy5lcnJvclRleHQKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJpbmdQb2ludGVyKG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgOCwgdHJ1ZSkKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlUm91dGVfUmVzcG9uc2VQYXJhbXMucmVzdWx0Q29kZQogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZUVudW0ob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAxNiwgUm91dGVSZXF1ZXN0UmVzdWx0Q29kZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIE1lZGlhUm91dGVQcm92aWRlcl9DcmVhdGVSb3V0ZV9SZXNwb25zZVBhcmFtcy5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMjQ7CgogIE1lZGlhUm91dGVQcm92aWRlcl9DcmVhdGVSb3V0ZV9SZXNwb25zZVBhcmFtcy5kZWNvZGUgPSBmdW5jdGlvbihkZWNvZGVyKSB7CiAgICB2YXIgcGFja2VkOwogICAgdmFyIHZhbCA9IG5ldyBNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlUm91dGVfUmVzcG9uc2VQYXJhbXMoKTsKICAgIHZhciBudW1iZXJPZkJ5dGVzID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YXIgdmVyc2lvbiA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFsLnJvdXRlID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3RQb2ludGVyKE1lZGlhUm91dGUpOwogICAgdmFsLmVycm9yVGV4dCA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLk51bGxhYmxlU3RyaW5nKTsKICAgIHZhbC5yZXN1bHRDb2RlID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuSW50MzIpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlUm91dGVfUmVzcG9uc2VQYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlUm91dGVfUmVzcG9uc2VQYXJhbXMuZW5jb2RlZFNpemUpOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMigwKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0UG9pbnRlcihNZWRpYVJvdXRlLCB2YWwucm91dGUpOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuTnVsbGFibGVTdHJpbmcsIHZhbC5lcnJvclRleHQpOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuSW50MzIsIHZhbC5yZXN1bHRDb2RlKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICB9OwogIGZ1bmN0aW9uIE1lZGlhUm91dGVQcm92aWRlcl9Kb2luUm91dGVfUGFyYW1zKHZhbHVlcykgewogICAgdGhpcy5pbml0RGVmYXVsdHNfKCk7CiAgICB0aGlzLmluaXRGaWVsZHNfKHZhbHVlcyk7CiAgfQoKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX0pvaW5Sb3V0ZV9QYXJhbXMucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMubWVkaWFTb3VyY2UgPSBudWxsOwogICAgdGhpcy5wcmVzZW50YXRpb25JZCA9IG51bGw7CiAgICB0aGlzLm9yaWdpbiA9IG51bGw7CiAgICB0aGlzLnRhYklkID0gMDsKICAgIHRoaXMuaW5jb2duaXRvID0gZmFsc2U7CiAgICB0aGlzLnRpbWVvdXQgPSBudWxsOwogIH07CiAgTWVkaWFSb3V0ZVByb3ZpZGVyX0pvaW5Sb3V0ZV9QYXJhbXMucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfSm9pblJvdXRlX1BhcmFtcy52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiA0OH0KICAgIF07CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0VmVyc2lvbihvZmZzZXQsIGtWZXJzaW9uU2l6ZXMpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhUm91dGVQcm92aWRlcl9Kb2luUm91dGVfUGFyYW1zLm1lZGlhU291cmNlCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDAsIGZhbHNlKQogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhUm91dGVQcm92aWRlcl9Kb2luUm91dGVfUGFyYW1zLnByZXNlbnRhdGlvbklkCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDgsIGZhbHNlKQogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhUm91dGVQcm92aWRlcl9Kb2luUm91dGVfUGFyYW1zLm9yaWdpbgogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFBvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAxNiwgb3JpZ2luJC5PcmlnaW4sIGZhbHNlKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZVByb3ZpZGVyX0pvaW5Sb3V0ZV9QYXJhbXMudGltZW91dAogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFBvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAzMiwgdGltZSQuVGltZURlbHRhLCBmYWxzZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfSm9pblJvdXRlX1BhcmFtcy5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgNDA7CgogIE1lZGlhUm91dGVQcm92aWRlcl9Kb2luUm91dGVfUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1lZGlhUm91dGVQcm92aWRlcl9Kb2luUm91dGVfUGFyYW1zKCk7CiAgICB2YXIgbnVtYmVyT2ZCeXRlcyA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFyIHZlcnNpb24gPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhbC5tZWRpYVNvdXJjZSA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLlN0cmluZyk7CiAgICB2YWwucHJlc2VudGF0aW9uSWQgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5TdHJpbmcpOwogICAgdmFsLm9yaWdpbiA9IGRlY29kZXIuZGVjb2RlU3RydWN0UG9pbnRlcihvcmlnaW4kLk9yaWdpbik7CiAgICB2YWwudGFiSWQgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5JbnQzMik7CiAgICBwYWNrZWQgPSBkZWNvZGVyLnJlYWRVaW50OCgpOwogICAgdmFsLmluY29nbml0byA9IChwYWNrZWQgPj4gMCkgJiAxID8gdHJ1ZSA6IGZhbHNlOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgdmFsLnRpbWVvdXQgPSBkZWNvZGVyLmRlY29kZVN0cnVjdFBvaW50ZXIodGltZSQuVGltZURlbHRhKTsKICAgIHJldHVybiB2YWw7CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX0pvaW5Sb3V0ZV9QYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNZWRpYVJvdXRlUHJvdmlkZXJfSm9pblJvdXRlX1BhcmFtcy5lbmNvZGVkU2l6ZSk7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKDApOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nLCB2YWwubWVkaWFTb3VyY2UpOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nLCB2YWwucHJlc2VudGF0aW9uSWQpOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3RQb2ludGVyKG9yaWdpbiQuT3JpZ2luLCB2YWwub3JpZ2luKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLkludDMyLCB2YWwudGFiSWQpOwogICAgcGFja2VkID0gMDsKICAgIHBhY2tlZCB8PSAodmFsLmluY29nbml0byAmIDEpIDw8IDAKICAgIGVuY29kZXIud3JpdGVVaW50OChwYWNrZWQpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3RQb2ludGVyKHRpbWUkLlRpbWVEZWx0YSwgdmFsLnRpbWVvdXQpOwogIH07CiAgZnVuY3Rpb24gTWVkaWFSb3V0ZVByb3ZpZGVyX0pvaW5Sb3V0ZV9SZXNwb25zZVBhcmFtcyh2YWx1ZXMpIHsKICAgIHRoaXMuaW5pdERlZmF1bHRzXygpOwogICAgdGhpcy5pbml0RmllbGRzXyh2YWx1ZXMpOwogIH0KCgogIE1lZGlhUm91dGVQcm92aWRlcl9Kb2luUm91dGVfUmVzcG9uc2VQYXJhbXMucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMucm91dGUgPSBudWxsOwogICAgdGhpcy5lcnJvclRleHQgPSBudWxsOwogICAgdGhpcy5yZXN1bHRDb2RlID0gMDsKICB9OwogIE1lZGlhUm91dGVQcm92aWRlcl9Kb2luUm91dGVfUmVzcG9uc2VQYXJhbXMucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfSm9pblJvdXRlX1Jlc3BvbnNlUGFyYW1zLnZhbGlkYXRlID0gZnVuY3Rpb24obWVzc2FnZVZhbGlkYXRvciwgb2Zmc2V0KSB7CiAgICB2YXIgZXJyOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdEhlYWRlcihvZmZzZXQsIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHZhciBrVmVyc2lvblNpemVzID0gWwogICAgICB7dmVyc2lvbjogMCwgbnVtQnl0ZXM6IDMyfQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZVByb3ZpZGVyX0pvaW5Sb3V0ZV9SZXNwb25zZVBhcmFtcy5yb3V0ZQogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFBvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAwLCBNZWRpYVJvdXRlLCB0cnVlKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBNZWRpYVJvdXRlUHJvdmlkZXJfSm9pblJvdXRlX1Jlc3BvbnNlUGFyYW1zLmVycm9yVGV4dAogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cmluZ1BvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA4LCB0cnVlKQogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhUm91dGVQcm92aWRlcl9Kb2luUm91dGVfUmVzcG9uc2VQYXJhbXMucmVzdWx0Q29kZQogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZUVudW0ob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAxNiwgUm91dGVSZXF1ZXN0UmVzdWx0Q29kZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIE1lZGlhUm91dGVQcm92aWRlcl9Kb2luUm91dGVfUmVzcG9uc2VQYXJhbXMuZW5jb2RlZFNpemUgPSBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDI0OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfSm9pblJvdXRlX1Jlc3BvbnNlUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1lZGlhUm91dGVQcm92aWRlcl9Kb2luUm91dGVfUmVzcG9uc2VQYXJhbXMoKTsKICAgIHZhciBudW1iZXJPZkJ5dGVzID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YXIgdmVyc2lvbiA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFsLnJvdXRlID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3RQb2ludGVyKE1lZGlhUm91dGUpOwogICAgdmFsLmVycm9yVGV4dCA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLk51bGxhYmxlU3RyaW5nKTsKICAgIHZhbC5yZXN1bHRDb2RlID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuSW50MzIpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfSm9pblJvdXRlX1Jlc3BvbnNlUGFyYW1zLmVuY29kZSA9IGZ1bmN0aW9uKGVuY29kZXIsIHZhbCkgewogICAgdmFyIHBhY2tlZDsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoTWVkaWFSb3V0ZVByb3ZpZGVyX0pvaW5Sb3V0ZV9SZXNwb25zZVBhcmFtcy5lbmNvZGVkU2l6ZSk7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKDApOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3RQb2ludGVyKE1lZGlhUm91dGUsIHZhbC5yb3V0ZSk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5OdWxsYWJsZVN0cmluZywgdmFsLmVycm9yVGV4dCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5JbnQzMiwgdmFsLnJlc3VsdENvZGUpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogIH07CiAgZnVuY3Rpb24gTWVkaWFSb3V0ZVByb3ZpZGVyX0Nvbm5lY3RSb3V0ZUJ5Um91dGVJZF9QYXJhbXModmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBNZWRpYVJvdXRlUHJvdmlkZXJfQ29ubmVjdFJvdXRlQnlSb3V0ZUlkX1BhcmFtcy5wcm90b3R5cGUuaW5pdERlZmF1bHRzXyA9IGZ1bmN0aW9uKCkgewogICAgdGhpcy5tZWRpYVNvdXJjZSA9IG51bGw7CiAgICB0aGlzLnJvdXRlSWQgPSBudWxsOwogICAgdGhpcy5wcmVzZW50YXRpb25JZCA9IG51bGw7CiAgICB0aGlzLm9yaWdpbiA9IG51bGw7CiAgICB0aGlzLnRhYklkID0gMDsKICAgIHRoaXMuaW5jb2duaXRvID0gZmFsc2U7CiAgICB0aGlzLnRpbWVvdXQgPSBudWxsOwogIH07CiAgTWVkaWFSb3V0ZVByb3ZpZGVyX0Nvbm5lY3RSb3V0ZUJ5Um91dGVJZF9QYXJhbXMucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfQ29ubmVjdFJvdXRlQnlSb3V0ZUlkX1BhcmFtcy52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiA1Nn0KICAgIF07CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0VmVyc2lvbihvZmZzZXQsIGtWZXJzaW9uU2l6ZXMpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhUm91dGVQcm92aWRlcl9Db25uZWN0Um91dGVCeVJvdXRlSWRfUGFyYW1zLm1lZGlhU291cmNlCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDAsIGZhbHNlKQogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhUm91dGVQcm92aWRlcl9Db25uZWN0Um91dGVCeVJvdXRlSWRfUGFyYW1zLnJvdXRlSWQKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJpbmdQb2ludGVyKG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgOCwgZmFsc2UpCiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZVByb3ZpZGVyX0Nvbm5lY3RSb3V0ZUJ5Um91dGVJZF9QYXJhbXMucHJlc2VudGF0aW9uSWQKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJpbmdQb2ludGVyKG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMTYsIGZhbHNlKQogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhUm91dGVQcm92aWRlcl9Db25uZWN0Um91dGVCeVJvdXRlSWRfUGFyYW1zLm9yaWdpbgogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFBvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAyNCwgb3JpZ2luJC5PcmlnaW4sIGZhbHNlKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZVByb3ZpZGVyX0Nvbm5lY3RSb3V0ZUJ5Um91dGVJZF9QYXJhbXMudGltZW91dAogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFBvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA0MCwgdGltZSQuVGltZURlbHRhLCBmYWxzZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfQ29ubmVjdFJvdXRlQnlSb3V0ZUlkX1BhcmFtcy5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgNDg7CgogIE1lZGlhUm91dGVQcm92aWRlcl9Db25uZWN0Um91dGVCeVJvdXRlSWRfUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1lZGlhUm91dGVQcm92aWRlcl9Db25uZWN0Um91dGVCeVJvdXRlSWRfUGFyYW1zKCk7CiAgICB2YXIgbnVtYmVyT2ZCeXRlcyA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFyIHZlcnNpb24gPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhbC5tZWRpYVNvdXJjZSA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLlN0cmluZyk7CiAgICB2YWwucm91dGVJZCA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLlN0cmluZyk7CiAgICB2YWwucHJlc2VudGF0aW9uSWQgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5TdHJpbmcpOwogICAgdmFsLm9yaWdpbiA9IGRlY29kZXIuZGVjb2RlU3RydWN0UG9pbnRlcihvcmlnaW4kLk9yaWdpbik7CiAgICB2YWwudGFiSWQgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5JbnQzMik7CiAgICBwYWNrZWQgPSBkZWNvZGVyLnJlYWRVaW50OCgpOwogICAgdmFsLmluY29nbml0byA9IChwYWNrZWQgPj4gMCkgJiAxID8gdHJ1ZSA6IGZhbHNlOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgdmFsLnRpbWVvdXQgPSBkZWNvZGVyLmRlY29kZVN0cnVjdFBvaW50ZXIodGltZSQuVGltZURlbHRhKTsKICAgIHJldHVybiB2YWw7CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX0Nvbm5lY3RSb3V0ZUJ5Um91dGVJZF9QYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNZWRpYVJvdXRlUHJvdmlkZXJfQ29ubmVjdFJvdXRlQnlSb3V0ZUlkX1BhcmFtcy5lbmNvZGVkU2l6ZSk7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKDApOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nLCB2YWwubWVkaWFTb3VyY2UpOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nLCB2YWwucm91dGVJZCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5TdHJpbmcsIHZhbC5wcmVzZW50YXRpb25JZCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdFBvaW50ZXIob3JpZ2luJC5PcmlnaW4sIHZhbC5vcmlnaW4pOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuSW50MzIsIHZhbC50YWJJZCk7CiAgICBwYWNrZWQgPSAwOwogICAgcGFja2VkIHw9ICh2YWwuaW5jb2duaXRvICYgMSkgPDwgMAogICAgZW5jb2Rlci53cml0ZVVpbnQ4KHBhY2tlZCk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdFBvaW50ZXIodGltZSQuVGltZURlbHRhLCB2YWwudGltZW91dCk7CiAgfTsKICBmdW5jdGlvbiBNZWRpYVJvdXRlUHJvdmlkZXJfQ29ubmVjdFJvdXRlQnlSb3V0ZUlkX1Jlc3BvbnNlUGFyYW1zKHZhbHVlcykgewogICAgdGhpcy5pbml0RGVmYXVsdHNfKCk7CiAgICB0aGlzLmluaXRGaWVsZHNfKHZhbHVlcyk7CiAgfQoKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX0Nvbm5lY3RSb3V0ZUJ5Um91dGVJZF9SZXNwb25zZVBhcmFtcy5wcm90b3R5cGUuaW5pdERlZmF1bHRzXyA9IGZ1bmN0aW9uKCkgewogICAgdGhpcy5yb3V0ZSA9IG51bGw7CiAgICB0aGlzLmVycm9yVGV4dCA9IG51bGw7CiAgICB0aGlzLnJlc3VsdENvZGUgPSAwOwogIH07CiAgTWVkaWFSb3V0ZVByb3ZpZGVyX0Nvbm5lY3RSb3V0ZUJ5Um91dGVJZF9SZXNwb25zZVBhcmFtcy5wcm90b3R5cGUuaW5pdEZpZWxkc18gPSBmdW5jdGlvbihmaWVsZHMpIHsKICAgIGZvcih2YXIgZmllbGQgaW4gZmllbGRzKSB7CiAgICAgICAgaWYgKHRoaXMuaGFzT3duUHJvcGVydHkoZmllbGQpKQogICAgICAgICAgdGhpc1tmaWVsZF0gPSBmaWVsZHNbZmllbGRdOwogICAgfQogIH07CgogIE1lZGlhUm91dGVQcm92aWRlcl9Db25uZWN0Um91dGVCeVJvdXRlSWRfUmVzcG9uc2VQYXJhbXMudmFsaWRhdGUgPSBmdW5jdGlvbihtZXNzYWdlVmFsaWRhdG9yLCBvZmZzZXQpIHsKICAgIHZhciBlcnI7CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0SGVhZGVyKG9mZnNldCwgY29kZWMua1N0cnVjdEhlYWRlclNpemUpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgdmFyIGtWZXJzaW9uU2l6ZXMgPSBbCiAgICAgIHt2ZXJzaW9uOiAwLCBudW1CeXRlczogMzJ9CiAgICBdOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFZlcnNpb24ob2Zmc2V0LCBrVmVyc2lvblNpemVzKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBNZWRpYVJvdXRlUHJvdmlkZXJfQ29ubmVjdFJvdXRlQnlSb3V0ZUlkX1Jlc3BvbnNlUGFyYW1zLnJvdXRlCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0UG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDAsIE1lZGlhUm91dGUsIHRydWUpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhUm91dGVQcm92aWRlcl9Db25uZWN0Um91dGVCeVJvdXRlSWRfUmVzcG9uc2VQYXJhbXMuZXJyb3JUZXh0CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDgsIHRydWUpCiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZVByb3ZpZGVyX0Nvbm5lY3RSb3V0ZUJ5Um91dGVJZF9SZXNwb25zZVBhcmFtcy5yZXN1bHRDb2RlCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlRW51bShvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDE2LCBSb3V0ZVJlcXVlc3RSZXN1bHRDb2RlKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX0Nvbm5lY3RSb3V0ZUJ5Um91dGVJZF9SZXNwb25zZVBhcmFtcy5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMjQ7CgogIE1lZGlhUm91dGVQcm92aWRlcl9Db25uZWN0Um91dGVCeVJvdXRlSWRfUmVzcG9uc2VQYXJhbXMuZGVjb2RlID0gZnVuY3Rpb24oZGVjb2RlcikgewogICAgdmFyIHBhY2tlZDsKICAgIHZhciB2YWwgPSBuZXcgTWVkaWFSb3V0ZVByb3ZpZGVyX0Nvbm5lY3RSb3V0ZUJ5Um91dGVJZF9SZXNwb25zZVBhcmFtcygpOwogICAgdmFyIG51bWJlck9mQnl0ZXMgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhciB2ZXJzaW9uID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YWwucm91dGUgPSBkZWNvZGVyLmRlY29kZVN0cnVjdFBvaW50ZXIoTWVkaWFSb3V0ZSk7CiAgICB2YWwuZXJyb3JUZXh0ID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuTnVsbGFibGVTdHJpbmcpOwogICAgdmFsLnJlc3VsdENvZGUgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5JbnQzMik7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICByZXR1cm4gdmFsOwogIH07CgogIE1lZGlhUm91dGVQcm92aWRlcl9Db25uZWN0Um91dGVCeVJvdXRlSWRfUmVzcG9uc2VQYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNZWRpYVJvdXRlUHJvdmlkZXJfQ29ubmVjdFJvdXRlQnlSb3V0ZUlkX1Jlc3BvbnNlUGFyYW1zLmVuY29kZWRTaXplKTsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoMCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdFBvaW50ZXIoTWVkaWFSb3V0ZSwgdmFsLnJvdXRlKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLk51bGxhYmxlU3RyaW5nLCB2YWwuZXJyb3JUZXh0KTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLkludDMyLCB2YWwucmVzdWx0Q29kZSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgfTsKICBmdW5jdGlvbiBNZWRpYVJvdXRlUHJvdmlkZXJfVGVybWluYXRlUm91dGVfUGFyYW1zKHZhbHVlcykgewogICAgdGhpcy5pbml0RGVmYXVsdHNfKCk7CiAgICB0aGlzLmluaXRGaWVsZHNfKHZhbHVlcyk7CiAgfQoKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1Rlcm1pbmF0ZVJvdXRlX1BhcmFtcy5wcm90b3R5cGUuaW5pdERlZmF1bHRzXyA9IGZ1bmN0aW9uKCkgewogICAgdGhpcy5yb3V0ZUlkID0gbnVsbDsKICB9OwogIE1lZGlhUm91dGVQcm92aWRlcl9UZXJtaW5hdGVSb3V0ZV9QYXJhbXMucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfVGVybWluYXRlUm91dGVfUGFyYW1zLnZhbGlkYXRlID0gZnVuY3Rpb24obWVzc2FnZVZhbGlkYXRvciwgb2Zmc2V0KSB7CiAgICB2YXIgZXJyOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdEhlYWRlcihvZmZzZXQsIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHZhciBrVmVyc2lvblNpemVzID0gWwogICAgICB7dmVyc2lvbjogMCwgbnVtQnl0ZXM6IDE2fQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZVByb3ZpZGVyX1Rlcm1pbmF0ZVJvdXRlX1BhcmFtcy5yb3V0ZUlkCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDAsIGZhbHNlKQogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfVGVybWluYXRlUm91dGVfUGFyYW1zLmVuY29kZWRTaXplID0gY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA4OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfVGVybWluYXRlUm91dGVfUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1lZGlhUm91dGVQcm92aWRlcl9UZXJtaW5hdGVSb3V0ZV9QYXJhbXMoKTsKICAgIHZhciBudW1iZXJPZkJ5dGVzID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YXIgdmVyc2lvbiA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFsLnJvdXRlSWQgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5TdHJpbmcpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfVGVybWluYXRlUm91dGVfUGFyYW1zLmVuY29kZSA9IGZ1bmN0aW9uKGVuY29kZXIsIHZhbCkgewogICAgdmFyIHBhY2tlZDsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoTWVkaWFSb3V0ZVByb3ZpZGVyX1Rlcm1pbmF0ZVJvdXRlX1BhcmFtcy5lbmNvZGVkU2l6ZSk7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKDApOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nLCB2YWwucm91dGVJZCk7CiAgfTsKICBmdW5jdGlvbiBNZWRpYVJvdXRlUHJvdmlkZXJfVGVybWluYXRlUm91dGVfUmVzcG9uc2VQYXJhbXModmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBNZWRpYVJvdXRlUHJvdmlkZXJfVGVybWluYXRlUm91dGVfUmVzcG9uc2VQYXJhbXMucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMuZXJyb3JUZXh0ID0gbnVsbDsKICAgIHRoaXMucmVzdWx0Q29kZSA9IDA7CiAgfTsKICBNZWRpYVJvdXRlUHJvdmlkZXJfVGVybWluYXRlUm91dGVfUmVzcG9uc2VQYXJhbXMucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfVGVybWluYXRlUm91dGVfUmVzcG9uc2VQYXJhbXMudmFsaWRhdGUgPSBmdW5jdGlvbihtZXNzYWdlVmFsaWRhdG9yLCBvZmZzZXQpIHsKICAgIHZhciBlcnI7CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0SGVhZGVyKG9mZnNldCwgY29kZWMua1N0cnVjdEhlYWRlclNpemUpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgdmFyIGtWZXJzaW9uU2l6ZXMgPSBbCiAgICAgIHt2ZXJzaW9uOiAwLCBudW1CeXRlczogMjR9CiAgICBdOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFZlcnNpb24ob2Zmc2V0LCBrVmVyc2lvblNpemVzKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBNZWRpYVJvdXRlUHJvdmlkZXJfVGVybWluYXRlUm91dGVfUmVzcG9uc2VQYXJhbXMuZXJyb3JUZXh0CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDAsIHRydWUpCiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZVByb3ZpZGVyX1Rlcm1pbmF0ZVJvdXRlX1Jlc3BvbnNlUGFyYW1zLnJlc3VsdENvZGUKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVFbnVtKG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgOCwgUm91dGVSZXF1ZXN0UmVzdWx0Q29kZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIE1lZGlhUm91dGVQcm92aWRlcl9UZXJtaW5hdGVSb3V0ZV9SZXNwb25zZVBhcmFtcy5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMTY7CgogIE1lZGlhUm91dGVQcm92aWRlcl9UZXJtaW5hdGVSb3V0ZV9SZXNwb25zZVBhcmFtcy5kZWNvZGUgPSBmdW5jdGlvbihkZWNvZGVyKSB7CiAgICB2YXIgcGFja2VkOwogICAgdmFyIHZhbCA9IG5ldyBNZWRpYVJvdXRlUHJvdmlkZXJfVGVybWluYXRlUm91dGVfUmVzcG9uc2VQYXJhbXMoKTsKICAgIHZhciBudW1iZXJPZkJ5dGVzID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YXIgdmVyc2lvbiA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFsLmVycm9yVGV4dCA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLk51bGxhYmxlU3RyaW5nKTsKICAgIHZhbC5yZXN1bHRDb2RlID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuSW50MzIpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfVGVybWluYXRlUm91dGVfUmVzcG9uc2VQYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNZWRpYVJvdXRlUHJvdmlkZXJfVGVybWluYXRlUm91dGVfUmVzcG9uc2VQYXJhbXMuZW5jb2RlZFNpemUpOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMigwKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLk51bGxhYmxlU3RyaW5nLCB2YWwuZXJyb3JUZXh0KTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLkludDMyLCB2YWwucmVzdWx0Q29kZSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgfTsKICBmdW5jdGlvbiBNZWRpYVJvdXRlUHJvdmlkZXJfU2VuZFJvdXRlTWVzc2FnZV9QYXJhbXModmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBNZWRpYVJvdXRlUHJvdmlkZXJfU2VuZFJvdXRlTWVzc2FnZV9QYXJhbXMucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMubWVkaWFSb3V0ZUlkID0gbnVsbDsKICAgIHRoaXMubWVzc2FnZSA9IG51bGw7CiAgfTsKICBNZWRpYVJvdXRlUHJvdmlkZXJfU2VuZFJvdXRlTWVzc2FnZV9QYXJhbXMucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfU2VuZFJvdXRlTWVzc2FnZV9QYXJhbXMudmFsaWRhdGUgPSBmdW5jdGlvbihtZXNzYWdlVmFsaWRhdG9yLCBvZmZzZXQpIHsKICAgIHZhciBlcnI7CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0SGVhZGVyKG9mZnNldCwgY29kZWMua1N0cnVjdEhlYWRlclNpemUpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgdmFyIGtWZXJzaW9uU2l6ZXMgPSBbCiAgICAgIHt2ZXJzaW9uOiAwLCBudW1CeXRlczogMjR9CiAgICBdOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFZlcnNpb24ob2Zmc2V0LCBrVmVyc2lvblNpemVzKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBNZWRpYVJvdXRlUHJvdmlkZXJfU2VuZFJvdXRlTWVzc2FnZV9QYXJhbXMubWVkaWFSb3V0ZUlkCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDAsIGZhbHNlKQogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhUm91dGVQcm92aWRlcl9TZW5kUm91dGVNZXNzYWdlX1BhcmFtcy5tZXNzYWdlCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDgsIGZhbHNlKQogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfU2VuZFJvdXRlTWVzc2FnZV9QYXJhbXMuZW5jb2RlZFNpemUgPSBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDE2OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfU2VuZFJvdXRlTWVzc2FnZV9QYXJhbXMuZGVjb2RlID0gZnVuY3Rpb24oZGVjb2RlcikgewogICAgdmFyIHBhY2tlZDsKICAgIHZhciB2YWwgPSBuZXcgTWVkaWFSb3V0ZVByb3ZpZGVyX1NlbmRSb3V0ZU1lc3NhZ2VfUGFyYW1zKCk7CiAgICB2YXIgbnVtYmVyT2ZCeXRlcyA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFyIHZlcnNpb24gPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhbC5tZWRpYVJvdXRlSWQgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5TdHJpbmcpOwogICAgdmFsLm1lc3NhZ2UgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5TdHJpbmcpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfU2VuZFJvdXRlTWVzc2FnZV9QYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNZWRpYVJvdXRlUHJvdmlkZXJfU2VuZFJvdXRlTWVzc2FnZV9QYXJhbXMuZW5jb2RlZFNpemUpOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMigwKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLlN0cmluZywgdmFsLm1lZGlhUm91dGVJZCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5TdHJpbmcsIHZhbC5tZXNzYWdlKTsKICB9OwogIGZ1bmN0aW9uIE1lZGlhUm91dGVQcm92aWRlcl9TZW5kUm91dGVNZXNzYWdlX1Jlc3BvbnNlUGFyYW1zKHZhbHVlcykgewogICAgdGhpcy5pbml0RGVmYXVsdHNfKCk7CiAgICB0aGlzLmluaXRGaWVsZHNfKHZhbHVlcyk7CiAgfQoKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1NlbmRSb3V0ZU1lc3NhZ2VfUmVzcG9uc2VQYXJhbXMucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMuc2VudCA9IGZhbHNlOwogIH07CiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1NlbmRSb3V0ZU1lc3NhZ2VfUmVzcG9uc2VQYXJhbXMucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfU2VuZFJvdXRlTWVzc2FnZV9SZXNwb25zZVBhcmFtcy52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiAxNn0KICAgIF07CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0VmVyc2lvbihvZmZzZXQsIGtWZXJzaW9uU2l6ZXMpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1NlbmRSb3V0ZU1lc3NhZ2VfUmVzcG9uc2VQYXJhbXMuZW5jb2RlZFNpemUgPSBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDg7CgogIE1lZGlhUm91dGVQcm92aWRlcl9TZW5kUm91dGVNZXNzYWdlX1Jlc3BvbnNlUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1lZGlhUm91dGVQcm92aWRlcl9TZW5kUm91dGVNZXNzYWdlX1Jlc3BvbnNlUGFyYW1zKCk7CiAgICB2YXIgbnVtYmVyT2ZCeXRlcyA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFyIHZlcnNpb24gPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHBhY2tlZCA9IGRlY29kZXIucmVhZFVpbnQ4KCk7CiAgICB2YWwuc2VudCA9IChwYWNrZWQgPj4gMCkgJiAxID8gdHJ1ZSA6IGZhbHNlOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfU2VuZFJvdXRlTWVzc2FnZV9SZXNwb25zZVBhcmFtcy5lbmNvZGUgPSBmdW5jdGlvbihlbmNvZGVyLCB2YWwpIHsKICAgIHZhciBwYWNrZWQ7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKE1lZGlhUm91dGVQcm92aWRlcl9TZW5kUm91dGVNZXNzYWdlX1Jlc3BvbnNlUGFyYW1zLmVuY29kZWRTaXplKTsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoMCk7CiAgICBwYWNrZWQgPSAwOwogICAgcGFja2VkIHw9ICh2YWwuc2VudCAmIDEpIDw8IDAKICAgIGVuY29kZXIud3JpdGVVaW50OChwYWNrZWQpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogIH07CiAgZnVuY3Rpb24gTWVkaWFSb3V0ZVByb3ZpZGVyX1NlbmRSb3V0ZUJpbmFyeU1lc3NhZ2VfUGFyYW1zKHZhbHVlcykgewogICAgdGhpcy5pbml0RGVmYXVsdHNfKCk7CiAgICB0aGlzLmluaXRGaWVsZHNfKHZhbHVlcyk7CiAgfQoKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1NlbmRSb3V0ZUJpbmFyeU1lc3NhZ2VfUGFyYW1zLnByb3RvdHlwZS5pbml0RGVmYXVsdHNfID0gZnVuY3Rpb24oKSB7CiAgICB0aGlzLm1lZGlhUm91dGVJZCA9IG51bGw7CiAgICB0aGlzLmRhdGEgPSBudWxsOwogIH07CiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1NlbmRSb3V0ZUJpbmFyeU1lc3NhZ2VfUGFyYW1zLnByb3RvdHlwZS5pbml0RmllbGRzXyA9IGZ1bmN0aW9uKGZpZWxkcykgewogICAgZm9yKHZhciBmaWVsZCBpbiBmaWVsZHMpIHsKICAgICAgICBpZiAodGhpcy5oYXNPd25Qcm9wZXJ0eShmaWVsZCkpCiAgICAgICAgICB0aGlzW2ZpZWxkXSA9IGZpZWxkc1tmaWVsZF07CiAgICB9CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1NlbmRSb3V0ZUJpbmFyeU1lc3NhZ2VfUGFyYW1zLnZhbGlkYXRlID0gZnVuY3Rpb24obWVzc2FnZVZhbGlkYXRvciwgb2Zmc2V0KSB7CiAgICB2YXIgZXJyOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdEhlYWRlcihvZmZzZXQsIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHZhciBrVmVyc2lvblNpemVzID0gWwogICAgICB7dmVyc2lvbjogMCwgbnVtQnl0ZXM6IDI0fQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZVByb3ZpZGVyX1NlbmRSb3V0ZUJpbmFyeU1lc3NhZ2VfUGFyYW1zLm1lZGlhUm91dGVJZAogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cmluZ1BvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAwLCBmYWxzZSkKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBNZWRpYVJvdXRlUHJvdmlkZXJfU2VuZFJvdXRlQmluYXJ5TWVzc2FnZV9QYXJhbXMuZGF0YQogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZUFycmF5UG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDgsIDEsIGNvZGVjLlVpbnQ4LCBmYWxzZSwgWzBdLCAwKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1NlbmRSb3V0ZUJpbmFyeU1lc3NhZ2VfUGFyYW1zLmVuY29kZWRTaXplID0gY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAxNjsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1NlbmRSb3V0ZUJpbmFyeU1lc3NhZ2VfUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1lZGlhUm91dGVQcm92aWRlcl9TZW5kUm91dGVCaW5hcnlNZXNzYWdlX1BhcmFtcygpOwogICAgdmFyIG51bWJlck9mQnl0ZXMgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhciB2ZXJzaW9uID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YWwubWVkaWFSb3V0ZUlkID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nKTsKICAgIHZhbC5kYXRhID0gZGVjb2Rlci5kZWNvZGVBcnJheVBvaW50ZXIoY29kZWMuVWludDgpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfU2VuZFJvdXRlQmluYXJ5TWVzc2FnZV9QYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNZWRpYVJvdXRlUHJvdmlkZXJfU2VuZFJvdXRlQmluYXJ5TWVzc2FnZV9QYXJhbXMuZW5jb2RlZFNpemUpOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMigwKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLlN0cmluZywgdmFsLm1lZGlhUm91dGVJZCk7CiAgICBlbmNvZGVyLmVuY29kZUFycmF5UG9pbnRlcihjb2RlYy5VaW50OCwgdmFsLmRhdGEpOwogIH07CiAgZnVuY3Rpb24gTWVkaWFSb3V0ZVByb3ZpZGVyX1NlbmRSb3V0ZUJpbmFyeU1lc3NhZ2VfUmVzcG9uc2VQYXJhbXModmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBNZWRpYVJvdXRlUHJvdmlkZXJfU2VuZFJvdXRlQmluYXJ5TWVzc2FnZV9SZXNwb25zZVBhcmFtcy5wcm90b3R5cGUuaW5pdERlZmF1bHRzXyA9IGZ1bmN0aW9uKCkgewogICAgdGhpcy5zZW50ID0gZmFsc2U7CiAgfTsKICBNZWRpYVJvdXRlUHJvdmlkZXJfU2VuZFJvdXRlQmluYXJ5TWVzc2FnZV9SZXNwb25zZVBhcmFtcy5wcm90b3R5cGUuaW5pdEZpZWxkc18gPSBmdW5jdGlvbihmaWVsZHMpIHsKICAgIGZvcih2YXIgZmllbGQgaW4gZmllbGRzKSB7CiAgICAgICAgaWYgKHRoaXMuaGFzT3duUHJvcGVydHkoZmllbGQpKQogICAgICAgICAgdGhpc1tmaWVsZF0gPSBmaWVsZHNbZmllbGRdOwogICAgfQogIH07CgogIE1lZGlhUm91dGVQcm92aWRlcl9TZW5kUm91dGVCaW5hcnlNZXNzYWdlX1Jlc3BvbnNlUGFyYW1zLnZhbGlkYXRlID0gZnVuY3Rpb24obWVzc2FnZVZhbGlkYXRvciwgb2Zmc2V0KSB7CiAgICB2YXIgZXJyOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdEhlYWRlcihvZmZzZXQsIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHZhciBrVmVyc2lvblNpemVzID0gWwogICAgICB7dmVyc2lvbjogMCwgbnVtQnl0ZXM6IDE2fQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfU2VuZFJvdXRlQmluYXJ5TWVzc2FnZV9SZXNwb25zZVBhcmFtcy5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgODsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1NlbmRSb3V0ZUJpbmFyeU1lc3NhZ2VfUmVzcG9uc2VQYXJhbXMuZGVjb2RlID0gZnVuY3Rpb24oZGVjb2RlcikgewogICAgdmFyIHBhY2tlZDsKICAgIHZhciB2YWwgPSBuZXcgTWVkaWFSb3V0ZVByb3ZpZGVyX1NlbmRSb3V0ZUJpbmFyeU1lc3NhZ2VfUmVzcG9uc2VQYXJhbXMoKTsKICAgIHZhciBudW1iZXJPZkJ5dGVzID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YXIgdmVyc2lvbiA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgcGFja2VkID0gZGVjb2Rlci5yZWFkVWludDgoKTsKICAgIHZhbC5zZW50ID0gKHBhY2tlZCA+PiAwKSAmIDEgPyB0cnVlIDogZmFsc2U7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICByZXR1cm4gdmFsOwogIH07CgogIE1lZGlhUm91dGVQcm92aWRlcl9TZW5kUm91dGVCaW5hcnlNZXNzYWdlX1Jlc3BvbnNlUGFyYW1zLmVuY29kZSA9IGZ1bmN0aW9uKGVuY29kZXIsIHZhbCkgewogICAgdmFyIHBhY2tlZDsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoTWVkaWFSb3V0ZVByb3ZpZGVyX1NlbmRSb3V0ZUJpbmFyeU1lc3NhZ2VfUmVzcG9uc2VQYXJhbXMuZW5jb2RlZFNpemUpOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMigwKTsKICAgIHBhY2tlZCA9IDA7CiAgICBwYWNrZWQgfD0gKHZhbC5zZW50ICYgMSkgPDwgMAogICAgZW5jb2Rlci53cml0ZVVpbnQ4KHBhY2tlZCk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgfTsKICBmdW5jdGlvbiBNZWRpYVJvdXRlUHJvdmlkZXJfU3RhcnRPYnNlcnZpbmdNZWRpYVNpbmtzX1BhcmFtcyh2YWx1ZXMpIHsKICAgIHRoaXMuaW5pdERlZmF1bHRzXygpOwogICAgdGhpcy5pbml0RmllbGRzXyh2YWx1ZXMpOwogIH0KCgogIE1lZGlhUm91dGVQcm92aWRlcl9TdGFydE9ic2VydmluZ01lZGlhU2lua3NfUGFyYW1zLnByb3RvdHlwZS5pbml0RGVmYXVsdHNfID0gZnVuY3Rpb24oKSB7CiAgICB0aGlzLm1lZGlhU291cmNlID0gbnVsbDsKICB9OwogIE1lZGlhUm91dGVQcm92aWRlcl9TdGFydE9ic2VydmluZ01lZGlhU2lua3NfUGFyYW1zLnByb3RvdHlwZS5pbml0RmllbGRzXyA9IGZ1bmN0aW9uKGZpZWxkcykgewogICAgZm9yKHZhciBmaWVsZCBpbiBmaWVsZHMpIHsKICAgICAgICBpZiAodGhpcy5oYXNPd25Qcm9wZXJ0eShmaWVsZCkpCiAgICAgICAgICB0aGlzW2ZpZWxkXSA9IGZpZWxkc1tmaWVsZF07CiAgICB9CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1N0YXJ0T2JzZXJ2aW5nTWVkaWFTaW5rc19QYXJhbXMudmFsaWRhdGUgPSBmdW5jdGlvbihtZXNzYWdlVmFsaWRhdG9yLCBvZmZzZXQpIHsKICAgIHZhciBlcnI7CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0SGVhZGVyKG9mZnNldCwgY29kZWMua1N0cnVjdEhlYWRlclNpemUpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgdmFyIGtWZXJzaW9uU2l6ZXMgPSBbCiAgICAgIHt2ZXJzaW9uOiAwLCBudW1CeXRlczogMTZ9CiAgICBdOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFZlcnNpb24ob2Zmc2V0LCBrVmVyc2lvblNpemVzKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBNZWRpYVJvdXRlUHJvdmlkZXJfU3RhcnRPYnNlcnZpbmdNZWRpYVNpbmtzX1BhcmFtcy5tZWRpYVNvdXJjZQogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cmluZ1BvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAwLCBmYWxzZSkKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1N0YXJ0T2JzZXJ2aW5nTWVkaWFTaW5rc19QYXJhbXMuZW5jb2RlZFNpemUgPSBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDg7CgogIE1lZGlhUm91dGVQcm92aWRlcl9TdGFydE9ic2VydmluZ01lZGlhU2lua3NfUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1lZGlhUm91dGVQcm92aWRlcl9TdGFydE9ic2VydmluZ01lZGlhU2lua3NfUGFyYW1zKCk7CiAgICB2YXIgbnVtYmVyT2ZCeXRlcyA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFyIHZlcnNpb24gPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhbC5tZWRpYVNvdXJjZSA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLlN0cmluZyk7CiAgICByZXR1cm4gdmFsOwogIH07CgogIE1lZGlhUm91dGVQcm92aWRlcl9TdGFydE9ic2VydmluZ01lZGlhU2lua3NfUGFyYW1zLmVuY29kZSA9IGZ1bmN0aW9uKGVuY29kZXIsIHZhbCkgewogICAgdmFyIHBhY2tlZDsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoTWVkaWFSb3V0ZVByb3ZpZGVyX1N0YXJ0T2JzZXJ2aW5nTWVkaWFTaW5rc19QYXJhbXMuZW5jb2RlZFNpemUpOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMigwKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLlN0cmluZywgdmFsLm1lZGlhU291cmNlKTsKICB9OwogIGZ1bmN0aW9uIE1lZGlhUm91dGVQcm92aWRlcl9TdG9wT2JzZXJ2aW5nTWVkaWFTaW5rc19QYXJhbXModmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBNZWRpYVJvdXRlUHJvdmlkZXJfU3RvcE9ic2VydmluZ01lZGlhU2lua3NfUGFyYW1zLnByb3RvdHlwZS5pbml0RGVmYXVsdHNfID0gZnVuY3Rpb24oKSB7CiAgICB0aGlzLm1lZGlhU291cmNlID0gbnVsbDsKICB9OwogIE1lZGlhUm91dGVQcm92aWRlcl9TdG9wT2JzZXJ2aW5nTWVkaWFTaW5rc19QYXJhbXMucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfU3RvcE9ic2VydmluZ01lZGlhU2lua3NfUGFyYW1zLnZhbGlkYXRlID0gZnVuY3Rpb24obWVzc2FnZVZhbGlkYXRvciwgb2Zmc2V0KSB7CiAgICB2YXIgZXJyOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdEhlYWRlcihvZmZzZXQsIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHZhciBrVmVyc2lvblNpemVzID0gWwogICAgICB7dmVyc2lvbjogMCwgbnVtQnl0ZXM6IDE2fQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZVByb3ZpZGVyX1N0b3BPYnNlcnZpbmdNZWRpYVNpbmtzX1BhcmFtcy5tZWRpYVNvdXJjZQogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cmluZ1BvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAwLCBmYWxzZSkKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1N0b3BPYnNlcnZpbmdNZWRpYVNpbmtzX1BhcmFtcy5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgODsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1N0b3BPYnNlcnZpbmdNZWRpYVNpbmtzX1BhcmFtcy5kZWNvZGUgPSBmdW5jdGlvbihkZWNvZGVyKSB7CiAgICB2YXIgcGFja2VkOwogICAgdmFyIHZhbCA9IG5ldyBNZWRpYVJvdXRlUHJvdmlkZXJfU3RvcE9ic2VydmluZ01lZGlhU2lua3NfUGFyYW1zKCk7CiAgICB2YXIgbnVtYmVyT2ZCeXRlcyA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFyIHZlcnNpb24gPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhbC5tZWRpYVNvdXJjZSA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLlN0cmluZyk7CiAgICByZXR1cm4gdmFsOwogIH07CgogIE1lZGlhUm91dGVQcm92aWRlcl9TdG9wT2JzZXJ2aW5nTWVkaWFTaW5rc19QYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNZWRpYVJvdXRlUHJvdmlkZXJfU3RvcE9ic2VydmluZ01lZGlhU2lua3NfUGFyYW1zLmVuY29kZWRTaXplKTsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoMCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5TdHJpbmcsIHZhbC5tZWRpYVNvdXJjZSk7CiAgfTsKICBmdW5jdGlvbiBNZWRpYVJvdXRlUHJvdmlkZXJfU3RhcnRPYnNlcnZpbmdNZWRpYVJvdXRlc19QYXJhbXModmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBNZWRpYVJvdXRlUHJvdmlkZXJfU3RhcnRPYnNlcnZpbmdNZWRpYVJvdXRlc19QYXJhbXMucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMubWVkaWFTb3VyY2UgPSBudWxsOwogIH07CiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1N0YXJ0T2JzZXJ2aW5nTWVkaWFSb3V0ZXNfUGFyYW1zLnByb3RvdHlwZS5pbml0RmllbGRzXyA9IGZ1bmN0aW9uKGZpZWxkcykgewogICAgZm9yKHZhciBmaWVsZCBpbiBmaWVsZHMpIHsKICAgICAgICBpZiAodGhpcy5oYXNPd25Qcm9wZXJ0eShmaWVsZCkpCiAgICAgICAgICB0aGlzW2ZpZWxkXSA9IGZpZWxkc1tmaWVsZF07CiAgICB9CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1N0YXJ0T2JzZXJ2aW5nTWVkaWFSb3V0ZXNfUGFyYW1zLnZhbGlkYXRlID0gZnVuY3Rpb24obWVzc2FnZVZhbGlkYXRvciwgb2Zmc2V0KSB7CiAgICB2YXIgZXJyOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdEhlYWRlcihvZmZzZXQsIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHZhciBrVmVyc2lvblNpemVzID0gWwogICAgICB7dmVyc2lvbjogMCwgbnVtQnl0ZXM6IDE2fQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZVByb3ZpZGVyX1N0YXJ0T2JzZXJ2aW5nTWVkaWFSb3V0ZXNfUGFyYW1zLm1lZGlhU291cmNlCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDAsIGZhbHNlKQogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfU3RhcnRPYnNlcnZpbmdNZWRpYVJvdXRlc19QYXJhbXMuZW5jb2RlZFNpemUgPSBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDg7CgogIE1lZGlhUm91dGVQcm92aWRlcl9TdGFydE9ic2VydmluZ01lZGlhUm91dGVzX1BhcmFtcy5kZWNvZGUgPSBmdW5jdGlvbihkZWNvZGVyKSB7CiAgICB2YXIgcGFja2VkOwogICAgdmFyIHZhbCA9IG5ldyBNZWRpYVJvdXRlUHJvdmlkZXJfU3RhcnRPYnNlcnZpbmdNZWRpYVJvdXRlc19QYXJhbXMoKTsKICAgIHZhciBudW1iZXJPZkJ5dGVzID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YXIgdmVyc2lvbiA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFsLm1lZGlhU291cmNlID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nKTsKICAgIHJldHVybiB2YWw7CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1N0YXJ0T2JzZXJ2aW5nTWVkaWFSb3V0ZXNfUGFyYW1zLmVuY29kZSA9IGZ1bmN0aW9uKGVuY29kZXIsIHZhbCkgewogICAgdmFyIHBhY2tlZDsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoTWVkaWFSb3V0ZVByb3ZpZGVyX1N0YXJ0T2JzZXJ2aW5nTWVkaWFSb3V0ZXNfUGFyYW1zLmVuY29kZWRTaXplKTsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoMCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5TdHJpbmcsIHZhbC5tZWRpYVNvdXJjZSk7CiAgfTsKICBmdW5jdGlvbiBNZWRpYVJvdXRlUHJvdmlkZXJfU3RvcE9ic2VydmluZ01lZGlhUm91dGVzX1BhcmFtcyh2YWx1ZXMpIHsKICAgIHRoaXMuaW5pdERlZmF1bHRzXygpOwogICAgdGhpcy5pbml0RmllbGRzXyh2YWx1ZXMpOwogIH0KCgogIE1lZGlhUm91dGVQcm92aWRlcl9TdG9wT2JzZXJ2aW5nTWVkaWFSb3V0ZXNfUGFyYW1zLnByb3RvdHlwZS5pbml0RGVmYXVsdHNfID0gZnVuY3Rpb24oKSB7CiAgICB0aGlzLm1lZGlhU291cmNlID0gbnVsbDsKICB9OwogIE1lZGlhUm91dGVQcm92aWRlcl9TdG9wT2JzZXJ2aW5nTWVkaWFSb3V0ZXNfUGFyYW1zLnByb3RvdHlwZS5pbml0RmllbGRzXyA9IGZ1bmN0aW9uKGZpZWxkcykgewogICAgZm9yKHZhciBmaWVsZCBpbiBmaWVsZHMpIHsKICAgICAgICBpZiAodGhpcy5oYXNPd25Qcm9wZXJ0eShmaWVsZCkpCiAgICAgICAgICB0aGlzW2ZpZWxkXSA9IGZpZWxkc1tmaWVsZF07CiAgICB9CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1N0b3BPYnNlcnZpbmdNZWRpYVJvdXRlc19QYXJhbXMudmFsaWRhdGUgPSBmdW5jdGlvbihtZXNzYWdlVmFsaWRhdG9yLCBvZmZzZXQpIHsKICAgIHZhciBlcnI7CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0SGVhZGVyKG9mZnNldCwgY29kZWMua1N0cnVjdEhlYWRlclNpemUpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgdmFyIGtWZXJzaW9uU2l6ZXMgPSBbCiAgICAgIHt2ZXJzaW9uOiAwLCBudW1CeXRlczogMTZ9CiAgICBdOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFZlcnNpb24ob2Zmc2V0LCBrVmVyc2lvblNpemVzKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBNZWRpYVJvdXRlUHJvdmlkZXJfU3RvcE9ic2VydmluZ01lZGlhUm91dGVzX1BhcmFtcy5tZWRpYVNvdXJjZQogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cmluZ1BvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAwLCBmYWxzZSkKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1N0b3BPYnNlcnZpbmdNZWRpYVJvdXRlc19QYXJhbXMuZW5jb2RlZFNpemUgPSBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDg7CgogIE1lZGlhUm91dGVQcm92aWRlcl9TdG9wT2JzZXJ2aW5nTWVkaWFSb3V0ZXNfUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1lZGlhUm91dGVQcm92aWRlcl9TdG9wT2JzZXJ2aW5nTWVkaWFSb3V0ZXNfUGFyYW1zKCk7CiAgICB2YXIgbnVtYmVyT2ZCeXRlcyA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFyIHZlcnNpb24gPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhbC5tZWRpYVNvdXJjZSA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLlN0cmluZyk7CiAgICByZXR1cm4gdmFsOwogIH07CgogIE1lZGlhUm91dGVQcm92aWRlcl9TdG9wT2JzZXJ2aW5nTWVkaWFSb3V0ZXNfUGFyYW1zLmVuY29kZSA9IGZ1bmN0aW9uKGVuY29kZXIsIHZhbCkgewogICAgdmFyIHBhY2tlZDsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoTWVkaWFSb3V0ZVByb3ZpZGVyX1N0b3BPYnNlcnZpbmdNZWRpYVJvdXRlc19QYXJhbXMuZW5jb2RlZFNpemUpOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMigwKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLlN0cmluZywgdmFsLm1lZGlhU291cmNlKTsKICB9OwogIGZ1bmN0aW9uIE1lZGlhUm91dGVQcm92aWRlcl9TdGFydExpc3RlbmluZ0ZvclJvdXRlTWVzc2FnZXNfUGFyYW1zKHZhbHVlcykgewogICAgdGhpcy5pbml0RGVmYXVsdHNfKCk7CiAgICB0aGlzLmluaXRGaWVsZHNfKHZhbHVlcyk7CiAgfQoKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1N0YXJ0TGlzdGVuaW5nRm9yUm91dGVNZXNzYWdlc19QYXJhbXMucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMucm91dGVJZCA9IG51bGw7CiAgfTsKICBNZWRpYVJvdXRlUHJvdmlkZXJfU3RhcnRMaXN0ZW5pbmdGb3JSb3V0ZU1lc3NhZ2VzX1BhcmFtcy5wcm90b3R5cGUuaW5pdEZpZWxkc18gPSBmdW5jdGlvbihmaWVsZHMpIHsKICAgIGZvcih2YXIgZmllbGQgaW4gZmllbGRzKSB7CiAgICAgICAgaWYgKHRoaXMuaGFzT3duUHJvcGVydHkoZmllbGQpKQogICAgICAgICAgdGhpc1tmaWVsZF0gPSBmaWVsZHNbZmllbGRdOwogICAgfQogIH07CgogIE1lZGlhUm91dGVQcm92aWRlcl9TdGFydExpc3RlbmluZ0ZvclJvdXRlTWVzc2FnZXNfUGFyYW1zLnZhbGlkYXRlID0gZnVuY3Rpb24obWVzc2FnZVZhbGlkYXRvciwgb2Zmc2V0KSB7CiAgICB2YXIgZXJyOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdEhlYWRlcihvZmZzZXQsIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHZhciBrVmVyc2lvblNpemVzID0gWwogICAgICB7dmVyc2lvbjogMCwgbnVtQnl0ZXM6IDE2fQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZVByb3ZpZGVyX1N0YXJ0TGlzdGVuaW5nRm9yUm91dGVNZXNzYWdlc19QYXJhbXMucm91dGVJZAogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cmluZ1BvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAwLCBmYWxzZSkKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1N0YXJ0TGlzdGVuaW5nRm9yUm91dGVNZXNzYWdlc19QYXJhbXMuZW5jb2RlZFNpemUgPSBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDg7CgogIE1lZGlhUm91dGVQcm92aWRlcl9TdGFydExpc3RlbmluZ0ZvclJvdXRlTWVzc2FnZXNfUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1lZGlhUm91dGVQcm92aWRlcl9TdGFydExpc3RlbmluZ0ZvclJvdXRlTWVzc2FnZXNfUGFyYW1zKCk7CiAgICB2YXIgbnVtYmVyT2ZCeXRlcyA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFyIHZlcnNpb24gPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhbC5yb3V0ZUlkID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nKTsKICAgIHJldHVybiB2YWw7CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1N0YXJ0TGlzdGVuaW5nRm9yUm91dGVNZXNzYWdlc19QYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNZWRpYVJvdXRlUHJvdmlkZXJfU3RhcnRMaXN0ZW5pbmdGb3JSb3V0ZU1lc3NhZ2VzX1BhcmFtcy5lbmNvZGVkU2l6ZSk7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKDApOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nLCB2YWwucm91dGVJZCk7CiAgfTsKICBmdW5jdGlvbiBNZWRpYVJvdXRlUHJvdmlkZXJfU3RvcExpc3RlbmluZ0ZvclJvdXRlTWVzc2FnZXNfUGFyYW1zKHZhbHVlcykgewogICAgdGhpcy5pbml0RGVmYXVsdHNfKCk7CiAgICB0aGlzLmluaXRGaWVsZHNfKHZhbHVlcyk7CiAgfQoKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1N0b3BMaXN0ZW5pbmdGb3JSb3V0ZU1lc3NhZ2VzX1BhcmFtcy5wcm90b3R5cGUuaW5pdERlZmF1bHRzXyA9IGZ1bmN0aW9uKCkgewogICAgdGhpcy5yb3V0ZUlkID0gbnVsbDsKICB9OwogIE1lZGlhUm91dGVQcm92aWRlcl9TdG9wTGlzdGVuaW5nRm9yUm91dGVNZXNzYWdlc19QYXJhbXMucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfU3RvcExpc3RlbmluZ0ZvclJvdXRlTWVzc2FnZXNfUGFyYW1zLnZhbGlkYXRlID0gZnVuY3Rpb24obWVzc2FnZVZhbGlkYXRvciwgb2Zmc2V0KSB7CiAgICB2YXIgZXJyOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdEhlYWRlcihvZmZzZXQsIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHZhciBrVmVyc2lvblNpemVzID0gWwogICAgICB7dmVyc2lvbjogMCwgbnVtQnl0ZXM6IDE2fQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZVByb3ZpZGVyX1N0b3BMaXN0ZW5pbmdGb3JSb3V0ZU1lc3NhZ2VzX1BhcmFtcy5yb3V0ZUlkCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDAsIGZhbHNlKQogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfU3RvcExpc3RlbmluZ0ZvclJvdXRlTWVzc2FnZXNfUGFyYW1zLmVuY29kZWRTaXplID0gY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA4OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfU3RvcExpc3RlbmluZ0ZvclJvdXRlTWVzc2FnZXNfUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1lZGlhUm91dGVQcm92aWRlcl9TdG9wTGlzdGVuaW5nRm9yUm91dGVNZXNzYWdlc19QYXJhbXMoKTsKICAgIHZhciBudW1iZXJPZkJ5dGVzID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YXIgdmVyc2lvbiA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFsLnJvdXRlSWQgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5TdHJpbmcpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfU3RvcExpc3RlbmluZ0ZvclJvdXRlTWVzc2FnZXNfUGFyYW1zLmVuY29kZSA9IGZ1bmN0aW9uKGVuY29kZXIsIHZhbCkgewogICAgdmFyIHBhY2tlZDsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoTWVkaWFSb3V0ZVByb3ZpZGVyX1N0b3BMaXN0ZW5pbmdGb3JSb3V0ZU1lc3NhZ2VzX1BhcmFtcy5lbmNvZGVkU2l6ZSk7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKDApOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nLCB2YWwucm91dGVJZCk7CiAgfTsKICBmdW5jdGlvbiBNZWRpYVJvdXRlUHJvdmlkZXJfRGV0YWNoUm91dGVfUGFyYW1zKHZhbHVlcykgewogICAgdGhpcy5pbml0RGVmYXVsdHNfKCk7CiAgICB0aGlzLmluaXRGaWVsZHNfKHZhbHVlcyk7CiAgfQoKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX0RldGFjaFJvdXRlX1BhcmFtcy5wcm90b3R5cGUuaW5pdERlZmF1bHRzXyA9IGZ1bmN0aW9uKCkgewogICAgdGhpcy5yb3V0ZUlkID0gbnVsbDsKICB9OwogIE1lZGlhUm91dGVQcm92aWRlcl9EZXRhY2hSb3V0ZV9QYXJhbXMucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfRGV0YWNoUm91dGVfUGFyYW1zLnZhbGlkYXRlID0gZnVuY3Rpb24obWVzc2FnZVZhbGlkYXRvciwgb2Zmc2V0KSB7CiAgICB2YXIgZXJyOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdEhlYWRlcihvZmZzZXQsIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHZhciBrVmVyc2lvblNpemVzID0gWwogICAgICB7dmVyc2lvbjogMCwgbnVtQnl0ZXM6IDE2fQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZVByb3ZpZGVyX0RldGFjaFJvdXRlX1BhcmFtcy5yb3V0ZUlkCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDAsIGZhbHNlKQogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfRGV0YWNoUm91dGVfUGFyYW1zLmVuY29kZWRTaXplID0gY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA4OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfRGV0YWNoUm91dGVfUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1lZGlhUm91dGVQcm92aWRlcl9EZXRhY2hSb3V0ZV9QYXJhbXMoKTsKICAgIHZhciBudW1iZXJPZkJ5dGVzID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YXIgdmVyc2lvbiA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFsLnJvdXRlSWQgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5TdHJpbmcpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfRGV0YWNoUm91dGVfUGFyYW1zLmVuY29kZSA9IGZ1bmN0aW9uKGVuY29kZXIsIHZhbCkgewogICAgdmFyIHBhY2tlZDsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoTWVkaWFSb3V0ZVByb3ZpZGVyX0RldGFjaFJvdXRlX1BhcmFtcy5lbmNvZGVkU2l6ZSk7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKDApOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nLCB2YWwucm91dGVJZCk7CiAgfTsKICBmdW5jdGlvbiBNZWRpYVJvdXRlUHJvdmlkZXJfRW5hYmxlTWRuc0Rpc2NvdmVyeV9QYXJhbXModmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBNZWRpYVJvdXRlUHJvdmlkZXJfRW5hYmxlTWRuc0Rpc2NvdmVyeV9QYXJhbXMucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICB9OwogIE1lZGlhUm91dGVQcm92aWRlcl9FbmFibGVNZG5zRGlzY292ZXJ5X1BhcmFtcy5wcm90b3R5cGUuaW5pdEZpZWxkc18gPSBmdW5jdGlvbihmaWVsZHMpIHsKICAgIGZvcih2YXIgZmllbGQgaW4gZmllbGRzKSB7CiAgICAgICAgaWYgKHRoaXMuaGFzT3duUHJvcGVydHkoZmllbGQpKQogICAgICAgICAgdGhpc1tmaWVsZF0gPSBmaWVsZHNbZmllbGRdOwogICAgfQogIH07CgogIE1lZGlhUm91dGVQcm92aWRlcl9FbmFibGVNZG5zRGlzY292ZXJ5X1BhcmFtcy52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiA4fQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIE1lZGlhUm91dGVQcm92aWRlcl9FbmFibGVNZG5zRGlzY292ZXJ5X1BhcmFtcy5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMDsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX0VuYWJsZU1kbnNEaXNjb3ZlcnlfUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1lZGlhUm91dGVQcm92aWRlcl9FbmFibGVNZG5zRGlzY292ZXJ5X1BhcmFtcygpOwogICAgdmFyIG51bWJlck9mQnl0ZXMgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhciB2ZXJzaW9uID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICByZXR1cm4gdmFsOwogIH07CgogIE1lZGlhUm91dGVQcm92aWRlcl9FbmFibGVNZG5zRGlzY292ZXJ5X1BhcmFtcy5lbmNvZGUgPSBmdW5jdGlvbihlbmNvZGVyLCB2YWwpIHsKICAgIHZhciBwYWNrZWQ7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKE1lZGlhUm91dGVQcm92aWRlcl9FbmFibGVNZG5zRGlzY292ZXJ5X1BhcmFtcy5lbmNvZGVkU2l6ZSk7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKDApOwogIH07CiAgZnVuY3Rpb24gTWVkaWFSb3V0ZVByb3ZpZGVyX1VwZGF0ZU1lZGlhU2lua3NfUGFyYW1zKHZhbHVlcykgewogICAgdGhpcy5pbml0RGVmYXVsdHNfKCk7CiAgICB0aGlzLmluaXRGaWVsZHNfKHZhbHVlcyk7CiAgfQoKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1VwZGF0ZU1lZGlhU2lua3NfUGFyYW1zLnByb3RvdHlwZS5pbml0RGVmYXVsdHNfID0gZnVuY3Rpb24oKSB7CiAgICB0aGlzLm1lZGlhU291cmNlID0gbnVsbDsKICB9OwogIE1lZGlhUm91dGVQcm92aWRlcl9VcGRhdGVNZWRpYVNpbmtzX1BhcmFtcy5wcm90b3R5cGUuaW5pdEZpZWxkc18gPSBmdW5jdGlvbihmaWVsZHMpIHsKICAgIGZvcih2YXIgZmllbGQgaW4gZmllbGRzKSB7CiAgICAgICAgaWYgKHRoaXMuaGFzT3duUHJvcGVydHkoZmllbGQpKQogICAgICAgICAgdGhpc1tmaWVsZF0gPSBmaWVsZHNbZmllbGRdOwogICAgfQogIH07CgogIE1lZGlhUm91dGVQcm92aWRlcl9VcGRhdGVNZWRpYVNpbmtzX1BhcmFtcy52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiAxNn0KICAgIF07CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0VmVyc2lvbihvZmZzZXQsIGtWZXJzaW9uU2l6ZXMpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhUm91dGVQcm92aWRlcl9VcGRhdGVNZWRpYVNpbmtzX1BhcmFtcy5tZWRpYVNvdXJjZQogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cmluZ1BvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAwLCBmYWxzZSkKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1VwZGF0ZU1lZGlhU2lua3NfUGFyYW1zLmVuY29kZWRTaXplID0gY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA4OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfVXBkYXRlTWVkaWFTaW5rc19QYXJhbXMuZGVjb2RlID0gZnVuY3Rpb24oZGVjb2RlcikgewogICAgdmFyIHBhY2tlZDsKICAgIHZhciB2YWwgPSBuZXcgTWVkaWFSb3V0ZVByb3ZpZGVyX1VwZGF0ZU1lZGlhU2lua3NfUGFyYW1zKCk7CiAgICB2YXIgbnVtYmVyT2ZCeXRlcyA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFyIHZlcnNpb24gPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhbC5tZWRpYVNvdXJjZSA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLlN0cmluZyk7CiAgICByZXR1cm4gdmFsOwogIH07CgogIE1lZGlhUm91dGVQcm92aWRlcl9VcGRhdGVNZWRpYVNpbmtzX1BhcmFtcy5lbmNvZGUgPSBmdW5jdGlvbihlbmNvZGVyLCB2YWwpIHsKICAgIHZhciBwYWNrZWQ7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKE1lZGlhUm91dGVQcm92aWRlcl9VcGRhdGVNZWRpYVNpbmtzX1BhcmFtcy5lbmNvZGVkU2l6ZSk7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKDApOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nLCB2YWwubWVkaWFTb3VyY2UpOwogIH07CiAgZnVuY3Rpb24gTWVkaWFSb3V0ZVByb3ZpZGVyX1NlYXJjaFNpbmtzX1BhcmFtcyh2YWx1ZXMpIHsKICAgIHRoaXMuaW5pdERlZmF1bHRzXygpOwogICAgdGhpcy5pbml0RmllbGRzXyh2YWx1ZXMpOwogIH0KCgogIE1lZGlhUm91dGVQcm92aWRlcl9TZWFyY2hTaW5rc19QYXJhbXMucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMuc2lua0lkID0gbnVsbDsKICAgIHRoaXMubWVkaWFTb3VyY2UgPSBudWxsOwogICAgdGhpcy5zZWFyY2hDcml0ZXJpYSA9IG51bGw7CiAgfTsKICBNZWRpYVJvdXRlUHJvdmlkZXJfU2VhcmNoU2lua3NfUGFyYW1zLnByb3RvdHlwZS5pbml0RmllbGRzXyA9IGZ1bmN0aW9uKGZpZWxkcykgewogICAgZm9yKHZhciBmaWVsZCBpbiBmaWVsZHMpIHsKICAgICAgICBpZiAodGhpcy5oYXNPd25Qcm9wZXJ0eShmaWVsZCkpCiAgICAgICAgICB0aGlzW2ZpZWxkXSA9IGZpZWxkc1tmaWVsZF07CiAgICB9CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1NlYXJjaFNpbmtzX1BhcmFtcy52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiAzMn0KICAgIF07CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0VmVyc2lvbihvZmZzZXQsIGtWZXJzaW9uU2l6ZXMpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhUm91dGVQcm92aWRlcl9TZWFyY2hTaW5rc19QYXJhbXMuc2lua0lkCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDAsIGZhbHNlKQogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhUm91dGVQcm92aWRlcl9TZWFyY2hTaW5rc19QYXJhbXMubWVkaWFTb3VyY2UKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJpbmdQb2ludGVyKG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgOCwgZmFsc2UpCiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZVByb3ZpZGVyX1NlYXJjaFNpbmtzX1BhcmFtcy5zZWFyY2hDcml0ZXJpYQogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFBvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAxNiwgU2lua1NlYXJjaENyaXRlcmlhLCBmYWxzZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIE1lZGlhUm91dGVQcm92aWRlcl9TZWFyY2hTaW5rc19QYXJhbXMuZW5jb2RlZFNpemUgPSBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDI0OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfU2VhcmNoU2lua3NfUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1lZGlhUm91dGVQcm92aWRlcl9TZWFyY2hTaW5rc19QYXJhbXMoKTsKICAgIHZhciBudW1iZXJPZkJ5dGVzID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YXIgdmVyc2lvbiA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFsLnNpbmtJZCA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLlN0cmluZyk7CiAgICB2YWwubWVkaWFTb3VyY2UgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5TdHJpbmcpOwogICAgdmFsLnNlYXJjaENyaXRlcmlhID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3RQb2ludGVyKFNpbmtTZWFyY2hDcml0ZXJpYSk7CiAgICByZXR1cm4gdmFsOwogIH07CgogIE1lZGlhUm91dGVQcm92aWRlcl9TZWFyY2hTaW5rc19QYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNZWRpYVJvdXRlUHJvdmlkZXJfU2VhcmNoU2lua3NfUGFyYW1zLmVuY29kZWRTaXplKTsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoMCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5TdHJpbmcsIHZhbC5zaW5rSWQpOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nLCB2YWwubWVkaWFTb3VyY2UpOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3RQb2ludGVyKFNpbmtTZWFyY2hDcml0ZXJpYSwgdmFsLnNlYXJjaENyaXRlcmlhKTsKICB9OwogIGZ1bmN0aW9uIE1lZGlhUm91dGVQcm92aWRlcl9TZWFyY2hTaW5rc19SZXNwb25zZVBhcmFtcyh2YWx1ZXMpIHsKICAgIHRoaXMuaW5pdERlZmF1bHRzXygpOwogICAgdGhpcy5pbml0RmllbGRzXyh2YWx1ZXMpOwogIH0KCgogIE1lZGlhUm91dGVQcm92aWRlcl9TZWFyY2hTaW5rc19SZXNwb25zZVBhcmFtcy5wcm90b3R5cGUuaW5pdERlZmF1bHRzXyA9IGZ1bmN0aW9uKCkgewogICAgdGhpcy5zaW5rSWQgPSBudWxsOwogIH07CiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1NlYXJjaFNpbmtzX1Jlc3BvbnNlUGFyYW1zLnByb3RvdHlwZS5pbml0RmllbGRzXyA9IGZ1bmN0aW9uKGZpZWxkcykgewogICAgZm9yKHZhciBmaWVsZCBpbiBmaWVsZHMpIHsKICAgICAgICBpZiAodGhpcy5oYXNPd25Qcm9wZXJ0eShmaWVsZCkpCiAgICAgICAgICB0aGlzW2ZpZWxkXSA9IGZpZWxkc1tmaWVsZF07CiAgICB9CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1NlYXJjaFNpbmtzX1Jlc3BvbnNlUGFyYW1zLnZhbGlkYXRlID0gZnVuY3Rpb24obWVzc2FnZVZhbGlkYXRvciwgb2Zmc2V0KSB7CiAgICB2YXIgZXJyOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdEhlYWRlcihvZmZzZXQsIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHZhciBrVmVyc2lvblNpemVzID0gWwogICAgICB7dmVyc2lvbjogMCwgbnVtQnl0ZXM6IDE2fQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZVByb3ZpZGVyX1NlYXJjaFNpbmtzX1Jlc3BvbnNlUGFyYW1zLnNpbmtJZAogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cmluZ1BvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAwLCBmYWxzZSkKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1NlYXJjaFNpbmtzX1Jlc3BvbnNlUGFyYW1zLmVuY29kZWRTaXplID0gY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA4OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfU2VhcmNoU2lua3NfUmVzcG9uc2VQYXJhbXMuZGVjb2RlID0gZnVuY3Rpb24oZGVjb2RlcikgewogICAgdmFyIHBhY2tlZDsKICAgIHZhciB2YWwgPSBuZXcgTWVkaWFSb3V0ZVByb3ZpZGVyX1NlYXJjaFNpbmtzX1Jlc3BvbnNlUGFyYW1zKCk7CiAgICB2YXIgbnVtYmVyT2ZCeXRlcyA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFyIHZlcnNpb24gPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhbC5zaW5rSWQgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5TdHJpbmcpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfU2VhcmNoU2lua3NfUmVzcG9uc2VQYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNZWRpYVJvdXRlUHJvdmlkZXJfU2VhcmNoU2lua3NfUmVzcG9uc2VQYXJhbXMuZW5jb2RlZFNpemUpOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMigwKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLlN0cmluZywgdmFsLnNpbmtJZCk7CiAgfTsKICBmdW5jdGlvbiBNZWRpYVJvdXRlUHJvdmlkZXJfUHJvdmlkZVNpbmtzX1BhcmFtcyh2YWx1ZXMpIHsKICAgIHRoaXMuaW5pdERlZmF1bHRzXygpOwogICAgdGhpcy5pbml0RmllbGRzXyh2YWx1ZXMpOwogIH0KCgogIE1lZGlhUm91dGVQcm92aWRlcl9Qcm92aWRlU2lua3NfUGFyYW1zLnByb3RvdHlwZS5pbml0RGVmYXVsdHNfID0gZnVuY3Rpb24oKSB7CiAgICB0aGlzLnByb3ZpZGVyTmFtZSA9IG51bGw7CiAgICB0aGlzLnNpbmtzID0gbnVsbDsKICB9OwogIE1lZGlhUm91dGVQcm92aWRlcl9Qcm92aWRlU2lua3NfUGFyYW1zLnByb3RvdHlwZS5pbml0RmllbGRzXyA9IGZ1bmN0aW9uKGZpZWxkcykgewogICAgZm9yKHZhciBmaWVsZCBpbiBmaWVsZHMpIHsKICAgICAgICBpZiAodGhpcy5oYXNPd25Qcm9wZXJ0eShmaWVsZCkpCiAgICAgICAgICB0aGlzW2ZpZWxkXSA9IGZpZWxkc1tmaWVsZF07CiAgICB9CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1Byb3ZpZGVTaW5rc19QYXJhbXMudmFsaWRhdGUgPSBmdW5jdGlvbihtZXNzYWdlVmFsaWRhdG9yLCBvZmZzZXQpIHsKICAgIHZhciBlcnI7CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0SGVhZGVyKG9mZnNldCwgY29kZWMua1N0cnVjdEhlYWRlclNpemUpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgdmFyIGtWZXJzaW9uU2l6ZXMgPSBbCiAgICAgIHt2ZXJzaW9uOiAwLCBudW1CeXRlczogMjR9CiAgICBdOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFZlcnNpb24ob2Zmc2V0LCBrVmVyc2lvblNpemVzKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBNZWRpYVJvdXRlUHJvdmlkZXJfUHJvdmlkZVNpbmtzX1BhcmFtcy5wcm92aWRlck5hbWUKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJpbmdQb2ludGVyKG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMCwgZmFsc2UpCiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZVByb3ZpZGVyX1Byb3ZpZGVTaW5rc19QYXJhbXMuc2lua3MKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVBcnJheVBvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA4LCA4LCBuZXcgY29kZWMuUG9pbnRlclRvKE1lZGlhU2luayksIGZhbHNlLCBbMF0sIDApOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfUHJvdmlkZVNpbmtzX1BhcmFtcy5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMTY7CgogIE1lZGlhUm91dGVQcm92aWRlcl9Qcm92aWRlU2lua3NfUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1lZGlhUm91dGVQcm92aWRlcl9Qcm92aWRlU2lua3NfUGFyYW1zKCk7CiAgICB2YXIgbnVtYmVyT2ZCeXRlcyA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFyIHZlcnNpb24gPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhbC5wcm92aWRlck5hbWUgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5TdHJpbmcpOwogICAgdmFsLnNpbmtzID0gZGVjb2Rlci5kZWNvZGVBcnJheVBvaW50ZXIobmV3IGNvZGVjLlBvaW50ZXJUbyhNZWRpYVNpbmspKTsKICAgIHJldHVybiB2YWw7CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX1Byb3ZpZGVTaW5rc19QYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNZWRpYVJvdXRlUHJvdmlkZXJfUHJvdmlkZVNpbmtzX1BhcmFtcy5lbmNvZGVkU2l6ZSk7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKDApOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nLCB2YWwucHJvdmlkZXJOYW1lKTsKICAgIGVuY29kZXIuZW5jb2RlQXJyYXlQb2ludGVyKG5ldyBjb2RlYy5Qb2ludGVyVG8oTWVkaWFTaW5rKSwgdmFsLnNpbmtzKTsKICB9OwogIGZ1bmN0aW9uIE1lZGlhUm91dGVQcm92aWRlcl9DcmVhdGVNZWRpYVJvdXRlQ29udHJvbGxlcl9QYXJhbXModmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlTWVkaWFSb3V0ZUNvbnRyb2xsZXJfUGFyYW1zLnByb3RvdHlwZS5pbml0RGVmYXVsdHNfID0gZnVuY3Rpb24oKSB7CiAgICB0aGlzLnJvdXRlSWQgPSBudWxsOwogICAgdGhpcy5tZWRpYUNvbnRyb2xsZXIgPSBuZXcgYmluZGluZ3MuSW50ZXJmYWNlUmVxdWVzdCgpOwogICAgdGhpcy5vYnNlcnZlciA9IG5ldyBtZWRpYV9zdGF0dXMkLk1lZGlhU3RhdHVzT2JzZXJ2ZXJQdHIoKTsKICB9OwogIE1lZGlhUm91dGVQcm92aWRlcl9DcmVhdGVNZWRpYVJvdXRlQ29udHJvbGxlcl9QYXJhbXMucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlTWVkaWFSb3V0ZUNvbnRyb2xsZXJfUGFyYW1zLnZhbGlkYXRlID0gZnVuY3Rpb24obWVzc2FnZVZhbGlkYXRvciwgb2Zmc2V0KSB7CiAgICB2YXIgZXJyOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdEhlYWRlcihvZmZzZXQsIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHZhciBrVmVyc2lvblNpemVzID0gWwogICAgICB7dmVyc2lvbjogMCwgbnVtQnl0ZXM6IDMyfQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZVByb3ZpZGVyX0NyZWF0ZU1lZGlhUm91dGVDb250cm9sbGVyX1BhcmFtcy5yb3V0ZUlkCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDAsIGZhbHNlKQogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhUm91dGVQcm92aWRlcl9DcmVhdGVNZWRpYVJvdXRlQ29udHJvbGxlcl9QYXJhbXMubWVkaWFDb250cm9sbGVyCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlSW50ZXJmYWNlUmVxdWVzdChvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDgsIGZhbHNlKQogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhUm91dGVQcm92aWRlcl9DcmVhdGVNZWRpYVJvdXRlQ29udHJvbGxlcl9QYXJhbXMub2JzZXJ2ZXIKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVJbnRlcmZhY2Uob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAxMiwgZmFsc2UpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlTWVkaWFSb3V0ZUNvbnRyb2xsZXJfUGFyYW1zLmVuY29kZWRTaXplID0gY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAyNDsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX0NyZWF0ZU1lZGlhUm91dGVDb250cm9sbGVyX1BhcmFtcy5kZWNvZGUgPSBmdW5jdGlvbihkZWNvZGVyKSB7CiAgICB2YXIgcGFja2VkOwogICAgdmFyIHZhbCA9IG5ldyBNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlTWVkaWFSb3V0ZUNvbnRyb2xsZXJfUGFyYW1zKCk7CiAgICB2YXIgbnVtYmVyT2ZCeXRlcyA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFyIHZlcnNpb24gPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhbC5yb3V0ZUlkID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nKTsKICAgIHZhbC5tZWRpYUNvbnRyb2xsZXIgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5JbnRlcmZhY2VSZXF1ZXN0KTsKICAgIHZhbC5vYnNlcnZlciA9IGRlY29kZXIuZGVjb2RlU3RydWN0KG5ldyBjb2RlYy5JbnRlcmZhY2UobWVkaWFfc3RhdHVzJC5NZWRpYVN0YXR1c09ic2VydmVyUHRyKSk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICByZXR1cm4gdmFsOwogIH07CgogIE1lZGlhUm91dGVQcm92aWRlcl9DcmVhdGVNZWRpYVJvdXRlQ29udHJvbGxlcl9QYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlTWVkaWFSb3V0ZUNvbnRyb2xsZXJfUGFyYW1zLmVuY29kZWRTaXplKTsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoMCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5TdHJpbmcsIHZhbC5yb3V0ZUlkKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLkludGVyZmFjZVJlcXVlc3QsIHZhbC5tZWRpYUNvbnRyb2xsZXIpOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QobmV3IGNvZGVjLkludGVyZmFjZShtZWRpYV9zdGF0dXMkLk1lZGlhU3RhdHVzT2JzZXJ2ZXJQdHIpLCB2YWwub2JzZXJ2ZXIpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogIH07CiAgZnVuY3Rpb24gTWVkaWFSb3V0ZVByb3ZpZGVyX0NyZWF0ZU1lZGlhUm91dGVDb250cm9sbGVyX1Jlc3BvbnNlUGFyYW1zKHZhbHVlcykgewogICAgdGhpcy5pbml0RGVmYXVsdHNfKCk7CiAgICB0aGlzLmluaXRGaWVsZHNfKHZhbHVlcyk7CiAgfQoKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX0NyZWF0ZU1lZGlhUm91dGVDb250cm9sbGVyX1Jlc3BvbnNlUGFyYW1zLnByb3RvdHlwZS5pbml0RGVmYXVsdHNfID0gZnVuY3Rpb24oKSB7CiAgICB0aGlzLnN1Y2Nlc3MgPSBmYWxzZTsKICB9OwogIE1lZGlhUm91dGVQcm92aWRlcl9DcmVhdGVNZWRpYVJvdXRlQ29udHJvbGxlcl9SZXNwb25zZVBhcmFtcy5wcm90b3R5cGUuaW5pdEZpZWxkc18gPSBmdW5jdGlvbihmaWVsZHMpIHsKICAgIGZvcih2YXIgZmllbGQgaW4gZmllbGRzKSB7CiAgICAgICAgaWYgKHRoaXMuaGFzT3duUHJvcGVydHkoZmllbGQpKQogICAgICAgICAgdGhpc1tmaWVsZF0gPSBmaWVsZHNbZmllbGRdOwogICAgfQogIH07CgogIE1lZGlhUm91dGVQcm92aWRlcl9DcmVhdGVNZWRpYVJvdXRlQ29udHJvbGxlcl9SZXNwb25zZVBhcmFtcy52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiAxNn0KICAgIF07CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0VmVyc2lvbihvZmZzZXQsIGtWZXJzaW9uU2l6ZXMpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyX0NyZWF0ZU1lZGlhUm91dGVDb250cm9sbGVyX1Jlc3BvbnNlUGFyYW1zLmVuY29kZWRTaXplID0gY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA4OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlTWVkaWFSb3V0ZUNvbnRyb2xsZXJfUmVzcG9uc2VQYXJhbXMuZGVjb2RlID0gZnVuY3Rpb24oZGVjb2RlcikgewogICAgdmFyIHBhY2tlZDsKICAgIHZhciB2YWwgPSBuZXcgTWVkaWFSb3V0ZVByb3ZpZGVyX0NyZWF0ZU1lZGlhUm91dGVDb250cm9sbGVyX1Jlc3BvbnNlUGFyYW1zKCk7CiAgICB2YXIgbnVtYmVyT2ZCeXRlcyA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFyIHZlcnNpb24gPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHBhY2tlZCA9IGRlY29kZXIucmVhZFVpbnQ4KCk7CiAgICB2YWwuc3VjY2VzcyA9IChwYWNrZWQgPj4gMCkgJiAxID8gdHJ1ZSA6IGZhbHNlOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlTWVkaWFSb3V0ZUNvbnRyb2xsZXJfUmVzcG9uc2VQYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlTWVkaWFSb3V0ZUNvbnRyb2xsZXJfUmVzcG9uc2VQYXJhbXMuZW5jb2RlZFNpemUpOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMigwKTsKICAgIHBhY2tlZCA9IDA7CiAgICBwYWNrZWQgfD0gKHZhbC5zdWNjZXNzICYgMSkgPDwgMAogICAgZW5jb2Rlci53cml0ZVVpbnQ4KHBhY2tlZCk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgfTsKICBmdW5jdGlvbiBNZWRpYVJvdXRlcl9SZWdpc3Rlck1lZGlhUm91dGVQcm92aWRlcl9QYXJhbXModmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBNZWRpYVJvdXRlcl9SZWdpc3Rlck1lZGlhUm91dGVQcm92aWRlcl9QYXJhbXMucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMucHJvdmlkZXJJZCA9IDA7CiAgICB0aGlzLm1lZGlhUm91dGVyUHJvdmlkZXIgPSBuZXcgTWVkaWFSb3V0ZVByb3ZpZGVyUHRyKCk7CiAgfTsKICBNZWRpYVJvdXRlcl9SZWdpc3Rlck1lZGlhUm91dGVQcm92aWRlcl9QYXJhbXMucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNZWRpYVJvdXRlcl9SZWdpc3Rlck1lZGlhUm91dGVQcm92aWRlcl9QYXJhbXMudmFsaWRhdGUgPSBmdW5jdGlvbihtZXNzYWdlVmFsaWRhdG9yLCBvZmZzZXQpIHsKICAgIHZhciBlcnI7CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0SGVhZGVyKG9mZnNldCwgY29kZWMua1N0cnVjdEhlYWRlclNpemUpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgdmFyIGtWZXJzaW9uU2l6ZXMgPSBbCiAgICAgIHt2ZXJzaW9uOiAwLCBudW1CeXRlczogMjR9CiAgICBdOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFZlcnNpb24ob2Zmc2V0LCBrVmVyc2lvblNpemVzKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBNZWRpYVJvdXRlcl9SZWdpc3Rlck1lZGlhUm91dGVQcm92aWRlcl9QYXJhbXMucHJvdmlkZXJJZAogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZUVudW0ob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAwLCBNZWRpYVJvdXRlUHJvdmlkZXIuSWQpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhUm91dGVyX1JlZ2lzdGVyTWVkaWFSb3V0ZVByb3ZpZGVyX1BhcmFtcy5tZWRpYVJvdXRlclByb3ZpZGVyCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlSW50ZXJmYWNlKG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgNCwgZmFsc2UpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKICB9OwoKICBNZWRpYVJvdXRlcl9SZWdpc3Rlck1lZGlhUm91dGVQcm92aWRlcl9QYXJhbXMuZW5jb2RlZFNpemUgPSBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDE2OwoKICBNZWRpYVJvdXRlcl9SZWdpc3Rlck1lZGlhUm91dGVQcm92aWRlcl9QYXJhbXMuZGVjb2RlID0gZnVuY3Rpb24oZGVjb2RlcikgewogICAgdmFyIHBhY2tlZDsKICAgIHZhciB2YWwgPSBuZXcgTWVkaWFSb3V0ZXJfUmVnaXN0ZXJNZWRpYVJvdXRlUHJvdmlkZXJfUGFyYW1zKCk7CiAgICB2YXIgbnVtYmVyT2ZCeXRlcyA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFyIHZlcnNpb24gPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhbC5wcm92aWRlcklkID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuSW50MzIpOwogICAgdmFsLm1lZGlhUm91dGVyUHJvdmlkZXIgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChuZXcgY29kZWMuSW50ZXJmYWNlKE1lZGlhUm91dGVQcm92aWRlclB0cikpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBNZWRpYVJvdXRlcl9SZWdpc3Rlck1lZGlhUm91dGVQcm92aWRlcl9QYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNZWRpYVJvdXRlcl9SZWdpc3Rlck1lZGlhUm91dGVQcm92aWRlcl9QYXJhbXMuZW5jb2RlZFNpemUpOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMigwKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLkludDMyLCB2YWwucHJvdmlkZXJJZCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChuZXcgY29kZWMuSW50ZXJmYWNlKE1lZGlhUm91dGVQcm92aWRlclB0ciksIHZhbC5tZWRpYVJvdXRlclByb3ZpZGVyKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICB9OwogIGZ1bmN0aW9uIE1lZGlhUm91dGVyX1JlZ2lzdGVyTWVkaWFSb3V0ZVByb3ZpZGVyX1Jlc3BvbnNlUGFyYW1zKHZhbHVlcykgewogICAgdGhpcy5pbml0RGVmYXVsdHNfKCk7CiAgICB0aGlzLmluaXRGaWVsZHNfKHZhbHVlcyk7CiAgfQoKCiAgTWVkaWFSb3V0ZXJfUmVnaXN0ZXJNZWRpYVJvdXRlUHJvdmlkZXJfUmVzcG9uc2VQYXJhbXMucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMuaW5zdGFuY2VJZCA9IG51bGw7CiAgICB0aGlzLmNvbmZpZyA9IG51bGw7CiAgfTsKICBNZWRpYVJvdXRlcl9SZWdpc3Rlck1lZGlhUm91dGVQcm92aWRlcl9SZXNwb25zZVBhcmFtcy5wcm90b3R5cGUuaW5pdEZpZWxkc18gPSBmdW5jdGlvbihmaWVsZHMpIHsKICAgIGZvcih2YXIgZmllbGQgaW4gZmllbGRzKSB7CiAgICAgICAgaWYgKHRoaXMuaGFzT3duUHJvcGVydHkoZmllbGQpKQogICAgICAgICAgdGhpc1tmaWVsZF0gPSBmaWVsZHNbZmllbGRdOwogICAgfQogIH07CgogIE1lZGlhUm91dGVyX1JlZ2lzdGVyTWVkaWFSb3V0ZVByb3ZpZGVyX1Jlc3BvbnNlUGFyYW1zLnZhbGlkYXRlID0gZnVuY3Rpb24obWVzc2FnZVZhbGlkYXRvciwgb2Zmc2V0KSB7CiAgICB2YXIgZXJyOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdEhlYWRlcihvZmZzZXQsIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHZhciBrVmVyc2lvblNpemVzID0gWwogICAgICB7dmVyc2lvbjogMCwgbnVtQnl0ZXM6IDI0fQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZXJfUmVnaXN0ZXJNZWRpYVJvdXRlUHJvdmlkZXJfUmVzcG9uc2VQYXJhbXMuaW5zdGFuY2VJZAogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cmluZ1BvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAwLCBmYWxzZSkKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBNZWRpYVJvdXRlcl9SZWdpc3Rlck1lZGlhUm91dGVQcm92aWRlcl9SZXNwb25zZVBhcmFtcy5jb25maWcKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RQb2ludGVyKG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgOCwgTWVkaWFSb3V0ZVByb3ZpZGVyQ29uZmlnLCBmYWxzZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIE1lZGlhUm91dGVyX1JlZ2lzdGVyTWVkaWFSb3V0ZVByb3ZpZGVyX1Jlc3BvbnNlUGFyYW1zLmVuY29kZWRTaXplID0gY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAxNjsKCiAgTWVkaWFSb3V0ZXJfUmVnaXN0ZXJNZWRpYVJvdXRlUHJvdmlkZXJfUmVzcG9uc2VQYXJhbXMuZGVjb2RlID0gZnVuY3Rpb24oZGVjb2RlcikgewogICAgdmFyIHBhY2tlZDsKICAgIHZhciB2YWwgPSBuZXcgTWVkaWFSb3V0ZXJfUmVnaXN0ZXJNZWRpYVJvdXRlUHJvdmlkZXJfUmVzcG9uc2VQYXJhbXMoKTsKICAgIHZhciBudW1iZXJPZkJ5dGVzID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YXIgdmVyc2lvbiA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFsLmluc3RhbmNlSWQgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5TdHJpbmcpOwogICAgdmFsLmNvbmZpZyA9IGRlY29kZXIuZGVjb2RlU3RydWN0UG9pbnRlcihNZWRpYVJvdXRlUHJvdmlkZXJDb25maWcpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBNZWRpYVJvdXRlcl9SZWdpc3Rlck1lZGlhUm91dGVQcm92aWRlcl9SZXNwb25zZVBhcmFtcy5lbmNvZGUgPSBmdW5jdGlvbihlbmNvZGVyLCB2YWwpIHsKICAgIHZhciBwYWNrZWQ7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKE1lZGlhUm91dGVyX1JlZ2lzdGVyTWVkaWFSb3V0ZVByb3ZpZGVyX1Jlc3BvbnNlUGFyYW1zLmVuY29kZWRTaXplKTsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoMCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5TdHJpbmcsIHZhbC5pbnN0YW5jZUlkKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0UG9pbnRlcihNZWRpYVJvdXRlUHJvdmlkZXJDb25maWcsIHZhbC5jb25maWcpOwogIH07CiAgZnVuY3Rpb24gTWVkaWFSb3V0ZXJfT25TaW5rc1JlY2VpdmVkX1BhcmFtcyh2YWx1ZXMpIHsKICAgIHRoaXMuaW5pdERlZmF1bHRzXygpOwogICAgdGhpcy5pbml0RmllbGRzXyh2YWx1ZXMpOwogIH0KCgogIE1lZGlhUm91dGVyX09uU2lua3NSZWNlaXZlZF9QYXJhbXMucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMucHJvdmlkZXJJZCA9IDA7CiAgICB0aGlzLm1lZGlhU291cmNlID0gbnVsbDsKICAgIHRoaXMuc2lua3MgPSBudWxsOwogICAgdGhpcy5vcmlnaW5zID0gbnVsbDsKICB9OwogIE1lZGlhUm91dGVyX09uU2lua3NSZWNlaXZlZF9QYXJhbXMucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNZWRpYVJvdXRlcl9PblNpbmtzUmVjZWl2ZWRfUGFyYW1zLnZhbGlkYXRlID0gZnVuY3Rpb24obWVzc2FnZVZhbGlkYXRvciwgb2Zmc2V0KSB7CiAgICB2YXIgZXJyOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdEhlYWRlcihvZmZzZXQsIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHZhciBrVmVyc2lvblNpemVzID0gWwogICAgICB7dmVyc2lvbjogMCwgbnVtQnl0ZXM6IDQwfQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZXJfT25TaW5rc1JlY2VpdmVkX1BhcmFtcy5wcm92aWRlcklkCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlRW51bShvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDAsIE1lZGlhUm91dGVQcm92aWRlci5JZCk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZXJfT25TaW5rc1JlY2VpdmVkX1BhcmFtcy5tZWRpYVNvdXJjZQogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cmluZ1BvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA4LCBmYWxzZSkKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBNZWRpYVJvdXRlcl9PblNpbmtzUmVjZWl2ZWRfUGFyYW1zLnNpbmtzCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlQXJyYXlQb2ludGVyKG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMTYsIDgsIG5ldyBjb2RlYy5Qb2ludGVyVG8oTWVkaWFTaW5rKSwgZmFsc2UsIFswXSwgMCk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZXJfT25TaW5rc1JlY2VpdmVkX1BhcmFtcy5vcmlnaW5zCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlQXJyYXlQb2ludGVyKG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMjQsIDgsIG5ldyBjb2RlYy5Qb2ludGVyVG8ob3JpZ2luJC5PcmlnaW4pLCBmYWxzZSwgWzBdLCAwKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgfTsKCiAgTWVkaWFSb3V0ZXJfT25TaW5rc1JlY2VpdmVkX1BhcmFtcy5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMzI7CgogIE1lZGlhUm91dGVyX09uU2lua3NSZWNlaXZlZF9QYXJhbXMuZGVjb2RlID0gZnVuY3Rpb24oZGVjb2RlcikgewogICAgdmFyIHBhY2tlZDsKICAgIHZhciB2YWwgPSBuZXcgTWVkaWFSb3V0ZXJfT25TaW5rc1JlY2VpdmVkX1BhcmFtcygpOwogICAgdmFyIG51bWJlck9mQnl0ZXMgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhciB2ZXJzaW9uID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YWwucHJvdmlkZXJJZCA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLkludDMyKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIHZhbC5tZWRpYVNvdXJjZSA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLlN0cmluZyk7CiAgICB2YWwuc2lua3MgPSBkZWNvZGVyLmRlY29kZUFycmF5UG9pbnRlcihuZXcgY29kZWMuUG9pbnRlclRvKE1lZGlhU2luaykpOwogICAgdmFsLm9yaWdpbnMgPSBkZWNvZGVyLmRlY29kZUFycmF5UG9pbnRlcihuZXcgY29kZWMuUG9pbnRlclRvKG9yaWdpbiQuT3JpZ2luKSk7CiAgICByZXR1cm4gdmFsOwogIH07CgogIE1lZGlhUm91dGVyX09uU2lua3NSZWNlaXZlZF9QYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNZWRpYVJvdXRlcl9PblNpbmtzUmVjZWl2ZWRfUGFyYW1zLmVuY29kZWRTaXplKTsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoMCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5JbnQzMiwgdmFsLnByb3ZpZGVySWQpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nLCB2YWwubWVkaWFTb3VyY2UpOwogICAgZW5jb2Rlci5lbmNvZGVBcnJheVBvaW50ZXIobmV3IGNvZGVjLlBvaW50ZXJUbyhNZWRpYVNpbmspLCB2YWwuc2lua3MpOwogICAgZW5jb2Rlci5lbmNvZGVBcnJheVBvaW50ZXIobmV3IGNvZGVjLlBvaW50ZXJUbyhvcmlnaW4kLk9yaWdpbiksIHZhbC5vcmlnaW5zKTsKICB9OwogIGZ1bmN0aW9uIE1lZGlhUm91dGVyX09uSXNzdWVfUGFyYW1zKHZhbHVlcykgewogICAgdGhpcy5pbml0RGVmYXVsdHNfKCk7CiAgICB0aGlzLmluaXRGaWVsZHNfKHZhbHVlcyk7CiAgfQoKCiAgTWVkaWFSb3V0ZXJfT25Jc3N1ZV9QYXJhbXMucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMuaXNzdWUgPSBudWxsOwogIH07CiAgTWVkaWFSb3V0ZXJfT25Jc3N1ZV9QYXJhbXMucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNZWRpYVJvdXRlcl9Pbklzc3VlX1BhcmFtcy52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiAxNn0KICAgIF07CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0VmVyc2lvbihvZmZzZXQsIGtWZXJzaW9uU2l6ZXMpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhUm91dGVyX09uSXNzdWVfUGFyYW1zLmlzc3VlCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0UG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDAsIElzc3VlLCBmYWxzZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIE1lZGlhUm91dGVyX09uSXNzdWVfUGFyYW1zLmVuY29kZWRTaXplID0gY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA4OwoKICBNZWRpYVJvdXRlcl9Pbklzc3VlX1BhcmFtcy5kZWNvZGUgPSBmdW5jdGlvbihkZWNvZGVyKSB7CiAgICB2YXIgcGFja2VkOwogICAgdmFyIHZhbCA9IG5ldyBNZWRpYVJvdXRlcl9Pbklzc3VlX1BhcmFtcygpOwogICAgdmFyIG51bWJlck9mQnl0ZXMgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhciB2ZXJzaW9uID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YWwuaXNzdWUgPSBkZWNvZGVyLmRlY29kZVN0cnVjdFBvaW50ZXIoSXNzdWUpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBNZWRpYVJvdXRlcl9Pbklzc3VlX1BhcmFtcy5lbmNvZGUgPSBmdW5jdGlvbihlbmNvZGVyLCB2YWwpIHsKICAgIHZhciBwYWNrZWQ7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKE1lZGlhUm91dGVyX09uSXNzdWVfUGFyYW1zLmVuY29kZWRTaXplKTsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoMCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdFBvaW50ZXIoSXNzdWUsIHZhbC5pc3N1ZSk7CiAgfTsKICBmdW5jdGlvbiBNZWRpYVJvdXRlcl9PblJvdXRlc1VwZGF0ZWRfUGFyYW1zKHZhbHVlcykgewogICAgdGhpcy5pbml0RGVmYXVsdHNfKCk7CiAgICB0aGlzLmluaXRGaWVsZHNfKHZhbHVlcyk7CiAgfQoKCiAgTWVkaWFSb3V0ZXJfT25Sb3V0ZXNVcGRhdGVkX1BhcmFtcy5wcm90b3R5cGUuaW5pdERlZmF1bHRzXyA9IGZ1bmN0aW9uKCkgewogICAgdGhpcy5wcm92aWRlcklkID0gMDsKICAgIHRoaXMucm91dGVzID0gbnVsbDsKICAgIHRoaXMubWVkaWFTb3VyY2UgPSBudWxsOwogICAgdGhpcy5qb2luYWJsZVJvdXRlSWRzID0gbnVsbDsKICB9OwogIE1lZGlhUm91dGVyX09uUm91dGVzVXBkYXRlZF9QYXJhbXMucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNZWRpYVJvdXRlcl9PblJvdXRlc1VwZGF0ZWRfUGFyYW1zLnZhbGlkYXRlID0gZnVuY3Rpb24obWVzc2FnZVZhbGlkYXRvciwgb2Zmc2V0KSB7CiAgICB2YXIgZXJyOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdEhlYWRlcihvZmZzZXQsIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHZhciBrVmVyc2lvblNpemVzID0gWwogICAgICB7dmVyc2lvbjogMCwgbnVtQnl0ZXM6IDQwfQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZXJfT25Sb3V0ZXNVcGRhdGVkX1BhcmFtcy5wcm92aWRlcklkCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlRW51bShvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDAsIE1lZGlhUm91dGVQcm92aWRlci5JZCk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZXJfT25Sb3V0ZXNVcGRhdGVkX1BhcmFtcy5yb3V0ZXMKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVBcnJheVBvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA4LCA4LCBuZXcgY29kZWMuUG9pbnRlclRvKE1lZGlhUm91dGUpLCBmYWxzZSwgWzBdLCAwKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBNZWRpYVJvdXRlcl9PblJvdXRlc1VwZGF0ZWRfUGFyYW1zLm1lZGlhU291cmNlCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDE2LCBmYWxzZSkKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBNZWRpYVJvdXRlcl9PblJvdXRlc1VwZGF0ZWRfUGFyYW1zLmpvaW5hYmxlUm91dGVJZHMKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVBcnJheVBvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAyNCwgOCwgY29kZWMuU3RyaW5nLCBmYWxzZSwgWzAsIDBdLCAwKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgfTsKCiAgTWVkaWFSb3V0ZXJfT25Sb3V0ZXNVcGRhdGVkX1BhcmFtcy5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMzI7CgogIE1lZGlhUm91dGVyX09uUm91dGVzVXBkYXRlZF9QYXJhbXMuZGVjb2RlID0gZnVuY3Rpb24oZGVjb2RlcikgewogICAgdmFyIHBhY2tlZDsKICAgIHZhciB2YWwgPSBuZXcgTWVkaWFSb3V0ZXJfT25Sb3V0ZXNVcGRhdGVkX1BhcmFtcygpOwogICAgdmFyIG51bWJlck9mQnl0ZXMgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhciB2ZXJzaW9uID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YWwucHJvdmlkZXJJZCA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLkludDMyKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIHZhbC5yb3V0ZXMgPSBkZWNvZGVyLmRlY29kZUFycmF5UG9pbnRlcihuZXcgY29kZWMuUG9pbnRlclRvKE1lZGlhUm91dGUpKTsKICAgIHZhbC5tZWRpYVNvdXJjZSA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLlN0cmluZyk7CiAgICB2YWwuam9pbmFibGVSb3V0ZUlkcyA9IGRlY29kZXIuZGVjb2RlQXJyYXlQb2ludGVyKGNvZGVjLlN0cmluZyk7CiAgICByZXR1cm4gdmFsOwogIH07CgogIE1lZGlhUm91dGVyX09uUm91dGVzVXBkYXRlZF9QYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNZWRpYVJvdXRlcl9PblJvdXRlc1VwZGF0ZWRfUGFyYW1zLmVuY29kZWRTaXplKTsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoMCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5JbnQzMiwgdmFsLnByb3ZpZGVySWQpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5lbmNvZGVBcnJheVBvaW50ZXIobmV3IGNvZGVjLlBvaW50ZXJUbyhNZWRpYVJvdXRlKSwgdmFsLnJvdXRlcyk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5TdHJpbmcsIHZhbC5tZWRpYVNvdXJjZSk7CiAgICBlbmNvZGVyLmVuY29kZUFycmF5UG9pbnRlcihjb2RlYy5TdHJpbmcsIHZhbC5qb2luYWJsZVJvdXRlSWRzKTsKICB9OwogIGZ1bmN0aW9uIE1lZGlhUm91dGVyX09uU2lua0F2YWlsYWJpbGl0eVVwZGF0ZWRfUGFyYW1zKHZhbHVlcykgewogICAgdGhpcy5pbml0RGVmYXVsdHNfKCk7CiAgICB0aGlzLmluaXRGaWVsZHNfKHZhbHVlcyk7CiAgfQoKCiAgTWVkaWFSb3V0ZXJfT25TaW5rQXZhaWxhYmlsaXR5VXBkYXRlZF9QYXJhbXMucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMucHJvdmlkZXJJZCA9IDA7CiAgICB0aGlzLmF2YWlsYWJpbGl0eSA9IDA7CiAgfTsKICBNZWRpYVJvdXRlcl9PblNpbmtBdmFpbGFiaWxpdHlVcGRhdGVkX1BhcmFtcy5wcm90b3R5cGUuaW5pdEZpZWxkc18gPSBmdW5jdGlvbihmaWVsZHMpIHsKICAgIGZvcih2YXIgZmllbGQgaW4gZmllbGRzKSB7CiAgICAgICAgaWYgKHRoaXMuaGFzT3duUHJvcGVydHkoZmllbGQpKQogICAgICAgICAgdGhpc1tmaWVsZF0gPSBmaWVsZHNbZmllbGRdOwogICAgfQogIH07CgogIE1lZGlhUm91dGVyX09uU2lua0F2YWlsYWJpbGl0eVVwZGF0ZWRfUGFyYW1zLnZhbGlkYXRlID0gZnVuY3Rpb24obWVzc2FnZVZhbGlkYXRvciwgb2Zmc2V0KSB7CiAgICB2YXIgZXJyOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdEhlYWRlcihvZmZzZXQsIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHZhciBrVmVyc2lvblNpemVzID0gWwogICAgICB7dmVyc2lvbjogMCwgbnVtQnl0ZXM6IDE2fQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZXJfT25TaW5rQXZhaWxhYmlsaXR5VXBkYXRlZF9QYXJhbXMucHJvdmlkZXJJZAogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZUVudW0ob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAwLCBNZWRpYVJvdXRlUHJvdmlkZXIuSWQpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhUm91dGVyX09uU2lua0F2YWlsYWJpbGl0eVVwZGF0ZWRfUGFyYW1zLmF2YWlsYWJpbGl0eQogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZUVudW0ob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA0LCBNZWRpYVJvdXRlci5TaW5rQXZhaWxhYmlsaXR5KTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgfTsKCiAgTWVkaWFSb3V0ZXJfT25TaW5rQXZhaWxhYmlsaXR5VXBkYXRlZF9QYXJhbXMuZW5jb2RlZFNpemUgPSBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDg7CgogIE1lZGlhUm91dGVyX09uU2lua0F2YWlsYWJpbGl0eVVwZGF0ZWRfUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1lZGlhUm91dGVyX09uU2lua0F2YWlsYWJpbGl0eVVwZGF0ZWRfUGFyYW1zKCk7CiAgICB2YXIgbnVtYmVyT2ZCeXRlcyA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFyIHZlcnNpb24gPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhbC5wcm92aWRlcklkID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuSW50MzIpOwogICAgdmFsLmF2YWlsYWJpbGl0eSA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLkludDMyKTsKICAgIHJldHVybiB2YWw7CiAgfTsKCiAgTWVkaWFSb3V0ZXJfT25TaW5rQXZhaWxhYmlsaXR5VXBkYXRlZF9QYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNZWRpYVJvdXRlcl9PblNpbmtBdmFpbGFiaWxpdHlVcGRhdGVkX1BhcmFtcy5lbmNvZGVkU2l6ZSk7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKDApOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuSW50MzIsIHZhbC5wcm92aWRlcklkKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLkludDMyLCB2YWwuYXZhaWxhYmlsaXR5KTsKICB9OwogIGZ1bmN0aW9uIE1lZGlhUm91dGVyX09uUHJlc2VudGF0aW9uQ29ubmVjdGlvblN0YXRlQ2hhbmdlZF9QYXJhbXModmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBNZWRpYVJvdXRlcl9PblByZXNlbnRhdGlvbkNvbm5lY3Rpb25TdGF0ZUNoYW5nZWRfUGFyYW1zLnByb3RvdHlwZS5pbml0RGVmYXVsdHNfID0gZnVuY3Rpb24oKSB7CiAgICB0aGlzLnJvdXRlSWQgPSBudWxsOwogICAgdGhpcy5zdGF0ZSA9IDA7CiAgfTsKICBNZWRpYVJvdXRlcl9PblByZXNlbnRhdGlvbkNvbm5lY3Rpb25TdGF0ZUNoYW5nZWRfUGFyYW1zLnByb3RvdHlwZS5pbml0RmllbGRzXyA9IGZ1bmN0aW9uKGZpZWxkcykgewogICAgZm9yKHZhciBmaWVsZCBpbiBmaWVsZHMpIHsKICAgICAgICBpZiAodGhpcy5oYXNPd25Qcm9wZXJ0eShmaWVsZCkpCiAgICAgICAgICB0aGlzW2ZpZWxkXSA9IGZpZWxkc1tmaWVsZF07CiAgICB9CiAgfTsKCiAgTWVkaWFSb3V0ZXJfT25QcmVzZW50YXRpb25Db25uZWN0aW9uU3RhdGVDaGFuZ2VkX1BhcmFtcy52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiAyNH0KICAgIF07CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0VmVyc2lvbihvZmZzZXQsIGtWZXJzaW9uU2l6ZXMpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhUm91dGVyX09uUHJlc2VudGF0aW9uQ29ubmVjdGlvblN0YXRlQ2hhbmdlZF9QYXJhbXMucm91dGVJZAogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cmluZ1BvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAwLCBmYWxzZSkKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBNZWRpYVJvdXRlcl9PblByZXNlbnRhdGlvbkNvbm5lY3Rpb25TdGF0ZUNoYW5nZWRfUGFyYW1zLnN0YXRlCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlRW51bShvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDgsIE1lZGlhUm91dGVyLlByZXNlbnRhdGlvbkNvbm5lY3Rpb25TdGF0ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIE1lZGlhUm91dGVyX09uUHJlc2VudGF0aW9uQ29ubmVjdGlvblN0YXRlQ2hhbmdlZF9QYXJhbXMuZW5jb2RlZFNpemUgPSBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDE2OwoKICBNZWRpYVJvdXRlcl9PblByZXNlbnRhdGlvbkNvbm5lY3Rpb25TdGF0ZUNoYW5nZWRfUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1lZGlhUm91dGVyX09uUHJlc2VudGF0aW9uQ29ubmVjdGlvblN0YXRlQ2hhbmdlZF9QYXJhbXMoKTsKICAgIHZhciBudW1iZXJPZkJ5dGVzID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YXIgdmVyc2lvbiA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFsLnJvdXRlSWQgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5TdHJpbmcpOwogICAgdmFsLnN0YXRlID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuSW50MzIpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBNZWRpYVJvdXRlcl9PblByZXNlbnRhdGlvbkNvbm5lY3Rpb25TdGF0ZUNoYW5nZWRfUGFyYW1zLmVuY29kZSA9IGZ1bmN0aW9uKGVuY29kZXIsIHZhbCkgewogICAgdmFyIHBhY2tlZDsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoTWVkaWFSb3V0ZXJfT25QcmVzZW50YXRpb25Db25uZWN0aW9uU3RhdGVDaGFuZ2VkX1BhcmFtcy5lbmNvZGVkU2l6ZSk7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKDApOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nLCB2YWwucm91dGVJZCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5JbnQzMiwgdmFsLnN0YXRlKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICB9OwogIGZ1bmN0aW9uIE1lZGlhUm91dGVyX09uUHJlc2VudGF0aW9uQ29ubmVjdGlvbkNsb3NlZF9QYXJhbXModmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBNZWRpYVJvdXRlcl9PblByZXNlbnRhdGlvbkNvbm5lY3Rpb25DbG9zZWRfUGFyYW1zLnByb3RvdHlwZS5pbml0RGVmYXVsdHNfID0gZnVuY3Rpb24oKSB7CiAgICB0aGlzLnJvdXRlSWQgPSBudWxsOwogICAgdGhpcy5yZWFzb24gPSAwOwogICAgdGhpcy5tZXNzYWdlID0gbnVsbDsKICB9OwogIE1lZGlhUm91dGVyX09uUHJlc2VudGF0aW9uQ29ubmVjdGlvbkNsb3NlZF9QYXJhbXMucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNZWRpYVJvdXRlcl9PblByZXNlbnRhdGlvbkNvbm5lY3Rpb25DbG9zZWRfUGFyYW1zLnZhbGlkYXRlID0gZnVuY3Rpb24obWVzc2FnZVZhbGlkYXRvciwgb2Zmc2V0KSB7CiAgICB2YXIgZXJyOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdEhlYWRlcihvZmZzZXQsIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHZhciBrVmVyc2lvblNpemVzID0gWwogICAgICB7dmVyc2lvbjogMCwgbnVtQnl0ZXM6IDMyfQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZXJfT25QcmVzZW50YXRpb25Db25uZWN0aW9uQ2xvc2VkX1BhcmFtcy5yb3V0ZUlkCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDAsIGZhbHNlKQogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhUm91dGVyX09uUHJlc2VudGF0aW9uQ29ubmVjdGlvbkNsb3NlZF9QYXJhbXMucmVhc29uCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlRW51bShvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDgsIE1lZGlhUm91dGVyLlByZXNlbnRhdGlvbkNvbm5lY3Rpb25DbG9zZVJlYXNvbik7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZXJfT25QcmVzZW50YXRpb25Db25uZWN0aW9uQ2xvc2VkX1BhcmFtcy5tZXNzYWdlCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDE2LCBmYWxzZSkKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgfTsKCiAgTWVkaWFSb3V0ZXJfT25QcmVzZW50YXRpb25Db25uZWN0aW9uQ2xvc2VkX1BhcmFtcy5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMjQ7CgogIE1lZGlhUm91dGVyX09uUHJlc2VudGF0aW9uQ29ubmVjdGlvbkNsb3NlZF9QYXJhbXMuZGVjb2RlID0gZnVuY3Rpb24oZGVjb2RlcikgewogICAgdmFyIHBhY2tlZDsKICAgIHZhciB2YWwgPSBuZXcgTWVkaWFSb3V0ZXJfT25QcmVzZW50YXRpb25Db25uZWN0aW9uQ2xvc2VkX1BhcmFtcygpOwogICAgdmFyIG51bWJlck9mQnl0ZXMgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhciB2ZXJzaW9uID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YWwucm91dGVJZCA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLlN0cmluZyk7CiAgICB2YWwucmVhc29uID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuSW50MzIpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgdmFsLm1lc3NhZ2UgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5TdHJpbmcpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBNZWRpYVJvdXRlcl9PblByZXNlbnRhdGlvbkNvbm5lY3Rpb25DbG9zZWRfUGFyYW1zLmVuY29kZSA9IGZ1bmN0aW9uKGVuY29kZXIsIHZhbCkgewogICAgdmFyIHBhY2tlZDsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoTWVkaWFSb3V0ZXJfT25QcmVzZW50YXRpb25Db25uZWN0aW9uQ2xvc2VkX1BhcmFtcy5lbmNvZGVkU2l6ZSk7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKDApOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nLCB2YWwucm91dGVJZCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5JbnQzMiwgdmFsLnJlYXNvbik7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5TdHJpbmcsIHZhbC5tZXNzYWdlKTsKICB9OwogIGZ1bmN0aW9uIE1lZGlhUm91dGVyX09uUm91dGVNZXNzYWdlc1JlY2VpdmVkX1BhcmFtcyh2YWx1ZXMpIHsKICAgIHRoaXMuaW5pdERlZmF1bHRzXygpOwogICAgdGhpcy5pbml0RmllbGRzXyh2YWx1ZXMpOwogIH0KCgogIE1lZGlhUm91dGVyX09uUm91dGVNZXNzYWdlc1JlY2VpdmVkX1BhcmFtcy5wcm90b3R5cGUuaW5pdERlZmF1bHRzXyA9IGZ1bmN0aW9uKCkgewogICAgdGhpcy5yb3V0ZUlkID0gbnVsbDsKICAgIHRoaXMubWVzc2FnZXMgPSBudWxsOwogIH07CiAgTWVkaWFSb3V0ZXJfT25Sb3V0ZU1lc3NhZ2VzUmVjZWl2ZWRfUGFyYW1zLnByb3RvdHlwZS5pbml0RmllbGRzXyA9IGZ1bmN0aW9uKGZpZWxkcykgewogICAgZm9yKHZhciBmaWVsZCBpbiBmaWVsZHMpIHsKICAgICAgICBpZiAodGhpcy5oYXNPd25Qcm9wZXJ0eShmaWVsZCkpCiAgICAgICAgICB0aGlzW2ZpZWxkXSA9IGZpZWxkc1tmaWVsZF07CiAgICB9CiAgfTsKCiAgTWVkaWFSb3V0ZXJfT25Sb3V0ZU1lc3NhZ2VzUmVjZWl2ZWRfUGFyYW1zLnZhbGlkYXRlID0gZnVuY3Rpb24obWVzc2FnZVZhbGlkYXRvciwgb2Zmc2V0KSB7CiAgICB2YXIgZXJyOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdEhlYWRlcihvZmZzZXQsIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHZhciBrVmVyc2lvblNpemVzID0gWwogICAgICB7dmVyc2lvbjogMCwgbnVtQnl0ZXM6IDI0fQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZXJfT25Sb3V0ZU1lc3NhZ2VzUmVjZWl2ZWRfUGFyYW1zLnJvdXRlSWQKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJpbmdQb2ludGVyKG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMCwgZmFsc2UpCiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZXJfT25Sb3V0ZU1lc3NhZ2VzUmVjZWl2ZWRfUGFyYW1zLm1lc3NhZ2VzCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlQXJyYXlQb2ludGVyKG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgOCwgOCwgbmV3IGNvZGVjLlBvaW50ZXJUbyhSb3V0ZU1lc3NhZ2UpLCBmYWxzZSwgWzBdLCAwKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgfTsKCiAgTWVkaWFSb3V0ZXJfT25Sb3V0ZU1lc3NhZ2VzUmVjZWl2ZWRfUGFyYW1zLmVuY29kZWRTaXplID0gY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAxNjsKCiAgTWVkaWFSb3V0ZXJfT25Sb3V0ZU1lc3NhZ2VzUmVjZWl2ZWRfUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1lZGlhUm91dGVyX09uUm91dGVNZXNzYWdlc1JlY2VpdmVkX1BhcmFtcygpOwogICAgdmFyIG51bWJlck9mQnl0ZXMgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhciB2ZXJzaW9uID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YWwucm91dGVJZCA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLlN0cmluZyk7CiAgICB2YWwubWVzc2FnZXMgPSBkZWNvZGVyLmRlY29kZUFycmF5UG9pbnRlcihuZXcgY29kZWMuUG9pbnRlclRvKFJvdXRlTWVzc2FnZSkpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBNZWRpYVJvdXRlcl9PblJvdXRlTWVzc2FnZXNSZWNlaXZlZF9QYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNZWRpYVJvdXRlcl9PblJvdXRlTWVzc2FnZXNSZWNlaXZlZF9QYXJhbXMuZW5jb2RlZFNpemUpOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMigwKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLlN0cmluZywgdmFsLnJvdXRlSWQpOwogICAgZW5jb2Rlci5lbmNvZGVBcnJheVBvaW50ZXIobmV3IGNvZGVjLlBvaW50ZXJUbyhSb3V0ZU1lc3NhZ2UpLCB2YWwubWVzc2FnZXMpOwogIH07CiAgZnVuY3Rpb24gTWVkaWFSb3V0ZXJfT25NZWRpYVJlbW90ZXJDcmVhdGVkX1BhcmFtcyh2YWx1ZXMpIHsKICAgIHRoaXMuaW5pdERlZmF1bHRzXygpOwogICAgdGhpcy5pbml0RmllbGRzXyh2YWx1ZXMpOwogIH0KCgogIE1lZGlhUm91dGVyX09uTWVkaWFSZW1vdGVyQ3JlYXRlZF9QYXJhbXMucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMudGFiSWQgPSAwOwogICAgdGhpcy5yZW1vdGVyID0gbmV3IG1pcnJvcl9zZXJ2aWNlX3JlbW90aW5nJC5NaXJyb3JTZXJ2aWNlUmVtb3RlclB0cigpOwogICAgdGhpcy5yZW1vdGluZ1NvdXJjZSA9IG5ldyBiaW5kaW5ncy5JbnRlcmZhY2VSZXF1ZXN0KCk7CiAgfTsKICBNZWRpYVJvdXRlcl9Pbk1lZGlhUmVtb3RlckNyZWF0ZWRfUGFyYW1zLnByb3RvdHlwZS5pbml0RmllbGRzXyA9IGZ1bmN0aW9uKGZpZWxkcykgewogICAgZm9yKHZhciBmaWVsZCBpbiBmaWVsZHMpIHsKICAgICAgICBpZiAodGhpcy5oYXNPd25Qcm9wZXJ0eShmaWVsZCkpCiAgICAgICAgICB0aGlzW2ZpZWxkXSA9IGZpZWxkc1tmaWVsZF07CiAgICB9CiAgfTsKCiAgTWVkaWFSb3V0ZXJfT25NZWRpYVJlbW90ZXJDcmVhdGVkX1BhcmFtcy52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiAyNH0KICAgIF07CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0VmVyc2lvbihvZmZzZXQsIGtWZXJzaW9uU2l6ZXMpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKCiAgICAvLyB2YWxpZGF0ZSBNZWRpYVJvdXRlcl9Pbk1lZGlhUmVtb3RlckNyZWF0ZWRfUGFyYW1zLnJlbW90ZXIKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVJbnRlcmZhY2Uob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA0LCBmYWxzZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFSb3V0ZXJfT25NZWRpYVJlbW90ZXJDcmVhdGVkX1BhcmFtcy5yZW1vdGluZ1NvdXJjZQogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZUludGVyZmFjZVJlcXVlc3Qob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAxMiwgZmFsc2UpCiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIE1lZGlhUm91dGVyX09uTWVkaWFSZW1vdGVyQ3JlYXRlZF9QYXJhbXMuZW5jb2RlZFNpemUgPSBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDE2OwoKICBNZWRpYVJvdXRlcl9Pbk1lZGlhUmVtb3RlckNyZWF0ZWRfUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1lZGlhUm91dGVyX09uTWVkaWFSZW1vdGVyQ3JlYXRlZF9QYXJhbXMoKTsKICAgIHZhciBudW1iZXJPZkJ5dGVzID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YXIgdmVyc2lvbiA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFsLnRhYklkID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuSW50MzIpOwogICAgdmFsLnJlbW90ZXIgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChuZXcgY29kZWMuSW50ZXJmYWNlKG1pcnJvcl9zZXJ2aWNlX3JlbW90aW5nJC5NaXJyb3JTZXJ2aWNlUmVtb3RlclB0cikpOwogICAgdmFsLnJlbW90aW5nU291cmNlID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuSW50ZXJmYWNlUmVxdWVzdCk7CiAgICByZXR1cm4gdmFsOwogIH07CgogIE1lZGlhUm91dGVyX09uTWVkaWFSZW1vdGVyQ3JlYXRlZF9QYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNZWRpYVJvdXRlcl9Pbk1lZGlhUmVtb3RlckNyZWF0ZWRfUGFyYW1zLmVuY29kZWRTaXplKTsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoMCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5JbnQzMiwgdmFsLnRhYklkKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KG5ldyBjb2RlYy5JbnRlcmZhY2UobWlycm9yX3NlcnZpY2VfcmVtb3RpbmckLk1pcnJvclNlcnZpY2VSZW1vdGVyUHRyKSwgdmFsLnJlbW90ZXIpOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuSW50ZXJmYWNlUmVxdWVzdCwgdmFsLnJlbW90aW5nU291cmNlKTsKICB9OwoKICBmdW5jdGlvbiBNZWRpYVNpbmtFeHRyYURhdGEodmFsdWUpIHsKICAgIHRoaXMuaW5pdERlZmF1bHRfKCk7CiAgICB0aGlzLmluaXRWYWx1ZV8odmFsdWUpOwogIH0KICAKICAKICBNZWRpYVNpbmtFeHRyYURhdGEuVGFncyA9IHsKICAgIGRpYWxNZWRpYVNpbms6IDAsCiAgICBjYXN0TWVkaWFTaW5rOiAxLAogIH07CiAgCiAgTWVkaWFTaW5rRXh0cmFEYXRhLnByb3RvdHlwZS5pbml0RGVmYXVsdF8gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMuJGRhdGEgPSBudWxsOwogICAgdGhpcy4kdGFnID0gdW5kZWZpbmVkOwogIH0KICAKICBNZWRpYVNpbmtFeHRyYURhdGEucHJvdG90eXBlLmluaXRWYWx1ZV8gPSBmdW5jdGlvbih2YWx1ZSkgewogICAgaWYgKHZhbHVlID09IHVuZGVmaW5lZCkgewogICAgICByZXR1cm47CiAgICB9CiAgCiAgICB2YXIga2V5cyA9IE9iamVjdC5rZXlzKHZhbHVlKTsKICAgIGlmIChrZXlzLmxlbmd0aCA9PSAwKSB7CiAgICAgIHJldHVybjsKICAgIH0KICAKICAgIGlmIChrZXlzLmxlbmd0aCA+IDEpIHsKICAgICAgdGhyb3cgbmV3IFR5cGVFcnJvcigiWW91IG1heSBzZXQgb25seSBvbmUgbWVtYmVyIG9uIGEgdW5pb24uIik7CiAgICB9CiAgCiAgICB2YXIgZmllbGRzID0gWwogICAgICAgICJkaWFsTWVkaWFTaW5rIiwKICAgICAgICAiY2FzdE1lZGlhU2luayIsCiAgICBdOwogIAogICAgaWYgKGZpZWxkcy5pbmRleE9mKGtleXNbMF0pIDwgMCkgewogICAgICB0aHJvdyBuZXcgUmVmZXJlbmNlRXJyb3Ioa2V5c1swXSArICIgaXMgbm90IGEgTWVkaWFTaW5rRXh0cmFEYXRhIG1lbWJlci4iKTsKICAKICAgIH0KICAKICAgIHRoaXNba2V5c1swXV0gPSB2YWx1ZVtrZXlzWzBdXTsKICB9CiAgT2JqZWN0LmRlZmluZVByb3BlcnR5KE1lZGlhU2lua0V4dHJhRGF0YS5wcm90b3R5cGUsICJkaWFsTWVkaWFTaW5rIiwgewogICAgZ2V0OiBmdW5jdGlvbigpIHsKICAgICAgaWYgKHRoaXMuJHRhZyAhPSBNZWRpYVNpbmtFeHRyYURhdGEuVGFncy5kaWFsTWVkaWFTaW5rKSB7CiAgICAgICAgdGhyb3cgbmV3IFJlZmVyZW5jZUVycm9yKAogICAgICAgICAgICAiTWVkaWFTaW5rRXh0cmFEYXRhLmRpYWxNZWRpYVNpbmsgaXMgbm90IGN1cnJlbnRseSBzZXQuIik7CiAgICAgIH0KICAgICAgcmV0dXJuIHRoaXMuJGRhdGE7CiAgICB9LAogIAogICAgc2V0OiBmdW5jdGlvbih2YWx1ZSkgewogICAgICB0aGlzLiR0YWcgPSBNZWRpYVNpbmtFeHRyYURhdGEuVGFncy5kaWFsTWVkaWFTaW5rOwogICAgICB0aGlzLiRkYXRhID0gdmFsdWU7CiAgICB9CiAgfSk7CiAgT2JqZWN0LmRlZmluZVByb3BlcnR5KE1lZGlhU2lua0V4dHJhRGF0YS5wcm90b3R5cGUsICJjYXN0TWVkaWFTaW5rIiwgewogICAgZ2V0OiBmdW5jdGlvbigpIHsKICAgICAgaWYgKHRoaXMuJHRhZyAhPSBNZWRpYVNpbmtFeHRyYURhdGEuVGFncy5jYXN0TWVkaWFTaW5rKSB7CiAgICAgICAgdGhyb3cgbmV3IFJlZmVyZW5jZUVycm9yKAogICAgICAgICAgICAiTWVkaWFTaW5rRXh0cmFEYXRhLmNhc3RNZWRpYVNpbmsgaXMgbm90IGN1cnJlbnRseSBzZXQuIik7CiAgICAgIH0KICAgICAgcmV0dXJuIHRoaXMuJGRhdGE7CiAgICB9LAogIAogICAgc2V0OiBmdW5jdGlvbih2YWx1ZSkgewogICAgICB0aGlzLiR0YWcgPSBNZWRpYVNpbmtFeHRyYURhdGEuVGFncy5jYXN0TWVkaWFTaW5rOwogICAgICB0aGlzLiRkYXRhID0gdmFsdWU7CiAgICB9CiAgfSk7CiAgCiAgCiAgICBNZWRpYVNpbmtFeHRyYURhdGEuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICAgIGlmICh2YWwgPT0gbnVsbCkgewogICAgICAgIGVuY29kZXIud3JpdGVVaW50NjQoMCk7CiAgICAgICAgZW5jb2Rlci53cml0ZVVpbnQ2NCgwKTsKICAgICAgICByZXR1cm47CiAgICAgIH0KICAgICAgaWYgKHZhbC4kdGFnID09IHVuZGVmaW5lZCkgewogICAgICAgIHRocm93IG5ldyBUeXBlRXJyb3IoIkNhbm5vdCBlbmNvZGUgdW5pb25zIHdpdGggYW4gdW5rbm93biBtZW1iZXIgc2V0LiIpOwogICAgICB9CiAgICAKICAgICAgZW5jb2Rlci53cml0ZVVpbnQzMigxNik7CiAgICAgIGVuY29kZXIud3JpdGVVaW50MzIodmFsLiR0YWcpOwogICAgICBzd2l0Y2ggKHZhbC4kdGFnKSB7CiAgICAgICAgY2FzZSBNZWRpYVNpbmtFeHRyYURhdGEuVGFncy5kaWFsTWVkaWFTaW5rOgogICAgICAgICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3RQb2ludGVyKERpYWxNZWRpYVNpbmssIHZhbC5kaWFsTWVkaWFTaW5rKTsKICAgICAgICAgIGJyZWFrOwogICAgICAgIGNhc2UgTWVkaWFTaW5rRXh0cmFEYXRhLlRhZ3MuY2FzdE1lZGlhU2luazoKICAgICAgICAgIGVuY29kZXIuZW5jb2RlU3RydWN0UG9pbnRlcihDYXN0TWVkaWFTaW5rLCB2YWwuY2FzdE1lZGlhU2luayk7CiAgICAgICAgICBicmVhazsKICAgICAgfQogICAgICBlbmNvZGVyLmFsaWduKCk7CiAgICB9OwogIAogIAogICAgTWVkaWFTaW5rRXh0cmFEYXRhLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgICAgdmFyIHNpemUgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgICAgaWYgKHNpemUgPT0gMCkgewogICAgICAgIGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgICAgIGRlY29kZXIucmVhZFVpbnQ2NCgpOwogICAgICAgIHJldHVybiBudWxsOwogICAgICB9CiAgICAKICAgICAgdmFyIHJlc3VsdCA9IG5ldyBNZWRpYVNpbmtFeHRyYURhdGEoKTsKICAgICAgdmFyIHRhZyA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgICBzd2l0Y2ggKHRhZykgewogICAgICAgIGNhc2UgTWVkaWFTaW5rRXh0cmFEYXRhLlRhZ3MuZGlhbE1lZGlhU2luazoKICAgICAgICAgIHJlc3VsdC5kaWFsTWVkaWFTaW5rID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3RQb2ludGVyKERpYWxNZWRpYVNpbmspOwogICAgICAgICAgYnJlYWs7CiAgICAgICAgY2FzZSBNZWRpYVNpbmtFeHRyYURhdGEuVGFncy5jYXN0TWVkaWFTaW5rOgogICAgICAgICAgcmVzdWx0LmNhc3RNZWRpYVNpbmsgPSBkZWNvZGVyLmRlY29kZVN0cnVjdFBvaW50ZXIoQ2FzdE1lZGlhU2luayk7CiAgICAgICAgICBicmVhazsKICAgICAgfQogICAgICBkZWNvZGVyLmFsaWduKCk7CiAgICAKICAgICAgcmV0dXJuIHJlc3VsdDsKICAgIH07CiAgCiAgCiAgICBNZWRpYVNpbmtFeHRyYURhdGEudmFsaWRhdGUgPSBmdW5jdGlvbihtZXNzYWdlVmFsaWRhdG9yLCBvZmZzZXQpIHsKICAgICAgdmFyIHNpemUgPSBtZXNzYWdlVmFsaWRhdG9yLmRlY29kZVVuaW9uU2l6ZShvZmZzZXQpOwogICAgICBpZiAoc2l6ZSAhPSAxNikgewogICAgICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLklOVkFMSURfVU5JT05fU0laRTsKICAgICAgfQogICAgCiAgICAgIHZhciB0YWcgPSBtZXNzYWdlVmFsaWRhdG9yLmRlY29kZVVuaW9uVGFnKG9mZnNldCk7CiAgICAgIHZhciBkYXRhX29mZnNldCA9IG9mZnNldCArIDg7CiAgICAgIHZhciBlcnI7CiAgICAgIHN3aXRjaCAodGFnKSB7CiAgICAgICAgY2FzZSBNZWRpYVNpbmtFeHRyYURhdGEuVGFncy5kaWFsTWVkaWFTaW5rOgogICAgICAgICAgCiAgICAKICAgIC8vIHZhbGlkYXRlIE1lZGlhU2lua0V4dHJhRGF0YS5kaWFsTWVkaWFTaW5rCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0UG9pbnRlcihkYXRhX29mZnNldCwgRGlhbE1lZGlhU2luaywgZmFsc2UpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CiAgICAgICAgICBicmVhazsKICAgICAgICBjYXNlIE1lZGlhU2lua0V4dHJhRGF0YS5UYWdzLmNhc3RNZWRpYVNpbms6CiAgICAgICAgICAKICAgIAogICAgLy8gdmFsaWRhdGUgTWVkaWFTaW5rRXh0cmFEYXRhLmNhc3RNZWRpYVNpbmsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RQb2ludGVyKGRhdGFfb2Zmc2V0LCBDYXN0TWVkaWFTaW5rLCBmYWxzZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKICAgICAgICAgIGJyZWFrOwogICAgICB9CiAgICAKICAgICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKICAgIH07CiAgCiAgTWVkaWFTaW5rRXh0cmFEYXRhLmVuY29kZWRTaXplID0gMTY7CiAgdmFyIGtNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlUm91dGVfTmFtZSA9IDgyNDE1NDQ0MjsKICB2YXIga01lZGlhUm91dGVQcm92aWRlcl9Kb2luUm91dGVfTmFtZSA9IDM5ODYzMzcwOwogIHZhciBrTWVkaWFSb3V0ZVByb3ZpZGVyX0Nvbm5lY3RSb3V0ZUJ5Um91dGVJZF9OYW1lID0gMTk4NTQ4MDQ4MTsKICB2YXIga01lZGlhUm91dGVQcm92aWRlcl9UZXJtaW5hdGVSb3V0ZV9OYW1lID0gMTczNzYyNDQ5OTsKICB2YXIga01lZGlhUm91dGVQcm92aWRlcl9TZW5kUm91dGVNZXNzYWdlX05hbWUgPSA2ODc0ODk1NjE7CiAgdmFyIGtNZWRpYVJvdXRlUHJvdmlkZXJfU2VuZFJvdXRlQmluYXJ5TWVzc2FnZV9OYW1lID0gMTQwMzMzNTAxNTsKICB2YXIga01lZGlhUm91dGVQcm92aWRlcl9TdGFydE9ic2VydmluZ01lZGlhU2lua3NfTmFtZSA9IDIwNTIzNzYwNzY7CiAgdmFyIGtNZWRpYVJvdXRlUHJvdmlkZXJfU3RvcE9ic2VydmluZ01lZGlhU2lua3NfTmFtZSA9IDM2NTE1MDI1NjsKICB2YXIga01lZGlhUm91dGVQcm92aWRlcl9TdGFydE9ic2VydmluZ01lZGlhUm91dGVzX05hbWUgPSAxOTg2NzI4NTI3OwogIHZhciBrTWVkaWFSb3V0ZVByb3ZpZGVyX1N0b3BPYnNlcnZpbmdNZWRpYVJvdXRlc19OYW1lID0gOTMwODczNzA7CiAgdmFyIGtNZWRpYVJvdXRlUHJvdmlkZXJfU3RhcnRMaXN0ZW5pbmdGb3JSb3V0ZU1lc3NhZ2VzX05hbWUgPSA0NjM0MTE0NTk7CiAgdmFyIGtNZWRpYVJvdXRlUHJvdmlkZXJfU3RvcExpc3RlbmluZ0ZvclJvdXRlTWVzc2FnZXNfTmFtZSA9IDE2ODgwODAxNDU7CiAgdmFyIGtNZWRpYVJvdXRlUHJvdmlkZXJfRGV0YWNoUm91dGVfTmFtZSA9IDcwODM4MDI2NzsKICB2YXIga01lZGlhUm91dGVQcm92aWRlcl9FbmFibGVNZG5zRGlzY292ZXJ5X05hbWUgPSAxMDQyMTYzMzIwOwogIHZhciBrTWVkaWFSb3V0ZVByb3ZpZGVyX1VwZGF0ZU1lZGlhU2lua3NfTmFtZSA9IDYxOTgzNjIzODsKICB2YXIga01lZGlhUm91dGVQcm92aWRlcl9TZWFyY2hTaW5rc19OYW1lID0gMjExOTAzNjkwMjsKICB2YXIga01lZGlhUm91dGVQcm92aWRlcl9Qcm92aWRlU2lua3NfTmFtZSA9IDYzMjE0OTI5NTsKICB2YXIga01lZGlhUm91dGVQcm92aWRlcl9DcmVhdGVNZWRpYVJvdXRlQ29udHJvbGxlcl9OYW1lID0gMTYwNTY1Njc5NzsKCiAgZnVuY3Rpb24gTWVkaWFSb3V0ZVByb3ZpZGVyUHRyKGhhbmRsZU9yUHRySW5mbykgewogICAgdGhpcy5wdHIgPSBuZXcgYmluZGluZ3MuSW50ZXJmYWNlUHRyQ29udHJvbGxlcihNZWRpYVJvdXRlUHJvdmlkZXIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGhhbmRsZU9yUHRySW5mbyk7CiAgfQoKICBmdW5jdGlvbiBNZWRpYVJvdXRlUHJvdmlkZXJBc3NvY2lhdGVkUHRyKGFzc29jaWF0ZWRJbnRlcmZhY2VQdHJJbmZvKSB7CiAgICB0aGlzLnB0ciA9IG5ldyBhc3NvY2lhdGVkQmluZGluZ3MuQXNzb2NpYXRlZEludGVyZmFjZVB0ckNvbnRyb2xsZXIoCiAgICAgICAgTWVkaWFSb3V0ZVByb3ZpZGVyLCBhc3NvY2lhdGVkSW50ZXJmYWNlUHRySW5mbyk7CiAgfQoKICBNZWRpYVJvdXRlUHJvdmlkZXJBc3NvY2lhdGVkUHRyLnByb3RvdHlwZSA9CiAgICAgIE9iamVjdC5jcmVhdGUoTWVkaWFSb3V0ZVByb3ZpZGVyUHRyLnByb3RvdHlwZSk7CiAgTWVkaWFSb3V0ZVByb3ZpZGVyQXNzb2NpYXRlZFB0ci5wcm90b3R5cGUuY29uc3RydWN0b3IgPQogICAgICBNZWRpYVJvdXRlUHJvdmlkZXJBc3NvY2lhdGVkUHRyOwoKICBmdW5jdGlvbiBNZWRpYVJvdXRlUHJvdmlkZXJQcm94eShyZWNlaXZlcikgewogICAgdGhpcy5yZWNlaXZlcl8gPSByZWNlaXZlcjsKICB9CiAgTWVkaWFSb3V0ZVByb3ZpZGVyUHRyLnByb3RvdHlwZS5jcmVhdGVSb3V0ZSA9IGZ1bmN0aW9uKCkgewogICAgcmV0dXJuIE1lZGlhUm91dGVQcm92aWRlclByb3h5LnByb3RvdHlwZS5jcmVhdGVSb3V0ZQogICAgICAgIC5hcHBseSh0aGlzLnB0ci5nZXRQcm94eSgpLCBhcmd1bWVudHMpOwogIH07CgogIE1lZGlhUm91dGVQcm92aWRlclByb3h5LnByb3RvdHlwZS5jcmVhdGVSb3V0ZSA9IGZ1bmN0aW9uKG1lZGlhU291cmNlLCBzaW5rSWQsIG9yaWdpbmFsUHJlc2VudGF0aW9uSWQsIG9yaWdpbiwgdGFiSWQsIHRpbWVvdXQsIGluY29nbml0bykgewogICAgdmFyIHBhcmFtcyA9IG5ldyBNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlUm91dGVfUGFyYW1zKCk7CiAgICBwYXJhbXMubWVkaWFTb3VyY2UgPSBtZWRpYVNvdXJjZTsKICAgIHBhcmFtcy5zaW5rSWQgPSBzaW5rSWQ7CiAgICBwYXJhbXMub3JpZ2luYWxQcmVzZW50YXRpb25JZCA9IG9yaWdpbmFsUHJlc2VudGF0aW9uSWQ7CiAgICBwYXJhbXMub3JpZ2luID0gb3JpZ2luOwogICAgcGFyYW1zLnRhYklkID0gdGFiSWQ7CiAgICBwYXJhbXMudGltZW91dCA9IHRpbWVvdXQ7CiAgICBwYXJhbXMuaW5jb2duaXRvID0gaW5jb2duaXRvOwogICAgcmV0dXJuIG5ldyBQcm9taXNlKGZ1bmN0aW9uKHJlc29sdmUsIHJlamVjdCkgewogICAgICB2YXIgYnVpbGRlciA9IG5ldyBjb2RlYy5NZXNzYWdlVjFCdWlsZGVyKAogICAgICAgICAga01lZGlhUm91dGVQcm92aWRlcl9DcmVhdGVSb3V0ZV9OYW1lLAogICAgICAgICAgY29kZWMuYWxpZ24oTWVkaWFSb3V0ZVByb3ZpZGVyX0NyZWF0ZVJvdXRlX1BhcmFtcy5lbmNvZGVkU2l6ZSksCiAgICAgICAgICBjb2RlYy5rTWVzc2FnZUV4cGVjdHNSZXNwb25zZSwgMCk7CiAgICAgIGJ1aWxkZXIuZW5jb2RlU3RydWN0KE1lZGlhUm91dGVQcm92aWRlcl9DcmVhdGVSb3V0ZV9QYXJhbXMsIHBhcmFtcyk7CiAgICAgIHZhciBtZXNzYWdlID0gYnVpbGRlci5maW5pc2goKTsKICAgICAgdGhpcy5yZWNlaXZlcl8uYWNjZXB0QW5kRXhwZWN0UmVzcG9uc2UobWVzc2FnZSkudGhlbihmdW5jdGlvbihtZXNzYWdlKSB7CiAgICAgICAgdmFyIHJlYWRlciA9IG5ldyBjb2RlYy5NZXNzYWdlUmVhZGVyKG1lc3NhZ2UpOwogICAgICAgIHZhciByZXNwb25zZVBhcmFtcyA9CiAgICAgICAgICAgIHJlYWRlci5kZWNvZGVTdHJ1Y3QoTWVkaWFSb3V0ZVByb3ZpZGVyX0NyZWF0ZVJvdXRlX1Jlc3BvbnNlUGFyYW1zKTsKICAgICAgICByZXNvbHZlKHJlc3BvbnNlUGFyYW1zKTsKICAgICAgfSkuY2F0Y2goZnVuY3Rpb24ocmVzdWx0KSB7CiAgICAgICAgcmVqZWN0KEVycm9yKCJDb25uZWN0aW9uIGVycm9yOiAiICsgcmVzdWx0KSk7CiAgICAgIH0pOwogICAgfS5iaW5kKHRoaXMpKTsKICB9OwogIE1lZGlhUm91dGVQcm92aWRlclB0ci5wcm90b3R5cGUuam9pblJvdXRlID0gZnVuY3Rpb24oKSB7CiAgICByZXR1cm4gTWVkaWFSb3V0ZVByb3ZpZGVyUHJveHkucHJvdG90eXBlLmpvaW5Sb3V0ZQogICAgICAgIC5hcHBseSh0aGlzLnB0ci5nZXRQcm94eSgpLCBhcmd1bWVudHMpOwogIH07CgogIE1lZGlhUm91dGVQcm92aWRlclByb3h5LnByb3RvdHlwZS5qb2luUm91dGUgPSBmdW5jdGlvbihtZWRpYVNvdXJjZSwgcHJlc2VudGF0aW9uSWQsIG9yaWdpbiwgdGFiSWQsIHRpbWVvdXQsIGluY29nbml0bykgewogICAgdmFyIHBhcmFtcyA9IG5ldyBNZWRpYVJvdXRlUHJvdmlkZXJfSm9pblJvdXRlX1BhcmFtcygpOwogICAgcGFyYW1zLm1lZGlhU291cmNlID0gbWVkaWFTb3VyY2U7CiAgICBwYXJhbXMucHJlc2VudGF0aW9uSWQgPSBwcmVzZW50YXRpb25JZDsKICAgIHBhcmFtcy5vcmlnaW4gPSBvcmlnaW47CiAgICBwYXJhbXMudGFiSWQgPSB0YWJJZDsKICAgIHBhcmFtcy50aW1lb3V0ID0gdGltZW91dDsKICAgIHBhcmFtcy5pbmNvZ25pdG8gPSBpbmNvZ25pdG87CiAgICByZXR1cm4gbmV3IFByb21pc2UoZnVuY3Rpb24ocmVzb2x2ZSwgcmVqZWN0KSB7CiAgICAgIHZhciBidWlsZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VWMUJ1aWxkZXIoCiAgICAgICAgICBrTWVkaWFSb3V0ZVByb3ZpZGVyX0pvaW5Sb3V0ZV9OYW1lLAogICAgICAgICAgY29kZWMuYWxpZ24oTWVkaWFSb3V0ZVByb3ZpZGVyX0pvaW5Sb3V0ZV9QYXJhbXMuZW5jb2RlZFNpemUpLAogICAgICAgICAgY29kZWMua01lc3NhZ2VFeHBlY3RzUmVzcG9uc2UsIDApOwogICAgICBidWlsZGVyLmVuY29kZVN0cnVjdChNZWRpYVJvdXRlUHJvdmlkZXJfSm9pblJvdXRlX1BhcmFtcywgcGFyYW1zKTsKICAgICAgdmFyIG1lc3NhZ2UgPSBidWlsZGVyLmZpbmlzaCgpOwogICAgICB0aGlzLnJlY2VpdmVyXy5hY2NlcHRBbmRFeHBlY3RSZXNwb25zZShtZXNzYWdlKS50aGVuKGZ1bmN0aW9uKG1lc3NhZ2UpIHsKICAgICAgICB2YXIgcmVhZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VSZWFkZXIobWVzc2FnZSk7CiAgICAgICAgdmFyIHJlc3BvbnNlUGFyYW1zID0KICAgICAgICAgICAgcmVhZGVyLmRlY29kZVN0cnVjdChNZWRpYVJvdXRlUHJvdmlkZXJfSm9pblJvdXRlX1Jlc3BvbnNlUGFyYW1zKTsKICAgICAgICByZXNvbHZlKHJlc3BvbnNlUGFyYW1zKTsKICAgICAgfSkuY2F0Y2goZnVuY3Rpb24ocmVzdWx0KSB7CiAgICAgICAgcmVqZWN0KEVycm9yKCJDb25uZWN0aW9uIGVycm9yOiAiICsgcmVzdWx0KSk7CiAgICAgIH0pOwogICAgfS5iaW5kKHRoaXMpKTsKICB9OwogIE1lZGlhUm91dGVQcm92aWRlclB0ci5wcm90b3R5cGUuY29ubmVjdFJvdXRlQnlSb3V0ZUlkID0gZnVuY3Rpb24oKSB7CiAgICByZXR1cm4gTWVkaWFSb3V0ZVByb3ZpZGVyUHJveHkucHJvdG90eXBlLmNvbm5lY3RSb3V0ZUJ5Um91dGVJZAogICAgICAgIC5hcHBseSh0aGlzLnB0ci5nZXRQcm94eSgpLCBhcmd1bWVudHMpOwogIH07CgogIE1lZGlhUm91dGVQcm92aWRlclByb3h5LnByb3RvdHlwZS5jb25uZWN0Um91dGVCeVJvdXRlSWQgPSBmdW5jdGlvbihtZWRpYVNvdXJjZSwgcm91dGVJZCwgcHJlc2VudGF0aW9uSWQsIG9yaWdpbiwgdGFiSWQsIHRpbWVvdXQsIGluY29nbml0bykgewogICAgdmFyIHBhcmFtcyA9IG5ldyBNZWRpYVJvdXRlUHJvdmlkZXJfQ29ubmVjdFJvdXRlQnlSb3V0ZUlkX1BhcmFtcygpOwogICAgcGFyYW1zLm1lZGlhU291cmNlID0gbWVkaWFTb3VyY2U7CiAgICBwYXJhbXMucm91dGVJZCA9IHJvdXRlSWQ7CiAgICBwYXJhbXMucHJlc2VudGF0aW9uSWQgPSBwcmVzZW50YXRpb25JZDsKICAgIHBhcmFtcy5vcmlnaW4gPSBvcmlnaW47CiAgICBwYXJhbXMudGFiSWQgPSB0YWJJZDsKICAgIHBhcmFtcy50aW1lb3V0ID0gdGltZW91dDsKICAgIHBhcmFtcy5pbmNvZ25pdG8gPSBpbmNvZ25pdG87CiAgICByZXR1cm4gbmV3IFByb21pc2UoZnVuY3Rpb24ocmVzb2x2ZSwgcmVqZWN0KSB7CiAgICAgIHZhciBidWlsZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VWMUJ1aWxkZXIoCiAgICAgICAgICBrTWVkaWFSb3V0ZVByb3ZpZGVyX0Nvbm5lY3RSb3V0ZUJ5Um91dGVJZF9OYW1lLAogICAgICAgICAgY29kZWMuYWxpZ24oTWVkaWFSb3V0ZVByb3ZpZGVyX0Nvbm5lY3RSb3V0ZUJ5Um91dGVJZF9QYXJhbXMuZW5jb2RlZFNpemUpLAogICAgICAgICAgY29kZWMua01lc3NhZ2VFeHBlY3RzUmVzcG9uc2UsIDApOwogICAgICBidWlsZGVyLmVuY29kZVN0cnVjdChNZWRpYVJvdXRlUHJvdmlkZXJfQ29ubmVjdFJvdXRlQnlSb3V0ZUlkX1BhcmFtcywgcGFyYW1zKTsKICAgICAgdmFyIG1lc3NhZ2UgPSBidWlsZGVyLmZpbmlzaCgpOwogICAgICB0aGlzLnJlY2VpdmVyXy5hY2NlcHRBbmRFeHBlY3RSZXNwb25zZShtZXNzYWdlKS50aGVuKGZ1bmN0aW9uKG1lc3NhZ2UpIHsKICAgICAgICB2YXIgcmVhZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VSZWFkZXIobWVzc2FnZSk7CiAgICAgICAgdmFyIHJlc3BvbnNlUGFyYW1zID0KICAgICAgICAgICAgcmVhZGVyLmRlY29kZVN0cnVjdChNZWRpYVJvdXRlUHJvdmlkZXJfQ29ubmVjdFJvdXRlQnlSb3V0ZUlkX1Jlc3BvbnNlUGFyYW1zKTsKICAgICAgICByZXNvbHZlKHJlc3BvbnNlUGFyYW1zKTsKICAgICAgfSkuY2F0Y2goZnVuY3Rpb24ocmVzdWx0KSB7CiAgICAgICAgcmVqZWN0KEVycm9yKCJDb25uZWN0aW9uIGVycm9yOiAiICsgcmVzdWx0KSk7CiAgICAgIH0pOwogICAgfS5iaW5kKHRoaXMpKTsKICB9OwogIE1lZGlhUm91dGVQcm92aWRlclB0ci5wcm90b3R5cGUudGVybWluYXRlUm91dGUgPSBmdW5jdGlvbigpIHsKICAgIHJldHVybiBNZWRpYVJvdXRlUHJvdmlkZXJQcm94eS5wcm90b3R5cGUudGVybWluYXRlUm91dGUKICAgICAgICAuYXBwbHkodGhpcy5wdHIuZ2V0UHJveHkoKSwgYXJndW1lbnRzKTsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJQcm94eS5wcm90b3R5cGUudGVybWluYXRlUm91dGUgPSBmdW5jdGlvbihyb3V0ZUlkKSB7CiAgICB2YXIgcGFyYW1zID0gbmV3IE1lZGlhUm91dGVQcm92aWRlcl9UZXJtaW5hdGVSb3V0ZV9QYXJhbXMoKTsKICAgIHBhcmFtcy5yb3V0ZUlkID0gcm91dGVJZDsKICAgIHJldHVybiBuZXcgUHJvbWlzZShmdW5jdGlvbihyZXNvbHZlLCByZWplY3QpIHsKICAgICAgdmFyIGJ1aWxkZXIgPSBuZXcgY29kZWMuTWVzc2FnZVYxQnVpbGRlcigKICAgICAgICAgIGtNZWRpYVJvdXRlUHJvdmlkZXJfVGVybWluYXRlUm91dGVfTmFtZSwKICAgICAgICAgIGNvZGVjLmFsaWduKE1lZGlhUm91dGVQcm92aWRlcl9UZXJtaW5hdGVSb3V0ZV9QYXJhbXMuZW5jb2RlZFNpemUpLAogICAgICAgICAgY29kZWMua01lc3NhZ2VFeHBlY3RzUmVzcG9uc2UsIDApOwogICAgICBidWlsZGVyLmVuY29kZVN0cnVjdChNZWRpYVJvdXRlUHJvdmlkZXJfVGVybWluYXRlUm91dGVfUGFyYW1zLCBwYXJhbXMpOwogICAgICB2YXIgbWVzc2FnZSA9IGJ1aWxkZXIuZmluaXNoKCk7CiAgICAgIHRoaXMucmVjZWl2ZXJfLmFjY2VwdEFuZEV4cGVjdFJlc3BvbnNlKG1lc3NhZ2UpLnRoZW4oZnVuY3Rpb24obWVzc2FnZSkgewogICAgICAgIHZhciByZWFkZXIgPSBuZXcgY29kZWMuTWVzc2FnZVJlYWRlcihtZXNzYWdlKTsKICAgICAgICB2YXIgcmVzcG9uc2VQYXJhbXMgPQogICAgICAgICAgICByZWFkZXIuZGVjb2RlU3RydWN0KE1lZGlhUm91dGVQcm92aWRlcl9UZXJtaW5hdGVSb3V0ZV9SZXNwb25zZVBhcmFtcyk7CiAgICAgICAgcmVzb2x2ZShyZXNwb25zZVBhcmFtcyk7CiAgICAgIH0pLmNhdGNoKGZ1bmN0aW9uKHJlc3VsdCkgewogICAgICAgIHJlamVjdChFcnJvcigiQ29ubmVjdGlvbiBlcnJvcjogIiArIHJlc3VsdCkpOwogICAgICB9KTsKICAgIH0uYmluZCh0aGlzKSk7CiAgfTsKICBNZWRpYVJvdXRlUHJvdmlkZXJQdHIucHJvdG90eXBlLnNlbmRSb3V0ZU1lc3NhZ2UgPSBmdW5jdGlvbigpIHsKICAgIHJldHVybiBNZWRpYVJvdXRlUHJvdmlkZXJQcm94eS5wcm90b3R5cGUuc2VuZFJvdXRlTWVzc2FnZQogICAgICAgIC5hcHBseSh0aGlzLnB0ci5nZXRQcm94eSgpLCBhcmd1bWVudHMpOwogIH07CgogIE1lZGlhUm91dGVQcm92aWRlclByb3h5LnByb3RvdHlwZS5zZW5kUm91dGVNZXNzYWdlID0gZnVuY3Rpb24obWVkaWFSb3V0ZUlkLCBtZXNzYWdlKSB7CiAgICB2YXIgcGFyYW1zID0gbmV3IE1lZGlhUm91dGVQcm92aWRlcl9TZW5kUm91dGVNZXNzYWdlX1BhcmFtcygpOwogICAgcGFyYW1zLm1lZGlhUm91dGVJZCA9IG1lZGlhUm91dGVJZDsKICAgIHBhcmFtcy5tZXNzYWdlID0gbWVzc2FnZTsKICAgIHJldHVybiBuZXcgUHJvbWlzZShmdW5jdGlvbihyZXNvbHZlLCByZWplY3QpIHsKICAgICAgdmFyIGJ1aWxkZXIgPSBuZXcgY29kZWMuTWVzc2FnZVYxQnVpbGRlcigKICAgICAgICAgIGtNZWRpYVJvdXRlUHJvdmlkZXJfU2VuZFJvdXRlTWVzc2FnZV9OYW1lLAogICAgICAgICAgY29kZWMuYWxpZ24oTWVkaWFSb3V0ZVByb3ZpZGVyX1NlbmRSb3V0ZU1lc3NhZ2VfUGFyYW1zLmVuY29kZWRTaXplKSwKICAgICAgICAgIGNvZGVjLmtNZXNzYWdlRXhwZWN0c1Jlc3BvbnNlLCAwKTsKICAgICAgYnVpbGRlci5lbmNvZGVTdHJ1Y3QoTWVkaWFSb3V0ZVByb3ZpZGVyX1NlbmRSb3V0ZU1lc3NhZ2VfUGFyYW1zLCBwYXJhbXMpOwogICAgICB2YXIgbWVzc2FnZSA9IGJ1aWxkZXIuZmluaXNoKCk7CiAgICAgIHRoaXMucmVjZWl2ZXJfLmFjY2VwdEFuZEV4cGVjdFJlc3BvbnNlKG1lc3NhZ2UpLnRoZW4oZnVuY3Rpb24obWVzc2FnZSkgewogICAgICAgIHZhciByZWFkZXIgPSBuZXcgY29kZWMuTWVzc2FnZVJlYWRlcihtZXNzYWdlKTsKICAgICAgICB2YXIgcmVzcG9uc2VQYXJhbXMgPQogICAgICAgICAgICByZWFkZXIuZGVjb2RlU3RydWN0KE1lZGlhUm91dGVQcm92aWRlcl9TZW5kUm91dGVNZXNzYWdlX1Jlc3BvbnNlUGFyYW1zKTsKICAgICAgICByZXNvbHZlKHJlc3BvbnNlUGFyYW1zKTsKICAgICAgfSkuY2F0Y2goZnVuY3Rpb24ocmVzdWx0KSB7CiAgICAgICAgcmVqZWN0KEVycm9yKCJDb25uZWN0aW9uIGVycm9yOiAiICsgcmVzdWx0KSk7CiAgICAgIH0pOwogICAgfS5iaW5kKHRoaXMpKTsKICB9OwogIE1lZGlhUm91dGVQcm92aWRlclB0ci5wcm90b3R5cGUuc2VuZFJvdXRlQmluYXJ5TWVzc2FnZSA9IGZ1bmN0aW9uKCkgewogICAgcmV0dXJuIE1lZGlhUm91dGVQcm92aWRlclByb3h5LnByb3RvdHlwZS5zZW5kUm91dGVCaW5hcnlNZXNzYWdlCiAgICAgICAgLmFwcGx5KHRoaXMucHRyLmdldFByb3h5KCksIGFyZ3VtZW50cyk7CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyUHJveHkucHJvdG90eXBlLnNlbmRSb3V0ZUJpbmFyeU1lc3NhZ2UgPSBmdW5jdGlvbihtZWRpYVJvdXRlSWQsIGRhdGEpIHsKICAgIHZhciBwYXJhbXMgPSBuZXcgTWVkaWFSb3V0ZVByb3ZpZGVyX1NlbmRSb3V0ZUJpbmFyeU1lc3NhZ2VfUGFyYW1zKCk7CiAgICBwYXJhbXMubWVkaWFSb3V0ZUlkID0gbWVkaWFSb3V0ZUlkOwogICAgcGFyYW1zLmRhdGEgPSBkYXRhOwogICAgcmV0dXJuIG5ldyBQcm9taXNlKGZ1bmN0aW9uKHJlc29sdmUsIHJlamVjdCkgewogICAgICB2YXIgYnVpbGRlciA9IG5ldyBjb2RlYy5NZXNzYWdlVjFCdWlsZGVyKAogICAgICAgICAga01lZGlhUm91dGVQcm92aWRlcl9TZW5kUm91dGVCaW5hcnlNZXNzYWdlX05hbWUsCiAgICAgICAgICBjb2RlYy5hbGlnbihNZWRpYVJvdXRlUHJvdmlkZXJfU2VuZFJvdXRlQmluYXJ5TWVzc2FnZV9QYXJhbXMuZW5jb2RlZFNpemUpLAogICAgICAgICAgY29kZWMua01lc3NhZ2VFeHBlY3RzUmVzcG9uc2UsIDApOwogICAgICBidWlsZGVyLmVuY29kZVN0cnVjdChNZWRpYVJvdXRlUHJvdmlkZXJfU2VuZFJvdXRlQmluYXJ5TWVzc2FnZV9QYXJhbXMsIHBhcmFtcyk7CiAgICAgIHZhciBtZXNzYWdlID0gYnVpbGRlci5maW5pc2goKTsKICAgICAgdGhpcy5yZWNlaXZlcl8uYWNjZXB0QW5kRXhwZWN0UmVzcG9uc2UobWVzc2FnZSkudGhlbihmdW5jdGlvbihtZXNzYWdlKSB7CiAgICAgICAgdmFyIHJlYWRlciA9IG5ldyBjb2RlYy5NZXNzYWdlUmVhZGVyKG1lc3NhZ2UpOwogICAgICAgIHZhciByZXNwb25zZVBhcmFtcyA9CiAgICAgICAgICAgIHJlYWRlci5kZWNvZGVTdHJ1Y3QoTWVkaWFSb3V0ZVByb3ZpZGVyX1NlbmRSb3V0ZUJpbmFyeU1lc3NhZ2VfUmVzcG9uc2VQYXJhbXMpOwogICAgICAgIHJlc29sdmUocmVzcG9uc2VQYXJhbXMpOwogICAgICB9KS5jYXRjaChmdW5jdGlvbihyZXN1bHQpIHsKICAgICAgICByZWplY3QoRXJyb3IoIkNvbm5lY3Rpb24gZXJyb3I6ICIgKyByZXN1bHQpKTsKICAgICAgfSk7CiAgICB9LmJpbmQodGhpcykpOwogIH07CiAgTWVkaWFSb3V0ZVByb3ZpZGVyUHRyLnByb3RvdHlwZS5zdGFydE9ic2VydmluZ01lZGlhU2lua3MgPSBmdW5jdGlvbigpIHsKICAgIHJldHVybiBNZWRpYVJvdXRlUHJvdmlkZXJQcm94eS5wcm90b3R5cGUuc3RhcnRPYnNlcnZpbmdNZWRpYVNpbmtzCiAgICAgICAgLmFwcGx5KHRoaXMucHRyLmdldFByb3h5KCksIGFyZ3VtZW50cyk7CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyUHJveHkucHJvdG90eXBlLnN0YXJ0T2JzZXJ2aW5nTWVkaWFTaW5rcyA9IGZ1bmN0aW9uKG1lZGlhU291cmNlKSB7CiAgICB2YXIgcGFyYW1zID0gbmV3IE1lZGlhUm91dGVQcm92aWRlcl9TdGFydE9ic2VydmluZ01lZGlhU2lua3NfUGFyYW1zKCk7CiAgICBwYXJhbXMubWVkaWFTb3VyY2UgPSBtZWRpYVNvdXJjZTsKICAgIHZhciBidWlsZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VWMEJ1aWxkZXIoCiAgICAgICAga01lZGlhUm91dGVQcm92aWRlcl9TdGFydE9ic2VydmluZ01lZGlhU2lua3NfTmFtZSwKICAgICAgICBjb2RlYy5hbGlnbihNZWRpYVJvdXRlUHJvdmlkZXJfU3RhcnRPYnNlcnZpbmdNZWRpYVNpbmtzX1BhcmFtcy5lbmNvZGVkU2l6ZSkpOwogICAgYnVpbGRlci5lbmNvZGVTdHJ1Y3QoTWVkaWFSb3V0ZVByb3ZpZGVyX1N0YXJ0T2JzZXJ2aW5nTWVkaWFTaW5rc19QYXJhbXMsIHBhcmFtcyk7CiAgICB2YXIgbWVzc2FnZSA9IGJ1aWxkZXIuZmluaXNoKCk7CiAgICB0aGlzLnJlY2VpdmVyXy5hY2NlcHQobWVzc2FnZSk7CiAgfTsKICBNZWRpYVJvdXRlUHJvdmlkZXJQdHIucHJvdG90eXBlLnN0b3BPYnNlcnZpbmdNZWRpYVNpbmtzID0gZnVuY3Rpb24oKSB7CiAgICByZXR1cm4gTWVkaWFSb3V0ZVByb3ZpZGVyUHJveHkucHJvdG90eXBlLnN0b3BPYnNlcnZpbmdNZWRpYVNpbmtzCiAgICAgICAgLmFwcGx5KHRoaXMucHRyLmdldFByb3h5KCksIGFyZ3VtZW50cyk7CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyUHJveHkucHJvdG90eXBlLnN0b3BPYnNlcnZpbmdNZWRpYVNpbmtzID0gZnVuY3Rpb24obWVkaWFTb3VyY2UpIHsKICAgIHZhciBwYXJhbXMgPSBuZXcgTWVkaWFSb3V0ZVByb3ZpZGVyX1N0b3BPYnNlcnZpbmdNZWRpYVNpbmtzX1BhcmFtcygpOwogICAgcGFyYW1zLm1lZGlhU291cmNlID0gbWVkaWFTb3VyY2U7CiAgICB2YXIgYnVpbGRlciA9IG5ldyBjb2RlYy5NZXNzYWdlVjBCdWlsZGVyKAogICAgICAgIGtNZWRpYVJvdXRlUHJvdmlkZXJfU3RvcE9ic2VydmluZ01lZGlhU2lua3NfTmFtZSwKICAgICAgICBjb2RlYy5hbGlnbihNZWRpYVJvdXRlUHJvdmlkZXJfU3RvcE9ic2VydmluZ01lZGlhU2lua3NfUGFyYW1zLmVuY29kZWRTaXplKSk7CiAgICBidWlsZGVyLmVuY29kZVN0cnVjdChNZWRpYVJvdXRlUHJvdmlkZXJfU3RvcE9ic2VydmluZ01lZGlhU2lua3NfUGFyYW1zLCBwYXJhbXMpOwogICAgdmFyIG1lc3NhZ2UgPSBidWlsZGVyLmZpbmlzaCgpOwogICAgdGhpcy5yZWNlaXZlcl8uYWNjZXB0KG1lc3NhZ2UpOwogIH07CiAgTWVkaWFSb3V0ZVByb3ZpZGVyUHRyLnByb3RvdHlwZS5zdGFydE9ic2VydmluZ01lZGlhUm91dGVzID0gZnVuY3Rpb24oKSB7CiAgICByZXR1cm4gTWVkaWFSb3V0ZVByb3ZpZGVyUHJveHkucHJvdG90eXBlLnN0YXJ0T2JzZXJ2aW5nTWVkaWFSb3V0ZXMKICAgICAgICAuYXBwbHkodGhpcy5wdHIuZ2V0UHJveHkoKSwgYXJndW1lbnRzKTsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJQcm94eS5wcm90b3R5cGUuc3RhcnRPYnNlcnZpbmdNZWRpYVJvdXRlcyA9IGZ1bmN0aW9uKG1lZGlhU291cmNlKSB7CiAgICB2YXIgcGFyYW1zID0gbmV3IE1lZGlhUm91dGVQcm92aWRlcl9TdGFydE9ic2VydmluZ01lZGlhUm91dGVzX1BhcmFtcygpOwogICAgcGFyYW1zLm1lZGlhU291cmNlID0gbWVkaWFTb3VyY2U7CiAgICB2YXIgYnVpbGRlciA9IG5ldyBjb2RlYy5NZXNzYWdlVjBCdWlsZGVyKAogICAgICAgIGtNZWRpYVJvdXRlUHJvdmlkZXJfU3RhcnRPYnNlcnZpbmdNZWRpYVJvdXRlc19OYW1lLAogICAgICAgIGNvZGVjLmFsaWduKE1lZGlhUm91dGVQcm92aWRlcl9TdGFydE9ic2VydmluZ01lZGlhUm91dGVzX1BhcmFtcy5lbmNvZGVkU2l6ZSkpOwogICAgYnVpbGRlci5lbmNvZGVTdHJ1Y3QoTWVkaWFSb3V0ZVByb3ZpZGVyX1N0YXJ0T2JzZXJ2aW5nTWVkaWFSb3V0ZXNfUGFyYW1zLCBwYXJhbXMpOwogICAgdmFyIG1lc3NhZ2UgPSBidWlsZGVyLmZpbmlzaCgpOwogICAgdGhpcy5yZWNlaXZlcl8uYWNjZXB0KG1lc3NhZ2UpOwogIH07CiAgTWVkaWFSb3V0ZVByb3ZpZGVyUHRyLnByb3RvdHlwZS5zdG9wT2JzZXJ2aW5nTWVkaWFSb3V0ZXMgPSBmdW5jdGlvbigpIHsKICAgIHJldHVybiBNZWRpYVJvdXRlUHJvdmlkZXJQcm94eS5wcm90b3R5cGUuc3RvcE9ic2VydmluZ01lZGlhUm91dGVzCiAgICAgICAgLmFwcGx5KHRoaXMucHRyLmdldFByb3h5KCksIGFyZ3VtZW50cyk7CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyUHJveHkucHJvdG90eXBlLnN0b3BPYnNlcnZpbmdNZWRpYVJvdXRlcyA9IGZ1bmN0aW9uKG1lZGlhU291cmNlKSB7CiAgICB2YXIgcGFyYW1zID0gbmV3IE1lZGlhUm91dGVQcm92aWRlcl9TdG9wT2JzZXJ2aW5nTWVkaWFSb3V0ZXNfUGFyYW1zKCk7CiAgICBwYXJhbXMubWVkaWFTb3VyY2UgPSBtZWRpYVNvdXJjZTsKICAgIHZhciBidWlsZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VWMEJ1aWxkZXIoCiAgICAgICAga01lZGlhUm91dGVQcm92aWRlcl9TdG9wT2JzZXJ2aW5nTWVkaWFSb3V0ZXNfTmFtZSwKICAgICAgICBjb2RlYy5hbGlnbihNZWRpYVJvdXRlUHJvdmlkZXJfU3RvcE9ic2VydmluZ01lZGlhUm91dGVzX1BhcmFtcy5lbmNvZGVkU2l6ZSkpOwogICAgYnVpbGRlci5lbmNvZGVTdHJ1Y3QoTWVkaWFSb3V0ZVByb3ZpZGVyX1N0b3BPYnNlcnZpbmdNZWRpYVJvdXRlc19QYXJhbXMsIHBhcmFtcyk7CiAgICB2YXIgbWVzc2FnZSA9IGJ1aWxkZXIuZmluaXNoKCk7CiAgICB0aGlzLnJlY2VpdmVyXy5hY2NlcHQobWVzc2FnZSk7CiAgfTsKICBNZWRpYVJvdXRlUHJvdmlkZXJQdHIucHJvdG90eXBlLnN0YXJ0TGlzdGVuaW5nRm9yUm91dGVNZXNzYWdlcyA9IGZ1bmN0aW9uKCkgewogICAgcmV0dXJuIE1lZGlhUm91dGVQcm92aWRlclByb3h5LnByb3RvdHlwZS5zdGFydExpc3RlbmluZ0ZvclJvdXRlTWVzc2FnZXMKICAgICAgICAuYXBwbHkodGhpcy5wdHIuZ2V0UHJveHkoKSwgYXJndW1lbnRzKTsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJQcm94eS5wcm90b3R5cGUuc3RhcnRMaXN0ZW5pbmdGb3JSb3V0ZU1lc3NhZ2VzID0gZnVuY3Rpb24ocm91dGVJZCkgewogICAgdmFyIHBhcmFtcyA9IG5ldyBNZWRpYVJvdXRlUHJvdmlkZXJfU3RhcnRMaXN0ZW5pbmdGb3JSb3V0ZU1lc3NhZ2VzX1BhcmFtcygpOwogICAgcGFyYW1zLnJvdXRlSWQgPSByb3V0ZUlkOwogICAgdmFyIGJ1aWxkZXIgPSBuZXcgY29kZWMuTWVzc2FnZVYwQnVpbGRlcigKICAgICAgICBrTWVkaWFSb3V0ZVByb3ZpZGVyX1N0YXJ0TGlzdGVuaW5nRm9yUm91dGVNZXNzYWdlc19OYW1lLAogICAgICAgIGNvZGVjLmFsaWduKE1lZGlhUm91dGVQcm92aWRlcl9TdGFydExpc3RlbmluZ0ZvclJvdXRlTWVzc2FnZXNfUGFyYW1zLmVuY29kZWRTaXplKSk7CiAgICBidWlsZGVyLmVuY29kZVN0cnVjdChNZWRpYVJvdXRlUHJvdmlkZXJfU3RhcnRMaXN0ZW5pbmdGb3JSb3V0ZU1lc3NhZ2VzX1BhcmFtcywgcGFyYW1zKTsKICAgIHZhciBtZXNzYWdlID0gYnVpbGRlci5maW5pc2goKTsKICAgIHRoaXMucmVjZWl2ZXJfLmFjY2VwdChtZXNzYWdlKTsKICB9OwogIE1lZGlhUm91dGVQcm92aWRlclB0ci5wcm90b3R5cGUuc3RvcExpc3RlbmluZ0ZvclJvdXRlTWVzc2FnZXMgPSBmdW5jdGlvbigpIHsKICAgIHJldHVybiBNZWRpYVJvdXRlUHJvdmlkZXJQcm94eS5wcm90b3R5cGUuc3RvcExpc3RlbmluZ0ZvclJvdXRlTWVzc2FnZXMKICAgICAgICAuYXBwbHkodGhpcy5wdHIuZ2V0UHJveHkoKSwgYXJndW1lbnRzKTsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJQcm94eS5wcm90b3R5cGUuc3RvcExpc3RlbmluZ0ZvclJvdXRlTWVzc2FnZXMgPSBmdW5jdGlvbihyb3V0ZUlkKSB7CiAgICB2YXIgcGFyYW1zID0gbmV3IE1lZGlhUm91dGVQcm92aWRlcl9TdG9wTGlzdGVuaW5nRm9yUm91dGVNZXNzYWdlc19QYXJhbXMoKTsKICAgIHBhcmFtcy5yb3V0ZUlkID0gcm91dGVJZDsKICAgIHZhciBidWlsZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VWMEJ1aWxkZXIoCiAgICAgICAga01lZGlhUm91dGVQcm92aWRlcl9TdG9wTGlzdGVuaW5nRm9yUm91dGVNZXNzYWdlc19OYW1lLAogICAgICAgIGNvZGVjLmFsaWduKE1lZGlhUm91dGVQcm92aWRlcl9TdG9wTGlzdGVuaW5nRm9yUm91dGVNZXNzYWdlc19QYXJhbXMuZW5jb2RlZFNpemUpKTsKICAgIGJ1aWxkZXIuZW5jb2RlU3RydWN0KE1lZGlhUm91dGVQcm92aWRlcl9TdG9wTGlzdGVuaW5nRm9yUm91dGVNZXNzYWdlc19QYXJhbXMsIHBhcmFtcyk7CiAgICB2YXIgbWVzc2FnZSA9IGJ1aWxkZXIuZmluaXNoKCk7CiAgICB0aGlzLnJlY2VpdmVyXy5hY2NlcHQobWVzc2FnZSk7CiAgfTsKICBNZWRpYVJvdXRlUHJvdmlkZXJQdHIucHJvdG90eXBlLmRldGFjaFJvdXRlID0gZnVuY3Rpb24oKSB7CiAgICByZXR1cm4gTWVkaWFSb3V0ZVByb3ZpZGVyUHJveHkucHJvdG90eXBlLmRldGFjaFJvdXRlCiAgICAgICAgLmFwcGx5KHRoaXMucHRyLmdldFByb3h5KCksIGFyZ3VtZW50cyk7CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyUHJveHkucHJvdG90eXBlLmRldGFjaFJvdXRlID0gZnVuY3Rpb24ocm91dGVJZCkgewogICAgdmFyIHBhcmFtcyA9IG5ldyBNZWRpYVJvdXRlUHJvdmlkZXJfRGV0YWNoUm91dGVfUGFyYW1zKCk7CiAgICBwYXJhbXMucm91dGVJZCA9IHJvdXRlSWQ7CiAgICB2YXIgYnVpbGRlciA9IG5ldyBjb2RlYy5NZXNzYWdlVjBCdWlsZGVyKAogICAgICAgIGtNZWRpYVJvdXRlUHJvdmlkZXJfRGV0YWNoUm91dGVfTmFtZSwKICAgICAgICBjb2RlYy5hbGlnbihNZWRpYVJvdXRlUHJvdmlkZXJfRGV0YWNoUm91dGVfUGFyYW1zLmVuY29kZWRTaXplKSk7CiAgICBidWlsZGVyLmVuY29kZVN0cnVjdChNZWRpYVJvdXRlUHJvdmlkZXJfRGV0YWNoUm91dGVfUGFyYW1zLCBwYXJhbXMpOwogICAgdmFyIG1lc3NhZ2UgPSBidWlsZGVyLmZpbmlzaCgpOwogICAgdGhpcy5yZWNlaXZlcl8uYWNjZXB0KG1lc3NhZ2UpOwogIH07CiAgTWVkaWFSb3V0ZVByb3ZpZGVyUHRyLnByb3RvdHlwZS5lbmFibGVNZG5zRGlzY292ZXJ5ID0gZnVuY3Rpb24oKSB7CiAgICByZXR1cm4gTWVkaWFSb3V0ZVByb3ZpZGVyUHJveHkucHJvdG90eXBlLmVuYWJsZU1kbnNEaXNjb3ZlcnkKICAgICAgICAuYXBwbHkodGhpcy5wdHIuZ2V0UHJveHkoKSwgYXJndW1lbnRzKTsKICB9OwoKICBNZWRpYVJvdXRlUHJvdmlkZXJQcm94eS5wcm90b3R5cGUuZW5hYmxlTWRuc0Rpc2NvdmVyeSA9IGZ1bmN0aW9uKCkgewogICAgdmFyIHBhcmFtcyA9IG5ldyBNZWRpYVJvdXRlUHJvdmlkZXJfRW5hYmxlTWRuc0Rpc2NvdmVyeV9QYXJhbXMoKTsKICAgIHZhciBidWlsZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VWMEJ1aWxkZXIoCiAgICAgICAga01lZGlhUm91dGVQcm92aWRlcl9FbmFibGVNZG5zRGlzY292ZXJ5X05hbWUsCiAgICAgICAgY29kZWMuYWxpZ24oTWVkaWFSb3V0ZVByb3ZpZGVyX0VuYWJsZU1kbnNEaXNjb3ZlcnlfUGFyYW1zLmVuY29kZWRTaXplKSk7CiAgICBidWlsZGVyLmVuY29kZVN0cnVjdChNZWRpYVJvdXRlUHJvdmlkZXJfRW5hYmxlTWRuc0Rpc2NvdmVyeV9QYXJhbXMsIHBhcmFtcyk7CiAgICB2YXIgbWVzc2FnZSA9IGJ1aWxkZXIuZmluaXNoKCk7CiAgICB0aGlzLnJlY2VpdmVyXy5hY2NlcHQobWVzc2FnZSk7CiAgfTsKICBNZWRpYVJvdXRlUHJvdmlkZXJQdHIucHJvdG90eXBlLnVwZGF0ZU1lZGlhU2lua3MgPSBmdW5jdGlvbigpIHsKICAgIHJldHVybiBNZWRpYVJvdXRlUHJvdmlkZXJQcm94eS5wcm90b3R5cGUudXBkYXRlTWVkaWFTaW5rcwogICAgICAgIC5hcHBseSh0aGlzLnB0ci5nZXRQcm94eSgpLCBhcmd1bWVudHMpOwogIH07CgogIE1lZGlhUm91dGVQcm92aWRlclByb3h5LnByb3RvdHlwZS51cGRhdGVNZWRpYVNpbmtzID0gZnVuY3Rpb24obWVkaWFTb3VyY2UpIHsKICAgIHZhciBwYXJhbXMgPSBuZXcgTWVkaWFSb3V0ZVByb3ZpZGVyX1VwZGF0ZU1lZGlhU2lua3NfUGFyYW1zKCk7CiAgICBwYXJhbXMubWVkaWFTb3VyY2UgPSBtZWRpYVNvdXJjZTsKICAgIHZhciBidWlsZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VWMEJ1aWxkZXIoCiAgICAgICAga01lZGlhUm91dGVQcm92aWRlcl9VcGRhdGVNZWRpYVNpbmtzX05hbWUsCiAgICAgICAgY29kZWMuYWxpZ24oTWVkaWFSb3V0ZVByb3ZpZGVyX1VwZGF0ZU1lZGlhU2lua3NfUGFyYW1zLmVuY29kZWRTaXplKSk7CiAgICBidWlsZGVyLmVuY29kZVN0cnVjdChNZWRpYVJvdXRlUHJvdmlkZXJfVXBkYXRlTWVkaWFTaW5rc19QYXJhbXMsIHBhcmFtcyk7CiAgICB2YXIgbWVzc2FnZSA9IGJ1aWxkZXIuZmluaXNoKCk7CiAgICB0aGlzLnJlY2VpdmVyXy5hY2NlcHQobWVzc2FnZSk7CiAgfTsKICBNZWRpYVJvdXRlUHJvdmlkZXJQdHIucHJvdG90eXBlLnNlYXJjaFNpbmtzID0gZnVuY3Rpb24oKSB7CiAgICByZXR1cm4gTWVkaWFSb3V0ZVByb3ZpZGVyUHJveHkucHJvdG90eXBlLnNlYXJjaFNpbmtzCiAgICAgICAgLmFwcGx5KHRoaXMucHRyLmdldFByb3h5KCksIGFyZ3VtZW50cyk7CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyUHJveHkucHJvdG90eXBlLnNlYXJjaFNpbmtzID0gZnVuY3Rpb24oc2lua0lkLCBtZWRpYVNvdXJjZSwgc2VhcmNoQ3JpdGVyaWEpIHsKICAgIHZhciBwYXJhbXMgPSBuZXcgTWVkaWFSb3V0ZVByb3ZpZGVyX1NlYXJjaFNpbmtzX1BhcmFtcygpOwogICAgcGFyYW1zLnNpbmtJZCA9IHNpbmtJZDsKICAgIHBhcmFtcy5tZWRpYVNvdXJjZSA9IG1lZGlhU291cmNlOwogICAgcGFyYW1zLnNlYXJjaENyaXRlcmlhID0gc2VhcmNoQ3JpdGVyaWE7CiAgICByZXR1cm4gbmV3IFByb21pc2UoZnVuY3Rpb24ocmVzb2x2ZSwgcmVqZWN0KSB7CiAgICAgIHZhciBidWlsZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VWMUJ1aWxkZXIoCiAgICAgICAgICBrTWVkaWFSb3V0ZVByb3ZpZGVyX1NlYXJjaFNpbmtzX05hbWUsCiAgICAgICAgICBjb2RlYy5hbGlnbihNZWRpYVJvdXRlUHJvdmlkZXJfU2VhcmNoU2lua3NfUGFyYW1zLmVuY29kZWRTaXplKSwKICAgICAgICAgIGNvZGVjLmtNZXNzYWdlRXhwZWN0c1Jlc3BvbnNlLCAwKTsKICAgICAgYnVpbGRlci5lbmNvZGVTdHJ1Y3QoTWVkaWFSb3V0ZVByb3ZpZGVyX1NlYXJjaFNpbmtzX1BhcmFtcywgcGFyYW1zKTsKICAgICAgdmFyIG1lc3NhZ2UgPSBidWlsZGVyLmZpbmlzaCgpOwogICAgICB0aGlzLnJlY2VpdmVyXy5hY2NlcHRBbmRFeHBlY3RSZXNwb25zZShtZXNzYWdlKS50aGVuKGZ1bmN0aW9uKG1lc3NhZ2UpIHsKICAgICAgICB2YXIgcmVhZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VSZWFkZXIobWVzc2FnZSk7CiAgICAgICAgdmFyIHJlc3BvbnNlUGFyYW1zID0KICAgICAgICAgICAgcmVhZGVyLmRlY29kZVN0cnVjdChNZWRpYVJvdXRlUHJvdmlkZXJfU2VhcmNoU2lua3NfUmVzcG9uc2VQYXJhbXMpOwogICAgICAgIHJlc29sdmUocmVzcG9uc2VQYXJhbXMpOwogICAgICB9KS5jYXRjaChmdW5jdGlvbihyZXN1bHQpIHsKICAgICAgICByZWplY3QoRXJyb3IoIkNvbm5lY3Rpb24gZXJyb3I6ICIgKyByZXN1bHQpKTsKICAgICAgfSk7CiAgICB9LmJpbmQodGhpcykpOwogIH07CiAgTWVkaWFSb3V0ZVByb3ZpZGVyUHRyLnByb3RvdHlwZS5wcm92aWRlU2lua3MgPSBmdW5jdGlvbigpIHsKICAgIHJldHVybiBNZWRpYVJvdXRlUHJvdmlkZXJQcm94eS5wcm90b3R5cGUucHJvdmlkZVNpbmtzCiAgICAgICAgLmFwcGx5KHRoaXMucHRyLmdldFByb3h5KCksIGFyZ3VtZW50cyk7CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyUHJveHkucHJvdG90eXBlLnByb3ZpZGVTaW5rcyA9IGZ1bmN0aW9uKHByb3ZpZGVyTmFtZSwgc2lua3MpIHsKICAgIHZhciBwYXJhbXMgPSBuZXcgTWVkaWFSb3V0ZVByb3ZpZGVyX1Byb3ZpZGVTaW5rc19QYXJhbXMoKTsKICAgIHBhcmFtcy5wcm92aWRlck5hbWUgPSBwcm92aWRlck5hbWU7CiAgICBwYXJhbXMuc2lua3MgPSBzaW5rczsKICAgIHZhciBidWlsZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VWMEJ1aWxkZXIoCiAgICAgICAga01lZGlhUm91dGVQcm92aWRlcl9Qcm92aWRlU2lua3NfTmFtZSwKICAgICAgICBjb2RlYy5hbGlnbihNZWRpYVJvdXRlUHJvdmlkZXJfUHJvdmlkZVNpbmtzX1BhcmFtcy5lbmNvZGVkU2l6ZSkpOwogICAgYnVpbGRlci5lbmNvZGVTdHJ1Y3QoTWVkaWFSb3V0ZVByb3ZpZGVyX1Byb3ZpZGVTaW5rc19QYXJhbXMsIHBhcmFtcyk7CiAgICB2YXIgbWVzc2FnZSA9IGJ1aWxkZXIuZmluaXNoKCk7CiAgICB0aGlzLnJlY2VpdmVyXy5hY2NlcHQobWVzc2FnZSk7CiAgfTsKICBNZWRpYVJvdXRlUHJvdmlkZXJQdHIucHJvdG90eXBlLmNyZWF0ZU1lZGlhUm91dGVDb250cm9sbGVyID0gZnVuY3Rpb24oKSB7CiAgICByZXR1cm4gTWVkaWFSb3V0ZVByb3ZpZGVyUHJveHkucHJvdG90eXBlLmNyZWF0ZU1lZGlhUm91dGVDb250cm9sbGVyCiAgICAgICAgLmFwcGx5KHRoaXMucHRyLmdldFByb3h5KCksIGFyZ3VtZW50cyk7CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyUHJveHkucHJvdG90eXBlLmNyZWF0ZU1lZGlhUm91dGVDb250cm9sbGVyID0gZnVuY3Rpb24ocm91dGVJZCwgbWVkaWFDb250cm9sbGVyLCBvYnNlcnZlcikgewogICAgdmFyIHBhcmFtcyA9IG5ldyBNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlTWVkaWFSb3V0ZUNvbnRyb2xsZXJfUGFyYW1zKCk7CiAgICBwYXJhbXMucm91dGVJZCA9IHJvdXRlSWQ7CiAgICBwYXJhbXMubWVkaWFDb250cm9sbGVyID0gbWVkaWFDb250cm9sbGVyOwogICAgcGFyYW1zLm9ic2VydmVyID0gb2JzZXJ2ZXI7CiAgICByZXR1cm4gbmV3IFByb21pc2UoZnVuY3Rpb24ocmVzb2x2ZSwgcmVqZWN0KSB7CiAgICAgIHZhciBidWlsZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VWMUJ1aWxkZXIoCiAgICAgICAgICBrTWVkaWFSb3V0ZVByb3ZpZGVyX0NyZWF0ZU1lZGlhUm91dGVDb250cm9sbGVyX05hbWUsCiAgICAgICAgICBjb2RlYy5hbGlnbihNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlTWVkaWFSb3V0ZUNvbnRyb2xsZXJfUGFyYW1zLmVuY29kZWRTaXplKSwKICAgICAgICAgIGNvZGVjLmtNZXNzYWdlRXhwZWN0c1Jlc3BvbnNlLCAwKTsKICAgICAgYnVpbGRlci5lbmNvZGVTdHJ1Y3QoTWVkaWFSb3V0ZVByb3ZpZGVyX0NyZWF0ZU1lZGlhUm91dGVDb250cm9sbGVyX1BhcmFtcywgcGFyYW1zKTsKICAgICAgdmFyIG1lc3NhZ2UgPSBidWlsZGVyLmZpbmlzaCgpOwogICAgICB0aGlzLnJlY2VpdmVyXy5hY2NlcHRBbmRFeHBlY3RSZXNwb25zZShtZXNzYWdlKS50aGVuKGZ1bmN0aW9uKG1lc3NhZ2UpIHsKICAgICAgICB2YXIgcmVhZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VSZWFkZXIobWVzc2FnZSk7CiAgICAgICAgdmFyIHJlc3BvbnNlUGFyYW1zID0KICAgICAgICAgICAgcmVhZGVyLmRlY29kZVN0cnVjdChNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlTWVkaWFSb3V0ZUNvbnRyb2xsZXJfUmVzcG9uc2VQYXJhbXMpOwogICAgICAgIHJlc29sdmUocmVzcG9uc2VQYXJhbXMpOwogICAgICB9KS5jYXRjaChmdW5jdGlvbihyZXN1bHQpIHsKICAgICAgICByZWplY3QoRXJyb3IoIkNvbm5lY3Rpb24gZXJyb3I6ICIgKyByZXN1bHQpKTsKICAgICAgfSk7CiAgICB9LmJpbmQodGhpcykpOwogIH07CgogIGZ1bmN0aW9uIE1lZGlhUm91dGVQcm92aWRlclN0dWIoZGVsZWdhdGUpIHsKICAgIHRoaXMuZGVsZWdhdGVfID0gZGVsZWdhdGU7CiAgfQogIE1lZGlhUm91dGVQcm92aWRlclN0dWIucHJvdG90eXBlLmNyZWF0ZVJvdXRlID0gZnVuY3Rpb24obWVkaWFTb3VyY2UsIHNpbmtJZCwgb3JpZ2luYWxQcmVzZW50YXRpb25JZCwgb3JpZ2luLCB0YWJJZCwgdGltZW91dCwgaW5jb2duaXRvKSB7CiAgICByZXR1cm4gdGhpcy5kZWxlZ2F0ZV8gJiYgdGhpcy5kZWxlZ2F0ZV8uY3JlYXRlUm91dGUgJiYgdGhpcy5kZWxlZ2F0ZV8uY3JlYXRlUm91dGUobWVkaWFTb3VyY2UsIHNpbmtJZCwgb3JpZ2luYWxQcmVzZW50YXRpb25JZCwgb3JpZ2luLCB0YWJJZCwgdGltZW91dCwgaW5jb2duaXRvKTsKICB9CiAgTWVkaWFSb3V0ZVByb3ZpZGVyU3R1Yi5wcm90b3R5cGUuam9pblJvdXRlID0gZnVuY3Rpb24obWVkaWFTb3VyY2UsIHByZXNlbnRhdGlvbklkLCBvcmlnaW4sIHRhYklkLCB0aW1lb3V0LCBpbmNvZ25pdG8pIHsKICAgIHJldHVybiB0aGlzLmRlbGVnYXRlXyAmJiB0aGlzLmRlbGVnYXRlXy5qb2luUm91dGUgJiYgdGhpcy5kZWxlZ2F0ZV8uam9pblJvdXRlKG1lZGlhU291cmNlLCBwcmVzZW50YXRpb25JZCwgb3JpZ2luLCB0YWJJZCwgdGltZW91dCwgaW5jb2duaXRvKTsKICB9CiAgTWVkaWFSb3V0ZVByb3ZpZGVyU3R1Yi5wcm90b3R5cGUuY29ubmVjdFJvdXRlQnlSb3V0ZUlkID0gZnVuY3Rpb24obWVkaWFTb3VyY2UsIHJvdXRlSWQsIHByZXNlbnRhdGlvbklkLCBvcmlnaW4sIHRhYklkLCB0aW1lb3V0LCBpbmNvZ25pdG8pIHsKICAgIHJldHVybiB0aGlzLmRlbGVnYXRlXyAmJiB0aGlzLmRlbGVnYXRlXy5jb25uZWN0Um91dGVCeVJvdXRlSWQgJiYgdGhpcy5kZWxlZ2F0ZV8uY29ubmVjdFJvdXRlQnlSb3V0ZUlkKG1lZGlhU291cmNlLCByb3V0ZUlkLCBwcmVzZW50YXRpb25JZCwgb3JpZ2luLCB0YWJJZCwgdGltZW91dCwgaW5jb2duaXRvKTsKICB9CiAgTWVkaWFSb3V0ZVByb3ZpZGVyU3R1Yi5wcm90b3R5cGUudGVybWluYXRlUm91dGUgPSBmdW5jdGlvbihyb3V0ZUlkKSB7CiAgICByZXR1cm4gdGhpcy5kZWxlZ2F0ZV8gJiYgdGhpcy5kZWxlZ2F0ZV8udGVybWluYXRlUm91dGUgJiYgdGhpcy5kZWxlZ2F0ZV8udGVybWluYXRlUm91dGUocm91dGVJZCk7CiAgfQogIE1lZGlhUm91dGVQcm92aWRlclN0dWIucHJvdG90eXBlLnNlbmRSb3V0ZU1lc3NhZ2UgPSBmdW5jdGlvbihtZWRpYVJvdXRlSWQsIG1lc3NhZ2UpIHsKICAgIHJldHVybiB0aGlzLmRlbGVnYXRlXyAmJiB0aGlzLmRlbGVnYXRlXy5zZW5kUm91dGVNZXNzYWdlICYmIHRoaXMuZGVsZWdhdGVfLnNlbmRSb3V0ZU1lc3NhZ2UobWVkaWFSb3V0ZUlkLCBtZXNzYWdlKTsKICB9CiAgTWVkaWFSb3V0ZVByb3ZpZGVyU3R1Yi5wcm90b3R5cGUuc2VuZFJvdXRlQmluYXJ5TWVzc2FnZSA9IGZ1bmN0aW9uKG1lZGlhUm91dGVJZCwgZGF0YSkgewogICAgcmV0dXJuIHRoaXMuZGVsZWdhdGVfICYmIHRoaXMuZGVsZWdhdGVfLnNlbmRSb3V0ZUJpbmFyeU1lc3NhZ2UgJiYgdGhpcy5kZWxlZ2F0ZV8uc2VuZFJvdXRlQmluYXJ5TWVzc2FnZShtZWRpYVJvdXRlSWQsIGRhdGEpOwogIH0KICBNZWRpYVJvdXRlUHJvdmlkZXJTdHViLnByb3RvdHlwZS5zdGFydE9ic2VydmluZ01lZGlhU2lua3MgPSBmdW5jdGlvbihtZWRpYVNvdXJjZSkgewogICAgcmV0dXJuIHRoaXMuZGVsZWdhdGVfICYmIHRoaXMuZGVsZWdhdGVfLnN0YXJ0T2JzZXJ2aW5nTWVkaWFTaW5rcyAmJiB0aGlzLmRlbGVnYXRlXy5zdGFydE9ic2VydmluZ01lZGlhU2lua3MobWVkaWFTb3VyY2UpOwogIH0KICBNZWRpYVJvdXRlUHJvdmlkZXJTdHViLnByb3RvdHlwZS5zdG9wT2JzZXJ2aW5nTWVkaWFTaW5rcyA9IGZ1bmN0aW9uKG1lZGlhU291cmNlKSB7CiAgICByZXR1cm4gdGhpcy5kZWxlZ2F0ZV8gJiYgdGhpcy5kZWxlZ2F0ZV8uc3RvcE9ic2VydmluZ01lZGlhU2lua3MgJiYgdGhpcy5kZWxlZ2F0ZV8uc3RvcE9ic2VydmluZ01lZGlhU2lua3MobWVkaWFTb3VyY2UpOwogIH0KICBNZWRpYVJvdXRlUHJvdmlkZXJTdHViLnByb3RvdHlwZS5zdGFydE9ic2VydmluZ01lZGlhUm91dGVzID0gZnVuY3Rpb24obWVkaWFTb3VyY2UpIHsKICAgIHJldHVybiB0aGlzLmRlbGVnYXRlXyAmJiB0aGlzLmRlbGVnYXRlXy5zdGFydE9ic2VydmluZ01lZGlhUm91dGVzICYmIHRoaXMuZGVsZWdhdGVfLnN0YXJ0T2JzZXJ2aW5nTWVkaWFSb3V0ZXMobWVkaWFTb3VyY2UpOwogIH0KICBNZWRpYVJvdXRlUHJvdmlkZXJTdHViLnByb3RvdHlwZS5zdG9wT2JzZXJ2aW5nTWVkaWFSb3V0ZXMgPSBmdW5jdGlvbihtZWRpYVNvdXJjZSkgewogICAgcmV0dXJuIHRoaXMuZGVsZWdhdGVfICYmIHRoaXMuZGVsZWdhdGVfLnN0b3BPYnNlcnZpbmdNZWRpYVJvdXRlcyAmJiB0aGlzLmRlbGVnYXRlXy5zdG9wT2JzZXJ2aW5nTWVkaWFSb3V0ZXMobWVkaWFTb3VyY2UpOwogIH0KICBNZWRpYVJvdXRlUHJvdmlkZXJTdHViLnByb3RvdHlwZS5zdGFydExpc3RlbmluZ0ZvclJvdXRlTWVzc2FnZXMgPSBmdW5jdGlvbihyb3V0ZUlkKSB7CiAgICByZXR1cm4gdGhpcy5kZWxlZ2F0ZV8gJiYgdGhpcy5kZWxlZ2F0ZV8uc3RhcnRMaXN0ZW5pbmdGb3JSb3V0ZU1lc3NhZ2VzICYmIHRoaXMuZGVsZWdhdGVfLnN0YXJ0TGlzdGVuaW5nRm9yUm91dGVNZXNzYWdlcyhyb3V0ZUlkKTsKICB9CiAgTWVkaWFSb3V0ZVByb3ZpZGVyU3R1Yi5wcm90b3R5cGUuc3RvcExpc3RlbmluZ0ZvclJvdXRlTWVzc2FnZXMgPSBmdW5jdGlvbihyb3V0ZUlkKSB7CiAgICByZXR1cm4gdGhpcy5kZWxlZ2F0ZV8gJiYgdGhpcy5kZWxlZ2F0ZV8uc3RvcExpc3RlbmluZ0ZvclJvdXRlTWVzc2FnZXMgJiYgdGhpcy5kZWxlZ2F0ZV8uc3RvcExpc3RlbmluZ0ZvclJvdXRlTWVzc2FnZXMocm91dGVJZCk7CiAgfQogIE1lZGlhUm91dGVQcm92aWRlclN0dWIucHJvdG90eXBlLmRldGFjaFJvdXRlID0gZnVuY3Rpb24ocm91dGVJZCkgewogICAgcmV0dXJuIHRoaXMuZGVsZWdhdGVfICYmIHRoaXMuZGVsZWdhdGVfLmRldGFjaFJvdXRlICYmIHRoaXMuZGVsZWdhdGVfLmRldGFjaFJvdXRlKHJvdXRlSWQpOwogIH0KICBNZWRpYVJvdXRlUHJvdmlkZXJTdHViLnByb3RvdHlwZS5lbmFibGVNZG5zRGlzY292ZXJ5ID0gZnVuY3Rpb24oKSB7CiAgICByZXR1cm4gdGhpcy5kZWxlZ2F0ZV8gJiYgdGhpcy5kZWxlZ2F0ZV8uZW5hYmxlTWRuc0Rpc2NvdmVyeSAmJiB0aGlzLmRlbGVnYXRlXy5lbmFibGVNZG5zRGlzY292ZXJ5KCk7CiAgfQogIE1lZGlhUm91dGVQcm92aWRlclN0dWIucHJvdG90eXBlLnVwZGF0ZU1lZGlhU2lua3MgPSBmdW5jdGlvbihtZWRpYVNvdXJjZSkgewogICAgcmV0dXJuIHRoaXMuZGVsZWdhdGVfICYmIHRoaXMuZGVsZWdhdGVfLnVwZGF0ZU1lZGlhU2lua3MgJiYgdGhpcy5kZWxlZ2F0ZV8udXBkYXRlTWVkaWFTaW5rcyhtZWRpYVNvdXJjZSk7CiAgfQogIE1lZGlhUm91dGVQcm92aWRlclN0dWIucHJvdG90eXBlLnNlYXJjaFNpbmtzID0gZnVuY3Rpb24oc2lua0lkLCBtZWRpYVNvdXJjZSwgc2VhcmNoQ3JpdGVyaWEpIHsKICAgIHJldHVybiB0aGlzLmRlbGVnYXRlXyAmJiB0aGlzLmRlbGVnYXRlXy5zZWFyY2hTaW5rcyAmJiB0aGlzLmRlbGVnYXRlXy5zZWFyY2hTaW5rcyhzaW5rSWQsIG1lZGlhU291cmNlLCBzZWFyY2hDcml0ZXJpYSk7CiAgfQogIE1lZGlhUm91dGVQcm92aWRlclN0dWIucHJvdG90eXBlLnByb3ZpZGVTaW5rcyA9IGZ1bmN0aW9uKHByb3ZpZGVyTmFtZSwgc2lua3MpIHsKICAgIHJldHVybiB0aGlzLmRlbGVnYXRlXyAmJiB0aGlzLmRlbGVnYXRlXy5wcm92aWRlU2lua3MgJiYgdGhpcy5kZWxlZ2F0ZV8ucHJvdmlkZVNpbmtzKHByb3ZpZGVyTmFtZSwgc2lua3MpOwogIH0KICBNZWRpYVJvdXRlUHJvdmlkZXJTdHViLnByb3RvdHlwZS5jcmVhdGVNZWRpYVJvdXRlQ29udHJvbGxlciA9IGZ1bmN0aW9uKHJvdXRlSWQsIG1lZGlhQ29udHJvbGxlciwgb2JzZXJ2ZXIpIHsKICAgIHJldHVybiB0aGlzLmRlbGVnYXRlXyAmJiB0aGlzLmRlbGVnYXRlXy5jcmVhdGVNZWRpYVJvdXRlQ29udHJvbGxlciAmJiB0aGlzLmRlbGVnYXRlXy5jcmVhdGVNZWRpYVJvdXRlQ29udHJvbGxlcihyb3V0ZUlkLCBtZWRpYUNvbnRyb2xsZXIsIG9ic2VydmVyKTsKICB9CgogIE1lZGlhUm91dGVQcm92aWRlclN0dWIucHJvdG90eXBlLmFjY2VwdCA9IGZ1bmN0aW9uKG1lc3NhZ2UpIHsKICAgIHZhciByZWFkZXIgPSBuZXcgY29kZWMuTWVzc2FnZVJlYWRlcihtZXNzYWdlKTsKICAgIHN3aXRjaCAocmVhZGVyLm1lc3NhZ2VOYW1lKSB7CiAgICBjYXNlIGtNZWRpYVJvdXRlUHJvdmlkZXJfU3RhcnRPYnNlcnZpbmdNZWRpYVNpbmtzX05hbWU6CiAgICAgIHZhciBwYXJhbXMgPSByZWFkZXIuZGVjb2RlU3RydWN0KE1lZGlhUm91dGVQcm92aWRlcl9TdGFydE9ic2VydmluZ01lZGlhU2lua3NfUGFyYW1zKTsKICAgICAgdGhpcy5zdGFydE9ic2VydmluZ01lZGlhU2lua3MocGFyYW1zLm1lZGlhU291cmNlKTsKICAgICAgcmV0dXJuIHRydWU7CiAgICBjYXNlIGtNZWRpYVJvdXRlUHJvdmlkZXJfU3RvcE9ic2VydmluZ01lZGlhU2lua3NfTmFtZToKICAgICAgdmFyIHBhcmFtcyA9IHJlYWRlci5kZWNvZGVTdHJ1Y3QoTWVkaWFSb3V0ZVByb3ZpZGVyX1N0b3BPYnNlcnZpbmdNZWRpYVNpbmtzX1BhcmFtcyk7CiAgICAgIHRoaXMuc3RvcE9ic2VydmluZ01lZGlhU2lua3MocGFyYW1zLm1lZGlhU291cmNlKTsKICAgICAgcmV0dXJuIHRydWU7CiAgICBjYXNlIGtNZWRpYVJvdXRlUHJvdmlkZXJfU3RhcnRPYnNlcnZpbmdNZWRpYVJvdXRlc19OYW1lOgogICAgICB2YXIgcGFyYW1zID0gcmVhZGVyLmRlY29kZVN0cnVjdChNZWRpYVJvdXRlUHJvdmlkZXJfU3RhcnRPYnNlcnZpbmdNZWRpYVJvdXRlc19QYXJhbXMpOwogICAgICB0aGlzLnN0YXJ0T2JzZXJ2aW5nTWVkaWFSb3V0ZXMocGFyYW1zLm1lZGlhU291cmNlKTsKICAgICAgcmV0dXJuIHRydWU7CiAgICBjYXNlIGtNZWRpYVJvdXRlUHJvdmlkZXJfU3RvcE9ic2VydmluZ01lZGlhUm91dGVzX05hbWU6CiAgICAgIHZhciBwYXJhbXMgPSByZWFkZXIuZGVjb2RlU3RydWN0KE1lZGlhUm91dGVQcm92aWRlcl9TdG9wT2JzZXJ2aW5nTWVkaWFSb3V0ZXNfUGFyYW1zKTsKICAgICAgdGhpcy5zdG9wT2JzZXJ2aW5nTWVkaWFSb3V0ZXMocGFyYW1zLm1lZGlhU291cmNlKTsKICAgICAgcmV0dXJuIHRydWU7CiAgICBjYXNlIGtNZWRpYVJvdXRlUHJvdmlkZXJfU3RhcnRMaXN0ZW5pbmdGb3JSb3V0ZU1lc3NhZ2VzX05hbWU6CiAgICAgIHZhciBwYXJhbXMgPSByZWFkZXIuZGVjb2RlU3RydWN0KE1lZGlhUm91dGVQcm92aWRlcl9TdGFydExpc3RlbmluZ0ZvclJvdXRlTWVzc2FnZXNfUGFyYW1zKTsKICAgICAgdGhpcy5zdGFydExpc3RlbmluZ0ZvclJvdXRlTWVzc2FnZXMocGFyYW1zLnJvdXRlSWQpOwogICAgICByZXR1cm4gdHJ1ZTsKICAgIGNhc2Uga01lZGlhUm91dGVQcm92aWRlcl9TdG9wTGlzdGVuaW5nRm9yUm91dGVNZXNzYWdlc19OYW1lOgogICAgICB2YXIgcGFyYW1zID0gcmVhZGVyLmRlY29kZVN0cnVjdChNZWRpYVJvdXRlUHJvdmlkZXJfU3RvcExpc3RlbmluZ0ZvclJvdXRlTWVzc2FnZXNfUGFyYW1zKTsKICAgICAgdGhpcy5zdG9wTGlzdGVuaW5nRm9yUm91dGVNZXNzYWdlcyhwYXJhbXMucm91dGVJZCk7CiAgICAgIHJldHVybiB0cnVlOwogICAgY2FzZSBrTWVkaWFSb3V0ZVByb3ZpZGVyX0RldGFjaFJvdXRlX05hbWU6CiAgICAgIHZhciBwYXJhbXMgPSByZWFkZXIuZGVjb2RlU3RydWN0KE1lZGlhUm91dGVQcm92aWRlcl9EZXRhY2hSb3V0ZV9QYXJhbXMpOwogICAgICB0aGlzLmRldGFjaFJvdXRlKHBhcmFtcy5yb3V0ZUlkKTsKICAgICAgcmV0dXJuIHRydWU7CiAgICBjYXNlIGtNZWRpYVJvdXRlUHJvdmlkZXJfRW5hYmxlTWRuc0Rpc2NvdmVyeV9OYW1lOgogICAgICB2YXIgcGFyYW1zID0gcmVhZGVyLmRlY29kZVN0cnVjdChNZWRpYVJvdXRlUHJvdmlkZXJfRW5hYmxlTWRuc0Rpc2NvdmVyeV9QYXJhbXMpOwogICAgICB0aGlzLmVuYWJsZU1kbnNEaXNjb3ZlcnkoKTsKICAgICAgcmV0dXJuIHRydWU7CiAgICBjYXNlIGtNZWRpYVJvdXRlUHJvdmlkZXJfVXBkYXRlTWVkaWFTaW5rc19OYW1lOgogICAgICB2YXIgcGFyYW1zID0gcmVhZGVyLmRlY29kZVN0cnVjdChNZWRpYVJvdXRlUHJvdmlkZXJfVXBkYXRlTWVkaWFTaW5rc19QYXJhbXMpOwogICAgICB0aGlzLnVwZGF0ZU1lZGlhU2lua3MocGFyYW1zLm1lZGlhU291cmNlKTsKICAgICAgcmV0dXJuIHRydWU7CiAgICBjYXNlIGtNZWRpYVJvdXRlUHJvdmlkZXJfUHJvdmlkZVNpbmtzX05hbWU6CiAgICAgIHZhciBwYXJhbXMgPSByZWFkZXIuZGVjb2RlU3RydWN0KE1lZGlhUm91dGVQcm92aWRlcl9Qcm92aWRlU2lua3NfUGFyYW1zKTsKICAgICAgdGhpcy5wcm92aWRlU2lua3MocGFyYW1zLnByb3ZpZGVyTmFtZSwgcGFyYW1zLnNpbmtzKTsKICAgICAgcmV0dXJuIHRydWU7CiAgICBkZWZhdWx0OgogICAgICByZXR1cm4gZmFsc2U7CiAgICB9CiAgfTsKCiAgTWVkaWFSb3V0ZVByb3ZpZGVyU3R1Yi5wcm90b3R5cGUuYWNjZXB0V2l0aFJlc3BvbmRlciA9CiAgICAgIGZ1bmN0aW9uKG1lc3NhZ2UsIHJlc3BvbmRlcikgewogICAgdmFyIHJlYWRlciA9IG5ldyBjb2RlYy5NZXNzYWdlUmVhZGVyKG1lc3NhZ2UpOwogICAgc3dpdGNoIChyZWFkZXIubWVzc2FnZU5hbWUpIHsKICAgIGNhc2Uga01lZGlhUm91dGVQcm92aWRlcl9DcmVhdGVSb3V0ZV9OYW1lOgogICAgICB2YXIgcGFyYW1zID0gcmVhZGVyLmRlY29kZVN0cnVjdChNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlUm91dGVfUGFyYW1zKTsKICAgICAgdGhpcy5jcmVhdGVSb3V0ZShwYXJhbXMubWVkaWFTb3VyY2UsIHBhcmFtcy5zaW5rSWQsIHBhcmFtcy5vcmlnaW5hbFByZXNlbnRhdGlvbklkLCBwYXJhbXMub3JpZ2luLCBwYXJhbXMudGFiSWQsIHBhcmFtcy50aW1lb3V0LCBwYXJhbXMuaW5jb2duaXRvKS50aGVuKGZ1bmN0aW9uKHJlc3BvbnNlKSB7CiAgICAgICAgdmFyIHJlc3BvbnNlUGFyYW1zID0KICAgICAgICAgICAgbmV3IE1lZGlhUm91dGVQcm92aWRlcl9DcmVhdGVSb3V0ZV9SZXNwb25zZVBhcmFtcygpOwogICAgICAgIHJlc3BvbnNlUGFyYW1zLnJvdXRlID0gcmVzcG9uc2Uucm91dGU7CiAgICAgICAgcmVzcG9uc2VQYXJhbXMuZXJyb3JUZXh0ID0gcmVzcG9uc2UuZXJyb3JUZXh0OwogICAgICAgIHJlc3BvbnNlUGFyYW1zLnJlc3VsdENvZGUgPSByZXNwb25zZS5yZXN1bHRDb2RlOwogICAgICAgIHZhciBidWlsZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VWMUJ1aWxkZXIoCiAgICAgICAgICAgIGtNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlUm91dGVfTmFtZSwKICAgICAgICAgICAgY29kZWMuYWxpZ24oTWVkaWFSb3V0ZVByb3ZpZGVyX0NyZWF0ZVJvdXRlX1Jlc3BvbnNlUGFyYW1zLmVuY29kZWRTaXplKSwKICAgICAgICAgICAgY29kZWMua01lc3NhZ2VJc1Jlc3BvbnNlLCByZWFkZXIucmVxdWVzdElEKTsKICAgICAgICBidWlsZGVyLmVuY29kZVN0cnVjdChNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlUm91dGVfUmVzcG9uc2VQYXJhbXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcmVzcG9uc2VQYXJhbXMpOwogICAgICAgIHZhciBtZXNzYWdlID0gYnVpbGRlci5maW5pc2goKTsKICAgICAgICByZXNwb25kZXIuYWNjZXB0KG1lc3NhZ2UpOwogICAgICB9KTsKICAgICAgcmV0dXJuIHRydWU7CiAgICBjYXNlIGtNZWRpYVJvdXRlUHJvdmlkZXJfSm9pblJvdXRlX05hbWU6CiAgICAgIHZhciBwYXJhbXMgPSByZWFkZXIuZGVjb2RlU3RydWN0KE1lZGlhUm91dGVQcm92aWRlcl9Kb2luUm91dGVfUGFyYW1zKTsKICAgICAgdGhpcy5qb2luUm91dGUocGFyYW1zLm1lZGlhU291cmNlLCBwYXJhbXMucHJlc2VudGF0aW9uSWQsIHBhcmFtcy5vcmlnaW4sIHBhcmFtcy50YWJJZCwgcGFyYW1zLnRpbWVvdXQsIHBhcmFtcy5pbmNvZ25pdG8pLnRoZW4oZnVuY3Rpb24ocmVzcG9uc2UpIHsKICAgICAgICB2YXIgcmVzcG9uc2VQYXJhbXMgPQogICAgICAgICAgICBuZXcgTWVkaWFSb3V0ZVByb3ZpZGVyX0pvaW5Sb3V0ZV9SZXNwb25zZVBhcmFtcygpOwogICAgICAgIHJlc3BvbnNlUGFyYW1zLnJvdXRlID0gcmVzcG9uc2Uucm91dGU7CiAgICAgICAgcmVzcG9uc2VQYXJhbXMuZXJyb3JUZXh0ID0gcmVzcG9uc2UuZXJyb3JUZXh0OwogICAgICAgIHJlc3BvbnNlUGFyYW1zLnJlc3VsdENvZGUgPSByZXNwb25zZS5yZXN1bHRDb2RlOwogICAgICAgIHZhciBidWlsZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VWMUJ1aWxkZXIoCiAgICAgICAgICAgIGtNZWRpYVJvdXRlUHJvdmlkZXJfSm9pblJvdXRlX05hbWUsCiAgICAgICAgICAgIGNvZGVjLmFsaWduKE1lZGlhUm91dGVQcm92aWRlcl9Kb2luUm91dGVfUmVzcG9uc2VQYXJhbXMuZW5jb2RlZFNpemUpLAogICAgICAgICAgICBjb2RlYy5rTWVzc2FnZUlzUmVzcG9uc2UsIHJlYWRlci5yZXF1ZXN0SUQpOwogICAgICAgIGJ1aWxkZXIuZW5jb2RlU3RydWN0KE1lZGlhUm91dGVQcm92aWRlcl9Kb2luUm91dGVfUmVzcG9uc2VQYXJhbXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcmVzcG9uc2VQYXJhbXMpOwogICAgICAgIHZhciBtZXNzYWdlID0gYnVpbGRlci5maW5pc2goKTsKICAgICAgICByZXNwb25kZXIuYWNjZXB0KG1lc3NhZ2UpOwogICAgICB9KTsKICAgICAgcmV0dXJuIHRydWU7CiAgICBjYXNlIGtNZWRpYVJvdXRlUHJvdmlkZXJfQ29ubmVjdFJvdXRlQnlSb3V0ZUlkX05hbWU6CiAgICAgIHZhciBwYXJhbXMgPSByZWFkZXIuZGVjb2RlU3RydWN0KE1lZGlhUm91dGVQcm92aWRlcl9Db25uZWN0Um91dGVCeVJvdXRlSWRfUGFyYW1zKTsKICAgICAgdGhpcy5jb25uZWN0Um91dGVCeVJvdXRlSWQocGFyYW1zLm1lZGlhU291cmNlLCBwYXJhbXMucm91dGVJZCwgcGFyYW1zLnByZXNlbnRhdGlvbklkLCBwYXJhbXMub3JpZ2luLCBwYXJhbXMudGFiSWQsIHBhcmFtcy50aW1lb3V0LCBwYXJhbXMuaW5jb2duaXRvKS50aGVuKGZ1bmN0aW9uKHJlc3BvbnNlKSB7CiAgICAgICAgdmFyIHJlc3BvbnNlUGFyYW1zID0KICAgICAgICAgICAgbmV3IE1lZGlhUm91dGVQcm92aWRlcl9Db25uZWN0Um91dGVCeVJvdXRlSWRfUmVzcG9uc2VQYXJhbXMoKTsKICAgICAgICByZXNwb25zZVBhcmFtcy5yb3V0ZSA9IHJlc3BvbnNlLnJvdXRlOwogICAgICAgIHJlc3BvbnNlUGFyYW1zLmVycm9yVGV4dCA9IHJlc3BvbnNlLmVycm9yVGV4dDsKICAgICAgICByZXNwb25zZVBhcmFtcy5yZXN1bHRDb2RlID0gcmVzcG9uc2UucmVzdWx0Q29kZTsKICAgICAgICB2YXIgYnVpbGRlciA9IG5ldyBjb2RlYy5NZXNzYWdlVjFCdWlsZGVyKAogICAgICAgICAgICBrTWVkaWFSb3V0ZVByb3ZpZGVyX0Nvbm5lY3RSb3V0ZUJ5Um91dGVJZF9OYW1lLAogICAgICAgICAgICBjb2RlYy5hbGlnbihNZWRpYVJvdXRlUHJvdmlkZXJfQ29ubmVjdFJvdXRlQnlSb3V0ZUlkX1Jlc3BvbnNlUGFyYW1zLmVuY29kZWRTaXplKSwKICAgICAgICAgICAgY29kZWMua01lc3NhZ2VJc1Jlc3BvbnNlLCByZWFkZXIucmVxdWVzdElEKTsKICAgICAgICBidWlsZGVyLmVuY29kZVN0cnVjdChNZWRpYVJvdXRlUHJvdmlkZXJfQ29ubmVjdFJvdXRlQnlSb3V0ZUlkX1Jlc3BvbnNlUGFyYW1zLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJlc3BvbnNlUGFyYW1zKTsKICAgICAgICB2YXIgbWVzc2FnZSA9IGJ1aWxkZXIuZmluaXNoKCk7CiAgICAgICAgcmVzcG9uZGVyLmFjY2VwdChtZXNzYWdlKTsKICAgICAgfSk7CiAgICAgIHJldHVybiB0cnVlOwogICAgY2FzZSBrTWVkaWFSb3V0ZVByb3ZpZGVyX1Rlcm1pbmF0ZVJvdXRlX05hbWU6CiAgICAgIHZhciBwYXJhbXMgPSByZWFkZXIuZGVjb2RlU3RydWN0KE1lZGlhUm91dGVQcm92aWRlcl9UZXJtaW5hdGVSb3V0ZV9QYXJhbXMpOwogICAgICB0aGlzLnRlcm1pbmF0ZVJvdXRlKHBhcmFtcy5yb3V0ZUlkKS50aGVuKGZ1bmN0aW9uKHJlc3BvbnNlKSB7CiAgICAgICAgdmFyIHJlc3BvbnNlUGFyYW1zID0KICAgICAgICAgICAgbmV3IE1lZGlhUm91dGVQcm92aWRlcl9UZXJtaW5hdGVSb3V0ZV9SZXNwb25zZVBhcmFtcygpOwogICAgICAgIHJlc3BvbnNlUGFyYW1zLmVycm9yVGV4dCA9IHJlc3BvbnNlLmVycm9yVGV4dDsKICAgICAgICByZXNwb25zZVBhcmFtcy5yZXN1bHRDb2RlID0gcmVzcG9uc2UucmVzdWx0Q29kZTsKICAgICAgICB2YXIgYnVpbGRlciA9IG5ldyBjb2RlYy5NZXNzYWdlVjFCdWlsZGVyKAogICAgICAgICAgICBrTWVkaWFSb3V0ZVByb3ZpZGVyX1Rlcm1pbmF0ZVJvdXRlX05hbWUsCiAgICAgICAgICAgIGNvZGVjLmFsaWduKE1lZGlhUm91dGVQcm92aWRlcl9UZXJtaW5hdGVSb3V0ZV9SZXNwb25zZVBhcmFtcy5lbmNvZGVkU2l6ZSksCiAgICAgICAgICAgIGNvZGVjLmtNZXNzYWdlSXNSZXNwb25zZSwgcmVhZGVyLnJlcXVlc3RJRCk7CiAgICAgICAgYnVpbGRlci5lbmNvZGVTdHJ1Y3QoTWVkaWFSb3V0ZVByb3ZpZGVyX1Rlcm1pbmF0ZVJvdXRlX1Jlc3BvbnNlUGFyYW1zLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJlc3BvbnNlUGFyYW1zKTsKICAgICAgICB2YXIgbWVzc2FnZSA9IGJ1aWxkZXIuZmluaXNoKCk7CiAgICAgICAgcmVzcG9uZGVyLmFjY2VwdChtZXNzYWdlKTsKICAgICAgfSk7CiAgICAgIHJldHVybiB0cnVlOwogICAgY2FzZSBrTWVkaWFSb3V0ZVByb3ZpZGVyX1NlbmRSb3V0ZU1lc3NhZ2VfTmFtZToKICAgICAgdmFyIHBhcmFtcyA9IHJlYWRlci5kZWNvZGVTdHJ1Y3QoTWVkaWFSb3V0ZVByb3ZpZGVyX1NlbmRSb3V0ZU1lc3NhZ2VfUGFyYW1zKTsKICAgICAgdGhpcy5zZW5kUm91dGVNZXNzYWdlKHBhcmFtcy5tZWRpYVJvdXRlSWQsIHBhcmFtcy5tZXNzYWdlKS50aGVuKGZ1bmN0aW9uKHJlc3BvbnNlKSB7CiAgICAgICAgdmFyIHJlc3BvbnNlUGFyYW1zID0KICAgICAgICAgICAgbmV3IE1lZGlhUm91dGVQcm92aWRlcl9TZW5kUm91dGVNZXNzYWdlX1Jlc3BvbnNlUGFyYW1zKCk7CiAgICAgICAgcmVzcG9uc2VQYXJhbXMuc2VudCA9IHJlc3BvbnNlLnNlbnQ7CiAgICAgICAgdmFyIGJ1aWxkZXIgPSBuZXcgY29kZWMuTWVzc2FnZVYxQnVpbGRlcigKICAgICAgICAgICAga01lZGlhUm91dGVQcm92aWRlcl9TZW5kUm91dGVNZXNzYWdlX05hbWUsCiAgICAgICAgICAgIGNvZGVjLmFsaWduKE1lZGlhUm91dGVQcm92aWRlcl9TZW5kUm91dGVNZXNzYWdlX1Jlc3BvbnNlUGFyYW1zLmVuY29kZWRTaXplKSwKICAgICAgICAgICAgY29kZWMua01lc3NhZ2VJc1Jlc3BvbnNlLCByZWFkZXIucmVxdWVzdElEKTsKICAgICAgICBidWlsZGVyLmVuY29kZVN0cnVjdChNZWRpYVJvdXRlUHJvdmlkZXJfU2VuZFJvdXRlTWVzc2FnZV9SZXNwb25zZVBhcmFtcywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICByZXNwb25zZVBhcmFtcyk7CiAgICAgICAgdmFyIG1lc3NhZ2UgPSBidWlsZGVyLmZpbmlzaCgpOwogICAgICAgIHJlc3BvbmRlci5hY2NlcHQobWVzc2FnZSk7CiAgICAgIH0pOwogICAgICByZXR1cm4gdHJ1ZTsKICAgIGNhc2Uga01lZGlhUm91dGVQcm92aWRlcl9TZW5kUm91dGVCaW5hcnlNZXNzYWdlX05hbWU6CiAgICAgIHZhciBwYXJhbXMgPSByZWFkZXIuZGVjb2RlU3RydWN0KE1lZGlhUm91dGVQcm92aWRlcl9TZW5kUm91dGVCaW5hcnlNZXNzYWdlX1BhcmFtcyk7CiAgICAgIHRoaXMuc2VuZFJvdXRlQmluYXJ5TWVzc2FnZShwYXJhbXMubWVkaWFSb3V0ZUlkLCBwYXJhbXMuZGF0YSkudGhlbihmdW5jdGlvbihyZXNwb25zZSkgewogICAgICAgIHZhciByZXNwb25zZVBhcmFtcyA9CiAgICAgICAgICAgIG5ldyBNZWRpYVJvdXRlUHJvdmlkZXJfU2VuZFJvdXRlQmluYXJ5TWVzc2FnZV9SZXNwb25zZVBhcmFtcygpOwogICAgICAgIHJlc3BvbnNlUGFyYW1zLnNlbnQgPSByZXNwb25zZS5zZW50OwogICAgICAgIHZhciBidWlsZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VWMUJ1aWxkZXIoCiAgICAgICAgICAgIGtNZWRpYVJvdXRlUHJvdmlkZXJfU2VuZFJvdXRlQmluYXJ5TWVzc2FnZV9OYW1lLAogICAgICAgICAgICBjb2RlYy5hbGlnbihNZWRpYVJvdXRlUHJvdmlkZXJfU2VuZFJvdXRlQmluYXJ5TWVzc2FnZV9SZXNwb25zZVBhcmFtcy5lbmNvZGVkU2l6ZSksCiAgICAgICAgICAgIGNvZGVjLmtNZXNzYWdlSXNSZXNwb25zZSwgcmVhZGVyLnJlcXVlc3RJRCk7CiAgICAgICAgYnVpbGRlci5lbmNvZGVTdHJ1Y3QoTWVkaWFSb3V0ZVByb3ZpZGVyX1NlbmRSb3V0ZUJpbmFyeU1lc3NhZ2VfUmVzcG9uc2VQYXJhbXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcmVzcG9uc2VQYXJhbXMpOwogICAgICAgIHZhciBtZXNzYWdlID0gYnVpbGRlci5maW5pc2goKTsKICAgICAgICByZXNwb25kZXIuYWNjZXB0KG1lc3NhZ2UpOwogICAgICB9KTsKICAgICAgcmV0dXJuIHRydWU7CiAgICBjYXNlIGtNZWRpYVJvdXRlUHJvdmlkZXJfU2VhcmNoU2lua3NfTmFtZToKICAgICAgdmFyIHBhcmFtcyA9IHJlYWRlci5kZWNvZGVTdHJ1Y3QoTWVkaWFSb3V0ZVByb3ZpZGVyX1NlYXJjaFNpbmtzX1BhcmFtcyk7CiAgICAgIHRoaXMuc2VhcmNoU2lua3MocGFyYW1zLnNpbmtJZCwgcGFyYW1zLm1lZGlhU291cmNlLCBwYXJhbXMuc2VhcmNoQ3JpdGVyaWEpLnRoZW4oZnVuY3Rpb24ocmVzcG9uc2UpIHsKICAgICAgICB2YXIgcmVzcG9uc2VQYXJhbXMgPQogICAgICAgICAgICBuZXcgTWVkaWFSb3V0ZVByb3ZpZGVyX1NlYXJjaFNpbmtzX1Jlc3BvbnNlUGFyYW1zKCk7CiAgICAgICAgcmVzcG9uc2VQYXJhbXMuc2lua0lkID0gcmVzcG9uc2Uuc2lua0lkOwogICAgICAgIHZhciBidWlsZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VWMUJ1aWxkZXIoCiAgICAgICAgICAgIGtNZWRpYVJvdXRlUHJvdmlkZXJfU2VhcmNoU2lua3NfTmFtZSwKICAgICAgICAgICAgY29kZWMuYWxpZ24oTWVkaWFSb3V0ZVByb3ZpZGVyX1NlYXJjaFNpbmtzX1Jlc3BvbnNlUGFyYW1zLmVuY29kZWRTaXplKSwKICAgICAgICAgICAgY29kZWMua01lc3NhZ2VJc1Jlc3BvbnNlLCByZWFkZXIucmVxdWVzdElEKTsKICAgICAgICBidWlsZGVyLmVuY29kZVN0cnVjdChNZWRpYVJvdXRlUHJvdmlkZXJfU2VhcmNoU2lua3NfUmVzcG9uc2VQYXJhbXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcmVzcG9uc2VQYXJhbXMpOwogICAgICAgIHZhciBtZXNzYWdlID0gYnVpbGRlci5maW5pc2goKTsKICAgICAgICByZXNwb25kZXIuYWNjZXB0KG1lc3NhZ2UpOwogICAgICB9KTsKICAgICAgcmV0dXJuIHRydWU7CiAgICBjYXNlIGtNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlTWVkaWFSb3V0ZUNvbnRyb2xsZXJfTmFtZToKICAgICAgdmFyIHBhcmFtcyA9IHJlYWRlci5kZWNvZGVTdHJ1Y3QoTWVkaWFSb3V0ZVByb3ZpZGVyX0NyZWF0ZU1lZGlhUm91dGVDb250cm9sbGVyX1BhcmFtcyk7CiAgICAgIHRoaXMuY3JlYXRlTWVkaWFSb3V0ZUNvbnRyb2xsZXIocGFyYW1zLnJvdXRlSWQsIHBhcmFtcy5tZWRpYUNvbnRyb2xsZXIsIHBhcmFtcy5vYnNlcnZlcikudGhlbihmdW5jdGlvbihyZXNwb25zZSkgewogICAgICAgIHZhciByZXNwb25zZVBhcmFtcyA9CiAgICAgICAgICAgIG5ldyBNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlTWVkaWFSb3V0ZUNvbnRyb2xsZXJfUmVzcG9uc2VQYXJhbXMoKTsKICAgICAgICByZXNwb25zZVBhcmFtcy5zdWNjZXNzID0gcmVzcG9uc2Uuc3VjY2VzczsKICAgICAgICB2YXIgYnVpbGRlciA9IG5ldyBjb2RlYy5NZXNzYWdlVjFCdWlsZGVyKAogICAgICAgICAgICBrTWVkaWFSb3V0ZVByb3ZpZGVyX0NyZWF0ZU1lZGlhUm91dGVDb250cm9sbGVyX05hbWUsCiAgICAgICAgICAgIGNvZGVjLmFsaWduKE1lZGlhUm91dGVQcm92aWRlcl9DcmVhdGVNZWRpYVJvdXRlQ29udHJvbGxlcl9SZXNwb25zZVBhcmFtcy5lbmNvZGVkU2l6ZSksCiAgICAgICAgICAgIGNvZGVjLmtNZXNzYWdlSXNSZXNwb25zZSwgcmVhZGVyLnJlcXVlc3RJRCk7CiAgICAgICAgYnVpbGRlci5lbmNvZGVTdHJ1Y3QoTWVkaWFSb3V0ZVByb3ZpZGVyX0NyZWF0ZU1lZGlhUm91dGVDb250cm9sbGVyX1Jlc3BvbnNlUGFyYW1zLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJlc3BvbnNlUGFyYW1zKTsKICAgICAgICB2YXIgbWVzc2FnZSA9IGJ1aWxkZXIuZmluaXNoKCk7CiAgICAgICAgcmVzcG9uZGVyLmFjY2VwdChtZXNzYWdlKTsKICAgICAgfSk7CiAgICAgIHJldHVybiB0cnVlOwogICAgZGVmYXVsdDoKICAgICAgcmV0dXJuIGZhbHNlOwogICAgfQogIH07CgogIGZ1bmN0aW9uIHZhbGlkYXRlTWVkaWFSb3V0ZVByb3ZpZGVyUmVxdWVzdChtZXNzYWdlVmFsaWRhdG9yKSB7CiAgICB2YXIgbWVzc2FnZSA9IG1lc3NhZ2VWYWxpZGF0b3IubWVzc2FnZTsKICAgIHZhciBwYXJhbXNDbGFzcyA9IG51bGw7CiAgICBzd2l0Y2ggKG1lc3NhZ2UuZ2V0TmFtZSgpKSB7CiAgICAgIGNhc2Uga01lZGlhUm91dGVQcm92aWRlcl9DcmVhdGVSb3V0ZV9OYW1lOgogICAgICAgIGlmIChtZXNzYWdlLmV4cGVjdHNSZXNwb25zZSgpKQogICAgICAgICAgcGFyYW1zQ2xhc3MgPSBNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlUm91dGVfUGFyYW1zOwogICAgICBicmVhazsKICAgICAgY2FzZSBrTWVkaWFSb3V0ZVByb3ZpZGVyX0pvaW5Sb3V0ZV9OYW1lOgogICAgICAgIGlmIChtZXNzYWdlLmV4cGVjdHNSZXNwb25zZSgpKQogICAgICAgICAgcGFyYW1zQ2xhc3MgPSBNZWRpYVJvdXRlUHJvdmlkZXJfSm9pblJvdXRlX1BhcmFtczsKICAgICAgYnJlYWs7CiAgICAgIGNhc2Uga01lZGlhUm91dGVQcm92aWRlcl9Db25uZWN0Um91dGVCeVJvdXRlSWRfTmFtZToKICAgICAgICBpZiAobWVzc2FnZS5leHBlY3RzUmVzcG9uc2UoKSkKICAgICAgICAgIHBhcmFtc0NsYXNzID0gTWVkaWFSb3V0ZVByb3ZpZGVyX0Nvbm5lY3RSb3V0ZUJ5Um91dGVJZF9QYXJhbXM7CiAgICAgIGJyZWFrOwogICAgICBjYXNlIGtNZWRpYVJvdXRlUHJvdmlkZXJfVGVybWluYXRlUm91dGVfTmFtZToKICAgICAgICBpZiAobWVzc2FnZS5leHBlY3RzUmVzcG9uc2UoKSkKICAgICAgICAgIHBhcmFtc0NsYXNzID0gTWVkaWFSb3V0ZVByb3ZpZGVyX1Rlcm1pbmF0ZVJvdXRlX1BhcmFtczsKICAgICAgYnJlYWs7CiAgICAgIGNhc2Uga01lZGlhUm91dGVQcm92aWRlcl9TZW5kUm91dGVNZXNzYWdlX05hbWU6CiAgICAgICAgaWYgKG1lc3NhZ2UuZXhwZWN0c1Jlc3BvbnNlKCkpCiAgICAgICAgICBwYXJhbXNDbGFzcyA9IE1lZGlhUm91dGVQcm92aWRlcl9TZW5kUm91dGVNZXNzYWdlX1BhcmFtczsKICAgICAgYnJlYWs7CiAgICAgIGNhc2Uga01lZGlhUm91dGVQcm92aWRlcl9TZW5kUm91dGVCaW5hcnlNZXNzYWdlX05hbWU6CiAgICAgICAgaWYgKG1lc3NhZ2UuZXhwZWN0c1Jlc3BvbnNlKCkpCiAgICAgICAgICBwYXJhbXNDbGFzcyA9IE1lZGlhUm91dGVQcm92aWRlcl9TZW5kUm91dGVCaW5hcnlNZXNzYWdlX1BhcmFtczsKICAgICAgYnJlYWs7CiAgICAgIGNhc2Uga01lZGlhUm91dGVQcm92aWRlcl9TdGFydE9ic2VydmluZ01lZGlhU2lua3NfTmFtZToKICAgICAgICBpZiAoIW1lc3NhZ2UuZXhwZWN0c1Jlc3BvbnNlKCkgJiYgIW1lc3NhZ2UuaXNSZXNwb25zZSgpKQogICAgICAgICAgcGFyYW1zQ2xhc3MgPSBNZWRpYVJvdXRlUHJvdmlkZXJfU3RhcnRPYnNlcnZpbmdNZWRpYVNpbmtzX1BhcmFtczsKICAgICAgYnJlYWs7CiAgICAgIGNhc2Uga01lZGlhUm91dGVQcm92aWRlcl9TdG9wT2JzZXJ2aW5nTWVkaWFTaW5rc19OYW1lOgogICAgICAgIGlmICghbWVzc2FnZS5leHBlY3RzUmVzcG9uc2UoKSAmJiAhbWVzc2FnZS5pc1Jlc3BvbnNlKCkpCiAgICAgICAgICBwYXJhbXNDbGFzcyA9IE1lZGlhUm91dGVQcm92aWRlcl9TdG9wT2JzZXJ2aW5nTWVkaWFTaW5rc19QYXJhbXM7CiAgICAgIGJyZWFrOwogICAgICBjYXNlIGtNZWRpYVJvdXRlUHJvdmlkZXJfU3RhcnRPYnNlcnZpbmdNZWRpYVJvdXRlc19OYW1lOgogICAgICAgIGlmICghbWVzc2FnZS5leHBlY3RzUmVzcG9uc2UoKSAmJiAhbWVzc2FnZS5pc1Jlc3BvbnNlKCkpCiAgICAgICAgICBwYXJhbXNDbGFzcyA9IE1lZGlhUm91dGVQcm92aWRlcl9TdGFydE9ic2VydmluZ01lZGlhUm91dGVzX1BhcmFtczsKICAgICAgYnJlYWs7CiAgICAgIGNhc2Uga01lZGlhUm91dGVQcm92aWRlcl9TdG9wT2JzZXJ2aW5nTWVkaWFSb3V0ZXNfTmFtZToKICAgICAgICBpZiAoIW1lc3NhZ2UuZXhwZWN0c1Jlc3BvbnNlKCkgJiYgIW1lc3NhZ2UuaXNSZXNwb25zZSgpKQogICAgICAgICAgcGFyYW1zQ2xhc3MgPSBNZWRpYVJvdXRlUHJvdmlkZXJfU3RvcE9ic2VydmluZ01lZGlhUm91dGVzX1BhcmFtczsKICAgICAgYnJlYWs7CiAgICAgIGNhc2Uga01lZGlhUm91dGVQcm92aWRlcl9TdGFydExpc3RlbmluZ0ZvclJvdXRlTWVzc2FnZXNfTmFtZToKICAgICAgICBpZiAoIW1lc3NhZ2UuZXhwZWN0c1Jlc3BvbnNlKCkgJiYgIW1lc3NhZ2UuaXNSZXNwb25zZSgpKQogICAgICAgICAgcGFyYW1zQ2xhc3MgPSBNZWRpYVJvdXRlUHJvdmlkZXJfU3RhcnRMaXN0ZW5pbmdGb3JSb3V0ZU1lc3NhZ2VzX1BhcmFtczsKICAgICAgYnJlYWs7CiAgICAgIGNhc2Uga01lZGlhUm91dGVQcm92aWRlcl9TdG9wTGlzdGVuaW5nRm9yUm91dGVNZXNzYWdlc19OYW1lOgogICAgICAgIGlmICghbWVzc2FnZS5leHBlY3RzUmVzcG9uc2UoKSAmJiAhbWVzc2FnZS5pc1Jlc3BvbnNlKCkpCiAgICAgICAgICBwYXJhbXNDbGFzcyA9IE1lZGlhUm91dGVQcm92aWRlcl9TdG9wTGlzdGVuaW5nRm9yUm91dGVNZXNzYWdlc19QYXJhbXM7CiAgICAgIGJyZWFrOwogICAgICBjYXNlIGtNZWRpYVJvdXRlUHJvdmlkZXJfRGV0YWNoUm91dGVfTmFtZToKICAgICAgICBpZiAoIW1lc3NhZ2UuZXhwZWN0c1Jlc3BvbnNlKCkgJiYgIW1lc3NhZ2UuaXNSZXNwb25zZSgpKQogICAgICAgICAgcGFyYW1zQ2xhc3MgPSBNZWRpYVJvdXRlUHJvdmlkZXJfRGV0YWNoUm91dGVfUGFyYW1zOwogICAgICBicmVhazsKICAgICAgY2FzZSBrTWVkaWFSb3V0ZVByb3ZpZGVyX0VuYWJsZU1kbnNEaXNjb3ZlcnlfTmFtZToKICAgICAgICBpZiAoIW1lc3NhZ2UuZXhwZWN0c1Jlc3BvbnNlKCkgJiYgIW1lc3NhZ2UuaXNSZXNwb25zZSgpKQogICAgICAgICAgcGFyYW1zQ2xhc3MgPSBNZWRpYVJvdXRlUHJvdmlkZXJfRW5hYmxlTWRuc0Rpc2NvdmVyeV9QYXJhbXM7CiAgICAgIGJyZWFrOwogICAgICBjYXNlIGtNZWRpYVJvdXRlUHJvdmlkZXJfVXBkYXRlTWVkaWFTaW5rc19OYW1lOgogICAgICAgIGlmICghbWVzc2FnZS5leHBlY3RzUmVzcG9uc2UoKSAmJiAhbWVzc2FnZS5pc1Jlc3BvbnNlKCkpCiAgICAgICAgICBwYXJhbXNDbGFzcyA9IE1lZGlhUm91dGVQcm92aWRlcl9VcGRhdGVNZWRpYVNpbmtzX1BhcmFtczsKICAgICAgYnJlYWs7CiAgICAgIGNhc2Uga01lZGlhUm91dGVQcm92aWRlcl9TZWFyY2hTaW5rc19OYW1lOgogICAgICAgIGlmIChtZXNzYWdlLmV4cGVjdHNSZXNwb25zZSgpKQogICAgICAgICAgcGFyYW1zQ2xhc3MgPSBNZWRpYVJvdXRlUHJvdmlkZXJfU2VhcmNoU2lua3NfUGFyYW1zOwogICAgICBicmVhazsKICAgICAgY2FzZSBrTWVkaWFSb3V0ZVByb3ZpZGVyX1Byb3ZpZGVTaW5rc19OYW1lOgogICAgICAgIGlmICghbWVzc2FnZS5leHBlY3RzUmVzcG9uc2UoKSAmJiAhbWVzc2FnZS5pc1Jlc3BvbnNlKCkpCiAgICAgICAgICBwYXJhbXNDbGFzcyA9IE1lZGlhUm91dGVQcm92aWRlcl9Qcm92aWRlU2lua3NfUGFyYW1zOwogICAgICBicmVhazsKICAgICAgY2FzZSBrTWVkaWFSb3V0ZVByb3ZpZGVyX0NyZWF0ZU1lZGlhUm91dGVDb250cm9sbGVyX05hbWU6CiAgICAgICAgaWYgKG1lc3NhZ2UuZXhwZWN0c1Jlc3BvbnNlKCkpCiAgICAgICAgICBwYXJhbXNDbGFzcyA9IE1lZGlhUm91dGVQcm92aWRlcl9DcmVhdGVNZWRpYVJvdXRlQ29udHJvbGxlcl9QYXJhbXM7CiAgICAgIGJyZWFrOwogICAgfQogICAgaWYgKHBhcmFtc0NsYXNzID09PSBudWxsKQogICAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogICAgcmV0dXJuIHBhcmFtc0NsYXNzLnZhbGlkYXRlKG1lc3NhZ2VWYWxpZGF0b3IsIG1lc3NhZ2VWYWxpZGF0b3IubWVzc2FnZS5nZXRIZWFkZXJOdW1CeXRlcygpKTsKICB9CgogIGZ1bmN0aW9uIHZhbGlkYXRlTWVkaWFSb3V0ZVByb3ZpZGVyUmVzcG9uc2UobWVzc2FnZVZhbGlkYXRvcikgewogICB2YXIgbWVzc2FnZSA9IG1lc3NhZ2VWYWxpZGF0b3IubWVzc2FnZTsKICAgdmFyIHBhcmFtc0NsYXNzID0gbnVsbDsKICAgc3dpdGNoIChtZXNzYWdlLmdldE5hbWUoKSkgewogICAgICBjYXNlIGtNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlUm91dGVfTmFtZToKICAgICAgICBpZiAobWVzc2FnZS5pc1Jlc3BvbnNlKCkpCiAgICAgICAgICBwYXJhbXNDbGFzcyA9IE1lZGlhUm91dGVQcm92aWRlcl9DcmVhdGVSb3V0ZV9SZXNwb25zZVBhcmFtczsKICAgICAgICBicmVhazsKICAgICAgY2FzZSBrTWVkaWFSb3V0ZVByb3ZpZGVyX0pvaW5Sb3V0ZV9OYW1lOgogICAgICAgIGlmIChtZXNzYWdlLmlzUmVzcG9uc2UoKSkKICAgICAgICAgIHBhcmFtc0NsYXNzID0gTWVkaWFSb3V0ZVByb3ZpZGVyX0pvaW5Sb3V0ZV9SZXNwb25zZVBhcmFtczsKICAgICAgICBicmVhazsKICAgICAgY2FzZSBrTWVkaWFSb3V0ZVByb3ZpZGVyX0Nvbm5lY3RSb3V0ZUJ5Um91dGVJZF9OYW1lOgogICAgICAgIGlmIChtZXNzYWdlLmlzUmVzcG9uc2UoKSkKICAgICAgICAgIHBhcmFtc0NsYXNzID0gTWVkaWFSb3V0ZVByb3ZpZGVyX0Nvbm5lY3RSb3V0ZUJ5Um91dGVJZF9SZXNwb25zZVBhcmFtczsKICAgICAgICBicmVhazsKICAgICAgY2FzZSBrTWVkaWFSb3V0ZVByb3ZpZGVyX1Rlcm1pbmF0ZVJvdXRlX05hbWU6CiAgICAgICAgaWYgKG1lc3NhZ2UuaXNSZXNwb25zZSgpKQogICAgICAgICAgcGFyYW1zQ2xhc3MgPSBNZWRpYVJvdXRlUHJvdmlkZXJfVGVybWluYXRlUm91dGVfUmVzcG9uc2VQYXJhbXM7CiAgICAgICAgYnJlYWs7CiAgICAgIGNhc2Uga01lZGlhUm91dGVQcm92aWRlcl9TZW5kUm91dGVNZXNzYWdlX05hbWU6CiAgICAgICAgaWYgKG1lc3NhZ2UuaXNSZXNwb25zZSgpKQogICAgICAgICAgcGFyYW1zQ2xhc3MgPSBNZWRpYVJvdXRlUHJvdmlkZXJfU2VuZFJvdXRlTWVzc2FnZV9SZXNwb25zZVBhcmFtczsKICAgICAgICBicmVhazsKICAgICAgY2FzZSBrTWVkaWFSb3V0ZVByb3ZpZGVyX1NlbmRSb3V0ZUJpbmFyeU1lc3NhZ2VfTmFtZToKICAgICAgICBpZiAobWVzc2FnZS5pc1Jlc3BvbnNlKCkpCiAgICAgICAgICBwYXJhbXNDbGFzcyA9IE1lZGlhUm91dGVQcm92aWRlcl9TZW5kUm91dGVCaW5hcnlNZXNzYWdlX1Jlc3BvbnNlUGFyYW1zOwogICAgICAgIGJyZWFrOwogICAgICBjYXNlIGtNZWRpYVJvdXRlUHJvdmlkZXJfU2VhcmNoU2lua3NfTmFtZToKICAgICAgICBpZiAobWVzc2FnZS5pc1Jlc3BvbnNlKCkpCiAgICAgICAgICBwYXJhbXNDbGFzcyA9IE1lZGlhUm91dGVQcm92aWRlcl9TZWFyY2hTaW5rc19SZXNwb25zZVBhcmFtczsKICAgICAgICBicmVhazsKICAgICAgY2FzZSBrTWVkaWFSb3V0ZVByb3ZpZGVyX0NyZWF0ZU1lZGlhUm91dGVDb250cm9sbGVyX05hbWU6CiAgICAgICAgaWYgKG1lc3NhZ2UuaXNSZXNwb25zZSgpKQogICAgICAgICAgcGFyYW1zQ2xhc3MgPSBNZWRpYVJvdXRlUHJvdmlkZXJfQ3JlYXRlTWVkaWFSb3V0ZUNvbnRyb2xsZXJfUmVzcG9uc2VQYXJhbXM7CiAgICAgICAgYnJlYWs7CiAgICB9CiAgICBpZiAocGFyYW1zQ2xhc3MgPT09IG51bGwpCiAgICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgICByZXR1cm4gcGFyYW1zQ2xhc3MudmFsaWRhdGUobWVzc2FnZVZhbGlkYXRvciwgbWVzc2FnZVZhbGlkYXRvci5tZXNzYWdlLmdldEhlYWRlck51bUJ5dGVzKCkpOwogIH0KCiAgdmFyIE1lZGlhUm91dGVQcm92aWRlciA9IHsKICAgIG5hbWU6ICdtZWRpYV9yb3V0ZXI6Om1vam9tOjpNZWRpYVJvdXRlUHJvdmlkZXInLAogICAga1ZlcnNpb246IDAsCiAgICBwdHJDbGFzczogTWVkaWFSb3V0ZVByb3ZpZGVyUHRyLAogICAgcHJveHlDbGFzczogTWVkaWFSb3V0ZVByb3ZpZGVyUHJveHksCiAgICBzdHViQ2xhc3M6IE1lZGlhUm91dGVQcm92aWRlclN0dWIsCiAgICB2YWxpZGF0ZVJlcXVlc3Q6IHZhbGlkYXRlTWVkaWFSb3V0ZVByb3ZpZGVyUmVxdWVzdCwKICAgIHZhbGlkYXRlUmVzcG9uc2U6IHZhbGlkYXRlTWVkaWFSb3V0ZVByb3ZpZGVyUmVzcG9uc2UsCiAgfTsKICBNZWRpYVJvdXRlUHJvdmlkZXIuSWQgPSB7fTsKICBNZWRpYVJvdXRlUHJvdmlkZXIuSWQuRVhURU5TSU9OID0gMDsKICBNZWRpYVJvdXRlUHJvdmlkZXIuSWQuV0lSRURfRElTUExBWSA9IE1lZGlhUm91dGVQcm92aWRlci5JZC5FWFRFTlNJT04gKyAxOwoKICBNZWRpYVJvdXRlUHJvdmlkZXIuSWQuaXNLbm93bkVudW1WYWx1ZSA9IGZ1bmN0aW9uKHZhbHVlKSB7CiAgICBzd2l0Y2ggKHZhbHVlKSB7CiAgICBjYXNlIDA6CiAgICBjYXNlIDE6CiAgICAgIHJldHVybiB0cnVlOwogICAgfQogICAgcmV0dXJuIGZhbHNlOwogIH07CgogIE1lZGlhUm91dGVQcm92aWRlci5JZC52YWxpZGF0ZSA9IGZ1bmN0aW9uKGVudW1WYWx1ZSkgewogICAgdmFyIGlzRXh0ZW5zaWJsZSA9IGZhbHNlOwogICAgaWYgKGlzRXh0ZW5zaWJsZSB8fCB0aGlzLmlzS25vd25FbnVtVmFsdWUoZW51bVZhbHVlKSkKICAgICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5VTktOT1dOX0VOVU1fVkFMVUU7CiAgfTsKICBNZWRpYVJvdXRlUHJvdmlkZXJTdHViLnByb3RvdHlwZS52YWxpZGF0b3IgPSB2YWxpZGF0ZU1lZGlhUm91dGVQcm92aWRlclJlcXVlc3Q7CiAgTWVkaWFSb3V0ZVByb3ZpZGVyUHJveHkucHJvdG90eXBlLnZhbGlkYXRvciA9IHZhbGlkYXRlTWVkaWFSb3V0ZVByb3ZpZGVyUmVzcG9uc2U7CiAgdmFyIGtNZWRpYVJvdXRlcl9SZWdpc3Rlck1lZGlhUm91dGVQcm92aWRlcl9OYW1lID0gMTM3MTExOTIxNzsKICB2YXIga01lZGlhUm91dGVyX09uU2lua3NSZWNlaXZlZF9OYW1lID0gMTI3Nzg0MDM5MTsKICB2YXIga01lZGlhUm91dGVyX09uSXNzdWVfTmFtZSA9IDExMTgyMDQwNzA7CiAgdmFyIGtNZWRpYVJvdXRlcl9PblJvdXRlc1VwZGF0ZWRfTmFtZSA9IDk1OTgyMjM5NjsKICB2YXIga01lZGlhUm91dGVyX09uU2lua0F2YWlsYWJpbGl0eVVwZGF0ZWRfTmFtZSA9IDE1ODI1NTE3OTg7CiAgdmFyIGtNZWRpYVJvdXRlcl9PblByZXNlbnRhdGlvbkNvbm5lY3Rpb25TdGF0ZUNoYW5nZWRfTmFtZSA9IDEzNjcwNDM3MDU7CiAgdmFyIGtNZWRpYVJvdXRlcl9PblByZXNlbnRhdGlvbkNvbm5lY3Rpb25DbG9zZWRfTmFtZSA9IDE3MDEwNTc0MTsKICB2YXIga01lZGlhUm91dGVyX09uUm91dGVNZXNzYWdlc1JlY2VpdmVkX05hbWUgPSAyNzcwNTQwNjM7CiAgdmFyIGtNZWRpYVJvdXRlcl9Pbk1lZGlhUmVtb3RlckNyZWF0ZWRfTmFtZSA9IDY5NzE2MzE0OwoKICBmdW5jdGlvbiBNZWRpYVJvdXRlclB0cihoYW5kbGVPclB0ckluZm8pIHsKICAgIHRoaXMucHRyID0gbmV3IGJpbmRpbmdzLkludGVyZmFjZVB0ckNvbnRyb2xsZXIoTWVkaWFSb3V0ZXIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGhhbmRsZU9yUHRySW5mbyk7CiAgfQoKICBmdW5jdGlvbiBNZWRpYVJvdXRlckFzc29jaWF0ZWRQdHIoYXNzb2NpYXRlZEludGVyZmFjZVB0ckluZm8pIHsKICAgIHRoaXMucHRyID0gbmV3IGFzc29jaWF0ZWRCaW5kaW5ncy5Bc3NvY2lhdGVkSW50ZXJmYWNlUHRyQ29udHJvbGxlcigKICAgICAgICBNZWRpYVJvdXRlciwgYXNzb2NpYXRlZEludGVyZmFjZVB0ckluZm8pOwogIH0KCiAgTWVkaWFSb3V0ZXJBc3NvY2lhdGVkUHRyLnByb3RvdHlwZSA9CiAgICAgIE9iamVjdC5jcmVhdGUoTWVkaWFSb3V0ZXJQdHIucHJvdG90eXBlKTsKICBNZWRpYVJvdXRlckFzc29jaWF0ZWRQdHIucHJvdG90eXBlLmNvbnN0cnVjdG9yID0KICAgICAgTWVkaWFSb3V0ZXJBc3NvY2lhdGVkUHRyOwoKICBmdW5jdGlvbiBNZWRpYVJvdXRlclByb3h5KHJlY2VpdmVyKSB7CiAgICB0aGlzLnJlY2VpdmVyXyA9IHJlY2VpdmVyOwogIH0KICBNZWRpYVJvdXRlclB0ci5wcm90b3R5cGUucmVnaXN0ZXJNZWRpYVJvdXRlUHJvdmlkZXIgPSBmdW5jdGlvbigpIHsKICAgIHJldHVybiBNZWRpYVJvdXRlclByb3h5LnByb3RvdHlwZS5yZWdpc3Rlck1lZGlhUm91dGVQcm92aWRlcgogICAgICAgIC5hcHBseSh0aGlzLnB0ci5nZXRQcm94eSgpLCBhcmd1bWVudHMpOwogIH07CgogIE1lZGlhUm91dGVyUHJveHkucHJvdG90eXBlLnJlZ2lzdGVyTWVkaWFSb3V0ZVByb3ZpZGVyID0gZnVuY3Rpb24ocHJvdmlkZXJJZCwgbWVkaWFSb3V0ZXJQcm92aWRlcikgewogICAgdmFyIHBhcmFtcyA9IG5ldyBNZWRpYVJvdXRlcl9SZWdpc3Rlck1lZGlhUm91dGVQcm92aWRlcl9QYXJhbXMoKTsKICAgIHBhcmFtcy5wcm92aWRlcklkID0gcHJvdmlkZXJJZDsKICAgIHBhcmFtcy5tZWRpYVJvdXRlclByb3ZpZGVyID0gbWVkaWFSb3V0ZXJQcm92aWRlcjsKICAgIHJldHVybiBuZXcgUHJvbWlzZShmdW5jdGlvbihyZXNvbHZlLCByZWplY3QpIHsKICAgICAgdmFyIGJ1aWxkZXIgPSBuZXcgY29kZWMuTWVzc2FnZVYxQnVpbGRlcigKICAgICAgICAgIGtNZWRpYVJvdXRlcl9SZWdpc3Rlck1lZGlhUm91dGVQcm92aWRlcl9OYW1lLAogICAgICAgICAgY29kZWMuYWxpZ24oTWVkaWFSb3V0ZXJfUmVnaXN0ZXJNZWRpYVJvdXRlUHJvdmlkZXJfUGFyYW1zLmVuY29kZWRTaXplKSwKICAgICAgICAgIGNvZGVjLmtNZXNzYWdlRXhwZWN0c1Jlc3BvbnNlLCAwKTsKICAgICAgYnVpbGRlci5lbmNvZGVTdHJ1Y3QoTWVkaWFSb3V0ZXJfUmVnaXN0ZXJNZWRpYVJvdXRlUHJvdmlkZXJfUGFyYW1zLCBwYXJhbXMpOwogICAgICB2YXIgbWVzc2FnZSA9IGJ1aWxkZXIuZmluaXNoKCk7CiAgICAgIHRoaXMucmVjZWl2ZXJfLmFjY2VwdEFuZEV4cGVjdFJlc3BvbnNlKG1lc3NhZ2UpLnRoZW4oZnVuY3Rpb24obWVzc2FnZSkgewogICAgICAgIHZhciByZWFkZXIgPSBuZXcgY29kZWMuTWVzc2FnZVJlYWRlcihtZXNzYWdlKTsKICAgICAgICB2YXIgcmVzcG9uc2VQYXJhbXMgPQogICAgICAgICAgICByZWFkZXIuZGVjb2RlU3RydWN0KE1lZGlhUm91dGVyX1JlZ2lzdGVyTWVkaWFSb3V0ZVByb3ZpZGVyX1Jlc3BvbnNlUGFyYW1zKTsKICAgICAgICByZXNvbHZlKHJlc3BvbnNlUGFyYW1zKTsKICAgICAgfSkuY2F0Y2goZnVuY3Rpb24ocmVzdWx0KSB7CiAgICAgICAgcmVqZWN0KEVycm9yKCJDb25uZWN0aW9uIGVycm9yOiAiICsgcmVzdWx0KSk7CiAgICAgIH0pOwogICAgfS5iaW5kKHRoaXMpKTsKICB9OwogIE1lZGlhUm91dGVyUHRyLnByb3RvdHlwZS5vblNpbmtzUmVjZWl2ZWQgPSBmdW5jdGlvbigpIHsKICAgIHJldHVybiBNZWRpYVJvdXRlclByb3h5LnByb3RvdHlwZS5vblNpbmtzUmVjZWl2ZWQKICAgICAgICAuYXBwbHkodGhpcy5wdHIuZ2V0UHJveHkoKSwgYXJndW1lbnRzKTsKICB9OwoKICBNZWRpYVJvdXRlclByb3h5LnByb3RvdHlwZS5vblNpbmtzUmVjZWl2ZWQgPSBmdW5jdGlvbihwcm92aWRlcklkLCBtZWRpYVNvdXJjZSwgc2lua3MsIG9yaWdpbnMpIHsKICAgIHZhciBwYXJhbXMgPSBuZXcgTWVkaWFSb3V0ZXJfT25TaW5rc1JlY2VpdmVkX1BhcmFtcygpOwogICAgcGFyYW1zLnByb3ZpZGVySWQgPSBwcm92aWRlcklkOwogICAgcGFyYW1zLm1lZGlhU291cmNlID0gbWVkaWFTb3VyY2U7CiAgICBwYXJhbXMuc2lua3MgPSBzaW5rczsKICAgIHBhcmFtcy5vcmlnaW5zID0gb3JpZ2luczsKICAgIHZhciBidWlsZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VWMEJ1aWxkZXIoCiAgICAgICAga01lZGlhUm91dGVyX09uU2lua3NSZWNlaXZlZF9OYW1lLAogICAgICAgIGNvZGVjLmFsaWduKE1lZGlhUm91dGVyX09uU2lua3NSZWNlaXZlZF9QYXJhbXMuZW5jb2RlZFNpemUpKTsKICAgIGJ1aWxkZXIuZW5jb2RlU3RydWN0KE1lZGlhUm91dGVyX09uU2lua3NSZWNlaXZlZF9QYXJhbXMsIHBhcmFtcyk7CiAgICB2YXIgbWVzc2FnZSA9IGJ1aWxkZXIuZmluaXNoKCk7CiAgICB0aGlzLnJlY2VpdmVyXy5hY2NlcHQobWVzc2FnZSk7CiAgfTsKICBNZWRpYVJvdXRlclB0ci5wcm90b3R5cGUub25Jc3N1ZSA9IGZ1bmN0aW9uKCkgewogICAgcmV0dXJuIE1lZGlhUm91dGVyUHJveHkucHJvdG90eXBlLm9uSXNzdWUKICAgICAgICAuYXBwbHkodGhpcy5wdHIuZ2V0UHJveHkoKSwgYXJndW1lbnRzKTsKICB9OwoKICBNZWRpYVJvdXRlclByb3h5LnByb3RvdHlwZS5vbklzc3VlID0gZnVuY3Rpb24oaXNzdWUpIHsKICAgIHZhciBwYXJhbXMgPSBuZXcgTWVkaWFSb3V0ZXJfT25Jc3N1ZV9QYXJhbXMoKTsKICAgIHBhcmFtcy5pc3N1ZSA9IGlzc3VlOwogICAgdmFyIGJ1aWxkZXIgPSBuZXcgY29kZWMuTWVzc2FnZVYwQnVpbGRlcigKICAgICAgICBrTWVkaWFSb3V0ZXJfT25Jc3N1ZV9OYW1lLAogICAgICAgIGNvZGVjLmFsaWduKE1lZGlhUm91dGVyX09uSXNzdWVfUGFyYW1zLmVuY29kZWRTaXplKSk7CiAgICBidWlsZGVyLmVuY29kZVN0cnVjdChNZWRpYVJvdXRlcl9Pbklzc3VlX1BhcmFtcywgcGFyYW1zKTsKICAgIHZhciBtZXNzYWdlID0gYnVpbGRlci5maW5pc2goKTsKICAgIHRoaXMucmVjZWl2ZXJfLmFjY2VwdChtZXNzYWdlKTsKICB9OwogIE1lZGlhUm91dGVyUHRyLnByb3RvdHlwZS5vblJvdXRlc1VwZGF0ZWQgPSBmdW5jdGlvbigpIHsKICAgIHJldHVybiBNZWRpYVJvdXRlclByb3h5LnByb3RvdHlwZS5vblJvdXRlc1VwZGF0ZWQKICAgICAgICAuYXBwbHkodGhpcy5wdHIuZ2V0UHJveHkoKSwgYXJndW1lbnRzKTsKICB9OwoKICBNZWRpYVJvdXRlclByb3h5LnByb3RvdHlwZS5vblJvdXRlc1VwZGF0ZWQgPSBmdW5jdGlvbihwcm92aWRlcklkLCByb3V0ZXMsIG1lZGlhU291cmNlLCBqb2luYWJsZVJvdXRlSWRzKSB7CiAgICB2YXIgcGFyYW1zID0gbmV3IE1lZGlhUm91dGVyX09uUm91dGVzVXBkYXRlZF9QYXJhbXMoKTsKICAgIHBhcmFtcy5wcm92aWRlcklkID0gcHJvdmlkZXJJZDsKICAgIHBhcmFtcy5yb3V0ZXMgPSByb3V0ZXM7CiAgICBwYXJhbXMubWVkaWFTb3VyY2UgPSBtZWRpYVNvdXJjZTsKICAgIHBhcmFtcy5qb2luYWJsZVJvdXRlSWRzID0gam9pbmFibGVSb3V0ZUlkczsKICAgIHZhciBidWlsZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VWMEJ1aWxkZXIoCiAgICAgICAga01lZGlhUm91dGVyX09uUm91dGVzVXBkYXRlZF9OYW1lLAogICAgICAgIGNvZGVjLmFsaWduKE1lZGlhUm91dGVyX09uUm91dGVzVXBkYXRlZF9QYXJhbXMuZW5jb2RlZFNpemUpKTsKICAgIGJ1aWxkZXIuZW5jb2RlU3RydWN0KE1lZGlhUm91dGVyX09uUm91dGVzVXBkYXRlZF9QYXJhbXMsIHBhcmFtcyk7CiAgICB2YXIgbWVzc2FnZSA9IGJ1aWxkZXIuZmluaXNoKCk7CiAgICB0aGlzLnJlY2VpdmVyXy5hY2NlcHQobWVzc2FnZSk7CiAgfTsKICBNZWRpYVJvdXRlclB0ci5wcm90b3R5cGUub25TaW5rQXZhaWxhYmlsaXR5VXBkYXRlZCA9IGZ1bmN0aW9uKCkgewogICAgcmV0dXJuIE1lZGlhUm91dGVyUHJveHkucHJvdG90eXBlLm9uU2lua0F2YWlsYWJpbGl0eVVwZGF0ZWQKICAgICAgICAuYXBwbHkodGhpcy5wdHIuZ2V0UHJveHkoKSwgYXJndW1lbnRzKTsKICB9OwoKICBNZWRpYVJvdXRlclByb3h5LnByb3RvdHlwZS5vblNpbmtBdmFpbGFiaWxpdHlVcGRhdGVkID0gZnVuY3Rpb24ocHJvdmlkZXJJZCwgYXZhaWxhYmlsaXR5KSB7CiAgICB2YXIgcGFyYW1zID0gbmV3IE1lZGlhUm91dGVyX09uU2lua0F2YWlsYWJpbGl0eVVwZGF0ZWRfUGFyYW1zKCk7CiAgICBwYXJhbXMucHJvdmlkZXJJZCA9IHByb3ZpZGVySWQ7CiAgICBwYXJhbXMuYXZhaWxhYmlsaXR5ID0gYXZhaWxhYmlsaXR5OwogICAgdmFyIGJ1aWxkZXIgPSBuZXcgY29kZWMuTWVzc2FnZVYwQnVpbGRlcigKICAgICAgICBrTWVkaWFSb3V0ZXJfT25TaW5rQXZhaWxhYmlsaXR5VXBkYXRlZF9OYW1lLAogICAgICAgIGNvZGVjLmFsaWduKE1lZGlhUm91dGVyX09uU2lua0F2YWlsYWJpbGl0eVVwZGF0ZWRfUGFyYW1zLmVuY29kZWRTaXplKSk7CiAgICBidWlsZGVyLmVuY29kZVN0cnVjdChNZWRpYVJvdXRlcl9PblNpbmtBdmFpbGFiaWxpdHlVcGRhdGVkX1BhcmFtcywgcGFyYW1zKTsKICAgIHZhciBtZXNzYWdlID0gYnVpbGRlci5maW5pc2goKTsKICAgIHRoaXMucmVjZWl2ZXJfLmFjY2VwdChtZXNzYWdlKTsKICB9OwogIE1lZGlhUm91dGVyUHRyLnByb3RvdHlwZS5vblByZXNlbnRhdGlvbkNvbm5lY3Rpb25TdGF0ZUNoYW5nZWQgPSBmdW5jdGlvbigpIHsKICAgIHJldHVybiBNZWRpYVJvdXRlclByb3h5LnByb3RvdHlwZS5vblByZXNlbnRhdGlvbkNvbm5lY3Rpb25TdGF0ZUNoYW5nZWQKICAgICAgICAuYXBwbHkodGhpcy5wdHIuZ2V0UHJveHkoKSwgYXJndW1lbnRzKTsKICB9OwoKICBNZWRpYVJvdXRlclByb3h5LnByb3RvdHlwZS5vblByZXNlbnRhdGlvbkNvbm5lY3Rpb25TdGF0ZUNoYW5nZWQgPSBmdW5jdGlvbihyb3V0ZUlkLCBzdGF0ZSkgewogICAgdmFyIHBhcmFtcyA9IG5ldyBNZWRpYVJvdXRlcl9PblByZXNlbnRhdGlvbkNvbm5lY3Rpb25TdGF0ZUNoYW5nZWRfUGFyYW1zKCk7CiAgICBwYXJhbXMucm91dGVJZCA9IHJvdXRlSWQ7CiAgICBwYXJhbXMuc3RhdGUgPSBzdGF0ZTsKICAgIHZhciBidWlsZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VWMEJ1aWxkZXIoCiAgICAgICAga01lZGlhUm91dGVyX09uUHJlc2VudGF0aW9uQ29ubmVjdGlvblN0YXRlQ2hhbmdlZF9OYW1lLAogICAgICAgIGNvZGVjLmFsaWduKE1lZGlhUm91dGVyX09uUHJlc2VudGF0aW9uQ29ubmVjdGlvblN0YXRlQ2hhbmdlZF9QYXJhbXMuZW5jb2RlZFNpemUpKTsKICAgIGJ1aWxkZXIuZW5jb2RlU3RydWN0KE1lZGlhUm91dGVyX09uUHJlc2VudGF0aW9uQ29ubmVjdGlvblN0YXRlQ2hhbmdlZF9QYXJhbXMsIHBhcmFtcyk7CiAgICB2YXIgbWVzc2FnZSA9IGJ1aWxkZXIuZmluaXNoKCk7CiAgICB0aGlzLnJlY2VpdmVyXy5hY2NlcHQobWVzc2FnZSk7CiAgfTsKICBNZWRpYVJvdXRlclB0ci5wcm90b3R5cGUub25QcmVzZW50YXRpb25Db25uZWN0aW9uQ2xvc2VkID0gZnVuY3Rpb24oKSB7CiAgICByZXR1cm4gTWVkaWFSb3V0ZXJQcm94eS5wcm90b3R5cGUub25QcmVzZW50YXRpb25Db25uZWN0aW9uQ2xvc2VkCiAgICAgICAgLmFwcGx5KHRoaXMucHRyLmdldFByb3h5KCksIGFyZ3VtZW50cyk7CiAgfTsKCiAgTWVkaWFSb3V0ZXJQcm94eS5wcm90b3R5cGUub25QcmVzZW50YXRpb25Db25uZWN0aW9uQ2xvc2VkID0gZnVuY3Rpb24ocm91dGVJZCwgcmVhc29uLCBtZXNzYWdlKSB7CiAgICB2YXIgcGFyYW1zID0gbmV3IE1lZGlhUm91dGVyX09uUHJlc2VudGF0aW9uQ29ubmVjdGlvbkNsb3NlZF9QYXJhbXMoKTsKICAgIHBhcmFtcy5yb3V0ZUlkID0gcm91dGVJZDsKICAgIHBhcmFtcy5yZWFzb24gPSByZWFzb247CiAgICBwYXJhbXMubWVzc2FnZSA9IG1lc3NhZ2U7CiAgICB2YXIgYnVpbGRlciA9IG5ldyBjb2RlYy5NZXNzYWdlVjBCdWlsZGVyKAogICAgICAgIGtNZWRpYVJvdXRlcl9PblByZXNlbnRhdGlvbkNvbm5lY3Rpb25DbG9zZWRfTmFtZSwKICAgICAgICBjb2RlYy5hbGlnbihNZWRpYVJvdXRlcl9PblByZXNlbnRhdGlvbkNvbm5lY3Rpb25DbG9zZWRfUGFyYW1zLmVuY29kZWRTaXplKSk7CiAgICBidWlsZGVyLmVuY29kZVN0cnVjdChNZWRpYVJvdXRlcl9PblByZXNlbnRhdGlvbkNvbm5lY3Rpb25DbG9zZWRfUGFyYW1zLCBwYXJhbXMpOwogICAgdmFyIG1lc3NhZ2UgPSBidWlsZGVyLmZpbmlzaCgpOwogICAgdGhpcy5yZWNlaXZlcl8uYWNjZXB0KG1lc3NhZ2UpOwogIH07CiAgTWVkaWFSb3V0ZXJQdHIucHJvdG90eXBlLm9uUm91dGVNZXNzYWdlc1JlY2VpdmVkID0gZnVuY3Rpb24oKSB7CiAgICByZXR1cm4gTWVkaWFSb3V0ZXJQcm94eS5wcm90b3R5cGUub25Sb3V0ZU1lc3NhZ2VzUmVjZWl2ZWQKICAgICAgICAuYXBwbHkodGhpcy5wdHIuZ2V0UHJveHkoKSwgYXJndW1lbnRzKTsKICB9OwoKICBNZWRpYVJvdXRlclByb3h5LnByb3RvdHlwZS5vblJvdXRlTWVzc2FnZXNSZWNlaXZlZCA9IGZ1bmN0aW9uKHJvdXRlSWQsIG1lc3NhZ2VzKSB7CiAgICB2YXIgcGFyYW1zID0gbmV3IE1lZGlhUm91dGVyX09uUm91dGVNZXNzYWdlc1JlY2VpdmVkX1BhcmFtcygpOwogICAgcGFyYW1zLnJvdXRlSWQgPSByb3V0ZUlkOwogICAgcGFyYW1zLm1lc3NhZ2VzID0gbWVzc2FnZXM7CiAgICB2YXIgYnVpbGRlciA9IG5ldyBjb2RlYy5NZXNzYWdlVjBCdWlsZGVyKAogICAgICAgIGtNZWRpYVJvdXRlcl9PblJvdXRlTWVzc2FnZXNSZWNlaXZlZF9OYW1lLAogICAgICAgIGNvZGVjLmFsaWduKE1lZGlhUm91dGVyX09uUm91dGVNZXNzYWdlc1JlY2VpdmVkX1BhcmFtcy5lbmNvZGVkU2l6ZSkpOwogICAgYnVpbGRlci5lbmNvZGVTdHJ1Y3QoTWVkaWFSb3V0ZXJfT25Sb3V0ZU1lc3NhZ2VzUmVjZWl2ZWRfUGFyYW1zLCBwYXJhbXMpOwogICAgdmFyIG1lc3NhZ2UgPSBidWlsZGVyLmZpbmlzaCgpOwogICAgdGhpcy5yZWNlaXZlcl8uYWNjZXB0KG1lc3NhZ2UpOwogIH07CiAgTWVkaWFSb3V0ZXJQdHIucHJvdG90eXBlLm9uTWVkaWFSZW1vdGVyQ3JlYXRlZCA9IGZ1bmN0aW9uKCkgewogICAgcmV0dXJuIE1lZGlhUm91dGVyUHJveHkucHJvdG90eXBlLm9uTWVkaWFSZW1vdGVyQ3JlYXRlZAogICAgICAgIC5hcHBseSh0aGlzLnB0ci5nZXRQcm94eSgpLCBhcmd1bWVudHMpOwogIH07CgogIE1lZGlhUm91dGVyUHJveHkucHJvdG90eXBlLm9uTWVkaWFSZW1vdGVyQ3JlYXRlZCA9IGZ1bmN0aW9uKHRhYklkLCByZW1vdGVyLCByZW1vdGluZ1NvdXJjZSkgewogICAgdmFyIHBhcmFtcyA9IG5ldyBNZWRpYVJvdXRlcl9Pbk1lZGlhUmVtb3RlckNyZWF0ZWRfUGFyYW1zKCk7CiAgICBwYXJhbXMudGFiSWQgPSB0YWJJZDsKICAgIHBhcmFtcy5yZW1vdGVyID0gcmVtb3RlcjsKICAgIHBhcmFtcy5yZW1vdGluZ1NvdXJjZSA9IHJlbW90aW5nU291cmNlOwogICAgdmFyIGJ1aWxkZXIgPSBuZXcgY29kZWMuTWVzc2FnZVYwQnVpbGRlcigKICAgICAgICBrTWVkaWFSb3V0ZXJfT25NZWRpYVJlbW90ZXJDcmVhdGVkX05hbWUsCiAgICAgICAgY29kZWMuYWxpZ24oTWVkaWFSb3V0ZXJfT25NZWRpYVJlbW90ZXJDcmVhdGVkX1BhcmFtcy5lbmNvZGVkU2l6ZSkpOwogICAgYnVpbGRlci5lbmNvZGVTdHJ1Y3QoTWVkaWFSb3V0ZXJfT25NZWRpYVJlbW90ZXJDcmVhdGVkX1BhcmFtcywgcGFyYW1zKTsKICAgIHZhciBtZXNzYWdlID0gYnVpbGRlci5maW5pc2goKTsKICAgIHRoaXMucmVjZWl2ZXJfLmFjY2VwdChtZXNzYWdlKTsKICB9OwoKICBmdW5jdGlvbiBNZWRpYVJvdXRlclN0dWIoZGVsZWdhdGUpIHsKICAgIHRoaXMuZGVsZWdhdGVfID0gZGVsZWdhdGU7CiAgfQogIE1lZGlhUm91dGVyU3R1Yi5wcm90b3R5cGUucmVnaXN0ZXJNZWRpYVJvdXRlUHJvdmlkZXIgPSBmdW5jdGlvbihwcm92aWRlcklkLCBtZWRpYVJvdXRlclByb3ZpZGVyKSB7CiAgICByZXR1cm4gdGhpcy5kZWxlZ2F0ZV8gJiYgdGhpcy5kZWxlZ2F0ZV8ucmVnaXN0ZXJNZWRpYVJvdXRlUHJvdmlkZXIgJiYgdGhpcy5kZWxlZ2F0ZV8ucmVnaXN0ZXJNZWRpYVJvdXRlUHJvdmlkZXIocHJvdmlkZXJJZCwgbWVkaWFSb3V0ZXJQcm92aWRlcik7CiAgfQogIE1lZGlhUm91dGVyU3R1Yi5wcm90b3R5cGUub25TaW5rc1JlY2VpdmVkID0gZnVuY3Rpb24ocHJvdmlkZXJJZCwgbWVkaWFTb3VyY2UsIHNpbmtzLCBvcmlnaW5zKSB7CiAgICByZXR1cm4gdGhpcy5kZWxlZ2F0ZV8gJiYgdGhpcy5kZWxlZ2F0ZV8ub25TaW5rc1JlY2VpdmVkICYmIHRoaXMuZGVsZWdhdGVfLm9uU2lua3NSZWNlaXZlZChwcm92aWRlcklkLCBtZWRpYVNvdXJjZSwgc2lua3MsIG9yaWdpbnMpOwogIH0KICBNZWRpYVJvdXRlclN0dWIucHJvdG90eXBlLm9uSXNzdWUgPSBmdW5jdGlvbihpc3N1ZSkgewogICAgcmV0dXJuIHRoaXMuZGVsZWdhdGVfICYmIHRoaXMuZGVsZWdhdGVfLm9uSXNzdWUgJiYgdGhpcy5kZWxlZ2F0ZV8ub25Jc3N1ZShpc3N1ZSk7CiAgfQogIE1lZGlhUm91dGVyU3R1Yi5wcm90b3R5cGUub25Sb3V0ZXNVcGRhdGVkID0gZnVuY3Rpb24ocHJvdmlkZXJJZCwgcm91dGVzLCBtZWRpYVNvdXJjZSwgam9pbmFibGVSb3V0ZUlkcykgewogICAgcmV0dXJuIHRoaXMuZGVsZWdhdGVfICYmIHRoaXMuZGVsZWdhdGVfLm9uUm91dGVzVXBkYXRlZCAmJiB0aGlzLmRlbGVnYXRlXy5vblJvdXRlc1VwZGF0ZWQocHJvdmlkZXJJZCwgcm91dGVzLCBtZWRpYVNvdXJjZSwgam9pbmFibGVSb3V0ZUlkcyk7CiAgfQogIE1lZGlhUm91dGVyU3R1Yi5wcm90b3R5cGUub25TaW5rQXZhaWxhYmlsaXR5VXBkYXRlZCA9IGZ1bmN0aW9uKHByb3ZpZGVySWQsIGF2YWlsYWJpbGl0eSkgewogICAgcmV0dXJuIHRoaXMuZGVsZWdhdGVfICYmIHRoaXMuZGVsZWdhdGVfLm9uU2lua0F2YWlsYWJpbGl0eVVwZGF0ZWQgJiYgdGhpcy5kZWxlZ2F0ZV8ub25TaW5rQXZhaWxhYmlsaXR5VXBkYXRlZChwcm92aWRlcklkLCBhdmFpbGFiaWxpdHkpOwogIH0KICBNZWRpYVJvdXRlclN0dWIucHJvdG90eXBlLm9uUHJlc2VudGF0aW9uQ29ubmVjdGlvblN0YXRlQ2hhbmdlZCA9IGZ1bmN0aW9uKHJvdXRlSWQsIHN0YXRlKSB7CiAgICByZXR1cm4gdGhpcy5kZWxlZ2F0ZV8gJiYgdGhpcy5kZWxlZ2F0ZV8ub25QcmVzZW50YXRpb25Db25uZWN0aW9uU3RhdGVDaGFuZ2VkICYmIHRoaXMuZGVsZWdhdGVfLm9uUHJlc2VudGF0aW9uQ29ubmVjdGlvblN0YXRlQ2hhbmdlZChyb3V0ZUlkLCBzdGF0ZSk7CiAgfQogIE1lZGlhUm91dGVyU3R1Yi5wcm90b3R5cGUub25QcmVzZW50YXRpb25Db25uZWN0aW9uQ2xvc2VkID0gZnVuY3Rpb24ocm91dGVJZCwgcmVhc29uLCBtZXNzYWdlKSB7CiAgICByZXR1cm4gdGhpcy5kZWxlZ2F0ZV8gJiYgdGhpcy5kZWxlZ2F0ZV8ub25QcmVzZW50YXRpb25Db25uZWN0aW9uQ2xvc2VkICYmIHRoaXMuZGVsZWdhdGVfLm9uUHJlc2VudGF0aW9uQ29ubmVjdGlvbkNsb3NlZChyb3V0ZUlkLCByZWFzb24sIG1lc3NhZ2UpOwogIH0KICBNZWRpYVJvdXRlclN0dWIucHJvdG90eXBlLm9uUm91dGVNZXNzYWdlc1JlY2VpdmVkID0gZnVuY3Rpb24ocm91dGVJZCwgbWVzc2FnZXMpIHsKICAgIHJldHVybiB0aGlzLmRlbGVnYXRlXyAmJiB0aGlzLmRlbGVnYXRlXy5vblJvdXRlTWVzc2FnZXNSZWNlaXZlZCAmJiB0aGlzLmRlbGVnYXRlXy5vblJvdXRlTWVzc2FnZXNSZWNlaXZlZChyb3V0ZUlkLCBtZXNzYWdlcyk7CiAgfQogIE1lZGlhUm91dGVyU3R1Yi5wcm90b3R5cGUub25NZWRpYVJlbW90ZXJDcmVhdGVkID0gZnVuY3Rpb24odGFiSWQsIHJlbW90ZXIsIHJlbW90aW5nU291cmNlKSB7CiAgICByZXR1cm4gdGhpcy5kZWxlZ2F0ZV8gJiYgdGhpcy5kZWxlZ2F0ZV8ub25NZWRpYVJlbW90ZXJDcmVhdGVkICYmIHRoaXMuZGVsZWdhdGVfLm9uTWVkaWFSZW1vdGVyQ3JlYXRlZCh0YWJJZCwgcmVtb3RlciwgcmVtb3RpbmdTb3VyY2UpOwogIH0KCiAgTWVkaWFSb3V0ZXJTdHViLnByb3RvdHlwZS5hY2NlcHQgPSBmdW5jdGlvbihtZXNzYWdlKSB7CiAgICB2YXIgcmVhZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VSZWFkZXIobWVzc2FnZSk7CiAgICBzd2l0Y2ggKHJlYWRlci5tZXNzYWdlTmFtZSkgewogICAgY2FzZSBrTWVkaWFSb3V0ZXJfT25TaW5rc1JlY2VpdmVkX05hbWU6CiAgICAgIHZhciBwYXJhbXMgPSByZWFkZXIuZGVjb2RlU3RydWN0KE1lZGlhUm91dGVyX09uU2lua3NSZWNlaXZlZF9QYXJhbXMpOwogICAgICB0aGlzLm9uU2lua3NSZWNlaXZlZChwYXJhbXMucHJvdmlkZXJJZCwgcGFyYW1zLm1lZGlhU291cmNlLCBwYXJhbXMuc2lua3MsIHBhcmFtcy5vcmlnaW5zKTsKICAgICAgcmV0dXJuIHRydWU7CiAgICBjYXNlIGtNZWRpYVJvdXRlcl9Pbklzc3VlX05hbWU6CiAgICAgIHZhciBwYXJhbXMgPSByZWFkZXIuZGVjb2RlU3RydWN0KE1lZGlhUm91dGVyX09uSXNzdWVfUGFyYW1zKTsKICAgICAgdGhpcy5vbklzc3VlKHBhcmFtcy5pc3N1ZSk7CiAgICAgIHJldHVybiB0cnVlOwogICAgY2FzZSBrTWVkaWFSb3V0ZXJfT25Sb3V0ZXNVcGRhdGVkX05hbWU6CiAgICAgIHZhciBwYXJhbXMgPSByZWFkZXIuZGVjb2RlU3RydWN0KE1lZGlhUm91dGVyX09uUm91dGVzVXBkYXRlZF9QYXJhbXMpOwogICAgICB0aGlzLm9uUm91dGVzVXBkYXRlZChwYXJhbXMucHJvdmlkZXJJZCwgcGFyYW1zLnJvdXRlcywgcGFyYW1zLm1lZGlhU291cmNlLCBwYXJhbXMuam9pbmFibGVSb3V0ZUlkcyk7CiAgICAgIHJldHVybiB0cnVlOwogICAgY2FzZSBrTWVkaWFSb3V0ZXJfT25TaW5rQXZhaWxhYmlsaXR5VXBkYXRlZF9OYW1lOgogICAgICB2YXIgcGFyYW1zID0gcmVhZGVyLmRlY29kZVN0cnVjdChNZWRpYVJvdXRlcl9PblNpbmtBdmFpbGFiaWxpdHlVcGRhdGVkX1BhcmFtcyk7CiAgICAgIHRoaXMub25TaW5rQXZhaWxhYmlsaXR5VXBkYXRlZChwYXJhbXMucHJvdmlkZXJJZCwgcGFyYW1zLmF2YWlsYWJpbGl0eSk7CiAgICAgIHJldHVybiB0cnVlOwogICAgY2FzZSBrTWVkaWFSb3V0ZXJfT25QcmVzZW50YXRpb25Db25uZWN0aW9uU3RhdGVDaGFuZ2VkX05hbWU6CiAgICAgIHZhciBwYXJhbXMgPSByZWFkZXIuZGVjb2RlU3RydWN0KE1lZGlhUm91dGVyX09uUHJlc2VudGF0aW9uQ29ubmVjdGlvblN0YXRlQ2hhbmdlZF9QYXJhbXMpOwogICAgICB0aGlzLm9uUHJlc2VudGF0aW9uQ29ubmVjdGlvblN0YXRlQ2hhbmdlZChwYXJhbXMucm91dGVJZCwgcGFyYW1zLnN0YXRlKTsKICAgICAgcmV0dXJuIHRydWU7CiAgICBjYXNlIGtNZWRpYVJvdXRlcl9PblByZXNlbnRhdGlvbkNvbm5lY3Rpb25DbG9zZWRfTmFtZToKICAgICAgdmFyIHBhcmFtcyA9IHJlYWRlci5kZWNvZGVTdHJ1Y3QoTWVkaWFSb3V0ZXJfT25QcmVzZW50YXRpb25Db25uZWN0aW9uQ2xvc2VkX1BhcmFtcyk7CiAgICAgIHRoaXMub25QcmVzZW50YXRpb25Db25uZWN0aW9uQ2xvc2VkKHBhcmFtcy5yb3V0ZUlkLCBwYXJhbXMucmVhc29uLCBwYXJhbXMubWVzc2FnZSk7CiAgICAgIHJldHVybiB0cnVlOwogICAgY2FzZSBrTWVkaWFSb3V0ZXJfT25Sb3V0ZU1lc3NhZ2VzUmVjZWl2ZWRfTmFtZToKICAgICAgdmFyIHBhcmFtcyA9IHJlYWRlci5kZWNvZGVTdHJ1Y3QoTWVkaWFSb3V0ZXJfT25Sb3V0ZU1lc3NhZ2VzUmVjZWl2ZWRfUGFyYW1zKTsKICAgICAgdGhpcy5vblJvdXRlTWVzc2FnZXNSZWNlaXZlZChwYXJhbXMucm91dGVJZCwgcGFyYW1zLm1lc3NhZ2VzKTsKICAgICAgcmV0dXJuIHRydWU7CiAgICBjYXNlIGtNZWRpYVJvdXRlcl9Pbk1lZGlhUmVtb3RlckNyZWF0ZWRfTmFtZToKICAgICAgdmFyIHBhcmFtcyA9IHJlYWRlci5kZWNvZGVTdHJ1Y3QoTWVkaWFSb3V0ZXJfT25NZWRpYVJlbW90ZXJDcmVhdGVkX1BhcmFtcyk7CiAgICAgIHRoaXMub25NZWRpYVJlbW90ZXJDcmVhdGVkKHBhcmFtcy50YWJJZCwgcGFyYW1zLnJlbW90ZXIsIHBhcmFtcy5yZW1vdGluZ1NvdXJjZSk7CiAgICAgIHJldHVybiB0cnVlOwogICAgZGVmYXVsdDoKICAgICAgcmV0dXJuIGZhbHNlOwogICAgfQogIH07CgogIE1lZGlhUm91dGVyU3R1Yi5wcm90b3R5cGUuYWNjZXB0V2l0aFJlc3BvbmRlciA9CiAgICAgIGZ1bmN0aW9uKG1lc3NhZ2UsIHJlc3BvbmRlcikgewogICAgdmFyIHJlYWRlciA9IG5ldyBjb2RlYy5NZXNzYWdlUmVhZGVyKG1lc3NhZ2UpOwogICAgc3dpdGNoIChyZWFkZXIubWVzc2FnZU5hbWUpIHsKICAgIGNhc2Uga01lZGlhUm91dGVyX1JlZ2lzdGVyTWVkaWFSb3V0ZVByb3ZpZGVyX05hbWU6CiAgICAgIHZhciBwYXJhbXMgPSByZWFkZXIuZGVjb2RlU3RydWN0KE1lZGlhUm91dGVyX1JlZ2lzdGVyTWVkaWFSb3V0ZVByb3ZpZGVyX1BhcmFtcyk7CiAgICAgIHRoaXMucmVnaXN0ZXJNZWRpYVJvdXRlUHJvdmlkZXIocGFyYW1zLnByb3ZpZGVySWQsIHBhcmFtcy5tZWRpYVJvdXRlclByb3ZpZGVyKS50aGVuKGZ1bmN0aW9uKHJlc3BvbnNlKSB7CiAgICAgICAgdmFyIHJlc3BvbnNlUGFyYW1zID0KICAgICAgICAgICAgbmV3IE1lZGlhUm91dGVyX1JlZ2lzdGVyTWVkaWFSb3V0ZVByb3ZpZGVyX1Jlc3BvbnNlUGFyYW1zKCk7CiAgICAgICAgcmVzcG9uc2VQYXJhbXMuaW5zdGFuY2VJZCA9IHJlc3BvbnNlLmluc3RhbmNlSWQ7CiAgICAgICAgcmVzcG9uc2VQYXJhbXMuY29uZmlnID0gcmVzcG9uc2UuY29uZmlnOwogICAgICAgIHZhciBidWlsZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VWMUJ1aWxkZXIoCiAgICAgICAgICAgIGtNZWRpYVJvdXRlcl9SZWdpc3Rlck1lZGlhUm91dGVQcm92aWRlcl9OYW1lLAogICAgICAgICAgICBjb2RlYy5hbGlnbihNZWRpYVJvdXRlcl9SZWdpc3Rlck1lZGlhUm91dGVQcm92aWRlcl9SZXNwb25zZVBhcmFtcy5lbmNvZGVkU2l6ZSksCiAgICAgICAgICAgIGNvZGVjLmtNZXNzYWdlSXNSZXNwb25zZSwgcmVhZGVyLnJlcXVlc3RJRCk7CiAgICAgICAgYnVpbGRlci5lbmNvZGVTdHJ1Y3QoTWVkaWFSb3V0ZXJfUmVnaXN0ZXJNZWRpYVJvdXRlUHJvdmlkZXJfUmVzcG9uc2VQYXJhbXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcmVzcG9uc2VQYXJhbXMpOwogICAgICAgIHZhciBtZXNzYWdlID0gYnVpbGRlci5maW5pc2goKTsKICAgICAgICByZXNwb25kZXIuYWNjZXB0KG1lc3NhZ2UpOwogICAgICB9KTsKICAgICAgcmV0dXJuIHRydWU7CiAgICBkZWZhdWx0OgogICAgICByZXR1cm4gZmFsc2U7CiAgICB9CiAgfTsKCiAgZnVuY3Rpb24gdmFsaWRhdGVNZWRpYVJvdXRlclJlcXVlc3QobWVzc2FnZVZhbGlkYXRvcikgewogICAgdmFyIG1lc3NhZ2UgPSBtZXNzYWdlVmFsaWRhdG9yLm1lc3NhZ2U7CiAgICB2YXIgcGFyYW1zQ2xhc3MgPSBudWxsOwogICAgc3dpdGNoIChtZXNzYWdlLmdldE5hbWUoKSkgewogICAgICBjYXNlIGtNZWRpYVJvdXRlcl9SZWdpc3Rlck1lZGlhUm91dGVQcm92aWRlcl9OYW1lOgogICAgICAgIGlmIChtZXNzYWdlLmV4cGVjdHNSZXNwb25zZSgpKQogICAgICAgICAgcGFyYW1zQ2xhc3MgPSBNZWRpYVJvdXRlcl9SZWdpc3Rlck1lZGlhUm91dGVQcm92aWRlcl9QYXJhbXM7CiAgICAgIGJyZWFrOwogICAgICBjYXNlIGtNZWRpYVJvdXRlcl9PblNpbmtzUmVjZWl2ZWRfTmFtZToKICAgICAgICBpZiAoIW1lc3NhZ2UuZXhwZWN0c1Jlc3BvbnNlKCkgJiYgIW1lc3NhZ2UuaXNSZXNwb25zZSgpKQogICAgICAgICAgcGFyYW1zQ2xhc3MgPSBNZWRpYVJvdXRlcl9PblNpbmtzUmVjZWl2ZWRfUGFyYW1zOwogICAgICBicmVhazsKICAgICAgY2FzZSBrTWVkaWFSb3V0ZXJfT25Jc3N1ZV9OYW1lOgogICAgICAgIGlmICghbWVzc2FnZS5leHBlY3RzUmVzcG9uc2UoKSAmJiAhbWVzc2FnZS5pc1Jlc3BvbnNlKCkpCiAgICAgICAgICBwYXJhbXNDbGFzcyA9IE1lZGlhUm91dGVyX09uSXNzdWVfUGFyYW1zOwogICAgICBicmVhazsKICAgICAgY2FzZSBrTWVkaWFSb3V0ZXJfT25Sb3V0ZXNVcGRhdGVkX05hbWU6CiAgICAgICAgaWYgKCFtZXNzYWdlLmV4cGVjdHNSZXNwb25zZSgpICYmICFtZXNzYWdlLmlzUmVzcG9uc2UoKSkKICAgICAgICAgIHBhcmFtc0NsYXNzID0gTWVkaWFSb3V0ZXJfT25Sb3V0ZXNVcGRhdGVkX1BhcmFtczsKICAgICAgYnJlYWs7CiAgICAgIGNhc2Uga01lZGlhUm91dGVyX09uU2lua0F2YWlsYWJpbGl0eVVwZGF0ZWRfTmFtZToKICAgICAgICBpZiAoIW1lc3NhZ2UuZXhwZWN0c1Jlc3BvbnNlKCkgJiYgIW1lc3NhZ2UuaXNSZXNwb25zZSgpKQogICAgICAgICAgcGFyYW1zQ2xhc3MgPSBNZWRpYVJvdXRlcl9PblNpbmtBdmFpbGFiaWxpdHlVcGRhdGVkX1BhcmFtczsKICAgICAgYnJlYWs7CiAgICAgIGNhc2Uga01lZGlhUm91dGVyX09uUHJlc2VudGF0aW9uQ29ubmVjdGlvblN0YXRlQ2hhbmdlZF9OYW1lOgogICAgICAgIGlmICghbWVzc2FnZS5leHBlY3RzUmVzcG9uc2UoKSAmJiAhbWVzc2FnZS5pc1Jlc3BvbnNlKCkpCiAgICAgICAgICBwYXJhbXNDbGFzcyA9IE1lZGlhUm91dGVyX09uUHJlc2VudGF0aW9uQ29ubmVjdGlvblN0YXRlQ2hhbmdlZF9QYXJhbXM7CiAgICAgIGJyZWFrOwogICAgICBjYXNlIGtNZWRpYVJvdXRlcl9PblByZXNlbnRhdGlvbkNvbm5lY3Rpb25DbG9zZWRfTmFtZToKICAgICAgICBpZiAoIW1lc3NhZ2UuZXhwZWN0c1Jlc3BvbnNlKCkgJiYgIW1lc3NhZ2UuaXNSZXNwb25zZSgpKQogICAgICAgICAgcGFyYW1zQ2xhc3MgPSBNZWRpYVJvdXRlcl9PblByZXNlbnRhdGlvbkNvbm5lY3Rpb25DbG9zZWRfUGFyYW1zOwogICAgICBicmVhazsKICAgICAgY2FzZSBrTWVkaWFSb3V0ZXJfT25Sb3V0ZU1lc3NhZ2VzUmVjZWl2ZWRfTmFtZToKICAgICAgICBpZiAoIW1lc3NhZ2UuZXhwZWN0c1Jlc3BvbnNlKCkgJiYgIW1lc3NhZ2UuaXNSZXNwb25zZSgpKQogICAgICAgICAgcGFyYW1zQ2xhc3MgPSBNZWRpYVJvdXRlcl9PblJvdXRlTWVzc2FnZXNSZWNlaXZlZF9QYXJhbXM7CiAgICAgIGJyZWFrOwogICAgICBjYXNlIGtNZWRpYVJvdXRlcl9Pbk1lZGlhUmVtb3RlckNyZWF0ZWRfTmFtZToKICAgICAgICBpZiAoIW1lc3NhZ2UuZXhwZWN0c1Jlc3BvbnNlKCkgJiYgIW1lc3NhZ2UuaXNSZXNwb25zZSgpKQogICAgICAgICAgcGFyYW1zQ2xhc3MgPSBNZWRpYVJvdXRlcl9Pbk1lZGlhUmVtb3RlckNyZWF0ZWRfUGFyYW1zOwogICAgICBicmVhazsKICAgIH0KICAgIGlmIChwYXJhbXNDbGFzcyA9PT0gbnVsbCkKICAgICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKICAgIHJldHVybiBwYXJhbXNDbGFzcy52YWxpZGF0ZShtZXNzYWdlVmFsaWRhdG9yLCBtZXNzYWdlVmFsaWRhdG9yLm1lc3NhZ2UuZ2V0SGVhZGVyTnVtQnl0ZXMoKSk7CiAgfQoKICBmdW5jdGlvbiB2YWxpZGF0ZU1lZGlhUm91dGVyUmVzcG9uc2UobWVzc2FnZVZhbGlkYXRvcikgewogICB2YXIgbWVzc2FnZSA9IG1lc3NhZ2VWYWxpZGF0b3IubWVzc2FnZTsKICAgdmFyIHBhcmFtc0NsYXNzID0gbnVsbDsKICAgc3dpdGNoIChtZXNzYWdlLmdldE5hbWUoKSkgewogICAgICBjYXNlIGtNZWRpYVJvdXRlcl9SZWdpc3Rlck1lZGlhUm91dGVQcm92aWRlcl9OYW1lOgogICAgICAgIGlmIChtZXNzYWdlLmlzUmVzcG9uc2UoKSkKICAgICAgICAgIHBhcmFtc0NsYXNzID0gTWVkaWFSb3V0ZXJfUmVnaXN0ZXJNZWRpYVJvdXRlUHJvdmlkZXJfUmVzcG9uc2VQYXJhbXM7CiAgICAgICAgYnJlYWs7CiAgICB9CiAgICBpZiAocGFyYW1zQ2xhc3MgPT09IG51bGwpCiAgICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgICByZXR1cm4gcGFyYW1zQ2xhc3MudmFsaWRhdGUobWVzc2FnZVZhbGlkYXRvciwgbWVzc2FnZVZhbGlkYXRvci5tZXNzYWdlLmdldEhlYWRlck51bUJ5dGVzKCkpOwogIH0KCiAgdmFyIE1lZGlhUm91dGVyID0gewogICAgbmFtZTogJ21lZGlhX3JvdXRlcjo6bW9qb206Ok1lZGlhUm91dGVyJywKICAgIGtWZXJzaW9uOiAwLAogICAgcHRyQ2xhc3M6IE1lZGlhUm91dGVyUHRyLAogICAgcHJveHlDbGFzczogTWVkaWFSb3V0ZXJQcm94eSwKICAgIHN0dWJDbGFzczogTWVkaWFSb3V0ZXJTdHViLAogICAgdmFsaWRhdGVSZXF1ZXN0OiB2YWxpZGF0ZU1lZGlhUm91dGVyUmVxdWVzdCwKICAgIHZhbGlkYXRlUmVzcG9uc2U6IHZhbGlkYXRlTWVkaWFSb3V0ZXJSZXNwb25zZSwKICB9OwogIE1lZGlhUm91dGVyLlNpbmtBdmFpbGFiaWxpdHkgPSB7fTsKICBNZWRpYVJvdXRlci5TaW5rQXZhaWxhYmlsaXR5LlVOQVZBSUxBQkxFID0gMDsKICBNZWRpYVJvdXRlci5TaW5rQXZhaWxhYmlsaXR5LlBFUl9TT1VSQ0UgPSBNZWRpYVJvdXRlci5TaW5rQXZhaWxhYmlsaXR5LlVOQVZBSUxBQkxFICsgMTsKICBNZWRpYVJvdXRlci5TaW5rQXZhaWxhYmlsaXR5LkFWQUlMQUJMRSA9IE1lZGlhUm91dGVyLlNpbmtBdmFpbGFiaWxpdHkuUEVSX1NPVVJDRSArIDE7CgogIE1lZGlhUm91dGVyLlNpbmtBdmFpbGFiaWxpdHkuaXNLbm93bkVudW1WYWx1ZSA9IGZ1bmN0aW9uKHZhbHVlKSB7CiAgICBzd2l0Y2ggKHZhbHVlKSB7CiAgICBjYXNlIDA6CiAgICBjYXNlIDE6CiAgICBjYXNlIDI6CiAgICAgIHJldHVybiB0cnVlOwogICAgfQogICAgcmV0dXJuIGZhbHNlOwogIH07CgogIE1lZGlhUm91dGVyLlNpbmtBdmFpbGFiaWxpdHkudmFsaWRhdGUgPSBmdW5jdGlvbihlbnVtVmFsdWUpIHsKICAgIHZhciBpc0V4dGVuc2libGUgPSBmYWxzZTsKICAgIGlmIChpc0V4dGVuc2libGUgfHwgdGhpcy5pc0tub3duRW51bVZhbHVlKGVudW1WYWx1ZSkpCiAgICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuVU5LTk9XTl9FTlVNX1ZBTFVFOwogIH07CiAgTWVkaWFSb3V0ZXIuUHJlc2VudGF0aW9uQ29ubmVjdGlvblN0YXRlID0ge307CiAgTWVkaWFSb3V0ZXIuUHJlc2VudGF0aW9uQ29ubmVjdGlvblN0YXRlLkNPTk5FQ1RJTkcgPSAwOwogIE1lZGlhUm91dGVyLlByZXNlbnRhdGlvbkNvbm5lY3Rpb25TdGF0ZS5DT05ORUNURUQgPSBNZWRpYVJvdXRlci5QcmVzZW50YXRpb25Db25uZWN0aW9uU3RhdGUuQ09OTkVDVElORyArIDE7CiAgTWVkaWFSb3V0ZXIuUHJlc2VudGF0aW9uQ29ubmVjdGlvblN0YXRlLkNMT1NFRCA9IE1lZGlhUm91dGVyLlByZXNlbnRhdGlvbkNvbm5lY3Rpb25TdGF0ZS5DT05ORUNURUQgKyAxOwogIE1lZGlhUm91dGVyLlByZXNlbnRhdGlvbkNvbm5lY3Rpb25TdGF0ZS5URVJNSU5BVEVEID0gTWVkaWFSb3V0ZXIuUHJlc2VudGF0aW9uQ29ubmVjdGlvblN0YXRlLkNMT1NFRCArIDE7CgogIE1lZGlhUm91dGVyLlByZXNlbnRhdGlvbkNvbm5lY3Rpb25TdGF0ZS5pc0tub3duRW51bVZhbHVlID0gZnVuY3Rpb24odmFsdWUpIHsKICAgIHN3aXRjaCAodmFsdWUpIHsKICAgIGNhc2UgMDoKICAgIGNhc2UgMToKICAgIGNhc2UgMjoKICAgIGNhc2UgMzoKICAgICAgcmV0dXJuIHRydWU7CiAgICB9CiAgICByZXR1cm4gZmFsc2U7CiAgfTsKCiAgTWVkaWFSb3V0ZXIuUHJlc2VudGF0aW9uQ29ubmVjdGlvblN0YXRlLnZhbGlkYXRlID0gZnVuY3Rpb24oZW51bVZhbHVlKSB7CiAgICB2YXIgaXNFeHRlbnNpYmxlID0gZmFsc2U7CiAgICBpZiAoaXNFeHRlbnNpYmxlIHx8IHRoaXMuaXNLbm93bkVudW1WYWx1ZShlbnVtVmFsdWUpKQogICAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLlVOS05PV05fRU5VTV9WQUxVRTsKICB9OwogIE1lZGlhUm91dGVyLlByZXNlbnRhdGlvbkNvbm5lY3Rpb25DbG9zZVJlYXNvbiA9IHt9OwogIE1lZGlhUm91dGVyLlByZXNlbnRhdGlvbkNvbm5lY3Rpb25DbG9zZVJlYXNvbi5DT05ORUNUSU9OX0VSUk9SID0gMDsKICBNZWRpYVJvdXRlci5QcmVzZW50YXRpb25Db25uZWN0aW9uQ2xvc2VSZWFzb24uQ0xPU0VEID0gTWVkaWFSb3V0ZXIuUHJlc2VudGF0aW9uQ29ubmVjdGlvbkNsb3NlUmVhc29uLkNPTk5FQ1RJT05fRVJST1IgKyAxOwogIE1lZGlhUm91dGVyLlByZXNlbnRhdGlvbkNvbm5lY3Rpb25DbG9zZVJlYXNvbi5XRU5UX0FXQVkgPSBNZWRpYVJvdXRlci5QcmVzZW50YXRpb25Db25uZWN0aW9uQ2xvc2VSZWFzb24uQ0xPU0VEICsgMTsKCiAgTWVkaWFSb3V0ZXIuUHJlc2VudGF0aW9uQ29ubmVjdGlvbkNsb3NlUmVhc29uLmlzS25vd25FbnVtVmFsdWUgPSBmdW5jdGlvbih2YWx1ZSkgewogICAgc3dpdGNoICh2YWx1ZSkgewogICAgY2FzZSAwOgogICAgY2FzZSAxOgogICAgY2FzZSAyOgogICAgICByZXR1cm4gdHJ1ZTsKICAgIH0KICAgIHJldHVybiBmYWxzZTsKICB9OwoKICBNZWRpYVJvdXRlci5QcmVzZW50YXRpb25Db25uZWN0aW9uQ2xvc2VSZWFzb24udmFsaWRhdGUgPSBmdW5jdGlvbihlbnVtVmFsdWUpIHsKICAgIHZhciBpc0V4dGVuc2libGUgPSBmYWxzZTsKICAgIGlmIChpc0V4dGVuc2libGUgfHwgdGhpcy5pc0tub3duRW51bVZhbHVlKGVudW1WYWx1ZSkpCiAgICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuVU5LTk9XTl9FTlVNX1ZBTFVFOwogIH07CiAgTWVkaWFSb3V0ZXJTdHViLnByb3RvdHlwZS52YWxpZGF0b3IgPSB2YWxpZGF0ZU1lZGlhUm91dGVyUmVxdWVzdDsKICBNZWRpYVJvdXRlclByb3h5LnByb3RvdHlwZS52YWxpZGF0b3IgPSB2YWxpZGF0ZU1lZGlhUm91dGVyUmVzcG9uc2U7CiAgZXhwb3J0cy5TaW5rSWNvblR5cGUgPSBTaW5rSWNvblR5cGU7CiAgZXhwb3J0cy5Sb3V0ZUNvbnRyb2xsZXJUeXBlID0gUm91dGVDb250cm9sbGVyVHlwZTsKICBleHBvcnRzLlJvdXRlUmVxdWVzdFJlc3VsdENvZGUgPSBSb3V0ZVJlcXVlc3RSZXN1bHRDb2RlOwogIGV4cG9ydHMuTWVkaWFTaW5rID0gTWVkaWFTaW5rOwogIGV4cG9ydHMuRGlhbE1lZGlhU2luayA9IERpYWxNZWRpYVNpbms7CiAgZXhwb3J0cy5DYXN0TWVkaWFTaW5rID0gQ2FzdE1lZGlhU2luazsKICBleHBvcnRzLk1lZGlhUm91dGUgPSBNZWRpYVJvdXRlOwogIGV4cG9ydHMuSXNzdWUgPSBJc3N1ZTsKICBleHBvcnRzLlJvdXRlTWVzc2FnZSA9IFJvdXRlTWVzc2FnZTsKICBleHBvcnRzLlNpbmtTZWFyY2hDcml0ZXJpYSA9IFNpbmtTZWFyY2hDcml0ZXJpYTsKICBleHBvcnRzLk1lZGlhUm91dGVQcm92aWRlckNvbmZpZyA9IE1lZGlhUm91dGVQcm92aWRlckNvbmZpZzsKICBleHBvcnRzLk1lZGlhU2lua0V4dHJhRGF0YSA9IE1lZGlhU2lua0V4dHJhRGF0YTsKICBleHBvcnRzLk1lZGlhUm91dGVQcm92aWRlciA9IE1lZGlhUm91dGVQcm92aWRlcjsKICBleHBvcnRzLk1lZGlhUm91dGVQcm92aWRlclB0ciA9IE1lZGlhUm91dGVQcm92aWRlclB0cjsKICBleHBvcnRzLk1lZGlhUm91dGVQcm92aWRlckFzc29jaWF0ZWRQdHIgPSBNZWRpYVJvdXRlUHJvdmlkZXJBc3NvY2lhdGVkUHRyOwogIGV4cG9ydHMuTWVkaWFSb3V0ZXIgPSBNZWRpYVJvdXRlcjsKICBleHBvcnRzLk1lZGlhUm91dGVyUHRyID0gTWVkaWFSb3V0ZXJQdHI7CiAgZXhwb3J0cy5NZWRpYVJvdXRlckFzc29jaWF0ZWRQdHIgPSBNZWRpYVJvdXRlckFzc29jaWF0ZWRQdHI7Cn0pKCk7Ly8gQ29weXJpZ2h0IDIwMTUgVGhlIENocm9taXVtIEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCi8vIFVzZSBvZiB0aGlzIHNvdXJjZSBjb2RlIGlzIGdvdmVybmVkIGJ5IGEgQlNELXN0eWxlIGxpY2Vuc2UgdGhhdCBjYW4gYmUKLy8gZm91bmQgaW4gdGhlIExJQ0VOU0UgZmlsZS4KCid1c2Ugc3RyaWN0JzsKCmlmICgodHlwZW9mIG1vam8gPT09ICd1bmRlZmluZWQnKSB8fCAhbW9qby5iaW5kaW5nc0xpYnJhcnlJbml0aWFsaXplZCkgewogIGxvYWRTY3JpcHQoJ21vam9fYmluZGluZ3MnKTsKfQptb2pvLmNvbmZpZy5hdXRvTG9hZE1vam9tRGVwcyA9IGZhbHNlOwoKbG9hZFNjcmlwdCgnY2hyb21lL2NvbW1vbi9tZWRpYV9yb3V0ZXIvbW9qby9tZWRpYV9jb250cm9sbGVyLm1vam9tJyk7CmxvYWRTY3JpcHQoJ2Nocm9tZS9jb21tb24vbWVkaWFfcm91dGVyL21vam8vbWVkaWFfcm91dGVyLm1vam9tJyk7CmxvYWRTY3JpcHQoJ2Nocm9tZS9jb21tb24vbWVkaWFfcm91dGVyL21vam8vbWVkaWFfc3RhdHVzLm1vam9tJyk7CmxvYWRTY3JpcHQoJ2V4dGVuc2lvbnMvY29tbW9uL21vam8va2VlcF9hbGl2ZS5tb2pvbScpOwpsb2FkU2NyaXB0KCdtZWRpYS9tb2pvL2ludGVyZmFjZXMvbWlycm9yX3NlcnZpY2VfcmVtb3RpbmcubW9qb20nKTsKbG9hZFNjcmlwdCgnbWVkaWEvbW9qby9pbnRlcmZhY2VzL3JlbW90aW5nX2NvbW1vbi5tb2pvbScpOwpsb2FkU2NyaXB0KCdtb2pvL2NvbW1vbi90aW1lLm1vam9tJyk7CmxvYWRTY3JpcHQoJ25ldC9pbnRlcmZhY2VzL2lwX2FkZHJlc3MubW9qb20nKTsKbG9hZFNjcmlwdCgnbmV0L2ludGVyZmFjZXMvaXBfZW5kcG9pbnQubW9qb20nKTsKbG9hZFNjcmlwdCgndXJsL21vam8vb3JpZ2luLm1vam9tJyk7CmxvYWRTY3JpcHQoJ3VybC9tb2pvL3VybC5tb2pvbScpOwoKLy8gVGhlIGZvbGxvd2luZyBhZGFwdGVyIGNsYXNzZXMgcHJlc2VydmUgYmFja3dhcmQgY29tcGF0aWJpbGl0eSBmb3IgdGhlIG1lZGlhCi8vIHJvdXRlciBjb21wb25lbnQgZXh0ZW5zaW9uLgovLyBUT0RPKGNyYnVnLmNvbS83ODcxMjgpOiBSZW1vdmUgdGhlc2UgYWRhcHRlcnMuCgpmdW5jdGlvbiBhc3NpZ25GaWVsZHMob2JqZWN0LCBmaWVsZHMpIHsKICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgaWYgKG9iamVjdC5oYXNPd25Qcm9wZXJ0eShmaWVsZCkpCiAgICAgIG9iamVjdFtmaWVsZF0gPSBmaWVsZHNbZmllbGRdOwogIH0KfQoKLyoqCiAqIEFkYXB0ZXIgZm9yIG1lZGlhUm91dGVyLm1vam9tLkRpYWxNZWRpYVNpbmsuCiAqIEBjb25zdHJ1Y3RvcgogKi8KZnVuY3Rpb24gRGlhbE1lZGlhU2lua0FkYXB0ZXIoZmllbGRzKSB7CiAgdGhpcy5pcF9hZGRyZXNzID0gbnVsbDsKICB0aGlzLm1vZGVsX25hbWUgPSBudWxsOwogIHRoaXMuYXBwX3VybCA9IG51bGw7CgogIGFzc2lnbkZpZWxkcyh0aGlzLCBmaWVsZHMpOwp9CgpEaWFsTWVkaWFTaW5rQWRhcHRlci5mcm9tTmV3VmVyc2lvbiA9IGZ1bmN0aW9uKG90aGVyKSB7CiAgcmV0dXJuIG5ldyBEaWFsTWVkaWFTaW5rQWRhcHRlcih7CiAgICAnaXBfYWRkcmVzcyc6IElQQWRkcmVzc0FkYXB0ZXIuZnJvbU5ld1ZlcnNpb24ob3RoZXIuaXBBZGRyZXNzKSwKICAgICdtb2RlbF9uYW1lJzogb3RoZXIubW9kZWxOYW1lLAogICAgJ2FwcF91cmwnOiBvdGhlci5hcHBVcmwsCiAgfSk7Cn07CgpEaWFsTWVkaWFTaW5rQWRhcHRlci5wcm90b3R5cGUudG9OZXdWZXJzaW9uID0gZnVuY3Rpb24oKSB7CiAgcmV0dXJuIG5ldyBtZWRpYVJvdXRlci5tb2pvbS5EaWFsTWVkaWFTaW5rKHsKICAgICdpcEFkZHJlc3MnIDogdGhpcy5pcF9hZGRyZXNzLnRvTmV3VmVyc2lvbigpLAogICAgJ21vZGVsTmFtZScgOiB0aGlzLm1vZGVsX25hbWUsCiAgICAnYXBwVXJsJyA6IHRoaXMuYXBwX3VybCwKICB9KTsKfTsKCi8qKgogKiBBZGFwdGVyIGZvciBtZWRpYVJvdXRlci5tb2pvbS5DYXN0TWVkaWFTaW5rLgogKiBAY29uc3RydWN0b3IKICovCmZ1bmN0aW9uIENhc3RNZWRpYVNpbmtBZGFwdGVyKGZpZWxkcykgewogIHRoaXMuaXBfZW5kcG9pbnQgPSBudWxsOwogIHRoaXMubW9kZWxfbmFtZSA9IG51bGw7CiAgdGhpcy5jYXBhYmlsaXRpZXMgPSAwOwogIHRoaXMuY2FzdF9jaGFubmVsX2lkID0gMDsKCiAgYXNzaWduRmllbGRzKHRoaXMsIGZpZWxkcyk7Cn0KCkNhc3RNZWRpYVNpbmtBZGFwdGVyLmZyb21OZXdWZXJzaW9uID0gZnVuY3Rpb24ob3RoZXIpIHsKICByZXR1cm4gbmV3IENhc3RNZWRpYVNpbmtBZGFwdGVyKHsKICAgICdpcF9lbmRwb2ludCc6IElQRW5kcG9pbnRBZGFwdGVyLmZyb21OZXdWZXJzaW9uKG90aGVyLmlwRW5kcG9pbnQpLAogICAgJ21vZGVsX25hbWUnOiBvdGhlci5tb2RlbE5hbWUsCiAgICAnY2FwYWJpbGl0aWVzJzogb3RoZXIuY2FwYWJpbGl0aWVzLAogICAgJ2Nhc3RfY2hhbm5lbF9pZCc6IG90aGVyLmNhc3RDaGFubmVsSWQsCiAgfSk7Cn07CgpDYXN0TWVkaWFTaW5rQWRhcHRlci5wcm90b3R5cGUudG9OZXdWZXJzaW9uID0gZnVuY3Rpb24oKSB7CiAgcmV0dXJuIG5ldyBtZWRpYVJvdXRlci5tb2pvbS5DYXN0TWVkaWFTaW5rKHsKICAgICdpcEVuZHBvaW50JzogdGhpcy5pcF9lbmRwb2ludC50b05ld1ZlcnNpb24oKSwKICAgICdtb2RlbE5hbWUnOiB0aGlzLm1vZGVsX25hbWUsCiAgICAnY2FwYWJpbGl0aWVzJzogdGhpcy5jYXBhYmlsaXRpZXMsCiAgICAnY2FzdENoYW5uZWxJZCc6IHRoaXMuY2FzdF9jaGFubmVsX2lkLAogIH0pOwp9OwoKLyoqCiAqIEFkYXB0ZXIgZm9yIG1lZGlhUm91dGVyLm1vam9tLkhhbmdvdXRzTWVkaWFTdGF0dXNFeHRyYURhdGEuCiAqIEBjb25zdHJ1Y3RvcgogKi8KZnVuY3Rpb24gSGFuZ291dHNNZWRpYVN0YXR1c0V4dHJhRGF0YUFkYXB0ZXIoZmllbGRzKSB7CiAgdGhpcy5sb2NhbF9wcmVzZW50ID0gZmFsc2U7CgogIGFzc2lnbkZpZWxkcyh0aGlzLCBmaWVsZHMpOwp9CgpIYW5nb3V0c01lZGlhU3RhdHVzRXh0cmFEYXRhQWRhcHRlci5wcm90b3R5cGUudG9OZXdWZXJzaW9uID0gZnVuY3Rpb24oKSB7CiAgcmV0dXJuIG5ldyBtZWRpYVJvdXRlci5tb2pvbS5IYW5nb3V0c01lZGlhU3RhdHVzRXh0cmFEYXRhKHsKICAgICdsb2NhbFByZXNlbnQnOiB0aGlzLmxvY2FsX3ByZXNlbnQsCiAgfSk7Cn07CgovKioKICogQWRhcHRlciBmb3IgbmV0LmludGVyZmFjZXMuSVBBZGRyZXNzLgogKiBAY29uc3RydWN0b3IKICovCmZ1bmN0aW9uIElQQWRkcmVzc0FkYXB0ZXIoZmllbGRzKSB7CiAgdGhpcy5hZGRyZXNzX2J5dGVzID0gbnVsbDsKCiAgYXNzaWduRmllbGRzKHRoaXMsIGZpZWxkcyk7Cn0KCklQQWRkcmVzc0FkYXB0ZXIuZnJvbU5ld1ZlcnNpb24gPSBmdW5jdGlvbihvdGhlcikgewogIHJldHVybiBuZXcgSVBBZGRyZXNzQWRhcHRlcih7CiAgICAnYWRkcmVzc19ieXRlcyc6IG90aGVyLmFkZHJlc3NCeXRlcywKICB9KTsKfTsKCklQQWRkcmVzc0FkYXB0ZXIucHJvdG90eXBlLnRvTmV3VmVyc2lvbiA9IGZ1bmN0aW9uKCkgewogIHJldHVybiBuZXcgbmV0LmludGVyZmFjZXMuSVBBZGRyZXNzKHsKICAgICdhZGRyZXNzQnl0ZXMnOiB0aGlzLmFkZHJlc3NfYnl0ZXMsCiAgfSk7Cn07CgovKioKICogQWRhcHRlciBmb3IgbmV0LmludGVyZmFjZXMuSVBFbmRwb2ludC4KICogQGNvbnN0cnVjdG9yCiAqLwpmdW5jdGlvbiBJUEVuZHBvaW50QWRhcHRlcihmaWVsZHMpIHsKICB0aGlzLmFkZHJlc3MgPSBudWxsOwogIHRoaXMucG9ydCA9IDA7CgogIGFzc2lnbkZpZWxkcyh0aGlzLCBmaWVsZHMpOwp9CgpJUEVuZHBvaW50QWRhcHRlci5mcm9tTmV3VmVyc2lvbiA9IGZ1bmN0aW9uKG90aGVyKSB7CiAgcmV0dXJuIG5ldyBJUEVuZHBvaW50QWRhcHRlcih7CiAgICAnYWRkcmVzcyc6IElQQWRkcmVzc0FkYXB0ZXIuZnJvbU5ld1ZlcnNpb24ob3RoZXIuYWRkcmVzcyksCiAgICAncG9ydCc6IG90aGVyLnBvcnQsCiAgfSk7Cn07CgpJUEVuZHBvaW50QWRhcHRlci5wcm90b3R5cGUudG9OZXdWZXJzaW9uID0gZnVuY3Rpb24oKSB7CiAgcmV0dXJuIG5ldyBuZXQuaW50ZXJmYWNlcy5JUEVuZHBvaW50KHsKICAgICdhZGRyZXNzJzogdGhpcy5hZGRyZXNzLnRvTmV3VmVyc2lvbigpLAogICAgJ3BvcnQnOiB0aGlzLnBvcnQsCiAgfSk7Cn07CgovKioKICogQWRhcHRlciBmb3IgbWVkaWFSb3V0ZXIubW9qb20uTWVkaWFTdGF0dXMuCiAqIEBjb25zdHJ1Y3RvcgogKi8KZnVuY3Rpb24gTWVkaWFTdGF0dXNBZGFwdGVyKGZpZWxkcykgewogIHRoaXMudGl0bGUgPSBudWxsOwogIHRoaXMuZGVzY3JpcHRpb24gPSBudWxsOwogIHRoaXMuY2FuX3BsYXlfcGF1c2UgPSBmYWxzZTsKICB0aGlzLmNhbl9tdXRlID0gZmFsc2U7CiAgdGhpcy5jYW5fc2V0X3ZvbHVtZSA9IGZhbHNlOwogIHRoaXMuY2FuX3NlZWsgPSBmYWxzZTsKICB0aGlzLmlzX211dGVkID0gZmFsc2U7CiAgdGhpcy5wbGF5X3N0YXRlID0gMDsKICB0aGlzLnZvbHVtZSA9IDA7CiAgdGhpcy5kdXJhdGlvbiA9IG51bGw7CiAgdGhpcy5jdXJyZW50X3RpbWUgPSBudWxsOwogIHRoaXMuaGFuZ291dHNfZXh0cmFfZGF0YSA9IG51bGw7CgogIGFzc2lnbkZpZWxkcyh0aGlzLCBmaWVsZHMpOwp9CgpNZWRpYVN0YXR1c0FkYXB0ZXIuUGxheVN0YXRlID0gbWVkaWFSb3V0ZXIubW9qb20uTWVkaWFTdGF0dXMuUGxheVN0YXRlOwoKTWVkaWFTdGF0dXNBZGFwdGVyLnByb3RvdHlwZS50b05ld1ZlcnNpb24gPSBmdW5jdGlvbigpIHsKICByZXR1cm4gbmV3IG1lZGlhUm91dGVyLm1vam9tLk1lZGlhU3RhdHVzKHsKICAgICd0aXRsZSc6IHRoaXMudGl0bGUsCiAgICAnZGVzY3JpcHRpb24nOiB0aGlzLmRlc2NyaXB0aW9uLAogICAgJ2NhblBsYXlQYXVzZSc6IHRoaXMuY2FuX3BsYXlfcGF1c2UsCiAgICAnY2FuTXV0ZSc6IHRoaXMuY2FuX211dGUsCiAgICAnY2FuU2V0Vm9sdW1lJzogdGhpcy5jYW5fc2V0X3ZvbHVtZSwKICAgICdjYW5TZWVrJzogdGhpcy5jYW5fc2VlaywKICAgICdpc011dGVkJzogdGhpcy5pc19tdXRlZCwKICAgICdwbGF5U3RhdGUnOiB0aGlzLnBsYXlfc3RhdGUsCiAgICAndm9sdW1lJzogdGhpcy52b2x1bWUsCiAgICAnZHVyYXRpb24nOiB0aGlzLmR1cmF0aW9uLAogICAgJ2N1cnJlbnRUaW1lJzogdGhpcy5jdXJyZW50X3RpbWUsCiAgICAnaGFuZ291dHNFeHRyYURhdGEnOgogICAgICAgIHRoaXMuaGFuZ291dHNfZXh0cmFfZGF0YSAmJiB0aGlzLmhhbmdvdXRzX2V4dHJhX2RhdGEudG9OZXdWZXJzaW9uKCksCiAgfSk7Cn07CgovKioKICogQWRhcHRlciBmb3IgbWVkaWEubW9qb20uUmVtb3RpbmdTaW5rTWV0YWRhdGEuCiAqIEBjb25zdHJ1Y3RvcgogKi8KZnVuY3Rpb24gUmVtb3RpbmdTaW5rTWV0YWRhdGFBZGFwdGVyKGZpZWxkcykgewogIHRoaXMuZmVhdHVyZXMgPSBudWxsOwogIHRoaXMuYXVkaW9fY2FwYWJpbGl0aWVzID0gbnVsbDsKICB0aGlzLnZpZGVvX2NhcGFiaWxpdGllcyA9IG51bGw7CiAgdGhpcy5mcmllbmRseV9uYW1lID0gbnVsbDsKCiAgYXNzaWduRmllbGRzKHRoaXMsIGZpZWxkcyk7Cn0KClJlbW90aW5nU2lua01ldGFkYXRhQWRhcHRlci5mcm9tTmV3VmVyc2lvbiA9IGZ1bmN0aW9uKG90aGVyKSB7CiAgcmV0dXJuIG5ldyBSZW1vdGluZ1NpbmtNZXRhZGF0YUFkYXB0ZXIoewogICAgJ2ZlYXR1cmVzJzogb3RoZXIuZmVhdHVyZXMsCiAgICAnYXVkaW9fY2FwYWJpbGl0aWVzJzogb3RoZXIuYXVkaW9DYXBhYmlsaXRpZXMsCiAgICAndmlkZW9fY2FwYWJpbGl0aWVzJzogb3RoZXIudmlkZW9DYXBhYmlsaXRpZXMsCiAgICAnZnJpZW5kbHlfbmFtZSc6IG90aGVyLmZyaWVuZGx5TmFtZSwKICB9KTsKfTsKClJlbW90aW5nU2lua01ldGFkYXRhQWRhcHRlci5wcm90b3R5cGUudG9OZXdWZXJzaW9uID0gZnVuY3Rpb24oKSB7CiAgcmV0dXJuIG5ldyBtZWRpYS5tb2pvbS5SZW1vdGluZ1NpbmtNZXRhZGF0YSh7CiAgICAnZmVhdHVyZXMnOiB0aGlzLmZlYXR1cmVzLAogICAgJ2F1ZGlvQ2FwYWJpbGl0aWVzJzogdGhpcy5hdWRpb19jYXBhYmlsaXRpZXMsCiAgICAndmlkZW9DYXBhYmlsaXRpZXMnOiB0aGlzLnZpZGVvX2NhcGFiaWxpdGllcywKICAgICdmcmllbmRseU5hbWUnOiB0aGlzLmZyaWVuZGx5X25hbWUsCiAgfSk7Cn07CgovKioKICogQWRhcHRlciBmb3IgbWVkaWFSb3V0ZXIubW9qb20uTWVkaWFTaW5rLgogKiBAY29uc3RydWN0b3IKICovCmZ1bmN0aW9uIE1lZGlhU2lua0FkYXB0ZXIoZmllbGRzKSB7CiAgdGhpcy5zaW5rX2lkID0gbnVsbDsKICB0aGlzLm5hbWUgPSBudWxsOwogIHRoaXMuZGVzY3JpcHRpb24gPSBudWxsOwogIHRoaXMuZG9tYWluID0gbnVsbDsKICB0aGlzLmljb25fdHlwZSA9IDA7CiAgdGhpcy5leHRyYV9kYXRhID0gbnVsbDsKCiAgYXNzaWduRmllbGRzKHRoaXMsIGZpZWxkcyk7Cn0KCk1lZGlhU2lua0FkYXB0ZXIuZnJvbU5ld1ZlcnNpb24gPSBmdW5jdGlvbihvdGhlcikgewogIHJldHVybiBuZXcgTWVkaWFTaW5rQWRhcHRlcih7CiAgICAnc2lua19pZCc6IG90aGVyLnNpbmtJZCwKICAgICduYW1lJzogb3RoZXIubmFtZSwKICAgICdkZXNjcmlwdGlvbic6IG90aGVyLmRlc2NyaXB0aW9uLAogICAgJ2RvbWFpbic6IG90aGVyLmRvbWFpbiwKICAgICdpY29uX3R5cGUnOiBvdGhlci5pY29uVHlwZSwKICAgICdleHRyYV9kYXRhJzogb3RoZXIuZXh0cmFEYXRhICYmCiAgICAgICAgTWVkaWFTaW5rRXh0cmFEYXRhQWRhcHRlci5mcm9tTmV3VmVyc2lvbihvdGhlci5leHRyYURhdGEpLAogIH0pOwp9OwoKTWVkaWFTaW5rQWRhcHRlci5wcm90b3R5cGUudG9OZXdWZXJzaW9uID0gZnVuY3Rpb24oKSB7CiAgcmV0dXJuIG5ldyBtZWRpYVJvdXRlci5tb2pvbS5NZWRpYVNpbmsoewogICAgJ3NpbmtJZCc6IHRoaXMuc2lua19pZCwKICAgICduYW1lJzogdGhpcy5uYW1lLAogICAgJ2Rlc2NyaXB0aW9uJzogdGhpcy5kZXNjcmlwdGlvbiwKICAgICdkb21haW4nOiB0aGlzLmRvbWFpbiwKICAgICdpY29uVHlwZSc6IHRoaXMuaWNvbl90eXBlLAogICAgJ2V4dHJhRGF0YSc6IHRoaXMuZXh0cmFfZGF0YSAmJiB0aGlzLmV4dHJhX2RhdGEudG9OZXdWZXJzaW9uKCksCiAgfSk7Cn07CgovKioKICogQWRhcHRlciBmb3IgbWVkaWFSb3V0ZXIubW9qb20uTWVkaWFTaW5rRXh0cmFEYXRhLgogKiBAY29uc3RydWN0b3IKICovCmZ1bmN0aW9uIE1lZGlhU2lua0V4dHJhRGF0YUFkYXB0ZXIodmFsdWUpIHsKICB0aGlzLiRkYXRhID0gbnVsbDsKICB0aGlzLiR0YWcgPSB1bmRlZmluZWQ7CgogIGlmICh2YWx1ZSA9PSB1bmRlZmluZWQpIHsKICAgIHJldHVybjsKICB9CgogIHZhciBrZXlzID0gT2JqZWN0LmtleXModmFsdWUpOwogIGlmIChrZXlzLmxlbmd0aCA9PSAwKSB7CiAgICByZXR1cm47CiAgfQoKICBpZiAoa2V5cy5sZW5ndGggPiAxKSB7CiAgICB0aHJvdyBuZXcgVHlwZUVycm9yKCdZb3UgbWF5IHNldCBvbmx5IG9uZSBtZW1iZXIgb24gYSB1bmlvbi4nKTsKICB9CgogIHZhciBmaWVsZHMgPSBbCiAgICAnZGlhbF9tZWRpYV9zaW5rJywKICAgICdjYXN0X21lZGlhX3NpbmsnLAogIF07CgogIGlmIChmaWVsZHMuaW5kZXhPZihrZXlzWzBdKSA8IDApIHsKICAgIHRocm93IG5ldyBSZWZlcmVuY2VFcnJvcihrZXlzWzBdICsKICAgICAgICAnIGlzIG5vdCBhIE1lZGlhU2lua0V4dHJhRGF0YUFkYXB0ZXIgbWVtYmVyLicpOwogIH0KCiAgdGhpc1trZXlzWzBdXSA9IHZhbHVlW2tleXNbMF1dOwp9CgpNZWRpYVNpbmtFeHRyYURhdGFBZGFwdGVyLlRhZ3MgPSB7CiAgZGlhbF9tZWRpYV9zaW5rOiAwLAogIGNhc3RfbWVkaWFfc2luazogMSwKfTsKCk9iamVjdC5kZWZpbmVQcm9wZXJ0eShNZWRpYVNpbmtFeHRyYURhdGFBZGFwdGVyLnByb3RvdHlwZSwgJ2RpYWxfbWVkaWFfc2luaycsIHsKICBnZXQ6IGZ1bmN0aW9uKCkgewogICAgaWYgKHRoaXMuJHRhZyAhPSBNZWRpYVNpbmtFeHRyYURhdGFBZGFwdGVyLlRhZ3MuZGlhbF9tZWRpYV9zaW5rKSB7CiAgICAgIHRocm93IG5ldyBSZWZlcmVuY2VFcnJvcigKICAgICAgICAgICdNZWRpYVNpbmtFeHRyYURhdGFBZGFwdGVyLmRpYWxfbWVkaWFfc2luayBpcyBub3QgY3VycmVudGx5IHNldC4nKTsKICAgIH0KICAgIHJldHVybiB0aGlzLiRkYXRhOwogIH0sCgogIHNldDogZnVuY3Rpb24odmFsdWUpIHsKICAgIHRoaXMuJHRhZyA9IE1lZGlhU2lua0V4dHJhRGF0YUFkYXB0ZXIuVGFncy5kaWFsX21lZGlhX3Npbms7CiAgICB0aGlzLiRkYXRhID0gdmFsdWU7CiAgfQp9KTsKCk9iamVjdC5kZWZpbmVQcm9wZXJ0eShNZWRpYVNpbmtFeHRyYURhdGFBZGFwdGVyLnByb3RvdHlwZSwgJ2Nhc3RfbWVkaWFfc2luaycsIHsKICBnZXQ6IGZ1bmN0aW9uKCkgewogICAgaWYgKHRoaXMuJHRhZyAhPSBNZWRpYVNpbmtFeHRyYURhdGFBZGFwdGVyLlRhZ3MuY2FzdF9tZWRpYV9zaW5rKSB7CiAgICAgIHRocm93IG5ldyBSZWZlcmVuY2VFcnJvcigKICAgICAgICAgICdNZWRpYVNpbmtFeHRyYURhdGFBZGFwdGVyLmNhc3RfbWVkaWFfc2luayBpcyBub3QgY3VycmVudGx5IHNldC4nKTsKICAgIH0KICAgIHJldHVybiB0aGlzLiRkYXRhOwogIH0sCgogIHNldDogZnVuY3Rpb24odmFsdWUpIHsKICAgIHRoaXMuJHRhZyA9IE1lZGlhU2lua0V4dHJhRGF0YUFkYXB0ZXIuVGFncy5jYXN0X21lZGlhX3Npbms7CiAgICB0aGlzLiRkYXRhID0gdmFsdWU7CiAgfQp9KTsKCk1lZGlhU2lua0V4dHJhRGF0YUFkYXB0ZXIuZnJvbU5ld1ZlcnNpb24gPSBmdW5jdGlvbihvdGhlcikgewogIGlmIChvdGhlci4kdGFnID09IG1lZGlhUm91dGVyLm1vam9tLk1lZGlhU2lua0V4dHJhRGF0YS5UYWdzLmRpYWxNZWRpYVNpbmspIHsKICAgIHJldHVybiBuZXcgTWVkaWFTaW5rRXh0cmFEYXRhQWRhcHRlcih7CiAgICAgICdkaWFsX21lZGlhX3NpbmsnOgogICAgICAgICAgRGlhbE1lZGlhU2lua0FkYXB0ZXIuZnJvbU5ld1ZlcnNpb24ob3RoZXIuZGlhbE1lZGlhU2luayksCiAgICB9KTsKICB9IGVsc2UgewogICAgcmV0dXJuIG5ldyBNZWRpYVNpbmtFeHRyYURhdGFBZGFwdGVyKHsKICAgICAgJ2Nhc3RfbWVkaWFfc2luayc6CiAgICAgICAgICBDYXN0TWVkaWFTaW5rQWRhcHRlci5mcm9tTmV3VmVyc2lvbihvdGhlci5jYXN0TWVkaWFTaW5rKSwKICAgIH0pOwogIH0KfTsKCk1lZGlhU2lua0V4dHJhRGF0YUFkYXB0ZXIucHJvdG90eXBlLnRvTmV3VmVyc2lvbiA9IGZ1bmN0aW9uKCkgewogIGlmICh0aGlzLiR0YWcgPT0gTWVkaWFTaW5rRXh0cmFEYXRhQWRhcHRlci5UYWdzLmRpYWxfbWVkaWFfc2luaykgewogICAgcmV0dXJuIG5ldyBtZWRpYVJvdXRlci5tb2pvbS5NZWRpYVNpbmtFeHRyYURhdGEoewogICAgICAnZGlhbE1lZGlhU2luayc6IHRoaXMuZGlhbF9tZWRpYV9zaW5rLnRvTmV3VmVyc2lvbigpLAogICAgfSk7CiAgfSBlbHNlIHsKICAgIHJldHVybiBuZXcgbWVkaWFSb3V0ZXIubW9qb20uTWVkaWFTaW5rRXh0cmFEYXRhKHsKICAgICAgJ2Nhc3RNZWRpYVNpbmsnOiB0aGlzLmNhc3RfbWVkaWFfc2luay50b05ld1ZlcnNpb24oKSwKICAgIH0pOwogIH0KfTsKCi8qKgogKiBBZGFwdGVyIGZvciBtZWRpYS5tb2pvbS5NaXJyb3JTZXJ2aWNlUmVtb3RlclB0ci4KICogQGNvbnN0cnVjdG9yCiAqLwpmdW5jdGlvbiBNaXJyb3JTZXJ2aWNlUmVtb3RlclB0ckFkYXB0ZXIoaGFuZGxlT3JQdHJJbmZvKSB7CiAgdGhpcy5wdHIgPSBuZXcgbW9qby5JbnRlcmZhY2VQdHJDb250cm9sbGVyKE1pcnJvclNlcnZpY2VSZW1vdGVyQWRhcHRlciwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaGFuZGxlT3JQdHJJbmZvKTsKfQoKTWlycm9yU2VydmljZVJlbW90ZXJQdHJBZGFwdGVyLnByb3RvdHlwZSA9CiAgICBPYmplY3QuY3JlYXRlKG1lZGlhLm1vam9tLk1pcnJvclNlcnZpY2VSZW1vdGVyUHRyLnByb3RvdHlwZSk7Ck1pcnJvclNlcnZpY2VSZW1vdGVyUHRyQWRhcHRlci5wcm90b3R5cGUuY29uc3RydWN0b3IgPQogICAgTWlycm9yU2VydmljZVJlbW90ZXJQdHJBZGFwdGVyOwoKTWlycm9yU2VydmljZVJlbW90ZXJQdHJBZGFwdGVyLnByb3RvdHlwZS5zdGFydERhdGFTdHJlYW1zID0gZnVuY3Rpb24oKSB7CiAgcmV0dXJuIE1pcnJvclNlcnZpY2VSZW1vdGVyUHJveHkucHJvdG90eXBlLnN0YXJ0RGF0YVN0cmVhbXMKICAgICAgLmFwcGx5KHRoaXMucHRyLmdldFByb3h5KCksIGFyZ3VtZW50cykudGhlbihmdW5jdGlvbihyZXNwb25zZSkgewogICAgcmV0dXJuIFByb21pc2UucmVzb2x2ZSh7CiAgICAgICdhdWRpb19zdHJlYW1faWQnOiByZXNwb25zZS5hdWRpb1N0cmVhbUlkLAogICAgICAndmlkZW9fc3RyZWFtX2lkJzogcmVzcG9uc2UudmlkZW9TdHJlYW1JZCwKICAgIH0pOwogIH0pOwp9OwoKLyoqCiAqIEFkYXB0ZXIgZm9yIG1lZGlhLm1vam9tLk1pcnJvclNlcnZpY2VSZW1vdGVyLnN0dWJjbGFzcy4KICogQGNvbnN0cnVjdG9yCiAqLwpmdW5jdGlvbiBNaXJyb3JTZXJ2aWNlUmVtb3RlclN0dWJBZGFwdGVyKGRlbGVnYXRlKSB7CiAgdGhpcy5kZWxlZ2F0ZV8gPSBkZWxlZ2F0ZTsKfQoKTWlycm9yU2VydmljZVJlbW90ZXJTdHViQWRhcHRlci5wcm90b3R5cGUgPSBPYmplY3QuY3JlYXRlKAogICAgbWVkaWEubW9qb20uTWlycm9yU2VydmljZVJlbW90ZXIuc3R1YkNsYXNzLnByb3RvdHlwZSk7Ck1pcnJvclNlcnZpY2VSZW1vdGVyU3R1YkFkYXB0ZXIucHJvdG90eXBlLmNvbnN0cnVjdG9yID0KICAgIE1pcnJvclNlcnZpY2VSZW1vdGVyU3R1YkFkYXB0ZXI7CgpNaXJyb3JTZXJ2aWNlUmVtb3RlclN0dWJBZGFwdGVyLnByb3RvdHlwZS5zdGFydERhdGFTdHJlYW1zID0KICAgIGZ1bmN0aW9uKGhhc0F1ZGlvLCBoYXNWaWRlbykgewogIHJldHVybiB0aGlzLmRlbGVnYXRlXyAmJiB0aGlzLmRlbGVnYXRlXy5zdGFydERhdGFTdHJlYW1zICYmCiAgICAgIHRoaXMuZGVsZWdhdGVfLnN0YXJ0RGF0YVN0cmVhbXMoaGFzQXVkaW8sIGhhc1ZpZGVvKS50aGVuKAogICAgICAgICAgZnVuY3Rpb24ocmVzcG9uc2UpIHsKICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAnYXVkaW9TdHJlYW1JZCc6IHJlc3BvbnNlLmF1ZGlvX3N0cmVhbV9pZCwKICAgICAgICAgICAgICAndmlkZW9TdHJlYW1JZCc6IHJlc3BvbnNlLnZpZGVvX3N0cmVhbV9pZCwKICAgICAgICAgICAgfTsKICAgICAgICAgIH0pOwp9OwoKLyoqCiAqIEFkYXB0ZXIgZm9yIG1lZGlhLm1vam9tLk1pcnJvclNlcnZpY2VSZW1vdGVyLgogKi8KdmFyIE1pcnJvclNlcnZpY2VSZW1vdGVyQWRhcHRlciA9IHsKICAgIG5hbWU6ICdtZWRpYTo6bW9qb206Ok1pcnJvclNlcnZpY2VSZW1vdGVyJywKICAgIGtWZXJzaW9uOiAwLAogICAgcHRyQ2xhc3M6IE1pcnJvclNlcnZpY2VSZW1vdGVyUHRyQWRhcHRlciwKICAgIHByb3h5Q2xhc3M6IG1lZGlhLm1vam9tLk1pcnJvclNlcnZpY2VSZW1vdGVyLnByb3h5Q2xhc3MsCiAgICBzdHViQ2xhc3M6IE1pcnJvclNlcnZpY2VSZW1vdGVyU3R1YkFkYXB0ZXIsCiAgICB2YWxpZGF0ZVJlcXVlc3Q6IG1lZGlhLm1vam9tLk1pcnJvclNlcnZpY2VSZW1vdGVyLnZhbGlkYXRlUmVxdWVzdCwKICAgIHZhbGlkYXRlUmVzcG9uc2U6IG1lZGlhLm1vam9tLk1pcnJvclNlcnZpY2VSZW1vdGVyLnZhbGlkYXRlUmVzcG9uc2UsCn07CgovKioKICogQWRhcHRlciBmb3IgbWVkaWEubW9qb20uTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlUHRyLgogKiBAY29uc3RydWN0b3IKICovCmZ1bmN0aW9uIE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZVB0ckFkYXB0ZXIoaGFuZGxlT3JQdHJJbmZvKSB7CiAgdGhpcy5wdHIgPSBuZXcgbW9qby5JbnRlcmZhY2VQdHJDb250cm9sbGVyKE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZUFkYXB0ZXIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGhhbmRsZU9yUHRySW5mbyk7Cn0KCk1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZVB0ckFkYXB0ZXIucHJvdG90eXBlID0KICAgIE9iamVjdC5jcmVhdGUobWVkaWEubW9qb20uTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlUHRyLnByb3RvdHlwZSk7Ck1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZVB0ckFkYXB0ZXIucHJvdG90eXBlLmNvbnN0cnVjdG9yID0KICAgIE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZVB0ckFkYXB0ZXI7CgpNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VQdHJBZGFwdGVyLnByb3RvdHlwZS5vblNpbmtBdmFpbGFibGUgPQogICAgZnVuY3Rpb24obWV0YWRhdGEpIHsKICByZXR1cm4gdGhpcy5wdHIuZ2V0UHJveHkoKS5vblNpbmtBdmFpbGFibGUobWV0YWRhdGEudG9OZXdWZXJzaW9uKCkpOwp9OwoKLyoqCiAqIEFkYXB0ZXIgZm9yIG1lZGlhLm1vam9tLk1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZS4KICovCnZhciBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VBZGFwdGVyID0gewogICAgbmFtZTogJ21lZGlhOjptb2pvbTo6TWlycm9yU2VydmljZVJlbW90aW5nU291cmNlJywKICAgIGtWZXJzaW9uOiAwLAogICAgcHRyQ2xhc3M6IE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZVB0ckFkYXB0ZXIsCiAgICBwcm94eUNsYXNzOiBtZWRpYS5tb2pvbS5NaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2UucHJveHlDbGFzcywKICAgIHN0dWJDbGFzczogbnVsbCwKICAgIHZhbGlkYXRlUmVxdWVzdDogbWVkaWEubW9qb20uTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlLnZhbGlkYXRlUmVxdWVzdCwKICAgIHZhbGlkYXRlUmVzcG9uc2U6IG51bGwsCn07CgovKioKICogQWRhcHRlciBmb3IgbWVkaWFSb3V0ZXIubW9qb20uTWVkaWFTdGF0dXNPYnNlcnZlci4KICogQGNvbnN0cnVjdG9yCiAqLwpmdW5jdGlvbiBNZWRpYVN0YXR1c09ic2VydmVyUHRyQWRhcHRlcihoYW5kbGVPclB0ckluZm8pIHsKICB0aGlzLnB0ciA9IG5ldyBtb2pvLkludGVyZmFjZVB0ckNvbnRyb2xsZXIoTWVkaWFTdGF0dXNPYnNlcnZlckFkYXB0ZXIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGhhbmRsZU9yUHRySW5mbyk7Cn0KCk1lZGlhU3RhdHVzT2JzZXJ2ZXJQdHJBZGFwdGVyLnByb3RvdHlwZSA9CiAgICBPYmplY3QuY3JlYXRlKG1lZGlhUm91dGVyLm1vam9tLk1lZGlhU3RhdHVzT2JzZXJ2ZXJQdHIucHJvdG90eXBlKTsKTWVkaWFTdGF0dXNPYnNlcnZlclB0ckFkYXB0ZXIucHJvdG90eXBlLmNvbnN0cnVjdG9yID0KICAgIE1lZGlhU3RhdHVzT2JzZXJ2ZXJQdHJBZGFwdGVyOwoKTWVkaWFTdGF0dXNPYnNlcnZlclB0ckFkYXB0ZXIucHJvdG90eXBlLm9uTWVkaWFTdGF0dXNVcGRhdGVkID0KICAgIGZ1bmN0aW9uKHN0YXR1cykgewogIHJldHVybiB0aGlzLnB0ci5nZXRQcm94eSgpLm9uTWVkaWFTdGF0dXNVcGRhdGVkKHN0YXR1cy50b05ld1ZlcnNpb24oKSk7Cn07CgovKioKICogQWRhcHRlciBmb3IgbWVkaWFSb3V0ZXIubW9qb20uTWVkaWFTdGF0dXNPYnNlcnZlci4KICovCnZhciBNZWRpYVN0YXR1c09ic2VydmVyQWRhcHRlciA9IHsKICBuYW1lOiAnbWVkaWFSb3V0ZXI6Om1vam9tOjpNZWRpYVN0YXR1c09ic2VydmVyJywKICBrVmVyc2lvbjogMCwKICBwdHJDbGFzczogTWVkaWFTdGF0dXNPYnNlcnZlclB0ckFkYXB0ZXIsCiAgcHJveHlDbGFzczogbWVkaWFSb3V0ZXIubW9qb20uTWVkaWFTdGF0dXNPYnNlcnZlci5wcm94eUNsYXNzLAogIHN0dWJDbGFzczogbnVsbCwKICB2YWxpZGF0ZVJlcXVlc3Q6IG1lZGlhUm91dGVyLm1vam9tLk1lZGlhU3RhdHVzT2JzZXJ2ZXIudmFsaWRhdGVSZXF1ZXN0LAogIHZhbGlkYXRlUmVzcG9uc2U6IG51bGwsCn07CgovKioKICogQ29udmVydHMgYSBtZWRpYSBzaW5rIHRvIGEgTWVkaWFTaW5rIE1vam8gb2JqZWN0LgogKiBAcGFyYW0geyFNZWRpYVNpbmt9IHNpbmsgQSBtZWRpYSBzaW5rLgogKiBAcmV0dXJuIHshbWVkaWFSb3V0ZXIubW9qb20uTWVkaWFTaW5rfSBBIE1vam8gTWVkaWFTaW5rIG9iamVjdC4KICovCmZ1bmN0aW9uIHNpbmtUb01vam9fKHNpbmspIHsKICByZXR1cm4gbmV3IG1lZGlhUm91dGVyLm1vam9tLk1lZGlhU2luayh7CiAgICAnbmFtZSc6IHNpbmsuZnJpZW5kbHlOYW1lLAogICAgJ2Rlc2NyaXB0aW9uJzogc2luay5kZXNjcmlwdGlvbiwKICAgICdkb21haW4nOiBzaW5rLmRvbWFpbiwKICAgICdzaW5rSWQnOiBzaW5rLmlkLAogICAgJ2ljb25UeXBlJzogc2lua0ljb25UeXBlVG9Nb2pvKHNpbmsuaWNvblR5cGUpLAogICAgJ3Byb3ZpZGVySWQnOiBtZWRpYVJvdXRlci5tb2pvbS5NZWRpYVJvdXRlUHJvdmlkZXIuSWQuRVhURU5TSU9OLAogIH0pOwp9CgovKioKICogQ29udmVydHMgYSBtZWRpYSBzaW5rJ3MgaWNvbiB0eXBlIHRvIGEgTWVkaWFTaW5rLkljb25UeXBlIE1vam8gb2JqZWN0LgogKiBAcGFyYW0geyFNZWRpYVNpbmsuSWNvblR5cGV9IHR5cGUgQSBtZWRpYSBzaW5rJ3MgaWNvbiB0eXBlLgogKiBAcmV0dXJuIHshbWVkaWFSb3V0ZXIubW9qb20uTWVkaWFTaW5rLkljb25UeXBlfSBBIE1vam8gTWVkaWFTaW5rLkljb25UeXBlCiAqICAgICBvYmplY3QuCiAqLwpmdW5jdGlvbiBzaW5rSWNvblR5cGVUb01vam8odHlwZSkgewogIHN3aXRjaCAodHlwZSkgewogICAgY2FzZSAnY2FzdCc6CiAgICAgIHJldHVybiBtZWRpYVJvdXRlci5tb2pvbS5TaW5rSWNvblR5cGUuQ0FTVDsKICAgIGNhc2UgJ2Nhc3RfYXVkaW9fZ3JvdXAnOgogICAgICByZXR1cm4gbWVkaWFSb3V0ZXIubW9qb20uU2lua0ljb25UeXBlLkNBU1RfQVVESU9fR1JPVVA7CiAgICBjYXNlICdjYXN0X2F1ZGlvJzoKICAgICAgcmV0dXJuIG1lZGlhUm91dGVyLm1vam9tLlNpbmtJY29uVHlwZS5DQVNUX0FVRElPOwogICAgY2FzZSAnbWVldGluZyc6CiAgICAgIHJldHVybiBtZWRpYVJvdXRlci5tb2pvbS5TaW5rSWNvblR5cGUuTUVFVElORzsKICAgIGNhc2UgJ2hhbmdvdXQnOgogICAgICByZXR1cm4gbWVkaWFSb3V0ZXIubW9qb20uU2lua0ljb25UeXBlLkhBTkdPVVQ7CiAgICBjYXNlICdlZHVjYXRpb24nOgogICAgICByZXR1cm4gbWVkaWFSb3V0ZXIubW9qb20uU2lua0ljb25UeXBlLkVEVUNBVElPTjsKICAgIGNhc2UgJ2dlbmVyaWMnOgogICAgICByZXR1cm4gbWVkaWFSb3V0ZXIubW9qb20uU2lua0ljb25UeXBlLkdFTkVSSUM7CiAgICBkZWZhdWx0OgogICAgICBjb25zb2xlLmVycm9yKCdVbmtub3duIHNpbmsgaWNvbiB0eXBlIDogJyArIHR5cGUpOwogICAgICByZXR1cm4gbWVkaWFSb3V0ZXIubW9qb20uU2lua0ljb25UeXBlLkdFTkVSSUM7CiAgfQp9CgovKioKICogUmV0dXJucyBhIE1vam8gTWVkaWFSb3V0ZSBvYmplY3QgZ2l2ZW4gYSBNZWRpYVJvdXRlIGFuZCBhCiAqIG1lZGlhIHNpbmsgbmFtZS4KICogQHBhcmFtIHshTWVkaWFSb3V0ZX0gcm91dGUKICogQHJldHVybiB7IW1lZGlhUm91dGVyLm1vam9tLk1lZGlhUm91dGV9CiAqLwpmdW5jdGlvbiByb3V0ZVRvTW9qb18ocm91dGUpIHsKICByZXR1cm4gbmV3IG1lZGlhUm91dGVyLm1vam9tLk1lZGlhUm91dGUoewogICAgJ21lZGlhUm91dGVJZCc6IHJvdXRlLmlkLAogICAgJ21lZGlhU291cmNlJzogcm91dGUubWVkaWFTb3VyY2UsCiAgICAnbWVkaWFTaW5rSWQnOiByb3V0ZS5zaW5rSWQsCiAgICAnZGVzY3JpcHRpb24nOiByb3V0ZS5kZXNjcmlwdGlvbiwKICAgICdpY29uVXJsJzogcm91dGUuaWNvblVybCwKICAgICdpc0xvY2FsJzogcm91dGUuaXNMb2NhbCwKICAgICdmb3JEaXNwbGF5Jzogcm91dGUuZm9yRGlzcGxheSwKICAgICdpc0luY29nbml0byc6IHJvdXRlLm9mZlRoZVJlY29yZCwKICAgICdpc0xvY2FsUHJlc2VudGF0aW9uJzogcm91dGUuaXNPZmZzY3JlZW5QcmVzZW50YXRpb24sCiAgICAnY29udHJvbGxlclR5cGUnOiByb3V0ZS5jb250cm9sbGVyVHlwZSwKICAgIC8vIEJlZ2luIG5ld2x5IGFkZGVkIHByb3BlcnRpZXMsIGZvbGxvd2VkIGJ5IHRoZSBtaWxlc3RvbmUgdGhleSB3ZXJlCiAgICAvLyBhZGRlZC4gIFRoZSBndWFyZCBzaG91bGQgYmUgc2FmZSB0byByZW1vdmUgTisyIG1pbGVzdG9uZXMgbGF0ZXIuCiAgICAncHJlc2VudGF0aW9uSWQnOiByb3V0ZS5wcmVzZW50YXRpb25JZCB8fCAnJyAgLy8gTTY0CiAgfSk7Cn0KCi8qKgogKiBDb252ZXJ0cyBhIHJvdXRlIG1lc3NhZ2UgdG8gYSBSb3V0ZU1lc3NhZ2UgTW9qbyBvYmplY3QuCiAqIEBwYXJhbSB7IVJvdXRlTWVzc2FnZX0gbWVzc2FnZQogKiBAcmV0dXJuIHshbWVkaWFSb3V0ZXIubW9qb20uUm91dGVNZXNzYWdlfSBBIE1vam8gUm91dGVNZXNzYWdlIG9iamVjdC4KICovCmZ1bmN0aW9uIG1lc3NhZ2VUb01vam9fKG1lc3NhZ2UpIHsKICBpZiAoInN0cmluZyIgPT0gdHlwZW9mIG1lc3NhZ2UubWVzc2FnZSkgewogICAgcmV0dXJuIG5ldyBtZWRpYVJvdXRlci5tb2pvbS5Sb3V0ZU1lc3NhZ2UoewogICAgICAndHlwZSc6IG1lZGlhUm91dGVyLm1vam9tLlJvdXRlTWVzc2FnZS5UeXBlLlRFWFQsCiAgICAgICdtZXNzYWdlJzogbWVzc2FnZS5tZXNzYWdlLAogICAgfSk7CiAgfSBlbHNlIHsKICAgIHJldHVybiBuZXcgbWVkaWFSb3V0ZXIubW9qb20uUm91dGVNZXNzYWdlKHsKICAgICAgJ3R5cGUnOiBtZWRpYVJvdXRlci5tb2pvbS5Sb3V0ZU1lc3NhZ2UuVHlwZS5CSU5BUlksCiAgICAgICdkYXRhJzogbWVzc2FnZS5tZXNzYWdlLAogICAgfSk7CiAgfQp9CgovKioKICogQ29udmVydHMgcHJlc2VudGF0aW9uIGNvbm5lY3Rpb24gc3RhdGUgdG8gTW9qbyBlbnVtIHZhbHVlLgogKiBAcGFyYW0geyFzdHJpbmd9IHN0YXRlCiAqIEByZXR1cm4geyFtZWRpYVJvdXRlci5tb2pvbS5NZWRpYVJvdXRlci5QcmVzZW50YXRpb25Db25uZWN0aW9uU3RhdGV9CiAqLwpmdW5jdGlvbiBwcmVzZW50YXRpb25Db25uZWN0aW9uU3RhdGVUb01vam9fKHN0YXRlKSB7CiAgdmFyIFByZXNlbnRhdGlvbkNvbm5lY3Rpb25TdGF0ZSA9CiAgICAgIG1lZGlhUm91dGVyLm1vam9tLk1lZGlhUm91dGVyLlByZXNlbnRhdGlvbkNvbm5lY3Rpb25TdGF0ZTsKICBzd2l0Y2ggKHN0YXRlKSB7CiAgICBjYXNlICdjb25uZWN0aW5nJzoKICAgICAgcmV0dXJuIFByZXNlbnRhdGlvbkNvbm5lY3Rpb25TdGF0ZS5DT05ORUNUSU5HOwogICAgY2FzZSAnY29ubmVjdGVkJzoKICAgICAgcmV0dXJuIFByZXNlbnRhdGlvbkNvbm5lY3Rpb25TdGF0ZS5DT05ORUNURUQ7CiAgICBjYXNlICdjbG9zZWQnOgogICAgICByZXR1cm4gUHJlc2VudGF0aW9uQ29ubmVjdGlvblN0YXRlLkNMT1NFRDsKICAgIGNhc2UgJ3Rlcm1pbmF0ZWQnOgogICAgICByZXR1cm4gUHJlc2VudGF0aW9uQ29ubmVjdGlvblN0YXRlLlRFUk1JTkFURUQ7CiAgICBkZWZhdWx0OgogICAgICBjb25zb2xlLmVycm9yKCdVbmtub3duIHByZXNlbnRhdGlvbiBjb25uZWN0aW9uIHN0YXRlOiAnICsgc3RhdGUpOwogICAgICByZXR1cm4gUHJlc2VudGF0aW9uQ29ubmVjdGlvblN0YXRlLlRFUk1JTkFURUQ7CiAgfQp9CgovKioKICogQ29udmVydHMgcHJlc2VudGF0aW9uIGNvbm5lY3Rpb24gY2xvc2UgcmVhc29uIHRvIE1vam8gZW51bSB2YWx1ZS4KICogQHBhcmFtIHshc3RyaW5nfSByZWFzb24KICogQHJldHVybiB7IW1lZGlhUm91dGVyLm1vam9tLk1lZGlhUm91dGVyLlByZXNlbnRhdGlvbkNvbm5lY3Rpb25DbG9zZVJlYXNvbn0KICovCmZ1bmN0aW9uIHByZXNlbnRhdGlvbkNvbm5lY3Rpb25DbG9zZVJlYXNvblRvTW9qb18ocmVhc29uKSB7CiAgdmFyIFByZXNlbnRhdGlvbkNvbm5lY3Rpb25DbG9zZVJlYXNvbiA9CiAgICAgIG1lZGlhUm91dGVyLm1vam9tLk1lZGlhUm91dGVyLlByZXNlbnRhdGlvbkNvbm5lY3Rpb25DbG9zZVJlYXNvbjsKICBzd2l0Y2ggKHJlYXNvbikgewogICAgY2FzZSAnZXJyb3InOgogICAgICByZXR1cm4gUHJlc2VudGF0aW9uQ29ubmVjdGlvbkNsb3NlUmVhc29uLkNPTk5FQ1RJT05fRVJST1I7CiAgICBjYXNlICdjbG9zZWQnOgogICAgICByZXR1cm4gUHJlc2VudGF0aW9uQ29ubmVjdGlvbkNsb3NlUmVhc29uLkNMT1NFRDsKICAgIGNhc2UgJ3dlbnRfYXdheSc6CiAgICAgIHJldHVybiBQcmVzZW50YXRpb25Db25uZWN0aW9uQ2xvc2VSZWFzb24uV0VOVF9BV0FZOwogICAgZGVmYXVsdDoKICAgICAgY29uc29sZS5lcnJvcignVW5rbm93biBwcmVzZW50YXRpb24gY29ubmVjdGlvbiBjbG9zZSByZWFzb24gOiAnICsKICAgICAgICAgIHJlYXNvbik7CiAgICAgIHJldHVybiBQcmVzZW50YXRpb25Db25uZWN0aW9uQ2xvc2VSZWFzb24uQ09OTkVDVElPTl9FUlJPUjsKICB9Cn0KCi8qKgogKiBDb252ZXJ0cyBzdHJpbmcgdG8gTW9qbyBvcmlnaW4uCiAqIEBwYXJhbSB7c3RyaW5nfCF1cmwubW9qb20uT3JpZ2lufSBvcmlnaW4KICogQHJldHVybiB7IXVybC5tb2pvbS5PcmlnaW59CiAqLwpmdW5jdGlvbiBzdHJpbmdUb01vam9PcmlnaW5fKG9yaWdpbikgewogIGlmIChvcmlnaW4gaW5zdGFuY2VvZiB1cmwubW9qb20uT3JpZ2luKSB7CiAgICByZXR1cm4gb3JpZ2luOwogIH0KICB2YXIgb3JpZ2luVXJsID0gbmV3IFVSTChvcmlnaW4pOwogIHZhciBtb2pvT3JpZ2luID0ge307CiAgbW9qb09yaWdpbi5zY2hlbWUgPSBvcmlnaW5VcmwucHJvdG9jb2wucmVwbGFjZSgnOicsICcnKTsKICBtb2pvT3JpZ2luLmhvc3QgPSBvcmlnaW5VcmwuaG9zdG5hbWU7CiAgdmFyIHBvcnQgPSBvcmlnaW5VcmwucG9ydCA/IE51bWJlci5wYXJzZUludChvcmlnaW5VcmwucG9ydCkgOiAwOwogIHN3aXRjaCAobW9qb09yaWdpbi5zY2hlbWUpIHsKICAgIGNhc2UgJ2h0dHAnOgogICAgICBtb2pvT3JpZ2luLnBvcnQgPSBwb3J0IHx8IDgwOwogICAgICBicmVhazsKICAgIGNhc2UgJ2h0dHBzJzoKICAgICAgbW9qb09yaWdpbi5wb3J0ID0gcG9ydCB8fCA0NDM7CiAgICAgIGJyZWFrOwogICAgZGVmYXVsdDoKICAgICAgdGhyb3cgbmV3IEVycm9yKCdTY2hlbWUgbXVzdCBiZSBodHRwIG9yIGh0dHBzJyk7CiAgfQogIG1vam9PcmlnaW4uc3Vib3JpZ2luID0gJyc7CiAgcmV0dXJuIG5ldyB1cmwubW9qb20uT3JpZ2luKG1vam9PcmlnaW4pOwp9CgovKioKICogUGFyc2VzIHRoZSBnaXZlbiByb3V0ZSByZXF1ZXN0IEVycm9yIG9iamVjdCBhbmQgY29udmVydHMgaXQgdG8gdGhlCiAqIGNvcnJlc3BvbmRpbmcgcmVzdWx0IGNvZGUuCiAqIEBwYXJhbSB7IUVycm9yfSBlcnJvcgogKiBAcmV0dXJuIHshbWVkaWFSb3V0ZXIubW9qb20uUm91dGVSZXF1ZXN0UmVzdWx0Q29kZX0KICovCmZ1bmN0aW9uIGdldFJvdXRlUmVxdWVzdFJlc3VsdENvZGVfKGVycm9yKSB7CiAgcmV0dXJuIGVycm9yLmVycm9yQ29kZSA/IGVycm9yLmVycm9yQ29kZSA6CiAgICBtZWRpYVJvdXRlci5tb2pvbS5Sb3V0ZVJlcXVlc3RSZXN1bHRDb2RlLlVOS05PV05fRVJST1I7Cn0KCi8qKgogKiBDcmVhdGVzIGFuZCByZXR1cm5zIGEgc3VjY2Vzc2Z1bCByb3V0ZSByZXNwb25zZSBmcm9tIGdpdmVuIHJvdXRlLgogKiBAcGFyYW0geyFNZWRpYVJvdXRlfSByb3V0ZQogKiBAcmV0dXJuIHshT2JqZWN0fQogKi8KZnVuY3Rpb24gdG9TdWNjZXNzUm91dGVSZXNwb25zZV8ocm91dGUpIHsKICByZXR1cm4gewogICAgICByb3V0ZTogcm91dGVUb01vam9fKHJvdXRlKSwKICAgICAgcmVzdWx0Q29kZTogbWVkaWFSb3V0ZXIubW9qb20uUm91dGVSZXF1ZXN0UmVzdWx0Q29kZS5PSwogIH07Cn0KCi8qKgogKiBDcmVhdGVzIGFuZCByZXR1cm5zIGEgZXJyb3Igcm91dGUgcmVzcG9uc2UgZnJvbSBnaXZlbiBFcnJvciBvYmplY3QuCiAqIEBwYXJhbSB7IUVycm9yfSBlcnJvcgogKiBAcmV0dXJuIHshT2JqZWN0fQogKi8KZnVuY3Rpb24gdG9FcnJvclJvdXRlUmVzcG9uc2VfKGVycm9yKSB7CiAgcmV0dXJuIHsKICAgICAgZXJyb3JUZXh0OiBlcnJvci5tZXNzYWdlLAogICAgICByZXN1bHRDb2RlOiBnZXRSb3V0ZVJlcXVlc3RSZXN1bHRDb2RlXyhlcnJvcikKICB9Owp9CgovKioKICogQ3JlYXRlcyBhIG5ldyBNZWRpYVJvdXRlci4KICogQ29udmVydHMgYSByb3V0ZSBzdHJ1Y3QgdG8gaXRzIE1vam8gZm9ybS4KICogQHBhcmFtIHshbWVkaWFSb3V0ZXIubW9qb20uTWVkaWFSb3V0ZXJQdHJ9IHNlcnZpY2UKICogQGNvbnN0cnVjdG9yCiAqLwpmdW5jdGlvbiBNZWRpYVJvdXRlcihzZXJ2aWNlKSB7CiAgLyoqCiAgICogVGhlIE1vam8gc2VydmljZSBwcm94eS4gQWxsb3dzIGV4dGVuc2lvbiBjb2RlIHRvIGNhbGwgbWV0aG9kcyB0aGF0IHJlc2lkZQogICAqIGluIHRoZSBicm93c2VyLgogICAqIEB0eXBlIHshbWVkaWFSb3V0ZXIubW9qb20uTWVkaWFSb3V0ZXJQdHJ9CiAgICovCiAgdGhpcy5zZXJ2aWNlXyA9IHNlcnZpY2U7CgogIC8qKgogICAqIFRoZSBwcm92aWRlciBtYW5hZ2VyIHNlcnZpY2UgZGVsZWdhdGUuIEl0cyBtZXRob2RzIGFyZSBjYWxsZWQgYnkgdGhlCiAgICogYnJvd3Nlci1yZXNpZGVudCBNb2pvIHNlcnZpY2UuCiAgICogQHR5cGUgeyFNZWRpYVJvdXRlcn0KICAgKi8KICB0aGlzLm1ycG1fID0gbmV3IE1lZGlhUm91dGVQcm92aWRlcih0aGlzKTsKCiAgLyoqCiAgICogSGFuZGxlIHRvIGEgS2VlcEFsaXZlIHNlcnZpY2Ugb2JqZWN0LCB3aGljaCBwcmV2ZW50cyB0aGUgZXh0ZW5zaW9uIGZyb20KICAgKiBiZWluZyBzdXNwZW5kZWQgYXMgbG9uZyBhcyBpdCByZW1haW5zIGluIHNjb3BlLgogICAqIEB0eXBlIHtib29sZWFufQogICAqLwogIHRoaXMua2VlcEFsaXZlXyA9IG51bGw7CgogIC8qKgogICAqIFRoZSBiaW5kaW5ncyB0byBiaW5kIHRoZSBzZXJ2aWNlIGRlbGVnYXRlIHRvIHRoZSBNb2pvIGludGVyZmFjZS4KICAgKiBPYmplY3QgbXVzdCByZW1haW4gaW4gc2NvcGUgZm9yIHRoZSBsaWZldGltZSBvZiB0aGUgY29ubmVjdGlvbiB0bwogICAqIHByZXZlbnQgdGhlIGNvbm5lY3Rpb24gZnJvbSBjbG9zaW5nIGF1dG9tYXRpY2FsbHkuCiAgICogQHR5cGUgeyFtb2pvLkJpbmRpbmd9CiAgICovCiAgdGhpcy5tZWRpYVJvdXRlUHJvdmlkZXJCaW5kaW5nXyA9IG5ldyBtb2pvLkJpbmRpbmcoCiAgICAgIG1lZGlhUm91dGVyLm1vam9tLk1lZGlhUm91dGVQcm92aWRlciwgdGhpcy5tcnBtXyk7Cn0KCi8qKgogKiBSZXR1cm5zIGRlZmluaXRpb25zIG9mIE1vam8gY29yZSBhbmQgZ2VuZXJhdGVkIE1vam9tIGNsYXNzZXMgdGhhdCBjYW4gYmUKICogdXNlZCBkaXJlY3RseSBieSB0aGUgY29tcG9uZW50LgogKiBAcmV0dXJuIHshT2JqZWN0fQogKiBUT0RPKGltY2hlbmcpOiBXZSBzaG91bGQgZXhwb3J0IHRoZXNlIGFsb25nIHdpdGggTWVkaWFSb3V0ZXIuIFRoaXMgcmVxdWlyZXMKICogdXMgdG8gbW9kaWZ5IHRoZSBjb21wb25lbnQgdG8gaGFuZGxlIG11bHRpcGxlIGV4cG9ydHMuIFdoZW4gdGhhdCBsb2dpYyBpcwogKiBiYWtlZCBpbiBmb3IgYSBjb3VwbGUgb2YgbWlsZXN0b25lcywgd2Ugc2hvdWxkIGJlIGFibGUgdG8gcmVtb3ZlIHRoaXMKICogbWV0aG9kLgogKiBUT0RPKGltY2hlbmcpOiBXZSBzaG91bGQgc3RvcCBleHBvcnRpbmcgbW9qbyBiaW5kaW5ncyBjbGFzc2VzIHRoYXQgdGhlCiAqIE1lZGlhIFJvdXRlciBleHRlbnNpb24gZG9lc24ndCBkaXJlY3RseSB1c2UsIHN1Y2ggYXMKICogbW9qby5Bc3NvY2lhdGVkSW50ZXJmYWNlUHRySW5mbywgbW9qby5JbnRlcmZhY2VQdHJDb250cm9sbGVyIGFuZAogKiBtb2pvLmludGVyZmFjZUNvbnRyb2wuCiAqLwpNZWRpYVJvdXRlci5wcm90b3R5cGUuZ2V0TW9qb0V4cG9ydHMgPSBmdW5jdGlvbigpIHsKICByZXR1cm4gewogICAgQXNzb2NpYXRlZEludGVyZmFjZVB0ckluZm86IG1vam8uQXNzb2NpYXRlZEludGVyZmFjZVB0ckluZm8sCiAgICBCaW5kaW5nOiBtb2pvLkJpbmRpbmcsCiAgICBEaWFsTWVkaWFTaW5rOiBEaWFsTWVkaWFTaW5rQWRhcHRlciwKICAgIENhc3RNZWRpYVNpbms6IENhc3RNZWRpYVNpbmtBZGFwdGVyLAogICAgSGFuZ291dHNNZWRpYVJvdXRlQ29udHJvbGxlcjoKICAgICAgICBtZWRpYVJvdXRlci5tb2pvbS5IYW5nb3V0c01lZGlhUm91dGVDb250cm9sbGVyLAogICAgSGFuZ291dHNNZWRpYVN0YXR1c0V4dHJhRGF0YTogSGFuZ291dHNNZWRpYVN0YXR1c0V4dHJhRGF0YUFkYXB0ZXIsCiAgICBJUEFkZHJlc3M6IElQQWRkcmVzc0FkYXB0ZXIsCiAgICBJUEVuZHBvaW50OiBJUEVuZHBvaW50QWRhcHRlciwKICAgIEludGVyZmFjZVB0ckNvbnRyb2xsZXI6IG1vam8uSW50ZXJmYWNlUHRyQ29udHJvbGxlciwKICAgIEludGVyZmFjZVB0ckluZm86IG1vam8uSW50ZXJmYWNlUHRySW5mbywKICAgIEludGVyZmFjZVJlcXVlc3Q6IG1vam8uSW50ZXJmYWNlUmVxdWVzdCwKICAgIE1lZGlhQ29udHJvbGxlcjogbWVkaWFSb3V0ZXIubW9qb20uTWVkaWFDb250cm9sbGVyLAogICAgTWVkaWFTdGF0dXM6IE1lZGlhU3RhdHVzQWRhcHRlciwKICAgIE1lZGlhU3RhdHVzT2JzZXJ2ZXJQdHI6IG1lZGlhUm91dGVyLm1vam9tLk1lZGlhU3RhdHVzT2JzZXJ2ZXJQdHIsCiAgICBNaXJyb3JTZXJ2aWNlUmVtb3RlcjogTWlycm9yU2VydmljZVJlbW90ZXJBZGFwdGVyLAogICAgTWlycm9yU2VydmljZVJlbW90ZXJQdHI6IE1pcnJvclNlcnZpY2VSZW1vdGVyUHRyQWRhcHRlciwKICAgIE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZVB0cjogTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlUHRyQWRhcHRlciwKICAgIFJlbW90aW5nU3RvcFJlYXNvbjogbWVkaWEubW9qb20uUmVtb3RpbmdTdG9wUmVhc29uLAogICAgUmVtb3RpbmdTdGFydEZhaWxSZWFzb246IG1lZGlhLm1vam9tLlJlbW90aW5nU3RhcnRGYWlsUmVhc29uLAogICAgUmVtb3RpbmdTaW5rRmVhdHVyZTogbWVkaWEubW9qb20uUmVtb3RpbmdTaW5rRmVhdHVyZSwKICAgIFJlbW90aW5nU2lua0F1ZGlvQ2FwYWJpbGl0eToKICAgICAgICBtZWRpYS5tb2pvbS5SZW1vdGluZ1NpbmtBdWRpb0NhcGFiaWxpdHksCiAgICBSZW1vdGluZ1NpbmtWaWRlb0NhcGFiaWxpdHk6CiAgICAgICAgbWVkaWEubW9qb20uUmVtb3RpbmdTaW5rVmlkZW9DYXBhYmlsaXR5LAogICAgUmVtb3RpbmdTaW5rTWV0YWRhdGE6IFJlbW90aW5nU2lua01ldGFkYXRhQWRhcHRlciwKICAgIFJvdXRlQ29udHJvbGxlclR5cGU6IG1lZGlhUm91dGVyLm1vam9tLlJvdXRlQ29udHJvbGxlclR5cGUsCiAgICBPcmlnaW46IHVybC5tb2pvbS5PcmlnaW4sCiAgICBTaW5rOiBNZWRpYVNpbmtBZGFwdGVyLAogICAgU2lua0V4dHJhRGF0YTogTWVkaWFTaW5rRXh0cmFEYXRhQWRhcHRlciwKICAgIFRpbWVEZWx0YTogbW9qby5jb21tb24ubW9qb20uVGltZURlbHRhLAogICAgVXJsOiB1cmwubW9qb20uVXJsLAogICAgaW50ZXJmYWNlQ29udHJvbDogbW9qby5pbnRlcmZhY2VDb250cm9sLAogICAgbWFrZVJlcXVlc3Q6IG1vam8ubWFrZVJlcXVlc3QsCiAgfTsKfTsKCi8qKgogKiBSZWdpc3RlcnMgdGhlIE1lZGlhIFJvdXRlciBQcm92aWRlciBNYW5hZ2VyIHdpdGggdGhlIE1lZGlhIFJvdXRlci4KICogQHJldHVybiB7IVByb21pc2U8T2JqZWN0Pn0gSW5zdGFuY2UgSUQgYW5kIGNvbmZpZyBmb3IgdGhlIE1lZGlhIFJvdXRlci4KICovCk1lZGlhUm91dGVyLnByb3RvdHlwZS5zdGFydCA9IGZ1bmN0aW9uKCkgewogIHJldHVybiB0aGlzLnNlcnZpY2VfLnJlZ2lzdGVyTWVkaWFSb3V0ZVByb3ZpZGVyKAogICAgICBtZWRpYVJvdXRlci5tb2pvbS5NZWRpYVJvdXRlUHJvdmlkZXIuSWQuRVhURU5TSU9OLAogICAgICB0aGlzLm1lZGlhUm91dGVQcm92aWRlckJpbmRpbmdfLmNyZWF0ZUludGVyZmFjZVB0ckFuZEJpbmQoKSkudGhlbigKICAgICAgICAgIGZ1bmN0aW9uKHJlc3BvbnNlKSB7CiAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgJ2luc3RhbmNlX2lkJzogcmVzcG9uc2UuaW5zdGFuY2VJZCwKICAgICAgICAgICAgICAnY29uZmlnJzogewogICAgICAgICAgICAgICAgJ2VuYWJsZV9kaWFsX2Rpc2NvdmVyeSc6IHJlc3BvbnNlLmNvbmZpZy5lbmFibGVEaWFsRGlzY292ZXJ5LAogICAgICAgICAgICAgICAgJ2VuYWJsZV9jYXN0X2Rpc2NvdmVyeSc6IHJlc3BvbnNlLmNvbmZpZy5lbmFibGVDYXN0RGlzY292ZXJ5LAogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfTsKICAgICAgICAgIH0pOwp9CgovKioKICogU2V0cyB0aGUgc2VydmljZSBkZWxlZ2F0ZSBtZXRob2RzLgogKiBAcGFyYW0ge09iamVjdH0gaGFuZGxlcnMKICovCk1lZGlhUm91dGVyLnByb3RvdHlwZS5zZXRIYW5kbGVycyA9IGZ1bmN0aW9uKGhhbmRsZXJzKSB7CiAgdGhpcy5tcnBtXy5zZXRIYW5kbGVycyhoYW5kbGVycyk7Cn0KCi8qKgogKiBUaGUga2VlcCBhbGl2ZSBzdGF0dXMuCiAqIEByZXR1cm4ge2Jvb2xlYW59CiAqLwpNZWRpYVJvdXRlci5wcm90b3R5cGUuZ2V0S2VlcEFsaXZlID0gZnVuY3Rpb24oKSB7CiAgcmV0dXJuIHRoaXMua2VlcEFsaXZlXyAhPSBudWxsOwp9OwoKLyoqCiAqIENhbGxlZCBieSB0aGUgcHJvdmlkZXIgbWFuYWdlciB3aGVuIGEgc2luayBsaXN0IGZvciBhIGdpdmVuIHNvdXJjZSBpcwogKiB1cGRhdGVkLgogKiBAcGFyYW0geyFzdHJpbmd9IHNvdXJjZVVybgogKiBAcGFyYW0geyFBcnJheTwhTWVkaWFTaW5rPn0gc2lua3MKICogQHBhcmFtIHshQXJyYXk8c3RyaW5nfCF1cmwubW9qb20uT3JpZ2luPn0gb3JpZ2lucwogKi8KTWVkaWFSb3V0ZXIucHJvdG90eXBlLm9uU2lua3NSZWNlaXZlZCA9IGZ1bmN0aW9uKHNvdXJjZVVybiwgc2lua3MsIG9yaWdpbnMpIHsKICAvLyB8b3JpZ2luc3wgaXMgYSBzdHJpbmcgYXJyYXkgaWYgdGhlIE1lZGlhIFJvdXRlciBjb21wb25lbnQgZXh0ZW5zaW9uIHZlcnNpb24KICAvLyBpcyA1OSBvciBvbGRlci4gV2l0aG91dCB0aGUgc3RyaW5nVG9Nb2pvT3JpZ2luXygpIGNvbnZlcnNpb24sIGNsaWVudHMgdXNpbmcKICAvLyB0aG9zZSBleHRlbnNpb24gdmVyc2lvbnMgd291bGQgc2VlIGEgY3Jhc2ggc2hvd24gaW4KICAvLyBodHRwczovL2NyYnVnLmNvbS83ODc0MjcuCiAgdGhpcy5zZXJ2aWNlXy5vblNpbmtzUmVjZWl2ZWQoCiAgICAgIG1lZGlhUm91dGVyLm1vam9tLk1lZGlhUm91dGVQcm92aWRlci5JZC5FWFRFTlNJT04sIHNvdXJjZVVybiwKICAgICAgc2lua3MubWFwKHNpbmtUb01vam9fKSwgb3JpZ2lucy5tYXAoc3RyaW5nVG9Nb2pvT3JpZ2luXykpOwp9OwoKLyoqCiAqIENhbGxlZCBieSB0aGUgcHJvdmlkZXIgbWFuYWdlciB3aGVuIGEgc2luayBpcyBmb3VuZCB0byBub3RpZnkgdGhlIE1SIG9mIHRoZQogKiBzaW5rJ3MgSUQuIFRoZSBhY3R1YWwgc2luayB3aWxsIGJlIHJldHVybmVkIHRocm91Z2ggdGhlIG5vcm1hbCBzaW5rIGxpc3QKICogdXBkYXRlIHByb2Nlc3MsIHNvIHRoaXMgaGVscHMgdGhlIE1SIGlkZW50aWZ5IHRoZSBzZWFyY2ggcmVzdWx0IGluIHRoZQogKiBsaXN0LgogKiBAcGFyYW0ge3N0cmluZ30gcHNldWRvU2lua0lkICBJRCBvZiB0aGUgcHNldWRvIHNpbmsgdGhhdCBzdGFydGVkIHRoZQogKiAgICAgc2VhcmNoLgogKiBAcGFyYW0ge3N0cmluZ30gc2lua0lkIElEIG9mIHRoZSBuZXdseS1mb3VuZCBzaW5rLgogKi8KTWVkaWFSb3V0ZXIucHJvdG90eXBlLm9uU2VhcmNoU2lua0lkUmVjZWl2ZWQgPSBmdW5jdGlvbigKICAgIHBzZXVkb1NpbmtJZCwgc2lua0lkKSB7CiAgdGhpcy5zZXJ2aWNlXy5vblNlYXJjaFNpbmtJZFJlY2VpdmVkKHBzZXVkb1NpbmtJZCwgc2lua0lkKTsKfTsKCi8qKgogKiBDYWxsZWQgYnkgdGhlIHByb3ZpZGVyIG1hbmFnZXIgdG8ga2VlcCB0aGUgZXh0ZW5zaW9uIGZyb20gc3VzcGVuZGluZwogKiBpZiBpdCBlbnRlcnMgYSBzdGF0ZSB3aGVyZSBzdXNwZW5zaW9uIGlzIHVuZGVzaXJhYmxlIChlLmcuIHRoZXJlIGlzIGFuCiAqIGFjdGl2ZSBNZWRpYVJvdXRlLikKICogSWYga2VlcEFsaXZlIGlzIHRydWUsIHRoZSBleHRlbnNpb24gaXMga2VwdCBhbGl2ZS4KICogSWYga2VlcEFsaXZlIGlzIGZhbHNlLCB0aGUgZXh0ZW5zaW9uIGlzIGFsbG93ZWQgdG8gc3VzcGVuZC4KICogQHBhcmFtIHtib29sZWFufSBrZWVwQWxpdmUKICovCk1lZGlhUm91dGVyLnByb3RvdHlwZS5zZXRLZWVwQWxpdmUgPSBmdW5jdGlvbihrZWVwQWxpdmUpIHsKICBpZiAoa2VlcEFsaXZlID09PSBmYWxzZSAmJiB0aGlzLmtlZXBBbGl2ZV8pIHsKICAgIHRoaXMua2VlcEFsaXZlXy5wdHIucmVzZXQoKTsKICAgIHRoaXMua2VlcEFsaXZlXyA9IG51bGw7CiAgfSBlbHNlIGlmIChrZWVwQWxpdmUgPT09IHRydWUgJiYgIXRoaXMua2VlcEFsaXZlXykgewogICAgdGhpcy5rZWVwQWxpdmVfID0gbmV3IGV4dGVuc2lvbnMuS2VlcEFsaXZlUHRyOwogICAgTW9qby5iaW5kSW50ZXJmYWNlKGV4dGVuc2lvbnMuS2VlcEFsaXZlLm5hbWUsCiAgICAgICAgICAgICAgICAgICAgICAgbW9qby5tYWtlUmVxdWVzdCh0aGlzLmtlZXBBbGl2ZV8pLmhhbmRsZSk7CiAgfQp9OwoKLyoqCiAqIENhbGxlZCBieSB0aGUgcHJvdmlkZXIgbWFuYWdlciB0byBzZW5kIGFuIGlzc3VlIGZyb20gYSBtZWRpYSByb3V0ZQogKiBwcm92aWRlciB0byB0aGUgTWVkaWEgUm91dGVyLCB0byBzaG93IHRoZSB1c2VyLgogKiBAcGFyYW0geyFPYmplY3R9IGlzc3VlIFRoZSBpc3N1ZSBvYmplY3QuCiAqLwpNZWRpYVJvdXRlci5wcm90b3R5cGUub25Jc3N1ZSA9IGZ1bmN0aW9uKGlzc3VlKSB7CiAgZnVuY3Rpb24gaXNzdWVTZXZlcml0eVRvTW9qb18oc2V2ZXJpdHkpIHsKICAgIHN3aXRjaCAoc2V2ZXJpdHkpIHsKICAgICAgY2FzZSAnZmF0YWwnOgogICAgICAgIHJldHVybiBtZWRpYVJvdXRlci5tb2pvbS5Jc3N1ZS5TZXZlcml0eS5GQVRBTDsKICAgICAgY2FzZSAnd2FybmluZyc6CiAgICAgICAgcmV0dXJuIG1lZGlhUm91dGVyLm1vam9tLklzc3VlLlNldmVyaXR5LldBUk5JTkc7CiAgICAgIGNhc2UgJ25vdGlmaWNhdGlvbic6CiAgICAgICAgcmV0dXJuIG1lZGlhUm91dGVyLm1vam9tLklzc3VlLlNldmVyaXR5Lk5PVElGSUNBVElPTjsKICAgICAgZGVmYXVsdDoKICAgICAgICBjb25zb2xlLmVycm9yKCdVbmtub3duIGlzc3VlIHNldmVyaXR5OiAnICsgc2V2ZXJpdHkpOwogICAgICAgIHJldHVybiBtZWRpYVJvdXRlci5tb2pvbS5Jc3N1ZS5TZXZlcml0eS5OT1RJRklDQVRJT047CiAgICB9CiAgfQoKICBmdW5jdGlvbiBpc3N1ZUFjdGlvblRvTW9qb18oYWN0aW9uKSB7CiAgICBzd2l0Y2ggKGFjdGlvbikgewogICAgICBjYXNlICdkaXNtaXNzJzoKICAgICAgICByZXR1cm4gbWVkaWFSb3V0ZXIubW9qb20uSXNzdWUuQWN0aW9uVHlwZS5ESVNNSVNTOwogICAgICBjYXNlICdsZWFybl9tb3JlJzoKICAgICAgICByZXR1cm4gbWVkaWFSb3V0ZXIubW9qb20uSXNzdWUuQWN0aW9uVHlwZS5MRUFSTl9NT1JFOwogICAgICBkZWZhdWx0OgogICAgICAgIGNvbnNvbGUuZXJyb3IoJ1Vua25vd24gaXNzdWUgYWN0aW9uIHR5cGUgOiAnICsgYWN0aW9uKTsKICAgICAgICByZXR1cm4gbWVkaWFSb3V0ZXIubW9qb20uSXNzdWUuQWN0aW9uVHlwZS5PSzsKICAgIH0KICB9CgogIHZhciBzZWNvbmRhcnlBY3Rpb25zID0gKGlzc3VlLnNlY29uZGFyeUFjdGlvbnMgfHwgW10pLm1hcChpc3N1ZUFjdGlvblRvTW9qb18pOwogIHRoaXMuc2VydmljZV8ub25Jc3N1ZShuZXcgbWVkaWFSb3V0ZXIubW9qb20uSXNzdWUoewogICAgJ3JvdXRlSWQnOiBpc3N1ZS5yb3V0ZUlkIHx8ICcnLAogICAgJ3NldmVyaXR5JzogaXNzdWVTZXZlcml0eVRvTW9qb18oaXNzdWUuc2V2ZXJpdHkpLAogICAgJ3RpdGxlJzogaXNzdWUudGl0bGUsCiAgICAnbWVzc2FnZSc6IGlzc3VlLm1lc3NhZ2UgfHwgJycsCiAgICAnZGVmYXVsdEFjdGlvbic6IGlzc3VlQWN0aW9uVG9Nb2pvXyhpc3N1ZS5kZWZhdWx0QWN0aW9uKSwKICAgICdzZWNvbmRhcnlBY3Rpb25zJzogc2Vjb25kYXJ5QWN0aW9ucywKICAgICdoZWxwUGFnZUlkJzogaXNzdWUuaGVscFBhZ2VJZCwKICAgICdpc0Jsb2NraW5nJzogaXNzdWUuaXNCbG9ja2luZwogIH0pKTsKfTsKCi8qKgogKiBDYWxsZWQgYnkgdGhlIHByb3ZpZGVyIG1hbmFnZXIgd2hlbiB0aGUgc2V0IG9mIGFjdGl2ZSByb3V0ZXMKICogaGFzIGJlZW4gdXBkYXRlZC4KICogQHBhcmFtIHshQXJyYXk8TWVkaWFSb3V0ZT59IHJvdXRlcyBUaGUgYWN0aXZlIHNldCBvZiBtZWRpYSByb3V0ZXMuCiAqIEBwYXJhbSB7c3RyaW5nPX0gc291cmNlVXJuIFRoZSBzb3VyY2VVcm4gYXNzb2NpYXRlZCB3aXRoIHRoaXMgcm91dGUKICogICAgIHF1ZXJ5LgogKiBAcGFyYW0ge0FycmF5PHN0cmluZz49fSBqb2luYWJsZVJvdXRlSWRzIFRoZSBhY3RpdmUgc2V0IG9mIGpvaW5hYmxlCiAqICAgICBtZWRpYSByb3V0ZXMuCiAqLwpNZWRpYVJvdXRlci5wcm90b3R5cGUub25Sb3V0ZXNVcGRhdGVkID0gZnVuY3Rpb24oCiAgICByb3V0ZXMsIHNvdXJjZVVybiA9ICcnLCBqb2luYWJsZVJvdXRlSWRzID0gW10pIHsKICB0aGlzLnNlcnZpY2VfLm9uUm91dGVzVXBkYXRlZCgKICAgICAgbWVkaWFSb3V0ZXIubW9qb20uTWVkaWFSb3V0ZVByb3ZpZGVyLklkLkVYVEVOU0lPTiwKICAgICAgcm91dGVzLm1hcChyb3V0ZVRvTW9qb18pLCBzb3VyY2VVcm4sIGpvaW5hYmxlUm91dGVJZHMpOwp9OwoKLyoqCiAqIENhbGxlZCBieSB0aGUgcHJvdmlkZXIgbWFuYWdlciB3aGVuIHNpbmsgYXZhaWxhYmlsaXR5IGhhcyBiZWVuIHVwZGF0ZWQuCiAqIEBwYXJhbSB7IW1lZGlhUm91dGVyLm1vam9tLk1lZGlhUm91dGVyLlNpbmtBdmFpbGFiaWxpdHl9IGF2YWlsYWJpbGl0eQogKiAgICAgVGhlIG5ldyBzaW5rIGF2YWlsYWJpbGl0eS4KICovCk1lZGlhUm91dGVyLnByb3RvdHlwZS5vblNpbmtBdmFpbGFiaWxpdHlVcGRhdGVkID0gZnVuY3Rpb24oYXZhaWxhYmlsaXR5KSB7CiAgdGhpcy5zZXJ2aWNlXy5vblNpbmtBdmFpbGFiaWxpdHlVcGRhdGVkKAogICAgICBtZWRpYVJvdXRlci5tb2pvbS5NZWRpYVJvdXRlUHJvdmlkZXIuSWQuRVhURU5TSU9OLCBhdmFpbGFiaWxpdHkpOwp9OwoKLyoqCiAqIENhbGxlZCBieSB0aGUgcHJvdmlkZXIgbWFuYWdlciB3aGVuIHRoZSBzdGF0ZSBvZiBhIHByZXNlbnRhdGlvbiBjb25uZWN0ZWQKICogdG8gYSByb3V0ZSBoYXMgY2hhbmdlZC4KICogQHBhcmFtIHtzdHJpbmd9IHJvdXRlSWQKICogQHBhcmFtIHtzdHJpbmd9IHN0YXRlCiAqLwpNZWRpYVJvdXRlci5wcm90b3R5cGUub25QcmVzZW50YXRpb25Db25uZWN0aW9uU3RhdGVDaGFuZ2VkID0KICAgIGZ1bmN0aW9uKHJvdXRlSWQsIHN0YXRlKSB7CiAgdGhpcy5zZXJ2aWNlXy5vblByZXNlbnRhdGlvbkNvbm5lY3Rpb25TdGF0ZUNoYW5nZWQoCiAgICAgIHJvdXRlSWQsIHByZXNlbnRhdGlvbkNvbm5lY3Rpb25TdGF0ZVRvTW9qb18oc3RhdGUpKTsKfTsKCi8qKgogKiBDYWxsZWQgYnkgdGhlIHByb3ZpZGVyIG1hbmFnZXIgd2hlbiB0aGUgc3RhdGUgb2YgYSBwcmVzZW50YXRpb24gY29ubmVjdGVkCiAqIHRvIGEgcm91dGUgaGFzIGNsb3NlZC4KICogQHBhcmFtIHtzdHJpbmd9IHJvdXRlSWQKICogQHBhcmFtIHtzdHJpbmd9IHJlYXNvbgogKiBAcGFyYW0ge3N0cmluZ30gbWVzc2FnZQogKi8KTWVkaWFSb3V0ZXIucHJvdG90eXBlLm9uUHJlc2VudGF0aW9uQ29ubmVjdGlvbkNsb3NlZCA9CiAgICBmdW5jdGlvbihyb3V0ZUlkLCByZWFzb24sIG1lc3NhZ2UpIHsKICB0aGlzLnNlcnZpY2VfLm9uUHJlc2VudGF0aW9uQ29ubmVjdGlvbkNsb3NlZCgKICAgICAgcm91dGVJZCwgcHJlc2VudGF0aW9uQ29ubmVjdGlvbkNsb3NlUmVhc29uVG9Nb2pvXyhyZWFzb24pLCBtZXNzYWdlKTsKfTsKCi8qKgogKiBAcGFyYW0ge3N0cmluZ30gcm91dGVJZAogKiBAcGFyYW0geyFBcnJheTwhUm91dGVNZXNzYWdlPn0gbWVzYWdlcwogKi8KTWVkaWFSb3V0ZXIucHJvdG90eXBlLm9uUm91dGVNZXNzYWdlc1JlY2VpdmVkID0gZnVuY3Rpb24ocm91dGVJZCwgbWVzc2FnZXMpIHsKICB0aGlzLnNlcnZpY2VfLm9uUm91dGVNZXNzYWdlc1JlY2VpdmVkKAogICAgICByb3V0ZUlkLCBtZXNzYWdlcy5tYXAobWVzc2FnZVRvTW9qb18pKTsKfTsKCi8qKgogKiBAcGFyYW0ge251bWJlcn0gdGFiSWQKICogQHBhcmFtIHshbWVkaWEubW9qb20uTWlycm9yU2VydmljZVJlbW90ZXJQdHJ9IHJlbW90ZXIKICogQHBhcmFtIHshbW9qby5JbnRlcmZhY2VSZXF1ZXN0fSByZW1vdGluZ1NvdXJjZQogKi8KTWVkaWFSb3V0ZXIucHJvdG90eXBlLm9uTWVkaWFSZW1vdGVyQ3JlYXRlZCA9IGZ1bmN0aW9uKHRhYklkLCByZW1vdGVyLAogICAgcmVtb3RpbmdTb3VyY2UpIHsKICB0aGlzLnNlcnZpY2VfLm9uTWVkaWFSZW1vdGVyQ3JlYXRlZCgKICAgICAgdGFiSWQsCiAgICAgIG5ldyBtZWRpYS5tb2pvbS5NaXJyb3JTZXJ2aWNlUmVtb3RlclB0cihyZW1vdGVyLnB0ci5wYXNzSW50ZXJmYWNlKCkpLAogICAgICByZW1vdGluZ1NvdXJjZSk7Cn0KCi8qKgogKiBPYmplY3QgY29udGFpbmluZyBjYWxsYmFja3Mgc2V0IGJ5IHRoZSBwcm92aWRlciBtYW5hZ2VyLgogKgogKiBAY29uc3RydWN0b3IKICogQHN0cnVjdAogKi8KZnVuY3Rpb24gTWVkaWFSb3V0ZXJIYW5kbGVycygpIHsKICAvKioKICAgKiBAdHlwZSB7ZnVuY3Rpb24oIXN0cmluZywgIXN0cmluZywgIXN0cmluZywgIXN0cmluZywgIW51bWJlcil9CiAgICovCiAgdGhpcy5jcmVhdGVSb3V0ZSA9IG51bGw7CgogIC8qKgogICAqIEB0eXBlIHtmdW5jdGlvbighc3RyaW5nLCAhc3RyaW5nLCAhc3RyaW5nLCAhbnVtYmVyKX0KICAgKi8KICB0aGlzLmpvaW5Sb3V0ZSA9IG51bGw7CgogIC8qKgogICAqIEB0eXBlIHtmdW5jdGlvbihzdHJpbmcpOiBQcm9taXNlfQogICAqLwogIHRoaXMudGVybWluYXRlUm91dGUgPSBudWxsOwoKICAvKioKICAgKiBAdHlwZSB7ZnVuY3Rpb24oc3RyaW5nKX0KICAgKi8KICB0aGlzLnN0YXJ0T2JzZXJ2aW5nTWVkaWFTaW5rcyA9IG51bGw7CgogIC8qKgogICAqIEB0eXBlIHtmdW5jdGlvbihzdHJpbmcpfQogICAqLwogIHRoaXMuc3RvcE9ic2VydmluZ01lZGlhU2lua3MgPSBudWxsOwoKICAvKioKICAgKiBAdHlwZSB7ZnVuY3Rpb24oc3RyaW5nLCBzdHJpbmcpOiBQcm9taXNlfQogICAqLwogIHRoaXMuc2VuZFJvdXRlTWVzc2FnZSA9IG51bGw7CgogIC8qKgogICAqIEB0eXBlIHtmdW5jdGlvbihzdHJpbmcsIFVpbnQ4QXJyYXkpOiBQcm9taXNlfQogICAqLwogIHRoaXMuc2VuZFJvdXRlQmluYXJ5TWVzc2FnZSA9IG51bGw7CgogIC8qKgogICAqIEB0eXBlIHtmdW5jdGlvbihzdHJpbmcpfQogICAqLwogIHRoaXMuc3RhcnRMaXN0ZW5pbmdGb3JSb3V0ZU1lc3NhZ2VzID0gbnVsbDsKCiAgLyoqCiAgICogQHR5cGUge2Z1bmN0aW9uKHN0cmluZyl9CiAgICovCiAgdGhpcy5zdG9wTGlzdGVuaW5nRm9yUm91dGVNZXNzYWdlcyA9IG51bGw7CgogIC8qKgogICAqIEB0eXBlIHtmdW5jdGlvbihzdHJpbmcpfQogICAqLwogIHRoaXMuZGV0YWNoUm91dGUgPSBudWxsOwoKICAvKioKICAgKiBAdHlwZSB7ZnVuY3Rpb24oKX0KICAgKi8KICB0aGlzLnN0YXJ0T2JzZXJ2aW5nTWVkaWFSb3V0ZXMgPSBudWxsOwoKICAvKioKICAgKiBAdHlwZSB7ZnVuY3Rpb24oKX0KICAgKi8KICB0aGlzLnN0b3BPYnNlcnZpbmdNZWRpYVJvdXRlcyA9IG51bGw7CgogIC8qKgogICAqIEB0eXBlIHtmdW5jdGlvbigpfQogICAqLwogIHRoaXMuY29ubmVjdFJvdXRlQnlSb3V0ZUlkID0gbnVsbDsKCiAgLyoqCiAgICogQHR5cGUge2Z1bmN0aW9uKCl9CiAgICovCiAgdGhpcy5lbmFibGVNZG5zRGlzY292ZXJ5ID0gbnVsbDsKCiAgLyoqCiAgICogQHR5cGUge2Z1bmN0aW9uKCl9CiAgICovCiAgdGhpcy51cGRhdGVNZWRpYVNpbmtzID0gbnVsbDsKCiAgLyoqCiAgICogQHR5cGUge2Z1bmN0aW9uKHN0cmluZywgc3RyaW5nLCAhU2lua1NlYXJjaENyaXRlcmlhKTogc3RyaW5nfQogICAqLwogIHRoaXMuc2VhcmNoU2lua3MgPSBudWxsOwoKICAvKioKICAgKiBAdHlwZSB7ZnVuY3Rpb24oKX0KICAgKi8KICB0aGlzLnByb3ZpZGVTaW5rcyA9IG51bGw7CgogIC8qKgogICAqIEB0eXBlIHtmdW5jdGlvbihzdHJpbmcsICFtb2pvLkludGVyZmFjZVJlcXVlc3QsCiAgICogICAgICAgICAgICAhbWVkaWFSb3V0ZXIubW9qb20uTWVkaWFTdGF0dXNPYnNlcnZlclB0cik6ICFQcm9taXNlPHZvaWQ+fQogICAqLwogIHRoaXMuY3JlYXRlTWVkaWFSb3V0ZUNvbnRyb2xsZXIgPSBudWxsOwp9OwoKLyoqCiAqIFJvdXRlcyBjYWxscyBmcm9tIE1lZGlhIFJvdXRlciB0byB0aGUgcHJvdmlkZXIgbWFuYWdlciBleHRlbnNpb24uCiAqIFJlZ2lzdGVyZWQgd2l0aCB0aGUgTWVkaWFSb3V0ZXIgc3R1Yi4KICogQHBhcmFtIHshTWVkaWFSb3V0ZXJ9IE1lZGlhUm91dGVyIHByb3h5IHRvIGNhbGwgaW50byB0aGUKICogTWVkaWEgUm91dGVyIG1vam8gaW50ZXJmYWNlLgogKiBAY29uc3RydWN0b3IKICovCmZ1bmN0aW9uIE1lZGlhUm91dGVQcm92aWRlcihtZWRpYVJvdXRlcikgewogIC8qKgogICAqIE9iamVjdCBjb250YWluaW5nIEpTIGNhbGxiYWNrcyBpbnRvIFByb3ZpZGVyIE1hbmFnZXIgY29kZS4KICAgKiBAdHlwZSB7IU1lZGlhUm91dGVySGFuZGxlcnN9CiAgICovCiAgdGhpcy5oYW5kbGVyc18gPSBuZXcgTWVkaWFSb3V0ZXJIYW5kbGVycygpOwoKICAvKioKICAgKiBQcm94eSBjbGFzcyB0byB0aGUgYnJvd3NlcidzIE1lZGlhIFJvdXRlciBNb2pvIHNlcnZpY2UuCiAgICogQHR5cGUgeyFNZWRpYVJvdXRlcn0KICAgKi8KICB0aGlzLm1lZGlhUm91dGVyXyA9IG1lZGlhUm91dGVyOwp9CgovKgogKiBTZXRzIHRoZSBjYWxsYmFjayBoYW5kbGVyIHVzZWQgdG8gaW52b2tlIG1ldGhvZHMgaW4gdGhlIHByb3ZpZGVyIG1hbmFnZXIuCiAqCiAqIEBwYXJhbSB7IU1lZGlhUm91dGVySGFuZGxlcnN9IGhhbmRsZXJzCiAqLwpNZWRpYVJvdXRlUHJvdmlkZXIucHJvdG90eXBlLnNldEhhbmRsZXJzID0gZnVuY3Rpb24oaGFuZGxlcnMpIHsKICB0aGlzLmhhbmRsZXJzXyA9IGhhbmRsZXJzOwogIHZhciByZXF1aXJlZEhhbmRsZXJzID0gWwogICAgJ3N0b3BPYnNlcnZpbmdNZWRpYVJvdXRlcycsCiAgICAnc3RhcnRPYnNlcnZpbmdNZWRpYVJvdXRlcycsCiAgICAnc2VuZFJvdXRlTWVzc2FnZScsCiAgICAnc2VuZFJvdXRlQmluYXJ5TWVzc2FnZScsCiAgICAnc3RhcnRMaXN0ZW5pbmdGb3JSb3V0ZU1lc3NhZ2VzJywKICAgICdzdG9wTGlzdGVuaW5nRm9yUm91dGVNZXNzYWdlcycsCiAgICAnZGV0YWNoUm91dGUnLAogICAgJ3Rlcm1pbmF0ZVJvdXRlJywKICAgICdqb2luUm91dGUnLAogICAgJ2NyZWF0ZVJvdXRlJywKICAgICdzdG9wT2JzZXJ2aW5nTWVkaWFTaW5rcycsCiAgICAnc3RhcnRPYnNlcnZpbmdNZWRpYVJvdXRlcycsCiAgICAnY29ubmVjdFJvdXRlQnlSb3V0ZUlkJywKICAgICdlbmFibGVNZG5zRGlzY292ZXJ5JywKICAgICd1cGRhdGVNZWRpYVNpbmtzJywKICAgICdzZWFyY2hTaW5rcycsCiAgICAncHJvdmlkZVNpbmtzJywKICAgICdjcmVhdGVNZWRpYVJvdXRlQ29udHJvbGxlcicsCiAgICAnb25CZWZvcmVJbnZva2VIYW5kbGVyJwogIF07CiAgcmVxdWlyZWRIYW5kbGVycy5mb3JFYWNoKGZ1bmN0aW9uKG5leHRIYW5kbGVyKSB7CiAgICBpZiAoaGFuZGxlcnNbbmV4dEhhbmRsZXJdID09PSB1bmRlZmluZWQpIHsKICAgICAgY29uc29sZS5lcnJvcihuZXh0SGFuZGxlciArICcgaGFuZGxlciBub3QgcmVnaXN0ZXJlZC4nKTsKICAgIH0KICB9KTsKfQoKLyoqCiAqIFN0YXJ0cyBxdWVyeWluZyBmb3Igc2lua3MgY2FwYWJsZSBvZiBkaXNwbGF5aW5nIHRoZSBtZWRpYSBzb3VyY2UKICogZGVzaWduYXRlZCBieSB8c291cmNlVXJufC4gIFJlc3VsdHMgYXJlIHJldHVybmVkIGJ5IGNhbGxpbmcKICogT25TaW5rc1JlY2VpdmVkLgogKiBAcGFyYW0geyFzdHJpbmd9IHNvdXJjZVVybgogKi8KTWVkaWFSb3V0ZVByb3ZpZGVyLnByb3RvdHlwZS5zdGFydE9ic2VydmluZ01lZGlhU2lua3MgPQogICAgZnVuY3Rpb24oc291cmNlVXJuKSB7CiAgdGhpcy5oYW5kbGVyc18ub25CZWZvcmVJbnZva2VIYW5kbGVyKCk7CiAgdGhpcy5oYW5kbGVyc18uc3RhcnRPYnNlcnZpbmdNZWRpYVNpbmtzKHNvdXJjZVVybik7Cn07CgovKioKICogU3RvcHMgcXVlcnlpbmcgZm9yIHNpbmtzIGNhcGFibGUgb2YgZGlzcGxheWluZyB8c291cmNlVXJufC4KICogQHBhcmFtIHshc3RyaW5nfSBzb3VyY2VVcm4KICovCk1lZGlhUm91dGVQcm92aWRlci5wcm90b3R5cGUuc3RvcE9ic2VydmluZ01lZGlhU2lua3MgPQogICAgZnVuY3Rpb24oc291cmNlVXJuKSB7CiAgdGhpcy5oYW5kbGVyc18ub25CZWZvcmVJbnZva2VIYW5kbGVyKCk7CiAgdGhpcy5oYW5kbGVyc18uc3RvcE9ic2VydmluZ01lZGlhU2lua3Moc291cmNlVXJuKTsKfTsKCi8qKgogKiBSZXF1ZXN0cyB0aGF0IHxzaW5rSWR8IHJlbmRlciB0aGUgbWVkaWEgcmVmZXJlbmNlZCBieSB8c291cmNlVXJufC4gSWYgdGhlCiAqIHJlcXVlc3QgaXMgZnJvbSB0aGUgUHJlc2VudGF0aW9uIEFQSSwgdGhlbiBvcmlnaW4gYW5kIHRhYklkIHdpbGwKICogYmUgcG9wdWxhdGVkLgogKiBAcGFyYW0geyFzdHJpbmd9IHNvdXJjZVVybiBNZWRpYSBzb3VyY2UgdG8gcmVuZGVyLgogKiBAcGFyYW0geyFzdHJpbmd9IHNpbmtJZCBNZWRpYSBzaW5rIElELgogKiBAcGFyYW0geyFzdHJpbmd9IHByZXNlbnRhdGlvbklkIFByZXNlbnRhdGlvbiBJRCBmcm9tIHRoZSBzaXRlCiAqICAgICByZXF1ZXN0aW5nIHByZXNlbnRhdGlvbi4gVE9ETyhtZm9sdHopOiBSZW1vdmUuCiAqIEBwYXJhbSB7IXVybC5tb2pvbS5PcmlnaW59IG9yaWdpbiBPcmlnaW4gb2Ygc2l0ZSByZXF1ZXN0aW5nIHByZXNlbnRhdGlvbi4KICogQHBhcmFtIHshbnVtYmVyfSB0YWJJZCBJRCBvZiB0YWIgcmVxdWVzdGluZyBwcmVzZW50YXRpb24uCiAqIEBwYXJhbSB7IW1vam8uY29tbW9uLm1vam9tLlRpbWVEZWx0YX0gdGltZW91dCBJZiBwb3NpdGl2ZSwgdGhlIHRpbWVvdXQKICogICAgIGR1cmF0aW9uIGZvciB0aGUgcmVxdWVzdC4gT3RoZXJ3aXNlLCB0aGUgZGVmYXVsdCBkdXJhdGlvbiB3aWxsIGJlIHVzZWQuCiAqIEBwYXJhbSB7IWJvb2xlYW59IGluY29nbml0byBJZiB0cnVlLCB0aGUgcm91dGUgaXMgYmVpbmcgcmVxdWVzdGVkIGJ5CiAqICAgICBhbiBpbmNvZ25pdG8gcHJvZmlsZS4KICogQHJldHVybiB7IVByb21pc2UuPCFPYmplY3Q+fSBBIFByb21pc2UgcmVzb2x2aW5nIHRvIGFuIG9iamVjdCBkZXNjcmliaW5nCiAqICAgICB0aGUgbmV3bHkgY3JlYXRlZCBtZWRpYSByb3V0ZSwgb3IgcmVqZWN0aW5nIHdpdGggYW4gZXJyb3IgbWVzc2FnZSBvbgogKiAgICAgZmFpbHVyZS4KICovCk1lZGlhUm91dGVQcm92aWRlci5wcm90b3R5cGUuY3JlYXRlUm91dGUgPQogICAgZnVuY3Rpb24oc291cmNlVXJuLCBzaW5rSWQsIHByZXNlbnRhdGlvbklkLCBvcmlnaW4sIHRhYklkLAogICAgICAgICAgICAgdGltZW91dCwgaW5jb2duaXRvKSB7CiAgdGhpcy5oYW5kbGVyc18ub25CZWZvcmVJbnZva2VIYW5kbGVyKCk7CiAgcmV0dXJuIHRoaXMuaGFuZGxlcnNfLmNyZWF0ZVJvdXRlKAogICAgICBzb3VyY2VVcm4sIHNpbmtJZCwgcHJlc2VudGF0aW9uSWQsIG9yaWdpbiwgdGFiSWQsCiAgICAgIE1hdGguZmxvb3IodGltZW91dC5taWNyb3NlY29uZHMgLyAxMDAwKSwgaW5jb2duaXRvKQogICAgICAudGhlbihmdW5jdGlvbihyb3V0ZSkgewogICAgICAgIHJldHVybiB0b1N1Y2Nlc3NSb3V0ZVJlc3BvbnNlXyhyb3V0ZSk7CiAgICAgIH0sCiAgICAgIGZ1bmN0aW9uKGVycikgewogICAgICAgIHJldHVybiB0b0Vycm9yUm91dGVSZXNwb25zZV8oZXJyKTsKICAgICAgfSk7Cn07CgovKioKICogSGFuZGxlcyBhIHJlcXVlc3QgdmlhIHRoZSBQcmVzZW50YXRpb24gQVBJIHRvIGpvaW4gYW4gZXhpc3Rpbmcgcm91dGUgZ2l2ZW4KICogYnkgfHNvdXJjZVVybnwgYW5kIHxwcmVzZW50YXRpb25JZHwuIHxvcmlnaW58IGFuZCB8dGFiSWR8IGFyZSB1c2VkIGZvcgogKiB2YWxpZGF0aW5nIHNhbWUtb3JpZ2luL3RhYiBzY29wZS4KICogQHBhcmFtIHshc3RyaW5nfSBzb3VyY2VVcm4gTWVkaWEgc291cmNlIHRvIHJlbmRlci4KICogQHBhcmFtIHshc3RyaW5nfSBwcmVzZW50YXRpb25JZCBQcmVzZW50YXRpb24gSUQgdG8gam9pbi4KICogQHBhcmFtIHshdXJsLm1vam9tLk9yaWdpbn0gb3JpZ2luIE9yaWdpbiBvZiBzaXRlIHJlcXVlc3Rpbmcgam9pbi4KICogQHBhcmFtIHshbnVtYmVyfSB0YWJJZCBJRCBvZiB0YWIgcmVxdWVzdGluZyBqb2luLgogKiBAcGFyYW0geyFtb2pvLmNvbW1vbi5tb2pvbS5UaW1lRGVsdGF9IHRpbWVvdXQgSWYgcG9zaXRpdmUsIHRoZSB0aW1lb3V0CiAqICAgICBkdXJhdGlvbiBmb3IgdGhlIHJlcXVlc3QuIE90aGVyd2lzZSwgdGhlIGRlZmF1bHQgZHVyYXRpb24gd2lsbCBiZSB1c2VkLgogKiBAcGFyYW0geyFib29sZWFufSBpbmNvZ25pdG8gSWYgdHJ1ZSwgdGhlIHJvdXRlIGlzIGJlaW5nIHJlcXVlc3RlZCBieQogKiAgICAgYW4gaW5jb2duaXRvIHByb2ZpbGUuCiAqIEByZXR1cm4geyFQcm9taXNlLjwhT2JqZWN0Pn0gQSBQcm9taXNlIHJlc29sdmluZyB0byBhbiBvYmplY3QgZGVzY3JpYmluZwogKiAgICAgdGhlIG5ld2x5IGNyZWF0ZWQgbWVkaWEgcm91dGUsIG9yIHJlamVjdGluZyB3aXRoIGFuIGVycm9yIG1lc3NhZ2Ugb24KICogICAgIGZhaWx1cmUuCiAqLwpNZWRpYVJvdXRlUHJvdmlkZXIucHJvdG90eXBlLmpvaW5Sb3V0ZSA9CiAgICBmdW5jdGlvbihzb3VyY2VVcm4sIHByZXNlbnRhdGlvbklkLCBvcmlnaW4sIHRhYklkLCB0aW1lb3V0LAogICAgICAgICAgICAgaW5jb2duaXRvKSB7CiAgdGhpcy5oYW5kbGVyc18ub25CZWZvcmVJbnZva2VIYW5kbGVyKCk7CiAgcmV0dXJuIHRoaXMuaGFuZGxlcnNfLmpvaW5Sb3V0ZSgKICAgICAgc291cmNlVXJuLCBwcmVzZW50YXRpb25JZCwgb3JpZ2luLCB0YWJJZCwKICAgICAgTWF0aC5mbG9vcih0aW1lb3V0Lm1pY3Jvc2Vjb25kcyAvIDEwMDApLCBpbmNvZ25pdG8pCiAgICAgIC50aGVuKGZ1bmN0aW9uKHJvdXRlKSB7CiAgICAgICAgcmV0dXJuIHRvU3VjY2Vzc1JvdXRlUmVzcG9uc2VfKHJvdXRlKTsKICAgICAgfSwKICAgICAgZnVuY3Rpb24oZXJyKSB7CiAgICAgICAgcmV0dXJuIHRvRXJyb3JSb3V0ZVJlc3BvbnNlXyhlcnIpOwogICAgICB9KTsKfTsKCi8qKgogKiBIYW5kbGVzIGEgcmVxdWVzdCB2aWEgdGhlIFByZXNlbnRhdGlvbiBBUEkgdG8gam9pbiBhbiBleGlzdGluZyByb3V0ZSBnaXZlbgogKiBieSB8c291cmNlVXJufCBhbmQgfHJvdXRlSWR8LiB8b3JpZ2lufCBhbmQgfHRhYklkfCBhcmUgdXNlZCBmb3IKICogdmFsaWRhdGluZyBzYW1lLW9yaWdpbi90YWIgc2NvcGUuCiAqIEBwYXJhbSB7IXN0cmluZ30gc291cmNlVXJuIE1lZGlhIHNvdXJjZSB0byByZW5kZXIuCiAqIEBwYXJhbSB7IXN0cmluZ30gcm91dGVJZCBSb3V0ZSBJRCB0byBqb2luLgogKiBAcGFyYW0geyFzdHJpbmd9IHByZXNlbnRhdGlvbklkIFByZXNlbnRhdGlvbiBJRCB0byBqb2luLgogKiBAcGFyYW0geyF1cmwubW9qb20uT3JpZ2lufSBvcmlnaW4gT3JpZ2luIG9mIHNpdGUgcmVxdWVzdGluZyBqb2luLgogKiBAcGFyYW0geyFudW1iZXJ9IHRhYklkIElEIG9mIHRhYiByZXF1ZXN0aW5nIGpvaW4uCiAqIEBwYXJhbSB7IW1vam8uY29tbW9uLm1vam9tLlRpbWVEZWx0YX0gdGltZW91dCBJZiBwb3NpdGl2ZSwgdGhlIHRpbWVvdXQKICogICAgIGR1cmF0aW9uIGZvciB0aGUgcmVxdWVzdC4gT3RoZXJ3aXNlLCB0aGUgZGVmYXVsdCBkdXJhdGlvbiB3aWxsIGJlIHVzZWQuCiAqIEBwYXJhbSB7IWJvb2xlYW59IGluY29nbml0byBJZiB0cnVlLCB0aGUgcm91dGUgaXMgYmVpbmcgcmVxdWVzdGVkIGJ5CiAqICAgICBhbiBpbmNvZ25pdG8gcHJvZmlsZS4KICogQHJldHVybiB7IVByb21pc2UuPCFPYmplY3Q+fSBBIFByb21pc2UgcmVzb2x2aW5nIHRvIGFuIG9iamVjdCBkZXNjcmliaW5nCiAqICAgICB0aGUgbmV3bHkgY3JlYXRlZCBtZWRpYSByb3V0ZSwgb3IgcmVqZWN0aW5nIHdpdGggYW4gZXJyb3IgbWVzc2FnZSBvbgogKiAgICAgZmFpbHVyZS4KICovCk1lZGlhUm91dGVQcm92aWRlci5wcm90b3R5cGUuY29ubmVjdFJvdXRlQnlSb3V0ZUlkID0KICAgIGZ1bmN0aW9uKHNvdXJjZVVybiwgcm91dGVJZCwgcHJlc2VudGF0aW9uSWQsIG9yaWdpbiwgdGFiSWQsCiAgICAgICAgICAgICB0aW1lb3V0LCBpbmNvZ25pdG8pIHsKICB0aGlzLmhhbmRsZXJzXy5vbkJlZm9yZUludm9rZUhhbmRsZXIoKTsKICByZXR1cm4gdGhpcy5oYW5kbGVyc18uY29ubmVjdFJvdXRlQnlSb3V0ZUlkKAogICAgICBzb3VyY2VVcm4sIHJvdXRlSWQsIHByZXNlbnRhdGlvbklkLCBvcmlnaW4sIHRhYklkLAogICAgICBNYXRoLmZsb29yKHRpbWVvdXQubWljcm9zZWNvbmRzIC8gMTAwMCksIGluY29nbml0bykKICAgICAgLnRoZW4oZnVuY3Rpb24ocm91dGUpIHsKICAgICAgICByZXR1cm4gdG9TdWNjZXNzUm91dGVSZXNwb25zZV8ocm91dGUpOwogICAgICB9LAogICAgICBmdW5jdGlvbihlcnIpIHsKICAgICAgICByZXR1cm4gdG9FcnJvclJvdXRlUmVzcG9uc2VfKGVycik7CiAgICAgIH0pOwp9OwoKLyoqCiAqIFRlcm1pbmF0ZXMgdGhlIHJvdXRlIHNwZWNpZmllZCBieSB8cm91dGVJZHwuCiAqIEBwYXJhbSB7IXN0cmluZ30gcm91dGVJZAogKiBAcmV0dXJuIHshUHJvbWlzZTwhT2JqZWN0Pn0gQSBQcm9taXNlIHJlc29sdmluZyB0byBhbiBvYmplY3QgZGVzY3JpYmluZwogKiAgICB0aGUgcmVzdWx0IG9mIHRoZSB0ZXJtaW5hdGUgb3BlcmF0aW9uLCBvciByZWplY3Rpbmcgd2l0aCBhbiBlcnJvcgogKiAgICBtZXNzYWdlIGFuZCBjb2RlIGlmIHRoZSBvcGVyYXRpb24gZmFpbGVkLgogKi8KTWVkaWFSb3V0ZVByb3ZpZGVyLnByb3RvdHlwZS50ZXJtaW5hdGVSb3V0ZSA9IGZ1bmN0aW9uKHJvdXRlSWQpIHsKICB0aGlzLmhhbmRsZXJzXy5vbkJlZm9yZUludm9rZUhhbmRsZXIoKTsKICByZXR1cm4gdGhpcy5oYW5kbGVyc18udGVybWluYXRlUm91dGUocm91dGVJZCkudGhlbigKICAgICAgKCkgPT4gKHtyZXN1bHRDb2RlOiBtZWRpYVJvdXRlci5tb2pvbS5Sb3V0ZVJlcXVlc3RSZXN1bHRDb2RlLk9LfSksCiAgICAgIChlcnIpID0+IHRvRXJyb3JSb3V0ZVJlc3BvbnNlXyhlcnIpKTsKfTsKCi8qKgogKiBQb3N0cyBhIG1lc3NhZ2UgdG8gdGhlIHJvdXRlIGRlc2lnbmF0ZWQgYnkgfHJvdXRlSWR8LgogKiBAcGFyYW0geyFzdHJpbmd9IHJvdXRlSWQKICogQHBhcmFtIHshc3RyaW5nfSBtZXNzYWdlCiAqIEByZXR1cm4geyFQcm9taXNlLjxib29sZWFuPn0gUmVzb2x2ZWQgd2l0aCB0cnVlIGlmIHRoZSBtZXNzYWdlIHdhcyBzZW50LAogKiAgICBvciBmYWxzZSBvbiBmYWlsdXJlLgogKi8KTWVkaWFSb3V0ZVByb3ZpZGVyLnByb3RvdHlwZS5zZW5kUm91dGVNZXNzYWdlID0gZnVuY3Rpb24oCiAgcm91dGVJZCwgbWVzc2FnZSkgewogIHRoaXMuaGFuZGxlcnNfLm9uQmVmb3JlSW52b2tlSGFuZGxlcigpOwogIHJldHVybiB0aGlzLmhhbmRsZXJzXy5zZW5kUm91dGVNZXNzYWdlKHJvdXRlSWQsIG1lc3NhZ2UpCiAgICAgIC50aGVuKGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB7J3NlbnQnOiB0cnVlfTsKICAgICAgfSwgZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHsnc2VudCc6IGZhbHNlfTsKICAgICAgfSk7Cn07CgovKioKICogU2VuZHMgYSBiaW5hcnkgbWVzc2FnZSB0byB0aGUgcm91dGUgZGVzaWduYXRlZCBieSB8cm91dGVJZHwuCiAqIEBwYXJhbSB7IXN0cmluZ30gcm91dGVJZAogKiBAcGFyYW0geyFBcnJheTxudW1iZXI+fSBkYXRhCiAqIEByZXR1cm4geyFQcm9taXNlLjxib29sZWFuPn0gUmVzb2x2ZWQgd2l0aCB0cnVlIGlmIHRoZSBkYXRhIHdhcyBzZW50LAogKiAgICBvciBmYWxzZSBvbiBmYWlsdXJlLgogKi8KTWVkaWFSb3V0ZVByb3ZpZGVyLnByb3RvdHlwZS5zZW5kUm91dGVCaW5hcnlNZXNzYWdlID0gZnVuY3Rpb24oCiAgcm91dGVJZCwgZGF0YSkgewogIHRoaXMuaGFuZGxlcnNfLm9uQmVmb3JlSW52b2tlSGFuZGxlcigpOwogIHJldHVybiB0aGlzLmhhbmRsZXJzXy5zZW5kUm91dGVCaW5hcnlNZXNzYWdlKHJvdXRlSWQsIG5ldyBVaW50OEFycmF5KGRhdGEpKQogICAgICAudGhlbihmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4geydzZW50JzogdHJ1ZX07CiAgICAgIH0sIGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB7J3NlbnQnOiBmYWxzZX07CiAgICAgIH0pOwp9OwoKLyoqCiAqIExpc3RlbiBmb3IgbWVzc2FnZXMgZnJvbSBhIHJvdXRlLgogKiBAcGFyYW0geyFzdHJpbmd9IHJvdXRlSWQKICovCk1lZGlhUm91dGVQcm92aWRlci5wcm90b3R5cGUuc3RhcnRMaXN0ZW5pbmdGb3JSb3V0ZU1lc3NhZ2VzID0gZnVuY3Rpb24oCiAgICByb3V0ZUlkKSB7CiAgdGhpcy5oYW5kbGVyc18ub25CZWZvcmVJbnZva2VIYW5kbGVyKCk7CiAgdGhpcy5oYW5kbGVyc18uc3RhcnRMaXN0ZW5pbmdGb3JSb3V0ZU1lc3NhZ2VzKHJvdXRlSWQpOwp9OwoKLyoqCiAqIEBwYXJhbSB7IXN0cmluZ30gcm91dGVJZAogKi8KTWVkaWFSb3V0ZVByb3ZpZGVyLnByb3RvdHlwZS5zdG9wTGlzdGVuaW5nRm9yUm91dGVNZXNzYWdlcyA9IGZ1bmN0aW9uKAogICAgcm91dGVJZCkgewogIHRoaXMuaGFuZGxlcnNfLm9uQmVmb3JlSW52b2tlSGFuZGxlcigpOwogIHRoaXMuaGFuZGxlcnNfLnN0b3BMaXN0ZW5pbmdGb3JSb3V0ZU1lc3NhZ2VzKHJvdXRlSWQpOwp9OwoKLyoqCiAqIEluZGljYXRlcyB0aGF0IHRoZSBwcmVzZW50YXRpb24gY29ubmVjdGlvbiB0aGF0IHdhcyBjb25uZWN0ZWQgdG8gfHJvdXRlSWR8CiAqIGlzIG5vIGxvbmdlciBjb25uZWN0ZWQgdG8gaXQuCiAqIEBwYXJhbSB7IXN0cmluZ30gcm91dGVJZAogKi8KTWVkaWFSb3V0ZVByb3ZpZGVyLnByb3RvdHlwZS5kZXRhY2hSb3V0ZSA9IGZ1bmN0aW9uKAogICAgcm91dGVJZCkgewogIHRoaXMuaGFuZGxlcnNfLmRldGFjaFJvdXRlKHJvdXRlSWQpOwp9OwoKLyoqCiAqIFJlcXVlc3RzIHRoYXQgdGhlIHByb3ZpZGVyIG1hbmFnZXIgc3RhcnQgc2VuZGluZyBpbmZvcm1hdGlvbiBhYm91dCBhY3RpdmUKICogbWVkaWEgcm91dGVzIHRvIHRoZSBNZWRpYSBSb3V0ZXIuCiAqIEBwYXJhbSB7IXN0cmluZ30gc291cmNlVXJuCiAqLwpNZWRpYVJvdXRlUHJvdmlkZXIucHJvdG90eXBlLnN0YXJ0T2JzZXJ2aW5nTWVkaWFSb3V0ZXMgPSBmdW5jdGlvbihzb3VyY2VVcm4pIHsKICB0aGlzLmhhbmRsZXJzXy5vbkJlZm9yZUludm9rZUhhbmRsZXIoKTsKICB0aGlzLmhhbmRsZXJzXy5zdGFydE9ic2VydmluZ01lZGlhUm91dGVzKHNvdXJjZVVybik7Cn07CgovKioKICogUmVxdWVzdHMgdGhhdCB0aGUgcHJvdmlkZXIgbWFuYWdlciBzdG9wIHNlbmRpbmcgaW5mb3JtYXRpb24gYWJvdXQgYWN0aXZlCiAqIG1lZGlhIHJvdXRlcyB0byB0aGUgTWVkaWEgUm91dGVyLgogKiBAcGFyYW0geyFzdHJpbmd9IHNvdXJjZVVybgogKi8KTWVkaWFSb3V0ZVByb3ZpZGVyLnByb3RvdHlwZS5zdG9wT2JzZXJ2aW5nTWVkaWFSb3V0ZXMgPSBmdW5jdGlvbihzb3VyY2VVcm4pIHsKICB0aGlzLmhhbmRsZXJzXy5vbkJlZm9yZUludm9rZUhhbmRsZXIoKTsKICB0aGlzLmhhbmRsZXJzXy5zdG9wT2JzZXJ2aW5nTWVkaWFSb3V0ZXMoc291cmNlVXJuKTsKfTsKCi8qKgogKiBFbmFibGVzIG1ETlMgZGV2aWNlIGRpc2NvdmVyeS4KICovCk1lZGlhUm91dGVQcm92aWRlci5wcm90b3R5cGUuZW5hYmxlTWRuc0Rpc2NvdmVyeSA9IGZ1bmN0aW9uKCkgewogIHRoaXMuaGFuZGxlcnNfLm9uQmVmb3JlSW52b2tlSGFuZGxlcigpOwogIHRoaXMuaGFuZGxlcnNfLmVuYWJsZU1kbnNEaXNjb3ZlcnkoKTsKfTsKCi8qKgogKiBSZXF1ZXN0cyB0aGF0IHRoZSBwcm92aWRlciBtYW5hZ2VyIHVwZGF0ZSBtZWRpYSBzaW5rcy4KICogQHBhcmFtIHshc3RyaW5nfSBzb3VyY2VVcm4KICovCk1lZGlhUm91dGVQcm92aWRlci5wcm90b3R5cGUudXBkYXRlTWVkaWFTaW5rcyA9IGZ1bmN0aW9uKHNvdXJjZVVybikgewogIHRoaXMuaGFuZGxlcnNfLm9uQmVmb3JlSW52b2tlSGFuZGxlcigpOwogIHRoaXMuaGFuZGxlcnNfLnVwZGF0ZU1lZGlhU2lua3Moc291cmNlVXJuKTsKfTsKCi8qKgogKiBSZXF1ZXN0cyB0aGF0IHRoZSBwcm92aWRlciBtYW5hZ2VyIHNlYXJjaCBpdHMgcHJvdmlkZXJzIGZvciBhIHNpbmsgbWF0Y2hpbmcKICogfHNlYXJjaENyaXRlcmlhfCB0aGF0IGlzIGNvbXBhdGlibGUgd2l0aCB8c291cmNlVXJufC4gSWYgYSBzaW5rIGlzIGZvdW5kCiAqIHRoYXQgY2FuIGJlIHVzZWQgaW1tZWRpYXRlbHkgZm9yIHJvdXRlIGNyZWF0aW9uLCBpdHMgSUQgaXMgcmV0dXJuZWQuCiAqIE90aGVyd2lzZSB0aGUgZW1wdHkgc3RyaW5nIGlzIHJldHVybmVkLgogKgogKiBAcGFyYW0ge3N0cmluZ30gc2lua0lkIFNpbmsgSUQgb2YgdGhlIHBzZXVkbyBzaW5rIGdlbmVyYXRpbmcgdGhlIHJlcXVlc3QuCiAqIEBwYXJhbSB7c3RyaW5nfSBzb3VyY2VVcm4gTWVkaWEgc291cmNlIHRvIGJlIHVzZWQgd2l0aCB0aGUgc2luay4KICogQHBhcmFtIHshU2lua1NlYXJjaENyaXRlcmlhfSBzZWFyY2hDcml0ZXJpYSBTZWFyY2ggY3JpdGVyaWEgZm9yIHRoZSByb3V0ZQogKiAgICAgcHJvdmlkZXJzLgogKiBAcmV0dXJuIHshUHJvbWlzZS48IXtzaW5rX2lkOiAhc3RyaW5nfT59IEEgUHJvbWlzZSByZXNvbHZpbmcgdG8gZWl0aGVyIHRoZQogKiAgICAgc2luayBJRCBvZiB0aGUgc2luayBmb3VuZCBieSB0aGUgc2VhcmNoIHRoYXQgY2FuIGJlIHVzZWQgZm9yIHJvdXRlCiAqICAgICBjcmVhdGlvbiwgb3IgdGhlIGVtcHR5IHN0cmluZyBpZiBubyByb3V0ZSBjYW4gYmUgaW1tZWRpYXRlbHkgY3JlYXRlZC4KICovCk1lZGlhUm91dGVQcm92aWRlci5wcm90b3R5cGUuc2VhcmNoU2lua3MgPSBmdW5jdGlvbigKICAgIHNpbmtJZCwgc291cmNlVXJuLCBzZWFyY2hDcml0ZXJpYSkgewogIHRoaXMuaGFuZGxlcnNfLm9uQmVmb3JlSW52b2tlSGFuZGxlcigpOwogcmV0dXJuIHRoaXMuaGFuZGxlcnNfLnNlYXJjaFNpbmtzKHNpbmtJZCwgc291cmNlVXJuLCBzZWFyY2hDcml0ZXJpYSkudGhlbigKICAgICAgc2lua0lkID0+IHsKICAgICAgICByZXR1cm4geyAnc2lua0lkJzogc2lua0lkIH07CiAgICAgIH0sCiAgICAgICgpID0+IHsKICAgICAgICByZXR1cm4geyAnc2lua0lkJzogJycgfTsKICAgICAgfSk7Cn07CgovKioKICogTm90aWZpZXMgdGhlIHByb3ZpZGVyIG1hbmFnZXIgdGhhdCBNZWRpYVJvdXRlciBoYXMgZGlzY292ZXJlZCBhIGxpc3Qgb2YKICogc2lua3MuCiAqIEBwYXJhbSB7c3RyaW5nfSBwcm92aWRlck5hbWUKICogQHBhcmFtIHshQXJyYXk8IW1lZGlhUm91dGVyLm1vam9tLk1lZGlhU2luaz59IHNpbmtzCiAqLwpNZWRpYVJvdXRlUHJvdmlkZXIucHJvdG90eXBlLnByb3ZpZGVTaW5rcyA9IGZ1bmN0aW9uKHByb3ZpZGVyTmFtZSwgc2lua3MpIHsKICB0aGlzLmhhbmRsZXJzXy5vbkJlZm9yZUludm9rZUhhbmRsZXIoKTsKICB0aGlzLmhhbmRsZXJzXy5wcm92aWRlU2lua3MocHJvdmlkZXJOYW1lLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzaW5rcy5tYXAoTWVkaWFTaW5rQWRhcHRlci5mcm9tTmV3VmVyc2lvbikpOwp9OwoKLyoqCiAqIENyZWF0ZXMgYSBjb250cm9sbGVyIGZvciB0aGUgZ2l2ZW4gcm91dGUgYW5kIGJpbmRzIHRoZSBnaXZlbgogKiBJbnRlcmZhY2VSZXF1ZXN0IHRvIGl0LCBhbmQgcmVnaXN0ZXJzIGFuIG9ic2VydmVyIGZvciBtZWRpYSBzdGF0dXMgdXBkYXRlcwogKiBmb3IgdGhlIHJvdXRlLgogKiBAcGFyYW0ge3N0cmluZ30gcm91dGVJZAogKiBAcGFyYW0geyFtb2pvLkludGVyZmFjZVJlcXVlc3R9IGNvbnRyb2xsZXJSZXF1ZXN0CiAqIEBwYXJhbSB7IW1lZGlhUm91dGVyLm1vam9tLk1lZGlhU3RhdHVzT2JzZXJ2ZXJQdHJ9IG9ic2VydmVyCiAqIEByZXR1cm4geyFQcm9taXNlPCF7c3VjY2VzczogYm9vbGVhbn0+fSBSZXNvbHZlcyB0byB0cnVlIGlmIGEgY29udHJvbGxlcgogKiAgICAgaXMgY3JlYXRlZC4gUmVzb2x2ZXMgdG8gZmFsc2UgaWYgYSBjb250cm9sbGVyIGNhbm5vdCBiZSBjcmVhdGVkLCBvciBpZgogKiAgICAgdGhlIGNvbnRyb2xsZXIgaXMgYWxyZWFkeSBib3VuZC4KICovCk1lZGlhUm91dGVQcm92aWRlci5wcm90b3R5cGUuY3JlYXRlTWVkaWFSb3V0ZUNvbnRyb2xsZXIgPSBmdW5jdGlvbigKICAgIHJvdXRlSWQsIGNvbnRyb2xsZXJSZXF1ZXN0LCBvYnNlcnZlcikgewogIHRoaXMuaGFuZGxlcnNfLm9uQmVmb3JlSW52b2tlSGFuZGxlcigpOwogIHJldHVybiB0aGlzLmhhbmRsZXJzXy5jcmVhdGVNZWRpYVJvdXRlQ29udHJvbGxlcigKICAgICAgcm91dGVJZCwgY29udHJvbGxlclJlcXVlc3QsCiAgICAgIG5ldyBNZWRpYVN0YXR1c09ic2VydmVyUHRyQWRhcHRlcihvYnNlcnZlci5wdHIucGFzc0ludGVyZmFjZSgpKSkudGhlbigKICAgICAgICAgICgpID0+ICh7c3VjY2VzczogdHJ1ZX0pLCBlID0+ICh7c3VjY2VzczogZmFsc2V9KSk7Cn07Cgp2YXIgcHRyID0gbmV3IG1lZGlhUm91dGVyLm1vam9tLk1lZGlhUm91dGVyUHRyOwpNb2pvLmJpbmRJbnRlcmZhY2UobWVkaWFSb3V0ZXIubW9qb20uTWVkaWFSb3V0ZXIubmFtZSwKICAgICAgICAgICAgICAgICAgIG1vam8ubWFrZVJlcXVlc3QocHRyKS5oYW5kbGUpOwpleHBvcnRzLiRzZXQoJ3JldHVyblZhbHVlJywgbmV3IE1lZGlhUm91dGVyKHB0cikpOwovLyBDb3B5cmlnaHQgMjAxNCBUaGUgQ2hyb21pdW0gQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KLy8gVXNlIG9mIHRoaXMgc291cmNlIGNvZGUgaXMgZ292ZXJuZWQgYnkgYSBCU0Qtc3R5bGUgbGljZW5zZSB0aGF0IGNhbiBiZQovLyBmb3VuZCBpbiB0aGUgTElDRU5TRSBmaWxlLgoKJ3VzZSBzdHJpY3QnOwoKKGZ1bmN0aW9uKCkgewogIHZhciBtb2pvbUlkID0gJ2Nocm9tZS9jb21tb24vbWVkaWFfcm91dGVyL21vam8vbWVkaWFfc3RhdHVzLm1vam9tJzsKICBpZiAobW9qby5pbnRlcm5hbC5pc01vam9tTG9hZGVkKG1vam9tSWQpKSB7CiAgICBjb25zb2xlLndhcm4oJ1RoZSBmb2xsb3dpbmcgbW9qb20gaXMgbG9hZGVkIG11bHRpcGxlIHRpbWVzOiAnICsgbW9qb21JZCk7CiAgICByZXR1cm47CiAgfQogIG1vam8uaW50ZXJuYWwubWFya01vam9tTG9hZGVkKG1vam9tSWQpOwogIHZhciBiaW5kaW5ncyA9IG1vam87CiAgdmFyIGFzc29jaWF0ZWRCaW5kaW5ncyA9IG1vam87CiAgdmFyIGNvZGVjID0gbW9qby5pbnRlcm5hbDsKICB2YXIgdmFsaWRhdG9yID0gbW9qby5pbnRlcm5hbDsKCiAgdmFyIGV4cG9ydHMgPSBtb2pvLmludGVybmFsLmV4cG9zZU5hbWVzcGFjZSgnbWVkaWFSb3V0ZXIubW9qb20nKTsKICB2YXIgdGltZSQgPQogICAgICBtb2pvLmludGVybmFsLmV4cG9zZU5hbWVzcGFjZSgnbW9qby5jb21tb24ubW9qb20nKTsKICBpZiAobW9qby5jb25maWcuYXV0b0xvYWRNb2pvbURlcHMpIHsKICAgIG1vam8uaW50ZXJuYWwubG9hZE1vam9tSWZOZWNlc3NhcnkoCiAgICAgICAgJ21vam8vY29tbW9uL3RpbWUubW9qb20nLCAnLi4vLi4vLi4vLi4vbW9qby9jb21tb24vdGltZS5tb2pvbS5qcycpOwogIH0KCgoKICBmdW5jdGlvbiBNZWRpYVN0YXR1cyh2YWx1ZXMpIHsKICAgIHRoaXMuaW5pdERlZmF1bHRzXygpOwogICAgdGhpcy5pbml0RmllbGRzXyh2YWx1ZXMpOwogIH0KCiAgTWVkaWFTdGF0dXMuUGxheVN0YXRlID0ge307CiAgTWVkaWFTdGF0dXMuUGxheVN0YXRlLlBMQVlJTkcgPSAwOwogIE1lZGlhU3RhdHVzLlBsYXlTdGF0ZS5QQVVTRUQgPSBNZWRpYVN0YXR1cy5QbGF5U3RhdGUuUExBWUlORyArIDE7CiAgTWVkaWFTdGF0dXMuUGxheVN0YXRlLkJVRkZFUklORyA9IE1lZGlhU3RhdHVzLlBsYXlTdGF0ZS5QQVVTRUQgKyAxOwoKICBNZWRpYVN0YXR1cy5QbGF5U3RhdGUuaXNLbm93bkVudW1WYWx1ZSA9IGZ1bmN0aW9uKHZhbHVlKSB7CiAgICBzd2l0Y2ggKHZhbHVlKSB7CiAgICBjYXNlIDA6CiAgICBjYXNlIDE6CiAgICBjYXNlIDI6CiAgICAgIHJldHVybiB0cnVlOwogICAgfQogICAgcmV0dXJuIGZhbHNlOwogIH07CgogIE1lZGlhU3RhdHVzLlBsYXlTdGF0ZS52YWxpZGF0ZSA9IGZ1bmN0aW9uKGVudW1WYWx1ZSkgewogICAgdmFyIGlzRXh0ZW5zaWJsZSA9IGZhbHNlOwogICAgaWYgKGlzRXh0ZW5zaWJsZSB8fCB0aGlzLmlzS25vd25FbnVtVmFsdWUoZW51bVZhbHVlKSkKICAgICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5VTktOT1dOX0VOVU1fVkFMVUU7CiAgfTsKCiAgTWVkaWFTdGF0dXMucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMudGl0bGUgPSBudWxsOwogICAgdGhpcy5kZXNjcmlwdGlvbiA9IG51bGw7CiAgICB0aGlzLmNhblBsYXlQYXVzZSA9IGZhbHNlOwogICAgdGhpcy5jYW5NdXRlID0gZmFsc2U7CiAgICB0aGlzLmNhblNldFZvbHVtZSA9IGZhbHNlOwogICAgdGhpcy5jYW5TZWVrID0gZmFsc2U7CiAgICB0aGlzLmlzTXV0ZWQgPSBmYWxzZTsKICAgIHRoaXMucGxheVN0YXRlID0gMDsKICAgIHRoaXMudm9sdW1lID0gMDsKICAgIHRoaXMuZHVyYXRpb24gPSBudWxsOwogICAgdGhpcy5jdXJyZW50VGltZSA9IG51bGw7CiAgICB0aGlzLmhhbmdvdXRzRXh0cmFEYXRhID0gbnVsbDsKICB9OwogIE1lZGlhU3RhdHVzLnByb3RvdHlwZS5pbml0RmllbGRzXyA9IGZ1bmN0aW9uKGZpZWxkcykgewogICAgZm9yKHZhciBmaWVsZCBpbiBmaWVsZHMpIHsKICAgICAgICBpZiAodGhpcy5oYXNPd25Qcm9wZXJ0eShmaWVsZCkpCiAgICAgICAgICB0aGlzW2ZpZWxkXSA9IGZpZWxkc1tmaWVsZF07CiAgICB9CiAgfTsKCiAgTWVkaWFTdGF0dXMudmFsaWRhdGUgPSBmdW5jdGlvbihtZXNzYWdlVmFsaWRhdG9yLCBvZmZzZXQpIHsKICAgIHZhciBlcnI7CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0SGVhZGVyKG9mZnNldCwgY29kZWMua1N0cnVjdEhlYWRlclNpemUpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgdmFyIGtWZXJzaW9uU2l6ZXMgPSBbCiAgICAgIHt2ZXJzaW9uOiAwLCBudW1CeXRlczogNjR9CiAgICBdOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFZlcnNpb24ob2Zmc2V0LCBrVmVyc2lvblNpemVzKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBNZWRpYVN0YXR1cy50aXRsZQogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cmluZ1BvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAwLCBmYWxzZSkKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBNZWRpYVN0YXR1cy5kZXNjcmlwdGlvbgogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cmluZ1BvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA4LCBmYWxzZSkKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCgoKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFTdGF0dXMucGxheVN0YXRlCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlRW51bShvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDIwLCBNZWRpYVN0YXR1cy5QbGF5U3RhdGUpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFTdGF0dXMuZHVyYXRpb24KICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RQb2ludGVyKG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMzIsIHRpbWUkLlRpbWVEZWx0YSwgZmFsc2UpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1lZGlhU3RhdHVzLmN1cnJlbnRUaW1lCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0UG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDQwLCB0aW1lJC5UaW1lRGVsdGEsIGZhbHNlKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBNZWRpYVN0YXR1cy5oYW5nb3V0c0V4dHJhRGF0YQogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFBvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA0OCwgSGFuZ291dHNNZWRpYVN0YXR1c0V4dHJhRGF0YSwgdHJ1ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIE1lZGlhU3RhdHVzLmVuY29kZWRTaXplID0gY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA1NjsKCiAgTWVkaWFTdGF0dXMuZGVjb2RlID0gZnVuY3Rpb24oZGVjb2RlcikgewogICAgdmFyIHBhY2tlZDsKICAgIHZhciB2YWwgPSBuZXcgTWVkaWFTdGF0dXMoKTsKICAgIHZhciBudW1iZXJPZkJ5dGVzID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YXIgdmVyc2lvbiA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFsLnRpdGxlID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nKTsKICAgIHZhbC5kZXNjcmlwdGlvbiA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLlN0cmluZyk7CiAgICBwYWNrZWQgPSBkZWNvZGVyLnJlYWRVaW50OCgpOwogICAgdmFsLmNhblBsYXlQYXVzZSA9IChwYWNrZWQgPj4gMCkgJiAxID8gdHJ1ZSA6IGZhbHNlOwogICAgdmFsLmNhbk11dGUgPSAocGFja2VkID4+IDEpICYgMSA/IHRydWUgOiBmYWxzZTsKICAgIHZhbC5jYW5TZXRWb2x1bWUgPSAocGFja2VkID4+IDIpICYgMSA/IHRydWUgOiBmYWxzZTsKICAgIHZhbC5jYW5TZWVrID0gKHBhY2tlZCA+PiAzKSAmIDEgPyB0cnVlIDogZmFsc2U7CiAgICB2YWwuaXNNdXRlZCA9IChwYWNrZWQgPj4gNCkgJiAxID8gdHJ1ZSA6IGZhbHNlOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgdmFsLnBsYXlTdGF0ZSA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLkludDMyKTsKICAgIHZhbC52b2x1bWUgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5GbG9hdCk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICB2YWwuZHVyYXRpb24gPSBkZWNvZGVyLmRlY29kZVN0cnVjdFBvaW50ZXIodGltZSQuVGltZURlbHRhKTsKICAgIHZhbC5jdXJyZW50VGltZSA9IGRlY29kZXIuZGVjb2RlU3RydWN0UG9pbnRlcih0aW1lJC5UaW1lRGVsdGEpOwogICAgdmFsLmhhbmdvdXRzRXh0cmFEYXRhID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3RQb2ludGVyKEhhbmdvdXRzTWVkaWFTdGF0dXNFeHRyYURhdGEpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBNZWRpYVN0YXR1cy5lbmNvZGUgPSBmdW5jdGlvbihlbmNvZGVyLCB2YWwpIHsKICAgIHZhciBwYWNrZWQ7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKE1lZGlhU3RhdHVzLmVuY29kZWRTaXplKTsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoMCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5TdHJpbmcsIHZhbC50aXRsZSk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5TdHJpbmcsIHZhbC5kZXNjcmlwdGlvbik7CiAgICBwYWNrZWQgPSAwOwogICAgcGFja2VkIHw9ICh2YWwuY2FuUGxheVBhdXNlICYgMSkgPDwgMAogICAgcGFja2VkIHw9ICh2YWwuY2FuTXV0ZSAmIDEpIDw8IDEKICAgIHBhY2tlZCB8PSAodmFsLmNhblNldFZvbHVtZSAmIDEpIDw8IDIKICAgIHBhY2tlZCB8PSAodmFsLmNhblNlZWsgJiAxKSA8PCAzCiAgICBwYWNrZWQgfD0gKHZhbC5pc011dGVkICYgMSkgPDwgNAogICAgZW5jb2Rlci53cml0ZVVpbnQ4KHBhY2tlZCk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5JbnQzMiwgdmFsLnBsYXlTdGF0ZSk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5GbG9hdCwgdmFsLnZvbHVtZSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdFBvaW50ZXIodGltZSQuVGltZURlbHRhLCB2YWwuZHVyYXRpb24pOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3RQb2ludGVyKHRpbWUkLlRpbWVEZWx0YSwgdmFsLmN1cnJlbnRUaW1lKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0UG9pbnRlcihIYW5nb3V0c01lZGlhU3RhdHVzRXh0cmFEYXRhLCB2YWwuaGFuZ291dHNFeHRyYURhdGEpOwogIH07CiAgZnVuY3Rpb24gSGFuZ291dHNNZWRpYVN0YXR1c0V4dHJhRGF0YSh2YWx1ZXMpIHsKICAgIHRoaXMuaW5pdERlZmF1bHRzXygpOwogICAgdGhpcy5pbml0RmllbGRzXyh2YWx1ZXMpOwogIH0KCgogIEhhbmdvdXRzTWVkaWFTdGF0dXNFeHRyYURhdGEucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMubG9jYWxQcmVzZW50ID0gZmFsc2U7CiAgfTsKICBIYW5nb3V0c01lZGlhU3RhdHVzRXh0cmFEYXRhLnByb3RvdHlwZS5pbml0RmllbGRzXyA9IGZ1bmN0aW9uKGZpZWxkcykgewogICAgZm9yKHZhciBmaWVsZCBpbiBmaWVsZHMpIHsKICAgICAgICBpZiAodGhpcy5oYXNPd25Qcm9wZXJ0eShmaWVsZCkpCiAgICAgICAgICB0aGlzW2ZpZWxkXSA9IGZpZWxkc1tmaWVsZF07CiAgICB9CiAgfTsKCiAgSGFuZ291dHNNZWRpYVN0YXR1c0V4dHJhRGF0YS52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiAxNn0KICAgIF07CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0VmVyc2lvbihvZmZzZXQsIGtWZXJzaW9uU2l6ZXMpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgfTsKCiAgSGFuZ291dHNNZWRpYVN0YXR1c0V4dHJhRGF0YS5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgODsKCiAgSGFuZ291dHNNZWRpYVN0YXR1c0V4dHJhRGF0YS5kZWNvZGUgPSBmdW5jdGlvbihkZWNvZGVyKSB7CiAgICB2YXIgcGFja2VkOwogICAgdmFyIHZhbCA9IG5ldyBIYW5nb3V0c01lZGlhU3RhdHVzRXh0cmFEYXRhKCk7CiAgICB2YXIgbnVtYmVyT2ZCeXRlcyA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFyIHZlcnNpb24gPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHBhY2tlZCA9IGRlY29kZXIucmVhZFVpbnQ4KCk7CiAgICB2YWwubG9jYWxQcmVzZW50ID0gKHBhY2tlZCA+PiAwKSAmIDEgPyB0cnVlIDogZmFsc2U7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICBkZWNvZGVyLnNraXAoMSk7CiAgICByZXR1cm4gdmFsOwogIH07CgogIEhhbmdvdXRzTWVkaWFTdGF0dXNFeHRyYURhdGEuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihIYW5nb3V0c01lZGlhU3RhdHVzRXh0cmFEYXRhLmVuY29kZWRTaXplKTsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoMCk7CiAgICBwYWNrZWQgPSAwOwogICAgcGFja2VkIHw9ICh2YWwubG9jYWxQcmVzZW50ICYgMSkgPDwgMAogICAgZW5jb2Rlci53cml0ZVVpbnQ4KHBhY2tlZCk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgfTsKICBmdW5jdGlvbiBNZWRpYVN0YXR1c09ic2VydmVyX09uTWVkaWFTdGF0dXNVcGRhdGVkX1BhcmFtcyh2YWx1ZXMpIHsKICAgIHRoaXMuaW5pdERlZmF1bHRzXygpOwogICAgdGhpcy5pbml0RmllbGRzXyh2YWx1ZXMpOwogIH0KCgogIE1lZGlhU3RhdHVzT2JzZXJ2ZXJfT25NZWRpYVN0YXR1c1VwZGF0ZWRfUGFyYW1zLnByb3RvdHlwZS5pbml0RGVmYXVsdHNfID0gZnVuY3Rpb24oKSB7CiAgICB0aGlzLnN0YXR1cyA9IG51bGw7CiAgfTsKICBNZWRpYVN0YXR1c09ic2VydmVyX09uTWVkaWFTdGF0dXNVcGRhdGVkX1BhcmFtcy5wcm90b3R5cGUuaW5pdEZpZWxkc18gPSBmdW5jdGlvbihmaWVsZHMpIHsKICAgIGZvcih2YXIgZmllbGQgaW4gZmllbGRzKSB7CiAgICAgICAgaWYgKHRoaXMuaGFzT3duUHJvcGVydHkoZmllbGQpKQogICAgICAgICAgdGhpc1tmaWVsZF0gPSBmaWVsZHNbZmllbGRdOwogICAgfQogIH07CgogIE1lZGlhU3RhdHVzT2JzZXJ2ZXJfT25NZWRpYVN0YXR1c1VwZGF0ZWRfUGFyYW1zLnZhbGlkYXRlID0gZnVuY3Rpb24obWVzc2FnZVZhbGlkYXRvciwgb2Zmc2V0KSB7CiAgICB2YXIgZXJyOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdEhlYWRlcihvZmZzZXQsIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHZhciBrVmVyc2lvblNpemVzID0gWwogICAgICB7dmVyc2lvbjogMCwgbnVtQnl0ZXM6IDE2fQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWVkaWFTdGF0dXNPYnNlcnZlcl9Pbk1lZGlhU3RhdHVzVXBkYXRlZF9QYXJhbXMuc3RhdHVzCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0UG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDAsIE1lZGlhU3RhdHVzLCBmYWxzZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIE1lZGlhU3RhdHVzT2JzZXJ2ZXJfT25NZWRpYVN0YXR1c1VwZGF0ZWRfUGFyYW1zLmVuY29kZWRTaXplID0gY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA4OwoKICBNZWRpYVN0YXR1c09ic2VydmVyX09uTWVkaWFTdGF0dXNVcGRhdGVkX1BhcmFtcy5kZWNvZGUgPSBmdW5jdGlvbihkZWNvZGVyKSB7CiAgICB2YXIgcGFja2VkOwogICAgdmFyIHZhbCA9IG5ldyBNZWRpYVN0YXR1c09ic2VydmVyX09uTWVkaWFTdGF0dXNVcGRhdGVkX1BhcmFtcygpOwogICAgdmFyIG51bWJlck9mQnl0ZXMgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhciB2ZXJzaW9uID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YWwuc3RhdHVzID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3RQb2ludGVyKE1lZGlhU3RhdHVzKTsKICAgIHJldHVybiB2YWw7CiAgfTsKCiAgTWVkaWFTdGF0dXNPYnNlcnZlcl9Pbk1lZGlhU3RhdHVzVXBkYXRlZF9QYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNZWRpYVN0YXR1c09ic2VydmVyX09uTWVkaWFTdGF0dXNVcGRhdGVkX1BhcmFtcy5lbmNvZGVkU2l6ZSk7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKDApOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3RQb2ludGVyKE1lZGlhU3RhdHVzLCB2YWwuc3RhdHVzKTsKICB9OwogIHZhciBrTWVkaWFTdGF0dXNPYnNlcnZlcl9Pbk1lZGlhU3RhdHVzVXBkYXRlZF9OYW1lID0gMTI1MzAyMDcyOTsKCiAgZnVuY3Rpb24gTWVkaWFTdGF0dXNPYnNlcnZlclB0cihoYW5kbGVPclB0ckluZm8pIHsKICAgIHRoaXMucHRyID0gbmV3IGJpbmRpbmdzLkludGVyZmFjZVB0ckNvbnRyb2xsZXIoTWVkaWFTdGF0dXNPYnNlcnZlciwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaGFuZGxlT3JQdHJJbmZvKTsKICB9CgogIGZ1bmN0aW9uIE1lZGlhU3RhdHVzT2JzZXJ2ZXJBc3NvY2lhdGVkUHRyKGFzc29jaWF0ZWRJbnRlcmZhY2VQdHJJbmZvKSB7CiAgICB0aGlzLnB0ciA9IG5ldyBhc3NvY2lhdGVkQmluZGluZ3MuQXNzb2NpYXRlZEludGVyZmFjZVB0ckNvbnRyb2xsZXIoCiAgICAgICAgTWVkaWFTdGF0dXNPYnNlcnZlciwgYXNzb2NpYXRlZEludGVyZmFjZVB0ckluZm8pOwogIH0KCiAgTWVkaWFTdGF0dXNPYnNlcnZlckFzc29jaWF0ZWRQdHIucHJvdG90eXBlID0KICAgICAgT2JqZWN0LmNyZWF0ZShNZWRpYVN0YXR1c09ic2VydmVyUHRyLnByb3RvdHlwZSk7CiAgTWVkaWFTdGF0dXNPYnNlcnZlckFzc29jaWF0ZWRQdHIucHJvdG90eXBlLmNvbnN0cnVjdG9yID0KICAgICAgTWVkaWFTdGF0dXNPYnNlcnZlckFzc29jaWF0ZWRQdHI7CgogIGZ1bmN0aW9uIE1lZGlhU3RhdHVzT2JzZXJ2ZXJQcm94eShyZWNlaXZlcikgewogICAgdGhpcy5yZWNlaXZlcl8gPSByZWNlaXZlcjsKICB9CiAgTWVkaWFTdGF0dXNPYnNlcnZlclB0ci5wcm90b3R5cGUub25NZWRpYVN0YXR1c1VwZGF0ZWQgPSBmdW5jdGlvbigpIHsKICAgIHJldHVybiBNZWRpYVN0YXR1c09ic2VydmVyUHJveHkucHJvdG90eXBlLm9uTWVkaWFTdGF0dXNVcGRhdGVkCiAgICAgICAgLmFwcGx5KHRoaXMucHRyLmdldFByb3h5KCksIGFyZ3VtZW50cyk7CiAgfTsKCiAgTWVkaWFTdGF0dXNPYnNlcnZlclByb3h5LnByb3RvdHlwZS5vbk1lZGlhU3RhdHVzVXBkYXRlZCA9IGZ1bmN0aW9uKHN0YXR1cykgewogICAgdmFyIHBhcmFtcyA9IG5ldyBNZWRpYVN0YXR1c09ic2VydmVyX09uTWVkaWFTdGF0dXNVcGRhdGVkX1BhcmFtcygpOwogICAgcGFyYW1zLnN0YXR1cyA9IHN0YXR1czsKICAgIHZhciBidWlsZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VWMEJ1aWxkZXIoCiAgICAgICAga01lZGlhU3RhdHVzT2JzZXJ2ZXJfT25NZWRpYVN0YXR1c1VwZGF0ZWRfTmFtZSwKICAgICAgICBjb2RlYy5hbGlnbihNZWRpYVN0YXR1c09ic2VydmVyX09uTWVkaWFTdGF0dXNVcGRhdGVkX1BhcmFtcy5lbmNvZGVkU2l6ZSkpOwogICAgYnVpbGRlci5lbmNvZGVTdHJ1Y3QoTWVkaWFTdGF0dXNPYnNlcnZlcl9Pbk1lZGlhU3RhdHVzVXBkYXRlZF9QYXJhbXMsIHBhcmFtcyk7CiAgICB2YXIgbWVzc2FnZSA9IGJ1aWxkZXIuZmluaXNoKCk7CiAgICB0aGlzLnJlY2VpdmVyXy5hY2NlcHQobWVzc2FnZSk7CiAgfTsKCiAgZnVuY3Rpb24gTWVkaWFTdGF0dXNPYnNlcnZlclN0dWIoZGVsZWdhdGUpIHsKICAgIHRoaXMuZGVsZWdhdGVfID0gZGVsZWdhdGU7CiAgfQogIE1lZGlhU3RhdHVzT2JzZXJ2ZXJTdHViLnByb3RvdHlwZS5vbk1lZGlhU3RhdHVzVXBkYXRlZCA9IGZ1bmN0aW9uKHN0YXR1cykgewogICAgcmV0dXJuIHRoaXMuZGVsZWdhdGVfICYmIHRoaXMuZGVsZWdhdGVfLm9uTWVkaWFTdGF0dXNVcGRhdGVkICYmIHRoaXMuZGVsZWdhdGVfLm9uTWVkaWFTdGF0dXNVcGRhdGVkKHN0YXR1cyk7CiAgfQoKICBNZWRpYVN0YXR1c09ic2VydmVyU3R1Yi5wcm90b3R5cGUuYWNjZXB0ID0gZnVuY3Rpb24obWVzc2FnZSkgewogICAgdmFyIHJlYWRlciA9IG5ldyBjb2RlYy5NZXNzYWdlUmVhZGVyKG1lc3NhZ2UpOwogICAgc3dpdGNoIChyZWFkZXIubWVzc2FnZU5hbWUpIHsKICAgIGNhc2Uga01lZGlhU3RhdHVzT2JzZXJ2ZXJfT25NZWRpYVN0YXR1c1VwZGF0ZWRfTmFtZToKICAgICAgdmFyIHBhcmFtcyA9IHJlYWRlci5kZWNvZGVTdHJ1Y3QoTWVkaWFTdGF0dXNPYnNlcnZlcl9Pbk1lZGlhU3RhdHVzVXBkYXRlZF9QYXJhbXMpOwogICAgICB0aGlzLm9uTWVkaWFTdGF0dXNVcGRhdGVkKHBhcmFtcy5zdGF0dXMpOwogICAgICByZXR1cm4gdHJ1ZTsKICAgIGRlZmF1bHQ6CiAgICAgIHJldHVybiBmYWxzZTsKICAgIH0KICB9OwoKICBNZWRpYVN0YXR1c09ic2VydmVyU3R1Yi5wcm90b3R5cGUuYWNjZXB0V2l0aFJlc3BvbmRlciA9CiAgICAgIGZ1bmN0aW9uKG1lc3NhZ2UsIHJlc3BvbmRlcikgewogICAgdmFyIHJlYWRlciA9IG5ldyBjb2RlYy5NZXNzYWdlUmVhZGVyKG1lc3NhZ2UpOwogICAgc3dpdGNoIChyZWFkZXIubWVzc2FnZU5hbWUpIHsKICAgIGRlZmF1bHQ6CiAgICAgIHJldHVybiBmYWxzZTsKICAgIH0KICB9OwoKICBmdW5jdGlvbiB2YWxpZGF0ZU1lZGlhU3RhdHVzT2JzZXJ2ZXJSZXF1ZXN0KG1lc3NhZ2VWYWxpZGF0b3IpIHsKICAgIHZhciBtZXNzYWdlID0gbWVzc2FnZVZhbGlkYXRvci5tZXNzYWdlOwogICAgdmFyIHBhcmFtc0NsYXNzID0gbnVsbDsKICAgIHN3aXRjaCAobWVzc2FnZS5nZXROYW1lKCkpIHsKICAgICAgY2FzZSBrTWVkaWFTdGF0dXNPYnNlcnZlcl9Pbk1lZGlhU3RhdHVzVXBkYXRlZF9OYW1lOgogICAgICAgIGlmICghbWVzc2FnZS5leHBlY3RzUmVzcG9uc2UoKSAmJiAhbWVzc2FnZS5pc1Jlc3BvbnNlKCkpCiAgICAgICAgICBwYXJhbXNDbGFzcyA9IE1lZGlhU3RhdHVzT2JzZXJ2ZXJfT25NZWRpYVN0YXR1c1VwZGF0ZWRfUGFyYW1zOwogICAgICBicmVhazsKICAgIH0KICAgIGlmIChwYXJhbXNDbGFzcyA9PT0gbnVsbCkKICAgICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKICAgIHJldHVybiBwYXJhbXNDbGFzcy52YWxpZGF0ZShtZXNzYWdlVmFsaWRhdG9yLCBtZXNzYWdlVmFsaWRhdG9yLm1lc3NhZ2UuZ2V0SGVhZGVyTnVtQnl0ZXMoKSk7CiAgfQoKICBmdW5jdGlvbiB2YWxpZGF0ZU1lZGlhU3RhdHVzT2JzZXJ2ZXJSZXNwb25zZShtZXNzYWdlVmFsaWRhdG9yKSB7CiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH0KCiAgdmFyIE1lZGlhU3RhdHVzT2JzZXJ2ZXIgPSB7CiAgICBuYW1lOiAnbWVkaWFfcm91dGVyOjptb2pvbTo6TWVkaWFTdGF0dXNPYnNlcnZlcicsCiAgICBrVmVyc2lvbjogMCwKICAgIHB0ckNsYXNzOiBNZWRpYVN0YXR1c09ic2VydmVyUHRyLAogICAgcHJveHlDbGFzczogTWVkaWFTdGF0dXNPYnNlcnZlclByb3h5LAogICAgc3R1YkNsYXNzOiBNZWRpYVN0YXR1c09ic2VydmVyU3R1YiwKICAgIHZhbGlkYXRlUmVxdWVzdDogdmFsaWRhdGVNZWRpYVN0YXR1c09ic2VydmVyUmVxdWVzdCwKICAgIHZhbGlkYXRlUmVzcG9uc2U6IG51bGwsCiAgfTsKICBNZWRpYVN0YXR1c09ic2VydmVyU3R1Yi5wcm90b3R5cGUudmFsaWRhdG9yID0gdmFsaWRhdGVNZWRpYVN0YXR1c09ic2VydmVyUmVxdWVzdDsKICBNZWRpYVN0YXR1c09ic2VydmVyUHJveHkucHJvdG90eXBlLnZhbGlkYXRvciA9IG51bGw7CiAgZXhwb3J0cy5NZWRpYVN0YXR1cyA9IE1lZGlhU3RhdHVzOwogIGV4cG9ydHMuSGFuZ291dHNNZWRpYVN0YXR1c0V4dHJhRGF0YSA9IEhhbmdvdXRzTWVkaWFTdGF0dXNFeHRyYURhdGE7CiAgZXhwb3J0cy5NZWRpYVN0YXR1c09ic2VydmVyID0gTWVkaWFTdGF0dXNPYnNlcnZlcjsKICBleHBvcnRzLk1lZGlhU3RhdHVzT2JzZXJ2ZXJQdHIgPSBNZWRpYVN0YXR1c09ic2VydmVyUHRyOwogIGV4cG9ydHMuTWVkaWFTdGF0dXNPYnNlcnZlckFzc29jaWF0ZWRQdHIgPSBNZWRpYVN0YXR1c09ic2VydmVyQXNzb2NpYXRlZFB0cjsKfSkoKTsvLyBDb3B5cmlnaHQgMjAxNCBUaGUgQ2hyb21pdW0gQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KLy8gVXNlIG9mIHRoaXMgc291cmNlIGNvZGUgaXMgZ292ZXJuZWQgYnkgYSBCU0Qtc3R5bGUgbGljZW5zZSB0aGF0IGNhbiBiZQovLyBmb3VuZCBpbiB0aGUgTElDRU5TRSBmaWxlLgoKJ3VzZSBzdHJpY3QnOwoKKGZ1bmN0aW9uKCkgewogIHZhciBtb2pvbUlkID0gJ21vam8vY29tbW9uL3RpbWUubW9qb20nOwogIGlmIChtb2pvLmludGVybmFsLmlzTW9qb21Mb2FkZWQobW9qb21JZCkpIHsKICAgIGNvbnNvbGUud2FybignVGhlIGZvbGxvd2luZyBtb2pvbSBpcyBsb2FkZWQgbXVsdGlwbGUgdGltZXM6ICcgKyBtb2pvbUlkKTsKICAgIHJldHVybjsKICB9CiAgbW9qby5pbnRlcm5hbC5tYXJrTW9qb21Mb2FkZWQobW9qb21JZCk7CiAgdmFyIGJpbmRpbmdzID0gbW9qbzsKICB2YXIgYXNzb2NpYXRlZEJpbmRpbmdzID0gbW9qbzsKICB2YXIgY29kZWMgPSBtb2pvLmludGVybmFsOwogIHZhciB2YWxpZGF0b3IgPSBtb2pvLmludGVybmFsOwoKICB2YXIgZXhwb3J0cyA9IG1vam8uaW50ZXJuYWwuZXhwb3NlTmFtZXNwYWNlKCdtb2pvLmNvbW1vbi5tb2pvbScpOwoKCgogIGZ1bmN0aW9uIFRpbWUodmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBUaW1lLnByb3RvdHlwZS5pbml0RGVmYXVsdHNfID0gZnVuY3Rpb24oKSB7CiAgICB0aGlzLmludGVybmFsVmFsdWUgPSAwOwogIH07CiAgVGltZS5wcm90b3R5cGUuaW5pdEZpZWxkc18gPSBmdW5jdGlvbihmaWVsZHMpIHsKICAgIGZvcih2YXIgZmllbGQgaW4gZmllbGRzKSB7CiAgICAgICAgaWYgKHRoaXMuaGFzT3duUHJvcGVydHkoZmllbGQpKQogICAgICAgICAgdGhpc1tmaWVsZF0gPSBmaWVsZHNbZmllbGRdOwogICAgfQogIH07CgogIFRpbWUudmFsaWRhdGUgPSBmdW5jdGlvbihtZXNzYWdlVmFsaWRhdG9yLCBvZmZzZXQpIHsKICAgIHZhciBlcnI7CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0SGVhZGVyKG9mZnNldCwgY29kZWMua1N0cnVjdEhlYWRlclNpemUpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgdmFyIGtWZXJzaW9uU2l6ZXMgPSBbCiAgICAgIHt2ZXJzaW9uOiAwLCBudW1CeXRlczogMTZ9CiAgICBdOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFZlcnNpb24ob2Zmc2V0LCBrVmVyc2lvblNpemVzKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIFRpbWUuZW5jb2RlZFNpemUgPSBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDg7CgogIFRpbWUuZGVjb2RlID0gZnVuY3Rpb24oZGVjb2RlcikgewogICAgdmFyIHBhY2tlZDsKICAgIHZhciB2YWwgPSBuZXcgVGltZSgpOwogICAgdmFyIG51bWJlck9mQnl0ZXMgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhciB2ZXJzaW9uID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YWwuaW50ZXJuYWxWYWx1ZSA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLkludDY0KTsKICAgIHJldHVybiB2YWw7CiAgfTsKCiAgVGltZS5lbmNvZGUgPSBmdW5jdGlvbihlbmNvZGVyLCB2YWwpIHsKICAgIHZhciBwYWNrZWQ7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKFRpbWUuZW5jb2RlZFNpemUpOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMigwKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLkludDY0LCB2YWwuaW50ZXJuYWxWYWx1ZSk7CiAgfTsKICBmdW5jdGlvbiBUaW1lRGVsdGEodmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBUaW1lRGVsdGEucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMubWljcm9zZWNvbmRzID0gMDsKICB9OwogIFRpbWVEZWx0YS5wcm90b3R5cGUuaW5pdEZpZWxkc18gPSBmdW5jdGlvbihmaWVsZHMpIHsKICAgIGZvcih2YXIgZmllbGQgaW4gZmllbGRzKSB7CiAgICAgICAgaWYgKHRoaXMuaGFzT3duUHJvcGVydHkoZmllbGQpKQogICAgICAgICAgdGhpc1tmaWVsZF0gPSBmaWVsZHNbZmllbGRdOwogICAgfQogIH07CgogIFRpbWVEZWx0YS52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiAxNn0KICAgIF07CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0VmVyc2lvbihvZmZzZXQsIGtWZXJzaW9uU2l6ZXMpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgfTsKCiAgVGltZURlbHRhLmVuY29kZWRTaXplID0gY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA4OwoKICBUaW1lRGVsdGEuZGVjb2RlID0gZnVuY3Rpb24oZGVjb2RlcikgewogICAgdmFyIHBhY2tlZDsKICAgIHZhciB2YWwgPSBuZXcgVGltZURlbHRhKCk7CiAgICB2YXIgbnVtYmVyT2ZCeXRlcyA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFyIHZlcnNpb24gPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhbC5taWNyb3NlY29uZHMgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5JbnQ2NCk7CiAgICByZXR1cm4gdmFsOwogIH07CgogIFRpbWVEZWx0YS5lbmNvZGUgPSBmdW5jdGlvbihlbmNvZGVyLCB2YWwpIHsKICAgIHZhciBwYWNrZWQ7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKFRpbWVEZWx0YS5lbmNvZGVkU2l6ZSk7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKDApOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuSW50NjQsIHZhbC5taWNyb3NlY29uZHMpOwogIH07CiAgZnVuY3Rpb24gVGltZVRpY2tzKHZhbHVlcykgewogICAgdGhpcy5pbml0RGVmYXVsdHNfKCk7CiAgICB0aGlzLmluaXRGaWVsZHNfKHZhbHVlcyk7CiAgfQoKCiAgVGltZVRpY2tzLnByb3RvdHlwZS5pbml0RGVmYXVsdHNfID0gZnVuY3Rpb24oKSB7CiAgICB0aGlzLmludGVybmFsVmFsdWUgPSAwOwogIH07CiAgVGltZVRpY2tzLnByb3RvdHlwZS5pbml0RmllbGRzXyA9IGZ1bmN0aW9uKGZpZWxkcykgewogICAgZm9yKHZhciBmaWVsZCBpbiBmaWVsZHMpIHsKICAgICAgICBpZiAodGhpcy5oYXNPd25Qcm9wZXJ0eShmaWVsZCkpCiAgICAgICAgICB0aGlzW2ZpZWxkXSA9IGZpZWxkc1tmaWVsZF07CiAgICB9CiAgfTsKCiAgVGltZVRpY2tzLnZhbGlkYXRlID0gZnVuY3Rpb24obWVzc2FnZVZhbGlkYXRvciwgb2Zmc2V0KSB7CiAgICB2YXIgZXJyOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdEhlYWRlcihvZmZzZXQsIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHZhciBrVmVyc2lvblNpemVzID0gWwogICAgICB7dmVyc2lvbjogMCwgbnVtQnl0ZXM6IDE2fQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKICB9OwoKICBUaW1lVGlja3MuZW5jb2RlZFNpemUgPSBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDg7CgogIFRpbWVUaWNrcy5kZWNvZGUgPSBmdW5jdGlvbihkZWNvZGVyKSB7CiAgICB2YXIgcGFja2VkOwogICAgdmFyIHZhbCA9IG5ldyBUaW1lVGlja3MoKTsKICAgIHZhciBudW1iZXJPZkJ5dGVzID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YXIgdmVyc2lvbiA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFsLmludGVybmFsVmFsdWUgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5JbnQ2NCk7CiAgICByZXR1cm4gdmFsOwogIH07CgogIFRpbWVUaWNrcy5lbmNvZGUgPSBmdW5jdGlvbihlbmNvZGVyLCB2YWwpIHsKICAgIHZhciBwYWNrZWQ7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKFRpbWVUaWNrcy5lbmNvZGVkU2l6ZSk7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKDApOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuSW50NjQsIHZhbC5pbnRlcm5hbFZhbHVlKTsKICB9OwogIGV4cG9ydHMuVGltZSA9IFRpbWU7CiAgZXhwb3J0cy5UaW1lRGVsdGEgPSBUaW1lRGVsdGE7CiAgZXhwb3J0cy5UaW1lVGlja3MgPSBUaW1lVGlja3M7Cn0pKCk7Ly8gQ29weXJpZ2h0IDIwMTQgVGhlIENocm9taXVtIEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCi8vIFVzZSBvZiB0aGlzIHNvdXJjZSBjb2RlIGlzIGdvdmVybmVkIGJ5IGEgQlNELXN0eWxlIGxpY2Vuc2UgdGhhdCBjYW4gYmUKLy8gZm91bmQgaW4gdGhlIExJQ0VOU0UgZmlsZS4KCid1c2Ugc3RyaWN0JzsKCihmdW5jdGlvbigpIHsKICB2YXIgbW9qb21JZCA9ICduZXQvaW50ZXJmYWNlcy9pcF9hZGRyZXNzLm1vam9tJzsKICBpZiAobW9qby5pbnRlcm5hbC5pc01vam9tTG9hZGVkKG1vam9tSWQpKSB7CiAgICBjb25zb2xlLndhcm4oJ1RoZSBmb2xsb3dpbmcgbW9qb20gaXMgbG9hZGVkIG11bHRpcGxlIHRpbWVzOiAnICsgbW9qb21JZCk7CiAgICByZXR1cm47CiAgfQogIG1vam8uaW50ZXJuYWwubWFya01vam9tTG9hZGVkKG1vam9tSWQpOwogIHZhciBiaW5kaW5ncyA9IG1vam87CiAgdmFyIGFzc29jaWF0ZWRCaW5kaW5ncyA9IG1vam87CiAgdmFyIGNvZGVjID0gbW9qby5pbnRlcm5hbDsKICB2YXIgdmFsaWRhdG9yID0gbW9qby5pbnRlcm5hbDsKCiAgdmFyIGV4cG9ydHMgPSBtb2pvLmludGVybmFsLmV4cG9zZU5hbWVzcGFjZSgnbmV0LmludGVyZmFjZXMnKTsKCgoKICBmdW5jdGlvbiBJUEFkZHJlc3ModmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBJUEFkZHJlc3MucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMuYWRkcmVzc0J5dGVzID0gbnVsbDsKICB9OwogIElQQWRkcmVzcy5wcm90b3R5cGUuaW5pdEZpZWxkc18gPSBmdW5jdGlvbihmaWVsZHMpIHsKICAgIGZvcih2YXIgZmllbGQgaW4gZmllbGRzKSB7CiAgICAgICAgaWYgKHRoaXMuaGFzT3duUHJvcGVydHkoZmllbGQpKQogICAgICAgICAgdGhpc1tmaWVsZF0gPSBmaWVsZHNbZmllbGRdOwogICAgfQogIH07CgogIElQQWRkcmVzcy52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiAxNn0KICAgIF07CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0VmVyc2lvbihvZmZzZXQsIGtWZXJzaW9uU2l6ZXMpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIElQQWRkcmVzcy5hZGRyZXNzQnl0ZXMKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVBcnJheVBvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAwLCAxLCBjb2RlYy5VaW50OCwgZmFsc2UsIFswXSwgMCk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIElQQWRkcmVzcy5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgODsKCiAgSVBBZGRyZXNzLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IElQQWRkcmVzcygpOwogICAgdmFyIG51bWJlck9mQnl0ZXMgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhciB2ZXJzaW9uID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YWwuYWRkcmVzc0J5dGVzID0gZGVjb2Rlci5kZWNvZGVBcnJheVBvaW50ZXIoY29kZWMuVWludDgpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBJUEFkZHJlc3MuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihJUEFkZHJlc3MuZW5jb2RlZFNpemUpOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMigwKTsKICAgIGVuY29kZXIuZW5jb2RlQXJyYXlQb2ludGVyKGNvZGVjLlVpbnQ4LCB2YWwuYWRkcmVzc0J5dGVzKTsKICB9OwogIGV4cG9ydHMuSVBBZGRyZXNzID0gSVBBZGRyZXNzOwp9KSgpOy8vIENvcHlyaWdodCAyMDE0IFRoZSBDaHJvbWl1bSBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgovLyBVc2Ugb2YgdGhpcyBzb3VyY2UgY29kZSBpcyBnb3Zlcm5lZCBieSBhIEJTRC1zdHlsZSBsaWNlbnNlIHRoYXQgY2FuIGJlCi8vIGZvdW5kIGluIHRoZSBMSUNFTlNFIGZpbGUuCgondXNlIHN0cmljdCc7CgooZnVuY3Rpb24oKSB7CiAgdmFyIG1vam9tSWQgPSAnbmV0L2ludGVyZmFjZXMvaXBfZW5kcG9pbnQubW9qb20nOwogIGlmIChtb2pvLmludGVybmFsLmlzTW9qb21Mb2FkZWQobW9qb21JZCkpIHsKICAgIGNvbnNvbGUud2FybignVGhlIGZvbGxvd2luZyBtb2pvbSBpcyBsb2FkZWQgbXVsdGlwbGUgdGltZXM6ICcgKyBtb2pvbUlkKTsKICAgIHJldHVybjsKICB9CiAgbW9qby5pbnRlcm5hbC5tYXJrTW9qb21Mb2FkZWQobW9qb21JZCk7CiAgdmFyIGJpbmRpbmdzID0gbW9qbzsKICB2YXIgYXNzb2NpYXRlZEJpbmRpbmdzID0gbW9qbzsKICB2YXIgY29kZWMgPSBtb2pvLmludGVybmFsOwogIHZhciB2YWxpZGF0b3IgPSBtb2pvLmludGVybmFsOwoKICB2YXIgZXhwb3J0cyA9IG1vam8uaW50ZXJuYWwuZXhwb3NlTmFtZXNwYWNlKCduZXQuaW50ZXJmYWNlcycpOwogIHZhciBpcF9hZGRyZXNzJCA9CiAgICAgIG1vam8uaW50ZXJuYWwuZXhwb3NlTmFtZXNwYWNlKCduZXQuaW50ZXJmYWNlcycpOwogIGlmIChtb2pvLmNvbmZpZy5hdXRvTG9hZE1vam9tRGVwcykgewogICAgbW9qby5pbnRlcm5hbC5sb2FkTW9qb21JZk5lY2Vzc2FyeSgKICAgICAgICAnbmV0L2ludGVyZmFjZXMvaXBfYWRkcmVzcy5tb2pvbScsICdpcF9hZGRyZXNzLm1vam9tLmpzJyk7CiAgfQoKCgogIGZ1bmN0aW9uIElQRW5kUG9pbnQodmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBJUEVuZFBvaW50LnByb3RvdHlwZS5pbml0RGVmYXVsdHNfID0gZnVuY3Rpb24oKSB7CiAgICB0aGlzLmFkZHJlc3MgPSBudWxsOwogICAgdGhpcy5wb3J0ID0gMDsKICB9OwogIElQRW5kUG9pbnQucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBJUEVuZFBvaW50LnZhbGlkYXRlID0gZnVuY3Rpb24obWVzc2FnZVZhbGlkYXRvciwgb2Zmc2V0KSB7CiAgICB2YXIgZXJyOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdEhlYWRlcihvZmZzZXQsIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHZhciBrVmVyc2lvblNpemVzID0gWwogICAgICB7dmVyc2lvbjogMCwgbnVtQnl0ZXM6IDI0fQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgSVBFbmRQb2ludC5hZGRyZXNzCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0UG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDAsIGlwX2FkZHJlc3MkLklQQWRkcmVzcywgZmFsc2UpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgfTsKCiAgSVBFbmRQb2ludC5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMTY7CgogIElQRW5kUG9pbnQuZGVjb2RlID0gZnVuY3Rpb24oZGVjb2RlcikgewogICAgdmFyIHBhY2tlZDsKICAgIHZhciB2YWwgPSBuZXcgSVBFbmRQb2ludCgpOwogICAgdmFyIG51bWJlck9mQnl0ZXMgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhciB2ZXJzaW9uID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YWwuYWRkcmVzcyA9IGRlY29kZXIuZGVjb2RlU3RydWN0UG9pbnRlcihpcF9hZGRyZXNzJC5JUEFkZHJlc3MpOwogICAgdmFsLnBvcnQgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5VaW50MTYpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBJUEVuZFBvaW50LmVuY29kZSA9IGZ1bmN0aW9uKGVuY29kZXIsIHZhbCkgewogICAgdmFyIHBhY2tlZDsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoSVBFbmRQb2ludC5lbmNvZGVkU2l6ZSk7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKDApOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3RQb2ludGVyKGlwX2FkZHJlc3MkLklQQWRkcmVzcywgdmFsLmFkZHJlc3MpOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuVWludDE2LCB2YWwucG9ydCk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgfTsKICBleHBvcnRzLklQRW5kUG9pbnQgPSBJUEVuZFBvaW50Owp9KSgpOy8vIENvcHlyaWdodCAyMDE0IFRoZSBDaHJvbWl1bSBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgovLyBVc2Ugb2YgdGhpcyBzb3VyY2UgY29kZSBpcyBnb3Zlcm5lZCBieSBhIEJTRC1zdHlsZSBsaWNlbnNlIHRoYXQgY2FuIGJlCi8vIGZvdW5kIGluIHRoZSBMSUNFTlNFIGZpbGUuCgondXNlIHN0cmljdCc7CgooZnVuY3Rpb24oKSB7CiAgdmFyIG1vam9tSWQgPSAndXJsL21vam8vb3JpZ2luLm1vam9tJzsKICBpZiAobW9qby5pbnRlcm5hbC5pc01vam9tTG9hZGVkKG1vam9tSWQpKSB7CiAgICBjb25zb2xlLndhcm4oJ1RoZSBmb2xsb3dpbmcgbW9qb20gaXMgbG9hZGVkIG11bHRpcGxlIHRpbWVzOiAnICsgbW9qb21JZCk7CiAgICByZXR1cm47CiAgfQogIG1vam8uaW50ZXJuYWwubWFya01vam9tTG9hZGVkKG1vam9tSWQpOwogIHZhciBiaW5kaW5ncyA9IG1vam87CiAgdmFyIGFzc29jaWF0ZWRCaW5kaW5ncyA9IG1vam87CiAgdmFyIGNvZGVjID0gbW9qby5pbnRlcm5hbDsKICB2YXIgdmFsaWRhdG9yID0gbW9qby5pbnRlcm5hbDsKCiAgdmFyIGV4cG9ydHMgPSBtb2pvLmludGVybmFsLmV4cG9zZU5hbWVzcGFjZSgndXJsLm1vam9tJyk7CgoKCiAgZnVuY3Rpb24gT3JpZ2luKHZhbHVlcykgewogICAgdGhpcy5pbml0RGVmYXVsdHNfKCk7CiAgICB0aGlzLmluaXRGaWVsZHNfKHZhbHVlcyk7CiAgfQoKCiAgT3JpZ2luLnByb3RvdHlwZS5pbml0RGVmYXVsdHNfID0gZnVuY3Rpb24oKSB7CiAgICB0aGlzLnNjaGVtZSA9IG51bGw7CiAgICB0aGlzLmhvc3QgPSBudWxsOwogICAgdGhpcy5wb3J0ID0gMDsKICAgIHRoaXMudW5pcXVlID0gZmFsc2U7CiAgICB0aGlzLnN1Ym9yaWdpbiA9IG51bGw7CiAgfTsKICBPcmlnaW4ucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBPcmlnaW4udmFsaWRhdGUgPSBmdW5jdGlvbihtZXNzYWdlVmFsaWRhdG9yLCBvZmZzZXQpIHsKICAgIHZhciBlcnI7CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0SGVhZGVyKG9mZnNldCwgY29kZWMua1N0cnVjdEhlYWRlclNpemUpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgdmFyIGtWZXJzaW9uU2l6ZXMgPSBbCiAgICAgIHt2ZXJzaW9uOiAwLCBudW1CeXRlczogNDB9CiAgICBdOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFZlcnNpb24ob2Zmc2V0LCBrVmVyc2lvblNpemVzKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBPcmlnaW4uc2NoZW1lCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDAsIGZhbHNlKQogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE9yaWdpbi5ob3N0CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDgsIGZhbHNlKQogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKCiAgICAvLyB2YWxpZGF0ZSBPcmlnaW4uc3Vib3JpZ2luCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RyaW5nUG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDI0LCBmYWxzZSkKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIE9yaWdpbi5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMzI7CgogIE9yaWdpbi5kZWNvZGUgPSBmdW5jdGlvbihkZWNvZGVyKSB7CiAgICB2YXIgcGFja2VkOwogICAgdmFyIHZhbCA9IG5ldyBPcmlnaW4oKTsKICAgIHZhciBudW1iZXJPZkJ5dGVzID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YXIgdmVyc2lvbiA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFsLnNjaGVtZSA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLlN0cmluZyk7CiAgICB2YWwuaG9zdCA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLlN0cmluZyk7CiAgICB2YWwucG9ydCA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLlVpbnQxNik7CiAgICBwYWNrZWQgPSBkZWNvZGVyLnJlYWRVaW50OCgpOwogICAgdmFsLnVuaXF1ZSA9IChwYWNrZWQgPj4gMCkgJiAxID8gdHJ1ZSA6IGZhbHNlOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgdmFsLnN1Ym9yaWdpbiA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLlN0cmluZyk7CiAgICByZXR1cm4gdmFsOwogIH07CgogIE9yaWdpbi5lbmNvZGUgPSBmdW5jdGlvbihlbmNvZGVyLCB2YWwpIHsKICAgIHZhciBwYWNrZWQ7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKE9yaWdpbi5lbmNvZGVkU2l6ZSk7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKDApOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nLCB2YWwuc2NoZW1lKTsKICAgIGVuY29kZXIuZW5jb2RlU3RydWN0KGNvZGVjLlN0cmluZywgdmFsLmhvc3QpOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuVWludDE2LCB2YWwucG9ydCk7CiAgICBwYWNrZWQgPSAwOwogICAgcGFja2VkIHw9ICh2YWwudW5pcXVlICYgMSkgPDwgMAogICAgZW5jb2Rlci53cml0ZVVpbnQ4KHBhY2tlZCk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5TdHJpbmcsIHZhbC5zdWJvcmlnaW4pOwogIH07CiAgZXhwb3J0cy5PcmlnaW4gPSBPcmlnaW47Cn0pKCk7Ly8gQ29weXJpZ2h0IDIwMTQgVGhlIENocm9taXVtIEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCi8vIFVzZSBvZiB0aGlzIHNvdXJjZSBjb2RlIGlzIGdvdmVybmVkIGJ5IGEgQlNELXN0eWxlIGxpY2Vuc2UgdGhhdCBjYW4gYmUKLy8gZm91bmQgaW4gdGhlIExJQ0VOU0UgZmlsZS4KCid1c2Ugc3RyaWN0JzsKCihmdW5jdGlvbigpIHsKICB2YXIgbW9qb21JZCA9ICd1cmwvbW9qby91cmwubW9qb20nOwogIGlmIChtb2pvLmludGVybmFsLmlzTW9qb21Mb2FkZWQobW9qb21JZCkpIHsKICAgIGNvbnNvbGUud2FybignVGhlIGZvbGxvd2luZyBtb2pvbSBpcyBsb2FkZWQgbXVsdGlwbGUgdGltZXM6ICcgKyBtb2pvbUlkKTsKICAgIHJldHVybjsKICB9CiAgbW9qby5pbnRlcm5hbC5tYXJrTW9qb21Mb2FkZWQobW9qb21JZCk7CiAgdmFyIGJpbmRpbmdzID0gbW9qbzsKICB2YXIgYXNzb2NpYXRlZEJpbmRpbmdzID0gbW9qbzsKICB2YXIgY29kZWMgPSBtb2pvLmludGVybmFsOwogIHZhciB2YWxpZGF0b3IgPSBtb2pvLmludGVybmFsOwoKICB2YXIgZXhwb3J0cyA9IG1vam8uaW50ZXJuYWwuZXhwb3NlTmFtZXNwYWNlKCd1cmwubW9qb20nKTsKCgoKICBmdW5jdGlvbiBVcmwodmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBVcmwucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMudXJsID0gbnVsbDsKICB9OwogIFVybC5wcm90b3R5cGUuaW5pdEZpZWxkc18gPSBmdW5jdGlvbihmaWVsZHMpIHsKICAgIGZvcih2YXIgZmllbGQgaW4gZmllbGRzKSB7CiAgICAgICAgaWYgKHRoaXMuaGFzT3duUHJvcGVydHkoZmllbGQpKQogICAgICAgICAgdGhpc1tmaWVsZF0gPSBmaWVsZHNbZmllbGRdOwogICAgfQogIH07CgogIFVybC52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiAxNn0KICAgIF07CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0VmVyc2lvbihvZmZzZXQsIGtWZXJzaW9uU2l6ZXMpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIFVybC51cmwKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJpbmdQb2ludGVyKG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMCwgZmFsc2UpCiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIFVybC5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgODsKCiAgVXJsLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IFVybCgpOwogICAgdmFyIG51bWJlck9mQnl0ZXMgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhciB2ZXJzaW9uID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YWwudXJsID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuU3RyaW5nKTsKICAgIHJldHVybiB2YWw7CiAgfTsKCiAgVXJsLmVuY29kZSA9IGZ1bmN0aW9uKGVuY29kZXIsIHZhbCkgewogICAgdmFyIHBhY2tlZDsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoVXJsLmVuY29kZWRTaXplKTsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoMCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5TdHJpbmcsIHZhbC51cmwpOwogIH07CiAgZXhwb3J0cy5VcmwgPSBVcmw7Cn0pKCk7Ly8gQ29weXJpZ2h0IDIwMTQgVGhlIENocm9taXVtIEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCi8vIFVzZSBvZiB0aGlzIHNvdXJjZSBjb2RlIGlzIGdvdmVybmVkIGJ5IGEgQlNELXN0eWxlIGxpY2Vuc2UgdGhhdCBjYW4gYmUKLy8gZm91bmQgaW4gdGhlIExJQ0VOU0UgZmlsZS4KCid1c2Ugc3RyaWN0JzsKCihmdW5jdGlvbigpIHsKICB2YXIgbW9qb21JZCA9ICdtZWRpYS9tb2pvL2ludGVyZmFjZXMvbWlycm9yX3NlcnZpY2VfcmVtb3RpbmcubW9qb20nOwogIGlmIChtb2pvLmludGVybmFsLmlzTW9qb21Mb2FkZWQobW9qb21JZCkpIHsKICAgIGNvbnNvbGUud2FybignVGhlIGZvbGxvd2luZyBtb2pvbSBpcyBsb2FkZWQgbXVsdGlwbGUgdGltZXM6ICcgKyBtb2pvbUlkKTsKICAgIHJldHVybjsKICB9CiAgbW9qby5pbnRlcm5hbC5tYXJrTW9qb21Mb2FkZWQobW9qb21JZCk7CiAgdmFyIGJpbmRpbmdzID0gbW9qbzsKICB2YXIgYXNzb2NpYXRlZEJpbmRpbmdzID0gbW9qbzsKICB2YXIgY29kZWMgPSBtb2pvLmludGVybmFsOwogIHZhciB2YWxpZGF0b3IgPSBtb2pvLmludGVybmFsOwoKICB2YXIgZXhwb3J0cyA9IG1vam8uaW50ZXJuYWwuZXhwb3NlTmFtZXNwYWNlKCdtZWRpYS5tb2pvbScpOwogIHZhciByZW1vdGluZ19jb21tb24kID0KICAgICAgbW9qby5pbnRlcm5hbC5leHBvc2VOYW1lc3BhY2UoJ21lZGlhLm1vam9tJyk7CiAgaWYgKG1vam8uY29uZmlnLmF1dG9Mb2FkTW9qb21EZXBzKSB7CiAgICBtb2pvLmludGVybmFsLmxvYWRNb2pvbUlmTmVjZXNzYXJ5KAogICAgICAgICdtZWRpYS9tb2pvL2ludGVyZmFjZXMvcmVtb3RpbmdfY29tbW9uLm1vam9tJywgJ3JlbW90aW5nX2NvbW1vbi5tb2pvbS5qcycpOwogIH0KCgoKICBmdW5jdGlvbiBNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdGFydF9QYXJhbXModmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdGFydF9QYXJhbXMucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICB9OwogIE1pcnJvclNlcnZpY2VSZW1vdGVyX1N0YXJ0X1BhcmFtcy5wcm90b3R5cGUuaW5pdEZpZWxkc18gPSBmdW5jdGlvbihmaWVsZHMpIHsKICAgIGZvcih2YXIgZmllbGQgaW4gZmllbGRzKSB7CiAgICAgICAgaWYgKHRoaXMuaGFzT3duUHJvcGVydHkoZmllbGQpKQogICAgICAgICAgdGhpc1tmaWVsZF0gPSBmaWVsZHNbZmllbGRdOwogICAgfQogIH07CgogIE1pcnJvclNlcnZpY2VSZW1vdGVyX1N0YXJ0X1BhcmFtcy52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiA4fQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIE1pcnJvclNlcnZpY2VSZW1vdGVyX1N0YXJ0X1BhcmFtcy5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMDsKCiAgTWlycm9yU2VydmljZVJlbW90ZXJfU3RhcnRfUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1pcnJvclNlcnZpY2VSZW1vdGVyX1N0YXJ0X1BhcmFtcygpOwogICAgdmFyIG51bWJlck9mQnl0ZXMgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhciB2ZXJzaW9uID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICByZXR1cm4gdmFsOwogIH07CgogIE1pcnJvclNlcnZpY2VSZW1vdGVyX1N0YXJ0X1BhcmFtcy5lbmNvZGUgPSBmdW5jdGlvbihlbmNvZGVyLCB2YWwpIHsKICAgIHZhciBwYWNrZWQ7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKE1pcnJvclNlcnZpY2VSZW1vdGVyX1N0YXJ0X1BhcmFtcy5lbmNvZGVkU2l6ZSk7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKDApOwogIH07CiAgZnVuY3Rpb24gTWlycm9yU2VydmljZVJlbW90ZXJfU3RhcnREYXRhU3RyZWFtc19QYXJhbXModmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdGFydERhdGFTdHJlYW1zX1BhcmFtcy5wcm90b3R5cGUuaW5pdERlZmF1bHRzXyA9IGZ1bmN0aW9uKCkgewogICAgdGhpcy5oYXNBdWRpbyA9IGZhbHNlOwogICAgdGhpcy5oYXNWaWRlbyA9IGZhbHNlOwogIH07CiAgTWlycm9yU2VydmljZVJlbW90ZXJfU3RhcnREYXRhU3RyZWFtc19QYXJhbXMucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdGFydERhdGFTdHJlYW1zX1BhcmFtcy52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiAxNn0KICAgIF07CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0VmVyc2lvbihvZmZzZXQsIGtWZXJzaW9uU2l6ZXMpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIE1pcnJvclNlcnZpY2VSZW1vdGVyX1N0YXJ0RGF0YVN0cmVhbXNfUGFyYW1zLmVuY29kZWRTaXplID0gY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA4OwoKICBNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdGFydERhdGFTdHJlYW1zX1BhcmFtcy5kZWNvZGUgPSBmdW5jdGlvbihkZWNvZGVyKSB7CiAgICB2YXIgcGFja2VkOwogICAgdmFyIHZhbCA9IG5ldyBNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdGFydERhdGFTdHJlYW1zX1BhcmFtcygpOwogICAgdmFyIG51bWJlck9mQnl0ZXMgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhciB2ZXJzaW9uID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICBwYWNrZWQgPSBkZWNvZGVyLnJlYWRVaW50OCgpOwogICAgdmFsLmhhc0F1ZGlvID0gKHBhY2tlZCA+PiAwKSAmIDEgPyB0cnVlIDogZmFsc2U7CiAgICB2YWwuaGFzVmlkZW8gPSAocGFja2VkID4+IDEpICYgMSA/IHRydWUgOiBmYWxzZTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIHJldHVybiB2YWw7CiAgfTsKCiAgTWlycm9yU2VydmljZVJlbW90ZXJfU3RhcnREYXRhU3RyZWFtc19QYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdGFydERhdGFTdHJlYW1zX1BhcmFtcy5lbmNvZGVkU2l6ZSk7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKDApOwogICAgcGFja2VkID0gMDsKICAgIHBhY2tlZCB8PSAodmFsLmhhc0F1ZGlvICYgMSkgPDwgMAogICAgcGFja2VkIHw9ICh2YWwuaGFzVmlkZW8gJiAxKSA8PCAxCiAgICBlbmNvZGVyLndyaXRlVWludDgocGFja2VkKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICAgIGVuY29kZXIuc2tpcCgxKTsKICB9OwogIGZ1bmN0aW9uIE1pcnJvclNlcnZpY2VSZW1vdGVyX1N0YXJ0RGF0YVN0cmVhbXNfUmVzcG9uc2VQYXJhbXModmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdGFydERhdGFTdHJlYW1zX1Jlc3BvbnNlUGFyYW1zLnByb3RvdHlwZS5pbml0RGVmYXVsdHNfID0gZnVuY3Rpb24oKSB7CiAgICB0aGlzLmF1ZGlvU3RyZWFtSWQgPSAwOwogICAgdGhpcy52aWRlb1N0cmVhbUlkID0gMDsKICB9OwogIE1pcnJvclNlcnZpY2VSZW1vdGVyX1N0YXJ0RGF0YVN0cmVhbXNfUmVzcG9uc2VQYXJhbXMucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdGFydERhdGFTdHJlYW1zX1Jlc3BvbnNlUGFyYW1zLnZhbGlkYXRlID0gZnVuY3Rpb24obWVzc2FnZVZhbGlkYXRvciwgb2Zmc2V0KSB7CiAgICB2YXIgZXJyOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdEhlYWRlcihvZmZzZXQsIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHZhciBrVmVyc2lvblNpemVzID0gWwogICAgICB7dmVyc2lvbjogMCwgbnVtQnl0ZXM6IDE2fQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgfTsKCiAgTWlycm9yU2VydmljZVJlbW90ZXJfU3RhcnREYXRhU3RyZWFtc19SZXNwb25zZVBhcmFtcy5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgODsKCiAgTWlycm9yU2VydmljZVJlbW90ZXJfU3RhcnREYXRhU3RyZWFtc19SZXNwb25zZVBhcmFtcy5kZWNvZGUgPSBmdW5jdGlvbihkZWNvZGVyKSB7CiAgICB2YXIgcGFja2VkOwogICAgdmFyIHZhbCA9IG5ldyBNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdGFydERhdGFTdHJlYW1zX1Jlc3BvbnNlUGFyYW1zKCk7CiAgICB2YXIgbnVtYmVyT2ZCeXRlcyA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFyIHZlcnNpb24gPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhbC5hdWRpb1N0cmVhbUlkID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuSW50MzIpOwogICAgdmFsLnZpZGVvU3RyZWFtSWQgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5JbnQzMik7CiAgICByZXR1cm4gdmFsOwogIH07CgogIE1pcnJvclNlcnZpY2VSZW1vdGVyX1N0YXJ0RGF0YVN0cmVhbXNfUmVzcG9uc2VQYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdGFydERhdGFTdHJlYW1zX1Jlc3BvbnNlUGFyYW1zLmVuY29kZWRTaXplKTsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoMCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5JbnQzMiwgdmFsLmF1ZGlvU3RyZWFtSWQpOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuSW50MzIsIHZhbC52aWRlb1N0cmVhbUlkKTsKICB9OwogIGZ1bmN0aW9uIE1pcnJvclNlcnZpY2VSZW1vdGVyX1N0b3BfUGFyYW1zKHZhbHVlcykgewogICAgdGhpcy5pbml0RGVmYXVsdHNfKCk7CiAgICB0aGlzLmluaXRGaWVsZHNfKHZhbHVlcyk7CiAgfQoKCiAgTWlycm9yU2VydmljZVJlbW90ZXJfU3RvcF9QYXJhbXMucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMucmVhc29uID0gMDsKICB9OwogIE1pcnJvclNlcnZpY2VSZW1vdGVyX1N0b3BfUGFyYW1zLnByb3RvdHlwZS5pbml0RmllbGRzXyA9IGZ1bmN0aW9uKGZpZWxkcykgewogICAgZm9yKHZhciBmaWVsZCBpbiBmaWVsZHMpIHsKICAgICAgICBpZiAodGhpcy5oYXNPd25Qcm9wZXJ0eShmaWVsZCkpCiAgICAgICAgICB0aGlzW2ZpZWxkXSA9IGZpZWxkc1tmaWVsZF07CiAgICB9CiAgfTsKCiAgTWlycm9yU2VydmljZVJlbW90ZXJfU3RvcF9QYXJhbXMudmFsaWRhdGUgPSBmdW5jdGlvbihtZXNzYWdlVmFsaWRhdG9yLCBvZmZzZXQpIHsKICAgIHZhciBlcnI7CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0SGVhZGVyKG9mZnNldCwgY29kZWMua1N0cnVjdEhlYWRlclNpemUpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgdmFyIGtWZXJzaW9uU2l6ZXMgPSBbCiAgICAgIHt2ZXJzaW9uOiAwLCBudW1CeXRlczogMTZ9CiAgICBdOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFZlcnNpb24ob2Zmc2V0LCBrVmVyc2lvblNpemVzKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdG9wX1BhcmFtcy5yZWFzb24KICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVFbnVtKG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMCwgcmVtb3RpbmdfY29tbW9uJC5SZW1vdGluZ1N0b3BSZWFzb24pOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKICB9OwoKICBNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdG9wX1BhcmFtcy5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgODsKCiAgTWlycm9yU2VydmljZVJlbW90ZXJfU3RvcF9QYXJhbXMuZGVjb2RlID0gZnVuY3Rpb24oZGVjb2RlcikgewogICAgdmFyIHBhY2tlZDsKICAgIHZhciB2YWwgPSBuZXcgTWlycm9yU2VydmljZVJlbW90ZXJfU3RvcF9QYXJhbXMoKTsKICAgIHZhciBudW1iZXJPZkJ5dGVzID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YXIgdmVyc2lvbiA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFsLnJlYXNvbiA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLkludDMyKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIGRlY29kZXIuc2tpcCgxKTsKICAgIHJldHVybiB2YWw7CiAgfTsKCiAgTWlycm9yU2VydmljZVJlbW90ZXJfU3RvcF9QYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdG9wX1BhcmFtcy5lbmNvZGVkU2l6ZSk7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKDApOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3QoY29kZWMuSW50MzIsIHZhbC5yZWFzb24pOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogICAgZW5jb2Rlci5za2lwKDEpOwogIH07CiAgZnVuY3Rpb24gTWlycm9yU2VydmljZVJlbW90ZXJfU2VuZE1lc3NhZ2VUb1NpbmtfUGFyYW1zKHZhbHVlcykgewogICAgdGhpcy5pbml0RGVmYXVsdHNfKCk7CiAgICB0aGlzLmluaXRGaWVsZHNfKHZhbHVlcyk7CiAgfQoKCiAgTWlycm9yU2VydmljZVJlbW90ZXJfU2VuZE1lc3NhZ2VUb1NpbmtfUGFyYW1zLnByb3RvdHlwZS5pbml0RGVmYXVsdHNfID0gZnVuY3Rpb24oKSB7CiAgICB0aGlzLm1lc3NhZ2UgPSBudWxsOwogIH07CiAgTWlycm9yU2VydmljZVJlbW90ZXJfU2VuZE1lc3NhZ2VUb1NpbmtfUGFyYW1zLnByb3RvdHlwZS5pbml0RmllbGRzXyA9IGZ1bmN0aW9uKGZpZWxkcykgewogICAgZm9yKHZhciBmaWVsZCBpbiBmaWVsZHMpIHsKICAgICAgICBpZiAodGhpcy5oYXNPd25Qcm9wZXJ0eShmaWVsZCkpCiAgICAgICAgICB0aGlzW2ZpZWxkXSA9IGZpZWxkc1tmaWVsZF07CiAgICB9CiAgfTsKCiAgTWlycm9yU2VydmljZVJlbW90ZXJfU2VuZE1lc3NhZ2VUb1NpbmtfUGFyYW1zLnZhbGlkYXRlID0gZnVuY3Rpb24obWVzc2FnZVZhbGlkYXRvciwgb2Zmc2V0KSB7CiAgICB2YXIgZXJyOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdEhlYWRlcihvZmZzZXQsIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHZhciBrVmVyc2lvblNpemVzID0gWwogICAgICB7dmVyc2lvbjogMCwgbnVtQnl0ZXM6IDE2fQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWlycm9yU2VydmljZVJlbW90ZXJfU2VuZE1lc3NhZ2VUb1NpbmtfUGFyYW1zLm1lc3NhZ2UKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVBcnJheVBvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAwLCAxLCBjb2RlYy5VaW50OCwgZmFsc2UsIFswXSwgMCk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIE1pcnJvclNlcnZpY2VSZW1vdGVyX1NlbmRNZXNzYWdlVG9TaW5rX1BhcmFtcy5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgODsKCiAgTWlycm9yU2VydmljZVJlbW90ZXJfU2VuZE1lc3NhZ2VUb1NpbmtfUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1pcnJvclNlcnZpY2VSZW1vdGVyX1NlbmRNZXNzYWdlVG9TaW5rX1BhcmFtcygpOwogICAgdmFyIG51bWJlck9mQnl0ZXMgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhciB2ZXJzaW9uID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YWwubWVzc2FnZSA9IGRlY29kZXIuZGVjb2RlQXJyYXlQb2ludGVyKGNvZGVjLlVpbnQ4KTsKICAgIHJldHVybiB2YWw7CiAgfTsKCiAgTWlycm9yU2VydmljZVJlbW90ZXJfU2VuZE1lc3NhZ2VUb1NpbmtfUGFyYW1zLmVuY29kZSA9IGZ1bmN0aW9uKGVuY29kZXIsIHZhbCkgewogICAgdmFyIHBhY2tlZDsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoTWlycm9yU2VydmljZVJlbW90ZXJfU2VuZE1lc3NhZ2VUb1NpbmtfUGFyYW1zLmVuY29kZWRTaXplKTsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoMCk7CiAgICBlbmNvZGVyLmVuY29kZUFycmF5UG9pbnRlcihjb2RlYy5VaW50OCwgdmFsLm1lc3NhZ2UpOwogIH07CiAgZnVuY3Rpb24gTWlycm9yU2VydmljZVJlbW90ZXJfRXN0aW1hdGVUcmFuc21pc3Npb25DYXBhY2l0eV9QYXJhbXModmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9Fc3RpbWF0ZVRyYW5zbWlzc2lvbkNhcGFjaXR5X1BhcmFtcy5wcm90b3R5cGUuaW5pdERlZmF1bHRzXyA9IGZ1bmN0aW9uKCkgewogIH07CiAgTWlycm9yU2VydmljZVJlbW90ZXJfRXN0aW1hdGVUcmFuc21pc3Npb25DYXBhY2l0eV9QYXJhbXMucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9Fc3RpbWF0ZVRyYW5zbWlzc2lvbkNhcGFjaXR5X1BhcmFtcy52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiA4fQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIE1pcnJvclNlcnZpY2VSZW1vdGVyX0VzdGltYXRlVHJhbnNtaXNzaW9uQ2FwYWNpdHlfUGFyYW1zLmVuY29kZWRTaXplID0gY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAwOwoKICBNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9Fc3RpbWF0ZVRyYW5zbWlzc2lvbkNhcGFjaXR5X1BhcmFtcy5kZWNvZGUgPSBmdW5jdGlvbihkZWNvZGVyKSB7CiAgICB2YXIgcGFja2VkOwogICAgdmFyIHZhbCA9IG5ldyBNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9Fc3RpbWF0ZVRyYW5zbWlzc2lvbkNhcGFjaXR5X1BhcmFtcygpOwogICAgdmFyIG51bWJlck9mQnl0ZXMgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhciB2ZXJzaW9uID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICByZXR1cm4gdmFsOwogIH07CgogIE1pcnJvclNlcnZpY2VSZW1vdGVyX0VzdGltYXRlVHJhbnNtaXNzaW9uQ2FwYWNpdHlfUGFyYW1zLmVuY29kZSA9IGZ1bmN0aW9uKGVuY29kZXIsIHZhbCkgewogICAgdmFyIHBhY2tlZDsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoTWlycm9yU2VydmljZVJlbW90ZXJfRXN0aW1hdGVUcmFuc21pc3Npb25DYXBhY2l0eV9QYXJhbXMuZW5jb2RlZFNpemUpOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMigwKTsKICB9OwogIGZ1bmN0aW9uIE1pcnJvclNlcnZpY2VSZW1vdGVyX0VzdGltYXRlVHJhbnNtaXNzaW9uQ2FwYWNpdHlfUmVzcG9uc2VQYXJhbXModmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9Fc3RpbWF0ZVRyYW5zbWlzc2lvbkNhcGFjaXR5X1Jlc3BvbnNlUGFyYW1zLnByb3RvdHlwZS5pbml0RGVmYXVsdHNfID0gZnVuY3Rpb24oKSB7CiAgICB0aGlzLnJhdGUgPSAwOwogIH07CiAgTWlycm9yU2VydmljZVJlbW90ZXJfRXN0aW1hdGVUcmFuc21pc3Npb25DYXBhY2l0eV9SZXNwb25zZVBhcmFtcy5wcm90b3R5cGUuaW5pdEZpZWxkc18gPSBmdW5jdGlvbihmaWVsZHMpIHsKICAgIGZvcih2YXIgZmllbGQgaW4gZmllbGRzKSB7CiAgICAgICAgaWYgKHRoaXMuaGFzT3duUHJvcGVydHkoZmllbGQpKQogICAgICAgICAgdGhpc1tmaWVsZF0gPSBmaWVsZHNbZmllbGRdOwogICAgfQogIH07CgogIE1pcnJvclNlcnZpY2VSZW1vdGVyX0VzdGltYXRlVHJhbnNtaXNzaW9uQ2FwYWNpdHlfUmVzcG9uc2VQYXJhbXMudmFsaWRhdGUgPSBmdW5jdGlvbihtZXNzYWdlVmFsaWRhdG9yLCBvZmZzZXQpIHsKICAgIHZhciBlcnI7CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0SGVhZGVyKG9mZnNldCwgY29kZWMua1N0cnVjdEhlYWRlclNpemUpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgdmFyIGtWZXJzaW9uU2l6ZXMgPSBbCiAgICAgIHt2ZXJzaW9uOiAwLCBudW1CeXRlczogMTZ9CiAgICBdOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFZlcnNpb24ob2Zmc2V0LCBrVmVyc2lvblNpemVzKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIE1pcnJvclNlcnZpY2VSZW1vdGVyX0VzdGltYXRlVHJhbnNtaXNzaW9uQ2FwYWNpdHlfUmVzcG9uc2VQYXJhbXMuZW5jb2RlZFNpemUgPSBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDg7CgogIE1pcnJvclNlcnZpY2VSZW1vdGVyX0VzdGltYXRlVHJhbnNtaXNzaW9uQ2FwYWNpdHlfUmVzcG9uc2VQYXJhbXMuZGVjb2RlID0gZnVuY3Rpb24oZGVjb2RlcikgewogICAgdmFyIHBhY2tlZDsKICAgIHZhciB2YWwgPSBuZXcgTWlycm9yU2VydmljZVJlbW90ZXJfRXN0aW1hdGVUcmFuc21pc3Npb25DYXBhY2l0eV9SZXNwb25zZVBhcmFtcygpOwogICAgdmFyIG51bWJlck9mQnl0ZXMgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhciB2ZXJzaW9uID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YWwucmF0ZSA9IGRlY29kZXIuZGVjb2RlU3RydWN0KGNvZGVjLkRvdWJsZSk7CiAgICByZXR1cm4gdmFsOwogIH07CgogIE1pcnJvclNlcnZpY2VSZW1vdGVyX0VzdGltYXRlVHJhbnNtaXNzaW9uQ2FwYWNpdHlfUmVzcG9uc2VQYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9Fc3RpbWF0ZVRyYW5zbWlzc2lvbkNhcGFjaXR5X1Jlc3BvbnNlUGFyYW1zLmVuY29kZWRTaXplKTsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoMCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5Eb3VibGUsIHZhbC5yYXRlKTsKICB9OwogIGZ1bmN0aW9uIE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9PblNpbmtBdmFpbGFibGVfUGFyYW1zKHZhbHVlcykgewogICAgdGhpcy5pbml0RGVmYXVsdHNfKCk7CiAgICB0aGlzLmluaXRGaWVsZHNfKHZhbHVlcyk7CiAgfQoKCiAgTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlX09uU2lua0F2YWlsYWJsZV9QYXJhbXMucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMubWV0YWRhdGEgPSBudWxsOwogIH07CiAgTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlX09uU2lua0F2YWlsYWJsZV9QYXJhbXMucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VfT25TaW5rQXZhaWxhYmxlX1BhcmFtcy52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiAxNn0KICAgIF07CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0VmVyc2lvbihvZmZzZXQsIGtWZXJzaW9uU2l6ZXMpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9PblNpbmtBdmFpbGFibGVfUGFyYW1zLm1ldGFkYXRhCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0UG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDAsIHJlbW90aW5nX2NvbW1vbiQuUmVtb3RpbmdTaW5rTWV0YWRhdGEsIGZhbHNlKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgfTsKCiAgTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlX09uU2lua0F2YWlsYWJsZV9QYXJhbXMuZW5jb2RlZFNpemUgPSBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDg7CgogIE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9PblNpbmtBdmFpbGFibGVfUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9PblNpbmtBdmFpbGFibGVfUGFyYW1zKCk7CiAgICB2YXIgbnVtYmVyT2ZCeXRlcyA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFyIHZlcnNpb24gPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhbC5tZXRhZGF0YSA9IGRlY29kZXIuZGVjb2RlU3RydWN0UG9pbnRlcihyZW1vdGluZ19jb21tb24kLlJlbW90aW5nU2lua01ldGFkYXRhKTsKICAgIHJldHVybiB2YWw7CiAgfTsKCiAgTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlX09uU2lua0F2YWlsYWJsZV9QYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VfT25TaW5rQXZhaWxhYmxlX1BhcmFtcy5lbmNvZGVkU2l6ZSk7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKDApOwogICAgZW5jb2Rlci5lbmNvZGVTdHJ1Y3RQb2ludGVyKHJlbW90aW5nX2NvbW1vbiQuUmVtb3RpbmdTaW5rTWV0YWRhdGEsIHZhbC5tZXRhZGF0YSk7CiAgfTsKICBmdW5jdGlvbiBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VfT25NZXNzYWdlRnJvbVNpbmtfUGFyYW1zKHZhbHVlcykgewogICAgdGhpcy5pbml0RGVmYXVsdHNfKCk7CiAgICB0aGlzLmluaXRGaWVsZHNfKHZhbHVlcyk7CiAgfQoKCiAgTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlX09uTWVzc2FnZUZyb21TaW5rX1BhcmFtcy5wcm90b3R5cGUuaW5pdERlZmF1bHRzXyA9IGZ1bmN0aW9uKCkgewogICAgdGhpcy5tZXNzYWdlID0gbnVsbDsKICB9OwogIE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9Pbk1lc3NhZ2VGcm9tU2lua19QYXJhbXMucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VfT25NZXNzYWdlRnJvbVNpbmtfUGFyYW1zLnZhbGlkYXRlID0gZnVuY3Rpb24obWVzc2FnZVZhbGlkYXRvciwgb2Zmc2V0KSB7CiAgICB2YXIgZXJyOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdEhlYWRlcihvZmZzZXQsIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKICAgIHZhciBrVmVyc2lvblNpemVzID0gWwogICAgICB7dmVyc2lvbjogMCwgbnVtQnl0ZXM6IDE2fQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCgogICAgLy8gdmFsaWRhdGUgTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlX09uTWVzc2FnZUZyb21TaW5rX1BhcmFtcy5tZXNzYWdlCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlQXJyYXlQb2ludGVyKG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMCwgMSwgY29kZWMuVWludDgsIGZhbHNlLCBbMF0sIDApOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKICB9OwoKICBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VfT25NZXNzYWdlRnJvbVNpbmtfUGFyYW1zLmVuY29kZWRTaXplID0gY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA4OwoKICBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VfT25NZXNzYWdlRnJvbVNpbmtfUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9Pbk1lc3NhZ2VGcm9tU2lua19QYXJhbXMoKTsKICAgIHZhciBudW1iZXJPZkJ5dGVzID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YXIgdmVyc2lvbiA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFsLm1lc3NhZ2UgPSBkZWNvZGVyLmRlY29kZUFycmF5UG9pbnRlcihjb2RlYy5VaW50OCk7CiAgICByZXR1cm4gdmFsOwogIH07CgogIE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9Pbk1lc3NhZ2VGcm9tU2lua19QYXJhbXMuZW5jb2RlID0gZnVuY3Rpb24oZW5jb2RlciwgdmFsKSB7CiAgICB2YXIgcGFja2VkOwogICAgZW5jb2Rlci53cml0ZVVpbnQzMihNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VfT25NZXNzYWdlRnJvbVNpbmtfUGFyYW1zLmVuY29kZWRTaXplKTsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoMCk7CiAgICBlbmNvZGVyLmVuY29kZUFycmF5UG9pbnRlcihjb2RlYy5VaW50OCwgdmFsLm1lc3NhZ2UpOwogIH07CiAgZnVuY3Rpb24gTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlX09uU3RvcHBlZF9QYXJhbXModmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VfT25TdG9wcGVkX1BhcmFtcy5wcm90b3R5cGUuaW5pdERlZmF1bHRzXyA9IGZ1bmN0aW9uKCkgewogICAgdGhpcy5yZWFzb24gPSAwOwogIH07CiAgTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlX09uU3RvcHBlZF9QYXJhbXMucHJvdG90eXBlLmluaXRGaWVsZHNfID0gZnVuY3Rpb24oZmllbGRzKSB7CiAgICBmb3IodmFyIGZpZWxkIGluIGZpZWxkcykgewogICAgICAgIGlmICh0aGlzLmhhc093blByb3BlcnR5KGZpZWxkKSkKICAgICAgICAgIHRoaXNbZmllbGRdID0gZmllbGRzW2ZpZWxkXTsKICAgIH0KICB9OwoKICBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VfT25TdG9wcGVkX1BhcmFtcy52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiAxNn0KICAgIF07CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0VmVyc2lvbihvZmZzZXQsIGtWZXJzaW9uU2l6ZXMpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9PblN0b3BwZWRfUGFyYW1zLnJlYXNvbgogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZUVudW0ob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAwLCByZW1vdGluZ19jb21tb24kLlJlbW90aW5nU3RvcFJlYXNvbik7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9PblN0b3BwZWRfUGFyYW1zLmVuY29kZWRTaXplID0gY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyA4OwoKICBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VfT25TdG9wcGVkX1BhcmFtcy5kZWNvZGUgPSBmdW5jdGlvbihkZWNvZGVyKSB7CiAgICB2YXIgcGFja2VkOwogICAgdmFyIHZhbCA9IG5ldyBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VfT25TdG9wcGVkX1BhcmFtcygpOwogICAgdmFyIG51bWJlck9mQnl0ZXMgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhciB2ZXJzaW9uID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YWwucmVhc29uID0gZGVjb2Rlci5kZWNvZGVTdHJ1Y3QoY29kZWMuSW50MzIpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgZGVjb2Rlci5za2lwKDEpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VfT25TdG9wcGVkX1BhcmFtcy5lbmNvZGUgPSBmdW5jdGlvbihlbmNvZGVyLCB2YWwpIHsKICAgIHZhciBwYWNrZWQ7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9PblN0b3BwZWRfUGFyYW1zLmVuY29kZWRTaXplKTsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoMCk7CiAgICBlbmNvZGVyLmVuY29kZVN0cnVjdChjb2RlYy5JbnQzMiwgdmFsLnJlYXNvbik7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgICBlbmNvZGVyLnNraXAoMSk7CiAgfTsKICBmdW5jdGlvbiBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VfT25FcnJvcl9QYXJhbXModmFsdWVzKSB7CiAgICB0aGlzLmluaXREZWZhdWx0c18oKTsKICAgIHRoaXMuaW5pdEZpZWxkc18odmFsdWVzKTsKICB9CgoKICBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VfT25FcnJvcl9QYXJhbXMucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICB9OwogIE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9PbkVycm9yX1BhcmFtcy5wcm90b3R5cGUuaW5pdEZpZWxkc18gPSBmdW5jdGlvbihmaWVsZHMpIHsKICAgIGZvcih2YXIgZmllbGQgaW4gZmllbGRzKSB7CiAgICAgICAgaWYgKHRoaXMuaGFzT3duUHJvcGVydHkoZmllbGQpKQogICAgICAgICAgdGhpc1tmaWVsZF0gPSBmaWVsZHNbZmllbGRdOwogICAgfQogIH07CgogIE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9PbkVycm9yX1BhcmFtcy52YWxpZGF0ZSA9IGZ1bmN0aW9uKG1lc3NhZ2VWYWxpZGF0b3IsIG9mZnNldCkgewogICAgdmFyIGVycjsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RIZWFkZXIob2Zmc2V0LCBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICB2YXIga1ZlcnNpb25TaXplcyA9IFsKICAgICAge3ZlcnNpb246IDAsIG51bUJ5dGVzOiA4fQogICAgXTsKICAgIGVyciA9IG1lc3NhZ2VWYWxpZGF0b3IudmFsaWRhdGVTdHJ1Y3RWZXJzaW9uKG9mZnNldCwga1ZlcnNpb25TaXplcyk7CiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9PbkVycm9yX1BhcmFtcy5lbmNvZGVkU2l6ZSA9IGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMDsKCiAgTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlX09uRXJyb3JfUGFyYW1zLmRlY29kZSA9IGZ1bmN0aW9uKGRlY29kZXIpIHsKICAgIHZhciBwYWNrZWQ7CiAgICB2YXIgdmFsID0gbmV3IE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9PbkVycm9yX1BhcmFtcygpOwogICAgdmFyIG51bWJlck9mQnl0ZXMgPSBkZWNvZGVyLnJlYWRVaW50MzIoKTsKICAgIHZhciB2ZXJzaW9uID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICByZXR1cm4gdmFsOwogIH07CgogIE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9PbkVycm9yX1BhcmFtcy5lbmNvZGUgPSBmdW5jdGlvbihlbmNvZGVyLCB2YWwpIHsKICAgIHZhciBwYWNrZWQ7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9PbkVycm9yX1BhcmFtcy5lbmNvZGVkU2l6ZSk7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKDApOwogIH07CiAgdmFyIGtNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdGFydF9OYW1lID0gMTU5NzI0NTQwMTsKICB2YXIga01pcnJvclNlcnZpY2VSZW1vdGVyX1N0YXJ0RGF0YVN0cmVhbXNfTmFtZSA9IDE0NzQ0OTc3OTY7CiAgdmFyIGtNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdG9wX05hbWUgPSAyNDc1MDY1OTY7CiAgdmFyIGtNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TZW5kTWVzc2FnZVRvU2lua19OYW1lID0gMTY1MTI1NjA1NTsKICB2YXIga01pcnJvclNlcnZpY2VSZW1vdGVyX0VzdGltYXRlVHJhbnNtaXNzaW9uQ2FwYWNpdHlfTmFtZSA9IDI1NTU4Mjg0MjsKCiAgZnVuY3Rpb24gTWlycm9yU2VydmljZVJlbW90ZXJQdHIoaGFuZGxlT3JQdHJJbmZvKSB7CiAgICB0aGlzLnB0ciA9IG5ldyBiaW5kaW5ncy5JbnRlcmZhY2VQdHJDb250cm9sbGVyKE1pcnJvclNlcnZpY2VSZW1vdGVyLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBoYW5kbGVPclB0ckluZm8pOwogIH0KCiAgZnVuY3Rpb24gTWlycm9yU2VydmljZVJlbW90ZXJBc3NvY2lhdGVkUHRyKGFzc29jaWF0ZWRJbnRlcmZhY2VQdHJJbmZvKSB7CiAgICB0aGlzLnB0ciA9IG5ldyBhc3NvY2lhdGVkQmluZGluZ3MuQXNzb2NpYXRlZEludGVyZmFjZVB0ckNvbnRyb2xsZXIoCiAgICAgICAgTWlycm9yU2VydmljZVJlbW90ZXIsIGFzc29jaWF0ZWRJbnRlcmZhY2VQdHJJbmZvKTsKICB9CgogIE1pcnJvclNlcnZpY2VSZW1vdGVyQXNzb2NpYXRlZFB0ci5wcm90b3R5cGUgPQogICAgICBPYmplY3QuY3JlYXRlKE1pcnJvclNlcnZpY2VSZW1vdGVyUHRyLnByb3RvdHlwZSk7CiAgTWlycm9yU2VydmljZVJlbW90ZXJBc3NvY2lhdGVkUHRyLnByb3RvdHlwZS5jb25zdHJ1Y3RvciA9CiAgICAgIE1pcnJvclNlcnZpY2VSZW1vdGVyQXNzb2NpYXRlZFB0cjsKCiAgZnVuY3Rpb24gTWlycm9yU2VydmljZVJlbW90ZXJQcm94eShyZWNlaXZlcikgewogICAgdGhpcy5yZWNlaXZlcl8gPSByZWNlaXZlcjsKICB9CiAgTWlycm9yU2VydmljZVJlbW90ZXJQdHIucHJvdG90eXBlLnN0YXJ0ID0gZnVuY3Rpb24oKSB7CiAgICByZXR1cm4gTWlycm9yU2VydmljZVJlbW90ZXJQcm94eS5wcm90b3R5cGUuc3RhcnQKICAgICAgICAuYXBwbHkodGhpcy5wdHIuZ2V0UHJveHkoKSwgYXJndW1lbnRzKTsKICB9OwoKICBNaXJyb3JTZXJ2aWNlUmVtb3RlclByb3h5LnByb3RvdHlwZS5zdGFydCA9IGZ1bmN0aW9uKCkgewogICAgdmFyIHBhcmFtcyA9IG5ldyBNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdGFydF9QYXJhbXMoKTsKICAgIHZhciBidWlsZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VWMEJ1aWxkZXIoCiAgICAgICAga01pcnJvclNlcnZpY2VSZW1vdGVyX1N0YXJ0X05hbWUsCiAgICAgICAgY29kZWMuYWxpZ24oTWlycm9yU2VydmljZVJlbW90ZXJfU3RhcnRfUGFyYW1zLmVuY29kZWRTaXplKSk7CiAgICBidWlsZGVyLmVuY29kZVN0cnVjdChNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdGFydF9QYXJhbXMsIHBhcmFtcyk7CiAgICB2YXIgbWVzc2FnZSA9IGJ1aWxkZXIuZmluaXNoKCk7CiAgICB0aGlzLnJlY2VpdmVyXy5hY2NlcHQobWVzc2FnZSk7CiAgfTsKICBNaXJyb3JTZXJ2aWNlUmVtb3RlclB0ci5wcm90b3R5cGUuc3RhcnREYXRhU3RyZWFtcyA9IGZ1bmN0aW9uKCkgewogICAgcmV0dXJuIE1pcnJvclNlcnZpY2VSZW1vdGVyUHJveHkucHJvdG90eXBlLnN0YXJ0RGF0YVN0cmVhbXMKICAgICAgICAuYXBwbHkodGhpcy5wdHIuZ2V0UHJveHkoKSwgYXJndW1lbnRzKTsKICB9OwoKICBNaXJyb3JTZXJ2aWNlUmVtb3RlclByb3h5LnByb3RvdHlwZS5zdGFydERhdGFTdHJlYW1zID0gZnVuY3Rpb24oaGFzQXVkaW8sIGhhc1ZpZGVvKSB7CiAgICB2YXIgcGFyYW1zID0gbmV3IE1pcnJvclNlcnZpY2VSZW1vdGVyX1N0YXJ0RGF0YVN0cmVhbXNfUGFyYW1zKCk7CiAgICBwYXJhbXMuaGFzQXVkaW8gPSBoYXNBdWRpbzsKICAgIHBhcmFtcy5oYXNWaWRlbyA9IGhhc1ZpZGVvOwogICAgcmV0dXJuIG5ldyBQcm9taXNlKGZ1bmN0aW9uKHJlc29sdmUsIHJlamVjdCkgewogICAgICB2YXIgYnVpbGRlciA9IG5ldyBjb2RlYy5NZXNzYWdlVjFCdWlsZGVyKAogICAgICAgICAga01pcnJvclNlcnZpY2VSZW1vdGVyX1N0YXJ0RGF0YVN0cmVhbXNfTmFtZSwKICAgICAgICAgIGNvZGVjLmFsaWduKE1pcnJvclNlcnZpY2VSZW1vdGVyX1N0YXJ0RGF0YVN0cmVhbXNfUGFyYW1zLmVuY29kZWRTaXplKSwKICAgICAgICAgIGNvZGVjLmtNZXNzYWdlRXhwZWN0c1Jlc3BvbnNlLCAwKTsKICAgICAgYnVpbGRlci5lbmNvZGVTdHJ1Y3QoTWlycm9yU2VydmljZVJlbW90ZXJfU3RhcnREYXRhU3RyZWFtc19QYXJhbXMsIHBhcmFtcyk7CiAgICAgIHZhciBtZXNzYWdlID0gYnVpbGRlci5maW5pc2goKTsKICAgICAgdGhpcy5yZWNlaXZlcl8uYWNjZXB0QW5kRXhwZWN0UmVzcG9uc2UobWVzc2FnZSkudGhlbihmdW5jdGlvbihtZXNzYWdlKSB7CiAgICAgICAgdmFyIHJlYWRlciA9IG5ldyBjb2RlYy5NZXNzYWdlUmVhZGVyKG1lc3NhZ2UpOwogICAgICAgIHZhciByZXNwb25zZVBhcmFtcyA9CiAgICAgICAgICAgIHJlYWRlci5kZWNvZGVTdHJ1Y3QoTWlycm9yU2VydmljZVJlbW90ZXJfU3RhcnREYXRhU3RyZWFtc19SZXNwb25zZVBhcmFtcyk7CiAgICAgICAgcmVzb2x2ZShyZXNwb25zZVBhcmFtcyk7CiAgICAgIH0pLmNhdGNoKGZ1bmN0aW9uKHJlc3VsdCkgewogICAgICAgIHJlamVjdChFcnJvcigiQ29ubmVjdGlvbiBlcnJvcjogIiArIHJlc3VsdCkpOwogICAgICB9KTsKICAgIH0uYmluZCh0aGlzKSk7CiAgfTsKICBNaXJyb3JTZXJ2aWNlUmVtb3RlclB0ci5wcm90b3R5cGUuc3RvcCA9IGZ1bmN0aW9uKCkgewogICAgcmV0dXJuIE1pcnJvclNlcnZpY2VSZW1vdGVyUHJveHkucHJvdG90eXBlLnN0b3AKICAgICAgICAuYXBwbHkodGhpcy5wdHIuZ2V0UHJveHkoKSwgYXJndW1lbnRzKTsKICB9OwoKICBNaXJyb3JTZXJ2aWNlUmVtb3RlclByb3h5LnByb3RvdHlwZS5zdG9wID0gZnVuY3Rpb24ocmVhc29uKSB7CiAgICB2YXIgcGFyYW1zID0gbmV3IE1pcnJvclNlcnZpY2VSZW1vdGVyX1N0b3BfUGFyYW1zKCk7CiAgICBwYXJhbXMucmVhc29uID0gcmVhc29uOwogICAgdmFyIGJ1aWxkZXIgPSBuZXcgY29kZWMuTWVzc2FnZVYwQnVpbGRlcigKICAgICAgICBrTWlycm9yU2VydmljZVJlbW90ZXJfU3RvcF9OYW1lLAogICAgICAgIGNvZGVjLmFsaWduKE1pcnJvclNlcnZpY2VSZW1vdGVyX1N0b3BfUGFyYW1zLmVuY29kZWRTaXplKSk7CiAgICBidWlsZGVyLmVuY29kZVN0cnVjdChNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdG9wX1BhcmFtcywgcGFyYW1zKTsKICAgIHZhciBtZXNzYWdlID0gYnVpbGRlci5maW5pc2goKTsKICAgIHRoaXMucmVjZWl2ZXJfLmFjY2VwdChtZXNzYWdlKTsKICB9OwogIE1pcnJvclNlcnZpY2VSZW1vdGVyUHRyLnByb3RvdHlwZS5zZW5kTWVzc2FnZVRvU2luayA9IGZ1bmN0aW9uKCkgewogICAgcmV0dXJuIE1pcnJvclNlcnZpY2VSZW1vdGVyUHJveHkucHJvdG90eXBlLnNlbmRNZXNzYWdlVG9TaW5rCiAgICAgICAgLmFwcGx5KHRoaXMucHRyLmdldFByb3h5KCksIGFyZ3VtZW50cyk7CiAgfTsKCiAgTWlycm9yU2VydmljZVJlbW90ZXJQcm94eS5wcm90b3R5cGUuc2VuZE1lc3NhZ2VUb1NpbmsgPSBmdW5jdGlvbihtZXNzYWdlKSB7CiAgICB2YXIgcGFyYW1zID0gbmV3IE1pcnJvclNlcnZpY2VSZW1vdGVyX1NlbmRNZXNzYWdlVG9TaW5rX1BhcmFtcygpOwogICAgcGFyYW1zLm1lc3NhZ2UgPSBtZXNzYWdlOwogICAgdmFyIGJ1aWxkZXIgPSBuZXcgY29kZWMuTWVzc2FnZVYwQnVpbGRlcigKICAgICAgICBrTWlycm9yU2VydmljZVJlbW90ZXJfU2VuZE1lc3NhZ2VUb1NpbmtfTmFtZSwKICAgICAgICBjb2RlYy5hbGlnbihNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TZW5kTWVzc2FnZVRvU2lua19QYXJhbXMuZW5jb2RlZFNpemUpKTsKICAgIGJ1aWxkZXIuZW5jb2RlU3RydWN0KE1pcnJvclNlcnZpY2VSZW1vdGVyX1NlbmRNZXNzYWdlVG9TaW5rX1BhcmFtcywgcGFyYW1zKTsKICAgIHZhciBtZXNzYWdlID0gYnVpbGRlci5maW5pc2goKTsKICAgIHRoaXMucmVjZWl2ZXJfLmFjY2VwdChtZXNzYWdlKTsKICB9OwogIE1pcnJvclNlcnZpY2VSZW1vdGVyUHRyLnByb3RvdHlwZS5lc3RpbWF0ZVRyYW5zbWlzc2lvbkNhcGFjaXR5ID0gZnVuY3Rpb24oKSB7CiAgICByZXR1cm4gTWlycm9yU2VydmljZVJlbW90ZXJQcm94eS5wcm90b3R5cGUuZXN0aW1hdGVUcmFuc21pc3Npb25DYXBhY2l0eQogICAgICAgIC5hcHBseSh0aGlzLnB0ci5nZXRQcm94eSgpLCBhcmd1bWVudHMpOwogIH07CgogIE1pcnJvclNlcnZpY2VSZW1vdGVyUHJveHkucHJvdG90eXBlLmVzdGltYXRlVHJhbnNtaXNzaW9uQ2FwYWNpdHkgPSBmdW5jdGlvbigpIHsKICAgIHZhciBwYXJhbXMgPSBuZXcgTWlycm9yU2VydmljZVJlbW90ZXJfRXN0aW1hdGVUcmFuc21pc3Npb25DYXBhY2l0eV9QYXJhbXMoKTsKICAgIHJldHVybiBuZXcgUHJvbWlzZShmdW5jdGlvbihyZXNvbHZlLCByZWplY3QpIHsKICAgICAgdmFyIGJ1aWxkZXIgPSBuZXcgY29kZWMuTWVzc2FnZVYxQnVpbGRlcigKICAgICAgICAgIGtNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9Fc3RpbWF0ZVRyYW5zbWlzc2lvbkNhcGFjaXR5X05hbWUsCiAgICAgICAgICBjb2RlYy5hbGlnbihNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9Fc3RpbWF0ZVRyYW5zbWlzc2lvbkNhcGFjaXR5X1BhcmFtcy5lbmNvZGVkU2l6ZSksCiAgICAgICAgICBjb2RlYy5rTWVzc2FnZUV4cGVjdHNSZXNwb25zZSwgMCk7CiAgICAgIGJ1aWxkZXIuZW5jb2RlU3RydWN0KE1pcnJvclNlcnZpY2VSZW1vdGVyX0VzdGltYXRlVHJhbnNtaXNzaW9uQ2FwYWNpdHlfUGFyYW1zLCBwYXJhbXMpOwogICAgICB2YXIgbWVzc2FnZSA9IGJ1aWxkZXIuZmluaXNoKCk7CiAgICAgIHRoaXMucmVjZWl2ZXJfLmFjY2VwdEFuZEV4cGVjdFJlc3BvbnNlKG1lc3NhZ2UpLnRoZW4oZnVuY3Rpb24obWVzc2FnZSkgewogICAgICAgIHZhciByZWFkZXIgPSBuZXcgY29kZWMuTWVzc2FnZVJlYWRlcihtZXNzYWdlKTsKICAgICAgICB2YXIgcmVzcG9uc2VQYXJhbXMgPQogICAgICAgICAgICByZWFkZXIuZGVjb2RlU3RydWN0KE1pcnJvclNlcnZpY2VSZW1vdGVyX0VzdGltYXRlVHJhbnNtaXNzaW9uQ2FwYWNpdHlfUmVzcG9uc2VQYXJhbXMpOwogICAgICAgIHJlc29sdmUocmVzcG9uc2VQYXJhbXMpOwogICAgICB9KS5jYXRjaChmdW5jdGlvbihyZXN1bHQpIHsKICAgICAgICByZWplY3QoRXJyb3IoIkNvbm5lY3Rpb24gZXJyb3I6ICIgKyByZXN1bHQpKTsKICAgICAgfSk7CiAgICB9LmJpbmQodGhpcykpOwogIH07CgogIGZ1bmN0aW9uIE1pcnJvclNlcnZpY2VSZW1vdGVyU3R1YihkZWxlZ2F0ZSkgewogICAgdGhpcy5kZWxlZ2F0ZV8gPSBkZWxlZ2F0ZTsKICB9CiAgTWlycm9yU2VydmljZVJlbW90ZXJTdHViLnByb3RvdHlwZS5zdGFydCA9IGZ1bmN0aW9uKCkgewogICAgcmV0dXJuIHRoaXMuZGVsZWdhdGVfICYmIHRoaXMuZGVsZWdhdGVfLnN0YXJ0ICYmIHRoaXMuZGVsZWdhdGVfLnN0YXJ0KCk7CiAgfQogIE1pcnJvclNlcnZpY2VSZW1vdGVyU3R1Yi5wcm90b3R5cGUuc3RhcnREYXRhU3RyZWFtcyA9IGZ1bmN0aW9uKGhhc0F1ZGlvLCBoYXNWaWRlbykgewogICAgcmV0dXJuIHRoaXMuZGVsZWdhdGVfICYmIHRoaXMuZGVsZWdhdGVfLnN0YXJ0RGF0YVN0cmVhbXMgJiYgdGhpcy5kZWxlZ2F0ZV8uc3RhcnREYXRhU3RyZWFtcyhoYXNBdWRpbywgaGFzVmlkZW8pOwogIH0KICBNaXJyb3JTZXJ2aWNlUmVtb3RlclN0dWIucHJvdG90eXBlLnN0b3AgPSBmdW5jdGlvbihyZWFzb24pIHsKICAgIHJldHVybiB0aGlzLmRlbGVnYXRlXyAmJiB0aGlzLmRlbGVnYXRlXy5zdG9wICYmIHRoaXMuZGVsZWdhdGVfLnN0b3AocmVhc29uKTsKICB9CiAgTWlycm9yU2VydmljZVJlbW90ZXJTdHViLnByb3RvdHlwZS5zZW5kTWVzc2FnZVRvU2luayA9IGZ1bmN0aW9uKG1lc3NhZ2UpIHsKICAgIHJldHVybiB0aGlzLmRlbGVnYXRlXyAmJiB0aGlzLmRlbGVnYXRlXy5zZW5kTWVzc2FnZVRvU2luayAmJiB0aGlzLmRlbGVnYXRlXy5zZW5kTWVzc2FnZVRvU2luayhtZXNzYWdlKTsKICB9CiAgTWlycm9yU2VydmljZVJlbW90ZXJTdHViLnByb3RvdHlwZS5lc3RpbWF0ZVRyYW5zbWlzc2lvbkNhcGFjaXR5ID0gZnVuY3Rpb24oKSB7CiAgICByZXR1cm4gdGhpcy5kZWxlZ2F0ZV8gJiYgdGhpcy5kZWxlZ2F0ZV8uZXN0aW1hdGVUcmFuc21pc3Npb25DYXBhY2l0eSAmJiB0aGlzLmRlbGVnYXRlXy5lc3RpbWF0ZVRyYW5zbWlzc2lvbkNhcGFjaXR5KCk7CiAgfQoKICBNaXJyb3JTZXJ2aWNlUmVtb3RlclN0dWIucHJvdG90eXBlLmFjY2VwdCA9IGZ1bmN0aW9uKG1lc3NhZ2UpIHsKICAgIHZhciByZWFkZXIgPSBuZXcgY29kZWMuTWVzc2FnZVJlYWRlcihtZXNzYWdlKTsKICAgIHN3aXRjaCAocmVhZGVyLm1lc3NhZ2VOYW1lKSB7CiAgICBjYXNlIGtNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdGFydF9OYW1lOgogICAgICB2YXIgcGFyYW1zID0gcmVhZGVyLmRlY29kZVN0cnVjdChNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdGFydF9QYXJhbXMpOwogICAgICB0aGlzLnN0YXJ0KCk7CiAgICAgIHJldHVybiB0cnVlOwogICAgY2FzZSBrTWlycm9yU2VydmljZVJlbW90ZXJfU3RvcF9OYW1lOgogICAgICB2YXIgcGFyYW1zID0gcmVhZGVyLmRlY29kZVN0cnVjdChNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdG9wX1BhcmFtcyk7CiAgICAgIHRoaXMuc3RvcChwYXJhbXMucmVhc29uKTsKICAgICAgcmV0dXJuIHRydWU7CiAgICBjYXNlIGtNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TZW5kTWVzc2FnZVRvU2lua19OYW1lOgogICAgICB2YXIgcGFyYW1zID0gcmVhZGVyLmRlY29kZVN0cnVjdChNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TZW5kTWVzc2FnZVRvU2lua19QYXJhbXMpOwogICAgICB0aGlzLnNlbmRNZXNzYWdlVG9TaW5rKHBhcmFtcy5tZXNzYWdlKTsKICAgICAgcmV0dXJuIHRydWU7CiAgICBkZWZhdWx0OgogICAgICByZXR1cm4gZmFsc2U7CiAgICB9CiAgfTsKCiAgTWlycm9yU2VydmljZVJlbW90ZXJTdHViLnByb3RvdHlwZS5hY2NlcHRXaXRoUmVzcG9uZGVyID0KICAgICAgZnVuY3Rpb24obWVzc2FnZSwgcmVzcG9uZGVyKSB7CiAgICB2YXIgcmVhZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VSZWFkZXIobWVzc2FnZSk7CiAgICBzd2l0Y2ggKHJlYWRlci5tZXNzYWdlTmFtZSkgewogICAgY2FzZSBrTWlycm9yU2VydmljZVJlbW90ZXJfU3RhcnREYXRhU3RyZWFtc19OYW1lOgogICAgICB2YXIgcGFyYW1zID0gcmVhZGVyLmRlY29kZVN0cnVjdChNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdGFydERhdGFTdHJlYW1zX1BhcmFtcyk7CiAgICAgIHRoaXMuc3RhcnREYXRhU3RyZWFtcyhwYXJhbXMuaGFzQXVkaW8sIHBhcmFtcy5oYXNWaWRlbykudGhlbihmdW5jdGlvbihyZXNwb25zZSkgewogICAgICAgIHZhciByZXNwb25zZVBhcmFtcyA9CiAgICAgICAgICAgIG5ldyBNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdGFydERhdGFTdHJlYW1zX1Jlc3BvbnNlUGFyYW1zKCk7CiAgICAgICAgcmVzcG9uc2VQYXJhbXMuYXVkaW9TdHJlYW1JZCA9IHJlc3BvbnNlLmF1ZGlvU3RyZWFtSWQ7CiAgICAgICAgcmVzcG9uc2VQYXJhbXMudmlkZW9TdHJlYW1JZCA9IHJlc3BvbnNlLnZpZGVvU3RyZWFtSWQ7CiAgICAgICAgdmFyIGJ1aWxkZXIgPSBuZXcgY29kZWMuTWVzc2FnZVYxQnVpbGRlcigKICAgICAgICAgICAga01pcnJvclNlcnZpY2VSZW1vdGVyX1N0YXJ0RGF0YVN0cmVhbXNfTmFtZSwKICAgICAgICAgICAgY29kZWMuYWxpZ24oTWlycm9yU2VydmljZVJlbW90ZXJfU3RhcnREYXRhU3RyZWFtc19SZXNwb25zZVBhcmFtcy5lbmNvZGVkU2l6ZSksCiAgICAgICAgICAgIGNvZGVjLmtNZXNzYWdlSXNSZXNwb25zZSwgcmVhZGVyLnJlcXVlc3RJRCk7CiAgICAgICAgYnVpbGRlci5lbmNvZGVTdHJ1Y3QoTWlycm9yU2VydmljZVJlbW90ZXJfU3RhcnREYXRhU3RyZWFtc19SZXNwb25zZVBhcmFtcywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICByZXNwb25zZVBhcmFtcyk7CiAgICAgICAgdmFyIG1lc3NhZ2UgPSBidWlsZGVyLmZpbmlzaCgpOwogICAgICAgIHJlc3BvbmRlci5hY2NlcHQobWVzc2FnZSk7CiAgICAgIH0pOwogICAgICByZXR1cm4gdHJ1ZTsKICAgIGNhc2Uga01pcnJvclNlcnZpY2VSZW1vdGVyX0VzdGltYXRlVHJhbnNtaXNzaW9uQ2FwYWNpdHlfTmFtZToKICAgICAgdmFyIHBhcmFtcyA9IHJlYWRlci5kZWNvZGVTdHJ1Y3QoTWlycm9yU2VydmljZVJlbW90ZXJfRXN0aW1hdGVUcmFuc21pc3Npb25DYXBhY2l0eV9QYXJhbXMpOwogICAgICB0aGlzLmVzdGltYXRlVHJhbnNtaXNzaW9uQ2FwYWNpdHkoKS50aGVuKGZ1bmN0aW9uKHJlc3BvbnNlKSB7CiAgICAgICAgdmFyIHJlc3BvbnNlUGFyYW1zID0KICAgICAgICAgICAgbmV3IE1pcnJvclNlcnZpY2VSZW1vdGVyX0VzdGltYXRlVHJhbnNtaXNzaW9uQ2FwYWNpdHlfUmVzcG9uc2VQYXJhbXMoKTsKICAgICAgICByZXNwb25zZVBhcmFtcy5yYXRlID0gcmVzcG9uc2UucmF0ZTsKICAgICAgICB2YXIgYnVpbGRlciA9IG5ldyBjb2RlYy5NZXNzYWdlVjFCdWlsZGVyKAogICAgICAgICAgICBrTWlycm9yU2VydmljZVJlbW90ZXJfRXN0aW1hdGVUcmFuc21pc3Npb25DYXBhY2l0eV9OYW1lLAogICAgICAgICAgICBjb2RlYy5hbGlnbihNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9Fc3RpbWF0ZVRyYW5zbWlzc2lvbkNhcGFjaXR5X1Jlc3BvbnNlUGFyYW1zLmVuY29kZWRTaXplKSwKICAgICAgICAgICAgY29kZWMua01lc3NhZ2VJc1Jlc3BvbnNlLCByZWFkZXIucmVxdWVzdElEKTsKICAgICAgICBidWlsZGVyLmVuY29kZVN0cnVjdChNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9Fc3RpbWF0ZVRyYW5zbWlzc2lvbkNhcGFjaXR5X1Jlc3BvbnNlUGFyYW1zLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJlc3BvbnNlUGFyYW1zKTsKICAgICAgICB2YXIgbWVzc2FnZSA9IGJ1aWxkZXIuZmluaXNoKCk7CiAgICAgICAgcmVzcG9uZGVyLmFjY2VwdChtZXNzYWdlKTsKICAgICAgfSk7CiAgICAgIHJldHVybiB0cnVlOwogICAgZGVmYXVsdDoKICAgICAgcmV0dXJuIGZhbHNlOwogICAgfQogIH07CgogIGZ1bmN0aW9uIHZhbGlkYXRlTWlycm9yU2VydmljZVJlbW90ZXJSZXF1ZXN0KG1lc3NhZ2VWYWxpZGF0b3IpIHsKICAgIHZhciBtZXNzYWdlID0gbWVzc2FnZVZhbGlkYXRvci5tZXNzYWdlOwogICAgdmFyIHBhcmFtc0NsYXNzID0gbnVsbDsKICAgIHN3aXRjaCAobWVzc2FnZS5nZXROYW1lKCkpIHsKICAgICAgY2FzZSBrTWlycm9yU2VydmljZVJlbW90ZXJfU3RhcnRfTmFtZToKICAgICAgICBpZiAoIW1lc3NhZ2UuZXhwZWN0c1Jlc3BvbnNlKCkgJiYgIW1lc3NhZ2UuaXNSZXNwb25zZSgpKQogICAgICAgICAgcGFyYW1zQ2xhc3MgPSBNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdGFydF9QYXJhbXM7CiAgICAgIGJyZWFrOwogICAgICBjYXNlIGtNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdGFydERhdGFTdHJlYW1zX05hbWU6CiAgICAgICAgaWYgKG1lc3NhZ2UuZXhwZWN0c1Jlc3BvbnNlKCkpCiAgICAgICAgICBwYXJhbXNDbGFzcyA9IE1pcnJvclNlcnZpY2VSZW1vdGVyX1N0YXJ0RGF0YVN0cmVhbXNfUGFyYW1zOwogICAgICBicmVhazsKICAgICAgY2FzZSBrTWlycm9yU2VydmljZVJlbW90ZXJfU3RvcF9OYW1lOgogICAgICAgIGlmICghbWVzc2FnZS5leHBlY3RzUmVzcG9uc2UoKSAmJiAhbWVzc2FnZS5pc1Jlc3BvbnNlKCkpCiAgICAgICAgICBwYXJhbXNDbGFzcyA9IE1pcnJvclNlcnZpY2VSZW1vdGVyX1N0b3BfUGFyYW1zOwogICAgICBicmVhazsKICAgICAgY2FzZSBrTWlycm9yU2VydmljZVJlbW90ZXJfU2VuZE1lc3NhZ2VUb1NpbmtfTmFtZToKICAgICAgICBpZiAoIW1lc3NhZ2UuZXhwZWN0c1Jlc3BvbnNlKCkgJiYgIW1lc3NhZ2UuaXNSZXNwb25zZSgpKQogICAgICAgICAgcGFyYW1zQ2xhc3MgPSBNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TZW5kTWVzc2FnZVRvU2lua19QYXJhbXM7CiAgICAgIGJyZWFrOwogICAgICBjYXNlIGtNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9Fc3RpbWF0ZVRyYW5zbWlzc2lvbkNhcGFjaXR5X05hbWU6CiAgICAgICAgaWYgKG1lc3NhZ2UuZXhwZWN0c1Jlc3BvbnNlKCkpCiAgICAgICAgICBwYXJhbXNDbGFzcyA9IE1pcnJvclNlcnZpY2VSZW1vdGVyX0VzdGltYXRlVHJhbnNtaXNzaW9uQ2FwYWNpdHlfUGFyYW1zOwogICAgICBicmVhazsKICAgIH0KICAgIGlmIChwYXJhbXNDbGFzcyA9PT0gbnVsbCkKICAgICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKICAgIHJldHVybiBwYXJhbXNDbGFzcy52YWxpZGF0ZShtZXNzYWdlVmFsaWRhdG9yLCBtZXNzYWdlVmFsaWRhdG9yLm1lc3NhZ2UuZ2V0SGVhZGVyTnVtQnl0ZXMoKSk7CiAgfQoKICBmdW5jdGlvbiB2YWxpZGF0ZU1pcnJvclNlcnZpY2VSZW1vdGVyUmVzcG9uc2UobWVzc2FnZVZhbGlkYXRvcikgewogICB2YXIgbWVzc2FnZSA9IG1lc3NhZ2VWYWxpZGF0b3IubWVzc2FnZTsKICAgdmFyIHBhcmFtc0NsYXNzID0gbnVsbDsKICAgc3dpdGNoIChtZXNzYWdlLmdldE5hbWUoKSkgewogICAgICBjYXNlIGtNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdGFydERhdGFTdHJlYW1zX05hbWU6CiAgICAgICAgaWYgKG1lc3NhZ2UuaXNSZXNwb25zZSgpKQogICAgICAgICAgcGFyYW1zQ2xhc3MgPSBNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9TdGFydERhdGFTdHJlYW1zX1Jlc3BvbnNlUGFyYW1zOwogICAgICAgIGJyZWFrOwogICAgICBjYXNlIGtNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9Fc3RpbWF0ZVRyYW5zbWlzc2lvbkNhcGFjaXR5X05hbWU6CiAgICAgICAgaWYgKG1lc3NhZ2UuaXNSZXNwb25zZSgpKQogICAgICAgICAgcGFyYW1zQ2xhc3MgPSBNaXJyb3JTZXJ2aWNlUmVtb3Rlcl9Fc3RpbWF0ZVRyYW5zbWlzc2lvbkNhcGFjaXR5X1Jlc3BvbnNlUGFyYW1zOwogICAgICAgIGJyZWFrOwogICAgfQogICAgaWYgKHBhcmFtc0NsYXNzID09PSBudWxsKQogICAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogICAgcmV0dXJuIHBhcmFtc0NsYXNzLnZhbGlkYXRlKG1lc3NhZ2VWYWxpZGF0b3IsIG1lc3NhZ2VWYWxpZGF0b3IubWVzc2FnZS5nZXRIZWFkZXJOdW1CeXRlcygpKTsKICB9CgogIHZhciBNaXJyb3JTZXJ2aWNlUmVtb3RlciA9IHsKICAgIG5hbWU6ICdtZWRpYTo6bW9qb206Ok1pcnJvclNlcnZpY2VSZW1vdGVyJywKICAgIGtWZXJzaW9uOiAwLAogICAgcHRyQ2xhc3M6IE1pcnJvclNlcnZpY2VSZW1vdGVyUHRyLAogICAgcHJveHlDbGFzczogTWlycm9yU2VydmljZVJlbW90ZXJQcm94eSwKICAgIHN0dWJDbGFzczogTWlycm9yU2VydmljZVJlbW90ZXJTdHViLAogICAgdmFsaWRhdGVSZXF1ZXN0OiB2YWxpZGF0ZU1pcnJvclNlcnZpY2VSZW1vdGVyUmVxdWVzdCwKICAgIHZhbGlkYXRlUmVzcG9uc2U6IHZhbGlkYXRlTWlycm9yU2VydmljZVJlbW90ZXJSZXNwb25zZSwKICB9OwogIE1pcnJvclNlcnZpY2VSZW1vdGVyU3R1Yi5wcm90b3R5cGUudmFsaWRhdG9yID0gdmFsaWRhdGVNaXJyb3JTZXJ2aWNlUmVtb3RlclJlcXVlc3Q7CiAgTWlycm9yU2VydmljZVJlbW90ZXJQcm94eS5wcm90b3R5cGUudmFsaWRhdG9yID0gdmFsaWRhdGVNaXJyb3JTZXJ2aWNlUmVtb3RlclJlc3BvbnNlOwogIHZhciBrTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlX09uU2lua0F2YWlsYWJsZV9OYW1lID0gMTAwMDM0OTExNzsKICB2YXIga01pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9Pbk1lc3NhZ2VGcm9tU2lua19OYW1lID0gMTE2NzgwNzI3NjsKICB2YXIga01pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9PblN0b3BwZWRfTmFtZSA9IDE1MTkxMDU2Mzk7CiAgdmFyIGtNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VfT25FcnJvcl9OYW1lID0gMTI2NjY3MjM4NTsKCiAgZnVuY3Rpb24gTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlUHRyKGhhbmRsZU9yUHRySW5mbykgewogICAgdGhpcy5wdHIgPSBuZXcgYmluZGluZ3MuSW50ZXJmYWNlUHRyQ29udHJvbGxlcihNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGhhbmRsZU9yUHRySW5mbyk7CiAgfQoKICBmdW5jdGlvbiBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VBc3NvY2lhdGVkUHRyKGFzc29jaWF0ZWRJbnRlcmZhY2VQdHJJbmZvKSB7CiAgICB0aGlzLnB0ciA9IG5ldyBhc3NvY2lhdGVkQmluZGluZ3MuQXNzb2NpYXRlZEludGVyZmFjZVB0ckNvbnRyb2xsZXIoCiAgICAgICAgTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlLCBhc3NvY2lhdGVkSW50ZXJmYWNlUHRySW5mbyk7CiAgfQoKICBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VBc3NvY2lhdGVkUHRyLnByb3RvdHlwZSA9CiAgICAgIE9iamVjdC5jcmVhdGUoTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlUHRyLnByb3RvdHlwZSk7CiAgTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlQXNzb2NpYXRlZFB0ci5wcm90b3R5cGUuY29uc3RydWN0b3IgPQogICAgICBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VBc3NvY2lhdGVkUHRyOwoKICBmdW5jdGlvbiBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VQcm94eShyZWNlaXZlcikgewogICAgdGhpcy5yZWNlaXZlcl8gPSByZWNlaXZlcjsKICB9CiAgTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlUHRyLnByb3RvdHlwZS5vblNpbmtBdmFpbGFibGUgPSBmdW5jdGlvbigpIHsKICAgIHJldHVybiBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VQcm94eS5wcm90b3R5cGUub25TaW5rQXZhaWxhYmxlCiAgICAgICAgLmFwcGx5KHRoaXMucHRyLmdldFByb3h5KCksIGFyZ3VtZW50cyk7CiAgfTsKCiAgTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlUHJveHkucHJvdG90eXBlLm9uU2lua0F2YWlsYWJsZSA9IGZ1bmN0aW9uKG1ldGFkYXRhKSB7CiAgICB2YXIgcGFyYW1zID0gbmV3IE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9PblNpbmtBdmFpbGFibGVfUGFyYW1zKCk7CiAgICBwYXJhbXMubWV0YWRhdGEgPSBtZXRhZGF0YTsKICAgIHZhciBidWlsZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VWMEJ1aWxkZXIoCiAgICAgICAga01pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9PblNpbmtBdmFpbGFibGVfTmFtZSwKICAgICAgICBjb2RlYy5hbGlnbihNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VfT25TaW5rQXZhaWxhYmxlX1BhcmFtcy5lbmNvZGVkU2l6ZSkpOwogICAgYnVpbGRlci5lbmNvZGVTdHJ1Y3QoTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlX09uU2lua0F2YWlsYWJsZV9QYXJhbXMsIHBhcmFtcyk7CiAgICB2YXIgbWVzc2FnZSA9IGJ1aWxkZXIuZmluaXNoKCk7CiAgICB0aGlzLnJlY2VpdmVyXy5hY2NlcHQobWVzc2FnZSk7CiAgfTsKICBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VQdHIucHJvdG90eXBlLm9uTWVzc2FnZUZyb21TaW5rID0gZnVuY3Rpb24oKSB7CiAgICByZXR1cm4gTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlUHJveHkucHJvdG90eXBlLm9uTWVzc2FnZUZyb21TaW5rCiAgICAgICAgLmFwcGx5KHRoaXMucHRyLmdldFByb3h5KCksIGFyZ3VtZW50cyk7CiAgfTsKCiAgTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlUHJveHkucHJvdG90eXBlLm9uTWVzc2FnZUZyb21TaW5rID0gZnVuY3Rpb24obWVzc2FnZSkgewogICAgdmFyIHBhcmFtcyA9IG5ldyBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VfT25NZXNzYWdlRnJvbVNpbmtfUGFyYW1zKCk7CiAgICBwYXJhbXMubWVzc2FnZSA9IG1lc3NhZ2U7CiAgICB2YXIgYnVpbGRlciA9IG5ldyBjb2RlYy5NZXNzYWdlVjBCdWlsZGVyKAogICAgICAgIGtNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VfT25NZXNzYWdlRnJvbVNpbmtfTmFtZSwKICAgICAgICBjb2RlYy5hbGlnbihNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VfT25NZXNzYWdlRnJvbVNpbmtfUGFyYW1zLmVuY29kZWRTaXplKSk7CiAgICBidWlsZGVyLmVuY29kZVN0cnVjdChNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VfT25NZXNzYWdlRnJvbVNpbmtfUGFyYW1zLCBwYXJhbXMpOwogICAgdmFyIG1lc3NhZ2UgPSBidWlsZGVyLmZpbmlzaCgpOwogICAgdGhpcy5yZWNlaXZlcl8uYWNjZXB0KG1lc3NhZ2UpOwogIH07CiAgTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlUHRyLnByb3RvdHlwZS5vblN0b3BwZWQgPSBmdW5jdGlvbigpIHsKICAgIHJldHVybiBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VQcm94eS5wcm90b3R5cGUub25TdG9wcGVkCiAgICAgICAgLmFwcGx5KHRoaXMucHRyLmdldFByb3h5KCksIGFyZ3VtZW50cyk7CiAgfTsKCiAgTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlUHJveHkucHJvdG90eXBlLm9uU3RvcHBlZCA9IGZ1bmN0aW9uKHJlYXNvbikgewogICAgdmFyIHBhcmFtcyA9IG5ldyBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VfT25TdG9wcGVkX1BhcmFtcygpOwogICAgcGFyYW1zLnJlYXNvbiA9IHJlYXNvbjsKICAgIHZhciBidWlsZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VWMEJ1aWxkZXIoCiAgICAgICAga01pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9PblN0b3BwZWRfTmFtZSwKICAgICAgICBjb2RlYy5hbGlnbihNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VfT25TdG9wcGVkX1BhcmFtcy5lbmNvZGVkU2l6ZSkpOwogICAgYnVpbGRlci5lbmNvZGVTdHJ1Y3QoTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlX09uU3RvcHBlZF9QYXJhbXMsIHBhcmFtcyk7CiAgICB2YXIgbWVzc2FnZSA9IGJ1aWxkZXIuZmluaXNoKCk7CiAgICB0aGlzLnJlY2VpdmVyXy5hY2NlcHQobWVzc2FnZSk7CiAgfTsKICBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VQdHIucHJvdG90eXBlLm9uRXJyb3IgPSBmdW5jdGlvbigpIHsKICAgIHJldHVybiBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VQcm94eS5wcm90b3R5cGUub25FcnJvcgogICAgICAgIC5hcHBseSh0aGlzLnB0ci5nZXRQcm94eSgpLCBhcmd1bWVudHMpOwogIH07CgogIE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZVByb3h5LnByb3RvdHlwZS5vbkVycm9yID0gZnVuY3Rpb24oKSB7CiAgICB2YXIgcGFyYW1zID0gbmV3IE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9PbkVycm9yX1BhcmFtcygpOwogICAgdmFyIGJ1aWxkZXIgPSBuZXcgY29kZWMuTWVzc2FnZVYwQnVpbGRlcigKICAgICAgICBrTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlX09uRXJyb3JfTmFtZSwKICAgICAgICBjb2RlYy5hbGlnbihNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VfT25FcnJvcl9QYXJhbXMuZW5jb2RlZFNpemUpKTsKICAgIGJ1aWxkZXIuZW5jb2RlU3RydWN0KE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9PbkVycm9yX1BhcmFtcywgcGFyYW1zKTsKICAgIHZhciBtZXNzYWdlID0gYnVpbGRlci5maW5pc2goKTsKICAgIHRoaXMucmVjZWl2ZXJfLmFjY2VwdChtZXNzYWdlKTsKICB9OwoKICBmdW5jdGlvbiBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VTdHViKGRlbGVnYXRlKSB7CiAgICB0aGlzLmRlbGVnYXRlXyA9IGRlbGVnYXRlOwogIH0KICBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VTdHViLnByb3RvdHlwZS5vblNpbmtBdmFpbGFibGUgPSBmdW5jdGlvbihtZXRhZGF0YSkgewogICAgcmV0dXJuIHRoaXMuZGVsZWdhdGVfICYmIHRoaXMuZGVsZWdhdGVfLm9uU2lua0F2YWlsYWJsZSAmJiB0aGlzLmRlbGVnYXRlXy5vblNpbmtBdmFpbGFibGUobWV0YWRhdGEpOwogIH0KICBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VTdHViLnByb3RvdHlwZS5vbk1lc3NhZ2VGcm9tU2luayA9IGZ1bmN0aW9uKG1lc3NhZ2UpIHsKICAgIHJldHVybiB0aGlzLmRlbGVnYXRlXyAmJiB0aGlzLmRlbGVnYXRlXy5vbk1lc3NhZ2VGcm9tU2luayAmJiB0aGlzLmRlbGVnYXRlXy5vbk1lc3NhZ2VGcm9tU2luayhtZXNzYWdlKTsKICB9CiAgTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlU3R1Yi5wcm90b3R5cGUub25TdG9wcGVkID0gZnVuY3Rpb24ocmVhc29uKSB7CiAgICByZXR1cm4gdGhpcy5kZWxlZ2F0ZV8gJiYgdGhpcy5kZWxlZ2F0ZV8ub25TdG9wcGVkICYmIHRoaXMuZGVsZWdhdGVfLm9uU3RvcHBlZChyZWFzb24pOwogIH0KICBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VTdHViLnByb3RvdHlwZS5vbkVycm9yID0gZnVuY3Rpb24oKSB7CiAgICByZXR1cm4gdGhpcy5kZWxlZ2F0ZV8gJiYgdGhpcy5kZWxlZ2F0ZV8ub25FcnJvciAmJiB0aGlzLmRlbGVnYXRlXy5vbkVycm9yKCk7CiAgfQoKICBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VTdHViLnByb3RvdHlwZS5hY2NlcHQgPSBmdW5jdGlvbihtZXNzYWdlKSB7CiAgICB2YXIgcmVhZGVyID0gbmV3IGNvZGVjLk1lc3NhZ2VSZWFkZXIobWVzc2FnZSk7CiAgICBzd2l0Y2ggKHJlYWRlci5tZXNzYWdlTmFtZSkgewogICAgY2FzZSBrTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlX09uU2lua0F2YWlsYWJsZV9OYW1lOgogICAgICB2YXIgcGFyYW1zID0gcmVhZGVyLmRlY29kZVN0cnVjdChNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VfT25TaW5rQXZhaWxhYmxlX1BhcmFtcyk7CiAgICAgIHRoaXMub25TaW5rQXZhaWxhYmxlKHBhcmFtcy5tZXRhZGF0YSk7CiAgICAgIHJldHVybiB0cnVlOwogICAgY2FzZSBrTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlX09uTWVzc2FnZUZyb21TaW5rX05hbWU6CiAgICAgIHZhciBwYXJhbXMgPSByZWFkZXIuZGVjb2RlU3RydWN0KE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9Pbk1lc3NhZ2VGcm9tU2lua19QYXJhbXMpOwogICAgICB0aGlzLm9uTWVzc2FnZUZyb21TaW5rKHBhcmFtcy5tZXNzYWdlKTsKICAgICAgcmV0dXJuIHRydWU7CiAgICBjYXNlIGtNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VfT25TdG9wcGVkX05hbWU6CiAgICAgIHZhciBwYXJhbXMgPSByZWFkZXIuZGVjb2RlU3RydWN0KE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9PblN0b3BwZWRfUGFyYW1zKTsKICAgICAgdGhpcy5vblN0b3BwZWQocGFyYW1zLnJlYXNvbik7CiAgICAgIHJldHVybiB0cnVlOwogICAgY2FzZSBrTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlX09uRXJyb3JfTmFtZToKICAgICAgdmFyIHBhcmFtcyA9IHJlYWRlci5kZWNvZGVTdHJ1Y3QoTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlX09uRXJyb3JfUGFyYW1zKTsKICAgICAgdGhpcy5vbkVycm9yKCk7CiAgICAgIHJldHVybiB0cnVlOwogICAgZGVmYXVsdDoKICAgICAgcmV0dXJuIGZhbHNlOwogICAgfQogIH07CgogIE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZVN0dWIucHJvdG90eXBlLmFjY2VwdFdpdGhSZXNwb25kZXIgPQogICAgICBmdW5jdGlvbihtZXNzYWdlLCByZXNwb25kZXIpIHsKICAgIHZhciByZWFkZXIgPSBuZXcgY29kZWMuTWVzc2FnZVJlYWRlcihtZXNzYWdlKTsKICAgIHN3aXRjaCAocmVhZGVyLm1lc3NhZ2VOYW1lKSB7CiAgICBkZWZhdWx0OgogICAgICByZXR1cm4gZmFsc2U7CiAgICB9CiAgfTsKCiAgZnVuY3Rpb24gdmFsaWRhdGVNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VSZXF1ZXN0KG1lc3NhZ2VWYWxpZGF0b3IpIHsKICAgIHZhciBtZXNzYWdlID0gbWVzc2FnZVZhbGlkYXRvci5tZXNzYWdlOwogICAgdmFyIHBhcmFtc0NsYXNzID0gbnVsbDsKICAgIHN3aXRjaCAobWVzc2FnZS5nZXROYW1lKCkpIHsKICAgICAgY2FzZSBrTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlX09uU2lua0F2YWlsYWJsZV9OYW1lOgogICAgICAgIGlmICghbWVzc2FnZS5leHBlY3RzUmVzcG9uc2UoKSAmJiAhbWVzc2FnZS5pc1Jlc3BvbnNlKCkpCiAgICAgICAgICBwYXJhbXNDbGFzcyA9IE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9PblNpbmtBdmFpbGFibGVfUGFyYW1zOwogICAgICBicmVhazsKICAgICAgY2FzZSBrTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlX09uTWVzc2FnZUZyb21TaW5rX05hbWU6CiAgICAgICAgaWYgKCFtZXNzYWdlLmV4cGVjdHNSZXNwb25zZSgpICYmICFtZXNzYWdlLmlzUmVzcG9uc2UoKSkKICAgICAgICAgIHBhcmFtc0NsYXNzID0gTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlX09uTWVzc2FnZUZyb21TaW5rX1BhcmFtczsKICAgICAgYnJlYWs7CiAgICAgIGNhc2Uga01pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9PblN0b3BwZWRfTmFtZToKICAgICAgICBpZiAoIW1lc3NhZ2UuZXhwZWN0c1Jlc3BvbnNlKCkgJiYgIW1lc3NhZ2UuaXNSZXNwb25zZSgpKQogICAgICAgICAgcGFyYW1zQ2xhc3MgPSBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VfT25TdG9wcGVkX1BhcmFtczsKICAgICAgYnJlYWs7CiAgICAgIGNhc2Uga01pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZV9PbkVycm9yX05hbWU6CiAgICAgICAgaWYgKCFtZXNzYWdlLmV4cGVjdHNSZXNwb25zZSgpICYmICFtZXNzYWdlLmlzUmVzcG9uc2UoKSkKICAgICAgICAgIHBhcmFtc0NsYXNzID0gTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlX09uRXJyb3JfUGFyYW1zOwogICAgICBicmVhazsKICAgIH0KICAgIGlmIChwYXJhbXNDbGFzcyA9PT0gbnVsbCkKICAgICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORTsKICAgIHJldHVybiBwYXJhbXNDbGFzcy52YWxpZGF0ZShtZXNzYWdlVmFsaWRhdG9yLCBtZXNzYWdlVmFsaWRhdG9yLm1lc3NhZ2UuZ2V0SGVhZGVyTnVtQnl0ZXMoKSk7CiAgfQoKICBmdW5jdGlvbiB2YWxpZGF0ZU1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZVJlc3BvbnNlKG1lc3NhZ2VWYWxpZGF0b3IpIHsKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CiAgfQoKICB2YXIgTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlID0gewogICAgbmFtZTogJ21lZGlhOjptb2pvbTo6TWlycm9yU2VydmljZVJlbW90aW5nU291cmNlJywKICAgIGtWZXJzaW9uOiAwLAogICAgcHRyQ2xhc3M6IE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZVB0ciwKICAgIHByb3h5Q2xhc3M6IE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZVByb3h5LAogICAgc3R1YkNsYXNzOiBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VTdHViLAogICAgdmFsaWRhdGVSZXF1ZXN0OiB2YWxpZGF0ZU1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZVJlcXVlc3QsCiAgICB2YWxpZGF0ZVJlc3BvbnNlOiBudWxsLAogIH07CiAgTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlU3R1Yi5wcm90b3R5cGUudmFsaWRhdG9yID0gdmFsaWRhdGVNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VSZXF1ZXN0OwogIE1pcnJvclNlcnZpY2VSZW1vdGluZ1NvdXJjZVByb3h5LnByb3RvdHlwZS52YWxpZGF0b3IgPSBudWxsOwogIGV4cG9ydHMuTWlycm9yU2VydmljZVJlbW90ZXIgPSBNaXJyb3JTZXJ2aWNlUmVtb3RlcjsKICBleHBvcnRzLk1pcnJvclNlcnZpY2VSZW1vdGVyUHRyID0gTWlycm9yU2VydmljZVJlbW90ZXJQdHI7CiAgZXhwb3J0cy5NaXJyb3JTZXJ2aWNlUmVtb3RlckFzc29jaWF0ZWRQdHIgPSBNaXJyb3JTZXJ2aWNlUmVtb3RlckFzc29jaWF0ZWRQdHI7CiAgZXhwb3J0cy5NaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2UgPSBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2U7CiAgZXhwb3J0cy5NaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VQdHIgPSBNaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VQdHI7CiAgZXhwb3J0cy5NaXJyb3JTZXJ2aWNlUmVtb3RpbmdTb3VyY2VBc3NvY2lhdGVkUHRyID0gTWlycm9yU2VydmljZVJlbW90aW5nU291cmNlQXNzb2NpYXRlZFB0cjsKfSkoKTsvLyBDb3B5cmlnaHQgMjAxNCBUaGUgQ2hyb21pdW0gQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KLy8gVXNlIG9mIHRoaXMgc291cmNlIGNvZGUgaXMgZ292ZXJuZWQgYnkgYSBCU0Qtc3R5bGUgbGljZW5zZSB0aGF0IGNhbiBiZQovLyBmb3VuZCBpbiB0aGUgTElDRU5TRSBmaWxlLgoKJ3VzZSBzdHJpY3QnOwoKKGZ1bmN0aW9uKCkgewogIHZhciBtb2pvbUlkID0gJ21lZGlhL21vam8vaW50ZXJmYWNlcy9yZW1vdGluZ19jb21tb24ubW9qb20nOwogIGlmIChtb2pvLmludGVybmFsLmlzTW9qb21Mb2FkZWQobW9qb21JZCkpIHsKICAgIGNvbnNvbGUud2FybignVGhlIGZvbGxvd2luZyBtb2pvbSBpcyBsb2FkZWQgbXVsdGlwbGUgdGltZXM6ICcgKyBtb2pvbUlkKTsKICAgIHJldHVybjsKICB9CiAgbW9qby5pbnRlcm5hbC5tYXJrTW9qb21Mb2FkZWQobW9qb21JZCk7CiAgdmFyIGJpbmRpbmdzID0gbW9qbzsKICB2YXIgYXNzb2NpYXRlZEJpbmRpbmdzID0gbW9qbzsKICB2YXIgY29kZWMgPSBtb2pvLmludGVybmFsOwogIHZhciB2YWxpZGF0b3IgPSBtb2pvLmludGVybmFsOwoKICB2YXIgZXhwb3J0cyA9IG1vam8uaW50ZXJuYWwuZXhwb3NlTmFtZXNwYWNlKCdtZWRpYS5tb2pvbScpOwoKCiAgdmFyIFJlbW90aW5nU3RvcFJlYXNvbiA9IHt9OwogIFJlbW90aW5nU3RvcFJlYXNvbi5ST1VURV9URVJNSU5BVEVEID0gMDsKICBSZW1vdGluZ1N0b3BSZWFzb24uTE9DQUxfUExBWUJBQ0sgPSBSZW1vdGluZ1N0b3BSZWFzb24uUk9VVEVfVEVSTUlOQVRFRCArIDE7CiAgUmVtb3RpbmdTdG9wUmVhc29uLlNPVVJDRV9HT05FID0gUmVtb3RpbmdTdG9wUmVhc29uLkxPQ0FMX1BMQVlCQUNLICsgMTsKICBSZW1vdGluZ1N0b3BSZWFzb24uTUVTU0FHRV9TRU5EX0ZBSUxFRCA9IFJlbW90aW5nU3RvcFJlYXNvbi5TT1VSQ0VfR09ORSArIDE7CiAgUmVtb3RpbmdTdG9wUmVhc29uLkRBVEFfU0VORF9GQUlMRUQgPSBSZW1vdGluZ1N0b3BSZWFzb24uTUVTU0FHRV9TRU5EX0ZBSUxFRCArIDE7CiAgUmVtb3RpbmdTdG9wUmVhc29uLlVORVhQRUNURURfRkFJTFVSRSA9IFJlbW90aW5nU3RvcFJlYXNvbi5EQVRBX1NFTkRfRkFJTEVEICsgMTsKICBSZW1vdGluZ1N0b3BSZWFzb24uU0VSVklDRV9HT05FID0gUmVtb3RpbmdTdG9wUmVhc29uLlVORVhQRUNURURfRkFJTFVSRSArIDE7CiAgUmVtb3RpbmdTdG9wUmVhc29uLlVTRVJfRElTQUJMRUQgPSBSZW1vdGluZ1N0b3BSZWFzb24uU0VSVklDRV9HT05FICsgMTsKCiAgUmVtb3RpbmdTdG9wUmVhc29uLmlzS25vd25FbnVtVmFsdWUgPSBmdW5jdGlvbih2YWx1ZSkgewogICAgc3dpdGNoICh2YWx1ZSkgewogICAgY2FzZSAwOgogICAgY2FzZSAxOgogICAgY2FzZSAyOgogICAgY2FzZSAzOgogICAgY2FzZSA0OgogICAgY2FzZSA1OgogICAgY2FzZSA2OgogICAgY2FzZSA3OgogICAgICByZXR1cm4gdHJ1ZTsKICAgIH0KICAgIHJldHVybiBmYWxzZTsKICB9OwoKICBSZW1vdGluZ1N0b3BSZWFzb24udmFsaWRhdGUgPSBmdW5jdGlvbihlbnVtVmFsdWUpIHsKICAgIHZhciBpc0V4dGVuc2libGUgPSBmYWxzZTsKICAgIGlmIChpc0V4dGVuc2libGUgfHwgdGhpcy5pc0tub3duRW51bVZhbHVlKGVudW1WYWx1ZSkpCiAgICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuVU5LTk9XTl9FTlVNX1ZBTFVFOwogIH07CiAgdmFyIFJlbW90aW5nU3RhcnRGYWlsUmVhc29uID0ge307CiAgUmVtb3RpbmdTdGFydEZhaWxSZWFzb24uQ0FOTk9UX1NUQVJUX01VTFRJUExFID0gMDsKICBSZW1vdGluZ1N0YXJ0RmFpbFJlYXNvbi5ST1VURV9URVJNSU5BVEVEID0gUmVtb3RpbmdTdGFydEZhaWxSZWFzb24uQ0FOTk9UX1NUQVJUX01VTFRJUExFICsgMTsKICBSZW1vdGluZ1N0YXJ0RmFpbFJlYXNvbi5TRVJWSUNFX05PVF9DT05ORUNURUQgPSBSZW1vdGluZ1N0YXJ0RmFpbFJlYXNvbi5ST1VURV9URVJNSU5BVEVEICsgMTsKCiAgUmVtb3RpbmdTdGFydEZhaWxSZWFzb24uaXNLbm93bkVudW1WYWx1ZSA9IGZ1bmN0aW9uKHZhbHVlKSB7CiAgICBzd2l0Y2ggKHZhbHVlKSB7CiAgICBjYXNlIDA6CiAgICBjYXNlIDE6CiAgICBjYXNlIDI6CiAgICAgIHJldHVybiB0cnVlOwogICAgfQogICAgcmV0dXJuIGZhbHNlOwogIH07CgogIFJlbW90aW5nU3RhcnRGYWlsUmVhc29uLnZhbGlkYXRlID0gZnVuY3Rpb24oZW51bVZhbHVlKSB7CiAgICB2YXIgaXNFeHRlbnNpYmxlID0gZmFsc2U7CiAgICBpZiAoaXNFeHRlbnNpYmxlIHx8IHRoaXMuaXNLbm93bkVudW1WYWx1ZShlbnVtVmFsdWUpKQogICAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLlVOS05PV05fRU5VTV9WQUxVRTsKICB9OwogIHZhciBSZW1vdGluZ1NpbmtGZWF0dXJlID0ge307CiAgUmVtb3RpbmdTaW5rRmVhdHVyZS5SRU5ERVJJTkcgPSAwOwogIFJlbW90aW5nU2lua0ZlYXR1cmUuQ09OVEVOVF9ERUNSWVBUSU9OID0gUmVtb3RpbmdTaW5rRmVhdHVyZS5SRU5ERVJJTkcgKyAxOwoKICBSZW1vdGluZ1NpbmtGZWF0dXJlLmlzS25vd25FbnVtVmFsdWUgPSBmdW5jdGlvbih2YWx1ZSkgewogICAgc3dpdGNoICh2YWx1ZSkgewogICAgY2FzZSAwOgogICAgY2FzZSAxOgogICAgICByZXR1cm4gdHJ1ZTsKICAgIH0KICAgIHJldHVybiBmYWxzZTsKICB9OwoKICBSZW1vdGluZ1NpbmtGZWF0dXJlLnZhbGlkYXRlID0gZnVuY3Rpb24oZW51bVZhbHVlKSB7CiAgICB2YXIgaXNFeHRlbnNpYmxlID0gZmFsc2U7CiAgICBpZiAoaXNFeHRlbnNpYmxlIHx8IHRoaXMuaXNLbm93bkVudW1WYWx1ZShlbnVtVmFsdWUpKQogICAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwoKICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLlVOS05PV05fRU5VTV9WQUxVRTsKICB9OwogIHZhciBSZW1vdGluZ1NpbmtBdWRpb0NhcGFiaWxpdHkgPSB7fTsKICBSZW1vdGluZ1NpbmtBdWRpb0NhcGFiaWxpdHkuQ09ERUNfQkFTRUxJTkVfU0VUID0gMDsKICBSZW1vdGluZ1NpbmtBdWRpb0NhcGFiaWxpdHkuQ09ERUNfQUFDID0gUmVtb3RpbmdTaW5rQXVkaW9DYXBhYmlsaXR5LkNPREVDX0JBU0VMSU5FX1NFVCArIDE7CiAgUmVtb3RpbmdTaW5rQXVkaW9DYXBhYmlsaXR5LkNPREVDX09QVVMgPSBSZW1vdGluZ1NpbmtBdWRpb0NhcGFiaWxpdHkuQ09ERUNfQUFDICsgMTsKCiAgUmVtb3RpbmdTaW5rQXVkaW9DYXBhYmlsaXR5LmlzS25vd25FbnVtVmFsdWUgPSBmdW5jdGlvbih2YWx1ZSkgewogICAgc3dpdGNoICh2YWx1ZSkgewogICAgY2FzZSAwOgogICAgY2FzZSAxOgogICAgY2FzZSAyOgogICAgICByZXR1cm4gdHJ1ZTsKICAgIH0KICAgIHJldHVybiBmYWxzZTsKICB9OwoKICBSZW1vdGluZ1NpbmtBdWRpb0NhcGFiaWxpdHkudmFsaWRhdGUgPSBmdW5jdGlvbihlbnVtVmFsdWUpIHsKICAgIHZhciBpc0V4dGVuc2libGUgPSBmYWxzZTsKICAgIGlmIChpc0V4dGVuc2libGUgfHwgdGhpcy5pc0tub3duRW51bVZhbHVlKGVudW1WYWx1ZSkpCiAgICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuVU5LTk9XTl9FTlVNX1ZBTFVFOwogIH07CiAgdmFyIFJlbW90aW5nU2lua1ZpZGVvQ2FwYWJpbGl0eSA9IHt9OwogIFJlbW90aW5nU2lua1ZpZGVvQ2FwYWJpbGl0eS5TVVBQT1JUXzRLID0gMDsKICBSZW1vdGluZ1NpbmtWaWRlb0NhcGFiaWxpdHkuQ09ERUNfQkFTRUxJTkVfU0VUID0gUmVtb3RpbmdTaW5rVmlkZW9DYXBhYmlsaXR5LlNVUFBPUlRfNEsgKyAxOwogIFJlbW90aW5nU2lua1ZpZGVvQ2FwYWJpbGl0eS5DT0RFQ19IMjY0ID0gUmVtb3RpbmdTaW5rVmlkZW9DYXBhYmlsaXR5LkNPREVDX0JBU0VMSU5FX1NFVCArIDE7CiAgUmVtb3RpbmdTaW5rVmlkZW9DYXBhYmlsaXR5LkNPREVDX1ZQOCA9IFJlbW90aW5nU2lua1ZpZGVvQ2FwYWJpbGl0eS5DT0RFQ19IMjY0ICsgMTsKICBSZW1vdGluZ1NpbmtWaWRlb0NhcGFiaWxpdHkuQ09ERUNfVlA5ID0gUmVtb3RpbmdTaW5rVmlkZW9DYXBhYmlsaXR5LkNPREVDX1ZQOCArIDE7CiAgUmVtb3RpbmdTaW5rVmlkZW9DYXBhYmlsaXR5LkNPREVDX0hFVkMgPSBSZW1vdGluZ1NpbmtWaWRlb0NhcGFiaWxpdHkuQ09ERUNfVlA5ICsgMTsKCiAgUmVtb3RpbmdTaW5rVmlkZW9DYXBhYmlsaXR5LmlzS25vd25FbnVtVmFsdWUgPSBmdW5jdGlvbih2YWx1ZSkgewogICAgc3dpdGNoICh2YWx1ZSkgewogICAgY2FzZSAwOgogICAgY2FzZSAxOgogICAgY2FzZSAyOgogICAgY2FzZSAzOgogICAgY2FzZSA0OgogICAgY2FzZSA1OgogICAgICByZXR1cm4gdHJ1ZTsKICAgIH0KICAgIHJldHVybiBmYWxzZTsKICB9OwoKICBSZW1vdGluZ1NpbmtWaWRlb0NhcGFiaWxpdHkudmFsaWRhdGUgPSBmdW5jdGlvbihlbnVtVmFsdWUpIHsKICAgIHZhciBpc0V4dGVuc2libGUgPSBmYWxzZTsKICAgIGlmIChpc0V4dGVuc2libGUgfHwgdGhpcy5pc0tub3duRW51bVZhbHVlKGVudW1WYWx1ZSkpCiAgICAgIHJldHVybiB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkU7CgogICAgcmV0dXJuIHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuVU5LTk9XTl9FTlVNX1ZBTFVFOwogIH07CgogIGZ1bmN0aW9uIFJlbW90aW5nU2lua01ldGFkYXRhKHZhbHVlcykgewogICAgdGhpcy5pbml0RGVmYXVsdHNfKCk7CiAgICB0aGlzLmluaXRGaWVsZHNfKHZhbHVlcyk7CiAgfQoKCiAgUmVtb3RpbmdTaW5rTWV0YWRhdGEucHJvdG90eXBlLmluaXREZWZhdWx0c18gPSBmdW5jdGlvbigpIHsKICAgIHRoaXMuZmVhdHVyZXMgPSBudWxsOwogICAgdGhpcy5hdWRpb0NhcGFiaWxpdGllcyA9IG51bGw7CiAgICB0aGlzLnZpZGVvQ2FwYWJpbGl0aWVzID0gbnVsbDsKICAgIHRoaXMuZnJpZW5kbHlOYW1lID0gbnVsbDsKICB9OwogIFJlbW90aW5nU2lua01ldGFkYXRhLnByb3RvdHlwZS5pbml0RmllbGRzXyA9IGZ1bmN0aW9uKGZpZWxkcykgewogICAgZm9yKHZhciBmaWVsZCBpbiBmaWVsZHMpIHsKICAgICAgICBpZiAodGhpcy5oYXNPd25Qcm9wZXJ0eShmaWVsZCkpCiAgICAgICAgICB0aGlzW2ZpZWxkXSA9IGZpZWxkc1tmaWVsZF07CiAgICB9CiAgfTsKCiAgUmVtb3RpbmdTaW5rTWV0YWRhdGEudmFsaWRhdGUgPSBmdW5jdGlvbihtZXNzYWdlVmFsaWRhdG9yLCBvZmZzZXQpIHsKICAgIHZhciBlcnI7CiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlU3RydWN0SGVhZGVyKG9mZnNldCwgY29kZWMua1N0cnVjdEhlYWRlclNpemUpOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgogICAgdmFyIGtWZXJzaW9uU2l6ZXMgPSBbCiAgICAgIHt2ZXJzaW9uOiAwLCBudW1CeXRlczogNDB9CiAgICBdOwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cnVjdFZlcnNpb24ob2Zmc2V0LCBrVmVyc2lvblNpemVzKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBSZW1vdGluZ1NpbmtNZXRhZGF0YS5mZWF0dXJlcwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZUFycmF5UG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDAsIDQsIG5ldyBjb2RlYy5FbnVtKFJlbW90aW5nU2lua0ZlYXR1cmUpLCBmYWxzZSwgWzBdLCAwKTsKICAgIGlmIChlcnIgIT09IHZhbGlkYXRvci52YWxpZGF0aW9uRXJyb3IuTk9ORSkKICAgICAgICByZXR1cm4gZXJyOwoKCiAgICAvLyB2YWxpZGF0ZSBSZW1vdGluZ1NpbmtNZXRhZGF0YS5hdWRpb0NhcGFiaWxpdGllcwogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZUFycmF5UG9pbnRlcihvZmZzZXQgKyBjb2RlYy5rU3RydWN0SGVhZGVyU2l6ZSArIDgsIDQsIG5ldyBjb2RlYy5FbnVtKFJlbW90aW5nU2lua0F1ZGlvQ2FwYWJpbGl0eSksIGZhbHNlLCBbMF0sIDApOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIFJlbW90aW5nU2lua01ldGFkYXRhLnZpZGVvQ2FwYWJpbGl0aWVzCiAgICBlcnIgPSBtZXNzYWdlVmFsaWRhdG9yLnZhbGlkYXRlQXJyYXlQb2ludGVyKG9mZnNldCArIGNvZGVjLmtTdHJ1Y3RIZWFkZXJTaXplICsgMTYsIDQsIG5ldyBjb2RlYy5FbnVtKFJlbW90aW5nU2lua1ZpZGVvQ2FwYWJpbGl0eSksIGZhbHNlLCBbMF0sIDApOwogICAgaWYgKGVyciAhPT0gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FKQogICAgICAgIHJldHVybiBlcnI7CgoKICAgIC8vIHZhbGlkYXRlIFJlbW90aW5nU2lua01ldGFkYXRhLmZyaWVuZGx5TmFtZQogICAgZXJyID0gbWVzc2FnZVZhbGlkYXRvci52YWxpZGF0ZVN0cmluZ1BvaW50ZXIob2Zmc2V0ICsgY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAyNCwgZmFsc2UpCiAgICBpZiAoZXJyICE9PSB2YWxpZGF0b3IudmFsaWRhdGlvbkVycm9yLk5PTkUpCiAgICAgICAgcmV0dXJuIGVycjsKCiAgICByZXR1cm4gdmFsaWRhdG9yLnZhbGlkYXRpb25FcnJvci5OT05FOwogIH07CgogIFJlbW90aW5nU2lua01ldGFkYXRhLmVuY29kZWRTaXplID0gY29kZWMua1N0cnVjdEhlYWRlclNpemUgKyAzMjsKCiAgUmVtb3RpbmdTaW5rTWV0YWRhdGEuZGVjb2RlID0gZnVuY3Rpb24oZGVjb2RlcikgewogICAgdmFyIHBhY2tlZDsKICAgIHZhciB2YWwgPSBuZXcgUmVtb3RpbmdTaW5rTWV0YWRhdGEoKTsKICAgIHZhciBudW1iZXJPZkJ5dGVzID0gZGVjb2Rlci5yZWFkVWludDMyKCk7CiAgICB2YXIgdmVyc2lvbiA9IGRlY29kZXIucmVhZFVpbnQzMigpOwogICAgdmFsLmZlYXR1cmVzID0gZGVjb2Rlci5kZWNvZGVBcnJheVBvaW50ZXIobmV3IGNvZGVjLkVudW0oUmVtb3RpbmdTaW5rRmVhdHVyZSkpOwogICAgdmFsLmF1ZGlvQ2FwYWJpbGl0aWVzID0gZGVjb2Rlci5kZWNvZGVBcnJheVBvaW50ZXIobmV3IGNvZGVjLkVudW0oUmVtb3RpbmdTaW5rQXVkaW9DYXBhYmlsaXR5KSk7CiAgICB2YWwudmlkZW9DYXBhYmlsaXRpZXMgPSBkZWNvZGVyLmRlY29kZUFycmF5UG9pbnRlcihuZXcgY29kZWMuRW51bShSZW1vdGluZ1NpbmtWaWRlb0NhcGFiaWxpdHkpKTsKICAgIHZhbC5mcmllbmRseU5hbWUgPSBkZWNvZGVyLmRlY29kZVN0cnVjdChjb2RlYy5TdHJpbmcpOwogICAgcmV0dXJuIHZhbDsKICB9OwoKICBSZW1vdGluZ1NpbmtNZXRhZGF0YS5lbmNvZGUgPSBmdW5jdGlvbihlbmNvZGVyLCB2YWwpIHsKICAgIHZhciBwYWNrZWQ7CiAgICBlbmNvZGVyLndyaXRlVWludDMyKFJlbW90aW5nU2lua01ldGFkYXRhLmVuY29kZWRTaXplKTsKICAgIGVuY29kZXIud3JpdGVVaW50MzIoMCk7CiAgICBlbmNvZGVyLmVuY29kZUFycmF5UG9pbnRlcihuZXcgY29kZWMuRW51bShSZW1vdGluZ1NpbmtGZWF0dXJlKSwgdmFsLmZlYXR1cmVzKTsKICAgIGVuY29kZXIuZW5jb2RlQXJyYXlQb2ludGVyKG5ldyBjb2RlYy5FbnVtKFJlbW90aW5nU2lua0F1ZGlvQ2FwYWJpbGl0eSksIHZhbC5hdWRpb0NhcGFiaWxpdGllcyk7CiAgICBlbmNvZGVyLmVuY29kZUFycmF5UG9pbnRlcihuZXcgY29kZWMuRW51bShSZW1vdGluZ1NpbmtWaWRlb0Nh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