LyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqDQoqIENvcHlyaWdodCAoQykgMjAxNiBieSBTYXZvaXItZmFpcmUgTGludXggICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICoNCiogQXV0aG9yOiBK5GdlciBOaWNvbGFzIDxuaWNvbGFzLmphZ2VyQHNhdm9pcmZhaXJlbGludXguY29tPiAgICAgICAgICAgICAgKg0KKiBBdXRob3I6IFRyYWN6eWsgQW5kcmVhcyA8YW5kcmVhcy50cmFjenlrQHNhdm9pcmZhaXJlbGludXguY29tPiAgICAgICAgICAqDQoqICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICoNCiogVGhpcyBwcm9ncmFtIGlzIGZyZWUgc29mdHdhcmU7IHlvdSBjYW4gcmVkaXN0cmlidXRlIGl0IGFuZC9vciBtb2RpZnkgICAgKg0KKiBpdCB1bmRlciB0aGUgdGVybXMgb2YgdGhlIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlIGFzIHB1Ymxpc2hlZCBieSAgICAqDQoqIHRoZSBGcmVlIFNvZnR3YXJlIEZvdW5kYXRpb247IGVpdGhlciB2ZXJzaW9uIDMgb2YgdGhlIExpY2Vuc2UsIG9yICAgICAgICoNCiogKGF0IHlvdXIgb3B0aW9uKSBhbnkgbGF0ZXIgdmVyc2lvbi4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKg0KKiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAqDQoqIFRoaXMgcHJvZ3JhbSBpcyBkaXN0cmlidXRlZCBpbiB0aGUgaG9wZSB0aGF0IGl0IHdpbGwgYmUgdXNlZnVsLCAgICAgICAgICoNCiogYnV0IFdJVEhPVVQgQU5ZIFdBUlJBTlRZOyB3aXRob3V0IGV2ZW4gdGhlIGltcGxpZWQgd2FycmFudHkgb2YgICAgICAgICAgKg0KKiBNRVJDSEFOVEFCSUxJVFkgb3IgRklUTkVTUyBGT1IgQSBQQVJUSUNVTEFSIFBVUlBPU0UuICBTZWUgdGhlICAgICAgICAgICAqDQoqIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlIGZvciBtb3JlIGRldGFpbHMuICAgICAgICAgICAgICAgICAgICAgICAgICAgICoNCiogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKg0KKiBZb3Ugc2hvdWxkIGhhdmUgcmVjZWl2ZWQgYSBjb3B5IG9mIHRoZSBHTlUgR2VuZXJhbCBQdWJsaWMgTGljZW5zZSAgICAgICAqDQoqIGFsb25nIHdpdGggdGhpcyBwcm9ncmFtLiAgSWYgbm90LCBzZWUgPGh0dHA6Ly93d3cuZ251Lm9yZy9saWNlbnNlcy8+LiAgICoNCioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLw0KI2luY2x1ZGUgInBjaC5oIg0KDQojaW5jbHVkZSAiVmlkZW9QYWdlLnhhbWwuaCINCg0KI2luY2x1ZGUgPE1lbW9yeUJ1ZmZlci5oPiAgIC8vIElNZW1vcnlCdWZmZXJCeXRlQWNjZXNzDQoNCnVzaW5nIG5hbWVzcGFjZSBSaW5nQ2xpZW50VVdQOjpWaWV3czsNCnVzaW5nIG5hbWVzcGFjZSBWaWV3TW9kZWw7DQp1c2luZyBuYW1lc3BhY2UgVmlkZW87DQoNCnVzaW5nIG5hbWVzcGFjZSBDb25jdXJyZW5jeTsNCnVzaW5nIG5hbWVzcGFjZSBQbGF0Zm9ybTsNCnVzaW5nIG5hbWVzcGFjZSBXaW5kb3dzOjpEZXZpY2VzOjpFbnVtZXJhdGlvbjsNCnVzaW5nIG5hbWVzcGFjZSBXaW5kb3dzOjpGb3VuZGF0aW9uOw0KdXNpbmcgbmFtZXNwYWNlIFdpbmRvd3M6OkZvdW5kYXRpb246OkNvbGxlY3Rpb25zOw0KdXNpbmcgbmFtZXNwYWNlIFdpbmRvd3M6OlVJOjpYYW1sOw0KdXNpbmcgbmFtZXNwYWNlIFdpbmRvd3M6OlVJOjpYYW1sOjpDb250cm9sczsNCnVzaW5nIG5hbWVzcGFjZSBXaW5kb3dzOjpVSTo6WGFtbDo6Q29udHJvbHM6OlByaW1pdGl2ZXM7DQp1c2luZyBuYW1lc3BhY2UgV2luZG93czo6VUk6OlhhbWw6OkRhdGE7DQp1c2luZyBuYW1lc3BhY2UgV2luZG93czo6VUk6OlhhbWw6OklucHV0Ow0KdXNpbmcgbmFtZXNwYWNlIFdpbmRvd3M6OlVJOjpYYW1sOjpNZWRpYTsNCnVzaW5nIG5hbWVzcGFjZSBXaW5kb3dzOjpVSTo6WGFtbDo6TmF2aWdhdGlvbjsNCnVzaW5nIG5hbWVzcGFjZSBXaW5kb3dzOjpNZWRpYTo6Q2FwdHVyZTsNCnVzaW5nIG5hbWVzcGFjZSBXaW5kb3dzOjpBcHBsaWNhdGlvbk1vZGVsOjpDb3JlOw0KdXNpbmcgbmFtZXNwYWNlIFdpbmRvd3M6OlVJOjpDb3JlOw0KDQp1c2luZyBuYW1lc3BhY2UgV2luZG93czo6R3JhcGhpY3M6OkRpc3BsYXk7DQp1c2luZyBuYW1lc3BhY2UgV2luZG93czo6R3JhcGhpY3M6OkltYWdpbmc7DQp1c2luZyBuYW1lc3BhY2UgV2luZG93czo6TWVkaWE7DQp1c2luZyBuYW1lc3BhY2UgV2luZG93czo6VUk6OlhhbWw6Ok1lZGlhOjpJbWFnaW5nOw0KdXNpbmcgbmFtZXNwYWNlIFdpbmRvd3M6Ok1lZGlhOjpDYXB0dXJlOw0KdXNpbmcgbmFtZXNwYWNlIFdpbmRvd3M6OkRldmljZXM6OlNlbnNvcnM7DQoNClZpZGVvUGFnZTo6VmlkZW9QYWdlKCkNCnsNCiAgICBJbml0aWFsaXplQ29tcG9uZW50KCk7DQoNCiAgICBWaWRlb01hbmFnZXI6Omluc3RhbmNlLT5jYXB0dXJlTWFuYWdlcigpLT5kaXNwbGF5SW5mb3JtYXRpb24gPSBEaXNwbGF5SW5mb3JtYXRpb246OkdldEZvckN1cnJlbnRWaWV3KCk7DQogICAgVmlkZW9NYW5hZ2VyOjppbnN0YW5jZS0+Y2FwdHVyZU1hbmFnZXIoKS0+RW51bWVyYXRlV2ViY2Ftc0FzeW5jKCk7DQoNCiAgICBQYWdlOjpOYXZpZ2F0aW9uQ2FjaGVNb2RlID0gTmF2aWdhdGlvbjo6TmF2aWdhdGlvbkNhY2hlTW9kZTo6UmVxdWlyZWQ7DQoNCiAgICBWaWRlb01hbmFnZXI6Omluc3RhbmNlLT5yZW5kZXJlck1hbmFnZXIoKS0+d3JpdGVWaWRlb0ZyYW1lICs9DQogICAgICAgIHJlZiBuZXcgV3JpdGVWaWRlb0ZyYW1lKFt0aGlzXShTdHJpbmdeIGlkLCB1aW50OF90KiBidWYsIGludCB3aWR0aCwgaW50IGhlaWdodCkNCiAgICB7DQogICAgICAgIENvcmVBcHBsaWNhdGlvbjo6TWFpblZpZXctPkNvcmVXaW5kb3ctPkRpc3BhdGNoZXItPlJ1bkFzeW5jKENvcmVEaXNwYXRjaGVyUHJpb3JpdHk6OkhpZ2gsDQogICAgICAgIHJlZiBuZXcgRGlzcGF0Y2hlZEhhbmRsZXIoWz1dKCkgew0KICAgICAgICAgICAgdHJ5IHsNCiAgICAgICAgICAgICAgICBpZiAoIVZpZGVvTWFuYWdlcjo6aW5zdGFuY2UtPnJlbmRlcmVyTWFuYWdlcigpLT5yZW5kZXJlcnMtPlNpemUpDQogICAgICAgICAgICAgICAgICAgIHJldHVybjsNCiAgICAgICAgICAgICAgICBWaWRlb01hbmFnZXI6Omluc3RhbmNlLT5yZW5kZXJlck1hbmFnZXIoKS0+cmVuZGVyZXIoaWQpLT5pc1JlbmRlcmluZyA9IHRydWU7DQogICAgICAgICAgICAgICAgY3JlYXRlX3Rhc2soV3JpdGVGcmFtZUFzU29mdHdhcmVCaXRtYXBBc3luYyhpZCwgYnVmLCB3aWR0aCwgaGVpZ2h0KSkNCiAgICAgICAgICAgICAgICAudGhlbihbPV0odGFzazx2b2lkPiBwcmV2aW91c1Rhc2spIHsNCiAgICAgICAgICAgICAgICAgICAgdHJ5IHsNCiAgICAgICAgICAgICAgICAgICAgICAgIHByZXZpb3VzVGFzay5nZXQoKTsNCiAgICAgICAgICAgICAgICAgICAgfQ0KICAgICAgICAgICAgICAgICAgICBjYXRjaCAoUGxhdGZvcm06OkV4Y2VwdGlvbl4gZSkgew0KICAgICAgICAgICAgICAgICAgICAgICAgUmluZ0RlYnVnOjppbnN0YW5jZS0+V3JpdGVMaW5lKCAiQ2F1Z2h0IGV4Y2VwdGlvbiBmcm9tIHByZXZpb3VzIHRhc2suXG4iICk7DQogICAgICAgICAgICAgICAgICAgIH0NCiAgICAgICAgICAgICAgICB9KTsNCiAgICAgICAgICAgIH0NCiAgICAgICAgICAgIGNhdGNoKFBsYXRmb3JtOjpDT01FeGNlcHRpb25eIGUpIHsNCiAgICAgICAgICAgICAgICBSaW5nRGVidWc6Omluc3RhbmNlLT5Xcml0ZUxpbmUoZS0+VG9TdHJpbmcoKSk7DQogICAgICAgICAgICB9DQogICAgICAgIH0pKTsNCiAgICB9KTsNCg0KICAgIFZpZGVvTWFuYWdlcjo6aW5zdGFuY2UtPmNhcHR1cmVNYW5hZ2VyKCktPnN0YXJ0UHJldmlld2luZyArPQ0KICAgICAgICByZWYgbmV3IFN0YXJ0UHJldmlld2luZyhbdGhpc10oKQ0KICAgIHsNCiAgICAgICAgUHJldmlld0ltYWdlLT5WaXNpYmlsaXR5ID0gV2luZG93czo6VUk6OlhhbWw6OlZpc2liaWxpdHk6OlZpc2libGU7DQogICAgICAgIFByZXZpZXdJbWFnZS0+Rmxvd0RpcmVjdGlvbiA9IFZpZGVvTWFuYWdlcjo6aW5zdGFuY2UtPmNhcHR1cmVNYW5hZ2VyKCktPm1pcnJvcmluZ1ByZXZpZXcgPw0KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBXaW5kb3dzOjpVSTo6WGFtbDo6Rmxvd0RpcmVjdGlvbjo6UmlnaHRUb0xlZnQgOg0KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBXaW5kb3dzOjpVSTo6WGFtbDo6Rmxvd0RpcmVjdGlvbjo6TGVmdFRvUmlnaHQ7DQogICAgfSk7DQoNCiAgICBWaWRlb01hbmFnZXI6Omluc3RhbmNlLT5jYXB0dXJlTWFuYWdlcigpLT5zdG9wUHJldmlld2luZyArPQ0KICAgICAgICByZWYgbmV3IFN0b3BQcmV2aWV3aW5nKFt0aGlzXSgpDQogICAgew0KICAgICAgICBQcmV2aWV3SW1hZ2UtPlNvdXJjZSA9IG51bGxwdHI7DQogICAgICAgIFByZXZpZXdJbWFnZS0+VmlzaWJpbGl0eSA9IFdpbmRvd3M6OlVJOjpYYW1sOjpWaXNpYmlsaXR5OjpDb2xsYXBzZWQ7DQogICAgfSk7DQoNCiAgICBWaWRlb01hbmFnZXI6Omluc3RhbmNlLT5jYXB0dXJlTWFuYWdlcigpLT5nZXRTaW5rICs9DQogICAgICAgIHJlZiBuZXcgR2V0U2luayhbdGhpc10oKQ0KICAgIHsNCiAgICAgICAgcmV0dXJuIFByZXZpZXdJbWFnZTsNCiAgICB9KTsNCg0KICAgIFZpZGVvTWFuYWdlcjo6aW5zdGFuY2UtPnJlbmRlcmVyTWFuYWdlcigpLT5jbGVhclJlbmRlclRhcmdldCArPQ0KICAgICAgICByZWYgbmV3IENsZWFyUmVuZGVyVGFyZ2V0KFt0aGlzXSgpDQogICAgew0KICAgICAgICBJbmNvbWluZ1ZpZGVvSW1hZ2UtPlNvdXJjZSA9IG51bGxwdHI7DQogICAgfSk7DQoNCiAgICBSaW5nRDo6aW5zdGFuY2UtPmluY29taW5nQWNjb3VudE1lc3NhZ2UgKz0NCiAgICAgICAgcmVmIG5ldyBJbmNvbWluZ0FjY291bnRNZXNzYWdlKFsmXShTdHJpbmdeIGFjY291bnRJZCwgU3RyaW5nXiBmcm9tLCBTdHJpbmdeIHBheWxvYWQpDQogICAgew0KICAgICAgICBzY3JvbGxEb3duKCk7DQogICAgfSk7DQoNCiAgICBSaW5nRDo6aW5zdGFuY2UtPnN0YXRlQ2hhbmdlICs9DQogICAgICAgIHJlZiBuZXcgU3RhdGVDaGFuZ2UoWyZdKFN0cmluZ14gY2FsbElkLCBDYWxsU3RhdHVzIHN0YXRlLCBpbnQgY29kZSkNCiAgICB7DQogICAgICAgIGlmIChzdGF0ZSA9PSBDYWxsU3RhdHVzOjpFTkRFRCkgew0KICAgICAgICAgICAgVmlkZW86OlZpZGVvTWFuYWdlcjo6aW5zdGFuY2UtPnJlbmRlcmVyTWFuYWdlcigpLT5yYWlzZUNsZWFyUmVuZGVyVGFyZ2V0KCk7DQogICAgICAgIH0NCiAgICB9KTsNCg0KICAgIFJpbmdEOjppbnN0YW5jZS0+aW5jb21pbmdNZXNzYWdlICs9IHJlZiBuZXcgUmluZ0NsaWVudFVXUDo6SW5jb21pbmdNZXNzYWdlKHRoaXMsICZSaW5nQ2xpZW50VVdQOjpWaWV3czo6VmlkZW9QYWdlOjpPbmluY29taW5nTWVzc2FnZSk7DQp9DQoNCnZvaWQNClJpbmdDbGllbnRVV1A6OlZpZXdzOjpWaWRlb1BhZ2U6Ok9uTmF2aWdhdGVkVG8oV2luZG93czo6VUk6OlhhbWw6Ok5hdmlnYXRpb246Ok5hdmlnYXRpb25FdmVudEFyZ3NeIGUpDQp7DQogICAgdXBkYXRlUGFnZUNvbnRlbnQoKTsNCn0NCg0Kdm9pZCBSaW5nQ2xpZW50VVdQOjpWaWV3czo6VmlkZW9QYWdlOjp1cGRhdGVQYWdlQ29udGVudCgpDQp7DQogICAgYXV0byBpdGVtID0gU21hcnRQYW5lbEl0ZW1zVmlld01vZGVsOjppbnN0YW5jZS0+X3NlbGVjdGVkSXRlbTsNCiAgICBhdXRvIGNvbnRhY3QgPSAoaXRlbSkgPyBpdGVtLT5fY29udGFjdCA6IG51bGxwdHI7DQoNCiAgICBpZiAoIWNvbnRhY3QpDQogICAgICAgIHJldHVybjsNCg0KICAgIF9jYWxsZWVfLT5UZXh0ID0gY29udGFjdC0+bmFtZV87DQoNCiAgICBfbWVzc2FnZXNMaXN0Xy0+SXRlbXNTb3VyY2UgPSBjb250YWN0LT5fY29udmVyc2F0aW9uLT5fbWVzc2FnZXM7DQoNCiAgICBzY3JvbGxEb3duKCk7DQp9DQoNCnZvaWQgUmluZ0NsaWVudFVXUDo6Vmlld3M6OlZpZGVvUGFnZTo6c2Nyb2xsRG93bigpDQp7DQogICAgX3Njcm9sbFZpZXdfLT5VcGRhdGVMYXlvdXQoKTsNCiAgICBfc2Nyb2xsVmlld18tPlNjcm9sbFRvVmVydGljYWxPZmZzZXQoX3Njcm9sbFZpZXdfLT5TY3JvbGxhYmxlSGVpZ2h0KTsNCn0NCg0Kdm9pZA0KUmluZ0NsaWVudFVXUDo6Vmlld3M6OlZpZGVvUGFnZTo6X3NlbmRCdG5fX0NsaWNrKFBsYXRmb3JtOjpPYmplY3ReIHNlbmRlciwgV2luZG93czo6VUk6OlhhbWw6OlJvdXRlZEV2ZW50QXJnc14gZSkNCnsNCiAgICBzZW5kTWVzc2FnZSgpOw0KfQ0KDQp2b2lkDQpSaW5nQ2xpZW50VVdQOjpWaWV3czo6VmlkZW9QYWdlOjpfbWVzc2FnZVRleHRCb3hfX0tleURvd24oUGxhdGZvcm06Ok9iamVjdF4gc2VuZGVyLCBXaW5kb3dzOjpVSTo6WGFtbDo6SW5wdXQ6OktleVJvdXRlZEV2ZW50QXJnc14gZSkNCnsNCiAgICBpZiAoZS0+S2V5ID09IFdpbmRvd3M6OlN5c3RlbTo6VmlydHVhbEtleTo6RW50ZXIpIHsNCiAgICAgICAgc2VuZE1lc3NhZ2UoKTsNCiAgICB9DQp9DQoNCnZvaWQNClJpbmdDbGllbnRVV1A6OlZpZXdzOjpWaWRlb1BhZ2U6OnNlbmRNZXNzYWdlKCkNCnsNCiAgICBhdXRvIGl0ZW0gPSBTbWFydFBhbmVsSXRlbXNWaWV3TW9kZWw6Omluc3RhbmNlLT5fc2VsZWN0ZWRJdGVtOw0KICAgIGF1dG8gY29udGFjdCA9IGl0ZW0tPl9jb250YWN0Ow0KDQogICAgYXV0byB0eHQgPSBfbWVzc2FnZVRleHRCb3hfLT5UZXh0Ow0KDQogICAgLyogZW1wdHkgdGhlIHRleHRib3ggKi8NCiAgICBfbWVzc2FnZVRleHRCb3hfLT5UZXh0ID0gIiI7DQoNCiAgICBpZiAoIWNvbnRhY3QgfHwgdHh0LT5Jc0VtcHR5KCkpDQogICAgICAgIHJldHVybjsNCg0KICAgIFJpbmdEOjppbnN0YW5jZS0+c2VuZFNJUFRleHRNZXNzYWdlKHR4dCk7DQogICAgc2Nyb2xsRG93bigpOw0KfQ0KDQp2b2lkIFJpbmdDbGllbnRVV1A6OlZpZXdzOjpWaWRlb1BhZ2U6OkJ1dHRvbl9DbGljayhQbGF0Zm9ybTo6T2JqZWN0XiBzZW5kZXIsIFdpbmRvd3M6OlVJOjpYYW1sOjpSb3V0ZWRFdmVudEFyZ3NeIGUpDQp7DQp9DQoNCg0Kdm9pZCBSaW5nQ2xpZW50VVdQOjpWaWV3czo6VmlkZW9QYWdlOjpfYnRuQ2FuY2VsX19DbGljayhQbGF0Zm9ybTo6T2JqZWN0XiBzZW5kZXIsIFdpbmRvd3M6OlVJOjpYYW1sOjpSb3V0ZWRFdmVudEFyZ3NeIGUpDQp7DQoNCn0NCg0Kdm9pZCBSaW5nQ2xpZW50VVdQOjpWaWV3czo6VmlkZW9QYWdlOjpfYnRuSGFuZ1VwX19UYXBwZWQoUGxhdGZvcm06Ok9iamVjdF4gc2VuZGVyLCBXaW5kb3dzOjpVSTo6WGFtbDo6SW5wdXQ6OlRhcHBlZFJvdXRlZEV2ZW50QXJnc14gZSkNCnsNCiAgICBhdXRvIGl0ZW0gPSBTbWFydFBhbmVsSXRlbXNWaWV3TW9kZWw6Omluc3RhbmNlLT5fc2VsZWN0ZWRJdGVtOw0KICAgIFJpbmdEOjppbnN0YW5jZS0+aGFuZ1VwQ2FsbDIoaXRlbS0+X2NhbGxJZCk7DQoNCiAgICBwcmVzc0hhbmdVcENhbGwoKTsNCn0NCg0KDQp2b2lkIFJpbmdDbGllbnRVV1A6OlZpZXdzOjpWaWRlb1BhZ2U6Ol9idG5QYXVzZV9fVGFwcGVkKFBsYXRmb3JtOjpPYmplY3ReIHNlbmRlciwgV2luZG93czo6VUk6OlhhbWw6OklucHV0OjpUYXBwZWRSb3V0ZWRFdmVudEFyZ3NeIGUpDQp7DQogICAgLyphdXRvIGl0ZW0gPSBTbWFydFBhbmVsSXRlbXNWaWV3TW9kZWw6Omluc3RhbmNlLT5fc2VsZWN0ZWRJdGVtOw0KICAgIGlmIChpdGVtLT5fY2FsbFN0YXR1cyA9PSBDYWxsU3RhdHVzOjpJTl9QUk9HUkVTUykNCiAgICAgICAgUmluZ0Q6Omluc3RhbmNlLT5wYXVzZUNhbGwoaXRlbS0+X2NhbGxJZCk7DQogICAgZWxzZSBpZiAoaXRlbS0+X2NhbGxTdGF0dXMgPT0gQ2FsbFN0YXR1czo6UEFVU0VEKQ0KICAgICAgICBSaW5nRDo6aW5zdGFuY2UtPnVuUGF1c2VDYWxsKGl0ZW0tPl9jYWxsSWQpOyovDQoNCiAgICBwYXVzZUNhbGwoKTsNCn0NCg0KDQp2b2lkIFJpbmdDbGllbnRVV1A6OlZpZXdzOjpWaWRlb1BhZ2U6Ol9idG5DaGF0X19UYXBwZWQoUGxhdGZvcm06Ok9iamVjdF4gc2VuZGVyLCBXaW5kb3dzOjpVSTo6WGFtbDo6SW5wdXQ6OlRhcHBlZFJvdXRlZEV2ZW50QXJnc14gZSkNCnsNCiAgICBjaGF0T3BlbiA9ICFjaGF0T3BlbjsNCiAgICBpZiAoY2hhdE9wZW4pIHsNCiAgICAgICAgX3Jvd0NoYXRCeF8tPkhlaWdodCA9IDIwMDsNCiAgICAgICAgY2hhdFBhbmVsQ2FsbCgpOw0KICAgIH0NCiAgICBlbHNlIHsNCiAgICAgICAgX3Jvd0NoYXRCeF8tPkhlaWdodCA9IDA7DQogICAgfQ0KfQ0KDQoNCnZvaWQgUmluZ0NsaWVudFVXUDo6Vmlld3M6OlZpZGVvUGFnZTo6X2J0bkFkZEZyaWVuZF9fVGFwcGVkKFBsYXRmb3JtOjpPYmplY3ReIHNlbmRlciwgV2luZG93czo6VUk6OlhhbWw6OklucHV0OjpUYXBwZWRSb3V0ZWRFdmVudEFyZ3NeIGUpDQp7DQogICAgYWRkQ29udGFjdENhbGwoKTsNCn0NCg0KDQp2b2lkIFJpbmdDbGllbnRVV1A6OlZpZXdzOjpWaWRlb1BhZ2U6Ol9idG5Td2l0Y2hfX1RhcHBlZChQbGF0Zm9ybTo6T2JqZWN0XiBzZW5kZXIsIFdpbmRvd3M6OlVJOjpYYW1sOjpJbnB1dDo6VGFwcGVkUm91dGVkRXZlbnRBcmdzXiBlKQ0Kew0KICAgIHRyYW5zZmVyQ2FsbCgpOw0KfQ0KDQoNCnZvaWQgUmluZ0NsaWVudFVXUDo6Vmlld3M6OlZpZGVvUGFnZTo6X2J0bk1pY3JvcGhvbmVfX1RhcHBlZChQbGF0Zm9ybTo6T2JqZWN0XiBzZW5kZXIsIFdpbmRvd3M6OlVJOjpYYW1sOjpJbnB1dDo6VGFwcGVkUm91dGVkRXZlbnRBcmdzXiBlKQ0Kew0KICAgIHN3aXRjaE1pY3JvcGhvbmVTdGF0ZUNhbGwoKTsNCn0NCg0KDQp2b2lkIFJpbmdDbGllbnRVV1A6OlZpZXdzOjpWaWRlb1BhZ2U6Ol9idG5NZW1vX19UYXBwZWQoUGxhdGZvcm06Ok9iamVjdF4gc2VuZGVyLCBXaW5kb3dzOjpVSTo6WGFtbDo6SW5wdXQ6OlRhcHBlZFJvdXRlZEV2ZW50QXJnc14gZSkNCnsNCiAgICByZWNjb3JkVmlkZW9DYWxsKCk7DQp9DQoNCg0Kdm9pZCBSaW5nQ2xpZW50VVdQOjpWaWV3czo6VmlkZW9QYWdlOjpfYnRuSFFfX1RhcHBlZChQbGF0Zm9ybTo6T2JqZWN0XiBzZW5kZXIsIFdpbmRvd3M6OlVJOjpYYW1sOjpJbnB1dDo6VGFwcGVkUm91dGVkRXZlbnRBcmdzXiBlKQ0Kew0KICAgIHF1YWxpdHlWaWRlb0xldmVsQ2FsbCgpOw0KfQ0KDQoNCnZvaWQgUmluZ0NsaWVudFVXUDo6Vmlld3M6OlZpZGVvUGFnZTo6X2J0blZpZGVvX19UYXBwZWQoUGxhdGZvcm06Ok9iamVjdF4gc2VuZGVyLCBXaW5kb3dzOjpVSTo6WGFtbDo6SW5wdXQ6OlRhcHBlZFJvdXRlZEV2ZW50QXJnc14gZSkNCnsNCiAgICBzd2l0Y2hWaWRlb1N0YXRlQ2FsbCgpOw0KfQ0KDQoNCnZvaWQgUmluZ0NsaWVudFVXUDo6Vmlld3M6OlZpZGVvUGFnZTo6X3ZpZGVvQ29udHJvbF9fUG9pbnRlck1vdmVkKFBsYXRmb3JtOjpPYmplY3ReIHNlbmRlciwgV2luZG93czo6VUk6OlhhbWw6OklucHV0OjpQb2ludGVyUm91dGVkRXZlbnRBcmdzXiBlKQ0Kew0KICAgIGlmIChiYXJGYWRpbmcpDQogICAgICAgIG15U3Rvcnlib2FyZC0+QmVnaW4oKTsNCiAgICBiYXJGYWRpbmdfID0gdHJ1ZTsNCn0NCg0KDQp2b2lkIFJpbmdDbGllbnRVV1A6OlZpZXdzOjpWaWRlb1BhZ2U6OmJ0bkFueV9lbnRlcmVkKFBsYXRmb3JtOjpPYmplY3ReIHNlbmRlciwgV2luZG93czo6VUk6OlhhbWw6OklucHV0OjpQb2ludGVyUm91dGVkRXZlbnRBcmdzXiBlKQ0Kew0KICAgIGJhckZhZGluZ18gPSBmYWxzZTsNCiAgICBteVN0b3J5Ym9hcmQtPlN0b3AoKTsNCn0NCg0KDQp2b2lkIFJpbmdDbGllbnRVV1A6OlZpZXdzOjpWaWRlb1BhZ2U6OmJ0bkFueV9leGl0ZWQoUGxhdGZvcm06Ok9iamVjdF4gc2VuZGVyLCBXaW5kb3dzOjpVSTo6WGFtbDo6SW5wdXQ6OlBvaW50ZXJSb3V0ZWRFdmVudEFyZ3NeIGUpDQp7DQogICAgYmFyRmFkaW5nXyA9IHRydWU7DQp9DQoNCnRhc2s8dm9pZD4NClZpZGVvUGFnZTo6V3JpdGVGcmFtZUFzU29mdHdhcmVCaXRtYXBBc3luYyhTdHJpbmdeIGlkLCB1aW50OF90KiBidWYsIGludCB3aWR0aCwgaW50IGhlaWdodCkNCnsNCiAgICBhdXRvIHZmcmFtZSA9IHJlZiBuZXcgVmlkZW9GcmFtZShCaXRtYXBQaXhlbEZvcm1hdDo6QmdyYTgsIHdpZHRoLCBoZWlnaHQpOw0KICAgIGF1dG8gZnJhbWUgPSB2ZnJhbWUtPlNvZnR3YXJlQml0bWFwOw0KDQogICAgY29uc3QgaW50IEJZVEVTX1BFUl9QSVhFTCA9IDQ7DQoNCiAgICBCaXRtYXBCdWZmZXJeIGJ1ZmZlciA9IGZyYW1lLT5Mb2NrQnVmZmVyKEJpdG1hcEJ1ZmZlckFjY2Vzc01vZGU6OlJlYWRXcml0ZSk7DQogICAgSU1lbW9yeUJ1ZmZlclJlZmVyZW5jZV4gcmVmZXJlbmNlID0gYnVmZmVyLT5DcmVhdGVSZWZlcmVuY2UoKTsNCg0KICAgIE1pY3Jvc29mdDo6V1JMOjpDb21QdHI8SU1lbW9yeUJ1ZmZlckJ5dGVBY2Nlc3M+IGJ5dGVBY2Nlc3M7DQogICAgaWYgKFNVQ0NFRURFRChyZWludGVycHJldF9jYXN0PElVbmtub3duKj4ocmVmZXJlbmNlKS0+UXVlcnlJbnRlcmZhY2UoSUlEX1BQVl9BUkdTKCZieXRlQWNjZXNzKSkpKQ0KICAgIHsNCiAgICAgICAgYnl0ZSogZGF0YTsNCiAgICAgICAgdW5zaWduZWQgY2FwYWNpdHk7DQogICAgICAgIGJ5dGVBY2Nlc3MtPkdldEJ1ZmZlcigmZGF0YSwgJmNhcGFjaXR5KTsNCg0KICAgICAgICBhdXRvIGRlc2MgPSBidWZmZXItPkdldFBsYW5lRGVzY3JpcHRpb24oMCk7DQoNCiAgICAgICAgZm9yIChpbnQgcm93ID0gMDsgcm93IDwgZGVzYy5IZWlnaHQ7IHJvdysrKQ0KICAgICAgICB7DQogICAgICAgICAgICBmb3IgKGludCBjb2wgPSAwOyBjb2wgPCBkZXNjLldpZHRoOyBjb2wrKykNCiAgICAgICAgICAgIHsNCiAgICAgICAgICAgICAgICBhdXRvIGN1cnJQaXhlbCA9IGRlc2MuU3RhcnRJbmRleCArIGRlc2MuU3RyaWRlICogcm93ICsgQllURVNfUEVSX1BJWEVMICogY29sOw0KDQogICAgICAgICAgICAgICAgZGF0YVtjdXJyUGl4ZWwgKyAwXSA9IGJ1ZltjdXJyUGl4ZWwgKyAwXTsNCiAgICAgICAgICAgICAgICBkYXRhW2N1cnJQaXhlbCArIDFdID0gYnVmW2N1cnJQaXhlbCArIDFdOw0KICAgICAgICAgICAgICAgIGRhdGFbY3VyclBpeGVsICsgMl0gPSBidWZbY3VyclBpeGVsICsgMl07DQogICAgICAgICAgICB9DQogICAgICAgIH0NCiAgICB9DQogICAgZGVsZXRlIHJlZmVyZW5jZTsNCiAgICBkZWxldGUgYnVmZmVyOw0KDQogICAgVmlkZW9NYW5hZ2VyOjppbnN0YW5jZS0+cmVuZGVyZXJNYW5hZ2VyKCktPnJlbmRlcmVyKGlkKS0+aXNSZW5kZXJpbmcgPSBmYWxzZTsNCg0KICAgIGF1dG8gc2JTb3VyY2UgPSByZWYgbmV3IE1lZGlhOjpJbWFnaW5nOjpTb2Z0d2FyZUJpdG1hcFNvdXJjZSgpOw0KICAgIHJldHVybiBjcmVhdGVfdGFzayhzYlNvdXJjZS0+U2V0Qml0bWFwQXN5bmMoZnJhbWUpKQ0KICAgICAgICAgICAudGhlbihbdGhpcywgc2JTb3VyY2VdKCkNCiAgICB7DQogICAgICAgIHRyeSB7DQogICAgICAgICAgICBJbmNvbWluZ1ZpZGVvSW1hZ2UtPlNvdXJjZSA9IHNiU291cmNlOw0KICAgICAgICB9DQogICAgICAgIGNhdGNoIChFeGNlcHRpb25eIGUpIHsNCiAgICAgICAgICAgIFdyaXRlRXhjZXB0aW9uKGUpOw0KICAgICAgICB9DQogICAgfSk7DQp9DQoNCg0Kdm9pZCBSaW5nQ2xpZW50VVdQOjpWaWV3czo6VmlkZW9QYWdlOjpPbmluY29taW5nTWVzc2FnZShQbGF0Zm9ybTo6U3RyaW5nIF5jYWxsSWQsIFBsYXRmb3JtOjpTdHJpbmcgXnBheWxvYWQpDQp7DQogICAgc2Nyb2xsRG93bigpOw0KfQ0K