Lyogdmk6IHNldCBzdz00IHRzPTQ6ICovCi8qCiAqICByZWFkcHJvZmlsZS5jIC0gdXNlZCB0byByZWFkIC9wcm9jL3Byb2ZpbGUKICoKICogIENvcHlyaWdodCAoQykgMTk5NCwxOTk2IEFsZXNzYW5kcm8gUnViaW5pIChydWJpbmlAaXB2dmlzLnVuaXB2Lml0KQogKgogKiBMaWNlbnNlZCB1bmRlciBHUEx2MiBvciBsYXRlciwgc2VlIGZpbGUgTElDRU5TRSBpbiB0aGlzIHRhcmJhbGwgZm9yIGRldGFpbHMuCiAqLwoKLyoKICogMTk5OS0wMi0yMiBBcmthZGl1c3ogTWm2a2lld2ljeiA8bWlzaWVrQHBsZC5PUkcuUEw+CiAqIC0gYWRkZWQgTmF0aXZlIExhbmd1YWdlIFN1cHBvcnQKICogMTk5OS0wOS0wMSBTdGVwaGFuZSBFcmFuaWFuIDxlcmFuaWFuQGNlbGxvLmhwbC5ocC5jb20+CiAqIC0gNjRiaXQgY2xlYW4gcGF0Y2gKICogM0ZlYjIwMDEgQW5kcmV3IE1vcnRvbiA8YW5kcmV3bUB1b3cuZWR1LmF1PgogKiAtIC1NIG9wdGlvbiB0byB3cml0ZSBwcm9maWxlIG11bHRpcGxpZXIuCiAqIDIwMDEtMTEtMDcgV2VybmVyIEFsbWVzYmVyZ2VyIDx3YUBhbG1lc2Jlcmdlci5uZXQ+CiAqIC0gYnl0ZSBvcmRlciBhdXRvLWRldGVjdGlvbiBhbmQgLW4gb3B0aW9uCiAqIDIwMDEtMTEtMDkgV2VybmVyIEFsbWVzYmVyZ2VyIDx3YUBhbG1lc2Jlcmdlci5uZXQ+CiAqIC0gc2tpcCBzdGVwIHNpemUgKGluZGV4IDApCiAqIDIwMDItMDMtMDkgSm9obiBMZXZvbiA8bW96QGNvbXBzb2MubWFuLmFjLnVrPgogKiAtIG1ha2UgbWFwbGluZW5vIGRvIHNvbWV0aGluZwogKiAyMDAyLTExLTI4IE1hZHMgTWFydGluIEpvZXJnZW5zZW4gKwogKiAtIGFsc28gdHJ5IC9ib290L1N5c3RlbS5tYXAtYHVuYW1lIC1yYAogKiAyMDAzLTA0LTA5IFdlcm5lciBBbG1lc2JlcmdlciA8d2FAYWxtZXNiZXJnZXIubmV0PgogKiAtIGZpeGVkIG9mZi1ieSBlaWdodCBlcnJvciBhbmQgaW1wcm92ZWQgaGV1cmlzdGljcyBpbiBieXRlIG9yZGVyIGRldGVjdGlvbgogKiAyMDAzLTA4LTEyIE5pa2l0YSBEYW5pbG92IDxOaWtpdGFATmFtZXN5cy5DT00+CiAqIC0gYWRkZWQgLXMgb3B0aW9uOyBleGFtcGxlIG9mIHVzZToKICogInJlYWRwcm9maWxlIC1zIC1tIC9ib290L1N5c3RlbS5tYXAtdGVzdCB8IGdyZXAgX19kX2xvb2t1cCB8IHNvcnQgLW4gLWszIgogKgogKiBUYWtlbiBmcm9tIHV0aWwtbGludXggYW5kIGFkYXB0ZWQgZm9yIGJ1c3lib3ggYnkKICogUGF1bCBNdW5kdCA8bGV0aGFsQGxpbnV4LXNoLm9yZz4uCiAqLwoKI2luY2x1ZGUgImxpYmJiLmgiCiNpbmNsdWRlIDxzeXMvdXRzbmFtZS5oPgoKI2RlZmluZSBTX0xFTiAxMjgKCi8qIFRoZXNlIGFyZSB0aGUgZGVmYXVsdHMgKi8Kc3RhdGljIGNvbnN0IGNoYXIgZGVmYXVsdG1hcFtdIEFMSUdOMSA9ICIvYm9vdC9TeXN0ZW0ubWFwIjsKc3RhdGljIGNvbnN0IGNoYXIgZGVmYXVsdHByb1tdIEFMSUdOMSA9ICIvcHJvYy9wcm9maWxlIjsKCmludCByZWFkcHJvZmlsZV9tYWluKGludCBhcmdjLCBjaGFyICoqYXJndikgTUFJTl9FWFRFUk5BTExZX1ZJU0lCTEU7CmludCByZWFkcHJvZmlsZV9tYWluKGludCBhcmdjLCBjaGFyICoqYXJndikKewoJRklMRSAqbWFwOwoJY29uc3QgY2hhciAqbWFwRmlsZSwgKnByb0ZpbGUsICptdWx0ID0gMDsKCXVuc2lnbmVkIGxvbmcgaW5keCA9IDE7CglzaXplX3QgbGVuOwoJdWludDY0X3QgYWRkMCA9IDA7Cgl1bnNpZ25lZCBpbnQgc3RlcDsKCXVuc2lnbmVkIGludCAqYnVmLCB0b3RhbCwgZm5fbGVuOwoJdW5zaWduZWQgbG9uZyBsb25nIGZuX2FkZCwgbmV4dF9hZGQ7ICAgICAvKiBjdXJyZW50IGFuZCBuZXh0IGFkZHJlc3MgKi8KCWNoYXIgZm5fbmFtZVtTX0xFTl0sIG5leHRfbmFtZVtTX0xFTl07ICAgLyogY3VycmVudCBhbmQgbmV4dCBuYW1lICovCgljaGFyIG1hcGxpbmVbU19MRU5dOwoJY2hhciBtb2RlWzhdOwoJaW50IG9wdEFsbCA9IDAsIG9wdEluZm8gPSAwLCBvcHRSZXNldCA9IDA7CglpbnQgb3B0VmVyYm9zZSA9IDAsIG9wdE5hdGl2ZSA9IDA7CglpbnQgb3B0QmlucyA9IDAsIG9wdFN1YiA9IDA7CglpbnQgbWFwbGluZW5vID0gMTsKCWludCBoZWFkZXJfcHJpbnRlZDsKCiNkZWZpbmUgbmV4dCAoY3VycmVudF4xKQoKCXByb0ZpbGUgPSBkZWZhdWx0cHJvOwoJbWFwRmlsZSA9IGRlZmF1bHRtYXA7CgoJb3B0X2NvbXBsZW1lbnRhcnkgPSAibm46YWE6YmI6c3M6aWk6cnI6dnYiOwoJZ2V0b3B0MzIoYXJndiwgIk06bTpwOm5hYnNpcnYiLAoJCQkmbXVsdCwgJm1hcEZpbGUsICZwcm9GaWxlLAoJCQkmb3B0TmF0aXZlLCAmb3B0QWxsLCAmb3B0QmlucywgJm9wdFN1YiwKCQkJJm9wdEluZm8sICZvcHRSZXNldCwgJm9wdFZlcmJvc2UpOwoKCWlmIChvcHRSZXNldCB8fCBtdWx0KSB7CgkJaW50IG11bHRpcGxpZXIsIGZkLCB0b193cml0ZTsKCgkJLyoKCQkgKiBXaGVuIHdyaXRpbmcgdGhlIG11bHRpcGxpZXIsIGlmIHRoZSBsZW5ndGggb2YgdGhlIHdyaXRlIGlzCgkJICogbm90IHNpemVvZihpbnQpLCB0aGUgbXVsdGlwbGllciBpcyBub3QgY2hhbmdlZAoJCSAqLwoJCWlmIChtdWx0KSB7CgkJCW11bHRpcGxpZXIgPSB4YXRvaV91KG11bHQpOwoJCQl0b193cml0ZSA9IHNpemVvZihpbnQpOwoJCX0gZWxzZSB7CgkJCW11bHRpcGxpZXIgPSAwOwoJCQl0b193cml0ZSA9IDE7CS8qIHN0aCBkaWZmZXJlbnQgZnJvbSBzaXplb2YoaW50KSAqLwoJCX0KCgkJZmQgPSB4b3BlbihkZWZhdWx0cHJvLCBPX1dST05MWSk7CgoJCWlmIChmdWxsX3dyaXRlKGZkLCAmbXVsdGlwbGllciwgdG9fd3JpdGUpICE9IHRvX3dyaXRlKQoJCQliYl9wZXJyb3JfbXNnX2FuZF9kaWUoImVycm9yIHdyaXRpbmcgJXMiLCBkZWZhdWx0cHJvKTsKCgkJY2xvc2UoZmQpOwoJCXJldHVybiBFWElUX1NVQ0NFU1M7Cgl9CgoJLyoKCSAqIFVzZSBhbiBmZCBmb3IgdGhlIHByb2ZpbGluZyBidWZmZXIsIHRvIHNraXAgc3RkaW8gb3ZlcmhlYWQKCSAqLwoJbGVuID0gTUFYSU5UKHNzaXplX3QpOwoJYnVmID0geG1hbGxvY19vcGVuX3JlYWRfY2xvc2UocHJvRmlsZSwgJmxlbik7CglpZiAoIW9wdE5hdGl2ZSkgewoJCWludCBlbnRyaWVzID0gbGVuL3NpemVvZigqYnVmKTsKCQlpbnQgYmlnID0gMCwgc21hbGwgPSAwLCBpOwoJCXVuc2lnbmVkICpwOwoKCQlmb3IgKHAgPSBidWYrMTsgcCA8IGJ1ZitlbnRyaWVzOyBwKyspIHsKCQkJaWYgKCpwICYgfjBVIDw8IChzaXplb2YoKmJ1ZikqNCkpCgkJCQliaWcrKzsKCQkJaWYgKCpwICYgKCgxIDw8IChzaXplb2YoKmJ1ZikqNCkpLTEpKQoJCQkJc21hbGwrKzsKCQl9CgkJaWYgKGJpZyA+IHNtYWxsKSB7CgkJCWJiX2Vycm9yX21zZygiYXNzdW1pbmcgcmV2ZXJzZWQgYnl0ZSBvcmRlciwgIgoJCQkJInVzZSAtbiB0byBmb3JjZSBuYXRpdmUgYnl0ZSBvcmRlciIpOwoJCQlmb3IgKHAgPSBidWY7IHAgPCBidWYrZW50cmllczsgcCsrKQoJCQkJZm9yIChpID0gMDsgaSA8IHNpemVvZigqYnVmKS8yOyBpKyspIHsKCQkJCQl1bnNpZ25lZCBjaGFyICpiID0gKHVuc2lnbmVkIGNoYXIgKikgcDsKCQkJCQl1bnNpZ25lZCBjaGFyIHRtcDsKCgkJCQkJdG1wID0gYltpXTsKCQkJCQliW2ldID0gYltzaXplb2YoKmJ1ZiktaS0xXTsKCQkJCQliW3NpemVvZigqYnVmKS1pLTFdID0gdG1wOwoJCQkJfQoJCX0KCX0KCglzdGVwID0gYnVmWzBdOwoJaWYgKG9wdEluZm8pIHsKCQlwcmludGYoIlNhbXBsaW5nX3N0ZXA6ICVpXG4iLCBzdGVwKTsKCQlyZXR1cm4gRVhJVF9TVUNDRVNTOwoJfQoKCXRvdGFsID0gMDsKCgltYXAgPSB4Zm9wZW4obWFwRmlsZSwgInIiKTsKCgl3aGlsZSAoZmdldHMobWFwbGluZSwgU19MRU4sIG1hcCkpIHsKCQlpZiAoc3NjYW5mKG1hcGxpbmUsICIlbGx4ICVzICVzIiwgJmZuX2FkZCwgbW9kZSwgZm5fbmFtZSkgIT0gMykKCQkJYmJfZXJyb3JfbXNnX2FuZF9kaWUoIiVzKCVpKTogd3JvbmcgbWFwIGxpbmUiLAoJCQkJCSAgICAgbWFwRmlsZSwgbWFwbGluZW5vKTsKCgkJaWYgKCFzdHJjbXAoZm5fbmFtZSwgIl9zdGV4dCIpKSAvKiBvbmx5IGVsZiB3b3JrcyBsaWtlIHRoaXMgKi8gewoJCQlhZGQwID0gZm5fYWRkOwoJCQlicmVhazsKCQl9CgkJbWFwbGluZW5vKys7Cgl9CgoJaWYgKCFhZGQwKQoJCWJiX2Vycm9yX21zZ19hbmRfZGllKCJjYW4ndCBmaW5kIFwiX3N0ZXh0XCIgaW4gJXMiLCBtYXBGaWxlKTsKCgkvKgoJICogTWFpbiBsb29wLgoJICovCgl3aGlsZSAoZmdldHMobWFwbGluZSwgU19MRU4sIG1hcCkpIHsKCQl1bnNpZ25lZCBpbnQgdGhpcyA9IDA7CgoJCWlmIChzc2NhbmYobWFwbGluZSwgIiVsbHggJXMgJXMiLCAmbmV4dF9hZGQsIG1vZGUsIG5leHRfbmFtZSkgIT0gMykKCQkJYmJfZXJyb3JfbXNnX2FuZF9kaWUoIiVzKCVpKTogd3JvbmcgbWFwIGxpbmUiLAoJCQkJCW1hcEZpbGUsIG1hcGxpbmVubyk7CgoJCWhlYWRlcl9wcmludGVkID0gMDsKCgkJLyogaWdub3JlIGFueSBMRUFESU5HIChiZWZvcmUgYSAnW3RUXScgc3ltYm9sIGlzIGZvdW5kKQoJCSAgIEFic29sdXRlIHN5bWJvbHMgKi8KCQlpZiAoKCptb2RlID09ICdBJyB8fCAqbW9kZSA9PSAnPycpICYmIHRvdGFsID09IDApIGNvbnRpbnVlOwoJCWlmICgqbW9kZSAhPSAnVCcgJiYgKm1vZGUgIT0gJ3QnICYmCgkJICAgICptb2RlICE9ICdXJyAmJiAqbW9kZSAhPSAndycpCgkJCWJyZWFrOwkvKiBvbmx5IHRleHQgaXMgcHJvZmlsZWQgKi8KCgkJaWYgKGluZHggPj0gbGVuIC8gc2l6ZW9mKCpidWYpKQoJCQliYl9lcnJvcl9tc2dfYW5kX2RpZSgicHJvZmlsZSBhZGRyZXNzIG91dCBvZiByYW5nZS4gIgoJCQkJCSAgICAgIldyb25nIG1hcCBmaWxlPyIpOwoKCQl3aGlsZSAoaW5keCA8IChuZXh0X2FkZC1hZGQwKS9zdGVwKSB7CgkJCWlmIChvcHRCaW5zICYmIChidWZbaW5keF0gfHwgb3B0QWxsKSkgewoJCQkJaWYgKCFoZWFkZXJfcHJpbnRlZCkgewoJCQkJCXByaW50ZigiJXM6XG4iLCBmbl9uYW1lKTsKCQkJCQloZWFkZXJfcHJpbnRlZCA9IDE7CgkJCQl9CgkJCQlwcmludGYoIlx0JSJQUkl4NjQiXHQldVxuIiwgKGluZHggLSAxKSpzdGVwICsgYWRkMCwgYnVmW2luZHhdKTsKCQkJfQoJCQl0aGlzICs9IGJ1ZltpbmR4KytdOwoJCX0KCQl0b3RhbCArPSB0aGlzOwoKCQlpZiAob3B0QmlucykgewoJCQlpZiAob3B0VmVyYm9zZSB8fCB0aGlzID4gMCkKCQkJCXByaW50ZigiICB0b3RhbFx0XHRcdFx0JXVcbiIsIHRoaXMpOwoJCX0gZWxzZSBpZiAoKHRoaXMgfHwgb3B0QWxsKSAmJgoJCQkgICAoZm5fbGVuID0gbmV4dF9hZGQtZm5fYWRkKSAhPSAwKSB7CgkJCWlmIChvcHRWZXJib3NlKQoJCQkJcHJpbnRmKCIlMDE2bGx4ICUtNDBzICU2aSAlOC40ZlxuIiwgZm5fYWRkLAoJCQkJICAgICAgIGZuX25hbWUsIHRoaXMsIHRoaXMvKGRvdWJsZSlmbl9sZW4pOwoJCQllbHNlCgkJCQlwcmludGYoIiU2aSAlLTQwcyAlOC40ZlxuIiwKCQkJCSAgICAgICB0aGlzLCBmbl9uYW1lLCB0aGlzLyhkb3VibGUpZm5fbGVuKTsKCQkJaWYgKG9wdFN1YikgewoJCQkJdW5zaWduZWQgbG9uZyBsb25nIHNjYW47CgoJCQkJZm9yIChzY2FuID0gKGZuX2FkZC1hZGQwKS9zdGVwICsgMTsKCQkJCSAgICAgc2NhbiA8IChuZXh0X2FkZC1hZGQwKS9zdGVwOyBzY2FuKyspIHsKCQkJCQl1bnNpZ25lZCBsb25nIGxvbmcgYWRkcjsKCgkJCQkJYWRkciA9IChzY2FuIC0gMSkqc3RlcCArIGFkZDA7CgkJCQkJcHJpbnRmKCJcdCUjbGx4XHQlcyslI2xseFx0JXVcbiIsCgkJCQkJICAgICAgIGFkZHIsIGZuX25hbWUsIGFkZHIgLSBmbl9hZGQsCgkJCQkJICAgICAgIGJ1ZltzY2FuXSk7CgkJCQl9CgkJCX0KCQl9CgoJCWZuX2FkZCA9IG5leHRfYWRkOwoJCXN0cmNweShmbl9uYW1lLCBuZXh0X25hbWUpOwoKCQltYXBsaW5lbm8rKzsKCX0KCgkvKiBjbG9jayB0aWNrcywgb3V0IG9mIGtlcm5lbCB0ZXh0IC0gcHJvYmFibHkgbW9kdWxlcyAqLwoJcHJpbnRmKCIlNmkgJXNcbiIsIGJ1ZltsZW4vc2l6ZW9mKCpidWYpLTFdLCAiKnVua25vd24qIik7CgoJLyogdHJhaWxlciAqLwoJaWYgKG9wdFZlcmJvc2UpCgkJcHJpbnRmKCIlMDE2eCAlLTQwcyAlNmkgJTguNGZcbiIsCgkJICAgICAgIDAsICJ0b3RhbCIsIHRvdGFsLCB0b3RhbC8oZG91YmxlKShmbl9hZGQtYWRkMCkpOwoJZWxzZQoJCXByaW50ZigiJTZpICUtNDBzICU4LjRmXG4iLAoJCSAgICAgICB0b3RhbCwgInRvdGFsIiwgdG90YWwvKGRvdWJsZSkoZm5fYWRkLWFkZDApKTsKCglmY2xvc2UobWFwKTsKCWZyZWUoYnVmKTsKCglyZXR1cm4gRVhJVF9TVUNDRVNTOwp9Cg==