Lyogdmk6IHNldCBzdz00IHRzPTQ6ICovCi8qCiAqIE1pbmkgbW91bnQgaW1wbGVtZW50YXRpb24gZm9yIGJ1c3lib3gKICoKICogQ29weXJpZ2h0IChDKSAxOTk1LCAxOTk2IGJ5IEJydWNlIFBlcmVucyA8YnJ1Y2VAcGl4YXIuY29tPi4KICogQ29weXJpZ2h0IChDKSAxOTk5LTIwMDQgYnkgRXJpayBBbmRlcnNlbiA8YW5kZXJzZW5AY29kZXBvZXQub3JnPgogKiBDb3B5cmlnaHQgKEMpIDIwMDUtMjAwNiBieSBSb2IgTGFuZGxleSA8cm9iQGxhbmRsZXkubmV0PgogKgogKiBMaWNlbnNlZCB1bmRlciBHUEx2MiBvciBsYXRlciwgc2VlIGZpbGUgTElDRU5TRSBpbiB0aGlzIHRhcmJhbGwgZm9yIGRldGFpbHMuCiAqLwoKLyogRGVzaWduIG5vdGVzOiBUaGVyZSBpcyBubyBzcGVjIGZvciBtb3VudC4gIFJlbWluZCBtZSB0byB3cml0ZSBvbmUuCgogICBtb3VudF9tYWluKCkgY2FsbHMgc2luZ2xlbW91bnQoKSB3aGljaCBjYWxscyBtb3VudF9pdF9ub3coKS4KCiAgIG1vdW50X21haW4oKSBjYW4gbG9vcCB0aHJvdWdoIC9ldGMvZnN0YWIgZm9yIG1vdW50IC1hCiAgIHNpbmdsZW1vdW50KCkgY2FuIGxvb3AgdGhyb3VnaCAvZXRjL2ZpbGVzeXN0ZW1zIGZvciBmc3R5cGUgZGV0ZWN0aW9uLgogICBtb3VudF9pdF9ub3coKSBkb2VzIHRoZSBhY3R1YWwgbW91bnQuCiovCgojaW5jbHVkZSAiYnVzeWJveC5oIgojaW5jbHVkZSA8bW50ZW50Lmg+CgovKiBOZWVkZWQgZm9yIG5mcyBzdXBwb3J0IG9ubHkuLi4gKi8KI2luY2x1ZGUgPHN5c2xvZy5oPgojaW5jbHVkZSA8c3lzL3V0c25hbWUuaD4KI3VuZGVmIFRSVUUKI3VuZGVmIEZBTFNFCiNpbmNsdWRlIDxycGMvcnBjLmg+CiNpbmNsdWRlIDxycGMvcG1hcF9wcm90Lmg+CiNpbmNsdWRlIDxycGMvcG1hcF9jbG50Lmg+CgoKI2lmIGRlZmluZWQoX19kaWV0bGliY19fKQovKiAxNi4xMi4yMDA2LCBTYW1wbyBLZWxsb21ha2kgKHNhbXBvQGlraS5maSkKICogZGlldGxpYmMtMC4zMCBkb2VzIG5vdCBoYXZlIGltcGxlbWVudGF0aW9uIG9mIGdldG1udGVudF9yKCkgKi8KLyogT1RPSDogd2h5IHdlIHVzZSBnZXRtbnRlbnRfciBpbnN0ZWFkIG9mIGdldG1udGVudD8gVE9ETy4uLiAqLwpzdHJ1Y3QgbW50ZW50ICpnZXRtbnRlbnRfcihGSUxFKiBzdHJlYW0sIHN0cnVjdCBtbnRlbnQqIHJlc3VsdCwgY2hhciogYnVmZmVyLCBpbnQgYnVmc2l6ZSkKewoJLyogKioqIFhYWCBGSVhNRSBXQVJOSU5HOiBUaGlzIGhhY2sgaXMgTk9UIHRocmVhZCBzYWZlLiAtLVNhbXBvICovCglzdHJ1Y3QgbW50ZW50KiBtZW50ID0gZ2V0bW50ZW50KHN0cmVhbSk7CgltZW1jcHkocmVzdWx0LCBtZW50LCBzaXplb2Yoc3RydWN0IG1udGVudCkpOwoJcmV0dXJuIHJlc3VsdDsKfQojZW5kaWYKCgovLyBOb3QgcmVhbCBmbGFncywgYnV0IHdlIHdhbnQgdG8gYmUgYWJsZSB0byBjaGVjayBmb3IgdGhpcy4KZW51bSB7CglNT1VOVF9VU0VSUyAgPSAoMTw8MjgpKkVOQUJMRV9ERVNLVE9QLAoJTU9VTlRfTk9BVVRPID0gKDE8PDI5KSwKCU1PVU5UX1NXQVAgICA9ICgxPDwzMCksCn07Ci8vIFRPRE86IG1vcmUgInVzZXIiIGZsYWcgY29tcGF0aWJpbGl0eS4KLy8gInVzZXIiIG9wdGlvbiAoZnJvbSBtb3VudCBtYW5wYWdlKToKLy8gT25seSB0aGUgdXNlciB0aGF0IG1vdW50ZWQgYSBmaWxlc3lzdGVtIGNhbiB1bm1vdW50IGl0IGFnYWluLgovLyBJZiBhbnkgdXNlciBzaG91bGQgYmUgYWJsZSB0byB1bm1vdW50LCB0aGVuIHVzZSB1c2VycyBpbnN0ZWFkIG9mIHVzZXIKLy8gaW4gdGhlIGZzdGFiIGxpbmUuICBUaGUgb3duZXIgb3B0aW9uIGlzIHNpbWlsYXIgdG8gdGhlIHVzZXIgb3B0aW9uLAovLyB3aXRoIHRoZSByZXN0cmljdGlvbiB0aGF0IHRoZSB1c2VyIG11c3QgYmUgdGhlIG93bmVyIG9mIHRoZSBzcGVjaWFsIGZpbGUuCi8vIFRoaXMgbWF5IGJlIHVzZWZ1bCBlLmcuIGZvciAvZGV2L2ZkIGlmIGEgbG9naW4gc2NyaXB0IG1ha2VzCi8vIHRoZSBjb25zb2xlIHVzZXIgb3duZXIgb2YgdGhpcyBkZXZpY2UuCgovKiBTdGFuZGFyZCBtb3VudCBvcHRpb25zIChmcm9tIC1vIG9wdGlvbnMgb3IgLS1vcHRpb25zKSwgd2l0aCBjb3JyZXNwb25kaW5nCiAqIGZsYWdzICovCgpzdHJ1Y3QgewoJY29uc3QgY2hhciAqbmFtZTsKCWxvbmcgZmxhZ3M7Cn0gc3RhdGljIG1vdW50X29wdGlvbnNbXSA9IHsKCS8vIE1TX0ZMQUdTIHNldCBhIGJpdC4gIH5NU19GTEFHUyBkaXNhYmxlIHRoYXQgYml0LiAgMCBmbGFncyBhcmUgTk9Qcy4KCglVU0VfRkVBVFVSRV9NT1VOVF9MT09QKAoJCXsibG9vcCIsIDB9LAoJKQoKCVVTRV9GRUFUVVJFX01PVU5UX0ZTVEFCKAoJCXsiZGVmYXVsdHMiLCAwfSwKCQkvKiB7InF1aWV0IiwgMH0sIC0gZG8gbm90IGZpbHRlciBvdXQsIHZmYXQgd2FudHMgdG8gc2VlIGl0ICovCgkJeyJub2F1dG8iLCBNT1VOVF9OT0FVVE99LAoJCXsic3ciLCBNT1VOVF9TV0FQfSwKCQl7InN3YXAiLCBNT1VOVF9TV0FQfSwKCQlVU0VfREVTS1RPUCh7InVzZXIiLCAgTU9VTlRfVVNFUlN9LCkKCQlVU0VfREVTS1RPUCh7InVzZXJzIiwgTU9VTlRfVVNFUlN9LCkKCSkKCglVU0VfRkVBVFVSRV9NT1VOVF9GTEFHUygKCQkvLyB2ZnMgZmxhZ3MKCQl7Im5vc3VpZCIsIE1TX05PU1VJRH0sCgkJeyJzdWlkIiwgfk1TX05PU1VJRH0sCgkJeyJkZXYiLCB+TVNfTk9ERVZ9LAoJCXsibm9kZXYiLCBNU19OT0RFVn0sCgkJeyJleGVjIiwgfk1TX05PRVhFQ30sCgkJeyJub2V4ZWMiLCBNU19OT0VYRUN9LAoJCXsic3luYyIsIE1TX1NZTkNIUk9OT1VTfSwKCQl7ImFzeW5jIiwgfk1TX1NZTkNIUk9OT1VTfSwKCQl7ImF0aW1lIiwgfk1TX05PQVRJTUV9LAoJCXsibm9hdGltZSIsIE1TX05PQVRJTUV9LAoJCXsiZGlyYXRpbWUiLCB+TVNfTk9ESVJBVElNRX0sCgkJeyJub2RpcmF0aW1lIiwgTVNfTk9ESVJBVElNRX0sCgkJeyJsb3VkIiwgfk1TX1NJTEVOVH0sCgoJCS8vIGFjdGlvbiBmbGFncwoKCQl7ImJpbmQiLCBNU19CSU5EfSwKCQl7Im1vdmUiLCBNU19NT1ZFfSwKCQl7InNoYXJlZCIsIE1TX1NIQVJFRH0sCgkJeyJzbGF2ZSIsIE1TX1NMQVZFfSwKCQl7InByaXZhdGUiLCBNU19QUklWQVRFfSwKCQl7InVuYmluZGFibGUiLCBNU19VTkJJTkRBQkxFfSwKCQl7InJzaGFyZWQiLCBNU19TSEFSRUR8TVNfUkVDVVJTSVZFfSwKCQl7InJzbGF2ZSIsIE1TX1NMQVZFfE1TX1JFQ1VSU0lWRX0sCgkJeyJycHJpdmF0ZSIsIE1TX1NMQVZFfE1TX1JFQ1VSU0lWRX0sCgkJeyJydW5iaW5kYWJsZSIsIE1TX1VOQklOREFCTEV8TVNfUkVDVVJTSVZFfSwKCSkKCgkvLyBBbHdheXMgdW5kZXJzdG9vZC4KCgl7InJvIiwgTVNfUkRPTkxZfSwgICAgICAgIC8vIHZmcyBmbGFnCgl7InJ3Iiwgfk1TX1JET05MWX0sICAgICAgIC8vIHZmcyBmbGFnCgl7InJlbW91bnQiLCBNU19SRU1PVU5UfSwgIC8vIGFjdGlvbiBmbGFnCn07CgojZGVmaW5lIFZFQ1RPUl9TSVpFKHYpIChzaXplb2YodikgLyBzaXplb2YoKHYpWzBdKSkKCi8qIEFwcGVuZCBtb3VudCBvcHRpb25zIHRvIHN0cmluZyAqLwpzdGF0aWMgdm9pZCBhcHBlbmRfbW91bnRfb3B0aW9ucyhjaGFyICoqb2xkb3B0cywgY29uc3QgY2hhciAqbmV3b3B0cykKewoJaWYgKCpvbGRvcHRzICYmICoqb2xkb3B0cykgewoJCS8qIGRvIG5vdCBpbnNlcnQgb3B0aW9ucyB3aGljaCBhcmUgYWxyZWFkeSB0aGVyZSAqLwoJCXdoaWxlIChuZXdvcHRzWzBdKSB7CgkJCWNoYXIgKnA7CgkJCWludCBsZW4gPSBzdHJsZW4obmV3b3B0cyk7CgkJCXAgPSBzdHJjaHIobmV3b3B0cywgJywnKTsKCQkJaWYgKHApIGxlbiA9IHAgLSBuZXdvcHRzOwoJCQlwID0gKm9sZG9wdHM7CgkJCXdoaWxlICgxKSB7CgkJCQlpZiAoIXN0cm5jbXAocCwgbmV3b3B0cywgbGVuKQoJCQkJICYmIChwW2xlbl09PScsJyB8fCBwW2xlbl09PTApKQoJCQkJCWdvdG8gc2tpcDsKCQkJCXAgPSBzdHJjaHIocCwnLCcpOwoJCQkJaWYgKCFwKSBicmVhazsKCQkJCXArKzsKCQkJfQoJCQlwID0geGFzcHJpbnRmKCIlcywlLipzIiwgKm9sZG9wdHMsIGxlbiwgbmV3b3B0cyk7CgkJCWZyZWUoKm9sZG9wdHMpOwoJCQkqb2xkb3B0cyA9IHA7CnNraXA6CgkJCW5ld29wdHMgKz0gbGVuOwoJCQl3aGlsZSAobmV3b3B0c1swXSA9PSAnLCcpIG5ld29wdHMrKzsKCQl9Cgl9IGVsc2UgewoJCWlmIChFTkFCTEVfRkVBVFVSRV9DTEVBTl9VUCkgZnJlZSgqb2xkb3B0cyk7CgkJKm9sZG9wdHMgPSB4c3RyZHVwKG5ld29wdHMpOwoJfQp9CgovKiBVc2UgdGhlIG1vdW50X29wdGlvbnMgbGlzdCB0byBwYXJzZSBvcHRpb25zIGludG8gZmxhZ3MuCiAqIEFsc28gcmV0dXJuIGxpc3Qgb2YgdW5yZWNvZ25pemVkIG9wdGlvbnMgaWYgdW5yZWNvZ25pemVkIT1OVUxMICovCnN0YXRpYyBpbnQgcGFyc2VfbW91bnRfb3B0aW9ucyhjaGFyICpvcHRpb25zLCBjaGFyICoqdW5yZWNvZ25pemVkKQp7CglpbnQgZmxhZ3MgPSBNU19TSUxFTlQ7CgoJLy8gTG9vcCB0aHJvdWdoIG9wdGlvbnMKCWZvciAoOzspIHsKCQlpbnQgaTsKCQljaGFyICpjb21tYSA9IHN0cmNocihvcHRpb25zLCAnLCcpOwoKCQlpZiAoY29tbWEpICpjb21tYSA9IDA7CgoJCS8vIEZpbmQgdGhpcyBvcHRpb24gaW4gbW91bnRfb3B0aW9ucwoJCWZvciAoaSA9IDA7IGkgPCBWRUNUT1JfU0laRShtb3VudF9vcHRpb25zKTsgaSsrKSB7CgkJCWlmICghc3RyY2FzZWNtcChtb3VudF9vcHRpb25zW2ldLm5hbWUsIG9wdGlvbnMpKSB7CgkJCQlsb25nIGZsID0gbW91bnRfb3B0aW9uc1tpXS5mbGFnczsKCQkJCWlmIChmbCA8IDApIGZsYWdzICY9IGZsOwoJCQkJZWxzZSBmbGFncyB8PSBmbDsKCQkJCWJyZWFrOwoJCQl9CgkJfQoJCS8vIElmIHVucmVjb2duaXplZCBub3QgTlVMTCwgYXBwZW5kIHVucmVjb2duaXplZCBtb3VudCBvcHRpb25zICovCgkJaWYgKHVucmVjb2duaXplZCAmJiBpID09IFZFQ1RPUl9TSVpFKG1vdW50X29wdGlvbnMpKSB7CgkJCS8vIEFkZCBpdCB0byBzdHJmbGFncywgdG8gcGFzcyBvbiB0byBrZXJuZWwKCQkJaSA9ICp1bnJlY29nbml6ZWQgPyBzdHJsZW4oKnVucmVjb2duaXplZCkgOiAwOwoJCQkqdW5yZWNvZ25pemVkID0geHJlYWxsb2MoKnVucmVjb2duaXplZCwgaStzdHJsZW4ob3B0aW9ucykrMik7CgoJCQkvLyBDb21tYSBzZXBhcmF0ZWQgaWYgaXQncyBub3QgdGhlIGZpcnN0IG9uZQoJCQlpZiAoaSkgKCp1bnJlY29nbml6ZWQpW2krK10gPSAnLCc7CgkJCXN0cmNweSgoKnVucmVjb2duaXplZCkraSwgb3B0aW9ucyk7CgkJfQoKCQkvLyBBZHZhbmNlIHRvIG5leHQgb3B0aW9uLCBvciBmaW5pc2gKCQlpZiAoY29tbWEpIHsKCQkJKmNvbW1hID0gJywnOwoJCQlvcHRpb25zID0gKytjb21tYTsKCQl9IGVsc2UgYnJlYWs7Cgl9CgoJcmV0dXJuIGZsYWdzOwp9CgovLyBSZXR1cm4gYSBsaXN0IG9mIGFsbCBibG9jayBkZXZpY2UgYmFja2VkIGZpbGVzeXN0ZW1zCgpzdGF0aWMgbGxpc3RfdCAqZ2V0X2Jsb2NrX2JhY2tlZF9maWxlc3lzdGVtcyh2b2lkKQp7CglzdGF0aWMgY29uc3QgY2hhciAqY29uc3QgZmlsZXN5c3RlbXNbXSA9IHsKCQkiL2V0Yy9maWxlc3lzdGVtcyIsCgkJIi9wcm9jL2ZpbGVzeXN0ZW1zIiwKCQkwCgl9OwoJY2hhciAqZnMsICpidWY7CglsbGlzdF90ICpsaXN0ID0gMDsKCWludCBpOwoJRklMRSAqZjsKCglmb3IgKGkgPSAwOyBmaWxlc3lzdGVtc1tpXTsgaSsrKSB7CgkJZiA9IGZvcGVuKGZpbGVzeXN0ZW1zW2ldLCAiciIpOwoJCWlmICghZikgY29udGludWU7CgoJCXdoaWxlICgoYnVmID0geG1hbGxvY19nZXRsaW5lKGYpKSAhPSAwKSB7CgkJCWlmICghc3RybmNtcChidWYsICJub2RldiIsIDUpICYmIGlzc3BhY2UoYnVmWzVdKSkKCQkJCWNvbnRpbnVlOwoJCQlmcyA9IHNraXBfd2hpdGVzcGFjZShidWYpOwoJCQlpZiAoKmZzPT0nIycgfHwgKmZzPT0nKicgfHwgISpmcykgY29udGludWU7CgoJCQlsbGlzdF9hZGRfdG9fZW5kKCZsaXN0LCB4c3RyZHVwKGZzKSk7CgkJCWZyZWUoYnVmKTsKCQl9CgkJaWYgKEVOQUJMRV9GRUFUVVJFX0NMRUFOX1VQKSBmY2xvc2UoZik7Cgl9CgoJcmV0dXJuIGxpc3Q7Cn0KCmxsaXN0X3QgKmZzbGlzdCA9IDA7CgojaWYgRU5BQkxFX0ZFQVRVUkVfQ0xFQU5fVVAKc3RhdGljIHZvaWQgZGVsZXRlX2Jsb2NrX2JhY2tlZF9maWxlc3lzdGVtcyh2b2lkKQp7CglsbGlzdF9mcmVlKGZzbGlzdCwgZnJlZSk7Cn0KI2Vsc2UKdm9pZCBkZWxldGVfYmxvY2tfYmFja2VkX2ZpbGVzeXN0ZW1zKHZvaWQpOwojZW5kaWYKCiNpZiBFTkFCTEVfRkVBVFVSRV9NVEFCX1NVUFBPUlQKc3RhdGljIGludCB1c2VNdGFiID0gMTsKc3RhdGljIGludCBmYWtlSXQ7CiNlbHNlCiNkZWZpbmUgdXNlTXRhYiAwCiNkZWZpbmUgZmFrZUl0IDAKI2VuZGlmCgovLyBQZXJmb3JtIGFjdHVhbCBtb3VudCBvZiBzcGVjaWZpYyBmaWxlc3lzdGVtIGF0IHNwZWNpZmljIGxvY2F0aW9uLgovLyBOQjogbXAtPnh4eCBmaWVsZHMgbWF5IGJlIHRyYXNoZWQgb24gZXhpdApzdGF0aWMgaW50IG1vdW50X2l0X25vdyhzdHJ1Y3QgbW50ZW50ICptcCwgaW50IHZmc2ZsYWdzLCBjaGFyICpmaWx0ZXJvcHRzKQp7CglpbnQgcmMgPSAwOwoKCWlmIChmYWtlSXQpIGdvdG8gbXRhYjsKCgkvLyBNb3VudCwgd2l0aCBmYWxsYmFjayB0byByZWFkLW9ubHkgaWYgbmVjZXNzYXJ5LgoKCWZvciAoOzspIHsKCQlyYyA9IG1vdW50KG1wLT5tbnRfZnNuYW1lLCBtcC0+bW50X2RpciwgbXAtPm1udF90eXBlLAoJCQkJdmZzZmxhZ3MsIGZpbHRlcm9wdHMpOwoJCWlmICghcmMgfHwgKHZmc2ZsYWdzJk1TX1JET05MWSkgfHwgKGVycm5vIT1FQUNDRVMgJiYgZXJybm8hPUVST0ZTKSkKCQkJYnJlYWs7CgkJYmJfZXJyb3JfbXNnKCIlcyBpcyB3cml0ZS1wcm90ZWN0ZWQsIG1vdW50aW5nIHJlYWQtb25seSIsCgkJCQltcC0+bW50X2ZzbmFtZSk7CgkJdmZzZmxhZ3MgfD0gTVNfUkRPTkxZOwoJfQoKCS8vIEFib3J0IGVudGlyZWx5IGlmIHBlcm1pc3Npb24gZGVuaWVkLgoKCWlmIChyYyAmJiBlcnJubyA9PSBFUEVSTSkKCQliYl9lcnJvcl9tc2dfYW5kX2RpZShiYl9tc2dfcGVybV9kZW5pZWRfYXJlX3lvdV9yb290KTsKCgkvKiBJZiB0aGUgbW91bnQgd2FzIHN1Y2Nlc3NmdWwsIGFuZCB3ZSdyZSBtYWludGFpbmluZyBhbiBvbGQtc3R5bGUKCSAqIG10YWIgZmlsZSBieSBoYW5kLCBhZGQgdGhlIG5ldyBlbnRyeSB0byBpdCBub3cuICovCiBtdGFiOgoJaWYgKEVOQUJMRV9GRUFUVVJFX01UQUJfU1VQUE9SVCAmJiB1c2VNdGFiICYmICFyYyAmJiAhKHZmc2ZsYWdzICYgTVNfUkVNT1VOVCkpIHsKCQljaGFyICpmc25hbWU7CgkJRklMRSAqbW91bnRUYWJsZSA9IHNldG1udGVudChiYl9wYXRoX210YWJfZmlsZSwgImErIik7CgkJaW50IGk7CgoJCWlmICghbW91bnRUYWJsZSkgewoJCQliYl9lcnJvcl9tc2coIm5vICVzIixiYl9wYXRoX210YWJfZmlsZSk7CgkJCWdvdG8gcmV0OwoJCX0KCgkJLy8gQWRkIHZmcyBzdHJpbmcgZmxhZ3MKCgkJZm9yIChpPTA7IG1vdW50X29wdGlvbnNbaV0uZmxhZ3MgIT0gTVNfUkVNT1VOVDsgaSsrKQoJCQlpZiAobW91bnRfb3B0aW9uc1tpXS5mbGFncyA+IDAgJiYgKG1vdW50X29wdGlvbnNbaV0uZmxhZ3MgJiB2ZnNmbGFncykpCgkJCQlhcHBlbmRfbW91bnRfb3B0aW9ucygmKG1wLT5tbnRfb3B0cyksIG1vdW50X29wdGlvbnNbaV0ubmFtZSk7CgoJCS8vIFJlbW92ZSB0cmFpbGluZyAvIChpZiBhbnkpIGZyb20gZGlyZWN0b3J5IHdlIG1vdW50ZWQgb24KCgkJaSA9IHN0cmxlbihtcC0+bW50X2RpcikgLSAxOwoJCWlmIChpID4gMCAmJiBtcC0+bW50X2RpcltpXSA9PSAnLycpIG1wLT5tbnRfZGlyW2ldID0gMDsKCgkJLy8gQ29udmVydCB0byBjYW5vbmljYWwgcGF0aG5hbWVzIGFzIG5lZWRlZAoKCQltcC0+bW50X2RpciA9IGJiX3NpbXBsaWZ5X3BhdGgobXAtPm1udF9kaXIpOwoJCWZzbmFtZSA9IDA7CgkJaWYgKCFtcC0+bW50X3R5cGUgfHwgISptcC0+bW50X3R5cGUpIHsgLyogYmluZCBtb3VudCAqLwoJCQltcC0+bW50X2ZzbmFtZSA9IGZzbmFtZSA9IGJiX3NpbXBsaWZ5X3BhdGgobXAtPm1udF9mc25hbWUpOwoJCQltcC0+bW50X3R5cGUgPSAoY2hhciopImJpbmQiOwoJCX0KCQltcC0+bW50X2ZyZXEgPSBtcC0+bW50X3Bhc3NubyA9IDA7CgoJCS8vIFdyaXRlIGFuZCBjbG9zZS4KCgkJYWRkbW50ZW50KG1vdW50VGFibGUsIG1wKTsKCQllbmRtbnRlbnQobW91bnRUYWJsZSk7CgkJaWYgKEVOQUJMRV9GRUFUVVJFX0NMRUFOX1VQKSB7CgkJCWZyZWUobXAtPm1udF9kaXIpOwoJCQlmcmVlKGZzbmFtZSk7CgkJfQoJfQogcmV0OgoJcmV0dXJuIHJjOwp9CgojaWYgRU5BQkxFX0ZFQVRVUkVfTU9VTlRfTkZTCgovKgogKiBMaW51eCBORlMgbW91bnQKICogQ29weXJpZ2h0IChDKSAxOTkzIFJpY2sgU2xhZGtleSA8anJzQHdvcmxkLnN0ZC5jb20+CiAqCiAqIExpY2Vuc2VkIHVuZGVyIEdQTHYyLCBzZWUgZmlsZSBMSUNFTlNFIGluIHRoaXMgdGFyYmFsbCBmb3IgZGV0YWlscy4KICoKICogV2VkIEZlYiAgOCAxMjo1MTo0OCAxOTk1LCBiaXJvQHlnZ2RyYXNpbC5jb20gKFJvc3MgQmlybyk6IGFsbG93IGFsbCBwb3J0CiAqIG51bWJlcnMgdG8gYmUgc3BlY2lmaWVkIG9uIHRoZSBjb21tYW5kIGxpbmUuCiAqCiAqIEZyaSwgOCBNYXIgMTk5NiAxODowMTozOSwgU3dlbiBUaHVlbW1sZXIgPHN3ZW5AdW5pLXBhZGVyYm9ybi5kZT46CiAqIE9taXQgdGhlIGNhbGwgdG8gY29ubmVjdCgpIGZvciBMaW51eCB2ZXJzaW9uIDEuMy4xMSBvciBsYXRlci4KICoKICogV2VkIE9jdCAgMSAyMzo1NToyOCAxOTk3OiBEaWNrIFN0cmVlZmxhbmQgPGRpY2tfc3RyZWVmbGFuZEB0YXNraW5nLmNvbT4KICogSW1wbGVtZW50ZWQgdGhlICJiZyIsICJmZyIgYW5kICJyZXRyeSIgbW91bnQgb3B0aW9ucyBmb3IgTkZTLgogKgogKiAxOTk5LTAyLTIyIEFya2FkaXVzeiBNabZraWV3aWN6IDxtaXNpZWtAbWlzaWVrLmV1Lm9yZz4KICogLSBhZGRlZCBOYXRpdmUgTGFuZ3VhZ2UgU3VwcG9ydAogKgogKiBNb2RpZmllZCBieSBPbGFmIEtpcmNoIGFuZCBUcm9uZCBNeWtsZWJ1c3QgZm9yIG5ldyBORlMgY29kZSwKICogcGx1cyBORlN2MyBzdHVmZi4KICovCgovKiBUaGlzIGlzIGp1c3QgYSB3YXJuaW5nIG9mIGEgY29tbW9uIG1pc3Rha2UuICBQb3NzaWJseSB0aGlzIHNob3VsZCBiZSBhCiAqIHVjbGliYyBmYXEgZW50cnkgcmF0aGVyIHRoYW4gaW4gYnVzeWJveC4uLiAqLwojaWYgZGVmaW5lZChfX1VDTElCQ19fKSAmJiAhIGRlZmluZWQoX19VQ0xJQkNfSEFTX1JQQ19fKQojZXJyb3IgIllvdSBuZWVkIHRvIGJ1aWxkIHVDbGliYyB3aXRoIFVDTElCQ19IQVNfUlBDIGZvciBORlMgc3VwcG9ydC4iCiNlbmRpZgoKI2RlZmluZSBNT1VOVFBPUlQgNjM1CiNkZWZpbmUgTU5UUEFUSExFTiAxMDI0CiNkZWZpbmUgTU5UTkFNTEVOIDI1NQojZGVmaW5lIEZIU0laRSAzMgojZGVmaW5lIEZIU0laRTMgNjQKCnR5cGVkZWYgY2hhciBmaGFuZGxlW0ZIU0laRV07Cgp0eXBlZGVmIHN0cnVjdCB7Cgl1bnNpZ25lZCBpbnQgZmhhbmRsZTNfbGVuOwoJY2hhciAqZmhhbmRsZTNfdmFsOwp9IGZoYW5kbGUzOwoKZW51bSBtb3VudHN0YXQzIHsKCU1OVF9PSyA9IDAsCglNTlQzRVJSX1BFUk0gPSAxLAoJTU5UM0VSUl9OT0VOVCA9IDIsCglNTlQzRVJSX0lPID0gNSwKCU1OVDNFUlJfQUNDRVMgPSAxMywKCU1OVDNFUlJfTk9URElSID0gMjAsCglNTlQzRVJSX0lOVkFMID0gMjIsCglNTlQzRVJSX05BTUVUT09MT05HID0gNjMsCglNTlQzRVJSX05PVFNVUFAgPSAxMDAwNCwKCU1OVDNFUlJfU0VSVkVSRkFVTFQgPSAxMDAwNiwKfTsKdHlwZWRlZiBlbnVtIG1vdW50c3RhdDMgbW91bnRzdGF0MzsKCnN0cnVjdCBmaHN0YXR1cyB7Cgl1bnNpZ25lZCBpbnQgZmhzX3N0YXR1czsKCXVuaW9uIHsKCQlmaGFuZGxlIGZoc19maGFuZGxlOwoJfSBmaHN0YXR1c191Owp9Owp0eXBlZGVmIHN0cnVjdCBmaHN0YXR1cyBmaHN0YXR1czsKCnN0cnVjdCBtb3VudHJlczNfb2sgewoJZmhhbmRsZTMgZmhhbmRsZTsKCXN0cnVjdCB7CgkJdW5zaWduZWQgaW50IGF1dGhfZmxhdm91cnNfbGVuOwoJCWNoYXIgKmF1dGhfZmxhdm91cnNfdmFsOwoJfSBhdXRoX2ZsYXZvdXJzOwp9Owp0eXBlZGVmIHN0cnVjdCBtb3VudHJlczNfb2sgbW91bnRyZXMzX29rOwoKc3RydWN0IG1vdW50cmVzMyB7Cgltb3VudHN0YXQzIGZoc19zdGF0dXM7Cgl1bmlvbiB7CgkJbW91bnRyZXMzX29rIG1vdW50aW5mbzsKCX0gbW91bnRyZXMzX3U7Cn07CnR5cGVkZWYgc3RydWN0IG1vdW50cmVzMyBtb3VudHJlczM7Cgp0eXBlZGVmIGNoYXIgKmRpcnBhdGg7Cgp0eXBlZGVmIGNoYXIgKm5hbWU7Cgp0eXBlZGVmIHN0cnVjdCBtb3VudGJvZHkgKm1vdW50bGlzdDsKCnN0cnVjdCBtb3VudGJvZHkgewoJbmFtZSBtbF9ob3N0bmFtZTsKCWRpcnBhdGggbWxfZGlyZWN0b3J5OwoJbW91bnRsaXN0IG1sX25leHQ7Cn07CnR5cGVkZWYgc3RydWN0IG1vdW50Ym9keSBtb3VudGJvZHk7Cgp0eXBlZGVmIHN0cnVjdCBncm91cG5vZGUgKmdyb3VwczsKCnN0cnVjdCBncm91cG5vZGUgewoJbmFtZSBncl9uYW1lOwoJZ3JvdXBzIGdyX25leHQ7Cn07CnR5cGVkZWYgc3RydWN0IGdyb3Vwbm9kZSBncm91cG5vZGU7Cgp0eXBlZGVmIHN0cnVjdCBleHBvcnRub2RlICpleHBvcnRzOwoKc3RydWN0IGV4cG9ydG5vZGUgewoJZGlycGF0aCBleF9kaXI7Cglncm91cHMgZXhfZ3JvdXBzOwoJZXhwb3J0cyBleF9uZXh0Owp9Owp0eXBlZGVmIHN0cnVjdCBleHBvcnRub2RlIGV4cG9ydG5vZGU7CgpzdHJ1Y3QgcHBhdGhjbmYgewoJaW50IHBjX2xpbmtfbWF4OwoJc2hvcnQgcGNfbWF4X2Nhbm9uOwoJc2hvcnQgcGNfbWF4X2lucHV0OwoJc2hvcnQgcGNfbmFtZV9tYXg7CglzaG9ydCBwY19wYXRoX21heDsKCXNob3J0IHBjX3BpcGVfYnVmOwoJdWludDhfdCBwY192ZGlzYWJsZTsKCWNoYXIgcGNfeHh4OwoJc2hvcnQgcGNfbWFza1syXTsKfTsKdHlwZWRlZiBzdHJ1Y3QgcHBhdGhjbmYgcHBhdGhjbmY7CgojZGVmaW5lIE1PVU5UUFJPRyAxMDAwMDUKI2RlZmluZSBNT1VOVFZFUlMgMQoKI2RlZmluZSBNT1VOVFBST0NfTlVMTCAwCiNkZWZpbmUgTU9VTlRQUk9DX01OVCAxCiNkZWZpbmUgTU9VTlRQUk9DX0RVTVAgMgojZGVmaW5lIE1PVU5UUFJPQ19VTU5UIDMKI2RlZmluZSBNT1VOVFBST0NfVU1OVEFMTCA0CiNkZWZpbmUgTU9VTlRQUk9DX0VYUE9SVCA1CiNkZWZpbmUgTU9VTlRQUk9DX0VYUE9SVEFMTCA2CgojZGVmaW5lIE1PVU5UVkVSU19QT1NJWCAyCgojZGVmaW5lIE1PVU5UUFJPQ19QQVRIQ09ORiA3CgojZGVmaW5lIE1PVU5UX1YzIDMKCiNkZWZpbmUgTU9VTlRQUk9DM19OVUxMIDAKI2RlZmluZSBNT1VOVFBST0MzX01OVCAxCiNkZWZpbmUgTU9VTlRQUk9DM19EVU1QIDIKI2RlZmluZSBNT1VOVFBST0MzX1VNTlQgMwojZGVmaW5lIE1PVU5UUFJPQzNfVU1OVEFMTCA0CiNkZWZpbmUgTU9VTlRQUk9DM19FWFBPUlQgNQoKZW51bSB7CiNpZm5kZWYgTkZTX0ZIU0laRQoJTkZTX0ZIU0laRSA9IDMyLAojZW5kaWYKI2lmbmRlZiBORlNfUE9SVAoJTkZTX1BPUlQgPSAyMDQ5CiNlbmRpZgp9OwoKLyoKICogV2Ugd2FudCB0byBiZSBhYmxlIHRvIGNvbXBpbGUgbW91bnQgb24gb2xkIGtlcm5lbHMgaW4gc3VjaCBhIHdheQogKiB0aGF0IHRoZSBiaW5hcnkgd2lsbCB3b3JrIHdlbGwgb24gbW9yZSByZWNlbnQga2VybmVscy4KICogVGh1cywgaWYgbmVjZXNzYXJ5IHdlIHRlYWNoIG5mc21vdW50LmMgdGhlIHN0cnVjdHVyZSBvZiBuZXcgZmllbGRzCiAqIHRoYXQgd2lsbCBjb21lIGxhdGVyLgogKgogKiBNb3Jlb3ZlciwgdGhlIG5ldyBrZXJuZWwgaW5jbHVkZXMgY29uZmxpY3Qgd2l0aCBnbGliYyBpbmNsdWRlcwogKiBzbyBpdCBpcyBlYXNpZXN0IHRvIGlnbm9yZSB0aGUga2VybmVsIGFsdG9nZXRoZXIgKGF0IGNvbXBpbGUgdGltZSkuCiAqLwoKc3RydWN0IG5mczJfZmggewoJY2hhciAgICAgICAgICAgICAgICAgICAgZGF0YVszMl07Cn07CnN0cnVjdCBuZnMzX2ZoIHsKCXVuc2lnbmVkIHNob3J0ICAgICAgICAgIHNpemU7Cgl1bnNpZ25lZCBjaGFyICAgICAgICAgICBkYXRhWzY0XTsKfTsKCnN0cnVjdCBuZnNfbW91bnRfZGF0YSB7CglpbnQJCXZlcnNpb247CQkvKiAxICovCglpbnQJCWZkOwkJCS8qIDEgKi8KCXN0cnVjdCBuZnMyX2ZoCW9sZF9yb290OwkJLyogMSAqLwoJaW50CQlmbGFnczsJCQkvKiAxICovCglpbnQJCXJzaXplOwkJCS8qIDEgKi8KCWludAkJd3NpemU7CQkJLyogMSAqLwoJaW50CQl0aW1lbzsJCQkvKiAxICovCglpbnQJCXJldHJhbnM7CQkvKiAxICovCglpbnQJCWFjcmVnbWluOwkJLyogMSAqLwoJaW50CQlhY3JlZ21heDsJCS8qIDEgKi8KCWludAkJYWNkaXJtaW47CQkvKiAxICovCglpbnQJCWFjZGlybWF4OwkJLyogMSAqLwoJc3RydWN0IHNvY2thZGRyX2luIGFkZHI7CQkvKiAxICovCgljaGFyCQlob3N0bmFtZVsyNTZdOwkJLyogMSAqLwoJaW50CQluYW1sZW47CQkJLyogMiAqLwoJdW5zaWduZWQgaW50CWJzaXplOwkJCS8qIDMgKi8KCXN0cnVjdCBuZnMzX2ZoCXJvb3Q7CQkJLyogNCAqLwp9OwoKLyogYml0cyBpbiB0aGUgZmxhZ3MgZmllbGQgKi8KZW51bSB7CglORlNfTU9VTlRfU09GVCA9IDB4MDAwMSwJLyogMSAqLwoJTkZTX01PVU5UX0lOVFIgPSAweDAwMDIsCS8qIDEgKi8KCU5GU19NT1VOVF9TRUNVUkUgPSAweDAwMDQsCS8qIDEgKi8KCU5GU19NT1VOVF9QT1NJWCA9IDB4MDAwOCwJLyogMSAqLwoJTkZTX01PVU5UX05PQ1RPID0gMHgwMDEwLAkvKiAxICovCglORlNfTU9VTlRfTk9BQyA9IDB4MDAyMCwJLyogMSAqLwoJTkZTX01PVU5UX1RDUCA9IDB4MDA0MCwJCS8qIDIgKi8KCU5GU19NT1VOVF9WRVIzID0gMHgwMDgwLAkvKiAzICovCglORlNfTU9VTlRfS0VSQkVST1MgPSAweDAxMDAsCS8qIDMgKi8KCU5GU19NT1VOVF9OT05MTSA9IDB4MDIwMAkvKiAzICovCn07CgoKLyoKICogV2UgbmVlZCB0byB0cmFuc2xhdGUgYmV0d2VlbiBuZnMgc3RhdHVzIHJldHVybiB2YWx1ZXMgYW5kCiAqIHRoZSBsb2NhbCBlcnJubyB2YWx1ZXMgd2hpY2ggbWF5IG5vdCBiZSB0aGUgc2FtZS4KICoKICogQW5kcmVhcyBTY2h3YWIgPHNjaHdhYkBMUzUuaW5mb3JtYXRpay51bmktZG9ydG11bmQuZGU+OiBjaGFuZ2UgZXJybm86CiAqICJhZnRlciAjaW5jbHVkZSA8ZXJybm8uaD4gdGhlIHN5bWJvbCBlcnJubyBpcyByZXNlcnZlZCBmb3IgYW55IHVzZSwKICogIGl0IGNhbm5vdCBldmVuIGJlIHVzZWQgYXMgYSBzdHJ1Y3QgdGFnIG9yIGZpZWxkIG5hbWUiLgogKi8KCiNpZm5kZWYgRURRVU9UCiNkZWZpbmUgRURRVU9UCUVOT1NQQwojZW5kaWYKCi8vIENvbnZlcnQgZWFjaCBORlNFUlJfQkxBSCBpbnRvIEVCTEFICgpzdGF0aWMgY29uc3Qgc3RydWN0IHsKCWludCBzdGF0OwoJaW50IGVycm51bTsKfSBuZnNfZXJydGJsW10gPSB7Cgl7MCwwfSwgezEsRVBFUk19LCB7MixFTk9FTlR9LCB7NSxFSU99LCB7NixFTlhJT30sIHsxMyxFQUNDRVN9LCB7MTcsRUVYSVNUfSwKCXsxOSxFTk9ERVZ9LCB7MjAsRU5PVERJUn0sIHsyMSxFSVNESVJ9LCB7MjIsRUlOVkFMfSwgezI3LEVGQklHfSwKCXsyOCxFTk9TUEN9LCB7MzAsRVJPRlN9LCB7NjMsRU5BTUVUT09MT05HfSwgezY2LEVOT1RFTVBUWX0sIHs2OSxFRFFVT1R9LAoJezcwLEVTVEFMRX0sIHs3MSxFUkVNT1RFfSwgey0xLEVJT30KfTsKCnN0YXRpYyBjaGFyICpuZnNfc3RyZXJyb3IoaW50IHN0YXR1cykKewoJaW50IGk7CglzdGF0aWMgY2hhciBidWZbc2l6ZW9mKCJ1bmtub3duIG5mcyBzdGF0dXMgcmV0dXJuIHZhbHVlOiAiKSArIHNpemVvZihpbnQpKjNdOwoKCWZvciAoaSA9IDA7IG5mc19lcnJ0YmxbaV0uc3RhdCAhPSAtMTsgaSsrKSB7CgkJaWYgKG5mc19lcnJ0YmxbaV0uc3RhdCA9PSBzdGF0dXMpCgkJCXJldHVybiBzdHJlcnJvcihuZnNfZXJydGJsW2ldLmVycm51bSk7Cgl9CglzcHJpbnRmKGJ1ZiwgInVua25vd24gbmZzIHN0YXR1cyByZXR1cm4gdmFsdWU6ICVkIiwgc3RhdHVzKTsKCXJldHVybiBidWY7Cn0KCnN0YXRpYyBib29sX3QgeGRyX2ZoYW5kbGUoWERSICp4ZHJzLCBmaGFuZGxlIG9ianApCnsKCWlmICgheGRyX29wYXF1ZSh4ZHJzLCBvYmpwLCBGSFNJWkUpKQoJCSByZXR1cm4gRkFMU0U7CglyZXR1cm4gVFJVRTsKfQoKc3RhdGljIGJvb2xfdCB4ZHJfZmhzdGF0dXMoWERSICp4ZHJzLCBmaHN0YXR1cyAqb2JqcCkKewoJaWYgKCF4ZHJfdV9pbnQoeGRycywgJm9ianAtPmZoc19zdGF0dXMpKQoJCSByZXR1cm4gRkFMU0U7Cglzd2l0Y2ggKG9ianAtPmZoc19zdGF0dXMpIHsKCWNhc2UgMDoKCQlpZiAoIXhkcl9maGFuZGxlKHhkcnMsIG9ianAtPmZoc3RhdHVzX3UuZmhzX2ZoYW5kbGUpKQoJCQkgcmV0dXJuIEZBTFNFOwoJCWJyZWFrOwoJZGVmYXVsdDoKCQlicmVhazsKCX0KCXJldHVybiBUUlVFOwp9CgpzdGF0aWMgYm9vbF90IHhkcl9kaXJwYXRoKFhEUiAqeGRycywgZGlycGF0aCAqb2JqcCkKewoJaWYgKCF4ZHJfc3RyaW5nKHhkcnMsIG9ianAsIE1OVFBBVEhMRU4pKQoJCSByZXR1cm4gRkFMU0U7CglyZXR1cm4gVFJVRTsKfQoKc3RhdGljIGJvb2xfdCB4ZHJfZmhhbmRsZTMoWERSICp4ZHJzLCBmaGFuZGxlMyAqb2JqcCkKewoJaWYgKCF4ZHJfYnl0ZXMoeGRycywgKGNoYXIgKiopJm9ianAtPmZoYW5kbGUzX3ZhbCwgKHVuc2lnbmVkIGludCAqKSAmb2JqcC0+ZmhhbmRsZTNfbGVuLCBGSFNJWkUzKSkKCQkgcmV0dXJuIEZBTFNFOwoJcmV0dXJuIFRSVUU7Cn0KCnN0YXRpYyBib29sX3QgeGRyX21vdW50cmVzM19vayhYRFIgKnhkcnMsIG1vdW50cmVzM19vayAqb2JqcCkKewoJaWYgKCF4ZHJfZmhhbmRsZTMoeGRycywgJm9ianAtPmZoYW5kbGUpKQoJCXJldHVybiBGQUxTRTsKCWlmICgheGRyX2FycmF5KHhkcnMsICYob2JqcC0+YXV0aF9mbGF2b3Vycy5hdXRoX2ZsYXZvdXJzX3ZhbCksICYob2JqcC0+YXV0aF9mbGF2b3Vycy5hdXRoX2ZsYXZvdXJzX2xlbiksIH4wLAoJCQkJc2l6ZW9mIChpbnQpLCAoeGRycHJvY190KSB4ZHJfaW50KSkKCQlyZXR1cm4gRkFMU0U7CglyZXR1cm4gVFJVRTsKfQoKc3RhdGljIGJvb2xfdCB4ZHJfbW91bnRzdGF0MyhYRFIgKnhkcnMsIG1vdW50c3RhdDMgKm9ianApCnsKCWlmICgheGRyX2VudW0oeGRycywgKGVudW1fdCAqKSBvYmpwKSkKCQkgcmV0dXJuIEZBTFNFOwoJcmV0dXJuIFRSVUU7Cn0KCnN0YXRpYyBib29sX3QgeGRyX21vdW50cmVzMyhYRFIgKnhkcnMsIG1vdW50cmVzMyAqb2JqcCkKewoJaWYgKCF4ZHJfbW91bnRzdGF0Myh4ZHJzLCAmb2JqcC0+ZmhzX3N0YXR1cykpCgkJcmV0dXJuIEZBTFNFOwoJc3dpdGNoIChvYmpwLT5maHNfc3RhdHVzKSB7CgljYXNlIE1OVF9PSzoKCQlpZiAoIXhkcl9tb3VudHJlczNfb2soeGRycywgJm9ianAtPm1vdW50cmVzM191Lm1vdW50aW5mbykpCgkJCSByZXR1cm4gRkFMU0U7CgkJYnJlYWs7CglkZWZhdWx0OgoJCWJyZWFrOwoJfQoJcmV0dXJuIFRSVUU7Cn0KCiNkZWZpbmUgTUFYX05GU1BST1QgKChuZnNfbW91bnRfdmVyc2lvbiA+PSA0KSA/IDMgOiAyKQoKLyoKICogbmZzX21vdW50X3ZlcnNpb24gYWNjb3JkaW5nIHRvIHRoZSBzb3VyY2VzIHNlZW4gYXQgY29tcGlsZSB0aW1lLgogKi8Kc3RhdGljIGludCBuZnNfbW91bnRfdmVyc2lvbjsKc3RhdGljIGludCBrZXJuZWxfdmVyc2lvbjsKCi8qCiAqIFVuZm9ydHVuYXRlbHksIHRoZSBrZXJuZWwgcHJpbnRzIGFubm95aW5nIGNvbnNvbGUgbWVzc2FnZXMKICogaW4gY2FzZSBvZiBhbiB1bmV4cGVjdGVkIG5mcyBtb3VudCB2ZXJzaW9uIChpbnN0ZWFkIG9mCiAqIGp1c3QgcmV0dXJuaW5nIHNvbWUgZXJyb3IpLiAgVGhlcmVmb3JlIHdlJ2xsIGhhdmUgdG8gdHJ5CiAqIGFuZCBmaWd1cmUgb3V0IHdoYXQgdmVyc2lvbiB0aGUga2VybmVsIGV4cGVjdHMuCiAqCiAqIFZhcmlhYmxlczoKICoJS0VSTkVMX05GU19NT1VOVF9WRVJTSU9OOiBrZXJuZWwgc291cmNlcyBhdCBjb21waWxlIHRpbWUKICoJTkZTX01PVU5UX1ZFUlNJT046IHRoZXNlIG5mc21vdW50IHNvdXJjZXMgYXQgY29tcGlsZSB0aW1lCiAqCW5mc19tb3VudF92ZXJzaW9uOiB2ZXJzaW9uIHRoaXMgc291cmNlIGFuZCBydW5uaW5nIGtlcm5lbCBjYW4gaGFuZGxlCiAqLwpzdGF0aWMgdm9pZApmaW5kX2tlcm5lbF9uZnNfbW91bnRfdmVyc2lvbih2b2lkKQp7CglpZiAoa2VybmVsX3ZlcnNpb24pCgkJcmV0dXJuOwoKCW5mc19tb3VudF92ZXJzaW9uID0gNDsgLyogZGVmYXVsdCAqLwoKCWtlcm5lbF92ZXJzaW9uID0gZ2V0X2xpbnV4X3ZlcnNpb25fY29kZSgpOwoJaWYgKGtlcm5lbF92ZXJzaW9uKSB7CgkJaWYgKGtlcm5lbF92ZXJzaW9uIDwgS0VSTkVMX1ZFUlNJT04oMiwxLDMyKSkKCQkJbmZzX21vdW50X3ZlcnNpb24gPSAxOwoJCWVsc2UgaWYgKGtlcm5lbF92ZXJzaW9uIDwgS0VSTkVMX1ZFUlNJT04oMiwyLDE4KSB8fAoJCQkJKGtlcm5lbF92ZXJzaW9uID49IEtFUk5FTF9WRVJTSU9OKDIsMywwKSAmJgoJCQkJIGtlcm5lbF92ZXJzaW9uIDwgS0VSTkVMX1ZFUlNJT04oMiwzLDk5KSkpCgkJCW5mc19tb3VudF92ZXJzaW9uID0gMzsKCQkvKiBlbHNlIHY0IHNpbmNlIDIuMy45OXByZTQgKi8KCX0KfQoKc3RhdGljIHN0cnVjdCBwbWFwICoKZ2V0X21vdW50cG9ydChzdHJ1Y3Qgc29ja2FkZHJfaW4gKnNlcnZlcl9hZGRyLAoJbG9uZyB1bnNpZ25lZCBwcm9nLAoJbG9uZyB1bnNpZ25lZCB2ZXJzaW9uLAoJbG9uZyB1bnNpZ25lZCBwcm90bywKCWxvbmcgdW5zaWduZWQgcG9ydCkKewoJc3RydWN0IHBtYXBsaXN0ICpwbWFwOwoJc3RhdGljIHN0cnVjdCBwbWFwIHAgPSB7MCwgMCwgMCwgMH07CgoJc2VydmVyX2FkZHItPnNpbl9wb3J0ID0gUE1BUFBPUlQ7Ci8qIGdsaWJjIDIuNCAoc3RpbGwpIGhhcyBwbWFwX2dldG1hcHMoc3RydWN0IHNvY2thZGRyX2luICopLgogKiBJIHVuZGVyc3RhbmQgaXQgbGlrZSAiSVB2NiBmb3IgdGhpcyBpcyBub3QgMTAwJSByZWFkeSIgKi8KCXBtYXAgPSBwbWFwX2dldG1hcHMoc2VydmVyX2FkZHIpOwoKCWlmICh2ZXJzaW9uID4gTUFYX05GU1BST1QpCgkJdmVyc2lvbiA9IE1BWF9ORlNQUk9UOwoJaWYgKCFwcm9nKQoJCXByb2cgPSBNT1VOVFBST0c7CglwLnBtX3Byb2cgPSBwcm9nOwoJcC5wbV92ZXJzID0gdmVyc2lvbjsKCXAucG1fcHJvdCA9IHByb3RvOwoJcC5wbV9wb3J0ID0gcG9ydDsKCgl3aGlsZSAocG1hcCkgewoJCWlmIChwbWFwLT5wbWxfbWFwLnBtX3Byb2cgIT0gcHJvZykKCQkJZ290byBuZXh0OwoJCWlmICghdmVyc2lvbiAmJiBwLnBtX3ZlcnMgPiBwbWFwLT5wbWxfbWFwLnBtX3ZlcnMpCgkJCWdvdG8gbmV4dDsKCQlpZiAodmVyc2lvbiA+IDIgJiYgcG1hcC0+cG1sX21hcC5wbV92ZXJzICE9IHZlcnNpb24pCgkJCWdvdG8gbmV4dDsKCQlpZiAodmVyc2lvbiAmJiB2ZXJzaW9uIDw9IDIgJiYgcG1hcC0+cG1sX21hcC5wbV92ZXJzID4gMikKCQkJZ290byBuZXh0OwoJCWlmIChwbWFwLT5wbWxfbWFwLnBtX3ZlcnMgPiBNQVhfTkZTUFJPVCB8fAoJCSAgICAocHJvdG8gJiYgcC5wbV9wcm90ICYmIHBtYXAtPnBtbF9tYXAucG1fcHJvdCAhPSBwcm90bykgfHwKCQkgICAgKHBvcnQgJiYgcG1hcC0+cG1sX21hcC5wbV9wb3J0ICE9IHBvcnQpKQoJCQlnb3RvIG5leHQ7CgkJbWVtY3B5KCZwLCAmcG1hcC0+cG1sX21hcCwgc2l6ZW9mKHApKTsKbmV4dDoKCQlwbWFwID0gcG1hcC0+cG1sX25leHQ7Cgl9CglpZiAoIXAucG1fdmVycykKCQlwLnBtX3ZlcnMgPSBNT1VOVFZFUlM7CglpZiAoIXAucG1fcG9ydCkKCQlwLnBtX3BvcnQgPSBNT1VOVFBPUlQ7CglpZiAoIXAucG1fcHJvdCkKCQlwLnBtX3Byb3QgPSBJUFBST1RPX1RDUDsKCXJldHVybiAmcDsKfQoKc3RhdGljIGludCBkYWVtb25pemUodm9pZCkKewoJaW50IGZkOwoJaW50IHBpZCA9IGZvcmsoKTsKCWlmIChwaWQgPCAwKSAvKiBlcnJvciAqLwoJCXJldHVybiAtZXJybm87CglpZiAocGlkID4gMCkgLyogcGFyZW50ICovCgkJcmV0dXJuIDA7CgkvKiBjaGlsZCAqLwoJZmQgPSB4b3BlbihiYl9kZXZfbnVsbCwgT19SRFdSKTsKCWR1cDIoZmQsIDApOwoJZHVwMihmZCwgMSk7CglkdXAyKGZkLCAyKTsKCXdoaWxlIChmZCA+IDIpIGNsb3NlKGZkLS0pOwoJc2V0c2lkKCk7CglvcGVubG9nKGFwcGxldF9uYW1lLCBMT0dfUElELCBMT0dfREFFTU9OKTsKCWxvZ21vZGUgPSBMT0dNT0RFX1NZU0xPRzsKCXJldHVybiAxOwp9CgovLyBUT0RPCnN0YXRpYyBpbmxpbmUgaW50IHdlX3Nhd190aGlzX2hvc3RfYmVmb3JlKGNvbnN0IGNoYXIgKmhvc3RuYW1lKQp7CglyZXR1cm4gMDsKfQoKLyogUlBDIHN0cmVycm9yIGFuYWxvZ3MgYXJlIHRlcm1pbmFsbHkgaWRpb3RpYzoKICogKm1hbmRhdG9yeSogcHJlZml4IGFuZCBcbiBhdCBlbmQuCiAqIFRoaXMgaG9wZWZ1bGx5IGhlbHBzLiBVc2FnZToKICogZXJyb3JfbXNnX3JwYyhjbG50XyplcnJvciooIiAiKSkgKi8Kc3RhdGljIHZvaWQgZXJyb3JfbXNnX3JwYyhjb25zdCBjaGFyICptc2cpCnsKCWludCBsZW47Cgl3aGlsZSAobXNnWzBdID09ICcgJyB8fCBtc2dbMF0gPT0gJzonKSBtc2crKzsKCWxlbiA9IHN0cmxlbihtc2cpOwoJd2hpbGUgKGxlbiAmJiBtc2dbbGVuLTFdID09ICdcbicpIGxlbi0tOwoJYmJfZXJyb3JfbXNnKCIlLipzIiwgbGVuLCBtc2cpOwp9CgovLyBOQjogbXAtPnh4eCBmaWVsZHMgbWF5IGJlIHRyYXNoZWQgb24gZXhpdApzdGF0aWMgaW50IG5mc21vdW50KHN0cnVjdCBtbnRlbnQgKm1wLCBpbnQgdmZzZmxhZ3MsIGNoYXIgKmZpbHRlcm9wdHMpCnsKCUNMSUVOVCAqbWNsaWVudDsKCWNoYXIgKmhvc3RuYW1lOwoJY2hhciAqcGF0aG5hbWU7CgljaGFyICptb3VudGhvc3Q7CglzdHJ1Y3QgbmZzX21vdW50X2RhdGEgZGF0YTsKCWNoYXIgKm9wdDsKCXN0cnVjdCBob3N0ZW50ICpocDsKCXN0cnVjdCBzb2NrYWRkcl9pbiBzZXJ2ZXJfYWRkcjsKCXN0cnVjdCBzb2NrYWRkcl9pbiBtb3VudF9zZXJ2ZXJfYWRkcjsKCWludCBtc29jaywgZnNvY2s7Cgl1bmlvbiB7CgkJc3RydWN0IGZoc3RhdHVzIG5mc3YyOwoJCXN0cnVjdCBtb3VudHJlczMgbmZzdjM7Cgl9IHN0YXR1czsKCWludCBkYWVtb25pemVkOwoJY2hhciAqczsKCWludCBwb3J0OwoJaW50IG1vdW50cG9ydDsKCWludCBwcm90bzsKCWludCBiZzsKCWludCBzb2Z0OwoJaW50IGludHI7CglpbnQgcG9zaXg7CglpbnQgbm9jdG87CglpbnQgbm9hYzsKCWludCBub2xvY2s7CglpbnQgcmV0cnk7CglpbnQgdGNwOwoJaW50IG1vdW50cHJvZzsKCWludCBtb3VudHZlcnM7CglpbnQgbmZzcHJvZzsKCWludCBuZnN2ZXJzOwoJaW50IHJldHZhbDsKCglmaW5kX2tlcm5lbF9uZnNfbW91bnRfdmVyc2lvbigpOwoKCWRhZW1vbml6ZWQgPSAwOwoJbW91bnRob3N0ID0gTlVMTDsKCXJldHZhbCA9IEVUSU1FRE9VVDsKCW1zb2NrID0gZnNvY2sgPSAtMTsKCW1jbGllbnQgPSBOVUxMOwoKCS8qIE5COiBob3N0bmFtZSwgbW91bnRob3N0LCBmaWx0ZXJvcHRzIG11c3QgYmUgZnJlZSgpZCBwcmlvciB0byByZXR1cm4gKi8KCglmaWx0ZXJvcHRzID0geHN0cmR1cChmaWx0ZXJvcHRzKTsgLyogZ29pbmcgdG8gdHJhc2ggaXQgbGF0ZXIuLi4gKi8KCglob3N0bmFtZSA9IHhzdHJkdXAobXAtPm1udF9mc25hbWUpOwoJLyogbW91bnRfbWFpbigpIGd1YXJhbnRlZXMgdGhhdCAnOicgaXMgdGhlcmUgKi8KCXMgPSBzdHJjaHIoaG9zdG5hbWUsICc6Jyk7CglwYXRobmFtZSA9IHMgKyAxOwoJKnMgPSAnXDAnOwoJLyogSWdub3JlIGFsbCBidXQgZmlyc3QgaG9zdG5hbWUgaW4gcmVwbGljYXRlZCBtb3VudHMKCSAgIHVudGlsIHRoZXkgY2FuIGJlIGZ1bGx5IHN1cHBvcnRlZC4gKG1hY2tAc2dpLmNvbSkgKi8KCXMgPSBzdHJjaHIoaG9zdG5hbWUsICcsJyk7CglpZiAocykgewoJCSpzID0gJ1wwJzsKCQliYl9lcnJvcl9tc2coIndhcm5pbmc6IG11bHRpcGxlIGhvc3RuYW1lcyBub3Qgc3VwcG9ydGVkIik7Cgl9CgoJc2VydmVyX2FkZHIuc2luX2ZhbWlseSA9IEFGX0lORVQ7CglpZiAoIWluZXRfYXRvbihob3N0bmFtZSwgJnNlcnZlcl9hZGRyLnNpbl9hZGRyKSkgewoJCWhwID0gZ2V0aG9zdGJ5bmFtZShob3N0bmFtZSk7CgkJaWYgKGhwID09IE5VTEwpIHsKCQkJYmJfaGVycm9yX21zZygiJXMiLCBob3N0bmFtZSk7CgkJCWdvdG8gZmFpbDsKCQl9CgkJaWYgKGhwLT5oX2xlbmd0aCA+IHNpemVvZihzdHJ1Y3QgaW5fYWRkcikpIHsKCQkJYmJfZXJyb3JfbXNnKCJnb3QgYmFkIGhwLT5oX2xlbmd0aCIpOwoJCQlocC0+aF9sZW5ndGggPSBzaXplb2Yoc3RydWN0IGluX2FkZHIpOwoJCX0KCQltZW1jcHkoJnNlcnZlcl9hZGRyLnNpbl9hZGRyLAoJCQkJaHAtPmhfYWRkciwgaHAtPmhfbGVuZ3RoKTsKCX0KCgltZW1jcHkoJm1vdW50X3NlcnZlcl9hZGRyLCAmc2VydmVyX2FkZHIsIHNpemVvZihtb3VudF9zZXJ2ZXJfYWRkcikpOwoKCS8qIGFkZCBJUCBhZGRyZXNzIHRvIG10YWIgb3B0aW9ucyBmb3IgdXNlIHdoZW4gdW5tb3VudGluZyAqLwoKCWlmICghbXAtPm1udF9vcHRzKSB7IC8qIFRPRE86IGFjdHVhbGx5IG1wLT5tbnRfb3B0cyBpcyBuZXZlciBOVUxMICovCgkJbXAtPm1udF9vcHRzID0geGFzcHJpbnRmKCJhZGRyPSVzIiwgaW5ldF9udG9hKHNlcnZlcl9hZGRyLnNpbl9hZGRyKSk7Cgl9IGVsc2UgewoJCWNoYXIgKnRtcCA9IHhhc3ByaW50ZigiJXMlc2FkZHI9JXMiLCBtcC0+bW50X29wdHMsCgkJCQkJbXAtPm1udF9vcHRzWzBdID8gIiwiIDogIiIsCgkJCQkJaW5ldF9udG9hKHNlcnZlcl9hZGRyLnNpbl9hZGRyKSk7CgkJZnJlZShtcC0+bW50X29wdHMpOwoJCW1wLT5tbnRfb3B0cyA9IHRtcDsKCX0KCgkvKiBTZXQgZGVmYXVsdCBvcHRpb25zLgoJICogcnNpemUvd3NpemUgKGFuZCBic2l6ZSwgZm9yIHZlciA+PSAzKSBhcmUgbGVmdCAwIGluIG9yZGVyIHRvCgkgKiBsZXQgdGhlIGtlcm5lbCBkZWNpZGUuCgkgKiB0aW1lbyBpcyBmaWxsZWQgaW4gYWZ0ZXIgd2Uga25vdyB3aGV0aGVyIGl0J2xsIGJlIFRDUCBvciBVRFAuICovCgltZW1zZXQoJmRhdGEsIDAsIHNpemVvZihkYXRhKSk7CglkYXRhLnJldHJhbnMJPSAzOwoJZGF0YS5hY3JlZ21pbgk9IDM7CglkYXRhLmFjcmVnbWF4CT0gNjA7CglkYXRhLmFjZGlybWluCT0gMzA7CglkYXRhLmFjZGlybWF4CT0gNjA7CglkYXRhLm5hbWxlbgk9IE5BTUVfTUFYOwoKCWJnID0gMDsKCXNvZnQgPSAwOwoJaW50ciA9IDA7Cglwb3NpeCA9IDA7Cglub2N0byA9IDA7Cglub2xvY2sgPSAwOwoJbm9hYyA9IDA7CglyZXRyeSA9IDEwMDAwOwkJLyogMTAwMDAgbWludXRlcyB+IDEgd2VlayAqLwoJdGNwID0gMDsKCgltb3VudHByb2cgPSBNT1VOVFBST0c7Cgltb3VudHZlcnMgPSAwOwoJcG9ydCA9IDA7Cgltb3VudHBvcnQgPSAwOwoJbmZzcHJvZyA9IDEwMDAwMzsKCW5mc3ZlcnMgPSAwOwoKCS8qIHBhcnNlIG9wdGlvbnMgKi8KCglmb3IgKG9wdCA9IHN0cnRvayhmaWx0ZXJvcHRzLCAiLCIpOyBvcHQ7IG9wdCA9IHN0cnRvayhOVUxMLCAiLCIpKSB7CgkJY2hhciAqb3B0ZXEgPSBzdHJjaHIob3B0LCAnPScpOwoJCWlmIChvcHRlcSkgewoJCQlzdGF0aWMgY29uc3QgY2hhciAqY29uc3Qgb3B0aW9uc1tdID0gewoJCQkJLyogMCAqLyAicnNpemUiLAoJCQkJLyogMSAqLyAid3NpemUiLAoJCQkJLyogMiAqLyAidGltZW8iLAoJCQkJLyogMyAqLyAicmV0cmFucyIsCgkJCQkvKiA0ICovICJhY3JlZ21pbiIsCgkJCQkvKiA1ICovICJhY3JlZ21heCIsCgkJCQkvKiA2ICovICJhY2Rpcm1pbiIsCgkJCQkvKiA3ICovICJhY2Rpcm1heCIsCgkJCQkvKiA4ICovICJhY3RpbWVvIiwKCQkJCS8qIDkgKi8gInJldHJ5IiwKCQkJCS8qIDEwICovICJwb3J0IiwKCQkJCS8qIDExICovICJtb3VudHBvcnQiLAoJCQkJLyogMTIgKi8gIm1vdW50aG9zdCIsCgkJCQkvKiAxMyAqLyAibW91bnRwcm9nIiwKCQkJCS8qIDE0ICovICJtb3VudHZlcnMiLAoJCQkJLyogMTUgKi8gIm5mc3Byb2ciLAoJCQkJLyogMTYgKi8gIm5mc3ZlcnMiLAoJCQkJLyogMTcgKi8gInZlcnMiLAoJCQkJLyogMTggKi8gInByb3RvIiwKCQkJCS8qIDE5ICovICJuYW1sZW4iLAoJCQkJLyogMjAgKi8gImFkZHIiLAoJCQkJTlVMTAoJCQl9OwoJCQlpbnQgdmFsID0geGF0b2lfdShvcHRlcSArIDEpOwoJCQkqb3B0ZXEgPSAnXDAnOwoJCQlzd2l0Y2ggKGluZGV4X2luX3N0cl9hcnJheShvcHRpb25zLCBvcHQpKSB7CgkJCWNhc2UgMDogLy8gInJzaXplIgoJCQkJZGF0YS5yc2l6ZSA9IHZhbDsKCQkJCWJyZWFrOwoJCQljYXNlIDE6IC8vICJ3c2l6ZSIKCQkJCWRhdGEud3NpemUgPSB2YWw7CgkJCQlicmVhazsKCQkJY2FzZSAyOiAvLyAidGltZW8iCgkJCQlkYXRhLnRpbWVvID0gdmFsOwoJCQkJYnJlYWs7CgkJCWNhc2UgMzogLy8gInJldHJhbnMiCgkJCQlkYXRhLnJldHJhbnMgPSB2YWw7CgkJCQlicmVhazsKCQkJY2FzZSA0OiAvLyAiYWNyZWdtaW4iCgkJCQlkYXRhLmFjcmVnbWluID0gdmFsOwoJCQkJYnJlYWs7CgkJCWNhc2UgNTogLy8gImFjcmVnbWF4IgoJCQkJZGF0YS5hY3JlZ21heCA9IHZhbDsKCQkJCWJyZWFrOwoJCQljYXNlIDY6IC8vICJhY2Rpcm1pbiIKCQkJCWRhdGEuYWNkaXJtaW4gPSB2YWw7CgkJCQlicmVhazsKCQkJY2FzZSA3OiAvLyAiYWNkaXJtYXgiCgkJCQlkYXRhLmFjZGlybWF4ID0gdmFsOwoJCQkJYnJlYWs7CgkJCWNhc2UgODogLy8gImFjdGltZW8iCgkJCQlkYXRhLmFjcmVnbWluID0gdmFsOwoJCQkJZGF0YS5hY3JlZ21heCA9IHZhbDsKCQkJCWRhdGEuYWNkaXJtaW4gPSB2YWw7CgkJCQlkYXRhLmFjZGlybWF4ID0gdmFsOwoJCQkJYnJlYWs7CgkJCWNhc2UgOTogLy8gInJldHJ5IgoJCQkJcmV0cnkgPSB2YWw7CgkJCQlicmVhazsKCQkJY2FzZSAxMDogLy8gInBvcnQiCgkJCQlwb3J0ID0gdmFsOwoJCQkJYnJlYWs7CgkJCWNhc2UgMTE6IC8vICJtb3VudHBvcnQiCgkJCQltb3VudHBvcnQgPSB2YWw7CgkJCQlicmVhazsKCQkJY2FzZSAxMjogLy8gIm1vdW50aG9zdCIKCQkJCW1vdW50aG9zdCA9IHhzdHJuZHVwKG9wdGVxKzEsCgkJCQkJCXN0cmNzcG4ob3B0ZXErMSwiIFx0XG5cciwiKSk7CgkJCQlicmVhazsKCQkJY2FzZSAxMzogLy8gIm1vdW50cHJvZyIKCQkJCW1vdW50cHJvZyA9IHZhbDsKCQkJCWJyZWFrOwoJCQljYXNlIDE0OiAvLyAibW91bnR2ZXJzIgoJCQkJbW91bnR2ZXJzID0gdmFsOwoJCQkJYnJlYWs7CgkJCWNhc2UgMTU6IC8vICJuZnNwcm9nIgoJCQkJbmZzcHJvZyA9IHZhbDsKCQkJCWJyZWFrOwoJCQljYXNlIDE2OiAvLyAibmZzdmVycyIKCQkJY2FzZSAxNzogLy8gInZlcnMiCgkJCQluZnN2ZXJzID0gdmFsOwoJCQkJYnJlYWs7CgkJCWNhc2UgMTg6IC8vICJwcm90byIKCQkJCWlmICghc3RybmNtcChvcHRlcSsxLCAidGNwIiwgMykpCgkJCQkJdGNwID0gMTsKCQkJCWVsc2UgaWYgKCFzdHJuY21wKG9wdGVxKzEsICJ1ZHAiLCAzKSkKCQkJCQl0Y3AgPSAwOwoJCQkJZWxzZQoJCQkJCWJiX2Vycm9yX21zZygid2FybmluZzogdW5yZWNvZ25pemVkIHByb3RvPSBvcHRpb24iKTsKCQkJCWJyZWFrOwoJCQljYXNlIDE5OiAvLyAibmFtbGVuIgoJCQkJaWYgKG5mc19tb3VudF92ZXJzaW9uID49IDIpCgkJCQkJZGF0YS5uYW1sZW4gPSB2YWw7CgkJCQllbHNlCgkJCQkJYmJfZXJyb3JfbXNnKCJ3YXJuaW5nOiBvcHRpb24gbmFtbGVuIGlzIG5vdCBzdXBwb3J0ZWRcbiIpOwoJCQkJYnJlYWs7CgkJCWNhc2UgMjA6IC8vICJhZGRyIiAtIGlnbm9yZQoJCQkJYnJlYWs7CgkJCWRlZmF1bHQ6CgkJCQliYl9lcnJvcl9tc2coInVua25vd24gbmZzIG1vdW50IHBhcmFtZXRlcjogJXM9JWQiLCBvcHQsIHZhbCk7CgkJCQlnb3RvIGZhaWw7CgkJCX0KCQl9CgkJZWxzZSB7CgkJCXN0YXRpYyBjb25zdCBjaGFyICpjb25zdCBvcHRpb25zW10gPSB7CgkJCQkiYmciLAoJCQkJImZnIiwKCQkJCSJzb2Z0IiwKCQkJCSJoYXJkIiwKCQkJCSJpbnRyIiwKCQkJCSJwb3NpeCIsCgkJCQkiY3RvIiwKCQkJCSJhYyIsCgkJCQkidGNwIiwKCQkJCSJ1ZHAiLAoJCQkJImxvY2siLAoJCQkJTlVMTAoJCQl9OwoJCQlpbnQgdmFsID0gMTsKCQkJaWYgKCFzdHJuY21wKG9wdCwgIm5vIiwgMikpIHsKCQkJCXZhbCA9IDA7CgkJCQlvcHQgKz0gMjsKCQkJfQoJCQlzd2l0Y2ggKGluZGV4X2luX3N0cl9hcnJheShvcHRpb25zLCBvcHQpKSB7CgkJCWNhc2UgMDogLy8gImJnIgoJCQkJYmcgPSB2YWw7CgkJCQlicmVhazsKCQkJY2FzZSAxOiAvLyAiZmciCgkJCQliZyA9ICF2YWw7CgkJCQlicmVhazsKCQkJY2FzZSAyOiAvLyAic29mdCIKCQkJCXNvZnQgPSB2YWw7CgkJCQlicmVhazsKCQkJY2FzZSAzOiAvLyAiaGFyZCIKCQkJCXNvZnQgPSAhdmFsOwoJCQkJYnJlYWs7CgkJCWNhc2UgNDogLy8gImludHIiCgkJCQlpbnRyID0gdmFsOwoJCQkJYnJlYWs7CgkJCWNhc2UgNTogLy8gInBvc2l4IgoJCQkJcG9zaXggPSB2YWw7CgkJCQlicmVhazsKCQkJY2FzZSA2OiAvLyAiY3RvIgoJCQkJbm9jdG8gPSAhdmFsOwoJCQkJYnJlYWs7CgkJCWNhc2UgNzogLy8gImFjIgoJCQkJbm9hYyA9ICF2YWw7CgkJCQlicmVhazsKCQkJY2FzZSA4OiAvLyAidGNwIgoJCQkJdGNwID0gdmFsOwoJCQkJYnJlYWs7CgkJCWNhc2UgOTogLy8gInVkcCIKCQkJCXRjcCA9ICF2YWw7CgkJCQlicmVhazsKCQkJY2FzZSAxMDogLy8gImxvY2siCgkJCQlpZiAobmZzX21vdW50X3ZlcnNpb24gPj0gMykKCQkJCQlub2xvY2sgPSAhdmFsOwoJCQkJZWxzZQoJCQkJCWJiX2Vycm9yX21zZygid2FybmluZzogb3B0aW9uIG5vbG9jayBpcyBub3Qgc3VwcG9ydGVkIik7CgkJCQlicmVhazsKCQkJZGVmYXVsdDoKCQkJCWJiX2Vycm9yX21zZygidW5rbm93biBuZnMgbW91bnQgb3B0aW9uOiAlcyVzIiwgdmFsID8gIiIgOiAibm8iLCBvcHQpOwoJCQkJZ290byBmYWlsOwoJCQl9CgkJfQoJfQoJcHJvdG8gPSAodGNwKSA/IElQUFJPVE9fVENQIDogSVBQUk9UT19VRFA7CgoJZGF0YS5mbGFncyA9IChzb2Z0ID8gTkZTX01PVU5UX1NPRlQgOiAwKQoJCXwgKGludHIgPyBORlNfTU9VTlRfSU5UUiA6IDApCgkJfCAocG9zaXggPyBORlNfTU9VTlRfUE9TSVggOiAwKQoJCXwgKG5vY3RvID8gTkZTX01PVU5UX05PQ1RPIDogMCkKCQl8IChub2FjID8gTkZTX01PVU5UX05PQUMgOiAwKTsKCWlmIChuZnNfbW91bnRfdmVyc2lvbiA+PSAyKQoJCWRhdGEuZmxhZ3MgfD0gKHRjcCA/IE5GU19NT1VOVF9UQ1AgOiAwKTsKCWlmIChuZnNfbW91bnRfdmVyc2lvbiA+PSAzKQoJCWRhdGEuZmxhZ3MgfD0gKG5vbG9jayA/IE5GU19NT1VOVF9OT05MTSA6IDApOwoJaWYgKG5mc3ZlcnMgPiBNQVhfTkZTUFJPVCB8fCBtb3VudHZlcnMgPiBNQVhfTkZTUFJPVCkgewoJCWJiX2Vycm9yX21zZygiTkZTdiVkIG5vdCBzdXBwb3J0ZWQiLCBuZnN2ZXJzKTsKCQlnb3RvIGZhaWw7Cgl9CglpZiAobmZzdmVycyAmJiAhbW91bnR2ZXJzKQoJCW1vdW50dmVycyA9IChuZnN2ZXJzIDwgMykgPyAxIDogbmZzdmVyczsKCWlmIChuZnN2ZXJzICYmIG5mc3ZlcnMgPCBtb3VudHZlcnMpIHsKCQltb3VudHZlcnMgPSBuZnN2ZXJzOwoJfQoKCS8qIEFkanVzdCBvcHRpb25zIGlmIG5vbmUgc3BlY2lmaWVkICovCglpZiAoIWRhdGEudGltZW8pCgkJZGF0YS50aW1lbyA9IHRjcCA/IDcwIDogNzsKCglkYXRhLnZlcnNpb24gPSBuZnNfbW91bnRfdmVyc2lvbjsKCglpZiAodmZzZmxhZ3MgJiBNU19SRU1PVU5UKQoJCWdvdG8gZG9fbW91bnQ7CgoJLyoKCSAqIElmIHRoZSBwcmV2aW91cyBtb3VudCBvcGVyYXRpb24gb24gdGhlIHNhbWUgaG9zdCB3YXMKCSAqIGJhY2tncm91bmRlZCwgYW5kIHRoZSAiYmciIGZvciB0aGlzIG1vdW50IGlzIGFsc28gc2V0LAoJICogZ2l2ZSB1cCBpbW1lZGlhdGVseSwgdG8gYXZvaWQgdGhlIGluaXRpYWwgdGltZW91dC4KCSAqLwoJaWYgKGJnICYmIHdlX3Nhd190aGlzX2hvc3RfYmVmb3JlKGhvc3RuYW1lKSkgewoJCWRhZW1vbml6ZWQgPSBkYWVtb25pemUoKTsgLyogcGFyZW50IG9yIGVycm9yICovCgkJaWYgKGRhZW1vbml6ZWQgPD0gMCkgeyAvKiBwYXJlbnQgb3IgZXJyb3IgKi8KCQkJcmV0dmFsID0gLWRhZW1vbml6ZWQ7CgkJCWdvdG8gcmV0OwoJCX0KCX0KCgkvKiBjcmVhdGUgbW91bnQgZGFlbW9uIGNsaWVudCAqLwoJLyogU2VlIGlmIHRoZSBuZnMgaG9zdCA9IG1vdW50IGhvc3QuICovCglpZiAobW91bnRob3N0KSB7CgkJaWYgKG1vdW50aG9zdFswXSA+PSAnMCcgJiYgbW91bnRob3N0WzBdIDw9ICc5JykgewoJCQltb3VudF9zZXJ2ZXJfYWRkci5zaW5fZmFtaWx5ID0gQUZfSU5FVDsKCQkJbW91bnRfc2VydmVyX2FkZHIuc2luX2FkZHIuc19hZGRyID0gaW5ldF9hZGRyKGhvc3RuYW1lKTsKCQl9IGVsc2UgewoJCQlocCA9IGdldGhvc3RieW5hbWUobW91bnRob3N0KTsKCQkJaWYgKGhwID09IE5VTEwpIHsKCQkJCWJiX2hlcnJvcl9tc2coIiVzIiwgbW91bnRob3N0KTsKCQkJCWdvdG8gZmFpbDsKCQkJfSBlbHNlIHsKCQkJCWlmIChocC0+aF9sZW5ndGggPiBzaXplb2Yoc3RydWN0IGluX2FkZHIpKSB7CgkJCQkJYmJfZXJyb3JfbXNnKCJnb3QgYmFkIGhwLT5oX2xlbmd0aD8iKTsKCQkJCQlocC0+aF9sZW5ndGggPSBzaXplb2Yoc3RydWN0IGluX2FkZHIpOwoJCQkJfQoJCQkJbW91bnRfc2VydmVyX2FkZHIuc2luX2ZhbWlseSA9IEFGX0lORVQ7CgkJCQltZW1jcHkoJm1vdW50X3NlcnZlcl9hZGRyLnNpbl9hZGRyLAoJCQkJCQlocC0+aF9hZGRyLCBocC0+aF9sZW5ndGgpOwoJCQl9CgkJfQoJfQoKCS8qCgkgKiBUaGUgZm9sbG93aW5nIGxvb3AgaW1wbGVtZW50cyB0aGUgbW91bnQgcmV0cmllcy4gV2hlbiB0aGUgbW91bnQKCSAqIHRpbWVzIG91dCwgYW5kIHRoZSAiYmciIG9wdGlvbiBpcyBzZXQsIHdlIGJhY2tncm91bmQgb3Vyc2VsZgoJICogYW5kIGNvbnRpbnVlIHRyeWluZy4KCSAqCgkgKiBUaGUgY2FzZSB3aGVyZSB0aGUgbW91bnQgcG9pbnQgaXMgbm90IHByZXNlbnQgYW5kIHRoZSAiYmciCgkgKiBvcHRpb24gaXMgc2V0LCBpcyB0cmVhdGVkIGFzIGEgdGltZW91dC4gVGhpcyBpcyBkb25lIHRvCgkgKiBzdXBwb3J0IG5lc3RlZCBtb3VudHMuCgkgKgoJICogVGhlICJyZXRyeSIgY291bnQgc3BlY2lmaWVkIGJ5IHRoZSB1c2VyIGlzIHRoZSBudW1iZXIgb2YKCSAqIG1pbnV0ZXMgdG8gcmV0cnkgYmVmb3JlIGdpdmluZyB1cC4KCSAqLwoJewoJCXN0cnVjdCB0aW1ldmFsIHRvdGFsX3RpbWVvdXQ7CgkJc3RydWN0IHRpbWV2YWwgcmV0cnlfdGltZW91dDsKCQlzdHJ1Y3QgcG1hcCogcG1fbW50OwoJCXRpbWVfdCB0OwoJCXRpbWVfdCBwcmV2dDsKCQl0aW1lX3QgdGltZW91dDsKCgkJcmV0cnlfdGltZW91dC50dl9zZWMgPSAzOwoJCXJldHJ5X3RpbWVvdXQudHZfdXNlYyA9IDA7CgkJdG90YWxfdGltZW91dC50dl9zZWMgPSAyMDsKCQl0b3RhbF90aW1lb3V0LnR2X3VzZWMgPSAwOwoJCXRpbWVvdXQgPSB0aW1lKE5VTEwpICsgNjAgKiByZXRyeTsKCQlwcmV2dCA9IDA7CgkJdCA9IDMwOwpyZXRyeToKCQkvKiBiZSBjYXJlZnVsIG5vdCB0byB1c2UgdG9vIG1hbnkgQ1BVIGN5Y2xlcyAqLwoJCWlmICh0IC0gcHJldnQgPCAzMCkKCQkJc2xlZXAoMzApOwoKCQlwbV9tbnQgPSBnZXRfbW91bnRwb3J0KCZtb3VudF9zZXJ2ZXJfYWRkciwKCQkJCW1vdW50cHJvZywKCQkJCW1vdW50dmVycywKCQkJCXByb3RvLAoJCQkJbW91bnRwb3J0KTsKCQluZnN2ZXJzID0gKHBtX21udC0+cG1fdmVycyA8IDIpID8gMiA6IHBtX21udC0+cG1fdmVyczsKCgkJLyogY29udGFjdCB0aGUgbW91bnQgZGFlbW9uIHZpYSBUQ1AgKi8KCQltb3VudF9zZXJ2ZXJfYWRkci5zaW5fcG9ydCA9IGh0b25zKHBtX21udC0+cG1fcG9ydCk7CgkJbXNvY2sgPSBSUENfQU5ZU09DSzsKCgkJc3dpdGNoIChwbV9tbnQtPnBtX3Byb3QpIHsKCQljYXNlIElQUFJPVE9fVURQOgoJCQltY2xpZW50ID0gY2xudHVkcF9jcmVhdGUoJm1vdW50X3NlcnZlcl9hZGRyLAoJCQkJCQkgcG1fbW50LT5wbV9wcm9nLAoJCQkJCQkgcG1fbW50LT5wbV92ZXJzLAoJCQkJCQkgcmV0cnlfdGltZW91dCwKCQkJCQkJICZtc29jayk7CgkJCWlmIChtY2xpZW50KQoJCQkJYnJlYWs7CgkJCW1vdW50X3NlcnZlcl9hZGRyLnNpbl9wb3J0ID0gaHRvbnMocG1fbW50LT5wbV9wb3J0KTsKCQkJbXNvY2sgPSBSUENfQU5ZU09DSzsKCQljYXNlIElQUFJPVE9fVENQOgoJCQltY2xpZW50ID0gY2xudHRjcF9jcmVhdGUoJm1vdW50X3NlcnZlcl9hZGRyLAoJCQkJCQkgcG1fbW50LT5wbV9wcm9nLAoJCQkJCQkgcG1fbW50LT5wbV92ZXJzLAoJCQkJCQkgJm1zb2NrLCAwLCAwKTsKCQkJYnJlYWs7CgkJZGVmYXVsdDoKCQkJbWNsaWVudCA9IDA7CgkJfQoJCWlmICghbWNsaWVudCkgewoJCQlpZiAoIWRhZW1vbml6ZWQgJiYgcHJldnQgPT0gMCkKCQkJCWVycm9yX21zZ19ycGMoY2xudF9zcGNyZWF0ZWVycm9yKCIgIikpOwoJCX0gZWxzZSB7CgkJCWVudW0gY2xudF9zdGF0IGNsbnRfc3RhdDsKCQkJLyogdHJ5IHRvIG1vdW50IGhvc3RuYW1lOnBhdGhuYW1lICovCgkJCW1jbGllbnQtPmNsX2F1dGggPSBhdXRodW5peF9jcmVhdGVfZGVmYXVsdCgpOwoKCQkJLyogbWFrZSBwb2ludGVycyBpbiB4ZHJfbW91bnRyZXMzIE5VTEwgc28KCQkJICogdGhhdCB4ZHJfYXJyYXkgYWxsb2NhdGVzIG1lbW9yeSBmb3IgdXMKCQkJICovCgkJCW1lbXNldCgmc3RhdHVzLCAwLCBzaXplb2Yoc3RhdHVzKSk7CgoJCQlpZiAocG1fbW50LT5wbV92ZXJzID09IDMpCgkJCQljbG50X3N0YXQgPSBjbG50X2NhbGwobWNsaWVudCwgTU9VTlRQUk9DM19NTlQsCgkJCQkJICAgICAgKHhkcnByb2NfdCkgeGRyX2RpcnBhdGgsCgkJCQkJICAgICAgKGNhZGRyX3QpICZwYXRobmFtZSwKCQkJCQkgICAgICAoeGRycHJvY190KSB4ZHJfbW91bnRyZXMzLAoJCQkJCSAgICAgIChjYWRkcl90KSAmc3RhdHVzLAoJCQkJCSAgICAgIHRvdGFsX3RpbWVvdXQpOwoJCQllbHNlCgkJCQljbG50X3N0YXQgPSBjbG50X2NhbGwobWNsaWVudCwgTU9VTlRQUk9DX01OVCwKCQkJCQkgICAgICAoeGRycHJvY190KSB4ZHJfZGlycGF0aCwKCQkJCQkgICAgICAoY2FkZHJfdCkgJnBhdGhuYW1lLAoJCQkJCSAgICAgICh4ZHJwcm9jX3QpIHhkcl9maHN0YXR1cywKCQkJCQkgICAgICAoY2FkZHJfdCkgJnN0YXR1cywKCQkJCQkgICAgICB0b3RhbF90aW1lb3V0KTsKCgkJCWlmIChjbG50X3N0YXQgPT0gUlBDX1NVQ0NFU1MpCgkJCQlnb3RvIHByZXBhcmVfa2VybmVsX2RhdGE7IC8qIHdlJ3JlIGRvbmUgKi8KCQkJaWYgKGVycm5vICE9IEVDT05OUkVGVVNFRCkgewoJCQkJZXJyb3JfbXNnX3JwYyhjbG50X3NwZXJyb3IobWNsaWVudCwgIiAiKSk7CgkJCQlnb3RvIGZhaWw7CS8qIGRvbid0IHJldHJ5ICovCgkJCX0KCQkJLyogQ29ubmVjdGlvbiByZWZ1c2VkICovCgkJCWlmICghZGFlbW9uaXplZCAmJiBwcmV2dCA9PSAwKSAvKiBwcmludCBqdXN0IG9uY2UgKi8KCQkJCWVycm9yX21zZ19ycGMoY2xudF9zcGVycm9yKG1jbGllbnQsICIgIikpOwoJCQlhdXRoX2Rlc3Ryb3kobWNsaWVudC0+Y2xfYXV0aCk7CgkJCWNsbnRfZGVzdHJveShtY2xpZW50KTsKCQkJbWNsaWVudCA9IDA7CgkJCWNsb3NlKG1zb2NrKTsKCQl9CgoJCS8qIFRpbWVvdXQuIFdlIGFyZSBnb2luZyB0byByZXRyeS4uLiBtYXliZSAqLwoKCQlpZiAoIWJnKQoJCQlnb3RvIGZhaWw7CgkJaWYgKCFkYWVtb25pemVkKSB7CgkJCWRhZW1vbml6ZWQgPSBkYWVtb25pemUoKTsKCQkJaWYgKGRhZW1vbml6ZWQgPD0gMCkgeyAvKiBwYXJlbnQgb3IgZXJyb3IgKi8KCQkJCXJldHZhbCA9IC1kYWVtb25pemVkOwoJCQkJZ290byByZXQ7CgkJCX0KCQl9CgkJcHJldnQgPSB0OwoJCXQgPSB0aW1lKE5VTEwpOwoJCWlmICh0ID49IHRpbWVvdXQpCgkJCS8qIFRPRE8gZXJyb3IgbWVzc2FnZSAqLwoJCQlnb3RvIGZhaWw7CgoJCWdvdG8gcmV0cnk7Cgl9CgpwcmVwYXJlX2tlcm5lbF9kYXRhOgoKCWlmIChuZnN2ZXJzID09IDIpIHsKCQlpZiAoc3RhdHVzLm5mc3YyLmZoc19zdGF0dXMgIT0gMCkgewoJCQliYl9lcnJvcl9tc2coIiVzOiVzIGZhaWxlZCwgcmVhc29uIGdpdmVuIGJ5IHNlcnZlcjogJXMiLAoJCQkJaG9zdG5hbWUsIHBhdGhuYW1lLAoJCQkJbmZzX3N0cmVycm9yKHN0YXR1cy5uZnN2Mi5maHNfc3RhdHVzKSk7CgkJCWdvdG8gZmFpbDsKCQl9CgkJbWVtY3B5KGRhdGEucm9vdC5kYXRhLAoJCQkJKGNoYXIgKikgc3RhdHVzLm5mc3YyLmZoc3RhdHVzX3UuZmhzX2ZoYW5kbGUsCgkJCQlORlNfRkhTSVpFKTsKCQlkYXRhLnJvb3Quc2l6ZSA9IE5GU19GSFNJWkU7CgkJbWVtY3B5KGRhdGEub2xkX3Jvb3QuZGF0YSwKCQkJCShjaGFyICopIHN0YXR1cy5uZnN2Mi5maHN0YXR1c191LmZoc19maGFuZGxlLAoJCQkJTkZTX0ZIU0laRSk7Cgl9IGVsc2UgewoJCWZoYW5kbGUzICpteV9maGFuZGxlOwoJCWlmIChzdGF0dXMubmZzdjMuZmhzX3N0YXR1cyAhPSAwKSB7CgkJCWJiX2Vycm9yX21zZygiJXM6JXMgZmFpbGVkLCByZWFzb24gZ2l2ZW4gYnkgc2VydmVyOiAlcyIsCgkJCQlob3N0bmFtZSwgcGF0aG5hbWUsCgkJCQluZnNfc3RyZXJyb3Ioc3RhdHVzLm5mc3YzLmZoc19zdGF0dXMpKTsKCQkJZ290byBmYWlsOwoJCX0KCQlteV9maGFuZGxlID0gJnN0YXR1cy5uZnN2My5tb3VudHJlczNfdS5tb3VudGluZm8uZmhhbmRsZTsKCQltZW1zZXQoZGF0YS5vbGRfcm9vdC5kYXRhLCAwLCBORlNfRkhTSVpFKTsKCQltZW1zZXQoJmRhdGEucm9vdCwgMCwgc2l6ZW9mKGRhdGEucm9vdCkpOwoJCWRhdGEucm9vdC5zaXplID0gbXlfZmhhbmRsZS0+ZmhhbmRsZTNfbGVuOwoJCW1lbWNweShkYXRhLnJvb3QuZGF0YSwKCQkJCShjaGFyICopIG15X2ZoYW5kbGUtPmZoYW5kbGUzX3ZhbCwKCQkJCW15X2ZoYW5kbGUtPmZoYW5kbGUzX2xlbik7CgoJCWRhdGEuZmxhZ3MgfD0gTkZTX01PVU5UX1ZFUjM7Cgl9CgoJLyogY3JlYXRlIG5mcyBzb2NrZXQgZm9yIGtlcm5lbCAqLwoKCWlmICh0Y3ApIHsKCQlpZiAobmZzX21vdW50X3ZlcnNpb24gPCAzKSB7CgkJCWJiX2Vycm9yX21zZygiTkZTIG92ZXIgVENQIGlzIG5vdCBzdXBwb3J0ZWQiKTsKCQkJZ290byBmYWlsOwoJCX0KCQlmc29jayA9IHNvY2tldChBRl9JTkVULCBTT0NLX1NUUkVBTSwgSVBQUk9UT19UQ1ApOwoJfSBlbHNlCgkJZnNvY2sgPSBzb2NrZXQoQUZfSU5FVCwgU09DS19ER1JBTSwgSVBQUk9UT19VRFApOwoJaWYgKGZzb2NrIDwgMCkgewoJCWJiX3BlcnJvcl9tc2coIm5mcyBzb2NrZXQiKTsKCQlnb3RvIGZhaWw7Cgl9CglpZiAoYmluZHJlc3Zwb3J0KGZzb2NrLCAwKSA8IDApIHsKCQliYl9wZXJyb3JfbXNnKCJuZnMgYmluZHJlc3Zwb3J0Iik7CgkJZ290byBmYWlsOwoJfQoJaWYgKHBvcnQgPT0gMCkgewoJCXNlcnZlcl9hZGRyLnNpbl9wb3J0ID0gUE1BUFBPUlQ7CgkJcG9ydCA9IHBtYXBfZ2V0cG9ydCgmc2VydmVyX2FkZHIsIG5mc3Byb2csIG5mc3ZlcnMsCgkJCQkJdGNwID8gSVBQUk9UT19UQ1AgOiBJUFBST1RPX1VEUCk7CgkJaWYgKHBvcnQgPT0gMCkKCQkJcG9ydCA9IE5GU19QT1JUOwoJfQoJc2VydmVyX2FkZHIuc2luX3BvcnQgPSBodG9ucyhwb3J0KTsKCgkvKiBwcmVwYXJlIGRhdGEgc3RydWN0dXJlIGZvciBrZXJuZWwgKi8KCglkYXRhLmZkID0gZnNvY2s7CgltZW1jcHkoKGNoYXIgKikgJmRhdGEuYWRkciwgKGNoYXIgKikgJnNlcnZlcl9hZGRyLCBzaXplb2YoZGF0YS5hZGRyKSk7CglzdHJuY3B5KGRhdGEuaG9zdG5hbWUsIGhvc3RuYW1lLCBzaXplb2YoZGF0YS5ob3N0bmFtZSkpOwoKCS8qIGNsZWFuIHVwICovCgoJYXV0aF9kZXN0cm95KG1jbGllbnQtPmNsX2F1dGgpOwoJY2xudF9kZXN0cm95KG1jbGllbnQpOwoJY2xvc2UobXNvY2spOwoKCWlmIChiZykgewoJCS8qIFdlIG11c3Qgd2FpdCB1bnRpbCBtb3VudCBkaXJlY3RvcnkgaXMgYXZhaWxhYmxlICovCgkJc3RydWN0IHN0YXQgc3RhdGJ1ZjsKCQlpbnQgZGVsYXkgPSAxOwoJCXdoaWxlIChzdGF0KG1wLT5tbnRfZGlyLCAmc3RhdGJ1ZikgPT0gLTEpIHsKCQkJaWYgKCFkYWVtb25pemVkKSB7CgkJCQlkYWVtb25pemVkID0gZGFlbW9uaXplKCk7CgkJCQlpZiAoZGFlbW9uaXplZCA8PSAwKSB7IC8qIHBhcmVudCBvciBlcnJvciAqLwoJCQkJCXJldHZhbCA9IC1kYWVtb25pemVkOwoJCQkJCWdvdG8gcmV0OwoJCQkJfQoJCQl9CgkJCXNsZWVwKGRlbGF5KTsJLyogMSwgMiwgNCwgOCwgMTYsIDMwLCAuLi4gKi8KCQkJZGVsYXkgKj0gMjsKCQkJaWYgKGRlbGF5ID4gMzApCgkJCQlkZWxheSA9IDMwOwoJCX0KCX0KCmRvX21vdW50OiAvKiBwZXJmb3JtIGFjdHVhbCBtb3VudCAqLwoKCW1wLT5tbnRfdHlwZSA9IChjaGFyKikibmZzIjsKCXJldHZhbCA9IG1vdW50X2l0X25vdyhtcCwgdmZzZmxhZ3MsIChjaGFyKikmZGF0YSk7Cglnb3RvIHJldDsKCmZhaWw6CS8qIGFib3J0ICovCgoJaWYgKG1zb2NrICE9IC0xKSB7CgkJaWYgKG1jbGllbnQpIHsKCQkJYXV0aF9kZXN0cm95KG1jbGllbnQtPmNsX2F1dGgpOwoJCQljbG50X2Rlc3Ryb3kobWNsaWVudCk7CgkJfQoJCWNsb3NlKG1zb2NrKTsKCX0KCWlmIChmc29jayAhPSAtMSkKCQljbG9zZShmc29jayk7CgpyZXQ6CglmcmVlKGhvc3RuYW1lKTsKCWZyZWUobW91bnRob3N0KTsKCWZyZWUoZmlsdGVyb3B0cyk7CglyZXR1cm4gcmV0dmFsOwp9CgojZWxzZSAvKiAhRU5BQkxFX0ZFQVRVUkVfTU9VTlRfTkZTICovCgovKiBOZXZlciBjYWxsZWQuIENhbGwgc2hvdWxkIGJlIG9wdGltaXplZCBvdXQuICovCmludCBuZnNtb3VudChzdHJ1Y3QgbW50ZW50ICptcCwgaW50IHZmc2ZsYWdzLCBjaGFyICpmaWx0ZXJvcHRzKTsKCiNlbmRpZiAvKiAhRU5BQkxFX0ZFQVRVUkVfTU9VTlRfTkZTICovCgovLyBNb3VudCBvbmUgZGlyZWN0b3J5LiAgSGFuZGxlcyBDSUZTLCBORlMsIGxvb3BiYWNrLCBhdXRvYmluZCwgYW5kIGZpbGVzeXN0ZW0KLy8gdHlwZSBkZXRlY3Rpb24uICBSZXR1cm5zIDAgZm9yIHN1Y2Nlc3MsIG5vbnplcm8gZm9yIGZhaWx1cmUuCi8vIE5COiBtcC0+eHh4IGZpZWxkcyBtYXkgYmUgdHJhc2hlZCBvbiBleGl0CnN0YXRpYyBpbnQgc2luZ2xlbW91bnQoc3RydWN0IG1udGVudCAqbXAsIGludCBpZ25vcmVfYnVzeSkKewoJaW50IHJjID0gLTEsIHZmc2ZsYWdzOwoJY2hhciAqbG9vcEZpbGUgPSAwLCAqZmlsdGVyb3B0cyA9IDA7CglsbGlzdF90ICpmbCA9IDA7CglzdHJ1Y3Qgc3RhdCBzdDsKCgl2ZnNmbGFncyA9IHBhcnNlX21vdW50X29wdGlvbnMobXAtPm1udF9vcHRzLCAmZmlsdGVyb3B0cyk7CgoJLy8gVHJlYXQgZnN0eXBlICJhdXRvIiBhcyB1bnNwZWNpZmllZC4KCglpZiAobXAtPm1udF90eXBlICYmIHN0cmNtcChtcC0+bW50X3R5cGUsImF1dG8iKSA9PSAwKQoJCW1wLT5tbnRfdHlwZSA9IDA7CgoJLy8gTWlnaHQgdGhpcyBiZSBhbiBDSUZTIGZpbGVzeXN0ZW0/CgoJaWYgKEVOQUJMRV9GRUFUVVJFX01PVU5UX0NJRlMKCSAmJiAoIW1wLT5tbnRfdHlwZSB8fCBzdHJjbXAobXAtPm1udF90eXBlLCJjaWZzIikgPT0gMCkKCSAmJiAobXAtPm1udF9mc25hbWVbMF09PScvJyB8fCBtcC0+bW50X2ZzbmFtZVswXT09J1xcJykKCSAmJiBtcC0+bW50X2ZzbmFtZVswXT09bXAtPm1udF9mc25hbWVbMV0KCSkgewoJCWxlbl9hbmRfc29ja2FkZHIgKmxzYTsKCQljaGFyICppcCwgKmRvdHRlZDsKCQljaGFyICpzOwoKCQlyYyA9IDE7CgkJLy8gUmVwbGFjZSAnLycgd2l0aCAnXCcgYW5kIHZlcmlmeSB0aGF0IHVuYyBwb2ludHMgdG8gIi8vc2VydmVyL3NoYXJlIi4KCgkJZm9yIChzID0gbXAtPm1udF9mc25hbWU7ICpzOyArK3MpCgkJCWlmICgqcyA9PSAnLycpICpzID0gJ1xcJzsKCgkJLy8gZ2V0IHNlcnZlciBJUAoKCQlzID0gc3RycmNocihtcC0+bW50X2ZzbmFtZSwgJ1xcJyk7CgkJaWYgKHMgPD0gbXAtPm1udF9mc25hbWUrMSkgZ290byByZXBvcnRfZXJyb3I7CgkJKnMgPSAnXDAnOwoJCWxzYSA9IGhvc3Qyc29ja2FkZHIobXAtPm1udF9mc25hbWUrMiwgMCk7CgkJKnMgPSAnXFwnOwoJCWlmICghbHNhKSBnb3RvIHJlcG9ydF9lcnJvcjsKCgkJLy8gaW5zZXJ0IGlwPS4uLiBvcHRpb24gaW50byBzdHJpbmcgZmxhZ3MuCgoJCWRvdHRlZCA9IHhtYWxsb2Nfc29ja2FkZHIyZG90dGVkX25vcG9ydCgmbHNhLT5zYSwgbHNhLT5sZW4pOwoJCWlwID0geGFzcHJpbnRmKCJpcD0lcyIsIGRvdHRlZCk7CgkJcGFyc2VfbW91bnRfb3B0aW9ucyhpcCwgJmZpbHRlcm9wdHMpOwoKCQkvLyBjb21wb3NlIG5ldyB1bmMgJ1xcc2VydmVyLWlwXHNoYXJlJwoJCS8vIChzID0+IHNsYXNoIGFmdGVyIGhvc3RuYW1lKQoKCQltcC0+bW50X2ZzbmFtZSA9IHhhc3ByaW50ZigiXFxcXCVzJXMiLCBkb3R0ZWQsIHMpOwoKCQkvLyBsb2NrIGlzIHJlcXVpcmVkCgkJdmZzZmxhZ3MgfD0gTVNfTUFORExPQ0s7CgoJCW1wLT5tbnRfdHlwZSA9IChjaGFyKikiY2lmcyI7CgkJcmMgPSBtb3VudF9pdF9ub3cobXAsIHZmc2ZsYWdzLCBmaWx0ZXJvcHRzKTsKCQlpZiAoRU5BQkxFX0ZFQVRVUkVfQ0xFQU5fVVApIHsKCQkJZnJlZShtcC0+bW50X2ZzbmFtZSk7CgkJCWZyZWUoaXApOwoJCQlmcmVlKGRvdHRlZCk7CgkJCWZyZWUobHNhKTsKCQl9CgkJZ290byByZXBvcnRfZXJyb3I7Cgl9CgoJLy8gTWlnaHQgdGhpcyBiZSBhbiBORlMgZmlsZXN5c3RlbT8KCglpZiAoRU5BQkxFX0ZFQVRVUkVfTU9VTlRfTkZTCgkgJiYgKCFtcC0+bW50X3R5cGUgfHwgIXN0cmNtcChtcC0+bW50X3R5cGUsIm5mcyIpKQoJICYmIHN0cmNocihtcC0+bW50X2ZzbmFtZSwgJzonKSAhPSBOVUxMCgkpIHsKCQlyYyA9IG5mc21vdW50KG1wLCB2ZnNmbGFncywgZmlsdGVyb3B0cyk7CgkJZ290byByZXBvcnRfZXJyb3I7Cgl9CgoJLy8gTG9vayBhdCB0aGUgZmlsZS4gIChOb3QgZm91bmQgaXNuJ3QgYSBmYWlsdXJlIGZvciByZW1vdW50LCBvciBmb3IKCS8vIGEgc3ludGhldGljIGZpbGVzeXN0ZW0gbGlrZSBwcm9jIG9yIHN5c2ZzLikKCglpZiAoIWxzdGF0KG1wLT5tbnRfZnNuYW1lLCAmc3QpCgkgJiYgISh2ZnNmbGFncyAmIChNU19SRU1PVU5UIHwgTVNfQklORCB8IE1TX01PVkUpKQoJKSB7CgkJLy8gRG8gd2UgbmVlZCB0byBhbGxvY2F0ZSBhIGxvb3BiYWNrIGRldmljZSBmb3IgaXQ/CgoJCWlmIChFTkFCTEVfRkVBVFVSRV9NT1VOVF9MT09QICYmIFNfSVNSRUcoc3Quc3RfbW9kZSkpIHsKCQkJbG9vcEZpbGUgPSBiYl9zaW1wbGlmeV9wYXRoKG1wLT5tbnRfZnNuYW1lKTsKCQkJbXAtPm1udF9mc25hbWUgPSAwOwoJCQlzd2l0Y2ggKHNldF9sb29wKCYobXAtPm1udF9mc25hbWUpLCBsb29wRmlsZSwgMCkpIHsKCQkJY2FzZSAwOgoJCQljYXNlIDE6CgkJCQlicmVhazsKCQkJZGVmYXVsdDoKCQkJCWJiX2Vycm9yX21zZyggZXJybm8gPT0gRVBFUk0gfHwgZXJybm8gPT0gRUFDQ0VTCgkJCQkJPyBiYl9tc2dfcGVybV9kZW5pZWRfYXJlX3lvdV9yb290CgkJCQkJOiAiY2Fubm90IHNldHVwIGxvb3AgZGV2aWNlIik7CgkJCQlyZXR1cm4gZXJybm87CgkJCX0KCgkJLy8gQXV0b2RldGVjdCBiaW5kIG1vdW50cwoKCQl9IGVsc2UgaWYgKFNfSVNESVIoc3Quc3RfbW9kZSkgJiYgIW1wLT5tbnRfdHlwZSkKCQkJdmZzZmxhZ3MgfD0gTVNfQklORDsKCX0KCgkvKiBJZiB3ZSBrbm93IHRoZSBmc3R5cGUgKG9yIGRvbid0IG5lZWQgdG8pLCBqdW1wIHN0cmFpZ2h0CgkgKiB0byB0aGUgYWN0dWFsIG1vdW50LiAqLwoKCWlmIChtcC0+bW50X3R5cGUgfHwgKHZmc2ZsYWdzICYgKE1TX1JFTU9VTlQgfCBNU19CSU5EIHwgTVNfTU9WRSkpKQoJCXJjID0gbW91bnRfaXRfbm93KG1wLCB2ZnNmbGFncywgZmlsdGVyb3B0cyk7CgllbHNlIHsKCQkvLyBMb29wIHRocm91Z2ggZmlsZXN5c3RlbSB0eXBlcyB1bnRpbCBtb3VudCBzdWNjZWVkcwoJCS8vIG9yIHdlIHJ1biBvdXQKCgkJLyogSW5pdGlhbGl6ZSBsaXN0IG9mIGJsb2NrIGJhY2tlZCBmaWxlc3lzdGVtcy4gIFRoaXMgaGFzIHRvIGJlCgkJICogZG9uZSBoZXJlIHNvIHRoYXQgZHVyaW5nICJtb3VudCAtYSIsIG1vdW50cyBhZnRlciAvcHJvYyBzaG93cyB1cAoJCSAqIGNhbiBhdXRvZGV0ZWN0LiAqLwoKCQlpZiAoIWZzbGlzdCkgewoJCQlmc2xpc3QgPSBnZXRfYmxvY2tfYmFja2VkX2ZpbGVzeXN0ZW1zKCk7CgkJCWlmIChFTkFCTEVfRkVBVFVSRV9DTEVBTl9VUCAmJiBmc2xpc3QpCgkJCQlhdGV4aXQoZGVsZXRlX2Jsb2NrX2JhY2tlZF9maWxlc3lzdGVtcyk7CgkJfQoKCQlmb3IgKGZsID0gZnNsaXN0OyBmbDsgZmwgPSBmbC0+bGluaykgewoJCQltcC0+bW50X3R5cGUgPSBmbC0+ZGF0YTsKCQkJcmMgPSBtb3VudF9pdF9ub3cobXAsIHZmc2ZsYWdzLCBmaWx0ZXJvcHRzKTsKCQkJaWYgKCFyYykgYnJlYWs7CgkJfQoJfQoKCS8vIElmIG1vdW50IGZhaWxlZCwgY2xlYW4gdXAgbG9vcCBmaWxlIChpZiBhbnkpLgoKCWlmIChFTkFCTEVfRkVBVFVSRV9NT1VOVF9MT09QICYmIHJjICYmIGxvb3BGaWxlKSB7CgkJZGVsX2xvb3AobXAtPm1udF9mc25hbWUpOwoJCWlmIChFTkFCTEVfRkVBVFVSRV9DTEVBTl9VUCkgewoJCQlmcmVlKGxvb3BGaWxlKTsKCQkJZnJlZShtcC0+bW50X2ZzbmFtZSk7CgkJfQoJfQoKIHJlcG9ydF9lcnJvcjoKCWlmIChFTkFCTEVfRkVBVFVSRV9DTEVBTl9VUCkKCQlmcmVlKGZpbHRlcm9wdHMpOwoKCWlmIChyYyAmJiBlcnJubyA9PSBFQlVTWSAmJiBpZ25vcmVfYnVzeSkgcmMgPSAwOwoJaWYgKHJjIDwgMCkKCQkvKiBwZXJyb3IgaGVyZSBzb21ldGltZXMgc2F5cyAibW91bnRpbmcgLi4uIG9uIC4uLiBmYWlsZWQ6IFN1Y2Nlc3MiICovCgkJYmJfZXJyb3JfbXNnKCJtb3VudGluZyAlcyBvbiAlcyBmYWlsZWQiLCBtcC0+bW50X2ZzbmFtZSwgbXAtPm1udF9kaXIpOwoKCXJldHVybiByYzsKfQoKLy8gUGFyc2Ugb3B0aW9ucywgaWYgbmVjZXNzYXJ5IHBhcnNlIGZzdGFiL210YWIsIGFuZCBjYWxsIHNpbmdsZW1vdW50IGZvcgovLyBlYWNoIGRpcmVjdG9yeSB0byBiZSBtb3VudGVkLgoKY29uc3QgY2hhciBtdXN0X2JlX3Jvb3RbXSA9ICJ5b3UgbXVzdCBiZSByb290IjsKCmludCBtb3VudF9tYWluKGludCBhcmdjLCBjaGFyICoqYXJndik7CmludCBtb3VudF9tYWluKGludCBhcmdjLCBjaGFyICoqYXJndikKewoJZW51bSB7IE9QVF9BTEwgPSAweDEwIH07CgoJY2hhciAqY21kb3B0cyA9IHhzdHJkdXAoIiIpLCAqZnN0eXBlPTAsICpzdG9yYWdlX3BhdGg9MDsKCWNoYXIgKm9wdF9vOwoJY29uc3QgY2hhciAqZnN0YWJuYW1lOwoJRklMRSAqZnN0YWI7CglpbnQgaSwgaiwgcmMgPSAwOwoJdW5zaWduZWQgb3B0OwoJc3RydWN0IG1udGVudCBtdHBhaXJbMl0sICptdGN1ciA9IG10cGFpcjsKCVNLSVBfREVTS1RPUChjb25zdCBpbnQgbm9ucm9vdCA9IDA7KQoJVVNFX0RFU0tUT1AoIGludCBub25yb290ID0gKGdldHVpZCgpICE9IDApOykKCgkvKiBwYXJzZSBsb25nIG9wdGlvbnMsIGxpa2UgLS1iaW5kIGFuZCAtLW1vdmUuICBOb3RlIHRoYXQgLW8gb3B0aW9uCgkgKiBhbmQgLS1vcHRpb24gYXJlIHN5bm9ueW1vdXMuICBZZXMsIHRoaXMgbWVhbnMgLS1yZW1vdW50LHJ3IHdvcmtzLiAqLwoKCWZvciAoaSA9IGogPSAwOyBpIDwgYXJnYzsgaSsrKSB7CgkJaWYgKGFyZ3ZbaV1bMF0gPT0gJy0nICYmIGFyZ3ZbaV1bMV0gPT0gJy0nKSB7CgkJCWFwcGVuZF9tb3VudF9vcHRpb25zKCZjbWRvcHRzLCBhcmd2W2ldKzIpOwoJCX0gZWxzZSBhcmd2W2orK10gPSBhcmd2W2ldOwoJfQoJYXJndltqXSA9IDA7CglhcmdjID0gajsKCgkvLyBQYXJzZSByZW1haW5pbmcgb3B0aW9ucwoKCW9wdCA9IGdldG9wdDMyKGFyZ2MsIGFyZ3YsICJvOnQ6cndhbmZ2cyIsICZvcHRfbywgJmZzdHlwZSk7CglpZiAob3B0ICYgMHgxKSBhcHBlbmRfbW91bnRfb3B0aW9ucygmY21kb3B0cywgb3B0X28pOyAvLyAtbwoJLy9pZiAob3B0ICYgMHgyKSAvLyAtdAoJaWYgKG9wdCAmIDB4NCkgYXBwZW5kX21vdW50X29wdGlvbnMoJmNtZG9wdHMsICJybyIpOyAvLyAtcgoJaWYgKG9wdCAmIDB4OCkgYXBwZW5kX21vdW50X29wdGlvbnMoJmNtZG9wdHMsICJydyIpOyAvLyAtdwoJLy9pZiAob3B0ICYgMHgxMCkgLy8gLWEKCWlmIChvcHQgJiAweDIwKSBVU0VfRkVBVFVSRV9NVEFCX1NVUFBPUlQodXNlTXRhYiA9IDApOyAvLyAtbgoJaWYgKG9wdCAmIDB4NDApIFVTRV9GRUFUVVJFX01UQUJfU1VQUE9SVChmYWtlSXQgPSAxKTsgLy8gLWYKCS8vaWYgKG9wdCAmIDB4ODApIC8vIC12OiB2ZXJib3NlIChpZ25vcmUpCgkvL2lmIChvcHQgJiAweDEwMCkgLy8gLXM6IHNsb3BweSAoaWdub3JlKQoJYXJndiArPSBvcHRpbmQ7CglhcmdjIC09IG9wdGluZDsKCgkvLyBUaHJlZSBvciBtb3JlIG5vbi1vcHRpb24gYXJndW1lbnRzPyAgRGllIHdpdGggYSB1c2FnZSBtZXNzYWdlLgoKCWlmIChhcmdjID4gMikgYmJfc2hvd191c2FnZSgpOwoKCS8vIElmIHdlIGhhdmUgbm8gYXJndW1lbnRzLCBzaG93IGN1cnJlbnRseSBtb3VudGVkIGZpbGVzeXN0ZW1zCgoJaWYgKCFhcmdjKSB7CgkJaWYgKCEob3B0ICYgT1BUX0FMTCkpIHsKCQkJRklMRSAqbW91bnRUYWJsZSA9IHNldG1udGVudChiYl9wYXRoX210YWJfZmlsZSwgInIiKTsKCgkJCWlmICghbW91bnRUYWJsZSkgYmJfZXJyb3JfbXNnX2FuZF9kaWUoIm5vICVzIiwgYmJfcGF0aF9tdGFiX2ZpbGUpOwoKCQkJd2hpbGUgKGdldG1udGVudF9yKG1vdW50VGFibGUsIG10cGFpciwgYmJfY29tbW9uX2J1ZnNpejEsCgkJCQkJCQkJc2l6ZW9mKGJiX2NvbW1vbl9idWZzaXoxKSkpCgkJCXsKCQkJCS8vIERvbid0IHNob3cgcm9vdGZzLiBGSVhNRTogd2h5Pz8KCQkJCS8vIHV0aWwtbGludXggMi4xMmEgaGFwcGlseSBzaG93cyByb290ZnMuLi4KCQkJCS8vaWYgKCFzdHJjbXAobXRwYWlyLT5tbnRfZnNuYW1lLCAicm9vdGZzIikpIGNvbnRpbnVlOwoKCQkJCWlmICghZnN0eXBlIHx8ICFzdHJjbXAobXRwYWlyLT5tbnRfdHlwZSwgZnN0eXBlKSkKCQkJCQlwcmludGYoIiVzIG9uICVzIHR5cGUgJXMgKCVzKVxuIiwgbXRwYWlyLT5tbnRfZnNuYW1lLAoJCQkJCQkJbXRwYWlyLT5tbnRfZGlyLCBtdHBhaXItPm1udF90eXBlLAoJCQkJCQkJbXRwYWlyLT5tbnRfb3B0cyk7CgkJCX0KCQkJaWYgKEVOQUJMRV9GRUFUVVJFX0NMRUFOX1VQKSBlbmRtbnRlbnQobW91bnRUYWJsZSk7CgkJCXJldHVybiBFWElUX1NVQ0NFU1M7CgkJfQoJfSBlbHNlIHN0b3JhZ2VfcGF0aCA9IGJiX3NpbXBsaWZ5X3BhdGgoYXJndlswXSk7CgoJLy8gV2hlbiB3ZSBoYXZlIHR3byBhcmd1bWVudHMsIHRoZSBzZWNvbmQgaXMgdGhlIGRpcmVjdG9yeSBhbmQgd2UgY2FuCgkvLyBza2lwIGxvb2tpbmcgYXQgZnN0YWIgZW50aXJlbHkuICBXZSBjYW4gYWx3YXlzIGFic3BhdGgoKSB0aGUgZGlyZWN0b3J5CgkvLyBhcmd1bWVudCB3aGVuIHdlIGdldCBpdC4KCglpZiAoYXJnYyA9PSAyKSB7CgkJaWYgKG5vbnJvb3QpCgkJCWJiX2Vycm9yX21zZ19hbmRfZGllKG11c3RfYmVfcm9vdCk7CgkJbXRwYWlyLT5tbnRfZnNuYW1lID0gYXJndlswXTsKCQltdHBhaXItPm1udF9kaXIgPSBhcmd2WzFdOwoJCW10cGFpci0+bW50X3R5cGUgPSBmc3R5cGU7CgkJbXRwYWlyLT5tbnRfb3B0cyA9IGNtZG9wdHM7CgkJcmMgPSBzaW5nbGVtb3VudChtdHBhaXIsIDApOwoJCWdvdG8gY2xlYW5fdXA7Cgl9CgoJaSA9IHBhcnNlX21vdW50X29wdGlvbnMoY21kb3B0cywgMCk7CglpZiAobm9ucm9vdCAmJiAoaSAmIH5NU19TSUxFTlQpKSAvLyBOb24tcm9vdCB1c2VycyBjYW5ub3Qgc3BlY2lmeSBmbGFncwoJCWJiX2Vycm9yX21zZ19hbmRfZGllKG11c3RfYmVfcm9vdCk7CgoJLy8gSWYgd2UgaGF2ZSBhIHNoYXJlZCBzdWJ0cmVlIGZsYWcsIGRvbid0IHdvcnJ5IGFib3V0IGZzdGFiIG9yIG10YWIuCgoJaWYgKEVOQUJMRV9GRUFUVVJFX01PVU5UX0ZMQUdTCgkgJiYgKGkgJiAoTVNfU0hBUkVEIHwgTVNfUFJJVkFURSB8IE1TX1NMQVZFIHwgTVNfVU5CSU5EQUJMRSkpCgkpIHsKCQlyYyA9IG1vdW50KCIiLCBhcmd2WzBdLCAiIiwgaSwgIiIpOwoJCWlmIChyYykgYmJfcGVycm9yX21zZ19hbmRfZGllKCIlcyIsIGFyZ3ZbMF0pOwoJCWdvdG8gY2xlYW5fdXA7Cgl9CgoJLy8gT3BlbiBlaXRoZXIgZnN0YWIgb3IgbXRhYgoKCWZzdGFibmFtZSA9ICIvZXRjL2ZzdGFiIjsKCWlmIChpICYgTVNfUkVNT1VOVCkgewoJCWZzdGFibmFtZSA9IGJiX3BhdGhfbXRhYl9maWxlOwoJfQoJZnN0YWIgPSBzZXRtbnRlbnQoZnN0YWJuYW1lLCAiciIpOwoJaWYgKCFmc3RhYikKCQliYl9wZXJyb3JfbXNnX2FuZF9kaWUoImNhbm5vdCByZWFkICVzIiwgZnN0YWJuYW1lKTsKCgkvLyBMb29wIHRocm91Z2ggZW50cmllcyB1bnRpbCB3ZSBmaW5kIHdoYXQgd2UncmUgbG9va2luZyBmb3IuCgoJbWVtc2V0KG10cGFpciwgMCwgc2l6ZW9mKG10cGFpcikpOwoJZm9yICg7OykgewoJCXN0cnVjdCBtbnRlbnQgKm10bmV4dCA9IChtdGN1cj09bXRwYWlyID8gbXRwYWlyKzEgOiBtdHBhaXIpOwoKCQkvLyBHZXQgbmV4dCBmc3RhYiBlbnRyeQoKCQlpZiAoIWdldG1udGVudF9yKGZzdGFiLCBtdGN1ciwgYmJfY29tbW9uX2J1ZnNpejEKCQkJCQkrIChtdGN1cj09bXRwYWlyID8gc2l6ZW9mKGJiX2NvbW1vbl9idWZzaXoxKS8yIDogMCksCgkJCQlzaXplb2YoYmJfY29tbW9uX2J1ZnNpejEpLzIpKQoJCXsKCQkJLy8gV2VyZSB3ZSBsb29raW5nIGZvciBzb21ldGhpbmcgc3BlY2lmaWM/CgoJCQlpZiAoYXJnYykgewoKCQkJCS8vIElmIHdlIGRpZG4ndCBmaW5kIGFueXRoaW5nLCBjb21wbGFpbi4KCgkJCQlpZiAoIW10bmV4dC0+bW50X2ZzbmFtZSkKCQkJCQliYl9lcnJvcl9tc2dfYW5kX2RpZSgiY2FuJ3QgZmluZCAlcyBpbiAlcyIsCgkJCQkJCWFyZ3ZbMF0sIGZzdGFibmFtZSk7CgoJCQkJbXRjdXIgPSBtdG5leHQ7CgkJCQlpZiAobm9ucm9vdCkgewoJCQkJCS8vIGZzdGFiIG11c3QgaGF2ZSAidXNlcnMiIG9yICJ1c2VyIgoJCQkJCWlmICghKHBhcnNlX21vdW50X29wdGlvbnMobXRjdXItPm1udF9vcHRzLCAwKSAmIE1PVU5UX1VTRVJTKSkKCQkJCQkJYmJfZXJyb3JfbXNnX2FuZF9kaWUobXVzdF9iZV9yb290KTsKCQkJCX0KCgkJCQkvLyBNb3VudCB0aGUgbGFzdCB0aGluZyB3ZSBmb3VuZC4KCgkJCQltdGN1ci0+bW50X29wdHMgPSB4c3RyZHVwKG10Y3VyLT5tbnRfb3B0cyk7CgkJCQlhcHBlbmRfbW91bnRfb3B0aW9ucygmKG10Y3VyLT5tbnRfb3B0cyksIGNtZG9wdHMpOwoJCQkJcmMgPSBzaW5nbGVtb3VudChtdGN1ciwgMCk7CgkJCQlmcmVlKG10Y3VyLT5tbnRfb3B0cyk7CgkJCX0KCQkJZ290byBjbGVhbl91cDsKCQl9CgoJCS8qIElmIHdlJ3JlIHRyeWluZyB0byBtb3VudCBzb21ldGhpbmcgc3BlY2lmaWMgYW5kIHRoaXMgaXNuJ3QgaXQsCgkJICogc2tpcCBpdC4gIE5vdGUgd2UgbXVzdCBtYXRjaCBib3RoIHRoZSBleGFjdCB0ZXh0IGluIGZzdGFiIChhbGEKCQkgKiAicHJvYyIpIG9yIGEgZnVsbCBwYXRoIGZyb20gcm9vdCAqLwoKCQlpZiAoYXJnYykgewoKCQkJLy8gSXMgdGhpcyB3aGF0IHdlJ3JlIGxvb2tpbmcgZm9yPwoKCQkJaWYgKHN0cmNtcChhcmd2WzBdLCBtdGN1ci0+bW50X2ZzbmFtZSkgJiYKCQkJICAgc3RyY21wKHN0b3JhZ2VfcGF0aCwgbXRjdXItPm1udF9mc25hbWUpICYmCgkJCSAgIHN0cmNtcChhcmd2WzBdLCBtdGN1ci0+bW50X2RpcikgJiYKCQkJICAgc3RyY21wKHN0b3JhZ2VfcGF0aCwgbXRjdXItPm1udF9kaXIpKSBjb250aW51ZTsKCgkJCS8vIFJlbWVtYmVyIHRoaXMgZW50cnkuICBTb21ldGhpbmcgbGF0ZXIgbWF5IGhhdmUgb3Zlcm1vdW50ZWQKCQkJLy8gaXQsIGFuZCB3ZSB3YW50IHRoZSBfbGFzdF8gbWF0Y2guCgoJCQltdGN1ciA9IG10bmV4dDsKCgkJLy8gSWYgd2UncmUgbW91bnRpbmcgYWxsLgoKCQl9IGVsc2UgewoJCQkvLyBEbyB3ZSBuZWVkIHRvIG1hdGNoIGEgZmlsZXN5c3RlbSB0eXBlPwoJCQlpZiAoZnN0eXBlICYmIG1hdGNoX2ZzdHlwZShtdGN1ciwgZnN0eXBlKSkgY29udGludWU7CgoJCQkvLyBTa2lwIG5vYXV0byBhbmQgc3dhcCBhbnl3YXkuCgoJCQlpZiAocGFyc2VfbW91bnRfb3B0aW9ucyhtdGN1ci0+bW50X29wdHMsIDApCgkJCQkmIChNT1VOVF9OT0FVVE8gfCBNT1VOVF9TV0FQKSkgY29udGludWU7CgoJCQkvLyBObywgbW91bnQgLWEgd29uJ3QgbW91bnQgYW55dGhpbmcsCgkJCS8vIGV2ZW4gdXNlciBtb3VudHMsIGZvciBtZXJlIGh1bWFucy4KCgkJCWlmIChub25yb290KQoJCQkJYmJfZXJyb3JfbXNnX2FuZF9kaWUobXVzdF9iZV9yb290KTsKCgkJCS8vIE1vdW50IHRoaXMgdGhpbmcuCgoJCQkvLyBORlMgbW91bnRzIHdhbnQgdGhpcyB0byBiZSB4cmVhbGxvYy1hYmxlCgkJCW10Y3VyLT5tbnRfb3B0cyA9IHhzdHJkdXAobXRjdXItPm1udF9vcHRzKTsKCQkJaWYgKHNpbmdsZW1vdW50KG10Y3VyLCAxKSkgewoJCQkJLyogQ291bnQgbnVtYmVyIG9mIGZhaWxlZCBtb3VudHMgKi8KCQkJCXJjKys7CgkJCX0KCQkJZnJlZShtdGN1ci0+bW50X29wdHMpOwoJCX0KCX0KCWlmIChFTkFCTEVfRkVBVFVSRV9DTEVBTl9VUCkgZW5kbW50ZW50KGZzdGFiKTsKCmNsZWFuX3VwOgoKCWlmIChFTkFCTEVfRkVBVFVSRV9DTEVBTl9VUCkgewoJCWZyZWUoc3RvcmFnZV9wYXRoKTsKCQlmcmVlKGNtZG9wdHMpOwoJfQoKCXJldHVybiByYzsKfQo=