LyoKICogKEMpIENvcHlyaWdodCAyMDAyLCAyMDAzCiAqIERhbmllbCBFbmdzdHL2bSwgT21pY3JvbiBDZXRpIEFCLCBkYW5pZWxAb21pY3Jvbi5zZQogKgogKiAoQykgQ29weXJpZ2h0IDIwMDIKICogU3lzZ28gUmVhbC1UaW1lIFNvbHV0aW9ucywgR21iSCA8d3d3LmVsaW5vcy5jb20+CiAqIEFsZXggWnVlcGtlIDxhenVAc3lzZ28uZGU+CiAqCiAqIFNlZSBmaWxlIENSRURJVFMgZm9yIGxpc3Qgb2YgcGVvcGxlIHdobyBjb250cmlidXRlZCB0byB0aGlzCiAqIHByb2plY3QuCiAqCiAqIFRoaXMgcHJvZ3JhbSBpcyBmcmVlIHNvZnR3YXJlOyB5b3UgY2FuIHJlZGlzdHJpYnV0ZSBpdCBhbmQvb3IKICogbW9kaWZ5IGl0IHVuZGVyIHRoZSB0ZXJtcyBvZiB0aGUgR05VIEdlbmVyYWwgUHVibGljIExpY2Vuc2UgYXMKICogcHVibGlzaGVkIGJ5IHRoZSBGcmVlIFNvZnR3YXJlIEZvdW5kYXRpb247IGVpdGhlciB2ZXJzaW9uIDIgb2YKICogdGhlIExpY2Vuc2UsIG9yIChhdCB5b3VyIG9wdGlvbikgYW55IGxhdGVyIHZlcnNpb24uCiAqCiAqIFRoaXMgcHJvZ3JhbSBpcyBkaXN0cmlidXRlZCBpbiB0aGUgaG9wZSB0aGF0IGl0IHdpbGwgYmUgdXNlZnVsLAogKiBidXQgV0lUSE9VVCBBTlkgV0FSUkFOVFk7IHdpdGhvdXQgZXZlbiB0aGUgaW1wbGllZCB3YXJyYW50eSBvZgogKiBNRVJDSEFOVEFCSUxJVFkgb3IgRklUTkVTUyBGT1IgQSBQQVJUSUNVTEFSIFBVUlBPU0UuICBTZWUgdGhlCiAqIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlIGZvciBtb3JlIGRldGFpbHMuCiAqCiAqIFlvdSBzaG91bGQgaGF2ZSByZWNlaXZlZCBhIGNvcHkgb2YgdGhlIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlCiAqIGFsb25nIHdpdGggdGhpcyBwcm9ncmFtOyBpZiBub3QsIHdyaXRlIHRvIHRoZSBGcmVlIFNvZnR3YXJlCiAqIEZvdW5kYXRpb24sIEluYy4sIDU5IFRlbXBsZSBQbGFjZSwgU3VpdGUgMzMwLCBCb3N0b24sCiAqIE1BIDAyMTExLTEzMDcgVVNBCiAqLwoKI2luY2x1ZGUgPGNvbW1vbi5oPgojaW5jbHVkZSA8YXNtL2lvLmg+CiNpbmNsdWRlIDxwY2kuaD4KI2luY2x1ZGUgPGFzbS9pYy9zYzUyMC5oPgoKI2RlZmluZSBQUk9CRV9CVUZGRVJfU0laRSAxMDI0CnN0YXRpYyB1bnNpZ25lZCBjaGFyIGJ1ZmZlcltQUk9CRV9CVUZGRVJfU0laRV07CgojZGVmaW5lIFNDNTIwX01BWF9GTEFTSF9CQU5LUyAgMQojZGVmaW5lIFNDNTIwX0ZMQVNIX0JBTkswX0JBU0UgMHgzODAwMDAwMCAgLyogQk9PVENTICovCiNkZWZpbmUgU0M1MjBfRkxBU0hfQkFOS1NJWkUgICAweDgwMDAwMDAKCiNkZWZpbmUgQTI5TFY2NDFESF9TSVpFICAgICAgICAweDgwMDAwMAojZGVmaW5lIEEyOUxWNjQxREhfU0VDVE9SUyAgICAgMTI4CgojZGVmaW5lIEEyOUxWNjQxTUhfU0laRSAgICAgICAgMHg4MDAwMDAKI2RlZmluZSBBMjlMVjY0MU1IX1NFQ1RPUlMgICAgIDEyOAoKI2RlZmluZSBJMjhGMzIwSjNBX1NJWkUgICAgICAgIDB4NDAwMDAwCiNkZWZpbmUgSTI4RjMyMEozQV9TRUNUT1JTICAgICAzMgoKI2RlZmluZSBJMjhGNjQwSjNBX1NJWkUgICAgICAgIDB4ODAwMDAwCiNkZWZpbmUgSTI4RjY0MEozQV9TRUNUT1JTICAgICA2NAoKI2RlZmluZSBJMjhGMTI4SjNBX1NJWkUgICAgICAgIDB4MTAwMDAwMAojZGVmaW5lIEkyOEYxMjhKM0FfU0VDVE9SUyAgICAgMTI4CgpmbGFzaF9pbmZvX3QgICAgZmxhc2hfaW5mb1tTQzUyMF9NQVhfRkxBU0hfQkFOS1NdOwoKI2RlZmluZSBSRUFEWSAxCiNkZWZpbmUgRVJSICAgMgojZGVmaW5lIFRNTyAgIDQKCi8qLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KICovCgpzdGF0aWMgdTMyIF9wcm9iZV9mbGFzaCh1MzIgYWRkciwgdTMyIGJ3LCBpbnQgaWwpCnsKCXUzMiByZXN1bHQ9MDsKCgkvKiBGaXJzdCBkbyBhbiB1bmxvY2sgY3ljbGUgZm9yIHRoZSBiZW5lZml0IG9mCgkgKiBkZXZpY2VzIHRoYXQgbmVlZCBpdCAqLwoKCXN3aXRjaCAoYncpIHsKCgljYXNlIDE6CgkJKih2b2xhdGlsZSB1OCopKGFkZHIrMHg1NTU1KSA9IDB4YWE7CgkJKih2b2xhdGlsZSB1OCopKGFkZHIrMHgyYWFhKSA9IDB4NTU7CgkJKih2b2xhdGlsZSB1OCopKGFkZHIrMHg1NTU1KSA9IDB4OTA7CgoJCS8qIFJlYWQgdmVuZG9yICovCgkJcmVzdWx0ID0gKih2b2xhdGlsZSB1OCopYWRkcjsKCQlyZXN1bHQgPDw9IDE2OwoKCQkvKiBSZWFkIGRldmljZSAqLwoJCXJlc3VsdCB8PSAqKHZvbGF0aWxlIHU4KikoYWRkcisyKTsKCgkJLyogUmV0dXJuIGRldmljZSB0byBkYXRhIG1vZGUgKi8KCQkqKHZvbGF0aWxlIHU4KilhZGRyID0gMHhmZjsKCQkqKHZvbGF0aWxlIHU4KikoYWRkcisweDU1NTUpLCAweGYwOwoJCWJyZWFrOwoKCWNhc2UgMjoKCQkqKHZvbGF0aWxlIHUxNiopKGFkZHIrMHhhYWFhKSA9IDB4YWFhYTsKCQkqKHZvbGF0aWxlIHUxNiopKGFkZHIrMHg1NTU0KSA9IDB4NTU1NTsKCgkJLyogSXNzdWUgaWRlbnRpZmljYXRpb24gY29tbWFuZCAqLwoJCWlmIChpbCA9PSAyKSB7CgkJCSoodm9sYXRpbGUgdTE2KikoYWRkcisweGFhYWEpID0gMHg5MDkwOwoKCQkJLyogUmVhZCB2ZW5kb3IgKi8KCQkJcmVzdWx0ID0gKih2b2xhdGlsZSB1OCopYWRkcjsKCQkJcmVzdWx0IDw8PSAxNjsKCgkJCS8qIFJlYWQgZGV2aWNlICovCgkJCXJlc3VsdCB8PSAqKHZvbGF0aWxlIHU4KikoYWRkcisyKTsKCgkJCS8qIFJldHVybiBkZXZpY2UgdG8gZGF0YSBtb2RlICovCgkJCSoodm9sYXRpbGUgdTE2KilhZGRyID0gIDB4ZmZmZjsKCQkJKih2b2xhdGlsZSB1MTYqKShhZGRyKzB4YWFhYSksIDB4ZjBmMDsKCgkJfSBlbHNlIHsKCQkJKih2b2xhdGlsZSB1OCopKGFkZHIrMHhhYWFhKSA9IDB4OTA7CgkJCS8qIFJlYWQgdmVuZG9yICovCgkJCXJlc3VsdCA9ICoodm9sYXRpbGUgdTE2KilhZGRyOwoJCQlyZXN1bHQgPDw9IDE2OwoKCQkJLyogUmVhZCBkZXZpY2UgKi8KCQkJcmVzdWx0IHw9ICoodm9sYXRpbGUgdTE2KikoYWRkcisyKTsKCgkJCS8qIFJldHVybiBkZXZpY2UgdG8gZGF0YSBtb2RlICovCgkJCSoodm9sYXRpbGUgdTgqKWFkZHIgPSAweGZmOwoJCQkqKHZvbGF0aWxlIHU4KikoYWRkcisweGFhYWEpLCAweGYwOwoJCX0KCgkJYnJlYWs7CgoJIGNhc2UgNDoKCQkqKHZvbGF0aWxlIHUzMiopKGFkZHIrMHg1NTU0KSA9IDB4YWFhYWFhYWE7CgkJKih2b2xhdGlsZSB1MzIqKShhZGRyKzB4YWFhOCkgPSAweDU1NTU1NTU1OwoKCQlzd2l0Y2ggKGlsKSB7CgkJY2FzZSAxOgoJCQkvKiBJc3N1ZSBpZGVudGlmaWNhdGlvbiBjb21tYW5kICovCgkJCSoodm9sYXRpbGUgdTgqKShhZGRyKzB4NTU1NCkgPSAweDkwOwoKCQkJLyogUmVhZCB2ZW5kb3IgKi8KCQkJcmVzdWx0ID0gKih2b2xhdGlsZSB1MTYqKWFkZHI7CgkJCXJlc3VsdCA8PD0gMTY7CgoJCQkvKiBSZWFkIGRldmljZSAqLwoJCQlyZXN1bHQgfD0gKih2b2xhdGlsZSB1MTYqKShhZGRyKzQpOwoKCQkJLyogUmV0dXJuIGRldmljZSB0byBkYXRhIG1vZGUgKi8KCQkJKih2b2xhdGlsZSB1OCopYWRkciA9ICAweGZmOwoJCQkqKHZvbGF0aWxlIHU4KikoYWRkcisweDU1NTQpLCAweGYwOwoJCQlicmVhazsKCgkJY2FzZSAyOgoJCQkvKiBJc3N1ZSBpZGVudGlmaWNhdGlvbiBjb21tYW5kICovCgkJCSoodm9sYXRpbGUgdTMyKikoYWRkciArIDB4NTU1NCkgPSAweDAwOTAwMDkwOwoKCQkJLyogUmVhZCB2ZW5kb3IgKi8KCQkJcmVzdWx0ID0gKih2b2xhdGlsZSB1MTYqKWFkZHI7CgkJCXJlc3VsdCA8PD0gMTY7CgoJCQkvKiBSZWFkIGRldmljZSAqLwoJCQlyZXN1bHQgfD0gKih2b2xhdGlsZSB1MTYqKShhZGRyKzQpOwoKCQkJLyogUmV0dXJuIGRldmljZSB0byBkYXRhIG1vZGUgKi8KCQkJKih2b2xhdGlsZSB1MzIqKWFkZHIgPSAgMHgwMGZmMDBmZjsKCQkJKih2b2xhdGlsZSB1MzIqKShhZGRyKzB4NTU1NCksIDB4MDBmMDAwZjA7CgkJCWJyZWFrOwoKCQljYXNlIDQ6CgkJCS8qIElzc3VlIGlkZW50aWZpY2F0aW9uIGNvbW1hbmQgKi8KCQkJKih2b2xhdGlsZSB1MzIqKShhZGRyKzB4NTU1NCkgPSAweDkwOTA5MDkwOwoKCQkJLyogUmVhZCB2ZW5kb3IgKi8KCQkJcmVzdWx0ID0gKih2b2xhdGlsZSB1OCopYWRkcjsKCQkJcmVzdWx0IDw8PSAxNjsKCgkJCS8qIFJlYWQgZGV2aWNlICovCgkJCXJlc3VsdCB8PSAqKHZvbGF0aWxlIHU4KikoYWRkcis0KTsKCgkJCS8qIFJldHVybiBkZXZpY2UgdG8gZGF0YSBtb2RlICovCgkJCSoodm9sYXRpbGUgdTMyKilhZGRyID0gIDB4ZmZmZmZmZmY7CgkJCSoodm9sYXRpbGUgdTMyKikoYWRkcisweDU1NTQpLCAweGYwZjBmMGYwOwoJCQlicmVhazsKCQl9CgkJYnJlYWs7Cgl9CgoJcmV0dXJuIHJlc3VsdDsKfQoKZXh0ZXJuIGludCBfcHJvYmVfZmxhc2hfZW5kOwphc20gKCJfcHJvYmVfZmxhc2hfZW5kOlxuIgogICAgICIubG9uZyAwXG4iKTsKCnN0YXRpYyBpbnQgaWRlbnRpZnlfZmxhc2godW5zaWduZWQgYWRkcmVzcywgaW50IHdpZHRoKQp7CglpbnQgaXM7CglpbnQgZGV2aWNlOwoJaW50IHZlbmRvcjsKCWludCBzaXplOwoJdW5zaWduZWQgcmVzOwoKCXUzMiAoKl9wcm9iZV9mbGFzaF9wdHIpKHUzMiBhLCB1MzIgYncsIGludCBpbCk7CgoJc2l6ZSA9ICh1bnNpZ25lZCkmX3Byb2JlX2ZsYXNoX2VuZCAtICh1bnNpZ25lZClfcHJvYmVfZmxhc2g7CgoJaWYgKHNpemUgPiBQUk9CRV9CVUZGRVJfU0laRSkgewoJCXByaW50ZigiX3Byb2JlX2ZsYXNoKCkgcm91dGluZSB0b28gbGFyZ2UgKCVkKSAlcCAtICVwXG4iLAoJCSAgICAgICBzaXplLCAmX3Byb2JlX2ZsYXNoX2VuZCwgX3Byb2JlX2ZsYXNoKTsKCQlyZXR1cm4gMDsKCX0KCgltZW1jcHkoYnVmZmVyLCBfcHJvYmVfZmxhc2gsIHNpemUpOwoJX3Byb2JlX2ZsYXNoX3B0ciA9ICh2b2lkKilidWZmZXI7CgoJaXMgPSBkaXNhYmxlX2ludGVycnVwdHMoKTsKCXJlcyA9IF9wcm9iZV9mbGFzaF9wdHIoYWRkcmVzcywgd2lkdGgsIDEpOwoJaWYgKGlzKSB7CgkJZW5hYmxlX2ludGVycnVwdHMoKTsKCX0KCgl2ZW5kb3IgPSByZXMgPj4gMTY7CglkZXZpY2UgPSByZXMgJiAweGZmZmY7CgoJcmV0dXJuIHJlczsKfQoKdWxvbmcgZmxhc2hfaW5pdCh2b2lkKQp7CglpbnQgaSwgajsKCXVsb25nIHNpemUgPSAwOwoKCWZvciAoaSA9IDA7IGkgPCBTQzUyMF9NQVhfRkxBU0hfQkFOS1M7IGkrKykgewoJCXVuc2lnbmVkIGlkOwoJCXVsb25nIGZsYXNoYmFzZSA9IDA7CgkJaW50IHNlY3RzaXplID0gMDsKCgkJbWVtc2V0KGZsYXNoX2luZm9baV0ucHJvdGVjdCwgMCwgQ09ORklHX1NZU19NQVhfRkxBU0hfU0VDVCk7CgkJc3dpdGNoIChpKSB7CgkJY2FzZSAwOgoJCQlmbGFzaGJhc2UgPSBTQzUyMF9GTEFTSF9CQU5LMF9CQVNFOwoJCQlicmVhazsKCQlkZWZhdWx0OgoJCQlwYW5pYygiY29uZmlndXJlZCB0b28gbWFueSBmbGFzaCBiYW5rcyFcbiIpOwoJCX0KCgkJaWQgPSBpZGVudGlmeV9mbGFzaChmbGFzaGJhc2UsIDIpOwoJCXN3aXRjaCAoaWQpIHsKCQljYXNlIDB4MDAwMTIyZDc6CgkJCS8qIDI5TFY2NDFESCAqLwoJCQlmbGFzaF9pbmZvW2ldLmZsYXNoX2lkID0KCQkJCShBTURfTUFOVUZBQ1QgJiBGTEFTSF9WRU5ETUFTSykgfAoJCQkJKEFNRF9JRF9MVjY0MFUgJiBGTEFTSF9UWVBFTUFTSyk7CgoJCQlmbGFzaF9pbmZvW2ldLnNpemUgPSBBMjlMVjY0MURIX1NJWkU7CgkJCWZsYXNoX2luZm9baV0uc2VjdG9yX2NvdW50ID0gQTI5TFY2NDFESF9TRUNUT1JTOwoJCQlzZWN0c2l6ZSA9IEEyOUxWNjQxREhfU0laRS9BMjlMVjY0MURIX1NFQ1RPUlM7CgkJCXByaW50ZigiQmFuayAlZDogQU1EIDI5TFY2NDFESFxuIiwgaSk7CgkJCWJyZWFrOwoKCQljYXNlIDB4MDAwMTIyN0U6CgkJCS8qIDI5TFY2NDFNSCAqLwoJCQlmbGFzaF9pbmZvW2ldLmZsYXNoX2lkID0KCQkJCShBTURfTUFOVUZBQ1QgJiBGTEFTSF9WRU5ETUFTSykgfAoJCQkJKEFNRF9JRF9ETDY0MCAmIEZMQVNIX1RZUEVNQVNLKTsKCgkJCWZsYXNoX2luZm9baV0uc2l6ZSA9IEEyOUxWNjQxTUhfU0laRTsKCQkJZmxhc2hfaW5mb1tpXS5zZWN0b3JfY291bnQgPSBBMjlMVjY0MU1IX1NFQ1RPUlM7CgkJCXNlY3RzaXplID0gQTI5TFY2NDFNSF9TSVpFL0EyOUxWNjQxTUhfU0VDVE9SUzsKCQkJcHJpbnRmKCJCYW5rICVkOiBBTUQgMjlMVjY0MU1IXG4iLCBpKTsKCQkJYnJlYWs7CgoJCWNhc2UgMHgwMDg5MDAxNjoKCQkJLyogMjhGMzIwSjNBICovCgkJCWZsYXNoX2luZm9baV0uZmxhc2hfaWQgPQoJCQkJKElOVEVMX01BTlVGQUNUICYgRkxBU0hfVkVORE1BU0spIHwKCQkJCShJTlRFTF9JRF8yOEYzMjBKM0EgJiBGTEFTSF9UWVBFTUFTSyk7CgoJCQlmbGFzaF9pbmZvW2ldLnNpemUgPSBJMjhGMzIwSjNBX1NJWkU7CgkJCWZsYXNoX2luZm9baV0uc2VjdG9yX2NvdW50ID0gSTI4RjMyMEozQV9TRUNUT1JTOwoJCQlzZWN0c2l6ZSA9IEkyOEYzMjBKM0FfU0laRS9JMjhGMzIwSjNBX1NFQ1RPUlM7CgkJCXByaW50ZigiQmFuayAlZDogSW50ZWwgMjhGMzIwSjNBXG4iLCBpKTsKCQkJYnJlYWs7CgoJCWNhc2UgMHgwMDg5MDAxNzoKCQkJLyogMjhGNjQwSjNBICovCgkJCWZsYXNoX2luZm9baV0uZmxhc2hfaWQgPQoJCQkJKElOVEVMX01BTlVGQUNUICYgRkxBU0hfVkVORE1BU0spIHwKCQkJCShJTlRFTF9JRF8yOEY2NDBKM0EgJiBGTEFTSF9UWVBFTUFTSyk7CgoJCQlmbGFzaF9pbmZvW2ldLnNpemUgPSBJMjhGNjQwSjNBX1NJWkU7CgkJCWZsYXNoX2luZm9baV0uc2VjdG9yX2NvdW50ID0gSTI4RjY0MEozQV9TRUNUT1JTOwoJCQlzZWN0c2l6ZSA9IEkyOEY2NDBKM0FfU0laRS9JMjhGNjQwSjNBX1NFQ1RPUlM7CgkJCXByaW50ZigiQmFuayAlZDogSW50ZWwgMjhGNjQwSjNBXG4iLCBpKTsKCQkJYnJlYWs7CgoJCWNhc2UgMHgwMDg5MDAxODoKCQkJLyogMjhGMTI4SjNBICovCgkJCWZsYXNoX2luZm9baV0uZmxhc2hfaWQgPQoJCQkJKElOVEVMX01BTlVGQUNUICYgRkxBU0hfVkVORE1BU0spIHwKCQkJCShJTlRFTF9JRF8yOEYxMjhKM0EgJiBGTEFTSF9UWVBFTUFTSyk7CgoJCQlmbGFzaF9pbmZvW2ldLnNpemUgPSBJMjhGMTI4SjNBX1NJWkU7CgkJCWZsYXNoX2luZm9baV0uc2VjdG9yX2NvdW50ID0gSTI4RjEyOEozQV9TRUNUT1JTOwoJCQlzZWN0c2l6ZSA9IEkyOEYxMjhKM0FfU0laRS9JMjhGMTI4SjNBX1NFQ1RPUlM7CgkJCXByaW50ZigiQmFuayAlZDogSW50ZWwgMjhGMTI4SjNBXG4iLCBpKTsKCQkJYnJlYWs7CgoJCWRlZmF1bHQ6CgkJCXByaW50ZigiQmFuayAlZCBoYXZlIHVua25vd24gZmxhc2ggJTA4eFxuIiwgaSwgaWQpOwoJCQlmbGFzaF9pbmZvW2ldLmZsYXNoX2lkID0gRkxBU0hfVU5LTk9XTjsKCQkJY29udGludWU7CgkJfQoKCQlmb3IgKGogPSAwOyBqIDwgZmxhc2hfaW5mb1tpXS5zZWN0b3JfY291bnQ7IGorKykgewoJCQlmbGFzaF9pbmZvW2ldLnN0YXJ0W2pdID0gZmxhc2hiYXNlICsgaiAqIHNlY3RzaXplOwoJCX0KCQlzaXplICs9IGZsYXNoX2luZm9baV0uc2l6ZTsKCgkJZmxhc2hfcHJvdGVjdChGTEFHX1BST1RFQ1RfQ0xFQVIsCgkJCSAgICAgIGZsYXNoX2luZm9baV0uc3RhcnRbMF0sCgkJCSAgICAgICBmbGFzaF9pbmZvW2ldLnN0YXJ0WzBdICsgZmxhc2hfaW5mb1tpXS5zaXplIC0gMSwKCQkJICAgICAgJmZsYXNoX2luZm9baV0pOwoJfQoKCS8qCgkgKiBQcm90ZWN0IG1vbml0b3IgYW5kIGVudmlyb25tZW50IHNlY3RvcnMKCSAqLwoJZmxhc2hfcHJvdGVjdChGTEFHX1BST1RFQ1RfU0VULAoJCSAgICAgIGkzODZib290X3N0YXJ0LAoJCSAgICAgIGkzODZib290X2VuZCwKCQkgICAgICAmZmxhc2hfaW5mb1swXSk7CiNpZmRlZiBDT05GSUdfRU5WX0FERFIKCWZsYXNoX3Byb3RlY3QoRkxBR19QUk9URUNUX1NFVCwKCQkgICAgICBDT05GSUdfRU5WX0FERFIsCgkJICAgICAgQ09ORklHX0VOVl9BRERSICsgQ09ORklHX0VOVl9TSVpFIC0gMSwKCQkgICAgICAmZmxhc2hfaW5mb1swXSk7CiNlbmRpZgoJcmV0dXJuIHNpemU7Cn0KCi8qLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KICovCnZvaWQgZmxhc2hfcHJpbnRfaW5mbyhmbGFzaF9pbmZvX3QgKmluZm8pCnsKCWludCBpOwoKCXN3aXRjaCAoaW5mby0+Zmxhc2hfaWQgJiBGTEFTSF9WRU5ETUFTSykgewoJY2FzZSAoSU5URUxfTUFOVUZBQ1QgJiBGTEFTSF9WRU5ETUFTSyk6CgkJcHJpbnRmKCJJTlRFTDogIik7CgkJc3dpdGNoIChpbmZvLT5mbGFzaF9pZCAmIEZMQVNIX1RZUEVNQVNLKSB7CgkJY2FzZSAoSU5URUxfSURfMjhGMzIwSjNBICYgRkxBU0hfVFlQRU1BU0spOgoJCQlwcmludGYoIjF4IEkyOEYzMjBKM0EgKDMyTWJpdClcbiIpOwoJCQlicmVhazsKCQljYXNlIChJTlRFTF9JRF8yOEY2NDBKM0EgJiBGTEFTSF9UWVBFTUFTSyk6CgkJCXByaW50ZigiMXggSTI4RjY0MEozQSAoNjRNYml0KVxuIik7CgkJCWJyZWFrOwoJCWNhc2UgKElOVEVMX0lEXzI4RjEyOEozQSAmIEZMQVNIX1RZUEVNQVNLKToKCQkJcHJpbnRmKCIxeCBJMjhGMTI4SjNBICgxMjhNYml0KVxuIik7CgkJCWJyZWFrOwoJCWRlZmF1bHQ6CgkJCXByaW50ZigiVW5rbm93biBDaGlwIFR5cGVcbiIpOwoJCQlnb3RvIGRvbmU7CgkJCWJyZWFrOwoJCX0KCgkJYnJlYWs7CgoJY2FzZSAoQU1EX01BTlVGQUNUICYgRkxBU0hfVkVORE1BU0spOgoJCXByaW50ZigiQU1EOiAgICIpOwoJCXN3aXRjaCAoaW5mby0+Zmxhc2hfaWQgJiBGTEFTSF9UWVBFTUFTSykgewoJCWNhc2UgKEFNRF9JRF9MVjY0MFUgJiBGTEFTSF9UWVBFTUFTSyk6CgkJCXByaW50ZigiMXggQU1EMjlMVjY0MURIICg2NE1iaXQpXG4iKTsKCQkJYnJlYWs7CgkJY2FzZSAoQU1EX0lEX0RMNjQwICYgRkxBU0hfVFlQRU1BU0spOgoJCQlwcmludGYoIjF4IEFNRDI5TFY2NDFNSCAoNjRNYml0KVxuIik7CgkJCWJyZWFrOwoJCWRlZmF1bHQ6CgkJCXByaW50ZigiVW5rbm93biBDaGlwIFR5cGVcbiIpOwoJCQlnb3RvIGRvbmU7CgkJCWJyZWFrOwoJCX0KCgkJYnJlYWs7CglkZWZhdWx0OgoJCXByaW50ZigiVW5rbm93biBWZW5kb3IgIik7CgkJYnJlYWs7Cgl9CgoJcHJpbnRmKCIgIFNpemU6ICVsZCBNQiBpbiAlZCBTZWN0b3JzXG4iLAoJICAgICAgIGluZm8tPnNpemUgPj4gMjAsIGluZm8tPnNlY3Rvcl9jb3VudCk7CgoJcHJpbnRmKCIgIFNlY3RvciBTdGFydCBBZGRyZXNzZXM6Iik7Cglmb3IgKGkgPSAwOyBpIDwgaW5mby0+c2VjdG9yX2NvdW50OyBpKyspIHsKCQlpZiAoKGkgJSA1KSA9PSAwKSB7CgkJCXByaW50ZiAoIlxuICAgIik7CgkJfQoJCXByaW50ZiAoIiAlMDhsWCVzIiwgaW5mby0+c3RhcnRbaV0sCgkJCWluZm8tPnByb3RlY3RbaV0gPyAiIChSTykiIDogIiAgICAgIik7Cgl9CglwcmludGYgKCJcbiIpOwoKZG9uZToKCXJldHVybjsKfQoKLyotLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQogKi8KCnN0YXRpYyB1MzIgX2FtZF9lcmFzZV9mbGFzaCh1MzIgYWRkciwgdTMyIHNlY3RvcikKewoJdW5zaWduZWQgZWxhcHNlZDsKCgkvKiBJc3N1ZSBlcmFzZSAqLwoJKih2b2xhdGlsZSB1MTYqKShhZGRyICsgMHhhYWFhKSA9IDB4MDBBQTsKCSoodm9sYXRpbGUgdTE2KikoYWRkciArIDB4NTU1NCkgPSAweDAwNTU7CgkqKHZvbGF0aWxlIHUxNiopKGFkZHIgKyAweGFhYWEpID0gMHgwMDgwOwoJLyogQW5kIG9uZSB1bmxvY2sgKi8KCSoodm9sYXRpbGUgdTE2KikoYWRkciArIDB4YWFhYSkgPSAweDAwQUE7CgkqKHZvbGF0aWxlIHUxNiopKGFkZHIgKyAweDU1NTQpID0gMHgwMDU1OwoJLyogU2VjdG9yIGVyYXNlIGNvbW1hbmQgY29tZXMgbGFzdCAqLwoJKih2b2xhdGlsZSB1MTYqKShhZGRyICsgc2VjdG9yKSA9IDB4MDAzMDsKCgllbGFwc2VkID0gKih2b2xhdGlsZSB1MTYqKSgweGZmZmVmMDAwK1NDNTIwX1NXVE1STUlMTEkpOyAvKiBkdW1teSByZWFkICovCgllbGFwc2VkID0gMDsKCXdoaWxlICgoKCoodm9sYXRpbGUgdTE2KikoYWRkciArIHNlY3RvcikpICYgMHgwMDgwKSAhPSAweDAwODApIHsKCgkJZWxhcHNlZCArPSAqKHZvbGF0aWxlIHUxNiopKDB4ZmZmZWYwMDArU0M1MjBfU1dUTVJNSUxMSSk7CgkJaWYgKGVsYXBzZWQgPiAoKENPTkZJR19TWVNfRkxBU0hfRVJBU0VfVE9VVC9DT05GSUdfU1lTX0haKSAqIDEwMDApKSB7CgkJCSoodm9sYXRpbGUgdTE2KikoYWRkcikgPSAweDAwZjA7CgkJCXJldHVybiAxOwoJCX0KCX0KCgkqKHZvbGF0aWxlIHUxNiopKGFkZHIpID0gMHgwMGYwOwoKCXJldHVybiAwOwp9CgpleHRlcm4gaW50IF9hbWRfZXJhc2VfZmxhc2hfZW5kOwphc20gKCJfYW1kX2VyYXNlX2ZsYXNoX2VuZDpcbiIKICAgICAiLmxvbmcgMFxuIik7CgovKiB0aGlzIG5lZWRzIHRvIGJlIGlubGluZWQsIHRoZSBTV1RNUk1NSUxMSSByZWdpc3RlciBpcyByZXNldCBieSBlYWNoIHJlYWQgKi8KI2RlZmluZSBfX3VkZWxheShkZWxheSkgXAp7CVwKCXVuc2lnbmVkIG1pY3JvOyBcCgl1bnNpZ25lZCBtaWxsaT0wOyBcCglcCgltaWNybyA9ICoodm9sYXRpbGUgdTE2KikoMHhmZmZlZjAwMCtTQzUyMF9TV1RNUk1JTExJKTsgXAoJIFwKCWZvciAoOzspIHsgXAoJCVwKCQltaWxsaSArPSAqKHZvbGF0aWxlIHUxNiopKDB4ZmZmZWYwMDArU0M1MjBfU1dUTVJNSUxMSSk7IFwKCQltaWNybyA9ICoodm9sYXRpbGUgdTE2KikoMHhmZmZlZjAwMCtTQzUyMF9TV1RNUk1JQ1JPKTsgXAoJCVwKCQlpZiAoKGRlbGF5KSA8PSAobWljcm8gKyAobWlsbGkgKiAxMDAwKSkpIHsgXAoJCQlicmVhazsgXAoJCX0gXAoJfSBcCn0gd2hpbGUgKDApCgpzdGF0aWMgdTMyIF9pbnRlbF9lcmFzZV9mbGFzaCh1MzIgYWRkciwgdTMyIHNlY3RvcikKewoJdW5zaWduZWQgZWxhcHNlZDsKCgkqKHZvbGF0aWxlIHUxNiopKGFkZHIgKyBzZWN0b3IpID0gMHgwMDUwOyAgIC8qIGNsZWFyIHN0YXR1cyByZWdpc3RlciAqLwoJKih2b2xhdGlsZSB1MTYqKShhZGRyICsgc2VjdG9yKSA9IDB4MDAyMDsgICAvKiBlcmFzZSBzZXR1cCAqLwoJKih2b2xhdGlsZSB1MTYqKShhZGRyICsgc2VjdG9yKSA9IDB4MDBEMDsgICAvKiBlcmFzZSBjb25maXJtICovCgoJLyogV2FpdCBhdCBsZWFzdCA4MHVzIC0gbGV0J3Mgd2FpdCAxIG1zICovCglfX3VkZWxheSgxMDAwKTsKCgllbGFwc2VkID0gMDsKCXdoaWxlICgoKCoodm9sYXRpbGUgdTE2KikoYWRkciArIHNlY3RvcikpICYgMHgwMDgwKSAhPSAweDAwODApIHsKCQllbGFwc2VkICs9ICoodm9sYXRpbGUgdTE2KikoMHhmZmZlZjAwMCtTQzUyMF9TV1RNUk1JTExJKTsKCQlpZiAoZWxhcHNlZCA+ICgoQ09ORklHX1NZU19GTEFTSF9FUkFTRV9UT1VUL0NPTkZJR19TWVNfSFopICogMTAwMCkpIHsKCQkJKih2b2xhdGlsZSB1MTYqKShhZGRyICsgc2VjdG9yKSA9IDB4MDBCMDsgIC8qIHN1c3BlbmQgZXJhc2UgICAgICAqLwoJCQkqKHZvbGF0aWxlIHUxNiopKGFkZHIgKyBzZWN0b3IpID0gMHgwMEZGOyAgLyogcmVzZXQgdG8gcmVhZCBtb2RlICovCgkJCXJldHVybiAxOwoJCX0KCX0KCgkqKHZvbGF0aWxlIHUxNiopKGFkZHIgKyBzZWN0b3IpID0gMHgwMEZGOyAgLyogcmVzZXQgdG8gcmVhZCBtb2RlICovCgoJcmV0dXJuIDA7Cn0KCmV4dGVybiBpbnQgX2ludGVsX2VyYXNlX2ZsYXNoX2VuZDsKYXNtICgiX2ludGVsX2VyYXNlX2ZsYXNoX2VuZDpcbiIKICAgICAiLmxvbmcgMFxuIik7CgppbnQgZmxhc2hfZXJhc2UoZmxhc2hfaW5mb190ICppbmZvLCBpbnQgc19maXJzdCwgaW50IHNfbGFzdCkKewoJdTMyICgqX2VyYXNlX2ZsYXNoX3B0cikodTMyIGEsIHUzMiBzbyk7CglpbnQgcHJvdDsKCWludCBzZWN0OwoJdW5zaWduZWQgc2l6ZTsKCglpZiAoKHNfZmlyc3QgPCAwKSB8fCAoc19maXJzdCA+IHNfbGFzdCkpIHsKCQlpZiAoaW5mby0+Zmxhc2hfaWQgPT0gRkxBU0hfVU5LTk9XTikgewoJCQlwcmludGYoIi0gbWlzc2luZ1xuIik7CgkJfSBlbHNlIHsKCQkJcHJpbnRmKCItIG5vIHNlY3RvcnMgdG8gZXJhc2VcbiIpOwoJCX0KCQlyZXR1cm4gMTsKCX0KCglpZiAoKGluZm8tPmZsYXNoX2lkICYgRkxBU0hfVkVORE1BU0spID09IChBTURfTUFOVUZBQ1QgJiBGTEFTSF9WRU5ETUFTSykpIHsKCQlzaXplID0gKHVuc2lnbmVkKSZfYW1kX2VyYXNlX2ZsYXNoX2VuZCAtICh1bnNpZ25lZClfYW1kX2VyYXNlX2ZsYXNoOwoKCQlpZiAoc2l6ZSA+IFBST0JFX0JVRkZFUl9TSVpFKSB7CgkJCXByaW50ZigiX2FtZF9lcmFzZV9mbGFzaCgpIHJvdXRpbmUgdG9vIGxhcmdlICglZCkgJXAgLSAlcFxuIiwKCQkJICAgICAgIHNpemUsICZfYW1kX2VyYXNlX2ZsYXNoX2VuZCwgX2FtZF9lcmFzZV9mbGFzaCk7CgkJCXJldHVybiAwOwoJCX0KCgkJbWVtY3B5KGJ1ZmZlciwgX2FtZF9lcmFzZV9mbGFzaCwgc2l6ZSk7CgkJX2VyYXNlX2ZsYXNoX3B0ciA9ICh2b2lkKilidWZmZXI7CgoJfSBlbHNlIGlmICgoaW5mby0+Zmxhc2hfaWQgJiBGTEFTSF9WRU5ETUFTSykgPT0gKElOVEVMX01BTlVGQUNUICYgRkxBU0hfVkVORE1BU0spKSB7CgkJc2l6ZSA9ICh1bnNpZ25lZCkmX2ludGVsX2VyYXNlX2ZsYXNoX2VuZCAtICh1bnNpZ25lZClfaW50ZWxfZXJhc2VfZmxhc2g7CgoJCWlmIChzaXplID4gUFJPQkVfQlVGRkVSX1NJWkUpIHsKCQkJcHJpbnRmKCJfaW50ZWxfZXJhc2VfZmxhc2goKSByb3V0aW5lIHRvbyBsYXJnZSAoJWQpICVwIC0gJXBcbiIsCgkJCSAgICAgICBzaXplLCAmX2ludGVsX2VyYXNlX2ZsYXNoX2VuZCwgX2ludGVsX2VyYXNlX2ZsYXNoKTsKCQkJcmV0dXJuIDA7CgkJfQoKCQltZW1jcHkoYnVmZmVyLCBfaW50ZWxfZXJhc2VfZmxhc2gsIHNpemUpOwoJCV9lcmFzZV9mbGFzaF9wdHIgPSAodm9pZCopYnVmZmVyOwoJfSBlbHNlIHsKCQlwcmludGYgKCJDYW4ndCBlcmFzZSB1bmtub3duIGZsYXNoIHR5cGUgLSBhYm9ydGVkXG4iKTsKCQlyZXR1cm4gMTsKCX0KCglwcm90ID0gMDsKCWZvciAoc2VjdD1zX2ZpcnN0OyBzZWN0PD1zX2xhc3Q7ICsrc2VjdCkgewoJCWlmIChpbmZvLT5wcm90ZWN0W3NlY3RdKSB7CgkJCXByb3QrKzsKCQl9Cgl9CgoJaWYgKHByb3QpIHsKCQlwcmludGYgKCItIFdhcm5pbmc6ICVkIHByb3RlY3RlZCBzZWN0b3JzIHdpbGwgbm90IGJlIGVyYXNlZCFcbiIsIHByb3QpOwoJfSBlbHNlIHsKCQlwcmludGYgKCJcbiIpOwoJfQoKCS8qIFN0YXJ0IGVyYXNlIG9uIHVucHJvdGVjdGVkIHNlY3RvcnMgKi8KCWZvciAoc2VjdCA9IHNfZmlyc3Q7IHNlY3Q8PXNfbGFzdDsgc2VjdCsrKSB7CgoJCWlmIChpbmZvLT5wcm90ZWN0W3NlY3RdID09IDApIHsgLyogbm90IHByb3RlY3RlZCAqLwoJCQlpbnQgcmVzOwoJCQlpbnQgZmxhZzsKCgkJCS8qIERpc2FibGUgaW50ZXJydXB0cyB3aGljaCBtaWdodCBjYXVzZSBhIHRpbWVvdXQgaGVyZSAqLwoJCQlmbGFnID0gZGlzYWJsZV9pbnRlcnJ1cHRzKCk7CgoJCQlyZXMgPSBfZXJhc2VfZmxhc2hfcHRyKGluZm8tPnN0YXJ0WzBdLCBpbmZvLT5zdGFydFtzZWN0XS1pbmZvLT5zdGFydFswXSk7CgoJCQkvKiByZS1lbmFibGUgaW50ZXJydXB0cyBpZiBuZWNlc3NhcnkgKi8KCQkJaWYgKGZsYWcpIHsKCQkJCWVuYWJsZV9pbnRlcnJ1cHRzKCk7CgkJCX0KCgkJCWlmIChyZXMpIHsKCQkJCXByaW50ZigiRXJhc2UgdGltZWQgb3V0LCBzZWN0b3IgJWRcbiIsIHNlY3QpOwoJCQkJcmV0dXJuIHJlczsKCQkJfQoKCQkJcHV0YygnLicpOwoJCX0KCX0KCglyZXR1cm4gMDsKfQoKLyotLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQogKiBXcml0ZSBhIHdvcmQgdG8gRmxhc2gsIHJldHVybnM6CiAqIDAgLSBPSwogKiAxIC0gd3JpdGUgdGltZW91dAogKiAyIC0gRmxhc2ggbm90IGVyYXNlZAogKi8Kc3RhdGljIGludCBfYW1kX3dyaXRlX3dvcmQodW5zaWduZWQgc3RhcnQsIHVuc2lnbmVkIGRlc3QsIHUxNiBkYXRhKQp7Cgl2b2xhdGlsZSB1MTYgKmFkZHIyID0gKHZvbGF0aWxlIHUxNiopc3RhcnQ7Cgl2b2xhdGlsZSB1MTYgKmRlc3QyID0gKHZvbGF0aWxlIHUxNiopZGVzdDsKCXZvbGF0aWxlIHUxNiAqZGF0YTIgPSAodm9sYXRpbGUgdTE2KikmZGF0YTsKCWludCBpOwoJdW5zaWduZWQgZWxhcHNlZDsKCgkvKiBDaGVjayBpZiBGbGFzaCBpcyAoc3VmZmljaWVudGx5KSBlcmFzZWQgKi8KCWlmICgoKigodm9sYXRpbGUgdTE2KilkZXN0KSAmICh1MTYpZGF0YSkgIT0gKHUxNilkYXRhKSB7CgkJcmV0dXJuIDI7Cgl9CgoJZm9yIChpID0gMDsgaSA8IDI7IGkrKykgewoKCQlhZGRyMlsweDU1NTVdID0gMHgwMEFBOwoJCWFkZHIyWzB4MmFhYV0gPSAweDAwNTU7CgkJYWRkcjJbMHg1NTU1XSA9IDB4MDBBMDsKCgkJZGVzdDJbaV0gPSAoZGF0YSA+PiAoaSoxNikpICYgMHhmZmZmOwoKCQllbGFwc2VkID0gKih2b2xhdGlsZSB1MTYqKSgweGZmZmVmMDAwK1NDNTIwX1NXVE1STUlMTEkpOyAvKiBkdW1teSByZWFkICovCgkJZWxhcHNlZCA9IDA7CgoJCS8qIGRhdGEgcG9sbGluZyBmb3IgRDcgKi8KCQl3aGlsZSAoKGRlc3QyW2ldICYgMHgwMDgwKSAhPSAoZGF0YTJbaV0gJiAweDAwODApKSB7CgkJCWVsYXBzZWQgKz0gKih2b2xhdGlsZSB1MTYqKSgweGZmZmVmMDAwK1NDNTIwX1NXVE1STUlMTEkpOwoJCQlpZiAoZWxhcHNlZCA+ICgoQ09ORklHX1NZU19GTEFTSF9XUklURV9UT1VUL0NPTkZJR19TWVNfSFopICogMTAwMCkpIHsKCQkJCWFkZHIyW2ldID0gMHgwMGYwOwoJCQkJcmV0dXJuIDE7CgkJCX0KCQl9Cgl9CgoJYWRkcjJbaV0gPSAweDAwZjA7CgoJcmV0dXJuIDA7Cn0KCmV4dGVybiBpbnQgX2FtZF93cml0ZV93b3JkX2VuZDsKYXNtICgiX2FtZF93cml0ZV93b3JkX2VuZDpcbiIKICAgICAiLmxvbmcgMFxuIik7CgpzdGF0aWMgaW50IF9pbnRlbF93cml0ZV93b3JkKHVuc2lnbmVkIHN0YXJ0LCB1bnNpZ25lZCBkZXN0LCB1bnNpZ25lZCBkYXRhKQp7CglpbnQgaTsKCXVuc2lnbmVkIGVsYXBzZWQ7CgoJLyogQ2hlY2sgaWYgRmxhc2ggaXMgKHN1ZmZpY2llbnRseSkgZXJhc2VkICovCglpZiAoKCooKHZvbGF0aWxlIHUxNiopZGVzdCkgJiAodTE2KWRhdGEpICE9ICh1MTYpZGF0YSkgewoJCXJldHVybiAyOwoJfQoKCWZvciAoaSA9IDA7IGkgPCAyOyBpKyspIHsKCgkJKih2b2xhdGlsZSB1MTYqKShkZXN0KzIqaSkgPSAweDAwNDA7IC8qIHdyaXRlIHNldHVwICovCgkJKih2b2xhdGlsZSB1MTYqKShkZXN0KzIqaSkgPSAoZGF0YSA+PiAoaSoxNikpICYgMHhmZmZmOwoKCQllbGFwc2VkID0gKih2b2xhdGlsZSB1MTYqKSgweGZmZmVmMDAwK1NDNTIwX1NXVE1STUlMTEkpOyAvKiBkdW1teSByZWFkICovCgkJZWxhcHNlZCA9IDA7CgoJCS8qIGRhdGEgcG9sbGluZyBmb3IgRDcgKi8KCQl3aGlsZSAoKCoodm9sYXRpbGUgdTE2KilkZXN0ICYgMHgwMDgwKSAhPSAweDAwODApIHsKCQkJZWxhcHNlZCArPSAqKHZvbGF0aWxlIHUxNiopKDB4ZmZmZWYwMDArU0M1MjBfU1dUTVJNSUxMSSk7CgkJCWlmIChlbGFwc2VkID4gKChDT05GSUdfU1lTX0ZMQVNIX1dSSVRFX1RPVVQvQ09ORklHX1NZU19IWikgKiAxMDAwKSkgewoJCQkJKih2b2xhdGlsZSB1MTYqKWRlc3QgPSAweDAwZmY7CgkJCQlyZXR1cm4gMTsKCQkJfQoJCX0KCX0KCgkqKHZvbGF0aWxlIHUxNiopZGVzdCA9IDB4MDBmZjsKCgoJcmV0dXJuIDA7Cn0KCmV4dGVybiBpbnQgX2ludGVsX3dyaXRlX3dvcmRfZW5kOwphc20gKCJfaW50ZWxfd3JpdGVfd29yZF9lbmQ6XG4iCiAgICAgIi5sb25nIDBcbiIpOwoKLyotLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQogKiBDb3B5IG1lbW9yeSB0byBmbGFzaCwgcmV0dXJuczoKICogMCAtIE9LCiAqIDEgLSB3cml0ZSB0aW1lb3V0CiAqIDIgLSBGbGFzaCBub3QgZXJhc2VkCiAqIDMgLSBVbnN1cHBvcnRlZCBmbGFzaCB0eXBlCiAqLwoKaW50IHdyaXRlX2J1ZmYoZmxhc2hfaW5mb190ICppbmZvLCB1Y2hhciAqc3JjLCB1bG9uZyBhZGRyLCB1bG9uZyBjbnQpCnsKCXVsb25nIGNwLCB3cCwgZGF0YTsKCWludCBpLCBsLCByYzsKCWludCBmbGFnOwoJdTMyICgqX3dyaXRlX3dvcmRfcHRyKSh1bnNpZ25lZCBzdGFydCwgdW5zaWduZWQgZGVzdCwgdW5zaWduZWQgZGF0YSk7Cgl1bnNpZ25lZCBzaXplOwoKCWlmICgoaW5mby0+Zmxhc2hfaWQgJiBGTEFTSF9WRU5ETUFTSykgPT0gKEFNRF9NQU5VRkFDVCAmIEZMQVNIX1ZFTkRNQVNLKSkgewoJCXNpemUgPSAodW5zaWduZWQpJl9hbWRfd3JpdGVfd29yZF9lbmQgLSAodW5zaWduZWQpX2FtZF93cml0ZV93b3JkOwoKCQlpZiAoc2l6ZSA+IFBST0JFX0JVRkZFUl9TSVpFKSB7CgkJCXByaW50ZigiX2FtZF93cml0ZV93b3JkKCkgcm91dGluZSB0b28gbGFyZ2UgKCVkKSAlcCAtICVwXG4iLAoJCQkgICAgICAgc2l6ZSwgJl9hbWRfd3JpdGVfd29yZF9lbmQsIF9hbWRfd3JpdGVfd29yZCk7CgkJCXJldHVybiAwOwoJCX0KCgkJbWVtY3B5KGJ1ZmZlciwgX2FtZF93cml0ZV93b3JkLCBzaXplKTsKCQlfd3JpdGVfd29yZF9wdHIgPSAodm9pZCopYnVmZmVyOwoKCX0gZWxzZSBpZiAoKGluZm8tPmZsYXNoX2lkICYgRkxBU0hfVkVORE1BU0spID09IChJTlRFTF9NQU5VRkFDVCAmIEZMQVNIX1ZFTkRNQVNLKSkgewoJCXNpemUgPSAodW5zaWduZWQpJl9pbnRlbF93cml0ZV93b3JkX2VuZCAtICh1bnNpZ25lZClfaW50ZWxfd3JpdGVfd29yZDsKCgkJaWYgKHNpemUgPiBQUk9CRV9CVUZGRVJfU0laRSkgewoJCQlwcmludGYoIl9pbnRlbF93cml0ZV93b3JkKCkgcm91dGluZSB0b28gbGFyZ2UgKCVkKSAlcCAtICVwXG4iLAoJCQkgICAgICAgc2l6ZSwgJl9pbnRlbF93cml0ZV93b3JkX2VuZCwgX2ludGVsX3dyaXRlX3dvcmQpOwoJCQlyZXR1cm4gMDsKCQl9CgoJCW1lbWNweShidWZmZXIsIF9pbnRlbF93cml0ZV93b3JkLCBzaXplKTsKCQlfd3JpdGVfd29yZF9wdHIgPSAodm9pZCopYnVmZmVyOwoJfSBlbHNlIHsKCQlwcmludGYgKCJDYW4ndCBwcm9ncmFtIHVua25vd24gZmxhc2ggdHlwZSAtIGFib3J0ZWRcbiIpOwoJCXJldHVybiAzOwoJfQoKCXdwID0gKGFkZHIgJiB+Myk7CS8qIGdldCBsb3dlciB3b3JkIGFsaWduZWQgYWRkcmVzcyAqLwoKCS8qCgkgKiBoYW5kbGUgdW5hbGlnbmVkIHN0YXJ0IGJ5dGVzCgkgKi8KCWlmICgobCA9IGFkZHIgLSB3cCkgIT0gMCkgewoJCWRhdGEgPSAwOwoJCWZvciAoaT0wLCBjcD13cDsgaTxsOyArK2ksICsrY3ApIHsKCQkJZGF0YSB8PSAoKih1Y2hhciAqKWNwKSA8PCAoOCppKTsKCQl9CgkJZm9yICg7IGk8NCAmJiBjbnQ+MDsgKytpKSB7CgkJCWRhdGEgfD0gKnNyYysrIDw8ICg4KmkpOwoJCQktLWNudDsKCQkJKytjcDsKCQl9CgkJZm9yICg7IGNudD09MCAmJiBpPDQ7ICsraSwgKytjcCkgewoJCQlkYXRhIHw9ICgqKHVjaGFyICopY3ApICA8PCAoOCppKTsKCQl9CgoJCS8qIERpc2FibGUgaW50ZXJydXB0cyB3aGljaCBtaWdodCBjYXVzZSBhIHRpbWVvdXQgaGVyZSAqLwoJCWZsYWcgPSBkaXNhYmxlX2ludGVycnVwdHMoKTsKCgkJcmMgPSBfd3JpdGVfd29yZF9wdHIoaW5mby0+c3RhcnRbMF0sIHdwLCBkYXRhKTsKCgkJLyogcmUtZW5hYmxlIGludGVycnVwdHMgaWYgbmVjZXNzYXJ5ICovCgkJaWYgKGZsYWcpIHsKCQkJZW5hYmxlX2ludGVycnVwdHMoKTsKCQl9CgkJaWYgKHJjICE9IDApIHsKCQkJcmV0dXJuIHJjOwoJCX0KCQl3cCArPSA0OwoJfQoKCS8qCgkgKiBoYW5kbGUgd29yZCBhbGlnbmVkIHBhcnQKCSAqLwoJd2hpbGUgKGNudCA+PSA0KSB7CgkJZGF0YSA9IDA7CgoJCWZvciAoaT0wOyBpPDQ7ICsraSkgewoJCQlkYXRhIHw9ICpzcmMrKyA8PCAoOCppKTsKCQl9CgoJCS8qIERpc2FibGUgaW50ZXJydXB0cyB3aGljaCBtaWdodCBjYXVzZSBhIHRpbWVvdXQgaGVyZSAqLwoJCWZsYWcgPSBkaXNhYmxlX2ludGVycnVwdHMoKTsKCgkJcmMgPSBfd3JpdGVfd29yZF9wdHIoaW5mby0+c3RhcnRbMF0sIHdwLCBkYXRhKTsKCgkJLyogcmUtZW5hYmxlIGludGVycnVwdHMgaWYgbmVjZXNzYXJ5ICovCgkJaWYgKGZsYWcpIHsKCQkJZW5hYmxlX2ludGVycnVwdHMoKTsKCQl9CgkJaWYgKHJjICE9IDApIHsKCQkJcmV0dXJuIHJjOwoJCX0KCQl3cCAgKz0gNDsKCQljbnQgLT0gNDsKCX0KCglpZiAoY250ID09IDApIHsKCQlyZXR1cm4gMDsKCX0KCgkvKgoJICogaGFuZGxlIHVuYWxpZ25lZCB0YWlsIGJ5dGVzCgkgKi8KCWRhdGEgPSAwOwoJZm9yIChpPTAsIGNwPXdwOyBpPDQgJiYgY250PjA7ICsraSwgKytjcCkgewoJCWRhdGEgfD0gKnNyYysrIDw8ICg4KmkpOwoJCS0tY250OwoJfQoKCWZvciAoOyBpPDQ7ICsraSwgKytjcCkgewoJCWRhdGEgfD0gKCoodWNoYXIgKiljcCkgPDwgKDgqaSk7Cgl9CgoJLyogRGlzYWJsZSBpbnRlcnJ1cHRzIHdoaWNoIG1pZ2h0IGNhdXNlIGEgdGltZW91dCBoZXJlICovCglmbGFnID0gZGlzYWJsZV9pbnRlcnJ1cHRzKCk7CgoJcmMgPSBfd3JpdGVfd29yZF9wdHIoaW5mby0+c3RhcnRbMF0sIHdwLCBkYXRhKTsKCgkvKiByZS1lbmFibGUgaW50ZXJydXB0cyBpZiBuZWNlc3NhcnkgKi8KCWlmIChmbGFnKSB7CgkJZW5hYmxlX2ludGVycnVwdHMoKTsKCX0KCglyZXR1cm4gcmM7Cn0K