LyoKICogQ29weXJpZ2h0IChjKSAyMDA2LCAyMDA3IEJvcmxhbmQgU29mdHdhcmUgQ29ycG9yYXRpb24KICogCiAqIEFsbCByaWdodHMgcmVzZXJ2ZWQuIFRoaXMgcHJvZ3JhbSBhbmQgdGhlIGFjY29tcGFueWluZyBtYXRlcmlhbHMKICogYXJlIG1hZGUgYXZhaWxhYmxlIHVuZGVyIHRoZSB0ZXJtcyBvZiB0aGUgRWNsaXBzZSBQdWJsaWMgTGljZW5zZSB2MS4wCiAqIHdoaWNoIGFjY29tcGFuaWVzIHRoaXMgZGlzdHJpYnV0aW9uLCBhbmQgaXMgYXZhaWxhYmxlIGF0CiAqIGh0dHA6Ly93d3cuZWNsaXBzZS5vcmcvbGVnYWwvZXBsLXYxMC5odG1sCiAqCiAqIENvbnRyaWJ1dG9yczoKICogICAgRG1pdHJ5IFN0YWRuaWsgKEJvcmxhbmQpIC0gaW5pdGlhbCBBUEkgYW5kIGltcGxlbWVudGF0aW9uCiAqICAgIEFsZXhhbmRlciBTaGF0YWxpbiAoQm9ybGFuZCkgLSBpbml0aWFsIEFQSSBhbmQgaW1wbGVtZW50YXRpb24KICovCgqrSU1QT1JUICJodHRwOi8vd3d3LmVjbGlwc2Uub3JnL2dtZi8yMDA4L0dlbk1vZGVsIrsKq0lNUE9SVCAiaHR0cDovL3d3dy5lY2xpcHNlLm9yZy9lbWYvMjAwMi9FY29yZSK7CqtFWFRFTlNJT04geHB0OjpkaWFncmFtOjpWaWV3bWFwQXR0cmlidXRlc1V0aWxzuwqrRVhURU5TSU9OIHhwdDo6ZGlhZ3JhbTo6ZWRpdHBhcnRzOjpVdGlsc7sKCqtERUZJTkUgZXh0ZW5kc0xpc3RDb250ZW50cyBGT1IgZ21mZ2VuOjpHZW5Ob2RlLbsKq0lGIGhhc0JvcmRlckl0ZW1zKCm7b3JnLmVjbGlwc2UuZ21mLnJ1bnRpbWUuZGlhZ3JhbS51aS5lZGl0cGFydHMuQWJzdHJhY3RCb3JkZXJlZFNoYXBlRWRpdFBhcnSrRUxTRbtvcmcuZWNsaXBzZS5nbWYucnVudGltZS5kaWFncmFtLnVpLmVkaXRwYXJ0cy5TaGFwZU5vZGVFZGl0UGFydKtFTkRJRi27CqtFTkRERUZJTkW7CgqrREVGSU5FIGV4dGVuZHNMaXN0Q29udGVudHMgRk9SIGdtZmdlbjo6R2VuQ2hpbGRTaWRlQWZmaXhlZE5vZGUtuwqrSUYgaGFzQm9yZGVySXRlbXMoKbtvcmcuZWNsaXBzZS5nbWYucnVudGltZS5kaWFncmFtLnVpLmVkaXRwYXJ0cy5Cb3JkZXJlZEJvcmRlckl0ZW1FZGl0UGFydKtFTFNFu29yZy5lY2xpcHNlLmdtZi5ydW50aW1lLmRpYWdyYW0udWkuZWRpdHBhcnRzLkFic3RyYWN0Qm9yZGVySXRlbUVkaXRQYXJ0q0VORElGLbsKq0VORERFRklORbsKCqtERUZJTkUgY29uc3RydWN0b3IgRk9SIGdtZmdlbjo6R2VuTm9kZS27CgmrRVhQQU5EIHhwdDo6Q29tbW9uOjpnZW5lcmF0ZWRNZW1iZXJDb21tZW50uwoJcHVibGljIKtlZGl0UGFydENsYXNzTmFtZbsob3JnLmVjbGlwc2UuZ21mLnJ1bnRpbWUubm90YXRpb24uVmlldyB2aWV3KSB7CgkJc3VwZXIodmlldyk7Cgl9CqtFTkRERUZJTkW7CgqrREVGSU5FIGNyZWF0ZURlZmF1bHRFZGl0UG9saWNpZXNCb2R5IEZPUiBnbWZnZW46Okdlbk5vZGUtuwoJq0VYUEFORCBpbnN0YWxsQ3JlYXRpb25Sb2xlUG9saWN5LbsKCXN1cGVyLmNyZWF0ZURlZmF1bHRFZGl0UG9saWNpZXMoKTsKCatFWFBBTkQgaW5zdGFsbFByaW1hcnlEcmFnRWRpdFBvbGljeS27CgmrRVhQQU5EIHhwdDo6ZGlhZ3JhbTo6ZWRpdHBhcnRzOjpDb21tb246Omluc3RhbGxTZW1hbnRpY0VkaXRQb2xpY3ktuwoJq0lGIG5lZWRzR3JhcGhpY2FsTm9kZUVkaXRQb2xpY3koKS27CgkJaW5zdGFsbEVkaXRQb2xpY3kob3JnLmVjbGlwc2UuZ2VmLkVkaXRQb2xpY3kuR1JBUEhJQ0FMX05PREVfUk9MRSwgbmV3IKtnZXRHcmFwaGljYWxOb2RlRWRpdFBvbGljeVF1YWxpZmllZENsYXNzTmFtZSgpuygpKTsKCatFTkRJRi27CgmrSUYgIWNoaWxkTm9kZXMuaXNFbXB0eSgpLbsKCQlpbnN0YWxsRWRpdFBvbGljeShvcmcuZWNsaXBzZS5nbWYucnVudGltZS5kaWFncmFtLnVpLmVkaXRwb2xpY2llcy5FZGl0UG9saWN5Um9sZXMuRFJBR19EUk9QX1JPTEUsIG5ldyBvcmcuZWNsaXBzZS5nbWYucnVudGltZS5kaWFncmFtLnVpLmVkaXRwb2xpY2llcy5EcmFnRHJvcEVkaXRQb2xpY3koKSk7CgmrRU5ESUYtuwoJq0VYUEFORCB4cHQ6OmRpYWdyYW06OmVkaXRwYXJ0czo6Q29tbW9uOjppbnN0YWxsQ2Fub25pY2FsRWRpdFBvbGljeS27CglpbnN0YWxsRWRpdFBvbGljeShvcmcuZWNsaXBzZS5nZWYuRWRpdFBvbGljeS5MQVlPVVRfUk9MRSwgY3JlYXRlTGF5b3V0RWRpdFBvbGljeSgpKTsKCatFWFBBTkQgeHB0OjpkaWFncmFtOjplZGl0cGFydHM6OkNvbW1vbjo6YmVoYXZpb3VyIEZPUiB0aGlzLbsKCS8vIFhYWCBuZWVkIGFuIFNDUiB0byBydW50aW1lIHRvIGhhdmUgYW5vdGhlciBhYnN0cmFjdCBzdXBlcmNsYXNzIHRoYXQgd291bGQgbGV0IGNoaWxkcmVuIGFkZCByZWFzb25hYmxlIGVkaXRwb2xpY2llcwoJLy8gcmVtb3ZlRWRpdFBvbGljeShvcmcuZWNsaXBzZS5nbWYucnVudGltZS5kaWFncmFtLnVpLmVkaXRwb2xpY2llcy5FZGl0UG9saWN5Um9sZXMuQ09OTkVDVElPTl9IQU5ETEVTX1JPTEUpOwqrRU5EREVGSU5FuwoKq0RFRklORSBpbnN0YWxsQ3JlYXRpb25Sb2xlUG9saWN5IEZPUiBnbWZnZW46Okdlbk5vZGUtuwoJq0lGIGhhc0NoaWxkcmVuKCkgfHwgaGFzQ2hpbGRyZW5Jbkxpc3RDb21wYXJ0bWVudHMoKS27CgkJaW5zdGFsbEVkaXRQb2xpY3kob3JnLmVjbGlwc2UuZ21mLnJ1bnRpbWUuZGlhZ3JhbS51aS5lZGl0cG9saWNpZXMuRWRpdFBvbGljeVJvbGVzLkNSRUFUSU9OX1JPTEUsCgkJCQluZXcgb3JnLmVjbGlwc2UuZ21mLnJ1bnRpbWUuZGlhZ3JhbS51aS5lZGl0cG9saWNpZXMuQ3JlYXRpb25FZGl0UG9saWN5KCmrSUYgaGFzQ2hpbGRyZW5Jbkxpc3RDb21wYXJ0bWVudHMoKbsgewoJCQlwdWJsaWMgb3JnLmVjbGlwc2UuZ2VmLmNvbW1hbmRzLkNvbW1hbmQgZ2V0Q29tbWFuZChvcmcuZWNsaXBzZS5nZWYuUmVxdWVzdCByZXF1ZXN0KSB7CgkJCQlpZiAodW5kZXJzdGFuZHNSZXF1ZXN0KHJlcXVlc3QpKSB7CgkJCQkJaWYgKHJlcXVlc3QgaW5zdGFuY2VvZiBvcmcuZWNsaXBzZS5nbWYucnVudGltZS5kaWFncmFtLnVpLnJlcXVlc3RzLkNyZWF0ZVZpZXdBbmRFbGVtZW50UmVxdWVzdCkgewoJCQkJCQlvcmcuZWNsaXBzZS5nbWYucnVudGltZS5kaWFncmFtLmNvcmUuZWRpdGhlbHBlcnMuQ3JlYXRlRWxlbWVudFJlcXVlc3RBZGFwdGVyIGFkYXB0ZXIgPQoJCQkJCQkJKChvcmcuZWNsaXBzZS5nbWYucnVudGltZS5kaWFncmFtLnVpLnJlcXVlc3RzLkNyZWF0ZVZpZXdBbmRFbGVtZW50UmVxdWVzdCkgcmVxdWVzdCkuCgkJCQkJCQkJZ2V0Vmlld0FuZEVsZW1lbnREZXNjcmlwdG9yKCkuZ2V0Q3JlYXRlRWxlbWVudFJlcXVlc3RBZGFwdGVyKCk7CgkJCQkJCW9yZy5lY2xpcHNlLmdtZi5ydW50aW1lLmVtZi50eXBlLmNvcmUuSUVsZW1lbnRUeXBlIHR5cGUgPQoJCQkJCQkJKG9yZy5lY2xpcHNlLmdtZi5ydW50aW1lLmVtZi50eXBlLmNvcmUuSUVsZW1lbnRUeXBlKSBhZGFwdGVyLmdldEFkYXB0ZXIoCgkJCQkJCQkJb3JnLmVjbGlwc2UuZ21mLnJ1bnRpbWUuZW1mLnR5cGUuY29yZS5JRWxlbWVudFR5cGUuY2xhc3MpOwoJCQkJCQmrRk9SRUFDSCBjb21wYXJ0bWVudHMgQVMgY29tcGFydG1lbnQtuwoJCQkJCQkJq0lGIGxpc3RDb21wYXJ0bWVudEhhc0NoaWxkcmVuKGNvbXBhcnRtZW50KS27CgkJCQkJCQkJq0ZPUkVBQ0ggY29tcGFydG1lbnQuY2hpbGROb2RlcyBBUyBjaGlsZE5vZGUtuwoJCQkJCQlpZiAodHlwZSA9PSCrZ2V0RGlhZ3JhbSgpLmdldEVsZW1lbnRUeXBlc1F1YWxpZmllZENsYXNzTmFtZSgpuy6rY2hpbGROb2RlLmdldFVuaXF1ZUlkZW50aWZpZXIoKbspIHsKCQkJCQkJCW9yZy5lY2xpcHNlLmdlZi5FZGl0UGFydCBjb21wYXJ0bWVudEVkaXRQYXJ0ID0KCQkJCQkJCQlnZXRDaGlsZEJ5U2VtYW50aWNIaW50KKtFWFBBTkQgeHB0OjplZGl0b3I6OlZpc3VhbElEUmVnaXN0cnk6OmdldFR5cGVNZXRob2RDYWxsIEZPUiBnZXREaWFncmFtKCm7KAoJCQkJCQkJCQmrRVhQQU5EIHhwdDo6ZWRpdG9yOjpWaXN1YWxJRFJlZ2lzdHJ5Ojp2aXN1YWxJRCBGT1IgY29tcGFydG1lbnS7KSk7CgkJCQkJCQlyZXR1cm4gY29tcGFydG1lbnRFZGl0UGFydCA9PSBudWxsID8gbnVsbCA6IGNvbXBhcnRtZW50RWRpdFBhcnQuZ2V0Q29tbWFuZChyZXF1ZXN0KTsKCQkJCQkJfQoJCQkJCQkJCatFTkRGT1JFQUNILbsKCQkJCQkJCatFTkRJRi27CgkJCQkJCatFTkRGT1JFQUNILbsKCQkJCQl9CgkJCQkJcmV0dXJuIHN1cGVyLmdldENvbW1hbmQocmVxdWVzdCk7CgkJCQl9CgkJCQlyZXR1cm4gbnVsbDsKCQkJfQoJCX0KCQmrRU5ESUa7KTsKCatFTkRJRi27CqtFTkRERUZJTkW7CgqrREVGSU5FIGluc3RhbGxQcmltYXJ5RHJhZ0VkaXRQb2xpY3kgRk9SIGdtZmdlbjo6R2VuTm9kZburRU5EREVGSU5FuwoKq0RFRklORSBpbnN0YWxsUHJpbWFyeURyYWdFZGl0UG9saWN5IEZPUiBnbWZnZW46OkdlbkNoaWxkU2lkZUFmZml4ZWROb2RlLbsKCQlpbnN0YWxsRWRpdFBvbGljeShvcmcuZWNsaXBzZS5nZWYuRWRpdFBvbGljeS5QUklNQVJZX0RSQUdfUk9MRSwgZ2V0UHJpbWFyeURyYWdFZGl0UG9saWN5KCkpOwqrRU5EREVGSU5FuwoKq0RFRklORSBjcmVhdGVMYXlvdXRFZGl0UG9saWN5IEZPUiBnbWZnZW46Okdlbk5vZGUtuwoJq0VYUEFORCB4cHQ6OkNvbW1vbjo6Z2VuZXJhdGVkTWVtYmVyQ29tbWVudLsKCXByb3RlY3RlZCBvcmcuZWNsaXBzZS5nZWYuZWRpdHBvbGljaWVzLkxheW91dEVkaXRQb2xpY3kgY3JlYXRlTGF5b3V0RWRpdFBvbGljeSgpIHsKCQmrRVhQQU5EIGNyZWF0ZUxheW91dEVkaXRQb2xpY3lCb2R5LbsKCX0Kq0VORERFRklORbsKCqtERUZJTkUgY3JlYXRlTGF5b3V0RWRpdFBvbGljeUJvZHkgRk9SIGdtZmdlbjo6R2VuTm9kZS27CgmrSUYgZ21mZ2VuOjpWaWV3bWFwTGF5b3V0VHlwZTo6WFlfTEFZT1VULnZhbHVlID09IGdldExheW91dFR5cGUoKS52YWx1ZS27CgkJb3JnLmVjbGlwc2UuZ21mLnJ1bnRpbWUuZGlhZ3JhbS51aS5lZGl0cG9saWNpZXMuWFlMYXlvdXRFZGl0UG9saWN5IGxlcCA9IG5ldyBvcmcuZWNsaXBzZS5nbWYucnVudGltZS5kaWFncmFtLnVpLmVkaXRwb2xpY2llcy5YWUxheW91dEVkaXRQb2xpY3koKSB7CgoJCQlwcm90ZWN0ZWQgb3JnLmVjbGlwc2UuZ2VmLkVkaXRQb2xpY3kgY3JlYXRlQ2hpbGRFZGl0UG9saWN5KG9yZy5lY2xpcHNlLmdlZi5FZGl0UGFydCBjaGlsZCkgewoJCQkJq0lGIGhhc0JvcmRlckl0ZW1zKCktuwoJCQkJCWlmIChjaGlsZCBpbnN0YW5jZW9mIG9yZy5lY2xpcHNlLmdtZi5ydW50aW1lLmRpYWdyYW0udWkuZWRpdHBhcnRzLklCb3JkZXJJdGVtRWRpdFBhcnQpIHsKCQkJCQkJcmV0dXJuIG5ldyBvcmcuZWNsaXBzZS5nbWYucnVudGltZS5kaWFncmFtLnVpLmVkaXRwb2xpY2llcy5Cb3JkZXJJdGVtU2VsZWN0aW9uRWRpdFBvbGljeSgpOwoJCQkJCX0KCQkJCatFTkRJRi27CgkJCQlvcmcuZWNsaXBzZS5nZWYuRWRpdFBvbGljeSByZXN1bHQgPSBzdXBlci5jcmVhdGVDaGlsZEVkaXRQb2xpY3koY2hpbGQpOwoJCQkJaWYgKHJlc3VsdCA9PSBudWxsKSB7CgkJCQkJcmV0dXJuIG5ldyBvcmcuZWNsaXBzZS5nbWYucnVudGltZS5kaWFncmFtLnVpLmVkaXRwb2xpY2llcy5SZXNpemFibGVTaGFwZUVkaXRQb2xpY3koKTsKCQkJCX0KCQkJCXJldHVybiByZXN1bHQ7CgkJCX0KCQl9OwoJCXJldHVybiBsZXA7CgmrRUxTRUlGIGdtZmdlbjo6Vmlld21hcExheW91dFR5cGU6OlRPT0xCQVJfTEFZT1VULnZhbHVlID09IGdldExheW91dFR5cGUoKS52YWx1ZbsKCQlvcmcuZWNsaXBzZS5nbWYucnVudGltZS5kaWFncmFtLnVpLmVkaXRwb2xpY2llcy5Db25zdHJhaW5lZFRvb2xiYXJMYXlvdXRFZGl0UG9saWN5IGxlcCA9IG5ldyBvcmcuZWNsaXBzZS5nbWYucnVudGltZS5kaWFncmFtLnVpLmVkaXRwb2xpY2llcy5Db25zdHJhaW5lZFRvb2xiYXJMYXlvdXRFZGl0UG9saWN5KCkgewoKCQkJcHJvdGVjdGVkIG9yZy5lY2xpcHNlLmdlZi5FZGl0UG9saWN5IGNyZWF0ZUNoaWxkRWRpdFBvbGljeShvcmcuZWNsaXBzZS5nZWYuRWRpdFBhcnQgY2hpbGQpIHsKCQkJCatJRiBoYXNCb3JkZXJJdGVtcygpLbsKCQkJCQlpZiAoY2hpbGQgaW5zdGFuY2VvZiBvcmcuZWNsaXBzZS5nbWYucnVudGltZS5kaWFncmFtLnVpLmVkaXRwYXJ0cy5JQm9yZGVySXRlbUVkaXRQYXJ0KSB7CgkJCQkJCXJldHVybiBuZXcgb3JnLmVjbGlwc2UuZ21mLnJ1bnRpbWUuZGlhZ3JhbS51aS5lZGl0cG9saWNpZXMuQm9yZGVySXRlbVNlbGVjdGlvbkVkaXRQb2xpY3koKTsKCQkJCQl9CgkJCQmrRU5ESUYtuwoJCQkJaWYgKGNoaWxkLmdldEVkaXRQb2xpY3kob3JnLmVjbGlwc2UuZ2VmLkVkaXRQb2xpY3kuUFJJTUFSWV9EUkFHX1JPTEUpID09IG51bGwpIHsKCQkJCQlpZiAoY2hpbGQgaW5zdGFuY2VvZiBvcmcuZWNsaXBzZS5nbWYucnVudGltZS5kaWFncmFtLnVpLmVkaXRwYXJ0cy5JVGV4dEF3YXJlRWRpdFBhcnQpIHsKCQkJCQkJcmV0dXJuIG5ldyCrZ2V0RGlhZ3JhbSgpLmdldFRleHRTZWxlY3Rpb25FZGl0UG9saWN5UXVhbGlmaWVkQ2xhc3NOYW1lKCm7KCk7CgkJCQkJfQoJCQkJfQoJCQkJcmV0dXJuIHN1cGVyLmNyZWF0ZUNoaWxkRWRpdFBvbGljeShjaGlsZCk7CgkJCX0KCQl9OwoJCXJldHVybiBsZXA7CgmrRUxTRUlGIGdtZmdlbjo6Vmlld21hcExheW91dFR5cGU6OkZMT1dfTEFZT1VULnZhbHVlID09IGdldExheW91dFR5cGUoKS52YWx1ZbsKCQlvcmcuZWNsaXBzZS5nZWYuZWRpdHBvbGljaWVzLkZsb3dMYXlvdXRFZGl0UG9saWN5IGxlcCA9IG5ldyBvcmcuZWNsaXBzZS5nZWYuZWRpdHBvbGljaWVzLkZsb3dMYXlvdXRFZGl0UG9saWN5KCkgewoKCQkJq0lGIGhhc0JvcmRlckl0ZW1zKCktuwoJCQkJcHJvdGVjdGVkIG9yZy5lY2xpcHNlLmdlZi5FZGl0UG9saWN5IGNyZWF0ZUNoaWxkRWRpdFBvbGljeShvcmcuZWNsaXBzZS5nZWYuRWRpdFBhcnQgY2hpbGQpIHsKCQkJCQlpZiAoY2hpbGQgaW5zdGFuY2VvZiBvcmcuZWNsaXBzZS5nbWYucnVudGltZS5kaWFncmFtLnVpLmVkaXRwYXJ0cy5JQm9yZGVySXRlbUVkaXRQYXJ0KSB7CgkJCQkJCXJldHVybiBuZXcgb3JnLmVjbGlwc2UuZ21mLnJ1bnRpbWUuZGlhZ3JhbS51aS5lZGl0cG9saWNpZXMuQm9yZGVySXRlbVNlbGVjdGlvbkVkaXRQb2xpY3koKTsKCQkJCQl9CgkJCQkJcmV0dXJuIHN1cGVyLmNyZWF0ZUNoaWxkRWRpdFBvbGljeShjaGlsZCk7CgkJCQl9CgkJCatFTkRJRi27CgoJCQlwcm90ZWN0ZWQgb3JnLmVjbGlwc2UuZ2VmLmNvbW1hbmRzLkNvbW1hbmQgY3JlYXRlQWRkQ29tbWFuZChvcmcuZWNsaXBzZS5nZWYuRWRpdFBhcnQgY2hpbGQsIG9yZy5lY2xpcHNlLmdlZi5FZGl0UGFydCBhZnRlcikgewoJCQkJcmV0dXJuIG51bGw7CgkJCX0KCgkJCXByb3RlY3RlZCBvcmcuZWNsaXBzZS5nZWYuY29tbWFuZHMuQ29tbWFuZCBjcmVhdGVNb3ZlQ2hpbGRDb21tYW5kKG9yZy5lY2xpcHNlLmdlZi5FZGl0UGFydCBjaGlsZCwgb3JnLmVjbGlwc2UuZ2VmLkVkaXRQYXJ0IGFmdGVyKSB7CgkJCQlyZXR1cm4gbnVsbDsKCQkJfQoKCQkJcHJvdGVjdGVkIG9yZy5lY2xpcHNlLmdlZi5jb21tYW5kcy5Db21tYW5kIGdldENyZWF0ZUNvbW1hbmQob3JnLmVjbGlwc2UuZ2VmLnJlcXVlc3RzLkNyZWF0ZVJlcXVlc3QgcmVxdWVzdCkgewoJCQkJcmV0dXJuIG51bGw7CgkJCX0KCQl9OwoJCXJldHVybiBsZXA7CgmrRUxTRS27CgkJb3JnLmVjbGlwc2UuZ2VmLmVkaXRwb2xpY2llcy5MYXlvdXRFZGl0UG9saWN5IGxlcCA9IG5ldyBvcmcuZWNsaXBzZS5nZWYuZWRpdHBvbGljaWVzLkxheW91dEVkaXRQb2xpY3koKSB7CgoJCQlwcm90ZWN0ZWQgb3JnLmVjbGlwc2UuZ2VmLkVkaXRQb2xpY3kgY3JlYXRlQ2hpbGRFZGl0UG9saWN5KG9yZy5lY2xpcHNlLmdlZi5FZGl0UGFydCBjaGlsZCkgewoJCQkJq0lGIGhhc0JvcmRlckl0ZW1zKCktuwoJCQkJCWlmIChjaGlsZCBpbnN0YW5jZW9mIG9yZy5lY2xpcHNlLmdtZi5ydW50aW1lLmRpYWdyYW0udWkuZWRpdHBhcnRzLklCb3JkZXJJdGVtRWRpdFBhcnQpIHsKCQkJCQkJcmV0dXJuIG5ldyBvcmcuZWNsaXBzZS5nbWYucnVudGltZS5kaWFncmFtLnVpLmVkaXRwb2xpY2llcy5Cb3JkZXJJdGVtU2VsZWN0aW9uRWRpdFBvbGljeSgpOwoJCQkJCX0KCQkJCatFTkRJRi27CgkJCQlvcmcuZWNsaXBzZS5nZWYuRWRpdFBvbGljeSByZXN1bHQgPSBjaGlsZC5nZXRFZGl0UG9saWN5KG9yZy5lY2xpcHNlLmdlZi5FZGl0UG9saWN5LlBSSU1BUllfRFJBR19ST0xFKTsKCQkJCWlmIChyZXN1bHQgPT0gbnVsbCkgewoJCQkJCXJlc3VsdCA9IG5ldyBvcmcuZWNsaXBzZS5nZWYuZWRpdHBvbGljaWVzLk5vblJlc2l6YWJsZUVkaXRQb2xpY3koKTsKCQkJCX0KCQkJCXJldHVybiByZXN1bHQ7CgkJCX0KCgkJCXByb3RlY3RlZCBvcmcuZWNsaXBzZS5nZWYuY29tbWFuZHMuQ29tbWFuZCBnZXRNb3ZlQ2hpbGRyZW5Db21tYW5kKG9yZy5lY2xpcHNlLmdlZi5SZXF1ZXN0IHJlcXVlc3QpIHsKCQkJCXJldHVybiBudWxsOwoJCQl9CgoJCQlwcm90ZWN0ZWQgb3JnLmVjbGlwc2UuZ2VmLmNvbW1hbmRzLkNvbW1hbmQgZ2V0Q3JlYXRlQ29tbWFuZChvcmcuZWNsaXBzZS5nZWYucmVxdWVzdHMuQ3JlYXRlUmVxdWVzdCByZXF1ZXN0KSB7CgkJCQlyZXR1cm4gbnVsbDsKCQkJfQoJCX07CgkJcmV0dXJuIGxlcDsKCatFTkRJRi27CqtFTkRERUZJTkW7CgqrREVGSU5FIGNyZWF0ZU5vZGVTaGFwZShnbWZnZW46Okdlbk5vZGUgbm9kZSkgRk9SIGdtZmdlbjo6Vmlld21hcC27CgmrRVJST1IgIlVua25vd24gdmlld21hcDogIiArIHRoaXMtuwqrRU5EREVGSU5FuwoKq0RFRklORSBjcmVhdGVOb2RlU2hhcGUoZ21mZ2VuOjpHZW5Ob2RlIG5vZGUpIEZPUiBnbWZnZW46OkZpZ3VyZVZpZXdtYXAtuwoJq0xFVCBmaWd1cmVRdWFsaWZpZWRDbGFzc05hbWUgPT0gbnVsbCA/ICJvcmcuZWNsaXBzZS5kcmF3MmQuUmVjdGFuZ2xlRmlndXJlIiA6IGZpZ3VyZVF1YWxpZmllZENsYXNzTmFtZSBBUyBmcW4tuwoJCatFWFBBTkQgeHB0OjpDb21tb246OmdlbmVyYXRlZE1lbWJlckNvbW1lbnS7CgkJcHJvdGVjdGVkIG9yZy5lY2xpcHNlLmRyYXcyZC5JRmlndXJlIGNyZWF0ZU5vZGVTaGFwZSgpIHsKCQkJcmV0dXJuIHByaW1hcnlTaGFwZSA9IG5ldyCrZnFuuygpq0lGIG5vZGUuZ2V0TGF5b3V0VHlwZSgpLnZhbHVlID09IGdtZmdlbjo6Vmlld21hcExheW91dFR5cGU6OlhZX0xBWU9VVC52YWx1Zbt7CgkJCQlwcm90ZWN0ZWQgYm9vbGVhbiB1c2VMb2NhbENvb3JkaW5hdGVzKCkgewoJCQkJCXJldHVybiB0cnVlOwoJCQkJfQoJCQl9q0VORElGuzsKCQl9CgoJCatFWFBBTkQgZ2V0UHJpbWFyeVNoYXBlTWV0aG9kIEZPUiBmcW4tuwoJq0VORExFVC27CqtFTkRERUZJTkW7CgqrREVGSU5FIGNyZWF0ZU5vZGVTaGFwZShnbWZnZW46Okdlbk5vZGUgbm9kZSkgRk9SIGdtZmdlbjo6U25pcHBldFZpZXdtYXAtuwoJq0VYUEFORCB4cHQ6OkNvbW1vbjo6Z2VuZXJhdGVkTWVtYmVyQ29tbWVudLsKCXByb3RlY3RlZCBvcmcuZWNsaXBzZS5kcmF3MmQuSUZpZ3VyZSBjcmVhdGVOb2RlU2hhcGUoKSB7CgkJcmV0dXJuIKtib2R5uzsKCX0Kq0VORERFRklORbsKCqtERUZJTkUgY3JlYXRlTm9kZVNoYXBlKGdtZmdlbjo6R2VuTm9kZSBub2RlKSBGT1IgZ21mZ2VuOjpJbm5lckNsYXNzVmlld21hcC27CgmrRVhQQU5EIHhwdDo6Q29tbW9uOjpnZW5lcmF0ZWRNZW1iZXJDb21tZW50uwoJcHJvdGVjdGVkIG9yZy5lY2xpcHNlLmRyYXcyZC5JRmlndXJlIGNyZWF0ZU5vZGVTaGFwZSgpIHsKCQmrY2xhc3NOYW1luyBmaWd1cmUgPSBuZXcgq2NsYXNzTmFtZbsoKTsKCQmrSUYgbm9kZS5jaGlsZE5vZGVzLnNpemUoKSA+IDAgJiYgbm9kZS5nZXRMYXlvdXRUeXBlKCkudmFsdWUgPT0gZ21mZ2VuOjpWaWV3bWFwTGF5b3V0VHlwZTo6WFlfTEFZT1VULnZhbHVlLbsKIAkJZmlndXJlLnNldFVzZUxvY2FsQ29vcmRpbmF0ZXModHJ1ZSk7CgkJq0VORElGLbsKIAkJcmV0dXJuIHByaW1hcnlTaGFwZSA9IGZpZ3VyZTsKCX0KCgmrRVhQQU5EIGdldFByaW1hcnlTaGFwZU1ldGhvZCBGT1IgY2xhc3NOYW1lLbsKq0VORERFRklORbsKCqtERUZJTkUgZ2V0UHJpbWFyeVNoYXBlTWV0aG9kIEZPUiBTdHJpbmctuwoJq0VYUEFORCB4cHQ6OkNvbW1vbjo6Z2VuZXJhdGVkTWVtYmVyQ29tbWVudLsKCXB1YmxpYyCrdGhpc7sgZ2V0UHJpbWFyeVNoYXBlKCkgewoJCXJldHVybiAoq3RoaXO7KSBwcmltYXJ5U2hhcGU7Cgl9CqtFTkRERUZJTkW7CgqrREVGSU5FIGFkZEZpeGVkQ2hpbGQgRk9SIGdtZmdlbjo6R2VuTm9kZS27CgmrSUYgaGFzRml4ZWRDaGlsZHJlbigpLbsKCQmrRVhQQU5EIHhwdDo6Q29tbW9uOjpnZW5lcmF0ZWRNZW1iZXJDb21tZW50uwoJCXByb3RlY3RlZCBib29sZWFuIGFkZEZpeGVkQ2hpbGQob3JnLmVjbGlwc2UuZ2VmLkVkaXRQYXJ0IGNoaWxkRWRpdFBhcnQpIHsKCQkJq0ZPUkVBQ0ggZ2V0SW5uZXJGaXhlZExhYmVscygpIEFTIGxhYmVsLbsKCQkJCatMRVQgKGdtZmdlbjo6UGFyZW50QXNzaWduZWRWaWV3bWFwKSBsYWJlbC52aWV3bWFwIEFTIGNoaWxkVmlld21hcC27CgkJCQkJaWYgKGNoaWxkRWRpdFBhcnQgaW5zdGFuY2VvZiCrbGFiZWwuZ2V0RWRpdFBhcnRRdWFsaWZpZWRDbGFzc05hbWUoKbspIHsKCQkJCQkJKCirbGFiZWwuZ2V0RWRpdFBhcnRRdWFsaWZpZWRDbGFzc05hbWUoKbspIGNoaWxkRWRpdFBhcnQpLqtFWFBBTkQgaW1wbDo6ZGlhZ3JhbTo6ZWRpdHBhcnRzOjpUZXh0QXdhcmU6OmxhYmVsU2V0dGVyTmFtZSBGT1IgY2hpbGRWaWV3bWFwuyhnZXRQcmltYXJ5U2hhcGUoKS6rY2hpbGRWaWV3bWFwLmdldHRlck5hbWW7KCkpOwoJCQkJCQlyZXR1cm4gdHJ1ZTsKCQkJCQl9CgkJCQmrRU5ETEVULbsKCQkJq0VOREZPUkVBQ0gtuwoJCQmrRk9SRUFDSCBnZXRQaW5uZWRDb21wYXJ0bWVudHMoKSBBUyBjb21wYXJ0bWVudC27CgkJCQmrTEVUIChnbWZnZW46OlBhcmVudEFzc2lnbmVkVmlld21hcCkgY29tcGFydG1lbnQudmlld21hcCBBUyBjaGlsZFZpZXdtYXAtuwoJCQkJCWlmIChjaGlsZEVkaXRQYXJ0IGluc3RhbmNlb2Ygq2NvbXBhcnRtZW50LmdldEVkaXRQYXJ0UXVhbGlmaWVkQ2xhc3NOYW1lKCm7KSB7CgkJCQkJCW9yZy5lY2xpcHNlLmRyYXcyZC5JRmlndXJlIHBhbmUgPSBnZXRQcmltYXJ5U2hhcGUoKS6rY2hpbGRWaWV3bWFwLmdldHRlck5hbWW7KCk7CgkJCQkJCXNldHVwQ29udGVudFBhbmUocGFuZSk7IC8vIEZJWE1FIGVhY2ggY29tcGFybWVudCBzaG91bGQgaGFuZGxlIGhpcyBjb250ZW50IHBhbmUgaW4gaGlzIG93biB3YXkgCgkJCQkJCXBhbmUuYWRkKCgoq2NvbXBhcnRtZW50LmdldEVkaXRQYXJ0UXVhbGlmaWVkQ2xhc3NOYW1lKCm7KSBjaGlsZEVkaXRQYXJ0KS5nZXRGaWd1cmUoKSk7CgkJCQkJCXJldHVybiB0cnVlOwoJCQkJCX0JCgkJCQmrRU5ETEVULbsKCQkJq0VOREZPUkVBQ0gtuwoJCQmrRk9SRUFDSCBnZXRTaWRlQWZmaXhlZENoaWxkcmVuKCkgQVMgY2hpbGQtuwoJCQkJaWYgKGNoaWxkRWRpdFBhcnQgaW5zdGFuY2VvZiCrY2hpbGQuZ2V0RWRpdFBhcnRRdWFsaWZpZWRDbGFzc05hbWUoKbspIHsKCQkJCQlvcmcuZWNsaXBzZS5nbWYucnVudGltZS5kaWFncmFtLnVpLmZpZ3VyZXMuQm9yZGVySXRlbUxvY2F0b3IgbG9jYXRvciA9IG5ldyBvcmcuZWNsaXBzZS5nbWYucnVudGltZS5kaWFncmFtLnVpLmZpZ3VyZXMuQm9yZGVySXRlbUxvY2F0b3IoZ2V0TWFpbkZpZ3VyZSgpLCBvcmcuZWNsaXBzZS5kcmF3MmQuUG9zaXRpb25Db25zdGFudHMuq2NoaWxkLnByZWZlcnJlZFNpZGVOYW1luyk7CgkJCQkJZ2V0Qm9yZGVyZWRGaWd1cmUoKS5nZXRCb3JkZXJJdGVtQ29udGFpbmVyKCkuYWRkKCgoq2NoaWxkLmdldEVkaXRQYXJ0UXVhbGlmaWVkQ2xhc3NOYW1lKCm7KSBjaGlsZEVkaXRQYXJ0KS5nZXRGaWd1cmUoKSwgbG9jYXRvcik7CgkJCQkJcmV0dXJuIHRydWU7CgkJCQl9CgkJCatFTkRGT1JFQUNILbsKCQkJcmV0dXJuIGZhbHNlOwoJCX0KCatFTkRJRi27CqtFTkRERUZJTkW7CgqrREVGSU5FIHJlbW92ZUZpeGVkQ2hpbGQgRk9SIGdtZmdlbjo6R2VuTm9kZS27CgmrSUYgaGFzRml4ZWRDaGlsZHJlbigpLbsKCQmrRVhQQU5EIHhwdDo6Q29tbW9uOjpnZW5lcmF0ZWRNZW1iZXJDb21tZW50uwoJCXByb3RlY3RlZCBib29sZWFuIHJlbW92ZUZpeGVkQ2hpbGQob3JnLmVjbGlwc2UuZ2VmLkVkaXRQYXJ0IGNoaWxkRWRpdFBhcnQpIHsKCQkJq1JFTbtpZ25vcmUgbGFiZWxzIGFzc3VtaW5nIHRoYXQgdGhleSBuZXZlciBtYXkgYmUgcmVtb3ZlZKtFTkRSRU27CgkJCatGT1JFQUNIIGdldFBpbm5lZENvbXBhcnRtZW50cygpIEFTIGNvbXBhcnRtZW50LbsKCQkJCatMRVQgKGdtZmdlbjo6UGFyZW50QXNzaWduZWRWaWV3bWFwKSBjb21wYXJ0bWVudC52aWV3bWFwIEFTIGNoaWxkVmlld21hcC27CgkJCQkJaWYgKGNoaWxkRWRpdFBhcnQgaW5zdGFuY2VvZiCrY29tcGFydG1lbnQuZ2V0RWRpdFBhcnRRdWFsaWZpZWRDbGFzc05hbWUoKbspIHsKCQkJCQkJb3JnLmVjbGlwc2UuZHJhdzJkLklGaWd1cmUgcGFuZSA9IGdldFByaW1hcnlTaGFwZSgpLqtjaGlsZFZpZXdtYXAuZ2V0dGVyTmFtZbsoKTsKCQkJCQkJc2V0dXBDb250ZW50UGFuZShwYW5lKTsgLy8gRklYTUUgZWFjaCBjb21wYXJtZW50IHNob3VsZCBoYW5kbGUgaGlzIGNvbnRlbnQgcGFuZSBpbiBoaXMgb3duIHdheSAKCQkJCQkJcGFuZS5yZW1vdmUoKCirY29tcGFydG1lbnQuZ2V0RWRpdFBhcnRRdWFsaWZpZWRDbGFzc05hbWUoKbspIGNoaWxkRWRpdFBhcnQpLmdldEZpZ3VyZSgpKTsKCQkJCQkJcmV0dXJuIHRydWU7CgkJCQkJfQkKCQkJCatFTkRMRVQtuwoJCQmrRU5ERk9SRUFDSC27CgkJCatGT1JFQUNIIGdldFNpZGVBZmZpeGVkQ2hpbGRyZW4oKSBBUyBjaGlsZC27CgkJCQlpZiAoY2hpbGRFZGl0UGFydCBpbnN0YW5jZW9mIKtjaGlsZC5nZXRFZGl0UGFydFF1YWxpZmllZENsYXNzTmFtZSgpuykgewoJCQkJCWdldEJvcmRlcmVkRmlndXJlKCkuZ2V0Qm9yZGVySXRlbUNvbnRhaW5lcigpLnJlbW92ZSgoKKtjaGlsZC5nZXRFZGl0UGFydFF1YWxpZmllZENsYXNzTmFtZSgpuykgY2hpbGRFZGl0UGFydCkuZ2V0RmlndXJlKCkpOwoJCQkJCXJldHVybiB0cnVlOwoJCQkJfQoJCQmrRU5ERk9SRUFDSC27CgkJCXJldHVybiBmYWxzZTsKCQl9CgmrRU5ESUYtuwqrRU5EREVGSU5FuwoKq0RFRklORSBhZGRDaGlsZFZpc3VhbCBGT1IgZ21mZ2VuOjpHZW5Ob2RlLbsKCatJRiBoYXNGaXhlZENoaWxkcmVuKCktuwoJCatFWFBBTkQgeHB0OjpDb21tb246OmdlbmVyYXRlZE1lbWJlckNvbW1lbnS7CgkJcHJvdGVjdGVkIHZvaWQgYWRkQ2hpbGRWaXN1YWwob3JnLmVjbGlwc2UuZ2VmLkVkaXRQYXJ0IGNoaWxkRWRpdFBhcnQsIGludCBpbmRleCkgewoJCQlpZiAoYWRkRml4ZWRDaGlsZChjaGlsZEVkaXRQYXJ0KSkgewoJCQkJcmV0dXJuOwoJCQl9CgkJCXN1cGVyLmFkZENoaWxkVmlzdWFsKGNoaWxkRWRpdFBhcnQsIC0xKTsKCQl9CgmrRU5ESUYtuwqrRU5EREVGSU5FuwoKq0RFRklORSByZW1vdmVDaGlsZFZpc3VhbCBGT1IgZ21mZ2VuOjpHZW5Ob2RlLbsKCatJRiBoYXNGaXhlZENoaWxkcmVuKCktuwoJCatFWFBBTkQgeHB0OjpDb21tb246OmdlbmVyYXRlZE1lbWJlckNvbW1lbnS7CgkJcHJvdGVjdGVkIHZvaWQgcmVtb3ZlQ2hpbGRWaXN1YWwob3JnLmVjbGlwc2UuZ2VmLkVkaXRQYXJ0IGNoaWxkRWRpdFBhcnQpIHsKCQkJaWYgKHJlbW92ZUZpeGVkQ2hpbGQoY2hpbGRFZGl0UGFydCkpewoJCQkJcmV0dXJuOwoJCQl9CgkJCXN1cGVyLnJlbW92ZUNoaWxkVmlzdWFsKGNoaWxkRWRpdFBhcnQpOwoJCX0KCatFTkRJRi27CqtFTkRERUZJTkW7CgqrREVGSU5FIGdldENvbnRlbnRQYW5lRm9yIEZPUiBnbWZnZW46Okdlbk5vZGUtuwoJq0lGIGhhc0ZpeGVkQ2hpbGRyZW4oKS27CgkJq0VYUEFORCB4cHQ6OkNvbW1vbjo6Z2VuZXJhdGVkTWVtYmVyQ29tbWVudLsKCQlwcm90ZWN0ZWQgb3JnLmVjbGlwc2UuZHJhdzJkLklGaWd1cmUgZ2V0Q29udGVudFBhbmVGb3Iob3JnLmVjbGlwc2UuZ21mLnJ1bnRpbWUuZGlhZ3JhbS51aS5lZGl0cGFydHMuSUdyYXBoaWNhbEVkaXRQYXJ0IGVkaXRQYXJ0KSB7CgkJCatSRU27aXQgaXMgdW5jbGVhciB3aGF0IHdlIHNob3VsZCByZXR1cm4gZm9yIGxhYmVscyBoZXJlq0VORFJFTbsKCQkJq0ZPUkVBQ0ggZ2V0UGlubmVkQ29tcGFydG1lbnRzKCkgQVMgY29tcGFydG1lbnQtuwoJCQkJq0xFVCAoZ21mZ2VuOjpQYXJlbnRBc3NpZ25lZFZpZXdtYXApIGNvbXBhcnRtZW50LnZpZXdtYXAgQVMgY2hpbGRWaWV3bWFwLbsKCQkJCQlpZiAoZWRpdFBhcnQgaW5zdGFuY2VvZiCrY29tcGFydG1lbnQuZ2V0RWRpdFBhcnRRdWFsaWZpZWRDbGFzc05hbWUoKbspIHsKCQkJCQkJcmV0dXJuIGdldFByaW1hcnlTaGFwZSgpLqtjaGlsZFZpZXdtYXAuZ2V0dGVyTmFtZbsoKTsKCQkJCQl9CQoJCQkJq0VORExFVC27CgkJCatFTkRGT1JFQUNILbsKCQkJq0ZPUkVBQ0ggZ2V0U2lkZUFmZml4ZWRDaGlsZHJlbigpIEFTIGNoaWxkLbsKCQkJCWlmIChlZGl0UGFydCBpbnN0YW5jZW9mIKtjaGlsZC5nZXRFZGl0UGFydFF1YWxpZmllZENsYXNzTmFtZSgpuykgewoJCQkJCXJldHVybiBnZXRCb3JkZXJlZEZpZ3VyZSgpLmdldEJvcmRlckl0ZW1Db250YWluZXIoKTsKCQkJCX0KCQkJq0VOREZPUkVBQ0gtuwoJCQlyZXR1cm4gc3VwZXIuZ2V0Q29udGVudFBhbmVGb3IoZWRpdFBhcnQpOwoJCX0KCatFTkRJRi27CqtFTkRERUZJTkW7CgqrREVGSU5FIGFkZEJvcmRlckl0ZW0gRk9SIGdtZmdlbjo6R2VuTm9kZS27CgmrSUYgZ2V0RXh0ZXJuYWxMYWJlbHMoKS5zaXplKCkgPiAwLbsKCQmrRVhQQU5EIHhwdDo6Q29tbW9uOjpnZW5lcmF0ZWRNZW1iZXJDb21tZW50uwoJCXByb3RlY3RlZCB2b2lkIGFkZEJvcmRlckl0ZW0ob3JnLmVjbGlwc2UuZHJhdzJkLklGaWd1cmUgYm9yZGVySXRlbUNvbnRhaW5lciwgb3JnLmVjbGlwc2UuZ21mLnJ1bnRpbWUuZGlhZ3JhbS51aS5lZGl0cGFydHMuSUJvcmRlckl0ZW1FZGl0UGFydCBib3JkZXJJdGVtRWRpdFBhcnQpIHsKCQkJaWYgKKtGT1JFQUNIIGdldEV4dGVybmFsTGFiZWxzKCkgQVMgbGFiZWwgU0VQQVJBVE9SICcgfHwgJ7tib3JkZXJJdGVtRWRpdFBhcnQgaW5zdGFuY2VvZiCrbGFiZWwuZ2V0RWRpdFBhcnRRdWFsaWZpZWRDbGFzc05hbWUoKburRU5ERk9SRUFDSLspIHsKCQkJCW9yZy5lY2xpcHNlLmdtZi5ydW50aW1lLmRpYWdyYW0udWkuZmlndXJlcy5Cb3JkZXJJdGVtTG9jYXRvciBsb2NhdG9yID0gbmV3IG9yZy5lY2xpcHNlLmdtZi5ydW50aW1lLmRpYWdyYW0udWkuZmlndXJlcy5Cb3JkZXJJdGVtTG9jYXRvcihnZXRNYWluRmlndXJlKCksIG9yZy5lY2xpcHNlLmRyYXcyZC5Qb3NpdGlvbkNvbnN0YW50cy5TT1VUSCk7CgkJCQlsb2NhdG9yLnNldEJvcmRlckl0ZW1PZmZzZXQobmV3IG9yZy5lY2xpcHNlLmRyYXcyZC5nZW9tZXRyeS5EaW1lbnNpb24oLTIwLCAtMjApKTsKCQkJCWJvcmRlckl0ZW1Db250YWluZXIuYWRkKGJvcmRlckl0ZW1FZGl0UGFydC5nZXRGaWd1cmUoKSwgbG9jYXRvcik7CgkJCX0gZWxzZSB7CgkJCQlzdXBlci5hZGRCb3JkZXJJdGVtKGJvcmRlckl0ZW1Db250YWluZXIsIGJvcmRlckl0ZW1FZGl0UGFydCk7CgkJCX0KCQl9CgmrRU5ESUYtuwqrRU5EREVGSU5FuwoKq0RFRklORSBjcmVhdGVOb2RlUGxhdGUgRk9SIGdtZmdlbjo6R2VuTm9kZS27CgmrRVhQQU5EIHhwdDo6Q29tbW9uOjpnZW5lcmF0ZWRNZW1iZXJDb21tZW50uwoJcHJvdGVjdGVkIG9yZy5lY2xpcHNlLmdtZi5ydW50aW1lLmdlZi51aS5maWd1cmVzLk5vZGVGaWd1cmUgY3JlYXRlTm9kZVBsYXRlKCkgewoJCW9yZy5lY2xpcHNlLmdtZi5ydW50aW1lLmdlZi51aS5maWd1cmVzLkRlZmF1bHRTaXplTm9kZUZpZ3VyZSByZXN1bHQgPQoJCQluZXcgb3JnLmVjbGlwc2UuZ21mLnJ1bnRpbWUuZ2VmLnVpLmZpZ3VyZXMuRGVmYXVsdFNpemVOb2RlRmlndXJlKGdldE1hcE1vZGUoKS5EUHRvTFAoq2RlZmF1bHRTaXplV2lkdGgodmlld21hcCwgNDApuyksIGdldE1hcE1vZGUoKS5EUHRvTFAoq2RlZmF1bHRTaXplSGVpZ2h0KHZpZXdtYXAsIDQwKbspKTsKCQmrRVhQQU5EIHNldHVwTm9kZVBsYXRlLbsKCQlyZXR1cm4gcmVzdWx0OwoJfQqrRU5EREVGSU5FuwoKq0RFRklORSBzZXR1cE5vZGVQbGF0ZSBGT1IgZ21mZ2VuOjpHZW5Ob2Rlu6tFTkRERUZJTkW7CgqrREVGSU5FIHNldHVwTm9kZVBsYXRlIEZPUiBnbWZnZW46OkdlbkNoaWxkU2lkZUFmZml4ZWROb2RluwoJLy9GSVhNRTogd29ya2Fyb3VuZCBmb3IgIzE1NDUzNgoJcmVzdWx0LmdldEJvdW5kcygpLnNldFNpemUocmVzdWx0LmdldFByZWZlcnJlZFNpemUoKSk7CqtFTkRERUZJTkW7CgqrREVGSU5FIGdldFByaW1hcnlEcmFnRWRpdFBvbGljeSBGT1IgZ21mZ2VuOjpHZW5Ob2RlLbsKCatMRVQgZ2V0UmVzaXplQ29uc3RyYWludHModmlld21hcCkgQVMgcmMtuwoJCatJRiBudWxsICE9IHByaW1hcnlEcmFnRWRpdFBvbGljeVF1YWxpZmllZENsYXNzTmFtZSB8fCBudWxsICE9IHJjLbsKCQkJq0VYUEFORCB4cHQ6OkNvbW1vbjo6Z2VuZXJhdGVkTWVtYmVyQ29tbWVudLsKCQkJcHVibGljIG9yZy5lY2xpcHNlLmdlZi5FZGl0UG9saWN5IGdldFByaW1hcnlEcmFnRWRpdFBvbGljeSgpIHsKCQkJCatJRiBudWxsICE9IHByaW1hcnlEcmFnRWRpdFBvbGljeVF1YWxpZmllZENsYXNzTmFtZS27CgkJCQkJcmV0dXJuIG5ldyCrcHJpbWFyeURyYWdFZGl0UG9saWN5UXVhbGlmaWVkQ2xhc3NOYW1luygpOwoJCQkJq0VMU0UtuwoJCQkJCW9yZy5lY2xpcHNlLmdlZi5FZGl0UG9saWN5IHJlc3VsdCA9IHN1cGVyLmdldFByaW1hcnlEcmFnRWRpdFBvbGljeSgpOwoJCQkJCWlmIChyZXN1bHQgaW5zdGFuY2VvZiBvcmcuZWNsaXBzZS5nZWYuZWRpdHBvbGljaWVzLlJlc2l6YWJsZUVkaXRQb2xpY3kpIHsKCQkJCQkJb3JnLmVjbGlwc2UuZ2VmLmVkaXRwb2xpY2llcy5SZXNpemFibGVFZGl0UG9saWN5IGVwID0gKG9yZy5lY2xpcHNlLmdlZi5lZGl0cG9saWNpZXMuUmVzaXphYmxlRWRpdFBvbGljeSkgcmVzdWx0OwoJCQkJCQllcC5zZXRSZXNpemVEaXJlY3Rpb25zKAoJCQkJCQkJq0lGIHJjLnJlc2l6ZUhhbmRsZU5hbWVzLnNpemUoKSA+IDAtuwoJCQkJCQkJCatGT1JFQUNIIHJjLnJlc2l6ZUhhbmRsZU5hbWVzIEFTIG5hbWUgU0VQQVJBVE9SICcgfCAnu29yZy5lY2xpcHNlLmRyYXcyZC5Qb3NpdGlvbkNvbnN0YW50cy6rbmFtZburRU5ERk9SRUFDSC27CgkJCQkJCQmrRUxTRbtvcmcuZWNsaXBzZS5kcmF3MmQuUG9zaXRpb25Db25zdGFudHMuTk9ORatFTkRJRrspOwoJCQkJCX0KCQkJCQlyZXR1cm4gcmVzdWx0OwoJCQkJq0VORElGLbsKCQkJfQoJCatFTkRJRi27CgmrRU5ETEVULbsKq0VORERFRklORbsKCqtERUZJTkUgY3JlYXRlRmlndXJlIEZPUiBnbWZnZW46Okdlbk5vZGUtuwoJq0VYUEFORCB4cHQ6OkNvbW1vbjo6Z2VuZXJhdGVkTWVtYmVyQ29tbWVudCgKCQkiQ3JlYXRlcyBmaWd1cmUgZm9yIHRoaXMgZWRpdCBwYXJ0LlxuIiArCgkJIlxuIiArCgkJIkJvZHkgb2YgdGhpcyBtZXRob2QgZG9lcyBub3QgZGVwZW5kIG9uIHNldHRpbmdzIGluIGdlbmVyYXRpb24gbW9kZWxcbiIgKwoJCSJzbyB5b3UgbWF5IHNhZmVseSByZW1vdmUgPGk+Z2VuZXJhdGVkPC9pPiB0YWcgYW5kIG1vZGlmeSBpdC5cbiIKCSm7Cglwcm90ZWN0ZWQgb3JnLmVjbGlwc2UuZ21mLnJ1bnRpbWUuZ2VmLnVpLmZpZ3VyZXMuTm9kZUZpZ3VyZSBjcmVhdGWrSUYgaGFzQm9yZGVySXRlbXMoKbtNYWluq0VMU0W7Tm9kZatFTkRJRrtGaWd1cmUoKSB7CgkJb3JnLmVjbGlwc2UuZ21mLnJ1bnRpbWUuZ2VmLnVpLmZpZ3VyZXMuTm9kZUZpZ3VyZSBmaWd1cmUgPSBjcmVhdGVOb2RlUGxhdGUoKTsKCQlmaWd1cmUuc2V0TGF5b3V0TWFuYWdlcihuZXcgb3JnLmVjbGlwc2UuZHJhdzJkLlN0YWNrTGF5b3V0KCkpOwoJCW9yZy5lY2xpcHNlLmRyYXcyZC5JRmlndXJlIHNoYXBlID0gY3JlYXRlTm9kZVNoYXBlKCk7CgkJZmlndXJlLmFkZChzaGFwZSk7CgkJY29udGVudFBhbmUgPSBzZXR1cENvbnRlbnRQYW5lKHNoYXBlKTsKCQlyZXR1cm4gZmlndXJlOwoJfQqrRU5EREVGSU5FuwoKq0RFRklORSBzZXR1cENvbnRlbnRQYW5lIEZPUiBnbWZnZW46Okdlbk5vZGUtuwoJq0VYUEFORCB4cHQ6OkNvbW1vbjo6Z2VuZXJhdGVkTWVtYmVyQ29tbWVudCgKCQkiRGVmYXVsdCBpbXBsZW1lbnRhdGlvbiB0cmVhdHMgcGFzc2VkIGZpZ3VyZSBhcyBjb250ZW50IHBhbmUuXG4iICsKCQkiUmVzcGVjdHMgbGF5b3V0IG9uZSBtYXkgaGF2ZSBzZXQgZm9yIGdlbmVyYXRlZCBmaWd1cmUuXG4iICsKCQkiQHBhcmFtIG5vZGVTaGFwZSBpbnN0YW5jZSBvZiBnZW5lcmF0ZWQgZmlndXJlIGNsYXNzIgoJKbsKCXByb3RlY3RlZCBvcmcuZWNsaXBzZS5kcmF3MmQuSUZpZ3VyZSBzZXR1cENvbnRlbnRQYW5lKG9yZy5lY2xpcHNlLmRyYXcyZC5JRmlndXJlIG5vZGVTaGFwZSkgewoJCatJRiAhY2hpbGROb2Rlcy5pc0VtcHR5KCkgfHwgIWNvbXBhcnRtZW50cy5pc0VtcHR5KCkgfHwgIWxhYmVscy53aXRob3V0KGxhYmVscy50eXBlU2VsZWN0KEdlbkV4dGVybmFsTm9kZUxhYmVsKSkuaXNFbXB0eSgpLbsKCQkJaWYgKG5vZGVTaGFwZS5nZXRMYXlvdXRNYW5hZ2VyKCkgPT0gbnVsbCkgewoJCQkJq0lGIGdldExheW91dFR5cGUoKS52YWx1ZSA9PSBnbWZnZW46OlZpZXdtYXBMYXlvdXRUeXBlOjpYWV9MQVlPVVQudmFsdWUtuwoJCQkJCW5vZGVTaGFwZS5zZXRMYXlvdXRNYW5hZ2VyKG5ldyBvcmcuZWNsaXBzZS5kcmF3MmQuRnJlZWZvcm1MYXlvdXQoKSB7CgoJCQkJCQlwdWJsaWMgT2JqZWN0IGdldENvbnN0cmFpbnQob3JnLmVjbGlwc2UuZHJhdzJkLklGaWd1cmUgZmlndXJlKSB7CgkJCQkJCQlPYmplY3QgcmVzdWx0ID0gY29uc3RyYWludHMuZ2V0KGZpZ3VyZSk7CgkJCQkJCQlpZiAocmVzdWx0ID09IG51bGwpIHsKCQkJCQkJCQlyZXN1bHQgPSBuZXcgb3JnLmVjbGlwc2UuZHJhdzJkLmdlb21ldHJ5LlJlY3RhbmdsZSgwLCAwLCAtMSwgLTEpOwoJCQkJCQkJfQoJCQkJCQkJcmV0dXJuIHJlc3VsdDsKCQkJCQkJfQoJCQkJCX0pOwoJCQkJq0VMU0UtuwoJCQkJCW9yZy5lY2xpcHNlLmdtZi5ydW50aW1lLmRyYXcyZC51aS5maWd1cmVzLkNvbnN0cmFpbmVkVG9vbGJhckxheW91dCBsYXlvdXQgPW5ldyBvcmcuZWNsaXBzZS5nbWYucnVudGltZS5kcmF3MmQudWkuZmlndXJlcy5Db25zdHJhaW5lZFRvb2xiYXJMYXlvdXQoKTsKCQkJCQlsYXlvdXQuc2V0U3BhY2luZyhnZXRNYXBNb2RlKCkuRFB0b0xQKDUpKTsKCQkJCQlub2RlU2hhcGUuc2V0TGF5b3V0TWFuYWdlcihsYXlvdXQpOwoJCQkJq0VORElGLbsKCQkJfQoJCatFTkRJRi27CgkJcmV0dXJuIG5vZGVTaGFwZTsgLy8gdXNlIG5vZGVTaGFwZSBpdHNlbGYgYXMgY29udGVudFBhbmUKCX0Kq0VORERFRklORbsKCqtERUZJTkUgZ2V0Q29udGVudFBhbmUgRk9SIGdtZmdlbjo6R2VuTm9kZS27CgmrRVhQQU5EIHhwdDo6Q29tbW9uOjpnZW5lcmF0ZWRNZW1iZXJDb21tZW50uwoJcHVibGljIG9yZy5lY2xpcHNlLmRyYXcyZC5JRmlndXJlIGdldENvbnRlbnRQYW5lKCkgewoJCWlmIChjb250ZW50UGFuZSAhPSBudWxsKSB7CgkJCXJldHVybiBjb250ZW50UGFuZTsKCQl9CgkJcmV0dXJuIHN1cGVyLmdldENvbnRlbnRQYW5lKCk7Cgl9CqtFTkRERUZJTkW7CgqrREVGSU5FIGdldFByaW1hcnlDaGlsZEVkaXRQYXJ0IEZPUiBnbWZnZW46Okdlbk5vZGUtuwoJq0lGICFsYWJlbHMuaXNFbXB0eSgpLbsKCQmrRVhQQU5EIHhwdDo6Q29tbW9uOjpnZW5lcmF0ZWRNZW1iZXJDb21tZW50uwoJCXB1YmxpYyBvcmcuZWNsaXBzZS5nZWYuRWRpdFBhcnQgZ2V0UHJpbWFyeUNoaWxkRWRpdFBhcnQoKSB7CgkJCXJldHVybiBnZXRDaGlsZEJ5U2VtYW50aWNIaW50KKtFWFBBTkQgeHB0OjplZGl0b3I6OlZpc3VhbElEUmVnaXN0cnk6OmdldFR5cGVNZXRob2RDYWxsIEZPUiBnZXREaWFncmFtKCm7KKtFWFBBTkQgeHB0OjplZGl0b3I6OlZpc3VhbElEUmVnaXN0cnk6OnZpc3VhbElEIEZPUiAoR2VuTGFiZWwpIGxhYmVscy50b0xpc3QoKS5maXJzdCgpuykpOwoJCX0KCatFTkRJRi27CqtFTkRERUZJTkW7CgqrREVGSU5FIGhhbmRsZU5vdGlmaWNhdGlvbkV2ZW50Qm9keSBGT1IgZ21mZ2VuOjpHZW5Ub3BMZXZlbE5vZGUtuwoJaWYgKGV2ZW50LmdldE5vdGlmaWVyKCkgPT0gZ2V0TW9kZWwoKSAmJiBvcmcuZWNsaXBzZS5lbWYuZWNvcmUuRWNvcmVQYWNrYWdlLmVJTlNUQU5DRS5nZXRFTW9kZWxFbGVtZW50X0VBbm5vdGF0aW9ucygpLmVxdWFscyhldmVudC5nZXRGZWF0dXJlKCkpKSB7CgkJaGFuZGxlTWFqb3JTZW1hbnRpY0NoYW5nZSgpOwoJfSBlbHNlIHsKCQlzdXBlci5oYW5kbGVOb3RpZmljYXRpb25FdmVudChldmVudCk7Cgl9CqtFTkRERUZJTkW7CgqrREVGSU5FIGlubmVyQ2xhc3NEZWNsYXJhdGlvbiBGT1IgZ21mZ2VuOjpWaWV3bWFwuwqrRU5EREVGSU5FuwoKq0RFRklORSBpbm5lckNsYXNzRGVjbGFyYXRpb24gRk9SIGdtZmdlbjo6SW5uZXJDbGFzc1ZpZXdtYXC7CgmrY2xhc3NCb2R5uwqrRU5EREVGSU5Fuw==