LyoKJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJQolICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAlCiUgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICUKJSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJQolICAgICAgICAgICAgICAgICAgICAgICAgIEREREQgICAgICAgSiAgViAgIFYgIFUgICBVICAgICAgICAgICAgICAgICAgICAgICAgICAlCiUgICAgICAgICAgICAgICAgICAgICAgICAgRCAgIEQgICAgICBKICBWICAgViAgVSAgIFUgICAgICAgICAgICAgICAgICAgICAgICAgICUKJSAgICAgICAgICAgICAgICAgICAgICAgICBEICAgRCAgICAgIEogIFYgICBWICBVICAgVSAgICAgICAgICAgICAgICAgICAgICAgICAgJQolICAgICAgICAgICAgICAgICAgICAgICAgIEQgICBEICBKICAgSiAgIFYgViAgIFUgICBVICAgICAgICAgICAgICAgICAgICAgICAgICAlCiUgICAgICAgICAgICAgICAgICAgICAgICAgRERERCAgICBKSkogICAgIFYgICAgIFVVVSAgICAgICAgICAgICAgICAgICAgICAgICAgICUKJSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJQolICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAlCiUgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFJlYWQgRGpWdSBJbWFnZXMuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICUKJSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJQolICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgU29mdHdhcmUgRGVzaWduICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAlCiUgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEpvaG4gQ3Jpc3R5ICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICUKJSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEp1bHkgMTk5MiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJQolICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAlCiUgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICUKJSAgQ29weXJpZ2h0IDE5OTktMjAxMiBJbWFnZU1hZ2ljayBTdHVkaW8gTExDLCBhIG5vbi1wcm9maXQgb3JnYW5pemF0aW9uICAgICAgJQolICBkZWRpY2F0ZWQgdG8gbWFraW5nIHNvZnR3YXJlIGltYWdpbmcgc29sdXRpb25zIGZyZWVseSBhdmFpbGFibGUuICAgICAgICAgICAlCiUgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICUKJSAgWW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLiAgWW91IG1heSAgJQolICBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0ICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAlCiUgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICUKJSAgICBodHRwOi8vd3d3LmltYWdlbWFnaWNrLm9yZy9zY3JpcHQvbGljZW5zZS5waHAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJQolICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAlCiUgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUgICAgICAgICUKJSAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywgICAgICAgICAgJQolICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4gICAlCiUgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQgICAgICAgICUKJSAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJQolICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAlCiUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUKJQolCiovCgwKLyoKICBJbmNsdWRlIGRlY2xhcmF0aW9ucy4KKi8KI2luY2x1ZGUgIk1hZ2lja0NvcmUvc3R1ZGlvLmgiCiNpbmNsdWRlICJNYWdpY2tDb3JlL2Jsb2IuaCIKI2luY2x1ZGUgIk1hZ2lja0NvcmUvYmxvYi1wcml2YXRlLmgiCiNpbmNsdWRlICJNYWdpY2tDb3JlL2NhY2hlLmgiCiNpbmNsdWRlICJNYWdpY2tDb3JlL2NvbG9ybWFwLmgiCiNpbmNsdWRlICJNYWdpY2tDb3JlL2NvbnN0aXR1dGUuaCIKI2luY2x1ZGUgIk1hZ2lja0NvcmUvZXhjZXB0aW9uLmgiCiNpbmNsdWRlICJNYWdpY2tDb3JlL2V4Y2VwdGlvbi1wcml2YXRlLmgiCiNpbmNsdWRlICJNYWdpY2tDb3JlL2xpc3QuaCIKI2luY2x1ZGUgIk1hZ2lja0NvcmUvbWFnaWNrLmgiCiNpbmNsdWRlICJNYWdpY2tDb3JlL21lbW9yeV8uaCIKI2luY2x1ZGUgIk1hZ2lja0NvcmUvbW9uaXRvci5oIgojaW5jbHVkZSAiTWFnaWNrQ29yZS9tb25pdG9yLXByaXZhdGUuaCIKI2luY2x1ZGUgIk1hZ2lja0NvcmUvcGl4ZWwtYWNjZXNzb3IuaCIKI2luY2x1ZGUgIk1hZ2lja0NvcmUvcXVhbnR1bS1wcml2YXRlLmgiCiNpbmNsdWRlICJNYWdpY2tDb3JlL3N0YXRpYy5oIgojaW5jbHVkZSAiTWFnaWNrQ29yZS9zdHJpbmdfLmgiCiNpbmNsdWRlICJNYWdpY2tDb3JlL21vZHVsZS5oIgojaWYgZGVmaW5lZChNQUdJQ0tDT1JFX0RKVlVfREVMRUdBVEUpCiNpbmNsdWRlIDxsaWJkanZ1L2RkanZ1YXBpLmg+CiNlbmRpZgoMCi8qCiUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUKJSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJQolICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAlCiUgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICUKJSAgIEkgcyBEIEogViBVICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJQolICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAlCiUgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICUKJSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJQolJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlCiUKJSAgSXNESlZVKCkgcmV0dXJucyBNYWdpY2tUcnVlIGlmIHRoZSBpbWFnZSBmb3JtYXQgdHlwZSwgaWRlbnRpZmllZCBieSB0aGUKJSAgbWFnaWNrIHN0cmluZywgaXMgREpWVS4KJQolICBUaGUgZm9ybWF0IG9mIHRoZSBJc0RKVlUgbWV0aG9kIGlzOgolCiUgICAgICBNYWdpY2tCb29sZWFuVHlwZSBJc0RKVlUoY29uc3QgdW5zaWduZWQgY2hhciAqbWFnaWNrLGNvbnN0IHNpemVfdCBsZW5ndGgpCiUKJSAgQSBkZXNjcmlwdGlvbiBvZiBlYWNoIHBhcmFtZXRlciBmb2xsb3dzOgolCiUgICAgbyBtYWdpY2s6IGNvbXBhcmUgaW1hZ2UgZm9ybWF0IHBhdHRlcm4gYWdhaW5zdCB0aGVzZSBieXRlcy4KJQolICAgIG8gbGVuZ3RoOiBTcGVjaWZpZXMgdGhlIGxlbmd0aCBvZiB0aGUgbWFnaWNrIHN0cmluZy4KJQoqLwpzdGF0aWMgTWFnaWNrQm9vbGVhblR5cGUgSXNESlZVKGNvbnN0IHVuc2lnbmVkIGNoYXIgKm1hZ2ljayxjb25zdCBzaXplX3QgbGVuZ3RoKQp7CiAgaWYgKGxlbmd0aCA8IDgpCiAgICByZXR1cm4oTWFnaWNrRmFsc2UpOwogIGlmIChtZW1jbXAobWFnaWNrLCJBVCZURk9STSIsOCkgPT0gMCkKICAgIHJldHVybihNYWdpY2tUcnVlKTsKICByZXR1cm4oTWFnaWNrRmFsc2UpOwp9CgwKI2lmIGRlZmluZWQoTUFHSUNLQ09SRV9ESlZVX0RFTEVHQVRFKQovKgolJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlCiUgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICUKJSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJQolICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAlCiUgICBSIGUgYSBkIEQgSiBWIFUgSSBtIGEgZyBlICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICUKJSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJQolICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAlCiUgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICUKJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJQolCiUgIFJlYWRESlZVSW1hZ2UoKSByZWFkcyBESlZVIGltYWdlIGFuZCByZXR1cm5zIGl0LiAgSXQgYWxsb2NhdGVzIHRoZSBtZW1vcnkKJSAgbmVjZXNzYXJ5IGZvciB0aGUgbmV3IEltYWdlIHN0cnVjdHVyZSBhbmQgcmV0dXJucyBhIHBvaW50ZXIgdG8gdGhlIG5ldwolICBpbWFnZSBvciBzZXQgb2YgaW1hZ2VzLgolCiUgIFRoZSBmb3JtYXQgb2YgdGhlIFJlYWRESlZVSW1hZ2UgbWV0aG9kIGlzOgolCiUgICAgICBJbWFnZSAqUmVhZERKVlVJbWFnZShjb25zdCBJbWFnZUluZm8gKmltYWdlX2luZm8sCiUgICAgICAgIEV4Y2VwdGlvbkluZm8gKmV4Y2VwdGlvbikKJQolICBBIGRlc2NyaXB0aW9uIG9mIGVhY2ggcGFyYW1ldGVyIGZvbGxvd3M6CiUKJSAgICBvIGltYWdlX2luZm86IHRoZSBpbWFnZSBpbmZvLgolCiUgICAgbyBleGNlcHRpb246IHJldHVybiBhbnkgZXJyb3JzIG9yIHdhcm5pbmdzIGluIHRoaXMgc3RydWN0dXJlLgolCiovCgojaWYgZGVmaW5lZChfX2NwbHVzcGx1cykgfHwgZGVmaW5lZChjX3BsdXNwbHVzKQpleHRlcm4gIkMiIHsKI2VuZGlmCgp0eXBlZGVmIHN0cnVjdCBfTG9hZENvbnRleHQKICAgTG9hZENvbnRleHQ7CgpzdHJ1Y3QgX0xvYWRDb250ZXh0CnsKICBkZGp2dV9jb250ZXh0X3QqIGNvbnRleHQ7CiAgZGRqdnVfZG9jdW1lbnRfdCAqZG9jdW1lbnQ7CiAgZGRqdnVfcGFnZV90ICpwYWdlOwogIGludCBzdHJlYW1pZDsKICBpbnQgcGFnZXM7CiAgSW1hZ2UgKmltYWdlOwp9OwoKI2RlZmluZSBCTE9DS1NJWkUgIDY1NTM2CiNpZiAwCnN0YXRpYyB2b2lkCnB1bXBfZGF0YShJbWFnZSAqaW1hZ2UsIExvYWRDb250ZXh0KiBsYykKewogICAgICAgIGludCBibG9ja3NpemUgPSBCTE9DS1NJWkU7CiAgICAgICAgY2hhciBkYXRhW0JMT0NLU0laRV07CiAgICAgICAgaW50IHNpemU7CgogICAgICAgIC8qIGkgbWlnaHQgY2hlY2sgZm9yIGEgY29uZGl0aW9uISAqLwogICAgICAgIHdoaWxlICgoc2l6ZSA9IChzaXplX3QpIFJlYWRCbG9iKGltYWdlLChzaXplX3QpIGJsb2Nrc2l6ZSxkYXRhKSkgPT0gYmxvY2tzaXplKSB7CiAgICAgICAgICAgICAgICBkZGp2dV9zdHJlYW1fd3JpdGUobGMtPmRvY3VtZW50LCBsYy0+c3RyZWFtaWQsIGRhdGEsIHNpemUpOwogICAgICAgIH0KICAgICAgICBpZiAoc2l6ZSkKICAgICAgICAgICAgICAgIGRkanZ1X3N0cmVhbV93cml0ZShsYy0+ZG9jdW1lbnQsIGxjLT5zdHJlYW1pZCwgZGF0YSwgc2l6ZSk7CiAgICAgICAgZGRqdnVfc3RyZWFtX2Nsb3NlKGxjLT5kb2N1bWVudCwgbGMtPnN0cmVhbWlkLCAwKTsKfQojZW5kaWYKCi8qIHJldHVybnMgTlVMTCBvbmx5IGFmdGVyIGFsbCBpcyBkZWxpdmVyZWQhICovCnN0YXRpYyBkZGp2dV9tZXNzYWdlX3QqCnB1bXBfZGF0YV91bnRpbF9tZXNzYWdlKExvYWRDb250ZXh0ICpsYyxJbWFnZSAqaW1hZ2UpIC8qIGRkanZ1X2NvbnRleHRfdCAqY29udGV4dCwgdHlwZSBkZGp2dV9kb2N1bWVudF90eXBlX3QgKi8KewogICAgICAgIHNpemVfdCBibG9ja3NpemUgPSBCTE9DS1NJWkU7CiAgICAgICAgdW5zaWduZWQgY2hhciBkYXRhW0JMT0NLU0laRV07CiAgICAgICAgc2l6ZV90IHNpemU7CiAgICAgICAgZGRqdnVfbWVzc2FnZV90ICptZXNzYWdlOwoKICAgICAgICAvKiBpIG1pZ2h0IGNoZWNrIGZvciBhIGNvbmRpdGlvbiEgKi8KICAgICAgICBzaXplPTA7CiAgICAgICAgd2hpbGUgKCEobWVzc2FnZSA9IGRkanZ1X21lc3NhZ2VfcGVlayhsYy0+Y29udGV4dCkpCiAgICAgICAgICAgICAgICYmIChzaXplID0gKHNpemVfdCkgUmVhZEJsb2IoaW1hZ2UsKHNpemVfdCkgYmxvY2tzaXplLGRhdGEpKSA9PSBibG9ja3NpemUpIHsKICAgICAgICAgICAgICAgIGRkanZ1X3N0cmVhbV93cml0ZShsYy0+ZG9jdW1lbnQsIGxjLT5zdHJlYW1pZCwgKGNoYXIgKikgZGF0YSwgc2l6ZSk7CiAgICAgICAgfQogICAgICAgIGlmIChtZXNzYWdlKQogICAgICAgICAgICAgICAgcmV0dXJuIG1lc3NhZ2U7CiAgICAgICAgaWYgKHNpemUpCiAgICAgICAgICAgICAgICBkZGp2dV9zdHJlYW1fd3JpdGUobGMtPmRvY3VtZW50LCBsYy0+c3RyZWFtaWQsIChjaGFyICopIGRhdGEsIHNpemUpOwogICAgICAgIGRkanZ1X3N0cmVhbV9jbG9zZShsYy0+ZG9jdW1lbnQsIGxjLT5zdHJlYW1pZCwgMCk7CiAgICAgICAgcmV0dXJuIE5VTEw7Cn0KI2RlZmluZSBERUJVRyAwCgojaWYgREVCVUcKc3RhdGljIGNvbnN0IGNoYXIqCm1lc3NhZ2VfdGFnX25hbWUoZGRqdnVfbWVzc2FnZV90YWdfdCB0YWcpCnsKICAgc3RhdGljIGNoYXIqIG5hbWVzW10gPQogICAgICB7CiAgICAgICAgICJFUlJPUiIsCiAgICAgICAgICJJTkZPIiwKICAgICAgICAgIk5FV1NUUkVBTSIsCiAgICAgICAgICJET0NJTkZPIiwKICAgICAgICAgIlBBR0VJTkZPIiwKICAgICAgICAgIlJFTEFZT1VUIiwKICAgICAgICAgIlJFRElTUExBWSIsCiAgICAgICAgICJDSFVOSyIsCiAgICAgICAgICJUSFVNQk5BSUwiLAogICAgICAgICAiUFJPR1JFU1MiLAogICAgICB9OwogICBpZiAodGFnIDw9IERESlZVX1BST0dSRVNTKQogICAgICByZXR1cm4gbmFtZXNbdGFnXTsKICAgZWxzZSB7CiAgICAgIC8qIGJhcmshICovCiAgICAgIHJldHVybiAwOwogICB9Cn0KI2VuZGlmCgovKiB3cml0ZSBvdXQgbmljZSBpbmZvIG9uIHRoZSBtZXNzYWdlLAogKiBhbmQgc3RvcmUgaW4gKnVzZXIqIGRhdGEgdGhlIGluZm8gb24gcHJvZ3Jlc3MuCiAqICovCmludApwcm9jZXNzX21lc3NhZ2UoZGRqdnVfbWVzc2FnZV90ICptZXNzYWdlKQp7CgojaWYgMAogICBkZGp2dV9jb250ZXh0X3QqIGNvbnRleHQ9IG1lc3NhZ2UtPm1fYW55LmNvbnRleHQ7CiNlbmRpZgoKICAgaWYgKCEgbWVzc2FnZSkKICAgICAgcmV0dXJuKC0xKTsKI2lmIERFQlVHCiAgIHByaW50ZigiKioqICVzOiAlcy5cbiIsX19GVU5DVElPTl9fLCBtZXNzYWdlX3RhZ19uYW1lKG1lc3NhZ2UtPm1fYW55LnRhZykpOwojZW5kaWYKCgogICBzd2l0Y2ggKG1lc3NhZ2UtPm1fYW55LnRhZyl7CiAgIGNhc2UgRERKVlVfRE9DSU5GTzoKICAgewogICAgICBkZGp2dV9kb2N1bWVudF90KiBkb2N1bWVudD0gbWVzc2FnZS0+bV9hbnkuZG9jdW1lbnQ7CiAgICAgIC8qIGRkanZ1X2RvY3VtZW50X2RlY29kaW5nX3N0YXR1cyAgaXMgc2V0IGJ5IGxpYmRqdnUhICovCiAgICAgIC8qIHdlIGhhdmUgc29tZSBpbmZvIG9uIHRoZSBkb2N1bWVudCAgKi8KICAgICAgTG9hZENvbnRleHQgKmxjID0gKExvYWRDb250ZXh0ICopIGRkanZ1X2RvY3VtZW50X2dldF91c2VyX2RhdGEoZG9jdW1lbnQpOwogICAgICBsYy0+cGFnZXMgPSBkZGp2dV9kb2N1bWVudF9nZXRfcGFnZW51bShkb2N1bWVudCk7CiNpZiBERUJVRwogICAgICBwcmludGYoInRoZSBkb2MgaGFzICVkIHBhZ2VzXG4iLCBkZGp2dV9kb2N1bWVudF9nZXRfcGFnZW51bShkb2N1bWVudCkpOwojZW5kaWYKICAgICAgYnJlYWs7CiAgIH0KICAgY2FzZSBEREpWVV9DSFVOSzoKI2lmIERFQlVHCiAgICAgICAgICAgcHJpbnRmKCJ0aGUgbmFtZSBvZiB0aGUgY2h1bmsgaXM6ICVzXG4iLCBtZXNzYWdlLT5tX2NodW5rLmNodW5raWQpOwojZW5kaWYKICAgICAgICAgICBicmVhazsKCgogICBjYXNlIERESlZVX1JFTEFZT1VUOgogICBjYXNlIERESlZVX1BBR0VJTkZPOgogICB7CiNpZiAwCiAgICAgIGRkanZ1X3BhZ2VfdCogcGFnZSA9IG1lc3NhZ2UtPm1fYW55LnBhZ2U7CiAgICAgIHBhZ2VfaW5mbyogaW5mbyA9IGRkanZ1X3BhZ2VfZ2V0X3VzZXJfZGF0YShwYWdlKTsKCiAgICAgIHByaW50ZigicGFnZSBkZWNvZGluZyBzdGF0dXM6ICVkICVzJXMlc1xuIiwKICAgICAgICAgICAgIGRkanZ1X3BhZ2VfZGVjb2Rpbmdfc3RhdHVzKHBhZ2UpLAogICAgICAgICAgICAgc3RhdHVzX2NvbG9yLCBzdGF0dXNfbmFtZShkZGp2dV9wYWdlX2RlY29kaW5nX3N0YXR1cyhwYWdlKSksIGNvbG9yX3Jlc2V0KTsKCiAgICAgIHByaW50ZigidGhlIHBhZ2UgTEFZT1VUIGNoYW5nZWQ6IHdpZHRoIHggaGVpZ2h0OiAlZCB4ICVkIEAgJWQgZHBpLiBWZXJzaW9uICVkLCB0eXBlICVkXG4iLAogICAgICAgICAgICAgLy8gcHJpbnRmKCJwYWdlIGluZm86XG4gd2lkdGggeCBoZWlnaHQ6ICVkIHggJWQgQCAlZCBkcGksIHZlcnNpb24gJWQsIHR5cGUgJWRcbiIsCiAgICAgICAgICAgICBkZGp2dV9wYWdlX2dldF93aWR0aChwYWdlKSwKICAgICAgICAgICAgIGRkanZ1X3BhZ2VfZ2V0X2hlaWdodChwYWdlKSwKICAgICAgICAgICAgIGRkanZ1X3BhZ2VfZ2V0X3Jlc29sdXRpb24ocGFnZSksCiAgICAgICAgICAgICBkZGp2dV9wYWdlX2dldF92ZXJzaW9uKHBhZ2UpLAogICAgICAgICAgICAgLyogRERKVlVfUEFHRVRZUEVfQklUT05BTCAqLwogICAgICAgICAgICAgZGRqdnVfcGFnZV9nZXRfdHlwZShwYWdlKSk7CgogICAgICBpbmZvLT5pbmZvID0gMTsKI2VuZGlmCiAgICAgIGJyZWFrOwogICB9CgogICBjYXNlIERESlZVX1JFRElTUExBWToKICAgewoKI2lmIDAKICAgIGRkanZ1X3BhZ2VfdCogcGFnZSA9IG1lc3NhZ2UtPm1fYW55LnBhZ2U7CiAgICAgIHBhZ2VfaW5mbyogaW5mbyA9IGRkanZ1X3BhZ2VfZ2V0X3VzZXJfZGF0YShwYWdlKTsKCiAgICAgIHByaW50ZigidGhlIHBhZ2UgY2FuL3Nob3VsZCBiZSBSRURJU1BMQVlFRFxuIik7CiAgICAgIGluZm8tPmRpc3BsYXkgPSAxOwojZW5kaWYKICAgICAgYnJlYWs7CiAgIH0KCiAgIGNhc2UgRERKVlVfUFJPR1JFU1M6CiNpZiBERUJVRwogICAgICAgICAgIHByaW50ZigiUFJPR1JFU1M6XG4iKTsKI2VuZGlmCiAgICAgICAgICAgYnJlYWs7CiAgIGNhc2UgRERKVlVfRVJST1I6CiAgICAgICAgICAgcHJpbnRmKCJzaW1wbHkgRVJST1IhXG4gbWVzc2FnZTpcdCVzXG5mdW5jdGlvbjpcdCVzKGZpbGUgJXMpXG5saW5lbm86XHQlZFxuIiwKICAgICAgICAgICAgICAgICAgbWVzc2FnZS0+bV9lcnJvci5tZXNzYWdlLAogICAgICAgICAgICAgICAgICBtZXNzYWdlLT5tX2Vycm9yLmZ1bmN0aW9uLAogICAgICAgICAgICAgICAgICBtZXNzYWdlLT5tX2Vycm9yLmZpbGVuYW1lLAogICAgICAgICAgICAgICAgICBtZXNzYWdlLT5tX2Vycm9yLmxpbmVubyk7CiAgICAgICAgICAgYnJlYWs7CiAgIGNhc2UgRERKVlVfSU5GTzoKI2lmIERFQlVHCiAgICAgICAgICAgcHJpbnRmKCJJTkZPOiAlcyFcbiIsIG1lc3NhZ2UtPm1faW5mby5tZXNzYWdlKTsKI2VuZGlmCiAgICAgICAgICAgYnJlYWs7CiAgIGRlZmF1bHQ6CiAgICAgIHByaW50ZigidW5leHBlY3RlZFxuIik7CiAgIH07CiAgcmV0dXJuKG1lc3NhZ2UtPm1fYW55LnRhZyk7Cn0KCgojaWYgZGVmaW5lZChfX2NwbHVzcGx1cykgfHwgZGVmaW5lZChjX3BsdXNwbHVzKQp9CiNlbmRpZgoKCiNkZWZpbmUgUkdCIDEKCi8qCiAqIERqVnUgYWR2ZXJ0aXNlZCByZWFkaW5lc3MgdG8gcHJvdmlkZSBiaXRtYXA6IFNvIGdldCBpdCEKICogd2UgdXNlIHRoZSBSR0IgZm9ybWF0IQogKi8Kc3RhdGljIHZvaWQKZ2V0X3BhZ2VfaW1hZ2UoTG9hZENvbnRleHQgKmxjLCBkZGp2dV9wYWdlX3QgKnBhZ2UsIGludCB4LCBpbnQgeSwgaW50IHcsIGludCBoLCBjb25zdCBJbWFnZUluZm8gKmltYWdlX2luZm8sIEV4Y2VwdGlvbkluZm8gKmV4Y2VwdGlvbiApIHsKICBkZGp2dV9mb3JtYXRfdAogICAgKmZvcm1hdDsKCiAgZGRqdnVfcGFnZV90eXBlX3QKICAgIHR5cGU7CgogIEltYWdlCiAgICAqaW1hZ2U7CgogIGludAogICAgcmV0LAogICAgc3RyaWRlOwoKICB1bnNpZ25lZCBjaGFyCiAgICAqcTsKCiAgICAgICAgZGRqdnVfcmVjdF90IHJlY3Q7CiAgICAgICAgcmVjdC54ID0geDsKICAgICAgICByZWN0LnkgPSB5OwogICAgICAgIHJlY3QudyA9ICh1bnNpZ25lZCBpbnQpIHc7ICAgICAgICAgICAgIC8qIC8xMCAqLwogICAgICAgIHJlY3QuaCA9ICh1bnNpZ25lZCBpbnQpIGg7ICAgICAgICAgICAgIC8qIC8xMCAqLwoKICAgICAgICBpbWFnZSA9IGxjLT5pbWFnZTsKICAgICAgICB0eXBlID0gZGRqdnVfcGFnZV9nZXRfdHlwZShsYy0+cGFnZSk7CgogICAgICAgIC8qIHN0cmlkZSBvZiB0aGlzIHRlbXBvcmFyeSBidWZmZXI6ICovCiAgICAgICAgc3RyaWRlID0gKHR5cGUgPT0gRERKVlVfUEFHRVRZUEVfQklUT05BTCk/CiAgICAgICAgICAgICAgICAoaW1hZ2UtPmNvbHVtbnMgKyA3KS84IDogaW1hZ2UtPmNvbHVtbnMgKjM7CgogICAgICAgIHEgPSAodW5zaWduZWQgY2hhciAqKSBBY3F1aXJlUXVhbnR1bU1lbW9yeShpbWFnZS0+cm93cyxzdHJpZGUpOwogICAgICAgIGlmIChxID09ICh1bnNpZ25lZCBjaGFyICopIE5VTEwpCiAgICAgICAgICByZXR1cm47CgogICAgICAgIGZvcm1hdCA9IGRkanZ1X2Zvcm1hdF9jcmVhdGUoCiAgICAgICAgICAgICAgICAodHlwZSA9PSBEREpWVV9QQUdFVFlQRV9CSVRPTkFMKT9EREpWVV9GT1JNQVRfTFNCVE9NU0IgOiBEREpWVV9GT1JNQVRfUkdCMjQsCiAgICAgICAgICAgICAgICAvKiBEREpWVV9GT1JNQVRfUkdCMjQKICAgICAgICAgICAgICAgICAqIERESlZVX0ZPUk1BVF9SR0JNQVNLMzIqLwogICAgICAgICAgICAgICAgLyogRERKVlVfRk9STUFUX1JHQk1BU0szMiAqLwogICAgICAgICAgICAgICAgMCwgTlVMTCk7CgojaWYgMAogICAgICAgIC8qIGZpeG1lOiAgVGhyb3dSZWFkZXJFeGNlcHRpb24gaXMgYSBtYWNybywgd2hpY2ggdXNlcyAgYGV4Y2VwdGlvbicgdmFyaWFibGUgKi8KICAgICAgICBpZiAoZm9ybWF0ID09IE5VTEwpCiAgICAgICAgICAgICAgICB7CiAgICAgICAgICAgICAgICAgICAgICAgIGFib3J0KCk7CiAgICAgICAgICAgICAgICAgICAgICAgIC8qIFRocm93UmVhZGVyRXhjZXB0aW9uKFJlc291cmNlTGltaXRFcnJvciwiTWVtb3J5QWxsb2NhdGlvbkZhaWxlZCIpOyAqLwogICAgICAgICAgICAgICAgfQoKI2VuZGlmCiAgICAgICAgZGRqdnVfZm9ybWF0X3NldF9yb3dfb3JkZXIoZm9ybWF0LCAxKTsKICAgICAgICBkZGp2dV9mb3JtYXRfc2V0X3lfZGlyZWN0aW9uKGZvcm1hdCwgMSk7CgogICAgICAgIHJldCA9IGRkanZ1X3BhZ2VfcmVuZGVyKHBhZ2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERESlZVX1JFTkRFUl9DT0xPUiwgLyogZGRqdnVfcmVuZGVyX21vZGVfdCAqLwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmcmVjdCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJnJlY3QsICAgICAvKiBtbWM6ID8/ICovCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGZvcm1hdCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc3RyaWRlLCAvKiA/PyAqLwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAoY2hhciopcSk7CiAgICAgICAgKHZvaWQpIHJldDsKICAgICAgICBkZGp2dV9mb3JtYXRfcmVsZWFzZShmb3JtYXQpOwoKCiAgICAgICAgaWYgKHR5cGUgPT0gRERKVlVfUEFHRVRZUEVfQklUT05BTCkgewogICAgICAgICAgICAgICAgLyogICovCiNpZiBERUJVRwogICAgICAgICAgICAgICAgcHJpbnRmKCIlczogZXhwYW5kaW5nIEJJVE9OQUwgcGFnZS9pbWFnZVxuIiwgX19GVU5DVElPTl9fKTsKI2VuZGlmCiAgICAgICAgICAgICAgICBzaXplX3QgYml0LCBieXRlOwoKICAgICAgICAgICAgICAgIGZvciAoeT0wOyB5IDwgKHNzaXplX3QpIGltYWdlLT5yb3dzOyB5KyspCiAgICAgICAgICAgICAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBRdWFudHVtICogbyA9IFF1ZXVlQXV0aGVudGljUGl4ZWxzKGltYWdlLDAseSxpbWFnZS0+Y29sdW1ucywxLGV4Y2VwdGlvbik7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaWYgKG8gPT0gKFF1YW50dW0gKikgTlVMTCkKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGJpdD0wOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGJ5dGU9MDsKCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgLyogZml4bWU6ICB0aGUgbm9uLWFsaWduZWQsIGxhc3QgPTw3IGJpdHMgISB0aGF0J3Mgb2shISEqLwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGZvciAoeD0gMDsgeCA8IChzc2l6ZV90KSBpbWFnZS0+Y29sdW1uczsgeCsrKQogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBpZiAoYml0ID09IDApIGJ5dGU9IChzaXplX3QpIHFbKHkgKiBzdHJpZGUpICsgKHggLyA4KV07CgogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBTZXRQaXhlbEluZGV4KGltYWdlLChRdWFudHVtKSAoKChieXRlICYgMHgwMSkgIT0gMCkgPyAweDAwIDogMHgwMSksbyk7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGJpdCsrOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBpZiAoYml0ID09IDgpCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgYml0PTA7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGJ5dGU+Pj0xOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBvKz1HZXRQaXhlbENoYW5uZWxzKGltYWdlKTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBpZiAoU3luY0F1dGhlbnRpY1BpeGVscyhpbWFnZSxleGNlcHRpb24pID09IE1hZ2lja0ZhbHNlKQogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGlmICghaW1hZ2UtPnBpbmcpCiAgICAgICAgICAgICAgICAgIFN5bmNJbWFnZShpbWFnZSxleGNlcHRpb24pOwogICAgICAgIH0gZWxzZSB7CiNpZiBERUJVRwogICAgICAgICAgICAgICAgcHJpbnRmKCIlczogZXhwYW5kaW5nIFBIT1RPIHBhZ2UvaW1hZ2VcbiIsIF9fRlVOQ1RJT05fXyk7CiNlbmRpZgogICAgICAgICAgICAgICAgLyogbm93IHRyYW5zZmVyIGxpbmUtd2lzZTogKi8KICAgICAgICAgICAgICAgIHNzaXplX3QgaTsKI2lmIDAKICAgICAgICAgICAgICAgIC8qIG9sZDogKi8KICAgICAgICAgICAgICAgIGNoYXIqIHI7CiNlbHNlCiAgICAgICAgICAgICAgICByZWdpc3RlciBRdWFudHVtICpyOwogICAgICAgICAgICAgICAgdW5zaWduZWQgY2hhciAqczsKI2VuZGlmCiAgICAgICAgICAgICAgICBzPXE7CiAgICAgICAgICAgICAgICBmb3IgKGkgPSAwO2k8IChzc2l6ZV90KSBpbWFnZS0+cm93czsgaSsrKQogICAgICAgICAgICAgICAgICAgICAgICB7CiNpZiBERUJVRwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaWYgKGkgJSAxMDAwID09IDApIHByaW50ZigiJWRcbiIsaSk7CiNlbmRpZgogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgciA9IFF1ZXVlQXV0aGVudGljUGl4ZWxzKGltYWdlLDAsaSxpbWFnZS0+Y29sdW1ucywxLGV4Y2VwdGlvbik7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBpZiAociA9PSAoUXVhbnR1bSAqKSBOVUxMKQogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgICAgZm9yICh4PTA7IHggPCAoc3NpemVfdCkgaW1hZ2UtPmNvbHVtbnM7IHgrKykKICAgICAgICAgICAgICAgICAgewogICAgICAgICAgICAgICAgICAgIFNldFBpeGVsUmVkKGltYWdlLFNjYWxlQ2hhclRvUXVhbnR1bSgqcysrKSxyKTsKICAgICAgICAgICAgICAgICAgICBTZXRQaXhlbEdyZWVuKGltYWdlLFNjYWxlQ2hhclRvUXVhbnR1bSgqcysrKSxyKTsKICAgICAgICAgICAgICAgICAgICBTZXRQaXhlbEJsdWUoaW1hZ2UsU2NhbGVDaGFyVG9RdWFudHVtKCpzKyspLHIpOwogICAgICAgICAgICAgICAgICAgIHIrPUdldFBpeGVsQ2hhbm5lbHMoaW1hZ2UpOwogICAgICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgICAgICAgICAgICAgICAgICBTeW5jQXV0aGVudGljUGl4ZWxzKGltYWdlLGV4Y2VwdGlvbik7CiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgcT0odW5zaWduZWQgY2hhciAqKSBSZWxpbnF1aXNoTWFnaWNrTWVtb3J5KHEpOwp9CgoKI2lmIGRlZmluZWQoTUFHSUNLQ09SRV9ESlZVX0RFTEVHQVRFKQoKI2lmIDAKc3RhdGljIGludApnZXRfcGFnZV9saW5lKExvYWRDb250ZXh0ICpsYywgaW50IHJvdywgUXVhbnR1bUluZm8qIHF1YW50dW1faW5mbykKewogIGRkanZ1X2Zvcm1hdF90CiAgICAqZm9ybWF0OwoKICBpbnQKICAgIHJldDsKCiAgc2l6ZV90CiAgICBzdHJpZGU7CgogIHVuc2lnbmVkIGNoYXIKICAgICpxOwoKICAgICAgICBkZGp2dV9yZWN0X3QgcmVjdCwgcGFnZXJlY3Q7CiAgICAgICAgcmVjdC54ID0gMDsKICAgICAgICByZWN0LnkgPSByb3c7CiAgICAgICAgcmVjdC53ID0gbGMtPmltYWdlLT5jb2x1bW5zOyAgICAgICAgICAgICAvKiAvMTAgKi8KICAgICAgICByZWN0LmggPSAxOyAgICAgICAgICAgICAvKiAvMTAgKi8KCiAgICAgICAgcGFnZXJlY3QueCA9IDA7CiAgICAgICAgcGFnZXJlY3QueSA9IDA7CiAgICAgICAgcGFnZXJlY3QudyA9IGxjLT5pbWFnZS0+Y29sdW1uczsKICAgICAgICBwYWdlcmVjdC5oID0gbGMtPmltYWdlLT5yb3dzOwoKCiAgICAgICAgZm9ybWF0ID0gZGRqdnVfZm9ybWF0X2NyZWF0ZSgKI2lmIFJHQgogICAgICAgICAgICAgICAgRERKVlVfRk9STUFUX1JHQjI0CiNlbHNlCiAgICAgICAgICAgICAgICBEREpWVV9GT1JNQVRfR1JFWTgKI2VuZGlmCiAgICAgICAgICAgICAgICAsCiAgICAgICAgICAgICAgICAwLCBOVUxMKTsKICAgICAgICBkZGp2dV9mb3JtYXRfc2V0X3Jvd19vcmRlcihmb3JtYXQsIDEpOwogICAgICAgIGRkanZ1X2Zvcm1hdF9zZXRfeV9kaXJlY3Rpb24oZm9ybWF0LCAxKTsKCiAgICAgICAgc3RyaWRlPTE7CiNpZiBSR0IKICAgICAgICBzdHJpZGU9MzsKI2VuZGlmCiAgICAgICAgcSA9ICh1bnNpZ25lZCBjaGFyICopIEFjcXVpcmVRdWFudHVtTWVtb3J5KGxjLT5pbWFnZS0+Y29sdW1ucyxzdHJpZGUpOwoKICAgICAgICByZXQgPSBkZGp2dV9wYWdlX3JlbmRlcihsYy0+cGFnZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRERKVlVfUkVOREVSX0NPTE9SLCAvKiBkZGp2dV9yZW5kZXJfbW9kZV90ICovCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICZwYWdlcmVjdCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJnJlY3QsICAgICAvKiBtbWM6ID8/ICovCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGZvcm1hdCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcGFnZXJlY3QudyAqIDMsIC8qID8/ICovCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIChjaGFyKilxKTsKCiAgICAgICAgSW1wb3J0UXVhbnR1bVBpeGVscyhsYy0+aW1hZ2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAoQ2FjaGVWaWV3ICopIE5VTEwsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBxdWFudHVtX2luZm8sCiNpZiBSR0IKICAgICAgICAgICAgICAgICAgICAgICAgICAgIFJHQlF1YW50dW0KI2Vsc2UKICAgICAgICAgICAgICAgICAgICAgICAgICAgIEdyYXlRdWFudHVtCiNlbmRpZgogICAgICAgICAgICAgICAgICAgICAgICAgICAgLHEsJmxjLT5pbWFnZS0+ZXhjZXB0aW9uKTsKICAgICAgICBxPSh1bnNpZ25lZCBjaGFyICopIFJlbGlucXVpc2hNYWdpY2tNZW1vcnkocSk7CiAgICAgICAgZGRqdnVfZm9ybWF0X3JlbGVhc2UoZm9ybWF0KTsKICAgICAgICByZXR1cm4gcmV0Owp9CiNlbmRpZgojZW5kaWYKCi8qCiUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUKJSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJQolICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAlCiUgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICUKJSAgIFIgZSBhIGQgTyBuIGUgRCBKIFYgVSBJIG0gYSBnIGUgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJQolICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAlCiUgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICUKJSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJQolJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlCiUKJSAgUmVhZE9uZURKVlVJbWFnZSgpIHJlYWRzIGEgUG9ydGFibGUgTmV0d29yayBHcmFwaGljcyAoREpWVSkgaW1hZ2UgZmlsZQolICAobWludXMgdGhlIDgtYnl0ZSBzaWduYXR1cmUpICBhbmQgcmV0dXJucyBpdC4gIEl0IGFsbG9jYXRlcyB0aGUgbWVtb3J5CiUgIG5lY2Vzc2FyeSBmb3IgdGhlIG5ldyBJbWFnZSBzdHJ1Y3R1cmUgYW5kIHJldHVybnMgYSBwb2ludGVyIHRvIHRoZSBuZXcKJSAgaW1hZ2UuCiUKJSAgVGhlIGZvcm1hdCBvZiB0aGUgUmVhZE9uZURKVlVJbWFnZSBtZXRob2QgaXM6CiUKJSAgICAgIEltYWdlICpSZWFkT25lREpWVUltYWdlKE1uZ0luZm8gKm1uZ19pbmZvLCBjb25zdCBJbWFnZUluZm8gKmltYWdlX2luZm8sCiUgICAgICAgICBFeGNlcHRpb25JbmZvICpleGNlcHRpb24pCiUKJSAgQSBkZXNjcmlwdGlvbiBvZiBlYWNoIHBhcmFtZXRlciBmb2xsb3dzOgolCiUgICAgbyBtbmdfaW5mbzogU3BlY2lmaWVzIGEgcG9pbnRlciB0byBhIE1uZ0luZm8gc3RydWN0dXJlLgolCiUgICAgbyBpbWFnZV9pbmZvOiB0aGUgaW1hZ2UgaW5mby4KJQolICAgIG8gZXhjZXB0aW9uOiByZXR1cm4gYW55IGVycm9ycyBvciB3YXJuaW5ncyBpbiB0aGlzIHN0cnVjdHVyZS4KJQoqLwoKc3RhdGljIGlubGluZSBkb3VibGUgTWFnaWNrTWF4KGNvbnN0IGRvdWJsZSB4LGNvbnN0IGRvdWJsZSB5KQp7CiAgaWYgKHggPiB5KQogICAgcmV0dXJuKHgpOwogIHJldHVybih5KTsKfQoKc3RhdGljIEltYWdlICpSZWFkT25lREpWVUltYWdlKExvYWRDb250ZXh0KiBsYyxjb25zdCBpbnQgcGFnZW51bSwKICBjb25zdCBJbWFnZUluZm8gKmltYWdlX2luZm8sRXhjZXB0aW9uSW5mbyAqZXhjZXB0aW9uKQp7CiAgZGRqdnVfcGFnZV90eXBlX3QKICAgICB0eXBlOwoKICBkZGp2dV9wYWdlaW5mb190IGluZm87CiAgZGRqdnVfbWVzc2FnZV90ICptZXNzYWdlOwogIEltYWdlICppbWFnZTsKICBpbnQgbG9nZ2luZzsKICBpbnQgdGFnOwoKICAgICAgICAvKiBzbywgd2Uga25vdyB0aGF0IHRoZSBwYWdlIGlzIHRoZXJlISBHZXQgaXRzIGRpbWVuc2lvbiwgYW5kICAqLwoKICAgICAgICAvKiBSZWFkIG9uZSBESlZVIGltYWdlICovCiAgICAgICAgaW1hZ2UgPSBsYy0+aW1hZ2U7CgogICAgICAgIC8qIHJlZ2lzdGVyIFF1YW50dW0gKnE7ICovCgogICAgICAgIGxvZ2dpbmc9TG9nTWFnaWNrRXZlbnQoQ29kZXJFdmVudCxHZXRNYWdpY2tNb2R1bGUoKSwgIiAgZW50ZXIgUmVhZE9uZURKVlVJbWFnZSgpIik7CiAgICAgICAgKHZvaWQpIGxvZ2dpbmc7CgojaWYgREVCVUcKICAgICAgICBwcmludGYoIj09PT0gIExvYWRpbmcgdGhlIHBhZ2UgJWRcbiIsIHBhZ2VudW0pOwojZW5kaWYKICAgICAgICBsYy0+cGFnZSA9IGRkanZ1X3BhZ2VfY3JlYXRlX2J5X3BhZ2VubyhsYy0+ZG9jdW1lbnQsIHBhZ2VudW0pOyAvKiAgMD8gKi8KCiAgICAgICAgLyogcHVtcCBkYXRhIHVudGlsbCB0aGUgcGFnZSBpcyByZWFkeSBmb3IgcmVuZGVyaW5nLiAqLwogICAgICAgIHRhZz0oLTEpOwogICAgICAgIGRvIHsKICAgICAgICAgICAgICAgIHdoaWxlICgobWVzc2FnZSA9IGRkanZ1X21lc3NhZ2VfcGVlayhsYy0+Y29udGV4dCkpKQogICAgICAgICAgICAgICAgICAgICAgICB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdGFnPXByb2Nlc3NfbWVzc2FnZShtZXNzYWdlKTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBpZiAodGFnID09IDApIGJyZWFrOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGRkanZ1X21lc3NhZ2VfcG9wKGxjLT5jb250ZXh0KTsKICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgLyogZml4bWU6IG1heWJlIGV4aXQ/ICovCiAgICAgICAgICAgICAgICAvKiBpZiAobGMtPmVycm9yKSBicmVhazsgKi8KCiAgICAgICAgICAgICAgICBtZXNzYWdlID0gcHVtcF9kYXRhX3VudGlsX21lc3NhZ2UobGMsaW1hZ2UpOwogICAgICAgICAgICAgICAgaWYgKG1lc3NhZ2UpCiAgICAgICAgICAgICAgICAgICAgICAgIGRvIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB0YWc9cHJvY2Vzc19tZXNzYWdlKG1lc3NhZ2UpOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGlmICh0YWcgPT0gMCkgYnJlYWs7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZGRqdnVfbWVzc2FnZV9wb3AobGMtPmNvbnRleHQpOwogICAgICAgICAgICAgICAgICAgICAgICB9IHdoaWxlICgobWVzc2FnZSA9IGRkanZ1X21lc3NhZ2VfcGVlayhsYy0+Y29udGV4dCkpKTsKICAgICAgICB9IHdoaWxlICghZGRqdnVfcGFnZV9kZWNvZGluZ19kb25lKGxjLT5wYWdlKSk7CgogICAgICAgIGRkanZ1X2RvY3VtZW50X2dldF9wYWdlaW5mbyhsYy0+ZG9jdW1lbnQsIHBhZ2VudW0sICZpbmZvKTsKCiAgICAgICAgaW1hZ2UtPnJlc29sdXRpb24ueCA9IChmbG9hdCkgaW5mby5kcGk7CiAgICAgICAgaW1hZ2UtPnJlc29sdXRpb24ueSA9KGZsb2F0KSBpbmZvLmRwaTsKICAgICAgICBpZiAoaW1hZ2VfaW5mby0+ZGVuc2l0eSAhPSAoY2hhciAqKSBOVUxMKQogICAgICAgICAgewogICAgICAgICAgICBpbnQKICAgICAgICAgICAgICBmbGFnczsKCiAgICAgICAgICAgIEdlb21ldHJ5SW5mbwogICAgICAgICAgICAgIGdlb21ldHJ5X2luZm87CgogICAgICAgICAgICAvKgogICAgICAgICAgICAgIFNldCByZW5kZXJpbmcgcmVzb2x1dGlvbi4KICAgICAgICAgICAgKi8KICAgICAgICAgICAgZmxhZ3M9UGFyc2VHZW9tZXRyeShpbWFnZV9pbmZvLT5kZW5zaXR5LCZnZW9tZXRyeV9pbmZvKTsKICAgICAgICAgICAgaW1hZ2UtPnJlc29sdXRpb24ueD1nZW9tZXRyeV9pbmZvLnJobzsKICAgICAgICAgICAgaW1hZ2UtPnJlc29sdXRpb24ueT1nZW9tZXRyeV9pbmZvLnNpZ21hOwogICAgICAgICAgICBpZiAoKGZsYWdzICYgU2lnbWFWYWx1ZSkgPT0gMCkKICAgICAgICAgICAgICBpbWFnZS0+cmVzb2x1dGlvbi55PWltYWdlLT5yZXNvbHV0aW9uLng7CiAgICAgICAgICAgIGluZm8ud2lkdGgqPWltYWdlLT5yZXNvbHV0aW9uLngvaW5mby5kcGk7CiAgICAgICAgICAgIGluZm8uaGVpZ2h0Kj1pbWFnZS0+cmVzb2x1dGlvbi55L2luZm8uZHBpOwogICAgICAgICAgICBpbmZvLmRwaT0oc3NpemVfdCkgTWFnaWNrTWF4KGltYWdlLT5yZXNvbHV0aW9uLngsaW1hZ2UtPnJlc29sdXRpb24ueSk7CiAgICAgICAgICB9CiAgICAgICAgdHlwZSA9IGRkanZ1X3BhZ2VfZ2V0X3R5cGUobGMtPnBhZ2UpOwoKICAgICAgICAvKiBkb3VibGUgLT4gZmxvYXQhICovCiAgICAgICAgLyogaW1hZ2UtPmdhbW1hID0gKGZsb2F0KWRkanZ1X3BhZ2VfZ2V0X2dhbW1hKGxjLT5wYWdlKTsgKi8KCiAgICAgICAgLyogbW1jOiAgc2V0ICBpbWFnZS0+ZGVwdGggICovCiAgICAgICAgLyogbW1jOiAgVGhpcyBmcm9tIHRoZSB0eXBlICovCgogICAgICAgIGltYWdlLT5jb2x1bW5zPShzaXplX3QpIGluZm8ud2lkdGg7CiAgICAgICAgaW1hZ2UtPnJvd3M9KHNpemVfdCkgaW5mby5oZWlnaHQ7CgogICAgICAgIC8qIG1tYzogYml0b25hbCBzaG91bGQgYmUgcGFsZXR0aXplZCwgYW5kIGNvbXByZXNzZWQhICovCiAgICAgICAgaWYgKHR5cGUgPT0gRERKVlVfUEFHRVRZUEVfQklUT05BTCl7CiAgICAgICAgICAgICAgICBpbWFnZS0+Y29sb3JzcGFjZSA9IEdSQVlDb2xvcnNwYWNlOwogICAgICAgICAgICAgICAgaW1hZ2UtPnN0b3JhZ2VfY2xhc3MgPSBQc2V1ZG9DbGFzczsKICAgICAgICAgICAgICAgIGltYWdlLT5kZXB0aCA9ICA4VUw7ICAgIC8qIGkgb25seSBzdXBwb3J0IHRoYXQ/ICovCiAgICAgICAgICAgICAgICBpbWFnZS0+Y29sb3JzPSAyOwogICAgICAgICAgICAgICAgaWYgKEFjcXVpcmVJbWFnZUNvbG9ybWFwKGltYWdlLGltYWdlLT5jb2xvcnMsZXhjZXB0aW9uKSA9PSBNYWdpY2tGYWxzZSkKICAgICAgICAgICAgICAgICAgVGhyb3dSZWFkZXJFeGNlcHRpb24oUmVzb3VyY2VMaW1pdEVycm9yLAogICAgICAgICAgICAgICAgICAgIk1lbW9yeUFsbG9jYXRpb25GYWlsZWQiKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgICAgaW1hZ2UtPmNvbG9yc3BhY2UgPSBSR0JDb2xvcnNwYWNlOwogICAgICAgICAgICAgICAgaW1hZ2UtPnN0b3JhZ2VfY2xhc3MgPSBEaXJlY3RDbGFzczsKICAgICAgICAgICAgICAgIC8qIGZpeG1lOiAgTUFHSUNLQ09SRV9RVUFOVFVNX0RFUFRIID8qLwogICAgICAgICAgICAgICAgaW1hZ2UtPmRlcHRoID0gIDhVTDsgICAgLyogaSBvbmx5IHN1cHBvcnQgdGhhdD8gKi8KCiAgICAgICAgICAgICAgICBpbWFnZS0+bWF0dGUgPSBNYWdpY2tUcnVlOwogICAgICAgICAgICAgICAgLyogaXMgdGhpcyB1c2VmdWw/ICovCiAgICAgICAgfQojaWYgREVCVUcKICAgICAgICBwcmludGYoIm5vdyBmaWxsaW5nICUuMjBnIHggJS4yMGdcbiIsKGRvdWJsZSkgaW1hZ2UtPmNvbHVtbnMsKGRvdWJsZSkKICAgICAgICAgIGltYWdlLT5yb3dzKTsKI2VuZGlmCgoKI2lmIDEgICAgICAgICAgICAgICAgICAgICAgICAgICAvKiBwZXJfbGluZSAqLwoKICAgICAgICAvKiBxID0gUXVldWVBdXRoZW50aWNQaXhlbHMoaW1hZ2UsMCwwLGltYWdlLT5jb2x1bW5zLGltYWdlLT5yb3dzKTsgKi8KICAgICAgICBnZXRfcGFnZV9pbWFnZShsYywgbGMtPnBhZ2UsIDAsIDAsIGluZm8ud2lkdGgsIGluZm8uaGVpZ2h0LCBpbWFnZV9pbmZvLAogICAgICAgICAgZXhjZXB0aW9uKTsKI2Vsc2UKICAgICAgICBpbnQgaTsKICAgICAgICBmb3IgKGkgPSAwO2k8IGltYWdlLT5yb3dzOyBpKyspCiAgICAgICAgICAgICAgICB7CiAgICAgICAgICAgICAgICAgICAgICAgIHByaW50ZigiJWRcbiIsaSk7CiAgICAgICAgICAgICAgICAgICAgICAgIHEgPSBRdWV1ZUF1dGhlbnRpY1BpeGVscyhpbWFnZSwwLGksaW1hZ2UtPmNvbHVtbnMsMSk7CiAgICAgICAgICAgICAgICAgICAgICAgIGdldF9wYWdlX2xpbmUobGMsIGksIHF1YW50dW1faW5mbyk7CiAgICAgICAgICAgICAgICAgICAgICAgIFN5bmNBdXRoZW50aWNQaXhlbHMoaW1hZ2UpOwogICAgICAgICAgICAgICAgfQoKI2VuZGlmIC8qIHBlcl9saW5lICovCgoKI2lmIERFQlVHCiAgICAgICAgcHJpbnRmKCJFTkQ6IGZpbmlzaGVkIGZpbGxpbmcgJS4yMGcgeCAlLjIwZ1xuIiwoZG91YmxlKSBpbWFnZS0+Y29sdW1ucywKICAgICAgICAgIChkb3VibGUpIGltYWdlLT5yb3dzKTsKI2VuZGlmCgogICAgICAgIGlmICghaW1hZ2UtPnBpbmcpCiAgICAgICAgICBTeW5jSW1hZ2UoaW1hZ2UsZXhjZXB0aW9uKTsKICAgICAgICAvKiBtbWM6ID8/PyBDb252ZXJ0IFBOTSBwaXhlbHMgdG8gcnVubGVuZ3RoLWVuY29kZWQgTUlGRiBwYWNrZXRzLiAqLwogICAgICAgIC8qIGltYWdlLT5jb2xvcnMgPSAgKi8KCiAgICAgICAgLyogaG93IGlzIHRoZSBsaW5lIHBhZGRpbmcgIC8gc3RyaWRlPyAqLwoKICAgICAgICBpZiAobGMtPnBhZ2UpIHsKICAgICAgICAgICAgICAgIGRkanZ1X3BhZ2VfcmVsZWFzZShsYy0+cGFnZSk7CiAgICAgICAgICAgICAgICBsYy0+cGFnZSA9IE5VTEw7CiAgICAgICAgfQoKICAgICAgICAvKiBpbWFnZS0+cGFnZS55PW1uZ19pbmZvLT55X29mZlttbmdfaW5mby0+b2JqZWN0X2lkXTsgKi8KICAgICAgICBpZiAodGFnID09IDApCiAgICAgICAgICBpbWFnZT1EZXN0cm95SW1hZ2UoaW1hZ2UpOwogICAgICAgIHJldHVybiBpbWFnZTsKICAgICAgICAvKiBlbmQgb2YgcmVhZGluZyBvbmUgREpWVSBwYWdlL2ltYWdlICovCn0KCiNpZiAwCi8qIHBhbGV0dGUgKi8KICBpZiAoQWNxdWlyZUltYWdlQ29sb3JtYXAoaW1hZ2UsMixleGNlcHRpb24pID09IE1hZ2lja0ZhbHNlKQogICAgVGhyb3dSZWFkZXJFeGNlcHRpb24oUmVzb3VyY2VMaW1pdEVycm9yLCJNZW1vcnlBbGxvY2F0aW9uRmFpbGVkIik7CiAgLyoKICAgIE1vbm9jaHJvbWUgY29sb3JtYXAuICAgbW1jOiB0aGlzIHRoZSBkZWZhdWx0IQogICovCiAgaW1hZ2UtPmNvbG9ybWFwWzBdLnJlZD1RdWFudHVtUmFuZ2U7CiAgaW1hZ2UtPmNvbG9ybWFwWzBdLmdyZWVuPVF1YW50dW1SYW5nZTsKICBpbWFnZS0+Y29sb3JtYXBbMF0uYmx1ZT1RdWFudHVtUmFuZ2U7CiAgaW1hZ2UtPmNvbG9ybWFwWzFdLnJlZD0wOwogIGltYWdlLT5jb2xvcm1hcFsxXS5ncmVlbj0wOwogIGltYWdlLT5jb2xvcm1hcFsxXS5ibHVlPTA7CiNlbmRpZgoKc3RhdGljIHZvaWQgZGp2dV9jbG9zZV9sYyhMb2FkQ29udGV4dCogbGMpCnsKICAgICAgICBpZiAobGMtPmRvY3VtZW50KQogICAgICAgICAgICAgICAgZGRqdnVfZG9jdW1lbnRfcmVsZWFzZShsYy0+ZG9jdW1lbnQpOwogICAgICAgIGlmIChsYy0+Y29udGV4dCkKICAgICAgICAgICAgICAgIGRkanZ1X2NvbnRleHRfcmVsZWFzZShsYy0+Y29udGV4dCk7CiAgICAgICAgaWYgKGxjLT5wYWdlKQogICAgICAgICAgICAgICAgZGRqdnVfcGFnZV9yZWxlYXNlKGxjLT5wYWdlKTsKICAgICAgICBSZWxpbnF1aXNoTWFnaWNrTWVtb3J5KGxjKTsKfQoKc3RhdGljIEltYWdlICpSZWFkREpWVUltYWdlKGNvbnN0IEltYWdlSW5mbyAqaW1hZ2VfaW5mbywKICBFeGNlcHRpb25JbmZvICpleGNlcHRpb24pCnsKICBjb25zdCBjaGFyCiAgICAqdXJsOwoKICBkZGp2dV9tZXNzYWdlX3QKICAgICptZXNzYWdlOwoKICBJbWFnZQogICAgKmltYWdlLAogICAgKmltYWdlczsKCiAgaW50CiAgICBsb2dnaW5nLAogICAgdXNlX2NhY2hlOwoKICBMb2FkQ29udGV4dAogICAgKmxjOwoKICBNYWdpY2tCb29sZWFuVHlwZQogICAgc3RhdHVzOwoKICByZWdpc3RlciBzc2l6ZV90CiAgICBpOwoKICAvKgogICAqIE9wZW4gaW1hZ2UgZmlsZS4KICAgKi8KICBhc3NlcnQoaW1hZ2VfaW5mbyAhPSAoY29uc3QgSW1hZ2VJbmZvICopIE5VTEwpOwogIGFzc2VydChpbWFnZV9pbmZvLT5zaWduYXR1cmUgPT0gTWFnaWNrU2lnbmF0dXJlKTsKCgogIGlmIChpbWFnZV9pbmZvLT5kZWJ1ZyAhPSBNYWdpY2tGYWxzZSkKICAgICh2b2lkKSBMb2dNYWdpY2tFdmVudChUcmFjZUV2ZW50LEdldE1hZ2lja01vZHVsZSgpLCIlcyIsIGltYWdlX2luZm8tPmZpbGVuYW1lKTsKCiAgYXNzZXJ0KGV4Y2VwdGlvbiAhPSAoRXhjZXB0aW9uSW5mbyAqKSBOVUxMKTsKICBhc3NlcnQoZXhjZXB0aW9uLT5zaWduYXR1cmUgPT0gTWFnaWNrU2lnbmF0dXJlKTsKCgogIGxvZ2dpbmcgPSBMb2dNYWdpY2tFdmVudChDb2RlckV2ZW50LEdldE1hZ2lja01vZHVsZSgpLCJlbnRlciBSZWFkREpWVUltYWdlKCkiKTsKICAodm9pZCkgbG9nZ2luZzsKCiAgaW1hZ2UgPSBBY3F1aXJlSW1hZ2UoaW1hZ2VfaW5mbyxleGNlcHRpb24pOyAvKiBtbWM6ID8/ICovCgoKICBsYyA9IChMb2FkQ29udGV4dCAqKSBOVUxMOwogIHN0YXR1cyA9IE9wZW5CbG9iKGltYWdlX2luZm8saW1hZ2UsUmVhZEJpbmFyeUJsb2JNb2RlLGV4Y2VwdGlvbik7CiAgaWYgKHN0YXR1cyA9PSBNYWdpY2tGYWxzZSkKICAgIFRocm93UmVhZGVyRXhjZXB0aW9uKEZpbGVPcGVuRXJyb3IsIlVuYWJsZVRvT3BlbkZpbGUiKTsKICAvKgogICAgVmVyaWZ5IERKVlUgc2lnbmF0dXJlLgogICovCiNpZiAwCiAgY291bnQgPSBSZWFkQmxvYihpbWFnZSw4LCh1bnNpZ25lZCBjaGFyICopIG1hZ2ljX251bWJlcik7CgogIC8qIElzREpWVShjb25zdCB1bnNpZ25lZCBjaGFyICptYWdpY2ssY29uc3Qgc2l6ZV90IGxlbmd0aCkgKi8KICBpZiAobWVtY21wKG1hZ2ljX251bWJlciwiQVQmVEZPUk0iLDgpICE9IDApCiAgICBUaHJvd1JlYWRlckV4Y2VwdGlvbihDb3JydXB0SW1hZ2VFcnJvciwiSW1wcm9wZXJJbWFnZUhlYWRlciIpOwojZW5kaWYKCgogIC8qCiAgICogQWxsb2NhdGUgYSBMb2FkQ29udGV4dCBzdHJ1Y3R1cmUuCiAgICovCiAgbGMgPSAoTG9hZENvbnRleHQgKikgQWNxdWlyZU1hZ2lja01lbW9yeShzaXplb2YoKmxjKSk7CiAgaWYgKGxjID09IE5VTEwpCiAgICBUaHJvd1JlYWRlckV4Y2VwdGlvbihSZXNvdXJjZUxpbWl0RXJyb3IsIk1lbW9yeUFsbG9jYXRpb25GYWlsZWQiKTsKCgogIC8qCiAgICogSW5pdGlhbGl6ZSBtZW1iZXJzIG9mIHRoZSBNbmdJbmZvIHN0cnVjdHVyZS4KICAgKi8KICAodm9pZCkgUmVzZXRNYWdpY2tNZW1vcnkobGMsMCxzaXplb2YoTG9hZENvbnRleHQpKTsKCiAgbGMtPmltYWdlID0gaW1hZ2U7CiAgbGMtPnBhZ2VzID0gMDsKICBsYy0+Y29udGV4dCA9IGRkanZ1X2NvbnRleHRfY3JlYXRlKCJJbWFnZU1hZ2ljayBkanZ1IGxvYWRlciIpOyAvKiBnX3Byb2dyYW1fbmFtZSAqLwoKICBkZGp2dV9jYWNoZV9zZXRfc2l6ZShsYy0+Y29udGV4dCwgMSk7IC8qIHJpZ2h0PyAqLwogIHVzZV9jYWNoZSA9IDA7CiAgLyogZG9jdW1lbnQ6IGhlcmUgd2UgZG9uJ3QgaGF2ZSBhIGZpbGVuYW1lLCBidXQsIGZvciB0aGUgc2FrZSBvZiBnZW5lcmFsaXR5LCBhIEZJTEUqICEgKi8KICB1cmw9Imh0dHA6Ly93d3cuaW1hZ2VtYWdpY2sub3JnL2Zha2UuZGp2dSI7CiAgbGMtPmRvY3VtZW50ID0gZGRqdnVfZG9jdW1lbnRfY3JlYXRlKGxjLT5jb250ZXh0LCB1cmwsIHVzZV9jYWNoZSk7IC8qIGRvbid0IGNhY2hlICovCiAgZGRqdnVfZG9jdW1lbnRfc2V0X3VzZXJfZGF0YShsYy0+ZG9jdW1lbnQsIGxjKTsKCgogIC8qIG5vdyB3ZSB3YWl0IHRoZSBtZXNzYWdlLXJlcXVlc3QgZm9yIGRhdGE6ICovCiAgbWVzc2FnZSA9IGRkanZ1X21lc3NhZ2Vfd2FpdChsYy0+Y29udGV4dCk7CgogIGlmIChtZXNzYWdlLT5tX2FueS50YWcgIT0gRERKVlVfTkVXU1RSRUFNKSB7CiAgICAgICAgICAvKiBmaXhtZTogdGhlIGRqdnUgY29udGV4dCwgZG9jdW1lbnQhICovCgogICAgICAgICAgZGRqdnVfZG9jdW1lbnRfcmVsZWFzZShsYy0+ZG9jdW1lbnQpOwogICAgICAgICAgZGRqdnVfY29udGV4dF9yZWxlYXNlKGxjLT5jb250ZXh0KTsKCiAgICAgICAgICBSZWxpbnF1aXNoTWFnaWNrTWVtb3J5KGxjKTsKCiAgICAgICAgICBUaHJvd1JlYWRlckV4Y2VwdGlvbihSZXNvdXJjZUxpbWl0RXJyb3IsIkRqdnUgaW5pdGlhbCBtZXNzYWdlOiB1bmV4cGVjdGVkIHR5cGUiKTsKICAgICAgICAgIHJldHVybiBOVUxMOyAgICAvKiBlcnJvciEgKi8KICB9OwoKICBsYy0+c3RyZWFtaWQgPSBtZXNzYWdlLT5tX25ld3N0cmVhbS5zdHJlYW1pZDsKICBkZGp2dV9tZXNzYWdlX3BvcChsYy0+Y29udGV4dCk7CgogIG1lc3NhZ2UgPSBwdW1wX2RhdGFfdW50aWxfbWVzc2FnZShsYyxpbWFnZSk7CiAgLyogbm93IHByb2Nlc3MgdGhlIG1lc3NhZ2VzOiAqLwoKCiAgaWYgKG1lc3NhZ2UpIGRvIHsKICAgICAgICAgIHByb2Nlc3NfbWVzc2FnZShtZXNzYWdlKTsKICAgICAgICAgIGRkanZ1X21lc3NhZ2VfcG9wKGxjLT5jb250ZXh0KTsKICB9IHdoaWxlICgobWVzc2FnZSA9IGRkanZ1X21lc3NhZ2VfcGVlayhsYy0+Y29udGV4dCkpKTsKCiAgLyogZml4bWU6IGkgaG9wZSB3ZSBoYXZlIG5vdCByZWFkIGFueSBtZXNzYWdlcyBwZXJ0aW5lbnQoPykgcmVsYXRlZCB0byB0aGUgcGFnZSBpdHNlbGYhICAqLwoKICB3aGlsZSAobGMtPnBhZ2VzID09IDApIHsKICAgICAgICAgIG1lc3NhZ2UgPSBkZGp2dV9tZXNzYWdlX3dhaXQobGMtPmNvbnRleHQpOwogICAgICAgICAgcHJvY2Vzc19tZXNzYWdlKG1lc3NhZ2UpOwogICAgICAgICAgZGRqdnVfbWVzc2FnZV9wb3AobGMtPmNvbnRleHQpOwogIH0KCiAgaW1hZ2VzPU5ld0ltYWdlTGlzdCgpOwogIGk9MDsKICBpZiAoaW1hZ2VfaW5mby0+bnVtYmVyX3NjZW5lcyAhPSAwKQogICAgaT1pbWFnZV9pbmZvLT5zY2VuZTsKICBmb3IgKCA7IGkgPCAoc3NpemVfdCkgbGMtPnBhZ2VzOyBpKyspCiAgewogICAgaW1hZ2U9UmVhZE9uZURKVlVJbWFnZShsYyxpLGltYWdlX2luZm8sZXhjZXB0aW9uKTsKICAgIGlmIChpbWFnZSA9PSAoSW1hZ2UgKikgTlVMTCkKICAgICAgYnJlYWs7CiAgICBpbWFnZS0+c2NlbmU9aTsKICAgIEFwcGVuZEltYWdlVG9MaXN0KCZpbWFnZXMsQ2xvbmVJbWFnZUxpc3QoaW1hZ2UsZXhjZXB0aW9uKSk7CiAgICBpbWFnZXMtPmV4dGVudD1HZXRCbG9iU2l6ZShpbWFnZSk7CiAgICBpZiAoaW1hZ2VfaW5mby0+bnVtYmVyX3NjZW5lcyAhPSAwKQogICAgICBpZiAoaW1hZ2UtPnNjZW5lID49IChpbWFnZV9pbmZvLT5zY2VuZStpbWFnZV9pbmZvLT5udW1iZXJfc2NlbmVzLTEpKQogICAgICAgIGJyZWFrOwogIH0KICBkanZ1X2Nsb3NlX2xjKGxjKTsKICAodm9pZCkgQ2xvc2VCbG9iKGltYWdlcyk7CiAgaWYgKGltYWdlICE9IChJbWFnZSAqKSBOVUxMKQogICAgaW1hZ2U9RGVzdHJveUltYWdlTGlzdChpbWFnZSk7CgojaWYgMAogIGlmICgoaW1hZ2UtPnBhZ2Uud2lkdGggPT0gMCkgJiYgKGltYWdlLT5wYWdlLmhlaWdodCA9PSAwKSkKICAgIHsKICAgICAgaW1hZ2UtPnBhZ2Uud2lkdGggPSBpbWFnZS0+Y29sdW1ucytpbWFnZS0+cGFnZS54OwogICAgICBpbWFnZS0+cGFnZS5oZWlnaHQgPSBpbWFnZS0+cm93cytpbWFnZS0+cGFnZS55OwogICAgfQogIGlmIChpbWFnZS0+Y29sdW1ucyA9PSAwIHx8IGltYWdlLT5yb3dzID09IDApCiAgICB7CiAgICAgIGlmIChsb2dnaW5nICE9IE1hZ2lja0ZhbHNlKQogICAgICAgICh2b2lkKSBMb2dNYWdpY2tFdmVudChDb2RlckV2ZW50LEdldE1hZ2lja01vZHVsZSgpLAogICAgICAgICAgImV4aXQgUmVhZERKVlVJbWFnZSgpIHdpdGggZXJyb3IuIik7CiAgICAgIFRocm93UmVhZGVyRXhjZXB0aW9uKENvcnJ1cHRJbWFnZUVycm9yLCJDb3JydXB0SW1hZ2UiKTsKICAgIH0KCiAgaWYgKGxvZ2dpbmcgIT0gTWFnaWNrRmFsc2UpCiAgICAodm9pZCkgTG9nTWFnaWNrRXZlbnQoQ29kZXJFdmVudCxHZXRNYWdpY2tNb2R1bGUoKSwiZXhpdCBSZWFkREpWVUltYWdlKCkiKTsKI2VuZGlmCgoKICByZXR1cm4oR2V0Rmlyc3RJbWFnZUluTGlzdChpbWFnZXMpKTsKfQojZW5kaWYKDAovKgolJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlCiUgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICUKJSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJQolICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAlCiUgICBSIGUgZyBpIHMgdCBlIHIgRCBKIFYgVSBJIG0gYSBnIGUgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICUKJSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJQolICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAlCiUgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICUKJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJQolCiUgIFJlZ2lzdGVyREpWVUltYWdlKCkgYWRkcyBhdHRyaWJ1dGVzIGZvciB0aGUgREpWVSBpbWFnZSBmb3JtYXQgdG8KJSAgdGhlIGxpc3Qgb2Ygc3VwcG9ydGVkIGZvcm1hdHMuICBUaGUgYXR0cmlidXRlcyBpbmNsdWRlIHRoZSBpbWFnZSBmb3JtYXQKJSAgdGFnLCBhIG1ldGhvZCB0byByZWFkIGFuZC9vciB3cml0ZSB0aGUgZm9ybWF0LCB3aGV0aGVyIHRoZSBmb3JtYXQKJSAgc3VwcG9ydHMgdGhlIHNhdmluZyBvZiBtb3JlIHRoYW4gb25lIGZyYW1lIHRvIHRoZSBzYW1lIGZpbGUgb3IgYmxvYiwKJSAgd2hldGhlciB0aGUgZm9ybWF0IHN1cHBvcnRzIG5hdGl2ZSBpbi1tZW1vcnkgSS9PLCBhbmQgYSBicmllZgolICBkZXNjcmlwdGlvbiBvZiB0aGUgZm9ybWF0LgolCiUgIFRoZSBmb3JtYXQgb2YgdGhlIFJlZ2lzdGVyREpWVUltYWdlIG1ldGhvZCBpczoKJQolICAgICAgc2l6ZV90IFJlZ2lzdGVyREpWVUltYWdlKHZvaWQpCiUKKi8KTW9kdWxlRXhwb3J0IHNpemVfdCBSZWdpc3RlckRKVlVJbWFnZSh2b2lkKQp7CiAgY2hhcgogICAgdmVyc2lvbltNYXhUZXh0RXh0ZW50XTsKCiAgTWFnaWNrSW5mbwogICAgKmVudHJ5OwoKICBzdGF0aWMgY29uc3QgY2hhcgogICAgKkRKVlVOb3RlID0KICAgIHsKICAgICAgIlNlZSBodHRwOi8vd3d3LmRqdnV6b25lLm9yZy8gZm9yIGRldGFpbHMgYWJvdXQgdGhlIERKVlUgZm9ybWF0LiAgVGhlXG4iCiAgICAgICJESlZVIDEuMiBzcGVjaWZpY2F0aW9uIGlzIGF2YWlsYWJsZSB0aGVyZSBhbmQgYXRcbiIKICAgICAgImZ0cDovL3N3cmluZGUubmRlLnN3cmkuZWR1L3B1Yi9kanZ1L2RvY3VtZW50cy8uIgogICAgfTsKCiAgKnZlcnNpb249J1wwJzsKI2lmIGRlZmluZWQoREpWVV9MSUJESlZVX1ZFUl9TVFJJTkcpCiAgKHZvaWQpIENvbmNhdGVuYXRlTWFnaWNrU3RyaW5nKHZlcnNpb24sImxpYmRqdnUgIixNYXhUZXh0RXh0ZW50KTsKICAodm9pZCkgQ29uY2F0ZW5hdGVNYWdpY2tTdHJpbmcodmVyc2lvbixESlZVX0xJQkRKVlVfVkVSX1NUUklORyxNYXhUZXh0RXh0ZW50KTsKI2VuZGlmCiAgZW50cnk9U2V0TWFnaWNrSW5mbygiREpWVSIpOwojaWYgZGVmaW5lZChNQUdJQ0tDT1JFX0RKVlVfREVMRUdBVEUpCiAgZW50cnktPmRlY29kZXI9KERlY29kZUltYWdlSGFuZGxlciAqKSBSZWFkREpWVUltYWdlOwojZW5kaWYKICBlbnRyeS0+cmF3PU1hZ2lja1RydWU7CiAgZW50cnktPm1hZ2ljaz0oSXNJbWFnZUZvcm1hdEhhbmRsZXIgKikgSXNESlZVOwogIGVudHJ5LT5hZGpvaW49TWFnaWNrRmFsc2U7CiAgZW50cnktPnRocmVhZF9zdXBwb3J0PU1hZ2lja1RydWU7CiAgZW50cnktPmRlc2NyaXB0aW9uPUFjcXVpcmVTdHJpbmcoIkTpauAgdnUiKTsKICBlbnRyeS0+bW9kdWxlPUFjcXVpcmVTdHJpbmcoIkRKVlUiKTsKICBpZiAoKnZlcnNpb24gIT0gJ1wwJykKICAgIGVudHJ5LT52ZXJzaW9uPUFjcXVpcmVTdHJpbmcodmVyc2lvbik7CiAgZW50cnktPm5vdGU9QWNxdWlyZVN0cmluZyhESlZVTm90ZSk7CiAgKHZvaWQpIFJlZ2lzdGVyTWFnaWNrSW5mbyhlbnRyeSk7CiAgcmV0dXJuKE1hZ2lja0ltYWdlQ29kZXJTaWduYXR1cmUpOwp9CgwKLyoKJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJQolICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAlCiUgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICUKJSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJQolICAgVSBuIHIgZSBnIGkgcyB0IGUgciBEIEogViBVIEkgbSBhIGcgZSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAlCiUgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICUKJSAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJQolICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAlCiUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUlJSUKJQolICBVbnJlZ2lzdGVyREpWVUltYWdlKCkgcmVtb3ZlcyBmb3JtYXQgcmVnaXN0cmF0aW9ucyBtYWRlIGJ5IHRoZQolICBESlZVIG1vZHVsZSBmcm9tIHRoZSBsaXN0IG9mIHN1cHBvcnRlZCBmb3JtYXRzLgolCiUgIFRoZSBmb3JtYXQgb2YgdGhlIFVucmVnaXN0ZXJESlZVSW1hZ2UgbWV0aG9kIGlzOgolCiUgICAgICBVbnJlZ2lzdGVyREpWVUltYWdlKHZvaWQpCiUKKi8KTW9kdWxlRXhwb3J0IHZvaWQgVW5yZWdpc3RlckRKVlVJbWFnZSh2b2lkKQp7CiAgKHZvaWQpIFVucmVnaXN0ZXJNYWdpY2tJbmZvKCJESlZVIik7Cn0K