LyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogWW91IG1heSBhbWVuZCBhbmQgZGlzdHJpYnV0ZSBhcyB5b3UgbGlrZSwgYnV0IGRvbid0IHJlbW92ZSB0aGlzIGhlYWRlciEKICoKICogRVBQbHVzIHByb3ZpZGVzIHNlcnZlci1zaWRlIGdlbmVyYXRpb24gb2YgRXhjZWwgMjAwNy8yMDEwIHNwcmVhZHNoZWV0cy4KICogU2VlIGh0dHA6Ly93d3cuY29kZXBsZXguY29tL0VQUGx1cyBmb3IgZGV0YWlscy4KICoKICogQ29weXJpZ2h0IChDKSAyMDExICBKYW4gS+RsbG1hbgogKgogKiBUaGlzIGxpYnJhcnkgaXMgZnJlZSBzb2Z0d2FyZTsgeW91IGNhbiByZWRpc3RyaWJ1dGUgaXQgYW5kL29yCiAqIG1vZGlmeSBpdCB1bmRlciB0aGUgdGVybXMgb2YgdGhlIEdOVSBMZXNzZXIgR2VuZXJhbCBQdWJsaWMKICogTGljZW5zZSBhcyBwdWJsaXNoZWQgYnkgdGhlIEZyZWUgU29mdHdhcmUgRm91bmRhdGlvbjsgZWl0aGVyCiAqIHZlcnNpb24gMi4xIG9mIHRoZSBMaWNlbnNlLCBvciAoYXQgeW91ciBvcHRpb24pIGFueSBsYXRlciB2ZXJzaW9uLgoKICogVGhpcyBsaWJyYXJ5IGlzIGRpc3RyaWJ1dGVkIGluIHRoZSBob3BlIHRoYXQgaXQgd2lsbCBiZSB1c2VmdWwsCiAqIGJ1dCBXSVRIT1VUIEFOWSBXQVJSQU5UWTsgd2l0aG91dCBldmVuIHRoZSBpbXBsaWVkIHdhcnJhbnR5IG9mCiAqIE1FUkNIQU5UQUJJTElUWSBvciBGSVRORVNTIEZPUiBBIFBBUlRJQ1VMQVIgUFVSUE9TRS4gIAogKiBTZWUgdGhlIEdOVSBMZXNzZXIgR2VuZXJhbCBQdWJsaWMgTGljZW5zZSBmb3IgbW9yZSBkZXRhaWxzLgogKgogKiBUaGUgR05VIExlc3NlciBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlIGNhbiBiZSB2aWV3ZWQgYXQgaHR0cDovL3d3dy5vcGVuc291cmNlLm9yZy9saWNlbnNlcy9sZ3BsLWxpY2Vuc2UucGhwCiAqIElmIHlvdSB1bmZhbWlsaWFyIHdpdGggdGhpcyBsaWNlbnNlIG9yIGhhdmUgcXVlc3Rpb25zIGFib3V0IGl0LCBoZXJlIGlzIGFuIGh0dHA6Ly93d3cuZ251Lm9yZy9saWNlbnNlcy9ncGwtZmFxLmh0bWwKICoKICogQWxsIGNvZGUgYW5kIGV4ZWN1dGFibGVzIGFyZSBwcm92aWRlZCAiYXMgaXMiIHdpdGggbm8gd2FycmFudHkgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4gCiAqIFRoZSBhdXRob3IgYWNjZXB0cyBubyBsaWFiaWxpdHkgZm9yIGFueSBkYW1hZ2Ugb3IgbG9zcyBvZiBidXNpbmVzcyB0aGF0IHRoaXMgcHJvZHVjdCBtYXkgY2F1c2UuCiAqCiAqIENvZGUgY2hhbmdlIG5vdGVzOgogKiAKICogQXV0aG9yCQkJCQkJCUNoYW5nZQkJCQkJCURhdGUKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSmFuIEvkbGxtYW4JCUluaXRpYWwgUmVsZWFzZQkJICAgICAgICAyMDA5LTEwLTAxCiAqIEphbiBL5GxsbWFuCQlMaWNlbnNlIGNoYW5nZWQgR1BMLS0+TEdQTCAyMDExLTEyLTI3CiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwp1c2luZyBTeXN0ZW07CnVzaW5nIFN5c3RlbS5YbWw7CnVzaW5nIE9mZmljZU9wZW5YbWwuU3R5bGU7Cm5hbWVzcGFjZSBPZmZpY2VPcGVuWG1sCnsKICAgIC8vLyA8c3VtbWFyeT4KCS8vLyBSZXByZXNlbnRzIG9uZSBvciBtb3JlIGNvbHVtbnMgd2l0aGluIHRoZSB3b3Jrc2hlZXQKCS8vLyA8L3N1bW1hcnk+CglwdWJsaWMgY2xhc3MgRXhjZWxDb2x1bW4gOiBJUmFuZ2VJRAoJewoJCXByaXZhdGUgRXhjZWxXb3Jrc2hlZXQgX3dvcmtzaGVldDsKCQlwcml2YXRlIFhtbEVsZW1lbnQgX2NvbEVsZW1lbnQgPSBudWxsOwoKCQkjcmVnaW9uIEV4Y2VsQ29sdW1uIENvbnN0cnVjdG9yCgkJLy8vIDxzdW1tYXJ5PgoJCS8vLyBDcmVhdGVzIGEgbmV3IGluc3RhbmNlIG9mIHRoZSBFeGNlbENvbHVtbiBjbGFzcy4gIAoJCS8vLyBGb3IgaW50ZXJuYWwgdXNlIG9ubHkhCgkJLy8vIDwvc3VtbWFyeT4KCQkvLy8gPHBhcmFtIG5hbWU9IldvcmtzaGVldCI+PC9wYXJhbT4KCQkvLy8gPHBhcmFtIG5hbWU9ImNvbCI+PC9wYXJhbT4KCQlwcm90ZWN0ZWQgaW50ZXJuYWwgRXhjZWxDb2x1bW4oRXhjZWxXb3Jrc2hlZXQgV29ya3NoZWV0LCBpbnQgY29sKQogICAgICAgIHsKICAgICAgICAgICAgX3dvcmtzaGVldCA9IFdvcmtzaGVldDsKICAgICAgICAgICAgX2NvbHVtbk1pbiA9IGNvbDsKICAgICAgICAgICAgX2NvbHVtbk1heCA9IGNvbDsKICAgICAgICAgICAgX3dpZHRoID0gX3dvcmtzaGVldC5EZWZhdWx0Q29sV2lkdGg7CiAgICAgICAgfQoJCSNlbmRyZWdpb24KICAgICAgICBpbnRlcm5hbCBpbnQgX2NvbHVtbk1pbjsJCQoJCS8vLyA8c3VtbWFyeT4KCQkvLy8gU2V0cyB0aGUgZmlyc3QgY29sdW1uIHRoZSBkZWZpbml0aW9uIHJlZmVycyB0by4KCQkvLy8gPC9zdW1tYXJ5PgoJCXB1YmxpYyBpbnQgQ29sdW1uTWluIAoJCXsKICAgICAgICAgICAgZ2V0IHsgcmV0dXJuIF9jb2x1bW5NaW47IH0KCQkJLy9zZXQgeyBfY29sdW1uTWluPXZhbHVlOyB9IAoJCX0KCiAgICAgICAgaW50ZXJuYWwgaW50IF9jb2x1bW5NYXg7CiAgICAgICAgLy8vIDxzdW1tYXJ5PgoJCS8vLyBTZXRzIHRoZSBsYXN0IGNvbHVtbiB0aGUgZGVmaW5pdGlvbiByZWZlcnMgdG8uCgkJLy8vIDwvc3VtbWFyeT4KICAgICAgICBwdWJsaWMgaW50IENvbHVtbk1heCAKCQl7IAogICAgICAgICAgICBnZXQgeyByZXR1cm4gX2NvbHVtbk1heDsgfQoJCQlzZXQgCiAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgIGlmICh2YWx1ZSA8IF9jb2x1bW5NaW4gJiYgdmFsdWUgPiBFeGNlbFBhY2thZ2UuTWF4Q29sdW1ucykKICAgICAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXhjZXB0aW9uKCJDb2x1bW5NYXggb3V0IG9mIHJhbmdlIik7CiAgICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgICAgdmFyIGNzZSA9IG5ldyBDZWxsc1N0b3JlRW51bWVyYXRvcjxvYmplY3Q+KF93b3Jrc2hlZXQuX3ZhbHVlcywgMCwgMCwgMCwgRXhjZWxQYWNrYWdlLk1heENvbHVtbnMpOwogICAgICAgICAgICAgICAgd2hpbGUoY3NlLk5leHQoKSkKICAgICAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgICAgICB2YXIgYyA9IGNzZS5WYWx1ZSBhcyBFeGNlbENvbHVtbjsKICAgICAgICAgICAgICAgICAgICBpZiAoY3NlLkNvbHVtbiA+IF9jb2x1bW5NaW4gJiYgYy5Db2x1bW5NYXggPD0gdmFsdWUgJiYgY3NlLkNvbHVtbiE9X2NvbHVtbk1pbikKICAgICAgICAgICAgICAgICAgICB7CiAgICAgICAgICAgICAgICAgICAgICAgIHRocm93IG5ldyBFeGNlcHRpb24oc3RyaW5nLkZvcm1hdCgiQ29sdW1uTWF4IGNhbiBub3Qgc3BhbiBvdmVyIGV4aXN0aW5nIGNvbHVtbiB7MH0uIixjLkNvbHVtbk1pbikpOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIF9jb2x1bW5NYXggPSB2YWx1ZTsgCiAgICAgICAgICAgIH0gCgkJfQogICAgICAgIC8vLyA8c3VtbWFyeT4KICAgICAgICAvLy8gSW50ZXJuYWwgcmFuZ2UgaWQgZm9yIHRoZSBjb2x1bW4KICAgICAgICAvLy8gPC9zdW1tYXJ5PgogICAgICAgIGludGVybmFsIHVsb25nIENvbHVtbklECiAgICAgICAgewogICAgICAgICAgICBnZXQKICAgICAgICAgICAgewogICAgICAgICAgICAgICAgcmV0dXJuIEV4Y2VsQ29sdW1uLkdldENvbHVtbklEKF93b3Jrc2hlZXQuU2hlZXRJRCwgQ29sdW1uTWluKTsKICAgICAgICAgICAgfQogICAgICAgIH0KCQkjcmVnaW9uIEV4Y2VsQ29sdW1uIEhpZGRlbgoJCS8vLyA8c3VtbWFyeT4KCQkvLy8gQWxsb3dzIHRoZSBjb2x1bW4gdG8gYmUgaGlkZGVuIGluIHRoZSB3b3Jrc2hlZXQKCQkvLy8gPC9zdW1tYXJ5PgogICAgICAgIGludGVybmFsIGJvb2wgX2hpZGRlbj1mYWxzZTsKICAgICAgICBwdWJsaWMgYm9vbCBIaWRkZW4KCQl7CgkJCWdldAoJCQl7CiAgICAgICAgICAgICAgICByZXR1cm4gX2hpZGRlbjsKCQkJfQoJCQlzZXQKCQkJewogICAgICAgICAgICAgICAgaWYgKF93b3Jrc2hlZXQuX3BhY2thZ2UuRG9BZGp1c3REcmF3aW5ncykKICAgICAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgICAgICB2YXIgcG9zID0gX3dvcmtzaGVldC5EcmF3aW5ncy5HZXREcmF3aW5nV2lkdGhzKCk7CiAgICAgICAgICAgICAgICAgICAgX2hpZGRlbiA9IHZhbHVlOwogICAgICAgICAgICAgICAgICAgIF93b3Jrc2hlZXQuRHJhd2luZ3MuQWRqdXN0V2lkdGgocG9zKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UKICAgICAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgICAgICBfaGlkZGVuID0gdmFsdWU7CiAgICAgICAgICAgICAgICB9CgkJCX0KCQl9CgkJI2VuZHJlZ2lvbgoKCQkjcmVnaW9uIEV4Y2VsQ29sdW1uIFdpZHRoCiAgICAgICAgaW50ZXJuYWwgZG91YmxlIFZpc3VhbFdpZHRoCiAgICAgICAgewogICAgICAgICAgICBnZXQKICAgICAgICAgICAgewogICAgICAgICAgICAgICAgaWYgKF9oaWRkZW4gfHwgKENvbGxhcHNlZCAmJiBPdXRsaW5lTGV2ZWw+MCkpCiAgICAgICAgICAgICAgICB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIDA7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlCiAgICAgICAgICAgICAgICB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIF93aWR0aDsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBpbnRlcm5hbCBkb3VibGUgX3dpZHRoOwogICAgICAgIC8vLyA8c3VtbWFyeT4KICAgICAgICAvLy8gU2V0cyB0aGUgd2lkdGggb2YgdGhlIGNvbHVtbiBpbiB0aGUgd29ya3NoZWV0CiAgICAgICAgLy8vIDwvc3VtbWFyeT4KICAgICAgICBwdWJsaWMgZG91YmxlIFdpZHRoCgkJewoJCQlnZXQKCQkJewogICAgICAgICAgICAgICAgcmV0dXJuIF93aWR0aDsKCQkJfQoJCQlzZXQJCiAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgIGlmIChfd29ya3NoZWV0Ll9wYWNrYWdlLkRvQWRqdXN0RHJhd2luZ3MpCiAgICAgICAgICAgICAgICB7CiAgICAgICAgICAgICAgICAgICAgdmFyIHBvcyA9IF93b3Jrc2hlZXQuRHJhd2luZ3MuR2V0RHJhd2luZ1dpZHRocygpOwogICAgICAgICAgICAgICAgICAgIF93aWR0aCA9IHZhbHVlOwogICAgICAgICAgICAgICAgICAgIF93b3Jrc2hlZXQuRHJhd2luZ3MuQWRqdXN0V2lkdGgocG9zKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UKICAgICAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgICAgICBfd2lkdGggPSB2YWx1ZTsKICAgICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgICBpZiAoX2hpZGRlbiAmJiB2YWx1ZSE9MCkKICAgICAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgICAgICBfaGlkZGVuID0gZmFsc2U7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KCQl9CiAgICAgICAgLy8vIDxzdW1tYXJ5PgogICAgICAgIC8vLyBJZiBzZXQgdG8gdHJ1ZSBhIGNvbHVtbiBhdXRvbWF0aWNsbHkgcmVzaXplKGdyb3cgd2lkZXIpIHdoZW4gYSB1c2VyIGlucHV0cyBudW1iZXJzIGluIGEgY2VsbC4gCiAgICAgICAgLy8vIDwvc3VtbWFyeT4KICAgICAgICBwdWJsaWMgYm9vbCBCZXN0Rml0CiAgICAgICAgewogICAgICAgICAgICBnZXQ7CiAgICAgICAgICAgIHNldDsKICAgICAgICB9CiAgICAgICAgLy8vIDxzdW1tYXJ5PgogICAgICAgIC8vLyBJZiB0aGUgY29sdW1uIGlzIGNvbGxhcHNlZCBpbiBvdXRsaW5lIG1vZGUKICAgICAgICAvLy8gPC9zdW1tYXJ5PgogICAgICAgIHB1YmxpYyBib29sIENvbGxhcHNlZCB7IGdldDsgc2V0OyB9CiAgICAgICAgLy8vIDxzdW1tYXJ5PgogICAgICAgIC8vLyBPdXRsaW5lIGxldmVsLiBaZXJvIGlmIG5vIG91dGxpbmUKICAgICAgICAvLy8gPC9zdW1tYXJ5PgogICAgICAgIHB1YmxpYyBpbnQgT3V0bGluZUxldmVsIHsgZ2V0OyBzZXQ7IH0KICAgICAgICAvLy8gPHN1bW1hcnk+CiAgICAgICAgLy8vIFBob25ldGljCiAgICAgICAgLy8vIDwvc3VtbWFyeT4KICAgICAgICBwdWJsaWMgYm9vbCBQaG9uZXRpYyB7IGdldDsgc2V0OyB9CiAgICAgICAgI2VuZHJlZ2lvbgoKCQkjcmVnaW9uIEV4Y2VsQ29sdW1uIFN0eWxlCiAgICAgICAgLy8vIDxzdW1tYXJ5PgogICAgICAgIC8vLyBUaGUgU3R5bGUgYXBwbGllZCB0byB0aGUgd2hvbGUgY29sdW1uLiBPbmx5IGVmZmVjdHMgY2VsbHMgd2l0aCBubyBpbmRpdmlkdWFsIHN0eWxlIHNldC4gCiAgICAgICAgLy8vIFVzZSBSYW5nZSBvYmplY3QgaWYgeW91IHdhbnQgdG8gc2V0IHNwZWNpZmljIHN0eWxlcy4KICAgICAgICAvLy8gPC9zdW1tYXJ5PgogICAgICAgIHB1YmxpYyBFeGNlbFN0eWxlIFN0eWxlCiAgICAgICAgewogICAgICAgICAgICBnZXQKICAgICAgICAgICAgewogICAgICAgICAgICAgICAgc3RyaW5nIGxldHRlciA9IEV4Y2VsQ2VsbEJhc2UuR2V0Q29sdW1uTGV0dGVyKENvbHVtbk1pbik7CiAgICAgICAgICAgICAgICBzdHJpbmcgZW5kTGV0dGVyID0gRXhjZWxDZWxsQmFzZS5HZXRDb2x1bW5MZXR0ZXIoQ29sdW1uTWF4KTsKICAgICAgICAgICAgICAgIHJldHVybiBfd29ya3NoZWV0Lldvcmtib29rLlN0eWxlcy5HZXRTdHlsZU9iamVjdChTdHlsZUlELCBfd29ya3NoZWV0LlBvc2l0aW9uSUQsIGxldHRlciArICI6IiArIGVuZExldHRlcik7CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgaW50ZXJuYWwgc3RyaW5nIF9zdHlsZU5hbWU9IiI7CiAgICAgICAgLy8vIDxzdW1tYXJ5PgoJCS8vLyBTZXRzIHRoZSBzdHlsZSBmb3IgdGhlIGVudGlyZSBjb2x1bW4gdXNpbmcgYSBzdHlsZSBuYW1lLgoJCS8vLyA8L3N1bW1hcnk+CgkJcHVibGljIHN0cmluZyBTdHlsZU5hbWUKCQl7CiAgICAgICAgICAgIGdldAogICAgICAgICAgICB7CiAgICAgICAgICAgICAgICByZXR1cm4gX3N0eWxlTmFtZTsKICAgICAgICAgICAgfQogICAgICAgICAgICBzZXQKICAgICAgICAgICAgewogICAgICAgICAgICAgICAgU3R5bGVJRCA9IF93b3Jrc2hlZXQuV29ya2Jvb2suU3R5bGVzLkdldFN0eWxlSWRGcm9tTmFtZSh2YWx1ZSk7CiAgICAgICAgICAgICAgICBfc3R5bGVOYW1lID0gdmFsdWU7CiAgICAgICAgICAgIH0KCQl9CiAgICAgICAgLy9pbnRlcm5hbCBpbnQgX3N0eWxlSUQgPSAwOwogICAgICAgIC8vLyA8c3VtbWFyeT4KICAgICAgICAvLy8gU2V0cyB0aGUgc3R5bGUgZm9yIHRoZSBlbnRpcmUgY29sdW1uIHVzaW5nIHRoZSBzdHlsZSBJRC4gIAogICAgICAgIC8vLyA8L3N1bW1hcnk+CiAgICAgICAgcHVibGljIGludCBTdHlsZUlECiAgICAgICAgewogICAgICAgICAgICBnZXQKICAgICAgICAgICAgewogICAgICAgICAgICAgICAgcmV0dXJuIF93b3Jrc2hlZXQuX3N0eWxlcy5HZXRWYWx1ZSgwLCBDb2x1bW5NaW4pOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHNldAogICAgICAgICAgICB7CiAgICAgICAgICAgICAgICBfd29ya3NoZWV0Ll9zdHlsZXMuU2V0VmFsdWUoMCwgQ29sdW1uTWluLCB2YWx1ZSk7CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgLy8vIDxzdW1tYXJ5PgogICAgICAgIC8vLyBBZGRzIGEgbWFudWFsIHBhZ2UgYnJlYWsgYWZ0ZXIgdGhlIGNvbHVtbi4KICAgICAgICAvLy8gPC9zdW1tYXJ5PgogICAgICAgIHB1YmxpYyBib29sIFBhZ2VCcmVhawogICAgICAgIHsKICAgICAgICAgICAgZ2V0OwogICAgICAgICAgICBzZXQ7CiAgICAgICAgfQogICAgICAgIHB1YmxpYyBib29sIE1lcmdlZAogICAgICAgIHsKICAgICAgICAgICAgZ2V0CiAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgIHJldHVybiBfd29ya3NoZWV0Lk1lcmdlZENlbGxzW0NvbHVtbk1pbiwgMF0gIT0gbnVsbDsKICAgICAgICAgICAgfQogICAgICAgICAgICBzZXQKICAgICAgICAgICAgewogICAgICAgICAgICAgICAgX3dvcmtzaGVldC5NZXJnZWRDZWxscy5BZGQobmV3IEV4Y2VsQWRkcmVzc0Jhc2UoMSwgQ29sdW1uTWluLCBFeGNlbFBhY2thZ2UuTWF4Um93cywgQ29sdW1uTWF4KSwgdHJ1ZSk7CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgI2VuZHJlZ2lvbgoKCQkvLy8gPHN1bW1hcnk+CgkJLy8vIFJldHVybnMgdGhlIHJhbmdlIG9mIGNvbHVtbnMgY292ZXJlZCBieSB0aGUgY29sdW1uIGRlZmluaXRpb24uCgkJLy8vIDwvc3VtbWFyeT4KCQkvLy8gPHJldHVybnM+QSBzdHJpbmcgZGVzY3JpYmluZyB0aGUgcmFuZ2Ugb2YgY29sdW1ucyBjb3ZlcmVkIGJ5IHRoZSBjb2x1bW4gZGVmaW5pdGlvbi48L3JldHVybnM+CgkJcHVibGljIG92ZXJyaWRlIHN0cmluZyBUb1N0cmluZygpCgkJewoJCQlyZXR1cm4gc3RyaW5nLkZvcm1hdCgiQ29sdW1uIFJhbmdlOiB7MH0gdG8gezF9IiwgX2NvbEVsZW1lbnQuR2V0QXR0cmlidXRlKCJtaW4iKSwgX2NvbEVsZW1lbnQuR2V0QXR0cmlidXRlKCJtaW4iKSk7CgkJfQogICAgICAgIC8vLyA8c3VtbWFyeT4KICAgICAgICAvLy8gU2V0IHRoZSBjb2x1bW4gd2lkdGggZnJvbSB0aGUgY29udGVudCBvZiB0aGUgcmFuZ2UuIFRoZSBtaW5pbXVtIHdpZHRoIGlzIHRoZSB2YWx1ZSBvZiB0aGUgRXhjZWxXb3Jrc2hlZXQuZGVmYXVsdENvbHVtbldpZHRoIHByb3BlcnR5LgogICAgICAgIC8vLyBOb3RlOiBDZWxscyBjb250YWluaW5nIGZvcm11bGFzIGFyZSBpZ25vcmVkIHNpbmNlIEVQUGx1cyBkb24ndCBoYXZlIGEgY2FsY3VsYXRpb24gZW5naW5lLgogICAgICAgIC8vLyAgICAgICBXcmFwcGVkIGFuZCBtZXJnZWQgY2VsbHMgYXJlIGFsc28gaWdub3JlZC4KICAgICAgICAvLy8gPC9zdW1tYXJ5PgogICAgICAgIHB1YmxpYyB2b2lkIEF1dG9GaXQoKQogICAgICAgIHsKICAgICAgICAgICAgX3dvcmtzaGVldC5DZWxsc1sxLCBfY29sdW1uTWluLCBFeGNlbFBhY2thZ2UuTWF4Um93cywgX2NvbHVtbk1heF0uQXV0b0ZpdENvbHVtbnMoKTsKICAgICAgICB9CgogICAgICAgIC8vLyA8c3VtbWFyeT4KICAgICAgICAvLy8gU2V0IHRoZSBjb2x1bW4gd2lkdGggZnJvbSB0aGUgY29udGVudC4KICAgICAgICAvLy8gTm90ZTogQ2VsbHMgY29udGFpbmluZyBmb3JtdWxhcyBhcmUgaWdub3JlZCBzaW5jZSBFUFBsdXMgZG9uJ3QgaGF2ZSBhIGNhbGN1bGF0aW9uIGVuZ2luZS4KICAgICAgICAvLy8gICAgICAgV3JhcHBlZCBhbmQgbWVyZ2VkIGNlbGxzIGFyZSBhbHNvIGlnbm9yZWQuCiAgICAgICAgLy8vIDwvc3VtbWFyeT4KICAgICAgICAvLy8gPHBhcmFtIG5hbWU9Ik1pbmltdW1XaWR0aCI+TWluaW11bSBjb2x1bW4gd2lkdGg8L3BhcmFtPgogICAgICAgIHB1YmxpYyB2b2lkIEF1dG9GaXQoZG91YmxlIE1pbmltdW1XaWR0aCkKICAgICAgICB7CiAgICAgICAgICAgIF93b3Jrc2hlZXQuQ2VsbHNbMSwgX2NvbHVtbk1pbiwgRXhjZWxQYWNrYWdlLk1heFJvd3MsIF9jb2x1bW5NYXhdLkF1dG9GaXRDb2x1bW5zKE1pbmltdW1XaWR0aCk7CiAgICAgICAgfQoKICAgICAgICAvLy8gPHN1bW1hcnk+CiAgICAgICAgLy8vIFNldCB0aGUgY29sdW1uIHdpZHRoIGZyb20gdGhlIGNvbnRlbnQuCiAgICAgICAgLy8vIE5vdGU6IENlbGxzIGNvbnRhaW5pbmcgZm9ybXVsYXMgYXJlIGlnbm9yZWQgc2luY2UgRVBQbHVzIGRvbid0IGhhdmUgYSBjYWxjdWxhdGlvbiBlbmdpbmUuCiAgICAgICAgLy8vICAgICAgIFdyYXBwZWQgYW5kIG1lcmdlZCBjZWxscyBhcmUgYWxzbyBpZ25vcmVkLgogICAgICAgIC8vLyA8L3N1bW1hcnk+CiAgICAgICAgLy8vIDxwYXJhbSBuYW1lPSJNaW5pbXVtV2lkdGgiPk1pbmltdW0gY29sdW1uIHdpZHRoPC9wYXJhbT4KICAgICAgICAvLy8gPHBhcmFtIG5hbWU9Ik1heGltdW1XaWR0aCI+TWF4aW11bSBjb2x1bW4gd2lkdGg8L3BhcmFtPgogICAgICAgIHB1YmxpYyB2b2lkIEF1dG9GaXQoZG91YmxlIE1pbmltdW1XaWR0aCwgZG91YmxlIE1heGltdW1XaWR0aCkKICAgICAgICB7CiAgICAgICAgICAgIF93b3Jrc2hlZXQuQ2VsbHNbMSwgX2NvbHVtbk1pbiwgRXhjZWxQYWNrYWdlLk1heFJvd3MsIF9jb2x1bW5NYXhdLkF1dG9GaXRDb2x1bW5zKE1pbmltdW1XaWR0aCwgTWF4aW11bVdpZHRoKTsKICAgICAgICB9CgogICAgICAgIC8vLyA8c3VtbWFyeT4KICAgICAgICAvLy8gR2V0IHRoZSBpbnRlcm5hbCBSYW5nZUlECiAgICAgICAgLy8vIDwvc3VtbWFyeT4KICAgICAgICAvLy8gPHBhcmFtIG5hbWU9InNoZWV0SUQiPlNoZWV0IG5vPC9wYXJhbT4KICAgICAgICAvLy8gPHBhcmFtIG5hbWU9ImNvbHVtbiI+Q29sdW1uPC9wYXJhbT4KICAgICAgICAvLy8gPHJldHVybnM+PC9yZXR1cm5zPgogICAgICAgIGludGVybmFsIHN0YXRpYyB1bG9uZyBHZXRDb2x1bW5JRChpbnQgc2hlZXRJRCwgaW50IGNvbHVtbikKICAgICAgICB7CiAgICAgICAgICAgIHJldHVybiAoKHVsb25nKXNoZWV0SUQpICsgKCgodWxvbmcpY29sdW1uKSA8PCAxNSk7CiAgICAgICAgfQoKICAgICAgICAjcmVnaW9uIElSYW5nZUlEIE1lbWJlcnMKCiAgICAgICAgdWxvbmcgSVJhbmdlSUQuUmFuZ2VJRAogICAgICAgIHsKICAgICAgICAgICAgZ2V0CiAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgIHJldHVybiBDb2x1bW5JRDsKICAgICAgICAgICAgfQogICAgICAgICAgICBzZXQKICAgICAgICAgICAgewogICAgICAgICAgICAgICAgaW50IHByZXZDb2xNaW4gPSBfY29sdW1uTWluOwogICAgICAgICAgICAgICAgX2NvbHVtbk1pbiA9ICgoaW50KSh2YWx1ZSA+PiAxNSkgJiAweDNGRik7CiAgICAgICAgICAgICAgICBfY29sdW1uTWF4ICs9IHByZXZDb2xNaW4gLSBDb2x1bW5NaW47CiAgICAgICAgICAgICAgICAvL1RvZG86TW9yZSBWYWxpZGF0aW9uCiAgICAgICAgICAgICAgICBpZiAoX2NvbHVtbk1heCA+IEV4Y2VsUGFja2FnZS5NYXhDb2x1bW5zKSBfY29sdW1uTWF4ID0gRXhjZWxQYWNrYWdlLk1heENvbHVtbnM7CiAgICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgICNlbmRyZWdpb24KCiAgICAgICAgLy8vIDxzdW1tYXJ5PgogICAgICAgIC8vLyBDb3BpZXMgdGhlIGN1cnJlbnQgY29sdW1uIHRvIGEgbmV3IHdvcmtzaGVldAogICAgICAgIC8vLyA8L3N1bW1hcnk+CiAgICAgICAgLy8vIDxwYXJhbSBuYW1lPSJhZGRlZCI+VGhlIHdvcmtzaGVldCB3aGVyZSB0aGUgY29weSB3aWxsIGJlIGNyZWF0ZWQ8L3BhcmFtPgogICAgICAgIGludGVybmFsIEV4Y2VsQ29sdW1uIENsb25lKEV4Y2VsV29ya3NoZWV0IGFkZGVkKQogICAgICAgIHsKICAgICAgICAgICAgcmV0dXJuIENsb25lKGFkZGVkLCBDb2x1bW5NaW4pOwogICAgICAgIH0KICAgICAgICBpbnRlcm5hbCBFeGNlbENvbHVtbiBDbG9uZShFeGNlbFdvcmtzaGVldCBhZGRlZCwgaW50IGNvbCkKICAgICAgICB7CiAgICAgICAgICAgIEV4Y2VsQ29sdW1uIG5ld0NvbCA9IGFkZGVkLkNvbHVtbihjb2wpOwogICAgICAgICAgICAgICAgbmV3Q29sLkNvbHVtbk1heCA9IENvbHVtbk1heDsKICAgICAgICAgICAgICAgIG5ld0NvbC5CZXN0Rml0ID0gQmVzdEZpdDsKICAgICAgICAgICAgICAgIG5ld0NvbC5Db2xsYXBzZWQgPSBDb2xsYXBzZWQ7CiAgICAgICAgICAgICAgICBuZXdDb2wuT3V0bGluZUxldmVsID0gT3V0bGluZUxldmVsOwogICAgICAgICAgICAgICAgbmV3Q29sLlBhZ2VCcmVhayA9IFBhZ2VCcmVhazsKICAgICAgICAgICAgICAgIG5ld0NvbC5QaG9uZXRpYyA9IFBob25ldGljOwogICAgICAgICAgICAgICAgbmV3Q29sLl9zdHlsZU5hbWUgPSBfc3R5bGVOYW1lOwogICAgICAgICAgICAgICAgbmV3Q29sLlN0eWxlSUQgPSBTdHlsZUlEOwogICAgICAgICAgICAgICAgbmV3Q29sLldpZHRoID0gV2lkdGg7CiAgICAgICAgICAgICAgICBuZXdDb2wuSGlkZGVuID0gSGlkZGVuOwogICAgICAgICAgICAgICAgcmV0dXJuIG5ld0NvbDsKICAgICAgICB9CiAgICB9Cn0K