LyoKICAgIDw6Y29weXJpZ2h0LUJSQ006MjAxMzpEVUFML0dQTDpzdGFuZGFyZAogICAgCiAgICAgICBDb3B5cmlnaHQgKGMpIDIwMTMgQnJvYWRjb20gQ29ycG9yYXRpb24KICAgICAgIEFsbCBSaWdodHMgUmVzZXJ2ZWQKICAgIAogICAgVW5sZXNzIHlvdSBhbmQgQnJvYWRjb20gZXhlY3V0ZSBhIHNlcGFyYXRlIHdyaXR0ZW4gc29mdHdhcmUgbGljZW5zZQogICAgYWdyZWVtZW50IGdvdmVybmluZyB1c2Ugb2YgdGhpcyBzb2Z0d2FyZSwgdGhpcyBzb2Z0d2FyZSBpcyBsaWNlbnNlZAogICAgdG8geW91IHVuZGVyIHRoZSB0ZXJtcyBvZiB0aGUgR05VIEdlbmVyYWwgUHVibGljIExpY2Vuc2UgdmVyc2lvbiAyCiAgICAodGhlICJHUEwiKSwgYXZhaWxhYmxlIGF0IGh0dHA6Ly93d3cuYnJvYWRjb20uY29tL2xpY2Vuc2VzL0dQTHYyLnBocCwKICAgIHdpdGggdGhlIGZvbGxvd2luZyBhZGRlZCB0byBzdWNoIGxpY2Vuc2U6CiAgICAKICAgICAgIEFzIGEgc3BlY2lhbCBleGNlcHRpb24sIHRoZSBjb3B5cmlnaHQgaG9sZGVycyBvZiB0aGlzIHNvZnR3YXJlIGdpdmUKICAgICAgIHlvdSBwZXJtaXNzaW9uIHRvIGxpbmsgdGhpcyBzb2Z0d2FyZSB3aXRoIGluZGVwZW5kZW50IG1vZHVsZXMsIGFuZAogICAgICAgdG8gY29weSBhbmQgZGlzdHJpYnV0ZSB0aGUgcmVzdWx0aW5nIGV4ZWN1dGFibGUgdW5kZXIgdGVybXMgb2YgeW91cgogICAgICAgY2hvaWNlLCBwcm92aWRlZCB0aGF0IHlvdSBhbHNvIG1lZXQsIGZvciBlYWNoIGxpbmtlZCBpbmRlcGVuZGVudAogICAgICAgbW9kdWxlLCB0aGUgdGVybXMgYW5kIGNvbmRpdGlvbnMgb2YgdGhlIGxpY2Vuc2Ugb2YgdGhhdCBtb2R1bGUuCiAgICAgICBBbiBpbmRlcGVuZGVudCBtb2R1bGUgaXMgYSBtb2R1bGUgd2hpY2ggaXMgbm90IGRlcml2ZWQgZnJvbSB0aGlzCiAgICAgICBzb2Z0d2FyZS4gIFRoZSBzcGVjaWFsIGV4Y2VwdGlvbiBkb2VzIG5vdCBhcHBseSB0byBhbnkgbW9kaWZpY2F0aW9ucwogICAgICAgb2YgdGhlIHNvZnR3YXJlLgogICAgCiAgICBOb3Qgd2l0aHN0YW5kaW5nIHRoZSBhYm92ZSwgdW5kZXIgbm8gY2lyY3Vtc3RhbmNlcyBtYXkgeW91IGNvbWJpbmUKICAgIHRoaXMgc29mdHdhcmUgaW4gYW55IHdheSB3aXRoIGFueSBvdGhlciBCcm9hZGNvbSBzb2Z0d2FyZSBwcm92aWRlZAogICAgdW5kZXIgYSBsaWNlbnNlIG90aGVyIHRoYW4gdGhlIEdQTCwgd2l0aG91dCBCcm9hZGNvbSdzIGV4cHJlc3MgcHJpb3IKICAgIHdyaXR0ZW4gY29uc2VudC4KICAgIAogICAgOj4gCgoqLwoKI2luY2x1ZGUgImJic2kuaCIKI2luY2x1ZGUgPGxpbnV4L29mLmg+CiNpZiBMSU5VWF9WRVJTSU9OX0NPREUgPj0gS0VSTkVMX1ZFUlNJT04oMywxMywwKQojaW5jbHVkZSA8bGludXgvZ3Bpby9jb25zdW1lci5oPgojZW5kaWYKI2luY2x1ZGUgPGxpbnV4L3NwaS9zcGkuaD4KCiNpZiBMSU5VWF9WRVJTSU9OX0NPREUgPj0gS0VSTkVMX1ZFUlNJT04oMiw2LDMwKQojZWxzZQp0eXBlZGVmIHVuc2lnbmVkIGxvbmcgdWludHB0cl90OwojZW5kaWYgLy8gTElOVVhfVkVSU0lPTl9DT0RFID49IEtFUk5FTF9WRVJTSU9OKDIsNiwzMCkKCiNkZWZpbmUgTU9DQV9SRCh4KQkoa2VyU3lzQmNtU3BpU2xhdmVSZWFkUmVnMzIodG9fc3BpX2RldmljZShwcml2LT5tb2NhX2RldiksICh1aW50MzJfdCkoeCkpKQoKI2RlZmluZSBNT0NBX1dSKHgseSkJZG8geyBrZXJTeXNCY21TcGlTbGF2ZVdyaXRlUmVnMzIodG9fc3BpX2RldmljZShwcml2LT5tb2NhX2RldiksICh1aW50MzJfdCkoeCksICh5KSk7IH0gd2hpbGUoMCkKCiNkZWZpbmUgTU9DQV9XUl9CTE9DSyhhZGRyLCBzcmMsIGxlbikgZG8geyBrZXJTeXNCY21TcGlTbGF2ZVdyaXRlQnVmKHRvX3NwaV9kZXZpY2UocHJpdi0+bW9jYV9kZXYpLCBhZGRyLCBzcmMsIGxlbiwgNCk7IH0gd2hpbGUoMCkKI2RlZmluZSBNT0NBX1JEX0JMT0NLKGFkZHIsIGRzdCwgbGVuKSBkbyB7IGtlclN5c0JjbVNwaVNsYXZlUmVhZEJ1Zih0b19zcGlfZGV2aWNlKHByaXYtPm1vY2FfZGV2KSwgYWRkciwgZHN0LCBsZW4sIDQpOyB9IHdoaWxlKDApCgojZGVmaW5lIEkyQ19SRCh4KQkJTU9DQV9SRCh4KQojZGVmaW5lIEkyQ19XUih4LCB5KQkJTU9DQV9XUih4LCB5KQoKI2RlZmluZSBNT0NBX0JQQ01fTlVNICAgICAgICAgNQojZGVmaW5lIE1PQ0FfQlBDTV9aT05FU19OVU0gICA4CgojZGVmaW5lIE1PQ0FfQ1BVX0NMT0NLX05VTSAgMQojZGVmaW5lIE1PQ0FfUEhZX0NMT0NLX05VTSAgMgoKdHlwZWRlZiBlbnVtIF9QTUJfQ09NTUFORF9FXwp7CiAgIFBNQl9DT01NQU5EX1BIWTFfT049MCwKICAgUE1CX0NPTU1BTkRfUEFSVElBTF9PTiwKICAgUE1CX0NPTU1BTkRfUEhZMV9PRkYsCiAgIFBNQl9DT01NQU5EX0FMTF9PRkYsCgogICBQTUJfQ09NTUFORF9MQVNUCn0gUE1CX0NPTU1BTkRfRTsKCnR5cGVkZWYgZW51bSBfUE1CX0dJVkVfT1dORVJTSElQX0VfCnsKICAgUE1CX0dJVkVfT1dORVJTSElQXzJfSE9TVCA9IDAsCiAgIFBNQl9HSVZFX09XTkVSU0hJUF8yX0ZXLAoKICAgUE1CX0dFVF9PV05FUlNISVBfTEFTVAp9IFBNQl9HSVZFX09XTkVSU0hJUF9FOwoKc3RydWN0IG1vY2FfNjgweF9jbGsKewoJc3RydWN0IGRldmljZSAqZGV2OwoJdWludDMyX3QgICAgICAgY2xvY2tfbnVtOwp9OwoKc3RhdGljIHVpbnQzMl90IHpvbmVfYWxsX29mZl9iaXRtYXNrW01PQ0FfQlBDTV9OVU1dID0geyAweEZGLCAweEZGLCAweEZGLCAweEZGLCAweEZGIH07CnN0YXRpYyB1aW50MzJfdCB6b25lX3BhcnRpYWxfb25fYml0bWFza1tNT0NBX0JQQ01fTlVNXSAgPSB7IDB4NDEsIDB4RkMsIDB4RkYsIDB4RkYsIDB4MDAgfTsKc3RhdGljIHVpbnQzMl90IHpvbmVfcGh5MV9iaXRtYXNrW01PQ0FfQlBDTV9OVU1dICA9IHsgMHgwMCwgMHgwMCwgMHgwMCwgMHgwMCwgMHhGRiB9OwoKCi8qIE1vQ0EgQ2xvY2sgRnVuY3Rpb25zICovCnN0cnVjdCBjbGsgKm1vY2FfY2xrX2dldChzdHJ1Y3QgZGV2aWNlICpkZXYsIGNvbnN0IGNoYXIgKmlkKQp7CgkvLyBXZSdyZSBub3QgYWN0dWFsbHkgdXNpbmcgdGhlICJzdHJ1Y3QgY2xrIiBmb3IgYW55dGhpbmcKCS8vIFdlJ2xsIHVzZSBvdXIgb3duIHN0cnVjdHVyZQoJc3RydWN0IG1vY2FfNjgweF9jbGsgKiBwY2xrID0ga3phbGxvYyhzaXplb2Yoc3RydWN0IG1vY2FfNjgweF9jbGspLCBHRlBfS0VSTkVMKTsKCglwY2xrLT5kZXYgPSBkZXY7CgoJaWYgKCFzdHJjbXAoaWQsICJtb2NhLWNwdSIpKQoJCXBjbGstPmNsb2NrX251bSA9IE1PQ0FfQ1BVX0NMT0NLX05VTTsKCWVsc2UgaWYgKCFzdHJjbXAoaWQsICJtb2NhLXBoeSIpKQoJCXBjbGstPmNsb2NrX251bSA9IE1PQ0FfUEhZX0NMT0NLX05VTTsKCWVsc2UKCXsKCQlrZnJlZShwY2xrKTsKCQlyZXR1cm4oTlVMTCk7Cgl9CgoJcmV0dXJuKChzdHJ1Y3QgY2xrICopcGNsayk7Cn0KCmludCBtb2NhX2Nsa19lbmFibGUoc3RydWN0IGNsayAqY2xrKQp7CglyZXR1cm4gMDsKfQoKdm9pZCBtb2NhX2Nsa19kaXNhYmxlKHN0cnVjdCBjbGsgKmNsaykKewp9Cgp2b2lkIG1vY2FfY2xrX3B1dChzdHJ1Y3QgY2xrICpjbGspCnsKCWtmcmVlKChzdHJ1Y3QgbW9jYV82ODB4X2NsayAqKWNsayk7Cn0KCnN0cnVjdCBtb2NhXzY4MDJjMF9jbG9ja19wYXJhbXMKewoJdWludDMyX3QgICAgICAgIGNwdV9oejsKCXVpbnQzMl90ICAgICAgICBwZGl2OwoJdWludDMyX3QgICAgICAgIG5kaXY7Cgl1aW50MzJfdCAgICAgICAgcGxsX21kaXZzWzZdOwp9OwoKI2RlZmluZSBOVU1fNjgwMkMwX0NMT0NLX09QVElPTlMgMgpzdHJ1Y3QgbW9jYV82ODAyYzBfY2xvY2tfcGFyYW1zIG1vY2FfNjgwMmMwX2Nsb2NrX3BhcmFtc1tOVU1fNjgwMkMwX0NMT0NLX09QVElPTlNdID0KewoJeyAgLy8gVkNPIG9mIDIyMDAsIGRlZmF1bHQKCQk0NDAwMDAwMDAsICAgICAgICAgICAgIC8vIGNwdV9oegoJCTEsICAgICAgICAgICAgICAgICAgICAgLy8gcGRpdgoJCTQ0LCAgICAgICAgICAgICAgICAgICAgLy8gbmRpdgoJCXs1LCAyMiwgNywgNywgNDQsIDQ0fSAgLy8gcGxsX21kaXZzWzZdCgl9LAoJeyAgLy8gVkNPIG9mIDI0MDAKCQk0MDAwMDAwMDAsICAgICAgICAgICAgIC8vIGNwdV9oegoJCTEsICAgICAgICAgICAgICAgICAgICAgLy8gcGRpdgoJCTQ4LCAgICAgICAgICAgICAgICAgICAgLy8gbmRpdgoJCXs2LCAyNCwgOCwgOCwgNDgsIDQ4fSAgLy8gcGxsX21kaXZzWzZdCgl9LAp9OwoKaW50IG1vY2FfY2xrX3NldF9yYXRlKHN0cnVjdCBjbGsgKmNsaywgdW5zaWduZWQgbG9uZyByYXRlKQp7CglzdHJ1Y3QgbW9jYV82ODB4X2NsayAqIHBjbGsgPSAoc3RydWN0IG1vY2FfNjgweF9jbGsgKikgY2xrOwoJc3RydWN0IG1vY2FfcHJpdl9kYXRhICpwcml2ID0gZGV2X2dldF9kcnZkYXRhKHBjbGstPmRldik7CglzdHJ1Y3QgbW9jYV82ODAyYzBfY2xvY2tfcGFyYW1zICogcF9jbG9ja19kYXRhID0gJm1vY2FfNjgwMmMwX2Nsb2NrX3BhcmFtc1swXTsKCXVpbnQzMl90IGk7Cgl1aW50MzJfdCBhZGRyOwoJdWludDMyX3QgZGF0YTsKCWludCByZXQgPSAtMTsKCglpZiAocGNsay0+Y2xvY2tfbnVtID09IE1PQ0FfQ1BVX0NMT0NLX05VTSkKCXsKCQlpZiAoKHByaXYtPmNoaXBfaWQgJiAweEZGRkZGRkYwKSA9PSAweDY4MDIwMEMwKQoJCXsKCQkJaWYgKHJhdGUgPT0gMCkKCQkJewoJCQkJcmF0ZSA9IDQ0MDAwMDAwMDsKCQkJfQoJCQkKCQkJZm9yIChpID0gMDsgaSA8IE5VTV82ODAyQzBfQ0xPQ0tfT1BUSU9OUzsgaSsrKQoJCQl7CgkJCQlpZiAobW9jYV82ODAyYzBfY2xvY2tfcGFyYW1zW2ldLmNwdV9oeiA9PSByYXRlKQoJCQkJewoJCQkJCXBfY2xvY2tfZGF0YSA9ICZtb2NhXzY4MDJjMF9jbG9ja19wYXJhbXNbaV07CgkJCQkJcmV0ID0gMDsKCQkJCX0KCQkJfQoKCQkJLy8gMS4gU2V0IFBPU1RfRElWSURFUl9IT0xEX0NIeCAoYml0IFsxMl0gaW4gZWFjaCBQTExfQ0hBTk5FTF9DVFJMX0NIX3ggCgkJCS8vICAgIHJlZ2lzdGVyKSAgLy8gdGhpcyB3aWxsIHplcm8gdGhlIG91dHB1dCBjaGFubmVscwoJCQlmb3IgKGFkZHIgPSAweDEwMTAwMDNjOyBhZGRyIDw9IDB4MTAxMDAwNTA7IGFkZHIgKz0gNCkKCQkJewoJCQkJTU9DQV9TRVQoYWRkciwgKDEgPDwgMTIpKTsKCQkJfQoKCQkJLy8yLiBQcm9ncmFtIG5ldyBQRElWL05ESVYgdmFsdWUsIHRoaXMgd2lsbCBsb3NlIGxvY2sgYW5kIAoJCQkvLyAgIHRyaWdnZXIgYSBuZXcgUExMIGxvY2sgcHJvY2VzcyBmb3IgYSBuZXcgVkNPIGZyZXF1ZW5jeQoJCQlNT0NBX1dSKDB4MTAxMDAwNTgsICgocF9jbG9ja19kYXRhLT5wZGl2IDw8IDEwKSB8IHBfY2xvY2tfZGF0YS0+bmRpdikpOwoKCQkJLy8zLiBXYWl0ID4xMCB1c2VjIGZvciBsb2NrIHRpbWUgLy8gbWF4IGxvY2sgdGltZSBwZXIgZGF0YSBzaGVldCBpcyA0NjAvRnJlZiwgCgkJCS8vICAgT3IgYWx0ZXJuYXRpdmVseSBtb25pdG9yIENMS0dFTl9QTExfU1lTKl9QTExfTE9DS19TVEFUVVMgdG8gY2hlY2sgaWYgUExMIGhhcyBsb2NrZWQKCQkJZGF0YSA9IDA7CgkJCWkgPSAwOwoJCQl3aGlsZSAoKGRhdGEgJiAweDEpID09IDApCgkJCXsKCQkJCS8qIFRoaXMgdHlwaWNhbGx5IGlzIG9ubHkgcmVhZCBvbmNlICovCgkJCQlkYXRhID0gTU9DQV9SRCgweDEwMTAwMDYwKTsgLy8gQ0xLR0VOX1BMTF9TWVMxX1BMTF9MT0NLX1NUQVRVUwoKCQkJCWlmIChpKysgPiAxMCkKCQkJCXsKCQkJCQlwcmludGsoIk1vQ0EgU1lTMSBQTEwgTk9UIExPQ0tFRCFcbiIpOwoJCQkJCWJyZWFrOwoJCQkJfQoJCQl9CgoJCQkvLzQuIENvbmZpZ3VyZSBuZXcgTURJViB2YWx1ZSBhbG9uZyB3aXRoIHNldCBQT1NUX0RJVklERVJfTE9BRF9FTl9DSHggCgkJCS8vICAgKGJpdCBbMTNdPTEsIHdoaWxlIGtlZXAgYml0WzEyXT0xKSBpbiBlYWNoIFBMTF9DSEFOTkVMX0NUUkxfQ0hfeCByZWdpc3RlcgoJCQlpID0gMDsKCQkJZm9yIChhZGRyID0gMHgxMDEwMDAzYzsgYWRkciA8PSAweDEwMTAwMDUwOyBhZGRyICs9IDQpCgkJCXsKCQkJCWRhdGEgPSBNT0NBX1JEKGFkZHIpOwoJCQkJZGF0YSB8PSAoMSA8PCAxMyk7CgkJCQlkYXRhICY9IH4oMHhGRiA8PCAxKTsKCQkJCWRhdGEgfD0gKHBfY2xvY2tfZGF0YS0+cGxsX21kaXZzW2ldIDw8IDEpOwoJCQkJTU9DQV9XUihhZGRyLCBkYXRhKTsKCQkJCWkrKzsKCQkJfQoKCQkJLy81LiBDbGVhciBiaXRzIFsxMl0gYW5kIGJpdCBbMTNdIGluIGVhY2ggUExMX0NIQU5ORUxfQ1RSTF9DSF94CgkJCWZvciAoYWRkciA9IDB4MTAxMDAwM2M7IGFkZHIgPD0gMHgxMDEwMDA1MDsgYWRkciArPSA0KQoJCQl7CgkJCQlNT0NBX1VOU0VUKGFkZHIsICgoMSA8PCAxMykgfCAoMSA8PCAxMikpKTsKCQkJfQoKCQl9Cgl9CgoJcmV0dXJuKHJldCk7Cn0KCnN0YXRpYyB2b2lkIG1vY2FfZW5hYmxlX2lycShzdHJ1Y3QgbW9jYV9wcml2X2RhdGEgKnByaXYpCnsKCWtlclN5c01vY2FIb3N0SW50ckVuYWJsZSh0b19zcGlfZGV2aWNlKHByaXYtPm1vY2FfZGV2KSk7Cn0KCnN0YXRpYyB2b2lkIG1vY2FfZGlzYWJsZV9pcnEoc3RydWN0IG1vY2FfcHJpdl9kYXRhICpwcml2KQp7CglrZXJTeXNNb2NhSG9zdEludHJEaXNhYmxlKHRvX3NwaV9kZXZpY2UocHJpdi0+bW9jYV9kZXYpKTsKfQoKc3RhdGljIHZvaWQgbW9jYV9wbWJfYnVzeV93YWl0KHN0cnVjdCBtb2NhX3ByaXZfZGF0YSAqcHJpdikKewoJI2lmIDAKCXVpbnQzMl90IGRhdGE7CgoJLyogUG9zc2libGUgdGltZSBzYXZlcjogVGhlIHJlZ2lzdGVyIGFjY2VzcyB0aW1lIG92ZXIgU1BJIG1heSAKCSAgIGFsd2F5cyBiZSBlbm91Z2ggdG8gZ3VhcmFudGVlIHRoYXQgdGhlIHdyaXRlIHdpbGwgY29tcGxldGUgCgkgICBpbiB0aW1lIHdpdGhvdXQgaGF2aW5nIHRvIGNoZWNrIHRoZSBzdGF0dXMuICovCglkbwoJewoJCWRhdGEgPSBNT0NBX1JEKHByaXYtPmJhc2UgKyBwcml2LT5yZWdzLT5wbWJfbWFzdGVyX3N0YXR1cyk7Cgl9IHdoaWxlIChkYXRhICYgMHgxKTsKCSNlbmRpZgp9Cgp2b2lkIG1vY2FfcG1iX2RlbGF5KHN0cnVjdCBtb2NhX3ByaXZfZGF0YSAqcHJpdikKewoJdW5zaWduZWQgaW50IGRhdGE7CglpbnQgaSwgajsKCQoJTU9DQV9XUihwcml2LT5iYXNlICsgcHJpdi0+cmVncy0+cG1iX21hc3Rlcl93ZGF0YV9vZmZzZXQsIDB4RkY0NDQwMDApOwoJCglmb3IgKGkgPSAwOyBpIDwgTU9DQV9CUENNX05VTTsgaSsrKQoJewoJCWZvciAoaiA9IDA7IGogPCBNT0NBX0JQQ01fWk9ORVNfTlVNOyBqKyspCgkJewoJCQlkYXRhID0gMHgxMDAwMTIgKyBqKjQgKyBpKjB4MTAwMDsgOwoJCQlNT0NBX1dSKHByaXYtPmJhc2UgKyBwcml2LT5yZWdzLT5wbWJfbWFzdGVyX2NtZF9vZmZzZXQsIGRhdGEpOwoJCQltb2NhX3BtYl9idXN5X3dhaXQocHJpdik7CgkJfQoJfQp9CgpzdGF0aWMgdm9pZCBtb2NhX3BtYl9jb250cm9sKHN0cnVjdCBtb2NhX3ByaXZfZGF0YSAqcHJpdiwgUE1CX0NPTU1BTkRfRSBjbWQpCnsKCWludCBpLCBqOwoJdWludDMyX3QgKiBwX3pvbmVfY29udHJvbDsKCXVpbnQzMl90IGRhdGE7CgoJc3dpdGNoIChjbWQpCgl7CgkJY2FzZSBQTUJfQ09NTUFORF9BTExfT0ZGOgoJCQkvLyBUdXJuIG9mZiB6b25lIGNvbW1hbmQKCQkJTU9DQV9XUihwcml2LT5iYXNlICsgcHJpdi0+cmVncy0+cG1iX21hc3Rlcl93ZGF0YV9vZmZzZXQsIDB4QTAwKTsKCQkJcF96b25lX2NvbnRyb2wgPSAmem9uZV9hbGxfb2ZmX2JpdG1hc2tbMF07CgkJCWJyZWFrOwoKCQljYXNlIFBNQl9DT01NQU5EX1BIWTFfT0ZGOgoJCQkvLyBUdXJuIG9mZiB6b25lIGNvbW1hbmQKCQkJTU9DQV9XUihwcml2LT5iYXNlICsgcHJpdi0+cmVncy0+cG1iX21hc3Rlcl93ZGF0YV9vZmZzZXQsIDB4QTAwKTsKCQkJcF96b25lX2NvbnRyb2wgPSAmem9uZV9waHkxX2JpdG1hc2tbMF07CgkJCWJyZWFrOwoJCSAKCSBjYXNlIFBNQl9DT01NQU5EX1BIWTFfT046CgkJCS8vIFR1cm4gb24gem9uZSBjb21tYW5kCgkJCU1PQ0FfV1IocHJpdi0+YmFzZSArIHByaXYtPnJlZ3MtPnBtYl9tYXN0ZXJfd2RhdGFfb2Zmc2V0LCAweEMwMCk7CgkJCXBfem9uZV9jb250cm9sID0gJnpvbmVfcGh5MV9iaXRtYXNrWzBdOwoJCQlicmVhazsKCQkgCgkgY2FzZSBQTUJfQ09NTUFORF9QQVJUSUFMX09OOgoJCQkvLyBUdXJuIG9uIHpvbmUgY29tbWFuZAoJCQlNT0NBX1dSKHByaXYtPmJhc2UgKyBwcml2LT5yZWdzLT5wbWJfbWFzdGVyX3dkYXRhX29mZnNldCwgMHhDMDApOwoJCQlwX3pvbmVfY29udHJvbCA9ICZ6b25lX3BhcnRpYWxfb25fYml0bWFza1swXTsKCQkJYnJlYWs7CgkJIAoJCSAKCQlkZWZhdWx0OgoJCQlwcmludGsoS0VSTl9XQVJOSU5HICIlczogaWxsZWdhbCBjbWQ6ICUwOHhcbiIsCgkJCQlfX0ZVTkNUSU9OX18sIGNtZCk7CgkJCXJldHVybjsKCX0KCglmb3IgKGkgPSAwOyBpIDwgTU9DQV9CUENNX05VTTsgaSsrKQoJewoJCWZvciAoaiA9IDA7IGogPCBNT0NBX0JQQ01fWk9ORVNfTlVNOyBqKyspCgkJewoJCQlpZiAoKnBfem9uZV9jb250cm9sICYgKDEgPDwgaikpCgkJCXsKCQkJCS8vIHpvbmUgYWRkcmVzcyBpbiBicGNtcwoJCQkJZGF0YSA9ICgweDEgPDwgMjApICsgMTYgKyAoaSAqIDQwOTYpICsgKGogKiA0KTsKCQkJCU1PQ0FfV1IocHJpdi0+YmFzZSArIHByaXYtPnJlZ3MtPnBtYl9tYXN0ZXJfY21kX29mZnNldCwgZGF0YSk7CgkJCQltb2NhX3BtYl9idXN5X3dhaXQocHJpdik7CgkJCX0KCQl9CgkJcF96b25lX2NvbnRyb2wrKzsKCX0KCn0KCnN0YXRpYyB2b2lkIG1vY2FfcG1iX2dpdmVfY250cmwoc3RydWN0IG1vY2FfcHJpdl9kYXRhICpwcml2LCBQTUJfR0lWRV9PV05FUlNISVBfRSBjbWQpCnsKCWludCBpOwoJdWludDMyX3QgZGF0YTsKCgkvKiBQYXNzIGNvbnRyb2wgb3ZlciB0aGUgbWVtb3JpZXMgdG8gdGhlIEZXICovCglNT0NBX1dSKHByaXYtPmJhc2UgKyBwcml2LT5yZWdzLT5wbWJfbWFzdGVyX3dkYXRhX29mZnNldCwgY21kKTsKCWZvciAoaSA9IDA7IGkgPCAzOyBpKyspCgl7CgkJZGF0YSA9IDB4MTAwMDAyICsgaSoweDEwMDA7CgkJTU9DQV9XUihwcml2LT5iYXNlICsgcHJpdi0+cmVncy0+cG1iX21hc3Rlcl9jbWRfb2Zmc2V0LCBkYXRhKTsgICAKCQltb2NhX3BtYl9idXN5X3dhaXQocHJpdik7Cgl9Cgltb2NhX3BtYl9idXN5X3dhaXQocHJpdik7Cn0KCnN0YXRpYyB2b2lkIG1vY2FfaHdfcmVzZXQoc3RydWN0IG1vY2FfcHJpdl9kYXRhICpwcml2KQp7Ci8vCXVuc2lnbmVkIGxvbmcgZmxhZ3M7Ci8vICAgdWludDMyX3QgY2hpcGlkOwogIAoKCS8qIGRpc2FibGUgYW5kIGNsZWFyIGFsbCBpbnRlcnJ1cHRzICovCglNT0NBX1dSKHByaXYtPmJhc2UgKyBwcml2LT5yZWdzLT5sMl9tYXNrX3NldF9vZmZzZXQsIDB4ZmZmZmZmZmYpOwoJTU9DQV9SRChwcml2LT5iYXNlICsgcHJpdi0+cmVncy0+bDJfbWFza19zZXRfb2Zmc2V0KTsKCgkvKiBhc3NlcnQgcmVzZXRzICovCgoJLyogcmVzZXQgQ1BVIGZpcnN0LCBib3RoIENQVXMgZm9yIE1vQ0EgMjAgSFcgKi8KCWlmIChwcml2LT5od19yZXYgPT0gSFdSRVZfTU9DQV8yMF9HRU4yMikKCQlNT0NBX1NFVChwcml2LT5iYXNlICsgcHJpdi0+cmVncy0+c3dfcmVzZXRfb2Zmc2V0LCA1KTsKCWVsc2UKCQlNT0NBX1NFVChwcml2LT5iYXNlICsgcHJpdi0+cmVncy0+c3dfcmVzZXRfb2Zmc2V0LCAxKTsKCglNT0NBX1JEKHByaXYtPmJhc2UgKyBwcml2LT5yZWdzLT5zd19yZXNldF9vZmZzZXQpOwoKCXVkZWxheSgyMCk7CgoJLyogcmVzZXQgZXZlcnl0aGluZyBlbHNlIGV4Y2VwdCBjbG9ja3MgKi8KCU1PQ0FfU0VUKHByaXYtPmJhc2UgKyBwcml2LT5yZWdzLT5zd19yZXNldF9vZmZzZXQsIAoJCX4oKDEgPDwgMykgfCAoMSA8PCA3KSB8ICgxIDw8IDE1KSB8ICgxIDw8IDE2KSkpOwoJTU9DQV9SRChwcml2LT5iYXNlICsgcHJpdi0+cmVncy0+c3dfcmVzZXRfb2Zmc2V0KTsKCgl1ZGVsYXkoMjApOwoKCS8qIGRpc2FibGUgY2xvY2tzICovCglNT0NBX1NFVChwcml2LT5iYXNlICsgcHJpdi0+cmVncy0+c3dfcmVzZXRfb2Zmc2V0LCAKCQl+KCgxIDw8IDMpIHwgKDEgPDwgMTUpIHwgKDEgPDwgMTYpKSk7CglNT0NBX1JEKHByaXYtPmJhc2UgKyBwcml2LT5yZWdzLT5zd19yZXNldF9vZmZzZXQpOwoKCU1PQ0FfV1IocHJpdi0+YmFzZSArIHByaXYtPnJlZ3MtPmwyX2NsZWFyX29mZnNldCwgMHhmZmZmZmZmZik7CglNT0NBX1JEKHByaXYtPmJhc2UgKyBwcml2LT5yZWdzLT5sMl9jbGVhcl9vZmZzZXQpOwoKCS8qIFBvd2VyIGRvd24gYWxsIHpvbmVzICovCgkvLyAgVGhlIGhvc3QgY2FuJ3QgZ2l2ZSB0byBpdHNlbGYgcGVybWlzc2lvbi4KCW1vY2FfcG1iX2NvbnRyb2wocHJpdiwgUE1CX0NPTU1BTkRfQUxMX09GRik7CgoJLyogUG93ZXIgZG93biBhbGwgU1lTX0NUUkwgbWVtb3JpZXMgKi8KCU1PQ0FfV1IoMHgxMDEwMDA2OCwgMSk7ICAgLy8gQ0xLR0VOX1BMTF9TWVMxX1BMTF9QV1JETgoJTU9DQV9TRVQoMHgxMDEwMDAwYywgMSk7ICAvLyBDTEtHRU5fUExMX1NZUzBfUExMX0NIQU5ORUxfQ1RSTF9DSF8zCgp9CgpzdGF0aWMgdW5zaWduZWQgaW50IG1vY2FfZ2V0X3BoeV9mcmVxKHN0cnVjdCBtb2NhX3ByaXZfZGF0YSAqcHJpdikKewoJdW5zaWduZWQgaW50IHggPSBNT0NBX1JEKDB4MTAxMDAwNDQpOyAvLyBDTEtHRU5fUExMX1NZUzFfUExMX0NIQU5ORUxfQ1RSTF9DSF8yCgoJeCA9ICh4ID4+IDEpICYgMHhGRjsgLy8gR2V0IHRoZSBNRElWX0NIMiBmaWVsZAoKCWlmICgheCkKCQlyZXR1cm4gMDsKCglyZXR1cm4oMjQwMCAvIHgpOyAKfQoKCnN0YXRpYyB2b2lkIG1vY2FfcHNfUG93ZXJDdHJsUEhZMShzdHJ1Y3QgbW9jYV9wcml2X2RhdGEgKnByaXYsICBQTUJfQ09NTUFORF9FIGNtZCkKewoJdWludDMyX3QgcGxsX2N0cmxfMywgcGxsX2N0cmxfNSwgc3dfcmVzZXQ7IAoJcGxsX2N0cmxfMyA9IE1PQ0FfUkQgKDB4MTAxMDAwNDgpOwoJcGxsX2N0cmxfNSA9IE1PQ0FfUkQgKDB4MTAxMDAwNTApOwoJc3dfcmVzZXQgPSBNT0NBX1JEIChwcml2LT5iYXNlICsgcHJpdi0+cmVncy0+c3dfcmVzZXRfb2Zmc2V0KTsKCgkvLyBlbmFibGUgUExMIAoJTU9DQV9VTlNFVCgweDEwMTAwMDQ4LCAxKTsgIC8vIENMS0dFTl9QTExfU1lTMV9QTExfQ0hBTk5FTF9DVFJMX0NIXzMgCglNT0NBX1VOU0VUKDB4MTAxMDAwNTAsIDEpOyAgLy8gQ0xLR0VOX1BMTF9TWVMxX1BMTF9DSEFOTkVMX0NUUkxfQ0hfNSAKCgl1ZGVsYXkoMSk7CgoJLy8gZGUgYXNzZXJ0IG1vY2FfcGh5MV9kaXNhYmxlX2NsawoJTU9DQV9VTlNFVChwcml2LT5iYXNlICsgcHJpdi0+cmVncy0+c3dfcmVzZXRfb2Zmc2V0LCAoMSA8PCA5KSk7CgoJbW9jYV9wbWJfY29udHJvbChwcml2LCBjbWQpOwoKCU1PQ0FfV1IgKDB4MTAxMDAwNDgsIHBsbF9jdHJsXzMpOwoJTU9DQV9XUiAoMHgxMDEwMDA1MCwgcGxsX2N0cmxfNSk7CgoJdWRlbGF5KDEpOwoJCglNT0NBX1dSIChwcml2LT5iYXNlICsgcHJpdi0+cmVncy0+c3dfcmVzZXRfb2Zmc2V0LCBzd19yZXNldCk7CQp9CgoKc3RhdGljIHZvaWQgbW9jYV9ncGh5X2luaXQoc3RydWN0IG1vY2FfcHJpdl9kYXRhICpwcml2KQp7Cgl1MzIgcG9ydF9tb2RlOwoJdTMyIHJnbWlpMF9vbjsKCXUzMiByZ21paTFfb247Cgl1MzIgZ3BoeV9lbmFibGVkID0gMDsKCglwb3J0X21vZGUgPSBNT0NBX1JEKDB4MTA4MDAwMDApICYgMHgzOwoJcmdtaWkwX29uID0gTU9DQV9SRCgweDEwODAwMDBjKSAmIDB4MTsKCXJnbWlpMV9vbiA9IE1PQ0FfUkQoMHgxMDgwMDAxOCkgJiAweDE7CgoJaWYgKChwcml2LT5jaGlwX2lkICYgMHhGRkZFRkZGMCkgPT0gMHg2ODAyMDBDMCkKCXsKCQlpZiAoKHBvcnRfbW9kZSA9PSAwKSB8fAoJCSAgICAoKHBvcnRfbW9kZSA9PSAxKSAmJiByZ21paTBfb24pIHx8CgkJICAgICgocG9ydF9tb2RlID09IDIpICYmIHJnbWlpMV9vbikpCgkJewoJCQlncGh5X2VuYWJsZWQgPSAxOwoJCX0KCX0KCWVsc2UKCXsKCQlpZiAoKHBvcnRfbW9kZSA9PSAwKSB8fAoJCSAgICAoKHBvcnRfbW9kZSAhPSAzKSAmJiByZ21paTFfb24pKQoJCXsKCQkJZ3BoeV9lbmFibGVkID0gMTsKCQl9Cgl9CgoJaWYgKGdwaHlfZW5hYmxlZCkKCXsKCQlNT0NBX1VOU0VUKDB4MTA4MDAwMDQsIDB4Rik7CgkJbXNsZWVwKDEwKTsKCQlNT0NBX1dSKDB4MTA0MDQzMWMsIDB4RkZGRkZGRkYpOwoJfQp9CgovKiBjYWxsZWQgYW55IHRpbWUgd2Ugc3RhcnQvcmVzdGFydC9zdG9wIE1vQ0EgKi8Kc3RhdGljIHZvaWQgbW9jYV9od19pbml0KHN0cnVjdCBtb2NhX3ByaXZfZGF0YSAqcHJpdiwgaW50IGFjdGlvbikKewoJdTMyIG1hc2s7Cgl1MzIgdGVtcDsKCXUzMiBkYXRhOwoJdTMyIGNvdW50ID0gMDsKCglpZiAoYWN0aW9uID09IE1PQ0FfRU5BQkxFICYmICFwcml2LT5lbmFibGVkKSB7CgkJbW9jYV9jbGtfZW5hYmxlKHByaXYtPmNsayk7CgoJCU1PQ0FfV1IoMHgxMDQwNDMxYywgfigxIDw8IDI2KSk7IC8vIFNVTl9UT1BfQ1RSTF9TV19JTklUXzBfQ0xFQVIgLS0+IERvIHRoaXMgYXQgc3RhcnQgb2Ygc2VxdWVuY2UsIGRvbid0IHRvdWNoIGdwaHlfc3dfaW5pdAoJCXVkZWxheSgyMCk7CgkJbW9jYV9ncGh5X2luaXQocHJpdik7CiAgIAoJCXByaXYtPmVuYWJsZWQgPSAxOwoJfQoKCS8qIGNsb2NrIG5vdCBlbmFibGVkLCByZWdpc3RlciBhY2Nlc3NlcyB3aWxsIGZhaWwgd2l0aCBidXMgZXJyb3IgKi8KCWlmICghcHJpdi0+ZW5hYmxlZCkKCQlyZXR1cm47CgoJbW9jYV9od19yZXNldChwcml2KTsKCXVkZWxheSgxKTsKCglpZiAoYWN0aW9uID09IE1PQ0FfRU5BQkxFKSB7CgoJCS8qIFBvd2VyIHVwIGFsbCB6b25lcyAqLwoJCW1vY2FfcG1iX2NvbnRyb2wocHJpdiwgUE1CX0NPTU1BTkRfUEFSVElBTF9PTik7CgoJCU1PQ0FfVU5TRVQoMHgxMDEwMDAwYywgMSk7ICAvLyBDTEtHRU5fUExMX1NZUzBfUExMX0NIQU5ORUxfQ1RSTF9DSF8zIAoKCQlNT0NBX1dSKDB4MTAxMDAwNkMsIDEpOyAgLy8gQ0xLR0VOX1BMTF9TWVMxX1BMTF9SRVNFVCAKCQlNT0NBX1dSKDB4MTAxMDAwNjgsIDApOyAgLy8gQ0xLR0VOX1BMTF9TWVMxX1BMTF9QV1JETiAKCQlkYXRhID0gMDsKCQl3aGlsZSAoKGRhdGEgJiAweDEpID09IDApCgkJewoJCQkvKiBUaGlzIHR5cGljYWxseSBpcyBvbmx5IHJlYWQgb25jZSAqLwoJCQlkYXRhID0gTU9DQV9SRCgweDEwMTAwMDYwKTsgLy8gQ0xLR0VOX1BMTF9TWVMxX1BMTF9MT0NLX1NUQVRVUwoKCQkJaWYgKGNvdW50KysgPiAxMCkKCQkJCWJyZWFrOwoJCX0KCQlNT0NBX1dSKDB4MTAxMDAwNkMsIDApOyAgLy8gQ0xLR0VOX1BMTF9TWVMxX1BMTF9SRVNFVCAKCgkJaWYgKHByaXYtPmJvbmRlZF9tb2RlKSB7CgkJCU1PQ0FfVU5TRVQoMHgxMDEwMDA0OCwgMSk7ICAvLyBDTEtHRU5fUExMX1NZUzFfUExMX0NIQU5ORUxfQ1RSTF9DSF8zIAoJCQlNT0NBX1VOU0VUKDB4MTAxMDAwNTAsIDEpOyAgLy8gQ0xLR0VOX1BMTF9TWVMxX1BMTF9DSEFOTkVMX0NUUkxfQ0hfNSAKCQl9IGVsc2UgewoJCQlNT0NBX1NFVCgweDEwMTAwMDQ4LCAxKTsgIC8vIENMS0dFTl9QTExfU1lTMV9QTExfQ0hBTk5FTF9DVFJMX0NIXzMgCgkJCU1PQ0FfU0VUKDB4MTAxMDAwNTAsIDEpOyAgLy8gQ0xLR0VOX1BMTF9TWVMxX1BMTF9DSEFOTkVMX0NUUkxfQ0hfNSAKCQl9CgkJdWRlbGF5KDEpOwoKCQkvKiBkZWFzc2VydCBtb2NhX3N5c19yZXNldCwgc3lzdGVtIGNsb2NrLCBwaHkwLCBwaHkwIGNsb2NrICovCgkJbWFzayA9ICgxIDw8IDEpIHwgKDEgPDwgNykgfCAoMSA8PCA0KSB8ICgxIDw8IDgpOwoKCQkvKiBkZWFzc2VydCBwaHkxIGFuZCBwaHkxIGNsb2NrIGluIGJvbmRlZCBtb2RlICovCgkJaWYgKHByaXYtPmJvbmRlZF9tb2RlKQoJCQltYXNrIHw9ICgxIDw8IDUpIHwgKDEgPDwgOSk7CgoJCU1PQ0FfVU5TRVQocHJpdi0+YmFzZSArIHByaXYtPnJlZ3MtPnN3X3Jlc2V0X29mZnNldCwgbWFzayk7CgkJTU9DQV9SRChwcml2LT5iYXNlICsgcHJpdi0+cmVncy0+c3dfcmVzZXRfb2Zmc2V0KTsKCQkKICAgICAgICAvLyBCZWZvcmUgcG93ZXIgb2ZmIHRoZSBtZW1vcmllcywgbW9jYV9waHkxX2Rpc2FibGVfY2xrLiAgICAKCQlpZiAocHJpdi0+Ym9uZGVkX21vZGU9PTApCgkJCW1vY2FfcHNfUG93ZXJDdHJsUEhZMShwcml2LCBQTUJfQ09NTUFORF9QSFkxX09GRik7CgkJZWxzZQoJCQltb2NhX3BzX1Bvd2VyQ3RybFBIWTEocHJpdiwgUE1CX0NPTU1BTkRfUEhZMV9PTik7CgogICAgICAgIAoJCW1vY2FfcG1iX2dpdmVfY250cmwocHJpdiwgUE1CX0dJVkVfT1dORVJTSElQXzJfRlcpOwoJCQkKCQkvKiBDaGVjayBmb3IgNjgwMi82ODAzIEEwIGNoaXAgb25seSB3aXRoIFh0YWwgbW9kICovCgkJaWYgKChwcml2LT5jaGlwX2lkICYgMHhGRkZFRkZGRikgPT0gMHg2ODAyMDBBMCkKCQl7CgkJCWRhdGEgPSBNT0NBX1JEKDB4MTA0MDQwMWMpOwoJCQlpZiAoKGRhdGEgJiAweDcpID09IDB4MikgewoJCQkJLyogMjVNSHogKi8KCQkJCXByaW50aygiTW9DQSBydW5uaW5nIHdpdGggMjVNSHogWFRBTFxuIik7CgkJCQlNT0NBX1dSKHByaXYtPmJhc2UgKyBwcml2LT5yZWdzLT5ob3N0Mm1vY2FfbW1wX291dGJveF8wX29mZnNldCwgMSk7CgkJCX0gZWxzZSB7CgkJCQlwcmludGsoIk1vQ0EgPT0gNTBNSHogWFRBTFxuIik7CgkJCQkvKiA1ME1IeiBjbG9jayBjaGFuZ2Ugb25seSAqLwoJCQkJTU9DQV9XUihwcml2LT5iYXNlICsgcHJpdi0+cmVncy0+aG9zdDJtb2NhX21tcF9vdXRib3hfMF9vZmZzZXQsIDApOwoJCQkJLy9Ob3RlOiBUaGUgcmUtY29uZmlndXJhdGlvbiBpcyBpbiBORElWX0lOVCwgbm90IFBESVYuCgkJCQkvL2BDTEtHRU5fUkVHX1NUQVJUICsgYENMS0dFTl9QTExfU1lTMV9QTExfRElWICgzMidoMTAxMDAwNTgpIFswOTowMF0gPSAxMJJkNDgKCQkJCXRlbXAgPSBNT0NBX1JEKDB4MTAxMDAwNTgpOwoJCQkJdGVtcCA9ICh0ZW1wICYgMHhGRkZGRkMwMCkgKyA0ODsKCQkJCU1PQ0FfV1IoMHgxMDEwMDA1OCwgdGVtcCk7CgoJCQkJLy9gQ0xLR0VOX1JFR19TVEFSVCArIGBDTEtHRU5fUExMX1NZUzBfUExMX0RJViAoMzInaDEwMTAwMDE4KSBbMDk6MDBdID0gMTCSZDQwCgkJCQl0ZW1wID0gTU9DQV9SRCgweDEwMTAwMDE4KTsKCQkJCXRlbXAgPSAodGVtcCAmIDB4RkZGRkZDMDApICsgNDA7CgkJCQlNT0NBX1dSKDB4MTAxMDAwMTgsIHRlbXApOwoKCQkJCS8vYENMS0dFTl9SRUdfU1RBUlQgKyBgQ0xLR0VOX1BMTF9TWVMxX1BMTF9DSEFOTkVMX0NUUkxfQ0hfNCAoMzInaDEwMTAwMDRDKSBbMDg6MDFdID0gOJJkNDgKCQkJCXRlbXAgPSBNT0NBX1JEKDB4MTAxMDAwNGMpOwoJCQkJdGVtcCA9ICh0ZW1wICYgMHhGRkZGRkUwMSkgKyAoNDggPDwgMSk7CgkJCQlNT0NBX1dSKDB4MTAxMDAwNGMsIHRlbXApOwoKCQkJCS8vYENMS0dFTl9SRUdfU1RBUlQgKyBgQ0xLR0VOX1BMTF9TWVMxX1BMTF9DSEFOTkVMX0NUUkxfQ0hfNSAoMzInaDEwMTAwMDUwKSBbMDg6MDFdID0gOJJkNDgKCQkJCXRlbXAgPSBNT0NBX1JEKDB4MTAxMDAwNTApOwoJCQkJdGVtcCA9ICh0ZW1wICYgMHhGRkZGRkUwMSkgKyAoNDggPDwgMSk7CgkJCQlNT0NBX1dSKDB4MTAxMDAwNTAsIHRlbXApOwoKCQkJCS8vIFRoZW4gUmVzdGFydCB0aGUgUExMLgoKCQkJCS8vYENMS0dFTl9SRUdfU1RBUlQgKyBgQ0xLR0VOX1BMTF9TWVMwX1BMTF9SRVNFVCAoMzInaDEwMTAwMDJDKSBbMF0gPSAxkmIxCgkJCQlNT0NBX1NFVCgweDEwMTAwMDJjLCAxKTsKCQkJCS8vYENMS0dFTl9SRUdfU1RBUlQgKyBgQ0xLR0VOX1BMTF9TWVMxX1BMTF9SRVNFVCAoMzInaDEwMTAwMDZDKSBbMF0gPSAxkmIxCgkJCQlNT0NBX1NFVCgweDEwMTAwMDZjLCAxKTsKCgkJCQl1ZGVsYXkoMSk7CgoJCQkJLy9gQ0xLR0VOX1JFR19TVEFSVCArIGBDTEtHRU5fUExMX1NZUzBfUExMX1JFU0VUICgzMidoMTAxMDAwMkMpIFswXSA9IDGSYjAKCQkJCU1PQ0FfVU5TRVQoMHgxMDEwMDAyYywgMSk7CgkJCQkvL2BDTEtHRU5fUkVHX1NUQVJUICsgYENMS0dFTl9QTExfU1lTMV9QTExfUkVTRVQgKDMyJ2gxMDEwMDA2QykgWzBdID0gMZJiMAoJCQkJTU9DQV9VTlNFVCgweDEwMTAwMDZjLCAxKTsKCQkJfQoJCX0KCgkJLy8gQ0xLR0VOX1BMTF9TWVMxX1BMTF9TU0NfTU9ERV9DT05UUk9MX0hJR0gKCQlkYXRhID0gTU9DQV9SRCgweDEwMTAwMDcwKTsKCQlkYXRhID0gKGRhdGEgJiAweEZGRkYwMDAwKSB8IDB4N2RkOwoJCU1PQ0FfV1IoMHgxMDEwMDA3MCwgZGF0YSk7CgoJCS8vIENMS0dFTl9QTExfU1lTMV9QTExfU1NDX01PREVfQ09OVFJPTF9MT1cKCQlkYXRhID0gTU9DQV9SRCgweDEwMTAwMDc0KTsKCQlkYXRhID0gKGRhdGEgJiAweGZmYzAwMDAwKSB8IDB4M2Q3MTsKCQlNT0NBX1dSKDB4MTAxMDAwNzQsIGRhdGEpOwoKCQkvLyBDTEtHRU5fUExMX1NZUzFfUExMX1NTQ19NT0RFX0NPTlRST0xfTE9XCgkJTU9DQV9TRVQoMHgxMDEwMDA3NCwgKDEgPDwgMjIpKTsKCX0KCgoJaWYgKHByaXYtPmh3X3JldiA8PSBIV1JFVl9NT0NBXzIwX0dFTjIxKSB7CgkvKiBjbGVhciBqdW5rIG91dCBvZiBHUDAvR1AxICovCgkJTU9DQV9XUihwcml2LT5iYXNlICsgcHJpdi0+cmVncy0+Z3AwX29mZnNldCwgMHhmZmZmZmZmZik7CgkJTU9DQV9XUihwcml2LT5iYXNlICsgcHJpdi0+cmVncy0+Z3AxX29mZnNldCwgMHgwKTsKCQkvKiBzZXQgdXAgYWN0aXZpdHkgTEVEIGZvciA1MCUgZHV0eSBjeWNsZSAqLwoJCU1PQ0FfV1IocHJpdi0+YmFzZSArIHByaXYtPnJlZ3MtPmxlZF9jdHJsX29mZnNldCwKCQkJMHg0MDAwNDAwMCk7Cgl9CgoJLyogZW5hYmxlIERNQSBjb21wbGV0aW9uIGludGVycnVwdHMgKi8KCW1hc2sgPSBNMkhfUkVRIHwgTTJIX1JFU1AgfCBNMkhfQVNTRVJUIHwgTTJIX1dEVF9DUFUxIHwKCQlNMkhfTkVYVENIVU5LIHwgTTJIX0RNQTsKCglpZiAocHJpdi0+aHdfcmV2ID49IEhXUkVWX01PQ0FfMjBfR0VOMjEpCgkJbWFzayB8PSBNMkhfV0RUX0NQVTAgfCBNMkhfTkVYVENIVU5LX0NQVTAgfAoJCQlNMkhfUkVRX0NQVTAgfCBNMkhfUkVTUF9DUFUwIHwgTTJIX0FTU0VSVF9DUFUwOwoKCU1PQ0FfV1IocHJpdi0+YmFzZSArIHByaXYtPnJlZ3MtPnJpbmdiZWxsX29mZnNldCwgMCk7CglNT0NBX1dSKHByaXYtPmJhc2UgKyBwcml2LT5yZWdzLT5sMl9tYXNrX2NsZWFyX29mZnNldCwgbWFzayk7CglNT0NBX1JEKHByaXYtPmJhc2UgKyBwcml2LT5yZWdzLT5sMl9tYXNrX2NsZWFyX29mZnNldCk7CgoKCS8qIFNldCBwaW5tdXhpbmcgZm9yIE1vQ0EgaW50ZXJydXB0IGFuZCBmbG93IGNvbnRyb2wgKi8KCU1PQ0FfVU5TRVQoMHgxMDQwNDExMCwgMHhGMDAwMDBGRik7CglNT0NBX1NFVCgweDEwNDA0MTEwLCAweDEwMDAwMDIyKTsKIAoJLyogU2V0IHBpbm11eGluZyBmb3IgTW9DQSBJSUMgY29udHJvbCAqLwoJaWYgKCgocHJpdi0+Y2hpcF9pZCAmIDB4RkZGRkZGRjApID09IDB4NjgwMjAwQzApIHx8CgkgICAgKChwcml2LT5jaGlwX2lkICYgMHhGRkZGRkZGMCkgPT0gMHg2ODAzMDBDMCkpCgl7CgkJTU9DQV9VTlNFVCgweDEwNDA0MTAwLCAweEZGKTsgIC8vIHBpbiBtdXhpbmcKCQlNT0NBX1NFVCgweDEwNDA0MTAwLCAweDIyKTsgIC8vIHBpbiBtdXhpbmcKCX0KCglNT0NBX1dSKDB4MTAwYjAzMTgsIDIpOwoKCWlmIChhY3Rpb24gPT0gTU9DQV9ESVNBQkxFICYmIHByaXYtPmVuYWJsZWQpIHsKCQlwcml2LT5lbmFibGVkID0gMDsKCQltb2NhX2Nsa19kaXNhYmxlKHByaXYtPmNsayk7Cgl9Cn0KCnN0YXRpYyB2b2lkIG1vY2FfcmluZ2JlbGwoc3RydWN0IG1vY2FfcHJpdl9kYXRhICpwcml2LCB1aW50MzJfdCBtYXNrKQp7CglNT0NBX1dSKHByaXYtPmJhc2UgKyBwcml2LT5yZWdzLT5yaW5nYmVsbF9vZmZzZXQsIG1hc2spOwp9CgpzdGF0aWMgdWludDMyX3QgbW9jYV9zdGFydF9taXBzKHN0cnVjdCBtb2NhX3ByaXZfZGF0YSAqcHJpdiwgdW5zaWduZWQgaW50IGNwdSkKewoJaWYgKHByaXYtPmh3X3JldiA9PSBIV1JFVl9NT0NBXzIwX0dFTjIyKSB7CgkJaWYgKGNwdSA9PSAxKQoJCQlNT0NBX1VOU0VUKHByaXYtPmJhc2UgKyBwcml2LT5yZWdzLT5zd19yZXNldF9vZmZzZXQsCgkJCQkoMSA8PCAwKSk7CgkJZWxzZSB7CgkJCW1vY2FfbW1wX2luaXQocHJpdiwgMSk7CgkJCU1PQ0FfVU5TRVQocHJpdi0+YmFzZSArIHByaXYtPnJlZ3MtPnN3X3Jlc2V0X29mZnNldCwKCQkJCSgxIDw8IDIpKTsKCQl9Cgl9IGVsc2UKCQlNT0NBX1VOU0VUKHByaXYtPmJhc2UgKyBwcml2LT5yZWdzLT5zd19yZXNldF9vZmZzZXQsICgxIDw8IDApKTsKCU1PQ0FfUkQocHJpdi0+YmFzZSArIHByaXYtPnJlZ3MtPnN3X3Jlc2V0X29mZnNldCk7CgoJcmV0dXJuKDApOwp9CgpzdGF0aWMgdm9pZCBtb2NhX20ybV94ZmVyKHN0cnVjdCBtb2NhX3ByaXZfZGF0YSAqcHJpdiwKCXVpbnQzMl90IGRzdCwgdWludDMyX3Qgc3JjLCB1aW50MzJfdCBjdGwpCnsKCXVpbnQzMl90IHN0YXR1czsKCglNT0NBX1dSKHByaXYtPmJhc2UgKyBwcml2LT5yZWdzLT5tMm1fc3JjX29mZnNldCwgc3JjKTsKCU1PQ0FfV1IocHJpdi0+YmFzZSArIHByaXYtPnJlZ3MtPm0ybV9kc3Rfb2Zmc2V0LCBkc3QpOwoJTU9DQV9XUihwcml2LT5iYXNlICsgcHJpdi0+cmVncy0+bTJtX3N0YXR1c19vZmZzZXQsIDApOwoJTU9DQV9SRChwcml2LT5iYXNlICsgcHJpdi0+cmVncy0+bTJtX3N0YXR1c19vZmZzZXQpOwoJTU9DQV9XUihwcml2LT5iYXNlICsgcHJpdi0+cmVncy0+bTJtX2NtZF9vZmZzZXQsIGN0bCk7CgoJZG8gewoJCXN0YXR1cyA9IE1PQ0FfUkQocHJpdi0+YmFzZSArIHByaXYtPnJlZ3MtPm0ybV9zdGF0dXNfb2Zmc2V0KTsKCX0gd2hpbGUoc3RhdHVzID09IDApOwoKfQoKc3RhdGljIHZvaWQgbW9jYV93cml0ZV9tZW0oc3RydWN0IG1vY2FfcHJpdl9kYXRhICpwcml2LAoJdWludDMyX3QgZHN0X29mZnNldCwgdm9pZCAqc3JjLCB1bnNpZ25lZCBpbnQgbGVuKQp7CglpZigoZHN0X29mZnNldCA+PSBwcml2LT5yZWdzLT5jbnRsX21lbV9vZmZzZXQrcHJpdi0+cmVncy0+Y250bF9tZW1fc2l6ZSkgfHwKCQkoKGRzdF9vZmZzZXQgKyBsZW4pID4gcHJpdi0+cmVncy0+Y250bF9tZW1fb2Zmc2V0K3ByaXYtPnJlZ3MtPmNudGxfbWVtX3NpemUpKSB7CgkJcHJpbnRrKEtFUk5fV0FSTklORyAiJXM6IGNvcHkgcGFzdCBlbmQgb2YgY250bCBtZW1vcnk6ICUwOHhcbiIsCgkJCV9fRlVOQ1RJT05fXywgZHN0X29mZnNldCk7CgkJcmV0dXJuOwoJfQoKCWlmICggMSA9PSBwcml2LT51c2VfZG1hICkKCXsKCQlkbWFfYWRkcl90IHBhOwoKCQlwYSA9IGRtYV9tYXBfc2luZ2xlKHByaXYtPm1vY2FfZGV2LCBzcmMsIGxlbiwgRE1BX1RPX0RFVklDRSk7CgkJbXV0ZXhfbG9jaygmcHJpdi0+Y29weV9tdXRleCk7CgkJbW9jYV9tMm1feGZlcihwcml2LCBkc3Rfb2Zmc2V0ICsgcHJpdi0+cmVncy0+ZGF0YV9tZW1fb2Zmc2V0LCAodWludDMyX3QpcGEsIGxlbiB8IE0yTV9XUklURSk7CgkJbXV0ZXhfdW5sb2NrKCZwcml2LT5jb3B5X211dGV4KTsKCQlkbWFfdW5tYXBfc2luZ2xlKHByaXYtPm1vY2FfZGV2LCBwYSwgbGVuLCBETUFfVE9fREVWSUNFKTsKCX0KCWVsc2UKCXsKCQl1aW50cHRyX3QgYWRkciA9ICh1aW50cHRyX3QpcHJpdi0+YmFzZSArIHByaXYtPnJlZ3MtPmRhdGFfbWVtX29mZnNldCArIGRzdF9vZmZzZXQ7CgkJdWludDMyX3QgKmRhdGEgPSBzcmM7CgkJaW50IGk7CgoJCW11dGV4X2xvY2soJnByaXYtPmNvcHlfbXV0ZXgpOwoJCWlmICgxKSAvKiAocHJpdi0+dXNlX3NwaSA9PSAxKSAqLwoJCXsKCQkJc3JjID0gZGF0YTsKCQkJTU9DQV9XUl9CTE9DSyhhZGRyLCBzcmMsIGxlbik7CgkJfQoJCWVsc2UKCQl7CgkJCWZvcihpID0gMDsgaSA8IGxlbjsgaSArPSA0LCBhZGRyICs9IDQsIGRhdGErKykKCQkJCU1PQ0FfV1IoYWRkciwgKmRhdGEpOwoJCQlNT0NBX1JEKGFkZHIgLSA0KTsJLyogZmx1c2ggd3JpdGUgKi8KCQl9CgoJCW11dGV4X3VubG9jaygmcHJpdi0+Y29weV9tdXRleCk7Cgl9Cn0KCnN0YXRpYyB2b2lkIG1vY2FfcmVhZF9tZW0oc3RydWN0IG1vY2FfcHJpdl9kYXRhICpwcml2LAoJdm9pZCAqZHN0LCB1aW50MzJfdCBzcmNfb2Zmc2V0LCB1bnNpZ25lZCBpbnQgbGVuKQp7CglpZigoc3JjX29mZnNldCA+PSBwcml2LT5yZWdzLT5jbnRsX21lbV9vZmZzZXQrcHJpdi0+cmVncy0+Y250bF9tZW1fc2l6ZSkgfHwKCQkoKHNyY19vZmZzZXQgKyBsZW4pID4gcHJpdi0+cmVncy0+Y250bF9tZW1fb2Zmc2V0K3ByaXYtPnJlZ3MtPmNudGxfbWVtX3NpemUpKSB7CgkJcHJpbnRrKEtFUk5fV0FSTklORyAiJXM6IGNvcHkgcGFzdCBlbmQgb2YgY250bCBtZW1vcnk6ICUwOHhcbiIsCgkJCV9fRlVOQ1RJT05fXywgc3JjX29mZnNldCk7CgkJcmV0dXJuOwoJfQoKCWlmICggMSA9PSBwcml2LT51c2VfZG1hICkKCXsKCQlkbWFfYWRkcl90IHBhOwoKCQlwYSA9IGRtYV9tYXBfc2luZ2xlKHByaXYtPm1vY2FfZGV2LCBkc3QsIGxlbiwgRE1BX0ZST01fREVWSUNFKTsKCQltdXRleF9sb2NrKCZwcml2LT5jb3B5X211dGV4KTsKCQltb2NhX20ybV94ZmVyKHByaXYsICh1aW50MzJfdClwYSwgc3JjX29mZnNldCArIHByaXYtPnJlZ3MtPmRhdGFfbWVtX29mZnNldCwgbGVuIHwgTTJNX1JFQUQpOwoJCW11dGV4X3VubG9jaygmcHJpdi0+Y29weV9tdXRleCk7CgkJZG1hX3VubWFwX3NpbmdsZShwcml2LT5tb2NhX2RldiwgcGEsIGxlbiwgRE1BX0ZST01fREVWSUNFKTsKCX0KCWVsc2UKCXsKCQl1aW50cHRyX3QgYWRkciA9IHByaXYtPnJlZ3MtPmRhdGFfbWVtX29mZnNldCArIHNyY19vZmZzZXQ7CgkJdWludDMyX3QgKmRhdGEgPSBkc3Q7CgkJaW50IGk7CgoJCW11dGV4X2xvY2soJnByaXYtPmNvcHlfbXV0ZXgpOwoJCWlmICgxKSAvKiAocHJpdi0+dXNlX3NwaSA9PSAxKSAqLwoJCXsKCQkJTU9DQV9SRF9CTE9DSygodWludHB0cl90KXByaXYtPmJhc2UgKyBhZGRyLCBkc3QsIGxlbik7CgkJfQoJCWVsc2UKCQl7CgkJCWZvcihpID0gMDsgaSA8IGxlbjsgaSArPSA0LCBhZGRyICs9IDQsIGRhdGErKykKCQkJCSpkYXRhID0gTU9DQV9SRCgodWludHB0cl90KXByaXYtPmJhc2UgKyBhZGRyKTsKCQl9CgkJbXV0ZXhfdW5sb2NrKCZwcml2LT5jb3B5X211dGV4KTsKCX0KfQoKc3RhdGljIHZvaWQgbW9jYV93cml0ZV9zZyhzdHJ1Y3QgbW9jYV9wcml2X2RhdGEgKnByaXYsCgl1aW50MzJfdCBkc3Rfb2Zmc2V0LCBzdHJ1Y3Qgc2NhdHRlcmxpc3QgKnNnLCBpbnQgbmVudHMpCnsKCWludCBqOwoJdWludHB0cl90IGFkZHIgPSBwcml2LT5yZWdzLT5kYXRhX21lbV9vZmZzZXQgKyBkc3Rfb2Zmc2V0OwoKCWRtYV9tYXBfc2cocHJpdi0+bW9jYV9kZXYsIHNnLCBuZW50cywgRE1BX1RPX0RFVklDRSk7CgoJbXV0ZXhfbG9jaygmcHJpdi0+Y29weV9tdXRleCk7Cglmb3IoaiA9IDA7IGogPCBuZW50czsgaisrKQoJewoJCWlmICggMSA9PSBwcml2LT51c2VfZG1hICkKCQl7CgkJICAgIC8vIHByaW50aygiWFhYIGNvcHlpbmcgcGFnZSAlZCwgUEEgJTA4eFxuIiwgaiwgKGludClzZ1tqXS5kbWFfYWRkcmVzcyk7CgkJCW1vY2FfbTJtX3hmZXIocHJpdiwgYWRkciwgKHVpbnQzMl90KXNnW2pdLmRtYV9hZGRyZXNzLCAKCQkJCXNnW2pdLmxlbmd0aCB8IE0yTV9XUklURSk7CgoJCQlhZGRyICs9IHNnW2pdLmxlbmd0aDsKCQl9CgkJZWxzZQoJCXsKCQkJdW5zaWduZWQgbG9uZyAqZGF0YSA9ICh2b2lkICopcGh5c190b192aXJ0KHNnW2pdLmRtYV9hZGRyZXNzKTsKICAgICAgICAgLy9wcmludGsoIiVzOiBXcml0aW5nIDB4JWx4IHRvIGFkZHIgMHglMDhseCAobGVuID0gJWQpXG4iLCBfX0ZVTkNUSU9OX18sICpkYXRhLCAoKHVuc2lnbmVkIGxvbmcpcHJpdi0+YmFzZSkgKyBhZGRyLCBzZ1tqXS5sZW5ndGgpOwoJCQlNT0NBX1dSX0JMT0NLKCgodW5zaWduZWQgbG9uZylwcml2LT5iYXNlKSArIGFkZHIsIGRhdGEsIHNnW2pdLmxlbmd0aCk7CgkJCWFkZHIgKz0gc2dbal0ubGVuZ3RoOwoJCX0KCX0KCW11dGV4X3VubG9jaygmcHJpdi0+Y29weV9tdXRleCk7CgoJZG1hX3VubWFwX3NnKHByaXYtPm1vY2FfZGV2LCBzZywgbmVudHMsIERNQV9UT19ERVZJQ0UpOwp9CgovKiBOT1RFOiB0aGlzIGZ1bmN0aW9uIGlzIG5vdCB0ZXN0ZWQgKi8KI2lmIDAKc3RhdGljIHZvaWQgbW9jYV9yZWFkX3NnKHN0cnVjdCBtb2NhX3ByaXZfZGF0YSAqcHJpdiwKCXVpbnQzMl90IHNyY19vZmZzZXQsIHN0cnVjdCBzY2F0dGVybGlzdCAqc2csIGludCBuZW50cykKewoJaW50IGo7Cgl1aW50cHRyX3QgYWRkciA9IHByaXYtPmRhdGFfbWVtX29mZnNldCArIHNyY19vZmZzZXQ7CgoJZG1hX21hcF9zZyhwcml2LT5tb2NhX2Rldiwgc2csIG5lbnRzLCBETUFfRlJPTV9ERVZJQ0UpOwoKCW11dGV4X2xvY2soJnByaXYtPmNvcHlfbXV0ZXgpOwoJZm9yKGogPSAwOyBqIDwgbmVudHM7IGorKykgewojaWYgMCAvL1VTRV9ETUEKCQkgcHJpbnRrKCJYWFggY29weWluZyBwYWdlICVkLCBQQSAlMDh4XG4iLCBqLCAoaW50KXNnW2pdLmRtYV9hZGRyZXNzKTsKCQltb2NhX20ybV94ZmVyKHByaXYsIGFkZHIsICh1aW50MzJfdClzZ1tqXS5kbWFfYWRkcmVzcywKCQkJc2dbal0ubGVuZ3RoIHwgTTJNX1JFQUQpOwoKCQlhZGRyICs9IHNnW2pdLmxlbmd0aDsKI2Vsc2UKCQl1aW50MzJfdCAqZGF0YSA9ICh2b2lkICopcGh5c190b192aXJ0KHNnW2pdLmRtYV9hZGRyZXNzKTsKCQl1bnNpZ25lZCBpbnQgbGVuID0gc2dbal0ubGVuZ3RoOwoJCWludCBpOwoKCQlmb3IoaSA9IDA7IGkgPCBsZW47IGkgKz0gNCwgYWRkciArPSA0LCBkYXRhKyspIHsKCQkJKmRhdGEgPSBjcHVfdG9fYmUzMigKCQkJCU1PQ0FfUkQoKHVpbnRwdHJfdClwcml2LT5iYXNlICsgYWRkcikpOwoJCQkvL3ByaW50aygiTW9DQSBSRUFEOiBBRCAweCV4ICA9IDB4JXggKDB4JXgpXG4iLCAocHJpdi0+YmFzZSArIGFkZHIpLCBNT0NBX1JEKCh1aW50cHRyX3QpcHJpdi0+YmFzZSArIGFkZHIpLCAqZGF0YSk7CgkJIH0KI2VuZGlmCgl9CgltdXRleF91bmxvY2soJnByaXYtPmNvcHlfbXV0ZXgpOwoKCWRtYV91bm1hcF9zZyhwcml2LT5tb2NhX2Rldiwgc2csIG5lbnRzLCBETUFfRlJPTV9ERVZJQ0UpOwp9CiNlbmRpZgoKc3RhdGljIHZvaWQgbW9jYV9yZWFkX21hY19hZGRyKHN0cnVjdCBtb2NhX3ByaXZfZGF0YSAqcHJpdiwgdWludDMyX3QgKiBoaSwgdWludDMyX3QgKiBsbykKewoJc3RydWN0IG5ldF9kZXZpY2UgKiBwZGV2IDsKCglwZGV2ID0gZGV2X2dldF9ieV9uYW1lICggJmluaXRfbmV0LCBwcml2LT5lbmV0X25hbWUgKSA7CgoJaWYgKChwZGV2ICE9IE5VTEwpICYmIChsbyAhPSBOVUxMKSAmJiAoaGkgIT0gTlVMTCkpIHsKCQltYWNfdG9fdTMyKGhpLCBsbywgcGRldi0+ZGV2X2FkZHIpOwoJfQp9CgoKI2lmIGRlZmluZWQoRFNMX01PQ0EpCgovKgogKiBUaGlzIGhlbHBlciBmdW5jdGlvbiB3YXMgYWRkZWQgdG8gYWxsb3cgdGhlIGVuZXQgZHJpdmVyIHRvIGNvbXBpbGUgaW4KICogY29uc3VtZXIgZW52aXJvbm1lbnQgZm9yIDY4eHggcHJvZmlsZXMuCiAqLwp2b2lkIG1vY2FfZ2V0X2ZjX2JpdHModm9pZCAqIGFyZywgdW5zaWduZWQgbG9uZyAqbW9jYV9mY19yZWcpCnsKCXN0cnVjdCBtb2NhX3ByaXZfZGF0YSAqICAgICBwcml2OwoJdW5zaWduZWQgbG9uZyAgICAgICAgICAgICAgIGZsYWdzOwoKCWlmIChhcmcgPT0gTlVMTCkgewoJCXJldHVybjsKCX0KCglwcml2ID0gKHN0cnVjdCBtb2NhX3ByaXZfZGF0YSAqKSBhcmc7CgoJKm1vY2FfZmNfcmVnID0gMDsKCWlmIChwcml2ICE9IE5VTEwpCgl7CgkJLyogV2UgY2FuJ3QgcmVhZCBtb2NhIGNvcmUgcmVncyB1bmxlc3MgdGhlIGNvcmUncyBjbG9ja3MgYXJlIG9uLiAqLwoJCXNwaW5fbG9ja19pcnFzYXZlKCZwcml2LT5jbG9ja19sb2NrLCBmbGFncyk7CgkJaWYgKHByaXYtPnJ1bm5pbmcpIHsKCQkJKm1vY2FfZmNfcmVnID0gTU9DQV9SRChwcml2LT5iYXNlK3ByaXYtPnJlZ3MtPnNpZGViYW5kX2dtaWlfZmNfb2Zmc2V0KTsKCQl9CgkJc3Bpbl91bmxvY2tfaXJxcmVzdG9yZSgmcHJpdi0+Y2xvY2tfbG9jaywgZmxhZ3MpOwoJfQp9CgojZW5kaWYgLyogRFNMX01PQ0EgKi8KCnN0YXRpYyBpbnQgYm1vY2Ffc3BpX3Byb2JlKHN0cnVjdCBzcGlfZGV2aWNlICpzcGkpIHsKCS8vIFRPRE8oYXBlbndhcnIpOiBtYXRjaCBvbmUgc3BpIGRldmljZSB0byBvbmUgbW9jYSBkZXZpY2Ugc3RydWN0LgoJLy8gSSBoYXBwZW4gdG8ga25vdyB0aGF0IHJpZ2h0IG5vdyB0aGUgc3lzdGVtIG9ubHkgcmVnaXN0ZXJzIG9uZSBvZgoJLy8gbW9jYV9sYW4gb3IgbW9jYV93YW4sIG5ldmVyIGJvdGgsIGFuZCB0aGVyZSBpcyBuZXZlciBtb3JlIHRoYW4KCS8vIG9uZSBtb2NhIGNoaXAgcHJlc2VudCBvbiBvdXIgc3lzdGVtcywgc28gdGhpcyBpcyBva2F5IGZvciBub3cuCglzdHJ1Y3QgbW9jYV9wcml2X2RhdGEgKnByaXY7Cgljb25zdCBjaGFyICpyZmI7Cgljb25zdCBjaGFyICppZm5hbWU7CglpbnQgc3RhdHVzID0gMCwgaSA9IDA7CglzdGF0aWMgY29uc3QgY2hhciAqY29uc3Qgb2ZfcmZiW01PQ0FfQkFORF9NQVggKyAxXSA9IE1PQ0FfQkFORF9OQU1FUzsKCXN0cnVjdCBkZXZpY2Vfbm9kZSAqb2Zfbm9kZSA9IHNwaS0+ZGV2Lm9mX25vZGU7Cgl1aW50MzJfdCBjaGlwX2ZhbWlseV9pZDsKI2lmIExJTlVYX1ZFUlNJT05fQ09ERSA+PSBLRVJORUxfVkVSU0lPTigzLDEzLDApCglzdHJ1Y3QgZ3Bpb19kZXNjICpncGlvZF9yZXNldDsKCglncGlvZF9yZXNldCA9IGRldm1fZ3Bpb2RfZ2V0X29wdGlvbmFsKCZzcGktPmRldiwgInJlc2V0Iik7CglpZiAoZ3Bpb2RfcmVzZXQpIHsKCQlkZXZfaW5mbygmc3BpLT5kZXYsICJSZXNldHRpbmcgTW9DQSBjaGlwIHRocm91Z2ggR1BJTyBwaW5cbiIpOwoJCWdwaW9kX2RpcmVjdGlvbl9vdXRwdXQoZ3Bpb2RfcmVzZXQsIDApOwoJCW1zbGVlcCgxMCk7CgkJZ3Bpb2Rfc2V0X3ZhbHVlKGdwaW9kX3Jlc2V0LCAxKTsKCQltc2xlZXAoMTApOwoJCWdwaW9kX3NldF92YWx1ZShncGlvZF9yZXNldCwgMCk7CgkJbXNsZWVwKDIxMCk7Cgl9CiNlbmRpZgoKCWNoaXBfZmFtaWx5X2lkID0ga2VyU3lzQmNtU3BpU2xhdmVSZWFkUmVnMzIoc3BpLCAweDEwNDA0MDAwKTsKCWRldl9pbmZvKCZzcGktPmRldiwgImJtb2NhX3NwaV9wcm9iZSBidXM9JWQgY2hpcF9zZWxlY3Q9JWQ6IGlkPSUwOHggJXNcbiIsCgkJc3BpLT5tYXN0ZXItPmJ1c19udW0sIHNwaS0+Y2hpcF9zZWxlY3QsIGNoaXBfZmFtaWx5X2lkLAoJCWNoaXBfZmFtaWx5X2lkICE9IDAgPyAiKHZhbGlkKSIgOiAiKGludmFsaWQpIik7CglpZiAoY2hpcF9mYW1pbHlfaWQgPT0gMCkgcmV0dXJuIC1FTk9ERVY7Cglwcml2ID0ga3phbGxvYyhzaXplb2YoKnByaXYpLCBHRlBfS0VSTkVMKTsKCWlmICghcHJpdikgewoJCWRldl9lcnIoJnNwaS0+ZGV2LCAiJXM6IG91dCBvZiBtZW1vcnlcbiIsIF9fZnVuY19fKTsKCQlyZXR1cm4gLUVOT01FTTsKCX0KCS8qIFdlIGRvbid0IHNldCBwcml2LT5od19yZXYgKi8KCWlmICgoY2hpcF9mYW1pbHlfaWQgJiAweEZGRkYwMDAwKSA9PSAweDY4MDIwMDAwKQoJCXByaXYtPnJlZ3MgPSAmcmVnc182ODAyOwoJZWxzZQoJCXByaXYtPnJlZ3MgPSAmcmVnc182ODE2OwoJcHJpdi0+bW9jYV9kZXYgPSAmc3BpLT5kZXY7Cglwcml2LT5jbGsgPSBtb2NhX2Nsa19nZXQocHJpdi0+bW9jYV9kZXYsICJtb2NhIik7Cglwcml2LT5jcHVfY2xrID0gbW9jYV9jbGtfZ2V0KHByaXYtPm1vY2FfZGV2LCAibW9jYS1jcHUiKTsKCXByaXYtPnBoeV9jbGsgPSBtb2NhX2Nsa19nZXQocHJpdi0+bW9jYV9kZXYsICJtb2NhLXBoeSIpOwoJc3RhdHVzID0gb2ZfcHJvcGVydHlfcmVhZF9zdHJpbmcob2Zfbm9kZSwgImlmLW5hbWUiLCAmaWZuYW1lKTsKCWlmIChzdGF0dXMpIHsKCQlkZXZfd2Fybigmc3BpLT5kZXYsICJBc3N1bWluZyBuZXR3b3JrIGludGVyZmFjZSBkZXZpY2UgbmFtZSBtb2NhMFxuIik7CgkJaWZuYW1lID0gIm1vY2EwIjsKCX0KCXN0cm5jcHkocHJpdi0+ZW5ldF9uYW1lLCBpZm5hbWUsIHNpemVvZihwcml2LT5lbmV0X25hbWUpKTsKCXByaXYtPmVuZXRfbmFtZVtzaXplb2YocHJpdi0+ZW5ldF9uYW1lKS0xXSA9ICdcMCc7Cglwcml2LT5lbmV0X2lkID0gfjBVTDsKCXByaXYtPm1hY2FkZHJfaGkgPSAweDAwMDAwMTAyOwoJcHJpdi0+bWFjYWRkcl9sbyA9IDB4MDMwNDAwMDA7CgkvKiBjaGlwX2lkIGlzIHNldCBpbiBod19zcGVjaWZpY19pbml0KCkqLwoJcHJpdi0+dXNlX2RtYSA9IDA7Cglwcml2LT5kZXZJZCA9IDA7IC8qIFRPRE86IE5lZWRzIHRvIGluY3JlYXNlICovCglwcml2LT5iYXNlID0gKHZvaWQgKikgMHgxMDYwMDAwMDsKCXByaXYtPmlycSA9IHNwaS0+aXJxOwoJc3RhdHVzID0gb2ZfcHJvcGVydHlfcmVhZF9zdHJpbmcob2Zfbm9kZSwgInJmLWJhbmQiLCAmcmZiKTsKCWlmICghc3RhdHVzKSB7CgkJZm9yIChpID0gMDsgaSA8IE1PQ0FfQkFORF9NQVg7IGkrKykgewoJCQlpZiAoc3RyY21wKHJmYiwgb2ZfcmZiW2ldKSA9PSAwKSB7CgkJCQlwcml2LT5yZl9iYW5kID0gaTsKCQkJCWRldl9pbmZvKCZzcGktPmRldiwgIlVzaW5nICVzKCVkKSBiYW5kXG4iLAoJCQkJCSBvZl9yZmJbaV0sIGkpOwoJCQkJYnJlYWs7CgkJCX0KCQl9Cgl9CgoJaWYgKHN0YXR1cyB8fCBpID09IE1PQ0FfQkFORF9NQVgpIHsKCQlwcml2LT5yZl9iYW5kID0gMzsKCQlkZXZfd2Fybigmc3BpLT5kZXYsICJEZWZhdWx0aW5nIHRvIHJmLWJhbmQgJXNcbiIsIG9mX3JmYltwcml2LT5yZl9iYW5kXSk7Cgl9CgkvKiBJMkMgZGVmYXVsdCB2YWx1ZXMgKi8KCXByaXYtPmkyY19iYXNlID0gKHZvaWQgX19pb21lbSAqKSAweDEwNDA2MjAwOwoJcHJpdi0+YmNtMzQ1MF9pMmNfYWRkciA9IDB4NzA7CglvZl9wcm9wZXJ0eV9yZWFkX3UzMihvZl9ub2RlLCAiaTJjLWJhc2UiLCAodTMyICopICZwcml2LT5pMmNfYmFzZSk7CglvZl9wcm9wZXJ0eV9yZWFkX3UzMihvZl9ub2RlLCAiaTJjLWFkZHIiLCAmcHJpdi0+YmNtMzQ1MF9pMmNfYWRkcik7Cgltb2NhX3JlYWRfbWFjX2FkZHIocHJpdiwgJnByaXYtPm1hY2FkZHJfaGksICZwcml2LT5tYWNhZGRyX2xvKTsKCXJldHVybiBtb2NhX2dlbmVyaWNfcHJvYmUocHJpdik7Cn0KCnN0YXRpYyBpbnQgYm1vY2Ffc3BpX3JlbW92ZShzdHJ1Y3Qgc3BpX2RldmljZSAqc3BpKSB7Cglwcl9pbmZvKCJibW9jYV9zcGlfcmVtb3ZlXG4iKTsKCS8qIFRPRE8gKi8KCXJldHVybiAwOyAvLyBzdWNjZXNzCn0KCnN0YXRpYyBjb25zdCBzdHJ1Y3Qgb2ZfZGV2aWNlX2lkIGJtb2NhX29mX21hdGNoW10gPSB7CgkJewoJCQkuY29tcGF0aWJsZQk9ICJicmNtLGJjbTY4MDItc3BpIiwKCQl9LAoJCXsKCQkJLmNvbXBhdGlibGUJPSAiYnJjbSxiY202ODAzLXNwaSIsCgkJfSwKCQl7fSwKfTsKTU9EVUxFX0RFVklDRV9UQUJMRShvZiwgYm1vY2Ffb2ZfbWF0Y2gpOwpzdGF0aWMgc3RydWN0IHNwaV9kcml2ZXIgYm1vY2Ffc3BpX2RyaXZlciA9IHsKCS5kcml2ZXIgPSB7CgkJLm5hbWUgPSAiYm1vY2EiLAoJCS5vd25lciA9IFRISVNfTU9EVUxFLAoJCS5vZl9tYXRjaF90YWJsZSA9IG9mX21hdGNoX3B0cihibW9jYV9vZl9tYXRjaCksCgl9LAoJLnByb2JlID0gYm1vY2Ffc3BpX3Byb2JlLAoJLnJlbW92ZSA9IF9fZXhpdF9wKGJtb2NhX3NwaV9yZW1vdmUpLAp9OwoKLy9leHRlcm4gdm9pZCBiY21lbmV0X3JlZ2lzdGVyX21vY2FfZmNfYml0c19jYih2b2lkIGNiKHZvaWQgKiwgdW5zaWduZWQgbG9uZyAqKSwgaW50IGlzV2FuLCB2b2lkICogYXJnKTsKCnN0YXRpYyB2b2lkIG1vY2FfbWVtX2luaXRfNjgweEMwKCBzdHJ1Y3QgbW9jYV9wcml2X2RhdGEgKnByaXYgKQp7CgkvLyBEZS1hc3NlcnQgcmVzZXQgKGFsbCBtZW1vcmllcyBhcmUgT0ZGIGJ5IGRlZmF1bHQgRm9yY2VfU1Bfb2ZmID0xLCBGb3JjZV9SZl9vZmYgPTEpCglNT0NBX1VOU0VUKHByaXYtPmJhc2UgKyBwcml2LT5yZWdzLT5zd19yZXNldF9vZmZzZXQsICgoMSA8PCAxNSkgfCAoMSA8PCAxNikpKTsKCgltb2NhX3BtYl9kZWxheShwcml2KTsKCW1vY2FfcG1iX2NvbnRyb2wocHJpdiwgUE1CX0NPTU1BTkRfQUxMX09GRik7CgoJLy9Xcml0ZSBGb3JjZV9TUF9vbiA9MCwgRm9yY2VfU1Bfb2ZmID0wLCBGb3JjZV9SRl9vbiA9MCwgRm9yY2VfUkZfb2ZmID0wCglNT0NBX1VOU0VUKHByaXYtPmJhc2UgKyAweDAwMWZmZDE0LCAoKDEgPDwgMTApIHwgKDEgPDwgMTEpKSk7Cgltb2NhX3BtYl9jb250cm9sKHByaXYsIFBNQl9DT01NQU5EX1BBUlRJQUxfT04pOwp9CgpzdGF0aWMgaW50ICBod19zcGVjaWZpY19pbml0KCBzdHJ1Y3QgbW9jYV9wcml2X2RhdGEgKnByaXYgKQp7CiNpZmRlZiBEU0xfTU9DQQoJdTMyIHBvcnRfbW9kZTsKCgkvKiBmaWxsIGluIHRoZSBod19yZXYgZmllbGQgKi8KCXByaXYtPmNoaXBfaWQgPSBNT0NBX1JEKDB4MTA0MDQwMDQpICsgMHhBMDsKCWRldl9pbmZvKHByaXYtPm1vY2FfZGV2LCAiTW9DQSBjaGlwIGlkOiAlMDh4XG4iLCBwcml2LT5jaGlwX2lkKTsKCWlmICgocHJpdi0+Y2hpcF9pZCAmIDB4RkZGRTAwMDApICE9IDB4NjgwMjAwMDApIHsgLyogNjgwMiBvciA2ODAzICovCgkJZGV2X2Vycihwcml2LT5tb2NhX2RldiwgIk5vIE1vQ0EgY2hpcCBmb3VuZFxuIik7CgkJcmV0dXJuIC1FRkFVTFQ7Cgl9CgoJTU9DQV9XUigweDEwNDA0MzFjLCAweDBGRkZGRkZGKTsgLy8gU1VOX1RPUF9DVFJMX1NXX0lOSVRfMF9DTEVBUgoJTU9DQV9XUigweDEwNDA0MGE0LCAweDAxKTsgICAgICAgLy8gR0VORVJBTF9DVFJMX05PX1NDQU5fMAoJLyogUG93ZXIgZG93biBHUEhZIExETyByZWd1bGF0b3IgdG8gc2F2ZSBwb3dlciAqLwoJTU9DQV9XUigweDEwNDA0MGE4LCAweDAzKTsgICAgICAgLy8gR0VORVJBTF9DVFJMX05PX1NDQU5fMQoJTU9DQV9XUigweDEwNDA0MTAwLCAweDExMTEwMDExKTsgLy8gUElOX01VWF9DVFJMXzAKCU1PQ0FfV1IoMHgxMDQwNDEwNCwgMHgxMTExMTExMSk7IC8vIFBJTl9NVVhfQ1RSTF8xCgoJLyogVGhlIGRlZmluaXRpb24gb2YgUE9SVF9NT0RFIGhhcyBjaGFuZ2VkIGZyb20gY2hpcCByZXZpc2lvbiBCMCB0byBDMAoJICogKi8KCWlmICgocHJpdi0+Y2hpcF9pZCAmIDB4RkZGRUZGRjApID09IDB4NjgwMjAwQzApCgkJcG9ydF9tb2RlID0gMjsgLyogUkdNSUlfMSA8LT4gR1BIWSwgUkdNSUlfMCA8LT4gTW9DQSAqLwoJZWxzZQoJCXBvcnRfbW9kZSA9IDM7IC8qIFJHTUlJXzAgPC0+IE1vQ0EgKi8KCglNT0NBX1dSKDB4MTA4MDAwMDAsIHBvcnRfbW9kZSk7ICAvLyBFTVVYX0NOVFJMCglNT0NBX1dSKDB4MTA4MDAwMGMsIDB4MTEpOyAgICAgICAvLyBSR01JSV8wX0NOVFJMCglNT0NBX1dSKDB4MTA4MDAwMTQsIDB4YzApOyAgICAgICAvLyBSR01JSV8wX1JYX0NMS19ERUxBWV9DTlRSTAoKCS8qIFNodXRkb3duIEdQSFkgdG8gc2F2ZSBwb3dlciAqLwoJTU9DQV9XUigweDEwODAwMDA0LCBNT0NBX1JEKDB4MTA4MDAwMDQpIHwgMHhGKTsgLy8gRVBPUlRfUkVHX0dQSFlfQ05UUkwKCS8qIERpc2FibGUgVUFSVHMgdG8gc2F2ZSBwb3dlciAqLwoJTU9DQV9XUigweDEwNDA2MTgwLCAweDQwMDApOyAvLyBQTV9DT05GSUcKCglpZiAoKChwcml2LT5jaGlwX2lkICYgMHhGRkZGRkZGMCkgPT0gMHg2ODAyMDBDMCkgfHwgKChwcml2LT5jaGlwX2lkICYgMHhGRkZGRkZGMCkgPT0gMHg2ODAzMDBDMCkpCgl7CgkJcHJpdi0+aTJjX2Jhc2UgPSBOVUxMOyAKCgkJLyogSW5pdGlhbGl6ZSA2ODB4IENPIG1lbW9yeSAqLwoJCW1vY2FfbWVtX2luaXRfNjgweEMwKHByaXYpOwoJfQoKCXByaXYtPmh3X3JldiA9IEhXUkVWX01PQ0FfMjBfR0VOMjI7CgoJLyogUG93ZXIgZG93biBhbGwgTEVBUCBtZW1vcmllcyAqLwoJTU9DQV9XUigweDEwMTAwMGU0LCAweDYpOyAvLyBDTEtHRU5fTEVBUF9UT1BfSU5TVF9EQVRBICAgCglNT0NBX1dSKDB4MTAxMDAwZTgsIDB4Nik7IC8vIENMS0dFTl9MRUFQX1RPUF9JTlNUX0hBQiAKCU1PQ0FfV1IoMHgxMDEwMDBlYywgMHg2KTsgLy8gQ0xLR0VOX0xFQVBfVE9QX0lOU1RfUFJPRzAKCU1PQ0FfV1IoMHgxMDEwMDBmMCwgMHg2KTsgLy8gQ0xLR0VOX0xFQVBfVE9QX0lOU1RfUFJPRzEgICAKCU1PQ0FfV1IoMHgxMDEwMDBmNCwgMHg2KTsgLy8gQ0xLR0VOX0xFQVBfVE9QX0lOU1RfUFJPRzIgIAoJTU9DQV9XUigweDEwMTAwMGY4LCAweDYpOyAvLyBDTEtHRU5fTEVBUF9UT1BfSU5TVF9ST00KCU1PQ0FfV1IoMHgxMDEwMDBmYywgMHg2KTsgLy8gQ0xLR0VOX0xFQVBfVE9QX0lOU1RfU0hBUkVEICAKCU1PQ0FfV1IoMHgxMDEwMDE2NCwgMHgzKTsgLy8gQ0xLR0VOX1NZU19DVFJMX0lOU1RfUE9XRVJfU1dJVENIX01FTU9SWSAKCgkvKiBEaXNhYmxlIGNsa29ic3Ygb3V0cHV0IHBpbiB0byBzYXZlIHBvd2VyICovCglNT0NBX1dSKDB4MTAxMDAxM0MsIDB4MSk7IC8vIENMS0dFTl9QQURfQ0xPQ0tfRElTQUJMRQoJLyogRGlzYWJsZSBMRUFQIGNsb2NrcyB0byBzYXZlIHBvd2VyICovCglNT0NBX1dSKDB4MTAxMDAwRDQsIDB4Nyk7IC8vIENMS0dFTl9MRUFQX1RPUF9JTlNUX0NMT0NLX0RJU0FCTEUKCi8vCWJjbWVuZXRfcmVnaXN0ZXJfbW9jYV9mY19iaXRzX2NiKAovLwkJbW9jYV9nZXRfZmNfYml0cywgcHJpdi0+dXNlX3NwaSA/IDEgOiAwLCAodm9pZCAqKXByaXYpOwojZW5kaWYKCglyZXR1cm4gMDsKfQoKc3RhdGljIGludCBzcGlfZHJpdmVyX3JlZ2lzdGVyKHZvaWQpIHsKCXJldHVybiBzcGlfcmVnaXN0ZXJfZHJpdmVyKCZibW9jYV9zcGlfZHJpdmVyKTsKfQpzdGF0aWMgdm9pZCBzcGlfZHJpdmVyX3VucmVnaXN0ZXIodm9pZCkgewoJc3BpX3VucmVnaXN0ZXJfZHJpdmVyKCZibW9jYV9zcGlfZHJpdmVyKTsKfQoKI2lmIDAKc3RhdGljIGludCBtb2NhX3BsYXRmb3JtX2Rldl9yZWdpc3Rlcih2b2lkKQp7CglzdHJ1Y3QgbW9jYV9wbGF0Zm9ybV9kYXRhICpwTW9jYURhdGE7CglzdHJ1Y3QgcGxhdGZvcm1fZGV2aWNlICpwUGxhdGZvcm1EZXY7CglCUF9NT0NBX0lORk8gbW9jYUluZm9bQlBfTU9DQV9NQVhfTlVNXTsKCWludCBtb2NhQ2hpcE51bSA9IEJQX01PQ0FfTUFYX05VTTsKCWludCBpOwoJaW50IHJldCA9IDA7ICAgCgoJQnBHZXRNb2NhSW5mbyhtb2NhSW5mbywgJm1vY2FDaGlwTnVtKTsKCglyZXQgPSBzcGlfcmVnaXN0ZXJfZHJpdmVyKCZibW9jYV9zcGlfZHJpdmVyKTsKCWlmIChyZXQgPCAwKSByZXR1cm4gcmV0OwoKCWZvciAoaSA9IDA7IGkgPCBtb2NhQ2hpcE51bTsgaSsrKSB7CgkJc3dpdGNoIChtb2NhSW5mb1tpXS50eXBlKSB7CgkJCWNhc2UgQlBfTU9DQV9UWVBFX0xBTjoKCQkJCXBNb2NhRGF0YSA9ICZtb2NhX2xhbl9kYXRhOwoJCQkJcFBsYXRmb3JtRGV2ID0gJm1vY2FfbGFuX3BsYXRfZGV2OwoJCQkJYnJlYWs7CgoJCQlkZWZhdWx0OgoJCQkJcHJpbnRrKEtFUk5fRVJSICJibW9jYTogdW5yZWNvZ25pemVkIE1vQ0EgdHlwZSAlZFxuIiwKCQkJCQltb2NhSW5mb1tpXS50eXBlKTsKCQkJCXJldHVybigtMSk7CgkJCQlicmVhazsKCQl9CgoJCXJldCA9IHBsYXRmb3JtX2RldmljZV9yZWdpc3RlcihwUGxhdGZvcm1EZXYpOwoJCWlmIChyZXQgPCAwKSB7CgkJCXNwaV91bnJlZ2lzdGVyX2RyaXZlcigmYm1vY2Ffc3BpX2RyaXZlcik7CgkJCXJldHVybihyZXQpOwoJCX0KCQllbHNlIHsKCQkJcE1vY2FEYXRhLT5kZXZJZCA9IGk7CgoJCQkvKiBNYXAgdGhlIGJvYXJkIHBhcmFtcyBSRiBCYW5kIHRvIHRoZSBibW9jYS5oIHZhbHVlICovCgkJCXN3aXRjaCAobW9jYUluZm9baV0ucmZCYW5kKQoJCQl7CgkJCQljYXNlIEJQX01PQ0FfUkZfQkFORF9EX0xPVzoKCQkJCQlwTW9jYURhdGEtPnJmX2JhbmQgPSBNT0NBX0JBTkRfRF9MT1c7CgkJCQkJYnJlYWs7CgkJCQljYXNlIEJQX01PQ0FfUkZfQkFORF9EX0hJR0g6CgkJCQkJcE1vY2FEYXRhLT5yZl9iYW5kID0gTU9DQV9CQU5EX0RfSElHSDsKCQkJCQlicmVhazsKCQkJCWNhc2UgQlBfTU9DQV9SRl9CQU5EX0VYVF9EOgoJCQkJCXBNb2NhRGF0YS0+cmZfYmFuZCA9IE1PQ0FfQkFORF9FWFRfRDsKCQkJCQlicmVhazsKCQkJCWNhc2UgQlBfTU9DQV9SRl9CQU5EX0U6CgkJCQkJcE1vY2FEYXRhLT5yZl9iYW5kID0gTU9DQV9CQU5EX0U7CgkJCQkJYnJlYWs7CgkJCQljYXNlIEJQX01PQ0FfUkZfQkFORF9GOiAgICAKCQkJCQlwTW9jYURhdGEtPnJmX2JhbmQgPSBNT0NBX0JBTkRfRjsKCQkJCQlicmVhazsKCQkJCWRlZmF1bHQ6CgkJCQkJLyogRG8gbm90aGluZyAqLwoJCQkJCWJyZWFrOwoJCQl9CgkJCXByaW50ayhLRVJOX0lORk8gImJtb2NhOiBGb3VuZCBNb0NBIGRldmljZSAlZC8lZCAgUkYgQmFuZCAlZFxuIiwKCQkJCWksIG1vY2FDaGlwTnVtLCBtb2NhSW5mb1tpXS5yZkJhbmQpOwoJCX0KCX0KCglyZXR1cm4ocmV0KTsKfQoKc3RhdGljIHZvaWQgbW9jYV9wbGF0Zm9ybV9kZXZfdW5yZWdpc3Rlcih2b2lkKQp7CglzcGlfdW5yZWdpc3Rlcl9kcml2ZXIoJmJtb2NhX3NwaV9kcml2ZXIpOwoKCWlmIChtb2NhX2xhbl9kYXRhLmRldklkICE9IE1PQ0FfREVWSUNFX0lEX1VOUkVHSVNURVJFRCkKCQlwbGF0Zm9ybV9kZXZpY2VfdW5yZWdpc3RlcigmbW9jYV9sYW5fcGxhdF9kZXYpOwp9CiNlbmRpZgoKc3RhdGljIHZvaWQgbW9jYV8zNDUwX3dyaXRlKHN0cnVjdCBtb2NhX3ByaXZfZGF0YSAqcHJpdiwgdTggYWRkciwgdTMyIGRhdGEpCnsKCS8qIGNvbW1lbnQgb3V0IGZvciBub3cuIFdlIGRvbid0IHVzZSBpMmMgb24gdGhlIDYzMjY4QkhSIGJvYXJkICovCiNpZmRlZiBNT0NBXzM0NTBfVVNFX0kyQwoJaWYgKDApIC8qIChwcml2LT51c2Vfc3BpID09IDApICovCgkJYmNtMzQ1MF93cml0ZV9yZWcoYWRkciwgZGF0YSk7CgllbHNlCiNlbmRpZgoJewoJCWlmIChwcml2LT5pMmNfYmFzZSAhPSBOVUxMKQoJCQltb2NhXzM0NTBfd3JpdGVfaTJjKHByaXYsIGFkZHIsIGRhdGEpOwoJfQp9CgpzdGF0aWMgdTMyIG1vY2FfMzQ1MF9yZWFkKHN0cnVjdCBtb2NhX3ByaXZfZGF0YSAqcHJpdiwgdTggYWRkcikKewoJLyogY29tbWVudCBvdXQgZm9yIG5vdy4gV2UgZG9uJ3QgdXNlIGkyYyBvbiB0aGUgNjMyNjhCSFIgYm9hcmQgKi8KI2lmZGVmIE1PQ0FfMzQ1MF9VU0VfSTJDCglpZiAoMCkgLyogKHByaXYtPnVzZV9zcGkgPT0gMCkgKi8KCQlyZXR1cm4oYmNtMzQ1MF9yZWFkX3JlZyhhZGRyKSk7CgllbHNlCiNlbmRpZgoJewoJCWlmIChwcml2LT5pMmNfYmFzZSAhPSBOVUxMKQoJCQlyZXR1cm4obW9jYV8zNDUwX3JlYWRfaTJjKHByaXYsIGFkZHIpKTsKCQllbHNlCgkJCXJldHVybigweGZmZmZmZmZmKTsKCX0KfQo=