LyoKICogT01BUDIgTWNTUEkgY29udHJvbGxlciBkcml2ZXIKICoKICogQ29weXJpZ2h0IChDKSAyMDA1LCAyMDA2IE5va2lhIENvcnBvcmF0aW9uCiAqIEF1dGhvcjoJU2FtdWVsIE9ydGl6IDxzYW11ZWwub3J0aXpAbm9raWEuY29tPiBhbmQKICoJCUp1aGEgWXJq9mzkIDxqdWhhLnlyam9sYUBub2tpYS5jb20+CiAqCiAqIFRoaXMgcHJvZ3JhbSBpcyBmcmVlIHNvZnR3YXJlOyB5b3UgY2FuIHJlZGlzdHJpYnV0ZSBpdCBhbmQvb3IgbW9kaWZ5CiAqIGl0IHVuZGVyIHRoZSB0ZXJtcyBvZiB0aGUgR05VIEdlbmVyYWwgUHVibGljIExpY2Vuc2UgYXMgcHVibGlzaGVkIGJ5CiAqIHRoZSBGcmVlIFNvZnR3YXJlIEZvdW5kYXRpb247IGVpdGhlciB2ZXJzaW9uIDIgb2YgdGhlIExpY2Vuc2UsIG9yCiAqIChhdCB5b3VyIG9wdGlvbikgYW55IGxhdGVyIHZlcnNpb24uCiAqCiAqIFRoaXMgcHJvZ3JhbSBpcyBkaXN0cmlidXRlZCBpbiB0aGUgaG9wZSB0aGF0IGl0IHdpbGwgYmUgdXNlZnVsLAogKiBidXQgV0lUSE9VVCBBTlkgV0FSUkFOVFk7IHdpdGhvdXQgZXZlbiB0aGUgaW1wbGllZCB3YXJyYW50eSBvZgogKiBNRVJDSEFOVEFCSUxJVFkgb3IgRklUTkVTUyBGT1IgQSBQQVJUSUNVTEFSIFBVUlBPU0UuIFNlZSB0aGUKICogR05VIEdlbmVyYWwgUHVibGljIExpY2Vuc2UgZm9yIG1vcmUgZGV0YWlscy4KICoKICogWW91IHNob3VsZCBoYXZlIHJlY2VpdmVkIGEgY29weSBvZiB0aGUgR05VIEdlbmVyYWwgUHVibGljIExpY2Vuc2UKICogYWxvbmcgd2l0aCB0aGlzIHByb2dyYW07IGlmIG5vdCwgd3JpdGUgdG8gdGhlIEZyZWUgU29mdHdhcmUKICogRm91bmRhdGlvbiwgSW5jLiwgNTkgVGVtcGxlIFBsYWNlLCBTdWl0ZSAzMzAsIEJvc3RvbiwgTUEgMDIxMTEtMTMwNyBVU0EKICoKICovCgojaW5jbHVkZSA8bGludXgva2VybmVsLmg+CiNpbmNsdWRlIDxsaW51eC9pbml0Lmg+CiNpbmNsdWRlIDxsaW51eC9pbnRlcnJ1cHQuaD4KI2luY2x1ZGUgPGxpbnV4L21vZHVsZS5oPgojaW5jbHVkZSA8bGludXgvZGV2aWNlLmg+CiNpbmNsdWRlIDxsaW51eC9kZWxheS5oPgojaW5jbHVkZSA8bGludXgvZG1hLW1hcHBpbmcuaD4KI2luY2x1ZGUgPGxpbnV4L3BsYXRmb3JtX2RldmljZS5oPgojaW5jbHVkZSA8bGludXgvZXJyLmg+CiNpbmNsdWRlIDxsaW51eC9jbGsuaD4KI2luY2x1ZGUgPGxpbnV4L2lvLmg+CiNpbmNsdWRlIDxsaW51eC9zbGFiLmg+CgojaW5jbHVkZSA8bGludXgvc3BpL3NwaS5oPgoKI2luY2x1ZGUgPHBsYXQvZG1hLmg+CiNpbmNsdWRlIDxwbGF0L2Nsb2NrLmg+CiNpbmNsdWRlIDxwbGF0L21jc3BpLmg+CgojZGVmaW5lIE9NQVAyX01DU1BJX01BWF9GUkVRCQk0ODAwMDAwMAoKLyogT01BUDIgaGFzIDMgU1BJIGNvbnRyb2xsZXJzLCB3aGlsZSBPTUFQMyBoYXMgNCAqLwojZGVmaW5lIE9NQVAyX01DU1BJX01BWF9DVFJMIAkJNAoKI2RlZmluZSBPTUFQMl9NQ1NQSV9SRVZJU0lPTgkJMHgwMAojZGVmaW5lIE9NQVAyX01DU1BJX1NZU0NPTkZJRwkJMHgxMAojZGVmaW5lIE9NQVAyX01DU1BJX1NZU1NUQVRVUwkJMHgxNAojZGVmaW5lIE9NQVAyX01DU1BJX0lSUVNUQVRVUwkJMHgxOAojZGVmaW5lIE9NQVAyX01DU1BJX0lSUUVOQUJMRQkJMHgxYwojZGVmaW5lIE9NQVAyX01DU1BJX1dBS0VVUEVOQUJMRQkweDIwCiNkZWZpbmUgT01BUDJfTUNTUElfU1lTVAkJMHgyNAojZGVmaW5lIE9NQVAyX01DU1BJX01PRFVMQ1RSTAkJMHgyOAoKLyogcGVyLWNoYW5uZWwgYmFua3MsIDB4MTQgYnl0ZXMgZWFjaCwgZmlyc3QgaXM6ICovCiNkZWZpbmUgT01BUDJfTUNTUElfQ0hDT05GMAkJMHgyYwojZGVmaW5lIE9NQVAyX01DU1BJX0NIU1RBVDAJCTB4MzAKI2RlZmluZSBPTUFQMl9NQ1NQSV9DSENUUkwwCQkweDM0CiNkZWZpbmUgT01BUDJfTUNTUElfVFgwCQkJMHgzOAojZGVmaW5lIE9NQVAyX01DU1BJX1JYMAkJCTB4M2MKCi8qIHBlci1yZWdpc3RlciBiaXRtYXNrczogKi8KCiNkZWZpbmUgT01BUDJfTUNTUElfU1lTQ09ORklHX1NNQVJUSURMRQlCSVQoNCkKI2RlZmluZSBPTUFQMl9NQ1NQSV9TWVNDT05GSUdfRU5BV0FLRVVQCUJJVCgyKQojZGVmaW5lIE9NQVAyX01DU1BJX1NZU0NPTkZJR19BVVRPSURMRQlCSVQoMCkKI2RlZmluZSBPTUFQMl9NQ1NQSV9TWVNDT05GSUdfU09GVFJFU0VUCUJJVCgxKQoKI2RlZmluZSBPTUFQMl9NQ1NQSV9TWVNTVEFUVVNfUkVTRVRET05FCUJJVCgwKQoKI2RlZmluZSBPTUFQMl9NQ1NQSV9NT0RVTENUUkxfU0lOR0xFCUJJVCgwKQojZGVmaW5lIE9NQVAyX01DU1BJX01PRFVMQ1RSTF9NUwlCSVQoMikKI2RlZmluZSBPTUFQMl9NQ1NQSV9NT0RVTENUUkxfU1RFU1QJQklUKDMpCgojZGVmaW5lIE9NQVAyX01DU1BJX0NIQ09ORl9QSEEJCUJJVCgwKQojZGVmaW5lIE9NQVAyX01DU1BJX0NIQ09ORl9QT0wJCUJJVCgxKQojZGVmaW5lIE9NQVAyX01DU1BJX0NIQ09ORl9DTEtEX01BU0sJKDB4MGYgPDwgMikKI2RlZmluZSBPTUFQMl9NQ1NQSV9DSENPTkZfRVBPTAkJQklUKDYpCiNkZWZpbmUgT01BUDJfTUNTUElfQ0hDT05GX1dMX01BU0sJKDB4MWYgPDwgNykKI2RlZmluZSBPTUFQMl9NQ1NQSV9DSENPTkZfVFJNX1JYX09OTFkJQklUKDEyKQojZGVmaW5lIE9NQVAyX01DU1BJX0NIQ09ORl9UUk1fVFhfT05MWQlCSVQoMTMpCiNkZWZpbmUgT01BUDJfTUNTUElfQ0hDT05GX1RSTV9NQVNLCSgweDAzIDw8IDEyKQojZGVmaW5lIE9NQVAyX01DU1BJX0NIQ09ORl9ETUFXCQlCSVQoMTQpCiNkZWZpbmUgT01BUDJfTUNTUElfQ0hDT05GX0RNQVIJCUJJVCgxNSkKI2RlZmluZSBPTUFQMl9NQ1NQSV9DSENPTkZfRFBFMAkJQklUKDE2KQojZGVmaW5lIE9NQVAyX01DU1BJX0NIQ09ORl9EUEUxCQlCSVQoMTcpCiNkZWZpbmUgT01BUDJfTUNTUElfQ0hDT05GX0lTCQlCSVQoMTgpCiNkZWZpbmUgT01BUDJfTUNTUElfQ0hDT05GX1RVUkJPCUJJVCgxOSkKI2RlZmluZSBPTUFQMl9NQ1NQSV9DSENPTkZfRk9SQ0UJQklUKDIwKQoKI2RlZmluZSBPTUFQMl9NQ1NQSV9DSFNUQVRfUlhTCQlCSVQoMCkKI2RlZmluZSBPTUFQMl9NQ1NQSV9DSFNUQVRfVFhTCQlCSVQoMSkKI2RlZmluZSBPTUFQMl9NQ1NQSV9DSFNUQVRfRU9UCQlCSVQoMikKCiNkZWZpbmUgT01BUDJfTUNTUElfQ0hDVFJMX0VOCQlCSVQoMCkKCiNkZWZpbmUgT01BUDJfTUNTUElfV0FLRVVQRU5BQkxFX1dLRU4JQklUKDApCgovKiBXZSBoYXZlIDIgRE1BIGNoYW5uZWxzIHBlciBDUywgb25lIGZvciBSWCBhbmQgb25lIGZvciBUWCAqLwpzdHJ1Y3Qgb21hcDJfbWNzcGlfZG1hIHsKCWludCBkbWFfdHhfY2hhbm5lbDsKCWludCBkbWFfcnhfY2hhbm5lbDsKCglpbnQgZG1hX3R4X3N5bmNfZGV2OwoJaW50IGRtYV9yeF9zeW5jX2RldjsKCglzdHJ1Y3QgY29tcGxldGlvbiBkbWFfdHhfY29tcGxldGlvbjsKCXN0cnVjdCBjb21wbGV0aW9uIGRtYV9yeF9jb21wbGV0aW9uOwp9OwoKLyogdXNlIFBJTyBmb3Igc21hbGwgdHJhbnNmZXJzLCBhdm9pZGluZyBETUEgc2V0dXAvdGVhcmRvd24gb3ZlcmhlYWQgYW5kCiAqIGNhY2hlIG9wZXJhdGlvbnM7IGJldHRlciBoZXVyaXN0aWNzIGNvbnNpZGVyIHdvcmRzaXplIGFuZCBiaXRyYXRlLgogKi8KI2RlZmluZSBETUFfTUlOX0JZVEVTCQkJMTYwCgoKc3RydWN0IG9tYXAyX21jc3BpIHsKCXN0cnVjdCB3b3JrX3N0cnVjdAl3b3JrOwoJLyogbG9jayBwcm90ZWN0cyBxdWV1ZSBhbmQgcmVnaXN0ZXJzICovCglzcGlubG9ja190CQlsb2NrOwoJc3RydWN0IGxpc3RfaGVhZAltc2dfcXVldWU7CglzdHJ1Y3Qgc3BpX21hc3RlcgkqbWFzdGVyOwoJc3RydWN0IGNsawkJKmljazsKCXN0cnVjdCBjbGsJCSpmY2s7CgkvKiBWaXJ0dWFsIGJhc2UgYWRkcmVzcyBvZiB0aGUgY29udHJvbGxlciAqLwoJdm9pZCBfX2lvbWVtCQkqYmFzZTsKCXVuc2lnbmVkIGxvbmcJCXBoeXM7CgkvKiBTUEkxIGhhcyA0IGNoYW5uZWxzLCB3aGlsZSBTUEkyIGhhcyAyICovCglzdHJ1Y3Qgb21hcDJfbWNzcGlfZG1hCSpkbWFfY2hhbm5lbHM7Cn07CgpzdHJ1Y3Qgb21hcDJfbWNzcGlfY3MgewoJdm9pZCBfX2lvbWVtCQkqYmFzZTsKCXVuc2lnbmVkIGxvbmcJCXBoeXM7CglpbnQJCQl3b3JkX2xlbjsKCXN0cnVjdCBsaXN0X2hlYWQJbm9kZTsKCS8qIENvbnRleHQgc2F2ZSBhbmQgcmVzdG9yZSBzaGFkb3cgcmVnaXN0ZXIgKi8KCXUzMgkJCWNoY29uZjA7Cn07CgovKiB1c2VkIGZvciBjb250ZXh0IHNhdmUgYW5kIHJlc3RvcmUsIHN0cnVjdHVyZSBtZW1iZXJzIHRvIGJlIHVwZGF0ZWQgd2hlbmV2ZXIKICogY29ycmVzcG9uZGluZyByZWdpc3RlcnMgYXJlIG1vZGlmaWVkLgogKi8Kc3RydWN0IG9tYXAyX21jc3BpX3JlZ3MgewoJdTMyIHN5c2NvbmZpZzsKCXUzMiBtb2R1bGN0cmw7Cgl1MzIgd2FrZXVwZW5hYmxlOwoJc3RydWN0IGxpc3RfaGVhZCBjczsKfTsKCnN0YXRpYyBzdHJ1Y3Qgb21hcDJfbWNzcGlfcmVncyBvbWFwMl9tY3NwaV9jdHhbT01BUDJfTUNTUElfTUFYX0NUUkxdOwoKc3RhdGljIHN0cnVjdCB3b3JrcXVldWVfc3RydWN0ICpvbWFwMl9tY3NwaV93cTsKCiNkZWZpbmUgTU9EX1JFR19CSVQodmFsLCBtYXNrLCBzZXQpIGRvIHsgXAoJaWYgKHNldCkgXAoJCXZhbCB8PSBtYXNrOyBcCgllbHNlIFwKCQl2YWwgJj0gfm1hc2s7IFwKfSB3aGlsZSAoMCkKCnN0YXRpYyBpbmxpbmUgdm9pZCBtY3NwaV93cml0ZV9yZWcoc3RydWN0IHNwaV9tYXN0ZXIgKm1hc3RlciwKCQlpbnQgaWR4LCB1MzIgdmFsKQp7CglzdHJ1Y3Qgb21hcDJfbWNzcGkgKm1jc3BpID0gc3BpX21hc3Rlcl9nZXRfZGV2ZGF0YShtYXN0ZXIpOwoKCV9fcmF3X3dyaXRlbCh2YWwsIG1jc3BpLT5iYXNlICsgaWR4KTsKfQoKc3RhdGljIGlubGluZSB1MzIgbWNzcGlfcmVhZF9yZWcoc3RydWN0IHNwaV9tYXN0ZXIgKm1hc3RlciwgaW50IGlkeCkKewoJc3RydWN0IG9tYXAyX21jc3BpICptY3NwaSA9IHNwaV9tYXN0ZXJfZ2V0X2RldmRhdGEobWFzdGVyKTsKCglyZXR1cm4gX19yYXdfcmVhZGwobWNzcGktPmJhc2UgKyBpZHgpOwp9CgpzdGF0aWMgaW5saW5lIHZvaWQgbWNzcGlfd3JpdGVfY3NfcmVnKGNvbnN0IHN0cnVjdCBzcGlfZGV2aWNlICpzcGksCgkJaW50IGlkeCwgdTMyIHZhbCkKewoJc3RydWN0IG9tYXAyX21jc3BpX2NzCSpjcyA9IHNwaS0+Y29udHJvbGxlcl9zdGF0ZTsKCglfX3Jhd193cml0ZWwodmFsLCBjcy0+YmFzZSArICBpZHgpOwp9CgpzdGF0aWMgaW5saW5lIHUzMiBtY3NwaV9yZWFkX2NzX3JlZyhjb25zdCBzdHJ1Y3Qgc3BpX2RldmljZSAqc3BpLCBpbnQgaWR4KQp7CglzdHJ1Y3Qgb21hcDJfbWNzcGlfY3MJKmNzID0gc3BpLT5jb250cm9sbGVyX3N0YXRlOwoKCXJldHVybiBfX3Jhd19yZWFkbChjcy0+YmFzZSArIGlkeCk7Cn0KCnN0YXRpYyBpbmxpbmUgdTMyIG1jc3BpX2NhY2hlZF9jaGNvbmYwKGNvbnN0IHN0cnVjdCBzcGlfZGV2aWNlICpzcGkpCnsKCXN0cnVjdCBvbWFwMl9tY3NwaV9jcyAqY3MgPSBzcGktPmNvbnRyb2xsZXJfc3RhdGU7CgoJcmV0dXJuIGNzLT5jaGNvbmYwOwp9CgpzdGF0aWMgaW5saW5lIHZvaWQgbWNzcGlfd3JpdGVfY2hjb25mMChjb25zdCBzdHJ1Y3Qgc3BpX2RldmljZSAqc3BpLCB1MzIgdmFsKQp7CglzdHJ1Y3Qgb21hcDJfbWNzcGlfY3MgKmNzID0gc3BpLT5jb250cm9sbGVyX3N0YXRlOwoKCWNzLT5jaGNvbmYwID0gdmFsOwoJbWNzcGlfd3JpdGVfY3NfcmVnKHNwaSwgT01BUDJfTUNTUElfQ0hDT05GMCwgdmFsKTsKCW1jc3BpX3JlYWRfY3NfcmVnKHNwaSwgT01BUDJfTUNTUElfQ0hDT05GMCk7Cn0KCnN0YXRpYyB2b2lkIG9tYXAyX21jc3BpX3NldF9kbWFfcmVxKGNvbnN0IHN0cnVjdCBzcGlfZGV2aWNlICpzcGksCgkJaW50IGlzX3JlYWQsIGludCBlbmFibGUpCnsKCXUzMiBsLCBydzsKCglsID0gbWNzcGlfY2FjaGVkX2NoY29uZjAoc3BpKTsKCglpZiAoaXNfcmVhZCkgLyogMSBpcyByZWFkLCAwIHdyaXRlICovCgkJcncgPSBPTUFQMl9NQ1NQSV9DSENPTkZfRE1BUjsKCWVsc2UKCQlydyA9IE9NQVAyX01DU1BJX0NIQ09ORl9ETUFXOwoKCU1PRF9SRUdfQklUKGwsIHJ3LCBlbmFibGUpOwoJbWNzcGlfd3JpdGVfY2hjb25mMChzcGksIGwpOwp9CgpzdGF0aWMgdm9pZCBvbWFwMl9tY3NwaV9zZXRfZW5hYmxlKGNvbnN0IHN0cnVjdCBzcGlfZGV2aWNlICpzcGksIGludCBlbmFibGUpCnsKCXUzMiBsOwoKCWwgPSBlbmFibGUgPyBPTUFQMl9NQ1NQSV9DSENUUkxfRU4gOiAwOwoJbWNzcGlfd3JpdGVfY3NfcmVnKHNwaSwgT01BUDJfTUNTUElfQ0hDVFJMMCwgbCk7CgkvKiBGbGFzaCBwb3N0LXdyaXRlcyAqLwoJbWNzcGlfcmVhZF9jc19yZWcoc3BpLCBPTUFQMl9NQ1NQSV9DSENUUkwwKTsKfQoKc3RhdGljIHZvaWQgb21hcDJfbWNzcGlfZm9yY2VfY3Moc3RydWN0IHNwaV9kZXZpY2UgKnNwaSwgaW50IGNzX2FjdGl2ZSkKewoJdTMyIGw7CgoJbCA9IG1jc3BpX2NhY2hlZF9jaGNvbmYwKHNwaSk7CglNT0RfUkVHX0JJVChsLCBPTUFQMl9NQ1NQSV9DSENPTkZfRk9SQ0UsIGNzX2FjdGl2ZSk7CgltY3NwaV93cml0ZV9jaGNvbmYwKHNwaSwgbCk7Cn0KCnN0YXRpYyB2b2lkIG9tYXAyX21jc3BpX3NldF9tYXN0ZXJfbW9kZShzdHJ1Y3Qgc3BpX21hc3RlciAqbWFzdGVyKQp7Cgl1MzIgbDsKCgkvKiBzZXR1cCB3aGVuIHN3aXRjaGluZyBmcm9tIChyZXNldCBkZWZhdWx0KSBzbGF2ZSBtb2RlCgkgKiB0byBzaW5nbGUtY2hhbm5lbCBtYXN0ZXIgbW9kZQoJICovCglsID0gbWNzcGlfcmVhZF9yZWcobWFzdGVyLCBPTUFQMl9NQ1NQSV9NT0RVTENUUkwpOwoJTU9EX1JFR19CSVQobCwgT01BUDJfTUNTUElfTU9EVUxDVFJMX1NURVNULCAwKTsKCU1PRF9SRUdfQklUKGwsIE9NQVAyX01DU1BJX01PRFVMQ1RSTF9NUywgMCk7CglNT0RfUkVHX0JJVChsLCBPTUFQMl9NQ1NQSV9NT0RVTENUUkxfU0lOR0xFLCAxKTsKCW1jc3BpX3dyaXRlX3JlZyhtYXN0ZXIsIE9NQVAyX01DU1BJX01PRFVMQ1RSTCwgbCk7CgoJb21hcDJfbWNzcGlfY3R4W21hc3Rlci0+YnVzX251bSAtIDFdLm1vZHVsY3RybCA9IGw7Cn0KCnN0YXRpYyB2b2lkIG9tYXAyX21jc3BpX3Jlc3RvcmVfY3R4KHN0cnVjdCBvbWFwMl9tY3NwaSAqbWNzcGkpCnsKCXN0cnVjdCBzcGlfbWFzdGVyICpzcGlfY250cmw7CglzdHJ1Y3Qgb21hcDJfbWNzcGlfY3MgKmNzOwoJc3BpX2NudHJsID0gbWNzcGktPm1hc3RlcjsKCgkvKiBNY1NQSTogY29udGV4dCByZXN0b3JlICovCgltY3NwaV93cml0ZV9yZWcoc3BpX2NudHJsLCBPTUFQMl9NQ1NQSV9NT0RVTENUUkwsCgkJCW9tYXAyX21jc3BpX2N0eFtzcGlfY250cmwtPmJ1c19udW0gLSAxXS5tb2R1bGN0cmwpOwoKCW1jc3BpX3dyaXRlX3JlZyhzcGlfY250cmwsIE9NQVAyX01DU1BJX1NZU0NPTkZJRywKCQkJb21hcDJfbWNzcGlfY3R4W3NwaV9jbnRybC0+YnVzX251bSAtIDFdLnN5c2NvbmZpZyk7CgoJbWNzcGlfd3JpdGVfcmVnKHNwaV9jbnRybCwgT01BUDJfTUNTUElfV0FLRVVQRU5BQkxFLAoJCQlvbWFwMl9tY3NwaV9jdHhbc3BpX2NudHJsLT5idXNfbnVtIC0gMV0ud2FrZXVwZW5hYmxlKTsKCglsaXN0X2Zvcl9lYWNoX2VudHJ5KGNzLCAmb21hcDJfbWNzcGlfY3R4W3NwaV9jbnRybC0+YnVzX251bSAtIDFdLmNzLAoJCQlub2RlKQoJCV9fcmF3X3dyaXRlbChjcy0+Y2hjb25mMCwgY3MtPmJhc2UgKyBPTUFQMl9NQ1NQSV9DSENPTkYwKTsKfQpzdGF0aWMgdm9pZCBvbWFwMl9tY3NwaV9kaXNhYmxlX2Nsb2NrcyhzdHJ1Y3Qgb21hcDJfbWNzcGkgKm1jc3BpKQp7CgljbGtfZGlzYWJsZShtY3NwaS0+aWNrKTsKCWNsa19kaXNhYmxlKG1jc3BpLT5mY2spOwp9CgpzdGF0aWMgaW50IG9tYXAyX21jc3BpX2VuYWJsZV9jbG9ja3Moc3RydWN0IG9tYXAyX21jc3BpICptY3NwaSkKewoJaWYgKGNsa19lbmFibGUobWNzcGktPmljaykpCgkJcmV0dXJuIC1FTk9ERVY7CglpZiAoY2xrX2VuYWJsZShtY3NwaS0+ZmNrKSkKCQlyZXR1cm4gLUVOT0RFVjsKCglvbWFwMl9tY3NwaV9yZXN0b3JlX2N0eChtY3NwaSk7CgoJcmV0dXJuIDA7Cn0KCnN0YXRpYyBpbnQgbWNzcGlfd2FpdF9mb3JfcmVnX2JpdCh2b2lkIF9faW9tZW0gKnJlZywgdW5zaWduZWQgbG9uZyBiaXQpCnsKCXVuc2lnbmVkIGxvbmcgdGltZW91dDsKCgl0aW1lb3V0ID0gamlmZmllcyArIG1zZWNzX3RvX2ppZmZpZXMoMTAwMCk7Cgl3aGlsZSAoIShfX3Jhd19yZWFkbChyZWcpICYgYml0KSkgewoJCWlmICh0aW1lX2FmdGVyKGppZmZpZXMsIHRpbWVvdXQpKQoJCQlyZXR1cm4gLTE7CgkJY3B1X3JlbGF4KCk7Cgl9CglyZXR1cm4gMDsKfQoKc3RhdGljIHVuc2lnbmVkCm9tYXAyX21jc3BpX3R4cnhfZG1hKHN0cnVjdCBzcGlfZGV2aWNlICpzcGksIHN0cnVjdCBzcGlfdHJhbnNmZXIgKnhmZXIpCnsKCXN0cnVjdCBvbWFwMl9tY3NwaQkqbWNzcGk7CglzdHJ1Y3Qgb21hcDJfbWNzcGlfY3MJKmNzID0gc3BpLT5jb250cm9sbGVyX3N0YXRlOwoJc3RydWN0IG9tYXAyX21jc3BpX2RtYSAgKm1jc3BpX2RtYTsKCXVuc2lnbmVkIGludAkJY291bnQsIGM7Cgl1bnNpZ25lZCBsb25nCQliYXNlLCB0eF9yZWcsIHJ4X3JlZzsKCWludAkJCXdvcmRfbGVuLCBkYXRhX3R5cGUsIGVsZW1lbnRfY291bnQ7CglpbnQJCQllbGVtZW50czsKCXUzMgkJCWw7Cgl1OAkJCSogcng7Cgljb25zdCB1OAkJKiB0eDsKCXZvaWQgX19pb21lbQkJKmNoc3RhdF9yZWc7CgoJbWNzcGkgPSBzcGlfbWFzdGVyX2dldF9kZXZkYXRhKHNwaS0+bWFzdGVyKTsKCW1jc3BpX2RtYSA9ICZtY3NwaS0+ZG1hX2NoYW5uZWxzW3NwaS0+Y2hpcF9zZWxlY3RdOwoJbCA9IG1jc3BpX2NhY2hlZF9jaGNvbmYwKHNwaSk7CgoJY2hzdGF0X3JlZyA9IGNzLT5iYXNlICsgT01BUDJfTUNTUElfQ0hTVEFUMDsKCgljb3VudCA9IHhmZXItPmxlbjsKCWMgPSBjb3VudDsKCXdvcmRfbGVuID0gY3MtPndvcmRfbGVuOwoKCWJhc2UgPSBjcy0+cGh5czsKCXR4X3JlZyA9IGJhc2UgKyBPTUFQMl9NQ1NQSV9UWDA7CglyeF9yZWcgPSBiYXNlICsgT01BUDJfTUNTUElfUlgwOwoJcnggPSB4ZmVyLT5yeF9idWY7Cgl0eCA9IHhmZXItPnR4X2J1ZjsKCglpZiAod29yZF9sZW4gPD0gOCkgewoJCWRhdGFfdHlwZSA9IE9NQVBfRE1BX0RBVEFfVFlQRV9TODsKCQllbGVtZW50X2NvdW50ID0gY291bnQ7Cgl9IGVsc2UgaWYgKHdvcmRfbGVuIDw9IDE2KSB7CgkJZGF0YV90eXBlID0gT01BUF9ETUFfREFUQV9UWVBFX1MxNjsKCQllbGVtZW50X2NvdW50ID0gY291bnQgPj4gMTsKCX0gZWxzZSAvKiB3b3JkX2xlbiA8PSAzMiAqLyB7CgkJZGF0YV90eXBlID0gT01BUF9ETUFfREFUQV9UWVBFX1MzMjsKCQllbGVtZW50X2NvdW50ID0gY291bnQgPj4gMjsKCX0KCglpZiAodHggIT0gTlVMTCkgewoJCW9tYXBfc2V0X2RtYV90cmFuc2Zlcl9wYXJhbXMobWNzcGlfZG1hLT5kbWFfdHhfY2hhbm5lbCwKCQkJCWRhdGFfdHlwZSwgZWxlbWVudF9jb3VudCwgMSwKCQkJCU9NQVBfRE1BX1NZTkNfRUxFTUVOVCwKCQkJCW1jc3BpX2RtYS0+ZG1hX3R4X3N5bmNfZGV2LCAwKTsKCgkJb21hcF9zZXRfZG1hX2Rlc3RfcGFyYW1zKG1jc3BpX2RtYS0+ZG1hX3R4X2NoYW5uZWwsIDAsCgkJCQlPTUFQX0RNQV9BTU9ERV9DT05TVEFOVCwKCQkJCXR4X3JlZywgMCwgMCk7CgoJCW9tYXBfc2V0X2RtYV9zcmNfcGFyYW1zKG1jc3BpX2RtYS0+ZG1hX3R4X2NoYW5uZWwsIDAsCgkJCQlPTUFQX0RNQV9BTU9ERV9QT1NUX0lOQywKCQkJCXhmZXItPnR4X2RtYSwgMCwgMCk7Cgl9CgoJaWYgKHJ4ICE9IE5VTEwpIHsKCQllbGVtZW50cyA9IGVsZW1lbnRfY291bnQgLSAxOwoJCWlmIChsICYgT01BUDJfTUNTUElfQ0hDT05GX1RVUkJPKQoJCQllbGVtZW50cy0tOwoKCQlvbWFwX3NldF9kbWFfdHJhbnNmZXJfcGFyYW1zKG1jc3BpX2RtYS0+ZG1hX3J4X2NoYW5uZWwsCgkJCQlkYXRhX3R5cGUsIGVsZW1lbnRzLCAxLAoJCQkJT01BUF9ETUFfU1lOQ19FTEVNRU5ULAoJCQkJbWNzcGlfZG1hLT5kbWFfcnhfc3luY19kZXYsIDEpOwoKCQlvbWFwX3NldF9kbWFfc3JjX3BhcmFtcyhtY3NwaV9kbWEtPmRtYV9yeF9jaGFubmVsLCAwLAoJCQkJT01BUF9ETUFfQU1PREVfQ09OU1RBTlQsCgkJCQlyeF9yZWcsIDAsIDApOwoKCQlvbWFwX3NldF9kbWFfZGVzdF9wYXJhbXMobWNzcGlfZG1hLT5kbWFfcnhfY2hhbm5lbCwgMCwKCQkJCU9NQVBfRE1BX0FNT0RFX1BPU1RfSU5DLAoJCQkJeGZlci0+cnhfZG1hLCAwLCAwKTsKCX0KCglpZiAodHggIT0gTlVMTCkgewoJCW9tYXBfc3RhcnRfZG1hKG1jc3BpX2RtYS0+ZG1hX3R4X2NoYW5uZWwpOwoJCW9tYXAyX21jc3BpX3NldF9kbWFfcmVxKHNwaSwgMCwgMSk7Cgl9CgoJaWYgKHJ4ICE9IE5VTEwpIHsKCQlvbWFwX3N0YXJ0X2RtYShtY3NwaV9kbWEtPmRtYV9yeF9jaGFubmVsKTsKCQlvbWFwMl9tY3NwaV9zZXRfZG1hX3JlcShzcGksIDEsIDEpOwoJfQoKCWlmICh0eCAhPSBOVUxMKSB7CgkJd2FpdF9mb3JfY29tcGxldGlvbigmbWNzcGlfZG1hLT5kbWFfdHhfY29tcGxldGlvbik7CgkJZG1hX3VubWFwX3NpbmdsZSgmc3BpLT5kZXYsIHhmZXItPnR4X2RtYSwgY291bnQsIERNQV9UT19ERVZJQ0UpOwoKCQkvKiBmb3IgVFhfT05MWSBtb2RlLCBiZSBzdXJlIGFsbCB3b3JkcyBoYXZlIHNoaWZ0ZWQgb3V0ICovCgkJaWYgKHJ4ID09IE5VTEwpIHsKCQkJaWYgKG1jc3BpX3dhaXRfZm9yX3JlZ19iaXQoY2hzdGF0X3JlZywKCQkJCQkJT01BUDJfTUNTUElfQ0hTVEFUX1RYUykgPCAwKQoJCQkJZGV2X2Vycigmc3BpLT5kZXYsICJUWFMgdGltZWQgb3V0XG4iKTsKCQkJZWxzZSBpZiAobWNzcGlfd2FpdF9mb3JfcmVnX2JpdChjaHN0YXRfcmVnLAoJCQkJCQlPTUFQMl9NQ1NQSV9DSFNUQVRfRU9UKSA8IDApCgkJCQlkZXZfZXJyKCZzcGktPmRldiwgIkVPVCB0aW1lZCBvdXRcbiIpOwoJCX0KCX0KCglpZiAocnggIT0gTlVMTCkgewoJCXdhaXRfZm9yX2NvbXBsZXRpb24oJm1jc3BpX2RtYS0+ZG1hX3J4X2NvbXBsZXRpb24pOwoJCWRtYV91bm1hcF9zaW5nbGUoJnNwaS0+ZGV2LCB4ZmVyLT5yeF9kbWEsIGNvdW50LCBETUFfRlJPTV9ERVZJQ0UpOwoJCW9tYXAyX21jc3BpX3NldF9lbmFibGUoc3BpLCAwKTsKCgkJaWYgKGwgJiBPTUFQMl9NQ1NQSV9DSENPTkZfVFVSQk8pIHsKCgkJCWlmIChsaWtlbHkobWNzcGlfcmVhZF9jc19yZWcoc3BpLCBPTUFQMl9NQ1NQSV9DSFNUQVQwKQoJCQkJICAgJiBPTUFQMl9NQ1NQSV9DSFNUQVRfUlhTKSkgewoJCQkJdTMyIHc7CgoJCQkJdyA9IG1jc3BpX3JlYWRfY3NfcmVnKHNwaSwgT01BUDJfTUNTUElfUlgwKTsKCQkJCWlmICh3b3JkX2xlbiA8PSA4KQoJCQkJCSgodTggKil4ZmVyLT5yeF9idWYpW2VsZW1lbnRzKytdID0gdzsKCQkJCWVsc2UgaWYgKHdvcmRfbGVuIDw9IDE2KQoJCQkJCSgodTE2ICopeGZlci0+cnhfYnVmKVtlbGVtZW50cysrXSA9IHc7CgkJCQllbHNlIC8qIHdvcmRfbGVuIDw9IDMyICovCgkJCQkJKCh1MzIgKil4ZmVyLT5yeF9idWYpW2VsZW1lbnRzKytdID0gdzsKCQkJfSBlbHNlIHsKCQkJCWRldl9lcnIoJnNwaS0+ZGV2LAoJCQkJCSJETUEgUlggcGVudWx0aW1hdGUgd29yZCBlbXB0eSIpOwoJCQkJY291bnQgLT0gKHdvcmRfbGVuIDw9IDgpICA/IDIgOgoJCQkJCSh3b3JkX2xlbiA8PSAxNikgPyA0IDoKCQkJCQkvKiB3b3JkX2xlbiA8PSAzMiAqLyA4OwoJCQkJb21hcDJfbWNzcGlfc2V0X2VuYWJsZShzcGksIDEpOwoJCQkJcmV0dXJuIGNvdW50OwoJCQl9CgkJfQoKCQlpZiAobGlrZWx5KG1jc3BpX3JlYWRfY3NfcmVnKHNwaSwgT01BUDJfTUNTUElfQ0hTVEFUMCkKCQkJCSYgT01BUDJfTUNTUElfQ0hTVEFUX1JYUykpIHsKCQkJdTMyIHc7CgoJCQl3ID0gbWNzcGlfcmVhZF9jc19yZWcoc3BpLCBPTUFQMl9NQ1NQSV9SWDApOwoJCQlpZiAod29yZF9sZW4gPD0gOCkKCQkJCSgodTggKil4ZmVyLT5yeF9idWYpW2VsZW1lbnRzXSA9IHc7CgkJCWVsc2UgaWYgKHdvcmRfbGVuIDw9IDE2KQoJCQkJKCh1MTYgKil4ZmVyLT5yeF9idWYpW2VsZW1lbnRzXSA9IHc7CgkJCWVsc2UgLyogd29yZF9sZW4gPD0gMzIgKi8KCQkJCSgodTMyICopeGZlci0+cnhfYnVmKVtlbGVtZW50c10gPSB3OwoJCX0gZWxzZSB7CgkJCWRldl9lcnIoJnNwaS0+ZGV2LCAiRE1BIFJYIGxhc3Qgd29yZCBlbXB0eSIpOwoJCQljb3VudCAtPSAod29yZF9sZW4gPD0gOCkgID8gMSA6CgkJCQkgKHdvcmRfbGVuIDw9IDE2KSA/IDIgOgoJCQkgICAgICAgLyogd29yZF9sZW4gPD0gMzIgKi8gNDsKCQl9CgkJb21hcDJfbWNzcGlfc2V0X2VuYWJsZShzcGksIDEpOwoJfQoJcmV0dXJuIGNvdW50Owp9CgpzdGF0aWMgdW5zaWduZWQKb21hcDJfbWNzcGlfdHhyeF9waW8oc3RydWN0IHNwaV9kZXZpY2UgKnNwaSwgc3RydWN0IHNwaV90cmFuc2ZlciAqeGZlcikKewoJc3RydWN0IG9tYXAyX21jc3BpCSptY3NwaTsKCXN0cnVjdCBvbWFwMl9tY3NwaV9jcwkqY3MgPSBzcGktPmNvbnRyb2xsZXJfc3RhdGU7Cgl1bnNpZ25lZCBpbnQJCWNvdW50LCBjOwoJdTMyCQkJbDsKCXZvaWQgX19pb21lbQkJKmJhc2UgPSBjcy0+YmFzZTsKCXZvaWQgX19pb21lbQkJKnR4X3JlZzsKCXZvaWQgX19pb21lbQkJKnJ4X3JlZzsKCXZvaWQgX19pb21lbQkJKmNoc3RhdF9yZWc7CglpbnQJCQl3b3JkX2xlbjsKCgltY3NwaSA9IHNwaV9tYXN0ZXJfZ2V0X2RldmRhdGEoc3BpLT5tYXN0ZXIpOwoJY291bnQgPSB4ZmVyLT5sZW47CgljID0gY291bnQ7Cgl3b3JkX2xlbiA9IGNzLT53b3JkX2xlbjsKCglsID0gbWNzcGlfY2FjaGVkX2NoY29uZjAoc3BpKTsKCgkvKiBXZSBzdG9yZSB0aGUgcHJlLWNhbGN1bGF0ZWQgcmVnaXN0ZXIgYWRkcmVzc2VzIG9uIHN0YWNrIHRvIHNwZWVkCgkgKiB1cCB0aGUgdHJhbnNmZXIgbG9vcC4gKi8KCXR4X3JlZwkJPSBiYXNlICsgT01BUDJfTUNTUElfVFgwOwoJcnhfcmVnCQk9IGJhc2UgKyBPTUFQMl9NQ1NQSV9SWDA7CgljaHN0YXRfcmVnCT0gYmFzZSArIE9NQVAyX01DU1BJX0NIU1RBVDA7CgoJaWYgKHdvcmRfbGVuIDw9IDgpIHsKCQl1OAkJKnJ4OwoJCWNvbnN0IHU4CSp0eDsKCgkJcnggPSB4ZmVyLT5yeF9idWY7CgkJdHggPSB4ZmVyLT50eF9idWY7CgoJCWRvIHsKCQkJYyAtPSAxOwoJCQlpZiAodHggIT0gTlVMTCkgewoJCQkJaWYgKG1jc3BpX3dhaXRfZm9yX3JlZ19iaXQoY2hzdGF0X3JlZywKCQkJCQkJT01BUDJfTUNTUElfQ0hTVEFUX1RYUykgPCAwKSB7CgkJCQkJZGV2X2Vycigmc3BpLT5kZXYsICJUWFMgdGltZWQgb3V0XG4iKTsKCQkJCQlnb3RvIG91dDsKCQkJCX0KCQkJCWRldl92ZGJnKCZzcGktPmRldiwgIndyaXRlLSVkICUwMnhcbiIsCgkJCQkJCXdvcmRfbGVuLCAqdHgpOwoJCQkJX19yYXdfd3JpdGVsKCp0eCsrLCB0eF9yZWcpOwoJCQl9CgkJCWlmIChyeCAhPSBOVUxMKSB7CgkJCQlpZiAobWNzcGlfd2FpdF9mb3JfcmVnX2JpdChjaHN0YXRfcmVnLAoJCQkJCQlPTUFQMl9NQ1NQSV9DSFNUQVRfUlhTKSA8IDApIHsKCQkJCQlkZXZfZXJyKCZzcGktPmRldiwgIlJYUyB0aW1lZCBvdXRcbiIpOwoJCQkJCWdvdG8gb3V0OwoJCQkJfQoKCQkJCWlmIChjID09IDEgJiYgdHggPT0gTlVMTCAmJgoJCQkJICAgIChsICYgT01BUDJfTUNTUElfQ0hDT05GX1RVUkJPKSkgewoJCQkJCW9tYXAyX21jc3BpX3NldF9lbmFibGUoc3BpLCAwKTsKCQkJCQkqcngrKyA9IF9fcmF3X3JlYWRsKHJ4X3JlZyk7CgkJCQkJZGV2X3ZkYmcoJnNwaS0+ZGV2LCAicmVhZC0lZCAlMDJ4XG4iLAoJCQkJCQkgICAgd29yZF9sZW4sICoocnggLSAxKSk7CgkJCQkJaWYgKG1jc3BpX3dhaXRfZm9yX3JlZ19iaXQoY2hzdGF0X3JlZywKCQkJCQkJT01BUDJfTUNTUElfQ0hTVEFUX1JYUykgPCAwKSB7CgkJCQkJCWRldl9lcnIoJnNwaS0+ZGV2LAoJCQkJCQkJIlJYUyB0aW1lZCBvdXRcbiIpOwoJCQkJCQlnb3RvIG91dDsKCQkJCQl9CgkJCQkJYyA9IDA7CgkJCQl9IGVsc2UgaWYgKGMgPT0gMCAmJiB0eCA9PSBOVUxMKSB7CgkJCQkJb21hcDJfbWNzcGlfc2V0X2VuYWJsZShzcGksIDApOwoJCQkJfQoKCQkJCSpyeCsrID0gX19yYXdfcmVhZGwocnhfcmVnKTsKCQkJCWRldl92ZGJnKCZzcGktPmRldiwgInJlYWQtJWQgJTAyeFxuIiwKCQkJCQkJd29yZF9sZW4sICoocnggLSAxKSk7CgkJCX0KCQl9IHdoaWxlIChjKTsKCX0gZWxzZSBpZiAod29yZF9sZW4gPD0gMTYpIHsKCQl1MTYJCSpyeDsKCQljb25zdCB1MTYJKnR4OwoKCQlyeCA9IHhmZXItPnJ4X2J1ZjsKCQl0eCA9IHhmZXItPnR4X2J1ZjsKCQlkbyB7CgkJCWMgLT0gMjsKCQkJaWYgKHR4ICE9IE5VTEwpIHsKCQkJCWlmIChtY3NwaV93YWl0X2Zvcl9yZWdfYml0KGNoc3RhdF9yZWcsCgkJCQkJCU9NQVAyX01DU1BJX0NIU1RBVF9UWFMpIDwgMCkgewoJCQkJCWRldl9lcnIoJnNwaS0+ZGV2LCAiVFhTIHRpbWVkIG91dFxuIik7CgkJCQkJZ290byBvdXQ7CgkJCQl9CgkJCQlkZXZfdmRiZygmc3BpLT5kZXYsICJ3cml0ZS0lZCAlMDR4XG4iLAoJCQkJCQl3b3JkX2xlbiwgKnR4KTsKCQkJCV9fcmF3X3dyaXRlbCgqdHgrKywgdHhfcmVnKTsKCQkJfQoJCQlpZiAocnggIT0gTlVMTCkgewoJCQkJaWYgKG1jc3BpX3dhaXRfZm9yX3JlZ19iaXQoY2hzdGF0X3JlZywKCQkJCQkJT01BUDJfTUNTUElfQ0hTVEFUX1JYUykgPCAwKSB7CgkJCQkJZGV2X2Vycigmc3BpLT5kZXYsICJSWFMgdGltZWQgb3V0XG4iKTsKCQkJCQlnb3RvIG91dDsKCQkJCX0KCgkJCQlpZiAoYyA9PSAyICYmIHR4ID09IE5VTEwgJiYKCQkJCSAgICAobCAmIE9NQVAyX01DU1BJX0NIQ09ORl9UVVJCTykpIHsKCQkJCQlvbWFwMl9tY3NwaV9zZXRfZW5hYmxlKHNwaSwgMCk7CgkJCQkJKnJ4KysgPSBfX3Jhd19yZWFkbChyeF9yZWcpOwoJCQkJCWRldl92ZGJnKCZzcGktPmRldiwgInJlYWQtJWQgJTA0eFxuIiwKCQkJCQkJICAgIHdvcmRfbGVuLCAqKHJ4IC0gMSkpOwoJCQkJCWlmIChtY3NwaV93YWl0X2Zvcl9yZWdfYml0KGNoc3RhdF9yZWcsCgkJCQkJCU9NQVAyX01DU1BJX0NIU1RBVF9SWFMpIDwgMCkgewoJCQkJCQlkZXZfZXJyKCZzcGktPmRldiwKCQkJCQkJCSJSWFMgdGltZWQgb3V0XG4iKTsKCQkJCQkJZ290byBvdXQ7CgkJCQkJfQoJCQkJCWMgPSAwOwoJCQkJfSBlbHNlIGlmIChjID09IDAgJiYgdHggPT0gTlVMTCkgewoJCQkJCW9tYXAyX21jc3BpX3NldF9lbmFibGUoc3BpLCAwKTsKCQkJCX0KCgkJCQkqcngrKyA9IF9fcmF3X3JlYWRsKHJ4X3JlZyk7CgkJCQlkZXZfdmRiZygmc3BpLT5kZXYsICJyZWFkLSVkICUwNHhcbiIsCgkJCQkJCXdvcmRfbGVuLCAqKHJ4IC0gMSkpOwoJCQl9CgkJfSB3aGlsZSAoYyk7Cgl9IGVsc2UgaWYgKHdvcmRfbGVuIDw9IDMyKSB7CgkJdTMyCQkqcng7CgkJY29uc3QgdTMyCSp0eDsKCgkJcnggPSB4ZmVyLT5yeF9idWY7CgkJdHggPSB4ZmVyLT50eF9idWY7CgkJZG8gewoJCQljIC09IDQ7CgkJCWlmICh0eCAhPSBOVUxMKSB7CgkJCQlpZiAobWNzcGlfd2FpdF9mb3JfcmVnX2JpdChjaHN0YXRfcmVnLAoJCQkJCQlPTUFQMl9NQ1NQSV9DSFNUQVRfVFhTKSA8IDApIHsKCQkJCQlkZXZfZXJyKCZzcGktPmRldiwgIlRYUyB0aW1lZCBvdXRcbiIpOwoJCQkJCWdvdG8gb3V0OwoJCQkJfQoJCQkJZGV2X3ZkYmcoJnNwaS0+ZGV2LCAid3JpdGUtJWQgJTA4eFxuIiwKCQkJCQkJd29yZF9sZW4sICp0eCk7CgkJCQlfX3Jhd193cml0ZWwoKnR4KyssIHR4X3JlZyk7CgkJCX0KCQkJaWYgKHJ4ICE9IE5VTEwpIHsKCQkJCWlmIChtY3NwaV93YWl0X2Zvcl9yZWdfYml0KGNoc3RhdF9yZWcsCgkJCQkJCU9NQVAyX01DU1BJX0NIU1RBVF9SWFMpIDwgMCkgewoJCQkJCWRldl9lcnIoJnNwaS0+ZGV2LCAiUlhTIHRpbWVkIG91dFxuIik7CgkJCQkJZ290byBvdXQ7CgkJCQl9CgoJCQkJaWYgKGMgPT0gNCAmJiB0eCA9PSBOVUxMICYmCgkJCQkgICAgKGwgJiBPTUFQMl9NQ1NQSV9DSENPTkZfVFVSQk8pKSB7CgkJCQkJb21hcDJfbWNzcGlfc2V0X2VuYWJsZShzcGksIDApOwoJCQkJCSpyeCsrID0gX19yYXdfcmVhZGwocnhfcmVnKTsKCQkJCQlkZXZfdmRiZygmc3BpLT5kZXYsICJyZWFkLSVkICUwOHhcbiIsCgkJCQkJCSAgICB3b3JkX2xlbiwgKihyeCAtIDEpKTsKCQkJCQlpZiAobWNzcGlfd2FpdF9mb3JfcmVnX2JpdChjaHN0YXRfcmVnLAoJCQkJCQlPTUFQMl9NQ1NQSV9DSFNUQVRfUlhTKSA8IDApIHsKCQkJCQkJZGV2X2Vycigmc3BpLT5kZXYsCgkJCQkJCQkiUlhTIHRpbWVkIG91dFxuIik7CgkJCQkJCWdvdG8gb3V0OwoJCQkJCX0KCQkJCQljID0gMDsKCQkJCX0gZWxzZSBpZiAoYyA9PSAwICYmIHR4ID09IE5VTEwpIHsKCQkJCQlvbWFwMl9tY3NwaV9zZXRfZW5hYmxlKHNwaSwgMCk7CgkJCQl9CgoJCQkJKnJ4KysgPSBfX3Jhd19yZWFkbChyeF9yZWcpOwoJCQkJZGV2X3ZkYmcoJnNwaS0+ZGV2LCAicmVhZC0lZCAlMDh4XG4iLAoJCQkJCQl3b3JkX2xlbiwgKihyeCAtIDEpKTsKCQkJfQoJCX0gd2hpbGUgKGMpOwoJfQoKCS8qIGZvciBUWF9PTkxZIG1vZGUsIGJlIHN1cmUgYWxsIHdvcmRzIGhhdmUgc2hpZnRlZCBvdXQgKi8KCWlmICh4ZmVyLT5yeF9idWYgPT0gTlVMTCkgewoJCWlmIChtY3NwaV93YWl0X2Zvcl9yZWdfYml0KGNoc3RhdF9yZWcsCgkJCQlPTUFQMl9NQ1NQSV9DSFNUQVRfVFhTKSA8IDApIHsKCQkJZGV2X2Vycigmc3BpLT5kZXYsICJUWFMgdGltZWQgb3V0XG4iKTsKCQl9IGVsc2UgaWYgKG1jc3BpX3dhaXRfZm9yX3JlZ19iaXQoY2hzdGF0X3JlZywKCQkJCU9NQVAyX01DU1BJX0NIU1RBVF9FT1QpIDwgMCkKCQkJZGV2X2Vycigmc3BpLT5kZXYsICJFT1QgdGltZWQgb3V0XG4iKTsKCgkJLyogZGlzYWJsZSBjaGFuIHRvIHB1cmdlIHJ4IGRhdGFzIHJlY2VpdmVkIGluIFRYX09OTFkgdHJhbnNmZXIsCgkJICogb3RoZXJ3aXNlIHRoZXNlIHJ4IGRhdGFzIHdpbGwgYWZmZWN0IHRoZSBkaXJlY3QgZm9sbG93aW5nCgkJICogUlhfT05MWSB0cmFuc2Zlci4KCQkgKi8KCQlvbWFwMl9tY3NwaV9zZXRfZW5hYmxlKHNwaSwgMCk7Cgl9Cm91dDoKCW9tYXAyX21jc3BpX3NldF9lbmFibGUoc3BpLCAxKTsKCXJldHVybiBjb3VudCAtIGM7Cn0KCi8qIGNhbGxlZCBvbmx5IHdoZW4gbm8gdHJhbnNmZXIgaXMgYWN0aXZlIHRvIHRoaXMgZGV2aWNlICovCnN0YXRpYyBpbnQgb21hcDJfbWNzcGlfc2V0dXBfdHJhbnNmZXIoc3RydWN0IHNwaV9kZXZpY2UgKnNwaSwKCQlzdHJ1Y3Qgc3BpX3RyYW5zZmVyICp0KQp7CglzdHJ1Y3Qgb21hcDJfbWNzcGlfY3MgKmNzID0gc3BpLT5jb250cm9sbGVyX3N0YXRlOwoJc3RydWN0IG9tYXAyX21jc3BpICptY3NwaTsKCXN0cnVjdCBzcGlfbWFzdGVyICpzcGlfY250cmw7Cgl1MzIgbCA9IDAsIGRpdiA9IDA7Cgl1OCB3b3JkX2xlbiA9IHNwaS0+Yml0c19wZXJfd29yZDsKCXUzMiBzcGVlZF9oeiA9IHNwaS0+bWF4X3NwZWVkX2h6OwoKCW1jc3BpID0gc3BpX21hc3Rlcl9nZXRfZGV2ZGF0YShzcGktPm1hc3Rlcik7CglzcGlfY250cmwgPSBtY3NwaS0+bWFzdGVyOwoKCWlmICh0ICE9IE5VTEwgJiYgdC0+Yml0c19wZXJfd29yZCkKCQl3b3JkX2xlbiA9IHQtPmJpdHNfcGVyX3dvcmQ7CgoJY3MtPndvcmRfbGVuID0gd29yZF9sZW47CgoJaWYgKHQgJiYgdC0+c3BlZWRfaHopCgkJc3BlZWRfaHogPSB0LT5zcGVlZF9oejsKCglpZiAoc3BlZWRfaHopIHsKCQl3aGlsZSAoZGl2IDw9IDE1ICYmIChPTUFQMl9NQ1NQSV9NQVhfRlJFUSAvICgxIDw8IGRpdikpCgkJCQkJPiBzcGVlZF9oeikKCQkJZGl2Kys7Cgl9IGVsc2UKCQlkaXYgPSAxNTsKCglsID0gbWNzcGlfY2FjaGVkX2NoY29uZjAoc3BpKTsKCgkvKiBzdGFuZGFyZCA0LXdpcmUgbWFzdGVyIG1vZGU6ICBTQ0ssIE1PU0kvb3V0LCBNSVNPL2luLCBuQ1MKCSAqIFJFVklTSVQ6IHRoaXMgY29udHJvbGxlciBjb3VsZCBzdXBwb3J0IFNQSV8zV0lSRSBtb2RlLgoJICovCglsICY9IH4oT01BUDJfTUNTUElfQ0hDT05GX0lTfE9NQVAyX01DU1BJX0NIQ09ORl9EUEUxKTsKCWwgfD0gT01BUDJfTUNTUElfQ0hDT05GX0RQRTA7CgoJLyogd29yZGxlbmd0aCAqLwoJbCAmPSB+T01BUDJfTUNTUElfQ0hDT05GX1dMX01BU0s7CglsIHw9ICh3b3JkX2xlbiAtIDEpIDw8IDc7CgoJLyogc2V0IGNoaXBzZWxlY3QgcG9sYXJpdHk7IG1hbmFnZSB3aXRoIEZPUkNFICovCglpZiAoIShzcGktPm1vZGUgJiBTUElfQ1NfSElHSCkpCgkJbCB8PSBPTUFQMl9NQ1NQSV9DSENPTkZfRVBPTDsJLyogYWN0aXZlLWxvdzsgbm9ybWFsICovCgllbHNlCgkJbCAmPSB+T01BUDJfTUNTUElfQ0hDT05GX0VQT0w7CgoJLyogc2V0IGNsb2NrIGRpdmlzb3IgKi8KCWwgJj0gfk9NQVAyX01DU1BJX0NIQ09ORl9DTEtEX01BU0s7CglsIHw9IGRpdiA8PCAyOwoKCS8qIHNldCBTUEkgbW9kZSAwLi4zICovCglpZiAoc3BpLT5tb2RlICYgU1BJX0NQT0wpCgkJbCB8PSBPTUFQMl9NQ1NQSV9DSENPTkZfUE9MOwoJZWxzZQoJCWwgJj0gfk9NQVAyX01DU1BJX0NIQ09ORl9QT0w7CglpZiAoc3BpLT5tb2RlICYgU1BJX0NQSEEpCgkJbCB8PSBPTUFQMl9NQ1NQSV9DSENPTkZfUEhBOwoJZWxzZQoJCWwgJj0gfk9NQVAyX01DU1BJX0NIQ09ORl9QSEE7CgoJbWNzcGlfd3JpdGVfY2hjb25mMChzcGksIGwpOwoKCWRldl9kYmcoJnNwaS0+ZGV2LCAic2V0dXA6IHNwZWVkICVkLCBzYW1wbGUgJXMgZWRnZSwgY2xrICVzXG4iLAoJCQlPTUFQMl9NQ1NQSV9NQVhfRlJFUSAvICgxIDw8IGRpdiksCgkJCShzcGktPm1vZGUgJiBTUElfQ1BIQSkgPyAidHJhaWxpbmciIDogImxlYWRpbmciLAoJCQkoc3BpLT5tb2RlICYgU1BJX0NQT0wpID8gImludmVydGVkIiA6ICJub3JtYWwiKTsKCglyZXR1cm4gMDsKfQoKc3RhdGljIHZvaWQgb21hcDJfbWNzcGlfZG1hX3J4X2NhbGxiYWNrKGludCBsY2gsIHUxNiBjaF9zdGF0dXMsIHZvaWQgKmRhdGEpCnsKCXN0cnVjdCBzcGlfZGV2aWNlCSpzcGkgPSBkYXRhOwoJc3RydWN0IG9tYXAyX21jc3BpCSptY3NwaTsKCXN0cnVjdCBvbWFwMl9tY3NwaV9kbWEJKm1jc3BpX2RtYTsKCgltY3NwaSA9IHNwaV9tYXN0ZXJfZ2V0X2RldmRhdGEoc3BpLT5tYXN0ZXIpOwoJbWNzcGlfZG1hID0gJihtY3NwaS0+ZG1hX2NoYW5uZWxzW3NwaS0+Y2hpcF9zZWxlY3RdKTsKCgljb21wbGV0ZSgmbWNzcGlfZG1hLT5kbWFfcnhfY29tcGxldGlvbik7CgoJLyogV2UgbXVzdCBkaXNhYmxlIHRoZSBETUEgUlggcmVxdWVzdCAqLwoJb21hcDJfbWNzcGlfc2V0X2RtYV9yZXEoc3BpLCAxLCAwKTsKfQoKc3RhdGljIHZvaWQgb21hcDJfbWNzcGlfZG1hX3R4X2NhbGxiYWNrKGludCBsY2gsIHUxNiBjaF9zdGF0dXMsIHZvaWQgKmRhdGEpCnsKCXN0cnVjdCBzcGlfZGV2aWNlCSpzcGkgPSBkYXRhOwoJc3RydWN0IG9tYXAyX21jc3BpCSptY3NwaTsKCXN0cnVjdCBvbWFwMl9tY3NwaV9kbWEJKm1jc3BpX2RtYTsKCgltY3NwaSA9IHNwaV9tYXN0ZXJfZ2V0X2RldmRhdGEoc3BpLT5tYXN0ZXIpOwoJbWNzcGlfZG1hID0gJihtY3NwaS0+ZG1hX2NoYW5uZWxzW3NwaS0+Y2hpcF9zZWxlY3RdKTsKCgljb21wbGV0ZSgmbWNzcGlfZG1hLT5kbWFfdHhfY29tcGxldGlvbik7CgoJLyogV2UgbXVzdCBkaXNhYmxlIHRoZSBETUEgVFggcmVxdWVzdCAqLwoJb21hcDJfbWNzcGlfc2V0X2RtYV9yZXEoc3BpLCAwLCAwKTsKfQoKc3RhdGljIGludCBvbWFwMl9tY3NwaV9yZXF1ZXN0X2RtYShzdHJ1Y3Qgc3BpX2RldmljZSAqc3BpKQp7CglzdHJ1Y3Qgc3BpX21hc3RlcgkqbWFzdGVyID0gc3BpLT5tYXN0ZXI7CglzdHJ1Y3Qgb21hcDJfbWNzcGkJKm1jc3BpOwoJc3RydWN0IG9tYXAyX21jc3BpX2RtYQkqbWNzcGlfZG1hOwoKCW1jc3BpID0gc3BpX21hc3Rlcl9nZXRfZGV2ZGF0YShtYXN0ZXIpOwoJbWNzcGlfZG1hID0gbWNzcGktPmRtYV9jaGFubmVscyArIHNwaS0+Y2hpcF9zZWxlY3Q7CgoJaWYgKG9tYXBfcmVxdWVzdF9kbWEobWNzcGlfZG1hLT5kbWFfcnhfc3luY19kZXYsICJNY1NQSSBSWCIsCgkJCW9tYXAyX21jc3BpX2RtYV9yeF9jYWxsYmFjaywgc3BpLAoJCQkmbWNzcGlfZG1hLT5kbWFfcnhfY2hhbm5lbCkpIHsKCQlkZXZfZXJyKCZzcGktPmRldiwgIm5vIFJYIERNQSBjaGFubmVsIGZvciBNY1NQSVxuIik7CgkJcmV0dXJuIC1FQUdBSU47Cgl9CgoJaWYgKG9tYXBfcmVxdWVzdF9kbWEobWNzcGlfZG1hLT5kbWFfdHhfc3luY19kZXYsICJNY1NQSSBUWCIsCgkJCW9tYXAyX21jc3BpX2RtYV90eF9jYWxsYmFjaywgc3BpLAoJCQkmbWNzcGlfZG1hLT5kbWFfdHhfY2hhbm5lbCkpIHsKCQlvbWFwX2ZyZWVfZG1hKG1jc3BpX2RtYS0+ZG1hX3J4X2NoYW5uZWwpOwoJCW1jc3BpX2RtYS0+ZG1hX3J4X2NoYW5uZWwgPSAtMTsKCQlkZXZfZXJyKCZzcGktPmRldiwgIm5vIFRYIERNQSBjaGFubmVsIGZvciBNY1NQSVxuIik7CgkJcmV0dXJuIC1FQUdBSU47Cgl9CgoJaW5pdF9jb21wbGV0aW9uKCZtY3NwaV9kbWEtPmRtYV9yeF9jb21wbGV0aW9uKTsKCWluaXRfY29tcGxldGlvbigmbWNzcGlfZG1hLT5kbWFfdHhfY29tcGxldGlvbik7CgoJcmV0dXJuIDA7Cn0KCnN0YXRpYyBpbnQgb21hcDJfbWNzcGlfc2V0dXAoc3RydWN0IHNwaV9kZXZpY2UgKnNwaSkKewoJaW50CQkJcmV0OwoJc3RydWN0IG9tYXAyX21jc3BpCSptY3NwaTsKCXN0cnVjdCBvbWFwMl9tY3NwaV9kbWEJKm1jc3BpX2RtYTsKCXN0cnVjdCBvbWFwMl9tY3NwaV9jcwkqY3MgPSBzcGktPmNvbnRyb2xsZXJfc3RhdGU7CgoJaWYgKHNwaS0+Yml0c19wZXJfd29yZCA8IDQgfHwgc3BpLT5iaXRzX3Blcl93b3JkID4gMzIpIHsKCQlkZXZfZGJnKCZzcGktPmRldiwgInNldHVwOiB1bnN1cHBvcnRlZCAlZCBiaXQgd29yZHNcbiIsCgkJCXNwaS0+Yml0c19wZXJfd29yZCk7CgkJcmV0dXJuIC1FSU5WQUw7Cgl9CgoJbWNzcGkgPSBzcGlfbWFzdGVyX2dldF9kZXZkYXRhKHNwaS0+bWFzdGVyKTsKCW1jc3BpX2RtYSA9ICZtY3NwaS0+ZG1hX2NoYW5uZWxzW3NwaS0+Y2hpcF9zZWxlY3RdOwoKCWlmICghY3MpIHsKCQljcyA9IGt6YWxsb2Moc2l6ZW9mICpjcywgR0ZQX0tFUk5FTCk7CgkJaWYgKCFjcykKCQkJcmV0dXJuIC1FTk9NRU07CgkJY3MtPmJhc2UgPSBtY3NwaS0+YmFzZSArIHNwaS0+Y2hpcF9zZWxlY3QgKiAweDE0OwoJCWNzLT5waHlzID0gbWNzcGktPnBoeXMgKyBzcGktPmNoaXBfc2VsZWN0ICogMHgxNDsKCQljcy0+Y2hjb25mMCA9IDA7CgkJc3BpLT5jb250cm9sbGVyX3N0YXRlID0gY3M7CgkJLyogTGluayB0aGlzIHRvIGNvbnRleHQgc2F2ZSBsaXN0ICovCgkJbGlzdF9hZGRfdGFpbCgmY3MtPm5vZGUsCgkJCSZvbWFwMl9tY3NwaV9jdHhbbWNzcGktPm1hc3Rlci0+YnVzX251bSAtIDFdLmNzKTsKCX0KCglpZiAobWNzcGlfZG1hLT5kbWFfcnhfY2hhbm5lbCA9PSAtMQoJCQl8fCBtY3NwaV9kbWEtPmRtYV90eF9jaGFubmVsID09IC0xKSB7CgkJcmV0ID0gb21hcDJfbWNzcGlfcmVxdWVzdF9kbWEoc3BpKTsKCQlpZiAocmV0IDwgMCkKCQkJcmV0dXJuIHJldDsKCX0KCglpZiAob21hcDJfbWNzcGlfZW5hYmxlX2Nsb2NrcyhtY3NwaSkpCgkJcmV0dXJuIC1FTk9ERVY7CgoJcmV0ID0gb21hcDJfbWNzcGlfc2V0dXBfdHJhbnNmZXIoc3BpLCBOVUxMKTsKCW9tYXAyX21jc3BpX2Rpc2FibGVfY2xvY2tzKG1jc3BpKTsKCglyZXR1cm4gcmV0Owp9CgpzdGF0aWMgdm9pZCBvbWFwMl9tY3NwaV9jbGVhbnVwKHN0cnVjdCBzcGlfZGV2aWNlICpzcGkpCnsKCXN0cnVjdCBvbWFwMl9tY3NwaQkqbWNzcGk7CglzdHJ1Y3Qgb21hcDJfbWNzcGlfZG1hCSptY3NwaV9kbWE7CglzdHJ1Y3Qgb21hcDJfbWNzcGlfY3MJKmNzOwoKCW1jc3BpID0gc3BpX21hc3Rlcl9nZXRfZGV2ZGF0YShzcGktPm1hc3Rlcik7CgoJaWYgKHNwaS0+Y29udHJvbGxlcl9zdGF0ZSkgewoJCS8qIFVubGluayBjb250cm9sbGVyIHN0YXRlIGZyb20gY29udGV4dCBzYXZlIGxpc3QgKi8KCQljcyA9IHNwaS0+Y29udHJvbGxlcl9zdGF0ZTsKCQlsaXN0X2RlbCgmY3MtPm5vZGUpOwoKCQlrZnJlZShzcGktPmNvbnRyb2xsZXJfc3RhdGUpOwoJfQoKCWlmIChzcGktPmNoaXBfc2VsZWN0IDwgc3BpLT5tYXN0ZXItPm51bV9jaGlwc2VsZWN0KSB7CgkJbWNzcGlfZG1hID0gJm1jc3BpLT5kbWFfY2hhbm5lbHNbc3BpLT5jaGlwX3NlbGVjdF07CgoJCWlmIChtY3NwaV9kbWEtPmRtYV9yeF9jaGFubmVsICE9IC0xKSB7CgkJCW9tYXBfZnJlZV9kbWEobWNzcGlfZG1hLT5kbWFfcnhfY2hhbm5lbCk7CgkJCW1jc3BpX2RtYS0+ZG1hX3J4X2NoYW5uZWwgPSAtMTsKCQl9CgkJaWYgKG1jc3BpX2RtYS0+ZG1hX3R4X2NoYW5uZWwgIT0gLTEpIHsKCQkJb21hcF9mcmVlX2RtYShtY3NwaV9kbWEtPmRtYV90eF9jaGFubmVsKTsKCQkJbWNzcGlfZG1hLT5kbWFfdHhfY2hhbm5lbCA9IC0xOwoJCX0KCX0KfQoKc3RhdGljIHZvaWQgb21hcDJfbWNzcGlfd29yayhzdHJ1Y3Qgd29ya19zdHJ1Y3QgKndvcmspCnsKCXN0cnVjdCBvbWFwMl9tY3NwaQkqbWNzcGk7CgoJbWNzcGkgPSBjb250YWluZXJfb2Yod29yaywgc3RydWN0IG9tYXAyX21jc3BpLCB3b3JrKTsKCXNwaW5fbG9ja19pcnEoJm1jc3BpLT5sb2NrKTsKCglpZiAob21hcDJfbWNzcGlfZW5hYmxlX2Nsb2NrcyhtY3NwaSkpCgkJZ290byBvdXQ7CgoJLyogV2Ugb25seSBlbmFibGUgb25lIGNoYW5uZWwgYXQgYSB0aW1lIC0tIHRoZSBvbmUgd2hvc2UgbWVzc2FnZSBpcwoJICogYXQgdGhlIGhlYWQgb2YgdGhlIHF1ZXVlIC0tIGFsdGhvdWdoIHRoaXMgY29udHJvbGxlciB3b3VsZCBnbGFkbHkKCSAqIGFyYml0cmF0ZSBhbW9uZyBtdWx0aXBsZSBjaGFubmVscy4gIFRoaXMgY29ycmVzcG9uZHMgdG8gInNpbmdsZQoJICogY2hhbm5lbCIgbWFzdGVyIG1vZGUuICBBcyBhIHNpZGUgZWZmZWN0LCB3ZSBuZWVkIHRvIG1hbmFnZSB0aGUKCSAqIGNoaXBzZWxlY3Qgd2l0aCB0aGUgRk9SQ0UgYml0IC4uLiBDUyAhPSBjaGFubmVsIGVuYWJsZS4KCSAqLwoJd2hpbGUgKCFsaXN0X2VtcHR5KCZtY3NwaS0+bXNnX3F1ZXVlKSkgewoJCXN0cnVjdCBzcGlfbWVzc2FnZQkJKm07CgkJc3RydWN0IHNwaV9kZXZpY2UJCSpzcGk7CgkJc3RydWN0IHNwaV90cmFuc2ZlcgkJKnQgPSBOVUxMOwoJCWludAkJCQljc19hY3RpdmUgPSAwOwoJCXN0cnVjdCBvbWFwMl9tY3NwaV9jcwkJKmNzOwoJCXN0cnVjdCBvbWFwMl9tY3NwaV9kZXZpY2VfY29uZmlnICpjZDsKCQlpbnQJCQkJcGFyX292ZXJyaWRlID0gMDsKCQlpbnQJCQkJc3RhdHVzID0gMDsKCQl1MzIJCQkJY2hjb25mOwoKCQltID0gY29udGFpbmVyX29mKG1jc3BpLT5tc2dfcXVldWUubmV4dCwgc3RydWN0IHNwaV9tZXNzYWdlLAoJCQkJIHF1ZXVlKTsKCgkJbGlzdF9kZWxfaW5pdCgmbS0+cXVldWUpOwoJCXNwaW5fdW5sb2NrX2lycSgmbWNzcGktPmxvY2spOwoKCQlzcGkgPSBtLT5zcGk7CgkJY3MgPSBzcGktPmNvbnRyb2xsZXJfc3RhdGU7CgkJY2QgPSBzcGktPmNvbnRyb2xsZXJfZGF0YTsKCgkJb21hcDJfbWNzcGlfc2V0X2VuYWJsZShzcGksIDEpOwoJCWxpc3RfZm9yX2VhY2hfZW50cnkodCwgJm0tPnRyYW5zZmVycywgdHJhbnNmZXJfbGlzdCkgewoJCQlpZiAodC0+dHhfYnVmID09IE5VTEwgJiYgdC0+cnhfYnVmID09IE5VTEwgJiYgdC0+bGVuKSB7CgkJCQlzdGF0dXMgPSAtRUlOVkFMOwoJCQkJYnJlYWs7CgkJCX0KCQkJaWYgKHBhcl9vdmVycmlkZSB8fCB0LT5zcGVlZF9oeiB8fCB0LT5iaXRzX3Blcl93b3JkKSB7CgkJCQlwYXJfb3ZlcnJpZGUgPSAxOwoJCQkJc3RhdHVzID0gb21hcDJfbWNzcGlfc2V0dXBfdHJhbnNmZXIoc3BpLCB0KTsKCQkJCWlmIChzdGF0dXMgPCAwKQoJCQkJCWJyZWFrOwoJCQkJaWYgKCF0LT5zcGVlZF9oeiAmJiAhdC0+Yml0c19wZXJfd29yZCkKCQkJCQlwYXJfb3ZlcnJpZGUgPSAwOwoJCQl9CgoJCQlpZiAoIWNzX2FjdGl2ZSkgewoJCQkJb21hcDJfbWNzcGlfZm9yY2VfY3Moc3BpLCAxKTsKCQkJCWNzX2FjdGl2ZSA9IDE7CgkJCX0KCgkJCWNoY29uZiA9IG1jc3BpX2NhY2hlZF9jaGNvbmYwKHNwaSk7CgkJCWNoY29uZiAmPSB+T01BUDJfTUNTUElfQ0hDT05GX1RSTV9NQVNLOwoJCQljaGNvbmYgJj0gfk9NQVAyX01DU1BJX0NIQ09ORl9UVVJCTzsKCgkJCWlmICh0LT50eF9idWYgPT0gTlVMTCkKCQkJCWNoY29uZiB8PSBPTUFQMl9NQ1NQSV9DSENPTkZfVFJNX1JYX09OTFk7CgkJCWVsc2UgaWYgKHQtPnJ4X2J1ZiA9PSBOVUxMKQoJCQkJY2hjb25mIHw9IE9NQVAyX01DU1BJX0NIQ09ORl9UUk1fVFhfT05MWTsKCgkJCWlmIChjZCAmJiBjZC0+dHVyYm9fbW9kZSAmJiB0LT50eF9idWYgPT0gTlVMTCkgewoJCQkJLyogVHVyYm8gbW9kZSBpcyBmb3IgbW9yZSB0aGFuIG9uZSB3b3JkICovCgkJCQlpZiAodC0+bGVuID4gKChjcy0+d29yZF9sZW4gKyA3KSA+PiAzKSkKCQkJCQljaGNvbmYgfD0gT01BUDJfTUNTUElfQ0hDT05GX1RVUkJPOwoJCQl9CgoJCQltY3NwaV93cml0ZV9jaGNvbmYwKHNwaSwgY2hjb25mKTsKCgkJCWlmICh0LT5sZW4pIHsKCQkJCXVuc2lnbmVkCWNvdW50OwoKCQkJCS8qIFJYX09OTFkgbW9kZSBuZWVkcyBkdW1teSBkYXRhIGluIFRYIHJlZyAqLwoJCQkJaWYgKHQtPnR4X2J1ZiA9PSBOVUxMKQoJCQkJCV9fcmF3X3dyaXRlbCgwLCBjcy0+YmFzZQoJCQkJCQkJKyBPTUFQMl9NQ1NQSV9UWDApOwoKCQkJCWlmIChtLT5pc19kbWFfbWFwcGVkIHx8IHQtPmxlbiA+PSBETUFfTUlOX0JZVEVTKQoJCQkJCWNvdW50ID0gb21hcDJfbWNzcGlfdHhyeF9kbWEoc3BpLCB0KTsKCQkJCWVsc2UKCQkJCQljb3VudCA9IG9tYXAyX21jc3BpX3R4cnhfcGlvKHNwaSwgdCk7CgkJCQltLT5hY3R1YWxfbGVuZ3RoICs9IGNvdW50OwoKCQkJCWlmIChjb3VudCAhPSB0LT5sZW4pIHsKCQkJCQlzdGF0dXMgPSAtRUlPOwoJCQkJCWJyZWFrOwoJCQkJfQoJCQl9CgoJCQlpZiAodC0+ZGVsYXlfdXNlY3MpCgkJCQl1ZGVsYXkodC0+ZGVsYXlfdXNlY3MpOwoKCQkJLyogaWdub3JlIHRoZSAibGVhdmUgaXQgb24gYWZ0ZXIgbGFzdCB4ZmVyIiBoaW50ICovCgkJCWlmICh0LT5jc19jaGFuZ2UpIHsKCQkJCW9tYXAyX21jc3BpX2ZvcmNlX2NzKHNwaSwgMCk7CgkJCQljc19hY3RpdmUgPSAwOwoJCQl9CgkJfQoKCQkvKiBSZXN0b3JlIGRlZmF1bHRzIGlmIHRoZXkgd2VyZSBvdmVycmlkZW4gKi8KCQlpZiAocGFyX292ZXJyaWRlKSB7CgkJCXBhcl9vdmVycmlkZSA9IDA7CgkJCXN0YXR1cyA9IG9tYXAyX21jc3BpX3NldHVwX3RyYW5zZmVyKHNwaSwgTlVMTCk7CgkJfQoKCQlpZiAoY3NfYWN0aXZlKQoJCQlvbWFwMl9tY3NwaV9mb3JjZV9jcyhzcGksIDApOwoKCQlvbWFwMl9tY3NwaV9zZXRfZW5hYmxlKHNwaSwgMCk7CgoJCW0tPnN0YXR1cyA9IHN0YXR1czsKCQltLT5jb21wbGV0ZShtLT5jb250ZXh0KTsKCgkJc3Bpbl9sb2NrX2lycSgmbWNzcGktPmxvY2spOwoJfQoKCW9tYXAyX21jc3BpX2Rpc2FibGVfY2xvY2tzKG1jc3BpKTsKCm91dDoKCXNwaW5fdW5sb2NrX2lycSgmbWNzcGktPmxvY2spOwp9CgpzdGF0aWMgaW50IG9tYXAyX21jc3BpX3RyYW5zZmVyKHN0cnVjdCBzcGlfZGV2aWNlICpzcGksIHN0cnVjdCBzcGlfbWVzc2FnZSAqbSkKewoJc3RydWN0IG9tYXAyX21jc3BpCSptY3NwaTsKCXVuc2lnbmVkIGxvbmcJCWZsYWdzOwoJc3RydWN0IHNwaV90cmFuc2ZlcgkqdDsKCgltLT5hY3R1YWxfbGVuZ3RoID0gMDsKCW0tPnN0YXR1cyA9IDA7CgoJLyogcmVqZWN0IGludmFsaWQgbWVzc2FnZXMgYW5kIHRyYW5zZmVycyAqLwoJaWYgKGxpc3RfZW1wdHkoJm0tPnRyYW5zZmVycykgfHwgIW0tPmNvbXBsZXRlKQoJCXJldHVybiAtRUlOVkFMOwoJbGlzdF9mb3JfZWFjaF9lbnRyeSh0LCAmbS0+dHJhbnNmZXJzLCB0cmFuc2Zlcl9saXN0KSB7CgkJY29uc3Qgdm9pZAkqdHhfYnVmID0gdC0+dHhfYnVmOwoJCXZvaWQJCSpyeF9idWYgPSB0LT5yeF9idWY7CgkJdW5zaWduZWQJbGVuID0gdC0+bGVuOwoKCQlpZiAodC0+c3BlZWRfaHogPiBPTUFQMl9NQ1NQSV9NQVhfRlJFUQoJCQkJfHwgKGxlbiAmJiAhKHJ4X2J1ZiB8fCB0eF9idWYpKQoJCQkJfHwgKHQtPmJpdHNfcGVyX3dvcmQgJiYKCQkJCQkoICB0LT5iaXRzX3Blcl93b3JkIDwgNAoJCQkJCXx8IHQtPmJpdHNfcGVyX3dvcmQgPiAzMikpKSB7CgkJCWRldl9kYmcoJnNwaS0+ZGV2LCAidHJhbnNmZXI6ICVkIEh6LCAlZCAlcyVzLCAlZCBicHdcbiIsCgkJCQkJdC0+c3BlZWRfaHosCgkJCQkJbGVuLAoJCQkJCXR4X2J1ZiA/ICJ0eCIgOiAiIiwKCQkJCQlyeF9idWYgPyAicngiIDogIiIsCgkJCQkJdC0+Yml0c19wZXJfd29yZCk7CgkJCXJldHVybiAtRUlOVkFMOwoJCX0KCQlpZiAodC0+c3BlZWRfaHogJiYgdC0+c3BlZWRfaHogPCBPTUFQMl9NQ1NQSV9NQVhfRlJFUS8oMTw8MTYpKSB7CgkJCWRldl9kYmcoJnNwaS0+ZGV2LCAiJWQgSHogbWF4IGV4Y2VlZHMgJWRcbiIsCgkJCQkJdC0+c3BlZWRfaHosCgkJCQkJT01BUDJfTUNTUElfTUFYX0ZSRVEvKDE8PDE2KSk7CgkJCXJldHVybiAtRUlOVkFMOwoJCX0KCgkJaWYgKG0tPmlzX2RtYV9tYXBwZWQgfHwgbGVuIDwgRE1BX01JTl9CWVRFUykKCQkJY29udGludWU7CgoJCWlmICh0eF9idWYgIT0gTlVMTCkgewoJCQl0LT50eF9kbWEgPSBkbWFfbWFwX3NpbmdsZSgmc3BpLT5kZXYsICh2b2lkICopIHR4X2J1ZiwKCQkJCQlsZW4sIERNQV9UT19ERVZJQ0UpOwoJCQlpZiAoZG1hX21hcHBpbmdfZXJyb3IoJnNwaS0+ZGV2LCB0LT50eF9kbWEpKSB7CgkJCQlkZXZfZGJnKCZzcGktPmRldiwgImRtYSAlY1ggJWQgYnl0ZXMgZXJyb3JcbiIsCgkJCQkJCSdUJywgbGVuKTsKCQkJCXJldHVybiAtRUlOVkFMOwoJCQl9CgkJfQoJCWlmIChyeF9idWYgIT0gTlVMTCkgewoJCQl0LT5yeF9kbWEgPSBkbWFfbWFwX3NpbmdsZSgmc3BpLT5kZXYsIHJ4X2J1ZiwgdC0+bGVuLAoJCQkJCURNQV9GUk9NX0RFVklDRSk7CgkJCWlmIChkbWFfbWFwcGluZ19lcnJvcigmc3BpLT5kZXYsIHQtPnJ4X2RtYSkpIHsKCQkJCWRldl9kYmcoJnNwaS0+ZGV2LCAiZG1hICVjWCAlZCBieXRlcyBlcnJvclxuIiwKCQkJCQkJJ1InLCBsZW4pOwoJCQkJaWYgKHR4X2J1ZiAhPSBOVUxMKQoJCQkJCWRtYV91bm1hcF9zaW5nbGUoJnNwaS0+ZGV2LCB0LT50eF9kbWEsCgkJCQkJCQlsZW4sIERNQV9UT19ERVZJQ0UpOwoJCQkJcmV0dXJuIC1FSU5WQUw7CgkJCX0KCQl9Cgl9CgoJbWNzcGkgPSBzcGlfbWFzdGVyX2dldF9kZXZkYXRhKHNwaS0+bWFzdGVyKTsKCglzcGluX2xvY2tfaXJxc2F2ZSgmbWNzcGktPmxvY2ssIGZsYWdzKTsKCWxpc3RfYWRkX3RhaWwoJm0tPnF1ZXVlLCAmbWNzcGktPm1zZ19xdWV1ZSk7CglxdWV1ZV93b3JrKG9tYXAyX21jc3BpX3dxLCAmbWNzcGktPndvcmspOwoJc3Bpbl91bmxvY2tfaXJxcmVzdG9yZSgmbWNzcGktPmxvY2ssIGZsYWdzKTsKCglyZXR1cm4gMDsKfQoKc3RhdGljIGludCBfX2luaXQgb21hcDJfbWNzcGlfcmVzZXQoc3RydWN0IG9tYXAyX21jc3BpICptY3NwaSkKewoJc3RydWN0IHNwaV9tYXN0ZXIJKm1hc3RlciA9IG1jc3BpLT5tYXN0ZXI7Cgl1MzIJCQl0bXA7CgoJaWYgKG9tYXAyX21jc3BpX2VuYWJsZV9jbG9ja3MobWNzcGkpKQoJCXJldHVybiAtMTsKCgltY3NwaV93cml0ZV9yZWcobWFzdGVyLCBPTUFQMl9NQ1NQSV9TWVNDT05GSUcsCgkJCU9NQVAyX01DU1BJX1NZU0NPTkZJR19TT0ZUUkVTRVQpOwoJZG8gewoJCXRtcCA9IG1jc3BpX3JlYWRfcmVnKG1hc3RlciwgT01BUDJfTUNTUElfU1lTU1RBVFVTKTsKCX0gd2hpbGUgKCEodG1wICYgT01BUDJfTUNTUElfU1lTU1RBVFVTX1JFU0VURE9ORSkpOwoKCXRtcCA9IE9NQVAyX01DU1BJX1NZU0NPTkZJR19BVVRPSURMRSB8CgkJT01BUDJfTUNTUElfU1lTQ09ORklHX0VOQVdBS0VVUCB8CgkJT01BUDJfTUNTUElfU1lTQ09ORklHX1NNQVJUSURMRTsKCW1jc3BpX3dyaXRlX3JlZyhtYXN0ZXIsIE9NQVAyX01DU1BJX1NZU0NPTkZJRywgdG1wKTsKCW9tYXAyX21jc3BpX2N0eFttYXN0ZXItPmJ1c19udW0gLSAxXS5zeXNjb25maWcgPSB0bXA7CgoJdG1wID0gT01BUDJfTUNTUElfV0FLRVVQRU5BQkxFX1dLRU47CgltY3NwaV93cml0ZV9yZWcobWFzdGVyLCBPTUFQMl9NQ1NQSV9XQUtFVVBFTkFCTEUsIHRtcCk7CglvbWFwMl9tY3NwaV9jdHhbbWFzdGVyLT5idXNfbnVtIC0gMV0ud2FrZXVwZW5hYmxlID0gdG1wOwoKCW9tYXAyX21jc3BpX3NldF9tYXN0ZXJfbW9kZShtYXN0ZXIpOwoJb21hcDJfbWNzcGlfZGlzYWJsZV9jbG9ja3MobWNzcGkpOwoJcmV0dXJuIDA7Cn0KCnN0YXRpYyB1OCBfX2luaXRkYXRhIHNwaTFfcnhkbWFfaWQgW10gPSB7CglPTUFQMjRYWF9ETUFfU1BJMV9SWDAsCglPTUFQMjRYWF9ETUFfU1BJMV9SWDEsCglPTUFQMjRYWF9ETUFfU1BJMV9SWDIsCglPTUFQMjRYWF9ETUFfU1BJMV9SWDMsCn07CgpzdGF0aWMgdTggX19pbml0ZGF0YSBzcGkxX3R4ZG1hX2lkIFtdID0gewoJT01BUDI0WFhfRE1BX1NQSTFfVFgwLAoJT01BUDI0WFhfRE1BX1NQSTFfVFgxLAoJT01BUDI0WFhfRE1BX1NQSTFfVFgyLAoJT01BUDI0WFhfRE1BX1NQSTFfVFgzLAp9OwoKc3RhdGljIHU4IF9faW5pdGRhdGEgc3BpMl9yeGRtYV9pZFtdID0gewoJT01BUDI0WFhfRE1BX1NQSTJfUlgwLAoJT01BUDI0WFhfRE1BX1NQSTJfUlgxLAp9OwoKc3RhdGljIHU4IF9faW5pdGRhdGEgc3BpMl90eGRtYV9pZFtdID0gewoJT01BUDI0WFhfRE1BX1NQSTJfVFgwLAoJT01BUDI0WFhfRE1BX1NQSTJfVFgxLAp9OwoKI2lmIGRlZmluZWQoQ09ORklHX0FSQ0hfT01BUDI0MzApIHx8IGRlZmluZWQoQ09ORklHX0FSQ0hfT01BUDMpIFwKCXx8IGRlZmluZWQoQ09ORklHX0FSQ0hfT01BUDQpCnN0YXRpYyB1OCBfX2luaXRkYXRhIHNwaTNfcnhkbWFfaWRbXSA9IHsKCU9NQVAyNFhYX0RNQV9TUEkzX1JYMCwKCU9NQVAyNFhYX0RNQV9TUEkzX1JYMSwKfTsKCnN0YXRpYyB1OCBfX2luaXRkYXRhIHNwaTNfdHhkbWFfaWRbXSA9IHsKCU9NQVAyNFhYX0RNQV9TUEkzX1RYMCwKCU9NQVAyNFhYX0RNQV9TUEkzX1RYMSwKfTsKI2VuZGlmCgojaWYgZGVmaW5lZChDT05GSUdfQVJDSF9PTUFQMykgfHwgZGVmaW5lZChDT05GSUdfQVJDSF9PTUFQNCkKc3RhdGljIHU4IF9faW5pdGRhdGEgc3BpNF9yeGRtYV9pZFtdID0gewoJT01BUDM0WFhfRE1BX1NQSTRfUlgwLAp9OwoKc3RhdGljIHU4IF9faW5pdGRhdGEgc3BpNF90eGRtYV9pZFtdID0gewoJT01BUDM0WFhfRE1BX1NQSTRfVFgwLAp9OwojZW5kaWYKCnN0YXRpYyBpbnQgX19pbml0IG9tYXAyX21jc3BpX3Byb2JlKHN0cnVjdCBwbGF0Zm9ybV9kZXZpY2UgKnBkZXYpCnsKCXN0cnVjdCBzcGlfbWFzdGVyCSptYXN0ZXI7CglzdHJ1Y3Qgb21hcDJfbWNzcGkJKm1jc3BpOwoJc3RydWN0IHJlc291cmNlCQkqcjsKCWludAkJCXN0YXR1cyA9IDAsIGk7Cgljb25zdCB1OAkJKnJ4ZG1hX2lkLCAqdHhkbWFfaWQ7Cgl1bnNpZ25lZAkJbnVtX2NoaXBzZWxlY3Q7CgoJc3dpdGNoIChwZGV2LT5pZCkgewoJY2FzZSAxOgoJCXJ4ZG1hX2lkID0gc3BpMV9yeGRtYV9pZDsKCQl0eGRtYV9pZCA9IHNwaTFfdHhkbWFfaWQ7CgkJbnVtX2NoaXBzZWxlY3QgPSA0OwoJCWJyZWFrOwoJY2FzZSAyOgoJCXJ4ZG1hX2lkID0gc3BpMl9yeGRtYV9pZDsKCQl0eGRtYV9pZCA9IHNwaTJfdHhkbWFfaWQ7CgkJbnVtX2NoaXBzZWxlY3QgPSAyOwoJCWJyZWFrOwojaWYgZGVmaW5lZChDT05GSUdfQVJDSF9PTUFQMjQzMCkgfHwgZGVmaW5lZChDT05GSUdfQVJDSF9PTUFQMykgXAoJfHwgZGVmaW5lZChDT05GSUdfQVJDSF9PTUFQNCkKCWNhc2UgMzoKCQlyeGRtYV9pZCA9IHNwaTNfcnhkbWFfaWQ7CgkJdHhkbWFfaWQgPSBzcGkzX3R4ZG1hX2lkOwoJCW51bV9jaGlwc2VsZWN0ID0gMjsKCQlicmVhazsKI2VuZGlmCiNpZiBkZWZpbmVkKENPTkZJR19BUkNIX09NQVAzKSB8fCBkZWZpbmVkKENPTkZJR19BUkNIX09NQVA0KQoJY2FzZSA0OgoJCXJ4ZG1hX2lkID0gc3BpNF9yeGRtYV9pZDsKCQl0eGRtYV9pZCA9IHNwaTRfdHhkbWFfaWQ7CgkJbnVtX2NoaXBzZWxlY3QgPSAxOwoJCWJyZWFrOwojZW5kaWYKCWRlZmF1bHQ6CgkJcmV0dXJuIC1FSU5WQUw7Cgl9CgoJbWFzdGVyID0gc3BpX2FsbG9jX21hc3RlcigmcGRldi0+ZGV2LCBzaXplb2YgKm1jc3BpKTsKCWlmIChtYXN0ZXIgPT0gTlVMTCkgewoJCWRldl9kYmcoJnBkZXYtPmRldiwgIm1hc3RlciBhbGxvY2F0aW9uIGZhaWxlZFxuIik7CgkJcmV0dXJuIC1FTk9NRU07Cgl9CgoJLyogdGhlIHNwaS0+bW9kZSBiaXRzIHVuZGVyc3Rvb2QgYnkgdGhpcyBkcml2ZXI6ICovCgltYXN0ZXItPm1vZGVfYml0cyA9IFNQSV9DUE9MIHwgU1BJX0NQSEEgfCBTUElfQ1NfSElHSDsKCglpZiAocGRldi0+aWQgIT0gLTEpCgkJbWFzdGVyLT5idXNfbnVtID0gcGRldi0+aWQ7CgoJbWFzdGVyLT5zZXR1cCA9IG9tYXAyX21jc3BpX3NldHVwOwoJbWFzdGVyLT50cmFuc2ZlciA9IG9tYXAyX21jc3BpX3RyYW5zZmVyOwoJbWFzdGVyLT5jbGVhbnVwID0gb21hcDJfbWNzcGlfY2xlYW51cDsKCW1hc3Rlci0+bnVtX2NoaXBzZWxlY3QgPSBudW1fY2hpcHNlbGVjdDsKCglkZXZfc2V0X2RydmRhdGEoJnBkZXYtPmRldiwgbWFzdGVyKTsKCgltY3NwaSA9IHNwaV9tYXN0ZXJfZ2V0X2RldmRhdGEobWFzdGVyKTsKCW1jc3BpLT5tYXN0ZXIgPSBtYXN0ZXI7CgoJciA9IHBsYXRmb3JtX2dldF9yZXNvdXJjZShwZGV2LCBJT1JFU09VUkNFX01FTSwgMCk7CglpZiAociA9PSBOVUxMKSB7CgkJc3RhdHVzID0gLUVOT0RFVjsKCQlnb3RvIGVycjE7Cgl9CglpZiAoIXJlcXVlc3RfbWVtX3JlZ2lvbihyLT5zdGFydCwgKHItPmVuZCAtIHItPnN0YXJ0KSArIDEsCgkJCWRldl9uYW1lKCZwZGV2LT5kZXYpKSkgewoJCXN0YXR1cyA9IC1FQlVTWTsKCQlnb3RvIGVycjE7Cgl9CgoJbWNzcGktPnBoeXMgPSByLT5zdGFydDsKCW1jc3BpLT5iYXNlID0gaW9yZW1hcChyLT5zdGFydCwgci0+ZW5kIC0gci0+c3RhcnQgKyAxKTsKCWlmICghbWNzcGktPmJhc2UpIHsKCQlkZXZfZGJnKCZwZGV2LT5kZXYsICJjYW4ndCBpb3JlbWFwIE1DU1BJXG4iKTsKCQlzdGF0dXMgPSAtRU5PTUVNOwoJCWdvdG8gZXJyMWFhOwoJfQoKCUlOSVRfV09SSygmbWNzcGktPndvcmssIG9tYXAyX21jc3BpX3dvcmspOwoKCXNwaW5fbG9ja19pbml0KCZtY3NwaS0+bG9jayk7CglJTklUX0xJU1RfSEVBRCgmbWNzcGktPm1zZ19xdWV1ZSk7CglJTklUX0xJU1RfSEVBRCgmb21hcDJfbWNzcGlfY3R4W21hc3Rlci0+YnVzX251bSAtIDFdLmNzKTsKCgltY3NwaS0+aWNrID0gY2xrX2dldCgmcGRldi0+ZGV2LCAiaWNrIik7CglpZiAoSVNfRVJSKG1jc3BpLT5pY2spKSB7CgkJZGV2X2RiZygmcGRldi0+ZGV2LCAiY2FuJ3QgZ2V0IG1jc3BpX2lja1xuIik7CgkJc3RhdHVzID0gUFRSX0VSUihtY3NwaS0+aWNrKTsKCQlnb3RvIGVycjFhOwoJfQoJbWNzcGktPmZjayA9IGNsa19nZXQoJnBkZXYtPmRldiwgImZjayIpOwoJaWYgKElTX0VSUihtY3NwaS0+ZmNrKSkgewoJCWRldl9kYmcoJnBkZXYtPmRldiwgImNhbid0IGdldCBtY3NwaV9mY2tcbiIpOwoJCXN0YXR1cyA9IFBUUl9FUlIobWNzcGktPmZjayk7CgkJZ290byBlcnIyOwoJfQoKCW1jc3BpLT5kbWFfY2hhbm5lbHMgPSBrY2FsbG9jKG1hc3Rlci0+bnVtX2NoaXBzZWxlY3QsCgkJCXNpemVvZihzdHJ1Y3Qgb21hcDJfbWNzcGlfZG1hKSwKCQkJR0ZQX0tFUk5FTCk7CgoJaWYgKG1jc3BpLT5kbWFfY2hhbm5lbHMgPT0gTlVMTCkKCQlnb3RvIGVycjM7CgoJZm9yIChpID0gMDsgaSA8IG51bV9jaGlwc2VsZWN0OyBpKyspIHsKCQltY3NwaS0+ZG1hX2NoYW5uZWxzW2ldLmRtYV9yeF9jaGFubmVsID0gLTE7CgkJbWNzcGktPmRtYV9jaGFubmVsc1tpXS5kbWFfcnhfc3luY19kZXYgPSByeGRtYV9pZFtpXTsKCQltY3NwaS0+ZG1hX2NoYW5uZWxzW2ldLmRtYV90eF9jaGFubmVsID0gLTE7CgkJbWNzcGktPmRtYV9jaGFubmVsc1tpXS5kbWFfdHhfc3luY19kZXYgPSB0eGRtYV9pZFtpXTsKCX0KCglpZiAob21hcDJfbWNzcGlfcmVzZXQobWNzcGkpIDwgMCkKCQlnb3RvIGVycjQ7CgoJc3RhdHVzID0gc3BpX3JlZ2lzdGVyX21hc3RlcihtYXN0ZXIpOwoJaWYgKHN0YXR1cyA8IDApCgkJZ290byBlcnI0OwoKCXJldHVybiBzdGF0dXM7CgplcnI0OgoJa2ZyZWUobWNzcGktPmRtYV9jaGFubmVscyk7CmVycjM6CgljbGtfcHV0KG1jc3BpLT5mY2spOwplcnIyOgoJY2xrX3B1dChtY3NwaS0+aWNrKTsKZXJyMWE6Cglpb3VubWFwKG1jc3BpLT5iYXNlKTsKZXJyMWFhOgoJcmVsZWFzZV9tZW1fcmVnaW9uKHItPnN0YXJ0LCAoci0+ZW5kIC0gci0+c3RhcnQpICsgMSk7CmVycjE6CglzcGlfbWFzdGVyX3B1dChtYXN0ZXIpOwoJcmV0dXJuIHN0YXR1czsKfQoKc3RhdGljIGludCBfX2V4aXQgb21hcDJfbWNzcGlfcmVtb3ZlKHN0cnVjdCBwbGF0Zm9ybV9kZXZpY2UgKnBkZXYpCnsKCXN0cnVjdCBzcGlfbWFzdGVyCSptYXN0ZXI7CglzdHJ1Y3Qgb21hcDJfbWNzcGkJKm1jc3BpOwoJc3RydWN0IG9tYXAyX21jc3BpX2RtYQkqZG1hX2NoYW5uZWxzOwoJc3RydWN0IHJlc291cmNlCQkqcjsKCXZvaWQgX19pb21lbSAqYmFzZTsKCgltYXN0ZXIgPSBkZXZfZ2V0X2RydmRhdGEoJnBkZXYtPmRldik7CgltY3NwaSA9IHNwaV9tYXN0ZXJfZ2V0X2RldmRhdGEobWFzdGVyKTsKCWRtYV9jaGFubmVscyA9IG1jc3BpLT5kbWFfY2hhbm5lbHM7CgoJY2xrX3B1dChtY3NwaS0+ZmNrKTsKCWNsa19wdXQobWNzcGktPmljayk7CgoJciA9IHBsYXRmb3JtX2dldF9yZXNvdXJjZShwZGV2LCBJT1JFU09VUkNFX01FTSwgMCk7CglyZWxlYXNlX21lbV9yZWdpb24oci0+c3RhcnQsIChyLT5lbmQgLSByLT5zdGFydCkgKyAxKTsKCgliYXNlID0gbWNzcGktPmJhc2U7CglzcGlfdW5yZWdpc3Rlcl9tYXN0ZXIobWFzdGVyKTsKCWlvdW5tYXAoYmFzZSk7CglrZnJlZShkbWFfY2hhbm5lbHMpOwoKCXJldHVybiAwOwp9CgovKiB3b3JrIHdpdGggaG90cGx1ZyBhbmQgY29sZHBsdWcgKi8KTU9EVUxFX0FMSUFTKCJwbGF0Zm9ybTpvbWFwMl9tY3NwaSIpOwoKI2lmZGVmCUNPTkZJR19TVVNQRU5ECi8qCiAqIFdoZW4gU1BJIHdha2UgdXAgZnJvbSBvZmYtbW9kZSwgQ1MgaXMgaW4gYWN0aXZhdGUgc3RhdGUuIElmIGl0IHdhcyBpbgogKiB1bmFjdGl2ZSBzdGF0ZSB3aGVuIGRyaXZlciB3YXMgc3VzcGVuZCwgdGhlbiBmb3JjZSBpdCB0byB1bmFjdGl2ZSBzdGF0ZSBhdAogKiB3YWtlIHVwLgogKi8Kc3RhdGljIGludCBvbWFwMl9tY3NwaV9yZXN1bWUoc3RydWN0IGRldmljZSAqZGV2KQp7CglzdHJ1Y3Qgc3BpX21hc3RlcgkqbWFzdGVyID0gZGV2X2dldF9kcnZkYXRhKGRldik7CglzdHJ1Y3Qgb21hcDJfbWNzcGkJKm1jc3BpID0gc3BpX21hc3Rlcl9nZXRfZGV2ZGF0YShtYXN0ZXIpOwoJc3RydWN0IG9tYXAyX21jc3BpX2NzICpjczsKCglvbWFwMl9tY3NwaV9lbmFibGVfY2xvY2tzKG1jc3BpKTsKCWxpc3RfZm9yX2VhY2hfZW50cnkoY3MsICZvbWFwMl9tY3NwaV9jdHhbbWFzdGVyLT5idXNfbnVtIC0gMV0uY3MsCgkJCSAgICBub2RlKSB7CgkJaWYgKChjcy0+Y2hjb25mMCAmIE9NQVAyX01DU1BJX0NIQ09ORl9GT1JDRSkgPT0gMCkgewoKCQkJLyoKCQkJICogV2UgbmVlZCB0byB0b2dnbGUgQ1Mgc3RhdGUgZm9yIE9NQVAgdGFrZSB0aGlzCgkJCSAqIGNoYW5nZSBpbiBhY2NvdW50LgoJCQkgKi8KCQkJTU9EX1JFR19CSVQoY3MtPmNoY29uZjAsIE9NQVAyX01DU1BJX0NIQ09ORl9GT1JDRSwgMSk7CgkJCV9fcmF3X3dyaXRlbChjcy0+Y2hjb25mMCwgY3MtPmJhc2UgKyBPTUFQMl9NQ1NQSV9DSENPTkYwKTsKCQkJTU9EX1JFR19CSVQoY3MtPmNoY29uZjAsIE9NQVAyX01DU1BJX0NIQ09ORl9GT1JDRSwgMCk7CgkJCV9fcmF3X3dyaXRlbChjcy0+Y2hjb25mMCwgY3MtPmJhc2UgKyBPTUFQMl9NQ1NQSV9DSENPTkYwKTsKCQl9Cgl9CglvbWFwMl9tY3NwaV9kaXNhYmxlX2Nsb2NrcyhtY3NwaSk7CglyZXR1cm4gMDsKfQojZWxzZQojZGVmaW5lCW9tYXAyX21jc3BpX3Jlc3VtZQlOVUxMCiNlbmRpZgoKc3RhdGljIGNvbnN0IHN0cnVjdCBkZXZfcG1fb3BzIG9tYXAyX21jc3BpX3BtX29wcyA9IHsKCS5yZXN1bWUgPSBvbWFwMl9tY3NwaV9yZXN1bWUsCn07CgpzdGF0aWMgc3RydWN0IHBsYXRmb3JtX2RyaXZlciBvbWFwMl9tY3NwaV9kcml2ZXIgPSB7CgkuZHJpdmVyID0gewoJCS5uYW1lID0JCSJvbWFwMl9tY3NwaSIsCgkJLm93bmVyID0JVEhJU19NT0RVTEUsCgkJLnBtID0JCSZvbWFwMl9tY3NwaV9wbV9vcHMKCX0sCgkucmVtb3ZlID0JX19leGl0X3Aob21hcDJfbWNzcGlfcmVtb3ZlKSwKfTsKCgpzdGF0aWMgaW50IF9faW5pdCBvbWFwMl9tY3NwaV9pbml0KHZvaWQpCnsKCW9tYXAyX21jc3BpX3dxID0gY3JlYXRlX3NpbmdsZXRocmVhZF93b3JrcXVldWUoCgkJCQlvbWFwMl9tY3NwaV9kcml2ZXIuZHJpdmVyLm5hbWUpOwoJaWYgKG9tYXAyX21jc3BpX3dxID09IE5VTEwpCgkJcmV0dXJuIC0xOwoJcmV0dXJuIHBsYXRmb3JtX2RyaXZlcl9wcm9iZSgmb21hcDJfbWNzcGlfZHJpdmVyLCBvbWFwMl9tY3NwaV9wcm9iZSk7Cn0Kc3Vic3lzX2luaXRjYWxsKG9tYXAyX21jc3BpX2luaXQpOwoKc3RhdGljIHZvaWQgX19leGl0IG9tYXAyX21jc3BpX2V4aXQodm9pZCkKewoJcGxhdGZvcm1fZHJpdmVyX3VucmVnaXN0ZXIoJm9tYXAyX21jc3BpX2RyaXZlcik7CgoJZGVzdHJveV93b3JrcXVldWUob21hcDJfbWNzcGlfd3EpOwp9Cm1vZHVsZV9leGl0KG9tYXAyX21jc3BpX2V4aXQpOwoKTU9EVUxFX0xJQ0VOU0UoIkdQTCIpOwo=