LyogUG9ydGlvbnMgb2YgdGhpcyBmaWxlIGFyZSBzdWJqZWN0IHRvIHRoZSBmb2xsb3dpbmcgY29weXJpZ2h0KHMpLiAgU2VlCiAqIHRoZSBOZXQtU05NUCdzIENPUFlJTkcgZmlsZSBmb3IgbW9yZSBkZXRhaWxzIGFuZCBvdGhlciBjb3B5cmlnaHRzCiAqIHRoYXQgbWF5IGFwcGx5OgogKi8KLyoKICogUG9ydGlvbnMgb2YgdGhpcyBmaWxlIGFyZSBjb3B5cmlnaHRlZCBieToKICogQ29weXJpZ2h0IKkgMjAwMyBTdW4gTWljcm9zeXN0ZW1zLCBJbmMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAqIFVzZSBpcyBzdWJqZWN0IHRvIGxpY2Vuc2UgdGVybXMgc3BlY2lmaWVkIGluIHRoZSBDT1BZSU5HIGZpbGUKICogZGlzdHJpYnV0ZWQgd2l0aCB0aGUgTmV0LVNOTVAgcGFja2FnZS4KICovCgovKi0gVGhpcyBpcyBhIC0qLSBDIC0qLSBjb21wYXRpYmxlIGNvZGUgZmlsZQogKgogKiBDb2RlIGZvciBTVU5PUzVfSU5TVFJVTUVOVEFUSU9OCiAqCiAqIFRoaXMgZmlsZSBjb250YWlucyBpbmNsdWRlcyBvZiBzdGFuZGFyZCBhbmQgbG9jYWwgc3lzdGVtIGhlYWRlciBmaWxlcywKICogaW5jbHVkZXMgb2Ygb3RoZXIgYXBwbGljYXRpb24gaGVhZGVyIGZpbGVzLCBnbG9iYWwgdmFyaWFibGUgZGVmaW5pdGlvbnMsCiAqIHN0YXRpYyB2YXJpYWJsZSBkZWZpbml0aW9ucywgc3RhdGljIGZ1bmN0aW9uIHByb3RvdHlwZXMsIGFuZCBmdW5jdGlvbgogKiBkZWZpbml0aW9ucy4KICoKICogVGhpcyBmaWxlIGNvbnRhaW5zIGZ1bmN0aW9uIHRvIG9idGFpbiBzdGF0aXN0aWNzIGZyb20gU3VuT1MgNS54IGtlcm5lbAogKgogKi8KCiNpbmNsdWRlIDxuZXQtc25tcC9uZXQtc25tcC1jb25maWcuaD4KI2lmZGVmIHNvbGFyaXMyCi8qLQogKiBJbmNsdWRlcyBvZiBzdGFuZGFyZCBBTlNJIEMgaGVhZGVyIGZpbGVzIAogKi8KCiNpbmNsdWRlIDxzdGRpby5oPgojaW5jbHVkZSA8c3RkbGliLmg+CiNpbmNsdWRlIDx1bmlzdGQuaD4KI2luY2x1ZGUgPHN0cmluZy5oPgoKLyotCiAqIEluY2x1ZGVzIG9mIHN5c3RlbSBoZWFkZXIgZmlsZXMgKHdyYXBwZWQgaW4gZHVwbGljYXRlIGluY2x1ZGUgcHJldmVudGlvbikKICovCgojaW5jbHVkZSA8ZmNudGwuaD4KI2luY2x1ZGUgPHN0cm9wdHMuaD4KI2luY2x1ZGUgPHN5cy90eXBlcy5oPgojaW5jbHVkZSA8a3ZtLmg+CiNpbmNsdWRlIDxzeXMvZmNudGwuaD4KI2luY2x1ZGUgPGtzdGF0Lmg+CiNpbmNsdWRlIDxlcnJuby5oPgojaW5jbHVkZSA8dGltZS5oPgoKI2luY2x1ZGUgPHN5cy9zb2NraW8uaD4KI2luY2x1ZGUgPHN5cy9zb2NrZXQuaD4KI2luY2x1ZGUgPHN5cy9zdHJlYW0uaD4KI2luY2x1ZGUgPHN5cy9zdHJvcHRzLmg+CiNpbmNsdWRlIDxzeXMvdGloZHIuaD4KI2luY2x1ZGUgPHN5cy90aXVzZXIuaD4KI2luY2x1ZGUgPHN5cy9kbHBpLmg+CiNpbmNsdWRlIDxpbmV0L2NvbW1vbi5oPgojaW5jbHVkZSA8aW5ldC9taWIyLmg+CiNpbmNsdWRlIDxpbmV0L2lwLmg+CiNpbmNsdWRlIDxuZXQvaWYuaD4KI2luY2x1ZGUgPG5ldGluZXQvaW4uaD4KCi8qLQogKiBJbmNsdWRlcyBvZiBsb2NhbCBhcHBsaWNhdGlvbiBoZWFkZXIgZmlsZXMgCiAqLwoKI2luY2x1ZGUgPG5ldC1zbm1wL25ldC1zbm1wLWluY2x1ZGVzLmg+CiNpbmNsdWRlIDxuZXQtc25tcC9hZ2VudC9uZXQtc25tcC1hZ2VudC1pbmNsdWRlcy5oPgoKI2luY2x1ZGUgImtlcm5lbF9zdW5vczUuaCIKCmtzdGF0X2N0bF90ICAgICprc3RhdF9mZCA9IDA7CgovKi0KICogR2xvYmFsIHZhcmlhYmxlIGRlZmluaXRpb25zICh3aXRoIGluaXRpYWxpemF0aW9uKQogKi8KCi8qLQogKiBTdGF0aWMgdmFyaWFibGUgZGVmaW5pdGlvbnMgKHdpdGggaW5pdGlhbGl6YXRpb24pCiAqLwoKc3RhdGljCm1pYmNhY2hlICAgICAgICBNaWJjYWNoZVtNSUJDQUNIRV9TSVpFKzFdID0gewogICAge01JQl9TWVNURU0sIDAsICh2b2lkICopIC0xLCAwLCAwLCAwLCAwfSwKICAgIHtNSUJfSU5URVJGQUNFUywgNTAgKiBzaXplb2YobWliMl9pZkVudHJ5X3QpLCAodm9pZCAqKSAtMSwgMCwgMzAsIDAsCiAgICAgMH0sCiAgICB7TUlCX0FULCAwLCAodm9pZCAqKSAtMSwgMCwgMCwgMCwgMH0sCiAgICB7TUlCX0lQLCBzaXplb2YobWliMl9pcF90KSwgKHZvaWQgKikgLTEsIDAsIDYwLCAwLCAwfSwKICAgIHtNSUJfSVBfQUREUiwgMjAgKiBzaXplb2YobWliMl9pcEFkZHJFbnRyeV90KSwgKHZvaWQgKikgLTEsIDAsIDYwLCAwLAogICAgIDB9LAogICAge01JQl9JUF9ST1VURSwgMjAwICogc2l6ZW9mKG1pYjJfaXBSb3V0ZUVudHJ5X3QpLCAodm9pZCAqKSAtMSwgMCwgMzAsCiAgICAgMCwgMH0sCiAgICB7TUlCX0lQX05FVCwgMTAwICogc2l6ZW9mKG1pYjJfaXBOZXRUb01lZGlhRW50cnlfdCksICh2b2lkICopIC0xLCAwLAogICAgIDMwMCwgMCwgMH0sCiAgICB7TUlCX0lDTVAsIHNpemVvZihtaWIyX2ljbXBfdCksICh2b2lkICopIC0xLCAwLCA2MCwgMCwgMH0sCiAgICB7TUlCX1RDUCwgc2l6ZW9mKG1pYjJfdGNwX3QpLCAodm9pZCAqKSAtMSwgMCwgNjAsIDAsIDB9LAogICAge01JQl9UQ1BfQ09OTiwgMTAwMCAqIHNpemVvZihtaWIyX3RjcENvbm5FbnRyeV90KSwgKHZvaWQgKikgLTEsIDAsIDMwLAogICAgIDAsIDB9LAogICAge01JQl9VRFAsIHNpemVvZihtaWIyX3VkcF90KSwgKHZvaWQgKikgLTEsIDAsIDMwLCAwLCAwfSwKICAgIHtNSUJfVURQX0xJU1RFTiwgMTAwMCAqIHNpemVvZihtaWIyX3VkcEVudHJ5X3QpLCAodm9pZCAqKSAtMSwgMCwgMzAsIDAsCiAgICAgMH0sCiAgICB7TUlCX0VHUCwgMCwgKHZvaWQgKikgLTEsIDAsIDAsIDAsIDB9LAogICAge01JQl9DTU9ULCAwLCAodm9pZCAqKSAtMSwgMCwgMCwgMCwgMH0sCiAgICB7TUlCX1RSQU5TTUlTU0lPTiwgMCwgKHZvaWQgKikgLTEsIDAsIDAsIDAsIDB9LAogICAge01JQl9TTk1QLCAwLCAodm9pZCAqKSAtMSwgMCwgMCwgMCwgMH0sCiNpZmRlZiBTT0xBUklTX0hBVkVfSVBWNl9NSUJfU1VQUE9SVAogICAge01JQl9JUDZfQUREUiwgMjAgKiBzaXplb2YobWliMl9pcHY2QWRkckVudHJ5X3QpLCAodm9pZCAqKS0xLCAwLCAzMCwgMCwgMH0sCiAgICB7TUlCX1RDUDZfQ09OTiwgMTAwMCAqIHNpemVvZihtaWIyX3RjcDZDb25uRW50cnlfdCksICh2b2lkICopIC0xLCAwLCAzMCwKICAgICAwLCAwfSwKICAgIHtNSUJfVURQNl9FTkRQT0lOVCwgMTAwMCAqIHNpemVvZihtaWIyX3VkcDZFbnRyeV90KSwgKHZvaWQgKikgLTEsIDAsIDMwLAogICAgIDAsIDB9LAojZW5kaWYKICAgIHswfSwKfTsKCnN0YXRpYwptaWJtYXAgICAgICAgICAgTWlibWFwW01JQkNBQ0hFX1NJWkUrMV0gPSB7CiAgICB7TUlCMl9TWVNURU0sIDAsfSwKICAgIHtNSUIyX0lOVEVSRkFDRVMsIDAsfSwKICAgIHtNSUIyX0FULCAwLH0sCiAgICB7TUlCMl9JUCwgMCx9LAogICAge01JQjJfSVAsIE1JQjJfSVBfMjAsfSwKICAgIHtNSUIyX0lQLCBNSUIyX0lQXzIxLH0sCiAgICB7TUlCMl9JUCwgTUlCMl9JUF8yMix9LAogICAge01JQjJfSUNNUCwgMCx9LAogICAge01JQjJfVENQLCAwLH0sCiAgICB7TUlCMl9UQ1AsIE1JQjJfVENQXzEzLH0sCiAgICB7TUlCMl9VRFAsIDAsfSwKICAgIHtNSUIyX1VEUCwgTUlCMl9VRFBfNX0sCiAgICB7TUlCMl9FR1AsIDAsfSwKICAgIHtNSUIyX0NNT1QsIDAsfSwKICAgIHtNSUIyX1RSQU5TTUlTU0lPTiwgMCx9LAogICAge01JQjJfU05NUCwgMCx9LAojaWZkZWYgU09MQVJJU19IQVZFX0lQVjZfTUlCX1NVUFBPUlQKICAgIHtNSUIyX0lQNiwgTUlCMl9JUDZfQUREUn0sCiAgICB7TUlCMl9UQ1A2LCBNSUIyX1RDUDZfQ09OTn0sCiAgICB7TUlCMl9VRFA2LCBNSUIyX1VEUDZfRU5UUll9LAojZW5kaWYKICAgIHswfSwKfTsKCnN0YXRpYyBpbnQgICAgICBzZCA9IC0yOyAgICAgICAgLyogL2Rldi9hcnAgc3RyZWFtIGRlc2NyaXB0b3IuICovCgovKi0KICogU3RhdGljIGZ1bmN0aW9uIHByb3RvdHlwZXMgKHVzZSB2b2lkIGFzIGFyZ3VtZW50IHR5cGUgaWYgdGhlcmUgYXJlIG5vbmUpCiAqLwoKc3RhdGljIGZvdW5kX2UKZ2V0ZW50cnkocmVxX2UgcmVxX3R5cGUsIHZvaWQgKmJ1ZmFkZHIsIHNpemVfdCBsZW4sIHNpemVfdCBlbnRyeXNpemUsCiAgICAgICAgIHZvaWQgKnJlc3AsIGludCAoKmNvbXApKHZvaWQgKiwgdm9pZCAqKSwgdm9pZCAqYXJnKTsKCnN0YXRpYyBpbnQKZ2V0bWliKGludCBncm91cG5hbWUsIGludCBzdWJncm91cG5hbWUsIHZvaWQgKnN0YXRidWYsIHNpemVfdCBzaXplLAogICAgICAgc2l6ZV90IGVudHJ5c2l6ZSwgcmVxX2UgcmVxX3R5cGUsIHZvaWQgKnJlc3AsIHNpemVfdCAqbGVuZ3RoLAogICAgICAgaW50ICgqY29tcCkodm9pZCAqLCB2b2lkICopLCB2b2lkICphcmcpOwoKc3RhdGljIGludApnZXRpZihtaWIyX2lmRW50cnlfdCAqaWZidWYsIHNpemVfdCBzaXplLCByZXFfZSByZXFfdHlwZSwgbWliMl9pZkVudHJ5X3QgKnJlc3AsCiAgICAgIHNpemVfdCAqbGVuZ3RoLCBpbnQgKCpjb21wKSh2b2lkICosIHZvaWQgKiksIHZvaWQgKmFyZyk7CnN0YXRpYyB2b2lkIApzZXRfaWZfaW5mbyhtaWIyX2lmRW50cnlfdCAqaWZwLCB1bnNpZ25lZCBpbmRleCwgY2hhciAqbmFtZSwgdWludDY0X3QgZmxhZ3MsCiAgICAgICAgICAgIGludCBtdHUpOwpzdGF0aWMgaW50IGdldF9pZl9zdGF0cyhtaWIyX2lmRW50cnlfdCAqaWZwKTsKCiNpZiBkZWZpbmVkKEhBVkVfSUZfTkFNRUlOREVYKSAmJiBkZWZpbmVkKE5FVFNOTVBfSU5DTFVERV9JRlRBQkxFX1JFV1JJVEVTKQpzdGF0aWMgaW50IF9kbHBpX29wZW4oY29uc3QgY2hhciAqZGV2bmFtZSk7CnN0YXRpYyBpbnQgX2RscGlfZ2V0X3BoeXNfYWRkcmVzcyhpbnQgZmQsIGNoYXIgKnBhZGRyLCBpbnQgbWF4bGVuLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaW50ICpwYWRkcmxlbik7CnN0YXRpYyBpbnQgX2RscGlfZ2V0X2lmdHlwZShpbnQgZmQsIHVuc2lnbmVkIGludCAqaWZ0eXBlKTsKc3RhdGljIGludCBfZGxwaV9hdHRhY2goaW50IGZkLCBpbnQgcHBhKTsKc3RhdGljIGludCBfZGxwaV9wYXJzZV9kZXZuYW1lKGNoYXIgKmRldm5hbWUsIGludCAqcHBhcCk7CiNlbmRpZgoKCgpzdGF0aWMgaW50Ck5hbWVfY21wKHZvaWQgKiwgdm9pZCAqKTsKCnN0YXRpYyB2b2lkCmluaXRfbWliY2FjaGVfZWxlbWVudChtaWJjYWNoZSAqIGNwKTsKCiNkZWZpbmUJU1RSRUFNX0RFVgkiL2Rldi9hcnAiCiNkZWZpbmUJQlVGU0laRQkJNDA5NjAgICAvKiBCdWZmZXIgZm9yICBtZXNzYWdlcyAoc2hvdWxkIGJlIG1vZHVsbyhwYWdlc2l6ZSkgKi8KCi8qLQogKiBGdW5jdGlvbiBkZWZpbml0aW9ucwogKi8KCiNpZmRlZiBfU1REQ19DT01QQVQKI2lmZGVmIF9fY3BsdXNwbHVzCmV4dGVybiAgICAgICAgICAiQyIgewojZW5kaWYKI2VuZGlmCgovKgogKiBJIHByb2ZpbGVkIHNubXBkIHVzaW5nIFF1YW50aWZ5IG9uIGEgU29sYXJpcyA3IGJveCwgYW5kIGl0IHR1cm5lZCBvdXQgdGhhdAogKiB0aGUgY2FsbHMgdG8gdGltZSgpIGluIGdldE1pYnN0YXQoKSB3ZXJlIHRha2luZyAxOCUgb2YgdGhlIHRvdGFsIGV4ZWN1dGlvbgogKiB0aW1lIG9mIHNubXBkIHdoZW4gZG9pbmcgc2ltcGxlIHdhbGtzIG92ZXIgdGhlIHdob2xlIHRyZWUuICBJIGd1ZXNzIGl0IG11c3QKICogYmUgZGlmZmljdWx0IGZvciBTdW4gaGFyZHdhcmUgdG8gdGVsbCB0aGUgdGltZSBvciBzb21ldGhpbmcgOy0pLiAgQW55d2F5LAogKiB0aGlzIHNlZW1lZCBsaWtlIGl0IHdhcyBuZWdhdGluZyB0aGUgcG9pbnQgb2YgaGF2aW5nIHRoZSBjYWNoZSwgc28gSSBoYXZlCiAqIGNoYW5nZWQgdGhlIGNvZGUgc28gdGhhdCBpdCBydW5zIGEgcGVyaW9kaWMgYWxhcm0gdG8gYWdlIHRoZSBjYWNoZSBlbnRyaWVzCiAqIGluc3RlYWQuICBUaGUgbWVhbmluZyBvZiB0aGUgY2FjaGVfdHRsIGFuZCBjYWNoZV90aW1lIG1lbWJlcnMgaGFzIGNoYW5nZWQgdG8KICogc3VwcG9ydCB0aGlzLiAgY2FjaGVfdHRsIGlzIG5vdyB0aGUgdmFsdWUgdGhhdCBjYWNoZV90aW1lIGdldHMgcmVzZXQgdG8gd2hlbgogKiB3ZSBmZXRjaCBhIHZhbHVlIGZyb20gdGhlIGtlcm5lbDsgY2FjaGVfdGltZSB0aGVuIHRpY2tzIGRvd24gdG8gemVybyBpbgogKiBzdGVwcyBvZiBwZXJpb2QgKHNlZSBiZWxvdykuICBXaGVuIGl0IHJlYWNoZXMgemVybywgdGhlIGNhY2hlIGVudHJ5IGlzIG5vCiAqIGxvbmdlciB2YWxpZCBhbmQgd2UgZmV0Y2ggYSBuZXcgb25lLiAgVGhlIGVmZmVjdCBvZiB0aGlzIGlzIHRoZSBzYW1lIGFzIHRoZQogKiBwcmV2aW91cyBjb2RlLCBidXQgbW9yZSBlZmZpY2llbnQgKGJlY2F1c2UgaXQncyBub3QgY2FsbGluZyB0aW1lKCkgZm9yIGV2ZXJ5CiAqIHZhcmlhYmxlIGZldGNoZWQpIHdoZW4geW91IGFyZSB3YWxraW5nIHRoZSB0YWJsZXMuICBqYnBuLCAyMDAyMDIyNi4KICovCgpzdGF0aWMgdm9pZAprZXJuZWxfc3Vub3M1X2NhY2hlX2FnZSh1bnNpZ25lZCBpbnQgcmVnbnVtYmVyLCB2b2lkICpkYXRhKQp7CiAgICBpbnQgaSA9IDAsIHBlcmlvZCA9IChpbnQpZGF0YTsKCiAgICBmb3IgKGkgPSAwOyBpIDwgTUlCQ0FDSEVfU0laRTsgaSsrKSB7CglERUJVR01TR1RMKCgia2VybmVsX3N1bm9zNSIsICJjYWNoZVslZF0gdGltZSAlbGQgdHRsICVkXG4iLCBpLAoJCSAgICBNaWJjYWNoZVtpXS5jYWNoZV90aW1lLCBNaWJjYWNoZVtpXS5jYWNoZV90dGwpKTsKCWlmIChNaWJjYWNoZVtpXS5jYWNoZV90aW1lIDwgcGVyaW9kKSB7CgkgICAgTWliY2FjaGVbaV0uY2FjaGVfdGltZSA9IDA7Cgl9IGVsc2UgewoJICAgIE1pYmNhY2hlW2ldLmNhY2hlX3RpbWUgLT0gcGVyaW9kOwoJfQogICAgfQp9Cgp2b2lkCmluaXRfa2VybmVsX3N1bm9zNSh2b2lkKQp7CiAgICBzdGF0aWMgaW50IGNyZWcgICA9IDA7CiAgICBjb25zdCAgaW50IHBlcmlvZCA9IDMwOwogICAgaW50ICAgIGFsYXJtX2lkICAgPSAwOwoKICAgIGlmIChjcmVnID09IDApIHsKCWFsYXJtX2lkID0gc25tcF9hbGFybV9yZWdpc3Rlcig1LCBOVUxMLCBrZXJuZWxfc3Vub3M1X2NhY2hlX2FnZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgTlVMTCk7CglERUJVR01TR1RMKCgia2VybmVsX3N1bm9zNSIsICJyZWdpc3RlcmVkIGFsYXJtICVkIHdpdGggcGVyaW9kIDVzXG4iLCAKCQkgICAgYWxhcm1faWQpKTsKCWFsYXJtX2lkID0gc25tcF9hbGFybV9yZWdpc3RlcihwZXJpb2QsIFNBX1JFUEVBVCwgCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGtlcm5lbF9zdW5vczVfY2FjaGVfYWdlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAodm9pZCAqKXBlcmlvZCk7CglERUJVR01TR1RMKCgia2VybmVsX3N1bm9zNSIsICJyZWdpc3RlcmVkIGFsYXJtICVkIHdpdGggcGVyaW9kICVkc1xuIiwgCgkJICAgIGFsYXJtX2lkLCBwZXJpb2QpKTsKICAgICAgICArK2NyZWc7CiAgICB9Cn0KCi8qCiAqIEdldCB2YXJpb3VzIGtlcm5lbCBzdGF0aXN0aWNzIHVzaW5nIHVuZG9jdW1lbnRlZCBTb2xhcmlzIGtzdGF0IGludGVyZmFjZS4KICogV2UgbmVlZCBpdCBtYWlubHkgZm9yIGdldHRpbmcgbmV0d29yayBpbnRlcmZhY2Ugc3RhdGlzdGljcywgYWx0aG91Z2ggaXQgaXMKICogZ2VuZXJpYyBlbm91Z2ggdG8gYmUgdXNlZCBmb3IgYW55IHB1cnBvc2UuICBJdCBrbm93cyBhYm91dCBrc3RhdF9oZWFkZXJzCiAqIG1vZHVsZSBuYW1lcyBhbmQgYnkgdGhlIG5hbWUgb2YgdGhlIHN0YXRpc3RpY3MgaXQgdHJpZXMgdG8gZmlndXJlIG91dCB0aGUKICogcmVzdCBvZiBuZWNlc3NhcnkgaW5mb3JtYXRpb24uICBSZXR1cm5zIDAgaW4gY2FzZSBvZiBzdWNjZXNzIGFuZCA8IDAgaWYKICogdGhlcmUgd2VyZSBhbnkgZXJyb3JzLgogCiAqIAogKiBOT1RFOiBUbyB1c2UgdGhpcyBmdW5jdGlvbiBjb3JyZWN0bHkgeW91IGhhdmUgdG8ga25vdyB0aGUgYWN0dWFsIHR5cGUgb2YgdGhlCiAqIHZhbHVlIHRvIGJlIHJldHVybmVkLCBzbyB5b3UgbWF5IGJ1aWxkIHRoZSB0ZXN0IHByb2dyYW0sIGZpZ3VyZSBvdXQgdGhlIHR5cGUKICogYW5kIHVzZSBpdC4gRXhwb3Npbmcga3N0YXQgZGF0YSB0eXBlcyB0byB1cHBlciBsYXllcnMgZG9lc24ndCBzZWVtIHRvIGJlCiAqIHJlYXNvbmFibGUuIEluIGFueSBjYXNlIEknZCBleHBlY3QgbW9yZSByZWFzb25hYmxlIGtzdGF0IGludGVyZmFjZS4gOi0oCiAqLwoKCmludApnZXRLc3RhdEludChjb25zdCBjaGFyICpjbGFzc25hbWUsIGNvbnN0IGNoYXIgKnN0YXRuYW1lLCAKCSAgICBjb25zdCBjaGFyICp2YXJuYW1lLCBpbnQgKnZhbHVlKQp7CiAgICBrc3RhdF9jdGxfdCAgICAqa3NjOwogICAga3N0YXRfdCAgICAgICAgKmtzOwogICAga2lkX3QgICAgICAgICAgIGtpZDsKICAgIGtzdGF0X25hbWVkX3QgICpuYW1lZDsKICAgIGludCAgICAgICAgICAgICByZXQgPSAtMTsgICAgICAgIC8qIGZhaWwgdW5sZXNzIC4uLiAqLwoKICAgIGlmIChrc3RhdF9mZCA9PSAwKSB7Cglrc3RhdF9mZCA9IGtzdGF0X29wZW4oKTsKCWlmIChrc3RhdF9mZCA9PSAwKSB7CgkgICAgc25tcF9sb2dfcGVycm9yKCJrc3RhdF9vcGVuIik7Cgl9CiAgICB9CiAgICBpZiAoKGtzYyA9IGtzdGF0X2ZkKSA9PSBOVUxMKSB7Cglnb3RvIFJldHVybjsKICAgIH0KICAgIGtzID0ga3N0YXRfbG9va3VwKGtzYywgY2xhc3NuYW1lLCAtMSwgc3RhdG5hbWUpOwogICAgaWYgKGtzID09IE5VTEwpIHsKCURFQlVHTVNHVEwoKCJrZXJuZWxfc3Vub3M1IiwgImNsYXNzICVzLCBzdGF0ICVzIG5vdCBmb3VuZFxuIiwKCQljbGFzc25hbWUgPyBjbGFzc25hbWUgOiAiTlVMTCIsCgkJc3RhdG5hbWUgPyBzdGF0bmFtZSA6ICJOVUxMIikpOwoJZ290byBSZXR1cm47CiAgICB9CiAgICBraWQgPSBrc3RhdF9yZWFkKGtzYywga3MsIE5VTEwpOwogICAgaWYgKGtpZCA9PSAtMSkgewoJREVCVUdNU0dUTCgoImtlcm5lbF9zdW5vczUiLCAiY2Fubm90IHJlYWQgY2xhc3MgJXMgc3RhdHMgJXNcbiIsCgkJY2xhc3NuYW1lID8gY2xhc3NuYW1lIDogIk5VTEwiLCBzdGF0bmFtZSA/IHN0YXRuYW1lIDogIk5VTEwiKSk7Cglnb3RvIFJldHVybjsKICAgIH0KICAgIG5hbWVkID0ga3N0YXRfZGF0YV9sb29rdXAoa3MsIHZhcm5hbWUpOwogICAgaWYgKG5hbWVkID09IE5VTEwpIHsKCURFQlVHTVNHVEwoKCJrZXJuZWxfc3Vub3M1IiwgIm5vIHZhciAlcyBmb3IgY2xhc3MgJXMgc3RhdCAlc1xuIiwKCQl2YXJuYW1lLCBjbGFzc25hbWUgPyBjbGFzc25hbWUgOiAiTlVMTCIsCgkJc3RhdG5hbWUgPyBzdGF0bmFtZSA6ICJOVUxMIikpOwoJZ290byBSZXR1cm47CiAgICB9CgogICAgcmV0ID0gMDsgICAgICAgICAgICAgICAgLyogbWF5YmUgc3VjY2Vzc2Z1bCAqLwogICAgc3dpdGNoIChuYW1lZC0+ZGF0YV90eXBlKSB7CiNpZmRlZiBLU1RBVF9EQVRBX0lOVDMyICAgICAgICAgLyogU29sYXJpcyAyLjYgYW5kIHVwICovCiAgICBjYXNlIEtTVEFUX0RBVEFfSU5UMzI6CgkqdmFsdWUgPSBuYW1lZC0+dmFsdWUuaTMyOwoJYnJlYWs7CiAgICBjYXNlIEtTVEFUX0RBVEFfVUlOVDMyOgoJKnZhbHVlID0gbmFtZWQtPnZhbHVlLnVpMzI7CglicmVhazsKICAgIGNhc2UgS1NUQVRfREFUQV9JTlQ2NDoKCSp2YWx1ZSA9IG5hbWVkLT52YWx1ZS5pNjQ7CglicmVhazsKICAgIGNhc2UgS1NUQVRfREFUQV9VSU5UNjQ6CgkqdmFsdWUgPSBuYW1lZC0+dmFsdWUudWk2NDsKCWJyZWFrOwojZWxzZQogICAgY2FzZSBLU1RBVF9EQVRBX0xPTkc6CgkqdmFsdWUgPSBuYW1lZC0+dmFsdWUubDsKCWJyZWFrOwogICAgY2FzZSBLU1RBVF9EQVRBX1VMT05HOgoJKnZhbHVlID0gbmFtZWQtPnZhbHVlLnVsOwoJYnJlYWs7CiAgICBjYXNlIEtTVEFUX0RBVEFfTE9OR0xPTkc6CgkqdmFsdWUgPSBuYW1lZC0+dmFsdWUubGw7CglicmVhazsKICAgIGNhc2UgS1NUQVRfREFUQV9VTE9OR0xPTkc6CgkqdmFsdWUgPSBuYW1lZC0+dmFsdWUudWxsOwoJYnJlYWs7CiNlbmRpZgogICAgZGVmYXVsdDoKCXNubXBfbG9nKExPR19FUlIsCgkJIm5vbi1pbnQgdHlwZSBpbiBrc3RhdCBkYXRhOiBcIiVzXCIgXCIlc1wiIFwiJXNcIiAlZFxuIiwKCQljbGFzc25hbWUgPyBjbGFzc25hbWUgOiAiTlVMTCIsCgkJc3RhdG5hbWUgPyBzdGF0bmFtZSA6ICJOVUxMIiwKCQl2YXJuYW1lID8gdmFybmFtZSA6ICJOVUxMIiwgbmFtZWQtPmRhdGFfdHlwZSk7CglyZXQgPSAtMTsgICAgICAgICAgICAvKiBmYWlsICovCglicmVhazsKICAgIH0KIFJldHVybjoKICAgIHJldHVybiByZXQ7Cn0KCmludApnZXRLc3RhdChjb25zdCBjaGFyICpzdGF0bmFtZSwgY29uc3QgY2hhciAqdmFybmFtZSwgdm9pZCAqdmFsdWUpCnsKICAgIGtzdGF0X2N0bF90ICAgICprc2M7CiAgICBrc3RhdF90ICAgICAgICAqa3MsICprc3RhdF9kYXRhOwogICAga3N0YXRfbmFtZWRfdCAgKmQ7CiAgICBzaXplX3QgICAgICAgICAgaSwgaW5zdGFuY2U7CiAgICBjaGFyICAgICAgICAgICAgbW9kdWxlX25hbWVbNjRdOwogICAgaW50ICAgICAgICAgICAgIHJldDsKICAgIHVfbG9uZ2xvbmdfdCAgICB2YWw7ICAgIC8qIFRoZSBsYXJnZXN0IHZhbHVlICovCiAgICB2b2lkICAgICAgICAgICAqdjsKICAgIHN0YXRpYyBjaGFyICAgIGJ1ZlsxMjhdOwoKICAgIGlmICh2YWx1ZSA9PSBOVUxMKSB7ICAgICAgLyogUHJldHR5IHVzZWxlc3MgYnV0IC4uLiAqLwoJdiA9ICh2b2lkICopICZ2YWw7CiAgICB9IGVsc2UgewoJdiA9IHZhbHVlOwogICAgfQoKICAgIGlmIChrc3RhdF9mZCA9PSAwKSB7Cglrc3RhdF9mZCA9IGtzdGF0X29wZW4oKTsKCWlmIChrc3RhdF9mZCA9PSAwKSB7CgkgICAgc25tcF9sb2dfcGVycm9yKCJrc3RhdF9vcGVuIik7Cgl9CiAgICB9CiAgICBpZiAoKGtzYyA9IGtzdGF0X2ZkKSA9PSBOVUxMKSB7CglyZXQgPSAtMTA7Cglnb3RvIFJldHVybjsgICAgICAgIC8qIGtzdGF0IGVycm9ycyAqLwogICAgfQogICAgaWYgKHN0YXRuYW1lID09IE5VTEwgfHwgdmFybmFtZSA9PSBOVUxMKSB7CglyZXQgPSAtMjA7Cglnb3RvIFJldHVybjsKICAgIH0KCiAgICAvKgogICAgICogRmlyc3QsIGdldCAia3N0YXRfaGVhZGVycyIgc3RhdGlzdGljcy4gSXQgc2hvdWxkCiAgICAgKiBjb250YWluIGFsbCBhdmFpbGFibGUgbW9kdWxlcy4gCiAgICAgKi8KCiAgICBpZiAoKGtzID0ga3N0YXRfbG9va3VwKGtzYywgInVuaXgiLCAwLCAia3N0YXRfaGVhZGVycyIpKSA9PSBOVUxMKSB7CglyZXQgPSAtMTA7Cglnb3RvIFJldHVybjsgICAgICAgIC8qIGtzdGF0IGVycm9ycyAqLwogICAgfQogICAgaWYgKGtzdGF0X3JlYWQoa3NjLCBrcywgTlVMTCkgPD0gMCkgewoJcmV0ID0gLTEwOwoJZ290byBSZXR1cm47ICAgICAgICAvKiBrc3RhdCBlcnJvcnMgKi8KICAgIH0KICAgIGtzdGF0X2RhdGEgPSBrcy0+a3NfZGF0YTsKICAgIAogICAgLyoKICAgICAqIE5vdywgbG9vayBmb3IgdGhlIG5hbWUgb2Ygb3VyIHN0YXQgaW4gdGhlIGhlYWRlcnMgYnVmIAogICAgICovCiAgICBmb3IgKGkgPSAwOyBpIDwga3MtPmtzX25kYXRhOyBpKyspIHsKCURFQlVHTVNHVEwoKCJrZXJuZWxfc3Vub3M1IiwKCQkgICAgIm1vZHVsZTogJXMgaW5zdGFuY2U6ICVkIG5hbWU6ICVzIGNsYXNzOiAlcyB0eXBlOiAlZCBmbGFnczogJXhcbiIsCgkJICAgIGtzdGF0X2RhdGFbaV0ua3NfbW9kdWxlLCBrc3RhdF9kYXRhW2ldLmtzX2luc3RhbmNlLAoJCSAgICBrc3RhdF9kYXRhW2ldLmtzX25hbWUsIGtzdGF0X2RhdGFbaV0ua3NfY2xhc3MsCgkJICAgIGtzdGF0X2RhdGFbaV0ua3NfdHlwZSwga3N0YXRfZGF0YVtpXS5rc19mbGFncykpOwoJaWYgKHN0cmNtcChzdGF0bmFtZSwga3N0YXRfZGF0YVtpXS5rc19uYW1lKSA9PSAwKSB7CgkgICAgc3RyY3B5KG1vZHVsZV9uYW1lLCBrc3RhdF9kYXRhW2ldLmtzX21vZHVsZSk7CgkgICAgaW5zdGFuY2UgPSBrc3RhdF9kYXRhW2ldLmtzX2luc3RhbmNlOwoJICAgIGJyZWFrOwoJfQogICAgfQogICAgCiAgICBpZiAoaSA9PSBrcy0+a3NfbmRhdGEpIHsKCXJldCA9IC0xOwoJZ290byBSZXR1cm47ICAgICAgICAvKiBOb3QgZm91bmQgKi8KICAgIH0KICAgIAogICAgLyoKICAgICAqIEdldCB0aGUgbmFtZWQgc3RhdGlzdGljcyAKICAgICAqLwogICAgaWYgKChrcyA9IGtzdGF0X2xvb2t1cChrc2MsIG1vZHVsZV9uYW1lLCBpbnN0YW5jZSwgc3RhdG5hbWUpKSA9PSBOVUxMKSB7CglyZXQgPSAtMTA7Cglnb3RvIFJldHVybjsgICAgICAgIC8qIGtzdGF0IGVycm9ycyAqLwogICAgfQoKICAgIGlmIChrc3RhdF9yZWFkKGtzYywga3MsIE5VTEwpIDw9IDApIHsKCXJldCA9IC0xMDsKCWdvdG8gUmV0dXJuOyAgICAgICAgLyoga3N0YXQgZXJyb3JzICovCiAgICB9CiAgICAvKgogICAgICogVGhpcyBmdW5jdGlvbiBleHBlY3RzIG9ubHkgbmFtZS92YWx1ZSB0eXBlIG9mIHN0YXRpc3RpY3MsIHNvIGlmIGl0IGlzCiAgICAgKiBub3QgdGhlIGNhc2UgcmV0dXJuIGFuIGVycm9yCiAgICAgKi8KICAgIGlmIChrcy0+a3NfdHlwZSAhPSBLU1RBVF9UWVBFX05BTUVEKSB7CglyZXQgPSAtMjsKCWdvdG8gUmV0dXJuOyAgICAgICAgLyogSW52YWxpZCBzdGF0IHR5cGUgKi8KICAgIH0KICAgIAogICAgZm9yIChpID0gMCwgZCA9IEtTVEFUX05BTUVEX1BUUihrcyk7IGkgPCBrcy0+a3NfbmRhdGE7IGkrKywgZCsrKSB7CglERUJVR01TR1RMKCgia2VybmVsX3N1bm9zNSIsICJ2YXJpYWJsZTogXCIlc1wiICh0eXBlICVkKVxuIiwgCgkJICAgIGQtPm5hbWUsIGQtPmRhdGFfdHlwZSkpOwoKCWlmIChzdHJjbXAoZC0+bmFtZSwgdmFybmFtZSkgPT0gMCkgewoJICAgIHN3aXRjaCAoZC0+ZGF0YV90eXBlKSB7CgkgICAgY2FzZSBLU1RBVF9EQVRBX0NIQVI6CgkJREVCVUdNU0dUTCgoImtlcm5lbF9zdW5vczUiLCAidmFsdWU6ICVzXG4iLCBkLT52YWx1ZS5jKSk7CgkJKihjaGFyICoqKXYgPSBidWY7CgkJc3RybGNweShidWYsIGQtPnZhbHVlLmMsIHNpemVvZihidWYpKTsKCQlicmVhazsKI2lmZGVmIEtTVEFUX0RBVEFfSU5UMzIgICAgICAgICAvKiBTb2xhcmlzIDIuNiBhbmQgdXAgKi8KCSAgICBjYXNlIEtTVEFUX0RBVEFfSU5UMzI6CgkJKihDb3VudGVyICopdiA9IGQtPnZhbHVlLmkzMjsKCQlERUJVR01TR1RMKCgia2VybmVsX3N1bm9zNSIsICJ2YWx1ZTogJWRcbiIsIGQtPnZhbHVlLmkzMikpOwoJCWJyZWFrOwoJICAgIGNhc2UgS1NUQVRfREFUQV9VSU5UMzI6CgkJKihDb3VudGVyICopdiA9IGQtPnZhbHVlLnVpMzI7CgkJREVCVUdNU0dUTCgoImtlcm5lbF9zdW5vczUiLCAidmFsdWU6ICV1XG4iLCBkLT52YWx1ZS51aTMyKSk7CgkJYnJlYWs7CgkgICAgY2FzZSBLU1RBVF9EQVRBX0lOVDY0OgoJCSooaW50NjRfdCAqKXYgPSBkLT52YWx1ZS5pNjQ7CgkJREVCVUdNU0dUTCgoImtlcm5lbF9zdW5vczUiLCAidmFsdWU6ICVsZFxuIiwgZC0+dmFsdWUuaTY0KSk7CgkJYnJlYWs7CgkgICAgY2FzZSBLU1RBVF9EQVRBX1VJTlQ2NDoKCQkqKHVpbnQ2NF90ICopdiA9IGQtPnZhbHVlLnVpNjQ7CgkJREVCVUdNU0dUTCgoImtlcm5lbF9zdW5vczUiLCAidmFsdWU6ICVsdVxuIiwgZC0+dmFsdWUudWk2NCkpOwoJCWJyZWFrOwojZWxzZQoJICAgIGNhc2UgS1NUQVRfREFUQV9MT05HOgoJCSooQ291bnRlciAqKXYgPSBkLT52YWx1ZS5sOwoJCURFQlVHTVNHVEwoKCJrZXJuZWxfc3Vub3M1IiwgInZhbHVlOiAlbGRcbiIsIGQtPnZhbHVlLmwpKTsKCQlicmVhazsKCSAgICBjYXNlIEtTVEFUX0RBVEFfVUxPTkc6CgkJKihDb3VudGVyICopdiA9IGQtPnZhbHVlLnVsOwoJCURFQlVHTVNHVEwoKCJrZXJuZWxfc3Vub3M1IiwgInZhbHVlOiAlbHVcbiIsIGQtPnZhbHVlLnVsKSk7CgkJYnJlYWs7CgkgICAgY2FzZSBLU1RBVF9EQVRBX0xPTkdMT05HOgoJCSooQ291bnRlciAqKXYgPSBkLT52YWx1ZS5sbDsKCQlERUJVR01TR1RMKCgia2VybmVsX3N1bm9zNSIsICJ2YWx1ZTogJWxsZFxuIiwKCQkJICAgIChsb25nKWQtPnZhbHVlLmxsKSk7CgkJYnJlYWs7CgkgICAgY2FzZSBLU1RBVF9EQVRBX1VMT05HTE9ORzoKCQkqKENvdW50ZXIgKil2ID0gZC0+dmFsdWUudWxsOwoJCURFQlVHTVNHVEwoKCJrZXJuZWxfc3Vub3M1IiwgInZhbHVlOiAlbGx1XG4iLAoJCQkgICAgKHVuc2lnbmVkIGxvbmcpZC0+dmFsdWUudWxsKSk7CgkJYnJlYWs7CiNlbmRpZgoJICAgIGNhc2UgS1NUQVRfREFUQV9GTE9BVDoKCQkqKGZsb2F0ICopdiA9IGQtPnZhbHVlLmY7CgkJREVCVUdNU0dUTCgoImtlcm5lbF9zdW5vczUiLCAidmFsdWU6ICVmXG4iLCBkLT52YWx1ZS5mKSk7CgkJYnJlYWs7CgkgICAgY2FzZSBLU1RBVF9EQVRBX0RPVUJMRToKCQkqKGRvdWJsZSAqKXYgPSBkLT52YWx1ZS5kOwoJCURFQlVHTVNHVEwoKCJrZXJuZWxfc3Vub3M1IiwgInZhbHVlOiAlZlxuIiwgZC0+dmFsdWUuZCkpOwoJCWJyZWFrOwoJICAgIGRlZmF1bHQ6CgkJREVCVUdNU0dUTCgoImtlcm5lbF9zdW5vczUiLAoJCQkgICAgIlVOS05PV04gVFlQRSAlZCAoc3RhdCBcIiVzXCIgdmFyIFwiJXNcIilcbiIsCgkJCSAgICBkLT5kYXRhX3R5cGUsIHN0YXRuYW1lLCB2YXJuYW1lKSk7CgkJcmV0ID0gLTM7CgkJZ290byBSZXR1cm47ICAgICAgICAvKiBJbnZhbGlkIGRhdGEgdHlwZSAqLwoJICAgIH0KCSAgICByZXQgPSAwOyAgICAgICAgLyogU3VjY2VzcyAgKi8KCSAgICBnb3RvIFJldHVybjsKCX0KICAgIH0KICAgIHJldCA9IC00OyAgICAgICAgICAgICAgIC8qIE5hbWUgbm90IGZvdW5kICovCiBSZXR1cm46CiAgICByZXR1cm4gcmV0Owp9CgppbnQKZ2V0S3N0YXRTdHJpbmcoY29uc3QgY2hhciAqc3RhdG5hbWUsIGNvbnN0IGNoYXIgKnZhcm5hbWUsCiAgICAgICAgICAgICAgIGNoYXIgKnZhbHVlLCBzaXplX3QgdmFsdWVfbGVuKQp7CiAgICBrc3RhdF9jdGxfdCAgICAqa3NjOwogICAga3N0YXRfdCAgICAgICAgKmtzLCAqa3N0YXRfZGF0YTsKICAgIGtzdGF0X25hbWVkX3QgICpkOwogICAgc2l6ZV90ICAgICAgICAgIGksIGluc3RhbmNlOwogICAgY2hhciAgICAgICAgICAgIG1vZHVsZV9uYW1lWzY0XTsKICAgIGludCAgICAgICAgICAgICByZXQ7CgogICAgaWYgKGtzdGF0X2ZkID09IDApIHsKICAgICAgICBrc3RhdF9mZCA9IGtzdGF0X29wZW4oKTsKICAgICAgICBpZiAoa3N0YXRfZmQgPT0gMCkgewogICAgICAgICAgICBzbm1wX2xvZ19wZXJyb3IoImtzdGF0X29wZW4iKTsKICAgICAgICB9CiAgICB9CiAgICBpZiAoKGtzYyA9IGtzdGF0X2ZkKSA9PSBOVUxMKSB7CiAgICAgICAgcmV0ID0gLTEwOwogICAgICAgIGdvdG8gUmV0dXJuOyAgICAgICAgLyoga3N0YXQgZXJyb3JzICovCiAgICB9CiAgICBpZiAoc3RhdG5hbWUgPT0gTlVMTCB8fCB2YXJuYW1lID09IE5VTEwpIHsKICAgICAgICByZXQgPSAtMjA7CiAgICAgICAgZ290byBSZXR1cm47CiAgICB9CgogICAgLyoKICAgICAqIEZpcnN0LCBnZXQgImtzdGF0X2hlYWRlcnMiIHN0YXRpc3RpY3MuIEl0IHNob3VsZAogICAgICogY29udGFpbiBhbGwgYXZhaWxhYmxlIG1vZHVsZXMuCiAgICAgKi8KCiAgICBpZiAoKGtzID0ga3N0YXRfbG9va3VwKGtzYywgInVuaXgiLCAwLCAia3N0YXRfaGVhZGVycyIpKSA9PSBOVUxMKSB7CiAgICAgICAgcmV0ID0gLTEwOwogICAgICAgIGdvdG8gUmV0dXJuOyAgICAgICAgLyoga3N0YXQgZXJyb3JzICovCiAgICB9CiAgICBpZiAoa3N0YXRfcmVhZChrc2MsIGtzLCBOVUxMKSA8PSAwKSB7CiAgICAgICAgcmV0ID0gLTEwOwogICAgICAgIGdvdG8gUmV0dXJuOyAgICAgICAgLyoga3N0YXQgZXJyb3JzICovCiAgICB9CiAgICBrc3RhdF9kYXRhID0ga3MtPmtzX2RhdGE7CgogICAgLyoKICAgICAqIE5vdywgbG9vayBmb3IgdGhlIG5hbWUgb2Ygb3VyIHN0YXQgaW4gdGhlIGhlYWRlcnMgYnVmCiAgICAgKi8KICAgIGZvciAoaSA9IDA7IGkgPCBrcy0+a3NfbmRhdGE7IGkrKykgewogICAgICAgIERFQlVHTVNHVEwoKCJrZXJuZWxfc3Vub3M1IiwKICAgICAgICAgICAgICAgICAgICAibW9kdWxlOiAlcyBpbnN0YW5jZTogJWQgbmFtZTogJXMgY2xhc3M6ICVzIHR5cGU6ICVkIGZsYWdzOiAleFxuIiwKICAgICAgICAgICAgICAgICAgICBrc3RhdF9kYXRhW2ldLmtzX21vZHVsZSwga3N0YXRfZGF0YVtpXS5rc19pbnN0YW5jZSwKICAgICAgICAgICAgICAgICAgICBrc3RhdF9kYXRhW2ldLmtzX25hbWUsIGtzdGF0X2RhdGFbaV0ua3NfY2xhc3MsCiAgICAgICAgICAgICAgICAgICAga3N0YXRfZGF0YVtpXS5rc190eXBlLCBrc3RhdF9kYXRhW2ldLmtzX2ZsYWdzKSk7CiAgICAgICAgaWYgKHN0cmNtcChzdGF0bmFtZSwga3N0YXRfZGF0YVtpXS5rc19uYW1lKSA9PSAwKSB7CiAgICAgICAgICAgIHN0cmNweShtb2R1bGVfbmFtZSwga3N0YXRfZGF0YVtpXS5rc19tb2R1bGUpOwogICAgICAgICAgICBpbnN0YW5jZSA9IGtzdGF0X2RhdGFbaV0ua3NfaW5zdGFuY2U7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgIH0KICAgIH0KCiAgICBpZiAoaSA9PSBrcy0+a3NfbmRhdGEpIHsKICAgICAgICByZXQgPSAtMTsKICAgICAgICBnb3RvIFJldHVybjsgICAgICAgIC8qIE5vdCBmb3VuZCAqLwogICAgfQoKICAgIC8qCiAgICAgKiBHZXQgdGhlIG5hbWVkIHN0YXRpc3RpY3MKICAgICAqLwogICAgaWYgKChrcyA9IGtzdGF0X2xvb2t1cChrc2MsIG1vZHVsZV9uYW1lLCBpbnN0YW5jZSwgc3RhdG5hbWUpKSA9PSBOVUxMKSB7CiAgICAgICAgcmV0ID0gLTEwOwogICAgICAgIGdvdG8gUmV0dXJuOyAgICAgICAgLyoga3N0YXQgZXJyb3JzICovCiAgICB9CgogICAgaWYgKGtzdGF0X3JlYWQoa3NjLCBrcywgTlVMTCkgPD0gMCkgewogICAgICAgIHJldCA9IC0xMDsKICAgICAgICBnb3RvIFJldHVybjsgICAgICAgIC8qIGtzdGF0IGVycm9ycyAqLwogICAgfQogICAgLyoKICAgICAqIFRoaXMgZnVuY3Rpb24gZXhwZWN0cyBvbmx5IG5hbWUvdmFsdWUgdHlwZSBvZiBzdGF0aXN0aWNzLCBzbyBpZiBpdCBpcwogICAgICogbm90IHRoZSBjYXNlIHJldHVybiBhbiBlcnJvcgogICAgICovCiAgICBpZiAoa3MtPmtzX3R5cGUgIT0gS1NUQVRfVFlQRV9OQU1FRCkgewogICAgICAgIHJldCA9IC0yOwogICAgICAgIGdvdG8gUmV0dXJuOyAgICAgICAgLyogSW52YWxpZCBzdGF0IHR5cGUgKi8KICAgIH0KCiAgICBmb3IgKGkgPSAwLCBkID0gS1NUQVRfTkFNRURfUFRSKGtzKTsgaSA8IGtzLT5rc19uZGF0YTsgaSsrLCBkKyspIHsKICAgICAgICBERUJVR01TR1RMKCgia2VybmVsX3N1bm9zNSIsICJ2YXJpYWJsZTogXCIlc1wiICh0eXBlICVkKVxuIiwKICAgICAgICAgICAgICAgICAgICBkLT5uYW1lLCBkLT5kYXRhX3R5cGUpKTsKCiAgICAgICAgaWYgKHN0cmNtcChkLT5uYW1lLCB2YXJuYW1lKSA9PSAwKSB7CiAgICAgICAgICAgIHN3aXRjaCAoZC0+ZGF0YV90eXBlKSB7CiAgICAgICAgICAgIGNhc2UgS1NUQVRfREFUQV9DSEFSOgogICAgICAgICAgICAgICAgc3RybGNweSh2YWx1ZSwgZC0+dmFsdWUuYywgdmFsdWVfbGVuKTsKICAgICAgICAgICAgICAgIERFQlVHTVNHVEwoKCJrZXJuZWxfc3Vub3M1IiwgInZhbHVlOiAlc1xuIiwgZC0+dmFsdWUuYykpOwogICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIGRlZmF1bHQ6CiAgICAgICAgICAgICAgICBERUJVR01TR1RMKCgia2VybmVsX3N1bm9zNSIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAiTk9OU1RSSU5HIFRZUEUgJWQgKHN0YXQgXCIlc1wiIHZhciBcIiVzXCIpXG4iLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgZC0+ZGF0YV90eXBlLCBzdGF0bmFtZSwgdmFybmFtZSkpOwogICAgICAgICAgICAgICAgcmV0ID0gLTM7CiAgICAgICAgICAgICAgICBnb3RvIFJldHVybjsgICAgICAgIC8qIEludmFsaWQgZGF0YSB0eXBlICovCiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0ID0gMDsgICAgICAgIC8qIFN1Y2Nlc3MgICovCiAgICAgICAgICAgIGdvdG8gUmV0dXJuOwogICAgICAgIH0KICAgIH0KICAgIHJldCA9IC00OyAgICAgICAgICAgICAgIC8qIE5hbWUgbm90IGZvdW5kICovCiBSZXR1cm46CiAgICByZXR1cm4gcmV0Owp9CgovKgogKiBnZXQgTUlCLUlJIHN0YXRpc3RpY3MuIEl0IG1haW50YWluZXMgYSBzaW1wbGUgY2FjaGUgd2hpY2ggYnVmZmVycyB0aGUgbGFzdAogKiByZWFkIGJsb2NrIG9mIE1JQiBzdGF0aXN0aWNzICh3aGljaCBtYXkgY29udGFpbiB0aGUgd2hvbGUgdGFibGUpLiBJdCBjYWxscwogKiAqY29tcCB0byBjb21wYXJlIGV2ZXJ5IGVudHJ5IHdpdGggYW4gZW50cnkgcG9pbnRlZCBieSBhcmcuICpjb21wIHNob3VsZAogKiByZXR1cm4gMCBpZiBjb21wYXJpc29uIGlzIHN1Y2Nlc3NmdWwuICBSZXFfdHlwZSBtYXkgYmUgR0VUX0ZJUlNULCBHRVRfRVhBQ1QsCiAqIEdFVF9ORVhULiAgSWYgc2VhcmNoIGlzIHN1Y2Nlc3NmdWwgZ2V0TWlic3RhdCByZXR1cm5zIDAsIG90aGVyd2lzZSAxLgogKi8KaW50CmdldE1pYnN0YXQobWliZ3JvdXBfZSBncmlkLCB2b2lkICpyZXNwLCBzaXplX3QgZW50cnlzaXplLAoJICAgcmVxX2UgcmVxX3R5cGUsIGludCAoKmNvbXApICh2b2lkICosIHZvaWQgKiksIHZvaWQgKmFyZykKewogICAgaW50ICAgICAgICAgICAgIHJldCwgcmMgPSAtMSwgbWliZ3IsIG1pYnRiLCBjYWNoZV92YWxpZDsKICAgIHNpemVfdCAgICAgICAgICBsZW5ndGg7CiAgICBtaWJjYWNoZSAgICAgICAqY2FjaGVwOwogICAgZm91bmRfZSAgICAgICAgIHJlc3VsdCA9IE5PVF9GT1VORDsKICAgIHZvaWQgICAgICAgICAgICplcDsKCiAgICAvKgogICAgICogV2UgYXNzdW1lIHRoYXQgTWliY2FjaGUgaXMgaW5pdGlhbGl6ZWQgaW4gbWliZ3JvdXBfZSBlbnVtIG9yZGVyIHNvIHdlCiAgICAgKiBkb24ndCBjaGVjayB0aGUgdmFsaWRpdHkgb2YgaW5kZXggaGVyZS4KICAgICAqLwoKICAgIERFQlVHTVNHVEwoKCJrZXJuZWxfc3Vub3M1IiwgImdldE1pYnN0YXQgKCVkLCAqLCAlZCwgJWQsICosICopXG4iLAoJCWdyaWQsIGVudHJ5c2l6ZSwgcmVxX3R5cGUpKTsKICAgIGNhY2hlcCA9ICZNaWJjYWNoZVtncmlkXTsKICAgIG1pYmdyID0gTWlibWFwW2dyaWRdLmdyb3VwOwogICAgbWlidGIgPSBNaWJtYXBbZ3JpZF0udGFibGU7CgogICAgaWYgKGNhY2hlcC0+Y2FjaGVfYWRkciA9PSAodm9pZCAqKSAtMSkgIC8qIEhhc24ndCBiZWVuIGluaXRpYWxpemVkIHlldCAqLwoJaW5pdF9taWJjYWNoZV9lbGVtZW50KGNhY2hlcCk7CiAgICBpZiAoY2FjaGVwLT5jYWNoZV9zaXplID09IDApIHsgIC8qIE1lbW9yeSBhbGxvY2F0aW9uIHByb2JsZW1zICovCgljYWNoZXAtPmNhY2hlX2FkZHIgPSByZXNwOyAgLyogU28gdXNlIGNhbGxlciBzdXBwbGllZCBhZGRyZXNzIGluc3RlYWQgb2YgY2FjaGUgKi8KCWNhY2hlcC0+Y2FjaGVfc2l6ZSA9IGVudHJ5c2l6ZTsKCWNhY2hlcC0+Y2FjaGVfbGFzdF9mb3VuZCA9IDA7CiAgICB9CiAgICBpZiAocmVxX3R5cGUgIT0gR0VUX05FWFQpCgljYWNoZXAtPmNhY2hlX2xhc3RfZm91bmQgPSAwOwoKICAgIGNhY2hlX3ZhbGlkID0gKGNhY2hlcC0+Y2FjaGVfdGltZSA+IDApOwoKICAgIERFQlVHTVNHVEwoKCJrZXJuZWxfc3Vub3M1IiwiLi4uIGNhY2hlX3ZhbGlkICVkIHRpbWUgJWxkIHR0bCAlZCBub3cgJWxkXG4iLAoJCWNhY2hlX3ZhbGlkLCBjYWNoZXAtPmNhY2hlX3RpbWUsIGNhY2hlcC0+Y2FjaGVfdHRsLAoJCXRpbWUoTlVMTCkpKTsKICAgIGlmIChjYWNoZV92YWxpZCkgewoJLyoKCSAqIElzIGl0IHJlYWxseT8gCgkgKi8KCWlmIChjYWNoZXAtPmNhY2hlX2NvbXAgIT0gKHZvaWQgKiljb21wIHx8IGNhY2hlcC0+Y2FjaGVfYXJnICE9IGFyZykgewoJICAgIGNhY2hlX3ZhbGlkID0gMDsgICAgICAgIC8qIE5vcGUuICovCgl9CiAgICB9CgogICAgaWYgKGNhY2hlX3ZhbGlkKSB7CgkvKgoJICogRW50cnkgaXMgdmFsaWQsIGxldCdzIHRyeSB0byBmaW5kIGEgbWF0Y2ggCgkgKi8KCglpZiAocmVxX3R5cGUgPT0gR0VUX05FWFQpIHsKCSAgICByZXN1bHQgPSBnZXRlbnRyeShyZXFfdHlwZSwKCQkJICAgICAgKHZvaWQgKikoKGNoYXIgKiljYWNoZXAtPmNhY2hlX2FkZHIgKwoJCQkJICAgICAgIChjYWNoZXAtPmNhY2hlX2xhc3RfZm91bmQgKiBlbnRyeXNpemUpKSwKCQkJICAgICAgY2FjaGVwLT5jYWNoZV9sZW5ndGggLQoJCQkgICAgICAoY2FjaGVwLT5jYWNoZV9sYXN0X2ZvdW5kICogZW50cnlzaXplKSwKCQkJICAgICAgZW50cnlzaXplLCAmZXAsIGNvbXAsIGFyZyk7CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICByZXN1bHQgPSBnZXRlbnRyeShyZXFfdHlwZSwgY2FjaGVwLT5jYWNoZV9hZGRyLAoJCQkJICBjYWNoZXAtPmNhY2hlX2xlbmd0aCwgZW50cnlzaXplLCAmZXAsIGNvbXAsCgkJCQkgIGFyZyk7CiAgICAgICAgICAgIH0KICAgIH0KCiAgICBpZiAoKGNhY2hlX3ZhbGlkID09IDApIHx8IChyZXN1bHQgPT0gTk9UX0ZPVU5EKSB8fAoJKHJlc3VsdCA9PSBORUVEX05FWFQgJiYgY2FjaGVwLT5jYWNoZV9mbGFncyAmIENBQ0hFX01PUkVEQVRBKSkgewoJLyoKCSAqIEVpdGhlciB0aGUgY2FjaGUgaXMgb2xkLCBvciB3ZSBoYXZlbid0IGZvdW5kIGFueXRoaW5nLCBvciBuZWVkIHRoZQoJICogbmV4dCBpdGVtIHdoaWNoIGhhc24ndCBiZWVuIHJlYWQgeWV0LiAgSW4gYW55IGNhc2UsIGZpbGwgdGhlIGNhY2hlCgkgKiB1cCBhbmQgdHJ5IHRvIGZpbmQgb3VyIGVudHJ5LgoJICovCgoJaWYgKGdyaWQgPT0gTUlCX0lOVEVSRkFDRVMpIHsKCSAgICByYyA9IGdldGlmKChtaWIyX2lmRW50cnlfdCAqKSBjYWNoZXAtPmNhY2hlX2FkZHIsCgkJICAgICAgIGNhY2hlcC0+Y2FjaGVfc2l6ZSwgcmVxX3R5cGUsCgkJICAgICAgIChtaWIyX2lmRW50cnlfdCAqKSAmIGVwLCAmbGVuZ3RoLCBjb21wLCBhcmcpOwoJfSBlbHNlIHsKCSAgICByYyA9IGdldG1pYihtaWJnciwgbWlidGIsIGNhY2hlcC0+Y2FjaGVfYWRkciwKCQkJY2FjaGVwLT5jYWNoZV9zaXplLCBlbnRyeXNpemUsIHJlcV90eXBlLCAmZXAsCgkJCSZsZW5ndGgsIGNvbXAsIGFyZyk7Cgl9CgoJaWYgKHJjID49IDApIHsgICAgICAvKiBDYWNoZSBoYXMgYmVlbiBmaWxsZWQgdXAgKi8KCSAgICBjYWNoZXAtPmNhY2hlX3RpbWUgPSBjYWNoZXAtPmNhY2hlX3R0bDsKCSAgICBjYWNoZXAtPmNhY2hlX2xlbmd0aCA9IGxlbmd0aDsKCSAgICBpZiAocmMgPT0gMSkgICAgLyogRm91bmQgYnV0IHRoZXJlIGFyZSBtb3JlIHVucmVhZCBkYXRhICovCgkJY2FjaGVwLT5jYWNoZV9mbGFncyB8PSBDQUNIRV9NT1JFREFUQTsKCSAgICBlbHNlIHsKCQljYWNoZXAtPmNhY2hlX2ZsYWdzICY9IH5DQUNIRV9NT1JFREFUQTsKICAgICAgICAgICAgICAgIGlmIChyYyA+IDEpICB7CiAgICAgICAgICAgICAgICAgICAgY2FjaGVwLT5jYWNoZV90aW1lID0gMDsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgfQoJICAgIGNhY2hlcC0+Y2FjaGVfY29tcCA9ICh2b2lkICopIGNvbXA7CgkgICAgY2FjaGVwLT5jYWNoZV9hcmcgPSBhcmc7Cgl9IGVsc2UgewoJICAgIGNhY2hlcC0+Y2FjaGVfY29tcCA9IE5VTEw7CgkgICAgY2FjaGVwLT5jYWNoZV9hcmcgPSBOVUxMOwoJfQogICAgfQogICAgREVCVUdNU0dUTCgoImtlcm5lbF9zdW5vczUiLCAiLi4uIHJlc3VsdCAlZCByYyAlZFxuIiwgcmVzdWx0LCByYykpOwogICAgCiAgICBpZiAocmVzdWx0ID09IEZPVU5EIHx8IHJjID09IDAgfHwgcmMgPT0gMSkgewoJLyoKCSAqIEVudHJ5IGhhcyBiZWVuIGZvdW5kLCBkZWxpdmVyIGl0IAoJICovCglpZiAocmVzcCAhPSBOVUxMKSB7CgkgICAgbWVtY3B5KHJlc3AsIGVwLCBlbnRyeXNpemUpOwoJfQoJcmV0ID0gMDsKCWNhY2hlcC0+Y2FjaGVfbGFzdF9mb3VuZCA9CgkgICAgKChjaGFyICopZXAgLSAoY2hhciAqKWNhY2hlcC0+Y2FjaGVfYWRkcikgLyBlbnRyeXNpemU7CiAgICB9IGVsc2UgewoJcmV0ID0gMTsgICAgICAgICAgICAvKiBOb3QgZm91bmQgKi8KICAgIH0KICAgIERFQlVHTVNHVEwoKCJrZXJuZWxfc3Vub3M1IiwgIi4uLiBnZXRNaWJzdGF0IHJldHVybnMgJWRcbiIsIHJldCkpOwogICAgcmV0dXJuIHJldDsKfQoKLyoKICogR2V0IGEgTUlCLUlJIGVudHJ5IGZyb20gdGhlIGJ1ZmZlciBidWZmYWRkciwgd2hpY2ggc2F0aXNmaWVzIHRoZSBjcml0ZXJpb24sCiAqIGNvbXB1dGVkIGJ5ICgqY29tcCksIHdoaWNoIGdldHMgYXJnIGFzIHRoZSBmaXJzdCBhcmd1bWVudCBhbmQgcG9pbnRlciB0byB0aGUKICogY3VycmVudCBwb3NpdGlvbiBpbiB0aGUgYnVmZmVyIGFzIHRoZSBzZWNvbmQuIElmIGZvdW5kIGVudHJ5IGlzIHBvaW50ZWQgYnkKICogcmVzcC4KICovCgpzdGF0aWMgZm91bmRfZQpnZXRlbnRyeShyZXFfZSByZXFfdHlwZSwgdm9pZCAqYnVmYWRkciwgc2l6ZV90IGxlbiwKCSBzaXplX3QgZW50cnlzaXplLCB2b2lkICpyZXNwLCBpbnQgKCpjb21wKSh2b2lkICosIHZvaWQgKiksCgkgdm9pZCAqYXJnKQp7CiAgICB2b2lkICpicCA9IGJ1ZmFkZHIsICoqcnAgPSByZXNwOwogICAgaW50IHByZXZpb3VzX2ZvdW5kID0gMDsKICAgIAogICAgaWYgKChsZW4gPiAwKSAmJiAobGVuICUgZW50cnlzaXplICE9IDApKSB7CiAgICAgICAgLyogCiAgICAgICAgICogVGhlIGRhdGEgaW4gdGhlIGNhY2hlIGRvZXMgbm90IG1ha2Ugc2Vuc2UsIHRoZSBzaXplIG11c3QgYmUgYSAKICAgICAgICAgKiBtdWx0aXBsZSBvZiB0aGUgZW50cnkuIENvdWxkIGJlIGNhdXNlZCBieSBhbGlnbm1lbnQgaXNzdWVzIGV0Yy4gCiAgICAgICAgICovCiAgICAgICAgREVCVUdNU0dUTCgoImtlcm5lbF9zdW5vczUiLCAKICAgICAgICAgICAgImJhZCBjYWNoZSBsZW5ndGggJWQgLSBub3QgbXVsdGlwbGUgb2YgZW50cnkgc2l6ZSAlZFxuIiwgCiAgICAgICAgICAgIGxlbiwgZW50cnlzaXplKSk7CiAgICAgICAgcmV0dXJuIE5PVF9GT1VORDsKICAgIH0KCiAgICAvKgogICAgICogSGVyZSB3ZSBoYXZlIHRvIHBlcmZvcm0gYWRkcmVzcyBhcml0aG1ldGljIHdpdGggcG9pbnRlciB0byB2b2lkLiBVZ2x5Li4uCiAgICAgKi8KCiAgICBmb3IgKDsgbGVuID4gMDsgbGVuIC09IGVudHJ5c2l6ZSwgYnAgPSAoY2hhciAqKSBicCArIGVudHJ5c2l6ZSkgewoJaWYgKHJwICE9ICh2b2lkICopIE5VTEwpIHsKCSAgICAqcnAgPSBicDsKCX0KCglpZiAocmVxX3R5cGUgPT0gR0VUX0ZJUlNUIHx8IChyZXFfdHlwZSA9PSBHRVRfTkVYVCAmJiBwcmV2aW91c19mb3VuZCkpewoJICAgIHJldHVybiBGT1VORDsKCX0KCglpZiAoKCpjb21wKShhcmcsIGJwKSA9PSAwKSB7CgkgICAgaWYgKHJlcV90eXBlID09IEdFVF9FWEFDVCkgewoJCXJldHVybiBGT1VORDsKCSAgICB9IGVsc2UgeyAgICAgICAgLyogR0VUX05FWFQgKi8KCQlwcmV2aW91c19mb3VuZCsrOwoJCWNvbnRpbnVlOwoJICAgIH0KCX0KICAgIH0KCiAgICBpZiAocHJldmlvdXNfZm91bmQpIHsKCXJldHVybiBORUVEX05FWFQ7CiAgICB9IGVsc2UgewoJcmV0dXJuIE5PVF9GT1VORDsKICAgIH0KfQoKLyoKICogSW5pdGlhbGl6ZSBhIGNhY2hlIGVsZW1lbnQuIEl0IGFsbG9jYXRlcyB0aGUgbWVtb3J5IGFuZCBzZXRzIHRoZSB0aW1lIHN0YW1wCiAqIHRvIGludmFsaWRhdGUgdGhlIGVsZW1lbnQuCiAqLwpzdGF0aWMgdm9pZAppbml0X21pYmNhY2hlX2VsZW1lbnQobWliY2FjaGUgKiBjcCkKewogICAgaWYgKGNwID09IChtaWJjYWNoZSAqKU5VTEwpIHsKCXJldHVybjsKICAgIH0KICAgIGlmIChjcC0+Y2FjaGVfc2l6ZSkgewoJY3AtPmNhY2hlX2FkZHIgPSBtYWxsb2MoY3AtPmNhY2hlX3NpemUpOwogICAgfQogICAgY3AtPmNhY2hlX3RpbWUgPSAwOwogICAgY3AtPmNhY2hlX2NvbXAgPSBOVUxMOwogICAgY3AtPmNhY2hlX2FyZyA9IE5VTEw7Cn0KCi8qCiAqIEdldCBNSUItSUkgc3RhdGlzdGljcyBmcm9tIHRoZSBTb2xhcmlzIGtlcm5lbC4gIEl0IHVzZXMgdW5kb2N1bWVudGVkCiAqIGludGVyZmFjZSB0byBUQ1AvSVAgc3RyZWFtcyBtb2R1bGVzLCB3aGljaCBwcm92aWRlcyBleHRlbmRlZCBNSUItSUkgZm9yIHRoZQogKiBmb2xsb3dpbmcgZ3JvdXBzOiBpcCwgaWNtcCwgdGNwLCB1ZHAsIGVncC4KIAogKiAKICogVXNhZ2U6IGdyb3VwbmFtZSwgc3ViZ3JvdXBuYW1lIGFyZSBmcm9tIDxpbmV0L21pYjIuaD4sIAogKiAgICAgICAgc2l6ZSVzaXplb2Yoc3RhdGJ1ZikgPT0gMCwKICogICAgICAgIGVudHJ5c2l6ZSBzaG91bGQgYmUgZXhhY3Qgc2l6ZSBvZiBNSUItSUkgZW50cnksCiAqICAgICAgICByZXFfdHlwZToKICogICAgICAgICAgICAgICAgICAgR0VUX0ZJUlNUIC0gZ2V0IHRoZSBmaXJzdCBlbnRyeSBpbiB0aGUgYnVmZmVyCiAqICAgICAgICAgICAgICAgICAgIEdFVF9FWEFDVCAtIGdldCBleGFjdCBtYXRjaAogKiAgICAgICAgICAgICAgICAgICBHRVRfTkVYVCAgLSBnZXQgbmV4dCBlbnRyeSBhZnRlciB0aGUgZXhhY3QgbWF0Y2gKICogCiAqICgqY29tcCkgaXMgYSBjb21wYXJlIGZ1bmN0aW9uLCBwcm92aWRlZCBieSB0aGUgY2FsbGVyLCB3aGljaCBnZXRzIGFyZyBhcyB0aGUKICogZmlyc3QgYXJndW1lbnQgYW5kIHBvaW50ZXIgdG8gdGhlIGN1cnJlbnQgZW50cnkgYXMgdGggc2Vjb25kLiBJZiBjb21wYXJlZCwKICogc2hvdWxkIHJldHVybiAwIGFuZCBmb3VuZCBlbnRyeSB3aWxsIGJlIHBvaW50ZWQgYnkgcmVzcC4KICogCiAqIElmIHNlYXJjaCBpcyBzdWNjZXNzZnVsIGFuZCBubyBtb3JlIGRhdGEgdG8gcmVhZCwgaXQgcmV0dXJucyAwLAogKiBpZiBzdWNjZXNzZnVsIGFuZCB0aGVyZSBpcyBtb3JlIGRhdGEgLS0gMSwKICogaWYgbm90IGZvdW5kIGFuZCBlbmQgb2YgZGF0YSAtLSAyLCBhbnkgb3RoZXIgZXJyb3JzIC0tIDwgMAogKiAobmVnYXRpdmUgZXJyb3IgbnVtYmVycyBhcmUgcHJldHR5IHJhbmRvbSkuCiAqIAogKiBOT1RFOiBuZWVkcyB0byBiZSBwcm90ZWN0ZWQgYnkgYSBtdXRleCBpbiByZWVudHJhbnQgZW52aXJvbm1lbnQgCiAqLwoKc3RhdGljIGludApnZXRtaWIoaW50IGdyb3VwbmFtZSwgaW50IHN1Ymdyb3VwbmFtZSwgdm9pZCAqc3RhdGJ1Ziwgc2l6ZV90IHNpemUsCiAgICAgICBzaXplX3QgZW50cnlzaXplLCByZXFfZSByZXFfdHlwZSwgdm9pZCAqcmVzcCwKICAgICAgIHNpemVfdCAqbGVuZ3RoLCBpbnQgKCpjb21wKSh2b2lkICosIHZvaWQgKiksIHZvaWQgKmFyZykKewogICAgaW50ICAgICAgICAgICAgIHJjLCByZXQgPSAwLCBmbGFnczsKICAgIGNoYXIgICAgICAgICAgICBidWZbQlVGU0laRV07CiAgICBzdHJ1Y3Qgc3RyYnVmICAgc3RyYnVmOwogICAgc3RydWN0IFRfb3B0bWdtdF9yZXEgKnRvciA9IChzdHJ1Y3QgVF9vcHRtZ210X3JlcSAqKSBidWY7CiAgICBzdHJ1Y3QgVF9vcHRtZ210X2FjayAqdG9hID0gKHN0cnVjdCBUX29wdG1nbXRfYWNrICopIGJ1ZjsKICAgIHN0cnVjdCBUX2Vycm9yX2FjayAqdGVhID0gKHN0cnVjdCBUX2Vycm9yX2FjayAqKSBidWY7CiAgICBzdHJ1Y3Qgb3B0aGRyICAqcmVxOwogICAgZm91bmRfZSAgICAgICAgIHJlc3VsdCA9IEZPVU5EOwoKICAgIERFQlVHTVNHVEwoKCJrZXJuZWxfc3Vub3M1IiwgIi4uLi4uLiBnZXRtaWIgKCVkLCAlZCwgLi4uKVxuIiwKCQlncm91cG5hbWUsIHN1Ymdyb3VwbmFtZSkpOwoKICAgIC8qCiAgICAgKiBPcGVuIHRoZSBzdHJlYW0gZHJpdmVyIGFuZCBwdXNoIGFsbCBNSUItcmVsYXRlZCBtb2R1bGVzIAogICAgICovCgogICAgaWYgKHNkID09IC0yKSB7ICAgICAgICAgLyogRmlyc3QgdGltZSAqLwoJaWYgKChzZCA9IG9wZW4oU1RSRUFNX0RFViwgT19SRFdSKSkgPT0gLTEpIHsKCSAgICBzbm1wX2xvZ19wZXJyb3IoU1RSRUFNX0RFVik7CgkgICAgcmV0ID0gLTE7CgkgICAgZ290byBSZXR1cm47Cgl9CglpZiAoaW9jdGwoc2QsIElfUFVTSCwgInRjcCIpID09IC0xKSB7CgkgICAgc25tcF9sb2dfcGVycm9yKCJJX1BVU0ggdGNwIik7CgkgICAgcmV0ID0gLTE7CgkgICAgZ290byBSZXR1cm47Cgl9CglpZiAoaW9jdGwoc2QsIElfUFVTSCwgInVkcCIpID09IC0xKSB7CgkgICAgc25tcF9sb2dfcGVycm9yKCJJX1BVU0ggdWRwIik7CgkgICAgcmV0ID0gLTE7CgkgICAgZ290byBSZXR1cm47Cgl9CglERUJVR01TR1RMKCgia2VybmVsX3N1bm9zNSIsICIuLi4uLi4gbW9kdWxlcyBwdXNoZWQgT0tcbiIpKTsKICAgIH0KICAgIGlmIChzZCA9PSAtMSkgewoJcmV0ID0gLTE7Cglnb3RvIFJldHVybjsKICAgIH0KCiAgICAvKgogICAgICogRmlyc3QsIHVzZSBiaWdnZXIgYnVmZmVyLCB0byBhY2NlbGVyYXRlIHNraXBwaW5nIHVud2FudGVkIG1lc3NhZ2VzCiAgICAgKi8KCiAgICBzdHJidWYuYnVmID0gYnVmOwogICAgc3RyYnVmLm1heGxlbiA9IEJVRlNJWkU7CiAgICAKICAgIHRvci0+UFJJTV90eXBlID0gVF9PUFRNR01UX1JFUTsKICAgIHRvci0+T1BUX29mZnNldCA9IHNpemVvZihzdHJ1Y3QgVF9vcHRtZ210X3JlcSk7CiAgICB0b3ItPk9QVF9sZW5ndGggPSBzaXplb2Yoc3RydWN0IG9wdGhkcik7CiNpZmRlZiBNSV9UX0NVUlJFTlQKICAgIHRvci0+TUdNVF9mbGFncyA9IE1JX1RfQ1VSUkVOVDsgLyogU29sYXJpcyA8IDIuNiAqLwojZWxzZQogICAgdG9yLT5NR01UX2ZsYWdzID0gVF9DVVJSRU5UOyAgICAvKiBTb2xhcmlzIDIuNiAqLwojZW5kaWYKICAgIHJlcSA9IChzdHJ1Y3Qgb3B0aGRyICopKHRvciArIDEpOwogICAgcmVxLT5sZXZlbCA9IGdyb3VwbmFtZTsKICAgIHJlcS0+bmFtZSA9IHN1Ymdyb3VwbmFtZTsKICAgIC8qCiAgICAgKiBub24temVybyBsZW4gZmllbGQgaXMgdXNlZCB0byByZXF1ZXN0IGV4dGVuZGVkIE1JQiBzdGF0aXN0aWNzCiAgICAgKiBvbiBTb2xhcmlzIDEwIFVwZGF0ZSA0IGFuZCBsYXRlci4gVGhlIExFR0FDWV9NSUJfU0laRSBtYWNybyBpcyBvbmx5CiAgICAgKiBhdmFpbGFibGUgZm9yIFMxMFU0Kywgc28gd2UgdXNlIHRoYXQgdG8gc2VlIHdoYXQgYWN0aW9uIHRvIHRha2UuCiAgICAgKi8KI2lmZGVmIExFR0FDWV9NSUJfU0laRQogICAgcmVxLT5sZW4gPSAxOwkvKiBhc2sgZm9yIGV4dGVuZGVkIE1JQnMgKi8KI2Vsc2UKICAgIHJlcS0+bGVuID0gMDsKI2VuZGlmCiAgICBzdHJidWYubGVuID0gdG9yLT5PUFRfbGVuZ3RoICsgdG9yLT5PUFRfb2Zmc2V0OwogICAgZmxhZ3MgPSAwOwogICAgaWYgKChyYyA9IHB1dG1zZyhzZCwgJnN0cmJ1ZiwgTlVMTCwgZmxhZ3MpKSkgewoJcmV0ID0gLTI7Cglnb3RvIFJldHVybjsKICAgIH0KCiAgICByZXEgPSAoc3RydWN0IG9wdGhkciAqKSAodG9hICsgMSk7CiAgICBmb3IgKDs7KSB7CglmbGFncyA9IDA7CglpZiAoKHJjID0gZ2V0bXNnKHNkLCAmc3RyYnVmLCBOVUxMLCAmZmxhZ3MpKSA9PSAtMSkgewoJICAgIHJldCA9IC1FSU87CgkgICAgYnJlYWs7Cgl9CglpZiAocmMgPT0gMCAmJiBzdHJidWYubGVuID49IHNpemVvZihzdHJ1Y3QgVF9vcHRtZ210X2FjaykgJiYKCSAgICB0b2EtPlBSSU1fdHlwZSAgPT0gVF9PUFRNR01UX0FDSyAmJgoJICAgIHRvYS0+TUdNVF9mbGFncyA9PSBUX1NVQ0NFU1MgJiYgcmVxLT5sZW4gPT0gMCkgewoJICAgIHJldCA9IDI7CgkgICAgYnJlYWs7Cgl9CglpZiAoc3RyYnVmLmxlbiA+PSBzaXplb2Yoc3RydWN0IFRfZXJyb3JfYWNrKSAmJgoJICAgIHRlYS0+UFJJTV90eXBlID09IFRfRVJST1JfQUNLKSB7CgkgICAgLyogUHJvdG9jb2wgZXJyb3IgKi8KCSAgICByZXQgPSAtKCh0ZWEtPlRMSV9lcnJvciA9PSBUU1lTRVJSKSA/IHRlYS0+VU5JWF9lcnJvciA6IEVQUk9UTyk7CgkgICAgYnJlYWs7Cgl9CglpZiAocmMgIT0gTU9SRURBVEEgfHwgc3RyYnVmLmxlbiA8IHNpemVvZihzdHJ1Y3QgVF9vcHRtZ210X2FjaykgfHwKCSAgICB0b2EtPlBSSU1fdHlwZSAhPSBUX09QVE1HTVRfQUNLIHx8CgkgICAgdG9hLT5NR01UX2ZsYWdzICE9IFRfU1VDQ0VTUykgewoJICAgIHJldCA9IC1FTk9NU0c7ICAvKiBObyBtb3JlIG1lc3NhZ2VzICovCgkgICAgYnJlYWs7Cgl9CgoJLyoKCSAqIFRoZSBvcmRlciBpbiB3aGljaCB3ZSBnZXQgdGhlIHN0YXRpc3RpY3MgaXMgZGV0ZXJtaW5lZCBieSB0aGUga2VybmVsCgkgKiBhbmQgbm90IGJ5IHRoZSBncm91cCBuYW1lLCBzbyB3ZSBoYXZlIHRvIGxvb3AgdW50aWwgd2UgZ2V0IHRoZQoJICogcmVxdWlyZWQgc3RhdGlzdGljcy4KCSAqLwoKCWlmIChyZXEtPmxldmVsICE9IGdyb3VwbmFtZSB8fCByZXEtPm5hbWUgIT0gc3ViZ3JvdXBuYW1lKSB7CgkgICAgc3RyYnVmLm1heGxlbiA9IEJVRlNJWkU7CgkgICAgc3RyYnVmLmJ1ZiA9IGJ1ZjsKCSAgICBkbyB7CgkJcmMgPSBnZXRtc2coc2QsIE5VTEwsICZzdHJidWYsICZmbGFncyk7CgkgICAgfSB3aGlsZSAocmMgPT0gTU9SRURBVEEpOwoJICAgIGNvbnRpbnVlOwoJfQogICAgICAgIAoJLyoKCSAqIE5vdyB3aGVuIHdlIGZvdW5kIG91ciBzdGF0LCBzd2l0Y2ggYnVmZmVyIHRvIGEgY2FsbGVyLXByb3ZpZGVkCgkgKiBvbmUuIE1hbmlwdWxhdGluZyB0aGUgc2l6ZSBvZiBpdCBvbmUgY2FuIGNvbnRyb2wgcGVyZm9ybWFuY2UsCgkgKiByZWR1Y2luZyB0aGUgbnVtYmVyIG9mIGdldG1zZyBjYWxscwoJICovCgoJc3RyYnVmLmJ1ZiA9IHN0YXRidWY7CglzdHJidWYubWF4bGVuID0gc2l6ZTsKCXN0cmJ1Zi5sZW4gPSAwOwoJZmxhZ3MgPSAwOwoJZG8gewoJICAgIHJjID0gZ2V0bXNnKHNkLCBOVUxMLCAmc3RyYnVmLCAmZmxhZ3MpOwoJICAgIHN3aXRjaCAocmMpIHsKCSAgICBjYXNlIC0xOgoJCXJjID0gLUVOT1NSOwoJCWdvdG8gUmV0dXJuOwoKCSAgICBkZWZhdWx0OgoJCXJjID0gLUVOT0RBVEE7CgkJZ290byBSZXR1cm47CgoJICAgIGNhc2UgTU9SRURBVEE6CgkgICAgY2FzZSAwOgoJCWlmIChyZXFfdHlwZSA9PSBHRVRfTkVYVCAmJiByZXN1bHQgPT0gTkVFRF9ORVhUKQoJCSAgICAvKgoJCSAgICAgKiBFbmQgb2YgYnVmZmVyLCBzbyAibmV4dCIgaXMgdGhlIGZpcnN0IGl0ZW0gaW4gdGhlIG5leHQKCQkgICAgICogYnVmZmVyICAKCQkgICAgICovCgkJICAgIHJlcV90eXBlID0gR0VUX0ZJUlNUOwoJCXJlc3VsdCA9IGdldGVudHJ5KHJlcV90eXBlLCAodm9pZCAqKSBzdHJidWYuYnVmLCBzdHJidWYubGVuLAoJCQkJICBlbnRyeXNpemUsIHJlc3AsIGNvbXAsIGFyZyk7CgkJKmxlbmd0aCA9IHN0cmJ1Zi5sZW47ICAgICAgIC8qIFRvIHVzZSBpbiBjYWxsZXIgZm9yIGNhY2hlaW5nICovCgkJYnJlYWs7CgkgICAgfQoJfSB3aGlsZSAocmMgPT0gTU9SRURBVEEgJiYgcmVzdWx0ICE9IEZPVU5EKTsKCglpZiAocmVzdWx0ID09IEZPVU5EKSB7ICAgICAgLyogU2VhcmNoIGlzIHN1Y2Nlc3NmdWwgKi8KCSAgICBpZiAocmMgIT0gTU9SRURBVEEpIHsKCQlyZXQgPSAwOyAgICAvKiBGb3VuZCBhbmQgbm8gbW9yZSBkYXRhICovCgkgICAgfSBlbHNlIHsKCQlyZXQgPSAxOyAgICAvKiBGb3VuZCBhbmQgdGhlcmUgaXMgYW5vdGhlciB1bnJlYWQgZGF0YSBibG9jayAqLwoJICAgIH0KCSAgICBicmVhazsKCX0gZWxzZSB7ICAgICAgICAgICAgLyogUmVzdG9yZSBidWZmZXJzLCBjb250aW51ZSBzZWFyY2ggKi8KCSAgICBzdHJidWYuYnVmID0gYnVmOwoJICAgIHN0cmJ1Zi5tYXhsZW4gPSBCVUZTSVpFOwoJfQogICAgfQogUmV0dXJuOgogICAgaWYgKHNkID49IDApIGlvY3RsKHNkLCBJX0ZMVVNILCBGTFVTSFJXKTsKICAgIERFQlVHTVNHVEwoKCJrZXJuZWxfc3Vub3M1IiwgIi4uLi4uLiBnZXRtaWIgcmV0dXJucyAlZFxuIiwgcmV0KSk7CiAgICByZXR1cm4gcmV0Owp9CiAgCi8qCiAqIEdldCBpbmZvIGZvciBpbnRlcmZhY2VzIGdyb3VwLiBNaW1pY3MgZ2V0bWliIGludGVyZmFjZSBhcyBtdWNoIGFzIHBvc3NpYmxlCiAqIHRvIGJlIHN1YnN0aXR1dGVkIGxhdGVyIGlmIFN1blNvZnQgZGVjaWRlcyB0byBleHRlbmQgaXRzIG1pYjIgaW50ZXJmYWNlLgogKi8KCiNpZiBkZWZpbmVkKEhBVkVfSUZfTkFNRUlOREVYKSAmJiBkZWZpbmVkKE5FVFNOTVBfSU5DTFVERV9JRlRBQkxFX1JFV1JJVEVTKQoKLyoKICogSWYgSUZUQUJMRV9SRVdSSVRFUyBpcyBlbmFibGVkLCB0aGVuIHdlIHdpbGwgYWxzbyByZWx5IG9uIERMUEkgdG8gb2J0YWluCiAqIGluZm9ybWF0aW9uIGZyb20gdGhlIE5JQy4KICovCgovKgogKiBPcGVuIGEgRExQSSBkZXZpY2UuCiAqCiAqIE9uIHN1Y2Nlc3MgdGhlIGZpbGUgZGVzY3JpcHRvciBpcyByZXR1cm5lZC4KICogT24gZXJyb3IgLTEgaXMgcmV0dXJuZWQuCiAqLwpzdGF0aWMgaW50Cl9kbHBpX29wZW4oY29uc3QgY2hhciAqZGV2bmFtZSkKewogICAgY2hhciAqZGV2c3RyOwogICAgaW50IGZkID0gLTE7CiAgICBpbnQgcHBhID0gLTE7CgogICAgREVCVUdNU0dUTCgoImtlcm5lbF9zdW5vczUiLCAiX2RscGlfb3BlbiBjYWxsZWRcbiIpKTsKCiAgICBpZiAoZGV2bmFtZSA9PSBOVUxMKQogICAgICAgIHJldHVybiAoLTEpOwoKICAgIGlmICgoZGV2c3RyID0gbWFsbG9jKDUgKyBzdHJsZW4oZGV2bmFtZSkgKyAxKSkgPT0gTlVMTCkKICAgICAgICByZXR1cm4gKC0xKTsKICAgICh2b2lkKSBzcHJpbnRmKGRldnN0ciwgIi9kZXYvJXMiLCBkZXZuYW1lKTsKICAgIERFQlVHTVNHVEwoKCJrZXJuZWxfc3Vub3M1OmRscGkiLCAiZGV2c3RyKCVzKVxuIiwgZGV2c3RyKSk7CiAgICAvKgogICAgICogRmlyc3QgdHJ5IG9wZW5pbmcgdGhlIGRldmljZSB1c2luZyBzdHlsZSAxLCBpZiB0aGUgZGV2aWNlIGRvZXMgbm90CiAgICAgKiBleGlzdCB3ZSB0cnkgc3R5bGUgMi4gTW9kdWxlcyB3aWxsIG5vdCBiZSBwdXNoZWQsIHNvIHNvbWV0aGluZyBsaWtlCiAgICAgKiBpcCB0dW5uZWxzIHdpbGwgbm90IHdvcmsuIAogICAgICovCiAgIAogICAgREVCVUdNU0dUTCgoImtlcm5lbF9zdW5vczU6ZGxwaSIsICJzdHlsZTEgb3BlbiglcylcbiIsIGRldnN0cikpOwogICAgaWYgKChmZCA9IG9wZW4oZGV2c3RyLCBPX1JEV1IgfCBPX05PTkJMT0NLKSkgPCAwKSB7CiAgICAgICAgREVCVUdNU0dUTCgoImtlcm5lbF9zdW5vczU6ZGxwaSIsICJzdHlsZTEgb3BlbiBmYWlsZWRcbiIpKTsKICAgICAgICBpZiAoX2RscGlfcGFyc2VfZGV2bmFtZShkZXZzdHIsICZwcGEpID09IDApIHsKICAgICAgICAgICAgREVCVUdNU0dUTCgoImtlcm5lbF9zdW5vczU6ZGxwaSIsICJzdHlsZTIgcGFyc2U6ICVzLCAlZFxuIiwgCiAgICAgICAgICAgICAgICAgICAgICAgZGV2c3RyLCBwcGEpKTsKICAgICAgICAgICAgLyogdHJ5IHN0eWxlIDIgKi8KICAgICAgICAgICAgREVCVUdNU0dUTCgoImtlcm5lbF9zdW5vczU6ZGxwaSIsICJzdHlsZTIgb3BlbiglcylcbiIsIGRldnN0cikpOwoKICAgICAgICAgICAgaWYgKChmZCA9IG9wZW4oZGV2c3RyLCBPX1JEV1IgfCBPX05PTkJMT0NLKSkgIT0gLTEpIHsKICAgICAgICAgICAgICAgIGlmIChfZGxwaV9hdHRhY2goZmQsIHBwYSkgPT0gMCkgewogICAgICAgICAgICAgICAgICAgIERFQlVHTVNHVEwoKCJrZXJuZWxfc3Vub3M1OmRscGkiLCAiYXR0YWNoZWRcbiIpKTsKICAgICAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgREVCVUdNU0dUTCgoImtlcm5lbF9zdW5vczU6ZGxwaSIsICJhdHRhY2hlZCBmYWlsZWRcbiIpKTsKICAgICAgICAgICAgICAgICAgICBjbG9zZShmZCk7CiAgICAgICAgICAgICAgICAgICAgZmQgPSAtMTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgIERFQlVHTVNHVEwoKCJrZXJuZWxfc3Vub3M1OmRscGkiLCAic3R5bGUyIG9wZW4gZmFpbGVkXG4iKSk7CiAgICAgICAgICAgIH0KICAgICAgICB9IAogICAgfSBlbHNlIHsKICAgICAgICBERUJVR01TR1RMKCgia2VybmVsX3N1bm9zNTpkbHBpIiwgInN0eWxlMSBvcGVuIHN1Y2NlZWRlZFxuIikpOwogICAgfQoKICAgIC8qIGNsZWFuIHVwICovCiAgICBmcmVlKGRldnN0cik7CgogICAgcmV0dXJuIChmZCk7Cn0KCi8qCiAqIE9idGFpbiB0aGUgcGh5c2ljYWwgYWRkcmVzcyBvZiB0aGUgaW50ZXJmYWNlIHVzaW5nIERMUEkKICovCnN0YXRpYyBpbnQKX2RscGlfZ2V0X3BoeXNfYWRkcmVzcyhpbnQgZmQsIGNoYXIgKmFkZHIsIGludCBtYXhsZW4sIGludCAqYWRkcmxlbikKewogICAgZGxfcGh5c19hZGRyX3JlcV90ICBwYWRkcl9yZXE7CiAgICB1bmlvbiBETF9wcmltaXRpdmVzICpkbHA7CiAgICBzdHJ1Y3Qgc3RyYnVmICAgICAgIGN0bGJ1ZjsKICAgIGNoYXIgICAgICAgICAgICAgICAgYnVmW01BWChETF9QSFlTX0FERFJfQUNLX1NJWkUrNjQsIERMX0VSUk9SX0FDS19TSVpFKV07CiAgICBpbnQgICAgICAgICAgICAgICAgIGZsYWcgPSAwOwoKICAgIERFQlVHTVNHVEwoKCJrZXJuZWxfc3Vub3M1OmRscGkiLCAiX2RscGlfZ2V0X3BoeXNfYWRkcmVzc1xuIikpOwoKICAgIHBhZGRyX3JlcS5kbF9wcmltaXRpdmUgPSBETF9QSFlTX0FERFJfUkVROwogICAgcGFkZHJfcmVxLmRsX2FkZHJfdHlwZSA9IERMX0NVUlJfUEhZU19BRERSOwogICAgY3RsYnVmLmJ1ZiA9IChjaGFyICopJnBhZGRyX3JlcTsKICAgIGN0bGJ1Zi5sZW4gPSBETF9QSFlTX0FERFJfUkVRX1NJWkU7CiAgICBpZiAocHV0bXNnKGZkLCAmY3RsYnVmLCBOVUxMLCAwKSA8IDApCiAgICAgICAgcmV0dXJuICgtMSk7CiAgICAKICAgIGN0bGJ1Zi5tYXhsZW4gPSBzaXplb2YoYnVmKTsKICAgIGN0bGJ1Zi5sZW4gPSAwOwogICAgY3RsYnVmLmJ1ZiA9IGJ1ZjsKICAgIGlmIChnZXRtc2coZmQsICZjdGxidWYsIE5VTEwsICZmbGFnKSA8IDApCiAgICAgICAgcmV0dXJuICgtMSk7CgogICAgaWYgKGN0bGJ1Zi5sZW4gPCBzaXplb2YodWludDMyX3QpKQogICAgICAgIHJldHVybiAoLTEpOwogICAgZGxwID0gKHVuaW9uIERMX3ByaW1pdGl2ZXMgKilidWY7CiAgICBzd2l0Y2ggKGRscC0+ZGxfcHJpbWl0aXZlKSB7CiAgICBjYXNlIERMX1BIWVNfQUREUl9BQ0s6IHsKICAgICAgICBkbF9waHlzX2FkZHJfYWNrX3QgKnBoeXAgPSAoZGxfcGh5c19hZGRyX2Fja190ICopYnVmOwoKICAgICAgICBERUJVR01TR1RMKCgia2VybmVsX3N1bm9zNTpkbHBpIiwgImdvdCBBQ0tcbiIpKTsKICAgICAgICBpZiAoY3RsYnVmLmxlbiA8IERMX1BIWVNfQUREUl9BQ0tfU0laRSB8fCBwaHlwLT5kbF9hZGRyX2xlbmd0aCA+IG1heGxlbikKICAgICAgICAgICAgcmV0dXJuICgtMSk7IAogICAgICAgICh2b2lkKSBtZW1jcHkoYWRkciwgYnVmK3BoeXAtPmRsX2FkZHJfb2Zmc2V0LCBwaHlwLT5kbF9hZGRyX2xlbmd0aCk7CiAgICAgICAgKmFkZHJsZW4gPSBwaHlwLT5kbF9hZGRyX2xlbmd0aDsKICAgICAgICByZXR1cm4gKDApOwogICAgfQogICAgY2FzZSBETF9FUlJPUl9BQ0s6IHsKICAgICAgICBkbF9lcnJvcl9hY2tfdCAqZXJycCA9IChkbF9lcnJvcl9hY2tfdCAqKWJ1ZjsKCiAgICAgICAgREVCVUdNU0dUTCgoImtlcm5lbF9zdW5vczU6ZGxwaSIsICJnb3QgRVJST1IgQUNLXG4iKSk7CiAgICAgICAgaWYgKGN0bGJ1Zi5sZW4gPCBETF9FUlJPUl9BQ0tfU0laRSkKICAgICAgICAgICAgcmV0dXJuICgtMSk7CiAgICAgICAgcmV0dXJuIChlcnJwLT5kbF9lcnJubyk7CiAgICB9CiAgICBkZWZhdWx0OgogICAgICAgIERFQlVHTVNHVEwoKCJrZXJuZWxfc3Vub3M1OmRscGkiLCAiZ290IHR5cGU6ICV4XG4iLCBkbHAtPmRsX3ByaW1pdGl2ZSkpOwogICAgICAgIHJldHVybiAoLTEpOwogICAgfQp9CgovKgogKiBRdWVyeSB0aGUgaW50ZXJmYWNlIGFib3V0IGl0J3MgdHlwZS4KICovCnN0YXRpYyBpbnQKX2RscGlfZ2V0X2lmdHlwZShpbnQgZmQsIHVuc2lnbmVkIGludCAqaWZ0eXBlKQp7CiAgICBkbF9pbmZvX3JlcV90IGluZm9fcmVxOwogICAgdW5pb24gRExfcHJpbWl0aXZlcyAqZGxwOwogICAgc3RydWN0IHN0cmJ1ZiAgICAgICBjdGxidWY7CiAgICBjaGFyICAgICAgICAgICAgICAgIGJ1ZltNQVgoRExfSU5GT19BQ0tfU0laRSwgRExfRVJST1JfQUNLX1NJWkUpXTsKICAgIGludCAgICAgICAgICAgICAgICAgZmxhZyA9IDA7CgogICAgREVCVUdNU0dUTCgoImtlcm5lbF9zdW5vczU6ZGxwaSIsICJfZGxwaV9nZXRfaWZ0eXBlXG4iKSk7CgogICAgaW5mb19yZXEuZGxfcHJpbWl0aXZlID0gRExfSU5GT19SRVE7CiAgICBjdGxidWYuYnVmID0gKGNoYXIgKikmaW5mb19yZXE7CiAgICBjdGxidWYubGVuID0gRExfSU5GT19SRVFfU0laRTsKICAgIGlmIChwdXRtc2coZmQsICZjdGxidWYsIE5VTEwsIDApIDwgMCkgewogICAgICAgIERFQlVHTVNHVEwoKCJrZXJuZWxfc3Vub3M1OmRscGkiLCAicHV0bXNnIGZhaWxlZDogJWRcbm4iLCBlcnJubykpOwogICAgICAgIHJldHVybiAoLTEpOwogICAgfQogICAgCiAgICBjdGxidWYubWF4bGVuID0gc2l6ZW9mKGJ1Zik7CiAgICBjdGxidWYubGVuID0gMDsKICAgIGN0bGJ1Zi5idWYgPSBidWY7CiAgICBpZiAoZ2V0bXNnKGZkLCAmY3RsYnVmLCBOVUxMLCAmZmxhZykgPCAwKSB7CiAgICAgICAgREVCVUdNU0dUTCgoImtlcm5lbF9zdW5vczU6ZGxwaSIsICJnZXRtc2cgZmFpbGVkOiAlZFxuIiwgZXJybm8pKTsKICAgICAgICByZXR1cm4gKC0xKTsKICAgIH0KCiAgICBpZiAoY3RsYnVmLmxlbiA8IHNpemVvZih1aW50MzJfdCkpCiAgICAgICAgcmV0dXJuICgtMSk7CiAgICBkbHAgPSAodW5pb24gRExfcHJpbWl0aXZlcyAqKWJ1ZjsKICAgIHN3aXRjaCAoZGxwLT5kbF9wcmltaXRpdmUpIHsKICAgIGNhc2UgRExfSU5GT19BQ0s6IHsKICAgICAgICBkbF9pbmZvX2Fja190ICppbmZvID0gKGRsX2luZm9fYWNrX3QgKilidWY7CgogICAgICAgIGlmIChjdGxidWYubGVuIDwgRExfSU5GT19BQ0tfU0laRSkKICAgICAgICAgICAgcmV0dXJuICgtMSk7IAoKICAgICAgICBERUJVR01TR1RMKCgia2VybmVsX3N1bm9zNTpkbHBpIiwgImRsX21hY190eXBlOiAleFxuIiwKCSAgICAgICAgICAgaW5mby0+ZGxfbWFjX3R5cGUpKTsKCXN3aXRjaCAoaW5mby0+ZGxfbWFjX3R5cGUpIHsKCWNhc2UgRExfQ1NNQUNEOgoJY2FzZSBETF9FVEhFUjoKCWNhc2UgRExfRVRIX0NTTUE6CgkJKmlmdHlwZSA9IDY7CgkJYnJlYWs7CgljYXNlIERMX1RQQjoJLyogVG9rZW4gUGFzc2luZyBCdXMgKi8KCQkqaWZ0eXBlID0gODsKCQlicmVhazsKCWNhc2UgRExfVFBSOgkvKiBUb2tlbiBQYXNzaW5nIFJpbmcgKi8KCQkqaWZ0eXBlID0gOTsKCQlicmVhazsKCWNhc2UgRExfSERMQzoKCQkqaWZ0eXBlID0gMTE4OwoJCWJyZWFrOwoJY2FzZSBETF9GRERJOgoJCSppZnR5cGUgPSAxNTsKCQlicmVhazsKCWNhc2UgRExfRkM6CS8qIEZpYnJlIGNoYW5uZWwgKi8KCQkqaWZ0eXBlID0gNTY7CgkJYnJlYWs7CgljYXNlIERMX0FUTToKCQkqaWZ0eXBlID0gMzc7CgkJYnJlYWs7CgljYXNlIERMX1gyNToKCWNhc2UgRExfSVNETjoKCQkqaWZ0eXBlID0gNjM7CgkJYnJlYWs7CgljYXNlIERMX0hJUFBJOgoJCSppZnR5cGUgPSA0NzsKCQlicmVhazsKI2lmZGVmIERMX0lCCgljYXNlIERMX0lCOgoJCSppZnR5cGUgPSAxOTk7CgkJYnJlYWs7CiNlbmRpZgoJY2FzZSBETF9GUkFNRToJLyogRnJhbWUgUmVsYXkgKi8KCQkqaWZ0eXBlID0gMzI7CgkJYnJlYWs7CgljYXNlIERMX0xPT1A6CgkJKmlmdHlwZSA9IDI0OwoJCWJyZWFrOwojaWZkZWYgRExfV0lGSQoJY2FzZSBETF9XSUZJOgoJCSppZnR5cGUgPSA3MTsKCQlicmVhazsKI2VuZGlmCiNpZmRlZiBETF9JUFY0CS8qIHRoZW4gSVB2NiBpcyBhbHNvIGRlZmluZWQgKi8KCWNhc2UgRExfSVBWNDoJLyogSVB2NCBUdW5uZWwgKi8KCWNhc2UgRExfSVBWNjoJLyogSVB2NiBUdW5uZWwgKi8KCQkqaWZ0eXBlID0gMTMxOwoJCWJyZWFrOwojZW5kaWYKCWRlZmF1bHQ6CgkJKmlmdHlwZSA9IDE7CS8qIE90aGVyICovCgkJYnJlYWs7Cgl9CgkKICAgICAgICByZXR1cm4gKDApOwogICAgfQogICAgY2FzZSBETF9FUlJPUl9BQ0s6IHsKICAgICAgICBkbF9lcnJvcl9hY2tfdCAqZXJycCA9IChkbF9lcnJvcl9hY2tfdCAqKWJ1ZjsKCiAgICAgICAgREVCVUdNU0dUTCgoImtlcm5lbF9zdW5vczU6ZGxwaSIsCiAgICAgICAgICAgICAgICAgICAgImdvdCBETF9FUlJPUl9BQ0s6IGRscGkgJWQsIGVycm9yICVkXG4iLCBlcnJwLT5kbF9lcnJubywKICAgICAgICAgICAgICAgICAgICBlcnJwLT5kbF91bml4X2Vycm5vKSk7CgogICAgICAgIGlmIChjdGxidWYubGVuIDwgRExfRVJST1JfQUNLX1NJWkUpCiAgICAgICAgICAgIHJldHVybiAoLTEpOwogICAgICAgIHJldHVybiAoZXJycC0+ZGxfZXJybm8pOwogICAgfQogICAgZGVmYXVsdDoKICAgICAgICBERUJVR01TR1RMKCgia2VybmVsX3N1bm9zNTpkbHBpIiwgImdvdCB0eXBlICV4XG4iLCBkbHAtPmRsX3ByaW1pdGl2ZSkpOwogICAgICAgIHJldHVybiAoLTEpOwogICAgfQp9CgpzdGF0aWMgaW50Cl9kbHBpX2F0dGFjaChpbnQgZmQsIGludCBwcGEpCnsKICAgIGRsX2F0dGFjaF9yZXFfdCAgICAgYXR0YWNoX3JlcTsKICAgIHN0cnVjdCBzdHJidWYgICAgICAgY3RsYnVmOwogICAgdW5pb24gRExfcHJpbWl0aXZlcyAqZGxwOwogICAgY2hhciAgICAgICAgICAgICAgICBidWZbTUFYKERMX09LX0FDS19TSVpFLCBETF9FUlJPUl9BQ0tfU0laRSldOwogICAgaW50ICAgICAgICAgICAgICAgICBmbGFnID0gMDsKICAgCiAgICBhdHRhY2hfcmVxLmRsX3ByaW1pdGl2ZSA9IERMX0FUVEFDSF9SRVE7CiAgICBhdHRhY2hfcmVxLmRsX3BwYSA9IHBwYTsKICAgIGN0bGJ1Zi5idWYgPSAoY2hhciAqKSZhdHRhY2hfcmVxOwogICAgY3RsYnVmLmxlbiA9IERMX0FUVEFDSF9SRVFfU0laRTsKICAgIGlmIChwdXRtc2coZmQsICZjdGxidWYsIE5VTEwsIDApICE9IDApCiAgICAgICAgcmV0dXJuICgtMSk7CgogICAgY3RsYnVmLmJ1ZiA9IGJ1ZjsKICAgIGN0bGJ1Zi5sZW4gPSAwOwogICAgY3RsYnVmLm1heGxlbiA9IHNpemVvZihidWYpOwogICAgaWYgKGdldG1zZyhmZCwgJmN0bGJ1ZiwgTlVMTCwgJmZsYWcpICE9IDApCiAgICAgICAgcmV0dXJuICgtMSk7CgogICAgaWYgKGN0bGJ1Zi5sZW4gPCBzaXplb2YodWludDMyX3QpKQogICAgICAgIHJldHVybiAoLTEpOyAKCiAgICBkbHAgPSAodW5pb24gRExfcHJpbWl0aXZlcyAqKWJ1ZjsKICAgIGlmIChkbHAtPmRsX3ByaW1pdGl2ZSA9PSBETF9PS19BQ0sgJiYgY3RsYnVmLmxlbiA+PSBETF9PS19BQ0tfU0laRSkKICAgICAgICByZXR1cm4gKDApOyAKICAgIHJldHVybiAoLTEpOwp9CgpzdGF0aWMgaW50Cl9kbHBpX3BhcnNlX2Rldm5hbWUoY2hhciAqZGV2bmFtZSwgaW50ICpwcGFwKQp7CiAgICBpbnQgcHBhID0gMDsKICAgIGludCBtID0gMTsKICAgIGludCBpID0gc3RybGVuKGRldm5hbWUpIC0gMTsKCiAgICB3aGlsZSAoaSA+PSAwICYmIGlzZGlnaXQoZGV2bmFtZVtpXSkpIHsKICAgICAgICBwcGEgKz0gbSAqIChkZXZuYW1lW2ldIC0gJzAnKTsgCiAgICAgICAgbSAqPSAxMDsKICAgICAgICBpLS07CiAgICB9CgogICAgaWYgKG0gPT0gMSkgewogICAgICAgIHJldHVybiAoLTEpOwogICAgfQogICAgKnBwYXAgPSBwcGE7CiAgICBkZXZuYW1lW2kgKyAxXSA9ICdcMCc7CgogICAgcmV0dXJuICgwKTsKfQpzdGF0aWMgaW50CmdldGlmKG1pYjJfaWZFbnRyeV90ICppZmJ1Ziwgc2l6ZV90IHNpemUsIHJlcV9lIHJlcV90eXBlLAogICAgICBtaWIyX2lmRW50cnlfdCAqcmVzcCwgIHNpemVfdCAqbGVuZ3RoLCBpbnQgKCpjb21wKSh2b2lkICosIHZvaWQgKiksCiAgICAgIHZvaWQgKmFyZykKewogICAgaW50ICAgICAgICAgICAgIGZkLCBpLCByZXQ7CiAgICBpbnQgICAgICAgICAgICAgaWZzZCwgaWZzZDYgPSAtMTsKICAgIHN0cnVjdCBsaWZyZXEgICBsaWZyZXEsICpsaWZycDsKICAgIG1pYjJfaWZFbnRyeV90ICppZnA7CiAgICBpbnQgICAgICAgICAgICAgbmVudHJpZXMgPSBzaXplIC8gc2l6ZW9mKG1pYjJfaWZFbnRyeV90KTsKICAgIGZvdW5kX2UgICAgICAgICByZXN1bHQgPSBOT1RfRk9VTkQ7CiAgICBib29sZWFuX3QgICAgICAgaWZfaXN2NjsKICAgIHVpbnQ2NF90ICAgICAgICBpZl9mbGFnczsgICAgCiAgICBzdHJ1Y3QgaWZfbmFtZWluZGV4ICppZm5hbWUsICppZm5wOwoKICAgIGxpZnJwID0gJmxpZnJlcTsgCgogICAgaWYgKChpZnNkID0gc29ja2V0KEFGX0lORVQsIFNPQ0tfREdSQU0sIDApKSA8IDApIHsKICAgICAgICByZXR1cm4gLTE7CiAgICB9CgogICAgREVCVUdNU0dUTCgoImtlcm5lbF9zdW5vczUiLCAiLi4uLi4uIHVzaW5nIGlmX25hbWVpbmRleFxuIikpOwogICAgaWYgKChpZm5hbWUgPSBpZl9uYW1laW5kZXgoKSkgPT0gTlVMTCkgewogICAgICAgIHJldCA9IC0xOwogICAgICAgIGdvdG8gUmV0dXJuOwogICAgfQogICAgCiAgICAvKgogICAgICogR2F0aGVyIGluZm9ybWF0aW9uIGFib3V0IGVhY2ggaW50ZXJmYWNlIGZvdW5kLiBXZSB0cnkgdG8gaGFuZGxlIGVycm9ycwogICAgICogZ3JhY2VmdWxseTogaWYgYW4gZXJyb3Igb2NjdXJzIHdoaWxlIHByb2Nlc3NpbmcgYW4gaW50ZXJmYWNlIHdlIHNpbXBseQogICAgICogbW92ZSBhbG9uZyB0byB0aGUgbmV4dCBvbmUuIFByZXZpb3VzbHksIHRoZSBmdW5jdGlvbiByZXR1cm5lZCB3aXRoIGFuCiAgICAgKiBlcnJvciByaWdodCBhd2F5LiAKICAgICAqCiAgICAgKiBpZl9uYW1laW5kZXgoKSBhbHJlYWR5IGVsaW1pbmF0ZXMgZHVwbGljYXRlIGludGVyZmFjZXMsIHNvIG5vIGV4dHJhCiAgICAgKiBjaGVja3MgYXJlIG5lZWRlZCBmb3IgaW50ZXJmYWNlcyB0aGF0IGhhdmUgYm90aCBJUHY0IGFuZCBJUHY2IHBsdW1iZWQKICAgICAqLwogQWdhaW46CiAgICBmb3IgKGkgPSAwLCBpZm5wID0gaWZuYW1lLCBpZnAgPSAobWliMl9pZkVudHJ5X3QgKikgaWZidWY7IAogICAgIGlmbnAtPmlmX2luZGV4ICE9IDAgJiYgKGkgPCBuZW50cmllcyk7IGlmbnArKykgewoKICAgICAgICBERUJVR01TR1RMKCgia2VybmVsX3N1bm9zNSIsICIuLi4uLi4gZ2V0aWYgJXNcbiIsIGlmbnAtPmlmX25hbWUpKTsKICAgICAgICBtZW1jcHkobGlmcnAtPmxpZnJfbmFtZSwgaWZucC0+aWZfbmFtZSwgTElGTkFNU0laKTsKICAgICAgICBpZl9pc3Y2ID0gQl9GQUxTRTsKCiAgICAgICAgaWYgKGlvY3RsKGlmc2QsIFNJT0NHTElGRkxBR1MsIGxpZnJwKSA8IDApIHsKICAgICAgICAgICAgaWYgKGlmc2Q2ID09IC0xKSB7CiAgICAgICAgICAgICAgICBpZiAoKGlmc2Q2ID0gc29ja2V0KEFGX0lORVQ2LCBTT0NLX0RHUkFNLCAwKSkgPCAwKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0ID0gLTE7CiAgICAgICAgICAgICAgICAgICAgZ290byBSZXR1cm47CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKGlvY3RsKGlmc2Q2LCBTSU9DR0xJRkZMQUdTLCBsaWZycCkgPCAwKSB7CiAgICAgICAgICAgICAgICBzbm1wX2xvZyhMT0dfRVJSLCAiU0lPQ0dMSUZGTEFHUyAlczogJXNcbiIsIAogICAgICAgICAgICAgICAgICAgICAgICAgbGlmcnAtPmxpZnJfbmFtZSwgc3RyZXJyb3IoZXJybm8pKTsKICAgICAgICAgICAgICAgIGNvbnRpbnVlOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmX2lzdjYgPSBCX1RSVUU7CiAgICAgICAgfSAKICAgICAgICBpZl9mbGFncyA9IGxpZnJwLT5saWZyX2ZsYWdzOwogICAgICAgICAgICAKICAgICAgICBpZiAoaW9jdGwoaWZfaXN2Nj9pZnNkNjppZnNkLCBTSU9DR0xJRk1UVSwgbGlmcnApIDwgMCkgewogICAgICAgICAgICBERUJVR01TR1RMKCgia2VybmVsX3N1bm9zNSIsICIuLi4uLi4gU0lPQ0dMSUZNVFUgZmFpbGVkXG4iKSk7CiAgICAgICAgICAgIGNvbnRpbnVlOwogICAgICAgIH0KCiAgICAgICAgbWVtc2V0KGlmcCwgMCwgc2l6ZW9mKG1pYjJfaWZFbnRyeV90KSk7CgogICAgICAgIGlmICgoZmQgPSBfZGxwaV9vcGVuKGlmbnAtPmlmX25hbWUpKSAhPSAtMSkgewogICAgICAgICAgICAvKiBDb3VsZCBvcGVuIERMUEkuLi4gbm93IHRyeSB0byBncmFiIHNvbWUgaW5mbyAqLwogICAgICAgICAgICAodm9pZCkgX2RscGlfZ2V0X3BoeXNfYWRkcmVzcyhmZCwgaWZwLT5pZlBoeXNBZGRyZXNzLm9fYnl0ZXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2l6ZW9mKGlmcC0+aWZQaHlzQWRkcmVzcy5vX2J5dGVzKSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmaWZwLT5pZlBoeXNBZGRyZXNzLm9fbGVuZ3RoKTsKICAgICAgICAgICAgKHZvaWQpIF9kbHBpX2dldF9pZnR5cGUoZmQsICZpZnAtPmlmVHlwZSk7CiAgICAgICAgICAgIGNsb3NlKGZkKTsKICAgICAgICB9CgogICAgICAgIHNldF9pZl9pbmZvKGlmcCwgaWZucC0+aWZfaW5kZXgsIGlmbnAtPmlmX25hbWUsIGlmX2ZsYWdzLCAKICAgICAgICAgICAgICAgICAgICBsaWZycC0+bGlmcl9tZXRyaWMpOwoKICAgICAgICBpZiAoZ2V0X2lmX3N0YXRzKGlmcCkgPCAwKSB7CiAgICAgICAgICAgIERFQlVHTVNHVEwoKCJrZXJuZWxfc3Vub3M1IiwgIi4uLi4uLiBnZXRfaWZfc3RhdHMgZmFpbGVkXG4iKSk7CiAgICAgICAgICAgIGNvbnRpbnVlOwogICAgICAgIH0KCiAgICAgICAgLyoKICAgICAgICAgKiBPbmNlIHdlIHJlYWNoIGhlcmUgd2Uga25vdyB0aGF0IGFsbCB3ZW50IHdlbGwsIHNvIG1vdmUgdG8KICAgICAgICAgKiB0aGUgbmV4dCBpZkVudHJ5LiAKICAgICAgICAgKi8KICAgICAgICBpKys7CiAgICAgICAgaWZwKys7CiAgICB9CgogICAgaWYgKChyZXFfdHlwZSA9PSBHRVRfTkVYVCkgJiYgKHJlc3VsdCA9PSBORUVEX05FWFQpKSB7CiAgICAgICAgICAgIC8qCiAgICAgICAgICAgICAqIEVuZCBvZiBidWZmZXIsIHNvICJuZXh0IiBpcyB0aGUgZmlyc3QgaXRlbSBpbiB0aGUgbmV4dCBidWZmZXIgCiAgICAgICAgICAgICAqLwogICAgICAgIHJlcV90eXBlID0gR0VUX0ZJUlNUOwogICAgfQoKICAgIHJlc3VsdCA9IGdldGVudHJ5KHJlcV90eXBlLCAodm9pZCAqKSBpZmJ1Ziwgc2l6ZSwgc2l6ZW9mKG1pYjJfaWZFbnRyeV90KSwKICAgICAgICAgICAgICAodm9pZCAqKXJlc3AsIGNvbXAsIGFyZyk7CgogICAgaWYgKChyZXN1bHQgIT0gRk9VTkQpICYmIChpID09IG5lbnRyaWVzKSAmJiBpZm5wLT5pZl9pbmRleCAhPSAwKSB7IAogICAgLyoKICAgICAqIFdlIHJlYWNoZWQgdGhlIGVuZCBvZiBzdXBwbGllZCBidWZmZXIsIGJ1dCB0aGVyZSBpcwogICAgICogc29tZSBtb3JlIHN0dWZmIHRvIHJlYWQsIHNvIGNvbnRpbnVlLgogICAgICovCiAgICAgICAgZ290byBBZ2FpbjsKICAgIH0KCiAgICBpZiAocmVzdWx0ICE9IEZPVU5EKSB7CiAgICAgICAgcmV0ID0gMjsKICAgIH0gZWxzZSB7CiAgICAgICAgaWYgKGlmbnAtPmlmX2luZGV4ICE9IDApIHsKICAgICAgICAgICAgcmV0ID0gMTsgICAgICAgIC8qIEZvdW5kIGFuZCBtb3JlIGRhdGEgdG8gZmV0Y2ggKi8KICAgICAgICB9IGVsc2UgewogICAgICAgICAgICByZXQgPSAwOyAgICAgICAgLyogRm91bmQgYW5kIG5vIG1vcmUgZGF0YSAqLwogICAgICAgIH0KICAgICAgICAqbGVuZ3RoID0gaSAqIHNpemVvZihtaWIyX2lmRW50cnlfdCk7ICAgICAgIC8qIEFjdHVhbCBjYWNoZSBsZW5ndGggKi8KICAgIH0KCiBSZXR1cm46CiAgICBpZiAoaWZuYW1lKQogICAgICAgIGlmX2ZyZWVuYW1laW5kZXgoaWZuYW1lKTsKICAgIGNsb3NlKGlmc2QpOwogICAgaWYgKGlmc2Q2ICE9IC0xKQogICAgICAgIGNsb3NlKGlmc2Q2KTsKICAgIHJldHVybiByZXQ7Cn0KI2Vsc2UgLyogb25seSByZWx5IG9uIFNJT0NHSUZDT05GIHRvIGdldCBpbnRlcmZhY2UgaW5mb3JtYXRpb24gKi8gCgpzdGF0aWMgaW50CmdldGlmKG1pYjJfaWZFbnRyeV90ICppZmJ1Ziwgc2l6ZV90IHNpemUsIHJlcV9lIHJlcV90eXBlLAogICAgICBtaWIyX2lmRW50cnlfdCAqcmVzcCwgIHNpemVfdCAqbGVuZ3RoLCBpbnQgKCpjb21wKSh2b2lkICosIHZvaWQgKiksCiAgICAgIHZvaWQgKmFyZykKewogICAgaW50ICAgICAgICAgICAgIGksIHJldCwgaWR4ID0gMTsKICAgIGludCAgICAgICAgICAgICBpZnNkOwogICAgc3RhdGljIGNoYXIgICAgKmJ1ZiA9IE5VTEw7CiAgICBzdGF0aWMgaW50ICAgICAgYnVmc2l6ZSA9IDA7CiAgICBzdHJ1Y3QgaWZjb25mICAgaWZjb25mOwogICAgc3RydWN0IGlmcmVxICAgKmlmcnA7CiAgICBtaWIyX2lmRW50cnlfdCAqaWZwOwogICAgbWliMl9pcE5ldFRvTWVkaWFFbnRyeV90IE1lZGlhOwogICAgaW50ICAgICAgICAgICAgIG5lbnRyaWVzID0gc2l6ZSAvIHNpemVvZihtaWIyX2lmRW50cnlfdCk7CiAgICBpbnQgICAgICAgICAgICAgaWZfZmxhZ3MgPSAwOwogICAgZm91bmRfZSAgICAgICAgIHJlc3VsdCA9IE5PVF9GT1VORDsKCiAgICBpZiAoKGlmc2QgPSBzb2NrZXQoQUZfSU5FVCwgU09DS19ER1JBTSwgMCkpIDwgMCkgewoJcmV0dXJuIC0xOwogICAgfQoKICAgIGlmICghYnVmKSB7CglidWZzaXplID0gMTAyNDA7CglidWYgPSBtYWxsb2MoYnVmc2l6ZSk7CglpZiAoIWJ1ZikgewoJICAgIHJldCA9IC0xOwoJICAgIGdvdG8gUmV0dXJuOwoJfQogICAgfQoKICAgIGlmY29uZi5pZmNfYnVmID0gYnVmOwogICAgaWZjb25mLmlmY19sZW4gPSBidWZzaXplOwogICAgd2hpbGUgKGlvY3RsKGlmc2QsIFNJT0NHSUZDT05GLCAmaWZjb25mKSA9PSAtMSkgewoJYnVmc2l6ZSArPSAxMDI0MDsKCWZyZWUoYnVmKTsKCWJ1ZiA9IG1hbGxvYyhidWZzaXplKTsKCWlmICghYnVmKSB7CgkgICAgcmV0ID0gLTE7CgkgICAgZ290byBSZXR1cm47Cgl9CglpZmNvbmYuaWZjX2J1ZiA9IGJ1ZjsKCWlmY29uZi5pZmNfbGVuID0gYnVmc2l6ZTsKICAgIH0KCiBBZ2FpbjoKICAgIGZvciAoaSA9IDAsIGlmcCA9IChtaWIyX2lmRW50cnlfdCAqKSBpZmJ1ZiwgaWZycCA9IGlmY29uZi5pZmNfcmVxOwoJICgoY2hhciAqKSBpZnJwIDwgKChjaGFyICopIGlmY29uZi5pZmNfYnVmICsgaWZjb25mLmlmY19sZW4pKQogICAgICAgICAgICAgJiYgKGkgPCBuZW50cmllcyk7IGkrKywgaWZwKyssIGlmcnArKywgaWR4KyspIHsKCglERUJVR01TR1RMKCgia2VybmVsX3N1bm9zNSIsICIuLi4uLi4gZ2V0aWYgJXNcbiIsIGlmcnAtPmlmcl9uYW1lKSk7CgoJaWYgKGlvY3RsKGlmc2QsIFNJT0NHSUZGTEFHUywgaWZycCkgPCAwKSB7CgkgICAgcmV0ID0gLTE7CgkgICAgc25tcF9sb2coTE9HX0VSUiwgIlNJT0NHSUZGTEFHUyAlczogJXNcbiIsIGlmcnAtPmlmcl9uYW1lLAogICAgICAgICAgICAgICAgICAgICBzdHJlcnJvcihlcnJubykpOwoJICAgIGdvdG8gUmV0dXJuOwoJfQogICAgICAgIGlmX2ZsYWdzID0gaWZycC0+aWZyX2ZsYWdzOwoKCWlmIChpb2N0bChpZnNkLCBTSU9DR0lGTVRVLCBpZnJwKSA8IDApIHsKCSAgICByZXQgPSAtMTsKCSAgICBERUJVR01TR1RMKCgia2VybmVsX3N1bm9zNSIsICIuLi4uLi4gU0lPQ0dJRk1UVSBmYWlsZWRcbiIpKTsKCSAgICBnb3RvIFJldHVybjsKCX0KCgltZW1zZXQoaWZwLCAwLCBzaXplb2YobWliMl9pZkVudHJ5X3QpKTsKCXNldF9pZl9pbmZvKGlmcCwgaWR4LCBpZnJwLT5pZnJfbmFtZSwgaWZfZmxhZ3MsIGlmcnAtPmlmcl9tZXRyaWMpOwoJCiAgICAgICAgaWYgKGdldF9pZl9zdGF0cyhpZnApIDwgMCkgewogICAgICAgICAgICByZXQgPSAtMTsKICAgICAgICAgICAgZ290byBSZXR1cm47CiAgICAgICAgfQoJLyoKCSAqIEFuIGF0dGVtcHQgdG8gZGV0ZXJtaW5lIHRoZSBwaHlzaWNhbCBhZGRyZXNzIG9mIHRoZSBpbnRlcmZhY2UuCgkgKiBUaGVyZSBzaG91bGQgYmUgYSBtb3JlIGVsZWdhbnQgc29sdXRpb24gdXNpbmcgRExQSSwgYnV0ICJ0aGUgbWFyZ2luCgkgKiBpcyB0b28gc21hbGwgdG8gcHV0IGl0IGhlcmUgLi4uIgoJICovCgoJaWYgKGlvY3RsKGlmc2QsIFNJT0NHSUZBRERSLCBpZnJwKSA8IDApIHsKCSAgICByZXQgPSAtMTsKCSAgICBnb3RvIFJldHVybjsKCX0KCglpZiAoZ2V0TWlic3RhdChNSUJfSVBfTkVULCAmTWVkaWEsIHNpemVvZihtaWIyX2lwTmV0VG9NZWRpYUVudHJ5X3QpLAoJCSAgICAgICBHRVRfRVhBQ1QsICZOYW1lX2NtcCwgaWZycCkgPT0gMCkgewoJICAgIGlmcC0+aWZQaHlzQWRkcmVzcyA9IE1lZGlhLmlwTmV0VG9NZWRpYVBoeXNBZGRyZXNzOwoJfQogICAgfQoKICAgIGlmICgocmVxX3R5cGUgPT0gR0VUX05FWFQpICYmIChyZXN1bHQgPT0gTkVFRF9ORVhUKSkgewogICAgICAgICAgICAvKgogICAgICAgICAgICAgKiBFbmQgb2YgYnVmZmVyLCBzbyAibmV4dCIgaXMgdGhlIGZpcnN0IGl0ZW0gaW4gdGhlIG5leHQgYnVmZmVyIAogICAgICAgICAgICAgKi8KICAgICAgICAgICAgcmVxX3R5cGUgPSBHRVRfRklSU1Q7CiAgICB9CgogICAgcmVzdWx0ID0gZ2V0ZW50cnkocmVxX3R5cGUsICh2b2lkICopIGlmYnVmLCBzaXplLCBzaXplb2YobWliMl9pZkVudHJ5X3QpLAoJCSAgICAgICh2b2lkICopcmVzcCwgY29tcCwgYXJnKTsKCiAgICBpZiAoKHJlc3VsdCAhPSBGT1VORCkgJiYgKGkgPT0gbmVudHJpZXMpICYmIAoJKChjaGFyICopaWZycCA8IChjaGFyICopaWZjb25mLmlmY19idWYgKyBpZmNvbmYuaWZjX2xlbikpIHsKCS8qCgkgKiBXZSByZWFjaGVkIHRoZSBlbmQgb2Ygc3VwcGxpZWQgYnVmZmVyLCBidXQgdGhlcmUgaXMKCSAqIHNvbWUgbW9yZSBzdHVmZiB0byByZWFkLCBzbyBjb250aW51ZS4KCSAqLwoJaWZjb25mLmlmY19sZW4gLT0gaSAqIHNpemVvZihzdHJ1Y3QgaWZyZXEpOwoJaWZjb25mLmlmY19yZXEgPSBpZnJwOwoJZ290byBBZ2FpbjsKICAgIH0KCiAgICBpZiAocmVzdWx0ICE9IEZPVU5EKSB7CiAgICAgICAgICAgIHJldCA9IDI7CiAgICB9IGVsc2UgewoJaWYgKChjaGFyICopaWZycCA8IChjaGFyICopaWZjb25mLmlmY19idWYgKyBpZmNvbmYuaWZjX2xlbikgewoJICAgIHJldCA9IDE7ICAgICAgICAvKiBGb3VuZCBhbmQgbW9yZSBkYXRhIHRvIGZldGNoICovCgl9IGVsc2UgewoJICAgIHJldCA9IDA7ICAgICAgICAvKiBGb3VuZCBhbmQgbm8gbW9yZSBkYXRhICovCgl9CgkqbGVuZ3RoID0gaSAqIHNpemVvZihtaWIyX2lmRW50cnlfdCk7ICAgICAgIC8qIEFjdHVhbCBjYWNoZSBsZW5ndGggKi8KICAgIH0KCiBSZXR1cm46CiAgICBjbG9zZShpZnNkKTsKICAgIHJldHVybiByZXQ7Cn0KI2VuZGlmIC8qZGVmaW5lZChIQVZFX0lGX05BTUVJTkRFWCkmJmRlZmluZWQoTkVUU05NUF9JTkNMVURFX0lGVEFCTEVfUkVXUklURVMpKi8KCnN0YXRpYyB2b2lkCnNldF9pZl9pbmZvKG1pYjJfaWZFbnRyeV90ICppZnAsIHVuc2lnbmVkIGluZGV4LCBjaGFyICpuYW1lLCB1aW50NjRfdCBmbGFncywKICAgICAgICAgICAgaW50IG10dSkKeyAKICAgIGJvb2xlYW5fdCBoYXZlc3BlZWQgPSBCX0ZBTFNFOwoKICAgIC8qCiAgICAgKiBTZXQgYmFzaWMgaW5mb3JtYXRpb24gCiAgICAgKi8KICAgIGlmcC0+aWZJbmRleCA9IGluZGV4OwogICAgaWZwLT5pZkRlc2NyLm9fbGVuZ3RoID0gc3RybGVuKG5hbWUpOwogICAgc3RyY3B5KGlmcC0+aWZEZXNjci5vX2J5dGVzLCBuYW1lKTsKICAgIGlmcC0+aWZBZG1pblN0YXR1cyA9IChmbGFncyAmIElGRl9VUCkgPyAxIDogMjsKICAgIGlmcC0+aWZPcGVyU3RhdHVzID0gKChmbGFncyAmIElGRl9VUCkgJiYgKGZsYWdzICYgSUZGX1JVTk5JTkcpKSA/IDEgOiAyOwogICAgaWZwLT5pZkxhc3RDaGFuZ2UgPSAwOyAgICAgIC8qIFdobyBrbm93cyAuLi4gICovCiAgICBpZnAtPmZsYWdzID0gZmxhZ3M7CiAgICBpZnAtPmlmTXR1ID0gbXR1OwogICAgaWZwLT5pZlNwZWVkID0gMDsKCiAgICAvKgogICAgICogR2V0IGxpbmsgc3BlZWQKICAgICAqLwogICAgaWYgKChnZXRLc3RhdEludChOVUxMLCBuYW1lLCAiaWZzcGVlZCIsICZpZnAtPmlmU3BlZWQpID09IDApKSB7CiAgICAgICAgLyoKICAgICAgICAgKiBjaGVjayBmb3IgU3VuT1MgcGF0Y2ggd2l0aCBoYWxmIGltcGxlbWVudGVkIGlmU3BlZWQgCiAgICAgICAgICovCiAgICAgICAgaWYgKGlmcC0+aWZTcGVlZCA+IDAgJiYgaWZwLT5pZlNwZWVkIDwgMTAwMDApIHsKICAgICAgICAgICAgaWZwLT5pZlNwZWVkICo9IDEwMDAwMDA7CiAgICAgICAgfQoJaGF2ZXNwZWVkID0gQl9UUlVFOwogICAgfSBlbHNlIGlmIChnZXRLc3RhdEludChOVUxMLCBuYW1lLCAiaWZTcGVlZCIsICZpZnAtPmlmU3BlZWQpID09IDApIHsKICAgICAgICAvKgogICAgICAgICAqIHRoaXMgaXMgZ29vZCAKICAgICAgICAgKi8KCWhhdmVzcGVlZCA9IEJfVFJVRTsKICAgIH0gZWxzZSBpZiAoZ2V0S3N0YXRJbnQoImxpbmsiLCBuYW1lLCAiaWZzcGVlZCIsICZpZnAtPmlmU3BlZWQpID09IDApIHsKCWhhdmVzcGVlZCA9IEJfVFJVRTsKICAgIH0KCiAgICAvKiBtYWtlIGlmT3BlclN0YXR1cyBkZXBlbmQgb24gbGluayBzdGF0dXMgaWYgYXZhaWxhYmxlICovCiAgICBpZiAoaWZwLT5pZkFkbWluU3RhdHVzID09IDEpIHsKICAgICAgICBpbnQgaV90bXA7CiAgICAgICAgLyogb25seSBVUGVkIGludGVyZmFjZXMgZ2V0IGNvcnJlY3QgbGluayBzdGF0dXMgLSBpZiBhbnkgKi8KICAgICAgICBpZiAoZ2V0S3N0YXRJbnQoTlVMTCwgbmFtZSwibGlua191cCIsJmlfdG1wKSA9PSAwKSB7CiAgICAgICAgICAgIGlmcC0+aWZPcGVyU3RhdHVzID0gaV90bXAgPyAxIDogMjsKI2lmZGVmIElGRl9GQUlMRUQKICAgICAgICB9IGVsc2UgaWYgKGZsYWdzICYgSUZGX0ZBSUxFRCkgewogICAgICAgICAgICAvKgoJICAgICAqIElmIElQTVAgaXMgdXNlZCwgYW5kIGlmIHRoZSBkYWVtb24gbWFya3MgdGhlIGludGVyZmFjZQoJICAgICAqIGFzICdmYWlsZWQnLCB0aGVuIHdlIGtub3cgZm9yIHN1cmUgc29tZXRoaW5nIGlzIGFtaXNzLgogICAgICAgICAgICAgKi8KICAgICAgICAgICAgaWZwLT5pZk9wZXJTdGF0dXMgPSAyOwojZW5kaWYKCX0gZWxzZSBpZiAoaGF2ZXNwZWVkID09IEJfVFJVRSAmJiBpZnAtPmlmU3BlZWQgPT0gMCkgewoJICAgIC8qIEhldXJpc3RpYyAqLwoJICAgIGlmcC0+aWZPcGVyU3RhdHVzID0gMjsKCX0KICAgIH0KCiAgICAvKgogICAgICogU2V0IGxpbmsgVHlwZSBhbmQgU3BlZWQgKGlmIGl0IGNvdWxkIG5vdCBiZSBkZXRlcm1pbmVkIGZyb20ga3N0YXQpCiAgICAgKi8KICAgIGlmIChpZnAtPmlmVHlwZSA9PSAyNCkgewogICAgICAgIGlmcC0+aWZTcGVlZCA9IDEyNzAwMDAwMDsKICAgIH0gZWxzZSBpZiAoaWZwLT5pZlR5cGUgPT0gMSB8fCBpZnAtPmlmVHlwZSA9PSAwKSB7CiAgICAgICAgLyoKCSAqIENvdWxkIG5vdCBnZXQgdGhlIHR5cGUgZnJvbSBETFBJLCBzbyBsZXRzIGZhbGwgYmFjayB0byB0aGUgaGFyZGNvZGVkCgkgKiB2YWx1ZXMuCgkgKi8KICAgICAgICBzd2l0Y2ggKG5hbWVbMF0pIHsKICAgICAgICBjYXNlICdhJzogICAgICAgICAgLyogYXRoICg4MDIuMTEpICovCiAgICAgICAgICAgIGlmIChuYW1lWzFdID09ICd0JyAmJiBuYW1lWzJdID09ICdoJykKICAgICAgICAgICAgICAgIGlmcC0+aWZUeXBlID0gNzE7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgIGNhc2UgJ2wnOiAgICAgICAgICAvKiBsZSAvIGxvIC8gbGFuZSAoQVRNIExBTiBFbXVsYXRpb24pICovCiAgICAgICAgICAgIGlmIChuYW1lWzFdID09ICdvJykgewogICAgICAgICAgICBpZiAoIWlmcC0+aWZTcGVlZCkKICAgICAgICAgICAgICAgIGlmcC0+aWZTcGVlZCA9IDEyNzAwMDAwMDsKICAgICAgICAgICAgaWZwLT5pZlR5cGUgPSAyNDsKICAgICAgICAgICAgfSBlbHNlIGlmIChuYW1lWzFdID09ICdlJykgewogICAgICAgICAgICBpZiAoIWlmcC0+aWZTcGVlZCkKICAgICAgICAgICAgICAgIGlmcC0+aWZTcGVlZCA9IDEwMDAwMDAwOwogICAgICAgICAgICBpZnAtPmlmVHlwZSA9IDY7CiAgICAgICAgICAgIH0gZWxzZSBpZiAobmFtZVsxXSA9PSAnYScpIHsKICAgICAgICAgICAgaWYgKCFpZnAtPmlmU3BlZWQpCiAgICAgICAgICAgICAgICBpZnAtPmlmU3BlZWQgPSAxNTUwMDAwMDA7CiAgICAgICAgICAgIGlmcC0+aWZUeXBlID0gMzc7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgYnJlYWs7CiAgICAKICAgICAgICBjYXNlICdnJzogICAgICAgICAgLyogZ2UgKGdpZ2FiaXQgZXRoZXJuZXQgY2FyZCkgICovCiAgICAgICAgY2FzZSAnYyc6ICAgICAgICAgIC8qIGNlIChDYXNzaW5pIEdpZ2FiaXQtRXRoZXJuZXQgKFBDSSkgKi8KICAgICAgICAgICAgaWYgKCFpZnAtPmlmU3BlZWQpCiAgICAgICAgICAgIGlmcC0+aWZTcGVlZCA9IDEwMDAwMDAwMDA7CiAgICAgICAgICAgIGlmcC0+aWZUeXBlID0gNjsKICAgICAgICAgICAgYnJlYWs7CiAgICAKICAgICAgICBjYXNlICdoJzogICAgICAgICAgLyogaG1lIChTQnVzIGNhcmQpICovCiAgICAgICAgY2FzZSAnZSc6ICAgICAgICAgIC8qIGVyaSAoUENJIGNhcmQpICovCiAgICAgICAgY2FzZSAnYic6ICAgICAgICAgIC8qIGJlICovCiAgICAgICAgY2FzZSAnZCc6ICAgICAgICAgIC8qIGRtZmUgLS0gZm91bmQgb24gbmV0cmEgWDEgKi8KICAgICAgICAgICAgaWYgKCFpZnAtPmlmU3BlZWQpCiAgICAgICAgICAgIGlmcC0+aWZTcGVlZCA9IDEwMDAwMDAwMDsKICAgICAgICAgICAgaWZwLT5pZlR5cGUgPSA2OwogICAgICAgICAgICBicmVhazsKICAgIAogICAgICAgIGNhc2UgJ2YnOiAgICAgICAgICAvKiBmYSAoRm9yZSBBVE0pICovCiAgICAgICAgICAgIGlmICghaWZwLT5pZlNwZWVkKQogICAgICAgICAgICBpZnAtPmlmU3BlZWQgPSAxNTUwMDAwMDA7CiAgICAgICAgICAgIGlmcC0+aWZUeXBlID0gMzc7CiAgICAgICAgICAgIGJyZWFrOwogICAgCiAgICAgICAgY2FzZSAncSc6ICAgICAgICAgLyogcWUgKFF1YWRFdGhlcikvcWEgKEZvcmUgQVRNKS9xZmUgKFF1YWRGYXN0RXRoZXIpICovCiAgICAgICAgICAgIGlmIChuYW1lWzFdID09ICdhJykgewogICAgICAgICAgICBpZiAoIWlmcC0+aWZTcGVlZCkKICAgICAgICAgICAgICAgIGlmcC0+aWZTcGVlZCA9IDE1NTAwMDAwMDsKICAgICAgICAgICAgaWZwLT5pZlR5cGUgPSAzNzsKICAgICAgICAgICAgfSBlbHNlIGlmIChuYW1lWzFdID09ICdlJykgewogICAgICAgICAgICAgICAgaWYgKCFpZnAtPmlmU3BlZWQpCiAgICAgICAgICAgICAgICAgICAgaWZwLT5pZlNwZWVkID0gMTAwMDAwMDA7CiAgICAgICAgICAgICAgICBpZnAtPmlmVHlwZSA9IDY7CiAgICAgICAgICAgIH0gZWxzZSBpZiAobmFtZVsxXSA9PSAnZicpIHsKICAgICAgICAgICAgICAgIGlmICghaWZwLT5pZlNwZWVkKQogICAgICAgICAgICAgICAgICAgIGlmcC0+aWZTcGVlZCA9IDEwMDAwMDAwMDsKICAgICAgICAgICAgICAgIGlmcC0+aWZUeXBlID0gNjsKICAgICAgICAgICAgfQogICAgICAgICAgICBicmVhazsKICAgIAogICAgICAgIGNhc2UgJ2knOiAgICAgICAgICAvKiBpYmQgKEluZmluaWJhbmQpL2lwLnR1biAoSVAgdHVubmVsKSAqLwogICAgICAgICAgICBpZiAobmFtZVsxXSA9PSAnYicpCiAgICAgICAgICAgICAgICBpZnAtPmlmVHlwZSA9IDE5OTsKICAgICAgICAgICAgZWxzZSBpZiAobmFtZVsxXSA9PSAncCcpCiAgICAgICAgICAgICAgICBpZnAtPmlmVHlwZSA9IDEzMTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgfQogICAgfQp9CgpzdGF0aWMgaW50IApnZXRfaWZfc3RhdHMobWliMl9pZkVudHJ5X3QgKmlmcCkKewogICAgQ291bnRlciBsX3RtcDsKICAgIGNoYXIgKm5hbWUgPSBpZnAtPmlmRGVzY3Iub19ieXRlczsKCiAgICBpZiAoc3RyY2hyKG5hbWUsICc6JykpCiAgICAgICAgcmV0dXJuICgwKTsgCgogICAgLyoKICAgICAqIEZpcnN0IHRyeSB0byBncmFiIDY0LWJpdCBjb3VudGVyczsgaWYgdGhleSBhcmUgbm90IGF2YWlsYWJsZSwKICAgICAqIGZhbGwgYmFjayB0byAzMi1iaXQuCiAgICAgKi8KICAgIGlmIChnZXRLc3RhdChuYW1lLCAiaXBhY2tldHM2NCIsICZpZnAtPmlmSENJblVjYXN0UGt0cykgIT0gMCkgewogICAgICAgIGlmIChnZXRLc3RhdEludChOVUxMLCBuYW1lLCAiaXBhY2tldHMiLCAmaWZwLT5pZkluVWNhc3RQa3RzKSAhPSAwKSB7CiAgICAgICAgICAgIHJldHVybiAoLTEpOwogICAgICAgIH0KICAgIH0gZWxzZSB7IAogICAgICAgICAgICBpZnAtPmlmSW5VY2FzdFBrdHMgPSAodWludDMyX3QpKGlmcC0+aWZIQ0luVWNhc3RQa3RzICYgMHhmZmZmZmZmZik7IAogICAgfQogICAgCiAgICBpZiAoZ2V0S3N0YXQobmFtZSwgInJieXRlczY0IiwgJmlmcC0+aWZIQ0luT2N0ZXRzKSAhPSAwKSB7CiAgICAgICAgaWYgKGdldEtzdGF0SW50KE5VTEwsIG5hbWUsICJyYnl0ZXMiLCAmaWZwLT5pZkluT2N0ZXRzKSAhPSAwKSB7CiAgICAgICAgICAgIGlmcC0+aWZJbk9jdGV0cyA9IGlmcC0+aWZJblVjYXN0UGt0cyAqIDMwODsgCiAgICAgICAgfQogICAgfSBlbHNlIHsKICAgICAgICAgICAgaWZwLT5pZkluT2N0ZXRzID0gKHVpbnQzMl90KShpZnAtPmlmSENJbk9jdGV0cyAmIDB4ZmZmZmZmZmYpOwogICAgfQogICAKICAgIGlmIChnZXRLc3RhdChuYW1lLCAib3BhY2tldHM2NCIsICZpZnAtPmlmSENPdXRVY2FzdFBrdHMpICE9IDApIHsKICAgICAgICBpZiAoZ2V0S3N0YXRJbnQoTlVMTCwgbmFtZSwgIm9wYWNrZXRzIiwgJmlmcC0+aWZPdXRVY2FzdFBrdHMpICE9IDApIHsKICAgICAgICAgICAgcmV0dXJuICgtMSk7CiAgICAgICAgfQogICAgfSBlbHNlIHsKICAgICAgICAgaWZwLT5pZk91dFVjYXN0UGt0cyA9ICh1aW50MzJfdCkoaWZwLT5pZkhDT3V0VWNhc3RQa3RzICYgMHhmZmZmZmZmZik7CiAgICB9CiAgICAKICAgIGlmIChnZXRLc3RhdChuYW1lLCAib2J5dGVzNjQiLCAmaWZwLT5pZkhDT3V0T2N0ZXRzKSAhPSAwKSB7CiAgICAgICAgaWYgKGdldEtzdGF0SW50KE5VTEwsIG5hbWUsICJvYnl0ZXMiLCAmaWZwLT5pZk91dE9jdGV0cykgIT0gMCkgeyAKICAgICAgICAgICAgaWZwLT5pZk91dE9jdGV0cyA9IGlmcC0+aWZPdXRVY2FzdFBrdHMgKiAzMDg7ICAgIC8qIFhYWCAqLwogICAgICAgIH0KICAgIH0gZWxzZSB7CiAgICAgICAgaWZwLT5pZk91dE9jdGV0cyA9ICh1aW50MzJfdCkoaWZwLT5pZkhDT3V0T2N0ZXRzICYgMHhmZmZmZmZmZik7CiAgICB9CgogICAgaWYgKGlmcC0+aWZUeXBlID09IDI0KSAgLyogTG9vcGJhY2sgKi8KICAgICAgICByZXR1cm4gKDApOwoKICAgIC8qIHNvbWU/IFZMQU4gaW50ZXJmYWNlcyBkb24ndCBoYXZlIGVycm9yIGNvdW50ZXJzLCBzbyBpZ25vcmUgZmFpbHVyZSAqLwogICAgZ2V0S3N0YXRJbnQoTlVMTCwgbmFtZSwgImllcnJvcnMiLCAmaWZwLT5pZkluRXJyb3JzKTsKICAgIGdldEtzdGF0SW50KE5VTEwsIG5hbWUsICJvZXJyb3JzIiwgJmlmcC0+aWZPdXRFcnJvcnMpOwoKICAgIC8qIFRyeSB0byBncmFiIHNvbWUgYWRkaXRpb25hbCBpbmZvcm1hdGlvbiAqLwogICAgZ2V0S3N0YXRJbnQoTlVMTCwgbmFtZSwgImNvbGxpc2lvbnMiLCAmaWZwLT5pZkNvbGxpc2lvbnMpOyAKICAgIGdldEtzdGF0SW50KE5VTEwsIG5hbWUsICJ1bmtub3ducyIsICZpZnAtPmlmSW5Vbmtub3duUHJvdG9zKTsgCiAgICAgICAgICAgICAgICAKCiAgICAvKgogICAgICogVE9ETyBzb21lIE5JQ3MgbWFpbnRhaW4gNjQtYml0IGNvdW50ZXJzIGZvciBtdWx0aS9icm9hZGNhc3QKICAgICAqIHBhY2tldHM7IHNob3VsZCB0cnkgdG8gZ2V0IHRoYXQgaW5mb3JtYXRpb24uCiAgICAgKi8KICAgIGlmIChnZXRLc3RhdEludChOVUxMLCBuYW1lLCAiYnJkY3N0cmN2IiwgJmxfdG1wKSA9PSAwKSAKICAgICAgICBpZnAtPmlmSENJbkJyb2FkY2FzdFBrdHMgPSBsX3RtcDsKCiAgICBpZiAoZ2V0S3N0YXRJbnQoTlVMTCwgbmFtZSwgIm11bHRpcmN2IiwgJmxfdG1wKSA9PSAwKQogICAgICAgIGlmcC0+aWZIQ0luTXVsdGljYXN0UGt0cyA9IGxfdG1wOwoKICAgIGlmcC0+aWZJbk5VY2FzdFBrdHMgPSAodWludDMyX3QpKGlmcC0+aWZIQ0luQnJvYWRjYXN0UGt0cyArIAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaWZwLT5pZkhDSW5NdWx0aWNhc3RQa3RzKTsKCiAgICBpZiAoZ2V0S3N0YXRJbnQoTlVMTCwgbmFtZSwgImJyZGNzdHhtdCIsICZsX3RtcCkgPT0gMCkKICAgICAgICBpZnAtPmlmSENPdXRCcm9hZGNhc3RQa3RzID0gbF90bXA7CgogICAgaWYgKGdldEtzdGF0SW50KE5VTEwsIG5hbWUsICJtdWx0aXhtdCIsICZsX3RtcCkgPT0gMCkKICAgICAgICBpZnAtPmlmSENPdXRNdWx0aWNhc3RQa3RzID0gbF90bXA7CgogICAgaWZwLT5pZk91dE5VY2FzdFBrdHMgPSAodWludDMyX3QpKGlmcC0+aWZIQ091dEJyb2FkY2FzdFBrdHMgKyAKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBpZnAtPmlmSENPdXRNdWx0aWNhc3RQa3RzKTsKICAgIHJldHVybigwKTsKfQovKgogKiBBbHdheXMgVFJVRS4gTWF5IGJlIHVzZWQgYXMgYSBjb21wYXJpc29uIGZ1bmN0aW9uIGluIGdldE1pYnN0YXQKICogdG8gb2J0YWluIHRoZSB3aG9sZSB0YWJsZSAoR0VUX0ZJUlNUIHNob3VsZCBiZSB1c2VkKSAKICovCmludApHZXRfZXZlcnl0aGluZyh2b2lkICp4LCB2b2lkICp5KQp7CiAgICByZXR1cm4gMDsgICAgICAgICAgICAgLyogQWx3YXlzIFRSVUUgKi8KfQoKLyoKICogQ29tcGFyZSBuYW1lIGFuZCBJUCBhZGRyZXNzIG9mIHRoZSBpbnRlcmZhY2UgdG8gQVJQIHRhYmxlIGVudHJ5LgogKiBOZWVkZWQgdG8gb2J0YWluIHRoZSBwaHlzaWNhbCBhZGRyZXNzIG9mIHRoZSBpbnRlcmZhY2UgaW4gZ2V0aWYuCiAqLwpzdGF0aWMgaW50Ck5hbWVfY21wKHZvaWQgKmlmcnAsIHZvaWQgKmVwKQp7CiAgICBzdHJ1Y3Qgc29ja2FkZHJfaW4gKnMgPSAoc3RydWN0IHNvY2thZGRyX2luICopCgkgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICYoKChzdHJ1Y3QgaWZyZXEgKilpZnJwKS0+aWZyX2FkZHIpOwogICAgbWliMl9pcE5ldFRvTWVkaWFFbnRyeV90ICpFcCA9IChtaWIyX2lwTmV0VG9NZWRpYUVudHJ5X3QgKillcDsKCiAgICBpZiAoKHN0cm5jbXAoRXAtPmlwTmV0VG9NZWRpYUlmSW5kZXgub19ieXRlcywKCQkgKChzdHJ1Y3QgaWZyZXEgKilpZnJwKS0+aWZyX25hbWUsCgkJIEVwLT5pcE5ldFRvTWVkaWFJZkluZGV4Lm9fbGVuZ3RoKSA9PSAwKSAmJgoJKHMtPnNpbl9hZGRyLnNfYWRkciA9PSBFcC0+aXBOZXRUb01lZGlhTmV0QWRkcmVzcykpIHsKCXJldHVybiAwOwogICAgfSBlbHNlIHsKCXJldHVybiAxOwogICAgfQp9CgovKgogKiBUcnkgdG8gZGV0ZXJtaW5lIHRoZSBpbmRleCBvZiBhIHBhcnRpY3VsYXIgaW50ZXJmYWNlLiBJZiBtZmQtcmV3cml0ZXMgaXMKICogc3BlY2lmaWVkLCB0aGVuIHRoaXMgZnVuY3Rpb24gd291bGQgb25seSBiZSB1c2VkIHdoZW4gdGhlIHN5c3RlbSBkb2VzIG5vdAogKiBoYXZlIGlmX25hbWV0b2luZGV4KDNTT0NLRVQpLgogKi8KaW50CnNvbGFyaXMyX2lmX25hbWV0b2luZGV4KGNvbnN0IGNoYXIgKk5hbWUsIGludCBMZW4pCnsKICAgIGludCAgICAgICAgICAgICBpLCBzZCwgbGFzdGxlbiA9IDAsIGludGVyZmFjZXMgPSAwOwogICAgc3RydWN0IGlmY29uZiAgIGlmYzsKICAgIHN0cnVjdCBpZnJlcSAgICppZnJwID0gTlVMTDsKICAgIGNoYXIgICAgICAgICAgICpidWYgPSBOVUxMOwoKICAgIGlmIChOYW1lID09IDApIHsKICAgICAgICByZXR1cm4gMDsKICAgIH0KICAgIGlmICgoc2QgPSBzb2NrZXQoQUZfSU5FVCwgU09DS19ER1JBTSwgMCkpIDwgMCkgewogICAgICAgIHJldHVybiAwOwogICAgfQoKICAgIC8qCiAgICAgKiBDb3BlIHdpdGggbG90cyBvZiBpbnRlcmZhY2VzIGFuZCBicm9rZW5uZXNzIG9mIGlvY3RsIFNJT0NHSUZDT05GCiAgICAgKiBvbiBzb21lIHBsYXRmb3Jtczsgc2VlIFcuIFIuIFN0ZXZlbnMsIGBgVW5peCBOZXR3b3JrIFByb2dyYW1taW5nCiAgICAgKiBWb2x1bWUgSScnLCBwLjQzNS4gIAogICAgICovCgogICAgZm9yIChpID0gODs7IGkgKz0gOCkgewogICAgICAgIGJ1ZiA9IGNhbGxvYyhpLCBzaXplb2Yoc3RydWN0IGlmcmVxKSk7CiAgICAgICAgaWYgKGJ1ZiA9PSBOVUxMKSB7CiAgICAgICAgICAgIGNsb3NlKHNkKTsKICAgICAgICAgICAgcmV0dXJuIDA7CiAgICAgICAgfQogICAgICAgIGlmYy5pZmNfbGVuID0gaSAqIHNpemVvZihzdHJ1Y3QgaWZyZXEpOwogICAgICAgIGlmYy5pZmNfYnVmID0gKGNhZGRyX3QpIGJ1ZjsKCiAgICAgICAgaWYgKGlvY3RsKHNkLCBTSU9DR0lGQ09ORiwgKGNoYXIgKikgJmlmYykgPCAwKSB7CiAgICAgICAgICAgIGlmIChlcnJubyAhPSBFSU5WQUwgfHwgbGFzdGxlbiAhPSAwKSB7CiAgICAgICAgICAgICAgICAvKgogICAgICAgICAgICAgICAgICogU29tZXRoaW5nIGhhcyBnb25lIGdlbnVpbmVseSB3cm9uZy4gIAogICAgICAgICAgICAgICAgICovCiAgICAgICAgICAgICAgICBmcmVlKGJ1Zik7CiAgICAgICAgICAgICAgICBjbG9zZShzZCk7CiAgICAgICAgICAgICAgICByZXR1cm4gMDsKICAgICAgICAgICAgfQogICAgICAgICAgICAvKgogICAgICAgICAgICAgKiBPdGhlcndpc2UsIGl0IGNvdWxkIGp1c3QgYmUgdGhhdCB0aGUgYnVmZmVyIGlzIHRvbyBzbWFsbC4gIAogICAgICAgICAgICAgKi8KICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBpZiAoaWZjLmlmY19sZW4gPT0gbGFzdGxlbikgewogICAgICAgICAgICAgICAgLyoKICAgICAgICAgICAgICAgICAqIFRoZSBsZW5ndGggaXMgdGhlIHNhbWUgYXMgdGhlIGxhc3QgdGltZTsgd2UncmUgZG9uZS4gIAogICAgICAgICAgICAgICAgICovCiAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgICAgICBsYXN0bGVuID0gaWZjLmlmY19sZW47CiAgICAgICAgfQogICAgICAgIGZyZWUoYnVmKTsKICAgIH0KCiAgICBpZnJwID0gaWZjLmlmY19yZXE7CiAgICBpbnRlcmZhY2VzID0gKGlmYy5pZmNfbGVuIC8gc2l6ZW9mKHN0cnVjdCBpZnJlcSkpICsgMTsKCiAgICBmb3IgKGkgPSAxOyBpIDwgaW50ZXJmYWNlczsgaSsrLCBpZnJwKyspIHsKICAgICAgICBpZiAoc3RybmNtcChpZnJwLT5pZnJfbmFtZSwgTmFtZSwgTGVuKSA9PSAwKSB7CiAgICAgICAgICAgIGZyZWUoYnVmKTsKICAgICAgICAgICAgY2xvc2Uoc2QpOwogICAgICAgICAgICByZXR1cm4gaTsKICAgICAgICB9CiAgICB9CgogICAgZnJlZShidWYpOwogICAgY2xvc2Uoc2QpOwogICAgcmV0dXJuIDA7Cn0KCiNpZmRlZiBfU1REQ19DT01QQVQKI2lmZGVmIF9fY3BsdXNwbHVzCn0KI2VuZGlmCiNlbmRpZgoKI2lmZGVmIF9HRVRLU1RBVF9URVNUCgppbnQKbWFpbihpbnQgYXJnYywgY2hhciAqKmFyZ3YpCnsKICAgIGludCAgICAgICAgICAgICByYyA9IDA7CiAgICB1X2xvbmcgICAgICAgICAgdmFsID0gMDsKCiAgICBpZiAoYXJnYyAhPSAzKSB7CiAgICAgICAgc25tcF9sb2coTE9HX0VSUiwgIlVzYWdlOiAlcyBzdGF0X25hbWUgdmFyX25hbWVcbiIsIGFyZ3ZbMF0pOwogICAgICAgIGV4aXQoMSk7CiAgICB9CgogICAgc25tcF9zZXRfZG9fZGVidWdnaW5nKDEpOwogICAgcmMgPSBnZXRLc3RhdChhcmd2WzFdLCBhcmd2WzJdLCAmdmFsKTsKCiAgICBpZiAocmMgPT0gMCkKICAgICAgICBzbm1wX2xvZyhMT0dfRVJSLCAiJXMgPSAlbHVcbiIsIGFyZ3ZbMl0sIHZhbCk7CiAgICBlbHNlCiAgICAgICAgc25tcF9sb2coTE9HX0VSUiwgInJjID0lZFxuIiwgcmMpOwogICAgcmV0dXJuIDA7Cn0KI2VuZGlmIC8qX0dFVEtTVEFUX1RFU1QgKi8KCiNpZmRlZiBfR0VUTUlCU1RBVF9URVNUCgppbnQKaXAyMGNvbXAodm9pZCAqaWZuYW1lLCB2b2lkICppcHApCnsKICAgIHJldHVybiAoc3RybmNtcCgoY2hhciAqKSBpZm5hbWUsCiAgICAgICAgICAgICAgICAgICAgKChtaWIyX2lwQWRkckVudHJ5X3QgKikgaXBwKS0+aXBBZEVudElmSW5kZXgub19ieXRlcywKICAgICAgICAgICAgICAgICAgICAoKG1pYjJfaXBBZGRyRW50cnlfdCAqKSBpcHApLT5pcEFkRW50SWZJbmRleC4KICAgICAgICAgICAgICAgICAgICBvX2xlbmd0aCkpOwp9CgppbnQKQVJQX0NtcF9BZGRyKHZvaWQgKmFkZHIsIHZvaWQgKmVwKQp7CiAgICBERUJVR01TR1RMKCgia2VybmVsX3N1bm9zNSIsICJBUlA6ICVseCA8PiAlbHhcbiIsCiAgICAgICAgICAgICAgICAoKG1pYjJfaXBOZXRUb01lZGlhRW50cnlfdCAqKSBlcCktPmlwTmV0VG9NZWRpYU5ldEFkZHJlc3MsCiAgICAgICAgICAgICAgICAqKElwQWRkcmVzcyAqKSBhZGRyKSk7CiAgICBpZiAoKChtaWIyX2lwTmV0VG9NZWRpYUVudHJ5X3QgKikgZXApLT5pcE5ldFRvTWVkaWFOZXRBZGRyZXNzID09CiAgICAgICAgKihJcEFkZHJlc3MgKilhZGRyKSB7CiAgICAgICAgcmV0dXJuIDA7CiAgICB9IGVsc2UgewogICAgICAgIHJldHVybiAxOwogICAgfQp9CgppbnQKSUZfY21wKHZvaWQgKmFkZHIsIHZvaWQgKmVwKQp7CiAgICBpZiAoKChtaWIyX2lmRW50cnlfdCAqKWVwKS0+aWZJbmRleCA9PSgobWliMl9pZkVudHJ5X3QgKilhZGRyKS0+aWZJbmRleCkgewogICAgICAgIHJldHVybiAwOwogICAgfSBlbHNlIHsKICAgICAgICByZXR1cm4gMTsKICAgIH0KfQoKaW50Cm1haW4oaW50IGFyZ2MsIGNoYXIgKiphcmd2KQp7CiAgICBpbnQgICAgICAgICAgICAgcmMgPSAwLCBpLCBpZHg7CiAgICBtaWIyX2lwQWRkckVudHJ5X3QgaXBidWYsICppcHAgPSAmaXBidWY7CiAgICBtaWIyX2lwTmV0VG9NZWRpYUVudHJ5X3QgZW50cnksICplcCA9ICZlbnRyeTsKICAgIG1pYjJfaWZFbnRyeV90ICBpZnN0YXQ7CiAgICByZXFfZSAgICAgICAgICAgcmVxX3R5cGU7CiAgICBJcEFkZHJlc3MgICAgICAgTGFzdEFkZHIgPSAwOwoKICAgIGlmIChhcmdjICE9IDMpIHsKICAgICAgICBzbm1wX2xvZyhMT0dfRVJSLAogICAgICAgICAgICAgICAgICJVc2FnZTogJXMgaWZfbmFtZSByZXFfdHlwZSAoMCBmaXJzdCwgMSBleGFjdCwgMiBuZXh0KSBcbiIsCiAgICAgICAgICAgICAgICAgYXJndlswXSk7CiAgICAgICAgZXhpdCgxKTsKICAgIH0KCiAgICBzd2l0Y2ggKGF0b2koYXJndlsyXSkpIHsKICAgIGNhc2UgMDoKICAgICAgICByZXFfdHlwZSA9IEdFVF9GSVJTVDsKICAgICAgICBicmVhazsKICAgIGNhc2UgMToKICAgICAgICByZXFfdHlwZSA9IEdFVF9FWEFDVDsKICAgICAgICBicmVhazsKICAgIGNhc2UgMjoKICAgICAgICByZXFfdHlwZSA9IEdFVF9ORVhUOwogICAgICAgIGJyZWFrOwogICAgfTsKCiAgICBzbm1wX3NldF9kb19kZWJ1Z2dpbmcoMCk7CiAgICB3aGlsZSAoKHJjID0KICAgICAgICAgICAgZ2V0TWlic3RhdChNSUJfSU5URVJGQUNFUywgJmlmc3RhdCwgc2l6ZW9mKG1pYjJfaWZFbnRyeV90KSwKICAgICAgICAgICAgICAgICAgICAgICByZXFfdHlwZSwgJklGX2NtcCwgJmlkeCkpID09IDApIHsKICAgICAgICBpZHggPSBpZnN0YXQuaWZJbmRleDsKICAgICAgICBERUJVR01TR1RMKCgia2VybmVsX3N1bm9zNSIsICJJZm5hbWUgPSAlc1xuIiwKICAgICAgICAgICAgICAgICAgICBpZnN0YXQuaWZEZXNjci5vX2J5dGVzKSk7CiAgICAgICAgcmVxX3R5cGUgPSBHRVRfTkVYVDsKICAgIH0KICAgIHJjID0gZ2V0TWlic3RhdChNSUJfSVBfQUREUiwgJmlwYnVmLCBzaXplb2YobWliMl9pcEFkZHJFbnRyeV90KSwKICAgICAgICAgICAgICAgICAgICByZXFfdHlwZSwgaXAyMGNvbXAsIGFyZ3ZbMV0pOwoKICAgIGlmIChyYyA9PSAwKQogICAgICAgIERFQlVHTVNHVEwoKCJrZXJuZWxfc3Vub3M1IiwgIm10dSA9ICVsZFxuIiwKICAgICAgICAgICAgICAgICAgICBpcHAtPmlwQWRFbnRJbmZvLmFlX210dSkpOwogICAgZWxzZQogICAgICAgIERFQlVHTVNHVEwoKCJrZXJuZWxfc3Vub3M1IiwgInJjID0lZFxuIiwgcmMpKTsKCiAgICB3aGlsZSAoKHJjID0KICAgICAgICAgICAgZ2V0TWlic3RhdChNSUJfSVBfTkVULCAmZW50cnksCiAgICAgICAgICAgICAgICAgICAgICAgc2l6ZW9mKG1pYjJfaXBOZXRUb01lZGlhRW50cnlfdCksIHJlcV90eXBlLAogICAgICAgICAgICAgICAgICAgICAgICZBUlBfQ21wX0FkZHIsICZMYXN0QWRkcikpID09IDApIHsKICAgICAgICBMYXN0QWRkciA9IGVwLT5pcE5ldFRvTWVkaWFOZXRBZGRyZXNzOwogICAgICAgIERFQlVHTVNHVEwoKCJrZXJuZWxfc3Vub3M1IiwgIklwYWRkciA9ICVsWFxuIiwgKHVfbG9uZykgTGFzdEFkZHIpKTsKICAgICAgICByZXFfdHlwZSA9IEdFVF9ORVhUOwogICAgfQogICAgcmV0dXJuIDA7Cn0KI2VuZGlmIC8qX0dFVE1JQlNUQVRfVEVTVCAqLwojZW5kaWYgICAgICAgICAgICAgICAgICAgICAgICAgIC8qIFNVTk9TNSAqLwoKCi8qLQogKiBUaGVzZSB2YXJpYWJsZXMgZGVzY3JpYmUgdGhlIGZvcm1hdHRpbmcgb2YgdGhpcyBmaWxlLiAgSWYgeW91IGRvbid0IGxpa2UgdGhlCiAqIHRlbXBsYXRlIGRlZmF1bHRzLCBmZWVsIGZyZWUgdG8gY2hhbmdlIHRoZW0gaGVyZSAobm90IGluIHlvdXIgLmVtYWNzIGZpbGUpLgogKgogKiBMb2NhbCBWYXJpYWJsZXM6CiAqIGNvbW1lbnQtY29sdW1uOiAzMgogKiBjLWluZGVudC1sZXZlbDogNAogKiBjLWNvbnRpbnVlZC1zdGF0ZW1lbnQtb2Zmc2V0OiA0CiAqIGMtYnJhY2Utb2Zmc2V0OiAtNAogKiBjLWFyZ2RlY2wtaW5kZW50OiAwCiAqIGMtbGFiZWwtb2Zmc2V0OiAtNAogKiBmaWxsLWNvbHVtbjogNzkKICogZmlsbC1wcmVmaXg6ICIgKiAiCiAqIEVuZDoKICovCg==