LyoKICogIGxpbnV4L2tlcm5lbC9zeXMuYwogKgogKiAgQ29weXJpZ2h0IChDKSAxOTkxLCAxOTkyICBMaW51cyBUb3J2YWxkcwogKi8KCiNpbmNsdWRlIDxsaW51eC9jb25maWcuaD4KI2luY2x1ZGUgPGxpbnV4L21vZHVsZS5oPgojaW5jbHVkZSA8bGludXgvbW0uaD4KI2luY2x1ZGUgPGxpbnV4L3V0c25hbWUuaD4KI2luY2x1ZGUgPGxpbnV4L21tYW4uaD4KI2luY2x1ZGUgPGxpbnV4L3NtcF9sb2NrLmg+CiNpbmNsdWRlIDxsaW51eC9ub3RpZmllci5oPgojaW5jbHVkZSA8bGludXgvcmVib290Lmg+CiNpbmNsdWRlIDxsaW51eC9wcmN0bC5oPgojaW5jbHVkZSA8bGludXgvaW5pdC5oPgojaW5jbHVkZSA8bGludXgvaGlnaHVpZC5oPgojaW5jbHVkZSA8bGludXgvZnMuaD4KI2luY2x1ZGUgPGxpbnV4L2tlcm5lbC5oPgojaW5jbHVkZSA8bGludXgva2V4ZWMuaD4KI2luY2x1ZGUgPGxpbnV4L3dvcmtxdWV1ZS5oPgojaW5jbHVkZSA8bGludXgvY2FwYWJpbGl0eS5oPgojaW5jbHVkZSA8bGludXgvZGV2aWNlLmg+CiNpbmNsdWRlIDxsaW51eC9rZXkuaD4KI2luY2x1ZGUgPGxpbnV4L3RpbWVzLmg+CiNpbmNsdWRlIDxsaW51eC9wb3NpeC10aW1lcnMuaD4KI2luY2x1ZGUgPGxpbnV4L3NlY3VyaXR5Lmg+CiNpbmNsdWRlIDxsaW51eC9kY29va2llcy5oPgojaW5jbHVkZSA8bGludXgvc3VzcGVuZC5oPgojaW5jbHVkZSA8bGludXgvdHR5Lmg+CiNpbmNsdWRlIDxsaW51eC9zaWduYWwuaD4KI2luY2x1ZGUgPGxpbnV4L2NuX3Byb2MuaD4KCiNpbmNsdWRlIDxsaW51eC9jb21wYXQuaD4KI2luY2x1ZGUgPGxpbnV4L3N5c2NhbGxzLmg+CiNpbmNsdWRlIDxsaW51eC9rcHJvYmVzLmg+CgojaW5jbHVkZSA8YXNtL3VhY2Nlc3MuaD4KI2luY2x1ZGUgPGFzbS9pby5oPgojaW5jbHVkZSA8YXNtL3VuaXN0ZC5oPgoKI2lmbmRlZiBTRVRfVU5BTElHTl9DVEwKIyBkZWZpbmUgU0VUX1VOQUxJR05fQ1RMKGEsYikJKC1FSU5WQUwpCiNlbmRpZgojaWZuZGVmIEdFVF9VTkFMSUdOX0NUTAojIGRlZmluZSBHRVRfVU5BTElHTl9DVEwoYSxiKQkoLUVJTlZBTCkKI2VuZGlmCiNpZm5kZWYgU0VUX0ZQRU1VX0NUTAojIGRlZmluZSBTRVRfRlBFTVVfQ1RMKGEsYikJKC1FSU5WQUwpCiNlbmRpZgojaWZuZGVmIEdFVF9GUEVNVV9DVEwKIyBkZWZpbmUgR0VUX0ZQRU1VX0NUTChhLGIpCSgtRUlOVkFMKQojZW5kaWYKI2lmbmRlZiBTRVRfRlBFWENfQ1RMCiMgZGVmaW5lIFNFVF9GUEVYQ19DVEwoYSxiKQkoLUVJTlZBTCkKI2VuZGlmCiNpZm5kZWYgR0VUX0ZQRVhDX0NUTAojIGRlZmluZSBHRVRfRlBFWENfQ1RMKGEsYikJKC1FSU5WQUwpCiNlbmRpZgoKLyoKICogdGhpcyBpcyB3aGVyZSB0aGUgc3lzdGVtLXdpZGUgb3ZlcmZsb3cgVUlEIGFuZCBHSUQgYXJlIGRlZmluZWQsIGZvcgogKiBhcmNoaXRlY3R1cmVzIHRoYXQgbm93IGhhdmUgMzItYml0IFVJRC9HSUQgYnV0IGRpZG4ndCBpbiB0aGUgcGFzdAogKi8KCmludCBvdmVyZmxvd3VpZCA9IERFRkFVTFRfT1ZFUkZMT1dVSUQ7CmludCBvdmVyZmxvd2dpZCA9IERFRkFVTFRfT1ZFUkZMT1dHSUQ7CgojaWZkZWYgQ09ORklHX1VJRDE2CkVYUE9SVF9TWU1CT0wob3ZlcmZsb3d1aWQpOwpFWFBPUlRfU1lNQk9MKG92ZXJmbG93Z2lkKTsKI2VuZGlmCgovKgogKiB0aGUgc2FtZSBhcyBhYm92ZSwgYnV0IGZvciBmaWxlc3lzdGVtcyB3aGljaCBjYW4gb25seSBzdG9yZSBhIDE2LWJpdAogKiBVSUQgYW5kIEdJRC4gYXMgc3VjaCwgdGhpcyBpcyBuZWVkZWQgb24gYWxsIGFyY2hpdGVjdHVyZXMKICovCgppbnQgZnNfb3ZlcmZsb3d1aWQgPSBERUZBVUxUX0ZTX09WRVJGTE9XVUlEOwppbnQgZnNfb3ZlcmZsb3dnaWQgPSBERUZBVUxUX0ZTX09WRVJGTE9XVUlEOwoKRVhQT1JUX1NZTUJPTChmc19vdmVyZmxvd3VpZCk7CkVYUE9SVF9TWU1CT0woZnNfb3ZlcmZsb3dnaWQpOwoKLyoKICogdGhpcyBpbmRpY2F0ZXMgd2hldGhlciB5b3UgY2FuIHJlYm9vdCB3aXRoIGN0cmwtYWx0LWRlbDogdGhlIGRlZmF1bHQgaXMgeWVzCiAqLwoKaW50IENfQV9EID0gMTsKaW50IGNhZF9waWQgPSAxOwoKLyoKICoJTm90aWZpZXIgbGlzdCBmb3Iga2VybmVsIGNvZGUgd2hpY2ggd2FudHMgdG8gYmUgY2FsbGVkCiAqCWF0IHNodXRkb3duLiBUaGlzIGlzIHVzZWQgdG8gc3RvcCBhbnkgaWRsaW5nIERNQSBvcGVyYXRpb25zCiAqCWFuZCB0aGUgbGlrZS4gCiAqLwoKc3RhdGljIEJMT0NLSU5HX05PVElGSUVSX0hFQUQocmVib290X25vdGlmaWVyX2xpc3QpOwoKLyoKICoJTm90aWZpZXIgY2hhaW4gY29yZSByb3V0aW5lcy4gIFRoZSBleHBvcnRlZCByb3V0aW5lcyBiZWxvdwogKglhcmUgbGF5ZXJlZCBvbiB0b3Agb2YgdGhlc2UsIHdpdGggYXBwcm9wcmlhdGUgbG9ja2luZyBhZGRlZC4KICovCgpzdGF0aWMgaW50IG5vdGlmaWVyX2NoYWluX3JlZ2lzdGVyKHN0cnVjdCBub3RpZmllcl9ibG9jayAqKm5sLAoJCXN0cnVjdCBub3RpZmllcl9ibG9jayAqbikKewoJd2hpbGUgKCgqbmwpICE9IE5VTEwpIHsKCQlpZiAobi0+cHJpb3JpdHkgPiAoKm5sKS0+cHJpb3JpdHkpCgkJCWJyZWFrOwoJCW5sID0gJigoKm5sKS0+bmV4dCk7Cgl9CgluLT5uZXh0ID0gKm5sOwoJcmN1X2Fzc2lnbl9wb2ludGVyKCpubCwgbik7CglyZXR1cm4gMDsKfQoKc3RhdGljIGludCBub3RpZmllcl9jaGFpbl91bnJlZ2lzdGVyKHN0cnVjdCBub3RpZmllcl9ibG9jayAqKm5sLAoJCXN0cnVjdCBub3RpZmllcl9ibG9jayAqbikKewoJd2hpbGUgKCgqbmwpICE9IE5VTEwpIHsKCQlpZiAoKCpubCkgPT0gbikgewoJCQlyY3VfYXNzaWduX3BvaW50ZXIoKm5sLCBuLT5uZXh0KTsKCQkJcmV0dXJuIDA7CgkJfQoJCW5sID0gJigoKm5sKS0+bmV4dCk7Cgl9CglyZXR1cm4gLUVOT0VOVDsKfQoKc3RhdGljIGludCBfX2twcm9iZXMgbm90aWZpZXJfY2FsbF9jaGFpbihzdHJ1Y3Qgbm90aWZpZXJfYmxvY2sgKipubCwKCQl1bnNpZ25lZCBsb25nIHZhbCwgdm9pZCAqdikKewoJaW50IHJldCA9IE5PVElGWV9ET05FOwoJc3RydWN0IG5vdGlmaWVyX2Jsb2NrICpuYjsKCgluYiA9IHJjdV9kZXJlZmVyZW5jZSgqbmwpOwoJd2hpbGUgKG5iKSB7CgkJcmV0ID0gbmItPm5vdGlmaWVyX2NhbGwobmIsIHZhbCwgdik7CgkJaWYgKChyZXQgJiBOT1RJRllfU1RPUF9NQVNLKSA9PSBOT1RJRllfU1RPUF9NQVNLKQoJCQlicmVhazsKCQluYiA9IHJjdV9kZXJlZmVyZW5jZShuYi0+bmV4dCk7Cgl9CglyZXR1cm4gcmV0Owp9CgovKgogKglBdG9taWMgbm90aWZpZXIgY2hhaW4gcm91dGluZXMuICBSZWdpc3RyYXRpb24gYW5kIHVucmVnaXN0cmF0aW9uCiAqCXVzZSBhIG11dGV4LCBhbmQgY2FsbF9jaGFpbiBpcyBzeW5jaHJvbml6ZWQgYnkgUkNVIChubyBsb2NrcykuCiAqLwoKLyoqCiAqCWF0b21pY19ub3RpZmllcl9jaGFpbl9yZWdpc3RlciAtIEFkZCBub3RpZmllciB0byBhbiBhdG9taWMgbm90aWZpZXIgY2hhaW4KICoJQG5oOiBQb2ludGVyIHRvIGhlYWQgb2YgdGhlIGF0b21pYyBub3RpZmllciBjaGFpbgogKglAbjogTmV3IGVudHJ5IGluIG5vdGlmaWVyIGNoYWluCiAqCiAqCUFkZHMgYSBub3RpZmllciB0byBhbiBhdG9taWMgbm90aWZpZXIgY2hhaW4uCiAqCiAqCUN1cnJlbnRseSBhbHdheXMgcmV0dXJucyB6ZXJvLgogKi8KCmludCBhdG9taWNfbm90aWZpZXJfY2hhaW5fcmVnaXN0ZXIoc3RydWN0IGF0b21pY19ub3RpZmllcl9oZWFkICpuaCwKCQlzdHJ1Y3Qgbm90aWZpZXJfYmxvY2sgKm4pCnsKCXVuc2lnbmVkIGxvbmcgZmxhZ3M7CglpbnQgcmV0OwoKCXNwaW5fbG9ja19pcnFzYXZlKCZuaC0+bG9jaywgZmxhZ3MpOwoJcmV0ID0gbm90aWZpZXJfY2hhaW5fcmVnaXN0ZXIoJm5oLT5oZWFkLCBuKTsKCXNwaW5fdW5sb2NrX2lycXJlc3RvcmUoJm5oLT5sb2NrLCBmbGFncyk7CglyZXR1cm4gcmV0Owp9CgpFWFBPUlRfU1lNQk9MX0dQTChhdG9taWNfbm90aWZpZXJfY2hhaW5fcmVnaXN0ZXIpOwoKLyoqCiAqCWF0b21pY19ub3RpZmllcl9jaGFpbl91bnJlZ2lzdGVyIC0gUmVtb3ZlIG5vdGlmaWVyIGZyb20gYW4gYXRvbWljIG5vdGlmaWVyIGNoYWluCiAqCUBuaDogUG9pbnRlciB0byBoZWFkIG9mIHRoZSBhdG9taWMgbm90aWZpZXIgY2hhaW4KICoJQG46IEVudHJ5IHRvIHJlbW92ZSBmcm9tIG5vdGlmaWVyIGNoYWluCiAqCiAqCVJlbW92ZXMgYSBub3RpZmllciBmcm9tIGFuIGF0b21pYyBub3RpZmllciBjaGFpbi4KICoKICoJUmV0dXJucyB6ZXJvIG9uIHN1Y2Nlc3Mgb3IgJS1FTk9FTlQgb24gZmFpbHVyZS4KICovCmludCBhdG9taWNfbm90aWZpZXJfY2hhaW5fdW5yZWdpc3RlcihzdHJ1Y3QgYXRvbWljX25vdGlmaWVyX2hlYWQgKm5oLAoJCXN0cnVjdCBub3RpZmllcl9ibG9jayAqbikKewoJdW5zaWduZWQgbG9uZyBmbGFnczsKCWludCByZXQ7CgoJc3Bpbl9sb2NrX2lycXNhdmUoJm5oLT5sb2NrLCBmbGFncyk7CglyZXQgPSBub3RpZmllcl9jaGFpbl91bnJlZ2lzdGVyKCZuaC0+aGVhZCwgbik7CglzcGluX3VubG9ja19pcnFyZXN0b3JlKCZuaC0+bG9jaywgZmxhZ3MpOwoJc3luY2hyb25pemVfcmN1KCk7CglyZXR1cm4gcmV0Owp9CgpFWFBPUlRfU1lNQk9MX0dQTChhdG9taWNfbm90aWZpZXJfY2hhaW5fdW5yZWdpc3Rlcik7CgovKioKICoJYXRvbWljX25vdGlmaWVyX2NhbGxfY2hhaW4gLSBDYWxsIGZ1bmN0aW9ucyBpbiBhbiBhdG9taWMgbm90aWZpZXIgY2hhaW4KICoJQG5oOiBQb2ludGVyIHRvIGhlYWQgb2YgdGhlIGF0b21pYyBub3RpZmllciBjaGFpbgogKglAdmFsOiBWYWx1ZSBwYXNzZWQgdW5tb2RpZmllZCB0byBub3RpZmllciBmdW5jdGlvbgogKglAdjogUG9pbnRlciBwYXNzZWQgdW5tb2RpZmllZCB0byBub3RpZmllciBmdW5jdGlvbgogKgogKglDYWxscyBlYWNoIGZ1bmN0aW9uIGluIGEgbm90aWZpZXIgY2hhaW4gaW4gdHVybi4gIFRoZSBmdW5jdGlvbnMKICoJcnVuIGluIGFuIGF0b21pYyBjb250ZXh0LCBzbyB0aGV5IG11c3Qgbm90IGJsb2NrLgogKglUaGlzIHJvdXRpbmUgdXNlcyBSQ1UgdG8gc3luY2hyb25pemUgd2l0aCBjaGFuZ2VzIHRvIHRoZSBjaGFpbi4KICoKICoJSWYgdGhlIHJldHVybiB2YWx1ZSBvZiB0aGUgbm90aWZpZXIgY2FuIGJlIGFuZCdlZAogKgl3aXRoICVOT1RJRllfU1RPUF9NQVNLIHRoZW4gYXRvbWljX25vdGlmaWVyX2NhbGxfY2hhaW4KICoJd2lsbCByZXR1cm4gaW1tZWRpYXRlbHksIHdpdGggdGhlIHJldHVybiB2YWx1ZSBvZgogKgl0aGUgbm90aWZpZXIgZnVuY3Rpb24gd2hpY2ggaGFsdGVkIGV4ZWN1dGlvbi4KICoJT3RoZXJ3aXNlIHRoZSByZXR1cm4gdmFsdWUgaXMgdGhlIHJldHVybiB2YWx1ZQogKglvZiB0aGUgbGFzdCBub3RpZmllciBmdW5jdGlvbiBjYWxsZWQuCiAqLwogCmludCBhdG9taWNfbm90aWZpZXJfY2FsbF9jaGFpbihzdHJ1Y3QgYXRvbWljX25vdGlmaWVyX2hlYWQgKm5oLAoJCXVuc2lnbmVkIGxvbmcgdmFsLCB2b2lkICp2KQp7CglpbnQgcmV0OwoKCXJjdV9yZWFkX2xvY2soKTsKCXJldCA9IG5vdGlmaWVyX2NhbGxfY2hhaW4oJm5oLT5oZWFkLCB2YWwsIHYpOwoJcmN1X3JlYWRfdW5sb2NrKCk7CglyZXR1cm4gcmV0Owp9CgpFWFBPUlRfU1lNQk9MX0dQTChhdG9taWNfbm90aWZpZXJfY2FsbF9jaGFpbik7CgovKgogKglCbG9ja2luZyBub3RpZmllciBjaGFpbiByb3V0aW5lcy4gIEFsbCBhY2Nlc3MgdG8gdGhlIGNoYWluIGlzCiAqCXN5bmNocm9uaXplZCBieSBhbiByd3NlbS4KICovCgovKioKICoJYmxvY2tpbmdfbm90aWZpZXJfY2hhaW5fcmVnaXN0ZXIgLSBBZGQgbm90aWZpZXIgdG8gYSBibG9ja2luZyBub3RpZmllciBjaGFpbgogKglAbmg6IFBvaW50ZXIgdG8gaGVhZCBvZiB0aGUgYmxvY2tpbmcgbm90aWZpZXIgY2hhaW4KICoJQG46IE5ldyBlbnRyeSBpbiBub3RpZmllciBjaGFpbgogKgogKglBZGRzIGEgbm90aWZpZXIgdG8gYSBibG9ja2luZyBub3RpZmllciBjaGFpbi4KICoJTXVzdCBiZSBjYWxsZWQgaW4gcHJvY2VzcyBjb250ZXh0LgogKgogKglDdXJyZW50bHkgYWx3YXlzIHJldHVybnMgemVyby4KICovCiAKaW50IGJsb2NraW5nX25vdGlmaWVyX2NoYWluX3JlZ2lzdGVyKHN0cnVjdCBibG9ja2luZ19ub3RpZmllcl9oZWFkICpuaCwKCQlzdHJ1Y3Qgbm90aWZpZXJfYmxvY2sgKm4pCnsKCWludCByZXQ7CgoJLyoKCSAqIFRoaXMgY29kZSBnZXRzIHVzZWQgZHVyaW5nIGJvb3QtdXAsIHdoZW4gdGFzayBzd2l0Y2hpbmcgaXMKCSAqIG5vdCB5ZXQgd29ya2luZyBhbmQgaW50ZXJydXB0cyBtdXN0IHJlbWFpbiBkaXNhYmxlZC4gIEF0CgkgKiBzdWNoIHRpbWVzIHdlIG11c3Qgbm90IGNhbGwgZG93bl93cml0ZSgpLgoJICovCglpZiAodW5saWtlbHkoc3lzdGVtX3N0YXRlID09IFNZU1RFTV9CT09USU5HKSkKCQlyZXR1cm4gbm90aWZpZXJfY2hhaW5fcmVnaXN0ZXIoJm5oLT5oZWFkLCBuKTsKCglkb3duX3dyaXRlKCZuaC0+cndzZW0pOwoJcmV0ID0gbm90aWZpZXJfY2hhaW5fcmVnaXN0ZXIoJm5oLT5oZWFkLCBuKTsKCXVwX3dyaXRlKCZuaC0+cndzZW0pOwoJcmV0dXJuIHJldDsKfQoKRVhQT1JUX1NZTUJPTF9HUEwoYmxvY2tpbmdfbm90aWZpZXJfY2hhaW5fcmVnaXN0ZXIpOwoKLyoqCiAqCWJsb2NraW5nX25vdGlmaWVyX2NoYWluX3VucmVnaXN0ZXIgLSBSZW1vdmUgbm90aWZpZXIgZnJvbSBhIGJsb2NraW5nIG5vdGlmaWVyIGNoYWluCiAqCUBuaDogUG9pbnRlciB0byBoZWFkIG9mIHRoZSBibG9ja2luZyBub3RpZmllciBjaGFpbgogKglAbjogRW50cnkgdG8gcmVtb3ZlIGZyb20gbm90aWZpZXIgY2hhaW4KICoKICoJUmVtb3ZlcyBhIG5vdGlmaWVyIGZyb20gYSBibG9ja2luZyBub3RpZmllciBjaGFpbi4KICoJTXVzdCBiZSBjYWxsZWQgZnJvbSBwcm9jZXNzIGNvbnRleHQuCiAqCiAqCVJldHVybnMgemVybyBvbiBzdWNjZXNzIG9yICUtRU5PRU5UIG9uIGZhaWx1cmUuCiAqLwppbnQgYmxvY2tpbmdfbm90aWZpZXJfY2hhaW5fdW5yZWdpc3RlcihzdHJ1Y3QgYmxvY2tpbmdfbm90aWZpZXJfaGVhZCAqbmgsCgkJc3RydWN0IG5vdGlmaWVyX2Jsb2NrICpuKQp7CglpbnQgcmV0OwoKCS8qCgkgKiBUaGlzIGNvZGUgZ2V0cyB1c2VkIGR1cmluZyBib290LXVwLCB3aGVuIHRhc2sgc3dpdGNoaW5nIGlzCgkgKiBub3QgeWV0IHdvcmtpbmcgYW5kIGludGVycnVwdHMgbXVzdCByZW1haW4gZGlzYWJsZWQuICBBdAoJICogc3VjaCB0aW1lcyB3ZSBtdXN0IG5vdCBjYWxsIGRvd25fd3JpdGUoKS4KCSAqLwoJaWYgKHVubGlrZWx5KHN5c3RlbV9zdGF0ZSA9PSBTWVNURU1fQk9PVElORykpCgkJcmV0dXJuIG5vdGlmaWVyX2NoYWluX3VucmVnaXN0ZXIoJm5oLT5oZWFkLCBuKTsKCglkb3duX3dyaXRlKCZuaC0+cndzZW0pOwoJcmV0ID0gbm90aWZpZXJfY2hhaW5fdW5yZWdpc3RlcigmbmgtPmhlYWQsIG4pOwoJdXBfd3JpdGUoJm5oLT5yd3NlbSk7CglyZXR1cm4gcmV0Owp9CgpFWFBPUlRfU1lNQk9MX0dQTChibG9ja2luZ19ub3RpZmllcl9jaGFpbl91bnJlZ2lzdGVyKTsKCi8qKgogKglibG9ja2luZ19ub3RpZmllcl9jYWxsX2NoYWluIC0gQ2FsbCBmdW5jdGlvbnMgaW4gYSBibG9ja2luZyBub3RpZmllciBjaGFpbgogKglAbmg6IFBvaW50ZXIgdG8gaGVhZCBvZiB0aGUgYmxvY2tpbmcgbm90aWZpZXIgY2hhaW4KICoJQHZhbDogVmFsdWUgcGFzc2VkIHVubW9kaWZpZWQgdG8gbm90aWZpZXIgZnVuY3Rpb24KICoJQHY6IFBvaW50ZXIgcGFzc2VkIHVubW9kaWZpZWQgdG8gbm90aWZpZXIgZnVuY3Rpb24KICoKICoJQ2FsbHMgZWFjaCBmdW5jdGlvbiBpbiBhIG5vdGlmaWVyIGNoYWluIGluIHR1cm4uICBUaGUgZnVuY3Rpb25zCiAqCXJ1biBpbiBhIHByb2Nlc3MgY29udGV4dCwgc28gdGhleSBhcmUgYWxsb3dlZCB0byBibG9jay4KICoKICoJSWYgdGhlIHJldHVybiB2YWx1ZSBvZiB0aGUgbm90aWZpZXIgY2FuIGJlIGFuZCdlZAogKgl3aXRoICVOT1RJRllfU1RPUF9NQVNLIHRoZW4gYmxvY2tpbmdfbm90aWZpZXJfY2FsbF9jaGFpbgogKgl3aWxsIHJldHVybiBpbW1lZGlhdGVseSwgd2l0aCB0aGUgcmV0dXJuIHZhbHVlIG9mCiAqCXRoZSBub3RpZmllciBmdW5jdGlvbiB3aGljaCBoYWx0ZWQgZXhlY3V0aW9uLgogKglPdGhlcndpc2UgdGhlIHJldHVybiB2YWx1ZSBpcyB0aGUgcmV0dXJuIHZhbHVlCiAqCW9mIHRoZSBsYXN0IG5vdGlmaWVyIGZ1bmN0aW9uIGNhbGxlZC4KICovCiAKaW50IGJsb2NraW5nX25vdGlmaWVyX2NhbGxfY2hhaW4oc3RydWN0IGJsb2NraW5nX25vdGlmaWVyX2hlYWQgKm5oLAoJCXVuc2lnbmVkIGxvbmcgdmFsLCB2b2lkICp2KQp7CglpbnQgcmV0OwoKCWRvd25fcmVhZCgmbmgtPnJ3c2VtKTsKCXJldCA9IG5vdGlmaWVyX2NhbGxfY2hhaW4oJm5oLT5oZWFkLCB2YWwsIHYpOwoJdXBfcmVhZCgmbmgtPnJ3c2VtKTsKCXJldHVybiByZXQ7Cn0KCkVYUE9SVF9TWU1CT0xfR1BMKGJsb2NraW5nX25vdGlmaWVyX2NhbGxfY2hhaW4pOwoKLyoKICoJUmF3IG5vdGlmaWVyIGNoYWluIHJvdXRpbmVzLiAgVGhlcmUgaXMgbm8gcHJvdGVjdGlvbjsKICoJdGhlIGNhbGxlciBtdXN0IHByb3ZpZGUgaXQuICBVc2UgYXQgeW91ciBvd24gcmlzayEKICovCgovKioKICoJcmF3X25vdGlmaWVyX2NoYWluX3JlZ2lzdGVyIC0gQWRkIG5vdGlmaWVyIHRvIGEgcmF3IG5vdGlmaWVyIGNoYWluCiAqCUBuaDogUG9pbnRlciB0byBoZWFkIG9mIHRoZSByYXcgbm90aWZpZXIgY2hhaW4KICoJQG46IE5ldyBlbnRyeSBpbiBub3RpZmllciBjaGFpbgogKgogKglBZGRzIGEgbm90aWZpZXIgdG8gYSByYXcgbm90aWZpZXIgY2hhaW4uCiAqCUFsbCBsb2NraW5nIG11c3QgYmUgcHJvdmlkZWQgYnkgdGhlIGNhbGxlci4KICoKICoJQ3VycmVudGx5IGFsd2F5cyByZXR1cm5zIHplcm8uCiAqLwoKaW50IHJhd19ub3RpZmllcl9jaGFpbl9yZWdpc3RlcihzdHJ1Y3QgcmF3X25vdGlmaWVyX2hlYWQgKm5oLAoJCXN0cnVjdCBub3RpZmllcl9ibG9jayAqbikKewoJcmV0dXJuIG5vdGlmaWVyX2NoYWluX3JlZ2lzdGVyKCZuaC0+aGVhZCwgbik7Cn0KCkVYUE9SVF9TWU1CT0xfR1BMKHJhd19ub3RpZmllcl9jaGFpbl9yZWdpc3Rlcik7CgovKioKICoJcmF3X25vdGlmaWVyX2NoYWluX3VucmVnaXN0ZXIgLSBSZW1vdmUgbm90aWZpZXIgZnJvbSBhIHJhdyBub3RpZmllciBjaGFpbgogKglAbmg6IFBvaW50ZXIgdG8gaGVhZCBvZiB0aGUgcmF3IG5vdGlmaWVyIGNoYWluCiAqCUBuOiBFbnRyeSB0byByZW1vdmUgZnJvbSBub3RpZmllciBjaGFpbgogKgogKglSZW1vdmVzIGEgbm90aWZpZXIgZnJvbSBhIHJhdyBub3RpZmllciBjaGFpbi4KICoJQWxsIGxvY2tpbmcgbXVzdCBiZSBwcm92aWRlZCBieSB0aGUgY2FsbGVyLgogKgogKglSZXR1cm5zIHplcm8gb24gc3VjY2VzcyBvciAlLUVOT0VOVCBvbiBmYWlsdXJlLgogKi8KaW50IHJhd19ub3RpZmllcl9jaGFpbl91bnJlZ2lzdGVyKHN0cnVjdCByYXdfbm90aWZpZXJfaGVhZCAqbmgsCgkJc3RydWN0IG5vdGlmaWVyX2Jsb2NrICpuKQp7CglyZXR1cm4gbm90aWZpZXJfY2hhaW5fdW5yZWdpc3RlcigmbmgtPmhlYWQsIG4pOwp9CgpFWFBPUlRfU1lNQk9MX0dQTChyYXdfbm90aWZpZXJfY2hhaW5fdW5yZWdpc3Rlcik7CgovKioKICoJcmF3X25vdGlmaWVyX2NhbGxfY2hhaW4gLSBDYWxsIGZ1bmN0aW9ucyBpbiBhIHJhdyBub3RpZmllciBjaGFpbgogKglAbmg6IFBvaW50ZXIgdG8gaGVhZCBvZiB0aGUgcmF3IG5vdGlmaWVyIGNoYWluCiAqCUB2YWw6IFZhbHVlIHBhc3NlZCB1bm1vZGlmaWVkIHRvIG5vdGlmaWVyIGZ1bmN0aW9uCiAqCUB2OiBQb2ludGVyIHBhc3NlZCB1bm1vZGlmaWVkIHRvIG5vdGlmaWVyIGZ1bmN0aW9uCiAqCiAqCUNhbGxzIGVhY2ggZnVuY3Rpb24gaW4gYSBub3RpZmllciBjaGFpbiBpbiB0dXJuLiAgVGhlIGZ1bmN0aW9ucwogKglydW4gaW4gYW4gdW5kZWZpbmVkIGNvbnRleHQuCiAqCUFsbCBsb2NraW5nIG11c3QgYmUgcHJvdmlkZWQgYnkgdGhlIGNhbGxlci4KICoKICoJSWYgdGhlIHJldHVybiB2YWx1ZSBvZiB0aGUgbm90aWZpZXIgY2FuIGJlIGFuZCdlZAogKgl3aXRoICVOT1RJRllfU1RPUF9NQVNLIHRoZW4gcmF3X25vdGlmaWVyX2NhbGxfY2hhaW4KICoJd2lsbCByZXR1cm4gaW1tZWRpYXRlbHksIHdpdGggdGhlIHJldHVybiB2YWx1ZSBvZgogKgl0aGUgbm90aWZpZXIgZnVuY3Rpb24gd2hpY2ggaGFsdGVkIGV4ZWN1dGlvbi4KICoJT3RoZXJ3aXNlIHRoZSByZXR1cm4gdmFsdWUgaXMgdGhlIHJldHVybiB2YWx1ZQogKglvZiB0aGUgbGFzdCBub3RpZmllciBmdW5jdGlvbiBjYWxsZWQuCiAqLwoKaW50IHJhd19ub3RpZmllcl9jYWxsX2NoYWluKHN0cnVjdCByYXdfbm90aWZpZXJfaGVhZCAqbmgsCgkJdW5zaWduZWQgbG9uZyB2YWwsIHZvaWQgKnYpCnsKCXJldHVybiBub3RpZmllcl9jYWxsX2NoYWluKCZuaC0+aGVhZCwgdmFsLCB2KTsKfQoKRVhQT1JUX1NZTUJPTF9HUEwocmF3X25vdGlmaWVyX2NhbGxfY2hhaW4pOwoKLyoqCiAqCXJlZ2lzdGVyX3JlYm9vdF9ub3RpZmllciAtIFJlZ2lzdGVyIGZ1bmN0aW9uIHRvIGJlIGNhbGxlZCBhdCByZWJvb3QgdGltZQogKglAbmI6IEluZm8gYWJvdXQgbm90aWZpZXIgZnVuY3Rpb24gdG8gYmUgY2FsbGVkCiAqCiAqCVJlZ2lzdGVycyBhIGZ1bmN0aW9uIHdpdGggdGhlIGxpc3Qgb2YgZnVuY3Rpb25zCiAqCXRvIGJlIGNhbGxlZCBhdCByZWJvb3QgdGltZS4KICoKICoJQ3VycmVudGx5IGFsd2F5cyByZXR1cm5zIHplcm8sIGFzIGJsb2NraW5nX25vdGlmaWVyX2NoYWluX3JlZ2lzdGVyCiAqCWFsd2F5cyByZXR1cm5zIHplcm8uCiAqLwogCmludCByZWdpc3Rlcl9yZWJvb3Rfbm90aWZpZXIoc3RydWN0IG5vdGlmaWVyX2Jsb2NrICogbmIpCnsKCXJldHVybiBibG9ja2luZ19ub3RpZmllcl9jaGFpbl9yZWdpc3RlcigmcmVib290X25vdGlmaWVyX2xpc3QsIG5iKTsKfQoKRVhQT1JUX1NZTUJPTChyZWdpc3Rlcl9yZWJvb3Rfbm90aWZpZXIpOwoKLyoqCiAqCXVucmVnaXN0ZXJfcmVib290X25vdGlmaWVyIC0gVW5yZWdpc3RlciBwcmV2aW91c2x5IHJlZ2lzdGVyZWQgcmVib290IG5vdGlmaWVyCiAqCUBuYjogSG9vayB0byBiZSB1bnJlZ2lzdGVyZWQKICoKICoJVW5yZWdpc3RlcnMgYSBwcmV2aW91c2x5IHJlZ2lzdGVyZWQgcmVib290CiAqCW5vdGlmaWVyIGZ1bmN0aW9uLgogKgogKglSZXR1cm5zIHplcm8gb24gc3VjY2Vzcywgb3IgJS1FTk9FTlQgb24gZmFpbHVyZS4KICovCiAKaW50IHVucmVnaXN0ZXJfcmVib290X25vdGlmaWVyKHN0cnVjdCBub3RpZmllcl9ibG9jayAqIG5iKQp7CglyZXR1cm4gYmxvY2tpbmdfbm90aWZpZXJfY2hhaW5fdW5yZWdpc3RlcigmcmVib290X25vdGlmaWVyX2xpc3QsIG5iKTsKfQoKRVhQT1JUX1NZTUJPTCh1bnJlZ2lzdGVyX3JlYm9vdF9ub3RpZmllcik7CgpzdGF0aWMgaW50IHNldF9vbmVfcHJpbyhzdHJ1Y3QgdGFza19zdHJ1Y3QgKnAsIGludCBuaWNldmFsLCBpbnQgZXJyb3IpCnsKCWludCBub19uaWNlOwoKCWlmIChwLT51aWQgIT0gY3VycmVudC0+ZXVpZCAmJgoJCXAtPmV1aWQgIT0gY3VycmVudC0+ZXVpZCAmJiAhY2FwYWJsZShDQVBfU1lTX05JQ0UpKSB7CgkJZXJyb3IgPSAtRVBFUk07CgkJZ290byBvdXQ7Cgl9CglpZiAobmljZXZhbCA8IHRhc2tfbmljZShwKSAmJiAhY2FuX25pY2UocCwgbmljZXZhbCkpIHsKCQllcnJvciA9IC1FQUNDRVM7CgkJZ290byBvdXQ7Cgl9Cglub19uaWNlID0gc2VjdXJpdHlfdGFza19zZXRuaWNlKHAsIG5pY2V2YWwpOwoJaWYgKG5vX25pY2UpIHsKCQllcnJvciA9IG5vX25pY2U7CgkJZ290byBvdXQ7Cgl9CglpZiAoZXJyb3IgPT0gLUVTUkNIKQoJCWVycm9yID0gMDsKCXNldF91c2VyX25pY2UocCwgbmljZXZhbCk7Cm91dDoKCXJldHVybiBlcnJvcjsKfQoKYXNtbGlua2FnZSBsb25nIHN5c19zZXRwcmlvcml0eShpbnQgd2hpY2gsIGludCB3aG8sIGludCBuaWNldmFsKQp7CglzdHJ1Y3QgdGFza19zdHJ1Y3QgKmcsICpwOwoJc3RydWN0IHVzZXJfc3RydWN0ICp1c2VyOwoJaW50IGVycm9yID0gLUVJTlZBTDsKCglpZiAod2hpY2ggPiAyIHx8IHdoaWNoIDwgMCkKCQlnb3RvIG91dDsKCgkvKiBub3JtYWxpemU6IGF2b2lkIHNpZ25lZCBkaXZpc2lvbiAocm91bmRpbmcgcHJvYmxlbXMpICovCgllcnJvciA9IC1FU1JDSDsKCWlmIChuaWNldmFsIDwgLTIwKQoJCW5pY2V2YWwgPSAtMjA7CglpZiAobmljZXZhbCA+IDE5KQoJCW5pY2V2YWwgPSAxOTsKCglyZWFkX2xvY2soJnRhc2tsaXN0X2xvY2spOwoJc3dpdGNoICh3aGljaCkgewoJCWNhc2UgUFJJT19QUk9DRVNTOgoJCQlpZiAoIXdobykKCQkJCXdobyA9IGN1cnJlbnQtPnBpZDsKCQkJcCA9IGZpbmRfdGFza19ieV9waWQod2hvKTsKCQkJaWYgKHApCgkJCQllcnJvciA9IHNldF9vbmVfcHJpbyhwLCBuaWNldmFsLCBlcnJvcik7CgkJCWJyZWFrOwoJCWNhc2UgUFJJT19QR1JQOgoJCQlpZiAoIXdobykKCQkJCXdobyA9IHByb2Nlc3NfZ3JvdXAoY3VycmVudCk7CgkJCWRvX2VhY2hfdGFza19waWQod2hvLCBQSURUWVBFX1BHSUQsIHApIHsKCQkJCWVycm9yID0gc2V0X29uZV9wcmlvKHAsIG5pY2V2YWwsIGVycm9yKTsKCQkJfSB3aGlsZV9lYWNoX3Rhc2tfcGlkKHdobywgUElEVFlQRV9QR0lELCBwKTsKCQkJYnJlYWs7CgkJY2FzZSBQUklPX1VTRVI6CgkJCXVzZXIgPSBjdXJyZW50LT51c2VyOwoJCQlpZiAoIXdobykKCQkJCXdobyA9IGN1cnJlbnQtPnVpZDsKCQkJZWxzZQoJCQkJaWYgKCh3aG8gIT0gY3VycmVudC0+dWlkKSAmJiAhKHVzZXIgPSBmaW5kX3VzZXIod2hvKSkpCgkJCQkJZ290byBvdXRfdW5sb2NrOwkvKiBObyBwcm9jZXNzZXMgZm9yIHRoaXMgdXNlciAqLwoKCQkJZG9fZWFjaF90aHJlYWQoZywgcCkKCQkJCWlmIChwLT51aWQgPT0gd2hvKQoJCQkJCWVycm9yID0gc2V0X29uZV9wcmlvKHAsIG5pY2V2YWwsIGVycm9yKTsKCQkJd2hpbGVfZWFjaF90aHJlYWQoZywgcCk7CgkJCWlmICh3aG8gIT0gY3VycmVudC0+dWlkKQoJCQkJZnJlZV91aWQodXNlcik7CQkvKiBGb3IgZmluZF91c2VyKCkgKi8KCQkJYnJlYWs7Cgl9Cm91dF91bmxvY2s6CglyZWFkX3VubG9jaygmdGFza2xpc3RfbG9jayk7Cm91dDoKCXJldHVybiBlcnJvcjsKfQoKLyoKICogVWdoLiBUbyBhdm9pZCBuZWdhdGl2ZSByZXR1cm4gdmFsdWVzLCAiZ2V0cHJpb3JpdHkoKSIgd2lsbAogKiBub3QgcmV0dXJuIHRoZSBub3JtYWwgbmljZS12YWx1ZSwgYnV0IGEgbmVnYXRlZCB2YWx1ZSB0aGF0CiAqIGhhcyBiZWVuIG9mZnNldCBieSAyMCAoaWUgaXQgcmV0dXJucyA0MC4uMSBpbnN0ZWFkIG9mIC0yMC4uMTkpCiAqIHRvIHN0YXkgY29tcGF0aWJsZS4KICovCmFzbWxpbmthZ2UgbG9uZyBzeXNfZ2V0cHJpb3JpdHkoaW50IHdoaWNoLCBpbnQgd2hvKQp7CglzdHJ1Y3QgdGFza19zdHJ1Y3QgKmcsICpwOwoJc3RydWN0IHVzZXJfc3RydWN0ICp1c2VyOwoJbG9uZyBuaWNldmFsLCByZXR2YWwgPSAtRVNSQ0g7CgoJaWYgKHdoaWNoID4gMiB8fCB3aGljaCA8IDApCgkJcmV0dXJuIC1FSU5WQUw7CgoJcmVhZF9sb2NrKCZ0YXNrbGlzdF9sb2NrKTsKCXN3aXRjaCAod2hpY2gpIHsKCQljYXNlIFBSSU9fUFJPQ0VTUzoKCQkJaWYgKCF3aG8pCgkJCQl3aG8gPSBjdXJyZW50LT5waWQ7CgkJCXAgPSBmaW5kX3Rhc2tfYnlfcGlkKHdobyk7CgkJCWlmIChwKSB7CgkJCQluaWNldmFsID0gMjAgLSB0YXNrX25pY2UocCk7CgkJCQlpZiAobmljZXZhbCA+IHJldHZhbCkKCQkJCQlyZXR2YWwgPSBuaWNldmFsOwoJCQl9CgkJCWJyZWFrOwoJCWNhc2UgUFJJT19QR1JQOgoJCQlpZiAoIXdobykKCQkJCXdobyA9IHByb2Nlc3NfZ3JvdXAoY3VycmVudCk7CgkJCWRvX2VhY2hfdGFza19waWQod2hvLCBQSURUWVBFX1BHSUQsIHApIHsKCQkJCW5pY2V2YWwgPSAyMCAtIHRhc2tfbmljZShwKTsKCQkJCWlmIChuaWNldmFsID4gcmV0dmFsKQoJCQkJCXJldHZhbCA9IG5pY2V2YWw7CgkJCX0gd2hpbGVfZWFjaF90YXNrX3BpZCh3aG8sIFBJRFRZUEVfUEdJRCwgcCk7CgkJCWJyZWFrOwoJCWNhc2UgUFJJT19VU0VSOgoJCQl1c2VyID0gY3VycmVudC0+dXNlcjsKCQkJaWYgKCF3aG8pCgkJCQl3aG8gPSBjdXJyZW50LT51aWQ7CgkJCWVsc2UKCQkJCWlmICgod2hvICE9IGN1cnJlbnQtPnVpZCkgJiYgISh1c2VyID0gZmluZF91c2VyKHdobykpKQoJCQkJCWdvdG8gb3V0X3VubG9jazsJLyogTm8gcHJvY2Vzc2VzIGZvciB0aGlzIHVzZXIgKi8KCgkJCWRvX2VhY2hfdGhyZWFkKGcsIHApCgkJCQlpZiAocC0+dWlkID09IHdobykgewoJCQkJCW5pY2V2YWwgPSAyMCAtIHRhc2tfbmljZShwKTsKCQkJCQlpZiAobmljZXZhbCA+IHJldHZhbCkKCQkJCQkJcmV0dmFsID0gbmljZXZhbDsKCQkJCX0KCQkJd2hpbGVfZWFjaF90aHJlYWQoZywgcCk7CgkJCWlmICh3aG8gIT0gY3VycmVudC0+dWlkKQoJCQkJZnJlZV91aWQodXNlcik7CQkvKiBmb3IgZmluZF91c2VyKCkgKi8KCQkJYnJlYWs7Cgl9Cm91dF91bmxvY2s6CglyZWFkX3VubG9jaygmdGFza2xpc3RfbG9jayk7CgoJcmV0dXJuIHJldHZhbDsKfQoKLyoqCiAqCWVtZXJnZW5jeV9yZXN0YXJ0IC0gcmVib290IHRoZSBzeXN0ZW0KICoKICoJV2l0aG91dCBzaHV0dGluZyBkb3duIGFueSBoYXJkd2FyZSBvciB0YWtpbmcgYW55IGxvY2tzCiAqCXJlYm9vdCB0aGUgc3lzdGVtLiAgVGhpcyBpcyBjYWxsZWQgd2hlbiB3ZSBrbm93IHdlIGFyZSBpbgogKgl0cm91YmxlIHNvIHRoaXMgaXMgb3VyIGJlc3QgZWZmb3J0IHRvIHJlYm9vdC4gIFRoaXMgaXMKICoJc2FmZSB0byBjYWxsIGluIGludGVycnVwdCBjb250ZXh0LgogKi8Kdm9pZCBlbWVyZ2VuY3lfcmVzdGFydCh2b2lkKQp7CgltYWNoaW5lX2VtZXJnZW5jeV9yZXN0YXJ0KCk7Cn0KRVhQT1JUX1NZTUJPTF9HUEwoZW1lcmdlbmN5X3Jlc3RhcnQpOwoKdm9pZCBrZXJuZWxfcmVzdGFydF9wcmVwYXJlKGNoYXIgKmNtZCkKewoJYmxvY2tpbmdfbm90aWZpZXJfY2FsbF9jaGFpbigmcmVib290X25vdGlmaWVyX2xpc3QsIFNZU19SRVNUQVJULCBjbWQpOwoJc3lzdGVtX3N0YXRlID0gU1lTVEVNX1JFU1RBUlQ7CglkZXZpY2Vfc2h1dGRvd24oKTsKfQoKLyoqCiAqCWtlcm5lbF9yZXN0YXJ0IC0gcmVib290IHRoZSBzeXN0ZW0KICoJQGNtZDogcG9pbnRlciB0byBidWZmZXIgY29udGFpbmluZyBjb21tYW5kIHRvIGV4ZWN1dGUgZm9yIHJlc3RhcnQKICoJCW9yICVOVUxMCiAqCiAqCVNodXRkb3duIGV2ZXJ5dGhpbmcgYW5kIHBlcmZvcm0gYSBjbGVhbiByZWJvb3QuCiAqCVRoaXMgaXMgbm90IHNhZmUgdG8gY2FsbCBpbiBpbnRlcnJ1cHQgY29udGV4dC4KICovCnZvaWQga2VybmVsX3Jlc3RhcnQoY2hhciAqY21kKQp7CglrZXJuZWxfcmVzdGFydF9wcmVwYXJlKGNtZCk7CglpZiAoIWNtZCkgewoJCXByaW50ayhLRVJOX0VNRVJHICJSZXN0YXJ0aW5nIHN5c3RlbS5cbiIpOwoJfSBlbHNlIHsKCQlwcmludGsoS0VSTl9FTUVSRyAiUmVzdGFydGluZyBzeXN0ZW0gd2l0aCBjb21tYW5kICclcycuXG4iLCBjbWQpOwoJfQoJcHJpbnRrKCIuXG4iKTsKCW1hY2hpbmVfcmVzdGFydChjbWQpOwp9CkVYUE9SVF9TWU1CT0xfR1BMKGtlcm5lbF9yZXN0YXJ0KTsKCi8qKgogKglrZXJuZWxfa2V4ZWMgLSByZWJvb3QgdGhlIHN5c3RlbQogKgogKglNb3ZlIGludG8gcGxhY2UgYW5kIHN0YXJ0IGV4ZWN1dGluZyBhIHByZWxvYWRlZCBzdGFuZGFsb25lCiAqCWV4ZWN1dGFibGUuICBJZiBub3RoaW5nIHdhcyBwcmVsb2FkZWQgcmV0dXJuIGFuIGVycm9yLgogKi8Kdm9pZCBrZXJuZWxfa2V4ZWModm9pZCkKewojaWZkZWYgQ09ORklHX0tFWEVDCglzdHJ1Y3Qga2ltYWdlICppbWFnZTsKCWltYWdlID0geGNoZygma2V4ZWNfaW1hZ2UsIE5VTEwpOwoJaWYgKCFpbWFnZSkgewoJCXJldHVybjsKCX0KCWtlcm5lbF9yZXN0YXJ0X3ByZXBhcmUoTlVMTCk7CglwcmludGsoS0VSTl9FTUVSRyAiU3RhcnRpbmcgbmV3IGtlcm5lbFxuIik7CgltYWNoaW5lX3NodXRkb3duKCk7CgltYWNoaW5lX2tleGVjKGltYWdlKTsKI2VuZGlmCn0KRVhQT1JUX1NZTUJPTF9HUEwoa2VybmVsX2tleGVjKTsKCnZvaWQga2VybmVsX3NodXRkb3duX3ByZXBhcmUoZW51bSBzeXN0ZW1fc3RhdGVzIHN0YXRlKQp7CglibG9ja2luZ19ub3RpZmllcl9jYWxsX2NoYWluKCZyZWJvb3Rfbm90aWZpZXJfbGlzdCwKCQkoc3RhdGUgPT0gU1lTVEVNX0hBTFQpP1NZU19IQUxUOlNZU19QT1dFUl9PRkYsIE5VTEwpOwoJc3lzdGVtX3N0YXRlID0gc3RhdGU7CglkZXZpY2Vfc2h1dGRvd24oKTsKfQovKioKICoJa2VybmVsX2hhbHQgLSBoYWx0IHRoZSBzeXN0ZW0KICoKICoJU2h1dGRvd24gZXZlcnl0aGluZyBhbmQgcGVyZm9ybSBhIGNsZWFuIHN5c3RlbSBoYWx0LgogKi8Kdm9pZCBrZXJuZWxfaGFsdCh2b2lkKQp7CglrZXJuZWxfc2h1dGRvd25fcHJlcGFyZShTWVNURU1fSEFMVCk7CglwcmludGsoS0VSTl9FTUVSRyAiU3lzdGVtIGhhbHRlZC5cbiIpOwoJbWFjaGluZV9oYWx0KCk7Cn0KCkVYUE9SVF9TWU1CT0xfR1BMKGtlcm5lbF9oYWx0KTsKCi8qKgogKglrZXJuZWxfcG93ZXJfb2ZmIC0gcG93ZXJfb2ZmIHRoZSBzeXN0ZW0KICoKICoJU2h1dGRvd24gZXZlcnl0aGluZyBhbmQgcGVyZm9ybSBhIGNsZWFuIHN5c3RlbSBwb3dlcl9vZmYuCiAqLwp2b2lkIGtlcm5lbF9wb3dlcl9vZmYodm9pZCkKewoJa2VybmVsX3NodXRkb3duX3ByZXBhcmUoU1lTVEVNX1BPV0VSX09GRik7CglwcmludGsoS0VSTl9FTUVSRyAiUG93ZXIgZG93bi5cbiIpOwoJbWFjaGluZV9wb3dlcl9vZmYoKTsKfQpFWFBPUlRfU1lNQk9MX0dQTChrZXJuZWxfcG93ZXJfb2ZmKTsKLyoKICogUmVib290IHN5c3RlbSBjYWxsOiBmb3Igb2J2aW91cyByZWFzb25zIG9ubHkgcm9vdCBtYXkgY2FsbCBpdCwKICogYW5kIGV2ZW4gcm9vdCBuZWVkcyB0byBzZXQgdXAgc29tZSBtYWdpYyBudW1iZXJzIGluIHRoZSByZWdpc3RlcnMKICogc28gdGhhdCBzb21lIG1pc3Rha2Ugd29uJ3QgbWFrZSB0aGlzIHJlYm9vdCB0aGUgd2hvbGUgbWFjaGluZS4KICogWW91IGNhbiBhbHNvIHNldCB0aGUgbWVhbmluZyBvZiB0aGUgY3RybC1hbHQtZGVsLWtleSBoZXJlLgogKgogKiByZWJvb3QgZG9lc24ndCBzeW5jOiBkbyB0aGF0IHlvdXJzZWxmIGJlZm9yZSBjYWxsaW5nIHRoaXMuCiAqLwphc21saW5rYWdlIGxvbmcgc3lzX3JlYm9vdChpbnQgbWFnaWMxLCBpbnQgbWFnaWMyLCB1bnNpZ25lZCBpbnQgY21kLCB2b2lkIF9fdXNlciAqIGFyZykKewoJY2hhciBidWZmZXJbMjU2XTsKCgkvKiBXZSBvbmx5IHRydXN0IHRoZSBzdXBlcnVzZXIgd2l0aCByZWJvb3RpbmcgdGhlIHN5c3RlbS4gKi8KCWlmICghY2FwYWJsZShDQVBfU1lTX0JPT1QpKQoJCXJldHVybiAtRVBFUk07CgoJLyogRm9yIHNhZmV0eSwgd2UgcmVxdWlyZSAibWFnaWMiIGFyZ3VtZW50cy4gKi8KCWlmIChtYWdpYzEgIT0gTElOVVhfUkVCT09UX01BR0lDMSB8fAoJICAgIChtYWdpYzIgIT0gTElOVVhfUkVCT09UX01BR0lDMiAmJgoJICAgICAgICAgICAgICAgIG1hZ2ljMiAhPSBMSU5VWF9SRUJPT1RfTUFHSUMyQSAmJgoJCQltYWdpYzIgIT0gTElOVVhfUkVCT09UX01BR0lDMkIgJiYKCSAgICAgICAgICAgICAgICBtYWdpYzIgIT0gTElOVVhfUkVCT09UX01BR0lDMkMpKQoJCXJldHVybiAtRUlOVkFMOwoKCS8qIEluc3RlYWQgb2YgdHJ5aW5nIHRvIG1ha2UgdGhlIHBvd2VyX29mZiBjb2RlIGxvb2sgbGlrZQoJICogaGFsdCB3aGVuIHBtX3Bvd2VyX29mZiBpcyBub3Qgc2V0IGRvIGl0IHRoZSBlYXN5IHdheS4KCSAqLwoJaWYgKChjbWQgPT0gTElOVVhfUkVCT09UX0NNRF9QT1dFUl9PRkYpICYmICFwbV9wb3dlcl9vZmYpCgkJY21kID0gTElOVVhfUkVCT09UX0NNRF9IQUxUOwoKCWxvY2tfa2VybmVsKCk7Cglzd2l0Y2ggKGNtZCkgewoJY2FzZSBMSU5VWF9SRUJPT1RfQ01EX1JFU1RBUlQ6CgkJa2VybmVsX3Jlc3RhcnQoTlVMTCk7CgkJYnJlYWs7CgoJY2FzZSBMSU5VWF9SRUJPT1RfQ01EX0NBRF9PTjoKCQlDX0FfRCA9IDE7CgkJYnJlYWs7CgoJY2FzZSBMSU5VWF9SRUJPT1RfQ01EX0NBRF9PRkY6CgkJQ19BX0QgPSAwOwoJCWJyZWFrOwoKCWNhc2UgTElOVVhfUkVCT09UX0NNRF9IQUxUOgoJCWtlcm5lbF9oYWx0KCk7CgkJdW5sb2NrX2tlcm5lbCgpOwoJCWRvX2V4aXQoMCk7CgkJYnJlYWs7CgoJY2FzZSBMSU5VWF9SRUJPT1RfQ01EX1BPV0VSX09GRjoKCQlrZXJuZWxfcG93ZXJfb2ZmKCk7CgkJdW5sb2NrX2tlcm5lbCgpOwoJCWRvX2V4aXQoMCk7CgkJYnJlYWs7CgoJY2FzZSBMSU5VWF9SRUJPT1RfQ01EX1JFU1RBUlQyOgoJCWlmIChzdHJuY3B5X2Zyb21fdXNlcigmYnVmZmVyWzBdLCBhcmcsIHNpemVvZihidWZmZXIpIC0gMSkgPCAwKSB7CgkJCXVubG9ja19rZXJuZWwoKTsKCQkJcmV0dXJuIC1FRkFVTFQ7CgkJfQoJCWJ1ZmZlcltzaXplb2YoYnVmZmVyKSAtIDFdID0gJ1wwJzsKCgkJa2VybmVsX3Jlc3RhcnQoYnVmZmVyKTsKCQlicmVhazsKCgljYXNlIExJTlVYX1JFQk9PVF9DTURfS0VYRUM6CgkJa2VybmVsX2tleGVjKCk7CgkJdW5sb2NrX2tlcm5lbCgpOwoJCXJldHVybiAtRUlOVkFMOwoKI2lmZGVmIENPTkZJR19TT0ZUV0FSRV9TVVNQRU5ECgljYXNlIExJTlVYX1JFQk9PVF9DTURfU1dfU1VTUEVORDoKCQl7CgkJCWludCByZXQgPSBzb2Z0d2FyZV9zdXNwZW5kKCk7CgkJCXVubG9ja19rZXJuZWwoKTsKCQkJcmV0dXJuIHJldDsKCQl9CiNlbmRpZgoKCWRlZmF1bHQ6CgkJdW5sb2NrX2tlcm5lbCgpOwoJCXJldHVybiAtRUlOVkFMOwoJfQoJdW5sb2NrX2tlcm5lbCgpOwoJcmV0dXJuIDA7Cn0KCnN0YXRpYyB2b2lkIGRlZmVycmVkX2NhZCh2b2lkICpkdW1teSkKewoJa2VybmVsX3Jlc3RhcnQoTlVMTCk7Cn0KCi8qCiAqIFRoaXMgZnVuY3Rpb24gZ2V0cyBjYWxsZWQgYnkgY3RybC1hbHQtZGVsIC0gaWUgdGhlIGtleWJvYXJkIGludGVycnVwdC4KICogQXMgaXQncyBjYWxsZWQgd2l0aGluIGFuIGludGVycnVwdCwgaXQgbWF5IE5PVCBzeW5jOiB0aGUgb25seSBjaG9pY2UKICogaXMgd2hldGhlciB0byByZWJvb3QgYXQgb25jZSwgb3IganVzdCBpZ25vcmUgdGhlIGN0cmwtYWx0LWRlbC4KICovCnZvaWQgY3RybF9hbHRfZGVsKHZvaWQpCnsKCXN0YXRpYyBERUNMQVJFX1dPUksoY2FkX3dvcmssIGRlZmVycmVkX2NhZCwgTlVMTCk7CgoJaWYgKENfQV9EKQoJCXNjaGVkdWxlX3dvcmsoJmNhZF93b3JrKTsKCWVsc2UKCQlraWxsX3Byb2MoY2FkX3BpZCwgU0lHSU5ULCAxKTsKfQoJCgovKgogKiBVbnByaXZpbGVnZWQgdXNlcnMgbWF5IGNoYW5nZSB0aGUgcmVhbCBnaWQgdG8gdGhlIGVmZmVjdGl2ZSBnaWQKICogb3IgdmljZSB2ZXJzYS4gIChCU0Qtc3R5bGUpCiAqCiAqIElmIHlvdSBzZXQgdGhlIHJlYWwgZ2lkIGF0IGFsbCwgb3Igc2V0IHRoZSBlZmZlY3RpdmUgZ2lkIHRvIGEgdmFsdWUgbm90CiAqIGVxdWFsIHRvIHRoZSByZWFsIGdpZCwgdGhlbiB0aGUgc2F2ZWQgZ2lkIGlzIHNldCB0byB0aGUgbmV3IGVmZmVjdGl2ZSBnaWQuCiAqCiAqIFRoaXMgbWFrZXMgaXQgcG9zc2libGUgZm9yIGEgc2V0Z2lkIHByb2dyYW0gdG8gY29tcGxldGVseSBkcm9wIGl0cwogKiBwcml2aWxlZ2VzLCB3aGljaCBpcyBvZnRlbiBhIHVzZWZ1bCBhc3NlcnRpb24gdG8gbWFrZSB3aGVuIHlvdSBhcmUgZG9pbmcKICogYSBzZWN1cml0eSBhdWRpdCBvdmVyIGEgcHJvZ3JhbS4KICoKICogVGhlIGdlbmVyYWwgaWRlYSBpcyB0aGF0IGEgcHJvZ3JhbSB3aGljaCB1c2VzIGp1c3Qgc2V0cmVnaWQoKSB3aWxsIGJlCiAqIDEwMCUgY29tcGF0aWJsZSB3aXRoIEJTRC4gIEEgcHJvZ3JhbSB3aGljaCB1c2VzIGp1c3Qgc2V0Z2lkKCkgd2lsbCBiZQogKiAxMDAlIGNvbXBhdGlibGUgd2l0aCBQT1NJWCB3aXRoIHNhdmVkIElEcy4gCiAqCiAqIFNNUDogVGhlcmUgYXJlIG5vdCByYWNlcywgdGhlIEdJRHMgYXJlIGNoZWNrZWQgb25seSBieSBmaWxlc3lzdGVtCiAqICAgICAgb3BlcmF0aW9ucyAoYXMgZmFyIGFzIHNlbWFudGljIHByZXNlcnZhdGlvbiBpcyBjb25jZXJuZWQpLgogKi8KYXNtbGlua2FnZSBsb25nIHN5c19zZXRyZWdpZChnaWRfdCByZ2lkLCBnaWRfdCBlZ2lkKQp7CglpbnQgb2xkX3JnaWQgPSBjdXJyZW50LT5naWQ7CglpbnQgb2xkX2VnaWQgPSBjdXJyZW50LT5lZ2lkOwoJaW50IG5ld19yZ2lkID0gb2xkX3JnaWQ7CglpbnQgbmV3X2VnaWQgPSBvbGRfZWdpZDsKCWludCByZXR2YWw7CgoJcmV0dmFsID0gc2VjdXJpdHlfdGFza19zZXRnaWQocmdpZCwgZWdpZCwgKGdpZF90KS0xLCBMU01fU0VUSURfUkUpOwoJaWYgKHJldHZhbCkKCQlyZXR1cm4gcmV0dmFsOwoKCWlmIChyZ2lkICE9IChnaWRfdCkgLTEpIHsKCQlpZiAoKG9sZF9yZ2lkID09IHJnaWQpIHx8CgkJICAgIChjdXJyZW50LT5lZ2lkPT1yZ2lkKSB8fAoJCSAgICBjYXBhYmxlKENBUF9TRVRHSUQpKQoJCQluZXdfcmdpZCA9IHJnaWQ7CgkJZWxzZQoJCQlyZXR1cm4gLUVQRVJNOwoJfQoJaWYgKGVnaWQgIT0gKGdpZF90KSAtMSkgewoJCWlmICgob2xkX3JnaWQgPT0gZWdpZCkgfHwKCQkgICAgKGN1cnJlbnQtPmVnaWQgPT0gZWdpZCkgfHwKCQkgICAgKGN1cnJlbnQtPnNnaWQgPT0gZWdpZCkgfHwKCQkgICAgY2FwYWJsZShDQVBfU0VUR0lEKSkKCQkJbmV3X2VnaWQgPSBlZ2lkOwoJCWVsc2UgewoJCQlyZXR1cm4gLUVQRVJNOwoJCX0KCX0KCWlmIChuZXdfZWdpZCAhPSBvbGRfZWdpZCkKCXsKCQljdXJyZW50LT5tbS0+ZHVtcGFibGUgPSBzdWlkX2R1bXBhYmxlOwoJCXNtcF93bWIoKTsKCX0KCWlmIChyZ2lkICE9IChnaWRfdCkgLTEgfHwKCSAgICAoZWdpZCAhPSAoZ2lkX3QpIC0xICYmIGVnaWQgIT0gb2xkX3JnaWQpKQoJCWN1cnJlbnQtPnNnaWQgPSBuZXdfZWdpZDsKCWN1cnJlbnQtPmZzZ2lkID0gbmV3X2VnaWQ7CgljdXJyZW50LT5lZ2lkID0gbmV3X2VnaWQ7CgljdXJyZW50LT5naWQgPSBuZXdfcmdpZDsKCWtleV9mc2dpZF9jaGFuZ2VkKGN1cnJlbnQpOwoJcHJvY19pZF9jb25uZWN0b3IoY3VycmVudCwgUFJPQ19FVkVOVF9HSUQpOwoJcmV0dXJuIDA7Cn0KCi8qCiAqIHNldGdpZCgpIGlzIGltcGxlbWVudGVkIGxpa2UgU3lzViB3LyBTQVZFRF9JRFMgCiAqCiAqIFNNUDogU2FtZSBpbXBsaWNpdCByYWNlcyBhcyBhYm92ZS4KICovCmFzbWxpbmthZ2UgbG9uZyBzeXNfc2V0Z2lkKGdpZF90IGdpZCkKewoJaW50IG9sZF9lZ2lkID0gY3VycmVudC0+ZWdpZDsKCWludCByZXR2YWw7CgoJcmV0dmFsID0gc2VjdXJpdHlfdGFza19zZXRnaWQoZ2lkLCAoZ2lkX3QpLTEsIChnaWRfdCktMSwgTFNNX1NFVElEX0lEKTsKCWlmIChyZXR2YWwpCgkJcmV0dXJuIHJldHZhbDsKCglpZiAoY2FwYWJsZShDQVBfU0VUR0lEKSkKCXsKCQlpZihvbGRfZWdpZCAhPSBnaWQpCgkJewoJCQljdXJyZW50LT5tbS0+ZHVtcGFibGUgPSBzdWlkX2R1bXBhYmxlOwoJCQlzbXBfd21iKCk7CgkJfQoJCWN1cnJlbnQtPmdpZCA9IGN1cnJlbnQtPmVnaWQgPSBjdXJyZW50LT5zZ2lkID0gY3VycmVudC0+ZnNnaWQgPSBnaWQ7Cgl9CgllbHNlIGlmICgoZ2lkID09IGN1cnJlbnQtPmdpZCkgfHwgKGdpZCA9PSBjdXJyZW50LT5zZ2lkKSkKCXsKCQlpZihvbGRfZWdpZCAhPSBnaWQpCgkJewoJCQljdXJyZW50LT5tbS0+ZHVtcGFibGUgPSBzdWlkX2R1bXBhYmxlOwoJCQlzbXBfd21iKCk7CgkJfQoJCWN1cnJlbnQtPmVnaWQgPSBjdXJyZW50LT5mc2dpZCA9IGdpZDsKCX0KCWVsc2UKCQlyZXR1cm4gLUVQRVJNOwoKCWtleV9mc2dpZF9jaGFuZ2VkKGN1cnJlbnQpOwoJcHJvY19pZF9jb25uZWN0b3IoY3VycmVudCwgUFJPQ19FVkVOVF9HSUQpOwoJcmV0dXJuIDA7Cn0KICAKc3RhdGljIGludCBzZXRfdXNlcih1aWRfdCBuZXdfcnVpZCwgaW50IGR1bXBjbGVhcikKewoJc3RydWN0IHVzZXJfc3RydWN0ICpuZXdfdXNlcjsKCgluZXdfdXNlciA9IGFsbG9jX3VpZChuZXdfcnVpZCk7CglpZiAoIW5ld191c2VyKQoJCXJldHVybiAtRUFHQUlOOwoKCWlmIChhdG9taWNfcmVhZCgmbmV3X3VzZXItPnByb2Nlc3NlcykgPj0KCQkJCWN1cnJlbnQtPnNpZ25hbC0+cmxpbVtSTElNSVRfTlBST0NdLnJsaW1fY3VyICYmCgkJCW5ld191c2VyICE9ICZyb290X3VzZXIpIHsKCQlmcmVlX3VpZChuZXdfdXNlcik7CgkJcmV0dXJuIC1FQUdBSU47Cgl9CgoJc3dpdGNoX3VpZChuZXdfdXNlcik7CgoJaWYoZHVtcGNsZWFyKQoJewoJCWN1cnJlbnQtPm1tLT5kdW1wYWJsZSA9IHN1aWRfZHVtcGFibGU7CgkJc21wX3dtYigpOwoJfQoJY3VycmVudC0+dWlkID0gbmV3X3J1aWQ7CglyZXR1cm4gMDsKfQoKLyoKICogVW5wcml2aWxlZ2VkIHVzZXJzIG1heSBjaGFuZ2UgdGhlIHJlYWwgdWlkIHRvIHRoZSBlZmZlY3RpdmUgdWlkCiAqIG9yIHZpY2UgdmVyc2EuICAoQlNELXN0eWxlKQogKgogKiBJZiB5b3Ugc2V0IHRoZSByZWFsIHVpZCBhdCBhbGwsIG9yIHNldCB0aGUgZWZmZWN0aXZlIHVpZCB0byBhIHZhbHVlIG5vdAogKiBlcXVhbCB0byB0aGUgcmVhbCB1aWQsIHRoZW4gdGhlIHNhdmVkIHVpZCBpcyBzZXQgdG8gdGhlIG5ldyBlZmZlY3RpdmUgdWlkLgogKgogKiBUaGlzIG1ha2VzIGl0IHBvc3NpYmxlIGZvciBhIHNldHVpZCBwcm9ncmFtIHRvIGNvbXBsZXRlbHkgZHJvcCBpdHMKICogcHJpdmlsZWdlcywgd2hpY2ggaXMgb2Z0ZW4gYSB1c2VmdWwgYXNzZXJ0aW9uIHRvIG1ha2Ugd2hlbiB5b3UgYXJlIGRvaW5nCiAqIGEgc2VjdXJpdHkgYXVkaXQgb3ZlciBhIHByb2dyYW0uCiAqCiAqIFRoZSBnZW5lcmFsIGlkZWEgaXMgdGhhdCBhIHByb2dyYW0gd2hpY2ggdXNlcyBqdXN0IHNldHJldWlkKCkgd2lsbCBiZQogKiAxMDAlIGNvbXBhdGlibGUgd2l0aCBCU0QuICBBIHByb2dyYW0gd2hpY2ggdXNlcyBqdXN0IHNldHVpZCgpIHdpbGwgYmUKICogMTAwJSBjb21wYXRpYmxlIHdpdGggUE9TSVggd2l0aCBzYXZlZCBJRHMuIAogKi8KYXNtbGlua2FnZSBsb25nIHN5c19zZXRyZXVpZCh1aWRfdCBydWlkLCB1aWRfdCBldWlkKQp7CglpbnQgb2xkX3J1aWQsIG9sZF9ldWlkLCBvbGRfc3VpZCwgbmV3X3J1aWQsIG5ld19ldWlkOwoJaW50IHJldHZhbDsKCglyZXR2YWwgPSBzZWN1cml0eV90YXNrX3NldHVpZChydWlkLCBldWlkLCAodWlkX3QpLTEsIExTTV9TRVRJRF9SRSk7CglpZiAocmV0dmFsKQoJCXJldHVybiByZXR2YWw7CgoJbmV3X3J1aWQgPSBvbGRfcnVpZCA9IGN1cnJlbnQtPnVpZDsKCW5ld19ldWlkID0gb2xkX2V1aWQgPSBjdXJyZW50LT5ldWlkOwoJb2xkX3N1aWQgPSBjdXJyZW50LT5zdWlkOwoKCWlmIChydWlkICE9ICh1aWRfdCkgLTEpIHsKCQluZXdfcnVpZCA9IHJ1aWQ7CgkJaWYgKChvbGRfcnVpZCAhPSBydWlkKSAmJgoJCSAgICAoY3VycmVudC0+ZXVpZCAhPSBydWlkKSAmJgoJCSAgICAhY2FwYWJsZShDQVBfU0VUVUlEKSkKCQkJcmV0dXJuIC1FUEVSTTsKCX0KCglpZiAoZXVpZCAhPSAodWlkX3QpIC0xKSB7CgkJbmV3X2V1aWQgPSBldWlkOwoJCWlmICgob2xkX3J1aWQgIT0gZXVpZCkgJiYKCQkgICAgKGN1cnJlbnQtPmV1aWQgIT0gZXVpZCkgJiYKCQkgICAgKGN1cnJlbnQtPnN1aWQgIT0gZXVpZCkgJiYKCQkgICAgIWNhcGFibGUoQ0FQX1NFVFVJRCkpCgkJCXJldHVybiAtRVBFUk07Cgl9CgoJaWYgKG5ld19ydWlkICE9IG9sZF9ydWlkICYmIHNldF91c2VyKG5ld19ydWlkLCBuZXdfZXVpZCAhPSBvbGRfZXVpZCkgPCAwKQoJCXJldHVybiAtRUFHQUlOOwoKCWlmIChuZXdfZXVpZCAhPSBvbGRfZXVpZCkKCXsKCQljdXJyZW50LT5tbS0+ZHVtcGFibGUgPSBzdWlkX2R1bXBhYmxlOwoJCXNtcF93bWIoKTsKCX0KCWN1cnJlbnQtPmZzdWlkID0gY3VycmVudC0+ZXVpZCA9IG5ld19ldWlkOwoJaWYgKHJ1aWQgIT0gKHVpZF90KSAtMSB8fAoJICAgIChldWlkICE9ICh1aWRfdCkgLTEgJiYgZXVpZCAhPSBvbGRfcnVpZCkpCgkJY3VycmVudC0+c3VpZCA9IGN1cnJlbnQtPmV1aWQ7CgljdXJyZW50LT5mc3VpZCA9IGN1cnJlbnQtPmV1aWQ7CgoJa2V5X2ZzdWlkX2NoYW5nZWQoY3VycmVudCk7Cglwcm9jX2lkX2Nvbm5lY3RvcihjdXJyZW50LCBQUk9DX0VWRU5UX1VJRCk7CgoJcmV0dXJuIHNlY3VyaXR5X3Rhc2tfcG9zdF9zZXR1aWQob2xkX3J1aWQsIG9sZF9ldWlkLCBvbGRfc3VpZCwgTFNNX1NFVElEX1JFKTsKfQoKCgkJCi8qCiAqIHNldHVpZCgpIGlzIGltcGxlbWVudGVkIGxpa2UgU3lzViB3aXRoIFNBVkVEX0lEUyAKICogCiAqIE5vdGUgdGhhdCBTQVZFRF9JRCdzIGlzIGRlZmljaWVudCBpbiB0aGF0IGEgc2V0dWlkIHJvb3QgcHJvZ3JhbQogKiBsaWtlIHNlbmRtYWlsLCBmb3IgZXhhbXBsZSwgY2Fubm90IHNldCBpdHMgdWlkIHRvIGJlIGEgbm9ybWFsIAogKiB1c2VyIGFuZCB0aGVuIHN3aXRjaCBiYWNrLCBiZWNhdXNlIGlmIHlvdSdyZSByb290LCBzZXR1aWQoKSBzZXRzCiAqIHRoZSBzYXZlZCB1aWQgdG9vLiAgSWYgeW91IGRvbid0IGxpa2UgdGhpcywgYmxhbWUgdGhlIGJyaWdodCBwZW9wbGUKICogaW4gdGhlIFBPU0lYIGNvbW1pdHRlZSBhbmQvb3IgVVNHLiAgTm90ZSB0aGF0IHRoZSBCU0Qtc3R5bGUgc2V0cmV1aWQoKQogKiB3aWxsIGFsbG93IGEgcm9vdCBwcm9ncmFtIHRvIHRlbXBvcmFyaWx5IGRyb3AgcHJpdmlsZWdlcyBhbmQgYmUgYWJsZSB0bwogKiByZWdhaW4gdGhlbSBieSBzd2FwcGluZyB0aGUgcmVhbCBhbmQgZWZmZWN0aXZlIHVpZC4gIAogKi8KYXNtbGlua2FnZSBsb25nIHN5c19zZXR1aWQodWlkX3QgdWlkKQp7CglpbnQgb2xkX2V1aWQgPSBjdXJyZW50LT5ldWlkOwoJaW50IG9sZF9ydWlkLCBvbGRfc3VpZCwgbmV3X3J1aWQsIG5ld19zdWlkOwoJaW50IHJldHZhbDsKCglyZXR2YWwgPSBzZWN1cml0eV90YXNrX3NldHVpZCh1aWQsICh1aWRfdCktMSwgKHVpZF90KS0xLCBMU01fU0VUSURfSUQpOwoJaWYgKHJldHZhbCkKCQlyZXR1cm4gcmV0dmFsOwoKCW9sZF9ydWlkID0gbmV3X3J1aWQgPSBjdXJyZW50LT51aWQ7CglvbGRfc3VpZCA9IGN1cnJlbnQtPnN1aWQ7CgluZXdfc3VpZCA9IG9sZF9zdWlkOwoJCglpZiAoY2FwYWJsZShDQVBfU0VUVUlEKSkgewoJCWlmICh1aWQgIT0gb2xkX3J1aWQgJiYgc2V0X3VzZXIodWlkLCBvbGRfZXVpZCAhPSB1aWQpIDwgMCkKCQkJcmV0dXJuIC1FQUdBSU47CgkJbmV3X3N1aWQgPSB1aWQ7Cgl9IGVsc2UgaWYgKCh1aWQgIT0gY3VycmVudC0+dWlkKSAmJiAodWlkICE9IG5ld19zdWlkKSkKCQlyZXR1cm4gLUVQRVJNOwoKCWlmIChvbGRfZXVpZCAhPSB1aWQpCgl7CgkJY3VycmVudC0+bW0tPmR1bXBhYmxlID0gc3VpZF9kdW1wYWJsZTsKCQlzbXBfd21iKCk7Cgl9CgljdXJyZW50LT5mc3VpZCA9IGN1cnJlbnQtPmV1aWQgPSB1aWQ7CgljdXJyZW50LT5zdWlkID0gbmV3X3N1aWQ7CgoJa2V5X2ZzdWlkX2NoYW5nZWQoY3VycmVudCk7Cglwcm9jX2lkX2Nvbm5lY3RvcihjdXJyZW50LCBQUk9DX0VWRU5UX1VJRCk7CgoJcmV0dXJuIHNlY3VyaXR5X3Rhc2tfcG9zdF9zZXR1aWQob2xkX3J1aWQsIG9sZF9ldWlkLCBvbGRfc3VpZCwgTFNNX1NFVElEX0lEKTsKfQoKCi8qCiAqIFRoaXMgZnVuY3Rpb24gaW1wbGVtZW50cyBhIGdlbmVyaWMgYWJpbGl0eSB0byB1cGRhdGUgcnVpZCwgZXVpZCwKICogYW5kIHN1aWQuICBUaGlzIGFsbG93cyB5b3UgdG8gaW1wbGVtZW50IHRoZSA0LjQgY29tcGF0aWJsZSBzZXRldWlkKCkuCiAqLwphc21saW5rYWdlIGxvbmcgc3lzX3NldHJlc3VpZCh1aWRfdCBydWlkLCB1aWRfdCBldWlkLCB1aWRfdCBzdWlkKQp7CglpbnQgb2xkX3J1aWQgPSBjdXJyZW50LT51aWQ7CglpbnQgb2xkX2V1aWQgPSBjdXJyZW50LT5ldWlkOwoJaW50IG9sZF9zdWlkID0gY3VycmVudC0+c3VpZDsKCWludCByZXR2YWw7CgoJcmV0dmFsID0gc2VjdXJpdHlfdGFza19zZXR1aWQocnVpZCwgZXVpZCwgc3VpZCwgTFNNX1NFVElEX1JFUyk7CglpZiAocmV0dmFsKQoJCXJldHVybiByZXR2YWw7CgoJaWYgKCFjYXBhYmxlKENBUF9TRVRVSUQpKSB7CgkJaWYgKChydWlkICE9ICh1aWRfdCkgLTEpICYmIChydWlkICE9IGN1cnJlbnQtPnVpZCkgJiYKCQkgICAgKHJ1aWQgIT0gY3VycmVudC0+ZXVpZCkgJiYgKHJ1aWQgIT0gY3VycmVudC0+c3VpZCkpCgkJCXJldHVybiAtRVBFUk07CgkJaWYgKChldWlkICE9ICh1aWRfdCkgLTEpICYmIChldWlkICE9IGN1cnJlbnQtPnVpZCkgJiYKCQkgICAgKGV1aWQgIT0gY3VycmVudC0+ZXVpZCkgJiYgKGV1aWQgIT0gY3VycmVudC0+c3VpZCkpCgkJCXJldHVybiAtRVBFUk07CgkJaWYgKChzdWlkICE9ICh1aWRfdCkgLTEpICYmIChzdWlkICE9IGN1cnJlbnQtPnVpZCkgJiYKCQkgICAgKHN1aWQgIT0gY3VycmVudC0+ZXVpZCkgJiYgKHN1aWQgIT0gY3VycmVudC0+c3VpZCkpCgkJCXJldHVybiAtRVBFUk07Cgl9CglpZiAocnVpZCAhPSAodWlkX3QpIC0xKSB7CgkJaWYgKHJ1aWQgIT0gY3VycmVudC0+dWlkICYmIHNldF91c2VyKHJ1aWQsIGV1aWQgIT0gY3VycmVudC0+ZXVpZCkgPCAwKQoJCQlyZXR1cm4gLUVBR0FJTjsKCX0KCWlmIChldWlkICE9ICh1aWRfdCkgLTEpIHsKCQlpZiAoZXVpZCAhPSBjdXJyZW50LT5ldWlkKQoJCXsKCQkJY3VycmVudC0+bW0tPmR1bXBhYmxlID0gc3VpZF9kdW1wYWJsZTsKCQkJc21wX3dtYigpOwoJCX0KCQljdXJyZW50LT5ldWlkID0gZXVpZDsKCX0KCWN1cnJlbnQtPmZzdWlkID0gY3VycmVudC0+ZXVpZDsKCWlmIChzdWlkICE9ICh1aWRfdCkgLTEpCgkJY3VycmVudC0+c3VpZCA9IHN1aWQ7CgoJa2V5X2ZzdWlkX2NoYW5nZWQoY3VycmVudCk7Cglwcm9jX2lkX2Nvbm5lY3RvcihjdXJyZW50LCBQUk9DX0VWRU5UX1VJRCk7CgoJcmV0dXJuIHNlY3VyaXR5X3Rhc2tfcG9zdF9zZXR1aWQob2xkX3J1aWQsIG9sZF9ldWlkLCBvbGRfc3VpZCwgTFNNX1NFVElEX1JFUyk7Cn0KCmFzbWxpbmthZ2UgbG9uZyBzeXNfZ2V0cmVzdWlkKHVpZF90IF9fdXNlciAqcnVpZCwgdWlkX3QgX191c2VyICpldWlkLCB1aWRfdCBfX3VzZXIgKnN1aWQpCnsKCWludCByZXR2YWw7CgoJaWYgKCEocmV0dmFsID0gcHV0X3VzZXIoY3VycmVudC0+dWlkLCBydWlkKSkgJiYKCSAgICAhKHJldHZhbCA9IHB1dF91c2VyKGN1cnJlbnQtPmV1aWQsIGV1aWQpKSkKCQlyZXR2YWwgPSBwdXRfdXNlcihjdXJyZW50LT5zdWlkLCBzdWlkKTsKCglyZXR1cm4gcmV0dmFsOwp9CgovKgogKiBTYW1lIGFzIGFib3ZlLCBidXQgZm9yIHJnaWQsIGVnaWQsIHNnaWQuCiAqLwphc21saW5rYWdlIGxvbmcgc3lzX3NldHJlc2dpZChnaWRfdCByZ2lkLCBnaWRfdCBlZ2lkLCBnaWRfdCBzZ2lkKQp7CglpbnQgcmV0dmFsOwoKCXJldHZhbCA9IHNlY3VyaXR5X3Rhc2tfc2V0Z2lkKHJnaWQsIGVnaWQsIHNnaWQsIExTTV9TRVRJRF9SRVMpOwoJaWYgKHJldHZhbCkKCQlyZXR1cm4gcmV0dmFsOwoKCWlmICghY2FwYWJsZShDQVBfU0VUR0lEKSkgewoJCWlmICgocmdpZCAhPSAoZ2lkX3QpIC0xKSAmJiAocmdpZCAhPSBjdXJyZW50LT5naWQpICYmCgkJICAgIChyZ2lkICE9IGN1cnJlbnQtPmVnaWQpICYmIChyZ2lkICE9IGN1cnJlbnQtPnNnaWQpKQoJCQlyZXR1cm4gLUVQRVJNOwoJCWlmICgoZWdpZCAhPSAoZ2lkX3QpIC0xKSAmJiAoZWdpZCAhPSBjdXJyZW50LT5naWQpICYmCgkJICAgIChlZ2lkICE9IGN1cnJlbnQtPmVnaWQpICYmIChlZ2lkICE9IGN1cnJlbnQtPnNnaWQpKQoJCQlyZXR1cm4gLUVQRVJNOwoJCWlmICgoc2dpZCAhPSAoZ2lkX3QpIC0xKSAmJiAoc2dpZCAhPSBjdXJyZW50LT5naWQpICYmCgkJICAgIChzZ2lkICE9IGN1cnJlbnQtPmVnaWQpICYmIChzZ2lkICE9IGN1cnJlbnQtPnNnaWQpKQoJCQlyZXR1cm4gLUVQRVJNOwoJfQoJaWYgKGVnaWQgIT0gKGdpZF90KSAtMSkgewoJCWlmIChlZ2lkICE9IGN1cnJlbnQtPmVnaWQpCgkJewoJCQljdXJyZW50LT5tbS0+ZHVtcGFibGUgPSBzdWlkX2R1bXBhYmxlOwoJCQlzbXBfd21iKCk7CgkJfQoJCWN1cnJlbnQtPmVnaWQgPSBlZ2lkOwoJfQoJY3VycmVudC0+ZnNnaWQgPSBjdXJyZW50LT5lZ2lkOwoJaWYgKHJnaWQgIT0gKGdpZF90KSAtMSkKCQljdXJyZW50LT5naWQgPSByZ2lkOwoJaWYgKHNnaWQgIT0gKGdpZF90KSAtMSkKCQljdXJyZW50LT5zZ2lkID0gc2dpZDsKCglrZXlfZnNnaWRfY2hhbmdlZChjdXJyZW50KTsKCXByb2NfaWRfY29ubmVjdG9yKGN1cnJlbnQsIFBST0NfRVZFTlRfR0lEKTsKCXJldHVybiAwOwp9Cgphc21saW5rYWdlIGxvbmcgc3lzX2dldHJlc2dpZChnaWRfdCBfX3VzZXIgKnJnaWQsIGdpZF90IF9fdXNlciAqZWdpZCwgZ2lkX3QgX191c2VyICpzZ2lkKQp7CglpbnQgcmV0dmFsOwoKCWlmICghKHJldHZhbCA9IHB1dF91c2VyKGN1cnJlbnQtPmdpZCwgcmdpZCkpICYmCgkgICAgIShyZXR2YWwgPSBwdXRfdXNlcihjdXJyZW50LT5lZ2lkLCBlZ2lkKSkpCgkJcmV0dmFsID0gcHV0X3VzZXIoY3VycmVudC0+c2dpZCwgc2dpZCk7CgoJcmV0dXJuIHJldHZhbDsKfQoKCi8qCiAqICJzZXRmc3VpZCgpIiBzZXRzIHRoZSBmc3VpZCAtIHRoZSB1aWQgdXNlZCBmb3IgZmlsZXN5c3RlbSBjaGVja3MuIFRoaXMKICogaXMgdXNlZCBmb3IgImFjY2VzcygpIiBhbmQgZm9yIHRoZSBORlMgZGFlbW9uIChsZXR0aW5nIG5mc2Qgc3RheSBhdAogKiB3aGF0ZXZlciB1aWQgaXQgd2FudHMgdG8pLiBJdCBub3JtYWxseSBzaGFkb3dzICJldWlkIiwgZXhjZXB0IHdoZW4KICogZXhwbGljaXRseSBzZXQgYnkgc2V0ZnN1aWQoKSBvciBmb3IgYWNjZXNzLi4KICovCmFzbWxpbmthZ2UgbG9uZyBzeXNfc2V0ZnN1aWQodWlkX3QgdWlkKQp7CglpbnQgb2xkX2ZzdWlkOwoKCW9sZF9mc3VpZCA9IGN1cnJlbnQtPmZzdWlkOwoJaWYgKHNlY3VyaXR5X3Rhc2tfc2V0dWlkKHVpZCwgKHVpZF90KS0xLCAodWlkX3QpLTEsIExTTV9TRVRJRF9GUykpCgkJcmV0dXJuIG9sZF9mc3VpZDsKCglpZiAodWlkID09IGN1cnJlbnQtPnVpZCB8fCB1aWQgPT0gY3VycmVudC0+ZXVpZCB8fAoJICAgIHVpZCA9PSBjdXJyZW50LT5zdWlkIHx8IHVpZCA9PSBjdXJyZW50LT5mc3VpZCB8fCAKCSAgICBjYXBhYmxlKENBUF9TRVRVSUQpKQoJewoJCWlmICh1aWQgIT0gb2xkX2ZzdWlkKQoJCXsKCQkJY3VycmVudC0+bW0tPmR1bXBhYmxlID0gc3VpZF9kdW1wYWJsZTsKCQkJc21wX3dtYigpOwoJCX0KCQljdXJyZW50LT5mc3VpZCA9IHVpZDsKCX0KCglrZXlfZnN1aWRfY2hhbmdlZChjdXJyZW50KTsKCXByb2NfaWRfY29ubmVjdG9yKGN1cnJlbnQsIFBST0NfRVZFTlRfVUlEKTsKCglzZWN1cml0eV90YXNrX3Bvc3Rfc2V0dWlkKG9sZF9mc3VpZCwgKHVpZF90KS0xLCAodWlkX3QpLTEsIExTTV9TRVRJRF9GUyk7CgoJcmV0dXJuIG9sZF9mc3VpZDsKfQoKLyoKICogU2FtbWEgcOUgc3ZlbnNrYS4uCiAqLwphc21saW5rYWdlIGxvbmcgc3lzX3NldGZzZ2lkKGdpZF90IGdpZCkKewoJaW50IG9sZF9mc2dpZDsKCglvbGRfZnNnaWQgPSBjdXJyZW50LT5mc2dpZDsKCWlmIChzZWN1cml0eV90YXNrX3NldGdpZChnaWQsIChnaWRfdCktMSwgKGdpZF90KS0xLCBMU01fU0VUSURfRlMpKQoJCXJldHVybiBvbGRfZnNnaWQ7CgoJaWYgKGdpZCA9PSBjdXJyZW50LT5naWQgfHwgZ2lkID09IGN1cnJlbnQtPmVnaWQgfHwKCSAgICBnaWQgPT0gY3VycmVudC0+c2dpZCB8fCBnaWQgPT0gY3VycmVudC0+ZnNnaWQgfHwgCgkgICAgY2FwYWJsZShDQVBfU0VUR0lEKSkKCXsKCQlpZiAoZ2lkICE9IG9sZF9mc2dpZCkKCQl7CgkJCWN1cnJlbnQtPm1tLT5kdW1wYWJsZSA9IHN1aWRfZHVtcGFibGU7CgkJCXNtcF93bWIoKTsKCQl9CgkJY3VycmVudC0+ZnNnaWQgPSBnaWQ7CgkJa2V5X2ZzZ2lkX2NoYW5nZWQoY3VycmVudCk7CgkJcHJvY19pZF9jb25uZWN0b3IoY3VycmVudCwgUFJPQ19FVkVOVF9HSUQpOwoJfQoJcmV0dXJuIG9sZF9mc2dpZDsKfQoKYXNtbGlua2FnZSBsb25nIHN5c190aW1lcyhzdHJ1Y3QgdG1zIF9fdXNlciAqIHRidWYpCnsKCS8qCgkgKglJbiB0aGUgU01QIHdvcmxkIHdlIG1pZ2h0IGp1c3QgYmUgdW5sdWNreSBhbmQgaGF2ZSBvbmUgb2YKCSAqCXRoZSB0aW1lcyBpbmNyZW1lbnQgYXMgd2UgdXNlIGl0LiBTaW5jZSB0aGUgdmFsdWUgaXMgYW4KCSAqCWF0b21pY2FsbHkgc2FmZSB0eXBlIHRoaXMgaXMganVzdCBmaW5lLiBDb25jZXB0dWFsbHkgaXRzCgkgKglhcyBpZiB0aGUgc3lzY2FsbCB0b29rIGFuIGluc3RhbnQgbG9uZ2VyIHRvIG9jY3VyLgoJICovCglpZiAodGJ1ZikgewoJCXN0cnVjdCB0bXMgdG1wOwoJCXN0cnVjdCB0YXNrX3N0cnVjdCAqdHNrID0gY3VycmVudDsKCQlzdHJ1Y3QgdGFza19zdHJ1Y3QgKnQ7CgkJY3B1dGltZV90IHV0aW1lLCBzdGltZSwgY3V0aW1lLCBjc3RpbWU7CgoJCXNwaW5fbG9ja19pcnEoJnRzay0+c2lnaGFuZC0+c2lnbG9jayk7CgkJdXRpbWUgPSB0c2stPnNpZ25hbC0+dXRpbWU7CgkJc3RpbWUgPSB0c2stPnNpZ25hbC0+c3RpbWU7CgkJdCA9IHRzazsKCQlkbyB7CgkJCXV0aW1lID0gY3B1dGltZV9hZGQodXRpbWUsIHQtPnV0aW1lKTsKCQkJc3RpbWUgPSBjcHV0aW1lX2FkZChzdGltZSwgdC0+c3RpbWUpOwoJCQl0ID0gbmV4dF90aHJlYWQodCk7CgkJfSB3aGlsZSAodCAhPSB0c2spOwoKCQljdXRpbWUgPSB0c2stPnNpZ25hbC0+Y3V0aW1lOwoJCWNzdGltZSA9IHRzay0+c2lnbmFsLT5jc3RpbWU7CgkJc3Bpbl91bmxvY2tfaXJxKCZ0c2stPnNpZ2hhbmQtPnNpZ2xvY2spOwoKCQl0bXAudG1zX3V0aW1lID0gY3B1dGltZV90b19jbG9ja190KHV0aW1lKTsKCQl0bXAudG1zX3N0aW1lID0gY3B1dGltZV90b19jbG9ja190KHN0aW1lKTsKCQl0bXAudG1zX2N1dGltZSA9IGNwdXRpbWVfdG9fY2xvY2tfdChjdXRpbWUpOwoJCXRtcC50bXNfY3N0aW1lID0gY3B1dGltZV90b19jbG9ja190KGNzdGltZSk7CgkJaWYgKGNvcHlfdG9fdXNlcih0YnVmLCAmdG1wLCBzaXplb2Yoc3RydWN0IHRtcykpKQoJCQlyZXR1cm4gLUVGQVVMVDsKCX0KCXJldHVybiAobG9uZykgamlmZmllc182NF90b19jbG9ja190KGdldF9qaWZmaWVzXzY0KCkpOwp9CgovKgogKiBUaGlzIG5lZWRzIHNvbWUgaGVhdnkgY2hlY2tpbmcgLi4uCiAqIEkganVzdCBoYXZlbid0IHRoZSBzdG9tYWNoIGZvciBpdC4gSSBhbHNvIGRvbid0IGZ1bGx5CiAqIHVuZGVyc3RhbmQgc2Vzc2lvbnMvcGdycCBldGMuIExldCBzb21lYm9keSB3aG8gZG9lcyBleHBsYWluIGl0LgogKgogKiBPSywgSSB0aGluayBJIGhhdmUgdGhlIHByb3RlY3Rpb24gc2VtYW50aWNzIHJpZ2h0Li4uLiB0aGlzIGlzIHJlYWxseQogKiBvbmx5IGltcG9ydGFudCBvbiBhIG11bHRpLXVzZXIgc3lzdGVtIGFueXdheSwgdG8gbWFrZSBzdXJlIG9uZSB1c2VyCiAqIGNhbid0IHNlbmQgYSBzaWduYWwgdG8gYSBwcm9jZXNzIG93bmVkIGJ5IGFub3RoZXIuICAtVFlULCAxMi8xMi85MQogKgogKiBBdWNoLiBIYWQgdG8gYWRkIHRoZSAnZGlkX2V4ZWMnIGZsYWcgdG8gY29uZm9ybSBjb21wbGV0ZWx5IHRvIFBPU0lYLgogKiBMQlQgMDQuMDMuOTQKICovCgphc21saW5rYWdlIGxvbmcgc3lzX3NldHBnaWQocGlkX3QgcGlkLCBwaWRfdCBwZ2lkKQp7CglzdHJ1Y3QgdGFza19zdHJ1Y3QgKnA7CglzdHJ1Y3QgdGFza19zdHJ1Y3QgKmdyb3VwX2xlYWRlciA9IGN1cnJlbnQtPmdyb3VwX2xlYWRlcjsKCWludCBlcnIgPSAtRUlOVkFMOwoKCWlmICghcGlkKQoJCXBpZCA9IGdyb3VwX2xlYWRlci0+cGlkOwoJaWYgKCFwZ2lkKQoJCXBnaWQgPSBwaWQ7CglpZiAocGdpZCA8IDApCgkJcmV0dXJuIC1FSU5WQUw7CgoJLyogRnJvbSB0aGlzIHBvaW50IGZvcndhcmQgd2Uga2VlcCBob2xkaW5nIG9udG8gdGhlIHRhc2tsaXN0IGxvY2sKCSAqIHNvIHRoYXQgb3VyIHBhcmVudCBkb2VzIG5vdCBjaGFuZ2UgZnJvbSB1bmRlciB1cy4gLURhdmVNCgkgKi8KCXdyaXRlX2xvY2tfaXJxKCZ0YXNrbGlzdF9sb2NrKTsKCgllcnIgPSAtRVNSQ0g7CglwID0gZmluZF90YXNrX2J5X3BpZChwaWQpOwoJaWYgKCFwKQoJCWdvdG8gb3V0OwoKCWVyciA9IC1FSU5WQUw7CglpZiAoIXRocmVhZF9ncm91cF9sZWFkZXIocCkpCgkJZ290byBvdXQ7CgoJaWYgKHAtPnJlYWxfcGFyZW50ID09IGdyb3VwX2xlYWRlcikgewoJCWVyciA9IC1FUEVSTTsKCQlpZiAocC0+c2lnbmFsLT5zZXNzaW9uICE9IGdyb3VwX2xlYWRlci0+c2lnbmFsLT5zZXNzaW9uKQoJCQlnb3RvIG91dDsKCQllcnIgPSAtRUFDQ0VTOwoJCWlmIChwLT5kaWRfZXhlYykKCQkJZ290byBvdXQ7Cgl9IGVsc2UgewoJCWVyciA9IC1FU1JDSDsKCQlpZiAocCAhPSBncm91cF9sZWFkZXIpCgkJCWdvdG8gb3V0OwoJfQoKCWVyciA9IC1FUEVSTTsKCWlmIChwLT5zaWduYWwtPmxlYWRlcikKCQlnb3RvIG91dDsKCglpZiAocGdpZCAhPSBwaWQpIHsKCQlzdHJ1Y3QgdGFza19zdHJ1Y3QgKnA7CgoJCWRvX2VhY2hfdGFza19waWQocGdpZCwgUElEVFlQRV9QR0lELCBwKSB7CgkJCWlmIChwLT5zaWduYWwtPnNlc3Npb24gPT0gZ3JvdXBfbGVhZGVyLT5zaWduYWwtPnNlc3Npb24pCgkJCQlnb3RvIG9rX3BnaWQ7CgkJfSB3aGlsZV9lYWNoX3Rhc2tfcGlkKHBnaWQsIFBJRFRZUEVfUEdJRCwgcCk7CgkJZ290byBvdXQ7Cgl9Cgpva19wZ2lkOgoJZXJyID0gc2VjdXJpdHlfdGFza19zZXRwZ2lkKHAsIHBnaWQpOwoJaWYgKGVycikKCQlnb3RvIG91dDsKCglpZiAocHJvY2Vzc19ncm91cChwKSAhPSBwZ2lkKSB7CgkJZGV0YWNoX3BpZChwLCBQSURUWVBFX1BHSUQpOwoJCXAtPnNpZ25hbC0+cGdycCA9IHBnaWQ7CgkJYXR0YWNoX3BpZChwLCBQSURUWVBFX1BHSUQsIHBnaWQpOwoJfQoKCWVyciA9IDA7Cm91dDoKCS8qIEFsbCBwYXRocyBsZWFkIHRvIGhlcmUsIHRodXMgd2UgYXJlIHNhZmUuIC1EYXZlTSAqLwoJd3JpdGVfdW5sb2NrX2lycSgmdGFza2xpc3RfbG9jayk7CglyZXR1cm4gZXJyOwp9Cgphc21saW5rYWdlIGxvbmcgc3lzX2dldHBnaWQocGlkX3QgcGlkKQp7CglpZiAoIXBpZCkgewoJCXJldHVybiBwcm9jZXNzX2dyb3VwKGN1cnJlbnQpOwoJfSBlbHNlIHsKCQlpbnQgcmV0dmFsOwoJCXN0cnVjdCB0YXNrX3N0cnVjdCAqcDsKCgkJcmVhZF9sb2NrKCZ0YXNrbGlzdF9sb2NrKTsKCQlwID0gZmluZF90YXNrX2J5X3BpZChwaWQpOwoKCQlyZXR2YWwgPSAtRVNSQ0g7CgkJaWYgKHApIHsKCQkJcmV0dmFsID0gc2VjdXJpdHlfdGFza19nZXRwZ2lkKHApOwoJCQlpZiAoIXJldHZhbCkKCQkJCXJldHZhbCA9IHByb2Nlc3NfZ3JvdXAocCk7CgkJfQoJCXJlYWRfdW5sb2NrKCZ0YXNrbGlzdF9sb2NrKTsKCQlyZXR1cm4gcmV0dmFsOwoJfQp9CgojaWZkZWYgX19BUkNIX1dBTlRfU1lTX0dFVFBHUlAKCmFzbWxpbmthZ2UgbG9uZyBzeXNfZ2V0cGdycCh2b2lkKQp7CgkvKiBTTVAgLSBhc3N1bWluZyB3cml0ZXMgYXJlIHdvcmQgYXRvbWljIHRoaXMgaXMgZmluZSAqLwoJcmV0dXJuIHByb2Nlc3NfZ3JvdXAoY3VycmVudCk7Cn0KCiNlbmRpZgoKYXNtbGlua2FnZSBsb25nIHN5c19nZXRzaWQocGlkX3QgcGlkKQp7CglpZiAoIXBpZCkgewoJCXJldHVybiBjdXJyZW50LT5zaWduYWwtPnNlc3Npb247Cgl9IGVsc2UgewoJCWludCByZXR2YWw7CgkJc3RydWN0IHRhc2tfc3RydWN0ICpwOwoKCQlyZWFkX2xvY2soJnRhc2tsaXN0X2xvY2spOwoJCXAgPSBmaW5kX3Rhc2tfYnlfcGlkKHBpZCk7CgoJCXJldHZhbCA9IC1FU1JDSDsKCQlpZihwKSB7CgkJCXJldHZhbCA9IHNlY3VyaXR5X3Rhc2tfZ2V0c2lkKHApOwoJCQlpZiAoIXJldHZhbCkKCQkJCXJldHZhbCA9IHAtPnNpZ25hbC0+c2Vzc2lvbjsKCQl9CgkJcmVhZF91bmxvY2soJnRhc2tsaXN0X2xvY2spOwoJCXJldHVybiByZXR2YWw7Cgl9Cn0KCmFzbWxpbmthZ2UgbG9uZyBzeXNfc2V0c2lkKHZvaWQpCnsKCXN0cnVjdCB0YXNrX3N0cnVjdCAqZ3JvdXBfbGVhZGVyID0gY3VycmVudC0+Z3JvdXBfbGVhZGVyOwoJc3RydWN0IHBpZCAqcGlkOwoJaW50IGVyciA9IC1FUEVSTTsKCgltdXRleF9sb2NrKCZ0dHlfbXV0ZXgpOwoJd3JpdGVfbG9ja19pcnEoJnRhc2tsaXN0X2xvY2spOwoKCXBpZCA9IGZpbmRfcGlkKFBJRFRZUEVfUEdJRCwgZ3JvdXBfbGVhZGVyLT5waWQpOwoJaWYgKHBpZCkKCQlnb3RvIG91dDsKCglncm91cF9sZWFkZXItPnNpZ25hbC0+bGVhZGVyID0gMTsKCV9fc2V0X3NwZWNpYWxfcGlkcyhncm91cF9sZWFkZXItPnBpZCwgZ3JvdXBfbGVhZGVyLT5waWQpOwoJZ3JvdXBfbGVhZGVyLT5zaWduYWwtPnR0eSA9IE5VTEw7Cglncm91cF9sZWFkZXItPnNpZ25hbC0+dHR5X29sZF9wZ3JwID0gMDsKCWVyciA9IHByb2Nlc3NfZ3JvdXAoZ3JvdXBfbGVhZGVyKTsKb3V0OgoJd3JpdGVfdW5sb2NrX2lycSgmdGFza2xpc3RfbG9jayk7CgltdXRleF91bmxvY2soJnR0eV9tdXRleCk7CglyZXR1cm4gZXJyOwp9CgovKgogKiBTdXBwbGVtZW50YXJ5IGdyb3VwIElEcwogKi8KCi8qIGluaXQgdG8gMiAtIG9uZSBmb3IgaW5pdF90YXNrLCBvbmUgdG8gZW5zdXJlIGl0IGlzIG5ldmVyIGZyZWVkICovCnN0cnVjdCBncm91cF9pbmZvIGluaXRfZ3JvdXBzID0geyAudXNhZ2UgPSBBVE9NSUNfSU5JVCgyKSB9OwoKc3RydWN0IGdyb3VwX2luZm8gKmdyb3Vwc19hbGxvYyhpbnQgZ2lkc2V0c2l6ZSkKewoJc3RydWN0IGdyb3VwX2luZm8gKmdyb3VwX2luZm87CglpbnQgbmJsb2NrczsKCWludCBpOwoKCW5ibG9ja3MgPSAoZ2lkc2V0c2l6ZSArIE5HUk9VUFNfUEVSX0JMT0NLIC0gMSkgLyBOR1JPVVBTX1BFUl9CTE9DSzsKCS8qIE1ha2Ugc3VyZSB3ZSBhbHdheXMgYWxsb2NhdGUgYXQgbGVhc3Qgb25lIGluZGlyZWN0IGJsb2NrIHBvaW50ZXIgKi8KCW5ibG9ja3MgPSBuYmxvY2tzID8gOiAxOwoJZ3JvdXBfaW5mbyA9IGttYWxsb2Moc2l6ZW9mKCpncm91cF9pbmZvKSArIG5ibG9ja3Mqc2l6ZW9mKGdpZF90ICopLCBHRlBfVVNFUik7CglpZiAoIWdyb3VwX2luZm8pCgkJcmV0dXJuIE5VTEw7Cglncm91cF9pbmZvLT5uZ3JvdXBzID0gZ2lkc2V0c2l6ZTsKCWdyb3VwX2luZm8tPm5ibG9ja3MgPSBuYmxvY2tzOwoJYXRvbWljX3NldCgmZ3JvdXBfaW5mby0+dXNhZ2UsIDEpOwoKCWlmIChnaWRzZXRzaXplIDw9IE5HUk9VUFNfU01BTEwpIHsKCQlncm91cF9pbmZvLT5ibG9ja3NbMF0gPSBncm91cF9pbmZvLT5zbWFsbF9ibG9jazsKCX0gZWxzZSB7CgkJZm9yIChpID0gMDsgaSA8IG5ibG9ja3M7IGkrKykgewoJCQlnaWRfdCAqYjsKCQkJYiA9ICh2b2lkICopX19nZXRfZnJlZV9wYWdlKEdGUF9VU0VSKTsKCQkJaWYgKCFiKQoJCQkJZ290byBvdXRfdW5kb19wYXJ0aWFsX2FsbG9jOwoJCQlncm91cF9pbmZvLT5ibG9ja3NbaV0gPSBiOwoJCX0KCX0KCXJldHVybiBncm91cF9pbmZvOwoKb3V0X3VuZG9fcGFydGlhbF9hbGxvYzoKCXdoaWxlICgtLWkgPj0gMCkgewoJCWZyZWVfcGFnZSgodW5zaWduZWQgbG9uZylncm91cF9pbmZvLT5ibG9ja3NbaV0pOwoJfQoJa2ZyZWUoZ3JvdXBfaW5mbyk7CglyZXR1cm4gTlVMTDsKfQoKRVhQT1JUX1NZTUJPTChncm91cHNfYWxsb2MpOwoKdm9pZCBncm91cHNfZnJlZShzdHJ1Y3QgZ3JvdXBfaW5mbyAqZ3JvdXBfaW5mbykKewoJaWYgKGdyb3VwX2luZm8tPmJsb2Nrc1swXSAhPSBncm91cF9pbmZvLT5zbWFsbF9ibG9jaykgewoJCWludCBpOwoJCWZvciAoaSA9IDA7IGkgPCBncm91cF9pbmZvLT5uYmxvY2tzOyBpKyspCgkJCWZyZWVfcGFnZSgodW5zaWduZWQgbG9uZylncm91cF9pbmZvLT5ibG9ja3NbaV0pOwoJfQoJa2ZyZWUoZ3JvdXBfaW5mbyk7Cn0KCkVYUE9SVF9TWU1CT0woZ3JvdXBzX2ZyZWUpOwoKLyogZXhwb3J0IHRoZSBncm91cF9pbmZvIHRvIGEgdXNlci1zcGFjZSBhcnJheSAqLwpzdGF0aWMgaW50IGdyb3Vwc190b191c2VyKGdpZF90IF9fdXNlciAqZ3JvdXBsaXN0LAogICAgc3RydWN0IGdyb3VwX2luZm8gKmdyb3VwX2luZm8pCnsKCWludCBpOwoJaW50IGNvdW50ID0gZ3JvdXBfaW5mby0+bmdyb3VwczsKCglmb3IgKGkgPSAwOyBpIDwgZ3JvdXBfaW5mby0+bmJsb2NrczsgaSsrKSB7CgkJaW50IGNwX2NvdW50ID0gbWluKE5HUk9VUFNfUEVSX0JMT0NLLCBjb3VudCk7CgkJaW50IG9mZiA9IGkgKiBOR1JPVVBTX1BFUl9CTE9DSzsKCQlpbnQgbGVuID0gY3BfY291bnQgKiBzaXplb2YoKmdyb3VwbGlzdCk7CgoJCWlmIChjb3B5X3RvX3VzZXIoZ3JvdXBsaXN0K29mZiwgZ3JvdXBfaW5mby0+YmxvY2tzW2ldLCBsZW4pKQoJCQlyZXR1cm4gLUVGQVVMVDsKCgkJY291bnQgLT0gY3BfY291bnQ7Cgl9CglyZXR1cm4gMDsKfQoKLyogZmlsbCBhIGdyb3VwX2luZm8gZnJvbSBhIHVzZXItc3BhY2UgYXJyYXkgLSBpdCBtdXN0IGJlIGFsbG9jYXRlZCBhbHJlYWR5ICovCnN0YXRpYyBpbnQgZ3JvdXBzX2Zyb21fdXNlcihzdHJ1Y3QgZ3JvdXBfaW5mbyAqZ3JvdXBfaW5mbywKICAgIGdpZF90IF9fdXNlciAqZ3JvdXBsaXN0KQogewoJaW50IGk7CglpbnQgY291bnQgPSBncm91cF9pbmZvLT5uZ3JvdXBzOwoKCWZvciAoaSA9IDA7IGkgPCBncm91cF9pbmZvLT5uYmxvY2tzOyBpKyspIHsKCQlpbnQgY3BfY291bnQgPSBtaW4oTkdST1VQU19QRVJfQkxPQ0ssIGNvdW50KTsKCQlpbnQgb2ZmID0gaSAqIE5HUk9VUFNfUEVSX0JMT0NLOwoJCWludCBsZW4gPSBjcF9jb3VudCAqIHNpemVvZigqZ3JvdXBsaXN0KTsKCgkJaWYgKGNvcHlfZnJvbV91c2VyKGdyb3VwX2luZm8tPmJsb2Nrc1tpXSwgZ3JvdXBsaXN0K29mZiwgbGVuKSkKCQkJcmV0dXJuIC1FRkFVTFQ7CgoJCWNvdW50IC09IGNwX2NvdW50OwoJfQoJcmV0dXJuIDA7Cn0KCi8qIGEgc2ltcGxlIFNoZWxsIHNvcnQgKi8Kc3RhdGljIHZvaWQgZ3JvdXBzX3NvcnQoc3RydWN0IGdyb3VwX2luZm8gKmdyb3VwX2luZm8pCnsKCWludCBiYXNlLCBtYXgsIHN0cmlkZTsKCWludCBnaWRzZXRzaXplID0gZ3JvdXBfaW5mby0+bmdyb3VwczsKCglmb3IgKHN0cmlkZSA9IDE7IHN0cmlkZSA8IGdpZHNldHNpemU7IHN0cmlkZSA9IDMgKiBzdHJpZGUgKyAxKQoJCTsgLyogbm90aGluZyAqLwoJc3RyaWRlIC89IDM7CgoJd2hpbGUgKHN0cmlkZSkgewoJCW1heCA9IGdpZHNldHNpemUgLSBzdHJpZGU7CgkJZm9yIChiYXNlID0gMDsgYmFzZSA8IG1heDsgYmFzZSsrKSB7CgkJCWludCBsZWZ0ID0gYmFzZTsKCQkJaW50IHJpZ2h0ID0gbGVmdCArIHN0cmlkZTsKCQkJZ2lkX3QgdG1wID0gR1JPVVBfQVQoZ3JvdXBfaW5mbywgcmlnaHQpOwoKCQkJd2hpbGUgKGxlZnQgPj0gMCAmJiBHUk9VUF9BVChncm91cF9pbmZvLCBsZWZ0KSA+IHRtcCkgewoJCQkJR1JPVVBfQVQoZ3JvdXBfaW5mbywgcmlnaHQpID0KCQkJCSAgICBHUk9VUF9BVChncm91cF9pbmZvLCBsZWZ0KTsKCQkJCXJpZ2h0ID0gbGVmdDsKCQkJCWxlZnQgLT0gc3RyaWRlOwoJCQl9CgkJCUdST1VQX0FUKGdyb3VwX2luZm8sIHJpZ2h0KSA9IHRtcDsKCQl9CgkJc3RyaWRlIC89IDM7Cgl9Cn0KCi8qIGEgc2ltcGxlIGJzZWFyY2ggKi8KaW50IGdyb3Vwc19zZWFyY2goc3RydWN0IGdyb3VwX2luZm8gKmdyb3VwX2luZm8sIGdpZF90IGdycCkKewoJdW5zaWduZWQgaW50IGxlZnQsIHJpZ2h0OwoKCWlmICghZ3JvdXBfaW5mbykKCQlyZXR1cm4gMDsKCglsZWZ0ID0gMDsKCXJpZ2h0ID0gZ3JvdXBfaW5mby0+bmdyb3VwczsKCXdoaWxlIChsZWZ0IDwgcmlnaHQpIHsKCQl1bnNpZ25lZCBpbnQgbWlkID0gKGxlZnQrcmlnaHQpLzI7CgkJaW50IGNtcCA9IGdycCAtIEdST1VQX0FUKGdyb3VwX2luZm8sIG1pZCk7CgkJaWYgKGNtcCA+IDApCgkJCWxlZnQgPSBtaWQgKyAxOwoJCWVsc2UgaWYgKGNtcCA8IDApCgkJCXJpZ2h0ID0gbWlkOwoJCWVsc2UKCQkJcmV0dXJuIDE7Cgl9CglyZXR1cm4gMDsKfQoKLyogdmFsaWRhdGUgYW5kIHNldCBjdXJyZW50LT5ncm91cF9pbmZvICovCmludCBzZXRfY3VycmVudF9ncm91cHMoc3RydWN0IGdyb3VwX2luZm8gKmdyb3VwX2luZm8pCnsKCWludCByZXR2YWw7CglzdHJ1Y3QgZ3JvdXBfaW5mbyAqb2xkX2luZm87CgoJcmV0dmFsID0gc2VjdXJpdHlfdGFza19zZXRncm91cHMoZ3JvdXBfaW5mbyk7CglpZiAocmV0dmFsKQoJCXJldHVybiByZXR2YWw7CgoJZ3JvdXBzX3NvcnQoZ3JvdXBfaW5mbyk7CglnZXRfZ3JvdXBfaW5mbyhncm91cF9pbmZvKTsKCgl0YXNrX2xvY2soY3VycmVudCk7CglvbGRfaW5mbyA9IGN1cnJlbnQtPmdyb3VwX2luZm87CgljdXJyZW50LT5ncm91cF9pbmZvID0gZ3JvdXBfaW5mbzsKCXRhc2tfdW5sb2NrKGN1cnJlbnQpOwoKCXB1dF9ncm91cF9pbmZvKG9sZF9pbmZvKTsKCglyZXR1cm4gMDsKfQoKRVhQT1JUX1NZTUJPTChzZXRfY3VycmVudF9ncm91cHMpOwoKYXNtbGlua2FnZSBsb25nIHN5c19nZXRncm91cHMoaW50IGdpZHNldHNpemUsIGdpZF90IF9fdXNlciAqZ3JvdXBsaXN0KQp7CglpbnQgaSA9IDA7CgoJLyoKCSAqCVNNUDogTm9ib2R5IGVsc2UgY2FuIGNoYW5nZSBvdXIgZ3JvdXBsaXN0LiBUaHVzIHdlIGFyZQoJICoJc2FmZS4KCSAqLwoKCWlmIChnaWRzZXRzaXplIDwgMCkKCQlyZXR1cm4gLUVJTlZBTDsKCgkvKiBubyBuZWVkIHRvIGdyYWIgdGFza19sb2NrIGhlcmU7IGl0IGNhbm5vdCBjaGFuZ2UgKi8KCWkgPSBjdXJyZW50LT5ncm91cF9pbmZvLT5uZ3JvdXBzOwoJaWYgKGdpZHNldHNpemUpIHsKCQlpZiAoaSA+IGdpZHNldHNpemUpIHsKCQkJaSA9IC1FSU5WQUw7CgkJCWdvdG8gb3V0OwoJCX0KCQlpZiAoZ3JvdXBzX3RvX3VzZXIoZ3JvdXBsaXN0LCBjdXJyZW50LT5ncm91cF9pbmZvKSkgewoJCQlpID0gLUVGQVVMVDsKCQkJZ290byBvdXQ7CgkJfQoJfQpvdXQ6CglyZXR1cm4gaTsKfQoKLyoKICoJU01QOiBPdXIgZ3JvdXBzIGFyZSBjb3B5LW9uLXdyaXRlLiBXZSBjYW4gc2V0IHRoZW0gc2FmZWx5CiAqCXdpdGhvdXQgYW5vdGhlciB0YXNrIGludGVyZmVyaW5nLgogKi8KIAphc21saW5rYWdlIGxvbmcgc3lzX3NldGdyb3VwcyhpbnQgZ2lkc2V0c2l6ZSwgZ2lkX3QgX191c2VyICpncm91cGxpc3QpCnsKCXN0cnVjdCBncm91cF9pbmZvICpncm91cF9pbmZvOwoJaW50IHJldHZhbDsKCglpZiAoIWNhcGFibGUoQ0FQX1NFVEdJRCkpCgkJcmV0dXJuIC1FUEVSTTsKCWlmICgodW5zaWduZWQpZ2lkc2V0c2l6ZSA+IE5HUk9VUFNfTUFYKQoJCXJldHVybiAtRUlOVkFMOwoKCWdyb3VwX2luZm8gPSBncm91cHNfYWxsb2MoZ2lkc2V0c2l6ZSk7CglpZiAoIWdyb3VwX2luZm8pCgkJcmV0dXJuIC1FTk9NRU07CglyZXR2YWwgPSBncm91cHNfZnJvbV91c2VyKGdyb3VwX2luZm8sIGdyb3VwbGlzdCk7CglpZiAocmV0dmFsKSB7CgkJcHV0X2dyb3VwX2luZm8oZ3JvdXBfaW5mbyk7CgkJcmV0dXJuIHJldHZhbDsKCX0KCglyZXR2YWwgPSBzZXRfY3VycmVudF9ncm91cHMoZ3JvdXBfaW5mbyk7CglwdXRfZ3JvdXBfaW5mbyhncm91cF9pbmZvKTsKCglyZXR1cm4gcmV0dmFsOwp9CgovKgogKiBDaGVjayB3aGV0aGVyIHdlJ3JlIGZzZ2lkL2VnaWQgb3IgaW4gdGhlIHN1cHBsZW1lbnRhbCBncm91cC4uCiAqLwppbnQgaW5fZ3JvdXBfcChnaWRfdCBncnApCnsKCWludCByZXR2YWwgPSAxOwoJaWYgKGdycCAhPSBjdXJyZW50LT5mc2dpZCkgewoJCXJldHZhbCA9IGdyb3Vwc19zZWFyY2goY3VycmVudC0+Z3JvdXBfaW5mbywgZ3JwKTsKCX0KCXJldHVybiByZXR2YWw7Cn0KCkVYUE9SVF9TWU1CT0woaW5fZ3JvdXBfcCk7CgppbnQgaW5fZWdyb3VwX3AoZ2lkX3QgZ3JwKQp7CglpbnQgcmV0dmFsID0gMTsKCWlmIChncnAgIT0gY3VycmVudC0+ZWdpZCkgewoJCXJldHZhbCA9IGdyb3Vwc19zZWFyY2goY3VycmVudC0+Z3JvdXBfaW5mbywgZ3JwKTsKCX0KCXJldHVybiByZXR2YWw7Cn0KCkVYUE9SVF9TWU1CT0woaW5fZWdyb3VwX3ApOwoKREVDTEFSRV9SV1NFTSh1dHNfc2VtKTsKCkVYUE9SVF9TWU1CT0wodXRzX3NlbSk7Cgphc21saW5rYWdlIGxvbmcgc3lzX25ld3VuYW1lKHN0cnVjdCBuZXdfdXRzbmFtZSBfX3VzZXIgKiBuYW1lKQp7CglpbnQgZXJybm8gPSAwOwoKCWRvd25fcmVhZCgmdXRzX3NlbSk7CglpZiAoY29weV90b191c2VyKG5hbWUsJnN5c3RlbV91dHNuYW1lLHNpemVvZiAqbmFtZSkpCgkJZXJybm8gPSAtRUZBVUxUOwoJdXBfcmVhZCgmdXRzX3NlbSk7CglyZXR1cm4gZXJybm87Cn0KCmFzbWxpbmthZ2UgbG9uZyBzeXNfc2V0aG9zdG5hbWUoY2hhciBfX3VzZXIgKm5hbWUsIGludCBsZW4pCnsKCWludCBlcnJubzsKCWNoYXIgdG1wW19fTkVXX1VUU19MRU5dOwoKCWlmICghY2FwYWJsZShDQVBfU1lTX0FETUlOKSkKCQlyZXR1cm4gLUVQRVJNOwoJaWYgKGxlbiA8IDAgfHwgbGVuID4gX19ORVdfVVRTX0xFTikKCQlyZXR1cm4gLUVJTlZBTDsKCWRvd25fd3JpdGUoJnV0c19zZW0pOwoJZXJybm8gPSAtRUZBVUxUOwoJaWYgKCFjb3B5X2Zyb21fdXNlcih0bXAsIG5hbWUsIGxlbikpIHsKCQltZW1jcHkoc3lzdGVtX3V0c25hbWUubm9kZW5hbWUsIHRtcCwgbGVuKTsKCQlzeXN0ZW1fdXRzbmFtZS5ub2RlbmFtZVtsZW5dID0gMDsKCQllcnJubyA9IDA7Cgl9Cgl1cF93cml0ZSgmdXRzX3NlbSk7CglyZXR1cm4gZXJybm87Cn0KCiNpZmRlZiBfX0FSQ0hfV0FOVF9TWVNfR0VUSE9TVE5BTUUKCmFzbWxpbmthZ2UgbG9uZyBzeXNfZ2V0aG9zdG5hbWUoY2hhciBfX3VzZXIgKm5hbWUsIGludCBsZW4pCnsKCWludCBpLCBlcnJubzsKCglpZiAobGVuIDwgMCkKCQlyZXR1cm4gLUVJTlZBTDsKCWRvd25fcmVhZCgmdXRzX3NlbSk7CglpID0gMSArIHN0cmxlbihzeXN0ZW1fdXRzbmFtZS5ub2RlbmFtZSk7CglpZiAoaSA+IGxlbikKCQlpID0gbGVuOwoJZXJybm8gPSAwOwoJaWYgKGNvcHlfdG9fdXNlcihuYW1lLCBzeXN0ZW1fdXRzbmFtZS5ub2RlbmFtZSwgaSkpCgkJZXJybm8gPSAtRUZBVUxUOwoJdXBfcmVhZCgmdXRzX3NlbSk7CglyZXR1cm4gZXJybm87Cn0KCiNlbmRpZgoKLyoKICogT25seSBzZXRkb21haW5uYW1lOyBnZXRkb21haW5uYW1lIGNhbiBiZSBpbXBsZW1lbnRlZCBieSBjYWxsaW5nCiAqIHVuYW1lKCkKICovCmFzbWxpbmthZ2UgbG9uZyBzeXNfc2V0ZG9tYWlubmFtZShjaGFyIF9fdXNlciAqbmFtZSwgaW50IGxlbikKewoJaW50IGVycm5vOwoJY2hhciB0bXBbX19ORVdfVVRTX0xFTl07CgoJaWYgKCFjYXBhYmxlKENBUF9TWVNfQURNSU4pKQoJCXJldHVybiAtRVBFUk07CglpZiAobGVuIDwgMCB8fCBsZW4gPiBfX05FV19VVFNfTEVOKQoJCXJldHVybiAtRUlOVkFMOwoKCWRvd25fd3JpdGUoJnV0c19zZW0pOwoJZXJybm8gPSAtRUZBVUxUOwoJaWYgKCFjb3B5X2Zyb21fdXNlcih0bXAsIG5hbWUsIGxlbikpIHsKCQltZW1jcHkoc3lzdGVtX3V0c25hbWUuZG9tYWlubmFtZSwgdG1wLCBsZW4pOwoJCXN5c3RlbV91dHNuYW1lLmRvbWFpbm5hbWVbbGVuXSA9IDA7CgkJZXJybm8gPSAwOwoJfQoJdXBfd3JpdGUoJnV0c19zZW0pOwoJcmV0dXJuIGVycm5vOwp9Cgphc21saW5rYWdlIGxvbmcgc3lzX2dldHJsaW1pdCh1bnNpZ25lZCBpbnQgcmVzb3VyY2UsIHN0cnVjdCBybGltaXQgX191c2VyICpybGltKQp7CglpZiAocmVzb3VyY2UgPj0gUkxJTV9OTElNSVRTKQoJCXJldHVybiAtRUlOVkFMOwoJZWxzZSB7CgkJc3RydWN0IHJsaW1pdCB2YWx1ZTsKCQl0YXNrX2xvY2soY3VycmVudC0+Z3JvdXBfbGVhZGVyKTsKCQl2YWx1ZSA9IGN1cnJlbnQtPnNpZ25hbC0+cmxpbVtyZXNvdXJjZV07CgkJdGFza191bmxvY2soY3VycmVudC0+Z3JvdXBfbGVhZGVyKTsKCQlyZXR1cm4gY29weV90b191c2VyKHJsaW0sICZ2YWx1ZSwgc2l6ZW9mKCpybGltKSkgPyAtRUZBVUxUIDogMDsKCX0KfQoKI2lmZGVmIF9fQVJDSF9XQU5UX1NZU19PTERfR0VUUkxJTUlUCgovKgogKglCYWNrIGNvbXBhdGliaWxpdHkgZm9yIGdldHJsaW1pdC4gTmVlZGVkIGZvciBzb21lIGFwcHMuCiAqLwogCmFzbWxpbmthZ2UgbG9uZyBzeXNfb2xkX2dldHJsaW1pdCh1bnNpZ25lZCBpbnQgcmVzb3VyY2UsIHN0cnVjdCBybGltaXQgX191c2VyICpybGltKQp7CglzdHJ1Y3QgcmxpbWl0IHg7CglpZiAocmVzb3VyY2UgPj0gUkxJTV9OTElNSVRTKQoJCXJldHVybiAtRUlOVkFMOwoKCXRhc2tfbG9jayhjdXJyZW50LT5ncm91cF9sZWFkZXIpOwoJeCA9IGN1cnJlbnQtPnNpZ25hbC0+cmxpbVtyZXNvdXJjZV07Cgl0YXNrX3VubG9jayhjdXJyZW50LT5ncm91cF9sZWFkZXIpOwoJaWYoeC5ybGltX2N1ciA+IDB4N0ZGRkZGRkYpCgkJeC5ybGltX2N1ciA9IDB4N0ZGRkZGRkY7CglpZih4LnJsaW1fbWF4ID4gMHg3RkZGRkZGRikKCQl4LnJsaW1fbWF4ID0gMHg3RkZGRkZGRjsKCXJldHVybiBjb3B5X3RvX3VzZXIocmxpbSwgJngsIHNpemVvZih4KSk/LUVGQVVMVDowOwp9CgojZW5kaWYKCmFzbWxpbmthZ2UgbG9uZyBzeXNfc2V0cmxpbWl0KHVuc2lnbmVkIGludCByZXNvdXJjZSwgc3RydWN0IHJsaW1pdCBfX3VzZXIgKnJsaW0pCnsKCXN0cnVjdCBybGltaXQgbmV3X3JsaW0sICpvbGRfcmxpbTsKCXVuc2lnbmVkIGxvbmcgaXRfcHJvZl9zZWNzOwoJaW50IHJldHZhbDsKCglpZiAocmVzb3VyY2UgPj0gUkxJTV9OTElNSVRTKQoJCXJldHVybiAtRUlOVkFMOwoJaWYgKGNvcHlfZnJvbV91c2VyKCZuZXdfcmxpbSwgcmxpbSwgc2l6ZW9mKCpybGltKSkpCgkJcmV0dXJuIC1FRkFVTFQ7CglpZiAobmV3X3JsaW0ucmxpbV9jdXIgPiBuZXdfcmxpbS5ybGltX21heCkKCQlyZXR1cm4gLUVJTlZBTDsKCW9sZF9ybGltID0gY3VycmVudC0+c2lnbmFsLT5ybGltICsgcmVzb3VyY2U7CglpZiAoKG5ld19ybGltLnJsaW1fbWF4ID4gb2xkX3JsaW0tPnJsaW1fbWF4KSAmJgoJICAgICFjYXBhYmxlKENBUF9TWVNfUkVTT1VSQ0UpKQoJCXJldHVybiAtRVBFUk07CglpZiAocmVzb3VyY2UgPT0gUkxJTUlUX05PRklMRSAmJiBuZXdfcmxpbS5ybGltX21heCA+IE5SX09QRU4pCgkJcmV0dXJuIC1FUEVSTTsKCglyZXR2YWwgPSBzZWN1cml0eV90YXNrX3NldHJsaW1pdChyZXNvdXJjZSwgJm5ld19ybGltKTsKCWlmIChyZXR2YWwpCgkJcmV0dXJuIHJldHZhbDsKCgl0YXNrX2xvY2soY3VycmVudC0+Z3JvdXBfbGVhZGVyKTsKCSpvbGRfcmxpbSA9IG5ld19ybGltOwoJdGFza191bmxvY2soY3VycmVudC0+Z3JvdXBfbGVhZGVyKTsKCglpZiAocmVzb3VyY2UgIT0gUkxJTUlUX0NQVSkKCQlnb3RvIG91dDsKCgkvKgoJICogUkxJTUlUX0NQVSBoYW5kbGluZy4gICBOb3RlIHRoYXQgdGhlIGtlcm5lbCBmYWlscyB0byByZXR1cm4gYW4gZXJyb3IKCSAqIGNvZGUgaWYgaXQgcmVqZWN0ZWQgdGhlIHVzZXIncyBhdHRlbXB0IHRvIHNldCBSTElNSVRfQ1BVLiAgVGhpcyBpcyBhCgkgKiB2ZXJ5IGxvbmctc3RhbmRpbmcgZXJyb3IsIGFuZCBmaXhpbmcgaXQgbm93IHJpc2tzIGJyZWFrYWdlIG9mCgkgKiBhcHBsaWNhdGlvbnMsIHNvIHdlIGxpdmUgd2l0aCBpdAoJICovCglpZiAobmV3X3JsaW0ucmxpbV9jdXIgPT0gUkxJTV9JTkZJTklUWSkKCQlnb3RvIG91dDsKCglpdF9wcm9mX3NlY3MgPSBjcHV0aW1lX3RvX3NlY3MoY3VycmVudC0+c2lnbmFsLT5pdF9wcm9mX2V4cGlyZXMpOwoJaWYgKGl0X3Byb2Zfc2VjcyA9PSAwIHx8IG5ld19ybGltLnJsaW1fY3VyIDw9IGl0X3Byb2Zfc2VjcykgewoJCXVuc2lnbmVkIGxvbmcgcmxpbV9jdXIgPSBuZXdfcmxpbS5ybGltX2N1cjsKCQljcHV0aW1lX3QgY3B1dGltZTsKCgkJaWYgKHJsaW1fY3VyID09IDApIHsKCQkJLyoKCQkJICogVGhlIGNhbGxlciBpcyBhc2tpbmcgZm9yIGFuIGltbWVkaWF0ZSBSTElNSVRfQ1BVCgkJCSAqIGV4cGlyeS4gIEJ1dCB3ZSB1c2UgdGhlIHplcm8gdmFsdWUgdG8gbWVhbiAiaXQgd2FzCgkJCSAqIG5ldmVyIHNldCIuICBTbyBsZXQncyBjaGVhdCBhbmQgbWFrZSBpdCBvbmUgc2Vjb25kCgkJCSAqIGluc3RlYWQKCQkJICovCgkJCXJsaW1fY3VyID0gMTsKCQl9CgkJY3B1dGltZSA9IHNlY3NfdG9fY3B1dGltZShybGltX2N1cik7CgkJcmVhZF9sb2NrKCZ0YXNrbGlzdF9sb2NrKTsKCQlzcGluX2xvY2tfaXJxKCZjdXJyZW50LT5zaWdoYW5kLT5zaWdsb2NrKTsKCQlzZXRfcHJvY2Vzc19jcHVfdGltZXIoY3VycmVudCwgQ1BVQ0xPQ0tfUFJPRiwgJmNwdXRpbWUsIE5VTEwpOwoJCXNwaW5fdW5sb2NrX2lycSgmY3VycmVudC0+c2lnaGFuZC0+c2lnbG9jayk7CgkJcmVhZF91bmxvY2soJnRhc2tsaXN0X2xvY2spOwoJfQpvdXQ6CglyZXR1cm4gMDsKfQoKLyoKICogSXQgd291bGQgbWFrZSBzZW5zZSB0byBwdXQgc3RydWN0IHJ1c2FnZSBpbiB0aGUgdGFza19zdHJ1Y3QsCiAqIGV4Y2VwdCB0aGF0IHdvdWxkIG1ha2UgdGhlIHRhc2tfc3RydWN0IGJlICpyZWFsbHkgYmlnKi4gIEFmdGVyCiAqIHRhc2tfc3RydWN0IGdldHMgbW92ZWQgaW50byBtYWxsb2MnZWQgbWVtb3J5LCBpdCB3b3VsZAogKiBtYWtlIHNlbnNlIHRvIGRvIHRoaXMuICBJdCB3aWxsIG1ha2UgbW92aW5nIHRoZSByZXN0IG9mIHRoZSBpbmZvcm1hdGlvbgogKiBhIGxvdCBzaW1wbGVyISAgKFdoaWNoIHdlJ3JlIG5vdCBkb2luZyByaWdodCBub3cgYmVjYXVzZSB3ZSdyZSBub3QKICogbWVhc3VyaW5nIHRoZW0geWV0KS4KICoKICogV2hlbiBzYW1wbGluZyBtdWx0aXBsZSB0aHJlYWRzIGZvciBSVVNBR0VfU0VMRiwgdW5kZXIgU01QIHdlIG1pZ2h0IGhhdmUKICogcmFjZXMgd2l0aCB0aHJlYWRzIGluY3JlbWVudGluZyB0aGVpciBvd24gY291bnRlcnMuICBCdXQgc2luY2Ugd29yZAogKiByZWFkcyBhcmUgYXRvbWljLCB3ZSBlaXRoZXIgZ2V0IG5ldyB2YWx1ZXMgb3Igb2xkIHZhbHVlcyBhbmQgd2UgZG9uJ3QKICogY2FyZSB3aGljaCBmb3IgdGhlIHN1bXMuICBXZSBhbHdheXMgdGFrZSB0aGUgc2lnbG9jayB0byBwcm90ZWN0IHJlYWRpbmcKICogdGhlIGMqIGZpZWxkcyBmcm9tIHAtPnNpZ25hbCBmcm9tIHJhY2VzIHdpdGggZXhpdC5jIHVwZGF0aW5nIHRob3NlCiAqIGZpZWxkcyB3aGVuIHJlYXBpbmcsIHNvIGEgc2FtcGxlIGVpdGhlciBnZXRzIGFsbCB0aGUgYWRkaXRpb25zIG9mIGEKICogZ2l2ZW4gY2hpbGQgYWZ0ZXIgaXQncyByZWFwZWQsIG9yIG5vbmUgc28gdGhpcyBzYW1wbGUgaXMgYmVmb3JlIHJlYXBpbmcuCiAqCiAqIHRhc2tsaXN0X2xvY2sgbG9ja2luZyBvcHRpbWlzYXRpb246CiAqIElmIHdlIGFyZSBjdXJyZW50IGFuZCBzaW5nbGUgdGhyZWFkZWQsIHdlIGRvIG5vdCBuZWVkIHRvIHRha2UgdGhlIHRhc2tsaXN0CiAqIGxvY2sgb3IgdGhlIHNpZ2xvY2suICBObyBvbmUgZWxzZSBjYW4gdGFrZSBvdXIgc2lnbmFsX3N0cnVjdCBhd2F5LAogKiBubyBvbmUgZWxzZSBjYW4gcmVhcCB0aGUgY2hpbGRyZW4gdG8gdXBkYXRlIHNpZ25hbC0+YyogY291bnRlcnMsIGFuZAogKiBubyBvbmUgZWxzZSBjYW4gcmFjZSB3aXRoIHRoZSBzaWduYWwtPiBmaWVsZHMuCiAqIElmIHdlIGRvIG5vdCB0YWtlIHRoZSB0YXNrbGlzdF9sb2NrLCB0aGUgc2lnbmFsLT4gZmllbGRzIGNvdWxkIGJlIHJlYWQKICogb3V0IG9mIG9yZGVyIHdoaWxlIGFub3RoZXIgdGhyZWFkIHdhcyBqdXN0IGV4aXRpbmcuIFNvIHdlIHBsYWNlIGEKICogcmVhZCBtZW1vcnkgYmFycmllciB3aGVuIHdlIGF2b2lkIHRoZSBsb2NrLiAgT24gdGhlIHdyaXRlciBzaWRlLAogKiB3cml0ZSBtZW1vcnkgYmFycmllciBpcyBpbXBsaWVkIGluICBfX2V4aXRfc2lnbmFsIGFzIF9fZXhpdF9zaWduYWwgcmVsZWFzZXMKICogdGhlIHNpZ2xvY2sgc3BpbmxvY2sgYWZ0ZXIgdXBkYXRpbmcgdGhlIHNpZ25hbC0+IGZpZWxkcy4KICoKICogV2UgZG9uJ3QgcmVhbGx5IG5lZWQgdGhlIHNpZ2xvY2sgd2hlbiB3ZSBhY2Nlc3MgdGhlIG5vbiBjKiBmaWVsZHMKICogb2YgdGhlIHNpZ25hbF9zdHJ1Y3QgKGZvciBSVVNBR0VfU0VMRikgZXZlbiBpbiBtdWx0aXRocmVhZGVkCiAqIGNhc2UsIHNpbmNlIHdlIHRha2UgdGhlIHRhc2tsaXN0IGxvY2sgZm9yIHJlYWQgYW5kIHRoZSBub24gYyogc2lnbmFsLT4KICogZmllbGRzIGFyZSB1cGRhdGVkIG9ubHkgaW4gX19leGl0X3NpZ25hbCwgd2hpY2ggaXMgY2FsbGVkIHdpdGgKICogdGFza2xpc3RfbG9jayB0YWtlbiBmb3Igd3JpdGUsIGhlbmNlIHRoZXNlIHR3byB0aHJlYWRzIGNhbm5vdCBleGVjdXRlCiAqIGNvbmN1cnJlbnRseS4KICoKICovCgpzdGF0aWMgdm9pZCBrX2dldHJ1c2FnZShzdHJ1Y3QgdGFza19zdHJ1Y3QgKnAsIGludCB3aG8sIHN0cnVjdCBydXNhZ2UgKnIpCnsKCXN0cnVjdCB0YXNrX3N0cnVjdCAqdDsKCXVuc2lnbmVkIGxvbmcgZmxhZ3M7CgljcHV0aW1lX3QgdXRpbWUsIHN0aW1lOwoJaW50IG5lZWRfbG9jayA9IDA7CgoJbWVtc2V0KChjaGFyICopIHIsIDAsIHNpemVvZiAqcik7Cgl1dGltZSA9IHN0aW1lID0gY3B1dGltZV96ZXJvOwoKCWlmIChwICE9IGN1cnJlbnQgfHwgIXRocmVhZF9ncm91cF9lbXB0eShwKSkKCQluZWVkX2xvY2sgPSAxOwoKCWlmIChuZWVkX2xvY2spIHsKCQlyZWFkX2xvY2soJnRhc2tsaXN0X2xvY2spOwoJCWlmICh1bmxpa2VseSghcC0+c2lnbmFsKSkgewoJCQlyZWFkX3VubG9jaygmdGFza2xpc3RfbG9jayk7CgkJCXJldHVybjsKCQl9Cgl9IGVsc2UKCQkvKiBTZWUgbG9ja2luZyBjb21tZW50cyBhYm92ZSAqLwoJCXNtcF9ybWIoKTsKCglzd2l0Y2ggKHdobykgewoJCWNhc2UgUlVTQUdFX0JPVEg6CgkJY2FzZSBSVVNBR0VfQ0hJTERSRU46CgkJCXNwaW5fbG9ja19pcnFzYXZlKCZwLT5zaWdoYW5kLT5zaWdsb2NrLCBmbGFncyk7CgkJCXV0aW1lID0gcC0+c2lnbmFsLT5jdXRpbWU7CgkJCXN0aW1lID0gcC0+c2lnbmFsLT5jc3RpbWU7CgkJCXItPnJ1X252Y3N3ID0gcC0+c2lnbmFsLT5jbnZjc3c7CgkJCXItPnJ1X25pdmNzdyA9IHAtPnNpZ25hbC0+Y25pdmNzdzsKCQkJci0+cnVfbWluZmx0ID0gcC0+c2lnbmFsLT5jbWluX2ZsdDsKCQkJci0+cnVfbWFqZmx0ID0gcC0+c2lnbmFsLT5jbWFqX2ZsdDsKCQkJc3Bpbl91bmxvY2tfaXJxcmVzdG9yZSgmcC0+c2lnaGFuZC0+c2lnbG9jaywgZmxhZ3MpOwoKCQkJaWYgKHdobyA9PSBSVVNBR0VfQ0hJTERSRU4pCgkJCQlicmVhazsKCgkJY2FzZSBSVVNBR0VfU0VMRjoKCQkJdXRpbWUgPSBjcHV0aW1lX2FkZCh1dGltZSwgcC0+c2lnbmFsLT51dGltZSk7CgkJCXN0aW1lID0gY3B1dGltZV9hZGQoc3RpbWUsIHAtPnNpZ25hbC0+c3RpbWUpOwoJCQlyLT5ydV9udmNzdyArPSBwLT5zaWduYWwtPm52Y3N3OwoJCQlyLT5ydV9uaXZjc3cgKz0gcC0+c2lnbmFsLT5uaXZjc3c7CgkJCXItPnJ1X21pbmZsdCArPSBwLT5zaWduYWwtPm1pbl9mbHQ7CgkJCXItPnJ1X21hamZsdCArPSBwLT5zaWduYWwtPm1hal9mbHQ7CgkJCXQgPSBwOwoJCQlkbyB7CgkJCQl1dGltZSA9IGNwdXRpbWVfYWRkKHV0aW1lLCB0LT51dGltZSk7CgkJCQlzdGltZSA9IGNwdXRpbWVfYWRkKHN0aW1lLCB0LT5zdGltZSk7CgkJCQlyLT5ydV9udmNzdyArPSB0LT5udmNzdzsKCQkJCXItPnJ1X25pdmNzdyArPSB0LT5uaXZjc3c7CgkJCQlyLT5ydV9taW5mbHQgKz0gdC0+bWluX2ZsdDsKCQkJCXItPnJ1X21hamZsdCArPSB0LT5tYWpfZmx0OwoJCQkJdCA9IG5leHRfdGhyZWFkKHQpOwoJCQl9IHdoaWxlICh0ICE9IHApOwoJCQlicmVhazsKCgkJZGVmYXVsdDoKCQkJQlVHKCk7Cgl9CgoJaWYgKG5lZWRfbG9jaykKCQlyZWFkX3VubG9jaygmdGFza2xpc3RfbG9jayk7CgljcHV0aW1lX3RvX3RpbWV2YWwodXRpbWUsICZyLT5ydV91dGltZSk7CgljcHV0aW1lX3RvX3RpbWV2YWwoc3RpbWUsICZyLT5ydV9zdGltZSk7Cn0KCmludCBnZXRydXNhZ2Uoc3RydWN0IHRhc2tfc3RydWN0ICpwLCBpbnQgd2hvLCBzdHJ1Y3QgcnVzYWdlIF9fdXNlciAqcnUpCnsKCXN0cnVjdCBydXNhZ2UgcjsKCWtfZ2V0cnVzYWdlKHAsIHdobywgJnIpOwoJcmV0dXJuIGNvcHlfdG9fdXNlcihydSwgJnIsIHNpemVvZihyKSkgPyAtRUZBVUxUIDogMDsKfQoKYXNtbGlua2FnZSBsb25nIHN5c19nZXRydXNhZ2UoaW50IHdobywgc3RydWN0IHJ1c2FnZSBfX3VzZXIgKnJ1KQp7CglpZiAod2hvICE9IFJVU0FHRV9TRUxGICYmIHdobyAhPSBSVVNBR0VfQ0hJTERSRU4pCgkJcmV0dXJuIC1FSU5WQUw7CglyZXR1cm4gZ2V0cnVzYWdlKGN1cnJlbnQsIHdobywgcnUpOwp9Cgphc21saW5rYWdlIGxvbmcgc3lzX3VtYXNrKGludCBtYXNrKQp7CgltYXNrID0geGNoZygmY3VycmVudC0+ZnMtPnVtYXNrLCBtYXNrICYgU19JUldYVUdPKTsKCXJldHVybiBtYXNrOwp9CiAgICAKYXNtbGlua2FnZSBsb25nIHN5c19wcmN0bChpbnQgb3B0aW9uLCB1bnNpZ25lZCBsb25nIGFyZzIsIHVuc2lnbmVkIGxvbmcgYXJnMywKCQkJICB1bnNpZ25lZCBsb25nIGFyZzQsIHVuc2lnbmVkIGxvbmcgYXJnNSkKewoJbG9uZyBlcnJvcjsKCgllcnJvciA9IHNlY3VyaXR5X3Rhc2tfcHJjdGwob3B0aW9uLCBhcmcyLCBhcmczLCBhcmc0LCBhcmc1KTsKCWlmIChlcnJvcikKCQlyZXR1cm4gZXJyb3I7CgoJc3dpdGNoIChvcHRpb24pIHsKCQljYXNlIFBSX1NFVF9QREVBVEhTSUc6CgkJCWlmICghdmFsaWRfc2lnbmFsKGFyZzIpKSB7CgkJCQllcnJvciA9IC1FSU5WQUw7CgkJCQlicmVhazsKCQkJfQoJCQljdXJyZW50LT5wZGVhdGhfc2lnbmFsID0gYXJnMjsKCQkJYnJlYWs7CgkJY2FzZSBQUl9HRVRfUERFQVRIU0lHOgoJCQllcnJvciA9IHB1dF91c2VyKGN1cnJlbnQtPnBkZWF0aF9zaWduYWwsIChpbnQgX191c2VyICopYXJnMik7CgkJCWJyZWFrOwoJCWNhc2UgUFJfR0VUX0RVTVBBQkxFOgoJCQllcnJvciA9IGN1cnJlbnQtPm1tLT5kdW1wYWJsZTsKCQkJYnJlYWs7CgkJY2FzZSBQUl9TRVRfRFVNUEFCTEU6CgkJCWlmIChhcmcyIDwgMCB8fCBhcmcyID4gMikgewoJCQkJZXJyb3IgPSAtRUlOVkFMOwoJCQkJYnJlYWs7CgkJCX0KCQkJY3VycmVudC0+bW0tPmR1bXBhYmxlID0gYXJnMjsKCQkJYnJlYWs7CgoJCWNhc2UgUFJfU0VUX1VOQUxJR046CgkJCWVycm9yID0gU0VUX1VOQUxJR05fQ1RMKGN1cnJlbnQsIGFyZzIpOwoJCQlicmVhazsKCQljYXNlIFBSX0dFVF9VTkFMSUdOOgoJCQllcnJvciA9IEdFVF9VTkFMSUdOX0NUTChjdXJyZW50LCBhcmcyKTsKCQkJYnJlYWs7CgkJY2FzZSBQUl9TRVRfRlBFTVU6CgkJCWVycm9yID0gU0VUX0ZQRU1VX0NUTChjdXJyZW50LCBhcmcyKTsKCQkJYnJlYWs7CgkJY2FzZSBQUl9HRVRfRlBFTVU6CgkJCWVycm9yID0gR0VUX0ZQRU1VX0NUTChjdXJyZW50LCBhcmcyKTsKCQkJYnJlYWs7CgkJY2FzZSBQUl9TRVRfRlBFWEM6CgkJCWVycm9yID0gU0VUX0ZQRVhDX0NUTChjdXJyZW50LCBhcmcyKTsKCQkJYnJlYWs7CgkJY2FzZSBQUl9HRVRfRlBFWEM6CgkJCWVycm9yID0gR0VUX0ZQRVhDX0NUTChjdXJyZW50LCBhcmcyKTsKCQkJYnJlYWs7CgkJY2FzZSBQUl9HRVRfVElNSU5HOgoJCQllcnJvciA9IFBSX1RJTUlOR19TVEFUSVNUSUNBTDsKCQkJYnJlYWs7CgkJY2FzZSBQUl9TRVRfVElNSU5HOgoJCQlpZiAoYXJnMiA9PSBQUl9USU1JTkdfU1RBVElTVElDQUwpCgkJCQllcnJvciA9IDA7CgkJCWVsc2UKCQkJCWVycm9yID0gLUVJTlZBTDsKCQkJYnJlYWs7CgoJCWNhc2UgUFJfR0VUX0tFRVBDQVBTOgoJCQlpZiAoY3VycmVudC0+a2VlcF9jYXBhYmlsaXRpZXMpCgkJCQllcnJvciA9IDE7CgkJCWJyZWFrOwoJCWNhc2UgUFJfU0VUX0tFRVBDQVBTOgoJCQlpZiAoYXJnMiAhPSAwICYmIGFyZzIgIT0gMSkgewoJCQkJZXJyb3IgPSAtRUlOVkFMOwoJCQkJYnJlYWs7CgkJCX0KCQkJY3VycmVudC0+a2VlcF9jYXBhYmlsaXRpZXMgPSBhcmcyOwoJCQlicmVhazsKCQljYXNlIFBSX1NFVF9OQU1FOiB7CgkJCXN0cnVjdCB0YXNrX3N0cnVjdCAqbWUgPSBjdXJyZW50OwoJCQl1bnNpZ25lZCBjaGFyIG5jb21tW3NpemVvZihtZS0+Y29tbSldOwoKCQkJbmNvbW1bc2l6ZW9mKG1lLT5jb21tKS0xXSA9IDA7CgkJCWlmIChzdHJuY3B5X2Zyb21fdXNlcihuY29tbSwgKGNoYXIgX191c2VyICopYXJnMiwKCQkJCQkJc2l6ZW9mKG1lLT5jb21tKS0xKSA8IDApCgkJCQlyZXR1cm4gLUVGQVVMVDsKCQkJc2V0X3Rhc2tfY29tbShtZSwgbmNvbW0pOwoJCQlyZXR1cm4gMDsKCQl9CgkJY2FzZSBQUl9HRVRfTkFNRTogewoJCQlzdHJ1Y3QgdGFza19zdHJ1Y3QgKm1lID0gY3VycmVudDsKCQkJdW5zaWduZWQgY2hhciB0Y29tbVtzaXplb2YobWUtPmNvbW0pXTsKCgkJCWdldF90YXNrX2NvbW0odGNvbW0sIG1lKTsKCQkJaWYgKGNvcHlfdG9fdXNlcigoY2hhciBfX3VzZXIgKilhcmcyLCB0Y29tbSwgc2l6ZW9mKHRjb21tKSkpCgkJCQlyZXR1cm4gLUVGQVVMVDsKCQkJcmV0dXJuIDA7CgkJfQoJCWRlZmF1bHQ6CgkJCWVycm9yID0gLUVJTlZBTDsKCQkJYnJlYWs7Cgl9CglyZXR1cm4gZXJyb3I7Cn0K