LyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKgogKiBGaWxlbmFtZTogICAgICBpcmxtcC5jCiAqIFZlcnNpb246ICAgICAgIDEuMAogKiBEZXNjcmlwdGlvbjogICBJckRBIExpbmsgTWFuYWdlbWVudCBQcm90b2NvbCAoTE1QKSBsYXllcgogKiBTdGF0dXM6ICAgICAgICBTdGFibGUuCiAqIEF1dGhvcjogICAgICAgIERhZyBCcmF0dGxpIDxkYWdiQGNzLnVpdC5ubz4KICogQ3JlYXRlZCBhdDogICAgU3VuIEF1ZyAxNyAyMDo1NDozMiAxOTk3CiAqIE1vZGlmaWVkIGF0OiAgIFdlZCBKYW4gIDUgMTE6MjY6MDMgMjAwMAogKiBNb2RpZmllZCBieTogICBEYWcgQnJhdHRsaSA8ZGFnYkBjcy51aXQubm8+CiAqCiAqICAgICBDb3B5cmlnaHQgKGMpIDE5OTgtMjAwMCBEYWcgQnJhdHRsaSA8ZGFnYkBjcy51aXQubm8+LAogKiAgICAgQWxsIFJpZ2h0cyBSZXNlcnZlZC4KICogICAgIENvcHlyaWdodCAoYykgMjAwMC0yMDAzIEplYW4gVG91cnJpbGhlcyA8anRAaHBsLmhwLmNvbT4KICoKICogICAgIFRoaXMgcHJvZ3JhbSBpcyBmcmVlIHNvZnR3YXJlOyB5b3UgY2FuIHJlZGlzdHJpYnV0ZSBpdCBhbmQvb3IKICogICAgIG1vZGlmeSBpdCB1bmRlciB0aGUgdGVybXMgb2YgdGhlIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlIGFzCiAqICAgICBwdWJsaXNoZWQgYnkgdGhlIEZyZWUgU29mdHdhcmUgRm91bmRhdGlvbjsgZWl0aGVyIHZlcnNpb24gMiBvZgogKiAgICAgdGhlIExpY2Vuc2UsIG9yIChhdCB5b3VyIG9wdGlvbikgYW55IGxhdGVyIHZlcnNpb24uCiAqCiAqICAgICBOZWl0aGVyIERhZyBCcmF0dGxpIG5vciBVbml2ZXJzaXR5IG9mIFRyb21z+CBhZG1pdCBsaWFiaWxpdHkgbm9yCiAqICAgICBwcm92aWRlIHdhcnJhbnR5IGZvciBhbnkgb2YgdGhpcyBzb2Z0d2FyZS4gVGhpcyBtYXRlcmlhbCBpcwogKiAgICAgcHJvdmlkZWQgIkFTLUlTIiBhbmQgYXQgbm8gY2hhcmdlLgogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCgojaW5jbHVkZSA8bGludXgvbW9kdWxlLmg+CiNpbmNsdWRlIDxsaW51eC9zbGFiLmg+CiNpbmNsdWRlIDxsaW51eC9zdHJpbmcuaD4KI2luY2x1ZGUgPGxpbnV4L3NrYnVmZi5oPgojaW5jbHVkZSA8bGludXgvdHlwZXMuaD4KI2luY2x1ZGUgPGxpbnV4L3Byb2NfZnMuaD4KI2luY2x1ZGUgPGxpbnV4L2luaXQuaD4KI2luY2x1ZGUgPGxpbnV4L2ttb2QuaD4KI2luY2x1ZGUgPGxpbnV4L3JhbmRvbS5oPgojaW5jbHVkZSA8bGludXgvc2VxX2ZpbGUuaD4KCiNpbmNsdWRlIDxuZXQvaXJkYS9pcmRhLmg+CiNpbmNsdWRlIDxuZXQvaXJkYS90aW1lci5oPgojaW5jbHVkZSA8bmV0L2lyZGEvcW9zLmg+CiNpbmNsdWRlIDxuZXQvaXJkYS9pcmxhcC5oPgojaW5jbHVkZSA8bmV0L2lyZGEvaXJpYXAuaD4KI2luY2x1ZGUgPG5ldC9pcmRhL2lybG1wLmg+CiNpbmNsdWRlIDxuZXQvaXJkYS9pcmxtcF9mcmFtZS5oPgoKI2luY2x1ZGUgPGFzbS91bmFsaWduZWQuaD4KCnN0YXRpYyBfX3U4IGlybG1wX2ZpbmRfZnJlZV9zbHNhcCh2b2lkKTsKc3RhdGljIGludCBpcmxtcF9zbHNhcF9pbnVzZShfX3U4IHNsc2FwX3NlbCk7CgovKiBNYXN0ZXIgc3RydWN0dXJlICovCnN0cnVjdCBpcmxtcF9jYiAqaXJsbXAgPSBOVUxMOwoKLyogVGhlc2UgY2FuIGJlIGFsdGVyZWQgYnkgdGhlIHN5c2N0bCBpbnRlcmZhY2UgKi8KaW50ICBzeXNjdGxfZGlzY292ZXJ5ICAgICAgICAgPSAwOwppbnQgIHN5c2N0bF9kaXNjb3ZlcnlfdGltZW91dCA9IDM7IC8qIDMgc2Vjb25kcyBieSBkZWZhdWx0ICovCmludCAgc3lzY3RsX2Rpc2NvdmVyeV9zbG90cyAgID0gNjsgLyogNiBzbG90cyBieSBkZWZhdWx0ICovCmludCAgc3lzY3RsX2xhcF9rZWVwYWxpdmVfdGltZSA9IExNX0lETEVfVElNRU9VVCAqIDEwMDAgLyBIWjsKY2hhciBzeXNjdGxfZGV2bmFtZVs2NV07Cgpjb25zdCBjaGFyICppcmxtcF9yZWFzb25zW10gPSB7CgkiRVJST1IsIE5PVCBVU0VEIiwKCSJMTV9VU0VSX1JFUVVFU1QiLAoJIkxNX0xBUF9ESVNDT05ORUNUIiwKCSJMTV9DT05ORUNUX0ZBSUxVUkUiLAoJIkxNX0xBUF9SRVNFVCIsCgkiTE1fSU5JVF9ESVNDT05ORUNUIiwKCSJFUlJPUiwgTk9UIFVTRUQiLAp9OwoKLyoKICogRnVuY3Rpb24gaXJsbXBfaW5pdCAodm9pZCkKICoKICogICAgQ3JlYXRlIChhbGxvY2F0ZSkgdGhlIG1haW4gSXJMTVAgc3RydWN0dXJlCiAqCiAqLwppbnQgX19pbml0IGlybG1wX2luaXQodm9pZCkKewoJSVJEQV9ERUJVRygxLCAiJXMoKVxuIiwgX19GVU5DVElPTl9fKTsKCS8qIEluaXRpYWxpemUgdGhlIGlybG1wIHN0cnVjdHVyZS4gKi8KCWlybG1wID0ga3phbGxvYyggc2l6ZW9mKHN0cnVjdCBpcmxtcF9jYiksIEdGUF9LRVJORUwpOwoJaWYgKGlybG1wID09IE5VTEwpCgkJcmV0dXJuIC1FTk9NRU07CgoJaXJsbXAtPm1hZ2ljID0gTE1QX01BR0lDOwoKCWlybG1wLT5jbGllbnRzID0gaGFzaGJpbl9uZXcoSEJfTE9DSyk7CglpcmxtcC0+c2VydmljZXMgPSBoYXNoYmluX25ldyhIQl9MT0NLKTsKCWlybG1wLT5saW5rcyA9IGhhc2hiaW5fbmV3KEhCX0xPQ0spOwoJaXJsbXAtPnVuY29ubmVjdGVkX2xzYXBzID0gaGFzaGJpbl9uZXcoSEJfTE9DSyk7CglpcmxtcC0+Y2FjaGVsb2cgPSBoYXNoYmluX25ldyhIQl9OT0xPQ0spOwoKCWlmICgoaXJsbXAtPmNsaWVudHMgPT0gTlVMTCkgfHwKCSAgICAoaXJsbXAtPnNlcnZpY2VzID09IE5VTEwpIHx8CgkgICAgKGlybG1wLT5saW5rcyA9PSBOVUxMKSB8fAoJICAgIChpcmxtcC0+dW5jb25uZWN0ZWRfbHNhcHMgPT0gTlVMTCkgfHwKCSAgICAoaXJsbXAtPmNhY2hlbG9nID09IE5VTEwpKSB7CgkJcmV0dXJuIC1FTk9NRU07Cgl9CgoJc3Bpbl9sb2NrX2luaXQoJmlybG1wLT5jYWNoZWxvZy0+aGJfc3BpbmxvY2spOwoKCWlybG1wLT5sYXN0X2xzYXBfc2VsID0gMHgwZjsgLyogUmVzZXJ2ZWQgMHgwMC0weDBmICovCglzdHJjcHkoc3lzY3RsX2Rldm5hbWUsICJMaW51eCIpOwoKCS8qIERvIGRpc2NvdmVyeSBldmVyeSAzIHNlY29uZHMgKi8KCWluaXRfdGltZXIoJmlybG1wLT5kaXNjb3ZlcnlfdGltZXIpOwoJaXJsbXBfc3RhcnRfZGlzY292ZXJ5X3RpbWVyKGlybG1wLCBzeXNjdGxfZGlzY292ZXJ5X3RpbWVvdXQqSFopOwoKCXJldHVybiAwOwp9CgovKgogKiBGdW5jdGlvbiBpcmxtcF9jbGVhbnVwICh2b2lkKQogKgogKiAgICBSZW1vdmUgSXJMTVAgbGF5ZXIKICoKICovCnZvaWQgX19leGl0IGlybG1wX2NsZWFudXAodm9pZCkgCnsKCS8qIENoZWNrIGZvciBtYWluIHN0cnVjdHVyZSAqLwoJSVJEQV9BU1NFUlQoaXJsbXAgIT0gTlVMTCwgcmV0dXJuOyk7CglJUkRBX0FTU0VSVChpcmxtcC0+bWFnaWMgPT0gTE1QX01BR0lDLCByZXR1cm47KTsKCglkZWxfdGltZXIoJmlybG1wLT5kaXNjb3ZlcnlfdGltZXIpOwoKCWhhc2hiaW5fZGVsZXRlKGlybG1wLT5saW5rcywgKEZSRUVfRlVOQykga2ZyZWUpOwoJaGFzaGJpbl9kZWxldGUoaXJsbXAtPnVuY29ubmVjdGVkX2xzYXBzLCAoRlJFRV9GVU5DKSBrZnJlZSk7CgloYXNoYmluX2RlbGV0ZShpcmxtcC0+Y2xpZW50cywgKEZSRUVfRlVOQykga2ZyZWUpOwoJaGFzaGJpbl9kZWxldGUoaXJsbXAtPnNlcnZpY2VzLCAoRlJFRV9GVU5DKSBrZnJlZSk7CgloYXNoYmluX2RlbGV0ZShpcmxtcC0+Y2FjaGVsb2csIChGUkVFX0ZVTkMpIGtmcmVlKTsKCgkvKiBEZS1hbGxvY2F0ZSBtYWluIHN0cnVjdHVyZSAqLwoJa2ZyZWUoaXJsbXApOwoJaXJsbXAgPSBOVUxMOwp9CgovKgogKiBGdW5jdGlvbiBpcmxtcF9vcGVuX2xzYXAgKHNsc2FwLCBub3RpZnkpCiAqCiAqICAgUmVnaXN0ZXIgd2l0aCBJckxNUCBhbmQgY3JlYXRlIGEgbG9jYWwgTFNBUCwKICogICByZXR1cm5zIGhhbmRsZSB0byBMU0FQLgogKi8Kc3RydWN0IGxzYXBfY2IgKmlybG1wX29wZW5fbHNhcChfX3U4IHNsc2FwX3NlbCwgbm90aWZ5X3QgKm5vdGlmeSwgX191OCBwaWQpCnsKCXN0cnVjdCBsc2FwX2NiICpzZWxmOwoKCUlSREFfQVNTRVJUKG5vdGlmeSAhPSBOVUxMLCByZXR1cm4gTlVMTDspOwoJSVJEQV9BU1NFUlQoaXJsbXAgIT0gTlVMTCwgcmV0dXJuIE5VTEw7KTsKCUlSREFfQVNTRVJUKGlybG1wLT5tYWdpYyA9PSBMTVBfTUFHSUMsIHJldHVybiBOVUxMOyk7CglJUkRBX0FTU0VSVChub3RpZnktPmluc3RhbmNlICE9IE5VTEwsIHJldHVybiBOVUxMOyk7CgoJLyogIERvZXMgdGhlIGNsaWVudCBjYXJlIHdoaWNoIFNvdXJjZSBMU0FQIHNlbGVjdG9yIGl0IGdldHM/ICAqLwoJaWYgKHNsc2FwX3NlbCA9PSBMU0FQX0FOWSkgewoJCXNsc2FwX3NlbCA9IGlybG1wX2ZpbmRfZnJlZV9zbHNhcCgpOwoJCWlmICghc2xzYXBfc2VsKQoJCQlyZXR1cm4gTlVMTDsKCX0gZWxzZSBpZiAoaXJsbXBfc2xzYXBfaW51c2Uoc2xzYXBfc2VsKSkKCQlyZXR1cm4gTlVMTDsKCgkvKiBBbGxvY2F0ZSBuZXcgaW5zdGFuY2Ugb2YgYSBMU0FQIGNvbm5lY3Rpb24gKi8KCXNlbGYgPSBremFsbG9jKHNpemVvZihzdHJ1Y3QgbHNhcF9jYiksIEdGUF9BVE9NSUMpOwoJaWYgKHNlbGYgPT0gTlVMTCkgewoJCUlSREFfRVJST1IoIiVzOiBjYW4ndCBhbGxvY2F0ZSBtZW1vcnlcbiIsIF9fRlVOQ1RJT05fXyk7CgkJcmV0dXJuIE5VTEw7Cgl9CgoJc2VsZi0+bWFnaWMgPSBMTVBfTFNBUF9NQUdJQzsKCXNlbGYtPnNsc2FwX3NlbCA9IHNsc2FwX3NlbDsKCgkvKiBGaXggY29ubmVjdGlvbmxlc3MgTFNBUCdzICovCglpZiAoc2xzYXBfc2VsID09IExTQVBfQ09OTkxFU1MpIHsKI2lmZGVmIENPTkZJR19JUkRBX1VMVFJBCgkJc2VsZi0+ZGxzYXBfc2VsID0gTFNBUF9DT05OTEVTUzsKCQlzZWxmLT5waWQgPSBwaWQ7CiNlbmRpZiAvKiBDT05GSUdfSVJEQV9VTFRSQSAqLwoJfSBlbHNlCgkJc2VsZi0+ZGxzYXBfc2VsID0gTFNBUF9BTlk7CgkvKiBzZWxmLT5jb25uZWN0ZWQgPSBGQUxTRTsgLT4gYWxyZWFkeSBOVUxMIHZpYSBtZW1zZXQoKSAqLwoKCWluaXRfdGltZXIoJnNlbGYtPndhdGNoZG9nX3RpbWVyKTsKCglzZWxmLT5ub3RpZnkgPSAqbm90aWZ5OwoKCXNlbGYtPmxzYXBfc3RhdGUgPSBMU0FQX0RJU0NPTk5FQ1RFRDsKCgkvKiBJbnNlcnQgaW50byBxdWV1ZSBvZiB1bmNvbm5lY3RlZCBMU0FQcyAqLwoJaGFzaGJpbl9pbnNlcnQoaXJsbXAtPnVuY29ubmVjdGVkX2xzYXBzLCAoaXJkYV9xdWV1ZV90ICopIHNlbGYsCgkJICAgICAgIChsb25nKSBzZWxmLCBOVUxMKTsKCglyZXR1cm4gc2VsZjsKfQpFWFBPUlRfU1lNQk9MKGlybG1wX29wZW5fbHNhcCk7CgovKgogKiBGdW5jdGlvbiBfX2lybG1wX2Nsb3NlX2xzYXAgKHNlbGYpCiAqCiAqICAgIFJlbW92ZSBhbiBpbnN0YW5jZSBvZiBMU0FQCiAqLwpzdGF0aWMgdm9pZCBfX2lybG1wX2Nsb3NlX2xzYXAoc3RydWN0IGxzYXBfY2IgKnNlbGYpCnsKCUlSREFfREVCVUcoNCwgIiVzKClcbiIsIF9fRlVOQ1RJT05fXyk7CgoJSVJEQV9BU1NFUlQoc2VsZiAhPSBOVUxMLCByZXR1cm47KTsKCUlSREFfQVNTRVJUKHNlbGYtPm1hZ2ljID09IExNUF9MU0FQX01BR0lDLCByZXR1cm47KTsKCgkvKgoJICogIFNldCBzb21lIG9mIHRoZSB2YXJpYWJsZXMgdG8gcHJlc2V0IHZhbHVlcwoJICovCglzZWxmLT5tYWdpYyA9IDA7CglkZWxfdGltZXIoJnNlbGYtPndhdGNoZG9nX3RpbWVyKTsgLyogSW1wb3J0YW50ISAqLwoKCWlmIChzZWxmLT5jb25uX3NrYikKCQlkZXZfa2ZyZWVfc2tiKHNlbGYtPmNvbm5fc2tiKTsKCglrZnJlZShzZWxmKTsKfQoKLyoKICogRnVuY3Rpb24gaXJsbXBfY2xvc2VfbHNhcCAoc2VsZikKICoKICogICAgQ2xvc2UgYW5kIHJlbW92ZSBMU0FQCiAqCiAqLwp2b2lkIGlybG1wX2Nsb3NlX2xzYXAoc3RydWN0IGxzYXBfY2IgKnNlbGYpCnsKCXN0cnVjdCBsYXBfY2IgKmxhcDsKCXN0cnVjdCBsc2FwX2NiICpsc2FwID0gTlVMTDsKCglJUkRBX0FTU0VSVChzZWxmICE9IE5VTEwsIHJldHVybjspOwoJSVJEQV9BU1NFUlQoc2VsZi0+bWFnaWMgPT0gTE1QX0xTQVBfTUFHSUMsIHJldHVybjspOwoKCS8qCgkgKiAgRmluZCBvdXQgaWYgd2Ugc2hvdWxkIHJlbW92ZSB0aGlzIExTQVAgZnJvbSBhIGxpbmsgb3IgZnJvbSB0aGUKCSAqICBsaXN0IG9mIHVuY29ubmVjdGVkIGxzYXBzIChub3QgYXNzb2NpYXRlZCB3aXRoIGEgbGluaykKCSAqLwoJbGFwID0gc2VsZi0+bGFwOwoJaWYgKGxhcCkgewoJCUlSREFfQVNTRVJUKGxhcC0+bWFnaWMgPT0gTE1QX0xBUF9NQUdJQywgcmV0dXJuOyk7CgkJLyogV2UgbWlnaHQgY2xvc2UgYSBMU0FQIGJlZm9yZSBpdCBoYXMgY29tcGxldGVkIHRoZQoJCSAqIGNvbm5lY3Rpb24gc2V0dXAuIEluIHRob3NlIGNhc2UsIGhpZ2hlciBsYXllcnMgd29uJ3QKCQkgKiBzZW5kIGEgcHJvcGVyIGRpc2Nvbm5lY3QgcmVxdWVzdC4gSGFybWxlc3MsIGV4Y2VwdAoJCSAqIHRoYXQgd2Ugd2lsbCBmb3JnZXQgdG8gY2xvc2UgTEFQLi4uIC0gSmVhbiBJSSAqLwoJCWlmKHNlbGYtPmxzYXBfc3RhdGUgIT0gTFNBUF9ESVNDT05ORUNURUQpIHsKCQkJc2VsZi0+bHNhcF9zdGF0ZSA9IExTQVBfRElTQ09OTkVDVEVEOwoJCQlpcmxtcF9kb19sYXBfZXZlbnQoc2VsZi0+bGFwLAoJCQkJCSAgIExNX0xBUF9ESVNDT05ORUNUX1JFUVVFU1QsIE5VTEwpOwoJCX0KCQkvKiBOb3csIHJlbW92ZSBmcm9tIHRoZSBsaW5rICovCgkJbHNhcCA9IGhhc2hiaW5fcmVtb3ZlKGxhcC0+bHNhcHMsIChsb25nKSBzZWxmLCBOVUxMKTsKI2lmZGVmIENPTkZJR19JUkRBX0NBQ0hFX0xBU1RfTFNBUAoJCWxhcC0+Y2FjaGUudmFsaWQgPSBGQUxTRTsKI2VuZGlmCgl9CglzZWxmLT5sYXAgPSBOVUxMOwoJLyogQ2hlY2sgaWYgd2UgZm91bmQgdGhlIExTQVAhIElmIG5vdCB0aGVuIHRyeSB0aGUgdW5jb25uZWN0ZWQgbHNhcHMgKi8KCWlmICghbHNhcCkgewoJCWxzYXAgPSBoYXNoYmluX3JlbW92ZShpcmxtcC0+dW5jb25uZWN0ZWRfbHNhcHMsIChsb25nKSBzZWxmLAoJCQkJICAgICAgTlVMTCk7Cgl9CglpZiAoIWxzYXApIHsKCQlJUkRBX0RFQlVHKDAsCgkJICAgICAiJXMoKSwgTG9va3MgbGlrZSBzb21lYm9keSBoYXMgcmVtb3ZlZCBtZSBhbHJlYWR5IVxuIiwKCQkJICAgX19GVU5DVElPTl9fKTsKCQlyZXR1cm47Cgl9CglfX2lybG1wX2Nsb3NlX2xzYXAoc2VsZik7Cn0KRVhQT1JUX1NZTUJPTChpcmxtcF9jbG9zZV9sc2FwKTsKCi8qCiAqIEZ1bmN0aW9uIGlybG1wX3JlZ2lzdGVyX2lybGFwIChzYWRkciwgbm90aWZ5KQogKgogKiAgICBSZWdpc3RlciBJckxBUCBsYXllciB3aXRoIElyTE1QLiBUaGVyZSBpcyBwb3NzaWJsZSB0byBoYXZlIG11bHRpcGxlCiAqICAgIGluc3RhbmNlcyBvZiB0aGUgSXJMQVAgbGF5ZXIsIGVhY2ggY29ubmVjdGVkIHRvIGRpZmZlcmVudCBJckRBIHBvcnRzCiAqCiAqLwp2b2lkIGlybG1wX3JlZ2lzdGVyX2xpbmsoc3RydWN0IGlybGFwX2NiICppcmxhcCwgX191MzIgc2FkZHIsIG5vdGlmeV90ICpub3RpZnkpCnsKCXN0cnVjdCBsYXBfY2IgKmxhcDsKCglJUkRBX0FTU0VSVChpcmxtcCAhPSBOVUxMLCByZXR1cm47KTsKCUlSREFfQVNTRVJUKGlybG1wLT5tYWdpYyA9PSBMTVBfTUFHSUMsIHJldHVybjspOwoJSVJEQV9BU1NFUlQobm90aWZ5ICE9IE5VTEwsIHJldHVybjspOwoKCS8qCgkgKiAgQWxsb2NhdGUgbmV3IGluc3RhbmNlIG9mIGEgTFNBUCBjb25uZWN0aW9uCgkgKi8KCWxhcCA9IGt6YWxsb2Moc2l6ZW9mKHN0cnVjdCBsYXBfY2IpLCBHRlBfS0VSTkVMKTsKCWlmIChsYXAgPT0gTlVMTCkgewoJCUlSREFfRVJST1IoIiVzOiB1bmFibGUgdG8ga21hbGxvY1xuIiwgX19GVU5DVElPTl9fKTsKCQlyZXR1cm47Cgl9CgoJbGFwLT5pcmxhcCA9IGlybGFwOwoJbGFwLT5tYWdpYyA9IExNUF9MQVBfTUFHSUM7CglsYXAtPnNhZGRyID0gc2FkZHI7CglsYXAtPmRhZGRyID0gREVWX0FERFJfQU5ZOwojaWZkZWYgQ09ORklHX0lSREFfQ0FDSEVfTEFTVF9MU0FQCglsYXAtPmNhY2hlLnZhbGlkID0gRkFMU0U7CiNlbmRpZgoJbGFwLT5sc2FwcyA9IGhhc2hiaW5fbmV3KEhCX0xPQ0spOwoJaWYgKGxhcC0+bHNhcHMgPT0gTlVMTCkgewoJCUlSREFfV0FSTklORygiJXMoKSwgdW5hYmxlIHRvIGttYWxsb2MgbHNhcHNcbiIsIF9fRlVOQ1RJT05fXyk7CgkJa2ZyZWUobGFwKTsKCQlyZXR1cm47Cgl9CgoJbGFwLT5sYXBfc3RhdGUgPSBMQVBfU1RBTkRCWTsKCglpbml0X3RpbWVyKCZsYXAtPmlkbGVfdGltZXIpOwoKCS8qCgkgKiAgSW5zZXJ0IGludG8gcXVldWUgb2YgTE1QIGxpbmtzCgkgKi8KCWhhc2hiaW5faW5zZXJ0KGlybG1wLT5saW5rcywgKGlyZGFfcXVldWVfdCAqKSBsYXAsIGxhcC0+c2FkZHIsIE5VTEwpOwoKCS8qCgkgKiAgV2Ugc2V0IG9ubHkgdGhpcyB2YXJpYWJsZSBzbyBJckxBUCBjYW4gdGVsbCB1cyBvbiB3aGljaCBsaW5rIHRoZQoJICogIGRpZmZlcmVudCBldmVudHMgaGFwcGVuZWQgb24KCSAqLwoJaXJkYV9ub3RpZnlfaW5pdChub3RpZnkpOwoJbm90aWZ5LT5pbnN0YW5jZSA9IGxhcDsKfQoKLyoKICogRnVuY3Rpb24gaXJsbXBfdW5yZWdpc3Rlcl9pcmxhcCAoc2FkZHIpCiAqCiAqICAgIElyTEFQIGxheWVyIGhhcyBiZWVuIHJlbW92ZWQhCiAqCiAqLwp2b2lkIGlybG1wX3VucmVnaXN0ZXJfbGluayhfX3UzMiBzYWRkcikKewoJc3RydWN0IGxhcF9jYiAqbGluazsKCglJUkRBX0RFQlVHKDQsICIlcygpXG4iLCBfX0ZVTkNUSU9OX18pOwoKCS8qIFdlIG11c3QgcmVtb3ZlIG91cnNlbHZlcyBmcm9tIHRoZSBoYXNoYmluICpmaXJzdCouIFRoaXMgZW5zdXJlCgkgKiB0aGF0IG5vIG1vcmUgTFNBUHMgd2lsbCBiZSBvcGVuIG9uIHRoaXMgbGluayBhbmQgbm8gZGlzY292ZXJ5CgkgKiB3aWxsIGJlIHRyaWdnZXJlZCBhbnltb3JlLiBKZWFuIElJICovCglsaW5rID0gaGFzaGJpbl9yZW1vdmUoaXJsbXAtPmxpbmtzLCBzYWRkciwgTlVMTCk7CglpZiAobGluaykgewoJCUlSREFfQVNTRVJUKGxpbmstPm1hZ2ljID09IExNUF9MQVBfTUFHSUMsIHJldHVybjspOwoKCQkvKiBLaWxsIGFsbCB0aGUgTFNBUHMgb24gdGhpcyBsaW5rLiBKZWFuIElJICovCgkJbGluay0+cmVhc29uID0gTEFQX0RJU0NfSU5ESUNBVElPTjsKCQlsaW5rLT5kYWRkciA9IERFVl9BRERSX0FOWTsKCQlpcmxtcF9kb19sYXBfZXZlbnQobGluaywgTE1fTEFQX0RJU0NPTk5FQ1RfSU5ESUNBVElPTiwgTlVMTCk7CgoJCS8qIFJlbW92ZSBhbGwgZGlzY292ZXJpZXMgZGlzY292ZXJlZCBhdCB0aGlzIGxpbmsgKi8KCQlpcmxtcF9leHBpcmVfZGlzY292ZXJpZXMoaXJsbXAtPmNhY2hlbG9nLCBsaW5rLT5zYWRkciwgVFJVRSk7CgoJCS8qIEZpbmFsIGNsZWFudXAgKi8KCQlkZWxfdGltZXIoJmxpbmstPmlkbGVfdGltZXIpOwoJCWxpbmstPm1hZ2ljID0gMDsKCQlrZnJlZShsaW5rKTsKCX0KfQoKLyoKICogRnVuY3Rpb24gaXJsbXBfY29ubmVjdF9yZXF1ZXN0IChoYW5kbGUsIGRsc2FwLCB1c2VyZGF0YSkKICoKICogICAgQ29ubmVjdCB3aXRoIGEgcGVlciBMU0FQCiAqCiAqLwppbnQgaXJsbXBfY29ubmVjdF9yZXF1ZXN0KHN0cnVjdCBsc2FwX2NiICpzZWxmLCBfX3U4IGRsc2FwX3NlbCwKCQkJICBfX3UzMiBzYWRkciwgX191MzIgZGFkZHIsCgkJCSAgc3RydWN0IHFvc19pbmZvICpxb3MsIHN0cnVjdCBza19idWZmICp1c2VyZGF0YSkKewoJc3RydWN0IHNrX2J1ZmYgKnR4X3NrYiA9IHVzZXJkYXRhOwoJc3RydWN0IGxhcF9jYiAqbGFwOwoJc3RydWN0IGxzYXBfY2IgKmxzYXA7CglpbnQgcmV0OwoKCUlSREFfQVNTRVJUKHNlbGYgIT0gTlVMTCwgcmV0dXJuIC1FQkFEUjspOwoJSVJEQV9BU1NFUlQoc2VsZi0+bWFnaWMgPT0gTE1QX0xTQVBfTUFHSUMsIHJldHVybiAtRUJBRFI7KTsKCglJUkRBX0RFQlVHKDIsCgkgICAgICAiJXMoKSwgc2xzYXBfc2VsPSUwMngsIGRsc2FwX3NlbD0lMDJ4LCBzYWRkcj0lMDh4LCBkYWRkcj0lMDh4XG4iLAoJICAgICAgX19GVU5DVElPTl9fLCBzZWxmLT5zbHNhcF9zZWwsIGRsc2FwX3NlbCwgc2FkZHIsIGRhZGRyKTsKCglpZiAodGVzdF9iaXQoMCwgJnNlbGYtPmNvbm5lY3RlZCkpIHsKCQlyZXQgPSAtRUlTQ09OTjsKCQlnb3RvIGVycjsKCX0KCgkvKiBDbGllbnQgbXVzdCBzdXBwbHkgZGVzdGluYXRpb24gZGV2aWNlIGFkZHJlc3MgKi8KCWlmICghZGFkZHIpIHsKCQlyZXQgPSAtRUlOVkFMOwoJCWdvdG8gZXJyOwoJfQoKCS8qIEFueSB1c2VyZGF0YT8gKi8KCWlmICh0eF9za2IgPT0gTlVMTCkgewoJCXR4X3NrYiA9IGFsbG9jX3NrYihMTVBfTUFYX0hFQURFUiwgR0ZQX0FUT01JQyk7CgkJaWYgKCF0eF9za2IpCgkJCXJldHVybiAtRU5PTUVNOwoKCQlza2JfcmVzZXJ2ZSh0eF9za2IsIExNUF9NQVhfSEVBREVSKTsKCX0KCgkvKiBNYWtlIHJvb20gZm9yIE1VWCBjb250cm9sIGhlYWRlciAoMyBieXRlcykgKi8KCUlSREFfQVNTRVJUKHNrYl9oZWFkcm9vbSh0eF9za2IpID49IExNUF9DT05UUk9MX0hFQURFUiwgcmV0dXJuIC0xOyk7Cglza2JfcHVzaCh0eF9za2IsIExNUF9DT05UUk9MX0hFQURFUik7CgoJc2VsZi0+ZGxzYXBfc2VsID0gZGxzYXBfc2VsOwoKCS8qCgkgKiBGaW5kIHRoZSBsaW5rIHRvIHdoZXJlIHdlIHNob3VsZCB0cnkgdG8gY29ubmVjdCBzaW5jZSB0aGVyZSBtYXkKCSAqIGJlIG1vcmUgdGhhbiBvbmUgSXJEQSBwb3J0IG9uIHRoaXMgbWFjaGluZS4gSWYgdGhlIGNsaWVudCBoYXMKCSAqIHBhc3NlZCB1cyB0aGUgc2FkZHIgKGFuZCBhbHJlYWR5IGtub3dzIHdoaWNoIGxpbmsgdG8gdXNlKSwgdGhlbgoJICogd2UgdXNlIHRoYXQgdG8gZmluZCB0aGUgbGluaywgaWYgbm90IHRoZW4gd2UgaGF2ZSB0byBsb29rIGluIHRoZQoJICogZGlzY292ZXJ5IGxvZyBhbmQgY2hlY2sgaWYgYW55IG9mIHRoZSBsaW5rcyBoYXMgZGlzY292ZXJlZCBhCgkgKiBkZXZpY2Ugd2l0aCB0aGUgZ2l2ZW4gZGFkZHIKCSAqLwoJaWYgKCghc2FkZHIpIHx8IChzYWRkciA9PSBERVZfQUREUl9BTlkpKSB7CgkJZGlzY292ZXJ5X3QgKmRpc2NvdmVyeTsKCQl1bnNpZ25lZCBsb25nIGZsYWdzOwoKCQlzcGluX2xvY2tfaXJxc2F2ZSgmaXJsbXAtPmNhY2hlbG9nLT5oYl9zcGlubG9jaywgZmxhZ3MpOwoJCWlmIChkYWRkciAhPSBERVZfQUREUl9BTlkpCgkJCWRpc2NvdmVyeSA9IGhhc2hiaW5fZmluZChpcmxtcC0+Y2FjaGVsb2csIGRhZGRyLCBOVUxMKTsKCQllbHNlIHsKCQkJSVJEQV9ERUJVRygyLCAiJXMoKSwgbm8gZGFkZHJcbiIsIF9fRlVOQ1RJT05fXyk7CgkJCWRpc2NvdmVyeSA9IChkaXNjb3ZlcnlfdCAqKQoJCQkJaGFzaGJpbl9nZXRfZmlyc3QoaXJsbXAtPmNhY2hlbG9nKTsKCQl9CgoJCWlmIChkaXNjb3ZlcnkpIHsKCQkJc2FkZHIgPSBkaXNjb3ZlcnktPmRhdGEuc2FkZHI7CgkJCWRhZGRyID0gZGlzY292ZXJ5LT5kYXRhLmRhZGRyOwoJCX0KCQlzcGluX3VubG9ja19pcnFyZXN0b3JlKCZpcmxtcC0+Y2FjaGVsb2ctPmhiX3NwaW5sb2NrLCBmbGFncyk7Cgl9CglsYXAgPSBoYXNoYmluX2xvY2tfZmluZChpcmxtcC0+bGlua3MsIHNhZGRyLCBOVUxMKTsKCWlmIChsYXAgPT0gTlVMTCkgewoJCUlSREFfREVCVUcoMSwgIiVzKCksIFVuYWJsZSB0byBmaW5kIGEgdXNhYmxlIGxpbmshXG4iLCBfX0ZVTkNUSU9OX18pOwoJCXJldCA9IC1FSE9TVFVOUkVBQ0g7CgkJZ290byBlcnI7Cgl9CgoJLyogQ2hlY2sgaWYgTEFQIGlzIGRpc2Nvbm5lY3RlZCBvciBhbHJlYWR5IGNvbm5lY3RlZCAqLwoJaWYgKGxhcC0+ZGFkZHIgPT0gREVWX0FERFJfQU5ZKQoJCWxhcC0+ZGFkZHIgPSBkYWRkcjsKCWVsc2UgaWYgKGxhcC0+ZGFkZHIgIT0gZGFkZHIpIHsKCQkvKiBDaGVjayBpZiBzb21lIExTQVBzIGFyZSBhY3RpdmUgb24gdGhpcyBMQVAgKi8KCQlpZiAoSEFTSEJJTl9HRVRfU0laRShsYXAtPmxzYXBzKSA9PSAwKSB7CgkJCS8qIE5vIGFjdGl2ZSBjb25uZWN0aW9uLCBidXQgTEFQIGhhc24ndCBiZWVuCgkJCSAqIGRpc2Nvbm5lY3RlZCB5ZXQgKHdhaXRpbmcgZm9yIHRpbWVvdXQgaW4gTEFQKS4KCQkJICogTWF5YmUgd2UgY291bGQgZ2l2ZSBMQVAgYSBiaXQgb2YgaGVscCBpbiB0aGlzIGNhc2UuCgkJCSAqLwoJCQlJUkRBX0RFQlVHKDAsICIlcygpLCBzb3JyeSwgYnV0IEknbSB3YWl0aW5nIGZvciBMQVAgdG8gdGltZW91dCFcbiIsIF9fRlVOQ1RJT05fXyk7CgkJCXJldCA9IC1FQUdBSU47CgkJCWdvdG8gZXJyOwoJCX0KCgkJLyogTEFQIGlzIGFscmVhZHkgY29ubmVjdGVkIHRvIGEgZGlmZmVyZW50IG5vZGUsIGFuZCBMQVAKCQkgKiBjYW4gb25seSB0YWxrIHRvIG9uZSBub2RlIGF0IGEgdGltZSAqLwoJCUlSREFfREVCVUcoMCwgIiVzKCksIHNvcnJ5LCBidXQgbGluayBpcyBidXN5IVxuIiwgX19GVU5DVElPTl9fKTsKCQlyZXQgPSAtRUJVU1k7CgkJZ290byBlcnI7Cgl9CgoJc2VsZi0+bGFwID0gbGFwOwoKCS8qCgkgKiAgUmVtb3ZlIExTQVAgZnJvbSBsaXN0IG9mIHVuY29ubmVjdGVkIExTQVBzIGFuZCBpbnNlcnQgaXQgaW50byB0aGUKCSAqICBsaXN0IG9mIGNvbm5lY3RlZCBMU0FQcyBmb3IgdGhlIHBhcnRpY3VsYXIgbGluawoJICovCglsc2FwID0gaGFzaGJpbl9yZW1vdmUoaXJsbXAtPnVuY29ubmVjdGVkX2xzYXBzLCAobG9uZykgc2VsZiwgTlVMTCk7CgoJSVJEQV9BU1NFUlQobHNhcCAhPSBOVUxMLCByZXR1cm4gLTE7KTsKCUlSREFfQVNTRVJUKGxzYXAtPm1hZ2ljID09IExNUF9MU0FQX01BR0lDLCByZXR1cm4gLTE7KTsKCUlSREFfQVNTRVJUKGxzYXAtPmxhcCAhPSBOVUxMLCByZXR1cm4gLTE7KTsKCUlSREFfQVNTRVJUKGxzYXAtPmxhcC0+bWFnaWMgPT0gTE1QX0xBUF9NQUdJQywgcmV0dXJuIC0xOyk7CgoJaGFzaGJpbl9pbnNlcnQoc2VsZi0+bGFwLT5sc2FwcywgKGlyZGFfcXVldWVfdCAqKSBzZWxmLCAobG9uZykgc2VsZiwKCQkgICAgICAgTlVMTCk7CgoJc2V0X2JpdCgwLCAmc2VsZi0+Y29ubmVjdGVkKTsJLyogVFJVRSAqLwoKCS8qCgkgKiAgVXNlciBzdXBwbGllZCBxb3Mgc3BlY2lmaWNhdGlvbnM/CgkgKi8KCWlmIChxb3MpCgkJc2VsZi0+cW9zID0gKnFvczsKCglpcmxtcF9kb19sc2FwX2V2ZW50KHNlbGYsIExNX0NPTk5FQ1RfUkVRVUVTVCwgdHhfc2tiKTsKCgkvKiBEcm9wIHJlZmVyZW5jZSBjb3VudCAtIHNlZSBpcmxhcF9kYXRhX3JlcXVlc3QoKS4gKi8KCWRldl9rZnJlZV9za2IodHhfc2tiKTsKCglyZXR1cm4gMDsKCmVycjoKCS8qIENsZWFudXAgKi8KCWlmKHR4X3NrYikKCQlkZXZfa2ZyZWVfc2tiKHR4X3NrYik7CglyZXR1cm4gcmV0Owp9CkVYUE9SVF9TWU1CT0woaXJsbXBfY29ubmVjdF9yZXF1ZXN0KTsKCi8qCiAqIEZ1bmN0aW9uIGlybG1wX2Nvbm5lY3RfaW5kaWNhdGlvbiAoc2VsZikKICoKICogICAgSW5jb21pbmcgY29ubmVjdGlvbgogKgogKi8Kdm9pZCBpcmxtcF9jb25uZWN0X2luZGljYXRpb24oc3RydWN0IGxzYXBfY2IgKnNlbGYsIHN0cnVjdCBza19idWZmICpza2IpCnsKCWludCBtYXhfc2VnX3NpemU7CglpbnQgbGFwX2hlYWRlcl9zaXplOwoJaW50IG1heF9oZWFkZXJfc2l6ZTsKCglJUkRBX0FTU0VSVChzZWxmICE9IE5VTEwsIHJldHVybjspOwoJSVJEQV9BU1NFUlQoc2VsZi0+bWFnaWMgPT0gTE1QX0xTQVBfTUFHSUMsIHJldHVybjspOwoJSVJEQV9BU1NFUlQoc2tiICE9IE5VTEwsIHJldHVybjspOwoJSVJEQV9BU1NFUlQoc2VsZi0+bGFwICE9IE5VTEwsIHJldHVybjspOwoKCUlSREFfREVCVUcoMiwgIiVzKCksIHNsc2FwX3NlbD0lMDJ4LCBkbHNhcF9zZWw9JTAyeFxuIiwKCQkgICBfX0ZVTkNUSU9OX18sIHNlbGYtPnNsc2FwX3NlbCwgc2VsZi0+ZGxzYXBfc2VsKTsKCgkvKiBOb3RlIDogc2VsZi0+bGFwIGlzIHNldCBpbiBpcmxtcF9saW5rX2RhdGFfaW5kaWNhdGlvbigpLAoJICogKGNhc2UgQ09OTkVDVF9DTUQ6KSBiZWNhdXNlIHdlIGhhdmUgbm8gd2F5IHRvIHNldCBpdCBoZXJlLgoJICogU2ltaWxhcmx5LCBzZWxmLT5kbHNhcF9zZWwgaXMgdXN1YWxseSBzZXQgaW4gaXJsbXBfZmluZF9sc2FwKCkuCgkgKiBKZWFuIElJICovCgoJc2VsZi0+cW9zID0gKnNlbGYtPmxhcC0+cW9zOwoKCW1heF9zZWdfc2l6ZSA9IHNlbGYtPmxhcC0+cW9zLT5kYXRhX3NpemUudmFsdWUtTE1QX0hFQURFUjsKCWxhcF9oZWFkZXJfc2l6ZSA9IElSTEFQX0dFVF9IRUFERVJfU0laRShzZWxmLT5sYXAtPmlybGFwKTsKCW1heF9oZWFkZXJfc2l6ZSA9IExNUF9IRUFERVIgKyBsYXBfaGVhZGVyX3NpemU7CgoJLyogSGlkZSBMTVBfQ09OVFJPTF9IRUFERVIgaGVhZGVyIGZyb20gbGF5ZXIgYWJvdmUgKi8KCXNrYl9wdWxsKHNrYiwgTE1QX0NPTlRST0xfSEVBREVSKTsKCglpZiAoc2VsZi0+bm90aWZ5LmNvbm5lY3RfaW5kaWNhdGlvbikgewoJCS8qIERvbid0IGZvcmdldCB0byByZWZjb3VudCBpdCAtIHNlZSBpcmxhcF9kcml2ZXJfcmN2KCkuICovCgkJc2tiX2dldChza2IpOwoJCXNlbGYtPm5vdGlmeS5jb25uZWN0X2luZGljYXRpb24oc2VsZi0+bm90aWZ5Lmluc3RhbmNlLCBzZWxmLAoJCQkJCQkmc2VsZi0+cW9zLCBtYXhfc2VnX3NpemUsCgkJCQkJCW1heF9oZWFkZXJfc2l6ZSwgc2tiKTsKCX0KfQoKLyoKICogRnVuY3Rpb24gaXJsbXBfY29ubmVjdF9yZXNwb25zZSAoaGFuZGxlLCB1c2VyZGF0YSkKICoKICogICAgU2VydmljZSB1c2VyIGlzIGFjY2VwdGluZyBjb25uZWN0aW9uCiAqCiAqLwppbnQgaXJsbXBfY29ubmVjdF9yZXNwb25zZShzdHJ1Y3QgbHNhcF9jYiAqc2VsZiwgc3RydWN0IHNrX2J1ZmYgKnVzZXJkYXRhKQp7CglJUkRBX0FTU0VSVChzZWxmICE9IE5VTEwsIHJldHVybiAtMTspOwoJSVJEQV9BU1NFUlQoc2VsZi0+bWFnaWMgPT0gTE1QX0xTQVBfTUFHSUMsIHJldHVybiAtMTspOwoJSVJEQV9BU1NFUlQodXNlcmRhdGEgIT0gTlVMTCwgcmV0dXJuIC0xOyk7CgoJLyogV2Ugc2V0IHRoZSBjb25uZWN0ZWQgYml0IGFuZCBtb3ZlIHRoZSBsc2FwIHRvIHRoZSBjb25uZWN0ZWQgbGlzdAoJICogaW4gdGhlIHN0YXRlIG1hY2hpbmUgaXRzZWxmLiBKZWFuIElJICovCgoJSVJEQV9ERUJVRygyLCAiJXMoKSwgc2xzYXBfc2VsPSUwMngsIGRsc2FwX3NlbD0lMDJ4XG4iLAoJCSAgIF9fRlVOQ1RJT05fXywgc2VsZi0+c2xzYXBfc2VsLCBzZWxmLT5kbHNhcF9zZWwpOwoKCS8qIE1ha2Ugcm9vbSBmb3IgTVVYIGNvbnRyb2wgaGVhZGVyICgzIGJ5dGVzKSAqLwoJSVJEQV9BU1NFUlQoc2tiX2hlYWRyb29tKHVzZXJkYXRhKSA+PSBMTVBfQ09OVFJPTF9IRUFERVIsIHJldHVybiAtMTspOwoJc2tiX3B1c2godXNlcmRhdGEsIExNUF9DT05UUk9MX0hFQURFUik7CgoJaXJsbXBfZG9fbHNhcF9ldmVudChzZWxmLCBMTV9DT05ORUNUX1JFU1BPTlNFLCB1c2VyZGF0YSk7CgoJLyogRHJvcCByZWZlcmVuY2UgY291bnQgLSBzZWUgaXJsYXBfZGF0YV9yZXF1ZXN0KCkuICovCglkZXZfa2ZyZWVfc2tiKHVzZXJkYXRhKTsKCglyZXR1cm4gMDsKfQpFWFBPUlRfU1lNQk9MKGlybG1wX2Nvbm5lY3RfcmVzcG9uc2UpOwoKLyoKICogRnVuY3Rpb24gaXJsbXBfY29ubmVjdF9jb25maXJtIChoYW5kbGUsIHNrYikKICoKICogICAgTFNBUCBjb25uZWN0aW9uIGNvbmZpcm1lZCBwZWVyIGRldmljZSEKICovCnZvaWQgaXJsbXBfY29ubmVjdF9jb25maXJtKHN0cnVjdCBsc2FwX2NiICpzZWxmLCBzdHJ1Y3Qgc2tfYnVmZiAqc2tiKQp7CglpbnQgbWF4X2hlYWRlcl9zaXplOwoJaW50IGxhcF9oZWFkZXJfc2l6ZTsKCWludCBtYXhfc2VnX3NpemU7CgoJSVJEQV9ERUJVRygzLCAiJXMoKVxuIiwgX19GVU5DVElPTl9fKTsKCglJUkRBX0FTU0VSVChza2IgIT0gTlVMTCwgcmV0dXJuOyk7CglJUkRBX0FTU0VSVChzZWxmICE9IE5VTEwsIHJldHVybjspOwoJSVJEQV9BU1NFUlQoc2VsZi0+bWFnaWMgPT0gTE1QX0xTQVBfTUFHSUMsIHJldHVybjspOwoJSVJEQV9BU1NFUlQoc2VsZi0+bGFwICE9IE5VTEwsIHJldHVybjspOwoKCXNlbGYtPnFvcyA9ICpzZWxmLT5sYXAtPnFvczsKCgltYXhfc2VnX3NpemUgICAgPSBzZWxmLT5sYXAtPnFvcy0+ZGF0YV9zaXplLnZhbHVlLUxNUF9IRUFERVI7CglsYXBfaGVhZGVyX3NpemUgPSBJUkxBUF9HRVRfSEVBREVSX1NJWkUoc2VsZi0+bGFwLT5pcmxhcCk7CgltYXhfaGVhZGVyX3NpemUgPSBMTVBfSEVBREVSICsgbGFwX2hlYWRlcl9zaXplOwoKCUlSREFfREVCVUcoMiwgIiVzKCksIG1heF9oZWFkZXJfc2l6ZT0lZFxuIiwKCQkgICBfX0ZVTkNUSU9OX18sIG1heF9oZWFkZXJfc2l6ZSk7CgoJLyogSGlkZSBMTVBfQ09OVFJPTF9IRUFERVIgaGVhZGVyIGZyb20gbGF5ZXIgYWJvdmUgKi8KCXNrYl9wdWxsKHNrYiwgTE1QX0NPTlRST0xfSEVBREVSKTsKCglpZiAoc2VsZi0+bm90aWZ5LmNvbm5lY3RfY29uZmlybSkgewoJCS8qIERvbid0IGZvcmdldCB0byByZWZjb3VudCBpdCAtIHNlZSBpcmxhcF9kcml2ZXJfcmN2KCkgKi8KCQlza2JfZ2V0KHNrYik7CgkJc2VsZi0+bm90aWZ5LmNvbm5lY3RfY29uZmlybShzZWxmLT5ub3RpZnkuaW5zdGFuY2UsIHNlbGYsCgkJCQkJICAgICAmc2VsZi0+cW9zLCBtYXhfc2VnX3NpemUsCgkJCQkJICAgICBtYXhfaGVhZGVyX3NpemUsIHNrYik7Cgl9Cn0KCi8qCiAqIEZ1bmN0aW9uIGlybG1wX2R1cCAob3JpZywgaW5zdGFuY2UpCiAqCiAqICAgIER1cGxpY2F0ZSBMU0FQLCBjYW4gYmUgdXNlZCBieSBzZXJ2ZXJzIHRvIGNvbmZpcm0gYSBjb25uZWN0aW9uIG9uIGEKICogICAgbmV3IExTQVAgc28gaXQgY2FuIGtlZXAgbGlzdGVuaW5nIG9uIHRoZSBvbGQgb25lLgogKgogKi8Kc3RydWN0IGxzYXBfY2IgKmlybG1wX2R1cChzdHJ1Y3QgbHNhcF9jYiAqb3JpZywgdm9pZCAqaW5zdGFuY2UpCnsKCXN0cnVjdCBsc2FwX2NiICpuZXc7Cgl1bnNpZ25lZCBsb25nIGZsYWdzOwoKCUlSREFfREVCVUcoMSwgIiVzKClcbiIsIF9fRlVOQ1RJT05fXyk7CgoJc3Bpbl9sb2NrX2lycXNhdmUoJmlybG1wLT51bmNvbm5lY3RlZF9sc2Fwcy0+aGJfc3BpbmxvY2ssIGZsYWdzKTsKCgkvKiBPbmx5IGFsbG93ZWQgdG8gZHVwbGljYXRlIHVuY29ubmVjdGVkIExTQVAncywgYW5kIG9ubHkgTFNBUHMKCSAqIHRoYXQgaGF2ZSByZWNlaXZlZCBhIGNvbm5lY3QgaW5kaWNhdGlvbi4gSmVhbiBJSSAqLwoJaWYgKCghaGFzaGJpbl9maW5kKGlybG1wLT51bmNvbm5lY3RlZF9sc2FwcywgKGxvbmcpIG9yaWcsIE5VTEwpKSB8fAoJICAgIChvcmlnLT5sYXAgPT0gTlVMTCkpIHsKCQlJUkRBX0RFQlVHKDAsICIlcygpLCBpbnZhbGlkIExTQVAgKHdyb25nIHN0YXRlKVxuIiwKCQkJICAgX19GVU5DVElPTl9fKTsKCQlzcGluX3VubG9ja19pcnFyZXN0b3JlKCZpcmxtcC0+dW5jb25uZWN0ZWRfbHNhcHMtPmhiX3NwaW5sb2NrLAoJCQkJICAgICAgIGZsYWdzKTsKCQlyZXR1cm4gTlVMTDsKCX0KCgkvKiBBbGxvY2F0ZSBhIG5ldyBpbnN0YW5jZSAqLwoJbmV3ID0ga21hbGxvYyhzaXplb2Yoc3RydWN0IGxzYXBfY2IpLCBHRlBfQVRPTUlDKTsKCWlmICghbmV3KSAgewoJCUlSREFfREVCVUcoMCwgIiVzKCksIHVuYWJsZSB0byBrbWFsbG9jXG4iLCBfX0ZVTkNUSU9OX18pOwoJCXNwaW5fdW5sb2NrX2lycXJlc3RvcmUoJmlybG1wLT51bmNvbm5lY3RlZF9sc2Fwcy0+aGJfc3BpbmxvY2ssCgkJCQkgICAgICAgZmxhZ3MpOwoJCXJldHVybiBOVUxMOwoJfQoJLyogRHVwICovCgltZW1jcHkobmV3LCBvcmlnLCBzaXplb2Yoc3RydWN0IGxzYXBfY2IpKTsKCS8qIG5ldy0+bGFwID0gb3JpZy0+bGFwOyA9PiBkb25lIGluIHRoZSBtZW1jcHkoKSAqLwoJLyogbmV3LT5zbHNhcF9zZWwgPSBvcmlnLT5zbHNhcF9zZWw7ID0+IGRvbmUgaW4gdGhlIG1lbWNweSgpICovCgluZXctPmNvbm5fc2tiID0gTlVMTDsKCglzcGluX3VubG9ja19pcnFyZXN0b3JlKCZpcmxtcC0+dW5jb25uZWN0ZWRfbHNhcHMtPmhiX3NwaW5sb2NrLCBmbGFncyk7CgoJLyogTm90IGV2ZXJ5dGhpbmcgaXMgdGhlIHNhbWUgKi8KCW5ldy0+bm90aWZ5Lmluc3RhbmNlID0gaW5zdGFuY2U7CgoJaW5pdF90aW1lcigmbmV3LT53YXRjaGRvZ190aW1lcik7CgoJaGFzaGJpbl9pbnNlcnQoaXJsbXAtPnVuY29ubmVjdGVkX2xzYXBzLCAoaXJkYV9xdWV1ZV90ICopIG5ldywKCQkgICAgICAgKGxvbmcpIG5ldywgTlVMTCk7CgojaWZkZWYgQ09ORklHX0lSREFfQ0FDSEVfTEFTVF9MU0FQCgkvKiBNYWtlIHN1cmUgdGhhdCB3ZSBpbnZhbGlkYXRlIHRoZSBMU0FQIGNhY2hlICovCgluZXctPmxhcC0+Y2FjaGUudmFsaWQgPSBGQUxTRTsKI2VuZGlmIC8qIENPTkZJR19JUkRBX0NBQ0hFX0xBU1RfTFNBUCAqLwoKCXJldHVybiBuZXc7Cn0KCi8qCiAqIEZ1bmN0aW9uIGlybG1wX2Rpc2Nvbm5lY3RfcmVxdWVzdCAoaGFuZGxlLCB1c2VyZGF0YSkKICoKICogICAgVGhlIHNlcnZpY2UgdXNlciBpcyByZXF1ZXN0aW5nIGRpc2Nvbm5lY3Rpb24sIHRoaXMgd2lsbCBub3QgcmVtb3ZlIHRoZQogKiAgICBMU0FQLCBidXQgb25seSBtYXJrIGl0IGFzIGRpc2Nvbm5lY3RlZAogKi8KaW50IGlybG1wX2Rpc2Nvbm5lY3RfcmVxdWVzdChzdHJ1Y3QgbHNhcF9jYiAqc2VsZiwgc3RydWN0IHNrX2J1ZmYgKnVzZXJkYXRhKQp7CglzdHJ1Y3QgbHNhcF9jYiAqbHNhcDsKCglJUkRBX0FTU0VSVChzZWxmICE9IE5VTEwsIHJldHVybiAtMTspOwoJSVJEQV9BU1NFUlQoc2VsZi0+bWFnaWMgPT0gTE1QX0xTQVBfTUFHSUMsIHJldHVybiAtMTspOwoJSVJEQV9BU1NFUlQodXNlcmRhdGEgIT0gTlVMTCwgcmV0dXJuIC0xOyk7CgoJLyogQWxyZWFkeSBkaXNjb25uZWN0ZWQgPwoJICogVGhlcmUgaXMgYSByYWNlIGNvbmRpdGlvbiBiZXR3ZWVuIGlybG1wX2Rpc2Nvbm5lY3RfaW5kaWNhdGlvbigpCgkgKiBhbmQgdXMgdGhhdCBtaWdodCBtZXNzIHVwIHRoZSBoYXNoYmlucyBiZWxvdy4gVGhpcyBmaXhlcyBpdC4KCSAqIEplYW4gSUkgKi8KCWlmICghIHRlc3RfYW5kX2NsZWFyX2JpdCgwLCAmc2VsZi0+Y29ubmVjdGVkKSkgewoJCUlSREFfREVCVUcoMCwgIiVzKCksIGFscmVhZHkgZGlzY29ubmVjdGVkIVxuIiwgX19GVU5DVElPTl9fKTsKCQlkZXZfa2ZyZWVfc2tiKHVzZXJkYXRhKTsKCQlyZXR1cm4gLTE7Cgl9CgoJc2tiX3B1c2godXNlcmRhdGEsIExNUF9DT05UUk9MX0hFQURFUik7CgoJLyoKCSAqICBEbyB0aGUgZXZlbnQgYmVmb3JlIHRoZSBvdGhlciBzdHVmZiBzaW5jZSB3ZSBtdXN0IGtub3cKCSAqICB3aGljaCBsYXAgbGF5ZXIgdGhhdCB0aGUgZnJhbWUgc2hvdWxkIGJlIHRyYW5zbWl0dGVkIG9uCgkgKi8KCWlybG1wX2RvX2xzYXBfZXZlbnQoc2VsZiwgTE1fRElTQ09OTkVDVF9SRVFVRVNULCB1c2VyZGF0YSk7CgoJLyogRHJvcCByZWZlcmVuY2UgY291bnQgLSBzZWUgaXJsYXBfZGF0YV9yZXF1ZXN0KCkuICovCglkZXZfa2ZyZWVfc2tiKHVzZXJkYXRhKTsKCgkvKgoJICogIFJlbW92ZSBMU0FQIGZyb20gbGlzdCBvZiBjb25uZWN0ZWQgTFNBUHMgZm9yIHRoZSBwYXJ0aWN1bGFyIGxpbmsKCSAqICBhbmQgaW5zZXJ0IGl0IGludG8gdGhlIGxpc3Qgb2YgdW5jb25uZWN0ZWQgTFNBUHMKCSAqLwoJSVJEQV9BU1NFUlQoc2VsZi0+bGFwICE9IE5VTEwsIHJldHVybiAtMTspOwoJSVJEQV9BU1NFUlQoc2VsZi0+bGFwLT5tYWdpYyA9PSBMTVBfTEFQX01BR0lDLCByZXR1cm4gLTE7KTsKCUlSREFfQVNTRVJUKHNlbGYtPmxhcC0+bHNhcHMgIT0gTlVMTCwgcmV0dXJuIC0xOyk7CgoJbHNhcCA9IGhhc2hiaW5fcmVtb3ZlKHNlbGYtPmxhcC0+bHNhcHMsIChsb25nKSBzZWxmLCBOVUxMKTsKI2lmZGVmIENPTkZJR19JUkRBX0NBQ0hFX0xBU1RfTFNBUAoJc2VsZi0+bGFwLT5jYWNoZS52YWxpZCA9IEZBTFNFOwojZW5kaWYKCglJUkRBX0FTU0VSVChsc2FwICE9IE5VTEwsIHJldHVybiAtMTspOwoJSVJEQV9BU1NFUlQobHNhcC0+bWFnaWMgPT0gTE1QX0xTQVBfTUFHSUMsIHJldHVybiAtMTspOwoJSVJEQV9BU1NFUlQobHNhcCA9PSBzZWxmLCByZXR1cm4gLTE7KTsKCgloYXNoYmluX2luc2VydChpcmxtcC0+dW5jb25uZWN0ZWRfbHNhcHMsIChpcmRhX3F1ZXVlX3QgKikgc2VsZiwKCQkgICAgICAgKGxvbmcpIHNlbGYsIE5VTEwpOwoKCS8qIFJlc2V0IHNvbWUgdmFsdWVzICovCglzZWxmLT5kbHNhcF9zZWwgPSBMU0FQX0FOWTsKCXNlbGYtPmxhcCA9IE5VTEw7CgoJcmV0dXJuIDA7Cn0KRVhQT1JUX1NZTUJPTChpcmxtcF9kaXNjb25uZWN0X3JlcXVlc3QpOwoKLyoKICogRnVuY3Rpb24gaXJsbXBfZGlzY29ubmVjdF9pbmRpY2F0aW9uIChyZWFzb24sIHVzZXJkYXRhKQogKgogKiAgICBMU0FQIGlzIGJlaW5nIGNsb3NlZCEKICovCnZvaWQgaXJsbXBfZGlzY29ubmVjdF9pbmRpY2F0aW9uKHN0cnVjdCBsc2FwX2NiICpzZWxmLCBMTV9SRUFTT04gcmVhc29uLAoJCQkJIHN0cnVjdCBza19idWZmICpza2IpCnsKCXN0cnVjdCBsc2FwX2NiICpsc2FwOwoKCUlSREFfREVCVUcoMSwgIiVzKCksIHJlYXNvbj0lc1xuIiwgX19GVU5DVElPTl9fLCBpcmxtcF9yZWFzb25zW3JlYXNvbl0pOwoJSVJEQV9BU1NFUlQoc2VsZiAhPSBOVUxMLCByZXR1cm47KTsKCUlSREFfQVNTRVJUKHNlbGYtPm1hZ2ljID09IExNUF9MU0FQX01BR0lDLCByZXR1cm47KTsKCglJUkRBX0RFQlVHKDMsICIlcygpLCBzbHNhcF9zZWw9JTAyeCwgZGxzYXBfc2VsPSUwMnhcbiIsCgkJICAgX19GVU5DVElPTl9fLCBzZWxmLT5zbHNhcF9zZWwsIHNlbGYtPmRsc2FwX3NlbCk7CgoJLyogQWxyZWFkeSBkaXNjb25uZWN0ZWQgPwoJICogVGhlcmUgaXMgYSByYWNlIGNvbmRpdGlvbiBiZXR3ZWVuIGlybG1wX2Rpc2Nvbm5lY3RfcmVxdWVzdCgpCgkgKiBhbmQgdXMgdGhhdCBtaWdodCBtZXNzIHVwIHRoZSBoYXNoYmlucyBiZWxvdy4gVGhpcyBmaXhlcyBpdC4KCSAqIEplYW4gSUkgKi8KCWlmICghIHRlc3RfYW5kX2NsZWFyX2JpdCgwLCAmc2VsZi0+Y29ubmVjdGVkKSkgewoJCUlSREFfREVCVUcoMCwgIiVzKCksIGFscmVhZHkgZGlzY29ubmVjdGVkIVxuIiwgX19GVU5DVElPTl9fKTsKCQlyZXR1cm47Cgl9CgoJLyoKCSAqICBSZW1vdmUgYXNzb2NpYXRpb24gYmV0d2VlbiB0aGlzIExTQVAgYW5kIHRoZSBsaW5rIGl0IHVzZWQKCSAqLwoJSVJEQV9BU1NFUlQoc2VsZi0+bGFwICE9IE5VTEwsIHJldHVybjspOwoJSVJEQV9BU1NFUlQoc2VsZi0+bGFwLT5sc2FwcyAhPSBOVUxMLCByZXR1cm47KTsKCglsc2FwID0gaGFzaGJpbl9yZW1vdmUoc2VsZi0+bGFwLT5sc2FwcywgKGxvbmcpIHNlbGYsIE5VTEwpOwojaWZkZWYgQ09ORklHX0lSREFfQ0FDSEVfTEFTVF9MU0FQCglzZWxmLT5sYXAtPmNhY2hlLnZhbGlkID0gRkFMU0U7CiNlbmRpZgoKCUlSREFfQVNTRVJUKGxzYXAgIT0gTlVMTCwgcmV0dXJuOyk7CglJUkRBX0FTU0VSVChsc2FwID09IHNlbGYsIHJldHVybjspOwoJaGFzaGJpbl9pbnNlcnQoaXJsbXAtPnVuY29ubmVjdGVkX2xzYXBzLCAoaXJkYV9xdWV1ZV90ICopIGxzYXAsCgkJICAgICAgIChsb25nKSBsc2FwLCBOVUxMKTsKCglzZWxmLT5kbHNhcF9zZWwgPSBMU0FQX0FOWTsKCXNlbGYtPmxhcCA9IE5VTEw7CgoJLyoKCSAqICBJbmZvcm0gc2VydmljZSB1c2VyCgkgKi8KCWlmIChzZWxmLT5ub3RpZnkuZGlzY29ubmVjdF9pbmRpY2F0aW9uKSB7CgkJLyogRG9uJ3QgZm9yZ2V0IHRvIHJlZmNvdW50IGl0IC0gc2VlIGlybGFwX2RyaXZlcl9yY3YoKS4gKi8KCQlpZihza2IpCgkJCXNrYl9nZXQoc2tiKTsKCQlzZWxmLT5ub3RpZnkuZGlzY29ubmVjdF9pbmRpY2F0aW9uKHNlbGYtPm5vdGlmeS5pbnN0YW5jZSwKCQkJCQkJICAgc2VsZiwgcmVhc29uLCBza2IpOwoJfSBlbHNlIHsKCQlJUkRBX0RFQlVHKDAsICIlcygpLCBubyBoYW5kbGVyXG4iLCBfX0ZVTkNUSU9OX18pOwoJfQp9CgovKgogKiBGdW5jdGlvbiBpcmxtcF9kb19leHBpcnkgKHZvaWQpCiAqCiAqICAgIERvIGEgY2xlYW51cCBvZiB0aGUgZGlzY292ZXJ5IGxvZyAocmVtb3ZlIG9sZCBlbnRyaWVzKQogKgogKiBOb3RlIDogc2VwYXJhdGUgZnJvbSBpcmxtcF9kb19kaXNjb3ZlcnkoKSBzbyB0aGF0IHdlIGNhbiBoYW5kbGUKICogcGFzc2l2ZSBkaXNjb3ZlcnkgcHJvcGVybHkuCiAqLwp2b2lkIGlybG1wX2RvX2V4cGlyeSh2b2lkKQp7CglzdHJ1Y3QgbGFwX2NiICpsYXA7CgoJLyoKCSAqIEV4cGlyZSBkaXNjb3Zlcnkgb24gYWxsIGxpbmtzIHdoaWNoIGFyZSAqbm90KiBjb25uZWN0ZWQuCgkgKiBPbiBsaW5rcyB3aGljaCBhcmUgY29ubmVjdGVkLCB3ZSBjYW4ndCBkbyBkaXNjb3ZlcnkKCSAqIGFueW1vcmUgYW5kIGNhbid0IHJlZnJlc2ggdGhlIGxvZywgc28gd2UgZnJlZXplIHRoZQoJICogZGlzY292ZXJ5IGxvZyB0byBrZWVwIGluZm8gYWJvdXQgdGhlIGRldmljZSB3ZSBhcmUKCSAqIGNvbm5lY3RlZCB0by4KCSAqIFRoaXMgaW5mbyBpcyBtYW5kYXRvcnkgaWYgd2Ugd2FudCBpcmxtcF9jb25uZWN0X3JlcXVlc3QoKQoJICogdG8gd29yayBwcm9wZXJseS4gLSBKZWFuIElJCgkgKi8KCWxhcCA9IChzdHJ1Y3QgbGFwX2NiICopIGhhc2hiaW5fZ2V0X2ZpcnN0KGlybG1wLT5saW5rcyk7Cgl3aGlsZSAobGFwICE9IE5VTEwpIHsKCQlJUkRBX0FTU0VSVChsYXAtPm1hZ2ljID09IExNUF9MQVBfTUFHSUMsIHJldHVybjspOwoKCQlpZiAobGFwLT5sYXBfc3RhdGUgPT0gTEFQX1NUQU5EQlkpIHsKCQkJLyogRXhwaXJlIGRpc2NvdmVyaWVzIGRpc2NvdmVyZWQgb24gdGhpcyBsaW5rICovCgkJCWlybG1wX2V4cGlyZV9kaXNjb3ZlcmllcyhpcmxtcC0+Y2FjaGVsb2csIGxhcC0+c2FkZHIsCgkJCQkJCSBGQUxTRSk7CgkJfQoJCWxhcCA9IChzdHJ1Y3QgbGFwX2NiICopIGhhc2hiaW5fZ2V0X25leHQoaXJsbXAtPmxpbmtzKTsKCX0KfQoKLyoKICogRnVuY3Rpb24gaXJsbXBfZG9fZGlzY292ZXJ5IChuc2xvdHMpCiAqCiAqICAgIERvIHNvbWUgZGlzY292ZXJ5IG9uIGFsbCBsaW5rcwogKgogKiBOb3RlIDogbG9nIGV4cGlyeSBpcyBkb25lIGFib3ZlLgogKi8Kdm9pZCBpcmxtcF9kb19kaXNjb3ZlcnkoaW50IG5zbG90cykKewoJc3RydWN0IGxhcF9jYiAqbGFwOwoJX191MTYgKmRhdGFfaGludHNwOwoKCS8qIE1ha2Ugc3VyZSB0aGUgdmFsdWUgaXMgc2FuZSAqLwoJaWYgKChuc2xvdHMgIT0gMSkgJiYgKG5zbG90cyAhPSA2KSAmJiAobnNsb3RzICE9IDgpICYmIChuc2xvdHMgIT0gMTYpKXsKCQlJUkRBX1dBUk5JTkcoIiVzOiBpbnZhbGlkIHZhbHVlIGZvciBudW1iZXIgb2Ygc2xvdHMhXG4iLAoJCQkgICAgIF9fRlVOQ1RJT05fXyk7CgkJbnNsb3RzID0gc3lzY3RsX2Rpc2NvdmVyeV9zbG90cyA9IDg7Cgl9CgoJLyogQ29uc3RydWN0IG5ldyBkaXNjb3ZlcnkgaW5mbyB0byBiZSB1c2VkIGJ5IElyTEFQLCAqLwoJZGF0YV9oaW50c3AgPSAoX191MTYgKikgaXJsbXAtPmRpc2NvdmVyeV9jbWQuZGF0YS5oaW50czsKCXB1dF91bmFsaWduZWQoaXJsbXAtPmhpbnRzLndvcmQsIGRhdGFfaGludHNwKTsKCgkvKgoJICogIFNldCBjaGFyYWN0ZXIgc2V0IGZvciBkZXZpY2UgbmFtZSAod2UgdXNlIEFTQ0lJKSwgYW5kCgkgKiAgY29weSBkZXZpY2UgbmFtZS4gUmVtZW1iZXIgdG8gbWFrZSByb29tIGZvciBhIFwwIGF0IHRoZQoJICogIGVuZAoJICovCglpcmxtcC0+ZGlzY292ZXJ5X2NtZC5kYXRhLmNoYXJzZXQgPSBDU19BU0NJSTsKCXN0cm5jcHkoaXJsbXAtPmRpc2NvdmVyeV9jbWQuZGF0YS5pbmZvLCBzeXNjdGxfZGV2bmFtZSwKCQlOSUNLTkFNRV9NQVhfTEVOKTsKCWlybG1wLT5kaXNjb3ZlcnlfY21kLm5hbWVfbGVuID0gc3RybGVuKGlybG1wLT5kaXNjb3ZlcnlfY21kLmRhdGEuaW5mbyk7CglpcmxtcC0+ZGlzY292ZXJ5X2NtZC5uc2xvdHMgPSBuc2xvdHM7CgoJLyoKCSAqIFRyeSB0byBzZW5kIGRpc2NvdmVyeSBwYWNrZXRzIG9uIGFsbCBsaW5rcwoJICovCglsYXAgPSAoc3RydWN0IGxhcF9jYiAqKSBoYXNoYmluX2dldF9maXJzdChpcmxtcC0+bGlua3MpOwoJd2hpbGUgKGxhcCAhPSBOVUxMKSB7CgkJSVJEQV9BU1NFUlQobGFwLT5tYWdpYyA9PSBMTVBfTEFQX01BR0lDLCByZXR1cm47KTsKCgkJaWYgKGxhcC0+bGFwX3N0YXRlID09IExBUF9TVEFOREJZKSB7CgkJCS8qIFRyeSB0byBkaXNjb3ZlciAqLwoJCQlpcmxtcF9kb19sYXBfZXZlbnQobGFwLCBMTV9MQVBfRElTQ09WRVJZX1JFUVVFU1QsCgkJCQkJICAgTlVMTCk7CgkJfQoJCWxhcCA9IChzdHJ1Y3QgbGFwX2NiICopIGhhc2hiaW5fZ2V0X25leHQoaXJsbXAtPmxpbmtzKTsKCX0KfQoKLyoKICogRnVuY3Rpb24gaXJsbXBfZGlzY292ZXJ5X3JlcXVlc3QgKG5zbG90cykKICoKICogICAgRG8gYSBkaXNjb3Zlcnkgb2YgZGV2aWNlcyBpbiBmcm9udCBvZiB0aGUgY29tcHV0ZXIKICoKICogSWYgdGhlIGNhbGxlciBoYXMgcmVnaXN0ZXJlZCBhIGNsaWVudCBkaXNjb3ZlcnkgY2FsbGJhY2ssIHRoaXMKICogYWxsb3cgaGltIHRvIHJlY2VpdmUgdGhlIGZ1bGwgY29udGVudCBvZiB0aGUgZGlzY292ZXJ5IGxvZyB0aHJvdWdoCiAqIHRoaXMgY2FsbGJhY2sgKGFzIG5vcm1hbGx5IGhlIHdpbGwgcmVjZWl2ZSBvbmx5IG5ldyBkaXNjb3ZlcmllcykuCiAqLwp2b2lkIGlybG1wX2Rpc2NvdmVyeV9yZXF1ZXN0KGludCBuc2xvdHMpCnsKCS8qIFJldHVybiBjdXJyZW50IGNhY2hlZCBkaXNjb3ZlcnkgbG9nIChpbiBmdWxsKSAqLwoJaXJsbXBfZGlzY292ZXJ5X2NvbmZpcm0oaXJsbXAtPmNhY2hlbG9nLCBESVNDT1ZFUllfTE9HKTsKCgkvKgoJICogU3RhcnQgYSBzaW5nbGUgZGlzY292ZXJ5IG9wZXJhdGlvbiBpZiBkaXNjb3ZlcnkgaXMgbm90IGFscmVhZHkKICAgICAgICAgKiBydW5uaW5nCgkgKi8KCWlmICghc3lzY3RsX2Rpc2NvdmVyeSkgewoJCS8qIENoZWNrIGlmIHVzZXIgd2FudHMgdG8gb3ZlcnJpZGUgdGhlIGRlZmF1bHQgKi8KCQlpZiAobnNsb3RzID09IERJU0NPVkVSWV9ERUZBVUxUX1NMT1RTKQoJCQluc2xvdHMgPSBzeXNjdGxfZGlzY292ZXJ5X3Nsb3RzOwoKCQlpcmxtcF9kb19kaXNjb3ZlcnkobnNsb3RzKTsKCQkvKiBOb3RlIDogd2UgbmV2ZXIgZG8gZXhwaXJ5IGhlcmUuIEV4cGlyeSB3aWxsIHJ1biBvbiB0aGUKCQkgKiBkaXNjb3ZlcnkgdGltZXIgcmVnYXJkbGVzcyBvZiB0aGUgc3RhdGUgb2Ygc3lzY3RsX2Rpc2NvdmVyeQoJCSAqIEplYW4gSUkgKi8KCX0KfQpFWFBPUlRfU1lNQk9MKGlybG1wX2Rpc2NvdmVyeV9yZXF1ZXN0KTsKCi8qCiAqIEZ1bmN0aW9uIGlybG1wX2dldF9kaXNjb3ZlcmllcyAocG4sIG1hc2ssIHNsb3RzKQogKgogKiAgICBSZXR1cm4gdGhlIGN1cnJlbnQgZGlzY292ZXJ5IGxvZwogKgogKiBJZiBkaXNjb3ZlcnkgaXMgbm90IGVuYWJsZWQsIHlvdSBzaG91bGQgY2FsbCB0aGlzIGZ1bmN0aW9uIGFnYWluCiAqIGFmdGVyIDEgb3IgMiBzZWNvbmRzIChpLmUuIGFmdGVyIGRpc2NvdmVyeSBoYXMgYmVlbiBkb25lKS4KICovCnN0cnVjdCBpcmRhX2RldmljZV9pbmZvICppcmxtcF9nZXRfZGlzY292ZXJpZXMoaW50ICpwbiwgX191MTYgbWFzaywgaW50IG5zbG90cykKewoJLyogSWYgZGlzY292ZXJ5IGlzIG5vdCBlbmFibGVkLCBpdCdzIGxpa2VseSB0aGF0IHRoZSBkaXNjb3ZlcnkgbG9nCgkgKiB3aWxsIGJlIGVtcHR5LiBTbywgd2UgdHJpZ2dlciBhIHNpbmdsZSBkaXNjb3ZlcnksIHNvIHRoYXQgbmV4dAoJICogdGltZSB0aGUgdXNlciBjYWxsIHVzIHRoZXJlIG1pZ2h0IGJlIHNvbWUgcmVzdWx0cyBpbiB0aGUgbG9nLgoJICogSmVhbiBJSQoJICovCglpZiAoIXN5c2N0bF9kaXNjb3ZlcnkpIHsKCQkvKiBDaGVjayBpZiB1c2VyIHdhbnRzIHRvIG92ZXJyaWRlIHRoZSBkZWZhdWx0ICovCgkJaWYgKG5zbG90cyA9PSBESVNDT1ZFUllfREVGQVVMVF9TTE9UUykKCQkJbnNsb3RzID0gc3lzY3RsX2Rpc2NvdmVyeV9zbG90czsKCgkJLyogU3RhcnQgZGlzY292ZXJ5IC0gd2lsbCBjb21wbGV0ZSBzb21ldGltZSBsYXRlciAqLwoJCWlybG1wX2RvX2Rpc2NvdmVyeShuc2xvdHMpOwoJCS8qIE5vdGUgOiB3ZSBuZXZlciBkbyBleHBpcnkgaGVyZS4gRXhwaXJ5IHdpbGwgcnVuIG9uIHRoZQoJCSAqIGRpc2NvdmVyeSB0aW1lciByZWdhcmRsZXNzIG9mIHRoZSBzdGF0ZSBvZiBzeXNjdGxfZGlzY292ZXJ5CgkJICogSmVhbiBJSSAqLwoJfQoKCS8qIFJldHVybiBjdXJyZW50IGNhY2hlZCBkaXNjb3ZlcnkgbG9nICovCglyZXR1cm4oaXJsbXBfY29weV9kaXNjb3ZlcmllcyhpcmxtcC0+Y2FjaGVsb2csIHBuLCBtYXNrLCBUUlVFKSk7Cn0KRVhQT1JUX1NZTUJPTChpcmxtcF9nZXRfZGlzY292ZXJpZXMpOwoKLyoKICogRnVuY3Rpb24gaXJsbXBfbm90aWZ5X2NsaWVudCAobG9nKQogKgogKiAgICBOb3RpZnkgYWxsIGFib3V0IGRpc2NvdmVyZWQgZGV2aWNlcwogKgogKiBDbGllbnRzIHJlZ2lzdGVyZWQgd2l0aCBJckxNUCBhcmUgOgogKglvIElyQ29tbQogKglvIElyTEFOCiAqCW8gQW55IHNvY2tldCAoaW4gYW55IHN0YXRlIC0gb3VjaCwgdGhhdCBtYXkgYmUgYSBsb3QgISkKICogVGhlIGNsaWVudCBtYXkgaGF2ZSBkZWZpbmVkIGEgY2FsbGJhY2sgdG8gYmUgbm90aWZpZWQgaW4gY2FzZSBvZgogKiBwYXJ0aWFsL3NlbGVjdGl2ZSBkaXNjb3ZlcnkgYmFzZWQgb24gdGhlIGhpbnRzIHRoYXQgaXQgcGFzc2VkIHRvIElyTE1QLgogKi8Kc3RhdGljIGlubGluZSB2b2lkCmlybG1wX25vdGlmeV9jbGllbnQoaXJsbXBfY2xpZW50X3QgKmNsaWVudCwKCQkgICAgaGFzaGJpbl90ICpsb2csIERJU0NPVkVSWV9NT0RFIG1vZGUpCnsKCWRpc2NpbmZvX3QgKmRpc2NvdmVyaWVzOwkvKiBDb3B5IG9mIHRoZSBkaXNjb3ZlcnkgbG9nICovCglpbnQJbnVtYmVyOwkJCS8qIE51bWJlciBvZiBub2RlcyBpbiB0aGUgbG9nICovCglpbnQJaTsKCglJUkRBX0RFQlVHKDMsICIlcygpXG4iLCBfX0ZVTkNUSU9OX18pOwoKCS8qIENoZWNrIGlmIGNsaWVudCB3YW50cyBvciBub3QgcGFydGlhbC9zZWxlY3RpdmUgbG9nIChvcHRpbWlzYXRpb24pICovCglpZiAoIWNsaWVudC0+ZGlzY29fY2FsbGJhY2spCgkJcmV0dXJuOwoKCS8qCgkgKiBMb2NraW5nIG5vdGVzIDoKCSAqIHRoZSBvbGQgY29kZSB3YXMgbWFuaXB1bGF0aW5nIHRoZSBsb2cgZGlyZWN0bHksIHdoaWNoIHdhcwoJICogdmVyeSByYWN5LiBOb3csIHdlIHVzZSBjb3B5X2Rpc2NvdmVyaWVzLCB0aGF0IHByb3RlY3RzCgkgKiBpdHNlbGYgd2hpbGUgZHVtcGluZyB0aGUgbG9nIGZvciB1cy4KCSAqIFRoZSBvdmVyaGVhZCBvZiB0aGUgY29weSBpcyBjb21wZW5zYXRlZCBieSB0aGUgZmFjdCB0aGF0CgkgKiB3ZSBvbmx5IHBhc3MgbmV3IGRpc2NvdmVyaWVzIGluIG5vcm1hbCBtb2RlIGFuZCBkb24ndAoJICogcGFzcyB0aGUgc2FtZSBvbGQgZW50cnkgZXZlcnkgM3MgdG8gdGhlIGNhbGxlciBhcyB3ZSB1c2VkCgkgKiB0byBkbyAodmlydHVhbCBmdW5jdGlvbiBjYWxsaW5nIGlzIGV4cGVuc2l2ZSkuCgkgKiBKZWFuIElJCgkgKi8KCgkvKgoJICogTm93LCBjaGVjayBhbGwgZGlzY292ZXJlZCBkZXZpY2VzIChpZiBhbnkpLCBhbmQgbm90aWZ5IGNsaWVudAoJICogb25seSBhYm91dCB0aGUgc2VydmljZXMgdGhhdCB0aGUgY2xpZW50IGlzIGludGVyZXN0ZWQgaW4KCSAqIFdlIGFsc28gbm90aWZ5IG9ubHkgYWJvdXQgdGhlIG5ldyBkZXZpY2VzIHVubGVzcyB0aGUgY2FsbGVyCgkgKiBleHBsaWNpdGx5IHJlcXVlc3QgYSBkdW1wIG9mIHRoZSBsb2cuIEplYW4gSUkKCSAqLwoJZGlzY292ZXJpZXMgPSBpcmxtcF9jb3B5X2Rpc2NvdmVyaWVzKGxvZywgJm51bWJlciwKCQkJCQkgICAgIGNsaWVudC0+aGludF9tYXNrLndvcmQsCgkJCQkJICAgICAobW9kZSA9PSBESVNDT1ZFUllfTE9HKSk7CgkvKiBDaGVjayBpZiB0aGUgd2UgZ290IHNvbWUgcmVzdWx0cyAqLwoJaWYgKGRpc2NvdmVyaWVzID09IE5VTEwpCgkJcmV0dXJuOwkvKiBObyBub2RlcyBkaXNjb3ZlcmVkICovCgoJLyogUGFzcyBhbGwgZW50cmllcyB0byB0aGUgbGlzdGVuZXIgKi8KCWZvcihpID0gMDsgaSA8IG51bWJlcjsgaSsrKQoJCWNsaWVudC0+ZGlzY29fY2FsbGJhY2soJihkaXNjb3Zlcmllc1tpXSksIG1vZGUsIGNsaWVudC0+cHJpdik7CgoJLyogRnJlZSB1cCBvdXIgYnVmZmVyICovCglrZnJlZShkaXNjb3Zlcmllcyk7Cn0KCi8qCiAqIEZ1bmN0aW9uIGlybG1wX2Rpc2NvdmVyeV9jb25maXJtICggc2VsZiwgbG9nKQogKgogKiAgICBTb21lIGRldmljZShzKSBhbnN3ZXJlZCB0byBvdXIgZGlzY292ZXJ5IHJlcXVlc3QhIENoZWNrIHRvIHNlZSB3aGljaAogKiAgICBkZXZpY2UgaXQgaXMsIGFuZCBnaXZlIGluZGljYXRpb24gdG8gdGhlIGNsaWVudChzKQogKgogKi8Kdm9pZCBpcmxtcF9kaXNjb3ZlcnlfY29uZmlybShoYXNoYmluX3QgKmxvZywgRElTQ09WRVJZX01PREUgbW9kZSkKewoJaXJsbXBfY2xpZW50X3QgKmNsaWVudDsKCWlybG1wX2NsaWVudF90ICpjbGllbnRfbmV4dDsKCglJUkRBX0RFQlVHKDMsICIlcygpXG4iLCBfX0ZVTkNUSU9OX18pOwoKCUlSREFfQVNTRVJUKGxvZyAhPSBOVUxMLCByZXR1cm47KTsKCglpZiAoIShIQVNIQklOX0dFVF9TSVpFKGxvZykpKQoJCXJldHVybjsKCgkvKiBGb3IgZWFjaCBjbGllbnQgLSBub3RpZnkgY2FsbGJhY2sgbWF5IHRvdWNoIGNsaWVudCBsaXN0ICovCgljbGllbnQgPSAoaXJsbXBfY2xpZW50X3QgKikgaGFzaGJpbl9nZXRfZmlyc3QoaXJsbXAtPmNsaWVudHMpOwoJd2hpbGUgKE5VTEwgIT0gaGFzaGJpbl9maW5kX25leHQoaXJsbXAtPmNsaWVudHMsIChsb25nKSBjbGllbnQsIE5VTEwsCgkJCQkJICh2b2lkICopICZjbGllbnRfbmV4dCkgKSB7CgkJLyogQ2hlY2sgaWYgd2Ugc2hvdWxkIG5vdGlmeSBjbGllbnQgKi8KCQlpcmxtcF9ub3RpZnlfY2xpZW50KGNsaWVudCwgbG9nLCBtb2RlKTsKCgkJY2xpZW50ID0gY2xpZW50X25leHQ7Cgl9Cn0KCi8qCiAqIEZ1bmN0aW9uIGlybG1wX2Rpc2NvdmVyeV9leHBpcnkgKGV4cGlyeSkKICoKICoJVGhpcyBkZXZpY2UgaXMgbm8gbG9uZ2VyIGJlZW4gZGlzY292ZXJlZCwgYW5kIHRoZXJlZm9yZSBpdCBpcyBiZWluZwogKglwdXJnZWQgZnJvbSB0aGUgZGlzY292ZXJ5IGxvZy4gSW5mb3JtIGFsbCBjbGllbnRzIHdobyBoYXZlCiAqCXJlZ2lzdGVyZWQgZm9yIHRoaXMgZXZlbnQuLi4KICoKICoJTm90ZSA6IGNhbGxlZCBleGNsdXNpdmVseSBmcm9tIGRpc2NvdmVyeS5jCiAqCU5vdGUgOiB0aGlzIGlzIG5vIGxvbmdlciBjYWxsZWQgdW5kZXIgZGlzY292ZXJ5IHNwaW5sb2NrLCBzbyB0aGUKICoJCWNsaWVudCBjYW4gZG8gd2hhdGV2ZXIgaGUgd2FudHMgaW4gdGhlIGNhbGxiYWNrLgogKi8Kdm9pZCBpcmxtcF9kaXNjb3ZlcnlfZXhwaXJ5KGRpc2NpbmZvX3QgKmV4cGlyaWVzLCBpbnQgbnVtYmVyKQp7CglpcmxtcF9jbGllbnRfdCAqY2xpZW50OwoJaXJsbXBfY2xpZW50X3QgKmNsaWVudF9uZXh0OwoJaW50CQlpOwoKCUlSREFfREVCVUcoMywgIiVzKClcbiIsIF9fRlVOQ1RJT05fXyk7CgoJSVJEQV9BU1NFUlQoZXhwaXJpZXMgIT0gTlVMTCwgcmV0dXJuOyk7CgoJLyogRm9yIGVhY2ggY2xpZW50IC0gbm90aWZ5IGNhbGxiYWNrIG1heSB0b3VjaCBjbGllbnQgbGlzdCAqLwoJY2xpZW50ID0gKGlybG1wX2NsaWVudF90ICopIGhhc2hiaW5fZ2V0X2ZpcnN0KGlybG1wLT5jbGllbnRzKTsKCXdoaWxlIChOVUxMICE9IGhhc2hiaW5fZmluZF9uZXh0KGlybG1wLT5jbGllbnRzLCAobG9uZykgY2xpZW50LCBOVUxMLAoJCQkJCSAodm9pZCAqKSAmY2xpZW50X25leHQpICkgewoKCQkvKiBQYXNzIGFsbCBlbnRyaWVzIHRvIHRoZSBsaXN0ZW5lciAqLwoJCWZvcihpID0gMDsgaSA8IG51bWJlcjsgaSsrKSB7CgkJCS8qIENoZWNrIGlmIHdlIHNob3VsZCBub3RpZnkgY2xpZW50ICovCgkJCWlmICgoY2xpZW50LT5leHBpcl9jYWxsYmFjaykgJiYKCQkJICAgIChjbGllbnQtPmhpbnRfbWFzay53b3JkICYgdTE2aG8oZXhwaXJpZXNbaV0uaGludHMpCgkJCSAgICAgJiAweDdmN2YpICkKCQkJCWNsaWVudC0+ZXhwaXJfY2FsbGJhY2soJihleHBpcmllc1tpXSksCgkJCQkJCSAgICAgICBFWFBJUllfVElNRU9VVCwKCQkJCQkJICAgICAgIGNsaWVudC0+cHJpdik7CgkJfQoKCQkvKiBOZXh0IGNsaWVudCAqLwoJCWNsaWVudCA9IGNsaWVudF9uZXh0OwoJfQp9CgovKgogKiBGdW5jdGlvbiBpcmxtcF9nZXRfZGlzY292ZXJ5X3Jlc3BvbnNlICgpCiAqCiAqICAgIFVzZWQgYnkgSXJMQVAgdG8gZ2V0IHRoZSBkaXNjb3ZlcnkgaW5mbyBpdCBuZWVkcyB3aGVuIGFuc3dlcmluZwogKiAgICBkaXNjb3ZlcnkgcmVxdWVzdHMgYnkgb3RoZXIgZGV2aWNlcy4KICovCmRpc2NvdmVyeV90ICppcmxtcF9nZXRfZGlzY292ZXJ5X3Jlc3BvbnNlKHZvaWQpCnsKCUlSREFfREVCVUcoNCwgIiVzKClcbiIsIF9fRlVOQ1RJT05fXyk7CgoJSVJEQV9BU1NFUlQoaXJsbXAgIT0gTlVMTCwgcmV0dXJuIE5VTEw7KTsKCgl1MTZobyhpcmxtcC0+ZGlzY292ZXJ5X3JzcC5kYXRhLmhpbnRzKSA9IGlybG1wLT5oaW50cy53b3JkOwoKCS8qCgkgKiAgU2V0IGNoYXJhY3RlciBzZXQgZm9yIGRldmljZSBuYW1lICh3ZSB1c2UgQVNDSUkpLCBhbmQKCSAqICBjb3B5IGRldmljZSBuYW1lLiBSZW1lbWJlciB0byBtYWtlIHJvb20gZm9yIGEgXDAgYXQgdGhlCgkgKiAgZW5kCgkgKi8KCWlybG1wLT5kaXNjb3ZlcnlfcnNwLmRhdGEuY2hhcnNldCA9IENTX0FTQ0lJOwoKCXN0cm5jcHkoaXJsbXAtPmRpc2NvdmVyeV9yc3AuZGF0YS5pbmZvLCBzeXNjdGxfZGV2bmFtZSwKCQlOSUNLTkFNRV9NQVhfTEVOKTsKCWlybG1wLT5kaXNjb3ZlcnlfcnNwLm5hbWVfbGVuID0gc3RybGVuKGlybG1wLT5kaXNjb3ZlcnlfcnNwLmRhdGEuaW5mbyk7CgoJcmV0dXJuICZpcmxtcC0+ZGlzY292ZXJ5X3JzcDsKfQoKLyoKICogRnVuY3Rpb24gaXJsbXBfZGF0YV9yZXF1ZXN0IChzZWxmLCBza2IpCiAqCiAqICAgIFNlbmQgc29tZSBkYXRhIHRvIHBlZXIgZGV2aWNlCiAqCiAqIE5vdGUgb24gc2tiIG1hbmFnZW1lbnQgOgogKiBBZnRlciBjYWxsaW5nIHRoZSBsb3dlciBsYXllcnMgb2YgdGhlIElyREEgc3RhY2ssIHdlIGFsd2F5cwogKiBrZnJlZSgpIHRoZSBza2IsIHdoaWNoIGRyb3AgdGhlIHJlZmVyZW5jZSBjb3VudCAoYW5kIHBvdGVudGlhbGx5CiAqIGRlc3Ryb3kgaXQpLgogKiBJckxNUCBhbmQgSXJMQVAgbWF5IHF1ZXVlIHRoZSBwYWNrZXQsIGFuZCBpbiB0aG9zZSBjYXNlcyB3aWxsIG5lZWQKICogdG8gdXNlIHNrYl9nZXQoKSB0byBrZWVwIGl0IGFyb3VuZC4KICogSmVhbiBJSQogKi8KaW50IGlybG1wX2RhdGFfcmVxdWVzdChzdHJ1Y3QgbHNhcF9jYiAqc2VsZiwgc3RydWN0IHNrX2J1ZmYgKnVzZXJkYXRhKQp7CglpbnQJcmV0OwoKCUlSREFfQVNTRVJUKHNlbGYgIT0gTlVMTCwgcmV0dXJuIC0xOyk7CglJUkRBX0FTU0VSVChzZWxmLT5tYWdpYyA9PSBMTVBfTFNBUF9NQUdJQywgcmV0dXJuIC0xOyk7CgoJLyogTWFrZSByb29tIGZvciBNVVggaGVhZGVyICovCglJUkRBX0FTU0VSVChza2JfaGVhZHJvb20odXNlcmRhdGEpID49IExNUF9IRUFERVIsIHJldHVybiAtMTspOwoJc2tiX3B1c2godXNlcmRhdGEsIExNUF9IRUFERVIpOwoKCXJldCA9IGlybG1wX2RvX2xzYXBfZXZlbnQoc2VsZiwgTE1fREFUQV9SRVFVRVNULCB1c2VyZGF0YSk7CgoJLyogRHJvcCByZWZlcmVuY2UgY291bnQgLSBzZWUgaXJsYXBfZGF0YV9yZXF1ZXN0KCkuICovCglkZXZfa2ZyZWVfc2tiKHVzZXJkYXRhKTsKCglyZXR1cm4gcmV0Owp9CkVYUE9SVF9TWU1CT0woaXJsbXBfZGF0YV9yZXF1ZXN0KTsKCi8qCiAqIEZ1bmN0aW9uIGlybG1wX2RhdGFfaW5kaWNhdGlvbiAoaGFuZGxlLCBza2IpCiAqCiAqICAgIEdvdCBkYXRhIGZyb20gTEFQIGxheWVyIHNvIHBhc3MgaXQgdXAgdG8gdXBwZXIgbGF5ZXIKICoKICovCnZvaWQgaXJsbXBfZGF0YV9pbmRpY2F0aW9uKHN0cnVjdCBsc2FwX2NiICpzZWxmLCBzdHJ1Y3Qgc2tfYnVmZiAqc2tiKQp7CgkvKiBIaWRlIExNUCBoZWFkZXIgZnJvbSBsYXllciBhYm92ZSAqLwoJc2tiX3B1bGwoc2tiLCBMTVBfSEVBREVSKTsKCglpZiAoc2VsZi0+bm90aWZ5LmRhdGFfaW5kaWNhdGlvbikgewoJCS8qIERvbid0IGZvcmdldCB0byByZWZjb3VudCBpdCAtIHNlZSBpcmxhcF9kcml2ZXJfcmN2KCkuICovCgkJc2tiX2dldChza2IpOwoJCXNlbGYtPm5vdGlmeS5kYXRhX2luZGljYXRpb24oc2VsZi0+bm90aWZ5Lmluc3RhbmNlLCBzZWxmLCBza2IpOwoJfQp9CgovKgogKiBGdW5jdGlvbiBpcmxtcF91ZGF0YV9yZXF1ZXN0IChzZWxmLCBza2IpCiAqLwppbnQgaXJsbXBfdWRhdGFfcmVxdWVzdChzdHJ1Y3QgbHNhcF9jYiAqc2VsZiwgc3RydWN0IHNrX2J1ZmYgKnVzZXJkYXRhKQp7CglpbnQJcmV0OwoKCUlSREFfREVCVUcoNCwgIiVzKClcbiIsIF9fRlVOQ1RJT05fXyk7CgoJSVJEQV9BU1NFUlQodXNlcmRhdGEgIT0gTlVMTCwgcmV0dXJuIC0xOyk7CgoJLyogTWFrZSByb29tIGZvciBNVVggaGVhZGVyICovCglJUkRBX0FTU0VSVChza2JfaGVhZHJvb20odXNlcmRhdGEpID49IExNUF9IRUFERVIsIHJldHVybiAtMTspOwoJc2tiX3B1c2godXNlcmRhdGEsIExNUF9IRUFERVIpOwoKCXJldCA9IGlybG1wX2RvX2xzYXBfZXZlbnQoc2VsZiwgTE1fVURBVEFfUkVRVUVTVCwgdXNlcmRhdGEpOwoKCS8qIERyb3AgcmVmZXJlbmNlIGNvdW50IC0gc2VlIGlybGFwX2RhdGFfcmVxdWVzdCgpLiAqLwoJZGV2X2tmcmVlX3NrYih1c2VyZGF0YSk7CgoJcmV0dXJuIHJldDsKfQoKLyoKICogRnVuY3Rpb24gaXJsbXBfdWRhdGFfaW5kaWNhdGlvbiAoc2VsZiwgc2tiKQogKgogKiAgICBTZW5kIHVucmVsaWFibGUgZGF0YSAoYnV0IHN0aWxsIHdpdGhpbiB0aGUgY29ubmVjdGlvbikKICoKICovCnZvaWQgaXJsbXBfdWRhdGFfaW5kaWNhdGlvbihzdHJ1Y3QgbHNhcF9jYiAqc2VsZiwgc3RydWN0IHNrX2J1ZmYgKnNrYikKewoJSVJEQV9ERUJVRyg0LCAiJXMoKVxuIiwgX19GVU5DVElPTl9fKTsKCglJUkRBX0FTU0VSVChzZWxmICE9IE5VTEwsIHJldHVybjspOwoJSVJEQV9BU1NFUlQoc2VsZi0+bWFnaWMgPT0gTE1QX0xTQVBfTUFHSUMsIHJldHVybjspOwoJSVJEQV9BU1NFUlQoc2tiICE9IE5VTEwsIHJldHVybjspOwoKCS8qIEhpZGUgTE1QIGhlYWRlciBmcm9tIGxheWVyIGFib3ZlICovCglza2JfcHVsbChza2IsIExNUF9IRUFERVIpOwoKCWlmIChzZWxmLT5ub3RpZnkudWRhdGFfaW5kaWNhdGlvbikgewoJCS8qIERvbid0IGZvcmdldCB0byByZWZjb3VudCBpdCAtIHNlZSBpcmxhcF9kcml2ZXJfcmN2KCkuICovCgkJc2tiX2dldChza2IpOwoJCXNlbGYtPm5vdGlmeS51ZGF0YV9pbmRpY2F0aW9uKHNlbGYtPm5vdGlmeS5pbnN0YW5jZSwgc2VsZiwKCQkJCQkgICAgICBza2IpOwoJfQp9CgovKgogKiBGdW5jdGlvbiBpcmxtcF9jb25ubGVzc19kYXRhX3JlcXVlc3QgKHNlbGYsIHNrYikKICovCiNpZmRlZiBDT05GSUdfSVJEQV9VTFRSQQppbnQgaXJsbXBfY29ubmxlc3NfZGF0YV9yZXF1ZXN0KHN0cnVjdCBsc2FwX2NiICpzZWxmLCBzdHJ1Y3Qgc2tfYnVmZiAqdXNlcmRhdGEsCgkJCQlfX3U4IHBpZCkKewoJc3RydWN0IHNrX2J1ZmYgKmNsb25lX3NrYjsKCXN0cnVjdCBsYXBfY2IgKmxhcDsKCglJUkRBX0RFQlVHKDQsICIlcygpXG4iLCBfX0ZVTkNUSU9OX18pOwoKCUlSREFfQVNTRVJUKHVzZXJkYXRhICE9IE5VTEwsIHJldHVybiAtMTspOwoKCS8qIE1ha2Ugcm9vbSBmb3IgTVVYIGFuZCBQSUQgaGVhZGVyICovCglJUkRBX0FTU0VSVChza2JfaGVhZHJvb20odXNlcmRhdGEpID49IExNUF9IRUFERVIrTE1QX1BJRF9IRUFERVIsCgkJICAgIHJldHVybiAtMTspOwoKCS8qIEluc2VydCBwcm90b2NvbCBpZGVudGlmaWVyICovCglza2JfcHVzaCh1c2VyZGF0YSwgTE1QX1BJRF9IRUFERVIpOwoJaWYoc2VsZiAhPSBOVUxMKQoJICB1c2VyZGF0YS0+ZGF0YVswXSA9IHNlbGYtPnBpZDsKCWVsc2UKCSAgdXNlcmRhdGEtPmRhdGFbMF0gPSBwaWQ7CgoJLyogQ29ubmVjdGlvbmxlc3Mgc29ja2V0cyBtdXN0IHVzZSAweDcwICovCglza2JfcHVzaCh1c2VyZGF0YSwgTE1QX0hFQURFUik7Cgl1c2VyZGF0YS0+ZGF0YVswXSA9IHVzZXJkYXRhLT5kYXRhWzFdID0gTFNBUF9DT05OTEVTUzsKCgkvKiBUcnkgdG8gc2VuZCBDb25uZWN0aW9ubGVzcyAgcGFja2V0cyBvdXQgb24gYWxsIGxpbmtzICovCglsYXAgPSAoc3RydWN0IGxhcF9jYiAqKSBoYXNoYmluX2dldF9maXJzdChpcmxtcC0+bGlua3MpOwoJd2hpbGUgKGxhcCAhPSBOVUxMKSB7CgkJSVJEQV9BU1NFUlQobGFwLT5tYWdpYyA9PSBMTVBfTEFQX01BR0lDLCByZXR1cm4gLTE7KTsKCgkJY2xvbmVfc2tiID0gc2tiX2Nsb25lKHVzZXJkYXRhLCBHRlBfQVRPTUlDKTsKCQlpZiAoIWNsb25lX3NrYikgewoJCQlkZXZfa2ZyZWVfc2tiKHVzZXJkYXRhKTsKCQkJcmV0dXJuIC1FTk9NRU07CgkJfQoKCQlpcmxhcF91bml0ZGF0YV9yZXF1ZXN0KGxhcC0+aXJsYXAsIGNsb25lX3NrYik7CgkJLyogaXJsYXBfdW5pdGRhdGFfcmVxdWVzdCgpIGRvbid0IGluY3JlYXNlIHJlZmNvdW50LAoJCSAqIHNvIG5vIGRldl9rZnJlZV9za2IoKSAtIEplYW4gSUkgKi8KCgkJbGFwID0gKHN0cnVjdCBsYXBfY2IgKikgaGFzaGJpbl9nZXRfbmV4dChpcmxtcC0+bGlua3MpOwoJfQoJZGV2X2tmcmVlX3NrYih1c2VyZGF0YSk7CgoJcmV0dXJuIDA7Cn0KI2VuZGlmIC8qIENPTkZJR19JUkRBX1VMVFJBICovCgovKgogKiBGdW5jdGlvbiBpcmxtcF9jb25ubGVzc19kYXRhX2luZGljYXRpb24gKHNlbGYsIHNrYikKICoKICogICAgUmVjZWl2ZSB1bnJlbGlhYmxlIGRhdGEgb3V0c2lkZSBhbnkgY29ubmVjdGlvbi4gTW9zdGx5IHVzZWQgYnkgVWx0cmEKICoKICovCiNpZmRlZiBDT05GSUdfSVJEQV9VTFRSQQp2b2lkIGlybG1wX2Nvbm5sZXNzX2RhdGFfaW5kaWNhdGlvbihzdHJ1Y3QgbHNhcF9jYiAqc2VsZiwgc3RydWN0IHNrX2J1ZmYgKnNrYikKewoJSVJEQV9ERUJVRyg0LCAiJXMoKVxuIiwgX19GVU5DVElPTl9fKTsKCglJUkRBX0FTU0VSVChzZWxmICE9IE5VTEwsIHJldHVybjspOwoJSVJEQV9BU1NFUlQoc2VsZi0+bWFnaWMgPT0gTE1QX0xTQVBfTUFHSUMsIHJldHVybjspOwoJSVJEQV9BU1NFUlQoc2tiICE9IE5VTEwsIHJldHVybjspOwoKCS8qIEhpZGUgTE1QIGFuZCBQSUQgaGVhZGVyIGZyb20gbGF5ZXIgYWJvdmUgKi8KCXNrYl9wdWxsKHNrYiwgTE1QX0hFQURFUitMTVBfUElEX0hFQURFUik7CgoJaWYgKHNlbGYtPm5vdGlmeS51ZGF0YV9pbmRpY2F0aW9uKSB7CgkJLyogRG9uJ3QgZm9yZ2V0IHRvIHJlZmNvdW50IGl0IC0gc2VlIGlybGFwX2RyaXZlcl9yY3YoKS4gKi8KCQlza2JfZ2V0KHNrYik7CgkJc2VsZi0+bm90aWZ5LnVkYXRhX2luZGljYXRpb24oc2VsZi0+bm90aWZ5Lmluc3RhbmNlLCBzZWxmLAoJCQkJCSAgICAgIHNrYik7Cgl9Cn0KI2VuZGlmIC8qIENPTkZJR19JUkRBX1VMVFJBICovCgovKgogKiBQcm9wYWdhdGUgc3RhdHVzIGluZGljYXRpb24gZnJvbSBMQVAgdG8gTFNBUHMgKHZpYSBMTVApCiAqIFRoaXMgZG9uJ3QgdHJpZ2dlciBhbnkgY2hhbmdlIG9mIHN0YXRlIGluIGxhcF9jYiwgbG1wX2NiIG9yIGxzYXBfY2IsCiAqIGFuZCB0aGUgZXZlbnQgaXMgc3RhdGVsZXNzLCB0aGVyZWZvcmUgd2UgY2FuIGJ5cGFzcyBib3RoIHN0YXRlIG1hY2hpbmVzCiAqIGFuZCBzZW5kIHRoZSBldmVudCBkaXJlY3QgdG8gdGhlIExTQVAgdXNlci4KICogSmVhbiBJSQogKi8Kdm9pZCBpcmxtcF9zdGF0dXNfaW5kaWNhdGlvbihzdHJ1Y3QgbGFwX2NiICpzZWxmLAoJCQkgICAgIExJTktfU1RBVFVTIGxpbmssIExPQ0tfU1RBVFVTIGxvY2spCnsKCXN0cnVjdCBsc2FwX2NiICpuZXh0OwoJc3RydWN0IGxzYXBfY2IgKmN1cnI7CgoJLyogU2VuZCBzdGF0dXNfaW5kaWNhdGlvbiB0byBhbGwgTFNBUHMgdXNpbmcgdGhpcyBsaW5rICovCgljdXJyID0gKHN0cnVjdCBsc2FwX2NiICopIGhhc2hiaW5fZ2V0X2ZpcnN0KCBzZWxmLT5sc2Fwcyk7Cgl3aGlsZSAoTlVMTCAhPSBoYXNoYmluX2ZpbmRfbmV4dChzZWxmLT5sc2FwcywgKGxvbmcpIGN1cnIsIE5VTEwsCgkJCQkJICh2b2lkICopICZuZXh0KSApIHsKCQlJUkRBX0FTU0VSVChjdXJyLT5tYWdpYyA9PSBMTVBfTFNBUF9NQUdJQywgcmV0dXJuOyk7CgkJLyoKCQkgKiAgSW5mb3JtIHNlcnZpY2UgdXNlciBpZiBoZSBoYXMgcmVxdWVzdGVkIGl0CgkJICovCgkJaWYgKGN1cnItPm5vdGlmeS5zdGF0dXNfaW5kaWNhdGlvbiAhPSBOVUxMKQoJCQljdXJyLT5ub3RpZnkuc3RhdHVzX2luZGljYXRpb24oY3Vyci0+bm90aWZ5Lmluc3RhbmNlLAoJCQkJCQkgICAgICAgbGluaywgbG9jayk7CgkJZWxzZQoJCQlJUkRBX0RFQlVHKDIsICIlcygpLCBubyBoYW5kbGVyXG4iLCBfX0ZVTkNUSU9OX18pOwoKCQljdXJyID0gbmV4dDsKCX0KfQoKLyoKICogUmVjZWl2ZSBmbG93IGNvbnRyb2wgaW5kaWNhdGlvbiBmcm9tIExBUC4KICogTEFQIHdhbnQgdXMgdG8gc2VuZCBpdCBvbmUgbW9yZSBmcmFtZS4gV2UgaW1wbGVtZW50IGEgc2ltcGxlIHJvdW5kCiAqIHJvYmluIHNjaGVkdWxlciBiZXR3ZWVuIHRoZSBhY3RpdmUgc29ja2V0cyBzbyB0aGF0IHdlIGdldCBhIGJpdCBvZgogKiBmYWlybmVzcy4gTm90ZSB0aGF0IHRoZSByb3VuZCByb2JpbiBpcyBmYXIgZnJvbSBwZXJmZWN0LCBidXQgaXQncwogKiBiZXR0ZXIgdGhhbiBub3RoaW5nLgogKiBXZSB0aGVuIHBvbGwgdGhlIHNlbGVjdGVkIHNvY2tldCBzbyB0aGF0IHdlIGNhbiBkbyBzeW5jaHJvbm91cwogKiByZWZpbGxpbmcgb2YgSXJMQVAgKHdoaWNoIGFsbG93IHRvIG1pbmltaXNlIHRoZSBudW1iZXIgb2YgYnVmZmVycykuCiAqIEplYW4gSUkKICovCnZvaWQgaXJsbXBfZmxvd19pbmRpY2F0aW9uKHN0cnVjdCBsYXBfY2IgKnNlbGYsIExPQ0FMX0ZMT1cgZmxvdykKewoJc3RydWN0IGxzYXBfY2IgKm5leHQ7CglzdHJ1Y3QgbHNhcF9jYiAqY3VycjsKCWludAlsc2FwX3RvZG87CgoJSVJEQV9BU1NFUlQoc2VsZi0+bWFnaWMgPT0gTE1QX0xBUF9NQUdJQywgcmV0dXJuOyk7CglJUkRBX0FTU0VSVChmbG93ID09IEZMT1dfU1RBUlQsIHJldHVybjspOwoKCS8qIEdldCB0aGUgbnVtYmVyIG9mIGxzYXAuIFRoYXQncyB0aGUgb25seSBzYWZlIHdheSB0byBrbm93CgkgKiB0aGF0IHdlIGhhdmUgbG9vcGVkIGFyb3VuZC4uLiAtIEplYW4gSUkgKi8KCWxzYXBfdG9kbyA9IEhBU0hCSU5fR0VUX1NJWkUoc2VsZi0+bHNhcHMpOwoJSVJEQV9ERUJVRyg0LCAiJXMoKSA6ICVkIGxzYXBzIHRvIHNjYW5cbiIsIF9fRlVOQ1RJT05fXywgbHNhcF90b2RvKTsKCgkvKiBQb2xsIGxzYXAgaW4gb3JkZXIgdW50aWwgdGhlIHF1ZXVlIGlzIGZ1bGwgb3IgdW50aWwgd2UKCSAqIHRyaWVkIHRoZW0gYWxsLgoJICogTW9zdCBvZnRlbiwgdGhlIGN1cnJlbnQgTFNBUCB3aWxsIGhhdmUgc29tZXRoaW5nIHRvIHNlbmQsCgkgKiBzbyB3ZSB3aWxsIGdvIHRocm91Z2ggdGhpcyBsb29wIG9ubHkgb25jZS4gLSBKZWFuIElJICovCgl3aGlsZSgobHNhcF90b2RvLS0pICYmCgkgICAgICAoSVJMQVBfR0VUX1RYX1FVRVVFX0xFTihzZWxmLT5pcmxhcCkgPCBMQVBfSElHSF9USFJFU0hPTEQpKSB7CgkJLyogVHJ5IHRvIGZpbmQgdGhlIG5leHQgbHNhcCB3ZSBzaG91bGQgcG9sbC4gKi8KCQluZXh0ID0gc2VsZi0+Zmxvd19uZXh0OwoJCS8qIElmIHdlIGhhdmUgbm8gbHNhcCwgcmVzdGFydCBmcm9tIGZpcnN0IG9uZSAqLwoJCWlmKG5leHQgPT0gTlVMTCkKCQkJbmV4dCA9IChzdHJ1Y3QgbHNhcF9jYiAqKSBoYXNoYmluX2dldF9maXJzdChzZWxmLT5sc2Fwcyk7CgkJLyogVmVyaWZ5IGN1cnJlbnQgb25lIGFuZCBmaW5kIHRoZSBuZXh0IG9uZSAqLwoJCWN1cnIgPSBoYXNoYmluX2ZpbmRfbmV4dChzZWxmLT5sc2FwcywgKGxvbmcpIG5leHQsIE5VTEwsCgkJCQkJICh2b2lkICopICZzZWxmLT5mbG93X25leHQpOwoJCS8qIFVoLW9oLi4uIFBhcmFub2lhICovCgkJaWYoY3VyciA9PSBOVUxMKQoJCQlicmVhazsKCQlJUkRBX0RFQlVHKDQsICIlcygpIDogY3VyciBpcyAlcCwgbmV4dCB3YXMgJXAgYW5kIGlzIG5vdyAlcCwgc3RpbGwgJWQgdG8gZ28gLSBxdWV1ZSBsZW4gPSAlZFxuIiwgX19GVU5DVElPTl9fLCBjdXJyLCBuZXh0LCBzZWxmLT5mbG93X25leHQsIGxzYXBfdG9kbywgSVJMQVBfR0VUX1RYX1FVRVVFX0xFTihzZWxmLT5pcmxhcCkpOwoKCQkvKiBJbmZvcm0gbHNhcCB1c2VyIHRoYXQgaXQgY2FuIHNlbmQgb25lIG1vcmUgcGFja2V0LiAqLwoJCWlmIChjdXJyLT5ub3RpZnkuZmxvd19pbmRpY2F0aW9uICE9IE5VTEwpCgkJCWN1cnItPm5vdGlmeS5mbG93X2luZGljYXRpb24oY3Vyci0+bm90aWZ5Lmluc3RhbmNlLAoJCQkJCQkgICAgIGN1cnIsIGZsb3cpOwoJCWVsc2UKCQkJSVJEQV9ERUJVRygxLCAiJXMoKSwgbm8gaGFuZGxlclxuIiwgX19GVU5DVElPTl9fKTsKCX0KfQoKI2lmIDAKLyoKICogRnVuY3Rpb24gaXJsbXBfaGludF90b19zZXJ2aWNlIChoaW50KQogKgogKiAgICBSZXR1cm5zIGEgbGlzdCBvZiBhbGwgc2VydmljcyBjb250YWluZWQgaW4gdGhlIGdpdmVuIGhpbnQgYml0cy4gVGhpcwogKiAgICBmdW5jdGlvbiBhc3N1bWVzIHRoYXQgdGhlIGhpbnQgYml0cyBoYXZlIHRoZSBzaXplIG9mIHR3byBieXRlcyBvbmx5CiAqLwpfX3U4ICppcmxtcF9oaW50X3RvX3NlcnZpY2UoX191OCAqaGludCkKewoJX191OCAqc2VydmljZTsKCWludCBpID0gMDsKCgkvKgoJICogQWxsb2NhdGUgYXJyYXkgdG8gc3RvcmUgc2VydmljZXMgaW4uIDE2IGVudHJpZXMgc2hvdWxkIGJlIHNhZmUKCSAqIHNpbmNlIHdlIGN1cnJlbnRseSBvbmx5IHN1cHBvcnQgMiBoaW50IGJ5dGVzCgkgKi8KCXNlcnZpY2UgPSBrbWFsbG9jKDE2LCBHRlBfQVRPTUlDKTsKCWlmICghc2VydmljZSkgewoJCUlSREFfREVCVUcoMSwgIiVzKCksIFVuYWJsZSB0byBrbWFsbG9jIVxuIiwgX19GVU5DVElPTl9fKTsKCQlyZXR1cm4gTlVMTDsKCX0KCglpZiAoIWhpbnRbMF0pIHsKCQlJUkRBX0RFQlVHKDEsICI8Tm9uZT5cbiIpOwoJCWtmcmVlKHNlcnZpY2UpOwoJCXJldHVybiBOVUxMOwoJfQoJaWYgKGhpbnRbMF0gJiBISU5UX1BOUCkKCQlJUkRBX0RFQlVHKDEsICJQblAgQ29tcGF0aWJsZSAiKTsKCWlmIChoaW50WzBdICYgSElOVF9QREEpCgkJSVJEQV9ERUJVRygxLCAiUERBL1BhbG10b3AgIik7CglpZiAoaGludFswXSAmIEhJTlRfQ09NUFVURVIpCgkJSVJEQV9ERUJVRygxLCAiQ29tcHV0ZXIgIik7CglpZiAoaGludFswXSAmIEhJTlRfUFJJTlRFUikgewoJCUlSREFfREVCVUcoMSwgIlByaW50ZXIgIik7CgkJc2VydmljZVtpKytdID0gU19QUklOVEVSOwoJfQoJaWYgKGhpbnRbMF0gJiBISU5UX01PREVNKQoJCUlSREFfREVCVUcoMSwgIk1vZGVtICIpOwoJaWYgKGhpbnRbMF0gJiBISU5UX0ZBWCkKCQlJUkRBX0RFQlVHKDEsICJGYXggIik7CglpZiAoaGludFswXSAmIEhJTlRfTEFOKSB7CgkJSVJEQV9ERUJVRygxLCAiTEFOIEFjY2VzcyAiKTsKCQlzZXJ2aWNlW2krK10gPSBTX0xBTjsKCX0KCS8qCgkgKiAgVGVzdCBpZiBleHRlbnNpb24gYnl0ZSBleGlzdHMuIFRoaXMgYnl0ZSB3aWxsIHVzdWFsbHkgYmUKCSAqICB0aGVyZSwgYnV0IHRoaXMgaXMgbm90IHJlYWxseSByZXF1aXJlZCBieSB0aGUgc3RhbmRhcmQuCgkgKiAgKElyTE1QIHAuIDI5KQoJICovCglpZiAoaGludFswXSAmIEhJTlRfRVhURU5TSU9OKSB7CgkJaWYgKGhpbnRbMV0gJiBISU5UX1RFTEVQSE9OWSkgewoJCQlJUkRBX0RFQlVHKDEsICJUZWxlcGhvbnkgIik7CgkJCXNlcnZpY2VbaSsrXSA9IFNfVEVMRVBIT05ZOwoJCX0gaWYgKGhpbnRbMV0gJiBISU5UX0ZJTEVfU0VSVkVSKQoJCQlJUkRBX0RFQlVHKDEsICJGaWxlIFNlcnZlciAiKTsKCgkJaWYgKGhpbnRbMV0gJiBISU5UX0NPTU0pIHsKCQkJSVJEQV9ERUJVRygxLCAiSXJDT01NICIpOwoJCQlzZXJ2aWNlW2krK10gPSBTX0NPTU07CgkJfQoJCWlmIChoaW50WzFdICYgSElOVF9PQkVYKSB7CgkJCUlSREFfREVCVUcoMSwgIklyT0JFWCAiKTsKCQkJc2VydmljZVtpKytdID0gU19PQkVYOwoJCX0KCX0KCUlSREFfREVCVUcoMSwgIlxuIik7CgoJLyogU28gdGhhdCBjbGllbnQgY2FuIGJlIG5vdGlmaWVkIGFib3V0IGFueSBkaXNjb3ZlcnkgKi8KCXNlcnZpY2VbaSsrXSA9IFNfQU5ZOwoKCXNlcnZpY2VbaV0gPSBTX0VORDsKCglyZXR1cm4gc2VydmljZTsKfQojZW5kaWYKCnN0YXRpYyBjb25zdCBfX3UxNiBzZXJ2aWNlX2hpbnRfbWFwcGluZ1tTX0VORF1bMl0gPSB7Cgl7IEhJTlRfUE5QLAkJMCB9LAkJCS8qIFNfUE5QICovCgl7IEhJTlRfUERBLAkJMCB9LAkJCS8qIFNfUERBICovCgl7IEhJTlRfQ09NUFVURVIsCTAgfSwJCQkvKiBTX0NPTVBVVEVSICovCgl7IEhJTlRfUFJJTlRFUiwJCTAgfSwJCQkvKiBTX1BSSU5URVIgKi8KCXsgSElOVF9NT0RFTSwJCTAgfSwJCQkvKiBTX01PREVNICovCgl7IEhJTlRfRkFYLAkJMCB9LAkJCS8qIFNfRkFYICovCgl7IEhJTlRfTEFOLAkJMCB9LAkJCS8qIFNfTEFOICovCgl7IEhJTlRfRVhURU5TSU9OLAlISU5UX1RFTEVQSE9OWSB9LAkvKiBTX1RFTEVQSE9OWSAqLwoJeyBISU5UX0VYVEVOU0lPTiwJSElOVF9DT01NIH0sCQkvKiBTX0NPTU0gKi8KCXsgSElOVF9FWFRFTlNJT04sCUhJTlRfT0JFWCB9LAkJLyogU19PQkVYICovCgl7IDB4RkYsCQkJMHhGRiB9LAkJCS8qIFNfQU5ZICovCn07CgovKgogKiBGdW5jdGlvbiBpcmxtcF9zZXJ2aWNlX3RvX2hpbnQgKHNlcnZpY2UpCiAqCiAqICAgIENvbnZlcnRzIGEgc2VydmljZSB0eXBlLCB0byBhIGhpbnQgYml0CiAqCiAqICAgIFJldHVybnM6IGEgMTYgYml0IGhpbnQgdmFsdWUsIHdpdGggdGhlIHNlcnZpY2UgYml0IHNldAogKi8KX191MTYgaXJsbXBfc2VydmljZV90b19oaW50KGludCBzZXJ2aWNlKQp7CglfX3UxNl9ob3N0X29yZGVyIGhpbnQ7CgoJaGludC5ieXRlWzBdID0gc2VydmljZV9oaW50X21hcHBpbmdbc2VydmljZV1bMF07CgloaW50LmJ5dGVbMV0gPSBzZXJ2aWNlX2hpbnRfbWFwcGluZ1tzZXJ2aWNlXVsxXTsKCglyZXR1cm4gaGludC53b3JkOwp9CkVYUE9SVF9TWU1CT0woaXJsbXBfc2VydmljZV90b19oaW50KTsKCi8qCiAqIEZ1bmN0aW9uIGlybG1wX3JlZ2lzdGVyX3NlcnZpY2UgKHNlcnZpY2UpCiAqCiAqICAgIFJlZ2lzdGVyIGxvY2FsIHNlcnZpY2Ugd2l0aCBJckxNUAogKgogKi8Kdm9pZCAqaXJsbXBfcmVnaXN0ZXJfc2VydmljZShfX3UxNiBoaW50cykKewoJaXJsbXBfc2VydmljZV90ICpzZXJ2aWNlOwoKCUlSREFfREVCVUcoNCwgIiVzKCksIGhpbnRzID0gJTA0eFxuIiwgX19GVU5DVElPTl9fLCBoaW50cyk7CgoJLyogTWFrZSBhIG5ldyByZWdpc3RyYXRpb24gKi8KCXNlcnZpY2UgPSBrbWFsbG9jKHNpemVvZihpcmxtcF9zZXJ2aWNlX3QpLCBHRlBfQVRPTUlDKTsKCWlmICghc2VydmljZSkgewoJCUlSREFfREVCVUcoMSwgIiVzKCksIFVuYWJsZSB0byBrbWFsbG9jIVxuIiwgX19GVU5DVElPTl9fKTsKCQlyZXR1cm4gTlVMTDsKCX0KCXNlcnZpY2UtPmhpbnRzLndvcmQgPSBoaW50czsKCWhhc2hiaW5faW5zZXJ0KGlybG1wLT5zZXJ2aWNlcywgKGlyZGFfcXVldWVfdCAqKSBzZXJ2aWNlLAoJCSAgICAgICAobG9uZykgc2VydmljZSwgTlVMTCk7CgoJaXJsbXAtPmhpbnRzLndvcmQgfD0gaGludHM7CgoJcmV0dXJuICh2b2lkICopc2VydmljZTsKfQpFWFBPUlRfU1lNQk9MKGlybG1wX3JlZ2lzdGVyX3NlcnZpY2UpOwoKLyoKICogRnVuY3Rpb24gaXJsbXBfdW5yZWdpc3Rlcl9zZXJ2aWNlIChoYW5kbGUpCiAqCiAqICAgIFVucmVnaXN0ZXIgc2VydmljZSB3aXRoIElyTE1QLgogKgogKiAgICBSZXR1cm5zOiAwIG9uIHN1Y2Nlc3MsIC0xIG9uIGVycm9yCiAqLwppbnQgaXJsbXBfdW5yZWdpc3Rlcl9zZXJ2aWNlKHZvaWQgKmhhbmRsZSkKewoJaXJsbXBfc2VydmljZV90ICpzZXJ2aWNlOwoJdW5zaWduZWQgbG9uZyBmbGFnczsKCglJUkRBX0RFQlVHKDQsICIlcygpXG4iLCBfX0ZVTkNUSU9OX18pOwoKCWlmICghaGFuZGxlKQoJCXJldHVybiAtMTsKCgkvKiBDYWxsZXIgbWF5IGNhbGwgd2l0aCBpbnZhbGlkIGhhbmRsZSAoaXQncyBsZWdhbCkgLSBKZWFuIElJICovCglzZXJ2aWNlID0gaGFzaGJpbl9sb2NrX2ZpbmQoaXJsbXAtPnNlcnZpY2VzLCAobG9uZykgaGFuZGxlLCBOVUxMKTsKCWlmICghc2VydmljZSkgewoJCUlSREFfREVCVUcoMSwgIiVzKCksIFVua25vd24gc2VydmljZSFcbiIsIF9fRlVOQ1RJT05fXyk7CgkJcmV0dXJuIC0xOwoJfQoKCWhhc2hiaW5fcmVtb3ZlX3RoaXMoaXJsbXAtPnNlcnZpY2VzLCAoaXJkYV9xdWV1ZV90ICopIHNlcnZpY2UpOwoJa2ZyZWUoc2VydmljZSk7CgoJLyogUmVtb3ZlIG9sZCBoaW50IGJpdHMgKi8KCWlybG1wLT5oaW50cy53b3JkID0gMDsKCgkvKiBSZWZyZXNoIGN1cnJlbnQgaGludCBiaXRzICovCglzcGluX2xvY2tfaXJxc2F2ZSgmaXJsbXAtPnNlcnZpY2VzLT5oYl9zcGlubG9jaywgZmxhZ3MpOwogICAgICAgIHNlcnZpY2UgPSAoaXJsbXBfc2VydmljZV90ICopIGhhc2hiaW5fZ2V0X2ZpcnN0KGlybG1wLT5zZXJ2aWNlcyk7CiAgICAgICAgd2hpbGUgKHNlcnZpY2UpIHsKCQlpcmxtcC0+aGludHMud29yZCB8PSBzZXJ2aWNlLT5oaW50cy53b3JkOwoKICAgICAgICAgICAgICAgIHNlcnZpY2UgPSAoaXJsbXBfc2VydmljZV90ICopaGFzaGJpbl9nZXRfbmV4dChpcmxtcC0+c2VydmljZXMpOwogICAgICAgIH0KCXNwaW5fdW5sb2NrX2lycXJlc3RvcmUoJmlybG1wLT5zZXJ2aWNlcy0+aGJfc3BpbmxvY2ssIGZsYWdzKTsKCXJldHVybiAwOwp9CkVYUE9SVF9TWU1CT0woaXJsbXBfdW5yZWdpc3Rlcl9zZXJ2aWNlKTsKCi8qCiAqIEZ1bmN0aW9uIGlybG1wX3JlZ2lzdGVyX2NsaWVudCAoaGludF9tYXNrLCBjYWxsYmFjazEsIGNhbGxiYWNrMikKICoKICogICAgUmVnaXN0ZXIgYSBsb2NhbCBjbGllbnQgd2l0aCBJckxNUAogKglGaXJzdCBjYWxsYmFjayBpcyBzZWxlY3RpdmUgZGlzY292ZXJ5IChiYXNlZCBvbiBoaW50cykKICoJU2Vjb25kIGNhbGxiYWNrIGlzIGZvciBzZWxlY3RpdmUgZGlzY292ZXJ5IGV4cGlyaWVzCiAqCiAqICAgIFJldHVybnM6IGhhbmRsZSA+IDAgb24gc3VjY2VzcywgMCBvbiBlcnJvcgogKi8Kdm9pZCAqaXJsbXBfcmVnaXN0ZXJfY2xpZW50KF9fdTE2IGhpbnRfbWFzaywgRElTQ09WRVJZX0NBTExCQUNLMSBkaXNjb19jbGIsCgkJCSAgICBESVNDT1ZFUllfQ0FMTEJBQ0syIGV4cGlyX2NsYiwgdm9pZCAqcHJpdikKewoJaXJsbXBfY2xpZW50X3QgKmNsaWVudDsKCglJUkRBX0RFQlVHKDEsICIlcygpXG4iLCBfX0ZVTkNUSU9OX18pOwoJSVJEQV9BU1NFUlQoaXJsbXAgIT0gTlVMTCwgcmV0dXJuIE5VTEw7KTsKCgkvKiBNYWtlIGEgbmV3IHJlZ2lzdHJhdGlvbiAqLwoJY2xpZW50ID0ga21hbGxvYyhzaXplb2YoaXJsbXBfY2xpZW50X3QpLCBHRlBfQVRPTUlDKTsKCWlmICghY2xpZW50KSB7CgkJSVJEQV9ERUJVRyggMSwgIiVzKCksIFVuYWJsZSB0byBrbWFsbG9jIVxuIiwgX19GVU5DVElPTl9fKTsKCQlyZXR1cm4gTlVMTDsKCX0KCgkvKiBSZWdpc3RlciB0aGUgZGV0YWlscyAqLwoJY2xpZW50LT5oaW50X21hc2sud29yZCA9IGhpbnRfbWFzazsKCWNsaWVudC0+ZGlzY29fY2FsbGJhY2sgPSBkaXNjb19jbGI7CgljbGllbnQtPmV4cGlyX2NhbGxiYWNrID0gZXhwaXJfY2xiOwoJY2xpZW50LT5wcml2ID0gcHJpdjsKCgloYXNoYmluX2luc2VydChpcmxtcC0+Y2xpZW50cywgKGlyZGFfcXVldWVfdCAqKSBjbGllbnQsCgkJICAgICAgIChsb25nKSBjbGllbnQsIE5VTEwpOwoKCXJldHVybiAodm9pZCAqKSBjbGllbnQ7Cn0KRVhQT1JUX1NZTUJPTChpcmxtcF9yZWdpc3Rlcl9jbGllbnQpOwoKLyoKICogRnVuY3Rpb24gaXJsbXBfdXBkYXRlX2NsaWVudCAoaGFuZGxlLCBoaW50X21hc2ssIGNhbGxiYWNrMSwgY2FsbGJhY2syKQogKgogKiAgICBVcGRhdGVzIHNwZWNpZmllZCBjbGllbnQgKGhhbmRsZSkgd2l0aCBwb3NzaWJseSBuZXcgaGludF9tYXNrIGFuZAogKiAgICBjYWxsYmFjawogKgogKiAgICBSZXR1cm5zOiAwIG9uIHN1Y2Nlc3MsIC0xIG9uIGVycm9yCiAqLwppbnQgaXJsbXBfdXBkYXRlX2NsaWVudCh2b2lkICpoYW5kbGUsIF9fdTE2IGhpbnRfbWFzaywKCQkJRElTQ09WRVJZX0NBTExCQUNLMSBkaXNjb19jbGIsCgkJCURJU0NPVkVSWV9DQUxMQkFDSzIgZXhwaXJfY2xiLCB2b2lkICpwcml2KQp7CglpcmxtcF9jbGllbnRfdCAqY2xpZW50OwoKCWlmICghaGFuZGxlKQoJCXJldHVybiAtMTsKCgljbGllbnQgPSBoYXNoYmluX2xvY2tfZmluZChpcmxtcC0+Y2xpZW50cywgKGxvbmcpIGhhbmRsZSwgTlVMTCk7CglpZiAoIWNsaWVudCkgewoJCUlSREFfREVCVUcoMSwgIiVzKCksIFVua25vd24gY2xpZW50IVxuIiwgX19GVU5DVElPTl9fKTsKCQlyZXR1cm4gLTE7Cgl9CgoJY2xpZW50LT5oaW50X21hc2sud29yZCA9IGhpbnRfbWFzazsKCWNsaWVudC0+ZGlzY29fY2FsbGJhY2sgPSBkaXNjb19jbGI7CgljbGllbnQtPmV4cGlyX2NhbGxiYWNrID0gZXhwaXJfY2xiOwoJY2xpZW50LT5wcml2ID0gcHJpdjsKCglyZXR1cm4gMDsKfQpFWFBPUlRfU1lNQk9MKGlybG1wX3VwZGF0ZV9jbGllbnQpOwoKLyoKICogRnVuY3Rpb24gaXJsbXBfdW5yZWdpc3Rlcl9jbGllbnQgKGhhbmRsZSkKICoKICogICAgUmV0dXJuczogMCBvbiBzdWNjZXNzLCAtMSBvbiBlcnJvcgogKgogKi8KaW50IGlybG1wX3VucmVnaXN0ZXJfY2xpZW50KHZvaWQgKmhhbmRsZSkKewoJc3RydWN0IGlybG1wX2NsaWVudCAqY2xpZW50OwoKCUlSREFfREVCVUcoNCwgIiVzKClcbiIsIF9fRlVOQ1RJT05fXyk7CgoJaWYgKCFoYW5kbGUpCgkJcmV0dXJuIC0xOwoKCS8qIENhbGxlciBtYXkgY2FsbCB3aXRoIGludmFsaWQgaGFuZGxlIChpdCdzIGxlZ2FsKSAtIEplYW4gSUkgKi8KCWNsaWVudCA9IGhhc2hiaW5fbG9ja19maW5kKGlybG1wLT5jbGllbnRzLCAobG9uZykgaGFuZGxlLCBOVUxMKTsKCWlmICghY2xpZW50KSB7CgkJSVJEQV9ERUJVRygxLCAiJXMoKSwgVW5rbm93biBjbGllbnQhXG4iLCBfX0ZVTkNUSU9OX18pOwoJCXJldHVybiAtMTsKCX0KCglJUkRBX0RFQlVHKDQsICIlcygpLCByZW1vdmluZyBjbGllbnQhXG4iLCBfX0ZVTkNUSU9OX18pOwoJaGFzaGJpbl9yZW1vdmVfdGhpcyhpcmxtcC0+Y2xpZW50cywgKGlyZGFfcXVldWVfdCAqKSBjbGllbnQpOwoJa2ZyZWUoY2xpZW50KTsKCglyZXR1cm4gMDsKfQpFWFBPUlRfU1lNQk9MKGlybG1wX3VucmVnaXN0ZXJfY2xpZW50KTsKCi8qCiAqIEZ1bmN0aW9uIGlybG1wX3Nsc2FwX2ludXNlIChzbHNhcCkKICoKICogICAgQ2hlY2sgaWYgdGhlIGdpdmVuIHNvdXJjZSBMU0FQIHNlbGVjdG9yIGlzIGluIHVzZQogKgogKiBUaGlzIGZ1bmN0aW9uIGlzIGNsZWFybHkgbm90IHZlcnkgZWZmaWNpZW50LiBPbiB0aGUgbWl0aWdhdGluZyBzaWRlLCB0aGUKICogc3RhY2sgbWFrZSBzdXJlIHRoYXQgaW4gOTklIG9mIHRoZSBjYXNlcywgd2UgYXJlIGNhbGxlZCBvbmx5IG9uY2UKICogZm9yIGVhY2ggc29ja2V0IGFsbG9jYXRpb24uIFdlIGNvdWxkIHByb2JhYmx5IGtlZXAgYSBiaXRtYXAKICogb2YgdGhlIGFsbG9jYXRlZCBMU0FQLCBidXQgSSdtIG5vdCBzdXJlIHRoZSBjb21wbGV4aXR5IGlzIHdvcnRoIGl0LgogKiBKZWFuIElJCiAqLwpzdGF0aWMgaW50IGlybG1wX3Nsc2FwX2ludXNlKF9fdTggc2xzYXBfc2VsKQp7CglzdHJ1Y3QgbHNhcF9jYiAqc2VsZjsKCXN0cnVjdCBsYXBfY2IgKmxhcDsKCXVuc2lnbmVkIGxvbmcgZmxhZ3M7CgoJSVJEQV9BU1NFUlQoaXJsbXAgIT0gTlVMTCwgcmV0dXJuIFRSVUU7KTsKCUlSREFfQVNTRVJUKGlybG1wLT5tYWdpYyA9PSBMTVBfTUFHSUMsIHJldHVybiBUUlVFOyk7CglJUkRBX0FTU0VSVChzbHNhcF9zZWwgIT0gTFNBUF9BTlksIHJldHVybiBUUlVFOyk7CgoJSVJEQV9ERUJVRyg0LCAiJXMoKVxuIiwgX19GVU5DVElPTl9fKTsKCiNpZmRlZiBDT05GSUdfSVJEQV9VTFRSQQoJLyogQWNjZXB0IGFsbCBiaW5kaW5ncyB0byB0aGUgY29ubmVjdGlvbmxlc3MgTFNBUCAqLwoJaWYgKHNsc2FwX3NlbCA9PSBMU0FQX0NPTk5MRVNTKQoJCXJldHVybiBGQUxTRTsKI2VuZGlmIC8qIENPTkZJR19JUkRBX1VMVFJBICovCgoJLyogVmFsaWQgdmFsdWVzIGFyZSBiZXR3ZWVuIDAgYW5kIDEyNyAoMHgwLTB4NkYpICovCglpZiAoc2xzYXBfc2VsID4gTFNBUF9NQVgpCgkJcmV0dXJuIFRSVUU7CgoJLyoKCSAqICBDaGVjayBpZiBzbHNhcCBpcyBhbHJlYWR5IGluIHVzZS4gVG8gZG8gdGhpcyB3ZSBoYXZlIHRvIGxvb3Agb3ZlcgoJICogIGV2ZXJ5IElyTEFQIGNvbm5lY3Rpb24gYW5kIGNoZWNrIGV2ZXJ5IExTQVAgYXNzb2NpYXRlZCB3aXRoIGVhY2gKCSAqICB0aGUgY29ubmVjdGlvbi4KCSAqLwoJc3Bpbl9sb2NrX2lycXNhdmVfbmVzdGVkKCZpcmxtcC0+bGlua3MtPmhiX3NwaW5sb2NrLCBmbGFncywKCQkJU0lOR0xFX0RFUFRIX05FU1RJTkcpOwoJbGFwID0gKHN0cnVjdCBsYXBfY2IgKikgaGFzaGJpbl9nZXRfZmlyc3QoaXJsbXAtPmxpbmtzKTsKCXdoaWxlIChsYXAgIT0gTlVMTCkgewoJCUlSREFfQVNTRVJUKGxhcC0+bWFnaWMgPT0gTE1QX0xBUF9NQUdJQywgZ290byBlcnJsYXA7KTsKCgkJLyogQ2FyZWZ1bCBmb3IgcHJpb3JpdHkgaW52ZXJzaW9ucyBoZXJlICEKCQkgKiBpcmxtcC0+bGlua3MgaXMgbmV2ZXIgdGFrZW4gd2hpbGUgYW5vdGhlciBJckRBCgkJICogc3BpbmxvY2sgaXMgaGVsZCwgc28gd2UgYXJlIHNhZmUuIEplYW4gSUkgKi8KCQlzcGluX2xvY2soJmxhcC0+bHNhcHMtPmhiX3NwaW5sb2NrKTsKCgkJLyogRm9yIHRoaXMgSXJMQVAsIGNoZWNrIGFsbCB0aGUgTFNBUHMgKi8KCQlzZWxmID0gKHN0cnVjdCBsc2FwX2NiICopIGhhc2hiaW5fZ2V0X2ZpcnN0KGxhcC0+bHNhcHMpOwoJCXdoaWxlIChzZWxmICE9IE5VTEwpIHsKCQkJSVJEQV9BU1NFUlQoc2VsZi0+bWFnaWMgPT0gTE1QX0xTQVBfTUFHSUMsCgkJCQkgICAgZ290byBlcnJsc2FwOyk7CgoJCQlpZiAoKHNlbGYtPnNsc2FwX3NlbCA9PSBzbHNhcF9zZWwpKSB7CgkJCQlJUkRBX0RFQlVHKDQsICJTb3VyY2UgTFNBUCBzZWxlY3Rvcj0lMDJ4IGluIHVzZVxuIiwKCQkJCQkgICBzZWxmLT5zbHNhcF9zZWwpOwoJCQkJZ290byBlcnJsc2FwOwoJCQl9CgkJCXNlbGYgPSAoc3RydWN0IGxzYXBfY2IqKSBoYXNoYmluX2dldF9uZXh0KGxhcC0+bHNhcHMpOwoJCX0KCQlzcGluX3VubG9jaygmbGFwLT5sc2Fwcy0+aGJfc3BpbmxvY2spOwoKCQkvKiBOZXh0IExBUCAqLwoJCWxhcCA9IChzdHJ1Y3QgbGFwX2NiICopIGhhc2hiaW5fZ2V0X25leHQoaXJsbXAtPmxpbmtzKTsKCX0KCXNwaW5fdW5sb2NrX2lycXJlc3RvcmUoJmlybG1wLT5saW5rcy0+aGJfc3BpbmxvY2ssIGZsYWdzKTsKCgkvKgoJICogU2VydmVyIHNvY2tldHMgYXJlIHR5cGljYWxseSB3YWl0aW5nIGZvciBjb25uZWN0aW9ucyBhbmQKCSAqIHRoZXJlZm9yZSByZXNpZGUgaW4gdGhlIHVuY29ubmVjdGVkIGxpc3QuIFdlIGRvbid0IHdhbnQKCSAqIHRvIGdpdmUgb3V0IHRoZWlyIExTQVBzIGZvciBvYnZpb3VzIHJlYXNvbnMuLi4KCSAqIEplYW4gSUkKCSAqLwoJc3Bpbl9sb2NrX2lycXNhdmUoJmlybG1wLT51bmNvbm5lY3RlZF9sc2Fwcy0+aGJfc3BpbmxvY2ssIGZsYWdzKTsKCglzZWxmID0gKHN0cnVjdCBsc2FwX2NiICopIGhhc2hiaW5fZ2V0X2ZpcnN0KGlybG1wLT51bmNvbm5lY3RlZF9sc2Fwcyk7Cgl3aGlsZSAoc2VsZiAhPSBOVUxMKSB7CgkJSVJEQV9BU1NFUlQoc2VsZi0+bWFnaWMgPT0gTE1QX0xTQVBfTUFHSUMsIGdvdG8gZXJydW5jb247KTsKCQlpZiAoKHNlbGYtPnNsc2FwX3NlbCA9PSBzbHNhcF9zZWwpKSB7CgkJCUlSREFfREVCVUcoNCwgIlNvdXJjZSBMU0FQIHNlbGVjdG9yPSUwMnggaW4gdXNlICh1bmNvbm5lY3RlZClcbiIsCgkJCQkgICBzZWxmLT5zbHNhcF9zZWwpOwoJCQlnb3RvIGVycnVuY29uOwoJCX0KCQlzZWxmID0gKHN0cnVjdCBsc2FwX2NiKikgaGFzaGJpbl9nZXRfbmV4dChpcmxtcC0+dW5jb25uZWN0ZWRfbHNhcHMpOwoJfQoJc3Bpbl91bmxvY2tfaXJxcmVzdG9yZSgmaXJsbXAtPnVuY29ubmVjdGVkX2xzYXBzLT5oYl9zcGlubG9jaywgZmxhZ3MpOwoKCXJldHVybiBGQUxTRTsKCgkvKiBFcnJvciBleGl0IGZyb20gd2l0aGluIG9uZSBvZiB0aGUgdHdvIG5lc3RlZCBsb29wcy4KCSAqIE1ha2Ugc3VyZSB3ZSByZWxlYXNlIHRoZSByaWdodCBzcGlubG9jayBpbiB0aGUgcmlnaCBvcmRlci4KCSAqIEplYW4gSUkgKi8KZXJybHNhcDoKCXNwaW5fdW5sb2NrKCZsYXAtPmxzYXBzLT5oYl9zcGlubG9jayk7CklSREFfQVNTRVJUX0xBQkVMKGVycmxhcDopCglzcGluX3VubG9ja19pcnFyZXN0b3JlKCZpcmxtcC0+bGlua3MtPmhiX3NwaW5sb2NrLCBmbGFncyk7CglyZXR1cm4gVFJVRTsKCgkvKiBFcnJvciBleGl0IGZyb20gd2l0aGluIHRoZSB1bmNvbm5lY3RlZCBsb29wLgoJICogSnVzdCBvbmUgc3BpbmxvY2sgdG8gcmVsZWFzZS4uLiBKZWFuIElJICovCmVycnVuY29uOgoJc3Bpbl91bmxvY2tfaXJxcmVzdG9yZSgmaXJsbXAtPnVuY29ubmVjdGVkX2xzYXBzLT5oYl9zcGlubG9jaywgZmxhZ3MpOwoJcmV0dXJuIFRSVUU7Cn0KCi8qCiAqIEZ1bmN0aW9uIGlybG1wX2ZpbmRfZnJlZV9zbHNhcCAoKQogKgogKiAgICBGaW5kIGEgZnJlZSBzb3VyY2UgTFNBUCB0byB1c2UuIFRoaXMgZnVuY3Rpb24gaXMgY2FsbGVkIGlmIHRoZSBzZXJ2aWNlCiAqICAgIHVzZXIgaGFzIHJlcXVlc3RlZCBhIHNvdXJjZSBMU0FQIGVxdWFsIHRvIExNX0FOWQogKi8Kc3RhdGljIF9fdTggaXJsbXBfZmluZF9mcmVlX3Nsc2FwKHZvaWQpCnsKCV9fdTggbHNhcF9zZWw7CglpbnQgd3JhcHBlZCA9IDA7CgoJSVJEQV9BU1NFUlQoaXJsbXAgIT0gTlVMTCwgcmV0dXJuIC0xOyk7CglJUkRBX0FTU0VSVChpcmxtcC0+bWFnaWMgPT0gTE1QX01BR0lDLCByZXR1cm4gLTE7KTsKCgkvKiBNb3N0IHVzZXJzIGRvbid0IHJlYWxseSBjYXJlIHdoaWNoIExTQVBzIHRoZXkgYXJlIGdpdmVuLAoJICogYW5kIHRoZXJlZm9yZSB3ZSBhdXRvbWF0aWNhbGx5IGdpdmUgdGhlbSBhIGZyZWUgTFNBUC4KCSAqIFRoaXMgZnVuY3Rpb24gdHJ5IHRvIGZpbmQgYSBzdWl0YWJsZSBMU0FQLCBpLmUuIHdoaWNoIGlzCgkgKiBub3QgaW4gdXNlIGFuZCBpcyB3aXRoaW4gdGhlIGFjY2VwdGFibGUgcmFuZ2UuIEplYW4gSUkgKi8KCglkbyB7CgkJLyogQWx3YXlzIGluY3JlbWVudCB0byBMU0FQIG51bWJlciBiZWZvcmUgdXNpbmcgaXQuCgkJICogSW4gdGhlb3J5LCB3ZSBjb3VsZCByZXVzZSB0aGUgbGFzdCBMU0FQIG51bWJlciwgYXMgbG9uZwoJCSAqIGFzIGl0IGlzIG5vIGxvbmdlciBpbiB1c2UuIFNvbWUgSXJEQSBzdGFjayBkbyB0aGF0LgoJCSAqIEhvd2V2ZXIsIHRoZSBwcmV2aW91cyBzb2NrZXQgbWF5IGJlIGhhbGYgY2xvc2VkLCBpLmUuCgkJICogd2UgY2xvc2VkIGl0LCB3ZSB0aGluayBpdCdzIG5vIGxvbmdlciBpbiB1c2UsIGJ1dCB0aGUKCQkgKiBvdGhlciBzaWRlIGRpZCBub3QgcmVjZWl2ZSBvdXIgY2xvc2UgYW5kIHRoaW5rIGl0J3MKCQkgKiBhY3RpdmUgYW5kIHN0aWxsIHNlbmQgZGF0YSBvbiBpdC4KCQkgKiBUaGlzIGlzIHNpbWlsYXIgdG8gd2hhdCBpcyBkb25lIHdpdGggUElEcyBhbmQgVENQIHBvcnRzLgoJCSAqIEFsc28sIHRoaXMgcmVkdWNlIHRoZSBudW1iZXIgb2YgY2FsbHMgdG8gaXJsbXBfc2xzYXBfaW51c2UoKQoJCSAqIHdoaWNoIGlzIGFuIGV4cGVuc2l2ZSBmdW5jdGlvbiB0byBjYWxsLgoJCSAqIEplYW4gSUkgKi8KCQlpcmxtcC0+bGFzdF9sc2FwX3NlbCsrOwoKCQkvKiBDaGVjayBpZiB3ZSBuZWVkIHRvIHdyYXBhcm91bmQgKDB4NzAtMHg3ZiBhcmUgcmVzZXJ2ZWQpICovCgkJaWYgKGlybG1wLT5sYXN0X2xzYXBfc2VsID4gTFNBUF9NQVgpIHsKCQkJLyogMHgwMC0weDEwIGFyZSBhbHNvIHJlc2VydmVkIGZvciB3ZWxsIGtub3cgcG9ydHMgKi8KCQkJaXJsbXAtPmxhc3RfbHNhcF9zZWwgPSAweDEwOwoKCQkJLyogTWFrZSBzdXJlIHdlIHRlcm1pbmF0ZSB0aGUgbG9vcCAqLwoJCQlpZiAod3JhcHBlZCsrKSB7CgkJCQlJUkRBX0VSUk9SKCIlczogbm8gbW9yZSBmcmVlIExTQVBzICFcbiIsCgkJCQkJICAgX19GVU5DVElPTl9fKTsKCQkJCXJldHVybiAwOwoJCQl9CgkJfQoKCQkvKiBJZiB0aGUgTFNBUCBpcyBpbiB1c2UsIHRyeSB0aGUgbmV4dCBvbmUuCgkJICogRGVzcGl0ZSB0aGUgYXV0b2luY3JlbWVudCwgd2UgbmVlZCB0byBjaGVjayBpZiB0aGUgbHNhcAoJCSAqIGlzIHJlYWxseSBpbiB1c2Ugb3Igbm90LCBmaXJzdCBiZWNhdXNlIExTQVAgbWF5IGJlCgkJICogZGlyZWN0bHkgYWxsb2NhdGVkIGluIGlybG1wX29wZW5fbHNhcCgpLCBhbmQgYWxzbyBiZWNhdXNlCgkJICogd2UgbWF5IHdyYXBhcm91bmQgb24gb2xkIHNvY2tldHMuIEplYW4gSUkgKi8KCX0gd2hpbGUgKGlybG1wX3Nsc2FwX2ludXNlKGlybG1wLT5sYXN0X2xzYXBfc2VsKSk7CgoJLyogR290IGl0ICEgKi8KCWxzYXBfc2VsID0gaXJsbXAtPmxhc3RfbHNhcF9zZWw7CglJUkRBX0RFQlVHKDQsICIlcygpLCBmb3VuZCBmcmVlIGxzYXBfc2VsPSUwMnhcbiIsCgkJICAgX19GVU5DVElPTl9fLCBsc2FwX3NlbCk7CgoJcmV0dXJuIGxzYXBfc2VsOwp9CgovKgogKiBGdW5jdGlvbiBpcmxtcF9jb252ZXJ0X2xhcF9yZWFzb24gKGxhcF9yZWFzb24pCiAqCiAqICAgIENvbnZlcnRzIElyTEFQIGRpc2Nvbm5lY3QgcmVhc29uIGNvZGVzIHRvIElyTE1QIGRpc2Nvbm5lY3QgcmVhc29uCiAqICAgIGNvZGVzCiAqCiAqLwpMTV9SRUFTT04gaXJsbXBfY29udmVydF9sYXBfcmVhc29uKCBMQVBfUkVBU09OIGxhcF9yZWFzb24pCnsKCWludCByZWFzb24gPSBMTV9MQVBfRElTQ09OTkVDVDsKCglzd2l0Y2ggKGxhcF9yZWFzb24pIHsKCWNhc2UgTEFQX0RJU0NfSU5ESUNBVElPTjogLyogUmVjZWl2ZWQgYSBkaXNjb25uZWN0IHJlcXVlc3QgZnJvbSBwZWVyICovCgkJSVJEQV9ERUJVRyggMSwgIiVzKCksIExBUF9ESVNDX0lORElDQVRJT05cbiIsIF9fRlVOQ1RJT05fXyk7CgkJcmVhc29uID0gTE1fVVNFUl9SRVFVRVNUOwoJCWJyZWFrOwoJY2FzZSBMQVBfTk9fUkVTUE9OU0U6ICAgIC8qIFRvIG1hbnkgcmV0cmFuc21pdHMgd2l0aG91dCByZXNwb25zZSAqLwoJCUlSREFfREVCVUcoIDEsICIlcygpLCBMQVBfTk9fUkVTUE9OU0VcbiIsIF9fRlVOQ1RJT05fXyk7CgkJcmVhc29uID0gTE1fTEFQX0RJU0NPTk5FQ1Q7CgkJYnJlYWs7CgljYXNlIExBUF9SRVNFVF9JTkRJQ0FUSU9OOgoJCUlSREFfREVCVUcoIDEsICIlcygpLCBMQVBfUkVTRVRfSU5ESUNBVElPTlxuIiwgX19GVU5DVElPTl9fKTsKCQlyZWFzb24gPSBMTV9MQVBfUkVTRVQ7CgkJYnJlYWs7CgljYXNlIExBUF9GT1VORF9OT05FOgoJY2FzZSBMQVBfTUVESUFfQlVTWToKCWNhc2UgTEFQX1BSSU1BUllfQ09ORkxJQ1Q6CgkJSVJEQV9ERUJVRygxLCAiJXMoKSwgTEFQX0ZPVU5EX05PTkUsIExBUF9NRURJQV9CVVNZIG9yIExBUF9QUklNQVJZX0NPTkZMSUNUXG4iLCBfX0ZVTkNUSU9OX18pOwoJCXJlYXNvbiA9IExNX0NPTk5FQ1RfRkFJTFVSRTsKCQlicmVhazsKCWRlZmF1bHQ6CgkJSVJEQV9ERUJVRygxLCAiJXMoKSwgVW5rbm93IElyTEFQIGRpc2Nvbm5lY3QgcmVhc29uICVkIVxuIiwKCQkJICAgX19GVU5DVElPTl9fLCBsYXBfcmVhc29uKTsKCQlyZWFzb24gPSBMTV9MQVBfRElTQ09OTkVDVDsKCQlicmVhazsKCX0KCglyZXR1cm4gcmVhc29uOwp9CgojaWZkZWYgQ09ORklHX1BST0NfRlMKCnN0cnVjdCBpcmxtcF9pdGVyX3N0YXRlIHsKCWhhc2hiaW5fdCAqaGFzaGJpbjsKfTsKCiNkZWZpbmUgTFNBUF9TVEFSVF9UT0tFTgkoKHZvaWQgKikxKQojZGVmaW5lIExJTktfU1RBUlRfVE9LRU4JKCh2b2lkICopMikKCnN0YXRpYyB2b2lkICppcmxtcF9zZXFfaGJfaWR4KHN0cnVjdCBpcmxtcF9pdGVyX3N0YXRlICppdGVyLCBsb2ZmX3QgKm9mZikKewoJdm9pZCAqZWxlbWVudDsKCglzcGluX2xvY2tfaXJxKCZpdGVyLT5oYXNoYmluLT5oYl9zcGlubG9jayk7Cglmb3IgKGVsZW1lbnQgPSBoYXNoYmluX2dldF9maXJzdChpdGVyLT5oYXNoYmluKTsKCSAgICAgZWxlbWVudCAhPSBOVUxMOyAKCSAgICAgZWxlbWVudCA9IGhhc2hiaW5fZ2V0X25leHQoaXRlci0+aGFzaGJpbikpIHsKCQlpZiAoIW9mZiB8fCAqb2ZmLS0gPT0gMCkgewoJCQkvKiBOQjogaGFzaGJpbiBsZWZ0IGxvY2tlZCAqLwoJCQlyZXR1cm4gZWxlbWVudDsKCQl9Cgl9CglzcGluX3VubG9ja19pcnEoJml0ZXItPmhhc2hiaW4tPmhiX3NwaW5sb2NrKTsKCWl0ZXItPmhhc2hiaW4gPSBOVUxMOwoJcmV0dXJuIE5VTEw7Cn0KCgpzdGF0aWMgdm9pZCAqaXJsbXBfc2VxX3N0YXJ0KHN0cnVjdCBzZXFfZmlsZSAqc2VxLCBsb2ZmX3QgKnBvcykKewoJc3RydWN0IGlybG1wX2l0ZXJfc3RhdGUgKml0ZXIgPSBzZXEtPnByaXZhdGU7Cgl2b2lkICp2OwoJbG9mZl90IG9mZiA9ICpwb3M7CgoJaXRlci0+aGFzaGJpbiA9IE5VTEw7CglpZiAob2ZmLS0gPT0gMCkKCQlyZXR1cm4gTFNBUF9TVEFSVF9UT0tFTjsKCglpdGVyLT5oYXNoYmluID0gaXJsbXAtPnVuY29ubmVjdGVkX2xzYXBzOwoJdiA9IGlybG1wX3NlcV9oYl9pZHgoaXRlciwgJm9mZik7CglpZiAodikKCQlyZXR1cm4gdjsKCglpZiAob2ZmLS0gPT0gMCkKCQlyZXR1cm4gTElOS19TVEFSVF9UT0tFTjsKCglpdGVyLT5oYXNoYmluID0gaXJsbXAtPmxpbmtzOwoJcmV0dXJuIGlybG1wX3NlcV9oYl9pZHgoaXRlciwgJm9mZik7Cn0KCnN0YXRpYyB2b2lkICppcmxtcF9zZXFfbmV4dChzdHJ1Y3Qgc2VxX2ZpbGUgKnNlcSwgdm9pZCAqdiwgbG9mZl90ICpwb3MpCnsKCXN0cnVjdCBpcmxtcF9pdGVyX3N0YXRlICppdGVyID0gc2VxLT5wcml2YXRlOwoKCSsrKnBvczsKCglpZiAodiA9PSBMU0FQX1NUQVJUX1RPS0VOKSB7CQkvKiBzdGFydCBvZiBsaXN0IG9mIGxzYXBzICovCgkJaXRlci0+aGFzaGJpbiA9IGlybG1wLT51bmNvbm5lY3RlZF9sc2FwczsKCQl2ID0gaXJsbXBfc2VxX2hiX2lkeChpdGVyLCBOVUxMKTsKCQlyZXR1cm4gdiA/IHYgOiBMSU5LX1NUQVJUX1RPS0VOOwoJfQoKCWlmICh2ID09IExJTktfU1RBUlRfVE9LRU4pIHsJCS8qIHN0YXJ0IG9mIGxpc3Qgb2YgbGlua3MgKi8KCQlpdGVyLT5oYXNoYmluID0gaXJsbXAtPmxpbmtzOwoJCXJldHVybiBpcmxtcF9zZXFfaGJfaWR4KGl0ZXIsIE5VTEwpOwoJfQoKCXYgPSBoYXNoYmluX2dldF9uZXh0KGl0ZXItPmhhc2hiaW4pOwoKCWlmICh2ID09IE5VTEwpIHsJCQkvKiBubyBtb3JlIGluIHRoaXMgaGFzaCBiaW4gKi8KCQlzcGluX3VubG9ja19pcnEoJml0ZXItPmhhc2hiaW4tPmhiX3NwaW5sb2NrKTsKCgkJaWYgKGl0ZXItPmhhc2hiaW4gPT0gaXJsbXAtPnVuY29ubmVjdGVkX2xzYXBzKSAKCQkJdiA9ICBMSU5LX1NUQVJUX1RPS0VOOwoKCQlpdGVyLT5oYXNoYmluID0gTlVMTDsKCX0KCXJldHVybiB2Owp9CgpzdGF0aWMgdm9pZCBpcmxtcF9zZXFfc3RvcChzdHJ1Y3Qgc2VxX2ZpbGUgKnNlcSwgdm9pZCAqdikKewoJc3RydWN0IGlybG1wX2l0ZXJfc3RhdGUgKml0ZXIgPSBzZXEtPnByaXZhdGU7CgoJaWYgKGl0ZXItPmhhc2hiaW4pCgkJc3Bpbl91bmxvY2tfaXJxKCZpdGVyLT5oYXNoYmluLT5oYl9zcGlubG9jayk7Cn0KCnN0YXRpYyBpbnQgaXJsbXBfc2VxX3Nob3coc3RydWN0IHNlcV9maWxlICpzZXEsIHZvaWQgKnYpCnsKCWNvbnN0IHN0cnVjdCBpcmxtcF9pdGVyX3N0YXRlICppdGVyID0gc2VxLT5wcml2YXRlOwoJc3RydWN0IGxzYXBfY2IgKnNlbGYgPSB2OwoKCWlmICh2ID09IExTQVBfU1RBUlRfVE9LRU4pCgkJc2VxX3B1dHMoc2VxLCAiVW5jb25uZWN0ZWQgTFNBUHM6XG4iKTsKCWVsc2UgaWYgKHYgPT0gTElOS19TVEFSVF9UT0tFTikKCQlzZXFfcHV0cyhzZXEsICJcblJlZ2lzdGVyZWQgTGluayBMYXllcnM6XG4iKTsKCWVsc2UgaWYgKGl0ZXItPmhhc2hiaW4gPT0gaXJsbXAtPnVuY29ubmVjdGVkX2xzYXBzKSB7CgkJc2VsZiA9IHY7CgkJSVJEQV9BU1NFUlQoc2VsZi0+bWFnaWMgPT0gTE1QX0xTQVBfTUFHSUMsIHJldHVybiAtRUlOVkFMOyApOwoJCXNlcV9wcmludGYoc2VxLCAibHNhcCBzdGF0ZTogJXMsICIsCgkJCSAgIGlybHNhcF9zdGF0ZVsgc2VsZi0+bHNhcF9zdGF0ZV0pOwoJCXNlcV9wcmludGYoc2VxLAoJCQkgICAic2xzYXBfc2VsOiAlIzAyeCwgZGxzYXBfc2VsOiAlIzAyeCwgIiwKCQkJICAgc2VsZi0+c2xzYXBfc2VsLCBzZWxmLT5kbHNhcF9zZWwpOwoJCXNlcV9wcmludGYoc2VxLCAiKCVzKSIsIHNlbGYtPm5vdGlmeS5uYW1lKTsKCQlzZXFfcHJpbnRmKHNlcSwgIlxuIik7Cgl9IGVsc2UgaWYgKGl0ZXItPmhhc2hiaW4gPT0gaXJsbXAtPmxpbmtzKSB7CgkJc3RydWN0IGxhcF9jYiAqbGFwID0gdjsKCgkJc2VxX3ByaW50ZihzZXEsICJsYXAgc3RhdGU6ICVzLCAiLAoJCQkgICBpcmxtcF9zdGF0ZVtsYXAtPmxhcF9zdGF0ZV0pOwoKCQlzZXFfcHJpbnRmKHNlcSwgInNhZGRyOiAlIzA4eCwgZGFkZHI6ICUjMDh4LCAiLAoJCQkgICBsYXAtPnNhZGRyLCBsYXAtPmRhZGRyKTsKCQlzZXFfcHJpbnRmKHNlcSwgIm51bSBsc2FwczogJWQiLAoJCQkgICBIQVNIQklOX0dFVF9TSVpFKGxhcC0+bHNhcHMpKTsKCQlzZXFfcHJpbnRmKHNlcSwgIlxuIik7CgoJCS8qIENhcmVmdWwgZm9yIHByaW9yaXR5IGludmVyc2lvbnMgaGVyZSAhCgkJICogQWxsIG90aGVyIHVzZXMgb2YgYXR0cmliIHNwaW5sb2NrIGFyZSBpbmRlcGVuZGVudCBvZgoJCSAqIHRoZSBvYmplY3Qgc3BpbmxvY2ssIHNvIHdlIGFyZSBzYWZlLiBKZWFuIElJICovCgkJc3Bpbl9sb2NrKCZsYXAtPmxzYXBzLT5oYl9zcGlubG9jayk7CgoJCXNlcV9wcmludGYoc2VxLCAiXG4gIENvbm5lY3RlZCBMU0FQczpcbiIpOwoJCWZvciAoc2VsZiA9IChzdHJ1Y3QgbHNhcF9jYiAqKSBoYXNoYmluX2dldF9maXJzdChsYXAtPmxzYXBzKTsKCQkgICAgIHNlbGYgIT0gTlVMTDsKCQkgICAgIHNlbGYgPSAoc3RydWN0IGxzYXBfY2IgKiloYXNoYmluX2dldF9uZXh0KGxhcC0+bHNhcHMpKSB7CgkJCUlSREFfQVNTRVJUKHNlbGYtPm1hZ2ljID09IExNUF9MU0FQX01BR0lDLAoJCQkJICAgIGdvdG8gb3V0bG9vcDspOwoJCQlzZXFfcHJpbnRmKHNlcSwgIiAgbHNhcCBzdGF0ZTogJXMsICIsCgkJCQkgICBpcmxzYXBfc3RhdGVbIHNlbGYtPmxzYXBfc3RhdGVdKTsKCQkJc2VxX3ByaW50ZihzZXEsCgkJCQkgICAic2xzYXBfc2VsOiAlIzAyeCwgZGxzYXBfc2VsOiAlIzAyeCwgIiwKCQkJCSAgIHNlbGYtPnNsc2FwX3NlbCwgc2VsZi0+ZGxzYXBfc2VsKTsKCQkJc2VxX3ByaW50ZihzZXEsICIoJXMpIiwgc2VsZi0+bm90aWZ5Lm5hbWUpOwoJCQlzZXFfcHV0YyhzZXEsICdcbicpOwoKCQl9CglJUkRBX0FTU0VSVF9MQUJFTChvdXRsb29wOikKCQlzcGluX3VubG9jaygmbGFwLT5sc2Fwcy0+aGJfc3BpbmxvY2spOwoJCXNlcV9wdXRjKHNlcSwgJ1xuJyk7Cgl9IGVsc2UKCQlyZXR1cm4gLUVJTlZBTDsKCglyZXR1cm4gMDsKfQoKc3RhdGljIHN0cnVjdCBzZXFfb3BlcmF0aW9ucyBpcmxtcF9zZXFfb3BzID0gewoJLnN0YXJ0ICA9IGlybG1wX3NlcV9zdGFydCwKCS5uZXh0ICAgPSBpcmxtcF9zZXFfbmV4dCwKCS5zdG9wICAgPSBpcmxtcF9zZXFfc3RvcCwKCS5zaG93ICAgPSBpcmxtcF9zZXFfc2hvdywKfTsKCnN0YXRpYyBpbnQgaXJsbXBfc2VxX29wZW4oc3RydWN0IGlub2RlICppbm9kZSwgc3RydWN0IGZpbGUgKmZpbGUpCnsKCXN0cnVjdCBzZXFfZmlsZSAqc2VxOwoJaW50IHJjID0gLUVOT01FTTsKCXN0cnVjdCBpcmxtcF9pdGVyX3N0YXRlICpzOwoKCUlSREFfQVNTRVJUKGlybG1wICE9IE5VTEwsIHJldHVybiAtRUlOVkFMOyk7CgoJcyA9IGttYWxsb2Moc2l6ZW9mKCpzKSwgR0ZQX0tFUk5FTCk7CglpZiAoIXMpCgkJZ290byBvdXQ7CgoJcmMgPSBzZXFfb3BlbihmaWxlLCAmaXJsbXBfc2VxX29wcyk7CglpZiAocmMpCgkJZ290byBvdXRfa2ZyZWU7CgoJc2VxCSAgICAgPSBmaWxlLT5wcml2YXRlX2RhdGE7CglzZXEtPnByaXZhdGUgPSBzOwpvdXQ6CglyZXR1cm4gcmM7Cm91dF9rZnJlZToKCWtmcmVlKHMpOwoJZ290byBvdXQ7Cn0KCnN0cnVjdCBmaWxlX29wZXJhdGlvbnMgaXJsbXBfc2VxX2ZvcHMgPSB7Cgkub3duZXIJCT0gVEhJU19NT0RVTEUsCgkub3BlbiAgICAgICAgICAgPSBpcmxtcF9zZXFfb3BlbiwKCS5yZWFkICAgICAgICAgICA9IHNlcV9yZWFkLAoJLmxsc2VlayAgICAgICAgID0gc2VxX2xzZWVrLAoJLnJlbGVhc2UJPSBzZXFfcmVsZWFzZV9wcml2YXRlLAp9OwoKI2VuZGlmIC8qIFBST0NfRlMgKi8K