LyoKICogKEMpIENvcHlyaWdodCAyMDAyCiAqIERhbmllbCBFbmdzdHL2bSwgT21pY3JvbiBDZXRpIEFCLCBkYW5pZWxAb21pY3Jvbi5zZQogKgogKiBTZWUgZmlsZSBDUkVESVRTIGZvciBsaXN0IG9mIHBlb3BsZSB3aG8gY29udHJpYnV0ZWQgdG8gdGhpcwogKiBwcm9qZWN0LgogKgogKiBUaGlzIHByb2dyYW0gaXMgZnJlZSBzb2Z0d2FyZTsgeW91IGNhbiByZWRpc3RyaWJ1dGUgaXQgYW5kL29yCiAqIG1vZGlmeSBpdCB1bmRlciB0aGUgdGVybXMgb2YgdGhlIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlIGFzCiAqIHB1Ymxpc2hlZCBieSB0aGUgRnJlZSBTb2Z0d2FyZSBGb3VuZGF0aW9uOyBlaXRoZXIgdmVyc2lvbiAyIG9mCiAqIHRoZSBMaWNlbnNlLCBvciAoYXQgeW91ciBvcHRpb24pIGFueSBsYXRlciB2ZXJzaW9uLgogKgogKiBUaGlzIHByb2dyYW0gaXMgZGlzdHJpYnV0ZWQgaW4gdGhlIGhvcGUgdGhhdCBpdCB3aWxsIGJlIHVzZWZ1bCwKICogYnV0IFdJVEhPVVQgQU5ZIFdBUlJBTlRZOyB3aXRob3V0IGV2ZW4gdGhlIGltcGxpZWQgd2FycmFudHkgb2YKICogTUVSQ0hBTlRBQklMSVRZIG9yIEZJVE5FU1MgRk9SIEEgUEFSVElDVUxBUiBQVVJQT1NFLiAgU2VlIHRoZQogKiBHTlUgR2VuZXJhbCBQdWJsaWMgTGljZW5zZSBmb3IgbW9yZSBkZXRhaWxzLgogKgogKiBZb3Ugc2hvdWxkIGhhdmUgcmVjZWl2ZWQgYSBjb3B5IG9mIHRoZSBHTlUgR2VuZXJhbCBQdWJsaWMgTGljZW5zZQogKiBhbG9uZyB3aXRoIHRoaXMgcHJvZ3JhbTsgaWYgbm90LCB3cml0ZSB0byB0aGUgRnJlZSBTb2Z0d2FyZQogKiBGb3VuZGF0aW9uLCBJbmMuLCA1OSBUZW1wbGUgUGxhY2UsIFN1aXRlIDMzMCwgQm9zdG9uLAogKiBNQSAwMjExMS0xMzA3IFVTQQogKi8KCiNpbmNsdWRlIDxjb21tb24uaD4KI2luY2x1ZGUgPHBjaS5oPgojaW5jbHVkZSA8YXNtL2lvLmg+CiNpbmNsdWRlIDxhc20vcGNpLmg+CgojaWZkZWYgQ09ORklHX1BDSQojdW5kZWYgUENJX1JPTV9TQ0FOX1ZFUkJPU0UKCmludCBwY2lfc2hhZG93X3JvbShwY2lfZGV2X3QgZGV2LCB1bnNpZ25lZCBjaGFyICpkZXN0KQp7CglzdHJ1Y3QgcGNpX2NvbnRyb2xsZXIgKmhvc2U7CglpbnQgcmVzID0gLTE7CglpbnQgaTsKCgl1MzIgcm9tX2FkZHI7Cgl1MzIgYWRkcl9yZWc7Cgl1MzIgc2l6ZTsKCgl1MTYgdmVuZG9yOwoJdTE2IGRldmljZTsKCXUzMiBjbGFzc19jb2RlOwoKCWhvc2UgPSBwY2lfYnVzX3RvX2hvc2UoUENJX0JVUyhkZXYpKTsKI2lmIDAKCXByaW50ZigicGNpX3NoYWRvd19yb20oKSBhc2tlZCB0byBzaGFkb3cgZGV2aWNlICV4IHRvICV4XG4iLAoJICAgICAgIGRldiwgKHUzMilkZXN0KTsKI2VuZGlmCglwY2lfcmVhZF9jb25maWdfd29yZChkZXYsIFBDSV9WRU5ET1JfSUQsICZ2ZW5kb3IpOwoJcGNpX3JlYWRfY29uZmlnX3dvcmQoZGV2LCBQQ0lfREVWSUNFX0lELCAmZGV2aWNlKTsKCXBjaV9yZWFkX2NvbmZpZ19kd29yZChkZXYsIFBDSV9DTEFTU19SRVZJU0lPTiwgJmNsYXNzX2NvZGUpOwoKCWNsYXNzX2NvZGUgJj0gMHhmZmZmZmYwMDsKCWNsYXNzX2NvZGUgPj49IDg7CgojaWYgMAoJcHJpbnRmKCJQQ0kgSGVhZGVyIFZlbmRvciAlMDR4IGRldmljZSAlMDR4IGNsYXNzICUwNnhcbiIsCgkgICAgICAgdmVuZG9yLCBkZXZpY2UsIGNsYXNzX2NvZGUpOwojZW5kaWYKCS8qIEVuYWJsZSB0aGUgcm9tIGFkZGVzcyBkZWNvZGVyICovCglwY2lfd3JpdGVfY29uZmlnX2R3b3JkKGRldiwgUENJX1JPTV9BRERSRVNTLCBQQ0lfUk9NX0FERFJFU1NfTUFTSyk7CglwY2lfcmVhZF9jb25maWdfZHdvcmQoZGV2LCBQQ0lfUk9NX0FERFJFU1MsICZhZGRyX3JlZyk7CgoJaWYgKCFhZGRyX3JlZykgewoJCS8qIHJlZ2lzdGVyIHVuaW1wbGVtZW50ZWQgKi8KCQlwcmludGYoInBjaV9jaGFkb3dfcm9tOiBkZXZpY2UgZG8gbm90IHNlZW0gdG8gaGF2ZSBhIHJvbVxuIik7CgkJcmV0dXJuIC0xOwoJfQoKCXNpemUgPSAofihhZGRyX3JlZyZQQ0lfUk9NX0FERFJFU1NfTUFTSykpKzE7CgojaWYgMAoJcHJpbnRmKCJST00gaXMgJWQgYnl0ZXNcbiIsIHNpemUpOwojZW5kaWYKCXJvbV9hZGRyID0gcGNpX2dldF9yb21fd2luZG93KGhvc2UsIHNpemUpOwojaWYgMAoJcHJpbnRmKCJST00gbWFwcGVkIGF0ICV4IFxuIiwgcm9tX2FkZHIpOwojZW5kaWYKCXBjaV93cml0ZV9jb25maWdfZHdvcmQoZGV2LCBQQ0lfUk9NX0FERFJFU1MsCgkJCSAgICAgICBwY2lfcGh5c190b19tZW0oZGV2LCByb21fYWRkcikKCQkJICAgICAgIHxQQ0lfUk9NX0FERFJFU1NfRU5BQkxFKTsKCgoJZm9yIChpPXJvbV9hZGRyO2k8cm9tX2FkZHIrc2l6ZTsgaSs9NTEyKSB7CgoKCQlpZiAocmVhZHcoaSkgPT0gMHhhYTU1KSB7CgkJCXUzMiBwY2lfZGF0YTsKI2lmZGVmIFBDSV9ST01fU0NBTl9WRVJCT1NFCgkJCXByaW50ZigiUk9NIHNpZ25hdHVyZSBmb3VuZFxuIik7CiNlbmRpZgoJCQlwY2lfZGF0YSA9IHJlYWR3KDB4MTgraSk7CgkJCXBjaV9kYXRhICs9IGk7CgoJCQlpZiAoMD09bWVtY21wKCh2b2lkKilwY2lfZGF0YSwgIlBDSVIiLCA0KSkgewojaWZkZWYgUENJX1JPTV9TQ0FOX1ZFUkJPU0UKCQkJCXByaW50ZigiRm91bnQgUENJIHJvbSBpbWFnZSBhdCBvZmZzZXQgJWRcbiIsIGktcm9tX2FkZHIpOwoJCQkJcHJpbnRmKCJWZW5kb3IgJTA0eCBkZXZpY2UgJTA0eCBjbGFzcyAlMDZ4XG4iLAoJCQkJICAgICAgIHJlYWR3KHBjaV9kYXRhKzQpLCByZWFkdyhwY2lfZGF0YSs2KSwKCQkJCSAgICAgICByZWFkbChwY2lfZGF0YSsweDBkKSYweGZmZmZmZik7CgkJCQlwcmludGYoIiVzXG4iLAoJCQkJICAgICAgIChyZWFkdyhwY2lfZGF0YSsweDE1KSAmMHg4MCk/CgkJCQkgICAgICAgIkxhc3QgaW1hZ2UiOiJNb3JlIGltYWdlcyBmb2xsb3ciKTsKCQkJCXN3aXRjaAkocmVhZGIocGNpX2RhdGErMHgxNCkpIHsKCQkJCWNhc2UgMDoKCQkJCQlwcmludGYoIlg4NiBjb2RlXG4iKTsKCQkJCQlicmVhazsKCQkJCWNhc2UgMToKCQkJCQlwcmludGYoIk9wZW5maXJtd2FyZSBjb2RlXG4iKTsKCQkJCQlicmVhazsKCQkJCWNhc2UgMjoKCQkJCQlwcmludGYoIlBBUklTQyBjb2RlXG4iKTsKCQkJCQlicmVhazsKCQkJCX0KCQkJCXByaW50ZigiSW1hZ2Ugc2l6ZSAlZFxuIiwgcmVhZHcocGNpX2RhdGErMHgxMCkgKiA1MTIpOwojZW5kaWYKCQkJCS8qIEZpeE1lOiBJIHRoaW5rIHdlIHNob3VsZCBjb21wYXJlIHRoZSBjbGFzcyBjb2RlCgkJCQkgKiBieXRlcyBhcyB3ZWxsIGJ1dCBJIGhhdmUgbm8gcmVmZXJlbmNlIG9uIHRoZQoJCQkJICogZXhhY3Qgb3JkZXIgb2YgdGhlc2UgYnl0ZXMgaW4gdGhlIFBDSSBST00gaGVhZGVyICovCgkJCQlpZiAocmVhZHcocGNpX2RhdGErNCkgPT0gdmVuZG9yICYmCgkJCQkgICAgcmVhZHcocGNpX2RhdGErNikgPT0gZGV2aWNlICYmCgkJCQkgICAgLyogKHJlYWRsKHBjaV9kYXRhKzB4MGQpJjB4ZmZmZmZmKSA9PSBjbGFzc19jb2RlICYmICovCgkJCQkgICAgcmVhZGIocGNpX2RhdGErMHgxNCkgPT0gMCAvKiB4ODYgY29kZSBpbWFnZSAqLyApIHsKI2lmZGVmIFBDSV9ST01fU0NBTl9WRVJCT1NFCgkJCQkJcHJpbnRmKCJTdWl0YWJsZSBST00gaW1hZ2UgZm91bmQsIGNvcHlpbmdcbiIpOwojZW5kaWYKCQkJCQltZW1tb3ZlKGRlc3QsICh2b2lkKilyb21fYWRkciwgcmVhZHcocGNpX2RhdGErMHgxMCkgKiA1MTIpOwoJCQkJCXJlcyA9IDA7CgkJCQkJYnJlYWs7CgoJCQkJfQoJCQkJaWYgKHJlYWR3KHBjaV9kYXRhKzB4MTUpICYweDgwKSB7CgkJCQkJYnJlYWs7CgkJCQl9CgkJCX0KCQl9CgoJfQoKI2lmZGVmIFBDSV9ST01fU0NBTl9WRVJCT1NFCglpZiAocmVzKSB7CgkJcHJpbnRmKCJObyBzdWl0YWJsZSBpbWFnZSBmb3VuZFxuIik7Cgl9CiNlbmRpZgoJLyogZGlzYWJsZSBQQVIgcmVnaXN0ZXIgYW5kIFBDSSBkZXZpY2UgUk9NIGFkZHJlc3MgZGV2b2NlciAqLwoJcGNpX3JlbW92ZV9yb21fd2luZG93KGhvc2UsIHJvbV9hZGRyKTsKCglwY2lfd3JpdGVfY29uZmlnX2R3b3JkKGRldiwgUENJX1JPTV9BRERSRVNTLCAwKTsKCglyZXR1cm4gcmVzOwp9CgojZW5kaWYK