LyoKICoJRnVuY3Rpb25zIHRvIGhhbmRsZSBJMk8gY29udHJvbGxlcnMgYW5kIEkyTyBtZXNzYWdlIGhhbmRsaW5nCiAqCiAqCUNvcHlyaWdodCAoQykgMTk5OS0yMDAyCVJlZCBIYXQgU29mdHdhcmUKICoKICoJV3JpdHRlbiBieSBBbGFuIENveCwgQnVpbGRpbmcgTnVtYmVyIFRocmVlIEx0ZAogKgogKglUaGlzIHByb2dyYW0gaXMgZnJlZSBzb2Z0d2FyZTsgeW91IGNhbiByZWRpc3RyaWJ1dGUgaXQgYW5kL29yIG1vZGlmeSBpdAogKgl1bmRlciB0aGUgdGVybXMgb2YgdGhlIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlIGFzIHB1Ymxpc2hlZCBieSB0aGUKICoJRnJlZSBTb2Z0d2FyZSBGb3VuZGF0aW9uOyBlaXRoZXIgdmVyc2lvbiAyIG9mIHRoZSBMaWNlbnNlLCBvciAoYXQgeW91cgogKglvcHRpb24pIGFueSBsYXRlciB2ZXJzaW9uLgogKgogKglBIGxvdCBvZiB0aGUgSTJPIG1lc3NhZ2Ugc2lkZSBjb2RlIGZyb20gdGhpcyBpcyB0YWtlbiBmcm9tIHRoZQogKglSZWQgQ3JlZWsgUkNQQ0k0NSBhZGFwdGVyIGRyaXZlciBieSBSZWQgQ3JlZWsgQ29tbXVuaWNhdGlvbnMKICoKICoJRml4ZXMvYWRkaXRpb25zOgogKgkJUGhpbGlwcCBSdW1wZgogKgkJSnVoYSBTaWV25G5lbiA8SnVoYS5TaWV2YW5lbkBjcy5IZWxzaW5raS5GST4KICoJCUF1dm8gSORra2luZW4gPEF1dm8uSGFra2luZW5AY3MuSGVsc2lua2kuRkk+CiAqCQlEZWVwYWsgU2F4ZW5hIDxkZWVwYWtAcGxleGl0eS5uZXQ+CiAqCQlCb2ppIFQgS2FubmFudGhhbmFtIDxib2ppLnQua2FubmFudGhhbmFtQGludGVsLmNvbT4KICoJCUFsYW4gQ294IDxhbGFuQHJlZGhhdC5jb20+OgogKgkJCVBvcnRlZCB0byBMaW51eCAyLjUuCiAqCQlNYXJrdXMgTGlkZWwgPE1hcmt1cy5MaWRlbEBzaGFkb3djb25uZWN0LmNvbT46CiAqCQkJTWlub3IgZml4ZXMgZm9yIDIuNi4KICovCgojaW5jbHVkZSA8bGludXgvbW9kdWxlLmg+CiNpbmNsdWRlIDxsaW51eC9pMm8uaD4KI2luY2x1ZGUgPGxpbnV4L2RlbGF5Lmg+CgojZGVmaW5lIE9TTV9WRVJTSU9OCSIkUmV2JCIKI2RlZmluZSBPU01fREVTQ1JJUFRJT04JIkkyTyBzdWJzeXN0ZW0iCgovKiBnbG9iYWwgSTJPIGNvbnRyb2xsZXIgbGlzdCAqLwpMSVNUX0hFQUQoaTJvX2NvbnRyb2xsZXJzKTsKCi8qCiAqIGdsb2JhbCBJMk8gU3lzdGVtIFRhYmxlLiBDb250YWlucyBpbmZvcm1hdGlvbiBhYm91dCBhbGwgdGhlIElPUHMgaW4gdGhlCiAqIHN5c3RlbS4gVXNlZCB0byBpbmZvcm0gSU9QcyBhYm91dCBlYWNoIG90aGVycyBleGlzdGVuY2UuCiAqLwpzdGF0aWMgc3RydWN0IGkyb19kbWEgaTJvX3N5c3RhYjsKCnN0YXRpYyBpbnQgaTJvX2hydF9nZXQoc3RydWN0IGkyb19jb250cm9sbGVyICpjKTsKCi8qIE1vZHVsZSBpbnRlcm5hbCBmdW5jdGlvbnMgZnJvbSBvdGhlciBzb3VyY2VzICovCmV4dGVybiBzdHJ1Y3QgaTJvX2RyaXZlciBpMm9fZXhlY19kcml2ZXI7CmV4dGVybiBpbnQgaTJvX2V4ZWNfbGN0X2dldChzdHJ1Y3QgaTJvX2NvbnRyb2xsZXIgKik7CmV4dGVybiB2b2lkIGkyb19kZXZpY2VfcmVtb3ZlKHN0cnVjdCBpMm9fZGV2aWNlICopOwoKZXh0ZXJuIGludCBfX2luaXQgaTJvX2RyaXZlcl9pbml0KHZvaWQpOwpleHRlcm4gdm9pZCBfX2V4aXQgaTJvX2RyaXZlcl9leGl0KHZvaWQpOwpleHRlcm4gaW50IF9faW5pdCBpMm9fZXhlY19pbml0KHZvaWQpOwpleHRlcm4gdm9pZCBfX2V4aXQgaTJvX2V4ZWNfZXhpdCh2b2lkKTsKZXh0ZXJuIGludCBfX2luaXQgaTJvX3BjaV9pbml0KHZvaWQpOwpleHRlcm4gdm9pZCBfX2V4aXQgaTJvX3BjaV9leGl0KHZvaWQpOwpleHRlcm4gaW50IGkyb19kZXZpY2VfaW5pdCh2b2lkKTsKZXh0ZXJuIHZvaWQgaTJvX2RldmljZV9leGl0KHZvaWQpOwoKLyoqCiAqCWkyb19tc2dfbm9wIC0gUmV0dXJucyBhIG1lc3NhZ2Ugd2hpY2ggaXMgbm90IHVzZWQKICoJQGM6IEkyTyBjb250cm9sbGVyIGZyb20gd2hpY2ggdGhlIG1lc3NhZ2Ugd2FzIGNyZWF0ZWQKICoJQG06IG1lc3NhZ2Ugd2hpY2ggc2hvdWxkIGJlIHJldHVybmVkCiAqCiAqCUlmIHlvdSBmZXRjaCBhIG1lc3NhZ2UgdmlhIGkyb19tc2dfZ2V0LCBhbmQgY2FuJ3QgdXNlIGl0LCB5b3UgbXVzdAogKglyZXR1cm4gdGhlIG1lc3NhZ2Ugd2l0aCB0aGlzIGZ1bmN0aW9uLiBPdGhlcndpc2UgdGhlIG1lc3NhZ2UgZnJhbWUKICoJaXMgbG9zdC4KICovCnZvaWQgaTJvX21zZ19ub3Aoc3RydWN0IGkyb19jb250cm9sbGVyICpjLCB1MzIgbSkKewoJc3RydWN0IGkyb19tZXNzYWdlIF9faW9tZW0gKm1zZyA9IGkyb19tc2dfaW5fdG9fdmlydChjLCBtKTsKCgl3cml0ZWwoVEhSRUVfV09SRF9NU0dfU0laRSB8IFNHTF9PRkZTRVRfMCwgJm1zZy0+dS5oZWFkWzBdKTsKCXdyaXRlbChJMk9fQ01EX1VUSUxfTk9QIDw8IDI0IHwgSE9TVF9USUQgPDwgMTIgfCBBREFQVEVSX1RJRCwKCSAgICAgICAmbXNnLT51LmhlYWRbMV0pOwoJd3JpdGVsKDAsICZtc2ctPnUuaGVhZFsyXSk7Cgl3cml0ZWwoMCwgJm1zZy0+dS5oZWFkWzNdKTsKCWkyb19tc2dfcG9zdChjLCBtKTsKfTsKCi8qKgogKglpMm9fbXNnX2dldF93YWl0IC0gb2J0YWluIGFuIEkyTyBtZXNzYWdlIGZyb20gdGhlIElPUAogKglAYzogSTJPIGNvbnRyb2xsZXIKICoJQG1zZzogcG9pbnRlciB0byBhIEkyTyBtZXNzYWdlIHBvaW50ZXIKICoJQHdhaXQ6IGhvdyBsb25nIHRvIHdhaXQgdW50aWwgdGltZW91dAogKgogKglUaGlzIGZ1bmN0aW9uIHdhaXRzIHVwIHRvIHdhaXQgc2Vjb25kcyBmb3IgYSBtZXNzYWdlIHNsb3QgdG8gYmUKICoJYXZhaWxhYmxlLgogKgogKglPbiBhIHN1Y2Nlc3MgdGhlIG1lc3NhZ2UgaXMgcmV0dXJuZWQgYW5kIHRoZSBwb2ludGVyIHRvIHRoZSBtZXNzYWdlIGlzCiAqCXNldCBpbiBtc2cuIFRoZSByZXR1cm5lZCBtZXNzYWdlIGlzIHRoZSBwaHlzaWNhbCBwYWdlIGZyYW1lIG9mZnNldAogKglhZGRyZXNzIGZyb20gdGhlIHJlYWQgcG9ydCAoc2VlIHRoZSBpMm8gc3BlYykuIElmIG5vIG1lc3NhZ2UgaXMKICoJYXZhaWxhYmxlIHJldHVybnMgSTJPX1FVRVVFX0VNUFRZIGFuZCBtc2cgaXMgbGVhdmVkIHVudG91Y2hlZC4KICovCnUzMiBpMm9fbXNnX2dldF93YWl0KHN0cnVjdCBpMm9fY29udHJvbGxlciAqYywgc3RydWN0IGkyb19tZXNzYWdlIF9faW9tZW0gKiptc2csCgkJICAgICBpbnQgd2FpdCkKewoJdW5zaWduZWQgbG9uZyB0aW1lb3V0ID0gamlmZmllcyArIHdhaXQgKiBIWjsKCXUzMiBtOwoKCXdoaWxlICgobSA9IGkyb19tc2dfZ2V0KGMsIG1zZykpID09IEkyT19RVUVVRV9FTVBUWSkgewoJCWlmICh0aW1lX2FmdGVyKGppZmZpZXMsIHRpbWVvdXQpKSB7CgkJCXByX2RlYnVnKCIlczogVGltZW91dCB3YWl0aW5nIGZvciBtZXNzYWdlIGZyYW1lLlxuIiwKCQkJCSBjLT5uYW1lKTsKCQkJcmV0dXJuIEkyT19RVUVVRV9FTVBUWTsKCQl9CgkJc2V0X2N1cnJlbnRfc3RhdGUoVEFTS19VTklOVEVSUlVQVElCTEUpOwoJCXNjaGVkdWxlX3RpbWVvdXQoMSk7Cgl9CgoJcmV0dXJuIG07Cn07CgojaWYgQklUU19QRVJfTE9ORyA9PSA2NAovKioKICogICAgICBpMm9fY250eHRfbGlzdF9hZGQgLSBBcHBlbmQgYSBwb2ludGVyIHRvIGNvbnRleHQgbGlzdCBhbmQgcmV0dXJuIGEgaWQKICoJQGM6IGNvbnRyb2xsZXIgdG8gd2hpY2ggdGhlIGNvbnRleHQgbGlzdCBiZWxvbmcKICoJQHB0cjogcG9pbnRlciB0byBhZGQgdG8gdGhlIGNvbnRleHQgbGlzdAogKgogKglCZWNhdXNlIHRoZSBjb250ZXh0IGZpZWxkIGluIEkyTyBpcyBvbmx5IDMyLWJpdCBsYXJnZSwgb24gNjQtYml0IHRoZQogKglwb2ludGVyIGlzIHRvIGxhcmdlIHRvIGZpdCBpbiB0aGUgY29udGV4dCBmaWVsZC4gVGhlIGkyb19jbnR4dF9saXN0CiAqCWZ1bmN0aW9ucyB0aGVyZWZvcmUgbWFwIHBvaW50ZXJzIHRvIGNvbnRleHQgZmllbGRzLgogKgogKglSZXR1cm5zIGNvbnRleHQgaWQgPiAwIG9uIHN1Y2Nlc3Mgb3IgMCBvbiBmYWlsdXJlLgogKi8KdTMyIGkyb19jbnR4dF9saXN0X2FkZChzdHJ1Y3QgaTJvX2NvbnRyb2xsZXIgKiBjLCB2b2lkICpwdHIpCnsKCXN0cnVjdCBpMm9fY29udGV4dF9saXN0X2VsZW1lbnQgKmVudHJ5OwoJdW5zaWduZWQgbG9uZyBmbGFnczsKCglpZiAoIXB0cikKCQlwcmludGsoS0VSTl9FUlIgIiVzOiBjb3VsZG4ndCBhZGQgTlVMTCBwb2ludGVyIHRvIGNvbnRleHQgbGlzdCEiCgkJICAgICAgICJcbiIsIGMtPm5hbWUpOwoKCWVudHJ5ID0ga21hbGxvYyhzaXplb2YoKmVudHJ5KSwgR0ZQX0FUT01JQyk7CglpZiAoIWVudHJ5KSB7CgkJcHJpbnRrKEtFUk5fRVJSICIlczogQ291bGQgbm90IGFsbG9jYXRlIG1lbW9yeSBmb3IgY29udGV4dCAiCgkJICAgICAgICJsaXN0IGVsZW1lbnRcbiIsIGMtPm5hbWUpOwoJCXJldHVybiAwOwoJfQoKCWVudHJ5LT5wdHIgPSBwdHI7CgllbnRyeS0+dGltZXN0YW1wID0gamlmZmllczsKCUlOSVRfTElTVF9IRUFEKCZlbnRyeS0+bGlzdCk7CgoJc3Bpbl9sb2NrX2lycXNhdmUoJmMtPmNvbnRleHRfbGlzdF9sb2NrLCBmbGFncyk7CgoJaWYgKHVubGlrZWx5KGF0b21pY19pbmNfYW5kX3Rlc3QoJmMtPmNvbnRleHRfbGlzdF9jb3VudGVyKSkpCgkJYXRvbWljX2luYygmYy0+Y29udGV4dF9saXN0X2NvdW50ZXIpOwoKCWVudHJ5LT5jb250ZXh0ID0gYXRvbWljX3JlYWQoJmMtPmNvbnRleHRfbGlzdF9jb3VudGVyKTsKCglsaXN0X2FkZCgmZW50cnktPmxpc3QsICZjLT5jb250ZXh0X2xpc3QpOwoKCXNwaW5fdW5sb2NrX2lycXJlc3RvcmUoJmMtPmNvbnRleHRfbGlzdF9sb2NrLCBmbGFncyk7CgoJcHJfZGVidWcoIiVzOiBBZGQgY29udGV4dCB0byBsaXN0ICVwIC0+ICVkXG4iLCBjLT5uYW1lLCBwdHIsIGNvbnRleHQpOwoKCXJldHVybiBlbnRyeS0+Y29udGV4dDsKfTsKCi8qKgogKiAgICAgIGkyb19jbnR4dF9saXN0X3JlbW92ZSAtIFJlbW92ZSBhIHBvaW50ZXIgZnJvbSB0aGUgY29udGV4dCBsaXN0CiAqCUBjOiBjb250cm9sbGVyIHRvIHdoaWNoIHRoZSBjb250ZXh0IGxpc3QgYmVsb25nCiAqCUBwdHI6IHBvaW50ZXIgd2hpY2ggc2hvdWxkIGJlIHJlbW92ZWQgZnJvbSB0aGUgY29udGV4dCBsaXN0CiAqCiAqCVJlbW92ZXMgYSBwcmV2aW91c2x5IGFkZGVkIHBvaW50ZXIgZnJvbSB0aGUgY29udGV4dCBsaXN0IGFuZCByZXR1cm5zCiAqCXRoZSBtYXRjaGluZyBjb250ZXh0IGlkLgogKgogKglSZXR1cm5zIGNvbnRleHQgaWQgb24gc3VjY2VzIG9yIDAgb24gZmFpbHVyZS4KICovCnUzMiBpMm9fY250eHRfbGlzdF9yZW1vdmUoc3RydWN0IGkyb19jb250cm9sbGVyICogYywgdm9pZCAqcHRyKQp7CglzdHJ1Y3QgaTJvX2NvbnRleHRfbGlzdF9lbGVtZW50ICplbnRyeTsKCXUzMiBjb250ZXh0ID0gMDsKCXVuc2lnbmVkIGxvbmcgZmxhZ3M7CgoJc3Bpbl9sb2NrX2lycXNhdmUoJmMtPmNvbnRleHRfbGlzdF9sb2NrLCBmbGFncyk7CglsaXN0X2Zvcl9lYWNoX2VudHJ5KGVudHJ5LCAmYy0+Y29udGV4dF9saXN0LCBsaXN0KQoJICAgIGlmIChlbnRyeS0+cHRyID09IHB0cikgewoJCWxpc3RfZGVsKCZlbnRyeS0+bGlzdCk7CgkJY29udGV4dCA9IGVudHJ5LT5jb250ZXh0OwoJCWtmcmVlKGVudHJ5KTsKCQlicmVhazsKCX0KCXNwaW5fdW5sb2NrX2lycXJlc3RvcmUoJmMtPmNvbnRleHRfbGlzdF9sb2NrLCBmbGFncyk7CgoJaWYgKCFjb250ZXh0KQoJCXByaW50ayhLRVJOX1dBUk5JTkcgIiVzOiBDb3VsZCBub3QgcmVtb3ZlIG5vbmV4aXN0ZW50IHB0ciAiCgkJICAgICAgICIlcFxuIiwgYy0+bmFtZSwgcHRyKTsKCglwcl9kZWJ1ZygiJXM6IHJlbW92ZSBwdHIgZnJvbSBjb250ZXh0IGxpc3QgJWQgLT4gJXBcbiIsIGMtPm5hbWUsCgkJIGNvbnRleHQsIHB0cik7CgoJcmV0dXJuIGNvbnRleHQ7Cn07CgovKioKICogICAgICBpMm9fY250eHRfbGlzdF9nZXQgLSBHZXQgYSBwb2ludGVyIGZyb20gdGhlIGNvbnRleHQgbGlzdCBhbmQgcmVtb3ZlIGl0CiAqCUBjOiBjb250cm9sbGVyIHRvIHdoaWNoIHRoZSBjb250ZXh0IGxpc3QgYmVsb25nCiAqCUBjb250ZXh0OiBjb250ZXh0IGlkIHRvIHdoaWNoIHRoZSBwb2ludGVyIGJlbG9uZwogKgogKglSZXR1cm5zIHBvaW50ZXIgdG8gdGhlIG1hdGNoaW5nIGNvbnRleHQgaWQgb24gc3VjY2VzcyBvciBOVUxMIG9uCiAqCWZhaWx1cmUuCiAqLwp2b2lkICppMm9fY250eHRfbGlzdF9nZXQoc3RydWN0IGkyb19jb250cm9sbGVyICpjLCB1MzIgY29udGV4dCkKewoJc3RydWN0IGkyb19jb250ZXh0X2xpc3RfZWxlbWVudCAqZW50cnk7Cgl1bnNpZ25lZCBsb25nIGZsYWdzOwoJdm9pZCAqcHRyID0gTlVMTDsKCglzcGluX2xvY2tfaXJxc2F2ZSgmYy0+Y29udGV4dF9saXN0X2xvY2ssIGZsYWdzKTsKCWxpc3RfZm9yX2VhY2hfZW50cnkoZW50cnksICZjLT5jb250ZXh0X2xpc3QsIGxpc3QpCgkgICAgaWYgKGVudHJ5LT5jb250ZXh0ID09IGNvbnRleHQpIHsKCQlsaXN0X2RlbCgmZW50cnktPmxpc3QpOwoJCXB0ciA9IGVudHJ5LT5wdHI7CgkJa2ZyZWUoZW50cnkpOwoJCWJyZWFrOwoJfQoJc3Bpbl91bmxvY2tfaXJxcmVzdG9yZSgmYy0+Y29udGV4dF9saXN0X2xvY2ssIGZsYWdzKTsKCglpZiAoIXB0cikKCQlwcmludGsoS0VSTl9XQVJOSU5HICIlczogY29udGV4dCBpZCAlZCBub3QgZm91bmRcbiIsIGMtPm5hbWUsCgkJICAgICAgIGNvbnRleHQpOwoKCXByX2RlYnVnKCIlczogZ2V0IHB0ciBmcm9tIGNvbnRleHQgbGlzdCAlZCAtPiAlcFxuIiwgYy0+bmFtZSwgY29udGV4dCwKCQkgcHRyKTsKCglyZXR1cm4gcHRyOwp9OwoKLyoqCiAqICAgICAgaTJvX2NudHh0X2xpc3RfZ2V0X3B0ciAtIEdldCBhIGNvbnRleHQgaWQgZnJvbSB0aGUgY29udGV4dCBsaXN0CiAqCUBjOiBjb250cm9sbGVyIHRvIHdoaWNoIHRoZSBjb250ZXh0IGxpc3QgYmVsb25nCiAqCUBwdHI6IHBvaW50ZXIgdG8gd2hpY2ggdGhlIGNvbnRleHQgaWQgc2hvdWxkIGJlIGZldGNoZWQKICoKICoJUmV0dXJucyBjb250ZXh0IGlkIHdoaWNoIG1hdGNoZXMgdG8gdGhlIHBvaW50ZXIgb24gc3VjY2VzIG9yIDAgb24KICoJZmFpbHVyZS4KICovCnUzMiBpMm9fY250eHRfbGlzdF9nZXRfcHRyKHN0cnVjdCBpMm9fY29udHJvbGxlciAqIGMsIHZvaWQgKnB0cikKewoJc3RydWN0IGkyb19jb250ZXh0X2xpc3RfZWxlbWVudCAqZW50cnk7Cgl1MzIgY29udGV4dCA9IDA7Cgl1bnNpZ25lZCBsb25nIGZsYWdzOwoKCXNwaW5fbG9ja19pcnFzYXZlKCZjLT5jb250ZXh0X2xpc3RfbG9jaywgZmxhZ3MpOwoJbGlzdF9mb3JfZWFjaF9lbnRyeShlbnRyeSwgJmMtPmNvbnRleHRfbGlzdCwgbGlzdCkKCSAgICBpZiAoZW50cnktPnB0ciA9PSBwdHIpIHsKCQljb250ZXh0ID0gZW50cnktPmNvbnRleHQ7CgkJYnJlYWs7Cgl9CglzcGluX3VubG9ja19pcnFyZXN0b3JlKCZjLT5jb250ZXh0X2xpc3RfbG9jaywgZmxhZ3MpOwoKCWlmICghY29udGV4dCkKCQlwcmludGsoS0VSTl9XQVJOSU5HICIlczogQ291bGQgbm90IGZpbmQgbm9uZXhpc3RlbnQgcHRyICIKCQkgICAgICAgIiVwXG4iLCBjLT5uYW1lLCBwdHIpOwoKCXByX2RlYnVnKCIlczogZ2V0IGNvbnRleHQgaWQgZnJvbSBjb250ZXh0IGxpc3QgJXAgLT4gJWRcbiIsIGMtPm5hbWUsCgkJIHB0ciwgY29udGV4dCk7CgoJcmV0dXJuIGNvbnRleHQ7Cn07CiNlbmRpZgoKLyoqCiAqCWkyb19pb3BfZmluZCAtIEZpbmQgYW4gSTJPIGNvbnRyb2xsZXIgYnkgaWQKICoJQHVuaXQ6IHVuaXQgbnVtYmVyIG9mIHRoZSBJMk8gY29udHJvbGxlciB0byBzZWFyY2ggZm9yCiAqCiAqCUxvb2t1cCB0aGUgSTJPIGNvbnRyb2xsZXIgb24gdGhlIGNvbnRyb2xsZXIgbGlzdC4KICoKICoJUmV0dXJucyBwb2ludGVyIHRvIHRoZSBJMk8gY29udHJvbGxlciBvbiBzdWNjZXNzIG9yIE5VTEwgaWYgbm90IGZvdW5kLgogKi8Kc3RydWN0IGkyb19jb250cm9sbGVyICppMm9fZmluZF9pb3AoaW50IHVuaXQpCnsKCXN0cnVjdCBpMm9fY29udHJvbGxlciAqYzsKCglsaXN0X2Zvcl9lYWNoX2VudHJ5KGMsICZpMm9fY29udHJvbGxlcnMsIGxpc3QpIHsKCQlpZiAoYy0+dW5pdCA9PSB1bml0KQoJCQlyZXR1cm4gYzsKCX0KCglyZXR1cm4gTlVMTDsKfTsKCi8qKgogKglpMm9faW9wX2ZpbmRfZGV2aWNlIC0gRmluZCBhIEkyTyBkZXZpY2Ugb24gYW4gSTJPIGNvbnRyb2xsZXIKICoJQGM6IEkyTyBjb250cm9sbGVyIHdoZXJlIHRoZSBJMk8gZGV2aWNlIGhhbmdzIG9uCiAqCUB0aWQ6IFRJRCBvZiB0aGUgSTJPIGRldmljZSB0byBzZWFyY2ggZm9yCiAqCiAqCVNlYXJjaGVzIHRoZSBkZXZpY2VzIG9mIHRoZSBJMk8gY29udHJvbGxlciBmb3IgYSBkZXZpY2Ugd2l0aCBUSUQgdGlkIGFuZAogKglyZXR1cm5zIGl0LgogKgogKglSZXR1cm5zIGEgcG9pbnRlciB0byB0aGUgSTJPIGRldmljZSBpZiBmb3VuZCwgb3RoZXJ3aXNlIE5VTEwuCiAqLwpzdHJ1Y3QgaTJvX2RldmljZSAqaTJvX2lvcF9maW5kX2RldmljZShzdHJ1Y3QgaTJvX2NvbnRyb2xsZXIgKmMsIHUxNiB0aWQpCnsKCXN0cnVjdCBpMm9fZGV2aWNlICpkZXY7CgoJbGlzdF9mb3JfZWFjaF9lbnRyeShkZXYsICZjLT5kZXZpY2VzLCBsaXN0KQoJICAgIGlmIChkZXYtPmxjdF9kYXRhLnRpZCA9PSB0aWQpCgkJcmV0dXJuIGRldjsKCglyZXR1cm4gTlVMTDsKfTsKCi8qKgogKglpMm9fcXVpZXNjZV9jb250cm9sbGVyIC0gcXVpZXNjZSBjb250cm9sbGVyCiAqCUBjOiBjb250cm9sbGVyCiAqCiAqCVF1aWVzY2UgYW4gSU9QLiBDYXVzZXMgSU9QIHRvIG1ha2UgZXh0ZXJuYWwgb3BlcmF0aW9uIHF1aWVzY2VudAogKgkoaTJvICdSRUFEWScgc3RhdGUpLiBJbnRlcm5hbCBvcGVyYXRpb24gb2YgdGhlIElPUCBjb250aW51ZXMgbm9ybWFsbHkuCiAqCiAqCVJldHVybnMgMCBvbiBzdWNjZXNzIG9yIG5lZ2F0aXZlIGVycm9yIGNvZGUgb24gZmFpbHVyZS4KICovCnN0YXRpYyBpbnQgaTJvX2lvcF9xdWllc2NlKHN0cnVjdCBpMm9fY29udHJvbGxlciAqYykKewoJc3RydWN0IGkyb19tZXNzYWdlIF9faW9tZW0gKm1zZzsKCXUzMiBtOwoJaTJvX3N0YXR1c19ibG9jayAqc2IgPSBjLT5zdGF0dXNfYmxvY2sudmlydDsKCWludCByYzsKCglpMm9fc3RhdHVzX2dldChjKTsKCgkvKiBTeXNRdWllc2NlIGRpc2NhcmRlZCBpZiBJT1Agbm90IGluIFJFQURZIG9yIE9QRVJBVElPTkFMIHN0YXRlICovCglpZiAoKHNiLT5pb3Bfc3RhdGUgIT0gQURBUFRFUl9TVEFURV9SRUFEWSkgJiYKCSAgICAoc2ItPmlvcF9zdGF0ZSAhPSBBREFQVEVSX1NUQVRFX09QRVJBVElPTkFMKSkKCQlyZXR1cm4gMDsKCgltID0gaTJvX21zZ19nZXRfd2FpdChjLCAmbXNnLCBJMk9fVElNRU9VVF9NRVNTQUdFX0dFVCk7CglpZiAobSA9PSBJMk9fUVVFVUVfRU1QVFkpCgkJcmV0dXJuIC1FVElNRURPVVQ7CgoJd3JpdGVsKEZPVVJfV09SRF9NU0dfU0laRSB8IFNHTF9PRkZTRVRfMCwgJm1zZy0+dS5oZWFkWzBdKTsKCXdyaXRlbChJMk9fQ01EX1NZU19RVUlFU0NFIDw8IDI0IHwgSE9TVF9USUQgPDwgMTIgfCBBREFQVEVSX1RJRCwKCSAgICAgICAmbXNnLT51LmhlYWRbMV0pOwoKCS8qIExvbmcgdGltZW91dCBuZWVkZWQgZm9yIHF1aWVzY2UgaWYgbG90cyBvZiBkZXZpY2VzICovCglpZiAoKHJjID0gaTJvX21zZ19wb3N0X3dhaXQoYywgbSwgMjQwKSkpCgkJcHJpbnRrKEtFUk5fSU5GTyAiJXM6IFVuYWJsZSB0byBxdWllc2NlIChzdGF0dXM9JSN4KS5cbiIsCgkJICAgICAgIGMtPm5hbWUsIC1yYyk7CgllbHNlCgkJcHJfZGVidWcoIiVzOiBRdWllc2NlZC5cbiIsIGMtPm5hbWUpOwoKCWkyb19zdGF0dXNfZ2V0KGMpOwkvLyBFbnRlcmVkIFJFQURZIHN0YXRlCgoJcmV0dXJuIHJjOwp9OwoKLyoqCiAqCWkyb19pb3BfZW5hYmxlIC0gbW92ZSBjb250cm9sbGVyIGZyb20gcmVhZHkgdG8gT1BFUkFUSU9OQUwKICoJQGM6IEkyTyBjb250cm9sbGVyCiAqCiAqCUVuYWJsZSBJT1AuIFRoaXMgYWxsb3dzIHRoZSBJT1AgdG8gcmVzdW1lIGV4dGVybmFsIG9wZXJhdGlvbnMgYW5kCiAqCXJldmVyc2VzIHRoZSBlZmZlY3Qgb2YgYSBxdWllc2NlLiBSZXR1cm5zIHplcm8gb3IgYW4gZXJyb3IgY29kZSBpZgogKglhbiBlcnJvciBvY2N1cnMuCiAqLwpzdGF0aWMgaW50IGkyb19pb3BfZW5hYmxlKHN0cnVjdCBpMm9fY29udHJvbGxlciAqYykKewoJc3RydWN0IGkyb19tZXNzYWdlIF9faW9tZW0gKm1zZzsKCXUzMiBtOwoJaTJvX3N0YXR1c19ibG9jayAqc2IgPSBjLT5zdGF0dXNfYmxvY2sudmlydDsKCWludCByYzsKCglpMm9fc3RhdHVzX2dldChjKTsKCgkvKiBFbmFibGUgb25seSBhbGxvd2VkIG9uIFJFQURZIHN0YXRlICovCglpZiAoc2ItPmlvcF9zdGF0ZSAhPSBBREFQVEVSX1NUQVRFX1JFQURZKQoJCXJldHVybiAtRUlOVkFMOwoKCW0gPSBpMm9fbXNnX2dldF93YWl0KGMsICZtc2csIEkyT19USU1FT1VUX01FU1NBR0VfR0VUKTsKCWlmIChtID09IEkyT19RVUVVRV9FTVBUWSkKCQlyZXR1cm4gLUVUSU1FRE9VVDsKCgl3cml0ZWwoRk9VUl9XT1JEX01TR19TSVpFIHwgU0dMX09GRlNFVF8wLCAmbXNnLT51LmhlYWRbMF0pOwoJd3JpdGVsKEkyT19DTURfU1lTX0VOQUJMRSA8PCAyNCB8IEhPU1RfVElEIDw8IDEyIHwgQURBUFRFUl9USUQsCgkgICAgICAgJm1zZy0+dS5oZWFkWzFdKTsKCgkvKiBIb3cgbG9uZyBvZiBhIHRpbWVvdXQgZG8gd2UgbmVlZD8gKi8KCWlmICgocmMgPSBpMm9fbXNnX3Bvc3Rfd2FpdChjLCBtLCAyNDApKSkKCQlwcmludGsoS0VSTl9FUlIgIiVzOiBDb3VsZCBub3QgZW5hYmxlIChzdGF0dXM9JSN4KS5cbiIsCgkJICAgICAgIGMtPm5hbWUsIC1yYyk7CgllbHNlCgkJcHJfZGVidWcoIiVzOiBFbmFibGVkLlxuIiwgYy0+bmFtZSk7CgoJaTJvX3N0YXR1c19nZXQoYyk7CS8vIGVudGVyZWQgT1BFUkFUSU9OQUwgc3RhdGUKCglyZXR1cm4gcmM7Cn07CgovKioKICoJaTJvX2lvcF9xdWllc2NlX2FsbCAtIFF1aWVzY2UgYWxsIEkyTyBjb250cm9sbGVycyBvbiB0aGUgc3lzdGVtCiAqCiAqCVF1aWVzY2UgYWxsIEkyTyBjb250cm9sbGVycyB3aGljaCBhcmUgY29ubmVjdGVkIHRvIHRoZSBzeXN0ZW0uCiAqLwpzdGF0aWMgaW5saW5lIHZvaWQgaTJvX2lvcF9xdWllc2NlX2FsbCh2b2lkKQp7CglzdHJ1Y3QgaTJvX2NvbnRyb2xsZXIgKmMsICp0bXA7CgoJbGlzdF9mb3JfZWFjaF9lbnRyeV9zYWZlKGMsIHRtcCwgJmkyb19jb250cm9sbGVycywgbGlzdCkgewoJCWlmICghYy0+bm9fcXVpZXNjZSkKCQkJaTJvX2lvcF9xdWllc2NlKGMpOwoJfQp9OwoKLyoqCiAqCWkyb19pb3BfZW5hYmxlX2FsbCAtIEVuYWJsZXMgYWxsIGNvbnRyb2xsZXJzIG9uIHRoZSBzeXN0ZW0KICoKICoJRW5hYmxlcyBhbGwgSTJPIGNvbnRyb2xsZXJzIHdoaWNoIGFyZSBjb25uZWN0ZWQgdG8gdGhlIHN5c3RlbS4KICovCnN0YXRpYyBpbmxpbmUgdm9pZCBpMm9faW9wX2VuYWJsZV9hbGwodm9pZCkKewoJc3RydWN0IGkyb19jb250cm9sbGVyICpjLCAqdG1wOwoKCWxpc3RfZm9yX2VhY2hfZW50cnlfc2FmZShjLCB0bXAsICZpMm9fY29udHJvbGxlcnMsIGxpc3QpCgkgICAgaTJvX2lvcF9lbmFibGUoYyk7Cn07CgovKioKICoJaTJvX2NsZWFyX2NvbnRyb2xsZXIgLSBCcmluZyBJMk8gY29udHJvbGxlciBpbnRvIEhPTEQgc3RhdGUKICoJQGM6IGNvbnRyb2xsZXIKICoKICoJQ2xlYXIgYW4gSU9QIHRvIEhPTEQgc3RhdGUsIGllLiB0ZXJtaW5hdGUgZXh0ZXJuYWwgb3BlcmF0aW9ucywgY2xlYXIgYWxsCiAqCWlucHV0IHF1ZXVlcyBhbmQgcHJlcGFyZSBmb3IgYSBzeXN0ZW0gcmVzdGFydC4gSU9QJ3MgaW50ZXJuYWwgb3BlcmF0aW9uCiAqCWNvbnRpbnVlcyBub3JtYWxseSBhbmQgdGhlIG91dGJvdW5kIHF1ZXVlIGlzIGFsaXZlLiBUaGUgSU9QIGlzIG5vdAogKglleHBlY3RlZCB0byByZWJ1aWxkIGl0cyBMQ1QuCiAqCiAqCVJldHVybnMgMCBvbiBzdWNjZXNzIG9yIG5lZ2F0aXZlIGVycm9yIGNvZGUgb24gZmFpbHVyZS4KICovCnN0YXRpYyBpbnQgaTJvX2lvcF9jbGVhcihzdHJ1Y3QgaTJvX2NvbnRyb2xsZXIgKmMpCnsKCXN0cnVjdCBpMm9fbWVzc2FnZSBfX2lvbWVtICptc2c7Cgl1MzIgbTsKCWludCByYzsKCgltID0gaTJvX21zZ19nZXRfd2FpdChjLCAmbXNnLCBJMk9fVElNRU9VVF9NRVNTQUdFX0dFVCk7CglpZiAobSA9PSBJMk9fUVVFVUVfRU1QVFkpCgkJcmV0dXJuIC1FVElNRURPVVQ7CgoJLyogUXVpZXNjZSBhbGwgSU9QcyBmaXJzdCAqLwoJaTJvX2lvcF9xdWllc2NlX2FsbCgpOwoKCXdyaXRlbChGT1VSX1dPUkRfTVNHX1NJWkUgfCBTR0xfT0ZGU0VUXzAsICZtc2ctPnUuaGVhZFswXSk7Cgl3cml0ZWwoSTJPX0NNRF9BREFQVEVSX0NMRUFSIDw8IDI0IHwgSE9TVF9USUQgPDwgMTIgfCBBREFQVEVSX1RJRCwKCSAgICAgICAmbXNnLT51LmhlYWRbMV0pOwoKCWlmICgocmMgPSBpMm9fbXNnX3Bvc3Rfd2FpdChjLCBtLCAzMCkpKQoJCXByaW50ayhLRVJOX0lORk8gIiVzOiBVbmFibGUgdG8gY2xlYXIgKHN0YXR1cz0lI3gpLlxuIiwKCQkgICAgICAgYy0+bmFtZSwgLXJjKTsKCWVsc2UKCQlwcl9kZWJ1ZygiJXM6IENsZWFyZWQuXG4iLCBjLT5uYW1lKTsKCgkvKiBFbmFibGUgYWxsIElPUHMgKi8KCWkyb19pb3BfZW5hYmxlX2FsbCgpOwoKCXJldHVybiByYzsKfQoKLyoqCiAqCWkyb19pb3BfaW5pdF9vdXRib3VuZF9xdWV1ZSAtIHNldHVwIHRoZSBvdXRib3VuZCBtZXNzYWdlIHF1ZXVlCiAqCUBjOiBJMk8gY29udHJvbGxlcgogKgogKglDbGVhciBhbmQgKHJlKWluaXRpYWxpemUgSU9QJ3Mgb3V0Ym91bmQgcXVldWUgYW5kIHBvc3QgdGhlIG1lc3NhZ2UKICoJZnJhbWVzIHRvIHRoZSBJT1AuCiAqCiAqCVJldHVybnMgMCBvbiBzdWNjZXNzIG9yIGEgbmVnYXRpdmUgZXJybm8gY29kZSBvbiBmYWlsdXJlLgogKi8Kc3RhdGljIGludCBpMm9faW9wX2luaXRfb3V0Ym91bmRfcXVldWUoc3RydWN0IGkyb19jb250cm9sbGVyICpjKQp7Cgl1OCAqc3RhdHVzID0gYy0+c3RhdHVzLnZpcnQ7Cgl1MzIgbTsKCXN0cnVjdCBpMm9fbWVzc2FnZSBfX2lvbWVtICptc2c7Cgl1bG9uZyB0aW1lb3V0OwoJaW50IGk7CgoJb3NtX2RlYnVnKCIlczogSW5pdGlhbGl6aW5nIE91dGJvdW5kIFF1ZXVlLi4uXG4iLCBjLT5uYW1lKTsKCgltZW1zZXQoc3RhdHVzLCAwLCA0KTsKCgltID0gaTJvX21zZ19nZXRfd2FpdChjLCAmbXNnLCBJMk9fVElNRU9VVF9NRVNTQUdFX0dFVCk7CglpZiAobSA9PSBJMk9fUVVFVUVfRU1QVFkpCgkJcmV0dXJuIC1FVElNRURPVVQ7CgoJd3JpdGVsKEVJR0hUX1dPUkRfTVNHX1NJWkUgfCBUUkxfT0ZGU0VUXzYsICZtc2ctPnUuaGVhZFswXSk7Cgl3cml0ZWwoSTJPX0NNRF9PVVRCT1VORF9JTklUIDw8IDI0IHwgSE9TVF9USUQgPDwgMTIgfCBBREFQVEVSX1RJRCwKCSAgICAgICAmbXNnLT51LmhlYWRbMV0pOwoJd3JpdGVsKGkyb19leGVjX2RyaXZlci5jb250ZXh0LCAmbXNnLT51LnMuaWNudHh0KTsKCXdyaXRlbCgweDAxMDYsICZtc2ctPnUucy50Y250eHQpOwkvKiBGSVhNRTogd2h5IDB4MDEwNiwgbWF5YmUgaW4KCQkJCQkJICAgU3BlYz8gKi8KCXdyaXRlbChQQUdFX1NJWkUsICZtc2ctPmJvZHlbMF0pOwoJLyogT3V0Ym91bmQgbXNnIGZyYW1lIHNpemUgaW4gd29yZHMgYW5kIEluaXRjb2RlICovCgl3cml0ZWwoTVNHX0ZSQU1FX1NJWkUgPDwgMTYgfCAweDgwLCAmbXNnLT5ib2R5WzFdKTsKCXdyaXRlbCgweGQwMDAwMDA0LCAmbXNnLT5ib2R5WzJdKTsKCXdyaXRlbChpMm9fZG1hX2xvdyhjLT5zdGF0dXMucGh5cyksICZtc2ctPmJvZHlbM10pOwoJd3JpdGVsKGkyb19kbWFfaGlnaChjLT5zdGF0dXMucGh5cyksICZtc2ctPmJvZHlbNF0pOwoKCWkyb19tc2dfcG9zdChjLCBtKTsKCgl0aW1lb3V0ID0gamlmZmllcyArIEkyT19USU1FT1VUX0lOSVRfT1VUQk9VTkRfUVVFVUUgKiBIWjsKCXdoaWxlICgqc3RhdHVzIDw9IEkyT19DTURfSU5fUFJPR1JFU1MpIHsKCQlpZiAodGltZV9hZnRlcihqaWZmaWVzLCB0aW1lb3V0KSkgewoJCQlvc21fd2FybigiJXM6IFRpbWVvdXQgSW5pdGlhbGl6aW5nXG4iLCBjLT5uYW1lKTsKCQkJcmV0dXJuIC1FVElNRURPVVQ7CgkJfQoJCXNldF9jdXJyZW50X3N0YXRlKFRBU0tfVU5JTlRFUlJVUFRJQkxFKTsKCQlzY2hlZHVsZV90aW1lb3V0KDEpOwoKCQlybWIoKTsKCX0KCgltID0gYy0+b3V0X3F1ZXVlLnBoeXM7CgoJLyogUG9zdCBmcmFtZXMgKi8KCWZvciAoaSA9IDA7IGkgPCBOTUJSX01TR19GUkFNRVM7IGkrKykgewoJCWkyb19mbHVzaF9yZXBseShjLCBtKTsKCQl1ZGVsYXkoMSk7CS8qIFByb21pc2UgKi8KCQltICs9IE1TR19GUkFNRV9TSVpFICogNDsKCX0KCglyZXR1cm4gMDsKfQoKLyoqCiAqCWkyb19pb3BfcmVzZXQgLSByZXNldCBhbiBJMk8gY29udHJvbGxlcgogKglAYzogY29udHJvbGxlciB0byByZXNldAogKgogKglSZXNldCB0aGUgSU9QIGludG8gSU5JVCBzdGF0ZSBhbmQgd2FpdCB1bnRpbCBJT1AgZ2V0cyBpbnRvIFJFU0VUIHN0YXRlLgogKglUZXJtaW5hdGUgYWxsIGV4dGVybmFsIG9wZXJhdGlvbnMsIGNsZWFyIElPUCdzIGluYm91bmQgYW5kIG91dGJvdW5kCiAqCXF1ZXVlcywgdGVybWluYXRlIGFsbCBERE1zLCBhbmQgcmVsb2FkIHRoZSBJT1AncyBvcGVyYXRpbmcgZW52aXJvbm1lbnQKICoJYW5kIGFsbCBsb2NhbCBERE1zLiBUaGUgSU9QIHJlYnVpbGRzIGl0cyBMQ1QuCiAqLwpzdGF0aWMgaW50IGkyb19pb3BfcmVzZXQoc3RydWN0IGkyb19jb250cm9sbGVyICpjKQp7Cgl1OCAqc3RhdHVzID0gYy0+c3RhdHVzLnZpcnQ7CglzdHJ1Y3QgaTJvX21lc3NhZ2UgX19pb21lbSAqbXNnOwoJdTMyIG07Cgl1bnNpZ25lZCBsb25nIHRpbWVvdXQ7CglpMm9fc3RhdHVzX2Jsb2NrICpzYiA9IGMtPnN0YXR1c19ibG9jay52aXJ0OwoJaW50IHJjID0gMDsKCglwcl9kZWJ1ZygiJXM6IFJlc2V0dGluZyBjb250cm9sbGVyXG4iLCBjLT5uYW1lKTsKCgltID0gaTJvX21zZ19nZXRfd2FpdChjLCAmbXNnLCBJMk9fVElNRU9VVF9NRVNTQUdFX0dFVCk7CglpZiAobSA9PSBJMk9fUVVFVUVfRU1QVFkpCgkJcmV0dXJuIC1FVElNRURPVVQ7CgoJbWVtc2V0KHN0YXR1cywgMCwgOCk7CgoJLyogUXVpZXNjZSBhbGwgSU9QcyBmaXJzdCAqLwoJaTJvX2lvcF9xdWllc2NlX2FsbCgpOwoKCXdyaXRlbChFSUdIVF9XT1JEX01TR19TSVpFIHwgU0dMX09GRlNFVF8wLCAmbXNnLT51LmhlYWRbMF0pOwoJd3JpdGVsKEkyT19DTURfQURBUFRFUl9SRVNFVCA8PCAyNCB8IEhPU1RfVElEIDw8IDEyIHwgQURBUFRFUl9USUQsCgkgICAgICAgJm1zZy0+dS5oZWFkWzFdKTsKCXdyaXRlbChpMm9fZXhlY19kcml2ZXIuY29udGV4dCwgJm1zZy0+dS5zLmljbnR4dCk7Cgl3cml0ZWwoMCwgJm1zZy0+dS5zLnRjbnR4dCk7CS8vRklYTUU6IHVzZSByZWFzb25hYmxlIHRyYW5zYWN0aW9uIGNvbnRleHQKCXdyaXRlbCgwLCAmbXNnLT5ib2R5WzBdKTsKCXdyaXRlbCgwLCAmbXNnLT5ib2R5WzFdKTsKCXdyaXRlbChpMm9fZG1hX2xvdyhjLT5zdGF0dXMucGh5cyksICZtc2ctPmJvZHlbMl0pOwoJd3JpdGVsKGkyb19kbWFfaGlnaChjLT5zdGF0dXMucGh5cyksICZtc2ctPmJvZHlbM10pOwoKCWkyb19tc2dfcG9zdChjLCBtKTsKCgkvKiBXYWl0IGZvciBhIHJlcGx5ICovCgl0aW1lb3V0ID0gamlmZmllcyArIEkyT19USU1FT1VUX1JFU0VUICogSFo7Cgl3aGlsZSAoISpzdGF0dXMpIHsKCQlpZiAodGltZV9hZnRlcihqaWZmaWVzLCB0aW1lb3V0KSkKCQkJYnJlYWs7CgoJCXNldF9jdXJyZW50X3N0YXRlKFRBU0tfVU5JTlRFUlJVUFRJQkxFKTsKCQlzY2hlZHVsZV90aW1lb3V0KDEpOwoKCQlybWIoKTsKCX0KCglzd2l0Y2ggKCpzdGF0dXMpIHsKCWNhc2UgSTJPX0NNRF9SRUpFQ1RFRDoKCQlvc21fd2FybigiJXM6IElPUCByZXNldCByZWplY3RlZFxuIiwgYy0+bmFtZSk7CgkJcmMgPSAtRVBFUk07CgkJYnJlYWs7CgoJY2FzZSBJMk9fQ01EX0lOX1BST0dSRVNTOgoJCS8qCgkJICogT25jZSB0aGUgcmVzZXQgaXMgc2VudCwgdGhlIElPUCBnb2VzIGludG8gdGhlIElOSVQgc3RhdGUKCQkgKiB3aGljaCBpcyBpbmRldGVybWluYXRlLiBXZSBuZWVkIHRvIHdhaXQgdW50aWwgdGhlIElPUCBoYXMKCQkgKiByZWJvb3RlZCBiZWZvcmUgd2UgY2FuIGxldCB0aGUgc3lzdGVtIHRhbGsgdG8gaXQuIFdlIHJlYWQKCQkgKiB0aGUgaW5ib3VuZCBGcmVlX0xpc3QgdW50aWwgYSBtZXNzYWdlIGlzIGF2YWlsYWJsZS4gSWYgd2UKCQkgKiBjYW4ndCByZWFkIG9uZSBpbiB0aGUgZ2l2ZW4gYW1tb3VudCBvZiB0aW1lLCB3ZSBhc3N1bWUgdGhlCgkJICogSU9QIGNvdWxkIG5vdCByZWJvb3QgcHJvcGVybHkuCgkJICovCgkJcHJfZGVidWcoIiVzOiBSZXNldCBpbiBwcm9ncmVzcywgd2FpdGluZyBmb3IgcmVib290Li4uXG4iLAoJCQkgYy0+bmFtZSk7CgoJCW0gPSBpMm9fbXNnX2dldF93YWl0KGMsICZtc2csIEkyT19USU1FT1VUX1JFU0VUKTsKCQl3aGlsZSAobSA9PSBJMk9fUVVFVUVfRU1QVFkpIHsKCQkJaWYgKHRpbWVfYWZ0ZXIoamlmZmllcywgdGltZW91dCkpIHsKCQkJCXByaW50ayhLRVJOX0VSUiAiJXM6IElPUCByZXNldCB0aW1lb3V0LlxuIiwKCQkJCSAgICAgICBjLT5uYW1lKTsKCQkJCXJjID0gLUVUSU1FRE9VVDsKCQkJCWdvdG8gZXhpdDsKCQkJfQoJCQlzZXRfY3VycmVudF9zdGF0ZShUQVNLX1VOSU5URVJSVVBUSUJMRSk7CgkJCXNjaGVkdWxlX3RpbWVvdXQoMSk7CgoJCQltID0gaTJvX21zZ19nZXRfd2FpdChjLCAmbXNnLCBJMk9fVElNRU9VVF9SRVNFVCk7CgkJfQoJCWkyb19tc2dfbm9wKGMsIG0pOwoKCQkvKiBmcm9tIGhlcmUgYWxsIHF1aWVzY2UgY29tbWFuZHMgYXJlIHNhZmUgKi8KCQljLT5ub19xdWllc2NlID0gMDsKCgkJLyogdmVyaWZ5IGlmIGNvbnRyb2xsZXIgaXMgaW4gc3RhdGUgUkVTRVQgKi8KCQlpMm9fc3RhdHVzX2dldChjKTsKCgkJaWYgKCFjLT5wcm9taXNlICYmIChzYi0+aW9wX3N0YXRlICE9IEFEQVBURVJfU1RBVEVfUkVTRVQpKQoJCQlvc21fd2FybigiJXM6IHJlc2V0IGNvbXBsZXRlZCwgYnV0IGFkYXB0ZXIgbm90IGluIFJFU0VUIgoJCQkJICIgc3RhdGUuXG4iLCBjLT5uYW1lKTsKCQllbHNlCgkJCW9zbV9kZWJ1ZygiJXM6IHJlc2V0IGNvbXBsZXRlZC5cbiIsIGMtPm5hbWUpOwoKCQlicmVhazsKCglkZWZhdWx0OgoJCW9zbV9lcnIoIiVzOiBJT1AgcmVzZXQgdGltZW91dC5cbiIsIGMtPm5hbWUpOwoJCXJjID0gLUVUSU1FRE9VVDsKCQlicmVhazsKCX0KCiAgICAgIGV4aXQ6CgkvKiBFbmFibGUgYWxsIElPUHMgKi8KCWkyb19pb3BfZW5hYmxlX2FsbCgpOwoKCXJldHVybiByYzsKfTsKCi8qKgogKglpMm9faW9wX2FjdGl2YXRlIC0gQnJpbmcgY29udHJvbGxlciB1cCB0byBIT0xECiAqCUBjOiBjb250cm9sbGVyCiAqCiAqCVRoaXMgZnVuY3Rpb24gYnJpbmdzIGFuIEkyTyBjb250cm9sbGVyIGludG8gSE9MRCBzdGF0ZS4gVGhlIGFkYXB0ZXIKICoJaXMgcmVzZXQgaWYgbmVjZXNzYXJ5IGFuZCB0aGVuIHRoZSBxdWV1ZXMgYW5kIHJlc291cmNlIHRhYmxlIGFyZSByZWFkLgogKgogKglSZXR1cm5zIDAgb24gc3VjY2VzcyBvciBuZWdhdGl2ZSBlcnJvciBjb2RlIG9uIGZhaWx1cmUuCiAqLwpzdGF0aWMgaW50IGkyb19pb3BfYWN0aXZhdGUoc3RydWN0IGkyb19jb250cm9sbGVyICpjKQp7CglpMm9fc3RhdHVzX2Jsb2NrICpzYiA9IGMtPnN0YXR1c19ibG9jay52aXJ0OwoJaW50IHJjOwoJaW50IHN0YXRlOwoKCS8qIEluIElOSVQgc3RhdGUsIFdhaXQgSW5ib3VuZCBRIHRvIGluaXRpYWxpemUgKGluIGkyb19zdGF0dXNfZ2V0KSAqLwoJLyogSW4gUkVBRFkgc3RhdGUsIEdldCBzdGF0dXMgKi8KCglyYyA9IGkyb19zdGF0dXNfZ2V0KGMpOwoJaWYgKHJjKSB7CgkJcHJpbnRrKEtFUk5fSU5GTyAiJXM6IFVuYWJsZSB0byBvYnRhaW4gc3RhdHVzLCAiCgkJICAgICAgICJhdHRlbXB0aW5nIGEgcmVzZXQuXG4iLCBjLT5uYW1lKTsKCQlyYyA9IGkyb19pb3BfcmVzZXQoYyk7CgkJaWYgKHJjKQoJCQlyZXR1cm4gcmM7Cgl9CgoJaWYgKHNiLT5pMm9fdmVyc2lvbiA+IEkyT1ZFUjE1KSB7CgkJcHJpbnRrKEtFUk5fRVJSICIlczogTm90IHJ1bm5pbmcgdmVyc2lvbiAxLjUgb2YgdGhlIEkyTyAiCgkJICAgICAgICJTcGVjaWZpY2F0aW9uLlxuIiwgYy0+bmFtZSk7CgkJcmV0dXJuIC1FTk9ERVY7Cgl9CgoJc3dpdGNoIChzYi0+aW9wX3N0YXRlKSB7CgljYXNlIEFEQVBURVJfU1RBVEVfRkFVTFRFRDoKCQlwcmludGsoS0VSTl9DUklUICIlczogaGFyZHdhcmUgZmF1bHRcbiIsIGMtPm5hbWUpOwoJCXJldHVybiAtRUZBVUxUOwoKCWNhc2UgQURBUFRFUl9TVEFURV9SRUFEWToKCWNhc2UgQURBUFRFUl9TVEFURV9PUEVSQVRJT05BTDoKCWNhc2UgQURBUFRFUl9TVEFURV9IT0xEOgoJY2FzZSBBREFQVEVSX1NUQVRFX0ZBSUxFRDoKCQlwcl9kZWJ1ZygiJXM6IGFscmVhZHkgcnVubmluZywgdHJ5aW5nIHRvIHJlc2V0Li4uXG4iLCBjLT5uYW1lKTsKCQlyYyA9IGkyb19pb3BfcmVzZXQoYyk7CgkJaWYgKHJjKQoJCQlyZXR1cm4gcmM7Cgl9CgoJLyogcHJlc2VydmUgc3RhdGUgKi8KCXN0YXRlID0gc2ItPmlvcF9zdGF0ZTsKCglyYyA9IGkyb19pb3BfaW5pdF9vdXRib3VuZF9xdWV1ZShjKTsKCWlmIChyYykKCQlyZXR1cm4gcmM7CgoJLyogaWYgYWRhcHRlciB3YXMgbm90IGluIFJFU0VUIHN0YXRlIGNsZWFyIG5vdyAqLwoJaWYgKHN0YXRlICE9IEFEQVBURVJfU1RBVEVfUkVTRVQpCgkJaTJvX2lvcF9jbGVhcihjKTsKCglpMm9fc3RhdHVzX2dldChjKTsKCglpZiAoc2ItPmlvcF9zdGF0ZSAhPSBBREFQVEVSX1NUQVRFX0hPTEQpIHsKCQlvc21fZXJyKCIlczogZmFpbGVkIHRvIGJyaW5nIElPUCBpbnRvIEhPTEQgc3RhdGVcbiIsIGMtPm5hbWUpOwoJCXJldHVybiAtRUlPOwoJfQoKCXJldHVybiBpMm9faHJ0X2dldChjKTsKfTsKCi8qKgogKglpMm9faW9wX3N5c3RhYl9zZXQgLSBTZXQgdGhlIEkyTyBTeXN0ZW0gVGFibGUgb2YgdGhlIHNwZWNpZmllZCBJT1AKICoJQGM6IEkyTyBjb250cm9sbGVyIHRvIHdoaWNoIHRoZSBzeXN0ZW0gdGFibGUgc2hvdWxkIGJlIHNlbmQKICoKICoJQmVmb3JlIHRoZSBzeXN0YWIgY291bGQgYmUgc2V0IGkyb19zeXN0YWJfYnVpbGQoKSBtdXN0IGJlIGNhbGxlZC4KICoKICoJUmV0dXJucyAwIG9uIHN1Y2Nlc3Mgb3IgbmVnYXRpdmUgZXJyb3IgY29kZSBvbiBmYWlsdXJlLgogKi8Kc3RhdGljIGludCBpMm9faW9wX3N5c3RhYl9zZXQoc3RydWN0IGkyb19jb250cm9sbGVyICpjKQp7CglzdHJ1Y3QgaTJvX21lc3NhZ2UgX19pb21lbSAqbXNnOwoJdTMyIG07CglpMm9fc3RhdHVzX2Jsb2NrICpzYiA9IGMtPnN0YXR1c19ibG9jay52aXJ0OwoJc3RydWN0IGRldmljZSAqZGV2ID0gJmMtPnBkZXYtPmRldjsKCXN0cnVjdCByZXNvdXJjZSAqcm9vdDsKCWludCByYzsKCglpZiAoc2ItPmN1cnJlbnRfbWVtX3NpemUgPCBzYi0+ZGVzaXJlZF9tZW1fc2l6ZSkgewoJCXN0cnVjdCByZXNvdXJjZSAqcmVzID0gJmMtPm1lbV9yZXNvdXJjZTsKCQlyZXMtPm5hbWUgPSBjLT5wZGV2LT5idXMtPm5hbWU7CgkJcmVzLT5mbGFncyA9IElPUkVTT1VSQ0VfTUVNOwoJCXJlcy0+c3RhcnQgPSAwOwoJCXJlcy0+ZW5kID0gMDsKCQlwcmludGsoS0VSTl9JTkZPICIlczogcmVxdWlyZXMgcHJpdmF0ZSBtZW1vcnkgcmVzb3VyY2VzLlxuIiwKCQkgICAgICAgYy0+bmFtZSk7CgkJcm9vdCA9IHBjaV9maW5kX3BhcmVudF9yZXNvdXJjZShjLT5wZGV2LCByZXMpOwoJCWlmIChyb290ID09IE5VTEwpCgkJCXByaW50ayhLRVJOX1dBUk5JTkcgIiVzOiBDYW4ndCBmaW5kIHBhcmVudCByZXNvdXJjZSFcbiIsCgkJCSAgICAgICBjLT5uYW1lKTsKCQlpZiAocm9vdCAmJiBhbGxvY2F0ZV9yZXNvdXJjZShyb290LCByZXMsIHNiLT5kZXNpcmVkX21lbV9zaXplLCBzYi0+ZGVzaXJlZF9tZW1fc2l6ZSwgc2ItPmRlc2lyZWRfbWVtX3NpemUsIDEgPDwgMjAsCS8qIFVuc3BlY2lmaWVkLCBzbyB1c2UgMU1iIGFuZCBwbGF5IHNhZmUgKi8KCQkJCQkgICAgICBOVUxMLCBOVUxMKSA+PSAwKSB7CgkJCWMtPm1lbV9hbGxvYyA9IDE7CgkJCXNiLT5jdXJyZW50X21lbV9zaXplID0gMSArIHJlcy0+ZW5kIC0gcmVzLT5zdGFydDsKCQkJc2ItPmN1cnJlbnRfbWVtX2Jhc2UgPSByZXMtPnN0YXJ0OwoJCQlwcmludGsoS0VSTl9JTkZPICIlczogYWxsb2NhdGVkICVsZCBieXRlcyBvZiBQQ0kgbWVtb3J5IgoJCQkgICAgICAgIiBhdCAweCUwOGxYLlxuIiwgYy0+bmFtZSwKCQkJICAgICAgIDEgKyByZXMtPmVuZCAtIHJlcy0+c3RhcnQsIHJlcy0+c3RhcnQpOwoJCX0KCX0KCglpZiAoc2ItPmN1cnJlbnRfaW9fc2l6ZSA8IHNiLT5kZXNpcmVkX2lvX3NpemUpIHsKCQlzdHJ1Y3QgcmVzb3VyY2UgKnJlcyA9ICZjLT5pb19yZXNvdXJjZTsKCQlyZXMtPm5hbWUgPSBjLT5wZGV2LT5idXMtPm5hbWU7CgkJcmVzLT5mbGFncyA9IElPUkVTT1VSQ0VfSU87CgkJcmVzLT5zdGFydCA9IDA7CgkJcmVzLT5lbmQgPSAwOwoJCXByaW50ayhLRVJOX0lORk8gIiVzOiByZXF1aXJlcyBwcml2YXRlIG1lbW9yeSByZXNvdXJjZXMuXG4iLAoJCSAgICAgICBjLT5uYW1lKTsKCQlyb290ID0gcGNpX2ZpbmRfcGFyZW50X3Jlc291cmNlKGMtPnBkZXYsIHJlcyk7CgkJaWYgKHJvb3QgPT0gTlVMTCkKCQkJcHJpbnRrKEtFUk5fV0FSTklORyAiJXM6IENhbid0IGZpbmQgcGFyZW50IHJlc291cmNlIVxuIiwKCQkJICAgICAgIGMtPm5hbWUpOwoJCWlmIChyb290ICYmIGFsbG9jYXRlX3Jlc291cmNlKHJvb3QsIHJlcywgc2ItPmRlc2lyZWRfaW9fc2l6ZSwgc2ItPmRlc2lyZWRfaW9fc2l6ZSwgc2ItPmRlc2lyZWRfaW9fc2l6ZSwgMSA8PCAyMCwJLyogVW5zcGVjaWZpZWQsIHNvIHVzZSAxTWIgYW5kIHBsYXkgc2FmZSAqLwoJCQkJCSAgICAgIE5VTEwsIE5VTEwpID49IDApIHsKCQkJYy0+aW9fYWxsb2MgPSAxOwoJCQlzYi0+Y3VycmVudF9pb19zaXplID0gMSArIHJlcy0+ZW5kIC0gcmVzLT5zdGFydDsKCQkJc2ItPmN1cnJlbnRfbWVtX2Jhc2UgPSByZXMtPnN0YXJ0OwoJCQlwcmludGsoS0VSTl9JTkZPICIlczogYWxsb2NhdGVkICVsZCBieXRlcyBvZiBQQ0kgSS9PIGF0IgoJCQkgICAgICAgIiAweCUwOGxYLlxuIiwgYy0+bmFtZSwKCQkJICAgICAgIDEgKyByZXMtPmVuZCAtIHJlcy0+c3RhcnQsIHJlcy0+c3RhcnQpOwoJCX0KCX0KCgltID0gaTJvX21zZ19nZXRfd2FpdChjLCAmbXNnLCBJMk9fVElNRU9VVF9NRVNTQUdFX0dFVCk7CglpZiAobSA9PSBJMk9fUVVFVUVfRU1QVFkpCgkJcmV0dXJuIC1FVElNRURPVVQ7CgoJaTJvX3N5c3RhYi5waHlzID0gZG1hX21hcF9zaW5nbGUoZGV2LCBpMm9fc3lzdGFiLnZpcnQsIGkyb19zeXN0YWIubGVuLAoJCQkJCSBQQ0lfRE1BX1RPREVWSUNFKTsKCWlmICghaTJvX3N5c3RhYi5waHlzKSB7CgkJaTJvX21zZ19ub3AoYywgbSk7CgkJcmV0dXJuIC1FTk9NRU07Cgl9CgoJd3JpdGVsKEkyT19NRVNTQUdFX1NJWkUoMTIpIHwgU0dMX09GRlNFVF82LCAmbXNnLT51LmhlYWRbMF0pOwoJd3JpdGVsKEkyT19DTURfU1lTX1RBQl9TRVQgPDwgMjQgfCBIT1NUX1RJRCA8PCAxMiB8IEFEQVBURVJfVElELAoJICAgICAgICZtc2ctPnUuaGVhZFsxXSk7CgoJLyoKCSAqIFByb3ZpZGUgdGhyZWUgU0dMLWVsZW1lbnRzOgoJICogU3lzdGVtIHRhYmxlIChTeXNUYWIpLCBQcml2YXRlIG1lbW9yeSBzcGFjZSBkZWNsYXJhdGlvbiBhbmQKCSAqIFByaXZhdGUgaS9vIHNwYWNlIGRlY2xhcmF0aW9uCgkgKgoJICogRklYTUU6IGlzIHRoaXMgc3RpbGwgdHJ1ZT8KCSAqIE5hc3R5IG9uZSBoZXJlLiBXZSBjYW4ndCB1c2UgZG1hX2FsbG9jX2NvaGVyZW50IHRvIHNlbmQgdGhlCgkgKiBzYW1lIHRhYmxlIHRvIGV2ZXJ5b25lLiBXZSBoYXZlIHRvIGdvIHJlbWFwIGl0IGZvciB0aGVtIGFsbAoJICovCgoJd3JpdGVsKGMtPnVuaXQgKyAyLCAmbXNnLT5ib2R5WzBdKTsKCXdyaXRlbCgwLCAmbXNnLT5ib2R5WzFdKTsKCXdyaXRlbCgweDU0MDAwMDAwIHwgaTJvX3N5c3RhYi5sZW4sICZtc2ctPmJvZHlbMl0pOwoJd3JpdGVsKGkyb19zeXN0YWIucGh5cywgJm1zZy0+Ym9keVszXSk7Cgl3cml0ZWwoMHg1NDAwMDAwMCB8IHNiLT5jdXJyZW50X21lbV9zaXplLCAmbXNnLT5ib2R5WzRdKTsKCXdyaXRlbChzYi0+Y3VycmVudF9tZW1fYmFzZSwgJm1zZy0+Ym9keVs1XSk7Cgl3cml0ZWwoMHhkNDAwMDAwMCB8IHNiLT5jdXJyZW50X2lvX3NpemUsICZtc2ctPmJvZHlbNl0pOwoJd3JpdGVsKHNiLT5jdXJyZW50X2lvX2Jhc2UsICZtc2ctPmJvZHlbNl0pOwoKCXJjID0gaTJvX21zZ19wb3N0X3dhaXQoYywgbSwgMTIwKTsKCglkbWFfdW5tYXBfc2luZ2xlKGRldiwgaTJvX3N5c3RhYi5waHlzLCBpMm9fc3lzdGFiLmxlbiwKCQkJIFBDSV9ETUFfVE9ERVZJQ0UpOwoKCWlmIChyYyA8IDApCgkJcHJpbnRrKEtFUk5fRVJSICIlczogVW5hYmxlIHRvIHNldCBTeXNUYWIgKHN0YXR1cz0lI3gpLlxuIiwKCQkgICAgICAgYy0+bmFtZSwgLXJjKTsKCWVsc2UKCQlwcl9kZWJ1ZygiJXM6IFN5c1RhYiBzZXQuXG4iLCBjLT5uYW1lKTsKCglpMm9fc3RhdHVzX2dldChjKTsJLy8gRW50ZXJlZCBSRUFEWSBzdGF0ZQoKCXJldHVybiByYzsKfQoKLyoqCiAqCWkyb19pb3Bfb25saW5lIC0gQnJpbmcgYSBjb250cm9sbGVyIG9ubGluZSBpbnRvIE9QRVJBVElPTkFMIHN0YXRlLgogKglAYzogSTJPIGNvbnRyb2xsZXIKICoKICoJU2VuZCB0aGUgc3lzdGVtIHRhYmxlIGFuZCBlbmFibGUgdGhlIEkyTyBjb250cm9sbGVyLgogKgogKglSZXR1cm5zIDAgb24gc3VjY2VzcyBvciBuZWdhdGl2ZXIgZXJyb3IgY29kZSBvbiBmYWlsdXJlLgogKi8Kc3RhdGljIGludCBpMm9faW9wX29ubGluZShzdHJ1Y3QgaTJvX2NvbnRyb2xsZXIgKmMpCnsKCWludCByYzsKCglyYyA9IGkyb19pb3Bfc3lzdGFiX3NldChjKTsKCWlmIChyYykKCQlyZXR1cm4gcmM7CgoJLyogSW4gUkVBRFkgc3RhdGUgKi8KCXByX2RlYnVnKCIlczogQXR0ZW1wdGluZyB0byBlbmFibGUuLi5cbiIsIGMtPm5hbWUpOwoJcmMgPSBpMm9faW9wX2VuYWJsZShjKTsKCWlmIChyYykKCQlyZXR1cm4gcmM7CgoJcmV0dXJuIDA7Cn07CgovKioKICoJaTJvX2lvcF9yZW1vdmUgLSBSZW1vdmUgdGhlIEkyTyBjb250cm9sbGVyIGZyb20gdGhlIEkyTyBjb3JlCiAqCUBjOiBJMk8gY29udHJvbGxlcgogKgogKglSZW1vdmUgdGhlIEkyTyBjb250cm9sbGVyIGZyb20gdGhlIEkyTyBjb3JlLiBJZiBkZXZpY2VzIGFyZSBhdHRhY2hlZCB0bwogKgl0aGUgY29udHJvbGxlciByZW1vdmUgdGhlc2UgYWxzbyBhbmQgZmluYWxseSByZXNldCB0aGUgY29udHJvbGxlci4KICovCnZvaWQgaTJvX2lvcF9yZW1vdmUoc3RydWN0IGkyb19jb250cm9sbGVyICpjKQp7CglzdHJ1Y3QgaTJvX2RldmljZSAqZGV2LCAqdG1wOwoKCXByX2RlYnVnKCIlczogZGVsZXRpbmcgY29udHJvbGxlclxuIiwgYy0+bmFtZSk7CgoJaTJvX2RyaXZlcl9ub3RpZnlfY29udHJvbGxlcl9yZW1vdmVfYWxsKGMpOwoKCWxpc3RfZGVsKCZjLT5saXN0KTsKCglsaXN0X2Zvcl9lYWNoX2VudHJ5X3NhZmUoZGV2LCB0bXAsICZjLT5kZXZpY2VzLCBsaXN0KQoJICAgIGkyb19kZXZpY2VfcmVtb3ZlKGRldik7CgoJZGV2aWNlX2RlbCgmYy0+ZGV2aWNlKTsKCgkvKiBBc2sgdGhlIElPUCB0byBzd2l0Y2ggdG8gUkVTRVQgc3RhdGUgKi8KCWkyb19pb3BfcmVzZXQoYyk7CgoJcHV0X2RldmljZSgmYy0+ZGV2aWNlKTsKfQoKLyoqCiAqCWkyb19zeXN0YWJfYnVpbGQgLSBCdWlsZCBzeXN0ZW0gdGFibGUKICoKICoJVGhlIHN5c3RlbSB0YWJsZSBjb250YWlucyBpbmZvcm1hdGlvbiBhYm91dCBhbGwgdGhlIElPUHMgaW4gdGhlIHN5c3RlbQogKgkoZHVoKSBhbmQgaXMgdXNlZCBieSB0aGUgRXhlY3V0aXZlcyBvbiB0aGUgSU9QcyB0byBlc3RhYmxpc2ggcGVlcjJwZWVyCiAqCWNvbm5lY3Rpb25zLiBXZSdyZSBub3Qgc3VwcG9ydGluZyBwZWVyMnBlZXIgYXQgdGhlIG1vbWVudCwgYnV0IHRoaXMKICoJd2lsbCBiZSBuZWVkZWQgZG93biB0aGUgcm9hZCBmb3IgdGhpbmdzIGxpa2UgbGFuMmxhbiBmb3J3YXJkaW5nLgogKgogKglSZXR1cm5zIDAgb24gc3VjY2VzcyBvciBuZWdhdGl2ZSBlcnJvciBjb2RlIG9uIGZhaWx1cmUuCiAqLwpzdGF0aWMgaW50IGkyb19zeXN0YWJfYnVpbGQodm9pZCkKewoJc3RydWN0IGkyb19jb250cm9sbGVyICpjLCAqdG1wOwoJaW50IG51bV9jb250cm9sbGVycyA9IDA7Cgl1MzIgY2hhbmdlX2luZCA9IDA7CglpbnQgY291bnQgPSAwOwoJc3RydWN0IGkyb19zeXNfdGJsICpzeXN0YWIgPSBpMm9fc3lzdGFiLnZpcnQ7CgoJbGlzdF9mb3JfZWFjaF9lbnRyeV9zYWZlKGMsIHRtcCwgJmkyb19jb250cm9sbGVycywgbGlzdCkKCSAgICBudW1fY29udHJvbGxlcnMrKzsKCglpZiAoc3lzdGFiKSB7CgkJY2hhbmdlX2luZCA9IHN5c3RhYi0+Y2hhbmdlX2luZDsKCQlrZnJlZShpMm9fc3lzdGFiLnZpcnQpOwoJfQoKCS8qIEhlYWRlciArIElPUHMgKi8KCWkyb19zeXN0YWIubGVuID0gc2l6ZW9mKHN0cnVjdCBpMm9fc3lzX3RibCkgKyBudW1fY29udHJvbGxlcnMgKgoJICAgIHNpemVvZihzdHJ1Y3QgaTJvX3N5c190YmxfZW50cnkpOwoKCXN5c3RhYiA9IGkyb19zeXN0YWIudmlydCA9IGttYWxsb2MoaTJvX3N5c3RhYi5sZW4sIEdGUF9LRVJORUwpOwoJaWYgKCFzeXN0YWIpIHsKCQlwcmludGsoS0VSTl9FUlIgImkybzogdW5hYmxlIHRvIGFsbG9jYXRlIG1lbW9yeSBmb3IgU3lzdGVtICIKCQkgICAgICAgIlRhYmxlXG4iKTsKCQlyZXR1cm4gLUVOT01FTTsKCX0KCW1lbXNldChzeXN0YWIsIDAsIGkyb19zeXN0YWIubGVuKTsKCglzeXN0YWItPnZlcnNpb24gPSBJMk9WRVJTSU9OOwoJc3lzdGFiLT5jaGFuZ2VfaW5kID0gY2hhbmdlX2luZCArIDE7CgoJbGlzdF9mb3JfZWFjaF9lbnRyeV9zYWZlKGMsIHRtcCwgJmkyb19jb250cm9sbGVycywgbGlzdCkgewoJCWkyb19zdGF0dXNfYmxvY2sgKnNiOwoKCQlpZiAoY291bnQgPj0gbnVtX2NvbnRyb2xsZXJzKSB7CgkJCXByaW50ayhLRVJOX0VSUiAiaTJvOiBjb250cm9sbGVyIGFkZGVkIHdoaWxlIGJ1aWxkaW5nICIKCQkJICAgICAgICJzeXN0ZW0gdGFibGVcbiIpOwoJCQlicmVhazsKCQl9CgoJCXNiID0gYy0+c3RhdHVzX2Jsb2NrLnZpcnQ7CgoJCS8qCgkJICogR2V0IHVwZGF0ZWQgSU9QIHN0YXRlIHNvIHdlIGhhdmUgdGhlIGxhdGVzdCBpbmZvcm1hdGlvbgoJCSAqCgkJICogV2Ugc2hvdWxkIGRlbGV0ZSB0aGUgY29udHJvbGxlciBhdCB0aGlzIHBvaW50IGlmIGl0CgkJICogZG9lc24ndCByZXNwb25kIHNpbmNlIGlmIGl0J3Mgbm90IG9uIHRoZSBzeXN0ZW0gdGFibGUKCQkgKiBpdCBpcyB0ZWNobmluaWNhbGx5IG5vdCBwYXJ0IG9mIHRoZSBJMk8gc3Vic3lzdGVtLi4uCgkJICovCgkJaWYgKHVubGlrZWx5KGkyb19zdGF0dXNfZ2V0KGMpKSkgewoJCQlwcmludGsoS0VSTl9FUlIgIiVzOiBEZWxldGluZyBiL2MgY291bGQgbm90IGdldCBzdGF0dXMiCgkJCSAgICAgICAiIHdoaWxlIGF0dGVtcHRpbmcgdG8gYnVpbGQgc3lzdGVtIHRhYmxlXG4iLAoJCQkgICAgICAgYy0+bmFtZSk7CgkJCWkyb19pb3BfcmVtb3ZlKGMpOwoJCQljb250aW51ZTsJLy8gdHJ5IHRoZSBuZXh0IG9uZQoJCX0KCgkJc3lzdGFiLT5pb3BzW2NvdW50XS5vcmdfaWQgPSBzYi0+b3JnX2lkOwoJCXN5c3RhYi0+aW9wc1tjb3VudF0uaW9wX2lkID0gYy0+dW5pdCArIDI7CgkJc3lzdGFiLT5pb3BzW2NvdW50XS5zZWdfbnVtID0gMDsKCQlzeXN0YWItPmlvcHNbY291bnRdLmkyb192ZXJzaW9uID0gc2ItPmkyb192ZXJzaW9uOwoJCXN5c3RhYi0+aW9wc1tjb3VudF0uaW9wX3N0YXRlID0gc2ItPmlvcF9zdGF0ZTsKCQlzeXN0YWItPmlvcHNbY291bnRdLm1zZ190eXBlID0gc2ItPm1zZ190eXBlOwoJCXN5c3RhYi0+aW9wc1tjb3VudF0uZnJhbWVfc2l6ZSA9IHNiLT5pbmJvdW5kX2ZyYW1lX3NpemU7CgkJc3lzdGFiLT5pb3BzW2NvdW50XS5sYXN0X2NoYW5nZWQgPSBjaGFuZ2VfaW5kOwoJCXN5c3RhYi0+aW9wc1tjb3VudF0uaW9wX2NhcGFiaWxpdGllcyA9IHNiLT5pb3BfY2FwYWJpbGl0aWVzOwoJCXN5c3RhYi0+aW9wc1tjb3VudF0uaW5ib3VuZF9sb3cgPQoJCSAgICBpMm9fZG1hX2xvdyhjLT5iYXNlLnBoeXMgKyBJMk9fSU5fUE9SVCk7CgkJc3lzdGFiLT5pb3BzW2NvdW50XS5pbmJvdW5kX2hpZ2ggPQoJCSAgICBpMm9fZG1hX2hpZ2goYy0+YmFzZS5waHlzICsgSTJPX0lOX1BPUlQpOwoKCQljb3VudCsrOwoJfQoKCXN5c3RhYi0+bnVtX2VudHJpZXMgPSBjb3VudDsKCglyZXR1cm4gMDsKfTsKCi8qKgogKglpMm9fcGFyc2VfaHJ0IC0gUGFyc2UgdGhlIGhhcmR3YXJlIHJlc291cmNlIHRhYmxlLgogKglAYzogSTJPIGNvbnRyb2xsZXIKICoKICoJV2UgZG9uJ3QgZG8gYW55dGhpbmcgd2l0aCBpdCBleGNlcHQgZHVtcGluZyBpdCAoaW4gZGVidWcgbW9kZSkuCiAqCiAqCVJldHVybnMgMC4KICovCnN0YXRpYyBpbnQgaTJvX3BhcnNlX2hydChzdHJ1Y3QgaTJvX2NvbnRyb2xsZXIgKmMpCnsKCWkyb19kdW1wX2hydChjKTsKCXJldHVybiAwOwp9OwoKLyoqCiAqCWkyb19zdGF0dXNfZ2V0IC0gR2V0IHRoZSBzdGF0dXMgYmxvY2sgZnJvbSB0aGUgSTJPIGNvbnRyb2xsZXIKICoJQGM6IEkyTyBjb250cm9sbGVyCiAqCiAqCUlzc3VlIGEgc3RhdHVzIHF1ZXJ5IG9uIHRoZSBjb250cm9sbGVyLiBUaGlzIHVwZGF0ZXMgdGhlIGF0dGFjaGVkCiAqCXN0YXR1cyBibG9jay4gVGhlIHN0YXR1cyBibG9jayBjb3VsZCB0aGVuIGJlIGFjY2Vzc2VkIHRocm91Z2gKICoJYy0+c3RhdHVzX2Jsb2NrLgogKgogKglSZXR1cm5zIDAgb24gc3VjZXNzIG9yIG5lZ2F0aXZlIGVycm9yIGNvZGUgb24gZmFpbHVyZS4KICovCmludCBpMm9fc3RhdHVzX2dldChzdHJ1Y3QgaTJvX2NvbnRyb2xsZXIgKmMpCnsKCXN0cnVjdCBpMm9fbWVzc2FnZSBfX2lvbWVtICptc2c7Cgl1MzIgbTsKCXU4ICpzdGF0dXNfYmxvY2s7Cgl1bnNpZ25lZCBsb25nIHRpbWVvdXQ7CgoJc3RhdHVzX2Jsb2NrID0gKHU4ICopIGMtPnN0YXR1c19ibG9jay52aXJ0OwoJbWVtc2V0KHN0YXR1c19ibG9jaywgMCwgc2l6ZW9mKGkyb19zdGF0dXNfYmxvY2spKTsKCgltID0gaTJvX21zZ19nZXRfd2FpdChjLCAmbXNnLCBJMk9fVElNRU9VVF9NRVNTQUdFX0dFVCk7CglpZiAobSA9PSBJMk9fUVVFVUVfRU1QVFkpCgkJcmV0dXJuIC1FVElNRURPVVQ7CgoJd3JpdGVsKE5JTkVfV09SRF9NU0dfU0laRSB8IFNHTF9PRkZTRVRfMCwgJm1zZy0+dS5oZWFkWzBdKTsKCXdyaXRlbChJMk9fQ01EX1NUQVRVU19HRVQgPDwgMjQgfCBIT1NUX1RJRCA8PCAxMiB8IEFEQVBURVJfVElELAoJICAgICAgICZtc2ctPnUuaGVhZFsxXSk7Cgl3cml0ZWwoaTJvX2V4ZWNfZHJpdmVyLmNvbnRleHQsICZtc2ctPnUucy5pY250eHQpOwoJd3JpdGVsKDAsICZtc2ctPnUucy50Y250eHQpOwkvLyBGSVhNRTogdXNlIHJlc29uYWJsZSB0cmFuc2FjdGlvbiBjb250ZXh0Cgl3cml0ZWwoMCwgJm1zZy0+Ym9keVswXSk7Cgl3cml0ZWwoMCwgJm1zZy0+Ym9keVsxXSk7Cgl3cml0ZWwoaTJvX2RtYV9sb3coYy0+c3RhdHVzX2Jsb2NrLnBoeXMpLCAmbXNnLT5ib2R5WzJdKTsKCXdyaXRlbChpMm9fZG1hX2hpZ2goYy0+c3RhdHVzX2Jsb2NrLnBoeXMpLCAmbXNnLT5ib2R5WzNdKTsKCXdyaXRlbChzaXplb2YoaTJvX3N0YXR1c19ibG9jayksICZtc2ctPmJvZHlbNF0pOwkvKiBhbHdheXMgODggYnl0ZXMgKi8KCglpMm9fbXNnX3Bvc3QoYywgbSk7CgoJLyogV2FpdCBmb3IgYSByZXBseSAqLwoJdGltZW91dCA9IGppZmZpZXMgKyBJMk9fVElNRU9VVF9TVEFUVVNfR0VUICogSFo7Cgl3aGlsZSAoc3RhdHVzX2Jsb2NrWzg3XSAhPSAweEZGKSB7CgkJaWYgKHRpbWVfYWZ0ZXIoamlmZmllcywgdGltZW91dCkpIHsKCQkJcHJpbnRrKEtFUk5fRVJSICIlczogR2V0IHN0YXR1cyB0aW1lb3V0LlxuIiwgYy0+bmFtZSk7CgkJCXJldHVybiAtRVRJTUVET1VUOwoJCX0KCgkJc2V0X2N1cnJlbnRfc3RhdGUoVEFTS19VTklOVEVSUlVQVElCTEUpOwoJCXNjaGVkdWxlX3RpbWVvdXQoMSk7CgoJCXJtYigpOwoJfQoKI2lmZGVmIERFQlVHCglpMm9fZGVidWdfc3RhdGUoYyk7CiNlbmRpZgoKCXJldHVybiAwOwp9CgovKgogKglpMm9faHJ0X2dldCAtIEdldCB0aGUgSGFyZHdhcmUgUmVzb3VyY2UgVGFibGUgZnJvbSB0aGUgSTJPIGNvbnRyb2xsZXIKICoJQGM6IEkyTyBjb250cm9sbGVyIGZyb20gd2hpY2ggdGhlIEhSVCBzaG91bGQgYmUgZmV0Y2hlZAogKgogKglUaGUgSFJUIGNvbnRhaW5zIGluZm9ybWF0aW9uIGFib3V0IHBvc3NpYmxlIGhpZGRlbiBkZXZpY2VzIGJ1dCBpcwogKgltb3N0bHkgdXNlbGVzcyB0byB1cy4KICoKICoJUmV0dXJucyAwIG9uIHN1Y2Nlc3Mgb3IgbmVnYXRpdmVyIGVycm9yIGNvZGUgb24gZmFpbHVyZS4KICovCnN0YXRpYyBpbnQgaTJvX2hydF9nZXQoc3RydWN0IGkyb19jb250cm9sbGVyICpjKQp7CglpbnQgcmM7CglpbnQgaTsKCWkyb19ocnQgKmhydCA9IGMtPmhydC52aXJ0OwoJdTMyIHNpemUgPSBzaXplb2YoaTJvX2hydCk7CglzdHJ1Y3QgZGV2aWNlICpkZXYgPSAmYy0+cGRldi0+ZGV2OwoKCWZvciAoaSA9IDA7IGkgPCBJMk9fSFJUX0dFVF9UUklFUzsgaSsrKSB7CgkJc3RydWN0IGkyb19tZXNzYWdlIF9faW9tZW0gKm1zZzsKCQl1MzIgbTsKCgkJbSA9IGkyb19tc2dfZ2V0X3dhaXQoYywgJm1zZywgSTJPX1RJTUVPVVRfTUVTU0FHRV9HRVQpOwoJCWlmIChtID09IEkyT19RVUVVRV9FTVBUWSkKCQkJcmV0dXJuIC1FVElNRURPVVQ7CgoJCXdyaXRlbChTSVhfV09SRF9NU0dfU0laRSB8IFNHTF9PRkZTRVRfNCwgJm1zZy0+dS5oZWFkWzBdKTsKCQl3cml0ZWwoSTJPX0NNRF9IUlRfR0VUIDw8IDI0IHwgSE9TVF9USUQgPDwgMTIgfCBBREFQVEVSX1RJRCwKCQkgICAgICAgJm1zZy0+dS5oZWFkWzFdKTsKCQl3cml0ZWwoMHhkMDAwMDAwMCB8IGMtPmhydC5sZW4sICZtc2ctPmJvZHlbMF0pOwoJCXdyaXRlbChjLT5ocnQucGh5cywgJm1zZy0+Ym9keVsxXSk7CgoJCXJjID0gaTJvX21zZ19wb3N0X3dhaXRfbWVtKGMsIG0sIDIwLCAmYy0+aHJ0KTsKCgkJaWYgKHJjIDwgMCkgewoJCQlwcmludGsoS0VSTl9FUlIgIiVzOiBVbmFibGUgdG8gZ2V0IEhSVCAoc3RhdHVzPSUjeClcbiIsCgkJCSAgICAgICBjLT5uYW1lLCAtcmMpOwoJCQlyZXR1cm4gcmM7CgkJfQoKCQlzaXplID0gaHJ0LT5udW1fZW50cmllcyAqIGhydC0+ZW50cnlfbGVuIDw8IDI7CgkJaWYgKHNpemUgPiBjLT5ocnQubGVuKSB7CgkJCWlmIChpMm9fZG1hX3JlYWxsb2MoZGV2LCAmYy0+aHJ0LCBzaXplLCBHRlBfS0VSTkVMKSkKCQkJCXJldHVybiAtRU5PTUVNOwoJCQllbHNlCgkJCQlocnQgPSBjLT5ocnQudmlydDsKCQl9IGVsc2UKCQkJcmV0dXJuIGkyb19wYXJzZV9ocnQoYyk7Cgl9CgoJcHJpbnRrKEtFUk5fRVJSICIlczogVW5hYmxlIHRvIGdldCBIUlQgYWZ0ZXIgJWQgdHJpZXMsIGdpdmluZyB1cFxuIiwKCSAgICAgICBjLT5uYW1lLCBJMk9fSFJUX0dFVF9UUklFUyk7CgoJcmV0dXJuIC1FQlVTWTsKfQoKLyoqCiAqCWkyb19pb3BfZnJlZSAtIEZyZWUgdGhlIGkyb19jb250cm9sbGVyIHN0cnVjdAogKglAYzogSTJPIGNvbnRyb2xsZXIgdG8gZnJlZQogKi8Kdm9pZCBpMm9faW9wX2ZyZWUoc3RydWN0IGkyb19jb250cm9sbGVyICpjKQp7CglrZnJlZShjKTsKfTsKCgovKioKICoJaTJvX2lvcF9yZWxlYXNlIC0gcmVsZWFzZSB0aGUgbWVtb3J5IGZvciBhIEkyTyBjb250cm9sbGVyCiAqCUBkZXY6IEkyTyBjb250cm9sbGVyIHdoaWNoIHNob3VsZCBiZSByZWxlYXNlZAogKgogKglSZWxlYXNlIHRoZSBhbGxvY2F0ZWQgbWVtb3J5LiBUaGlzIGZ1bmN0aW9uIGlzIGNhbGxlZCBpZiByZWZjb3VudCBvZgogKglkZXZpY2UgcmVhY2hlcyAwIGF1dG9tYXRpY2FsbHkuCiAqLwpzdGF0aWMgdm9pZCBpMm9faW9wX3JlbGVhc2Uoc3RydWN0IGRldmljZSAqZGV2KQp7CglzdHJ1Y3QgaTJvX2NvbnRyb2xsZXIgKmMgPSB0b19pMm9fY29udHJvbGxlcihkZXYpOwoKCWkyb19pb3BfZnJlZShjKTsKfTsKCi8qKgogKglpMm9faW9wX2FsbG9jIC0gQWxsb2NhdGUgYW5kIGluaXRpYWxpemUgYSBpMm9fY29udHJvbGxlciBzdHJ1Y3QKICoKICoJQWxsb2NhdGUgdGhlIG5lY2Vzc2FyeSBtZW1vcnkgZm9yIGEgaTJvX2NvbnRyb2xsZXIgc3RydWN0IGFuZAogKglpbml0aWFsaXplIHRoZSBsaXN0cy4KICoKICoJUmV0dXJucyBhIHBvaW50ZXIgdG8gdGhlIEkyTyBjb250cm9sbGVyIG9yIGEgbmVnYXRpdmUgZXJyb3IgY29kZSBvbgogKglmYWlsdXJlLgogKi8Kc3RydWN0IGkyb19jb250cm9sbGVyICppMm9faW9wX2FsbG9jKHZvaWQpCnsKCXN0YXRpYyBpbnQgdW5pdCA9IDA7CS8qIDAgYW5kIDEgYXJlIE5VTEwgSU9QIGFuZCBMb2NhbCBIb3N0ICovCglzdHJ1Y3QgaTJvX2NvbnRyb2xsZXIgKmM7CgoJYyA9IGttYWxsb2Moc2l6ZW9mKCpjKSwgR0ZQX0tFUk5FTCk7CglpZiAoIWMpIHsKCQlwcmludGsoS0VSTl9FUlIgImkybzogSW5zdWZmaWNpZW50IG1lbW9yeSB0byBhbGxvY2F0ZSBhIEkyTyAiCgkJICAgICAgICJjb250cm9sbGVyLlxuIik7CgkJcmV0dXJuIEVSUl9QVFIoLUVOT01FTSk7Cgl9CgltZW1zZXQoYywgMCwgc2l6ZW9mKCpjKSk7CgoJSU5JVF9MSVNUX0hFQUQoJmMtPmRldmljZXMpOwoJc3Bpbl9sb2NrX2luaXQoJmMtPmxvY2spOwoJaW5pdF9NVVRFWCgmYy0+bGN0X2xvY2spOwoJYy0+dW5pdCA9IHVuaXQrKzsKCXNwcmludGYoYy0+bmFtZSwgImlvcCVkIiwgYy0+dW5pdCk7CgoJZGV2aWNlX2luaXRpYWxpemUoJmMtPmRldmljZSk7CgljLT5kZXZpY2UucmVsZWFzZSA9ICZpMm9faW9wX3JlbGVhc2U7CglzbnByaW50ZihjLT5kZXZpY2UuYnVzX2lkLCBCVVNfSURfU0laRSwgImlvcCVkIiwgYy0+dW5pdCk7CgojaWYgQklUU19QRVJfTE9ORyA9PSA2NAoJc3Bpbl9sb2NrX2luaXQoJmMtPmNvbnRleHRfbGlzdF9sb2NrKTsKCWF0b21pY19zZXQoJmMtPmNvbnRleHRfbGlzdF9jb3VudGVyLCAwKTsKCUlOSVRfTElTVF9IRUFEKCZjLT5jb250ZXh0X2xpc3QpOwojZW5kaWYKCglyZXR1cm4gYzsKfTsKCi8qKgogKglpMm9faW9wX2FkZCAtIEluaXRpYWxpemUgdGhlIEkyTyBjb250cm9sbGVyIGFuZCBhZGQgaGltIHRvIHRoZSBJMk8gY29yZQogKglAYzogY29udHJvbGxlcgogKgogKglJbml0aWFsaXplIHRoZSBJMk8gY29udHJvbGxlciBhbmQgaWYgbm8gZXJyb3Igb2NjdXJzIGFkZCBoaW0gdG8gdGhlIEkyTwogKgljb3JlLgogKgogKglSZXR1cm5zIDAgb24gc3VjY2VzcyBvciBuZWdhdGl2ZSBlcnJvciBjb2RlIG9uIGZhaWx1cmUuCiAqLwppbnQgaTJvX2lvcF9hZGQoc3RydWN0IGkyb19jb250cm9sbGVyICpjKQp7CglpbnQgcmM7CgoJaWYoKHJjID0gZGV2aWNlX2FkZCgmYy0+ZGV2aWNlKSkpIHsKCQlwcmludGsoS0VSTl9FUlIgIiVzOiBjb3VsZCBub3QgcmVnaXN0ZXIgY29udHJvbGxlclxuIiwgYy0+bmFtZSk7CgkJZ290byBpb3BfcmVzZXQ7Cgl9CgoJcHJpbnRrKEtFUk5fSU5GTyAiJXM6IEFjdGl2YXRpbmcgSTJPIGNvbnRyb2xsZXIuLi5cbiIsIGMtPm5hbWUpOwoJcHJpbnRrKEtFUk5fSU5GTyAiJXM6IFRoaXMgbWF5IHRha2UgYSBmZXcgbWludXRlcyBpZiB0aGVyZSBhcmUgbWFueSAiCgkgICAgICAgImRldmljZXNcbiIsIGMtPm5hbWUpOwoKCWlmICgocmMgPSBpMm9faW9wX2FjdGl2YXRlKGMpKSkgewoJCXByaW50ayhLRVJOX0VSUiAiJXM6IGNvdWxkIG5vdCBhY3RpdmF0ZSBjb250cm9sbGVyXG4iLAoJCSAgICAgICBjLT5uYW1lKTsKCQlnb3RvIGlvcF9yZXNldDsKCX0KCglwcl9kZWJ1ZygiJXM6IGJ1aWxkaW5nIHN5cyB0YWJsZS4uLlxuIiwgYy0+bmFtZSk7CgoJaWYgKChyYyA9IGkyb19zeXN0YWJfYnVpbGQoKSkpCgkJZ290byBpb3BfcmVzZXQ7CgoJcHJfZGVidWcoIiVzOiBvbmxpbmUgY29udHJvbGxlci4uLlxuIiwgYy0+bmFtZSk7CgoJaWYgKChyYyA9IGkyb19pb3Bfb25saW5lKGMpKSkKCQlnb3RvIGlvcF9yZXNldDsKCglwcl9kZWJ1ZygiJXM6IGdldHRpbmcgTENULi4uXG4iLCBjLT5uYW1lKTsKCglpZiAoKHJjID0gaTJvX2V4ZWNfbGN0X2dldChjKSkpCgkJZ290byBpb3BfcmVzZXQ7CgoJbGlzdF9hZGQoJmMtPmxpc3QsICZpMm9fY29udHJvbGxlcnMpOwoKCWkyb19kcml2ZXJfbm90aWZ5X2NvbnRyb2xsZXJfYWRkX2FsbChjKTsKCglwcmludGsoS0VSTl9JTkZPICIlczogQ29udHJvbGxlciBhZGRlZFxuIiwgYy0+bmFtZSk7CgoJcmV0dXJuIDA7Cgppb3BfcmVzZXQ6CglpMm9faW9wX3Jlc2V0KGMpOwoKCXJldHVybiByYzsKfTsKCi8qKgogKglpMm9fZXZlbnRfcmVnaXN0ZXIgLSBUdXJuIG9uL29mZiBldmVudCBub3RpZmljYXRpb24gZm9yIGEgSTJPIGRldmljZQogKglAZGV2OiBJMk8gZGV2aWNlIHdoaWNoIHNob3VsZCByZWNlaXZlIHRoZSBldmVudCByZWdpc3RyYXRpb24gcmVxdWVzdAogKglAZHJ2OiBkcml2ZXIgd2hpY2ggd2FudCB0byBnZXQgbm90aWZpZWQKICoJQHRjbnR4dDogdHJhbnNhY3Rpb24gY29udGV4dCB0byB1c2Ugd2l0aCB0aGlzIG5vdGlmaWVyCiAqCUBldnRfbWFzazogbWFzayBvZiBldmVudHMKICoKICoJQ3JlYXRlIGFuZCBwb3N0cyBhbiBldmVudCByZWdpc3RyYXRpb24gbWVzc2FnZSB0byB0aGUgdGFzay4gTm8gcmVwbHkKICoJaXMgd2FpdGVkIGZvciwgb3IgZXhwZWN0ZWQuIElmIHlvdSBkbyBub3Qgd2FudCBmdXJ0aGVyIG5vdGlmaWNhdGlvbnMsCiAqCWNhbGwgdGhlIGkyb19ldmVudF9yZWdpc3RlciBhZ2FpbiB3aXRoIGEgZXZ0X21hc2sgb2YgMC4KICoKICoJUmV0dXJucyAwIG9uIHN1Y2Nlc3Mgb3IgLUVUSU1FRE9VVCBpZiBubyBtZXNzYWdlIGNvdWxkIGJlIGZldGNoZWQgZm9yCiAqCXNlbmRpbmcgdGhlIHJlcXVlc3QuCiAqLwppbnQgaTJvX2V2ZW50X3JlZ2lzdGVyKHN0cnVjdCBpMm9fZGV2aWNlICpkZXYsIHN0cnVjdCBpMm9fZHJpdmVyICpkcnYsCgkJICAgICAgIGludCB0Y250eHQsIHUzMiBldnRfbWFzaykKewoJc3RydWN0IGkyb19jb250cm9sbGVyICpjID0gZGV2LT5pb3A7CglzdHJ1Y3QgaTJvX21lc3NhZ2UgX19pb21lbSAqbXNnOwoJdTMyIG07CgoJbSA9IGkyb19tc2dfZ2V0X3dhaXQoYywgJm1zZywgSTJPX1RJTUVPVVRfTUVTU0FHRV9HRVQpOwoJaWYgKG0gPT0gSTJPX1FVRVVFX0VNUFRZKQoJCXJldHVybiAtRVRJTUVET1VUOwoKCXdyaXRlbChGSVZFX1dPUkRfTVNHX1NJWkUgfCBTR0xfT0ZGU0VUXzAsICZtc2ctPnUuaGVhZFswXSk7Cgl3cml0ZWwoSTJPX0NNRF9VVElMX0VWVF9SRUdJU1RFUiA8PCAyNCB8IEhPU1RfVElEIDw8IDEyIHwgZGV2LT5sY3RfZGF0YS4KCSAgICAgICB0aWQsICZtc2ctPnUuaGVhZFsxXSk7Cgl3cml0ZWwoZHJ2LT5jb250ZXh0LCAmbXNnLT51LnMuaWNudHh0KTsKCXdyaXRlbCh0Y250eHQsICZtc2ctPnUucy50Y250eHQpOwoJd3JpdGVsKGV2dF9tYXNrLCAmbXNnLT5ib2R5WzBdKTsKCglpMm9fbXNnX3Bvc3QoYywgbSk7CgoJcmV0dXJuIDA7Cn07CgovKioKICoJaTJvX2lvcF9pbml0IC0gSTJPIG1haW4gaW5pdGlhbGl6YXRpb24gZnVuY3Rpb24KICoKICoJSW5pdGlhbGl6ZSB0aGUgSTJPIGRyaXZlcnMgKE9TTSkgZnVuY3Rpb25zLCByZWdpc3RlciB0aGUgRXhlY3V0aXZlIE9TTSwKICoJaW5pdGlhbGl6ZSB0aGUgSTJPIFBDSSBwYXJ0IGFuZCBmaW5hbGx5IGluaXRpYWxpemUgSTJPIGRldmljZSBzdHVmZi4KICoKICoJUmV0dXJucyAwIG9uIHN1Y2Nlc3Mgb3IgbmVnYXRpdmUgZXJyb3IgY29kZSBvbiBmYWlsdXJlLgogKi8Kc3RhdGljIGludCBfX2luaXQgaTJvX2lvcF9pbml0KHZvaWQpCnsKCWludCByYyA9IDA7CgoJcHJpbnRrKEtFUk5fSU5GTyBPU01fREVTQ1JJUFRJT04gIiB2IiBPU01fVkVSU0lPTiAiXG4iKTsKCglyYyA9IGkyb19kZXZpY2VfaW5pdCgpOwoJaWYgKHJjKQoJCWdvdG8gZXhpdDsKCglyYyA9IGkyb19kcml2ZXJfaW5pdCgpOwoJaWYgKHJjKQoJCWdvdG8gZGV2aWNlX2V4aXQ7CgoJcmMgPSBpMm9fZXhlY19pbml0KCk7CglpZiAocmMpCgkJZ290byBkcml2ZXJfZXhpdDsKCglyYyA9IGkyb19wY2lfaW5pdCgpOwoJaWYgKHJjIDwgMCkKCQlnb3RvIGV4ZWNfZXhpdDsKCglyZXR1cm4gMDsKCiAgICAgIGV4ZWNfZXhpdDoKCWkyb19leGVjX2V4aXQoKTsKCiAgICAgIGRyaXZlcl9leGl0OgoJaTJvX2RyaXZlcl9leGl0KCk7CgogICAgICBkZXZpY2VfZXhpdDoKCWkyb19kZXZpY2VfZXhpdCgpOwoKICAgICAgZXhpdDoKCXJldHVybiByYzsKfQoKLyoqCiAqCWkyb19pb3BfZXhpdCAtIEkyTyBtYWluIGV4aXQgZnVuY3Rpb24KICoKICoJUmVtb3ZlcyBJMk8gY29udHJvbGxlcnMgZnJvbSBQQ0kgc3Vic3lzdGVtIGFuZCBzaHV0IGRvd24gT1NNcy4KICovCnN0YXRpYyB2b2lkIF9fZXhpdCBpMm9faW9wX2V4aXQodm9pZCkKewoJaTJvX3BjaV9leGl0KCk7CglpMm9fZXhlY19leGl0KCk7CglpMm9fZHJpdmVyX2V4aXQoKTsKCWkyb19kZXZpY2VfZXhpdCgpOwp9OwoKbW9kdWxlX2luaXQoaTJvX2lvcF9pbml0KTsKbW9kdWxlX2V4aXQoaTJvX2lvcF9leGl0KTsKCk1PRFVMRV9BVVRIT1IoIlJlZCBIYXQgU29mdHdhcmUiKTsKTU9EVUxFX0xJQ0VOU0UoIkdQTCIpOwpNT0RVTEVfREVTQ1JJUFRJT04oT1NNX0RFU0NSSVBUSU9OKTsKTU9EVUxFX1ZFUlNJT04oT1NNX1ZFUlNJT04pOwoKI2lmIEJJVFNfUEVSX0xPTkcgPT0gNjQKRVhQT1JUX1NZTUJPTChpMm9fY250eHRfbGlzdF9hZGQpOwpFWFBPUlRfU1lNQk9MKGkyb19jbnR4dF9saXN0X2dldCk7CkVYUE9SVF9TWU1CT0woaTJvX2NudHh0X2xpc3RfcmVtb3ZlKTsKRVhQT1JUX1NZTUJPTChpMm9fY250eHRfbGlzdF9nZXRfcHRyKTsKI2VuZGlmCkVYUE9SVF9TWU1CT0woaTJvX21zZ19nZXRfd2FpdCk7CkVYUE9SVF9TWU1CT0woaTJvX21zZ19ub3ApOwpFWFBPUlRfU1lNQk9MKGkyb19maW5kX2lvcCk7CkVYUE9SVF9TWU1CT0woaTJvX2lvcF9maW5kX2RldmljZSk7CkVYUE9SVF9TWU1CT0woaTJvX2V2ZW50X3JlZ2lzdGVyKTsKRVhQT1JUX1NZTUJPTChpMm9fc3RhdHVzX2dldCk7CkVYUE9SVF9TWU1CT0woaTJvX2NvbnRyb2xsZXJzKTsK