LyoKKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiogICBDb3B5cmlnaHQgKEMpIDE5OTctMjAwMSwgSW50ZXJuYXRpb25hbCBCdXNpbmVzcyBNYWNoaW5lcwoqICAgQ29ycG9yYXRpb24gYW5kIG90aGVycy4gIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgoqLwoKLyoqCiogRmlsZSBjb2xlaXRyLmgKKgoqIAoqCiogQ3JlYXRlZCBieTogSGVsZW5hIFNoaWgKKgoqIE1vZGlmaWNhdGlvbiBIaXN0b3J5OgoqCiogIERhdGUgICAgICAgTmFtZSAgICAgICAgRGVzY3JpcHRpb24KKgoqICA4LzE4Lzk3ICAgIGhlbGVuYSAgICAgIEFkZGVkIGludGVybmFsIEFQSSBkb2N1bWVudGF0aW9uLgoqIDA4LzAzLzk4ICAgIGVybSAgICAgICAgIFN5bmNoZWQgd2l0aCAxLjIgdmVyc2lvbiBDb2xsYXRpb25FbGVtZW50SXRlcmF0b3IuamF2YQoqIDEyLzEwLzk5ICAgIGFsaXUgICAgICAgIFBvcnRlZCBUaGFpIGNvbGxhdGlvbiBzdXBwb3J0IGZyb20gSmF2YS4KKiAwMS8yNS8wMSAgICBzd3F1ZWsgICAgICBNb2RpZmllZCBpbnRvIGEgQysrIHdyYXBwZXIgY2FsbGluZyBDIEFQSXMgKHVjb2xpdGVyLmgpCiogMDIvMTkvMDEgICAgc3dxdWVrICAgICAgUmVtb3ZlZCBDb2xsYXRpb25FbGVtZW50c0l0ZXJhdG9yKCkgc2luY2UgaXQgaXMgCiogICAgICAgICAgICAgICAgICAgICAgICAgcHJpdmF0ZSBjb25zdHJ1Y3RvciBhbmQgbm8gY2FsbHMgYXJlIG1hZGUgdG8gaXQKKi8KCiNpZm5kZWYgQ09MRUlUUl9ICiNkZWZpbmUgQ09MRUlUUl9ICgojaW5jbHVkZSAidW5pY29kZS91dHlwZXMuaCIKCiNpZiAhVUNPTkZJR19OT19DT0xMQVRJT04KCiNpbmNsdWRlICJ1bmljb2RlL3VvYmplY3QuaCIKI2luY2x1ZGUgInVuaWNvZGUvdGJsY29sbC5oIgojaW5jbHVkZSAidW5pY29kZS91Y29sZWl0ci5oIgoKdHlwZWRlZiBzdHJ1Y3QgVUNvbGxhdGlvbkVsZW1lbnRzIFVDb2xsYXRpb25FbGVtZW50czsKClVfTkFNRVNQQUNFX0JFR0lOCgovKioKKiBUaGUgQ29sbGF0aW9uRWxlbWVudEl0ZXJhdG9yIGNsYXNzIGlzIHVzZWQgYXMgYW4gaXRlcmF0b3IgdG8gd2FsayB0aHJvdWdoICAgICAKKiBlYWNoIGNoYXJhY3RlciBvZiBhbiBpbnRlcm5hdGlvbmFsIHN0cmluZy4gVXNlIHRoZSBpdGVyYXRvciB0byByZXR1cm4gdGhlCiogb3JkZXJpbmcgcHJpb3JpdHkgb2YgdGhlIHBvc2l0aW9uZWQgY2hhcmFjdGVyLiBUaGUgb3JkZXJpbmcgcHJpb3JpdHkgb2YgYSAKKiBjaGFyYWN0ZXIsIHdoaWNoIHdlIHJlZmVyIHRvIGFzIGEga2V5LCBkZWZpbmVzIGhvdyBhIGNoYXJhY3RlciBpcyBjb2xsYXRlZCBpbiAKKiB0aGUgZ2l2ZW4gY29sbGF0aW9uIG9iamVjdC4KKiBGb3IgZXhhbXBsZSwgY29uc2lkZXIgdGhlIGZvbGxvd2luZyBpbiBTcGFuaXNoOgoqIDxwcmU+CiogXGNvZGUKKiAgICAgICAgImNhIiAtPiB0aGUgZmlyc3Qga2V5IGlzIGtleSgnYycpIGFuZCBzZWNvbmQga2V5IGlzIGtleSgnYScpLgoqICAgICAgICAiY2hhIiAtPiB0aGUgZmlyc3Qga2V5IGlzIGtleSgnY2gnKSBhbmQgc2Vjb25kIGtleSBpcyBrZXkoJ2EnKS4KKiBcZW5kY29kZQoqIDwvcHJlPgoqIEFuZCBpbiBHZXJtYW4sCiogPHByZT4KKiBcY29kZQoqICAgICAgICAi5mIiLT4gdGhlIGZpcnN0IGtleSBpcyBrZXkoJ2EnKSwgdGhlIHNlY29uZCBrZXkgaXMga2V5KCdlJyksIGFuZAoqICAgICAgICB0aGUgdGhpcmQga2V5IGlzIGtleSgnYicpLgoqIFxlbmRjb2RlCiogPC9wcmU+CiogVGhlIGtleSBvZiBhIGNoYXJhY3RlciwgaXMgYW4gaW50ZWdlciBjb21wb3NlZCBvZiBwcmltYXJ5IG9yZGVyKHNob3J0KSwKKiBzZWNvbmRhcnkgb3JkZXIoY2hhciksIGFuZCB0ZXJ0aWFyeSBvcmRlcihjaGFyKS4gSmF2YSBzdHJpY3RseSBkZWZpbmVzIHRoZSAKKiBzaXplIGFuZCBzaWduZWRuZXNzIG9mIGl0cyBwcmltaXRpdmUgZGF0YSB0eXBlcy4gVGhlcmVmb3JlLCB0aGUgc3RhdGljCiogZnVuY3Rpb25zIHByaW1hcnlPcmRlcigpLCBzZWNvbmRhcnlPcmRlcigpLCBhbmQgdGVydGlhcnlPcmRlcigpIHJldHVybiAKKiBpbnQzMl90IHRvIGVuc3VyZSB0aGUgY29ycmVjdG5lc3Mgb2YgdGhlIGtleSB2YWx1ZS4KKiA8cD5FeGFtcGxlIG9mIHRoZSBpdGVyYXRvciB1c2FnZTogKHdpdGhvdXQgZXJyb3IgY2hlY2tpbmcpCiogPHByZT4KKiBcY29kZQoqICAgdm9pZCBDb2xsYXRpb25FbGVtZW50SXRlcmF0b3JfRXhhbXBsZSgpCiogICB7CiogICAgICAgVW5pY29kZVN0cmluZyBzdHIgPSAiVGhpcyBpcyBhIHRlc3QiOwoqICAgICAgIFVFcnJvckNvZGUgc3VjY2VzcyA9IFVfWkVST19FUlJPUjsKKiAgICAgICBSdWxlQmFzZWRDb2xsYXRvciogcmJjID0KKiAgICAgICAgICAgKFJ1bGVCYXNlZENvbGxhdG9yKikgUnVsZUJhc2VkQ29sbGF0b3I6OmNyZWF0ZUluc3RhbmNlKHN1Y2Nlc3MpOwoqICAgICAgIENvbGxhdGlvbkVsZW1lbnRJdGVyYXRvciogYyA9CiogICAgICAgICAgIHJiYy0+Y3JlYXRlQ29sbGF0aW9uRWxlbWVudEl0ZXJhdG9yKCBzdHIgKTsKKiAgICAgICBpbnQzMl90IG9yZGVyID0gYy0+bmV4dChzdWNjZXNzKTsKKiAgICAgICBjLT5yZXNldCgpOwoqICAgICAgIG9yZGVyID0gYy0+cHJldmlvdXMoc3VjY2Vzcyk7CiogICAgICAgZGVsZXRlIGM7CiogICAgICAgZGVsZXRlIHJiYzsKKiAgIH0KKiBcZW5kY29kZQoqIDwvcHJlPgoqIDxwPgoqIENvbGxhdGlvbkVsZW1lbnRJdGVyYXRvcjo6bmV4dCByZXR1cm5zIHRoZSBjb2xsYXRpb24gb3JkZXIgb2YgdGhlIG5leHQKKiBjaGFyYWN0ZXIgYmFzZWQgb24gdGhlIGNvbXBhcmlzb24gbGV2ZWwgb2YgdGhlIGNvbGxhdG9yLiAKKiBDb2xsYXRpb25FbGVtZW50SXRlcmF0b3I6OnByZXZpb3VzIHJldHVybnMgdGhlIGNvbGxhdGlvbiBvcmRlciBvZiB0aGUgCiogcHJldmlvdXMgY2hhcmFjdGVyIGJhc2VkIG9uIHRoZSBjb21wYXJpc29uIGxldmVsIG9mIHRoZSBjb2xsYXRvci4gCiogVGhlIENvbGxhdGlvbiBFbGVtZW50IEl0ZXJhdG9yIG1vdmVzIG9ubHkgaW4gb25lIGRpcmVjdGlvbiBiZXR3ZWVuIGNhbGxzIHRvCiogQ29sbGF0aW9uRWxlbWVudEl0ZXJhdG9yOjpyZXNldC4gVGhhdCBpcywgQ29sbGF0aW9uRWxlbWVudEl0ZXJhdG9yOjpuZXh0KCkgCiogYW5kIENvbGxhdGlvbkVsZW1lbnRJdGVyYXRvcjo6cHJldmlvdXMgY2FuIG5vdCBiZSBpbnRlci11c2VkLiBXaGVuZXZlciAKKiBDb2xsYXRpb25FbGVtZW50SXRlcmF0b3I6OnByZXZpb3VzIGlzIHRvIGJlIGNhbGxlZCBhZnRlciAKKiBDb2xsYXRpb25FbGVtZW50SXRlcmF0b3I6Om5leHQoKSBvciB2aWNlIHZlcnNhLCAKKiBDb2xsYXRpb25FbGVtZW50SXRlcmF0b3I6OnJlc2V0IGhhcyB0byBiZSBjYWxsZWQgZmlyc3QgdG8gcmVzZXQgdGhlIHN0YXR1cywgCiogc2hpZnRpbmcgcG9pbnRlcnMgdG8gZWl0aGVyIHRoZSBlbmQgb3IgdGhlIHN0YXJ0IG9mIHRoZSBzdHJpbmcuIEhlbmNlIGF0IHRoZSAKKiBuZXh0IGNhbGwgb2YgQ29sbGF0aW9uRWxlbWVudEl0ZXJhdG9yOjpwcmV2aW91cyBvciAKKiBDb2xsYXRpb25FbGVtZW50SXRlcmF0b3I6Om5leHQoKSwgdGhlIGZpcnN0IG9yIGxhc3QgY29sbGF0aW9uIG9yZGVyIHdpbGwgYmUgCiogcmV0dXJuZWQuIAoqIElmIGEgY2hhbmdlIG9mIGRpcmVjdGlvbiBpcyBkb25lIHdpdGhvdXQgYSBDb2xsYXRpb25FbGVtZW50SXRlcmF0b3I6OnJlc2V0KCksIAoqIHRoZSByZXN1bHQgaXMgdW5kZWZpbmVkLgoqIFRoZSByZXN1bHQgb2YgYSBmb3J3YXJkIGl0ZXJhdGUgKENvbGxhdGlvbkVsZW1lbnRJdGVyYXRvcjo6bmV4dCkgYW5kIAoqIHJldmVyc2VkIHJlc3VsdCBvZiB0aGUgYmFja3dhcmQgaXRlcmF0ZSAoQ29sbGF0aW9uRWxlbWVudEl0ZXJhdG9yOjpwcmV2aW91cykgCiogb24gdGhlIHNhbWUgc3RyaW5nIGFyZSBlcXVpdmFsZW50LCBpZiBjb2xsYXRpb24gb3JkZXJzIHdpdGggdGhlIHZhbHVlIAoqIFVDT0xfSUdOT1JBQkxFIGFyZSBpZ25vcmVkLgoqIENoYXJhY3RlciBiYXNlZCBvbiB0aGUgY29tcGFyaXNvbiBsZXZlbCBvZiB0aGUgY29sbGF0b3IuICBBIGNvbGxhdGlvbiBvcmRlciAKKiBjb25zaXN0cyBvZiBwcmltYXJ5IG9yZGVyLCBzZWNvbmRhcnkgb3JkZXIgYW5kIHRlcnRpYXJ5IG9yZGVyLiAgVGhlIGRhdGEgCiogdHlwZSBvZiB0aGUgY29sbGF0aW9uIG9yZGVyIGlzIDxzdHJvbmc+dF9pbnQzMjwvc3Ryb25nPi4gCioKKiBOb3RlLCBDb2xsYXRpb25FbGVtZW50SXRlcmF0b3Igc2hvdWxkIG5vdCBiZSBzdWJjbGFzc2VkLgoqIEBzZWUgICAgIENvbGxhdG9yCiogQHNlZSAgICAgUnVsZUJhc2VkQ29sbGF0b3IKKiBAdmVyc2lvbiAxLjggSmFuIDE2IDIwMDEKKi8KY2xhc3MgVV9JMThOX0FQSSBDb2xsYXRpb25FbGVtZW50SXRlcmF0b3IgOiBwdWJsaWMgVU9iamVjdCB7CnB1YmxpYzogCgogIC8vIENvbGxhdGlvbkVsZW1lbnRJdGVyYXRvciBwdWJsaWMgZGF0YSBtZW1iZXIgLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCgogIC8qKgogICogTlVMTE9SREVSIGluZGljYXRlcyB0aGF0IGFuIGVycm9yIGhhcyBvY2N1cmVkIHdoaWxlIHByb2Nlc3NpbmcKICAqIEBzdGFibGUgSUNVIDIuMAogICovCiAgc3RhdGljIGludDMyX3QgY29uc3QgTlVMTE9SREVSOwoKICAvLyBDb2xsYXRpb25FbGVtZW50SXRlcmF0b3IgcHVibGljIGNvbnN0cnVjdG9yL2Rlc3RydWN0b3IgLS0tLS0tLS0tLS0tLS0tLS0tLQoKICAvKioKICAqIENvcHkgY29uc3RydWN0b3IuCiAgKgogICogQHBhcmFtIG90aGVyICAgIHRoZSBvYmplY3QgdG8gYmUgY29waWVkIGZyb20KICAqIEBzdGFibGUgSUNVIDIuMAogICovCiAgQ29sbGF0aW9uRWxlbWVudEl0ZXJhdG9yKGNvbnN0IENvbGxhdGlvbkVsZW1lbnRJdGVyYXRvciYgb3RoZXIpOwoKICAvKiogCiAgKiBEZXN0cnVjdG9yCiAgKiBAc3RhYmxlIElDVSAyLjAKICAqLwogIH5Db2xsYXRpb25FbGVtZW50SXRlcmF0b3IoKTsKICAKICAvLyBDb2xsYXRpb25FbGVtZW50SXRlcmF0b3IgcHVibGljIG1ldGhvZHMgLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQoKICAvKioKICAqIFJldHVybnMgdHJ1ZSBpZiAib3RoZXIiIGlzIHRoZSBzYW1lIGFzICJ0aGlzIgogICoKICAqIEBwYXJhbSBvdGhlciAgICB0aGUgb2JqZWN0IHRvIGJlIGNvbXBhcmVkCiAgKiBAcmV0dXJuICAgICAgICAgdHJ1ZSBpZiAib3RoZXIiIGlzIHRoZSBzYW1lIGFzICJ0aGlzIgogICogQHN0YWJsZSBJQ1UgMi4wCiAgKi8KICBVQm9vbCBvcGVyYXRvcj09KGNvbnN0IENvbGxhdGlvbkVsZW1lbnRJdGVyYXRvciYgb3RoZXIpIGNvbnN0OwoKICAvKioKICAqIFJldHVybnMgdHJ1ZSBpZiAib3RoZXIiIGlzIG5vdCB0aGUgc2FtZSBhcyAidGhpcyIuCiAgKgogICogQHBhcmFtIG90aGVyICAgIHRoZSBvYmplY3QgdG8gYmUgY29tcGFyZWQKICAqIEByZXR1cm4gICAgICAgICB0cnVlIGlmICJvdGhlciIgaXMgbm90IHRoZSBzYW1lIGFzICJ0aGlzIgogICogQHN0YWJsZSBJQ1UgMi4wCiAgKi8KICBVQm9vbCBvcGVyYXRvciE9KGNvbnN0IENvbGxhdGlvbkVsZW1lbnRJdGVyYXRvciYgb3RoZXIpIGNvbnN0OwoKICAvKioKICAqIFJlc2V0cyB0aGUgY3Vyc29yIHRvIHRoZSBiZWdpbm5pbmcgb2YgdGhlIHN0cmluZy4KICAqIEBzdGFibGUgSUNVIDIuMAogICovCiAgdm9pZCByZXNldCh2b2lkKTsKICAgIAogIC8qKgogICogR2V0cyB0aGUgb3JkZXJpbmcgcHJpb3JpdHkgb2YgdGhlIG5leHQgY2hhcmFjdGVyIGluIHRoZSBzdHJpbmcuCiAgKiBAcGFyYW0gc3RhdHVzIHRoZSBlcnJvciBjb2RlIHN0YXR1cy4KICAqIEByZXR1cm4gdGhlIG5leHQgY2hhcmFjdGVyJ3Mgb3JkZXJpbmcuIG90aGVyd2lzZSByZXR1cm5zIE5VTExPUkRFUiBpZiBhbiAKICAqICAgICAgICAgZXJyb3IgaGFzIG9jY3VyZWQgb3IgaWYgdGhlIGVuZCBvZiBzdHJpbmcgaGFzIGJlZW4gcmVhY2hlZAogICogQHN0YWJsZSBJQ1UgMi4wCiAgKi8KICBpbnQzMl90IG5leHQoVUVycm9yQ29kZSYgc3RhdHVzKTsKCiAgLyoqCiAgKiBHZXQgdGhlIG9yZGVyaW5nIHByaW9yaXR5IG9mIHRoZSBwcmV2aW91cyBjb2xsYXRpb24gZWxlbWVudCBpbiB0aGUgc3RyaW5nLgogICogQHBhcmFtIHN0YXR1cyB0aGUgZXJyb3IgY29kZSBzdGF0dXMuCiAgKiBAcmV0dXJuIHRoZSBwcmV2aW91cyBlbGVtZW50J3Mgb3JkZXJpbmcuIG90aGVyd2lzZSByZXR1cm5zIE5VTExPUkRFUiBpZiBhbiAKICAqICAgICAgICAgZXJyb3IgaGFzIG9jY3VyZWQgb3IgaWYgdGhlIHN0YXJ0IG9mIHN0cmluZyBoYXMgYmVlbiByZWFjaGVkCiAgKiBAc3RhYmxlIElDVSAyLjAKICAqLwogIGludDMyX3QgcHJldmlvdXMoVUVycm9yQ29kZSYgc3RhdHVzKTsKCiAgLyoqCiAgKiBHZXRzIHRoZSBwcmltYXJ5IG9yZGVyIG9mIGEgY29sbGF0aW9uIG9yZGVyLgogICogQHBhcmFtIG9yZGVyIHRoZSBjb2xsYXRpb24gb3JkZXIKICAqIEByZXR1cm4gdGhlIHByaW1hcnkgb3JkZXIgb2YgYSBjb2xsYXRpb24gb3JkZXIuCiAgKiBAc3RhYmxlIElDVSAyLjAKICAqLwogIHN0YXRpYyBpbnQzMl90IHByaW1hcnlPcmRlcihpbnQzMl90IG9yZGVyKTsKCiAgLyoqCiAgKiBHZXRzIHRoZSBzZWNvbmRhcnkgb3JkZXIgb2YgYSBjb2xsYXRpb24gb3JkZXIuCiAgKiBAcGFyYW0gb3JkZXIgdGhlIGNvbGxhdGlvbiBvcmRlcgogICogQHJldHVybiB0aGUgc2Vjb25kYXJ5IG9yZGVyIG9mIGEgY29sbGF0aW9uIG9yZGVyLgogICogQHN0YWJsZSBJQ1UgMi4wCiAgKi8KICBzdGF0aWMgaW50MzJfdCBzZWNvbmRhcnlPcmRlcihpbnQzMl90IG9yZGVyKTsKCiAgLyoqCiAgKiBHZXRzIHRoZSB0ZXJ0aWFyeSBvcmRlciBvZiBhIGNvbGxhdGlvbiBvcmRlci4KICAqIEBwYXJhbSBvcmRlciB0aGUgY29sbGF0aW9uIG9yZGVyCiAgKiBAcmV0dXJuIHRoZSB0ZXJ0aWFyeSBvcmRlciBvZiBhIGNvbGxhdGlvbiBvcmRlci4KICAqIEBzdGFibGUgSUNVIDIuMAogICovCiAgc3RhdGljIGludDMyX3QgdGVydGlhcnlPcmRlcihpbnQzMl90IG9yZGVyKTsKCiAgLyoqCiAgKiBSZXR1cm4gdGhlIG1heGltdW0gbGVuZ3RoIG9mIGFueSBleHBhbnNpb24gc2VxdWVuY2VzIHRoYXQgZW5kIHdpdGggdGhlIAogICogc3BlY2lmaWVkIGNvbXBhcmlzb24gb3JkZXIuCiAgKiBAcGFyYW0gb3JkZXIgYSBjb2xsYXRpb24gb3JkZXIgcmV0dXJuZWQgYnkgcHJldmlvdXMgb3IgbmV4dC4KICAqIEByZXR1cm4gbWF4aW11bSBzaXplIG9mIHRoZSBleHBhbnNpb24gc2VxdWVuY2VzIGVuZGluZyB3aXRoIHRoZSBjb2xsYXRpb24gCiAgKiAgICAgICAgIGVsZW1lbnQgb3IgMSBpZiBjb2xsYXRpb24gZWxlbWVudCBkb2VzIG5vdCBvY2N1ciBhdCB0aGUgZW5kIG9mIGFueSAKICAqICAgICAgICAgZXhwYW5zaW9uIHNlcXVlbmNlCiAgKiBAc3RhYmxlIElDVSAyLjAKICAqLwogIGludDMyX3QgZ2V0TWF4RXhwYW5zaW9uKGludDMyX3Qgb3JkZXIpIGNvbnN0OwoKICAvKioKICAqIEdldHMgdGhlIGNvbXBhcmlzb24gb3JkZXIgaW4gdGhlIGRlc2lyZWQgc3RyZW5ndGguIElnbm9yZSB0aGUgb3RoZXIKICAqIGRpZmZlcmVuY2VzLgogICogQHBhcmFtIG9yZGVyIFRoZSBvcmRlciB2YWx1ZQogICogQHN0YWJsZSBJQ1UgMi4wCiAgKi8KICBpbnQzMl90IHN0cmVuZ3RoT3JkZXIoaW50MzJfdCBvcmRlcikgY29uc3Q7CgogIC8qKgogICogU2V0cyB0aGUgc291cmNlIHN0cmluZy4KICAqIEBwYXJhbSBzdHIgdGhlIHNvdXJjZSBzdHJpbmcuCiAgKiBAcGFyYW0gc3RhdHVzIHRoZSBlcnJvciBjb2RlIHN0YXR1cy4KICAqIEBzdGFibGUgSUNVIDIuMAogICovCiAgdm9pZCBzZXRUZXh0KGNvbnN0IFVuaWNvZGVTdHJpbmcmIHN0ciwgVUVycm9yQ29kZSYgc3RhdHVzKTsKCiAgLyoqCiAgKiBTZXRzIHRoZSBzb3VyY2Ugc3RyaW5nLgogICogQHBhcmFtIHN0ciB0aGUgc291cmNlIGNoYXJhY3RlciBpdGVyYXRvci4KICAqIEBwYXJhbSBzdGF0dXMgdGhlIGVycm9yIGNvZGUgc3RhdHVzLgogICogQHN0YWJsZSBJQ1UgMi4wCiAgKi8KICB2b2lkIHNldFRleHQoQ2hhcmFjdGVySXRlcmF0b3ImIHN0ciwgVUVycm9yQ29kZSYgc3RhdHVzKTsKCiAgLyoqCiAgKiBDaGVja3MgaWYgYSBjb21wYXJpc29uIG9yZGVyIGlzIGlnbm9yYWJsZS4KICAqIEBwYXJhbSBvcmRlciB0aGUgY29sbGF0aW9uIG9yZGVyLgogICogQHJldHVybiBUUlVFIGlmIGEgY2hhcmFjdGVyIGlzIGlnbm9yYWJsZSwgRkFMU0Ugb3RoZXJ3aXNlLgogICogQHN0YWJsZSBJQ1UgMi4wCiAgKi8KICBzdGF0aWMgVUJvb2wgaXNJZ25vcmFibGUoaW50MzJfdCBvcmRlcik7CgogIC8qKgogICogR2V0cyB0aGUgb2Zmc2V0IG9mIHRoZSBjdXJyZW50bHkgcHJvY2Vzc2VkIGNoYXJhY3RlciBpbiB0aGUgc291cmNlIHN0cmluZy4KICAqIEByZXR1cm4gdGhlIG9mZnNldCBvZiB0aGUgY2hhcmFjdGVyLgogICogQHN0YWJsZSBJQ1UgMi4wCiAgKi8KICBpbnQzMl90IGdldE9mZnNldCh2b2lkKSBjb25zdDsKCiAgLyoqCiAgKiBTZXRzIHRoZSBvZmZzZXQgb2YgdGhlIGN1cnJlbnRseSBwcm9jZXNzZWQgY2hhcmFjdGVyIGluIHRoZSBzb3VyY2Ugc3RyaW5nLgogICogQHBhcmFtIG5ld09mZnNldCB0aGUgbmV3IG9mZnNldC4KICAqIEBwYXJhbSBzdGF0dXMgdGhlIGVycm9yIGNvZGUgc3RhdHVzLgogICogQHJldHVybiB0aGUgb2Zmc2V0IG9mIHRoZSBjaGFyYWN0ZXIuCiAgKiBAc3RhYmxlIElDVSAyLjAKICAqLwogIHZvaWQgc2V0T2Zmc2V0KGludDMyX3QgbmV3T2Zmc2V0LCBVRXJyb3JDb2RlJiBzdGF0dXMpOwoKICAvKioKICAgKiBJQ1UgInBvb3IgbWFuJ3MgUlRUSSIsIHJldHVybnMgYSBVQ2xhc3NJRCBmb3IgdGhlIGFjdHVhbCBjbGFzcy4KICAgKgogICAqIEBkcmFmdCBJQ1UgMi4yCiAgICovCiAgdmlydHVhbCBpbmxpbmUgVUNsYXNzSUQgZ2V0RHluYW1pY0NsYXNzSUQoKSBjb25zdCB7IHJldHVybiBnZXRTdGF0aWNDbGFzc0lEKCk7IH0KCiAgLyoqCiAgICogSUNVICJwb29yIG1hbidzIFJUVEkiLCByZXR1cm5zIGEgVUNsYXNzSUQgZm9yIHRoaXMgY2xhc3MuCiAgICoKICAgKiBAZHJhZnQgSUNVIDIuMgogICAqLwogIHN0YXRpYyBpbmxpbmUgVUNsYXNzSUQgZ2V0U3RhdGljQ2xhc3NJRCgpIHsgcmV0dXJuIChVQ2xhc3NJRCkmZmdDbGFzc0lEOyB9Cgpwcm90ZWN0ZWQ6CiAgCiAgLy8gQ29sbGF0aW9uRWxlbWVudEl0ZXJhdG9yIHByb3RlY3RlZCBjb25zdHJ1Y3RvcnMgLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KICAvKioKICAqIEBzdGFibGUgSUNVIDIuMAogICovCiAgZnJpZW5kIGNsYXNzIFJ1bGVCYXNlZENvbGxhdG9yOwoKICAvKioKICAqIENvbGxhdGlvbkVsZW1lbnRJdGVyYXRvciBjb25zdHJ1Y3Rvci4gVGhpcyB0YWtlcyB0aGUgc291cmNlIHN0cmluZyBhbmQgdGhlIAogICogY29sbGF0aW9uIG9iamVjdC4gVGhlIGN1cnNvciB3aWxsIHdhbGsgdGhydSB0aGUgc291cmNlIHN0cmluZyBiYXNlZCBvbiB0aGUgCiAgKiBwcmVkZWZpbmVkIGNvbGxhdGlvbiBydWxlcy4gSWYgdGhlIHNvdXJjZSBzdHJpbmcgaXMgZW1wdHksIE5VTExPUkRFUiB3aWxsIAogICogYmUgcmV0dXJuZWQgb24gdGhlIGNhbGxzIHRvIG5leHQoKS4KICAqIEBwYXJhbSBzb3VyY2VUZXh0ICAgIHRoZSBzb3VyY2Ugc3RyaW5nLgogICogQHBhcmFtIG9yZGVyICAgICAgICAgdGhlIGNvbGxhdGlvbiBvYmplY3QuCiAgKiBAcGFyYW0gc3RhdHVzICAgICAgICB0aGUgZXJyb3IgY29kZSBzdGF0dXMuCiAgKiBAc3RhYmxlIElDVSAyLjAKICAqLwogIENvbGxhdGlvbkVsZW1lbnRJdGVyYXRvcihjb25zdCBVbmljb2RlU3RyaW5nJiBzb3VyY2VUZXh0LAogICAgICAgICAgICAgICAgICAgICAgICAgICBjb25zdCBSdWxlQmFzZWRDb2xsYXRvciogb3JkZXIsIFVFcnJvckNvZGUmIHN0YXR1cyk7CgogIC8qKgogICogQ29sbGF0aW9uRWxlbWVudEl0ZXJhdG9yIGNvbnN0cnVjdG9yLiBUaGlzIHRha2VzIHRoZSBzb3VyY2Ugc3RyaW5nIGFuZCB0aGUgCiAgKiBjb2xsYXRpb24gb2JqZWN0LiAgVGhlIGN1cnNvciB3aWxsIHdhbGsgdGhydSB0aGUgc291cmNlIHN0cmluZyBiYXNlZCBvbiB0aGUgCiAgKiBwcmVkZWZpbmVkIGNvbGxhdGlvbiBydWxlcy4gIElmIHRoZSBzb3VyY2Ugc3RyaW5nIGlzIGVtcHR5LCBOVUxMT1JERVIgd2lsbCAKICAqIGJlIHJldHVybmVkIG9uIHRoZSBjYWxscyB0byBuZXh0KCkuCiAgKiBAcGFyYW0gc291cmNlVGV4dCAgICB0aGUgc291cmNlIHN0cmluZy4KICAqIEBwYXJhbSBvcmRlciAgICAgICAgIHRoZSBjb2xsYXRpb24gb2JqZWN0LgogICogQHBhcmFtIHN0YXR1cyAgICAgICAgdGhlIGVycm9yIGNvZGUgc3RhdHVzLgogICogQHN0YWJsZSBJQ1UgMi4wCiAgKi8KICBDb2xsYXRpb25FbGVtZW50SXRlcmF0b3IoY29uc3QgQ2hhcmFjdGVySXRlcmF0b3ImIHNvdXJjZVRleHQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IFJ1bGVCYXNlZENvbGxhdG9yKiBvcmRlciwgVUVycm9yQ29kZSYgc3RhdHVzKTsKICAKICAvLyBDb2xsYXRpb25FbGVtZW50SXRlcmF0b3IgcHJvdGVjdGVkIG1ldGhvZHMgLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQoKICAvKioKICAqIEFzc2lnbm1lbnQgb3BlcmF0b3IKICAqCiAgKiBAcGFyYW0gb3RoZXIgICAgdGhlIG9iamVjdCB0byBiZSBjb3BpZWQKICAqIEBzdGFibGUgSUNVIDIuMAogICovCiAgY29uc3QgQ29sbGF0aW9uRWxlbWVudEl0ZXJhdG9yJgogICAgICAgICAgICAgICAgICAgICAgICAgICAgICBvcGVyYXRvcj0oY29uc3QgQ29sbGF0aW9uRWxlbWVudEl0ZXJhdG9yJiBvdGhlcik7Cgpwcml2YXRlOgoKICAvLyBDb2xsYXRpb25FbGVtZW50SXRlcmF0b3IgcHJpdmF0ZSBkYXRhIG1lbWJlcnMgLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQoKICAvKioKICAqIERhdGEgd3JhcHBlciBmb3IgY29sbGF0aW9uIGVsZW1lbnRzCiAgKi8KICBVQ29sbGF0aW9uRWxlbWVudHMgKm1fZGF0YV87CgogIC8qKgogICogSW5kaWNhdGVzIGlmIG1fZGF0YV8gYmVsb25ncyB0byB0aGlzIG9iamVjdC4KICAqLwogIFVCb29sIGlzRGF0YU93bmVkXzsKCiAgLyoqCiAgICogVGhlIGFkZHJlc3Mgb2YgdGhpcyBzdGF0aWMgY2xhc3MgdmFyaWFibGUgc2VydmVzIGFzIHRoaXMgY2xhc3MncyBJRAogICAqIGZvciBJQ1UgInBvb3IgbWFuJ3MgUlRUSSIuCiAgICovCiAgc3RhdGljIGNvbnN0IGNoYXIgZmdDbGFzc0lEOwp9OwoKLy8gQ29sbGF0aW9uRWxlbWVudEl0ZXJhdG9yIGlubGluZSBtZXRob2QgZGVmaW5hdGlvbiAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQoKLyoqCiogR2V0IHRoZSBwcmltYXJ5IG9yZGVyIG9mIGEgY29sbGF0aW9uIG9yZGVyLgoqIEBwYXJhbSBvcmRlciB0aGUgY29sbGF0aW9uIG9yZGVyCiogQHJldHVybiB0aGUgcHJpbWFyeSBvcmRlciBvZiBhIGNvbGxhdGlvbiBvcmRlci4KKi8KaW5saW5lIGludDMyX3QgQ29sbGF0aW9uRWxlbWVudEl0ZXJhdG9yOjpwcmltYXJ5T3JkZXIoaW50MzJfdCBvcmRlcikKewogIG9yZGVyICY9IFJ1bGVCYXNlZENvbGxhdG9yOjpQUklNQVJZT1JERVJNQVNLOwogIHJldHVybiAob3JkZXIgPj4gUnVsZUJhc2VkQ29sbGF0b3I6OlBSSU1BUllPUkRFUlNISUZUKTsKfQoKLyoqCiogR2V0IHRoZSBzZWNvbmRhcnkgb3JkZXIgb2YgYSBjb2xsYXRpb24gb3JkZXIuCiogQHBhcmFtIG9yZGVyIHRoZSBjb2xsYXRpb24gb3JkZXIKKiBAcmV0dXJuIHRoZSBzZWNvbmRhcnkgb3JkZXIgb2YgYSBjb2xsYXRpb24gb3JkZXIuCiovCmlubGluZSBpbnQzMl90IENvbGxhdGlvbkVsZW1lbnRJdGVyYXRvcjo6c2Vjb25kYXJ5T3JkZXIoaW50MzJfdCBvcmRlcikKewogIG9yZGVyID0gb3JkZXIgJiBSdWxlQmFzZWRDb2xsYXRvcjo6U0VDT05EQVJZT1JERVJNQVNLOwogIHJldHVybiAob3JkZXIgPj4gUnVsZUJhc2VkQ29sbGF0b3I6OlNFQ09OREFSWU9SREVSU0hJRlQpOwp9CgovKioKKiBHZXQgdGhlIHRlcnRpYXJ5IG9yZGVyIG9mIGEgY29sbGF0aW9uIG9yZGVyLgoqIEBwYXJhbSBvcmRlciB0aGUgY29sbGF0aW9uIG9yZGVyCiogQHJldHVybiB0aGUgdGVydGlhcnkgb3JkZXIgb2YgYSBjb2xsYXRpb24gb3JkZXIuCiovCmlubGluZSBpbnQzMl90IENvbGxhdGlvbkVsZW1lbnRJdGVyYXRvcjo6dGVydGlhcnlPcmRlcihpbnQzMl90IG9yZGVyKQp7CiAgcmV0dXJuIChvcmRlciAmPSBSdWxlQmFzZWRDb2xsYXRvcjo6VEVSVElBUllPUkRFUk1BU0spOwp9CgppbmxpbmUgaW50MzJfdCBDb2xsYXRpb25FbGVtZW50SXRlcmF0b3I6OmdldE1heEV4cGFuc2lvbihpbnQzMl90IG9yZGVyKSBjb25zdAp7CiAgcmV0dXJuIHVjb2xfZ2V0TWF4RXhwYW5zaW9uKG1fZGF0YV8sICh1aW50MzJfdClvcmRlcik7Cn0KCmlubGluZSBVQm9vbCBDb2xsYXRpb25FbGVtZW50SXRlcmF0b3I6OmlzSWdub3JhYmxlKGludDMyX3Qgb3JkZXIpCnsKICByZXR1cm4gKHByaW1hcnlPcmRlcihvcmRlcikgPT0gUnVsZUJhc2VkQ29sbGF0b3I6OlBSSU1JR05PUkFCTEUpOwp9CgpVX05BTUVTUEFDRV9FTkQKCiNlbmRpZiAvKiAjaWYgIVVDT05GSUdfTk9fQ09MTEFUSU9OICovCgojZW5kaWYK