LyoKICogc25tcF9hbGFybS5jOgogKi8KLyogUG9ydGlvbnMgb2YgdGhpcyBmaWxlIGFyZSBzdWJqZWN0IHRvIHRoZSBmb2xsb3dpbmcgY29weXJpZ2h0KHMpLiAgU2VlCiAqIHRoZSBOZXQtU05NUCdzIENPUFlJTkcgZmlsZSBmb3IgbW9yZSBkZXRhaWxzIGFuZCBvdGhlciBjb3B5cmlnaHRzCiAqIHRoYXQgbWF5IGFwcGx5OgogKi8KLyoKICogUG9ydGlvbnMgb2YgdGhpcyBmaWxlIGFyZSBjb3B5cmlnaHRlZCBieToKICogQ29weXJpZ2h0IKkgMjAwMyBTdW4gTWljcm9zeXN0ZW1zLCBJbmMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAqIFVzZSBpcyBzdWJqZWN0IHRvIGxpY2Vuc2UgdGVybXMgc3BlY2lmaWVkIGluIHRoZSBDT1BZSU5HIGZpbGUKICogZGlzdHJpYnV0ZWQgd2l0aCB0aGUgTmV0LVNOTVAgcGFja2FnZS4KICovCi8qKiBAZGVmZ3JvdXAgc25tcF9hbGFybSAgZ2VuZXJpYyBsaWJyYXJ5IGJhc2VkIGFsYXJtIHRpbWVycyBmb3IgdmFyaW91cyBwYXJ0cyBvZiBhbiBhcHBsaWNhdGlvbiAKICogIEBpbmdyb3VwIGxpYnJhcnkKICogCiAqICBAewogKi8KI2luY2x1ZGUgPG5ldC1zbm1wL25ldC1zbm1wLWNvbmZpZy5oPgoKI2lmIEhBVkVfVU5JU1REX0gKI2luY2x1ZGUgPHVuaXN0ZC5oPgojZW5kaWYKI2luY2x1ZGUgPHNpZ25hbC5oPgojaWYgSEFWRV9TVERMSUJfSAojaW5jbHVkZSA8c3RkbGliLmg+CiNlbmRpZgojaW5jbHVkZSA8c3lzL3R5cGVzLmg+CiNpZiBIQVZFX05FVElORVRfSU5fSAojaW5jbHVkZSA8bmV0aW5ldC9pbi5oPgojZW5kaWYKI2lmIEhBVkVfU1RSSU5HX0gKI2luY2x1ZGUgPHN0cmluZy5oPgojZW5kaWYKCiNpZiBUSU1FX1dJVEhfU1lTX1RJTUUKIyBpbmNsdWRlIDxzeXMvdGltZS5oPgojIGluY2x1ZGUgPHRpbWUuaD4KI2Vsc2UKIyBpZiBIQVZFX1NZU19USU1FX0gKIyAgaW5jbHVkZSA8c3lzL3RpbWUuaD4KIyBlbHNlCiMgIGluY2x1ZGUgPHRpbWUuaD4KIyBlbmRpZgojZW5kaWYKCiNpZiBIQVZFX0RNQUxMT0NfSAojaW5jbHVkZSA8ZG1hbGxvYy5oPgojZW5kaWYKCiNpbmNsdWRlIDxuZXQtc25tcC90eXBlcy5oPgojaW5jbHVkZSA8bmV0LXNubXAvb3V0cHV0X2FwaS5oPgojaW5jbHVkZSA8bmV0LXNubXAvY29uZmlnX2FwaS5oPgojaW5jbHVkZSA8bmV0LXNubXAvdXRpbGl0aWVzLmg+CgojaW5jbHVkZSA8bmV0LXNubXAvbGlicmFyeS9zbm1wX2FwaS5oPgojaW5jbHVkZSA8bmV0LXNubXAvbGlicmFyeS9jYWxsYmFjay5oPgojaW5jbHVkZSA8bmV0LXNubXAvbGlicmFyeS9zbm1wX2FsYXJtLmg+CgpzdGF0aWMgc3RydWN0IHNubXBfYWxhcm0gKnRoZWFsYXJtcyA9IE5VTEw7CnN0YXRpYyBpbnQgICAgICBzdGFydF9hbGFybXMgPSAwOwpzdGF0aWMgdW5zaWduZWQgaW50IHJlZ251bSA9IDE7CgppbnQKaW5pdF9hbGFybV9wb3N0X2NvbmZpZyhpbnQgbWFqb3JpZCwgaW50IG1pbm9yaWQsIHZvaWQgKnNlcnZlcmFyZywKICAgICAgICAgICAgICAgICAgICAgICB2b2lkICpjbGllbnRhcmcpCnsKICAgIHN0YXJ0X2FsYXJtcyA9IDE7CiAgICBzZXRfYW5fYWxhcm0oKTsKICAgIHJldHVybiBTTk1QRVJSX1NVQ0NFU1M7Cn0KCnZvaWQKaW5pdF9zbm1wX2FsYXJtKHZvaWQpCnsKICAgIHN0YXJ0X2FsYXJtcyA9IDA7CiAgICBzbm1wX3JlZ2lzdGVyX2NhbGxiYWNrKFNOTVBfQ0FMTEJBQ0tfTElCUkFSWSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgU05NUF9DQUxMQkFDS19QT1NUX1JFQURfQ09ORklHLAogICAgICAgICAgICAgICAgICAgICAgICAgICBpbml0X2FsYXJtX3Bvc3RfY29uZmlnLCBOVUxMKTsKfQoKdm9pZApzYV91cGRhdGVfZW50cnkoc3RydWN0IHNubXBfYWxhcm0gKmEpCnsKICAgIGlmICghdGltZXJpc3NldCgmYS0+dF9sYXN0TSkpIHsKICAgICAgICAvKgogICAgICAgICAqIEZpcnN0IGNhbGwgb2Ygc2FfdXBkYXRlX2VudHJ5KCkgZm9yIGFsYXJtIGE6IHNldCB0X2xhc3RNIGFuZCB0X25leHRNLgogICAgICAgICAqLwogICAgICAgIG5ldHNubXBfZ2V0X21vbm90b25pY19jbG9jaygmYS0+dF9sYXN0TSk7CiAgICAgICAgTkVUU05NUF9USU1FUkFERCgmYS0+dF9sYXN0TSwgJmEtPnQsICZhLT50X25leHRNKTsKICAgIH0gZWxzZSBpZiAoIXRpbWVyaXNzZXQoJmEtPnRfbmV4dE0pKSB7CiAgICAgICAgLyoKICAgICAgICAgKiBXZSd2ZSBiZWVuIGNhbGxlZCBidXQgbm90IHJlc2V0IGZvciB0aGUgbmV4dCBjYWxsLiAgCiAgICAgICAgICovCiAgICAgICAgaWYgKGEtPmZsYWdzICYgU0FfUkVQRUFUKSB7CiAgICAgICAgICAgIGlmICh0aW1lcmlzc2V0KCZhLT50KSkgewogICAgICAgICAgICAgICAgTkVUU05NUF9USU1FUkFERCgmYS0+dF9sYXN0TSwgJmEtPnQsICZhLT50X25leHRNKTsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgIERFQlVHTVNHVEwoKCJzbm1wX2FsYXJtIiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICJ1cGRhdGVfZW50cnk6IGlsbGVnYWwgaW50ZXJ2YWwgc3BlY2lmaWVkXG4iKSk7CiAgICAgICAgICAgICAgICBzbm1wX2FsYXJtX3VucmVnaXN0ZXIoYS0+Y2xpZW50cmVnKTsKICAgICAgICAgICAgfQogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIC8qCiAgICAgICAgICAgICAqIFNpbmdsZSB0aW1lIGNhbGwsIHJlbW92ZSBpdC4gIAogICAgICAgICAgICAgKi8KICAgICAgICAgICAgc25tcF9hbGFybV91bnJlZ2lzdGVyKGEtPmNsaWVudHJlZyk7CiAgICAgICAgfQogICAgfQp9CgovKioKICogVGhpcyBmdW5jdGlvbiByZW1vdmVzIHRoZSBjYWxsYmFjayBmdW5jdGlvbiBmcm9tIGEgbGlzdCBvZiByZWdpc3RlcmVkCiAqIGFsYXJtcywgdW5yZWdpc3RlcmluZyB0aGUgYWxhcm0uCiAqCiAqIEBwYXJhbSBjbGllbnRyZWcgaXMgYSB1bmlxdWUgdW5zaWduZWQgaW50ZWdlciByZXByZXNlbnRpbmcgYSByZWdpc3RlcmVkCiAqCWFsYXJtIHdoaWNoIHRoZSBjbGllbnQgd2FudHMgdG8gdW5yZWdpc3Rlci4KICoKICogQHJldHVybiB2b2lkCiAqCiAqIEBzZWUgc25tcF9hbGFybV9yZWdpc3RlcgogKiBAc2VlIHNubXBfYWxhcm1fcmVnaXN0ZXJfaHIKICogQHNlZSBzbm1wX2FsYXJtX3VucmVnaXN0ZXJfYWxsCiAqLwp2b2lkCnNubXBfYWxhcm1fdW5yZWdpc3Rlcih1bnNpZ25lZCBpbnQgY2xpZW50cmVnKQp7CiAgICBzdHJ1Y3Qgc25tcF9hbGFybSAqc2FfcHRyLCAqKnByZXZOZXh0ID0gJnRoZWFsYXJtczsKCiAgICBmb3IgKHNhX3B0ciA9IHRoZWFsYXJtczsKICAgICAgICAgc2FfcHRyICE9IE5VTEwgJiYgc2FfcHRyLT5jbGllbnRyZWcgIT0gY2xpZW50cmVnOwogICAgICAgICBzYV9wdHIgPSBzYV9wdHItPm5leHQpIHsKICAgICAgICBwcmV2TmV4dCA9ICYoc2FfcHRyLT5uZXh0KTsKICAgIH0KCiAgICBpZiAoc2FfcHRyICE9IE5VTEwpIHsKICAgICAgICAqcHJldk5leHQgPSBzYV9wdHItPm5leHQ7CiAgICAgICAgREVCVUdNU0dUTCgoInNubXBfYWxhcm0iLCAidW5yZWdpc3RlcmVkIGFsYXJtICVkXG4iLCAKCQkgICAgc2FfcHRyLT5jbGllbnRyZWcpKTsKICAgICAgICAvKgogICAgICAgICAqIE5vdGU6IGRvIG5vdCBmcmVlIHRoZSBjbGllbnRhcmcsIGl0J3MgdGhlIGNsaWVudCdzIHJlc3BvbnNpYmlsaXR5IAogICAgICAgICAqLwogICAgICAgIGZyZWUoc2FfcHRyKTsKICAgIH0gZWxzZSB7CiAgICAgICAgREVCVUdNU0dUTCgoInNubXBfYWxhcm0iLCAibm8gYWxhcm0gJWQgdG8gdW5yZWdpc3RlclxuIiwgY2xpZW50cmVnKSk7CiAgICB9Cn0KCi8qKgogKiBUaGlzIGZ1bmN0aW9uIHVucmVnaXN0ZXJzIGFsbCBhbGFybXMgY3VycmVudGx5IHN0b3JlZC4KICoKICogQHJldHVybiB2b2lkCiAqCiAqIEBzZWUgc25tcF9hbGFybV9yZWdpc3RlcgogKiBAc2VlIHNubXBfYWxhcm1fcmVnaXN0ZXJfaHIKICogQHNlZSBzbm1wX2FsYXJtX3VucmVnaXN0ZXIKICovCnZvaWQKc25tcF9hbGFybV91bnJlZ2lzdGVyX2FsbCh2b2lkKQp7CiAgc3RydWN0IHNubXBfYWxhcm0gKnNhX3B0ciwgKnNhX3RtcDsKCiAgZm9yIChzYV9wdHIgPSB0aGVhbGFybXM7IHNhX3B0ciAhPSBOVUxMOyBzYV9wdHIgPSBzYV90bXApIHsKICAgIHNhX3RtcCA9IHNhX3B0ci0+bmV4dDsKICAgIGZyZWUoc2FfcHRyKTsKICB9CiAgREVCVUdNU0dUTCgoInNubXBfYWxhcm0iLCAiQUxMIGFsYXJtcyB1bnJlZ2lzdGVyZWRcbiIpKTsKICB0aGVhbGFybXMgPSBOVUxMOwp9ICAKCnN0cnVjdCBzbm1wX2FsYXJtICoKc2FfZmluZF9uZXh0KHZvaWQpCnsKICAgIHN0cnVjdCBzbm1wX2FsYXJtICphLCAqbG93ZXN0ID0gTlVMTDsKCiAgICBmb3IgKGEgPSB0aGVhbGFybXM7IGEgIT0gTlVMTDsgYSA9IGEtPm5leHQpCiAgICAgICAgaWYgKCEoYS0+ZmxhZ3MgJiBTQV9GSVJFRCkKICAgICAgICAgICAgJiYgKGxvd2VzdCA9PSBOVUxMIHx8IHRpbWVyY21wKCZhLT50X25leHRNLCAmbG93ZXN0LT50X25leHRNLCA8KSkpCiAgICAgICAgICAgIGxvd2VzdCA9IGE7CgogICAgcmV0dXJuIGxvd2VzdDsKfQoKTkVUU05NUF9JTVBPUlQgc3RydWN0IHNubXBfYWxhcm0gKnNhX2ZpbmRfc3BlY2lmaWModW5zaWduZWQgaW50IGNsaWVudHJlZyk7CnN0cnVjdCBzbm1wX2FsYXJtICoKc2FfZmluZF9zcGVjaWZpYyh1bnNpZ25lZCBpbnQgY2xpZW50cmVnKQp7CiAgICBzdHJ1Y3Qgc25tcF9hbGFybSAqc2FfcHRyOwogICAgZm9yIChzYV9wdHIgPSB0aGVhbGFybXM7IHNhX3B0ciAhPSBOVUxMOyBzYV9wdHIgPSBzYV9wdHItPm5leHQpIHsKICAgICAgICBpZiAoc2FfcHRyLT5jbGllbnRyZWcgPT0gY2xpZW50cmVnKSB7CiAgICAgICAgICAgIHJldHVybiBzYV9wdHI7CiAgICAgICAgfQogICAgfQogICAgcmV0dXJuIE5VTEw7Cn0KCnZvaWQKcnVuX2FsYXJtcyh2b2lkKQp7CiAgICBzdHJ1Y3Qgc25tcF9hbGFybSAqYTsKICAgIHVuc2lnbmVkIGludCAgICBjbGllbnRyZWc7CiAgICBzdHJ1Y3QgdGltZXZhbCAgdF9ub3c7CgogICAgLyoKICAgICAqIExvb3AgdGhyb3VnaCBldmVyeXRoaW5nIHdlIGhhdmUgcmVwZWF0ZWRseSBsb29raW5nIGZvciB0aGUgbmV4dCB0aGluZyB0bwogICAgICogY2FsbCB1bnRpbCBhbGwgZXZlbnRzIGFyZSBmaW5hbGx5IGluIHRoZSBmdXR1cmUgYWdhaW4uICAKICAgICAqLwoKICAgIHdoaWxlICgoYSA9IHNhX2ZpbmRfbmV4dCgpKSAhPSBOVUxMKSB7CiAgICAgICAgbmV0c25tcF9nZXRfbW9ub3RvbmljX2Nsb2NrKCZ0X25vdyk7CgogICAgICAgIGlmICh0aW1lcmNtcCgmYS0+dF9uZXh0TSwgJnRfbm93LCA+KSkKICAgICAgICAgICAgcmV0dXJuOwoKICAgICAgICBjbGllbnRyZWcgPSBhLT5jbGllbnRyZWc7CiAgICAgICAgYS0+ZmxhZ3MgfD0gU0FfRklSRUQ7CiAgICAgICAgREVCVUdNU0dUTCgoInNubXBfYWxhcm0iLCAicnVuIGFsYXJtICVkXG4iLCBjbGllbnRyZWcpKTsKICAgICAgICAoKihhLT50aGVjYWxsYmFjaykpIChjbGllbnRyZWcsIGEtPmNsaWVudGFyZyk7CiAgICAgICAgREVCVUdNU0dUTCgoInNubXBfYWxhcm0iLCAiYWxhcm0gJWQgY29tcGxldGVkXG4iLCBjbGllbnRyZWcpKTsKCiAgICAgICAgYSA9IHNhX2ZpbmRfc3BlY2lmaWMoY2xpZW50cmVnKTsKICAgICAgICBpZiAoYSkgewogICAgICAgICAgICBhLT50X2xhc3RNID0gdF9ub3c7CiAgICAgICAgICAgIHRpbWVyY2xlYXIoJmEtPnRfbmV4dE0pOwogICAgICAgICAgICBhLT5mbGFncyAmPSB+U0FfRklSRUQ7CiAgICAgICAgICAgIHNhX3VwZGF0ZV9lbnRyeShhKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBERUJVR01TR1RMKCgic25tcF9hbGFybSIsICJhbGFybSAlZCBkZWxldGVkIGl0c2VsZlxuIiwKICAgICAgICAgICAgICAgICAgICAgICAgY2xpZW50cmVnKSk7CiAgICAgICAgfQogICAgfQp9CgoKClJFVFNJR1RZUEUKYWxhcm1faGFuZGxlcihpbnQgYSkKewogICAgcnVuX2FsYXJtcygpOwogICAgc2V0X2FuX2FsYXJtKCk7Cn0KCgoKLyoqCiAqIExvb2sgdXAgdGhlIHRpbWUgYXQgd2hpY2ggdGhlIG5leHQgYWxhcm0gd2lsbCBmaXJlLgogKgogKiBAcGFyYW1bb3V0XSBhbGFybV90bSBUaW1lIGF0IHdoaWNoIHRoZSBuZXh0IGFsYXJtIHdpbGwgZmlyZS4KICogQHBhcmFtW2luXSBub3cgRWFybGllc3QgdGltZSB0aGF0IHNob3VsZCBiZSB3cml0dGVuIGludG8gKmFsYXJtX3RtLgogKgogKiBAcmV0dXJuIFplcm8gaWYgbm8gYWxhcm1zIGFyZSBzY2hlZHVsZWQ7IG5vbi16ZXJvICdjbGllbnRyZWcnIHZhbHVlCiAqICAgaWRlbnRpZnlpbmcgdGhlIGZpcnN0IGFsYXJtIHRoYXQgd2lsbCBmaXJlIGlmIG9uZSBvciBtb3JlIGFsYXJtcyBhcmUKICogICBzY2hlZHVsZWQuCiAqLwppbnQKbmV0c25tcF9nZXRfbmV4dF9hbGFybV90aW1lKHN0cnVjdCB0aW1ldmFsICphbGFybV90bSwgY29uc3Qgc3RydWN0IHRpbWV2YWwgKm5vdykKewogICAgc3RydWN0IHNubXBfYWxhcm0gKnNhX3B0cjsKCiAgICBzYV9wdHIgPSBzYV9maW5kX25leHQoKTsKCiAgICBpZiAoc2FfcHRyKSB7CiAgICAgICAgbmV0c25tcF9hc3NlcnQoYWxhcm1fdG0pOwogICAgICAgIG5ldHNubXBfYXNzZXJ0KHRpbWVyaXNzZXQoJnNhX3B0ci0+dF9uZXh0TSkpOwogICAgICAgIGlmICh0aW1lcmNtcCgmc2FfcHRyLT50X25leHRNLCBub3csID4pKQogICAgICAgICAgICAqYWxhcm1fdG0gPSBzYV9wdHItPnRfbmV4dE07CiAgICAgICAgZWxzZQogICAgICAgICAgICAqYWxhcm1fdG0gPSAqbm93OwogICAgICAgIHJldHVybiBzYV9wdHItPmNsaWVudHJlZzsKICAgIH0gZWxzZSB7CiAgICAgICAgcmV0dXJuIDA7CiAgICB9Cn0KCi8qKgogKiBHZXQgdGhlIHRpbWUgdW50aWwgdGhlIG5leHQgYWxhcm0gd2lsbCBmaXJlLgogKgogKiBAcGFyYW1bb3V0XSBkZWx0YSBUaW1lIHVudGlsIHRoZSBuZXh0IGFsYXJtLgogKgogKiBAcmV0dXJuIFplcm8gaWYgbm8gYWxhcm1zIGFyZSBzY2hlZHVsZWQ7IG5vbi16ZXJvICdjbGllbnRyZWcnIHZhbHVlCiAqICAgaWRlbnRpZnlpbmcgdGhlIGZpcnN0IGFsYXJtIHRoYXQgd2lsbCBmaXJlIGlmIG9uZSBvciBtb3JlIGFsYXJtcyBhcmUKICogICBzY2hlZHVsZWQuCiAqLwppbnQKZ2V0X25leHRfYWxhcm1fZGVsYXlfdGltZShzdHJ1Y3QgdGltZXZhbCAqZGVsdGEpCnsKICAgIHN0cnVjdCB0aW1ldmFsIHRfbm93LCBhbGFybV90bTsKICAgIGludCByZXM7CgogICAgbmV0c25tcF9nZXRfbW9ub3RvbmljX2Nsb2NrKCZ0X25vdyk7CiAgICByZXMgPSBuZXRzbm1wX2dldF9uZXh0X2FsYXJtX3RpbWUoJmFsYXJtX3RtLCAmdF9ub3cpOwogICAgaWYgKHJlcykKICAgICAgICBORVRTTk1QX1RJTUVSU1VCKCZhbGFybV90bSwgJnRfbm93LCBkZWx0YSk7CiAgICByZXR1cm4gcmVzOwp9CgoKdm9pZApzZXRfYW5fYWxhcm0odm9pZCkKewogICAgc3RydWN0IHRpbWV2YWwgIGRlbHRhOwogICAgaW50ICAgICAgICAgICAgIG5leHRhbGFybSA9IGdldF9uZXh0X2FsYXJtX2RlbGF5X3RpbWUoJmRlbHRhKTsKCiAgICAvKgogICAgICogV2UgZG9uJ3QgdXNlIHNpZ25hbHMgaWYgdGhleSBhc2tlZCB1cyBuaWNlbHkgbm90IHRvLiAgSXQncyBleHBlY3RlZAogICAgICogdGhleSdsbCBjaGVjayB0aGUgbmV4dCBhbGFybSB0aW1lIGFuZCBkbyB0aGVpciBvd24gY2FsbGluZyBvZgogICAgICogcnVuX2FsYXJtcygpLiAgCiAgICAgKi8KCiAgICBpZiAobmV4dGFsYXJtICYmICFuZXRzbm1wX2RzX2dldF9ib29sZWFuKE5FVFNOTVBfRFNfTElCUkFSWV9JRCwKCQkJCQlORVRTTk1QX0RTX0xJQl9BTEFSTV9ET05UX1VTRV9TSUcpKSB7CiNpZm5kZWYgV0lOMzIKIyBpZmRlZiBIQVZFX1NFVElUSU1FUgogICAgICAgIHN0cnVjdCBpdGltZXJ2YWwgaXQ7CgogICAgICAgIGl0Lml0X3ZhbHVlID0gZGVsdGE7CiAgICAgICAgdGltZXJjbGVhcigmaXQuaXRfaW50ZXJ2YWwpOwoKICAgICAgICBzaWduYWwoU0lHQUxSTSwgYWxhcm1faGFuZGxlcik7CiAgICAgICAgc2V0aXRpbWVyKElUSU1FUl9SRUFMLCAmaXQsIE5VTEwpOwogICAgICAgIERFQlVHTVNHVEwoKCJzbm1wX2FsYXJtIiwgInNjaGVkdWxlIGFsYXJtICVkIGluICVsZC4lMDNsZCBzZWNvbmRzXG4iLAogICAgICAgICAgICAgICAgICAgIG5leHRhbGFybSwgKGxvbmcpIGRlbHRhLnR2X3NlYywgKGxvbmcpKGRlbHRhLnR2X3VzZWMgLyAxMDAwKSkpOwojIGVsc2UgIC8qIEhBVkVfU0VUSVRJTUVSICovCiMgIGlmZGVmIFNJR0FMUk0KICAgICAgICBzaWduYWwoU0lHQUxSTSwgYWxhcm1faGFuZGxlcik7CiAgICAgICAgYWxhcm0oZGVsdGEudHZfc2VjKTsKICAgICAgICBERUJVR01TR1RMKCgic25tcF9hbGFybSIsCiAgICAgICAgICAgICAgICAgICAgInNjaGVkdWxlIGFsYXJtICVkIGluIHJvdWdobHkgJWxkIHNlY29uZHNcbiIsIG5leHRhbGFybSwKICAgICAgICAgICAgICAgICAgICBkZWx0YS50dl9zZWMpKTsKIyAgZW5kaWYgIC8qIFNJR0FMUk0gKi8KIyBlbmRpZiAgLyogSEFWRV9TRVRJVElNRVIgKi8KI2VuZGlmICAvKiBXSU4zMiAqLwoKICAgIH0gZWxzZSB7CiAgICAgICAgREVCVUdNU0dUTCgoInNubXBfYWxhcm0iLCAibm8gYWxhcm1zIGZvdW5kIHRvIHNjaGVkdWxlXG4iKSk7CiAgICB9Cn0KCgovKioKICogVGhpcyBmdW5jdGlvbiByZWdpc3RlcnMgZnVuY3Rpb24gY2FsbGJhY2tzIHRvIG9jY3VyIGF0IGEgc3BlY2lmaWMgdGltZQogKiBpbiB0aGUgZnV0dXJlLgogKgogKiBAcGFyYW0gd2hlbiBpcyBhbiB1bnNpZ25lZCBpbnRlZ2VyIHNwZWNpZnlpbmcgd2hlbiB0aGUgY2FsbGJhY2sgZnVuY3Rpb24KICogICAgICAgICAgICAgd2lsbCBiZSBjYWxsZWQgaW4gc2Vjb25kcy4KICoKICogQHBhcmFtIGZsYWdzIGlzIGFuIHVuc2lnbmVkIGludGVnZXIgdGhhdCBzcGVjaWZpZXMgaG93IGZyZXF1ZW50IHRoZSBjYWxsYmFjawogKglmdW5jdGlvbiBpcyBjYWxsZWQgaW4gc2Vjb25kcy4gIFNob3VsZCBiZSBTQV9SRVBFQVQgb3IgMC4gIElmICAKICoJZmxhZ3MgIGlzICBzZXQgd2l0aCBTQV9SRVBFQVQsIHRoZW4gdGhlIHJlZ2lzdGVyZWQgY2FsbGJhY2sgZnVuY3Rpb24KICoJd2lsbCBiZSBjYWxsZWQgZXZlcnkgU0FfUkVQRUFUIHNlY29uZHMuICBJZiBmbGFncyBpcyAwIHRoZW4gdGhlIAogKglmdW5jdGlvbiB3aWxsIG9ubHkgYmUgY2FsbGVkIG9uY2UgYW5kIHRoZW4gcmVtb3ZlZCBmcm9tIHRoZSAKICoJcmVnaXN0ZXJlZCBhbGFybSBsaXN0LgogKgogKiBAcGFyYW0gdGhlY2FsbGJhY2sgaXMgYSBwb2ludGVyIFNOTVBBbGFybUNhbGxiYWNrIHdoaWNoIGlzIHRoZSBjYWxsYmFjayAKICoJZnVuY3Rpb24gYmVpbmcgc3RvcmVkIGFuZCByZWdpc3RlcmVkLgogKgogKiBAcGFyYW0gY2xpZW50YXJnIGlzIGEgdm9pZCBwb2ludGVyIHVzZWQgYnkgdGhlIGNhbGxiYWNrIGZ1bmN0aW9uLiAgVGhpcyAKICoJcG9pbnRlciBpcyBhc3NpZ25lZCB0byBzbm1wX2FsYXJtLT5jbGllbnRhcmcgYW5kIHBhc3NlZCBpbnRvIHRoZQogKgljYWxsYmFjayBmdW5jdGlvbiBmb3IgdGhlIGNsaWVudCdzIHNwZWNpZmljIG5lZWRzLgogKgogKiBAcmV0dXJuIFJldHVybnMgYSB1bmlxdWUgdW5zaWduZWQgaW50ZWdlcih3aGljaCBpcyBhbHNvIHBhc3NlZCBhcyB0aGUgZmlyc3QgCiAqCWFyZ3VtZW50IG9mIGVhY2ggY2FsbGJhY2spLCB3aGljaCBjYW4gdGhlbiBiZSB1c2VkIHRvIHJlbW92ZSB0aGUKICoJY2FsbGJhY2sgZnJvbSB0aGUgbGlzdCBhdCBhIGxhdGVyIHBvaW50IGluIHRoZSBmdXR1cmUgdXNpbmcgdGhlCiAqCXNubXBfYWxhcm1fdW5yZWdpc3RlcigpIGZ1bmN0aW9uLiAgSWYgbWVtb3J5IGNvdWxkIG5vdCBiZSBhbGxvY2F0ZWQKICoJZm9yIHRoZSBzbm1wX2FsYXJtIHN0cnVjdCAwIGlzIHJldHVybmVkLgogKgogKiBAc2VlIHNubXBfYWxhcm1fdW5yZWdpc3RlcgogKiBAc2VlIHNubXBfYWxhcm1fcmVnaXN0ZXJfaHIKICogQHNlZSBzbm1wX2FsYXJtX3VucmVnaXN0ZXJfYWxsCiAqLwp1bnNpZ25lZCBpbnQKc25tcF9hbGFybV9yZWdpc3Rlcih1bnNpZ25lZCBpbnQgd2hlbiwgdW5zaWduZWQgaW50IGZsYWdzLAogICAgICAgICAgICAgICAgICAgIFNOTVBBbGFybUNhbGxiYWNrICogdGhlY2FsbGJhY2ssIHZvaWQgKmNsaWVudGFyZykKewogICAgc3RydWN0IHRpbWV2YWwgIHQ7CgogICAgaWYgKDAgPT0gd2hlbikgewogICAgICAgIHQudHZfc2VjID0gMDsKICAgICAgICB0LnR2X3VzZWMgPSAxOwogICAgfSBlbHNlIHsKICAgICAgICB0LnR2X3NlYyA9IHdoZW47CiAgICAgICAgdC50dl91c2VjID0gMDsKICAgIH0KCiAgICByZXR1cm4gc25tcF9hbGFybV9yZWdpc3Rlcl9ocih0LCBmbGFncywgdGhlY2FsbGJhY2ssIGNsaWVudGFyZyk7Cn0KCgovKioKICogVGhpcyBmdW5jdGlvbiBvZmZlcnMgZmluZXIgZ3JhbnVsYXJpdHkgYXMgdG8gd2hlbiB0aGUgY2FsbGJhY2sgCiAqIGZ1bmN0aW9uIGlzIGNhbGxlZCBieSBtYWtpbmcgdXNlIG9mIHQtPnR2X3VzZWMgdmFsdWUgZm9ybWluZyB0aGUgCiAqICJ3aGVuIiBhc3BlY3Qgb2Ygc25tcF9hbGFybV9yZWdpc3RlcigpLgogKgogKiBAcGFyYW0gdCBpcyBhIHRpbWV2YWwgc3RydWN0dXJlIHVzZWQgdG8gc3BlY2lmeSB3aGVuIHRoZSBjYWxsYmFjayAKICoJZnVuY3Rpb24oYWxhcm0pIHdpbGwgYmUgY2FsbGVkLiAgQWRkcyB0aGUgYWJpbGl0eSB0byBzcGVjaWZ5CiAqCW1pY3Jvc2Vjb25kcy4gIHQudHZfc2VjIGFuZCB0LnR2X3VzZWMgYXJlIGFzc2lnbmVkCiAqCXRvIHNubXBfYWxhcm0tPnR2X3NlYyBhbmQgc25tcF9hbGFybS0+dHZfdXNlYyByZXNwZWN0aXZlbHkgaW50ZXJuYWxseS4KICoJVGhlIHNubXBfYWxhcm1fcmVnaXN0ZXIgZnVuY3Rpb24gb25seSBhc3NpZ25zIHNlY29uZHMoaXQncyB3aGVuIAogKglhcmd1bWVudCkuCiAqCiAqIEBwYXJhbSBmbGFncyBpcyBhbiB1bnNpZ25lZCBpbnRlZ2VyIHRoYXQgc3BlY2lmaWVzIGhvdyBmcmVxdWVudCB0aGUgY2FsbGJhY2sKICoJZnVuY3Rpb24gaXMgY2FsbGVkIGluIHNlY29uZHMuICBTaG91bGQgYmUgU0FfUkVQRUFUIG9yIE5VTEwuICBJZiAgCiAqCWZsYWdzICBpcyAgc2V0IHdpdGggU0FfUkVQRUFULCB0aGVuIHRoZSByZWdpc3RlcmVkIGNhbGxiYWNrIGZ1bmN0aW9uCiAqCXdpbGwgYmUgY2FsbGVkIGV2ZXJ5IFNBX1JFUEVBVCBzZWNvbmRzLiAgSWYgZmxhZ3MgaXMgTlVMTCB0aGVuIHRoZSAKICoJZnVuY3Rpb24gd2lsbCBvbmx5IGJlIGNhbGxlZCBvbmNlIGFuZCB0aGVuIHJlbW92ZWQgZnJvbSB0aGUgCiAqCXJlZ2lzdGVyZWQgYWxhcm0gbGlzdC4KICoKICogQHBhcmFtIGNiIGlzIGEgcG9pbnRlciBTTk1QQWxhcm1DYWxsYmFjayB3aGljaCBpcyB0aGUgY2FsbGJhY2sgCiAqCWZ1bmN0aW9uIGJlaW5nIHN0b3JlZCBhbmQgcmVnaXN0ZXJlZC4KICoKICogQHBhcmFtIGNkIGlzIGEgdm9pZCBwb2ludGVyIHVzZWQgYnkgdGhlIGNhbGxiYWNrIGZ1bmN0aW9uLiAgVGhpcyAKICoJcG9pbnRlciBpcyBhc3NpZ25lZCB0byBzbm1wX2FsYXJtLT5jbGllbnRhcmcgYW5kIHBhc3NlZCBpbnRvIHRoZQogKgljYWxsYmFjayBmdW5jdGlvbiBmb3IgdGhlIGNsaWVudCdzIHNwZWNpZmljIG5lZWRzLgogKgogKiBAcmV0dXJuIFJldHVybnMgYSB1bmlxdWUgdW5zaWduZWQgaW50ZWdlcih3aGljaCBpcyBhbHNvIHBhc3NlZCBhcyB0aGUgZmlyc3QgCiAqCWFyZ3VtZW50IG9mIGVhY2ggY2FsbGJhY2spLCB3aGljaCBjYW4gdGhlbiBiZSB1c2VkIHRvIHJlbW92ZSB0aGUKICoJY2FsbGJhY2sgZnJvbSB0aGUgbGlzdCBhdCBhIGxhdGVyIHBvaW50IGluIHRoZSBmdXR1cmUgdXNpbmcgdGhlCiAqCXNubXBfYWxhcm1fdW5yZWdpc3RlcigpIGZ1bmN0aW9uLiAgSWYgbWVtb3J5IGNvdWxkIG5vdCBiZSBhbGxvY2F0ZWQKICoJZm9yIHRoZSBzbm1wX2FsYXJtIHN0cnVjdCAwIGlzIHJldHVybmVkLgogKgogKiBAc2VlIHNubXBfYWxhcm1fcmVnaXN0ZXIKICogQHNlZSBzbm1wX2FsYXJtX3VucmVnaXN0ZXIKICogQHNlZSBzbm1wX2FsYXJtX3VucmVnaXN0ZXJfYWxsCiAqLwp1bnNpZ25lZCBpbnQKc25tcF9hbGFybV9yZWdpc3Rlcl9ocihzdHJ1Y3QgdGltZXZhbCB0LCB1bnNpZ25lZCBpbnQgZmxhZ3MsCiAgICAgICAgICAgICAgICAgICAgICAgU05NUEFsYXJtQ2FsbGJhY2sgKiBjYiwgdm9pZCAqY2QpCnsKICAgIHN0cnVjdCBzbm1wX2FsYXJtICoqcyA9IE5VTEw7CgogICAgZm9yIChzID0gJih0aGVhbGFybXMpOyAqcyAhPSBOVUxMOyBzID0gJigoKnMpLT5uZXh0KSk7CgogICAgKnMgPSBTTk1QX01BTExPQ19TVFJVQ1Qoc25tcF9hbGFybSk7CiAgICBpZiAoKnMgPT0gTlVMTCkgewogICAgICAgIHJldHVybiAwOwogICAgfQoKICAgICgqcyktPnQgPSB0OwogICAgKCpzKS0+ZmxhZ3MgPSBmbGFnczsKICAgICgqcyktPmNsaWVudGFyZyA9IGNkOwogICAgKCpzKS0+dGhlY2FsbGJhY2sgPSBjYjsKICAgICgqcyktPmNsaWVudHJlZyA9IHJlZ251bSsrOwogICAgKCpzKS0+bmV4dCA9IE5VTEw7CgogICAgc2FfdXBkYXRlX2VudHJ5KCpzKTsKCiAgICBERUJVR01TR1RMKCgic25tcF9hbGFybSIsCiAgICAgICAgICAgICAgICAicmVnaXN0ZXJlZCBhbGFybSAlZCwgdCA9ICVsZC4lMDNsZCwgZmxhZ3M9MHglMDJ4XG4iLAogICAgICAgICAgICAgICAgKCpzKS0+Y2xpZW50cmVnLCAobG9uZykgKCpzKS0+dC50dl9zZWMsIChsb25nKSgoKnMpLT50LnR2X3VzZWMgLyAxMDAwKSwKICAgICAgICAgICAgICAgICgqcyktPmZsYWdzKSk7CgogICAgaWYgKHN0YXJ0X2FsYXJtcykgewogICAgICAgIHNldF9hbl9hbGFybSgpOwogICAgfQoKICAgIHJldHVybiAoKnMpLT5jbGllbnRyZWc7Cn0KCi8qKgogKiBUaGlzIGZ1bmN0aW9uIHJlc2V0cyBhbiBleGlzdGluZyBhbGFybS4KICoKICogQHBhcmFtIGNsaWVudHJlZyBpcyBhIHVuaXF1ZSB1bnNpZ25lZCBpbnRlZ2VyIHJlcHJlc2VudGluZyBhIHJlZ2lzdGVyZWQKICoJYWxhcm0gd2hpY2ggdGhlIGNsaWVudCB3YW50cyB0byB1bnJlZ2lzdGVyLgogKgogKiBAcmV0dXJuIDAgb24gc3VjY2VzcywgLTEgaWYgdGhlIGFsYXJtIHdhcyBub3QgZm91bmQKICoKICogQHNlZSBzbm1wX2FsYXJtX3JlZ2lzdGVyCiAqIEBzZWUgc25tcF9hbGFybV9yZWdpc3Rlcl9ocgogKiBAc2VlIHNubXBfYWxhcm1fdW5yZWdpc3RlcgogKi8KaW50CnNubXBfYWxhcm1fcmVzZXQodW5zaWduZWQgaW50IGNsaWVudHJlZykKewogICAgc3RydWN0IHNubXBfYWxhcm0gKmE7CiAgICBzdHJ1Y3QgdGltZXZhbCAgdF9ub3c7CiAgICBpZiAoKGEgPSBzYV9maW5kX3NwZWNpZmljKGNsaWVudHJlZykpICE9IE5VTEwpIHsKICAgICAgICBuZXRzbm1wX2dldF9tb25vdG9uaWNfY2xvY2soJnRfbm93KTsKICAgICAgICBhLT50X2xhc3RNLnR2X3NlYyA9IHRfbm93LnR2X3NlYzsKICAgICAgICBhLT50X2xhc3RNLnR2X3VzZWMgPSB0X25vdy50dl91c2VjOwogICAgICAgIGEtPnRfbmV4dE0udHZfc2VjID0gMDsKICAgICAgICBhLT50X25leHRNLnR2X3VzZWMgPSAwOwogICAgICAgIE5FVFNOTVBfVElNRVJBREQoJnRfbm93LCAmYS0+dCwgJmEtPnRfbmV4dE0pOwogICAgICAgIHJldHVybiAwOwogICAgfQogICAgREVCVUdNU0dUTCgoInNubXBfYWxhcm1fcmVzZXQiLCAiYWxhcm0gJWQgbm90IGZvdW5kXG4iLAogICAgICAgICAgICAgICAgY2xpZW50cmVnKSk7CiAgICByZXR1cm4gLTE7Cn0KLyoqICBAfSAqLwo=