LyoKICogKEMpIENvcHlyaWdodCAyMDAzCiAqIERhdmlkIE38bGxlciBFTFNPRlQgQUcgU3dpdHplcmxhbmQuIGQubXVlbGxlckBlbHNvZnQuY2gKICoKICogU2VlIGZpbGUgQ1JFRElUUyBmb3IgbGlzdCBvZiBwZW9wbGUgd2hvIGNvbnRyaWJ1dGVkIHRvIHRoaXMKICogcHJvamVjdC4KICoKICogVGhpcyBwcm9ncmFtIGlzIGZyZWUgc29mdHdhcmU7IHlvdSBjYW4gcmVkaXN0cmlidXRlIGl0IGFuZC9vcgogKiBtb2RpZnkgaXQgdW5kZXIgdGhlIHRlcm1zIG9mIHRoZSBHTlUgR2VuZXJhbCBQdWJsaWMgTGljZW5zZSBhcwogKiBwdWJsaXNoZWQgYnkgdGhlIEZyZWUgU29mdHdhcmUgRm91bmRhdGlvbjsgZWl0aGVyIHZlcnNpb24gMiBvZgogKiB0aGUgTGljZW5zZSwgb3IgKGF0IHlvdXIgb3B0aW9uKSBhbnkgbGF0ZXIgdmVyc2lvbi4KICoKICogVGhpcyBwcm9ncmFtIGlzIGRpc3RyaWJ1dGVkIGluIHRoZSBob3BlIHRoYXQgaXQgd2lsbCBiZSB1c2VmdWwsCiAqIGJ1dCBXSVRIT1VUIEFOWSBXQVJSQU5UWTsgd2l0aG91dCBldmVuIHRoZSBpbXBsaWVkIHdhcnJhbnR5IG9mCiAqIE1FUkNIQU5UQUJJTElUWSBvciBGSVRORVNTIEZPUiBBIFBBUlRJQ1VMQVIgUFVSUE9TRS4gIFNlZSB0aGUKICogR05VIEdlbmVyYWwgUHVibGljIExpY2Vuc2UgZm9yIG1vcmUgZGV0YWlscy4KICoKICogWW91IHNob3VsZCBoYXZlIHJlY2VpdmVkIGEgY29weSBvZiB0aGUgR05VIEdlbmVyYWwgUHVibGljIExpY2Vuc2UKICogYWxvbmcgd2l0aCB0aGlzIHByb2dyYW07IGlmIG5vdCwgd3JpdGUgdG8gdGhlIEZyZWUgU29mdHdhcmUKICogRm91bmRhdGlvbiwgSW5jLiwgNTkgVGVtcGxlIFBsYWNlLCBTdWl0ZSAzMzAsIEJvc3RvbiwKICogTUEgMDIxMTEtMTMwNyBVU0EKICovCgovKgogKiBEYXRlICYgVGltZSBzdXBwb3J0IGZvciB0aGUgYnVpbHQtaW4gU2Ftc3VuZyBTM0MyNFgwIFJUQwogKi8KCiNpbmNsdWRlIDxjb21tb24uaD4KI2luY2x1ZGUgPGNvbW1hbmQuaD4KCiNpZiBkZWZpbmVkKENPTkZJR19SVENfUzNDMjRYMCkgJiYgKGRlZmluZWQoQ09ORklHX0NNRF9EQVRFKSkKCiNpZiBkZWZpbmVkKENPTkZJR19TM0MyNDAwKQojaW5jbHVkZSA8czNjMjQwMC5oPgojZWxpZiBkZWZpbmVkKENPTkZJR19TM0MyNDEwKQojaW5jbHVkZSA8czNjMjQxMC5oPgojZW5kaWYKCiNpbmNsdWRlIDxydGMuaD4KCi8qI2RlZmluZQlERUJVRyovCgp0eXBlZGVmIGVudW0gewoJUlRDX0VOQUJMRSwKCVJUQ19ESVNBQkxFCn0gUlRDX0FDQ0VTUzsKCgpzdGF0aWMgaW5saW5lIHZvaWQgU2V0UlRDX0FjY2VzcyhSVENfQUNDRVNTIGEpCnsKCVMzQzI0WDBfUlRDICogY29uc3QgcnRjID0gUzNDMjRYMF9HZXRCYXNlX1JUQygpOwoJc3dpdGNoIChhKSB7CgkJY2FzZSBSVENfRU5BQkxFOgoJCQlydGMtPlJUQ0NPTiB8PSAweDAxOyBicmVhazsKCgkJY2FzZSBSVENfRElTQUJMRToKCQkJcnRjLT5SVENDT04gJj0gfjB4MDE7IGJyZWFrOwoJfQp9CgpzdGF0aWMgdW5zaWduZWQgYmNkMmJpbiAodWNoYXIgbikKewoJcmV0dXJuICgoKChuID4+IDQpICYgMHgwRikgKiAxMCkgKyAobiAmIDB4MEYpKTsKfQoKc3RhdGljIHVuc2lnbmVkIGNoYXIgYmluMmJjZCAodW5zaWduZWQgaW50IG4pCnsKCXJldHVybiAoKChuIC8gMTApIDw8IDQpIHwgKG4gJSAxMCkpOwp9CgovKiAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tICovCgppbnQgcnRjX2dldCAoc3RydWN0IHJ0Y190aW1lICp0bXApCnsKCVMzQzI0WDBfUlRDICogY29uc3QgcnRjID0gUzNDMjRYMF9HZXRCYXNlX1JUQygpOwoJdWNoYXIgc2VjLCBtaW4sIGhvdXIsIG1kYXksIHdkYXksIG1vbiwgeWVhcjsKCXVjaGFyIGFfc2VjLGFfbWluLCBhX2hvdXIsIGFfZGF0ZSwgYV9tb24sIGFfeWVhciwgYV9hcm1lZDsKCgkvKiBlbmFibGUgYWNjZXNzIHRvIFJUQyByZWdpc3RlcnMgKi8KCVNldFJUQ19BY2Nlc3MoUlRDX0VOQUJMRSk7CgoJLyogcmVhZCBSVEMgcmVnaXN0ZXJzICovCglkbyB7CgkJc2VjCT0gcnRjLT5CQ0RTRUM7CgkJbWluCT0gcnRjLT5CQ0RNSU47CgkJaG91cgk9IHJ0Yy0+QkNESE9VUjsKCQltZGF5CT0gcnRjLT5CQ0REQVRFOwoJCXdkYXkJPSBydGMtPkJDRERBWTsKCQltb24JPSBydGMtPkJDRE1PTjsKCQl5ZWFyCT0gcnRjLT5CQ0RZRUFSOwoJfSB3aGlsZSAoc2VjICE9IHJ0Yy0+QkNEU0VDKTsKCgkvKiByZWFkIEFMQVJNIHJlZ2lzdGVycyAqLwoJYV9zZWMJPSBydGMtPkFMTVNFQzsKCWFfbWluCT0gcnRjLT5BTE1NSU47CglhX2hvdXIJPSBydGMtPkFMTUhPVVI7CglhX2RhdGUJPSBydGMtPkFMTURBVEU7CglhX21vbgk9IHJ0Yy0+QUxNTU9OOwoJYV95ZWFyCT0gcnRjLT5BTE1ZRUFSOwoJYV9hcm1lZAk9IHJ0Yy0+UlRDQUxNOwoKCS8qIGRpc2FibGUgYWNjZXNzIHRvIFJUQyByZWdpc3RlcnMgKi8KCVNldFJUQ19BY2Nlc3MoUlRDX0RJU0FCTEUpOwoKI2lmZGVmIFJUQ19ERUJVRwoJcHJpbnRmICggIkdldCBSVEMgeWVhcjogJTAyeCBtb24vY2VudDogJTAyeCBtZGF5OiAlMDJ4IHdkYXk6ICUwMnggIgoJCSJocjogJTAyeCBtaW46ICUwMnggc2VjOiAlMDJ4XG4iLAoJCXllYXIsIG1vbiwgbWRheSwgd2RheSwKCQlob3VyLCBtaW4sIHNlYyk7CglwcmludGYgKCAiQWxhcm1zOiAlMDJ4OiB5ZWFyOiAlMDJ4IG1vbnRoOiAlMDJ4IGRhdGU6ICUwMnggaG91cjogJTAyeCBtaW46ICUwMnggc2VjOiAlMDJ4XG4iLAoJCWFfYXJtZWQsCgkJYV95ZWFyLCBhX21vbiwgYV9kYXRlLAoJCWFfaG91ciwgYV9taW4sIGFfc2VjKTsKI2VuZGlmCgoJdG1wLT50bV9zZWMgID0gYmNkMmJpbihzZWMgICYgMHg3Rik7Cgl0bXAtPnRtX21pbiAgPSBiY2QyYmluKG1pbiAgJiAweDdGKTsKCXRtcC0+dG1faG91ciA9IGJjZDJiaW4oaG91ciAmIDB4M0YpOwoJdG1wLT50bV9tZGF5ID0gYmNkMmJpbihtZGF5ICYgMHgzRik7Cgl0bXAtPnRtX21vbiAgPSBiY2QyYmluKG1vbiAmIDB4MUYpOwoJdG1wLT50bV95ZWFyID0gYmNkMmJpbih5ZWFyKTsKCXRtcC0+dG1fd2RheSA9IGJjZDJiaW4od2RheSAmIDB4MDcpOwoJaWYodG1wLT50bV95ZWFyPDcwKQoJCXRtcC0+dG1feWVhcis9MjAwMDsKCWVsc2UKCQl0bXAtPnRtX3llYXIrPTE5MDA7Cgl0bXAtPnRtX3lkYXkgPSAwOwoJdG1wLT50bV9pc2RzdD0gMDsKI2lmZGVmIFJUQ19ERUJVRwoJcHJpbnRmICggIkdldCBEQVRFOiAlNGQtJTAyZC0lMDJkICh3ZGF5PSVkKSAgVElNRTogJTJkOiUwMmQ6JTAyZFxuIiwKCQl0bXAtPnRtX3llYXIsIHRtcC0+dG1fbW9uLCB0bXAtPnRtX21kYXksIHRtcC0+dG1fd2RheSwKCQl0bXAtPnRtX2hvdXIsIHRtcC0+dG1fbWluLCB0bXAtPnRtX3NlYyk7CiNlbmRpZgoKCXJldHVybiAwOwp9Cgp2b2lkIHJ0Y19zZXQgKHN0cnVjdCBydGNfdGltZSAqdG1wKQp7CglTM0MyNFgwX1JUQyAqIGNvbnN0IHJ0YyA9IFMzQzI0WDBfR2V0QmFzZV9SVEMoKTsKCXVjaGFyIHNlYywgbWluLCBob3VyLCBtZGF5LCB3ZGF5LCBtb24sIHllYXI7CgojaWZkZWYgUlRDX0RFQlVHCglwcmludGYgKCAiU2V0IERBVEU6ICU0ZC0lMDJkLSUwMmQgKHdkYXk9JWQpICBUSU1FOiAlMmQ6JTAyZDolMDJkXG4iLAoJCXRtcC0+dG1feWVhciwgdG1wLT50bV9tb24sIHRtcC0+dG1fbWRheSwgdG1wLT50bV93ZGF5LAoJCXRtcC0+dG1faG91ciwgdG1wLT50bV9taW4sIHRtcC0+dG1fc2VjKTsKI2VuZGlmCgl5ZWFyCT0gYmluMmJjZCh0bXAtPnRtX3llYXIgJSAxMDApOwoJbW9uCT0gYmluMmJjZCh0bXAtPnRtX21vbik7Cgl3ZGF5CT0gYmluMmJjZCh0bXAtPnRtX3dkYXkpOwoJbWRheQk9IGJpbjJiY2QodG1wLT50bV9tZGF5KTsKCWhvdXIJPSBiaW4yYmNkKHRtcC0+dG1faG91cik7CgltaW4JPSBiaW4yYmNkKHRtcC0+dG1fbWluKTsKCXNlYwk9IGJpbjJiY2QodG1wLT50bV9zZWMpOwoKCS8qIGVuYWJsZSBhY2Nlc3MgdG8gUlRDIHJlZ2lzdGVycyAqLwoJU2V0UlRDX0FjY2VzcyhSVENfRU5BQkxFKTsKCgkvKiB3cml0ZSBSVEMgcmVnaXN0ZXJzICovCglydGMtPkJDRFNFQwk9IHNlYzsKCXJ0Yy0+QkNETUlOCT0gbWluOwoJcnRjLT5CQ0RIT1VSCT0gaG91cjsKCXJ0Yy0+QkNEREFURQk9IG1kYXk7CglydGMtPkJDRERBWQk9IHdkYXk7CglydGMtPkJDRE1PTgk9IG1vbjsKCXJ0Yy0+QkNEWUVBUgk9IHllYXI7CgoJLyogZGlzYWJsZSBhY2Nlc3MgdG8gUlRDIHJlZ2lzdGVycyAqLwoJU2V0UlRDX0FjY2VzcyhSVENfRElTQUJMRSk7Cn0KCnZvaWQgcnRjX3Jlc2V0ICh2b2lkKQp7CglTM0MyNFgwX1JUQyAqIGNvbnN0IHJ0YyA9IFMzQzI0WDBfR2V0QmFzZV9SVEMoKTsKCglydGMtPlJUQ0NPTiA9IChydGMtPlJUQ0NPTiAmIH4weDA2KSB8IDB4MDg7CglydGMtPlJUQ0NPTiAmPSB+KDB4MDh8MHgwMSk7Cn0KCiNlbmRpZgo=