LyoKICogU2VydmVyLXNpZGUgc29ja2V0IG1hbmFnZW1lbnQKICoKICogQ29weXJpZ2h0IChDKSAxOTk5IE1hcmN1cyBNZWlzc25lciwgT3ZlIEvldmVuCiAqCiAqIEZJWE1FOiB3ZSB1c2UgcmVhZHx3cml0ZSBhY2Nlc3MgaW4gYWxsIGNhc2VzLiBTaG91bGRuJ3Qgd2UgZGVwZW5kIHRoYXQKICogb24gdGhlIGFjY2VzcyBvZiB0aGUgY3VycmVudCBoYW5kbGU/CiAqLwoKI2luY2x1ZGUgImNvbmZpZy5oIgoKI2luY2x1ZGUgPGFzc2VydC5oPgojaW5jbHVkZSA8ZmNudGwuaD4KI2luY2x1ZGUgPHN0ZGlvLmg+CiNpbmNsdWRlIDxzdHJpbmcuaD4KI2luY2x1ZGUgPHN0ZGxpYi5oPgojaW5jbHVkZSA8ZXJybm8uaD4KI2lmZGVmIEhBVkVfU1lTX0VSUk5PX0gKIyBpbmNsdWRlIDxzeXMvZXJybm8uaD4KI2VuZGlmCiNpbmNsdWRlIDxzeXMvdGltZS5oPgojaW5jbHVkZSA8c3lzL3R5cGVzLmg+CiNpZmRlZiBIQVZFX1NZU19TT0NLRVRfSAojIGluY2x1ZGUgPHN5cy9zb2NrZXQuaD4KI2VuZGlmCiNpbmNsdWRlIDxzeXMvaW9jdGwuaD4KI2lmZGVmIEhBVkVfU1lTX0ZJTElPX0gKIyBpbmNsdWRlIDxzeXMvZmlsaW8uaD4KI2VuZGlmCiNpbmNsdWRlIDx0aW1lLmg+CiNpbmNsdWRlIDx1bmlzdGQuaD4KCiNpbmNsdWRlICJ3aW5lcnJvci5oIgojaW5jbHVkZSAid2luYmFzZS5oIgojaW5jbHVkZSAicHJvY2Vzcy5oIgojaW5jbHVkZSAiaGFuZGxlLmgiCiNpbmNsdWRlICJ0aHJlYWQuaCIKI2luY2x1ZGUgInJlcXVlc3QuaCIKCi8qIFRvIGF2b2lkIGNvbmZsaWN0cyB3aXRoIHRoZSBVbml4IHNvY2tldCBoZWFkZXJzLiBQbHVzIHdlIG9ubHkgbmVlZCBhIGZldwogKiBtYWNyb3MgYW55d2F5LgogKi8KI2RlZmluZSBVU0VfV1NfUFJFRklYCiNpbmNsdWRlICJ3aW5zb2NrMi5oIgoKc3RydWN0IHNvY2sKewogICAgc3RydWN0IG9iamVjdCAgICAgICBvYmo7ICAgICAgICAgLyogb2JqZWN0IGhlYWRlciAqLwogICAgdW5zaWduZWQgaW50ICAgICAgICBzdGF0ZTsgICAgICAgLyogc3RhdHVzIGJpdHMgKi8KICAgIHVuc2lnbmVkIGludCAgICAgICAgbWFzazsgICAgICAgIC8qIGV2ZW50IG1hc2sgKi8KICAgIHVuc2lnbmVkIGludCAgICAgICAgaG1hc2s7ICAgICAgIC8qIGhlbGQgKGJsb2NrZWQpIGV2ZW50cyAqLwogICAgdW5zaWduZWQgaW50ICAgICAgICBwbWFzazsgICAgICAgLyogcGVuZGluZyBldmVudHMgKi8KICAgIHN0cnVjdCBldmVudCAgICAgICAqZXZlbnQ7ICAgICAgIC8qIGV2ZW50IG9iamVjdCAqLwogICAgaW50ICAgICAgICAgICAgICAgICBlcnJvcnNbRkRfTUFYX0VWRU5UU107IC8qIGV2ZW50IGVycm9ycyAqLwp9OwoKc3RhdGljIHZvaWQgc29ja19kdW1wKCBzdHJ1Y3Qgb2JqZWN0ICpvYmosIGludCB2ZXJib3NlICk7CnN0YXRpYyBpbnQgc29ja19zaWduYWxlZCggc3RydWN0IG9iamVjdCAqb2JqLCBzdHJ1Y3QgdGhyZWFkICp0aHJlYWQgKTsKc3RhdGljIGludCBzb2NrX2dldF9wb2xsX2V2ZW50cyggc3RydWN0IG9iamVjdCAqb2JqICk7CnN0YXRpYyB2b2lkIHNvY2tfcG9sbF9ldmVudCggc3RydWN0IG9iamVjdCAqb2JqLCBpbnQgZXZlbnQgKTsKc3RhdGljIGludCBzb2NrX2dldF9mZCggc3RydWN0IG9iamVjdCAqb2JqICk7CnN0YXRpYyBpbnQgc29ja19nZXRfaW5mbyggc3RydWN0IG9iamVjdCAqb2JqLCBzdHJ1Y3QgZ2V0X2ZpbGVfaW5mb19yZXBseSAqcmVwbHkgKTsKc3RhdGljIHZvaWQgc29ja19kZXN0cm95KCBzdHJ1Y3Qgb2JqZWN0ICpvYmogKTsKc3RhdGljIGludCBzb2NrX2dldF9lcnJvciggaW50IGVyciApOwpzdGF0aWMgdm9pZCBzb2NrX3NldF9lcnJvcih2b2lkKTsKCnN0YXRpYyBjb25zdCBzdHJ1Y3Qgb2JqZWN0X29wcyBzb2NrX29wcyA9CnsKICAgIHNpemVvZihzdHJ1Y3Qgc29jayksICAgICAgICAgIC8qIHNpemUgKi8KICAgIHNvY2tfZHVtcCwgICAgICAgICAgICAgICAgICAgIC8qIGR1bXAgKi8KICAgIGFkZF9xdWV1ZSwgICAgICAgICAgICAgICAgICAgIC8qIGFkZF9xdWV1ZSAqLwogICAgcmVtb3ZlX3F1ZXVlLCAgICAgICAgICAgICAgICAgLyogcmVtb3ZlX3F1ZXVlICovCiAgICBzb2NrX3NpZ25hbGVkLCAgICAgICAgICAgICAgICAvKiBzaWduYWxlZCAqLwogICAgbm9fc2F0aXNmaWVkLCAgICAgICAgICAgICAgICAgLyogc2F0aXNmaWVkICovCiAgICBzb2NrX2dldF9wb2xsX2V2ZW50cywgICAgICAgICAvKiBnZXRfcG9sbF9ldmVudHMgKi8KICAgIHNvY2tfcG9sbF9ldmVudCwgICAgICAgICAgICAgIC8qIHBvbGxfZXZlbnQgKi8KICAgIHNvY2tfZ2V0X2ZkLCAgICAgICAgICAgICAgICAgIC8qIGdldF9mZCAqLwogICAgbm9fZmx1c2gsICAgICAgICAgICAgICAgICAgICAgLyogZmx1c2ggKi8KICAgIHNvY2tfZ2V0X2luZm8sICAgICAgICAgICAgICAgIC8qIGdldF9maWxlX2luZm8gKi8KICAgIE5VTEwsICAgICAgICAgICAgICAgICAgICAgICAgIC8qIHF1ZXVlX2FzeW5jICovCiAgICBzb2NrX2Rlc3Ryb3kgICAgICAgICAgICAgICAgICAvKiBkZXN0cm95ICovCn07CgpzdGF0aWMgdm9pZCBzb2NrX3Jlc2VsZWN0KCBzdHJ1Y3Qgc29jayAqc29jayApCnsKICAgIGludCBldiA9IHNvY2tfZ2V0X3BvbGxfZXZlbnRzKCAmc29jay0+b2JqICk7CiAgICBzdHJ1Y3QgcG9sbGZkIHBmZDsKCiAgICBpZiAoZGVidWdfbGV2ZWwpCiAgICAgICAgZnByaW50ZihzdGRlcnIsInNvY2tfcmVzZWxlY3QoJWQpOiBuZXcgbWFzayAleFxuIiwgc29jay0+b2JqLmZkLCBldik7CgogICAgaWYgKHNvY2stPm9iai5zZWxlY3QgPT0gLTEpIHsKICAgICAgICAvKiBwcmV2aW91c2x5IHVuY29ubmVjdGVkIHNvY2tldCwgaXMgdGhpcyByZXNlbGVjdCBzdXBwb3NlZCB0byBjb25uZWN0IGl0PyAqLwogICAgICAgIGlmICghKHNvY2stPnN0YXRlICYgfkZEX1dJTkVfTk9OQkxPQ0tJTkcpKSByZXR1cm47CiAgICAgICAgLyogb2ssIGl0IGlzLCBhdHRhY2ggaXQgdG8gdGhlIHdpbmVzZXJ2ZXIncyBtYWluIHBvbGwgbG9vcCAqLwogICAgICAgIGFkZF9zZWxlY3RfdXNlciggJnNvY2stPm9iaiApOwogICAgfQogICAgLyogdXBkYXRlIGNvbmRpdGlvbiBtYXNrICovCiAgICBzZXRfc2VsZWN0X2V2ZW50cyggJnNvY2stPm9iaiwgZXYgKTsKCiAgICAvKiBjaGVjayB3aGV0aGVyIGNvbmRpdGlvbiBpcyBzYXRpc2ZpZWQgYWxyZWFkeSAqLwogICAgcGZkLmZkID0gc29jay0+b2JqLmZkOwogICAgcGZkLmV2ZW50cyA9IGV2OwogICAgcGZkLnJldmVudHMgPSAwOwogICAgcG9sbCggJnBmZCwgMSwgMCApOwogICAgaWYgKHBmZC5yZXZlbnRzKQogICAgICAgIHNvY2tfcG9sbF9ldmVudCggJnNvY2stPm9iaiwgcGZkLnJldmVudHMpOwp9CgppbmxpbmUgc3RhdGljIGludCBzb2NrX2Vycm9yKGludCBzKQp7CiAgICB1bnNpZ25lZCBpbnQgb3B0dmFsID0gMCwgb3B0bGVuOwogICAgCiAgICBvcHRsZW4gPSBzaXplb2Yob3B0dmFsKTsKICAgIGdldHNvY2tvcHQocywgU09MX1NPQ0tFVCwgU09fRVJST1IsICh2b2lkICopICZvcHR2YWwsICZvcHRsZW4pOwogICAgcmV0dXJuIG9wdHZhbCA/IHNvY2tfZ2V0X2Vycm9yKG9wdHZhbCkgOiAwOwp9CgpzdGF0aWMgdm9pZCBzb2NrX3BvbGxfZXZlbnQoIHN0cnVjdCBvYmplY3QgKm9iaiwgaW50IGV2ZW50ICkKewogICAgc3RydWN0IHNvY2sgKnNvY2sgPSAoc3RydWN0IHNvY2sgKilvYmo7CiAgICB1bnNpZ25lZCBpbnQgZW1hc2s7CiAgICBhc3NlcnQoIHNvY2stPm9iai5vcHMgPT0gJnNvY2tfb3BzICk7CiAgICBpZiAoZGVidWdfbGV2ZWwpCiAgICAgICAgZnByaW50ZihzdGRlcnIsICJzb2NrZXQgJWQgc2VsZWN0IGV2ZW50OiAleFxuIiwgc29jay0+b2JqLmZkLCBldmVudCk7CiAgICBpZiAoc29jay0+c3RhdGUgJiBGRF9DT05ORUNUKQogICAgewogICAgICAgIC8qIGNvbm5lY3RpbmcgKi8KICAgICAgICBpZiAoZXZlbnQgJiBQT0xMT1VUKQogICAgICAgIHsKICAgICAgICAgICAgLyogd2UgZ290IGNvbm5lY3RlZCAqLwogICAgICAgICAgICBzb2NrLT5zdGF0ZSB8PSBGRF9XSU5FX0NPTk5FQ1RFRHxGRF9SRUFEfEZEX1dSSVRFOwogICAgICAgICAgICBzb2NrLT5zdGF0ZSAmPSB+RkRfQ09OTkVDVDsKICAgICAgICAgICAgc29jay0+cG1hc2sgfD0gRkRfQ09OTkVDVDsKICAgICAgICAgICAgc29jay0+ZXJyb3JzW0ZEX0NPTk5FQ1RfQklUXSA9IDA7CiAgICAgICAgICAgIGlmIChkZWJ1Z19sZXZlbCkKICAgICAgICAgICAgICAgIGZwcmludGYoc3RkZXJyLCAic29ja2V0ICVkIGNvbm5lY3Rpb24gc3VjY2Vzc1xuIiwgc29jay0+b2JqLmZkKTsKICAgICAgICB9CiAgICAgICAgZWxzZSBpZiAoZXZlbnQgJiAoUE9MTEVSUnxQT0xMSFVQKSkKICAgICAgICB7CiAgICAgICAgICAgIC8qIHdlIGRpZG4ndCBnZXQgY29ubmVjdGVkPyAqLwogICAgICAgICAgICBzb2NrLT5zdGF0ZSAmPSB+RkRfQ09OTkVDVDsKICAgICAgICAgICAgc29jay0+cG1hc2sgfD0gRkRfQ09OTkVDVDsKICAgICAgICAgICAgc29jay0+ZXJyb3JzW0ZEX0NPTk5FQ1RfQklUXSA9IHNvY2tfZXJyb3IoIHNvY2stPm9iai5mZCApOwogICAgICAgICAgICBpZiAoZGVidWdfbGV2ZWwpCiAgICAgICAgICAgICAgICBmcHJpbnRmKHN0ZGVyciwgInNvY2tldCAlZCBjb25uZWN0aW9uIGZhaWx1cmVcbiIsIHNvY2stPm9iai5mZCk7CiAgICAgICAgfQogICAgfSBlbHNlCiAgICBpZiAoc29jay0+c3RhdGUgJiBGRF9XSU5FX0xJU1RFTklORykKICAgIHsKICAgICAgICAvKiBsaXN0ZW5pbmcgKi8KICAgICAgICBpZiAoZXZlbnQgJiBQT0xMSU4pCiAgICAgICAgewogICAgICAgICAgICAvKiBpbmNvbWluZyBjb25uZWN0aW9uICovCiAgICAgICAgICAgIHNvY2stPnBtYXNrIHw9IEZEX0FDQ0VQVDsKICAgICAgICAgICAgc29jay0+ZXJyb3JzW0ZEX0FDQ0VQVF9CSVRdID0gMDsKICAgICAgICAgICAgc29jay0+aG1hc2sgfD0gRkRfQUNDRVBUOwogICAgICAgIH0KICAgICAgICBlbHNlIGlmIChldmVudCAmIChQT0xMRVJSfFBPTExIVVApKQogICAgICAgIHsKICAgICAgICAgICAgLyogZmFpbGVkIGluY29taW5nIGNvbm5lY3Rpb24/ICovCiAgICAgICAgICAgIHNvY2stPnBtYXNrIHw9IEZEX0FDQ0VQVDsKICAgICAgICAgICAgc29jay0+ZXJyb3JzW0ZEX0FDQ0VQVF9CSVRdID0gc29ja19lcnJvciggc29jay0+b2JqLmZkICk7CiAgICAgICAgICAgIHNvY2stPmhtYXNrIHw9IEZEX0FDQ0VQVDsKICAgICAgICB9CiAgICB9IGVsc2UKICAgIHsKICAgICAgICAvKiBub3JtYWwgZGF0YSBmbG93ICovCiAgICAgICAgaWYgKGV2ZW50ICYgUE9MTElOKQogICAgICAgIHsKICAgICAgICAgICAgY2hhciBkdW1teTsKCiAgICAgICAgICAgIC8qIExpbnV4IDIuNCBkb2Vzbid0IHJlcG9ydCBQT0xMSFVQIGlmIG9ubHkgb25lIHNpZGUgb2YgdGhlIHNvY2tldAogICAgICAgICAgICAgKiBoYXMgYmVlbiBjbG9zZWQsIHNvIHdlIG5lZWQgdG8gY2hlY2sgZm9yIGl0IGV4cGxpY2l0bHkgaGVyZSAqLwogICAgICAgICAgICBpZiAoIXJlY3YoIHNvY2stPm9iai5mZCwgJmR1bW15LCAxLCBNU0dfUEVFSyApKSBldmVudCA9IFBPTExIVVA7CiAgICAgICAgICAgIGVsc2UKICAgICAgICAgICAgewogICAgICAgICAgICAgICAgLyogaW5jb21pbmcgZGF0YSAqLwogICAgICAgICAgICAgICAgc29jay0+cG1hc2sgfD0gRkRfUkVBRDsKICAgICAgICAgICAgICAgIHNvY2stPmhtYXNrIHw9IEZEX1JFQUQ7CiAgICAgICAgICAgICAgICBzb2NrLT5lcnJvcnNbRkRfUkVBRF9CSVRdID0gMDsKICAgICAgICAgICAgICAgIGlmIChkZWJ1Z19sZXZlbCkKICAgICAgICAgICAgICAgICAgICBmcHJpbnRmKHN0ZGVyciwgInNvY2tldCAlZCBpcyByZWFkYWJsZVxuIiwgc29jay0+b2JqLmZkICk7CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgaWYgKGV2ZW50ICYgUE9MTE9VVCkKICAgICAgICB7CiAgICAgICAgICAgIHNvY2stPnBtYXNrIHw9IEZEX1dSSVRFOwogICAgICAgICAgICBzb2NrLT5obWFzayB8PSBGRF9XUklURTsKICAgICAgICAgICAgc29jay0+ZXJyb3JzW0ZEX1dSSVRFX0JJVF0gPSAwOwogICAgICAgICAgICBpZiAoZGVidWdfbGV2ZWwpCiAgICAgICAgICAgICAgICBmcHJpbnRmKHN0ZGVyciwgInNvY2tldCAlZCBpcyB3cml0YWJsZVxuIiwgc29jay0+b2JqLmZkKTsKICAgICAgICB9CiAgICAgICAgaWYgKGV2ZW50ICYgUE9MTFBSSSkKICAgICAgICB7CiAgICAgICAgICAgIHNvY2stPnBtYXNrIHw9IEZEX09PQjsKICAgICAgICAgICAgc29jay0+aG1hc2sgfD0gRkRfT09COwogICAgICAgICAgICBzb2NrLT5lcnJvcnNbRkRfT09CX0JJVF0gPSAwOwogICAgICAgICAgICBpZiAoZGVidWdfbGV2ZWwpCiAgICAgICAgICAgICAgICBmcHJpbnRmKHN0ZGVyciwgInNvY2tldCAlZCBnb3QgT09CIGRhdGFcbiIsIHNvY2stPm9iai5mZCk7CiAgICAgICAgfQogICAgICAgIGlmICgoKGV2ZW50ICYgUE9MTEVSUikgfHwgKChldmVudCAmIChQT0xMSU58UE9MTEhVUCkpID09IFBPTExIVVApKQogICAgICAgICAgICAmJiAoc29jay0+c3RhdGUgJiAoRkRfUkVBRHxGRF9XUklURSkpKSB7CiAgICAgICAgICAgIC8qIHNvY2tldCBjbG9zaW5nICovCiAgICAgICAgICAgIHNvY2stPmVycm9yc1tGRF9DTE9TRV9CSVRdID0gc29ja19lcnJvciggc29jay0+b2JqLmZkICk7CiAgICAgICAgICAgIHNvY2stPnN0YXRlICY9IH4oRkRfV0lORV9DT05ORUNURUR8RkRfUkVBRHxGRF9XUklURSk7CiAgICAgICAgICAgIHNvY2stPnBtYXNrIHw9IEZEX0NMT1NFOwogICAgICAgICAgICBpZiAoZGVidWdfbGV2ZWwpCiAgICAgICAgICAgICAgICBmcHJpbnRmKHN0ZGVyciwgInNvY2tldCAlZCBhYm9ydGVkIGJ5IGVycm9yICVkXG4iLAogICAgICAgICAgICAgICAgICAgICAgICBzb2NrLT5vYmouZmQsIHNvY2stPmVycm9yc1tGRF9DTE9TRV9CSVRdKTsKICAgICAgICB9CiAgICB9CgogICAgaWYgKGV2ZW50ICYgKFBPTExFUlJ8UE9MTEhVUCkpCiAgICAgICAgc2V0X3NlbGVjdF9ldmVudHMoICZzb2NrLT5vYmosIC0xICk7CiAgICBlbHNlCiAgICAgICAgc29ja19yZXNlbGVjdCggc29jayApOwogICAgLyogd2FrZSB1cCBhbnlvbmUgd2FpdGluZyBmb3Igd2hhdGV2ZXIganVzdCBoYXBwZW5lZCAqLwogICAgZW1hc2sgPSBzb2NrLT5wbWFzayAmIHNvY2stPm1hc2s7CiAgICBpZiAoZGVidWdfbGV2ZWwgJiYgZW1hc2spCiAgICAgICAgZnByaW50ZihzdGRlcnIsICJzb2NrZXQgJWQgcGVuZGluZyBldmVudHM6ICV4XG4iLCBzb2NrLT5vYmouZmQsIGVtYXNrKTsKICAgIGlmIChlbWFzayAmJiBzb2NrLT5ldmVudCkgewogICAgICAgIGlmIChkZWJ1Z19sZXZlbCkgZnByaW50ZihzdGRlcnIsICJzaWduYWxsaW5nIGV2ZW50IHB0ciAlcFxuIiwgc29jay0+ZXZlbnQpOwogICAgICAgIHNldF9ldmVudChzb2NrLT5ldmVudCk7CiAgICB9CgogICAgLyogaWYgYW55b25lIGlzIHN0dXBpZCBlbm91Z2ggdG8gd2FpdCBvbiB0aGUgc29ja2V0IG9iamVjdCBpdHNlbGYsCiAgICAgKiBtYXliZSB3ZSBzaG91bGQgd2FrZSB0aGVtIHVwIHRvbywganVzdCBpbiBjYXNlPyAqLwogICAgd2FrZV91cCggJnNvY2stPm9iaiwgMCApOwp9CgpzdGF0aWMgdm9pZCBzb2NrX2R1bXAoIHN0cnVjdCBvYmplY3QgKm9iaiwgaW50IHZlcmJvc2UgKQp7CiAgICBzdHJ1Y3Qgc29jayAqc29jayA9IChzdHJ1Y3Qgc29jayAqKW9iajsKICAgIGFzc2VydCggb2JqLT5vcHMgPT0gJnNvY2tfb3BzICk7CiAgICBwcmludGYoICJTb2NrZXQgZmQ9JWQsIHN0YXRlPSV4LCBtYXNrPSV4LCBwZW5kaW5nPSV4LCBoZWxkPSV4XG4iLAogICAgICAgICAgICBzb2NrLT5vYmouZmQsIHNvY2stPnN0YXRlLAogICAgICAgICAgICBzb2NrLT5tYXNrLCBzb2NrLT5wbWFzaywgc29jay0+aG1hc2sgKTsKfQoKc3RhdGljIGludCBzb2NrX3NpZ25hbGVkKCBzdHJ1Y3Qgb2JqZWN0ICpvYmosIHN0cnVjdCB0aHJlYWQgKnRocmVhZCApCnsKICAgIHN0cnVjdCBzb2NrICpzb2NrID0gKHN0cnVjdCBzb2NrICopb2JqOwogICAgYXNzZXJ0KCBvYmotPm9wcyA9PSAmc29ja19vcHMgKTsKCiAgICByZXR1cm4gY2hlY2tfc2VsZWN0X2V2ZW50cyggc29jay0+b2JqLmZkLCBzb2NrX2dldF9wb2xsX2V2ZW50cyggJnNvY2stPm9iaiApICk7Cn0KCnN0YXRpYyBpbnQgc29ja19nZXRfcG9sbF9ldmVudHMoIHN0cnVjdCBvYmplY3QgKm9iaiApCnsKICAgIHN0cnVjdCBzb2NrICpzb2NrID0gKHN0cnVjdCBzb2NrICopb2JqOwogICAgdW5zaWduZWQgaW50IG1hc2sgPSBzb2NrLT5tYXNrICYgc29jay0+c3RhdGUgJiB+c29jay0+aG1hc2s7CiAgICBpbnQgZXYgPSAwOwoKICAgIGFzc2VydCggb2JqLT5vcHMgPT0gJnNvY2tfb3BzICk7CgogICAgaWYgKHNvY2stPnN0YXRlICYgRkRfQ09OTkVDVCkKICAgICAgICAvKiBjb25uZWN0aW5nLCB3YWl0IGZvciB3cml0YWJsZSAqLwogICAgICAgIHJldHVybiBQT0xMT1VUOwogICAgaWYgKHNvY2stPnN0YXRlICYgRkRfV0lORV9MSVNURU5JTkcpCiAgICAgICAgLyogbGlzdGVuaW5nLCB3YWl0IGZvciByZWFkYWJsZSAqLwogICAgICAgIHJldHVybiAoc29jay0+aG1hc2sgJiBGRF9BQ0NFUFQpID8gMCA6IFBPTExJTjsKCiAgICBpZiAobWFzayAmIEZEX1JFQUQpICBldiB8PSBQT0xMSU4gfCBQT0xMUFJJOwogICAgaWYgKG1hc2sgJiBGRF9XUklURSkgZXYgfD0gUE9MTE9VVDsKICAgIHJldHVybiBldjsKfQoKc3RhdGljIGludCBzb2NrX2dldF9mZCggc3RydWN0IG9iamVjdCAqb2JqICkKewogICAgc3RydWN0IHNvY2sgKnNvY2sgPSAoc3RydWN0IHNvY2sgKilvYmo7CiAgICBhc3NlcnQoIG9iai0+b3BzID09ICZzb2NrX29wcyApOwogICAgcmV0dXJuIHNvY2stPm9iai5mZDsKfQoKc3RhdGljIGludCBzb2NrX2dldF9pbmZvKCBzdHJ1Y3Qgb2JqZWN0ICpvYmosIHN0cnVjdCBnZXRfZmlsZV9pbmZvX3JlcGx5ICpyZXBseSApCnsKICAgIGlmIChyZXBseSkKICAgIHsKICAgICAgICByZXBseS0+dHlwZSAgICAgICAgPSBGSUxFX1RZUEVfUElQRTsKICAgICAgICByZXBseS0+YXR0ciAgICAgICAgPSAwOwogICAgICAgIHJlcGx5LT5hY2Nlc3NfdGltZSA9IDA7CiAgICAgICAgcmVwbHktPndyaXRlX3RpbWUgID0gMDsKICAgICAgICByZXBseS0+c2l6ZV9oaWdoICAgPSAwOwogICAgICAgIHJlcGx5LT5zaXplX2xvdyAgICA9IDA7CiAgICAgICAgcmVwbHktPmxpbmtzICAgICAgID0gMDsKICAgICAgICByZXBseS0+aW5kZXhfaGlnaCAgPSAwOwogICAgICAgIHJlcGx5LT5pbmRleF9sb3cgICA9IDA7CiAgICAgICAgcmVwbHktPnNlcmlhbCAgICAgID0gMDsKICAgIH0KICAgIHJldHVybiBGRF9UWVBFX0RFRkFVTFQ7Cn0KCnN0YXRpYyB2b2lkIHNvY2tfZGVzdHJveSggc3RydWN0IG9iamVjdCAqb2JqICkKewogICAgc3RydWN0IHNvY2sgKnNvY2sgPSAoc3RydWN0IHNvY2sgKilvYmo7CiAgICBhc3NlcnQoIG9iai0+b3BzID09ICZzb2NrX29wcyApOwoKICAgIC8qIEZJWE1FOiBzcGVjaWFsIHNvY2tldCBzaHV0ZG93biBzdHVmZj8gKi8KICAgIGlmIChzb2NrLT5ldmVudCkKICAgIHsKICAgICAgICAvKiBpZiB0aGUgc2VydmljZSB0aHJlYWQgd2FzIHdhaXRpbmcgZm9yIHRoZSBldmVudCBvYmplY3QsCiAgICAgICAgICogd2Ugc2hvdWxkIG5vdyBzaWduYWwgaXQsIHRvIGxldCB0aGUgc2VydmljZSB0aHJlYWQKICAgICAgICAgKiBvYmplY3QgZGV0ZWN0IHRoYXQgaXQgaXMgbm93IG9ycGhhbmVkLi4uICovCiAgICAgICAgaWYgKHNvY2stPm1hc2sgJiBGRF9XSU5FX1NFUlZFVkVOVCkKICAgICAgICAgICAgc2V0X2V2ZW50KCBzb2NrLT5ldmVudCApOwogICAgICAgIC8qIHdlJ3JlIHRocm91Z2ggd2l0aCBpdCAqLwogICAgICAgIHJlbGVhc2Vfb2JqZWN0KCBzb2NrLT5ldmVudCApOwogICAgfQp9CgovKiBjcmVhdGUgYSBuZXcgYW5kIHVuY29ubmVjdGVkIHNvY2tldCAqLwpzdGF0aWMgc3RydWN0IG9iamVjdCAqY3JlYXRlX3NvY2tldCggaW50IGZhbWlseSwgaW50IHR5cGUsIGludCBwcm90b2NvbCApCnsKICAgIHN0cnVjdCBzb2NrICpzb2NrOwogICAgaW50IHNvY2tmZDsKCiAgICBzb2NrZmQgPSBzb2NrZXQoIGZhbWlseSwgdHlwZSwgcHJvdG9jb2wgKTsKICAgIGlmIChkZWJ1Z19sZXZlbCkKICAgICAgICBmcHJpbnRmKHN0ZGVyciwic29ja2V0KCVkLCVkLCVkKT0lZFxuIixmYW1pbHksdHlwZSxwcm90b2NvbCxzb2NrZmQpOwogICAgaWYgKHNvY2tmZCA9PSAtMSkgewogICAgICAgIHNvY2tfc2V0X2Vycm9yKCk7CiAgICAgICAgcmV0dXJuIE5VTEw7CiAgICB9CiAgICBmY250bChzb2NrZmQsIEZfU0VURkwsIE9fTk9OQkxPQ0spOyAvKiBtYWtlIHNvY2tldCBub25ibG9ja2luZyAqLwogICAgaWYgKCEoc29jayA9IGFsbG9jX29iamVjdCggJnNvY2tfb3BzLCAtMSApKSkgcmV0dXJuIE5VTEw7CiAgICBzb2NrLT5vYmouZmQgPSBzb2NrZmQ7CiAgICBzb2NrLT5zdGF0ZSA9ICh0eXBlICE9IFNPQ0tfU1RSRUFNKSA/IChGRF9SRUFEfEZEX1dSSVRFKSA6IDA7CiAgICBzb2NrLT5tYXNrICA9IDA7CiAgICBzb2NrLT5obWFzayA9IDA7CiAgICBzb2NrLT5wbWFzayA9IDA7CiAgICBzb2NrLT5ldmVudCA9IE5VTEw7CiAgICBzb2NrX3Jlc2VsZWN0KCBzb2NrICk7CiAgICBjbGVhcl9lcnJvcigpOwogICAgcmV0dXJuICZzb2NrLT5vYmo7Cn0KCi8qIGFjY2VwdCBhIHNvY2tldCAoY3JlYXRlcyBhIG5ldyBmZCkgKi8Kc3RhdGljIHN0cnVjdCBvYmplY3QgKmFjY2VwdF9zb2NrZXQoIGhhbmRsZV90IGhhbmRsZSApCnsKICAgIHN0cnVjdCBzb2NrICphY2NlcHRzb2NrOwogICAgc3RydWN0IHNvY2sgKnNvY2s7CiAgICBpbnQJYWNjZXB0ZmQ7CiAgICBzdHJ1Y3Qgc29ja2FkZHIJc2FkZHI7CiAgICBpbnQJCQlzbGVuOwoKICAgIHNvY2s9KHN0cnVjdCBzb2NrKilnZXRfaGFuZGxlX29iaihjdXJyZW50LT5wcm9jZXNzLGhhbmRsZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBHRU5FUklDX1JFQUR8R0VORVJJQ19XUklURXxTWU5DSFJPTklaRSwmc29ja19vcHMpOwogICAgaWYgKCFzb2NrKQogICAgCXJldHVybiBOVUxMOwogICAgLyogVHJ5IHRvIGFjY2VwdCgyKS4gV2UgY2FuJ3QgYmUgc2FmZSB0aGF0IHRoaXMgYW4gYWxyZWFkeSBjb25uZWN0ZWQgc29ja2V0IAogICAgICogb3IgdGhhdCBhY2NlcHQoKSBpcyBhbGxvd2VkIG9uIGl0LiBJbiB0aG9zZSBjYXNlcyB3ZSB3aWxsIGdldCAtMS9lcnJubwogICAgICogcmV0dXJuLgogICAgICovCiAgICBzbGVuID0gc2l6ZW9mKHNhZGRyKTsKICAgIGFjY2VwdGZkID0gYWNjZXB0KHNvY2stPm9iai5mZCwmc2FkZHIsJnNsZW4pOwogICAgaWYgKGFjY2VwdGZkPT0tMSkgewogICAgCXNvY2tfc2V0X2Vycm9yKCk7CiAgICAgICAgcmVsZWFzZV9vYmplY3QoIHNvY2sgKTsKCXJldHVybiBOVUxMOwogICAgfQogICAgaWYgKCEoYWNjZXB0c29jayA9IGFsbG9jX29iamVjdCggJnNvY2tfb3BzLCAtMSApKSkKICAgIHsKICAgICAgICByZWxlYXNlX29iamVjdCggc29jayApOwogICAgICAgIHJldHVybiBOVUxMOwogICAgfQoKICAgIC8qIG5ld2x5IGNyZWF0ZWQgc29ja2V0IGdldHMgdGhlIHNhbWUgcHJvcGVydGllcyBvZiB0aGUgbGlzdGVuaW5nIHNvY2tldCAqLwogICAgZmNudGwoYWNjZXB0ZmQsIEZfU0VURkwsIE9fTk9OQkxPQ0spOyAvKiBtYWtlIHNvY2tldCBub25ibG9ja2luZyAqLwogICAgYWNjZXB0c29jay0+b2JqLmZkID0gYWNjZXB0ZmQ7CiAgICBhY2NlcHRzb2NrLT5zdGF0ZSAgPSBGRF9XSU5FX0NPTk5FQ1RFRHxGRF9SRUFEfEZEX1dSSVRFOwogICAgaWYgKHNvY2stPnN0YXRlICYgRkRfV0lORV9OT05CTE9DS0lORykKICAgICAgICBhY2NlcHRzb2NrLT5zdGF0ZSB8PSBGRF9XSU5FX05PTkJMT0NLSU5HOwogICAgYWNjZXB0c29jay0+bWFzayAgID0gc29jay0+bWFzazsKICAgIGFjY2VwdHNvY2stPmhtYXNrICA9IDA7CiAgICBhY2NlcHRzb2NrLT5wbWFzayAgPSAwOwogICAgYWNjZXB0c29jay0+ZXZlbnQgID0gTlVMTDsKICAgIGlmIChzb2NrLT5ldmVudCAmJiAhKHNvY2stPm1hc2sgJiBGRF9XSU5FX1NFUlZFVkVOVCkpCiAgICAgICAgYWNjZXB0c29jay0+ZXZlbnQgPSAoc3RydWN0IGV2ZW50ICopZ3JhYl9vYmplY3QoIHNvY2stPmV2ZW50ICk7CgogICAgc29ja19yZXNlbGVjdCggYWNjZXB0c29jayApOwogICAgY2xlYXJfZXJyb3IoKTsKICAgIHNvY2stPnBtYXNrICY9IH5GRF9BQ0NFUFQ7CiAgICBzb2NrLT5obWFzayAmPSB+RkRfQUNDRVBUOwogICAgc29ja19yZXNlbGVjdCggc29jayApOwogICAgcmVsZWFzZV9vYmplY3QoIHNvY2sgKTsKICAgIHJldHVybiAmYWNjZXB0c29jay0+b2JqOwp9CgovKiBzZXQgdGhlIGxhc3QgZXJyb3IgZGVwZW5kaW5nIG9uIGVycm5vICovCnN0YXRpYyBpbnQgc29ja19nZXRfZXJyb3IoIGludCBlcnIgKQp7CiAgICBzd2l0Y2ggKGVycikKICAgIHsKICAgICAgICBjYXNlIEVJTlRSOiAgICAgICAgICAgICByZXR1cm4gV1NBRUlOVFI7IGJyZWFrOwogICAgICAgIGNhc2UgRUJBREY6ICAgICAgICAgICAgIHJldHVybiBXU0FFQkFERjsgYnJlYWs7CiAgICAgICAgY2FzZSBFUEVSTToKICAgICAgICBjYXNlIEVBQ0NFUzogICAgICAgICAgICByZXR1cm4gV1NBRUFDQ0VTOyBicmVhazsKICAgICAgICBjYXNlIEVGQVVMVDogICAgICAgICAgICByZXR1cm4gV1NBRUZBVUxUOyBicmVhazsKICAgICAgICBjYXNlIEVJTlZBTDogICAgICAgICAgICByZXR1cm4gV1NBRUlOVkFMOyBicmVhazsKICAgICAgICBjYXNlIEVNRklMRTogICAgICAgICAgICByZXR1cm4gV1NBRU1GSUxFOyBicmVhazsKICAgICAgICBjYXNlIEVXT1VMREJMT0NLOiAgICAgICByZXR1cm4gV1NBRVdPVUxEQkxPQ0s7IGJyZWFrOwogICAgICAgIGNhc2UgRUlOUFJPR1JFU1M6ICAgICAgIHJldHVybiBXU0FFSU5QUk9HUkVTUzsgYnJlYWs7CiAgICAgICAgY2FzZSBFQUxSRUFEWTogICAgICAgICAgcmV0dXJuIFdTQUVBTFJFQURZOyBicmVhazsKICAgICAgICBjYXNlIEVOT1RTT0NLOiAgICAgICAgICByZXR1cm4gV1NBRU5PVFNPQ0s7IGJyZWFrOwogICAgICAgIGNhc2UgRURFU1RBRERSUkVROiAgICAgIHJldHVybiBXU0FFREVTVEFERFJSRVE7IGJyZWFrOwogICAgICAgIGNhc2UgRU1TR1NJWkU6ICAgICAgICAgIHJldHVybiBXU0FFTVNHU0laRTsgYnJlYWs7CiAgICAgICAgY2FzZSBFUFJPVE9UWVBFOiAgICAgICAgcmV0dXJuIFdTQUVQUk9UT1RZUEU7IGJyZWFrOwogICAgICAgIGNhc2UgRU5PUFJPVE9PUFQ6ICAgICAgIHJldHVybiBXU0FFTk9QUk9UT09QVDsgYnJlYWs7CiAgICAgICAgY2FzZSBFUFJPVE9OT1NVUFBPUlQ6ICAgcmV0dXJuIFdTQUVQUk9UT05PU1VQUE9SVDsgYnJlYWs7CiAgICAgICAgY2FzZSBFU09DS1ROT1NVUFBPUlQ6ICAgcmV0dXJuIFdTQUVTT0NLVE5PU1VQUE9SVDsgYnJlYWs7CiAgICAgICAgY2FzZSBFT1BOT1RTVVBQOiAgICAgICAgcmV0dXJuIFdTQUVPUE5PVFNVUFA7IGJyZWFrOwogICAgICAgIGNhc2UgRVBGTk9TVVBQT1JUOiAgICAgIHJldHVybiBXU0FFUEZOT1NVUFBPUlQ7IGJyZWFrOwogICAgICAgIGNhc2UgRUFGTk9TVVBQT1JUOiAgICAgIHJldHVybiBXU0FFQUZOT1NVUFBPUlQ7IGJyZWFrOwogICAgICAgIGNhc2UgRUFERFJJTlVTRTogICAgICAgIHJldHVybiBXU0FFQUREUklOVVNFOyBicmVhazsKICAgICAgICBjYXNlIEVBRERSTk9UQVZBSUw6ICAgICByZXR1cm4gV1NBRUFERFJOT1RBVkFJTDsgYnJlYWs7CiAgICAgICAgY2FzZSBFTkVURE9XTjogICAgICAgICAgcmV0dXJuIFdTQUVORVRET1dOOyBicmVhazsKICAgICAgICBjYXNlIEVORVRVTlJFQUNIOiAgICAgICByZXR1cm4gV1NBRU5FVFVOUkVBQ0g7IGJyZWFrOwogICAgICAgIGNhc2UgRU5FVFJFU0VUOiAgICAgICAgIHJldHVybiBXU0FFTkVUUkVTRVQ7IGJyZWFrOwogICAgICAgIGNhc2UgRUNPTk5BQk9SVEVEOiAgICAgIHJldHVybiBXU0FFQ09OTkFCT1JURUQ7IGJyZWFrOwogICAgICAgIGNhc2UgRVBJUEU6CiAgICAgICAgY2FzZSBFQ09OTlJFU0VUOiAgICAgICAgcmV0dXJuIFdTQUVDT05OUkVTRVQ7IGJyZWFrOwogICAgICAgIGNhc2UgRU5PQlVGUzogICAgICAgICAgIHJldHVybiBXU0FFTk9CVUZTOyBicmVhazsKICAgICAgICBjYXNlIEVJU0NPTk46ICAgICAgICAgICByZXR1cm4gV1NBRUlTQ09OTjsgYnJlYWs7CiAgICAgICAgY2FzZSBFTk9UQ09OTjogICAgICAgICAgcmV0dXJuIFdTQUVOT1RDT05OOyBicmVhazsKICAgICAgICBjYXNlIEVTSFVURE9XTjogICAgICAgICByZXR1cm4gV1NBRVNIVVRET1dOOyBicmVhazsKICAgICAgICBjYXNlIEVUT09NQU5ZUkVGUzogICAgICByZXR1cm4gV1NBRVRPT01BTllSRUZTOyBicmVhazsKICAgICAgICBjYXNlIEVUSU1FRE9VVDogICAgICAgICByZXR1cm4gV1NBRVRJTUVET1VUOyBicmVhazsKICAgICAgICBjYXNlIEVDT05OUkVGVVNFRDogICAgICByZXR1cm4gV1NBRUNPTk5SRUZVU0VEOyBicmVhazsKICAgICAgICBjYXNlIEVMT09QOiAgICAgICAgICAgICByZXR1cm4gV1NBRUxPT1A7IGJyZWFrOwogICAgICAgIGNhc2UgRU5BTUVUT09MT05HOiAgICAgIHJldHVybiBXU0FFTkFNRVRPT0xPTkc7IGJyZWFrOwogICAgICAgIGNhc2UgRUhPU1RET1dOOiAgICAgICAgIHJldHVybiBXU0FFSE9TVERPV047IGJyZWFrOwogICAgICAgIGNhc2UgRUhPU1RVTlJFQUNIOiAgICAgIHJldHVybiBXU0FFSE9TVFVOUkVBQ0g7IGJyZWFrOwogICAgICAgIGNhc2UgRU5PVEVNUFRZOiAgICAgICAgIHJldHVybiBXU0FFTk9URU1QVFk7IGJyZWFrOwojaWZkZWYgRVBST0NMSU0KICAgICAgICBjYXNlIEVQUk9DTElNOiAgICAgICAgICByZXR1cm4gV1NBRVBST0NMSU07IGJyZWFrOwojZW5kaWYKI2lmZGVmIEVVU0VSUwogICAgICAgIGNhc2UgRVVTRVJTOiAgICAgICAgICAgIHJldHVybiBXU0FFVVNFUlM7IGJyZWFrOwojZW5kaWYKI2lmZGVmIEVEUVVPVAogICAgICAgIGNhc2UgRURRVU9UOiAgICAgICAgICAgIHJldHVybiBXU0FFRFFVT1Q7IGJyZWFrOwojZW5kaWYKI2lmZGVmIEVTVEFMRQogICAgICAgIGNhc2UgRVNUQUxFOiAgICAgICAgICAgIHJldHVybiBXU0FFU1RBTEU7IGJyZWFrOwojZW5kaWYKI2lmZGVmIEVSRU1PVEUKICAgICAgICBjYXNlIEVSRU1PVEU6ICAgICAgICAgICByZXR1cm4gV1NBRVJFTU9URTsgYnJlYWs7CiNlbmRpZgogICAgZGVmYXVsdDogZXJybm89ZXJyOyBwZXJyb3IoInNvY2tfc2V0X2Vycm9yIik7IHJldHVybiBFUlJPUl9VTktOT1dOOyBicmVhazsKICAgIH0KfQoKLyogc2V0IHRoZSBsYXN0IGVycm9yIGRlcGVuZGluZyBvbiBlcnJubyAqLwpzdGF0aWMgdm9pZCBzb2NrX3NldF9lcnJvcih2b2lkKQp7CiAgICBzZXRfZXJyb3IoIHNvY2tfZ2V0X2Vycm9yKCBlcnJubyApICk7Cn0KCi8qIGNyZWF0ZSBhIHNvY2tldCAqLwpERUNMX0hBTkRMRVIoY3JlYXRlX3NvY2tldCkKewogICAgc3RydWN0IG9iamVjdCAqb2JqOwoKICAgIHJlcGx5LT5oYW5kbGUgPSAwOwogICAgaWYgKChvYmogPSBjcmVhdGVfc29ja2V0KCByZXEtPmZhbWlseSwgcmVxLT50eXBlLCByZXEtPnByb3RvY29sICkpICE9IE5VTEwpCiAgICB7CiAgICAgICAgcmVwbHktPmhhbmRsZSA9IGFsbG9jX2hhbmRsZSggY3VycmVudC0+cHJvY2Vzcywgb2JqLCByZXEtPmFjY2VzcywgcmVxLT5pbmhlcml0ICk7CiAgICAgICAgcmVsZWFzZV9vYmplY3QoIG9iaiApOwogICAgfQp9CgovKiBhY2NlcHQgYSBzb2NrZXQgKi8KREVDTF9IQU5ETEVSKGFjY2VwdF9zb2NrZXQpCnsKICAgIHN0cnVjdCBvYmplY3QgKm9iajsKCiAgICByZXBseS0+aGFuZGxlID0gMDsKICAgIGlmICgob2JqID0gYWNjZXB0X3NvY2tldCggcmVxLT5saGFuZGxlICkpICE9IE5VTEwpCiAgICB7CiAgICAgICAgcmVwbHktPmhhbmRsZSA9IGFsbG9jX2hhbmRsZSggY3VycmVudC0+cHJvY2Vzcywgb2JqLCByZXEtPmFjY2VzcywgcmVxLT5pbmhlcml0ICk7CiAgICAgICAgcmVsZWFzZV9vYmplY3QoIG9iaiApOwogICAgfQp9CgovKiBzZXQgc29ja2V0IGV2ZW50IHBhcmFtZXRlcnMgKi8KREVDTF9IQU5ETEVSKHNldF9zb2NrZXRfZXZlbnQpCnsKICAgIHN0cnVjdCBzb2NrICpzb2NrOwogICAgc3RydWN0IGV2ZW50ICpvZXZlbnQ7CiAgICB1bnNpZ25lZCBpbnQgb21hc2s7CgogICAgc29jaz0oc3RydWN0IHNvY2sqKWdldF9oYW5kbGVfb2JqKGN1cnJlbnQtPnByb2Nlc3MscmVxLT5oYW5kbGUsR0VORVJJQ19SRUFEfEdFTkVSSUNfV1JJVEV8U1lOQ0hST05JWkUsJnNvY2tfb3BzKTsKICAgIGlmICghc29jaykKCXJldHVybjsKICAgIG9ldmVudCA9IHNvY2stPmV2ZW50OwogICAgb21hc2sgID0gc29jay0+bWFzazsKICAgIHNvY2stPm1hc2sgICAgPSByZXEtPm1hc2s7CiAgICBzb2NrLT5ldmVudCAgID0gZ2V0X2V2ZW50X29iaiggY3VycmVudC0+cHJvY2VzcywgcmVxLT5ldmVudCwgRVZFTlRfTU9ESUZZX1NUQVRFICk7CiAgICBpZiAoZGVidWdfbGV2ZWwgJiYgc29jay0+ZXZlbnQpIGZwcmludGYoc3RkZXJyLCAiZXZlbnQgcHRyOiAlcFxuIiwgc29jay0+ZXZlbnQpOwogICAgc29ja19yZXNlbGVjdCggc29jayApOwogICAgaWYgKHNvY2stPm1hc2spCiAgICAgICAgc29jay0+c3RhdGUgfD0gRkRfV0lORV9OT05CTE9DS0lORzsKCiAgICAvKiBpZiBhIG5ldHdvcmsgZXZlbnQgaXMgcGVuZGluZywgc2lnbmFsIHRoZSBldmVudCBvYmplY3QgCiAgICAgICBpdCBpcyBwb3NzaWJsZSB0aGF0IEZEX0NPTk5FQ1Qgb3IgRkRfQUNDRVBUIG5ldHdvcmsgZXZlbnRzIGhhcyBoYXBwZW5lZAogICAgICAgYmVmb3JlIGEgV1NBRXZlbnRTZWxlY3QoKSB3YXMgZG9uZSBvbiBpdC4gCiAgICAgICAod2hlbiBkZWFsaW5nIHdpdGggQXN5bmNocm9ub3VzIHNvY2tldCkgICovCiAgICBpZiAoc29jay0+cG1hc2sgJiBzb2NrLT5tYXNrKQogICAgICAgIHNldF9ldmVudChzb2NrLT5ldmVudCk7CiAgICAKICAgIGlmIChvZXZlbnQpCiAgICB7CiAgICAgICAgaWYgKChvZXZlbnQgIT0gc29jay0+ZXZlbnQpICYmIChvbWFzayAmIEZEX1dJTkVfU0VSVkVWRU5UKSkKICAgICAgICAgICAgLyogaWYgdGhlIHNlcnZpY2UgdGhyZWFkIHdhcyB3YWl0aW5nIGZvciB0aGUgb2xkIGV2ZW50IG9iamVjdCwKICAgICAgICAgICAgICogd2Ugc2hvdWxkIG5vdyBzaWduYWwgaXQsIHRvIGxldCB0aGUgc2VydmljZSB0aHJlYWQKICAgICAgICAgICAgICogb2JqZWN0IGRldGVjdCB0aGF0IGl0IGlzIG5vdyBvcnBoYW5lZC4uLiAqLwogICAgICAgICAgICBzZXRfZXZlbnQoIG9ldmVudCApOwogICAgICAgIC8qIHdlJ3JlIHRocm91Z2ggd2l0aCBpdCAqLwogICAgICAgIHJlbGVhc2Vfb2JqZWN0KCBvZXZlbnQgKTsKICAgIH0KICAgIHJlbGVhc2Vfb2JqZWN0KCAmc29jay0+b2JqICk7Cn0KCi8qIGdldCBzb2NrZXQgZXZlbnQgcGFyYW1ldGVycyAqLwpERUNMX0hBTkRMRVIoZ2V0X3NvY2tldF9ldmVudCkKewogICAgc3RydWN0IHNvY2sgKnNvY2s7CgogICAgc29jaz0oc3RydWN0IHNvY2sqKWdldF9oYW5kbGVfb2JqKGN1cnJlbnQtPnByb2Nlc3MscmVxLT5oYW5kbGUsR0VORVJJQ19SRUFEfEdFTkVSSUNfV1JJVEV8U1lOQ0hST05JWkUsJnNvY2tfb3BzKTsKICAgIGlmICghc29jaykKICAgIHsKICAgICAgICByZXBseS0+bWFzayAgPSAwOwogICAgICAgIHJlcGx5LT5wbWFzayA9IDA7CiAgICAgICAgcmVwbHktPnN0YXRlID0gMDsKICAgICAgICBzZXRfZXJyb3IoIFdTQUVOT1RTT0NLICk7CiAgICAgICAgcmV0dXJuOwogICAgfQogICAgcmVwbHktPm1hc2sgID0gc29jay0+bWFzazsKICAgIHJlcGx5LT5wbWFzayA9IHNvY2stPnBtYXNrOwogICAgcmVwbHktPnN0YXRlID0gc29jay0+c3RhdGU7CiAgICBzZXRfcmVwbHlfZGF0YSggc29jay0+ZXJyb3JzLCBtaW4oIGdldF9yZXBseV9tYXhfc2l6ZSgpLCBzaXplb2Yoc29jay0+ZXJyb3JzKSApKTsKCiAgICBpZiAocmVxLT5zZXJ2aWNlKQogICAgewogICAgICAgIGhhbmRsZV90IHNfZXZlbnQgPSByZXEtPnNfZXZlbnQ7CiAgICAgICAgaWYgKHNfZXZlbnQpCiAgICAgICAgewogICAgICAgICAgICBzdHJ1Y3QgZXZlbnQgKnNldmVudCA9IGdldF9ldmVudF9vYmooY3VycmVudC0+cHJvY2VzcywgcmVxLT5zX2V2ZW50LCAwKTsKICAgICAgICAgICAgaWYgKHNldmVudCA9PSBzb2NrLT5ldmVudCkgc19ldmVudCA9IDA7CiAgICAgICAgICAgIHJlbGVhc2Vfb2JqZWN0KCBzZXZlbnQgKTsKICAgICAgICB9CiAgICAgICAgaWYgKCFzX2V2ZW50KQogICAgICAgIHsKICAgICAgICAgICAgaWYgKHJlcS0+Y19ldmVudCkKICAgICAgICAgICAgewogICAgICAgICAgICAgICAgc3RydWN0IGV2ZW50ICpjZXZlbnQgPSBnZXRfZXZlbnRfb2JqKGN1cnJlbnQtPnByb2Nlc3MsIHJlcS0+Y19ldmVudCwgRVZFTlRfTU9ESUZZX1NUQVRFKTsKICAgICAgICAgICAgICAgIHJlc2V0X2V2ZW50KCBjZXZlbnQgKTsKICAgICAgICAgICAgICAgIHJlbGVhc2Vfb2JqZWN0KCBjZXZlbnQgKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBzb2NrLT5wbWFzayA9IDA7CiAgICAgICAgICAgIHNvY2tfcmVzZWxlY3QoIHNvY2sgKTsKICAgICAgICB9CiAgICAgICAgZWxzZSBzZXRfZXJyb3IoV1NBRUlOVkFMKTsKICAgIH0KICAgIHJlbGVhc2Vfb2JqZWN0KCAmc29jay0+b2JqICk7Cn0KCi8qIHJlLWVuYWJsZSBwZW5kaW5nIHNvY2tldCBldmVudHMgKi8KREVDTF9IQU5ETEVSKGVuYWJsZV9zb2NrZXRfZXZlbnQpCnsKICAgIHN0cnVjdCBzb2NrICpzb2NrOwoKICAgIHNvY2s9KHN0cnVjdCBzb2NrKilnZXRfaGFuZGxlX29iaihjdXJyZW50LT5wcm9jZXNzLHJlcS0+aGFuZGxlLEdFTkVSSUNfUkVBRHxHRU5FUklDX1dSSVRFfFNZTkNIUk9OSVpFLCZzb2NrX29wcyk7CiAgICBpZiAoIXNvY2spCiAgICAJcmV0dXJuOwogICAgc29jay0+cG1hc2sgJj0gfnJlcS0+bWFzazsgLyogaXMgdGhpcyBzYWZlPyAqLwogICAgc29jay0+aG1hc2sgJj0gfnJlcS0+bWFzazsKICAgIHNvY2stPnN0YXRlIHw9IHJlcS0+c3N0YXRlOwogICAgc29jay0+c3RhdGUgJj0gfnJlcS0+Y3N0YXRlOwogICAgc29ja19yZXNlbGVjdCggc29jayApOwoKICAgIC8qIHNlcnZpY2UgdHJpZ2dlciAqLwogICAgaWYgKHJlcS0+bWFzayAmIEZEX1dJTkVfU0VSVkVWRU5UKQogICAgewogICAgICAgIHNvY2stPnBtYXNrIHw9IEZEX1dJTkVfU0VSVkVWRU5UOwogICAgICAgIGlmIChzb2NrLT5ldmVudCkgewogICAgICAgICAgICBpZiAoZGVidWdfbGV2ZWwpIGZwcmludGYoc3RkZXJyLCAic2lnbmFsbGluZyBzZXJ2aWNlIGV2ZW50IHB0ciAlcFxuIiwgc29jay0+ZXZlbnQpOwogICAgICAgICAgICBzZXRfZXZlbnQoc29jay0+ZXZlbnQpOwogICAgICAgIH0KICAgIH0KCiAgICByZWxlYXNlX29iamVjdCggJnNvY2stPm9iaiApOwp9Cg==