LyoKICogSUJNIEFTTSBTZXJ2aWNlIFByb2Nlc3NvciBEZXZpY2UgRHJpdmVyCiAqCiAqIFRoaXMgcHJvZ3JhbSBpcyBmcmVlIHNvZnR3YXJlOyB5b3UgY2FuIHJlZGlzdHJpYnV0ZSBpdCBhbmQvb3IgbW9kaWZ5CiAqIGl0IHVuZGVyIHRoZSB0ZXJtcyBvZiB0aGUgR05VIEdlbmVyYWwgUHVibGljIExpY2Vuc2UgYXMgcHVibGlzaGVkIGJ5CiAqIHRoZSBGcmVlIFNvZnR3YXJlIEZvdW5kYXRpb247IGVpdGhlciB2ZXJzaW9uIDIgb2YgdGhlIExpY2Vuc2UsIG9yCiAqIChhdCB5b3VyIG9wdGlvbikgYW55IGxhdGVyIHZlcnNpb24uCiAqCiAqIFRoaXMgcHJvZ3JhbSBpcyBkaXN0cmlidXRlZCBpbiB0aGUgaG9wZSB0aGF0IGl0IHdpbGwgYmUgdXNlZnVsLAogKiBidXQgV0lUSE9VVCBBTlkgV0FSUkFOVFk7IHdpdGhvdXQgZXZlbiB0aGUgaW1wbGllZCB3YXJyYW50eSBvZgogKiBNRVJDSEFOVEFCSUxJVFkgb3IgRklUTkVTUyBGT1IgQSBQQVJUSUNVTEFSIFBVUlBPU0UuICBTZWUgdGhlCiAqIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlIGZvciBtb3JlIGRldGFpbHMuCiAqCiAqIFlvdSBzaG91bGQgaGF2ZSByZWNlaXZlZCBhIGNvcHkgb2YgdGhlIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlCiAqIGFsb25nIHdpdGggdGhpcyBwcm9ncmFtOyBpZiBub3QsIHdyaXRlIHRvIHRoZSBGcmVlIFNvZnR3YXJlCiAqIEZvdW5kYXRpb24sIEluYy4sIDU5IFRlbXBsZSBQbGFjZSAtIFN1aXRlIDMzMCwgQm9zdG9uLCBNQSAwMjExMS0xMzA3LCBVU0EuCiAqCiAqIENvcHlyaWdodCAoQykgSUJNIENvcnBvcmF0aW9uLCAyMDA0CiAqCiAqIEF1dGhvcjogTWF4IEFzYvZjayA8YW1heEB1cy5pYm0uY29tPgogKgogKi8KCi8qIENvbmRvciBzZXJ2aWNlIHByb2Nlc3NvciBzcGVjaWZpYyBoYXJkd2FyZSBkZWZpbml0aW9ucyAqLwoKI2lmbmRlZiBfX0lCTUFTTV9DT05ET1JfSF9fCiNkZWZpbmUgX19JQk1BU01fQ09ORE9SX0hfXwoKI2luY2x1ZGUgPGFzbS9pby5oPgoKI2RlZmluZSBWRU5ET1JJRF9JQk0JMHgxMDE0CiNkZWZpbmUgREVWSUNFSURfUlNBCTB4MDEwRgoKI2RlZmluZSBHRVRfTUZBX0FERFIoeCkgICh4ICYgMHhGRkZGRkYwMCkKCiNkZWZpbmUgTUFJTEJPWF9GVUxMKHgpICAoeCAmIDB4MDAwMDAwMDEpCgojZGVmaW5lIE5PX01GQVNfQVZBSUxBQkxFICAgICAweEZGRkZGRkZGCgoKI2RlZmluZSBJTkJPVU5EX1FVRVVFX1BPUlQgICAweDQwICAvKiBjb250YWlucyBhZGRyZXNzIG9mIG5leHQgZnJlZSBNRkEgKi8KI2RlZmluZSBPVVRCT1VORF9RVUVVRV9QT1JUICAweDQ0ICAvKiBjb250YWlucyBhZGRyZXNzIG9mIHBvc3RlZCBNRkEgICAgKi8KCiNkZWZpbmUgU1BfSU5UUl9NQVNLCTB4MDAwMDAwMDgKI2RlZmluZSBVQVJUX0lOVFJfTUFTSwkweDAwMDAwMDEwCgojZGVmaW5lIElOVFJfU1RBVFVTX1JFR0lTVEVSICAgMHgxM0EwCiNkZWZpbmUgSU5UUl9DT05UUk9MX1JFR0lTVEVSICAweDEzQTQKCiNkZWZpbmUgU0NPVVRfQ09NX0FfQkFTRSAgICAgICAgIDB4MDAwMAojZGVmaW5lIFNDT1VUX0NPTV9CX0JBU0UgICAgICAgICAweDAxMDAKI2RlZmluZSBTQ09VVF9DT01fQ19CQVNFICAgICAgICAgMHgwMjAwCiNkZWZpbmUgU0NPVVRfQ09NX0RfQkFTRSAgICAgICAgIDB4MDMwMAoKc3RhdGljIGlubGluZSBpbnQgc3BfaW50ZXJydXB0X3BlbmRpbmcodm9pZCBfX2lvbWVtICpiYXNlX2FkZHJlc3MpCnsKCXJldHVybiBTUF9JTlRSX01BU0sgJiByZWFkbChiYXNlX2FkZHJlc3MgKyBJTlRSX1NUQVRVU19SRUdJU1RFUik7Cn0KCnN0YXRpYyBpbmxpbmUgaW50IHVhcnRfaW50ZXJydXB0X3BlbmRpbmcodm9pZCBfX2lvbWVtICpiYXNlX2FkZHJlc3MpCnsKCXJldHVybiBVQVJUX0lOVFJfTUFTSyAmIHJlYWRsKGJhc2VfYWRkcmVzcyArIElOVFJfU1RBVFVTX1JFR0lTVEVSKTsKfQoKc3RhdGljIGlubGluZSB2b2lkIGlibWFzbV9lbmFibGVfaW50ZXJydXB0cyh2b2lkIF9faW9tZW0gKmJhc2VfYWRkcmVzcywgaW50IG1hc2spCnsKCXZvaWQgX19pb21lbSAqY3RybF9yZWcgPSBiYXNlX2FkZHJlc3MgKyBJTlRSX0NPTlRST0xfUkVHSVNURVI7Cgl3cml0ZWwoIHJlYWRsKGN0cmxfcmVnKSAmIH5tYXNrLCBjdHJsX3JlZyk7Cn0KCnN0YXRpYyBpbmxpbmUgdm9pZCBpYm1hc21fZGlzYWJsZV9pbnRlcnJ1cHRzKHZvaWQgX19pb21lbSAqYmFzZV9hZGRyZXNzLCBpbnQgbWFzaykKewoJdm9pZCBfX2lvbWVtICpjdHJsX3JlZyA9IGJhc2VfYWRkcmVzcyArIElOVFJfQ09OVFJPTF9SRUdJU1RFUjsKCXdyaXRlbCggcmVhZGwoY3RybF9yZWcpIHwgbWFzaywgY3RybF9yZWcpOwp9CgpzdGF0aWMgaW5saW5lIHZvaWQgZW5hYmxlX3NwX2ludGVycnVwdHModm9pZCBfX2lvbWVtICpiYXNlX2FkZHJlc3MpCnsKCWlibWFzbV9lbmFibGVfaW50ZXJydXB0cyhiYXNlX2FkZHJlc3MsIFNQX0lOVFJfTUFTSyk7Cn0KCnN0YXRpYyBpbmxpbmUgdm9pZCBkaXNhYmxlX3NwX2ludGVycnVwdHModm9pZCBfX2lvbWVtICpiYXNlX2FkZHJlc3MpCnsKCWlibWFzbV9kaXNhYmxlX2ludGVycnVwdHMoYmFzZV9hZGRyZXNzLCBTUF9JTlRSX01BU0spOwp9CgpzdGF0aWMgaW5saW5lIHZvaWQgZW5hYmxlX3VhcnRfaW50ZXJydXB0cyh2b2lkIF9faW9tZW0gKmJhc2VfYWRkcmVzcykKewoJaWJtYXNtX2VuYWJsZV9pbnRlcnJ1cHRzKGJhc2VfYWRkcmVzcywgVUFSVF9JTlRSX01BU0spOwp9CgpzdGF0aWMgaW5saW5lIHZvaWQgZGlzYWJsZV91YXJ0X2ludGVycnVwdHModm9pZCBfX2lvbWVtICpiYXNlX2FkZHJlc3MpCnsKCWlibWFzbV9kaXNhYmxlX2ludGVycnVwdHMoYmFzZV9hZGRyZXNzLCBVQVJUX0lOVFJfTUFTSyk7Cn0KCiNkZWZpbmUgdmFsaWRfbWZhKG1mYSkJKCAobWZhKSAhPSBOT19NRkFTX0FWQUlMQUJMRSApCgpzdGF0aWMgaW5saW5lIHUzMiBnZXRfbWZhX291dGJvdW5kKHZvaWQgX19pb21lbSAqYmFzZV9hZGRyZXNzKQp7CglpbnQgcmV0cnk7Cgl1MzIgbWZhOwoKCWZvciAocmV0cnk9MDsgcmV0cnk8PTEwOyByZXRyeSsrKSB7CgkJbWZhID0gcmVhZGwoYmFzZV9hZGRyZXNzICsgT1VUQk9VTkRfUVVFVUVfUE9SVCk7CgkJaWYgKHZhbGlkX21mYShtZmEpKQoJCQlicmVhazsKCX0KCXJldHVybiBtZmE7Cn0KCnN0YXRpYyBpbmxpbmUgdm9pZCBzZXRfbWZhX291dGJvdW5kKHZvaWQgX19pb21lbSAqYmFzZV9hZGRyZXNzLCB1MzIgbWZhKQp7Cgl3cml0ZWwobWZhLCBiYXNlX2FkZHJlc3MgKyBPVVRCT1VORF9RVUVVRV9QT1JUKTsKfQoKc3RhdGljIGlubGluZSB1MzIgZ2V0X21mYV9pbmJvdW5kKHZvaWQgX19pb21lbSAqYmFzZV9hZGRyZXNzKQp7Cgl1MzIgbWZhID0gcmVhZGwoYmFzZV9hZGRyZXNzICsgSU5CT1VORF9RVUVVRV9QT1JUKTsKCglpZiAoTUFJTEJPWF9GVUxMKG1mYSkpCgkJcmV0dXJuIDA7CgoJcmV0dXJuIG1mYTsKfQoKc3RhdGljIGlubGluZSB2b2lkIHNldF9tZmFfaW5ib3VuZCh2b2lkIF9faW9tZW0gKmJhc2VfYWRkcmVzcywgdTMyIG1mYSkKewoJd3JpdGVsKG1mYSwgYmFzZV9hZGRyZXNzICsgSU5CT1VORF9RVUVVRV9QT1JUKTsKfQoKc3RhdGljIGlubGluZSBzdHJ1Y3QgaTJvX21lc3NhZ2UgKmdldF9pMm9fbWVzc2FnZSh2b2lkIF9faW9tZW0gKmJhc2VfYWRkcmVzcywgdTMyIG1mYSkKewoJcmV0dXJuIChzdHJ1Y3QgaTJvX21lc3NhZ2UgKikoR0VUX01GQV9BRERSKG1mYSkgKyBiYXNlX2FkZHJlc3MpOwp9CgojZW5kaWYgLyogX19JQk1BU01fQ09ORE9SX0hfXyAqLwo=