LyogZmRmb3JtYXQuYyAgLSAgTG93LWxldmVsIGZvcm1hdHMgYSBmbG9wcHkgZGlzayAtIFdlcm5lciBBbG1lc2JlcmdlciAqLwoKLyogMTk5OS0wMi0yMiBBcmthZGl1c3ogTWm2a2lld2ljeiA8bWlzaWVrQHBsZC5PUkcuUEw+CiAqIC0gYWRkZWQgTmF0aXZlIExhbmd1YWdlIFN1cHBvcnQKICogMTk5OS0wMy0yMCBBcm5hbGRvIENhcnZhbGhvIGRlIE1lbG8gPGFjbWVAY29uZWN0aXZhLmNvbS5icj4KICogLSBtb3JlIGkxOG4vbmxzIHRyYW5zbGF0YWJsZSBzdHJpbmdzIG1hcmtlZAogKgogKiA1IEp1bHkgMjAwMyAtLSBtb2RpZmllZCBmb3IgQnVzeWJveCBieSBFcmlrIEFuZGVyc2VuCiAqLwoKI2luY2x1ZGUgPHN0ZGlvLmg+CiNpbmNsdWRlIDxzdHJpbmcuaD4KI2luY2x1ZGUgPGZjbnRsLmg+CiNpbmNsdWRlIDxlcnJuby5oPgojaW5jbHVkZSA8dW5pc3RkLmg+CiNpbmNsdWRlIDxzdGRsaWIuaD4KI2luY2x1ZGUgPHN5cy9zdGF0Lmg+CiNpbmNsdWRlIDxzeXMvaW9jdGwuaD4KI2luY2x1ZGUgImJ1c3lib3guaCIKCgovKiBTdHVmZiBleHRyYWN0ZWQgZnJvbSBsaW51eC9mZC5oICovCnN0cnVjdCBmbG9wcHlfc3RydWN0IHsKCXVuc2lnbmVkIGludAlzaXplLAkJLyogbnIgb2Ygc2VjdG9ycyB0b3RhbCAqLwoJCQlzZWN0LAkJLyogc2VjdG9ycyBwZXIgdHJhY2sgKi8KCQkJaGVhZCwJCS8qIG5yIG9mIGhlYWRzICovCgkJCXRyYWNrLAkJLyogbnIgb2YgdHJhY2tzICovCgkJCXN0cmV0Y2g7CS8qICE9MCBtZWFucyBkb3VibGUgdHJhY2sgc3RlcHMgKi8KI2RlZmluZSBGRF9TVFJFVENIIDEKI2RlZmluZSBGRF9TV0FQU0lERVMgMgoKCXVuc2lnbmVkIGNoYXIJZ2FwLAkJLyogZ2FwMSBzaXplICovCgoJCQlyYXRlLAkJLyogZGF0YSByYXRlLiB8PSAweDQwIGZvciBwZXJwZW5kaWN1bGFyICovCiNkZWZpbmUgRkRfMk0gMHg0CiNkZWZpbmUgRkRfU0laRUNPREVNQVNLIDB4MzgKI2RlZmluZSBGRF9TSVpFQ09ERShmbG9wcHkpICgoKCgoZmxvcHB5KS0+cmF0ZSZGRF9TSVpFQ09ERU1BU0spPj4gMykrIDIpICU4KQojZGVmaW5lIEZEX1NFQ1RTSVpFKGZsb3BweSkgKCAoZmxvcHB5KS0+cmF0ZSAmIEZEXzJNID8gXAoJCQkgICAgIDUxMiA6IDEyOCA8PCBGRF9TSVpFQ09ERShmbG9wcHkpICkKI2RlZmluZSBGRF9QRVJQIDB4NDAKCgkJCXNwZWMxLAkJLyogc3RlcHBpbmcgcmF0ZSwgaGVhZCB1bmxvYWQgdGltZSAqLwoJCQlmbXRfZ2FwOwkvKiBnYXAyIHNpemUgKi8KCWNvbnN0IGNoYXIJKiBuYW1lOyAvKiB1c2VkIG9ubHkgZm9yIHByZWRlZmluZWQgZm9ybWF0cyAqLwp9OwpzdHJ1Y3QgZm9ybWF0X2Rlc2NyIHsKCXVuc2lnbmVkIGludCBkZXZpY2UsaGVhZCx0cmFjazsKfTsKI2RlZmluZSBGREZNVEJFRyBfSU8oMiwweDQ3KQojZGVmaW5lCUZERk1UVFJLIF9JT1coMiwweDQ4LCBzdHJ1Y3QgZm9ybWF0X2Rlc2NyKQojZGVmaW5lIEZERk1URU5EIF9JTygyLDB4NDkpCiNkZWZpbmUgRkRHRVRQUk0gX0lPUigyLCAweDA0LCBzdHJ1Y3QgZmxvcHB5X3N0cnVjdCkKI2RlZmluZSBGRF9GSUxMX0JZVEUgMHhGNiAvKiBmb3JtYXQgZmlsbCBieXRlLiAqLwoKc3RhdGljIHZvaWQgcHJpbnRfYW5kX2ZsdXNoKGNvbnN0IGNoYXIgKiBfX3Jlc3RyaWN0IGZvcm1hdCwgLi4uKQp7Cgl2YV9saXN0IGFyZzsKCgl2YV9zdGFydChhcmcsIGZvcm1hdCk7CgliYl92ZnByaW50ZihzdGRvdXQsIGZvcm1hdCwgYXJnKTsKCXZhX2VuZChhcmcpOwoJYmJfeGZmbHVzaF9zdGRvdXQoKTsKfQoKc3RhdGljIHZvaWQgYmJfeGlvY3RsKGludCBmZCwgaW50IHJlcXVlc3QsIHZvaWQgKmFyZ3AsIGNvbnN0IGNoYXIgKnN0cmluZykKewoJaWYgKGlvY3RsIChmZCwgcmVxdWVzdCwgYXJncCkgPCAwKSB7CgkJYmJfcGVycm9yX21zZ19hbmRfZGllKHN0cmluZyk7Cgl9Cn0KCmludCBmZGZvcm1hdF9tYWluKGludCBhcmdjLGNoYXIgKiphcmd2KQp7CglpbnQgZmQsIG4sIGN5bCwgcmVhZF9ieXRlcywgdmVyaWZ5OwoJdW5zaWduZWQgY2hhciAqZGF0YTsKCXN0cnVjdCBzdGF0IHN0OwoJc3RydWN0IGZsb3BweV9zdHJ1Y3QgcGFyYW07CglzdHJ1Y3QgZm9ybWF0X2Rlc2NyIGRlc2NyOwoKCWlmIChhcmdjIDwgMikgewoJCWJiX3Nob3dfdXNhZ2UoKTsKCX0KCXZlcmlmeSA9ICFiYl9nZXRvcHRfdWxmbGFncyhhcmdjLCBhcmd2LCAibiIpOwoJYXJndiArPSBvcHRpbmQ7CgoJLyogUl9PSyBpcyBuZWVkZWQgZm9yIHZlcmlmeWluZyAqLwoJaWYgKHN0YXQoKmFyZ3YsJnN0KSA8IDAgfHwgYWNjZXNzKCphcmd2LFdfT0sgfCBSX09LICkgPCAwKSB7CgkJYmJfcGVycm9yX21zZ19hbmRfZGllKCphcmd2KTsKCX0KCWlmICghU19JU0JMSyhzdC5zdF9tb2RlKSkgewoJCWJiX2Vycm9yX21zZ19hbmRfZGllKCIlczogbm90IGEgYmxvY2sgZGV2aWNlIiwqYXJndik7CgkJLyogZG8gbm90IHRlc3QgbWFqb3IgLSBwZXJoYXBzIHRoaXMgd2FzIGFuIFVTQiBmbG9wcHkgKi8KCX0KCgoJLyogT19SRFdSIGZvciBmb3JtYXR0aW5nIGFuZCB2ZXJpZnlpbmcgKi8KCWZkID0gYmJfeG9wZW4oKmFyZ3YsT19SRFdSICk7CgoJYmJfeGlvY3RsKGZkLCBGREdFVFBSTSwgJnBhcmFtLCAiRkRHRVRQUk0iKTsvKm9yaWdpbmFsIG1lc3NhZ2Ugd2FzOiAiQ291bGQgbm90IGRldGVybWluZSBjdXJyZW50IGZvcm1hdCB0eXBlIiAqLwoKCXByaW50X2FuZF9mbHVzaCgiJXMtc2lkZWQsICVkIHRyYWNrcywgJWQgc2VjL3RyYWNrLiBUb3RhbCBjYXBhY2l0eSAlZCBrQi5cbiIsCgkJKHBhcmFtLmhlYWQgPT0gMikgPyAiRG91YmxlIiA6ICJTaW5nbGUiLAoJCXBhcmFtLnRyYWNrLCBwYXJhbS5zZWN0LCBwYXJhbS5zaXplID4+IDEpOwoKCS8qIEZPUk1BVCAqLwoJcHJpbnRfYW5kX2ZsdXNoKCJGb3JtYXR0aW5nIC4uLiAiLCBOVUxMKTsKCWJiX3hpb2N0bChmZCwgRkRGTVRCRUcsTlVMTCwiRkRGTVRCRUciKTsKCgkvKiBuID09IHRyYWNrICovCglmb3IgKG4gPSAwOyBuIDwgcGFyYW0udHJhY2s7IG4rKykKCXsKCSAgICBkZXNjci5oZWFkID0gMDsKCSAgICBkZXNjci50cmFjayA9IG47CgkgICAgYmJfeGlvY3RsKGZkLCBGREZNVFRSSywmZGVzY3IsIkZERk1UVFJLIik7CgkgICAgcHJpbnRfYW5kX2ZsdXNoKCIlM2RcYlxiXGIiLCBuKTsKCSAgICBpZiAocGFyYW0uaGVhZCA9PSAyKSB7CgkJZGVzY3IuaGVhZCA9IDE7CgkJYmJfeGlvY3RsKGZkLCBGREZNVFRSSywmZGVzY3IsIkZERk1UVFJLIik7CgkgICAgfQoJfQoKCWJiX3hpb2N0bChmZCxGREZNVEVORCxOVUxMLCJGREZNVEVORCIpOwoJcHJpbnRfYW5kX2ZsdXNoKCJkb25lXG4iLCBOVUxMKTsKCgkvKiBWRVJJRlkgKi8KCWlmKHZlcmlmeSkgewoJCS8qIG4gPT0gY3lsX3NpemUgKi8KCQluID0gcGFyYW0uc2VjdCpwYXJhbS5oZWFkKjUxMjsKCgkJZGF0YSA9IHhtYWxsb2Mobik7CgkJcHJpbnRfYW5kX2ZsdXNoKCJWZXJpZnlpbmcgLi4uICIsIE5VTEwpOwoJCWZvciAoY3lsID0gMDsgY3lsIDwgcGFyYW0udHJhY2s7IGN5bCsrKSB7CgkJCXByaW50X2FuZF9mbHVzaCgiJTNkXGJcYlxiIiwgY3lsKTsKCQkJaWYoKHJlYWRfYnl0ZXMgPSBzYWZlX3JlYWQoZmQsZGF0YSxuKSkhPSBuICkgewoJCQkJaWYocmVhZF9ieXRlcyA8IDApIHsKCQkJCQliYl9wZXJyb3JfbXNnKCJSZWFkOiAiKTsKCSAgICAJCX0KCQkJCWJiX2Vycm9yX21zZ19hbmRfZGllKCJQcm9ibGVtIHJlYWRpbmcgY3lsaW5kZXIgJWQsIGV4cGVjdGVkICVkLCByZWFkICVkIiwgY3lsLCBuLCByZWFkX2J5dGVzKTsKCQkJfQoJCQkvKiBDaGVjayBiYWNrd2FyZHMgc28gd2UgZG9uJ3QgbmVlZCBhIGNvdW50ZXIgKi8KCQkJd2hpbGUoLS1yZWFkX2J5dGVzPj0wKSB7CgkJCQlpZiggZGF0YVtyZWFkX2J5dGVzXSAhPSBGRF9GSUxMX0JZVEUpIHsKCQkJCQkgcHJpbnRfYW5kX2ZsdXNoKCJiYWQgZGF0YSBpbiBjeWwgJWRcbkNvbnRpbnVpbmcgLi4uICIsY3lsKTsKCQkJCX0KCQkJfQoJCX0KCQkvKiBUaGVyZSBpcyBubyBwb2ludCBpbiBmcmVlaW5nIGJsb2NrcyBhdCB0aGUgZW5kIG9mIGEgcHJvZ3JhbSwgYmVjYXVzZQoJCWFsbCBvZiB0aGUgcHJvZ3JhbSdzIHNwYWNlIGlzIGdpdmVuIGJhY2sgdG8gdGhlIHN5c3RlbSB3aGVuIHRoZSBwcm9jZXNzCgkJdGVybWluYXRlcy4qLwoJCQoJCWlmIChFTkFCTEVfRkVBVFVSRV9DTEVBTl9VUCkgZnJlZShkYXRhKTsKCQkKCQlwcmludF9hbmRfZmx1c2goImRvbmVcbiIsIE5VTEwpOwoJfQoKCWlmIChFTkFCTEVfRkVBVFVSRV9DTEVBTl9VUCkgY2xvc2UoZmQpOwoJCgkvKiBEb24ndCBib3RoZXIgY2xvc2luZy4gIEV4aXQgZG9lcwoJICogdGhhdCwgc28gd2UgY2FuIHNhdmUgYSBmZXcgYnl0ZXMgKi8KCXJldHVybiBFWElUX1NVQ0NFU1M7Cn0K