LyoKICogRGVidWdnZXIgc3RhY2sgaGFuZGxpbmcKICoKICogQ29weXJpZ2h0IDE5OTUgQWxleGFuZHJlIEp1bGxpYXJkCiAqIENvcHlyaWdodCAxOTk2IEVyaWMgWW91bmdkYWxlCiAqIENvcHlyaWdodCAxOTk5IE92ZSBL5XZlbgogKi8KCiNpbmNsdWRlICJjb25maWcuaCIKCiNpbmNsdWRlIDxzdGRpby5oPgojaW5jbHVkZSA8c3RkbGliLmg+CgojaW5jbHVkZSAiZGVidWdnZXIuaCIKI2luY2x1ZGUgInN0YWNrZnJhbWUuaCIKI2luY2x1ZGUgIndpbmJhc2UuaCIKCiNpZmRlZiBfX2kzODZfXwovKgogKiBXZSBrZWVwIHRoaXMgaW5mbyBmb3IgZWFjaCBmcmFtZSwgc28gdGhhdCB3ZSBjYW4KICogZmluZCBsb2NhbCB2YXJpYWJsZSBpbmZvcm1hdGlvbiBjb3JyZWN0bHkuCiAqLwpzdHJ1Y3QgYnRfaW5mbwp7CiAgdW5zaWduZWQgaW50CSAgICAgY3M7CiAgdW5zaWduZWQgaW50CSAgICAgZWlwOwogIHVuc2lnbmVkIGludAkgICAgIHNzOwogIHVuc2lnbmVkIGludAkgICAgIGVicDsKICBzdHJ1Y3Qgc3ltYm9sX2luZm8gZnJhbWU7Cn07CgpzdGF0aWMgaW50IG5mcmFtZTsKc3RhdGljIHN0cnVjdCBidF9pbmZvICogZnJhbWVzID0gTlVMTDsKaW50IGN1cnJfZnJhbWU7Cgp0eXBlZGVmIHN0cnVjdAp7CiAgICBXT1JEIGJwOwogICAgV09SRCBpcDsKICAgIFdPUkQgY3M7Cn0gRlJBTUUxNjsKCnR5cGVkZWYgc3RydWN0CnsKICAgIERXT1JEIGJwOwogICAgRFdPUkQgaXA7CiAgICBXT1JEIGNzOwp9IEZSQU1FMzI7CiNlbmRpZgoKCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiAgICAgICAgICAgREVCVUdfSW5mb1N0YWNrCiAqCiAqIER1bXAgdGhlIHRvcCBvZiB0aGUgc3RhY2sKICovCnZvaWQgREVCVUdfSW5mb1N0YWNrKHZvaWQpCnsKI2lmZGVmIF9faTM4Nl9fCiAgICBEQkdfVkFMVUUJdmFsdWU7CiAgICAKICAgIHZhbHVlLnR5cGUgPSBOVUxMOwogICAgdmFsdWUuY29va2llID0gRFZfVEFSR0VUOwogICAgdmFsdWUuYWRkci5zZWcgPSBERUJVR19jb250ZXh0LlNlZ1NzOwogICAgdmFsdWUuYWRkci5vZmYgPSBERUJVR19jb250ZXh0LkVzcDsKCiAgICBmcHJpbnRmKHN0ZGVyciwiU3RhY2sgZHVtcDpcbiIpOwogICAgc3dpdGNoIChERUJVR19HZXRTZWxlY3RvclR5cGUodmFsdWUuYWRkci5zZWcpKSB7CiAgICBjYXNlIDMyOiAvKiAzMi1iaXQgbW9kZSAqLwogICAgICAgREVCVUdfRXhhbWluZU1lbW9yeSggJnZhbHVlLCAyNCwgJ3gnICk7CiAgICAgICBicmVhazsKICAgIGNhc2UgMTY6ICAvKiAxNi1iaXQgbW9kZSAqLwogICAgICAgIHZhbHVlLmFkZHIub2ZmICY9IDB4ZmZmZjsKICAgICAgICBERUJVR19FeGFtaW5lTWVtb3J5KCAmdmFsdWUsIDI0LCAndycgKTsKCWJyZWFrOwogICAgZGVmYXVsdDoKICAgICAgIGZwcmludGYoc3RkZXJyLCAiQmFkIHNlZ21lbnQgKCVsZClcbiIsIHZhbHVlLmFkZHIuc2VnKTsKICAgIH0KICAgIGZwcmludGYoc3RkZXJyLCJcbiIpOwojZW5kaWYKfQoKI2lmZGVmIF9faTM4Nl9fCnN0YXRpYyB2b2lkIERFQlVHX0ZvcmNlRnJhbWUoREJHX0FERFIgKnN0YWNrLCBEQkdfQUREUiAqY29kZSwgaW50IGZyYW1lbm8sIGludCBiaXRzLCBpbnQgbm9pc3kpCnsKICAgIGludCB0aGVmcmFtZSA9IG5mcmFtZSsrOwogICAgZnJhbWVzID0gKHN0cnVjdCBidF9pbmZvICopREJHX3JlYWxsb2MoZnJhbWVzLAoJCQkJCSAgIG5mcmFtZSpzaXplb2Yoc3RydWN0IGJ0X2luZm8pKTsKICAgIGlmIChub2lzeSkKICAgICAgZnByaW50ZihzdGRlcnIsIiVzJWQgIiwgKHRoZWZyYW1lID09IGN1cnJfZnJhbWUgPyAiPT4iIDogIiAgIiksCiAgICAgICAgICAgICAgZnJhbWVubyk7CiAgICBmcmFtZXNbdGhlZnJhbWVdLmNzID0gY29kZS0+c2VnOwogICAgZnJhbWVzW3RoZWZyYW1lXS5laXAgPSBjb2RlLT5vZmY7CiAgICBpZiAobm9pc3kpCiAgICAgIGZyYW1lc1t0aGVmcmFtZV0uZnJhbWUgPSBERUJVR19QcmludEFkZHJlc3NBbmRBcmdzKCBjb2RlLCBiaXRzLCAKCQkJCQkJCSAgc3RhY2stPm9mZiwgVFJVRSApOwogICAgZWxzZQogICAgICBERUJVR19GaW5kTmVhcmVzdFN5bWJvbCggY29kZSwgVFJVRSwgCgkJCSAgICAgICAmZnJhbWVzW3RoZWZyYW1lXS5mcmFtZS5zeW0sIHN0YWNrLT5vZmYsIAoJCQkgICAgICAgJmZyYW1lc1t0aGVmcmFtZV0uZnJhbWUubGlzdCk7CiAgICBmcmFtZXNbdGhlZnJhbWVdLnNzID0gc3RhY2stPnNlZzsKICAgIGZyYW1lc1t0aGVmcmFtZV0uZWJwID0gc3RhY2stPm9mZjsKICAgIGlmIChub2lzeSkgewogICAgICBmcHJpbnRmKCBzdGRlcnIsIChiaXRzID09IDE2KSA/ICIgKGJwPSUwNGx4KVxuIiA6ICIgKGVicD0lMDhseClcbiIsIHN0YWNrLT5vZmYgKTsKICAgIH0KfQoKc3RhdGljIEJPT0wgREVCVUdfRnJhbWUxNihEQkdfQUREUiAqYWRkciwgdW5zaWduZWQgaW50ICpjcywgaW50IGZyYW1lbm8sIGludCBub2lzeSkKewogICAgdW5zaWduZWQgaW50CXNzID0gYWRkci0+c2VnLCBwb3NzaWJsZV9jcyA9IDA7CiAgICBGUkFNRTE2IAkJZnJhbWU7CiAgICBpbnQgCQl0aGVmcmFtZSA9IG5mcmFtZTsKICAgIHZvaWQqCQlwID0gKHZvaWQqKURFQlVHX1RvTGluZWFyKGFkZHIpOwogICAgCiAgICBpZiAoIXApIHJldHVybiBGQUxTRTsKICAgIAogICAgaWYgKCFERUJVR19SRUFEX01FTShwLCAmZnJhbWUsIHNpemVvZihmcmFtZSkpKSB7CiAgICAgICAgaWYgKG5vaXN5KSB7CgkgICAgZnByaW50ZihzdGRlcnIsIioqKiBJbnZhbGlkIGFkZHJlc3MgIik7CgkgICAgREVCVUdfUHJpbnRBZGRyZXNzKGFkZHIsIERFQlVHX0N1cnJUaHJlYWQtPmRiZ19tb2RlLCBGQUxTRSk7CgkgICAgZnByaW50ZihzdGRlcnIsIlxuIik7Cgl9CglyZXR1cm4gRkFMU0U7CiAgICB9CiAgICBpZiAoIWZyYW1lLmJwKSByZXR1cm4gRkFMU0U7CiAgICBuZnJhbWUrKzsKICAgIGZyYW1lcyA9IChzdHJ1Y3QgYnRfaW5mbyAqKURCR19yZWFsbG9jKGZyYW1lcywKCQkJCQkgICBuZnJhbWUqc2l6ZW9mKHN0cnVjdCBidF9pbmZvKSk7CiAgICBpZiAobm9pc3kpCiAgICAgICAgZnByaW50ZihzdGRlcnIsIiVzJWQgIiwgKHRoZWZyYW1lID09IGN1cnJfZnJhbWUgPyAiPT4iIDogIiAgIiksCgkJZnJhbWVubyk7CiAgICBpZiAoZnJhbWUuYnAgJiAxKSAqY3MgPSBmcmFtZS5jczsKICAgIGVsc2UgewogICAgICAgIC8qIG5vdCBleHBsaWNpdGx5IG1hcmtlZCBhcyBmYXIgY2FsbCwKCSAqIGJ1dCBjaGVjayB3aGV0aGVyIGl0IGNvdWxkIGJlIGFueXdheSAqLwogICAgICAgIGlmICgoKGZyYW1lLmNzJjcpPT03KSAmJiAoZnJhbWUuY3MgIT0gKmNzKSkgewoJICAgIExEVF9FTlRSWQlsZTsKCSAKCSAgICBpZiAoR2V0VGhyZWFkU2VsZWN0b3JFbnRyeSggREVCVUdfQ3VyclRocmVhZC0+aGFuZGxlLCBmcmFtZS5jcywgJmxlKSAmJgoJCShsZS5IaWdoV29yZC5CaXRzLlR5cGUgJiAweDA4KSkgeyAvKiBjb2RlIHNlZ21lbnQgKi8KCSAgICAgICAgLyogaXQgaXMgdmVyeSB1bmNvbW1vbiB0byBwdXNoIGEgY29kZSBzZWdtZW50IGNzIGFzCgkJICogYSBwYXJhbWV0ZXIsIHNvIHRoaXMgc2hvdWxkIHdvcmsgaW4gbW9zdCBjYXNlcyAqLwoJICAgICAgICAqY3MgPSBwb3NzaWJsZV9jcyA9IGZyYW1lLmNzOwoJICAgIH0KCX0KICAgIH0KICAgIGZyYW1lc1t0aGVmcmFtZV0uY3MgPSBhZGRyLT5zZWcgPSAqY3M7CiAgICBmcmFtZXNbdGhlZnJhbWVdLmVpcCA9IGFkZHItPm9mZiA9IGZyYW1lLmlwOwogICAgaWYgKG5vaXN5KQogICAgICAgIGZyYW1lc1t0aGVmcmFtZV0uZnJhbWUgPSBERUJVR19QcmludEFkZHJlc3NBbmRBcmdzKCBhZGRyLCAxNiwgCgkJCQkJCQkgICAgZnJhbWUuYnAsIFRSVUUgKTsKICAgIGVsc2UKICAgICAgICBERUJVR19GaW5kTmVhcmVzdFN5bWJvbCggYWRkciwgVFJVRSwgCgkJCQkgJmZyYW1lc1t0aGVmcmFtZV0uZnJhbWUuc3ltLCBmcmFtZS5icCwgCgkJCQkgJmZyYW1lc1t0aGVmcmFtZV0uZnJhbWUubGlzdCk7CiAgICBmcmFtZXNbdGhlZnJhbWVdLnNzID0gYWRkci0+c2VnID0gc3M7CiAgICBmcmFtZXNbdGhlZnJhbWVdLmVicCA9IGFkZHItPm9mZiA9IGZyYW1lLmJwICYgfjE7CiAgICBpZiAobm9pc3kpIHsKICAgICAgICBmcHJpbnRmKCBzdGRlcnIsICIgKGJwPSUwNGx4IiwgYWRkci0+b2ZmICk7CiAgICAgICAgaWYgKHBvc3NpYmxlX2NzKSB7CgkgICAgZnByaW50Ziggc3RkZXJyLCAiLCBmYXIgY2FsbCBhc3N1bWVkIiApOwoJfQoJZnByaW50Ziggc3RkZXJyLCAiKVxuIiApOwogICAgfQogICAgcmV0dXJuIFRSVUU7Cn0KCnN0YXRpYyBCT09MIERFQlVHX0ZyYW1lMzIoREJHX0FERFIgKmFkZHIsIHVuc2lnbmVkIGludCAqY3MsIGludCBmcmFtZW5vLCBpbnQgbm9pc3kpCnsKICAgIHVuc2lnbmVkIGludCAJc3MgPSBhZGRyLT5zZWc7CiAgICBGUkFNRTMyIAkJZnJhbWU7CiAgICBpbnQgCQl0aGVmcmFtZSA9IG5mcmFtZTsKICAgIHZvaWQqCQlwID0gKHZvaWQqKURFQlVHX1RvTGluZWFyKGFkZHIpOwogICAgCiAgICBpZiAoIXApIHJldHVybiBGQUxTRTsKICAgIAogICAgaWYgKCFERUJVR19SRUFEX01FTShwLCAmZnJhbWUsIHNpemVvZihmcmFtZSkpKSB7CiAgICAgICBpZiAobm9pc3kpIHsKCSAgZnByaW50ZihzdGRlcnIsIioqKiBJbnZhbGlkIGFkZHJlc3MgIik7CgkgIERFQlVHX1ByaW50QWRkcmVzcyhhZGRyLCBERUJVR19DdXJyVGhyZWFkLT5kYmdfbW9kZSwgRkFMU0UpOwoJICBmcHJpbnRmKHN0ZGVyciwiXG4iKTsKICAgICAgIH0KICAgICAgIHJldHVybiBGQUxTRTsKICAgIH0KICAgIGlmICghZnJhbWUuaXApIHJldHVybiBGQUxTRTsKICAgIAogICAgbmZyYW1lKys7CiAgICBmcmFtZXMgPSAoc3RydWN0IGJ0X2luZm8gKilEQkdfcmVhbGxvYyhmcmFtZXMsCgkJCQkJICAgbmZyYW1lKnNpemVvZihzdHJ1Y3QgYnRfaW5mbykpOwogICAgaWYgKG5vaXN5KQogICAgICAgZnByaW50ZihzdGRlcnIsIiVzJWQgIiwgKHRoZWZyYW1lID09IGN1cnJfZnJhbWUgPyAiPT4iIDogIiAgIiksCgkgICAgICAgZnJhbWVubyk7CiAgICBmcmFtZXNbdGhlZnJhbWVdLmNzID0gYWRkci0+c2VnID0gKmNzOwogICAgZnJhbWVzW3RoZWZyYW1lXS5laXAgPSBhZGRyLT5vZmYgPSBmcmFtZS5pcDsKICAgIGlmIChub2lzeSkKICAgICAgICBmcmFtZXNbdGhlZnJhbWVdLmZyYW1lID0gREVCVUdfUHJpbnRBZGRyZXNzQW5kQXJncyggYWRkciwgMzIsIAoJCQkJCQkJICAgIGZyYW1lLmJwLCBUUlVFICk7CiAgICBlbHNlCiAgICAgICAgREVCVUdfRmluZE5lYXJlc3RTeW1ib2woIGFkZHIsIFRSVUUsIAoJCQkJICZmcmFtZXNbdGhlZnJhbWVdLmZyYW1lLnN5bSwgZnJhbWUuYnAsIAoJCQkJICZmcmFtZXNbdGhlZnJhbWVdLmZyYW1lLmxpc3QpOwogICAgaWYgKG5vaXN5KSBmcHJpbnRmKCBzdGRlcnIsICIgKGVicD0lMDhseClcbiIsIGZyYW1lLmJwICk7CiAgICBmcmFtZXNbdGhlZnJhbWVdLnNzID0gYWRkci0+c2VnID0gc3M7CiAgICBmcmFtZXNbdGhlZnJhbWVdLmVicCA9IGZyYW1lLmJwOwogICAgaWYgKGFkZHItPm9mZiA9PSBmcmFtZS5icCkgcmV0dXJuIEZBTFNFOwogICAgYWRkci0+b2ZmID0gZnJhbWUuYnA7CiAgICByZXR1cm4gVFJVRTsKfQojZW5kaWYKCgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogICAgICAgICAgIERFQlVHX0JhY2tUcmFjZQogKgogKiBEaXNwbGF5IGEgc3RhY2sgYmFjay10cmFjZS4KICovCnZvaWQgREVCVUdfQmFja1RyYWNlKEJPT0wgbm9pc3kpCnsKI2lmZGVmIF9faTM4NgogICAgREJHX0FERFIgCQlhZGRyLCBzd19hZGRyLCBjb2RlLCB0bXA7CiAgICB1bnNpZ25lZCBpbnQgCXNzID0gREVCVUdfY29udGV4dC5TZWdTczsKICAgIHVuc2lnbmVkIGludAljcyA9IERFQlVHX2NvbnRleHQuU2VnQ3M7CiAgICBpbnQgCQlmcmFtZW5vID0gMCwgaXMxNiwgb2s7CiAgICBEV09SRCAJCW5leHRfc3dpdGNoLCBjdXJfc3dpdGNoLCBwOwogICAgU1RBQ0sxNkZSQU1FICAgICAgIAlmcmFtZTE2OwogICAgU1RBQ0szMkZSQU1FICAgICAgIAlmcmFtZTMyOwogICAgY2hhcgkJY2g7CgogICAgaWYgKG5vaXN5KSBmcHJpbnRmKCBzdGRlcnIsICJCYWNrdHJhY2U6XG4iICk7CgogICAgbmZyYW1lID0gMTsKICAgIGlmIChmcmFtZXMpIERCR19mcmVlKCBmcmFtZXMgKTsKICAgIGZyYW1lcyA9IChzdHJ1Y3QgYnRfaW5mbyAqKSBEQkdfYWxsb2MoIHNpemVvZihzdHJ1Y3QgYnRfaW5mbykgKTsKICAgIGlmIChub2lzeSkKICAgICAgICBmcHJpbnRmKHN0ZGVyciwiJXMlZCAiLChjdXJyX2ZyYW1lID09IDAgPyAiPT4iIDogIiAgIiksIGZyYW1lbm8pOwoKICAgIGlmIChERUJVR19Jc1NlbGVjdG9yU3lzdGVtKHNzKSkgc3MgPSAwOwogICAgaWYgKERFQlVHX0lzU2VsZWN0b3JTeXN0ZW0oY3MpKSBjcyA9IDA7CgogICAgLyogZmlyc3Qgc3RhY2sgZnJhbWUgZnJvbSByZWdpc3RlcnMgKi8KICAgIHN3aXRjaCAoREVCVUdfR2V0U2VsZWN0b3JUeXBlKHNzKSkKICAgIHsKICAgIGNhc2UgMzI6CiAgICAgICAgZnJhbWVzWzBdLmNzID0gYWRkci5zZWcgPSBjczsKICAgICAgICBmcmFtZXNbMF0uZWlwID0gYWRkci5vZmYgPSBERUJVR19jb250ZXh0LkVpcDsKICAgICAgICBpZiAobm9pc3kpCiAgICAgICAgICAgIGZyYW1lc1swXS5mcmFtZSA9IERFQlVHX1ByaW50QWRkcmVzcyggJmFkZHIsIDMyLCBUUlVFICk7CiAgICAgICAgZWxzZQoJICAgIERFQlVHX0ZpbmROZWFyZXN0U3ltYm9sKCAmYWRkciwgVFJVRSwgJmZyYW1lc1swXS5mcmFtZS5zeW0sIDAsIAoJCQkJICAgICAmZnJhbWVzWzBdLmZyYW1lLmxpc3QpOwogICAgICAgIGZyYW1lc1swXS5zcyA9IGFkZHIuc2VnID0gc3M7CglmcmFtZXNbMF0uZWJwID0gYWRkci5vZmYgPSBERUJVR19jb250ZXh0LkVicDsKICAgICAgICBpZiAobm9pc3kpIGZwcmludGYoIHN0ZGVyciwgIiAoZWJwPSUwOHgpXG4iLCBmcmFtZXNbMF0uZWJwICk7CiAgICAgICAgaXMxNiA9IEZBTFNFOwoJYnJlYWs7CiAgICBjYXNlIDE2OgogICAgICAgIGZyYW1lc1swXS5jcyA9IGFkZHIuc2VnID0gY3M7CiAgICAgICAgZnJhbWVzWzBdLmVpcCA9IGFkZHIub2ZmID0gTE9XT1JEKERFQlVHX2NvbnRleHQuRWlwKTsKICAgICAgICBpZiAobm9pc3kpCgkgICAgZnJhbWVzWzBdLmZyYW1lID0gREVCVUdfUHJpbnRBZGRyZXNzKCAmYWRkciwgMTYsIFRSVUUgKTsKICAgICAgICBlbHNlCgkgICAgREVCVUdfRmluZE5lYXJlc3RTeW1ib2woICZhZGRyLCBUUlVFLCAmZnJhbWVzWzBdLmZyYW1lLnN5bSwgMCwgCgkJCQkgICAgICZmcmFtZXNbMF0uZnJhbWUubGlzdCk7CiAgICAgICAgZnJhbWVzWzBdLnNzID0gYWRkci5zZWcgPSBzczsKCWZyYW1lc1swXS5lYnAgPSBhZGRyLm9mZiA9IExPV09SRChERUJVR19jb250ZXh0LkVicCk7CiAgICAgICAgaWYgKG5vaXN5KSBmcHJpbnRmKCBzdGRlcnIsICIgKGJwPSUwNHgpXG4iLCBmcmFtZXNbMF0uZWJwICk7CiAgICAgICAgaXMxNiA9IFRSVUU7CglicmVhazsKICAgIGRlZmF1bHQ6CiAgICAgICAgaWYgKG5vaXN5KSBmcHJpbnRmKCBzdGRlcnIsICJCYWQgc2VnbWVudCAnJXUnXG4iLCBzcyk7CglyZXR1cm47CiAgICB9CgogICAgLyogY3VyX3N3aXRjaCBob2xkcyBhZGRyZXNzIG9mIGN1cnJfc3RhY2sncyBmaWVsZCBpbiBURUIgaW4gZGVidWdnZWUgCiAgICAgKiBhZGRyZXNzIHNwYWNlIAogICAgICovCiAgICBjdXJfc3dpdGNoID0gKERXT1JEKURFQlVHX0N1cnJUaHJlYWQtPnRlYiArIE9GRlNFVF9PRihURUIsIGN1cl9zdGFjayk7CiAgICBpZiAoIURFQlVHX1JFQURfTUVNKCh2b2lkKiljdXJfc3dpdGNoLCAmbmV4dF9zd2l0Y2gsIHNpemVvZihuZXh0X3N3aXRjaCkpKSB7CiAgICAgICAgaWYgKG5vaXN5KSBmcHJpbnRmKCBzdGRlcnIsICJDYW4ndCByZWFkIFRFQjpjdXJfc3RhY2tcbiIpOwoJcmV0dXJuOwogICAgfQoKICAgIGlmIChpczE2KSB7CiAgICAgICAgaWYgKCFERUJVR19SRUFEX01FTSgodm9pZCopbmV4dF9zd2l0Y2gsICZmcmFtZTMyLCBzaXplb2YoU1RBQ0szMkZSQU1FKSkpIHsKCSAgICBpZiAobm9pc3kpIGZwcmludGYoIHN0ZGVyciwgIkJhZCBzdGFjayBmcmFtZSAlcFxuIiwgCgkJCQkoU1RBQ0szMkZSQU1FKiluZXh0X3N3aXRjaCApOwoJICAgIHJldHVybjsKCX0KCWN1cl9zd2l0Y2ggPSAoRFdPUkQpZnJhbWUzMi5mcmFtZTE2OwoJc3dfYWRkci5zZWcgPSBTRUxFQ1RPUk9GKGN1cl9zd2l0Y2gpOwoJc3dfYWRkci5vZmYgPSBPRkZTRVRPRihjdXJfc3dpdGNoKTsKICAgIH0gZWxzZSB7CiAgICAgICAgdG1wLnNlZyA9IFNFTEVDVE9ST0YobmV4dF9zd2l0Y2gpOwoJdG1wLm9mZiA9IE9GRlNFVE9GKG5leHRfc3dpdGNoKTsKCXAgPSBERUJVR19Ub0xpbmVhcigmdG1wKTsKCQoJaWYgKCFERUJVR19SRUFEX01FTSgodm9pZCopcCwgJmZyYW1lMTYsIHNpemVvZihTVEFDSzE2RlJBTUUpKSkgewoJICAgIGlmIChub2lzeSkgZnByaW50Ziggc3RkZXJyLCAiQmFkIHN0YWNrIGZyYW1lICVwXG4iLCAoU1RBQ0sxNkZSQU1FKilwICk7CgkgICAgcmV0dXJuOwoJfQoJY3VyX3N3aXRjaCA9IChEV09SRClmcmFtZTE2LmZyYW1lMzI7Cglzd19hZGRyLnNlZyA9IHNzOwoJc3dfYWRkci5vZmYgPSBjdXJfc3dpdGNoOwogICAgfQogICAgaWYgKCFERUJVR19SRUFEX01FTSgodm9pZCopREVCVUdfVG9MaW5lYXIoJnN3X2FkZHIpLCAmY2gsIHNpemVvZihjaCkpKSB7CiAgICAgICAgc3dfYWRkci5zZWcgPSAoRFdPUkQpLTE7Cglzd19hZGRyLm9mZiA9IChEV09SRCktMTsKICAgIH0KICAgIAogICAgZm9yIChvayA9IFRSVUU7IG9rOykgewogICAgICAgIGlmICgoZnJhbWVzW2ZyYW1lbm9dLnNzID09IHN3X2FkZHIuc2VnKSAmJgoJICAgIChmcmFtZXNbZnJhbWVub10uZWJwID49IHN3X2FkZHIub2ZmKSkgewoJICAgLyogMTY8LT4zMiBzd2l0Y2guLi4KCSAgICAqIHllcywgSSBrbm93IHRoaXMgaXMgY29uZnVzaW5nLCBpdCBnYXZlIG1lIGEgaGVhZGFjaGUgdG9vICovCgkgICBpZiAoaXMxNikgewoJICAgICAgCgkgICAgICAgaWYgKCFERUJVR19SRUFEX01FTSgodm9pZCopbmV4dF9zd2l0Y2gsICZmcmFtZTMyLCBzaXplb2YoU1RBQ0szMkZSQU1FKSkpIHsKCQkgIGlmIChub2lzeSkgZnByaW50Ziggc3RkZXJyLCAiQmFkIHN0YWNrIGZyYW1lICVwXG4iLCAoU1RBQ0szMkZSQU1FKiluZXh0X3N3aXRjaCApOwoJCSAgcmV0dXJuOwoJICAgICAgIH0KCgkgICAgICAgY29kZS5zZWcgID0gMDsKCSAgICAgICBjb2RlLm9mZiAgPSBmcmFtZTMyLnJldGFkZHI7CgkgICAgICAgCgkgICAgICAgY3MgPSAwOwoJICAgICAgIGFkZHIuc2VnID0gMDsKCSAgICAgICBhZGRyLm9mZiA9IGZyYW1lMzIuZWJwOwoJICAgICAgIERFQlVHX0ZvcmNlRnJhbWUoICZhZGRyLCAmY29kZSwgKytmcmFtZW5vLCAzMiwgbm9pc3kgKTsKCSAgICAgICAKCSAgICAgICBuZXh0X3N3aXRjaCA9IGN1cl9zd2l0Y2g7CgkgICAgICAgdG1wLnNlZyA9IFNFTEVDVE9ST0YobmV4dF9zd2l0Y2gpOwoJICAgICAgIHRtcC5vZmYgPSBPRkZTRVRPRihuZXh0X3N3aXRjaCk7CgkgICAgICAgcCA9IERFQlVHX1RvTGluZWFyKCZ0bXApOwoJICAgICAgIAoJICAgICAgIGlmICghREVCVUdfUkVBRF9NRU0oKHZvaWQqKXAsICZmcmFtZTE2LCBzaXplb2YoU1RBQ0sxNkZSQU1FKSkpIHsKCQkgICBpZiAobm9pc3kpIGZwcmludGYoIHN0ZGVyciwgIkJhZCBzdGFjayBmcmFtZSAlcFxuIiwgCgkJCQkgICAgICAgKFNUQUNLMTZGUkFNRSopcCApOwoJCSAgIHJldHVybjsKCSAgICAgICB9CgkgICAgICAgY3VyX3N3aXRjaCA9IChEV09SRClmcmFtZTE2LmZyYW1lMzI7CgkgICAgICAgc3dfYWRkci5zZWcgPSAwOwoJICAgICAgIHN3X2FkZHIub2ZmID0gY3VyX3N3aXRjaDsKCSAgICAgICAKCSAgICAgICBpczE2ID0gRkFMU0U7CgkgICB9IGVsc2UgewoJICAgICAgdG1wLnNlZyA9IFNFTEVDVE9ST0YobmV4dF9zd2l0Y2gpOwoJICAgICAgdG1wLm9mZiA9IE9GRlNFVE9GKG5leHRfc3dpdGNoKTsKCSAgICAgIHAgPSBERUJVR19Ub0xpbmVhcigmdG1wKTsKCSAgICAgIAoJICAgICAgaWYgKCFERUJVR19SRUFEX01FTSgodm9pZCopcCwgJmZyYW1lMTYsIHNpemVvZihTVEFDSzE2RlJBTUUpKSkgewoJCSAgaWYgKG5vaXN5KSBmcHJpbnRmKCBzdGRlcnIsICJCYWQgc3RhY2sgZnJhbWUgJXBcbiIsCgkJCQkgICAgICAoU1RBQ0sxNkZSQU1FKilwICk7CgkJICByZXR1cm47CgkgICAgICB9CgkgICAgICAKCSAgICAgIGNvZGUuc2VnICA9IGZyYW1lMTYuY3M7CgkgICAgICBjb2RlLm9mZiAgPSBmcmFtZTE2LmlwOwoJICAgICAgCgkgICAgICBjcyA9IGZyYW1lMTYuY3M7CgkgICAgICBhZGRyLnNlZyA9IFNFTEVDVE9ST0YobmV4dF9zd2l0Y2gpOwoJICAgICAgYWRkci5vZmYgPSBmcmFtZTE2LmJwOwoJICAgICAgREVCVUdfRm9yY2VGcmFtZSggJmFkZHIsICZjb2RlLCArK2ZyYW1lbm8sIDE2LCBub2lzeSApOwoJICAgICAgCgkgICAgICBuZXh0X3N3aXRjaCA9IGN1cl9zd2l0Y2g7CgkgICAgICBpZiAoIURFQlVHX1JFQURfTUVNKCh2b2lkKiluZXh0X3N3aXRjaCwgJmZyYW1lMzIsIHNpemVvZihTVEFDSzMyRlJBTUUpKSkgewoJCSBpZiAobm9pc3kpIGZwcmludGYoIHN0ZGVyciwgIkJhZCBzdGFjayBmcmFtZSAlcFxuIiwgCgkJCQkgICAgIChTVEFDSzMyRlJBTUUqKW5leHRfc3dpdGNoICk7CgkJIHJldHVybjsKCSAgICAgIH0KCSAgICAgIGN1cl9zd2l0Y2ggPSAoRFdPUkQpZnJhbWUzMi5mcmFtZTE2OwoJICAgICAgc3dfYWRkci5zZWcgPSBTRUxFQ1RPUk9GKGN1cl9zd2l0Y2gpOwoJICAgICAgc3dfYWRkci5vZmYgPSBPRkZTRVRPRihjdXJfc3dpdGNoKTsKCSAgICAgIAoJICAgICAgaXMxNiA9IFRSVUU7CgkgICB9CgkgICBpZiAoIURFQlVHX1JFQURfTUVNKCh2b2lkKilERUJVR19Ub0xpbmVhcigmc3dfYWRkciksICZjaCwgc2l6ZW9mKGNoKSkpIHsKCSAgICAgIHN3X2FkZHIuc2VnID0gKERXT1JEKS0xOwoJICAgICAgc3dfYWRkci5vZmYgPSAoRFdPUkQpLTE7CgkgICB9Cgl9IGVsc2UgewoJICAgIC8qIG9yZGluYXJ5IHN0YWNrIGZyYW1lICovCgkgICBvayA9IGlzMTYgPyBERUJVR19GcmFtZTE2KCAmYWRkciwgJmNzLCArK2ZyYW1lbm8sIG5vaXN5KQoJICAgICAgOiBERUJVR19GcmFtZTMyKCAmYWRkciwgJmNzLCArK2ZyYW1lbm8sIG5vaXN5KTsKCX0KICAgIH0KICAgIGlmIChub2lzeSkgZnByaW50Ziggc3RkZXJyLCAiXG4iICk7CiNlbmRpZgp9CgppbnQKREVCVUdfU2V0RnJhbWUoaW50IG5ld2ZyYW1lKQp7CiAgaW50CQlydG4gPSBGQUxTRTsKCiAgY3Vycl9mcmFtZSA9IG5ld2ZyYW1lOwoKICBpZiggY3Vycl9mcmFtZSA+PSBuZnJhbWUgKQogICAgewogICAgICBjdXJyX2ZyYW1lID0gbmZyYW1lIC0gMTsKICAgIH0KCiAgaWYoIGN1cnJfZnJhbWUgPCAwICkKICAgIHsKICAgICAgY3Vycl9mcmFtZSA9IDA7CiAgICB9CgogICBpZiggZnJhbWVzICYmIGZyYW1lc1tjdXJyX2ZyYW1lXS5mcmFtZS5saXN0LnNvdXJjZWZpbGUgIT0gTlVMTCApCiAgICB7CiAgICAgIERFQlVHX0xpc3QoJmZyYW1lc1tjdXJyX2ZyYW1lXS5mcmFtZS5saXN0LCBOVUxMLCAwKTsKICAgIH0KCiAgcnRuID0gVFJVRTsKICByZXR1cm4gKHJ0bik7Cn0KCmludApERUJVR19HZXRDdXJyZW50RnJhbWUoc3RydWN0IG5hbWVfaGFzaCAqKiBuYW1lLCB1bnNpZ25lZCBpbnQgKiBlaXAsCgkJICAgICAgdW5zaWduZWQgaW50ICogZWJwKQp7CiAgLyoKICAgKiBJZiB3ZSBkb24ndCBoYXZlIGEgdmFsaWQgYmFja3RyYWNlLCB0aGVuIGp1c3QgcmV0dXJuLgogICAqLwogIGlmKCBmcmFtZXMgPT0gTlVMTCApCiAgICB7CiAgICAgIHJldHVybiBGQUxTRTsKICAgIH0KCiAgLyoKICAgKiBJZiB3ZSBkb24ndCBrbm93IHdoYXQgdGhlIGN1cnJlbnQgZnVuY3Rpb24gaXMsIHRoZW4gd2UgYWxzbyBoYXZlCiAgICogbm90aGluZyB0byByZXBvcnQgaGVyZS4KICAgKi8KICBpZiggZnJhbWVzW2N1cnJfZnJhbWVdLmZyYW1lLnN5bSA9PSBOVUxMICkKICAgIHsKICAgICAgcmV0dXJuIEZBTFNFOwogICAgfQoKICAqbmFtZSA9IGZyYW1lc1tjdXJyX2ZyYW1lXS5mcmFtZS5zeW07CiAgKmVpcCA9IGZyYW1lc1tjdXJyX2ZyYW1lXS5laXA7CiAgKmVicCA9IGZyYW1lc1tjdXJyX2ZyYW1lXS5lYnA7CgogIHJldHVybiBUUlVFOwp9Cgo=