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+dW5jb25uZWN0ZWRfbHNhcHMtPmhiX3NwaW5sb2NrLAoJCQkJICAgICAgIGZsYWdzKTsKCQlyZXR1cm4gTlVMTDsKCX0KCgkvKiBBbGxvY2F0ZSBhIG5ldyBpbnN0YW5jZSAqLwoJbmV3ID0ga21lbWR1cChvcmlnLCBzaXplb2YoKm5ldyksIEdGUF9BVE9NSUMpOwoJaWYgKCFuZXcpICB7CgkJSVJEQV9ERUJVRygwLCAiJXMoKSwgdW5hYmxlIHRvIGttYWxsb2NcbiIsIF9fRlVOQ1RJT05fXyk7CgkJc3Bpbl91bmxvY2tfaXJxcmVzdG9yZSgmaXJsbXAtPnVuY29ubmVjdGVkX2xzYXBzLT5oYl9zcGlubG9jaywKCQkJCSAgICAgICBmbGFncyk7CgkJcmV0dXJuIE5VTEw7Cgl9CgkvKiBuZXctPmxhcCA9IG9yaWctPmxhcDsgPT4gZG9uZSBpbiB0aGUgbWVtY3B5KCkgKi8KCS8qIG5ldy0+c2xzYXBfc2VsID0gb3JpZy0+c2xzYXBfc2VsOyA9PiBkb25lIGluIHRoZSBtZW1jcHkoKSAqLwoJbmV3LT5jb25uX3NrYiA9IE5VTEw7CgoJc3Bpbl91bmxvY2tfaXJxcmVzdG9yZSgmaXJsbXAtPnVuY29ubmVjdGVkX2xzYXBzLT5oYl9zcGlubG9jaywgZmxhZ3MpOwoKCS8qIE5vdCBldmVyeXRoaW5nIGlzIHRoZSBzYW1lICovCgluZXctPm5vdGlmeS5pbnN0YW5jZSA9IGluc3RhbmNlOwoKCWluaXRfdGltZXIoJm5ldy0+d2F0Y2hkb2dfdGltZXIpOwoKCWhhc2hiaW5faW5zZXJ0KGlybG1wLT51bmNvbm5lY3RlZF9sc2FwcywgKGlyZGFfcXVldWVfdCAqKSBuZXcsCgkJICAgICAgIChsb25nKSBuZXcsIE5VTEwpOwoKI2lmZGVmIENPTkZJR19JUkRBX0NBQ0hFX0xBU1RfTFNBUAoJLyogTWFrZSBzdXJlIHRoYXQgd2UgaW52YWxpZGF0ZSB0aGUgTFNBUCBjYWNoZSAqLwoJbmV3LT5sYXAtPmNhY2hlLnZhbGlkID0gRkFMU0U7CiNlbmRpZiAvKiBDT05GSUdfSVJEQV9DQUNIRV9MQVNUX0xTQVAgKi8KCglyZXR1cm4gbmV3Owp9CgovKgogKiBGdW5jdGlvbiBpcmxtcF9kaXNjb25uZWN0X3JlcXVlc3QgKGhhbmRsZSwgdXNlcmRhdGEpCiAqCiAqICAgIFRoZSBzZXJ2aWNlIHVzZXIgaXMgcmVxdWVzdGluZyBkaXNjb25uZWN0aW9uLCB0aGlzIHdpbGwgbm90IHJlbW92ZSB0aGUKICogICAgTFNBUCwgYnV0IG9ubHkgbWFyayBpdCBhcyBkaXNjb25uZWN0ZWQKICovCmludCBpcmxtcF9kaXNjb25uZWN0X3JlcXVlc3Qoc3RydWN0IGxzYXBfY2IgKnNlbGYsIHN0cnVjdCBza19idWZmICp1c2VyZGF0YSkKewoJc3RydWN0IGxzYXBfY2IgKmxzYXA7CgoJSVJEQV9BU1NFUlQoc2VsZiAhPSBOVUxMLCByZXR1cm4gLTE7KTsKCUlSREFfQVNTRVJUKHNlbGYtPm1hZ2ljID09IExNUF9MU0FQX01BR0lDLCByZXR1cm4gLTE7KTsKCUlSREFfQVNTRVJUKHVzZXJkYXRhICE9IE5VTEwsIHJldHVybiAtMTspOwoKCS8qIEFscmVhZHkgZGlzY29ubmVjdGVkID8KCSAqIFRoZXJlIGlzIGEgcmFjZSBjb25kaXRpb24gYmV0d2VlbiBpcmxtcF9kaXNjb25uZWN0X2luZGljYXRpb24oKQoJICogYW5kIHVzIHRoYXQgbWlnaHQgbWVzcyB1cCB0aGUgaGFzaGJpbnMgYmVsb3cuIFRoaXMgZml4ZXMgaXQuCgkgKiBKZWFuIElJICovCglpZiAoISB0ZXN0X2FuZF9jbGVhcl9iaXQoMCwgJnNlbGYtPmNvbm5lY3RlZCkpIHsKCQlJUkRBX0RFQlVHKDAsICIlcygpLCBhbHJlYWR5IGRpc2Nvbm5lY3RlZCFcbiIsIF9fRlVOQ1RJT05fXyk7CgkJZGV2X2tmcmVlX3NrYih1c2VyZGF0YSk7CgkJcmV0dXJuIC0xOwoJfQoKCXNrYl9wdXNoKHVzZXJkYXRhLCBMTVBfQ09OVFJPTF9IRUFERVIpOwoKCS8qCgkgKiAgRG8gdGhlIGV2ZW50IGJlZm9yZSB0aGUgb3RoZXIgc3R1ZmYgc2luY2Ugd2UgbXVzdCBrbm93CgkgKiAgd2hpY2ggbGFwIGxheWVyIHRoYXQgdGhlIGZyYW1lIHNob3VsZCBiZSB0cmFuc21pdHRlZCBvbgoJICovCglpcmxtcF9kb19sc2FwX2V2ZW50KHNlbGYsIExNX0RJU0NPTk5FQ1RfUkVRVUVTVCwgdXNlcmRhdGEpOwoKCS8qIERyb3AgcmVmZXJlbmNlIGNvdW50IC0gc2VlIGlybGFwX2RhdGFfcmVxdWVzdCgpLiAqLwoJZGV2X2tmcmVlX3NrYih1c2VyZGF0YSk7CgoJLyoKCSAqICBSZW1vdmUgTFNBUCBmcm9tIGxpc3Qgb2YgY29ubmVjdGVkIExTQVBzIGZvciB0aGUgcGFydGljdWxhciBsaW5rCgkgKiAgYW5kIGluc2VydCBpdCBpbnRvIHRoZSBsaXN0IG9mIHVuY29ubmVjdGVkIExTQVBzCgkgKi8KCUlSREFfQVNTRVJUKHNlbGYtPmxhcCAhPSBOVUxMLCByZXR1cm4gLTE7KTsKCUlSREFfQVNTRVJUKHNlbGYtPmxhcC0+bWFnaWMgPT0gTE1QX0xBUF9NQUdJQywgcmV0dXJuIC0xOyk7CglJUkRBX0FTU0VSVChzZWxmLT5sYXAtPmxzYXBzICE9IE5VTEwsIHJldHVybiAtMTspOwoKCWxzYXAgPSBoYXNoYmluX3JlbW92ZShzZWxmLT5sYXAtPmxzYXBzLCAobG9uZykgc2VsZiwgTlVMTCk7CiNpZmRlZiBDT05GSUdfSVJEQV9DQUNIRV9MQVNUX0xTQVAKCXNlbGYtPmxhcC0+Y2FjaGUudmFsaWQgPSBGQUxTRTsKI2VuZGlmCgoJSVJEQV9BU1NFUlQobHNhcCAhPSBOVUxMLCByZXR1cm4gLTE7KTsKCUlSREFfQVNTRVJUKGxzYXAtPm1hZ2ljID09IExNUF9MU0FQX01BR0lDLCByZXR1cm4gLTE7KTsKCUlSREFfQVNTRVJUKGxzYXAgPT0gc2VsZiwgcmV0dXJuIC0xOyk7CgoJaGFzaGJpbl9pbnNlcnQoaXJsbXAtPnVuY29ubmVjdGVkX2xzYXBzLCAoaXJkYV9xdWV1ZV90ICopIHNlbGYsCgkJICAgICAgIChsb25nKSBzZWxmLCBOVUxMKTsKCgkvKiBSZXNldCBzb21lIHZhbHVlcyAqLwoJc2VsZi0+ZGxzYXBfc2VsID0gTFNBUF9BTlk7CglzZWxmLT5sYXAgPSBOVUxMOwoKCXJldHVybiAwOwp9CkVYUE9SVF9TWU1CT0woaXJsbXBfZGlzY29ubmVjdF9yZXF1ZXN0KTsKCi8qCiAqIEZ1bmN0aW9uIGlybG1wX2Rpc2Nvbm5lY3RfaW5kaWNhdGlvbiAocmVhc29uLCB1c2VyZGF0YSkKICoKICogICAgTFNBUCBpcyBiZWluZyBjbG9zZWQhCiAqLwp2b2lkIGlybG1wX2Rpc2Nvbm5lY3RfaW5kaWNhdGlvbihzdHJ1Y3QgbHNhcF9jYiAqc2VsZiwgTE1fUkVBU09OIHJlYXNvbiwKCQkJCSBzdHJ1Y3Qgc2tfYnVmZiAqc2tiKQp7CglzdHJ1Y3QgbHNhcF9jYiAqbHNhcDsKCglJUkRBX0RFQlVHKDEsICIlcygpLCByZWFzb249JXNcbiIsIF9fRlVOQ1RJT05fXywgaXJsbXBfcmVhc29uc1tyZWFzb25dKTsKCUlSREFfQVNTRVJUKHNlbGYgIT0gTlVMTCwgcmV0dXJuOyk7CglJUkRBX0FTU0VSVChzZWxmLT5tYWdpYyA9PSBMTVBfTFNBUF9NQUdJQywgcmV0dXJuOyk7CgoJSVJEQV9ERUJVRygzLCAiJXMoKSwgc2xzYXBfc2VsPSUwMngsIGRsc2FwX3NlbD0lMDJ4XG4iLAoJCSAgIF9fRlVOQ1RJT05fXywgc2VsZi0+c2xzYXBfc2VsLCBzZWxmLT5kbHNhcF9zZWwpOwoKCS8qIEFscmVhZHkgZGlzY29ubmVjdGVkID8KCSAqIFRoZXJlIGlzIGEgcmFjZSBjb25kaXRpb24gYmV0d2VlbiBpcmxtcF9kaXNjb25uZWN0X3JlcXVlc3QoKQoJICogYW5kIHVzIHRoYXQgbWlnaHQgbWVzcyB1cCB0aGUgaGFzaGJpbnMgYmVsb3cuIFRoaXMgZml4ZXMgaXQuCgkgKiBKZWFuIElJICovCglpZiAoISB0ZXN0X2FuZF9jbGVhcl9iaXQoMCwgJnNlbGYtPmNvbm5lY3RlZCkpIHsKCQlJUkRBX0RFQlVHKDAsICIlcygpLCBhbHJlYWR5IGRpc2Nvbm5lY3RlZCFcbiIsIF9fRlVOQ1RJT05fXyk7CgkJcmV0dXJuOwoJfQoKCS8qCgkgKiAgUmVtb3ZlIGFzc29jaWF0aW9uIGJldHdlZW4gdGhpcyBMU0FQIGFuZCB0aGUgbGluayBpdCB1c2VkCgkgKi8KCUlSREFfQVNTRVJUKHNlbGYtPmxhcCAhPSBOVUxMLCByZXR1cm47KTsKCUlSREFfQVNTRVJUKHNlbGYtPmxhcC0+bHNhcHMgIT0gTlVMTCwgcmV0dXJuOyk7CgoJbHNhcCA9IGhhc2hiaW5fcmVtb3ZlKHNlbGYtPmxhcC0+bHNhcHMsIChsb25nKSBzZWxmLCBOVUxMKTsKI2lmZGVmIENPTkZJR19JUkRBX0NBQ0hFX0xBU1RfTFNBUAoJc2VsZi0+bGFwLT5jYWNoZS52YWxpZCA9IEZBTFNFOwojZW5kaWYKCglJUkRBX0FTU0VSVChsc2FwICE9IE5VTEwsIHJldHVybjspOwoJSVJEQV9BU1NFUlQobHNhcCA9PSBzZWxmLCByZXR1cm47KTsKCWhhc2hiaW5faW5zZXJ0KGlybG1wLT51bmNvbm5lY3RlZF9sc2FwcywgKGlyZGFfcXVldWVfdCAqKSBsc2FwLAoJCSAgICAgICAobG9uZykgbHNhcCwgTlVMTCk7CgoJc2VsZi0+ZGxzYXBfc2VsID0gTFNBUF9BTlk7CglzZWxmLT5sYXAgPSBOVUxMOwoKCS8qCgkgKiAgSW5mb3JtIHNlcnZpY2UgdXNlcgoJICovCglpZiAoc2VsZi0+bm90aWZ5LmRpc2Nvbm5lY3RfaW5kaWNhdGlvbikgewoJCS8qIERvbid0IGZvcmdldCB0byByZWZjb3VudCBpdCAtIHNlZSBpcmxhcF9kcml2ZXJfcmN2KCkuICovCgkJaWYoc2tiKQoJCQlza2JfZ2V0KHNrYik7CgkJc2VsZi0+bm90aWZ5LmRpc2Nvbm5lY3RfaW5kaWNhdGlvbihzZWxmLT5ub3RpZnkuaW5zdGFuY2UsCgkJCQkJCSAgIHNlbGYsIHJlYXNvbiwgc2tiKTsKCX0gZWxzZSB7CgkJSVJEQV9ERUJVRygwLCAiJXMoKSwgbm8gaGFuZGxlclxuIiwgX19GVU5DVElPTl9fKTsKCX0KfQoKLyoKICogRnVuY3Rpb24gaXJsbXBfZG9fZXhwaXJ5ICh2b2lkKQogKgogKiAgICBEbyBhIGNsZWFudXAgb2YgdGhlIGRpc2NvdmVyeSBsb2cgKHJlbW92ZSBvbGQgZW50cmllcykKICoKICogTm90ZSA6IHNlcGFyYXRlIGZyb20gaXJsbXBfZG9fZGlzY292ZXJ5KCkgc28gdGhhdCB3ZSBjYW4gaGFuZGxlCiAqIHBhc3NpdmUgZGlzY292ZXJ5IHByb3Blcmx5LgogKi8Kdm9pZCBpcmxtcF9kb19leHBpcnkodm9pZCkKewoJc3RydWN0IGxhcF9jYiAqbGFwOwoKCS8qCgkgKiBFeHBpcmUgZGlzY292ZXJ5IG9uIGFsbCBsaW5rcyB3aGljaCBhcmUgKm5vdCogY29ubmVjdGVkLgoJICogT24gbGlua3Mgd2hpY2ggYXJlIGNvbm5lY3RlZCwgd2UgY2FuJ3QgZG8gZGlzY292ZXJ5CgkgKiBhbnltb3JlIGFuZCBjYW4ndCByZWZyZXNoIHRoZSBsb2csIHNvIHdlIGZyZWV6ZSB0aGUKCSAqIGRpc2NvdmVyeSBsb2cgdG8ga2VlcCBpbmZvIGFib3V0IHRoZSBkZXZpY2Ugd2UgYXJlCgkgKiBjb25uZWN0ZWQgdG8uCgkgKiBUaGlzIGluZm8gaXMgbWFuZGF0b3J5IGlmIHdlIHdhbnQgaXJsbXBfY29ubmVjdF9yZXF1ZXN0KCkKCSAqIHRvIHdvcmsgcHJvcGVybHkuIC0gSmVhbiBJSQoJICovCglsYXAgPSAoc3RydWN0IGxhcF9jYiAqKSBoYXNoYmluX2dldF9maXJzdChpcmxtcC0+bGlua3MpOwoJd2hpbGUgKGxhcCAhPSBOVUxMKSB7CgkJSVJEQV9BU1NFUlQobGFwLT5tYWdpYyA9PSBMTVBfTEFQX01BR0lDLCByZXR1cm47KTsKCgkJaWYgKGxhcC0+bGFwX3N0YXRlID09IExBUF9TVEFOREJZKSB7CgkJCS8qIEV4cGlyZSBkaXNjb3ZlcmllcyBkaXNjb3ZlcmVkIG9uIHRoaXMgbGluayAqLwoJCQlpcmxtcF9leHBpcmVfZGlzY292ZXJpZXMoaXJsbXAtPmNhY2hlbG9nLCBsYXAtPnNhZGRyLAoJCQkJCQkgRkFMU0UpOwoJCX0KCQlsYXAgPSAoc3RydWN0IGxhcF9jYiAqKSBoYXNoYmluX2dldF9uZXh0KGlybG1wLT5saW5rcyk7Cgl9Cn0KCi8qCiAqIEZ1bmN0aW9uIGlybG1wX2RvX2Rpc2NvdmVyeSAobnNsb3RzKQogKgogKiAgICBEbyBzb21lIGRpc2NvdmVyeSBvbiBhbGwgbGlua3MKICoKICogTm90ZSA6IGxvZyBleHBpcnkgaXMgZG9uZSBhYm92ZS4KICovCnZvaWQgaXJsbXBfZG9fZGlzY292ZXJ5KGludCBuc2xvdHMpCnsKCXN0cnVjdCBsYXBfY2IgKmxhcDsKCV9fdTE2ICpkYXRhX2hpbnRzcDsKCgkvKiBNYWtlIHN1cmUgdGhlIHZhbHVlIGlzIHNhbmUgKi8KCWlmICgobnNsb3RzICE9IDEpICYmIChuc2xvdHMgIT0gNikgJiYgKG5zbG90cyAhPSA4KSAmJiAobnNsb3RzICE9IDE2KSl7CgkJSVJEQV9XQVJOSU5HKCIlczogaW52YWxpZCB2YWx1ZSBmb3IgbnVtYmVyIG9mIHNsb3RzIVxuIiwKCQkJICAgICBfX0ZVTkNUSU9OX18pOwoJCW5zbG90cyA9IHN5c2N0bF9kaXNjb3Zlcnlfc2xvdHMgPSA4OwoJfQoKCS8qIENvbnN0cnVjdCBuZXcgZGlzY292ZXJ5IGluZm8gdG8gYmUgdXNlZCBieSBJckxBUCwgKi8KCWRhdGFfaGludHNwID0gKF9fdTE2ICopIGlybG1wLT5kaXNjb3ZlcnlfY21kLmRhdGEuaGludHM7CglwdXRfdW5hbGlnbmVkKGlybG1wLT5oaW50cy53b3JkLCBkYXRhX2hpbnRzcCk7CgoJLyoKCSAqICBTZXQgY2hhcmFjdGVyIHNldCBmb3IgZGV2aWNlIG5hbWUgKHdlIHVzZSBBU0NJSSksIGFuZAoJICogIGNvcHkgZGV2aWNlIG5hbWUuIFJlbWVtYmVyIHRvIG1ha2Ugcm9vbSBmb3IgYSBcMCBhdCB0aGUKCSAqICBlbmQKCSAqLwoJaXJsbXAtPmRpc2NvdmVyeV9jbWQuZGF0YS5jaGFyc2V0ID0gQ1NfQVNDSUk7CglzdHJuY3B5KGlybG1wLT5kaXNjb3ZlcnlfY21kLmRhdGEuaW5mbywgc3lzY3RsX2Rldm5hbWUsCgkJTklDS05BTUVfTUFYX0xFTik7CglpcmxtcC0+ZGlzY292ZXJ5X2NtZC5uYW1lX2xlbiA9IHN0cmxlbihpcmxtcC0+ZGlzY292ZXJ5X2NtZC5kYXRhLmluZm8pOwoJaXJsbXAtPmRpc2NvdmVyeV9jbWQubnNsb3RzID0gbnNsb3RzOwoKCS8qCgkgKiBUcnkgdG8gc2VuZCBkaXNjb3ZlcnkgcGFja2V0cyBvbiBhbGwgbGlua3MKCSAqLwoJbGFwID0gKHN0cnVjdCBsYXBfY2IgKikgaGFzaGJpbl9nZXRfZmlyc3QoaXJsbXAtPmxpbmtzKTsKCXdoaWxlIChsYXAgIT0gTlVMTCkgewoJCUlSREFfQVNTRVJUKGxhcC0+bWFnaWMgPT0gTE1QX0xBUF9NQUdJQywgcmV0dXJuOyk7CgoJCWlmIChsYXAtPmxhcF9zdGF0ZSA9PSBMQVBfU1RBTkRCWSkgewoJCQkvKiBUcnkgdG8gZGlzY292ZXIgKi8KCQkJaXJsbXBfZG9fbGFwX2V2ZW50KGxhcCwgTE1fTEFQX0RJU0NPVkVSWV9SRVFVRVNULAoJCQkJCSAgIE5VTEwpOwoJCX0KCQlsYXAgPSAoc3RydWN0IGxhcF9jYiAqKSBoYXNoYmluX2dldF9uZXh0KGlybG1wLT5saW5rcyk7Cgl9Cn0KCi8qCiAqIEZ1bmN0aW9uIGlybG1wX2Rpc2NvdmVyeV9yZXF1ZXN0IChuc2xvdHMpCiAqCiAqICAgIERvIGEgZGlzY292ZXJ5IG9mIGRldmljZXMgaW4gZnJvbnQgb2YgdGhlIGNvbXB1dGVyCiAqCiAqIElmIHRoZSBjYWxsZXIgaGFzIHJlZ2lzdGVyZWQgYSBjbGllbnQgZGlzY292ZXJ5IGNhbGxiYWNrLCB0aGlzCiAqIGFsbG93IGhpbSB0byByZWNlaXZlIHRoZSBmdWxsIGNvbnRlbnQgb2YgdGhlIGRpc2NvdmVyeSBsb2cgdGhyb3VnaAogKiB0aGlzIGNhbGxiYWNrIChhcyBub3JtYWxseSBoZSB3aWxsIHJlY2VpdmUgb25seSBuZXcgZGlzY292ZXJpZXMpLgogKi8Kdm9pZCBpcmxtcF9kaXNjb3ZlcnlfcmVxdWVzdChpbnQgbnNsb3RzKQp7CgkvKiBSZXR1cm4gY3VycmVudCBjYWNoZWQgZGlzY292ZXJ5IGxvZyAoaW4gZnVsbCkgKi8KCWlybG1wX2Rpc2NvdmVyeV9jb25maXJtKGlybG1wLT5jYWNoZWxvZywgRElTQ09WRVJZX0xPRyk7CgoJLyoKCSAqIFN0YXJ0IGEgc2luZ2xlIGRpc2NvdmVyeSBvcGVyYXRpb24gaWYgZGlzY292ZXJ5IGlzIG5vdCBhbHJlYWR5CiAgICAgICAgICogcnVubmluZwoJICovCglpZiAoIXN5c2N0bF9kaXNjb3ZlcnkpIHsKCQkvKiBDaGVjayBpZiB1c2VyIHdhbnRzIHRvIG92ZXJyaWRlIHRoZSBkZWZhdWx0ICovCgkJaWYgKG5zbG90cyA9PSBESVNDT1ZFUllfREVGQVVMVF9TTE9UUykKCQkJbnNsb3RzID0gc3lzY3RsX2Rpc2NvdmVyeV9zbG90czsKCgkJaXJsbXBfZG9fZGlzY292ZXJ5KG5zbG90cyk7CgkJLyogTm90ZSA6IHdlIG5ldmVyIGRvIGV4cGlyeSBoZXJlLiBFeHBpcnkgd2lsbCBydW4gb24gdGhlCgkJICogZGlzY292ZXJ5IHRpbWVyIHJlZ2FyZGxlc3Mgb2YgdGhlIHN0YXRlIG9mIHN5c2N0bF9kaXNjb3ZlcnkKCQkgKiBKZWFuIElJICovCgl9Cn0KRVhQT1JUX1NZTUJPTChpcmxtcF9kaXNjb3ZlcnlfcmVxdWVzdCk7CgovKgogKiBGdW5jdGlvbiBpcmxtcF9nZXRfZGlzY292ZXJpZXMgKHBuLCBtYXNrLCBzbG90cykKICoKICogICAgUmV0dXJuIHRoZSBjdXJyZW50IGRpc2NvdmVyeSBsb2cKICoKICogSWYgZGlzY292ZXJ5IGlzIG5vdCBlbmFibGVkLCB5b3Ugc2hvdWxkIGNhbGwgdGhpcyBmdW5jdGlvbiBhZ2FpbgogKiBhZnRlciAxIG9yIDIgc2Vjb25kcyAoaS5lLiBhZnRlciBkaXNjb3ZlcnkgaGFzIGJlZW4gZG9uZSkuCiAqLwpzdHJ1Y3QgaXJkYV9kZXZpY2VfaW5mbyAqaXJsbXBfZ2V0X2Rpc2NvdmVyaWVzKGludCAqcG4sIF9fdTE2IG1hc2ssIGludCBuc2xvdHMpCnsKCS8qIElmIGRpc2NvdmVyeSBpcyBub3QgZW5hYmxlZCwgaXQncyBsaWtlbHkgdGhhdCB0aGUgZGlzY292ZXJ5IGxvZwoJICogd2lsbCBiZSBlbXB0eS4gU28sIHdlIHRyaWdnZXIgYSBzaW5nbGUgZGlzY292ZXJ5LCBzbyB0aGF0IG5leHQKCSAqIHRpbWUgdGhlIHVzZXIgY2FsbCB1cyB0aGVyZSBtaWdodCBiZSBzb21lIHJlc3VsdHMgaW4gdGhlIGxvZy4KCSAqIEplYW4gSUkKCSAqLwoJaWYgKCFzeXNjdGxfZGlzY292ZXJ5KSB7CgkJLyogQ2hlY2sgaWYgdXNlciB3YW50cyB0byBvdmVycmlkZSB0aGUgZGVmYXVsdCAqLwoJCWlmIChuc2xvdHMgPT0gRElTQ09WRVJZX0RFRkFVTFRfU0xPVFMpCgkJCW5zbG90cyA9IHN5c2N0bF9kaXNjb3Zlcnlfc2xvdHM7CgoJCS8qIFN0YXJ0IGRpc2NvdmVyeSAtIHdpbGwgY29tcGxldGUgc29tZXRpbWUgbGF0ZXIgKi8KCQlpcmxtcF9kb19kaXNjb3ZlcnkobnNsb3RzKTsKCQkvKiBOb3RlIDogd2UgbmV2ZXIgZG8gZXhwaXJ5IGhlcmUuIEV4cGlyeSB3aWxsIHJ1biBvbiB0aGUKCQkgKiBkaXNjb3ZlcnkgdGltZXIgcmVnYXJkbGVzcyBvZiB0aGUgc3RhdGUgb2Ygc3lzY3RsX2Rpc2NvdmVyeQoJCSAqIEplYW4gSUkgKi8KCX0KCgkvKiBSZXR1cm4gY3VycmVudCBjYWNoZWQgZGlzY292ZXJ5IGxvZyAqLwoJcmV0dXJuKGlybG1wX2NvcHlfZGlzY292ZXJpZXMoaXJsbXAtPmNhY2hlbG9nLCBwbiwgbWFzaywgVFJVRSkpOwp9CkVYUE9SVF9TWU1CT0woaXJsbXBfZ2V0X2Rpc2NvdmVyaWVzKTsKCi8qCiAqIEZ1bmN0aW9uIGlybG1wX25vdGlmeV9jbGllbnQgKGxvZykKICoKICogICAgTm90aWZ5IGFsbCBhYm91dCBkaXNjb3ZlcmVkIGRldmljZXMKICoKICogQ2xpZW50cyByZWdpc3RlcmVkIHdpdGggSXJMTVAgYXJlIDoKICoJbyBJckNvbW0KICoJbyBJckxBTgogKglvIEFueSBzb2NrZXQgKGluIGFueSBzdGF0ZSAtIG91Y2gsIHRoYXQgbWF5IGJlIGEgbG90ICEpCiAqIFRoZSBjbGllbnQgbWF5IGhhdmUgZGVmaW5lZCBhIGNhbGxiYWNrIHRvIGJlIG5vdGlmaWVkIGluIGNhc2Ugb2YKICogcGFydGlhbC9zZWxlY3RpdmUgZGlzY292ZXJ5IGJhc2VkIG9uIHRoZSBoaW50cyB0aGF0IGl0IHBhc3NlZCB0byBJckxNUC4KICovCnN0YXRpYyBpbmxpbmUgdm9pZAppcmxtcF9ub3RpZnlfY2xpZW50KGlybG1wX2NsaWVudF90ICpjbGllbnQsCgkJICAgIGhhc2hiaW5fdCAqbG9nLCBESVNDT1ZFUllfTU9ERSBtb2RlKQp7CglkaXNjaW5mb190ICpkaXNjb3ZlcmllczsJLyogQ29weSBvZiB0aGUgZGlzY292ZXJ5IGxvZyAqLwoJaW50CW51bWJlcjsJCQkvKiBOdW1iZXIgb2Ygbm9kZXMgaW4gdGhlIGxvZyAqLwoJaW50CWk7CgoJSVJEQV9ERUJVRygzLCAiJXMoKVxuIiwgX19GVU5DVElPTl9fKTsKCgkvKiBDaGVjayBpZiBjbGllbnQgd2FudHMgb3Igbm90IHBhcnRpYWwvc2VsZWN0aXZlIGxvZyAob3B0aW1pc2F0aW9uKSAqLwoJaWYgKCFjbGllbnQtPmRpc2NvX2NhbGxiYWNrKQoJCXJldHVybjsKCgkvKgoJICogTG9ja2luZyBub3RlcyA6CgkgKiB0aGUgb2xkIGNvZGUgd2FzIG1hbmlwdWxhdGluZyB0aGUgbG9nIGRpcmVjdGx5LCB3aGljaCB3YXMKCSAqIHZlcnkgcmFjeS4gTm93LCB3ZSB1c2UgY29weV9kaXNjb3ZlcmllcywgdGhhdCBwcm90ZWN0cwoJICogaXRzZWxmIHdoaWxlIGR1bXBpbmcgdGhlIGxvZyBmb3IgdXMuCgkgKiBUaGUgb3ZlcmhlYWQgb2YgdGhlIGNvcHkgaXMgY29tcGVuc2F0ZWQgYnkgdGhlIGZhY3QgdGhhdAoJICogd2Ugb25seSBwYXNzIG5ldyBkaXNjb3ZlcmllcyBpbiBub3JtYWwgbW9kZSBhbmQgZG9uJ3QKCSAqIHBhc3MgdGhlIHNhbWUgb2xkIGVudHJ5IGV2ZXJ5IDNzIHRvIHRoZSBjYWxsZXIgYXMgd2UgdXNlZAoJICogdG8gZG8gKHZpcnR1YWwgZnVuY3Rpb24gY2FsbGluZyBpcyBleHBlbnNpdmUpLgoJICogSmVhbiBJSQoJICovCgoJLyoKCSAqIE5vdywgY2hlY2sgYWxsIGRpc2NvdmVyZWQgZGV2aWNlcyAoaWYgYW55KSwgYW5kIG5vdGlmeSBjbGllbnQKCSAqIG9ubHkgYWJvdXQgdGhlIHNlcnZpY2VzIHRoYXQgdGhlIGNsaWVudCBpcyBpbnRlcmVzdGVkIGluCgkgKiBXZSBhbHNvIG5vdGlmeSBvbmx5IGFib3V0IHRoZSBuZXcgZGV2aWNlcyB1bmxlc3MgdGhlIGNhbGxlcgoJICogZXhwbGljaXRseSByZXF1ZXN0IGEgZHVtcCBvZiB0aGUgbG9nLiBKZWFuIElJCgkgKi8KCWRpc2NvdmVyaWVzID0gaXJsbXBfY29weV9kaXNjb3Zlcmllcyhsb2csICZudW1iZXIsCgkJCQkJICAgICBjbGllbnQtPmhpbnRfbWFzay53b3JkLAoJCQkJCSAgICAgKG1vZGUgPT0gRElTQ09WRVJZX0xPRykpOwoJLyogQ2hlY2sgaWYgdGhlIHdlIGdvdCBzb21lIHJlc3VsdHMgKi8KCWlmIChkaXNjb3ZlcmllcyA9PSBOVUxMKQoJCXJldHVybjsJLyogTm8gbm9kZXMgZGlzY292ZXJlZCAqLwoKCS8qIFBhc3MgYWxsIGVudHJpZXMgdG8gdGhlIGxpc3RlbmVyICovCglmb3IoaSA9IDA7IGkgPCBudW1iZXI7IGkrKykKCQljbGllbnQtPmRpc2NvX2NhbGxiYWNrKCYoZGlzY292ZXJpZXNbaV0pLCBtb2RlLCBjbGllbnQtPnByaXYpOwoKCS8qIEZyZWUgdXAgb3VyIGJ1ZmZlciAqLwoJa2ZyZWUoZGlzY292ZXJpZXMpOwp9CgovKgogKiBGdW5jdGlvbiBpcmxtcF9kaXNjb3ZlcnlfY29uZmlybSAoIHNlbGYsIGxvZykKICoKICogICAgU29tZSBkZXZpY2UocykgYW5zd2VyZWQgdG8gb3VyIGRpc2NvdmVyeSByZXF1ZXN0ISBDaGVjayB0byBzZWUgd2hpY2gKICogICAgZGV2aWNlIGl0IGlzLCBhbmQgZ2l2ZSBpbmRpY2F0aW9uIHRvIHRoZSBjbGllbnQocykKICoKICovCnZvaWQgaXJsbXBfZGlzY292ZXJ5X2NvbmZpcm0oaGFzaGJpbl90ICpsb2csIERJU0NPVkVSWV9NT0RFIG1vZGUpCnsKCWlybG1wX2NsaWVudF90ICpjbGllbnQ7CglpcmxtcF9jbGllbnRfdCAqY2xpZW50X25leHQ7CgoJSVJEQV9ERUJVRygzLCAiJXMoKVxuIiwgX19GVU5DVElPTl9fKTsKCglJUkRBX0FTU0VSVChsb2cgIT0gTlVMTCwgcmV0dXJuOyk7CgoJaWYgKCEoSEFTSEJJTl9HRVRfU0laRShsb2cpKSkKCQlyZXR1cm47CgoJLyogRm9yIGVhY2ggY2xpZW50IC0gbm90aWZ5IGNhbGxiYWNrIG1heSB0b3VjaCBjbGllbnQgbGlzdCAqLwoJY2xpZW50ID0gKGlybG1wX2NsaWVudF90ICopIGhhc2hiaW5fZ2V0X2ZpcnN0KGlybG1wLT5jbGllbnRzKTsKCXdoaWxlIChOVUxMICE9IGhhc2hiaW5fZmluZF9uZXh0KGlybG1wLT5jbGllbnRzLCAobG9uZykgY2xpZW50LCBOVUxMLAoJCQkJCSAodm9pZCAqKSAmY2xpZW50X25leHQpICkgewoJCS8qIENoZWNrIGlmIHdlIHNob3VsZCBub3RpZnkgY2xpZW50ICovCgkJaXJsbXBfbm90aWZ5X2NsaWVudChjbGllbnQsIGxvZywgbW9kZSk7CgoJCWNsaWVudCA9IGNsaWVudF9uZXh0OwoJfQp9CgovKgogKiBGdW5jdGlvbiBpcmxtcF9kaXNjb3ZlcnlfZXhwaXJ5IChleHBpcnkpCiAqCiAqCVRoaXMgZGV2aWNlIGlzIG5vIGxvbmdlciBiZWVuIGRpc2NvdmVyZWQsIGFuZCB0aGVyZWZvcmUgaXQgaXMgYmVpbmcKICoJcHVyZ2VkIGZyb20gdGhlIGRpc2NvdmVyeSBsb2cuIEluZm9ybSBhbGwgY2xpZW50cyB3aG8gaGF2ZQogKglyZWdpc3RlcmVkIGZvciB0aGlzIGV2ZW50Li4uCiAqCiAqCU5vdGUgOiBjYWxsZWQgZXhjbHVzaXZlbHkgZnJvbSBkaXNjb3ZlcnkuYwogKglOb3RlIDogdGhpcyBpcyBubyBsb25nZXIgY2FsbGVkIHVuZGVyIGRpc2NvdmVyeSBzcGlubG9jaywgc28gdGhlCiAqCQljbGllbnQgY2FuIGRvIHdoYXRldmVyIGhlIHdhbnRzIGluIHRoZSBjYWxsYmFjay4KICovCnZvaWQgaXJsbXBfZGlzY292ZXJ5X2V4cGlyeShkaXNjaW5mb190ICpleHBpcmllcywgaW50IG51bWJlcikKewoJaXJsbXBfY2xpZW50X3QgKmNsaWVudDsKCWlybG1wX2NsaWVudF90ICpjbGllbnRfbmV4dDsKCWludAkJaTsKCglJUkRBX0RFQlVHKDMsICIlcygpXG4iLCBfX0ZVTkNUSU9OX18pOwoKCUlSREFfQVNTRVJUKGV4cGlyaWVzICE9IE5VTEwsIHJldHVybjspOwoKCS8qIEZvciBlYWNoIGNsaWVudCAtIG5vdGlmeSBjYWxsYmFjayBtYXkgdG91Y2ggY2xpZW50IGxpc3QgKi8KCWNsaWVudCA9IChpcmxtcF9jbGllbnRfdCAqKSBoYXNoYmluX2dldF9maXJzdChpcmxtcC0+Y2xpZW50cyk7Cgl3aGlsZSAoTlVMTCAhPSBoYXNoYmluX2ZpbmRfbmV4dChpcmxtcC0+Y2xpZW50cywgKGxvbmcpIGNsaWVudCwgTlVMTCwKCQkJCQkgKHZvaWQgKikgJmNsaWVudF9uZXh0KSApIHsKCgkJLyogUGFzcyBhbGwgZW50cmllcyB0byB0aGUgbGlzdGVuZXIgKi8KCQlmb3IoaSA9IDA7IGkgPCBudW1iZXI7IGkrKykgewoJCQkvKiBDaGVjayBpZiB3ZSBzaG91bGQgbm90aWZ5IGNsaWVudCAqLwoJCQlpZiAoKGNsaWVudC0+ZXhwaXJfY2FsbGJhY2spICYmCgkJCSAgICAoY2xpZW50LT5oaW50X21hc2sud29yZCAmIHUxNmhvKGV4cGlyaWVzW2ldLmhpbnRzKQoJCQkgICAgICYgMHg3ZjdmKSApCgkJCQljbGllbnQtPmV4cGlyX2NhbGxiYWNrKCYoZXhwaXJpZXNbaV0pLAoJCQkJCQkgICAgICAgRVhQSVJZX1RJTUVPVVQsCgkJCQkJCSAgICAgICBjbGllbnQtPnByaXYpOwoJCX0KCgkJLyogTmV4dCBjbGllbnQgKi8KCQljbGllbnQgPSBjbGllbnRfbmV4dDsKCX0KfQoKLyoKICogRnVuY3Rpb24gaXJsbXBfZ2V0X2Rpc2NvdmVyeV9yZXNwb25zZSAoKQogKgogKiAgICBVc2VkIGJ5IElyTEFQIHRvIGdldCB0aGUgZGlzY292ZXJ5IGluZm8gaXQgbmVlZHMgd2hlbiBhbnN3ZXJpbmcKICogICAgZGlzY292ZXJ5IHJlcXVlc3RzIGJ5IG90aGVyIGRldmljZXMuCiAqLwpkaXNjb3ZlcnlfdCAqaXJsbXBfZ2V0X2Rpc2NvdmVyeV9yZXNwb25zZSh2b2lkKQp7CglJUkRBX0RFQlVHKDQsICIlcygpXG4iLCBfX0ZVTkNUSU9OX18pOwoKCUlSREFfQVNTRVJUKGlybG1wICE9IE5VTEwsIHJldHVybiBOVUxMOyk7CgoJdTE2aG8oaXJsbXAtPmRpc2NvdmVyeV9yc3AuZGF0YS5oaW50cykgPSBpcmxtcC0+aGludHMud29yZDsKCgkvKgoJICogIFNldCBjaGFyYWN0ZXIgc2V0IGZvciBkZXZpY2UgbmFtZSAod2UgdXNlIEFTQ0lJKSwgYW5kCgkgKiAgY29weSBkZXZpY2UgbmFtZS4gUmVtZW1iZXIgdG8gbWFrZSByb29tIGZvciBhIFwwIGF0IHRoZQoJICogIGVuZAoJICovCglpcmxtcC0+ZGlzY292ZXJ5X3JzcC5kYXRhLmNoYXJzZXQgPSBDU19BU0NJSTsKCglzdHJuY3B5KGlybG1wLT5kaXNjb3ZlcnlfcnNwLmRhdGEuaW5mbywgc3lzY3RsX2Rldm5hbWUsCgkJTklDS05BTUVfTUFYX0xFTik7CglpcmxtcC0+ZGlzY292ZXJ5X3JzcC5uYW1lX2xlbiA9IHN0cmxlbihpcmxtcC0+ZGlzY292ZXJ5X3JzcC5kYXRhLmluZm8pOwoKCXJldHVybiAmaXJsbXAtPmRpc2NvdmVyeV9yc3A7Cn0KCi8qCiAqIEZ1bmN0aW9uIGlybG1wX2RhdGFfcmVxdWVzdCAoc2VsZiwgc2tiKQogKgogKiAgICBTZW5kIHNvbWUgZGF0YSB0byBwZWVyIGRldmljZQogKgogKiBOb3RlIG9uIHNrYiBtYW5hZ2VtZW50IDoKICogQWZ0ZXIgY2FsbGluZyB0aGUgbG93ZXIgbGF5ZXJzIG9mIHRoZSBJckRBIHN0YWNrLCB3ZSBhbHdheXMKICoga2ZyZWUoKSB0aGUgc2tiLCB3aGljaCBkcm9wIHRoZSByZWZlcmVuY2UgY291bnQgKGFuZCBwb3RlbnRpYWxseQogKiBkZXN0cm95IGl0KS4KICogSXJMTVAgYW5kIElyTEFQIG1heSBxdWV1ZSB0aGUgcGFja2V0LCBhbmQgaW4gdGhvc2UgY2FzZXMgd2lsbCBuZWVkCiAqIHRvIHVzZSBza2JfZ2V0KCkgdG8ga2VlcCBpdCBhcm91bmQuCiAqIEplYW4gSUkKICovCmludCBpcmxtcF9kYXRhX3JlcXVlc3Qoc3RydWN0IGxzYXBfY2IgKnNlbGYsIHN0cnVjdCBza19idWZmICp1c2VyZGF0YSkKewoJaW50CXJldDsKCglJUkRBX0FTU0VSVChzZWxmICE9IE5VTEwsIHJldHVybiAtMTspOwoJSVJEQV9BU1NFUlQoc2VsZi0+bWFnaWMgPT0gTE1QX0xTQVBfTUFHSUMsIHJldHVybiAtMTspOwoKCS8qIE1ha2Ugcm9vbSBmb3IgTVVYIGhlYWRlciAqLwoJSVJEQV9BU1NFUlQoc2tiX2hlYWRyb29tKHVzZXJkYXRhKSA+PSBMTVBfSEVBREVSLCByZXR1cm4gLTE7KTsKCXNrYl9wdXNoKHVzZXJkYXRhLCBMTVBfSEVBREVSKTsKCglyZXQgPSBpcmxtcF9kb19sc2FwX2V2ZW50KHNlbGYsIExNX0RBVEFfUkVRVUVTVCwgdXNlcmRhdGEpOwoKCS8qIERyb3AgcmVmZXJlbmNlIGNvdW50IC0gc2VlIGlybGFwX2RhdGFfcmVxdWVzdCgpLiAqLwoJZGV2X2tmcmVlX3NrYih1c2VyZGF0YSk7CgoJcmV0dXJuIHJldDsKfQpFWFBPUlRfU1lNQk9MKGlybG1wX2RhdGFfcmVxdWVzdCk7CgovKgogKiBGdW5jdGlvbiBpcmxtcF9kYXRhX2luZGljYXRpb24gKGhhbmRsZSwgc2tiKQogKgogKiAgICBHb3QgZGF0YSBmcm9tIExBUCBsYXllciBzbyBwYXNzIGl0IHVwIHRvIHVwcGVyIGxheWVyCiAqCiAqLwp2b2lkIGlybG1wX2RhdGFfaW5kaWNhdGlvbihzdHJ1Y3QgbHNhcF9jYiAqc2VsZiwgc3RydWN0IHNrX2J1ZmYgKnNrYikKewoJLyogSGlkZSBMTVAgaGVhZGVyIGZyb20gbGF5ZXIgYWJvdmUgKi8KCXNrYl9wdWxsKHNrYiwgTE1QX0hFQURFUik7CgoJaWYgKHNlbGYtPm5vdGlmeS5kYXRhX2luZGljYXRpb24pIHsKCQkvKiBEb24ndCBmb3JnZXQgdG8gcmVmY291bnQgaXQgLSBzZWUgaXJsYXBfZHJpdmVyX3JjdigpLiAqLwoJCXNrYl9nZXQoc2tiKTsKCQlzZWxmLT5ub3RpZnkuZGF0YV9pbmRpY2F0aW9uKHNlbGYtPm5vdGlmeS5pbnN0YW5jZSwgc2VsZiwgc2tiKTsKCX0KfQoKLyoKICogRnVuY3Rpb24gaXJsbXBfdWRhdGFfcmVxdWVzdCAoc2VsZiwgc2tiKQogKi8KaW50IGlybG1wX3VkYXRhX3JlcXVlc3Qoc3RydWN0IGxzYXBfY2IgKnNlbGYsIHN0cnVjdCBza19idWZmICp1c2VyZGF0YSkKewoJaW50CXJldDsKCglJUkRBX0RFQlVHKDQsICIlcygpXG4iLCBfX0ZVTkNUSU9OX18pOwoKCUlSREFfQVNTRVJUKHVzZXJkYXRhICE9IE5VTEwsIHJldHVybiAtMTspOwoKCS8qIE1ha2Ugcm9vbSBmb3IgTVVYIGhlYWRlciAqLwoJSVJEQV9BU1NFUlQoc2tiX2hlYWRyb29tKHVzZXJkYXRhKSA+PSBMTVBfSEVBREVSLCByZXR1cm4gLTE7KTsKCXNrYl9wdXNoKHVzZXJkYXRhLCBMTVBfSEVBREVSKTsKCglyZXQgPSBpcmxtcF9kb19sc2FwX2V2ZW50KHNlbGYsIExNX1VEQVRBX1JFUVVFU1QsIHVzZXJkYXRhKTsKCgkvKiBEcm9wIHJlZmVyZW5jZSBjb3VudCAtIHNlZSBpcmxhcF9kYXRhX3JlcXVlc3QoKS4gKi8KCWRldl9rZnJlZV9za2IodXNlcmRhdGEpOwoKCXJldHVybiByZXQ7Cn0KCi8qCiAqIEZ1bmN0aW9uIGlybG1wX3VkYXRhX2luZGljYXRpb24gKHNlbGYsIHNrYikKICoKICogICAgU2VuZCB1bnJlbGlhYmxlIGRhdGEgKGJ1dCBzdGlsbCB3aXRoaW4gdGhlIGNvbm5lY3Rpb24pCiAqCiAqLwp2b2lkIGlybG1wX3VkYXRhX2luZGljYXRpb24oc3RydWN0IGxzYXBfY2IgKnNlbGYsIHN0cnVjdCBza19idWZmICpza2IpCnsKCUlSREFfREVCVUcoNCwgIiVzKClcbiIsIF9fRlVOQ1RJT05fXyk7CgoJSVJEQV9BU1NFUlQoc2VsZiAhPSBOVUxMLCByZXR1cm47KTsKCUlSREFfQVNTRVJUKHNlbGYtPm1hZ2ljID09IExNUF9MU0FQX01BR0lDLCByZXR1cm47KTsKCUlSREFfQVNTRVJUKHNrYiAhPSBOVUxMLCByZXR1cm47KTsKCgkvKiBIaWRlIExNUCBoZWFkZXIgZnJvbSBsYXllciBhYm92ZSAqLwoJc2tiX3B1bGwoc2tiLCBMTVBfSEVBREVSKTsKCglpZiAoc2VsZi0+bm90aWZ5LnVkYXRhX2luZGljYXRpb24pIHsKCQkvKiBEb24ndCBmb3JnZXQgdG8gcmVmY291bnQgaXQgLSBzZWUgaXJsYXBfZHJpdmVyX3JjdigpLiAqLwoJCXNrYl9nZXQoc2tiKTsKCQlzZWxmLT5ub3RpZnkudWRhdGFfaW5kaWNhdGlvbihzZWxmLT5ub3RpZnkuaW5zdGFuY2UsIHNlbGYsCgkJCQkJICAgICAgc2tiKTsKCX0KfQoKLyoKICogRnVuY3Rpb24gaXJsbXBfY29ubmxlc3NfZGF0YV9yZXF1ZXN0IChzZWxmLCBza2IpCiAqLwojaWZkZWYgQ09ORklHX0lSREFfVUxUUkEKaW50IGlybG1wX2Nvbm5sZXNzX2RhdGFfcmVxdWVzdChzdHJ1Y3QgbHNhcF9jYiAqc2VsZiwgc3RydWN0IHNrX2J1ZmYgKnVzZXJkYXRhLAoJCQkJX191OCBwaWQpCnsKCXN0cnVjdCBza19idWZmICpjbG9uZV9za2I7CglzdHJ1Y3QgbGFwX2NiICpsYXA7CgoJSVJEQV9ERUJVRyg0LCAiJXMoKVxuIiwgX19GVU5DVElPTl9fKTsKCglJUkRBX0FTU0VSVCh1c2VyZGF0YSAhPSBOVUxMLCByZXR1cm4gLTE7KTsKCgkvKiBNYWtlIHJvb20gZm9yIE1VWCBhbmQgUElEIGhlYWRlciAqLwoJSVJEQV9BU1NFUlQoc2tiX2hlYWRyb29tKHVzZXJkYXRhKSA+PSBMTVBfSEVBREVSK0xNUF9QSURfSEVBREVSLAoJCSAgICByZXR1cm4gLTE7KTsKCgkvKiBJbnNlcnQgcHJvdG9jb2wgaWRlbnRpZmllciAqLwoJc2tiX3B1c2godXNlcmRhdGEsIExNUF9QSURfSEVBREVSKTsKCWlmKHNlbGYgIT0gTlVMTCkKCSAgdXNlcmRhdGEtPmRhdGFbMF0gPSBzZWxmLT5waWQ7CgllbHNlCgkgIHVzZXJkYXRhLT5kYXRhWzBdID0gcGlkOwoKCS8qIENvbm5lY3Rpb25sZXNzIHNvY2tldHMgbXVzdCB1c2UgMHg3MCAqLwoJc2tiX3B1c2godXNlcmRhdGEsIExNUF9IRUFERVIpOwoJdXNlcmRhdGEtPmRhdGFbMF0gPSB1c2VyZGF0YS0+ZGF0YVsxXSA9IExTQVBfQ09OTkxFU1M7CgoJLyogVHJ5IHRvIHNlbmQgQ29ubmVjdGlvbmxlc3MgIHBhY2tldHMgb3V0IG9uIGFsbCBsaW5rcyAqLwoJbGFwID0gKHN0cnVjdCBsYXBfY2IgKikgaGFzaGJpbl9nZXRfZmlyc3QoaXJsbXAtPmxpbmtzKTsKCXdoaWxlIChsYXAgIT0gTlVMTCkgewoJCUlSREFfQVNTRVJUKGxhcC0+bWFnaWMgPT0gTE1QX0xBUF9NQUdJQywgcmV0dXJuIC0xOyk7CgoJCWNsb25lX3NrYiA9IHNrYl9jbG9uZSh1c2VyZGF0YSwgR0ZQX0FUT01JQyk7CgkJaWYgKCFjbG9uZV9za2IpIHsKCQkJZGV2X2tmcmVlX3NrYih1c2VyZGF0YSk7CgkJCXJldHVybiAtRU5PTUVNOwoJCX0KCgkJaXJsYXBfdW5pdGRhdGFfcmVxdWVzdChsYXAtPmlybGFwLCBjbG9uZV9za2IpOwoJCS8qIGlybGFwX3VuaXRkYXRhX3JlcXVlc3QoKSBkb24ndCBpbmNyZWFzZSByZWZjb3VudCwKCQkgKiBzbyBubyBkZXZfa2ZyZWVfc2tiKCkgLSBKZWFuIElJICovCgoJCWxhcCA9IChzdHJ1Y3QgbGFwX2NiICopIGhhc2hiaW5fZ2V0X25leHQoaXJsbXAtPmxpbmtzKTsKCX0KCWRldl9rZnJlZV9za2IodXNlcmRhdGEpOwoKCXJldHVybiAwOwp9CiNlbmRpZiAvKiBDT05GSUdfSVJEQV9VTFRSQSAqLwoKLyoKICogRnVuY3Rpb24gaXJsbXBfY29ubmxlc3NfZGF0YV9pbmRpY2F0aW9uIChzZWxmLCBza2IpCiAqCiAqICAgIFJlY2VpdmUgdW5yZWxpYWJsZSBkYXRhIG91dHNpZGUgYW55IGNvbm5lY3Rpb24uIE1vc3RseSB1c2VkIGJ5IFVsdHJhCiAqCiAqLwojaWZkZWYgQ09ORklHX0lSREFfVUxUUkEKdm9pZCBpcmxtcF9jb25ubGVzc19kYXRhX2luZGljYXRpb24oc3RydWN0IGxzYXBfY2IgKnNlbGYsIHN0cnVjdCBza19idWZmICpza2IpCnsKCUlSREFfREVCVUcoNCwgIiVzKClcbiIsIF9fRlVOQ1RJT05fXyk7CgoJSVJEQV9BU1NFUlQoc2VsZiAhPSBOVUxMLCByZXR1cm47KTsKCUlSREFfQVNTRVJUKHNlbGYtPm1hZ2ljID09IExNUF9MU0FQX01BR0lDLCByZXR1cm47KTsKCUlSREFfQVNTRVJUKHNrYiAhPSBOVUxMLCByZXR1cm47KTsKCgkvKiBIaWRlIExNUCBhbmQgUElEIGhlYWRlciBmcm9tIGxheWVyIGFib3ZlICovCglza2JfcHVsbChza2IsIExNUF9IRUFERVIrTE1QX1BJRF9IRUFERVIpOwoKCWlmIChzZWxmLT5ub3RpZnkudWRhdGFfaW5kaWNhdGlvbikgewoJCS8qIERvbid0IGZvcmdldCB0byByZWZjb3VudCBpdCAtIHNlZSBpcmxhcF9kcml2ZXJfcmN2KCkuICovCgkJc2tiX2dldChza2IpOwoJCXNlbGYtPm5vdGlmeS51ZGF0YV9pbmRpY2F0aW9uKHNlbGYtPm5vdGlmeS5pbnN0YW5jZSwgc2VsZiwKCQkJCQkgICAgICBza2IpOwoJfQp9CiNlbmRpZiAvKiBDT05GSUdfSVJEQV9VTFRSQSAqLwoKLyoKICogUHJvcGFnYXRlIHN0YXR1cyBpbmRpY2F0aW9uIGZyb20gTEFQIHRvIExTQVBzICh2aWEgTE1QKQogKiBUaGlzIGRvbid0IHRyaWdnZXIgYW55IGNoYW5nZSBvZiBzdGF0ZSBpbiBsYXBfY2IsIGxtcF9jYiBvciBsc2FwX2NiLAogKiBhbmQgdGhlIGV2ZW50IGlzIHN0YXRlbGVzcywgdGhlcmVmb3JlIHdlIGNhbiBieXBhc3MgYm90aCBzdGF0ZSBtYWNoaW5lcwogKiBhbmQgc2VuZCB0aGUgZXZlbnQgZGlyZWN0IHRvIHRoZSBMU0FQIHVzZXIuCiAqIEplYW4gSUkKICovCnZvaWQgaXJsbXBfc3RhdHVzX2luZGljYXRpb24oc3RydWN0IGxhcF9jYiAqc2VsZiwKCQkJICAgICBMSU5LX1NUQVRVUyBsaW5rLCBMT0NLX1NUQVRVUyBsb2NrKQp7CglzdHJ1Y3QgbHNhcF9jYiAqbmV4dDsKCXN0cnVjdCBsc2FwX2NiICpjdXJyOwoKCS8qIFNlbmQgc3RhdHVzX2luZGljYXRpb24gdG8gYWxsIExTQVBzIHVzaW5nIHRoaXMgbGluayAqLwoJY3VyciA9IChzdHJ1Y3QgbHNhcF9jYiAqKSBoYXNoYmluX2dldF9maXJzdCggc2VsZi0+bHNhcHMpOwoJd2hpbGUgKE5VTEwgIT0gaGFzaGJpbl9maW5kX25leHQoc2VsZi0+bHNhcHMsIChsb25nKSBjdXJyLCBOVUxMLAoJCQkJCSAodm9pZCAqKSAmbmV4dCkgKSB7CgkJSVJEQV9BU1NFUlQoY3Vyci0+bWFnaWMgPT0gTE1QX0xTQVBfTUFHSUMsIHJldHVybjspOwoJCS8qCgkJICogIEluZm9ybSBzZXJ2aWNlIHVzZXIgaWYgaGUgaGFzIHJlcXVlc3RlZCBpdAoJCSAqLwoJCWlmIChjdXJyLT5ub3RpZnkuc3RhdHVzX2luZGljYXRpb24gIT0gTlVMTCkKCQkJY3Vyci0+bm90aWZ5LnN0YXR1c19pbmRpY2F0aW9uKGN1cnItPm5vdGlmeS5pbnN0YW5jZSwKCQkJCQkJICAgICAgIGxpbmssIGxvY2spOwoJCWVsc2UKCQkJSVJEQV9ERUJVRygyLCAiJXMoKSwgbm8gaGFuZGxlclxuIiwgX19GVU5DVElPTl9fKTsKCgkJY3VyciA9IG5leHQ7Cgl9Cn0KCi8qCiAqIFJlY2VpdmUgZmxvdyBjb250cm9sIGluZGljYXRpb24gZnJvbSBMQVAuCiAqIExBUCB3YW50IHVzIHRvIHNlbmQgaXQgb25lIG1vcmUgZnJhbWUuIFdlIGltcGxlbWVudCBhIHNpbXBsZSByb3VuZAogKiByb2JpbiBzY2hlZHVsZXIgYmV0d2VlbiB0aGUgYWN0aXZlIHNvY2tldHMgc28gdGhhdCB3ZSBnZXQgYSBiaXQgb2YKICogZmFpcm5lc3MuIE5vdGUgdGhhdCB0aGUgcm91bmQgcm9iaW4gaXMgZmFyIGZyb20gcGVyZmVjdCwgYnV0IGl0J3MKICogYmV0dGVyIHRoYW4gbm90aGluZy4KICogV2UgdGhlbiBwb2xsIHRoZSBzZWxlY3RlZCBzb2NrZXQgc28gdGhhdCB3ZSBjYW4gZG8gc3luY2hyb25vdXMKICogcmVmaWxsaW5nIG9mIElyTEFQICh3aGljaCBhbGxvdyB0byBtaW5pbWlzZSB0aGUgbnVtYmVyIG9mIGJ1ZmZlcnMpLgogKiBKZWFuIElJCiAqLwp2b2lkIGlybG1wX2Zsb3dfaW5kaWNhdGlvbihzdHJ1Y3QgbGFwX2NiICpzZWxmLCBMT0NBTF9GTE9XIGZsb3cpCnsKCXN0cnVjdCBsc2FwX2NiICpuZXh0OwoJc3RydWN0IGxzYXBfY2IgKmN1cnI7CglpbnQJbHNhcF90b2RvOwoKCUlSREFfQVNTRVJUKHNlbGYtPm1hZ2ljID09IExNUF9MQVBfTUFHSUMsIHJldHVybjspOwoJSVJEQV9BU1NFUlQoZmxvdyA9PSBGTE9XX1NUQVJULCByZXR1cm47KTsKCgkvKiBHZXQgdGhlIG51bWJlciBvZiBsc2FwLiBUaGF0J3MgdGhlIG9ubHkgc2FmZSB3YXkgdG8ga25vdwoJICogdGhhdCB3ZSBoYXZlIGxvb3BlZCBhcm91bmQuLi4gLSBKZWFuIElJICovCglsc2FwX3RvZG8gPSBIQVNIQklOX0dFVF9TSVpFKHNlbGYtPmxzYXBzKTsKCUlSREFfREVCVUcoNCwgIiVzKCkgOiAlZCBsc2FwcyB0byBzY2FuXG4iLCBfX0ZVTkNUSU9OX18sIGxzYXBfdG9kbyk7CgoJLyogUG9sbCBsc2FwIGluIG9yZGVyIHVudGlsIHRoZSBxdWV1ZSBpcyBmdWxsIG9yIHVudGlsIHdlCgkgKiB0cmllZCB0aGVtIGFsbC4KCSAqIE1vc3Qgb2Z0ZW4sIHRoZSBjdXJyZW50IExTQVAgd2lsbCBoYXZlIHNvbWV0aGluZyB0byBzZW5kLAoJICogc28gd2Ugd2lsbCBnbyB0aHJvdWdoIHRoaXMgbG9vcCBvbmx5IG9uY2UuIC0gSmVhbiBJSSAqLwoJd2hpbGUoKGxzYXBfdG9kby0tKSAmJgoJICAgICAgKElSTEFQX0dFVF9UWF9RVUVVRV9MRU4oc2VsZi0+aXJsYXApIDwgTEFQX0hJR0hfVEhSRVNIT0xEKSkgewoJCS8qIFRyeSB0byBmaW5kIHRoZSBuZXh0IGxzYXAgd2Ugc2hvdWxkIHBvbGwuICovCgkJbmV4dCA9IHNlbGYtPmZsb3dfbmV4dDsKCQkvKiBJZiB3ZSBoYXZlIG5vIGxzYXAsIHJlc3RhcnQgZnJvbSBmaXJzdCBvbmUgKi8KCQlpZihuZXh0ID09IE5VTEwpCgkJCW5leHQgPSAoc3RydWN0IGxzYXBfY2IgKikgaGFzaGJpbl9nZXRfZmlyc3Qoc2VsZi0+bHNhcHMpOwoJCS8qIFZlcmlmeSBjdXJyZW50IG9uZSBhbmQgZmluZCB0aGUgbmV4dCBvbmUgKi8KCQljdXJyID0gaGFzaGJpbl9maW5kX25leHQoc2VsZi0+bHNhcHMsIChsb25nKSBuZXh0LCBOVUxMLAoJCQkJCSAodm9pZCAqKSAmc2VsZi0+Zmxvd19uZXh0KTsKCQkvKiBVaC1vaC4uLiBQYXJhbm9pYSAqLwoJCWlmKGN1cnIgPT0gTlVMTCkKCQkJYnJlYWs7CgkJSVJEQV9ERUJVRyg0LCAiJXMoKSA6IGN1cnIgaXMgJXAsIG5leHQgd2FzICVwIGFuZCBpcyBub3cgJXAsIHN0aWxsICVkIHRvIGdvIC0gcXVldWUgbGVuID0gJWRcbiIsIF9fRlVOQ1RJT05fXywgY3VyciwgbmV4dCwgc2VsZi0+Zmxvd19uZXh0LCBsc2FwX3RvZG8sIElSTEFQX0dFVF9UWF9RVUVVRV9MRU4oc2VsZi0+aXJsYXApKTsKCgkJLyogSW5mb3JtIGxzYXAgdXNlciB0aGF0IGl0IGNhbiBzZW5kIG9uZSBtb3JlIHBhY2tldC4gKi8KCQlpZiAoY3Vyci0+bm90aWZ5LmZsb3dfaW5kaWNhdGlvbiAhPSBOVUxMKQoJCQljdXJyLT5ub3RpZnkuZmxvd19pbmRpY2F0aW9uKGN1cnItPm5vdGlmeS5pbnN0YW5jZSwKCQkJCQkJICAgICBjdXJyLCBmbG93KTsKCQllbHNlCgkJCUlSREFfREVCVUcoMSwgIiVzKCksIG5vIGhhbmRsZXJcbiIsIF9fRlVOQ1RJT05fXyk7Cgl9Cn0KCiNpZiAwCi8qCiAqIEZ1bmN0aW9uIGlybG1wX2hpbnRfdG9fc2VydmljZSAoaGludCkKICoKICogICAgUmV0dXJucyBhIGxpc3Qgb2YgYWxsIHNlcnZpY3MgY29udGFpbmVkIGluIHRoZSBnaXZlbiBoaW50IGJpdHMuIFRoaXMKICogICAgZnVuY3Rpb24gYXNzdW1lcyB0aGF0IHRoZSBoaW50IGJpdHMgaGF2ZSB0aGUgc2l6ZSBvZiB0d28gYnl0ZXMgb25seQogKi8KX191OCAqaXJsbXBfaGludF90b19zZXJ2aWNlKF9fdTggKmhpbnQpCnsKCV9fdTggKnNlcnZpY2U7CglpbnQgaSA9IDA7CgoJLyoKCSAqIEFsbG9jYXRlIGFycmF5IHRvIHN0b3JlIHNlcnZpY2VzIGluLiAxNiBlbnRyaWVzIHNob3VsZCBiZSBzYWZlCgkgKiBzaW5jZSB3ZSBjdXJyZW50bHkgb25seSBzdXBwb3J0IDIgaGludCBieXRlcwoJICovCglzZXJ2aWNlID0ga21hbGxvYygxNiwgR0ZQX0FUT01JQyk7CglpZiAoIXNlcnZpY2UpIHsKCQlJUkRBX0RFQlVHKDEsICIlcygpLCBVbmFibGUgdG8ga21hbGxvYyFcbiIsIF9fRlVOQ1RJT05fXyk7CgkJcmV0dXJuIE5VTEw7Cgl9CgoJaWYgKCFoaW50WzBdKSB7CgkJSVJEQV9ERUJVRygxLCAiPE5vbmU+XG4iKTsKCQlrZnJlZShzZXJ2aWNlKTsKCQlyZXR1cm4gTlVMTDsKCX0KCWlmIChoaW50WzBdICYgSElOVF9QTlApCgkJSVJEQV9ERUJVRygxLCAiUG5QIENvbXBhdGlibGUgIik7CglpZiAoaGludFswXSAmIEhJTlRfUERBKQoJCUlSREFfREVCVUcoMSwgIlBEQS9QYWxtdG9wICIpOwoJaWYgKGhpbnRbMF0gJiBISU5UX0NPTVBVVEVSKQoJCUlSREFfREVCVUcoMSwgIkNvbXB1dGVyICIpOwoJaWYgKGhpbnRbMF0gJiBISU5UX1BSSU5URVIpIHsKCQlJUkRBX0RFQlVHKDEsICJQcmludGVyICIpOwoJCXNlcnZpY2VbaSsrXSA9IFNfUFJJTlRFUjsKCX0KCWlmIChoaW50WzBdICYgSElOVF9NT0RFTSkKCQlJUkRBX0RFQlVHKDEsICJNb2RlbSAiKTsKCWlmIChoaW50WzBdICYgSElOVF9GQVgpCgkJSVJEQV9ERUJVRygxLCAiRmF4ICIpOwoJaWYgKGhpbnRbMF0gJiBISU5UX0xBTikgewoJCUlSREFfREVCVUcoMSwgIkxBTiBBY2Nlc3MgIik7CgkJc2VydmljZVtpKytdID0gU19MQU47Cgl9CgkvKgoJICogIFRlc3QgaWYgZXh0ZW5zaW9uIGJ5dGUgZXhpc3RzLiBUaGlzIGJ5dGUgd2lsbCB1c3VhbGx5IGJlCgkgKiAgdGhlcmUsIGJ1dCB0aGlzIGlzIG5vdCByZWFsbHkgcmVxdWlyZWQgYnkgdGhlIHN0YW5kYXJkLgoJICogIChJckxNUCBwLiAyOSkKCSAqLwoJaWYgKGhpbnRbMF0gJiBISU5UX0VYVEVOU0lPTikgewoJCWlmIChoaW50WzFdICYgSElOVF9URUxFUEhPTlkpIHsKCQkJSVJEQV9ERUJVRygxLCAiVGVsZXBob255ICIpOwoJCQlzZXJ2aWNlW2krK10gPSBTX1RFTEVQSE9OWTsKCQl9IGlmIChoaW50WzFdICYgSElOVF9GSUxFX1NFUlZFUikKCQkJSVJEQV9ERUJVRygxLCAiRmlsZSBTZXJ2ZXIgIik7CgoJCWlmIChoaW50WzFdICYgSElOVF9DT01NKSB7CgkJCUlSREFfREVCVUcoMSwgIklyQ09NTSAiKTsKCQkJc2VydmljZVtpKytdID0gU19DT01NOwoJCX0KCQlpZiAoaGludFsxXSAmIEhJTlRfT0JFWCkgewoJCQlJUkRBX0RFQlVHKDEsICJJck9CRVggIik7CgkJCXNlcnZpY2VbaSsrXSA9IFNfT0JFWDsKCQl9Cgl9CglJUkRBX0RFQlVHKDEsICJcbiIpOwoKCS8qIFNvIHRoYXQgY2xpZW50IGNhbiBiZSBub3RpZmllZCBhYm91dCBhbnkgZGlzY292ZXJ5ICovCglzZXJ2aWNlW2krK10gPSBTX0FOWTsKCglzZXJ2aWNlW2ldID0gU19FTkQ7CgoJcmV0dXJuIHNlcnZpY2U7Cn0KI2VuZGlmCgpzdGF0aWMgY29uc3QgX191MTYgc2VydmljZV9oaW50X21hcHBpbmdbU19FTkRdWzJdID0gewoJeyBISU5UX1BOUCwJCTAgfSwJCQkvKiBTX1BOUCAqLwoJeyBISU5UX1BEQSwJCTAgfSwJCQkvKiBTX1BEQSAqLwoJeyBISU5UX0NPTVBVVEVSLAkwIH0sCQkJLyogU19DT01QVVRFUiAqLwoJeyBISU5UX1BSSU5URVIsCQkwIH0sCQkJLyogU19QUklOVEVSICovCgl7IEhJTlRfTU9ERU0sCQkwIH0sCQkJLyogU19NT0RFTSAqLwoJeyBISU5UX0ZBWCwJCTAgfSwJCQkvKiBTX0ZBWCAqLwoJeyBISU5UX0xBTiwJCTAgfSwJCQkvKiBTX0xBTiAqLwoJeyBISU5UX0VYVEVOU0lPTiwJSElOVF9URUxFUEhPTlkgfSwJLyogU19URUxFUEhPTlkgKi8KCXsgSElOVF9FWFRFTlNJT04sCUhJTlRfQ09NTSB9LAkJLyogU19DT01NICovCgl7IEhJTlRfRVhURU5TSU9OLAlISU5UX09CRVggfSwJCS8qIFNfT0JFWCAqLwoJeyAweEZGLAkJCTB4RkYgfSwJCQkvKiBTX0FOWSAqLwp9OwoKLyoKICogRnVuY3Rpb24gaXJsbXBfc2VydmljZV90b19oaW50IChzZXJ2aWNlKQogKgogKiAgICBDb252ZXJ0cyBhIHNlcnZpY2UgdHlwZSwgdG8gYSBoaW50IGJpdAogKgogKiAgICBSZXR1cm5zOiBhIDE2IGJpdCBoaW50IHZhbHVlLCB3aXRoIHRoZSBzZXJ2aWNlIGJpdCBzZXQKICovCl9fdTE2IGlybG1wX3NlcnZpY2VfdG9faGludChpbnQgc2VydmljZSkKewoJX191MTZfaG9zdF9vcmRlciBoaW50OwoKCWhpbnQuYnl0ZVswXSA9IHNlcnZpY2VfaGludF9tYXBwaW5nW3NlcnZpY2VdWzBdOwoJaGludC5ieXRlWzFdID0gc2VydmljZV9oaW50X21hcHBpbmdbc2VydmljZV1bMV07CgoJcmV0dXJuIGhpbnQud29yZDsKfQpFWFBPUlRfU1lNQk9MKGlybG1wX3NlcnZpY2VfdG9faGludCk7CgovKgogKiBGdW5jdGlvbiBpcmxtcF9yZWdpc3Rlcl9zZXJ2aWNlIChzZXJ2aWNlKQogKgogKiAgICBSZWdpc3RlciBsb2NhbCBzZXJ2aWNlIHdpdGggSXJMTVAKICoKICovCnZvaWQgKmlybG1wX3JlZ2lzdGVyX3NlcnZpY2UoX191MTYgaGludHMpCnsKCWlybG1wX3NlcnZpY2VfdCAqc2VydmljZTsKCglJUkRBX0RFQlVHKDQsICIlcygpLCBoaW50cyA9ICUwNHhcbiIsIF9fRlVOQ1RJT05fXywgaGludHMpOwoKCS8qIE1ha2UgYSBuZXcgcmVnaXN0cmF0aW9uICovCglzZXJ2aWNlID0ga21hbGxvYyhzaXplb2YoaXJsbXBfc2VydmljZV90KSwgR0ZQX0FUT01JQyk7CglpZiAoIXNlcnZpY2UpIHsKCQlJUkRBX0RFQlVHKDEsICIlcygpLCBVbmFibGUgdG8ga21hbGxvYyFcbiIsIF9fRlVOQ1RJT05fXyk7CgkJcmV0dXJuIE5VTEw7Cgl9CglzZXJ2aWNlLT5oaW50cy53b3JkID0gaGludHM7CgloYXNoYmluX2luc2VydChpcmxtcC0+c2VydmljZXMsIChpcmRhX3F1ZXVlX3QgKikgc2VydmljZSwKCQkgICAgICAgKGxvbmcpIHNlcnZpY2UsIE5VTEwpOwoKCWlybG1wLT5oaW50cy53b3JkIHw9IGhpbnRzOwoKCXJldHVybiAodm9pZCAqKXNlcnZpY2U7Cn0KRVhQT1JUX1NZTUJPTChpcmxtcF9yZWdpc3Rlcl9zZXJ2aWNlKTsKCi8qCiAqIEZ1bmN0aW9uIGlybG1wX3VucmVnaXN0ZXJfc2VydmljZSAoaGFuZGxlKQogKgogKiAgICBVbnJlZ2lzdGVyIHNlcnZpY2Ugd2l0aCBJckxNUC4KICoKICogICAgUmV0dXJuczogMCBvbiBzdWNjZXNzLCAtMSBvbiBlcnJvcgogKi8KaW50IGlybG1wX3VucmVnaXN0ZXJfc2VydmljZSh2b2lkICpoYW5kbGUpCnsKCWlybG1wX3NlcnZpY2VfdCAqc2VydmljZTsKCXVuc2lnbmVkIGxvbmcgZmxhZ3M7CgoJSVJEQV9ERUJVRyg0LCAiJXMoKVxuIiwgX19GVU5DVElPTl9fKTsKCglpZiAoIWhhbmRsZSkKCQlyZXR1cm4gLTE7CgoJLyogQ2FsbGVyIG1heSBjYWxsIHdpdGggaW52YWxpZCBoYW5kbGUgKGl0J3MgbGVnYWwpIC0gSmVhbiBJSSAqLwoJc2VydmljZSA9IGhhc2hiaW5fbG9ja19maW5kKGlybG1wLT5zZXJ2aWNlcywgKGxvbmcpIGhhbmRsZSwgTlVMTCk7CglpZiAoIXNlcnZpY2UpIHsKCQlJUkRBX0RFQlVHKDEsICIlcygpLCBVbmtub3duIHNlcnZpY2UhXG4iLCBfX0ZVTkNUSU9OX18pOwoJCXJldHVybiAtMTsKCX0KCgloYXNoYmluX3JlbW92ZV90aGlzKGlybG1wLT5zZXJ2aWNlcywgKGlyZGFfcXVldWVfdCAqKSBzZXJ2aWNlKTsKCWtmcmVlKHNlcnZpY2UpOwoKCS8qIFJlbW92ZSBvbGQgaGludCBiaXRzICovCglpcmxtcC0+aGludHMud29yZCA9IDA7CgoJLyogUmVmcmVzaCBjdXJyZW50IGhpbnQgYml0cyAqLwoJc3Bpbl9sb2NrX2lycXNhdmUoJmlybG1wLT5zZXJ2aWNlcy0+aGJfc3BpbmxvY2ssIGZsYWdzKTsKICAgICAgICBzZXJ2aWNlID0gKGlybG1wX3NlcnZpY2VfdCAqKSBoYXNoYmluX2dldF9maXJzdChpcmxtcC0+c2VydmljZXMpOwogICAgICAgIHdoaWxlIChzZXJ2aWNlKSB7CgkJaXJsbXAtPmhpbnRzLndvcmQgfD0gc2VydmljZS0+aGludHMud29yZDsKCiAgICAgICAgICAgICAgICBzZXJ2aWNlID0gKGlybG1wX3NlcnZpY2VfdCAqKWhhc2hiaW5fZ2V0X25leHQoaXJsbXAtPnNlcnZpY2VzKTsKICAgICAgICB9CglzcGluX3VubG9ja19pcnFyZXN0b3JlKCZpcmxtcC0+c2VydmljZXMtPmhiX3NwaW5sb2NrLCBmbGFncyk7CglyZXR1cm4gMDsKfQpFWFBPUlRfU1lNQk9MKGlybG1wX3VucmVnaXN0ZXJfc2VydmljZSk7CgovKgogKiBGdW5jdGlvbiBpcmxtcF9yZWdpc3Rlcl9jbGllbnQgKGhpbnRfbWFzaywgY2FsbGJhY2sxLCBjYWxsYmFjazIpCiAqCiAqICAgIFJlZ2lzdGVyIGEgbG9jYWwgY2xpZW50IHdpdGggSXJMTVAKICoJRmlyc3QgY2FsbGJhY2sgaXMgc2VsZWN0aXZlIGRpc2NvdmVyeSAoYmFzZWQgb24gaGludHMpCiAqCVNlY29uZCBjYWxsYmFjayBpcyBmb3Igc2VsZWN0aXZlIGRpc2NvdmVyeSBleHBpcmllcwogKgogKiAgICBSZXR1cm5zOiBoYW5kbGUgPiAwIG9uIHN1Y2Nlc3MsIDAgb24gZXJyb3IKICovCnZvaWQgKmlybG1wX3JlZ2lzdGVyX2NsaWVudChfX3UxNiBoaW50X21hc2ssIERJU0NPVkVSWV9DQUxMQkFDSzEgZGlzY29fY2xiLAoJCQkgICAgRElTQ09WRVJZX0NBTExCQUNLMiBleHBpcl9jbGIsIHZvaWQgKnByaXYpCnsKCWlybG1wX2NsaWVudF90ICpjbGllbnQ7CgoJSVJEQV9ERUJVRygxLCAiJXMoKVxuIiwgX19GVU5DVElPTl9fKTsKCUlSREFfQVNTRVJUKGlybG1wICE9IE5VTEwsIHJldHVybiBOVUxMOyk7CgoJLyogTWFrZSBhIG5ldyByZWdpc3RyYXRpb24gKi8KCWNsaWVudCA9IGttYWxsb2Moc2l6ZW9mKGlybG1wX2NsaWVudF90KSwgR0ZQX0FUT01JQyk7CglpZiAoIWNsaWVudCkgewoJCUlSREFfREVCVUcoIDEsICIlcygpLCBVbmFibGUgdG8ga21hbGxvYyFcbiIsIF9fRlVOQ1RJT05fXyk7CgkJcmV0dXJuIE5VTEw7Cgl9CgoJLyogUmVnaXN0ZXIgdGhlIGRldGFpbHMgKi8KCWNsaWVudC0+aGludF9tYXNrLndvcmQgPSBoaW50X21hc2s7CgljbGllbnQtPmRpc2NvX2NhbGxiYWNrID0gZGlzY29fY2xiOwoJY2xpZW50LT5leHBpcl9jYWxsYmFjayA9IGV4cGlyX2NsYjsKCWNsaWVudC0+cHJpdiA9IHByaXY7CgoJaGFzaGJpbl9pbnNlcnQoaXJsbXAtPmNsaWVudHMsIChpcmRhX3F1ZXVlX3QgKikgY2xpZW50LAoJCSAgICAgICAobG9uZykgY2xpZW50LCBOVUxMKTsKCglyZXR1cm4gKHZvaWQgKikgY2xpZW50Owp9CkVYUE9SVF9TWU1CT0woaXJsbXBfcmVnaXN0ZXJfY2xpZW50KTsKCi8qCiAqIEZ1bmN0aW9uIGlybG1wX3VwZGF0ZV9jbGllbnQgKGhhbmRsZSwgaGludF9tYXNrLCBjYWxsYmFjazEsIGNhbGxiYWNrMikKICoKICogICAgVXBkYXRlcyBzcGVjaWZpZWQgY2xpZW50IChoYW5kbGUpIHdpdGggcG9zc2libHkgbmV3IGhpbnRfbWFzayBhbmQKICogICAgY2FsbGJhY2sKICoKICogICAgUmV0dXJuczogMCBvbiBzdWNjZXNzLCAtMSBvbiBlcnJvcgogKi8KaW50IGlybG1wX3VwZGF0ZV9jbGllbnQodm9pZCAqaGFuZGxlLCBfX3UxNiBoaW50X21hc2ssCgkJCURJU0NPVkVSWV9DQUxMQkFDSzEgZGlzY29fY2xiLAoJCQlESVNDT1ZFUllfQ0FMTEJBQ0syIGV4cGlyX2NsYiwgdm9pZCAqcHJpdikKewoJaXJsbXBfY2xpZW50X3QgKmNsaWVudDsKCglpZiAoIWhhbmRsZSkKCQlyZXR1cm4gLTE7CgoJY2xpZW50ID0gaGFzaGJpbl9sb2NrX2ZpbmQoaXJsbXAtPmNsaWVudHMsIChsb25nKSBoYW5kbGUsIE5VTEwpOwoJaWYgKCFjbGllbnQpIHsKCQlJUkRBX0RFQlVHKDEsICIlcygpLCBVbmtub3duIGNsaWVudCFcbiIsIF9fRlVOQ1RJT05fXyk7CgkJcmV0dXJuIC0xOwoJfQoKCWNsaWVudC0+aGludF9tYXNrLndvcmQgPSBoaW50X21hc2s7CgljbGllbnQtPmRpc2NvX2NhbGxiYWNrID0gZGlzY29fY2xiOwoJY2xpZW50LT5leHBpcl9jYWxsYmFjayA9IGV4cGlyX2NsYjsKCWNsaWVudC0+cHJpdiA9IHByaXY7CgoJcmV0dXJuIDA7Cn0KRVhQT1JUX1NZTUJPTChpcmxtcF91cGRhdGVfY2xpZW50KTsKCi8qCiAqIEZ1bmN0aW9uIGlybG1wX3VucmVnaXN0ZXJfY2xpZW50IChoYW5kbGUpCiAqCiAqICAgIFJldHVybnM6IDAgb24gc3VjY2VzcywgLTEgb24gZXJyb3IKICoKICovCmludCBpcmxtcF91bnJlZ2lzdGVyX2NsaWVudCh2b2lkICpoYW5kbGUpCnsKCXN0cnVjdCBpcmxtcF9jbGllbnQgKmNsaWVudDsKCglJUkRBX0RFQlVHKDQsICIlcygpXG4iLCBfX0ZVTkNUSU9OX18pOwoKCWlmICghaGFuZGxlKQoJCXJldHVybiAtMTsKCgkvKiBDYWxsZXIgbWF5IGNhbGwgd2l0aCBpbnZhbGlkIGhhbmRsZSAoaXQncyBsZWdhbCkgLSBKZWFuIElJICovCgljbGllbnQgPSBoYXNoYmluX2xvY2tfZmluZChpcmxtcC0+Y2xpZW50cywgKGxvbmcpIGhhbmRsZSwgTlVMTCk7CglpZiAoIWNsaWVudCkgewoJCUlSREFfREVCVUcoMSwgIiVzKCksIFVua25vd24gY2xpZW50IVxuIiwgX19GVU5DVElPTl9fKTsKCQlyZXR1cm4gLTE7Cgl9CgoJSVJEQV9ERUJVRyg0LCAiJXMoKSwgcmVtb3ZpbmcgY2xpZW50IVxuIiwgX19GVU5DVElPTl9fKTsKCWhhc2hiaW5fcmVtb3ZlX3RoaXMoaXJsbXAtPmNsaWVudHMsIChpcmRhX3F1ZXVlX3QgKikgY2xpZW50KTsKCWtmcmVlKGNsaWVudCk7CgoJcmV0dXJuIDA7Cn0KRVhQT1JUX1NZTUJPTChpcmxtcF91bnJlZ2lzdGVyX2NsaWVudCk7CgovKgogKiBGdW5jdGlvbiBpcmxtcF9zbHNhcF9pbnVzZSAoc2xzYXApCiAqCiAqICAgIENoZWNrIGlmIHRoZSBnaXZlbiBzb3VyY2UgTFNBUCBzZWxlY3RvciBpcyBpbiB1c2UKICoKICogVGhpcyBmdW5jdGlvbiBpcyBjbGVhcmx5IG5vdCB2ZXJ5IGVmZmljaWVudC4gT24gdGhlIG1pdGlnYXRpbmcgc2lkZSwgdGhlCiAqIHN0YWNrIG1ha2Ugc3VyZSB0aGF0IGluIDk5JSBvZiB0aGUgY2FzZXMsIHdlIGFyZSBjYWxsZWQgb25seSBvbmNlCiAqIGZvciBlYWNoIHNvY2tldCBhbGxvY2F0aW9uLiBXZSBjb3VsZCBwcm9iYWJseSBrZWVwIGEgYml0bWFwCiAqIG9mIHRoZSBhbGxvY2F0ZWQgTFNBUCwgYnV0IEknbSBub3Qgc3VyZSB0aGUgY29tcGxleGl0eSBpcyB3b3J0aCBpdC4KICogSmVhbiBJSQogKi8Kc3RhdGljIGludCBpcmxtcF9zbHNhcF9pbnVzZShfX3U4IHNsc2FwX3NlbCkKewoJc3RydWN0IGxzYXBfY2IgKnNlbGY7CglzdHJ1Y3QgbGFwX2NiICpsYXA7Cgl1bnNpZ25lZCBsb25nIGZsYWdzOwoKCUlSREFfQVNTRVJUKGlybG1wICE9IE5VTEwsIHJldHVybiBUUlVFOyk7CglJUkRBX0FTU0VSVChpcmxtcC0+bWFnaWMgPT0gTE1QX01BR0lDLCByZXR1cm4gVFJVRTspOwoJSVJEQV9BU1NFUlQoc2xzYXBfc2VsICE9IExTQVBfQU5ZLCByZXR1cm4gVFJVRTspOwoKCUlSREFfREVCVUcoNCwgIiVzKClcbiIsIF9fRlVOQ1RJT05fXyk7CgojaWZkZWYgQ09ORklHX0lSREFfVUxUUkEKCS8qIEFjY2VwdCBhbGwgYmluZGluZ3MgdG8gdGhlIGNvbm5lY3Rpb25sZXNzIExTQVAgKi8KCWlmIChzbHNhcF9zZWwgPT0gTFNBUF9DT05OTEVTUykKCQlyZXR1cm4gRkFMU0U7CiNlbmRpZiAvKiBDT05GSUdfSVJEQV9VTFRSQSAqLwoKCS8qIFZhbGlkIHZhbHVlcyBhcmUgYmV0d2VlbiAwIGFuZCAxMjcgKDB4MC0weDZGKSAqLwoJaWYgKHNsc2FwX3NlbCA+IExTQVBfTUFYKQoJCXJldHVybiBUUlVFOwoKCS8qCgkgKiAgQ2hlY2sgaWYgc2xzYXAgaXMgYWxyZWFkeSBpbiB1c2UuIFRvIGRvIHRoaXMgd2UgaGF2ZSB0byBsb29wIG92ZXIKCSAqICBldmVyeSBJckxBUCBjb25uZWN0aW9uIGFuZCBjaGVjayBldmVyeSBMU0FQIGFzc29jaWF0ZWQgd2l0aCBlYWNoCgkgKiAgdGhlIGNvbm5lY3Rpb24uCgkgKi8KCXNwaW5fbG9ja19pcnFzYXZlX25lc3RlZCgmaXJsbXAtPmxpbmtzLT5oYl9zcGlubG9jaywgZmxhZ3MsCgkJCVNJTkdMRV9ERVBUSF9ORVNUSU5HKTsKCWxhcCA9IChzdHJ1Y3QgbGFwX2NiICopIGhhc2hiaW5fZ2V0X2ZpcnN0KGlybG1wLT5saW5rcyk7Cgl3aGlsZSAobGFwICE9IE5VTEwpIHsKCQlJUkRBX0FTU0VSVChsYXAtPm1hZ2ljID09IExNUF9MQVBfTUFHSUMsIGdvdG8gZXJybGFwOyk7CgoJCS8qIENhcmVmdWwgZm9yIHByaW9yaXR5IGludmVyc2lvbnMgaGVyZSAhCgkJICogaXJsbXAtPmxpbmtzIGlzIG5ldmVyIHRha2VuIHdoaWxlIGFub3RoZXIgSXJEQQoJCSAqIHNwaW5sb2NrIGlzIGhlbGQsIHNvIHdlIGFyZSBzYWZlLiBKZWFuIElJICovCgkJc3Bpbl9sb2NrKCZsYXAtPmxzYXBzLT5oYl9zcGlubG9jayk7CgoJCS8qIEZvciB0aGlzIElyTEFQLCBjaGVjayBhbGwgdGhlIExTQVBzICovCgkJc2VsZiA9IChzdHJ1Y3QgbHNhcF9jYiAqKSBoYXNoYmluX2dldF9maXJzdChsYXAtPmxzYXBzKTsKCQl3aGlsZSAoc2VsZiAhPSBOVUxMKSB7CgkJCUlSREFfQVNTRVJUKHNlbGYtPm1hZ2ljID09IExNUF9MU0FQX01BR0lDLAoJCQkJICAgIGdvdG8gZXJybHNhcDspOwoKCQkJaWYgKChzZWxmLT5zbHNhcF9zZWwgPT0gc2xzYXBfc2VsKSkgewoJCQkJSVJEQV9ERUJVRyg0LCAiU291cmNlIExTQVAgc2VsZWN0b3I9JTAyeCBpbiB1c2VcbiIsCgkJCQkJICAgc2VsZi0+c2xzYXBfc2VsKTsKCQkJCWdvdG8gZXJybHNhcDsKCQkJfQoJCQlzZWxmID0gKHN0cnVjdCBsc2FwX2NiKikgaGFzaGJpbl9nZXRfbmV4dChsYXAtPmxzYXBzKTsKCQl9CgkJc3Bpbl91bmxvY2soJmxhcC0+bHNhcHMtPmhiX3NwaW5sb2NrKTsKCgkJLyogTmV4dCBMQVAgKi8KCQlsYXAgPSAoc3RydWN0IGxhcF9jYiAqKSBoYXNoYmluX2dldF9uZXh0KGlybG1wLT5saW5rcyk7Cgl9CglzcGluX3VubG9ja19pcnFyZXN0b3JlKCZpcmxtcC0+bGlua3MtPmhiX3NwaW5sb2NrLCBmbGFncyk7CgoJLyoKCSAqIFNlcnZlciBzb2NrZXRzIGFyZSB0eXBpY2FsbHkgd2FpdGluZyBmb3IgY29ubmVjdGlvbnMgYW5kCgkgKiB0aGVyZWZvcmUgcmVzaWRlIGluIHRoZSB1bmNvbm5lY3RlZCBsaXN0LiBXZSBkb24ndCB3YW50CgkgKiB0byBnaXZlIG91dCB0aGVpciBMU0FQcyBmb3Igb2J2aW91cyByZWFzb25zLi4uCgkgKiBKZWFuIElJCgkgKi8KCXNwaW5fbG9ja19pcnFzYXZlKCZpcmxtcC0+dW5jb25uZWN0ZWRfbHNhcHMtPmhiX3NwaW5sb2NrLCBmbGFncyk7CgoJc2VsZiA9IChzdHJ1Y3QgbHNhcF9jYiAqKSBoYXNoYmluX2dldF9maXJzdChpcmxtcC0+dW5jb25uZWN0ZWRfbHNhcHMpOwoJd2hpbGUgKHNlbGYgIT0gTlVMTCkgewoJCUlSREFfQVNTRVJUKHNlbGYtPm1hZ2ljID09IExNUF9MU0FQX01BR0lDLCBnb3RvIGVycnVuY29uOyk7CgkJaWYgKChzZWxmLT5zbHNhcF9zZWwgPT0gc2xzYXBfc2VsKSkgewoJCQlJUkRBX0RFQlVHKDQsICJTb3VyY2UgTFNBUCBzZWxlY3Rvcj0lMDJ4IGluIHVzZSAodW5jb25uZWN0ZWQpXG4iLAoJCQkJICAgc2VsZi0+c2xzYXBfc2VsKTsKCQkJZ290byBlcnJ1bmNvbjsKCQl9CgkJc2VsZiA9IChzdHJ1Y3QgbHNhcF9jYiopIGhhc2hiaW5fZ2V0X25leHQoaXJsbXAtPnVuY29ubmVjdGVkX2xzYXBzKTsKCX0KCXNwaW5fdW5sb2NrX2lycXJlc3RvcmUoJmlybG1wLT51bmNvbm5lY3RlZF9sc2Fwcy0+aGJfc3BpbmxvY2ssIGZsYWdzKTsKCglyZXR1cm4gRkFMU0U7CgoJLyogRXJyb3IgZXhpdCBmcm9tIHdpdGhpbiBvbmUgb2YgdGhlIHR3byBuZXN0ZWQgbG9vcHMuCgkgKiBNYWtlIHN1cmUgd2UgcmVsZWFzZSB0aGUgcmlnaHQgc3BpbmxvY2sgaW4gdGhlIHJpZ2ggb3JkZXIuCgkgKiBKZWFuIElJICovCmVycmxzYXA6CglzcGluX3VubG9jaygmbGFwLT5sc2Fwcy0+aGJfc3BpbmxvY2spOwpJUkRBX0FTU0VSVF9MQUJFTChlcnJsYXA6KQoJc3Bpbl91bmxvY2tfaXJxcmVzdG9yZSgmaXJsbXAtPmxpbmtzLT5oYl9zcGlubG9jaywgZmxhZ3MpOwoJcmV0dXJuIFRSVUU7CgoJLyogRXJyb3IgZXhpdCBmcm9tIHdpdGhpbiB0aGUgdW5jb25uZWN0ZWQgbG9vcC4KCSAqIEp1c3Qgb25lIHNwaW5sb2NrIHRvIHJlbGVhc2UuLi4gSmVhbiBJSSAqLwplcnJ1bmNvbjoKCXNwaW5fdW5sb2NrX2lycXJlc3RvcmUoJmlybG1wLT51bmNvbm5lY3RlZF9sc2Fwcy0+aGJfc3BpbmxvY2ssIGZsYWdzKTsKCXJldHVybiBUUlVFOwp9CgovKgogKiBGdW5jdGlvbiBpcmxtcF9maW5kX2ZyZWVfc2xzYXAgKCkKICoKICogICAgRmluZCBhIGZyZWUgc291cmNlIExTQVAgdG8gdXNlLiBUaGlzIGZ1bmN0aW9uIGlzIGNhbGxlZCBpZiB0aGUgc2VydmljZQogKiAgICB1c2VyIGhhcyByZXF1ZXN0ZWQgYSBzb3VyY2UgTFNBUCBlcXVhbCB0byBMTV9BTlkKICovCnN0YXRpYyBfX3U4IGlybG1wX2ZpbmRfZnJlZV9zbHNhcCh2b2lkKQp7CglfX3U4IGxzYXBfc2VsOwoJaW50IHdyYXBwZWQgPSAwOwoKCUlSREFfQVNTRVJUKGlybG1wICE9IE5VTEwsIHJldHVybiAtMTspOwoJSVJEQV9BU1NFUlQoaXJsbXAtPm1hZ2ljID09IExNUF9NQUdJQywgcmV0dXJuIC0xOyk7CgoJLyogTW9zdCB1c2VycyBkb24ndCByZWFsbHkgY2FyZSB3aGljaCBMU0FQcyB0aGV5IGFyZSBnaXZlbiwKCSAqIGFuZCB0aGVyZWZvcmUgd2UgYXV0b21hdGljYWxseSBnaXZlIHRoZW0gYSBmcmVlIExTQVAuCgkgKiBUaGlzIGZ1bmN0aW9uIHRyeSB0byBmaW5kIGEgc3VpdGFibGUgTFNBUCwgaS5lLiB3aGljaCBpcwoJICogbm90IGluIHVzZSBhbmQgaXMgd2l0aGluIHRoZSBhY2NlcHRhYmxlIHJhbmdlLiBKZWFuIElJICovCgoJZG8gewoJCS8qIEFsd2F5cyBpbmNyZW1lbnQgdG8gTFNBUCBudW1iZXIgYmVmb3JlIHVzaW5nIGl0LgoJCSAqIEluIHRoZW9yeSwgd2UgY291bGQgcmV1c2UgdGhlIGxhc3QgTFNBUCBudW1iZXIsIGFzIGxvbmcKCQkgKiBhcyBpdCBpcyBubyBsb25nZXIgaW4gdXNlLiBTb21lIElyREEgc3RhY2sgZG8gdGhhdC4KCQkgKiBIb3dldmVyLCB0aGUgcHJldmlvdXMgc29ja2V0IG1heSBiZSBoYWxmIGNsb3NlZCwgaS5lLgoJCSAqIHdlIGNsb3NlZCBpdCwgd2UgdGhpbmsgaXQncyBubyBsb25nZXIgaW4gdXNlLCBidXQgdGhlCgkJICogb3RoZXIgc2lkZSBkaWQgbm90IHJlY2VpdmUgb3VyIGNsb3NlIGFuZCB0aGluayBpdCdzCgkJICogYWN0aXZlIGFuZCBzdGlsbCBzZW5kIGRhdGEgb24gaXQuCgkJICogVGhpcyBpcyBzaW1pbGFyIHRvIHdoYXQgaXMgZG9uZSB3aXRoIFBJRHMgYW5kIFRDUCBwb3J0cy4KCQkgKiBBbHNvLCB0aGlzIHJlZHVjZSB0aGUgbnVtYmVyIG9mIGNhbGxzIHRvIGlybG1wX3Nsc2FwX2ludXNlKCkKCQkgKiB3aGljaCBpcyBhbiBleHBlbnNpdmUgZnVuY3Rpb24gdG8gY2FsbC4KCQkgKiBKZWFuIElJICovCgkJaXJsbXAtPmxhc3RfbHNhcF9zZWwrKzsKCgkJLyogQ2hlY2sgaWYgd2UgbmVlZCB0byB3cmFwYXJvdW5kICgweDcwLTB4N2YgYXJlIHJlc2VydmVkKSAqLwoJCWlmIChpcmxtcC0+bGFzdF9sc2FwX3NlbCA+IExTQVBfTUFYKSB7CgkJCS8qIDB4MDAtMHgxMCBhcmUgYWxzbyByZXNlcnZlZCBmb3Igd2VsbCBrbm93IHBvcnRzICovCgkJCWlybG1wLT5sYXN0X2xzYXBfc2VsID0gMHgxMDsKCgkJCS8qIE1ha2Ugc3VyZSB3ZSB0ZXJtaW5hdGUgdGhlIGxvb3AgKi8KCQkJaWYgKHdyYXBwZWQrKykgewoJCQkJSVJEQV9FUlJPUigiJXM6IG5vIG1vcmUgZnJlZSBMU0FQcyAhXG4iLAoJCQkJCSAgIF9fRlVOQ1RJT05fXyk7CgkJCQlyZXR1cm4gMDsKCQkJfQoJCX0KCgkJLyogSWYgdGhlIExTQVAgaXMgaW4gdXNlLCB0cnkgdGhlIG5leHQgb25lLgoJCSAqIERlc3BpdGUgdGhlIGF1dG9pbmNyZW1lbnQsIHdlIG5lZWQgdG8gY2hlY2sgaWYgdGhlIGxzYXAKCQkgKiBpcyByZWFsbHkgaW4gdXNlIG9yIG5vdCwgZmlyc3QgYmVjYXVzZSBMU0FQIG1heSBiZQoJCSAqIGRpcmVjdGx5IGFsbG9jYXRlZCBpbiBpcmxtcF9vcGVuX2xzYXAoKSwgYW5kIGFsc28gYmVjYXVzZQoJCSAqIHdlIG1heSB3cmFwYXJvdW5kIG9uIG9sZCBzb2NrZXRzLiBKZWFuIElJICovCgl9IHdoaWxlIChpcmxtcF9zbHNhcF9pbnVzZShpcmxtcC0+bGFzdF9sc2FwX3NlbCkpOwoKCS8qIEdvdCBpdCAhICovCglsc2FwX3NlbCA9IGlybG1wLT5sYXN0X2xzYXBfc2VsOwoJSVJEQV9ERUJVRyg0LCAiJXMoKSwgZm91bmQgZnJlZSBsc2FwX3NlbD0lMDJ4XG4iLAoJCSAgIF9fRlVOQ1RJT05fXywgbHNhcF9zZWwpOwoKCXJldHVybiBsc2FwX3NlbDsKfQoKLyoKICogRnVuY3Rpb24gaXJsbXBfY29udmVydF9sYXBfcmVhc29uIChsYXBfcmVhc29uKQogKgogKiAgICBDb252ZXJ0cyBJckxBUCBkaXNjb25uZWN0IHJlYXNvbiBjb2RlcyB0byBJckxNUCBkaXNjb25uZWN0IHJlYXNvbgogKiAgICBjb2RlcwogKgogKi8KTE1fUkVBU09OIGlybG1wX2NvbnZlcnRfbGFwX3JlYXNvbiggTEFQX1JFQVNPTiBsYXBfcmVhc29uKQp7CglpbnQgcmVhc29uID0gTE1fTEFQX0RJU0NPTk5FQ1Q7CgoJc3dpdGNoIChsYXBfcmVhc29uKSB7CgljYXNlIExBUF9ESVNDX0lORElDQVRJT046IC8qIFJlY2VpdmVkIGEgZGlzY29ubmVjdCByZXF1ZXN0IGZyb20gcGVlciAqLwoJCUlSREFfREVCVUcoIDEsICIlcygpLCBMQVBfRElTQ19JTkRJQ0FUSU9OXG4iLCBfX0ZVTkNUSU9OX18pOwoJCXJlYXNvbiA9IExNX1VTRVJfUkVRVUVTVDsKCQlicmVhazsKCWNhc2UgTEFQX05PX1JFU1BPTlNFOiAgICAvKiBUbyBtYW55IHJldHJhbnNtaXRzIHdpdGhvdXQgcmVzcG9uc2UgKi8KCQlJUkRBX0RFQlVHKCAxLCAiJXMoKSwgTEFQX05PX1JFU1BPTlNFXG4iLCBfX0ZVTkNUSU9OX18pOwoJCXJlYXNvbiA9IExNX0xBUF9ESVNDT05ORUNUOwoJCWJyZWFrOwoJY2FzZSBMQVBfUkVTRVRfSU5ESUNBVElPTjoKCQlJUkRBX0RFQlVHKCAxLCAiJXMoKSwgTEFQX1JFU0VUX0lORElDQVRJT05cbiIsIF9fRlVOQ1RJT05fXyk7CgkJcmVhc29uID0gTE1fTEFQX1JFU0VUOwoJCWJyZWFrOwoJY2FzZSBMQVBfRk9VTkRfTk9ORToKCWNhc2UgTEFQX01FRElBX0JVU1k6CgljYXNlIExBUF9QUklNQVJZX0NPTkZMSUNUOgoJCUlSREFfREVCVUcoMSwgIiVzKCksIExBUF9GT1VORF9OT05FLCBMQVBfTUVESUFfQlVTWSBvciBMQVBfUFJJTUFSWV9DT05GTElDVFxuIiwgX19GVU5DVElPTl9fKTsKCQlyZWFzb24gPSBMTV9DT05ORUNUX0ZBSUxVUkU7CgkJYnJlYWs7CglkZWZhdWx0OgoJCUlSREFfREVCVUcoMSwgIiVzKCksIFVua25vdyBJckxBUCBkaXNjb25uZWN0IHJlYXNvbiAlZCFcbiIsCgkJCSAgIF9fRlVOQ1RJT05fXywgbGFwX3JlYXNvbik7CgkJcmVhc29uID0gTE1fTEFQX0RJU0NPTk5FQ1Q7CgkJYnJlYWs7Cgl9CgoJcmV0dXJuIHJlYXNvbjsKfQoKI2lmZGVmIENPTkZJR19QUk9DX0ZTCgpzdHJ1Y3QgaXJsbXBfaXRlcl9zdGF0ZSB7CgloYXNoYmluX3QgKmhhc2hiaW47Cn07CgojZGVmaW5lIExTQVBfU1RBUlRfVE9LRU4JKCh2b2lkICopMSkKI2RlZmluZSBMSU5LX1NUQVJUX1RPS0VOCSgodm9pZCAqKTIpCgpzdGF0aWMgdm9pZCAqaXJsbXBfc2VxX2hiX2lkeChzdHJ1Y3QgaXJsbXBfaXRlcl9zdGF0ZSAqaXRlciwgbG9mZl90ICpvZmYpCnsKCXZvaWQgKmVsZW1lbnQ7CgoJc3Bpbl9sb2NrX2lycSgmaXRlci0+aGFzaGJpbi0+aGJfc3BpbmxvY2spOwoJZm9yIChlbGVtZW50ID0gaGFzaGJpbl9nZXRfZmlyc3QoaXRlci0+aGFzaGJpbik7CgkgICAgIGVsZW1lbnQgIT0gTlVMTDsgCgkgICAgIGVsZW1lbnQgPSBoYXNoYmluX2dldF9uZXh0KGl0ZXItPmhhc2hiaW4pKSB7CgkJaWYgKCFvZmYgfHwgKm9mZi0tID09IDApIHsKCQkJLyogTkI6IGhhc2hiaW4gbGVmdCBsb2NrZWQgKi8KCQkJcmV0dXJuIGVsZW1lbnQ7CgkJfQoJfQoJc3Bpbl91bmxvY2tfaXJxKCZpdGVyLT5oYXNoYmluLT5oYl9zcGlubG9jayk7CglpdGVyLT5oYXNoYmluID0gTlVMTDsKCXJldHVybiBOVUxMOwp9CgoKc3RhdGljIHZvaWQgKmlybG1wX3NlcV9zdGFydChzdHJ1Y3Qgc2VxX2ZpbGUgKnNlcSwgbG9mZl90ICpwb3MpCnsKCXN0cnVjdCBpcmxtcF9pdGVyX3N0YXRlICppdGVyID0gc2VxLT5wcml2YXRlOwoJdm9pZCAqdjsKCWxvZmZfdCBvZmYgPSAqcG9zOwoKCWl0ZXItPmhhc2hiaW4gPSBOVUxMOwoJaWYgKG9mZi0tID09IDApCgkJcmV0dXJuIExTQVBfU1RBUlRfVE9LRU47CgoJaXRlci0+aGFzaGJpbiA9IGlybG1wLT51bmNvbm5lY3RlZF9sc2FwczsKCXYgPSBpcmxtcF9zZXFfaGJfaWR4KGl0ZXIsICZvZmYpOwoJaWYgKHYpCgkJcmV0dXJuIHY7CgoJaWYgKG9mZi0tID09IDApCgkJcmV0dXJuIExJTktfU1RBUlRfVE9LRU47CgoJaXRlci0+aGFzaGJpbiA9IGlybG1wLT5saW5rczsKCXJldHVybiBpcmxtcF9zZXFfaGJfaWR4KGl0ZXIsICZvZmYpOwp9CgpzdGF0aWMgdm9pZCAqaXJsbXBfc2VxX25leHQoc3RydWN0IHNlcV9maWxlICpzZXEsIHZvaWQgKnYsIGxvZmZfdCAqcG9zKQp7CglzdHJ1Y3QgaXJsbXBfaXRlcl9zdGF0ZSAqaXRlciA9IHNlcS0+cHJpdmF0ZTsKCgkrKypwb3M7CgoJaWYgKHYgPT0gTFNBUF9TVEFSVF9UT0tFTikgewkJLyogc3RhcnQgb2YgbGlzdCBvZiBsc2FwcyAqLwoJCWl0ZXItPmhhc2hiaW4gPSBpcmxtcC0+dW5jb25uZWN0ZWRfbHNhcHM7CgkJdiA9IGlybG1wX3NlcV9oYl9pZHgoaXRlciwgTlVMTCk7CgkJcmV0dXJuIHYgPyB2IDogTElOS19TVEFSVF9UT0tFTjsKCX0KCglpZiAodiA9PSBMSU5LX1NUQVJUX1RPS0VOKSB7CQkvKiBzdGFydCBvZiBsaXN0IG9mIGxpbmtzICovCgkJaXRlci0+aGFzaGJpbiA9IGlybG1wLT5saW5rczsKCQlyZXR1cm4gaXJsbXBfc2VxX2hiX2lkeChpdGVyLCBOVUxMKTsKCX0KCgl2ID0gaGFzaGJpbl9nZXRfbmV4dChpdGVyLT5oYXNoYmluKTsKCglpZiAodiA9PSBOVUxMKSB7CQkJLyogbm8gbW9yZSBpbiB0aGlzIGhhc2ggYmluICovCgkJc3Bpbl91bmxvY2tfaXJxKCZpdGVyLT5oYXNoYmluLT5oYl9zcGlubG9jayk7CgoJCWlmIChpdGVyLT5oYXNoYmluID09IGlybG1wLT51bmNvbm5lY3RlZF9sc2FwcykgCgkJCXYgPSAgTElOS19TVEFSVF9UT0tFTjsKCgkJaXRlci0+aGFzaGJpbiA9IE5VTEw7Cgl9CglyZXR1cm4gdjsKfQoKc3RhdGljIHZvaWQgaXJsbXBfc2VxX3N0b3Aoc3RydWN0IHNlcV9maWxlICpzZXEsIHZvaWQgKnYpCnsKCXN0cnVjdCBpcmxtcF9pdGVyX3N0YXRlICppdGVyID0gc2VxLT5wcml2YXRlOwoKCWlmIChpdGVyLT5oYXNoYmluKQoJCXNwaW5fdW5sb2NrX2lycSgmaXRlci0+aGFzaGJpbi0+aGJfc3BpbmxvY2spOwp9CgpzdGF0aWMgaW50IGlybG1wX3NlcV9zaG93KHN0cnVjdCBzZXFfZmlsZSAqc2VxLCB2b2lkICp2KQp7Cgljb25zdCBzdHJ1Y3QgaXJsbXBfaXRlcl9zdGF0ZSAqaXRlciA9IHNlcS0+cHJpdmF0ZTsKCXN0cnVjdCBsc2FwX2NiICpzZWxmID0gdjsKCglpZiAodiA9PSBMU0FQX1NUQVJUX1RPS0VOKQoJCXNlcV9wdXRzKHNlcSwgIlVuY29ubmVjdGVkIExTQVBzOlxuIik7CgllbHNlIGlmICh2ID09IExJTktfU1RBUlRfVE9LRU4pCgkJc2VxX3B1dHMoc2VxLCAiXG5SZWdpc3RlcmVkIExpbmsgTGF5ZXJzOlxuIik7CgllbHNlIGlmIChpdGVyLT5oYXNoYmluID09IGlybG1wLT51bmNvbm5lY3RlZF9sc2FwcykgewoJCXNlbGYgPSB2OwoJCUlSREFfQVNTRVJUKHNlbGYtPm1hZ2ljID09IExNUF9MU0FQX01BR0lDLCByZXR1cm4gLUVJTlZBTDsgKTsKCQlzZXFfcHJpbnRmKHNlcSwgImxzYXAgc3RhdGU6ICVzLCAiLAoJCQkgICBpcmxzYXBfc3RhdGVbIHNlbGYtPmxzYXBfc3RhdGVdKTsKCQlzZXFfcHJpbnRmKHNlcSwKCQkJICAgInNsc2FwX3NlbDogJSMwMngsIGRsc2FwX3NlbDogJSMwMngsICIsCgkJCSAgIHNlbGYtPnNsc2FwX3NlbCwgc2VsZi0+ZGxzYXBfc2VsKTsKCQlzZXFfcHJpbnRmKHNlcSwgIiglcykiLCBzZWxmLT5ub3RpZnkubmFtZSk7CgkJc2VxX3ByaW50ZihzZXEsICJcbiIpOwoJfSBlbHNlIGlmIChpdGVyLT5oYXNoYmluID09IGlybG1wLT5saW5rcykgewoJCXN0cnVjdCBsYXBfY2IgKmxhcCA9IHY7CgoJCXNlcV9wcmludGYoc2VxLCAibGFwIHN0YXRlOiAlcywgIiwKCQkJICAgaXJsbXBfc3RhdGVbbGFwLT5sYXBfc3RhdGVdKTsKCgkJc2VxX3ByaW50ZihzZXEsICJzYWRkcjogJSMwOHgsIGRhZGRyOiAlIzA4eCwgIiwKCQkJICAgbGFwLT5zYWRkciwgbGFwLT5kYWRkcik7CgkJc2VxX3ByaW50ZihzZXEsICJudW0gbHNhcHM6ICVkIiwKCQkJICAgSEFTSEJJTl9HRVRfU0laRShsYXAtPmxzYXBzKSk7CgkJc2VxX3ByaW50ZihzZXEsICJcbiIpOwoKCQkvKiBDYXJlZnVsIGZvciBwcmlvcml0eSBpbnZlcnNpb25zIGhlcmUgIQoJCSAqIEFsbCBvdGhlciB1c2VzIG9mIGF0dHJpYiBzcGlubG9jayBhcmUgaW5kZXBlbmRlbnQgb2YKCQkgKiB0aGUgb2JqZWN0IHNwaW5sb2NrLCBzbyB3ZSBhcmUgc2FmZS4gSmVhbiBJSSAqLwoJCXNwaW5fbG9jaygmbGFwLT5sc2Fwcy0+aGJfc3BpbmxvY2spOwoKCQlzZXFfcHJpbnRmKHNlcSwgIlxuICBDb25uZWN0ZWQgTFNBUHM6XG4iKTsKCQlmb3IgKHNlbGYgPSAoc3RydWN0IGxzYXBfY2IgKikgaGFzaGJpbl9nZXRfZmlyc3QobGFwLT5sc2Fwcyk7CgkJICAgICBzZWxmICE9IE5VTEw7CgkJICAgICBzZWxmID0gKHN0cnVjdCBsc2FwX2NiICopaGFzaGJpbl9nZXRfbmV4dChsYXAtPmxzYXBzKSkgewoJCQlJUkRBX0FTU0VSVChzZWxmLT5tYWdpYyA9PSBMTVBfTFNBUF9NQUdJQywKCQkJCSAgICBnb3RvIG91dGxvb3A7KTsKCQkJc2VxX3ByaW50ZihzZXEsICIgIGxzYXAgc3RhdGU6ICVzLCAiLAoJCQkJICAgaXJsc2FwX3N0YXRlWyBzZWxmLT5sc2FwX3N0YXRlXSk7CgkJCXNlcV9wcmludGYoc2VxLAoJCQkJICAgInNsc2FwX3NlbDogJSMwMngsIGRsc2FwX3NlbDogJSMwMngsICIsCgkJCQkgICBzZWxmLT5zbHNhcF9zZWwsIHNlbGYtPmRsc2FwX3NlbCk7CgkJCXNlcV9wcmludGYoc2VxLCAiKCVzKSIsIHNlbGYtPm5vdGlmeS5uYW1lKTsKCQkJc2VxX3B1dGMoc2VxLCAnXG4nKTsKCgkJfQoJSVJEQV9BU1NFUlRfTEFCRUwob3V0bG9vcDopCgkJc3Bpbl91bmxvY2soJmxhcC0+bHNhcHMtPmhiX3NwaW5sb2NrKTsKCQlzZXFfcHV0YyhzZXEsICdcbicpOwoJfSBlbHNlCgkJcmV0dXJuIC1FSU5WQUw7CgoJcmV0dXJuIDA7Cn0KCnN0YXRpYyBzdHJ1Y3Qgc2VxX29wZXJhdGlvbnMgaXJsbXBfc2VxX29wcyA9IHsKCS5zdGFydCAgPSBpcmxtcF9zZXFfc3RhcnQsCgkubmV4dCAgID0gaXJsbXBfc2VxX25leHQsCgkuc3RvcCAgID0gaXJsbXBfc2VxX3N0b3AsCgkuc2hvdyAgID0gaXJsbXBfc2VxX3Nob3csCn07CgpzdGF0aWMgaW50IGlybG1wX3NlcV9vcGVuKHN0cnVjdCBpbm9kZSAqaW5vZGUsIHN0cnVjdCBmaWxlICpmaWxlKQp7CglzdHJ1Y3Qgc2VxX2ZpbGUgKnNlcTsKCWludCByYyA9IC1FTk9NRU07CglzdHJ1Y3QgaXJsbXBfaXRlcl9zdGF0ZSAqczsKCglJUkRBX0FTU0VSVChpcmxtcCAhPSBOVUxMLCByZXR1cm4gLUVJTlZBTDspOwoKCXMgPSBrbWFsbG9jKHNpemVvZigqcyksIEdGUF9LRVJORUwpOwoJaWYgKCFzKQoJCWdvdG8gb3V0OwoKCXJjID0gc2VxX29wZW4oZmlsZSwgJmlybG1wX3NlcV9vcHMpOwoJaWYgKHJjKQoJCWdvdG8gb3V0X2tmcmVlOwoKCXNlcQkgICAgID0gZmlsZS0+cHJpdmF0ZV9kYXRhOwoJc2VxLT5wcml2YXRlID0gczsKb3V0OgoJcmV0dXJuIHJjOwpvdXRfa2ZyZWU6CglrZnJlZShzKTsKCWdvdG8gb3V0Owp9CgpzdHJ1Y3QgZmlsZV9vcGVyYXRpb25zIGlybG1wX3NlcV9mb3BzID0gewoJLm93bmVyCQk9IFRISVNfTU9EVUxFLAoJLm9wZW4gICAgICAgICAgID0gaXJsbXBfc2VxX29wZW4sCgkucmVhZCAgICAgICAgICAgPSBzZXFfcmVhZCwKCS5sbHNlZWsgICAgICAgICA9IHNlcV9sc2VlaywKCS5yZWxlYXNlCT0gc2VxX3JlbGVhc2VfcHJpdmF0ZSwKfTsKCiNlbmRpZiAvKiBQUk9DX0ZTICovCg==