LyoKICogRE9TIChNWikgbG9hZGVyCiAqCiAqIENvcHlyaWdodCAxOTk4IE92ZSBL5XZlbgogKgogKiBUaGlzIGNvZGUgaGFzbid0IGJlZW4gY29tcGxldGVseSBjbGVhbmVkIHVwIHlldC4KICovCgojaW5jbHVkZSA8c3RkaW8uaD4KI2luY2x1ZGUgPHN0ZGxpYi5oPgojaW5jbHVkZSA8c3RyaW5nLmg+CiNpbmNsdWRlIDxlcnJuby5oPgojaW5jbHVkZSA8ZmNudGwuaD4KI2luY2x1ZGUgPHNpZ25hbC5oPgojaW5jbHVkZSA8dW5pc3RkLmg+CiNpbmNsdWRlIDxzeXMvdHlwZXMuaD4KI2luY2x1ZGUgPHN5cy9zdGF0Lmg+CiNpbmNsdWRlIDxzeXMvdGltZS5oPgojaW5jbHVkZSAid2luZGVmLmgiCiNpbmNsdWRlICJ3aW5lL3dpbmJhc2UxNi5oIgojaW5jbHVkZSAid2luZXJyb3IuaCIKI2luY2x1ZGUgIm1vZHVsZS5oIgojaW5jbHVkZSAicGVleGUuaCIKI2luY2x1ZGUgIm5lZXhlLmgiCiNpbmNsdWRlICJ0YXNrLmgiCiNpbmNsdWRlICJzZWxlY3RvcnMuaCIKI2luY2x1ZGUgImZpbGUuaCIKI2luY2x1ZGUgImxkdC5oIgojaW5jbHVkZSAicHJvY2Vzcy5oIgojaW5jbHVkZSAibWlzY2VtdS5oIgojaW5jbHVkZSAiZGVidWcuaCIKI2luY2x1ZGUgImRvc2V4ZS5oIgojaW5jbHVkZSAiZG9zbW9kLmgiCiNpbmNsdWRlICJvcHRpb25zLmgiCiNpbmNsdWRlICJzZXJ2ZXIuaCIKCiNpZmRlZiBNWl9TVVBQT1JURUQKCiNpbmNsdWRlIDxzeXMvbW1hbi5oPgoKLyogZGVmaW5lIHRoaXMgdG8gdHJ5IG1hcHBpbmcgdGhyb3VnaCAvcHJvYy9waWQvbWVtIGluc3RlYWQgb2YgYSB0ZW1wIGZpbGUsCiAgIGJ1dCBMaW51cyBkb2Vzbid0IGxpa2UgbW1hcHBpbmcgL3Byb2MvcGlkL21lbSwgc28gaXQgZG9lc24ndCB3b3JrIGZvciBtZSAqLwojdW5kZWYgTVpfTUFQU0VMRgoKI2RlZmluZSBCSU9TX0RBVEFfU0VHTUVOVCAweDQwCiNkZWZpbmUgU1RBUlRfT0ZGU0VUIDAKI2RlZmluZSBQU1BfU0laRSAweDEwCgojZGVmaW5lIFNFRzE2KHB0cixzZWcpICgoTFBWT0lEKSgoQllURSopcHRyKygoRFdPUkQpKHNlZyk8PDQpKSkKI2RlZmluZSBTRUdQVFIxNihwdHIsc2VncHRyKSAoKExQVk9JRCkoKEJZVEUqKXB0cisoKERXT1JEKVNFTEVDVE9ST0Yoc2VncHRyKTw8NCkrT0ZGU0VUT0Yoc2VncHRyKSkpCgpzdGF0aWMgdm9pZCBNWl9Jbml0UFNQKCBMUFZPSUQgbHBQU1AsIExQQ1NUUiBjbWRsaW5lLCBXT1JEIGVudiApCnsKIFBEQjE2KnBzcD1scFBTUDsKIGNvbnN0IGNoYXIqY21kPWNtZGxpbmU/c3RyY2hyKGNtZGxpbmUsJyAnKTpOVUxMOwoKIHBzcC0+aW50MjA9MHgyMENEOyAvKiBpbnQgMjAgKi8KIC8qIHNvbWUgcHJvZ3JhbXMgdXNlIHRoaXMgdG8gY2FsY3VsYXRlIGhvdyBtdWNoIG1lbW9yeSB0aGV5IG5lZWQgKi8KIHBzcC0+bmV4dFBhcmFncmFwaD0weDlGRkY7CiBwc3AtPmVudmlyb25tZW50PWVudjsKIC8qIGNvcHkgcGFyYW1ldGVycyAqLwogaWYgKGNtZCkgewojaWYgMAogIC8qIGNvbW1hbmQuY29tIGRvZXNuJ3QgZG8gdGhpcyAqLwogIHdoaWxlICgqY21kID09ICcgJykgY21kKys7CiNlbmRpZgogIHBzcC0+Y21kTGluZVswXT1zdHJsZW4oY21kKTsKICBzdHJjcHkocHNwLT5jbWRMaW5lKzEsY21kKTsKICBwc3AtPmNtZExpbmVbcHNwLT5jbWRMaW5lWzBdKzFdPSdccic7CiB9IGVsc2UgcHNwLT5jbWRMaW5lWzFdPSdccic7CiAvKiBGSVhNRTogaW50ZWdyYXRlIHRoZSBtZW1vcnkgc3R1ZmYgZnJvbSBXaW5lIChtc2Rvcy9kb3NtZW0uYykgKi8KIC8qIEZJWE1FOiBpbnRlZ3JhdGUgdGhlIFBEQiBzdHVmZiBmcm9tIFdpbmUgKGxvYWRlci90YXNrLmMpICovCn0KCi8qIGRlZmF1bHQgSU5UIDA4IGhhbmRsZXI6IGluY3JlYXNlcyB0aW1lciB0aWNrIGNvdW50ZXIgYnV0IG5vdCBtdWNoIG1vcmUgKi8Kc3RhdGljIGNoYXIgaW50MDhbXT17CiAweENELDB4MUMsICAgICAgICAgICAvKiBpbnQgJDB4MWMgKi8KIDB4NTAsICAgICAgICAgICAgICAgIC8qIHB1c2h3ICVheCAqLwogMHgxRSwgICAgICAgICAgICAgICAgLyogcHVzaHcgJWRzICovCiAweEI4LDB4NDAsMHgwMCwgICAgICAvKiBtb3Z3ICQweDQwLCVheCAqLwogMHg4RSwweEQ4LCAgICAgICAgICAgLyogbW92dyAlYXgsJWRzICovCiNpZiAwCiAweDgzLDB4MDYsMHg2QywweDAwLDB4MDEsIC8qIGFkZHcgJDEsKDB4NmMpICovCiAweDgzLDB4MTYsMHg2RSwweDAwLDB4MDAsIC8qIGFkY3cgJDAsKDB4NmUpICovCiNlbHNlCiAweDY2LDB4RkYsMHgwNiwweDZDLDB4MDAsIC8qIGluY2wgKDB4NmMpICovCiNlbmRpZgogMHhCMCwweDIwLCAgICAgICAgICAgLyogbW92YiAkMHgyMCwlYWwgKi8KIDB4RTYsMHgyMCwgICAgICAgICAgIC8qIG91dGIgJWFsLCQweDIwICovCiAweDFGLCAgICAgICAgICAgICAgICAvKiBwb3B3ICVheCAqLwogMHg1OCwgICAgICAgICAgICAgICAgLyogcG9wdyAlYXggKi8KIDB4Q0YgICAgICAgICAgICAgICAgIC8qIGlyZXQgKi8KfTsKCnN0YXRpYyB2b2lkIE1aX0luaXRIYW5kbGVycyggTFBET1NUQVNLIGxwRG9zVGFzayApCnsKIFdPUkQgc2VnOwogTFBCWVRFIHN0YXJ0PURPU01FTV9HZXRCbG9jayhscERvc1Rhc2stPmhNb2R1bGUsc2l6ZW9mKGludDA4KSwmc2VnKTsKIG1lbWNweShzdGFydCxpbnQwOCxzaXplb2YoaW50MDgpKTsKLyogSU5UIDA4OiBwb2ludCBpdCBhdCBvdXIgdGljay1pbmNyZW1lbnRpbmcgaGFuZGxlciAqLwogKChTRUdQVFIqKShscERvc1Rhc2stPmltZykpWzB4MDhdPVBUUl9TRUdfT0ZGX1RPX1NFR1BUUihzZWcsMCk7Ci8qIElOVCAxQzoganVzdCBwb2ludCBpdCB0byBJUkVULCB3ZSBkb24ndCB3YW50IHRvIGhhbmRsZSBpdCBvdXJzZWx2ZXMgKi8KICgoU0VHUFRSKikobHBEb3NUYXNrLT5pbWcpKVsweDFDXT1QVFJfU0VHX09GRl9UT19TRUdQVFIoc2VnLHNpemVvZihpbnQwOCktMSk7Cn0KCnN0YXRpYyBjaGFyIGVudGVyX3htc1tdPXsKLyogWE1TIGhvb2thYmxlIGVudHJ5IHBvaW50ICovCiAweEVCLDB4MDMsICAgICAgICAgICAvKiBqbXAgZW50cnkgKi8KIDB4OTAsMHg5MCwweDkwLCAgICAgIC8qIG5vcDtub3A7bm9wICovCiAgICAgICAgICAgICAgICAgICAgICAvKiBlbnRyeTogKi8KLyogcmVhbCBlbnRyeSBwb2ludCAqLwovKiBmb3Igc2ltcGxpY2l0eSwgd2UnbGwganVzdCB1c2UgdGhlIHNhbWUgaG9vayBhcyBEUE1JIGJlbG93ICovCiAweENELDB4MzEsICAgICAgICAgICAvKiBpbnQgJDB4MzEgKi8KIDB4Q0IgICAgICAgICAgICAgICAgIC8qIGxyZXQgKi8KfTsKCnN0YXRpYyB2b2lkIE1aX0luaXRYTVMoIExQRE9TVEFTSyBscERvc1Rhc2sgKQp7CiBMUEJZVEUgc3RhcnQ9RE9TTUVNX0dldEJsb2NrKGxwRG9zVGFzay0+aE1vZHVsZSxzaXplb2YoZW50ZXJfeG1zKSwmKGxwRG9zVGFzay0+eG1zX3NlZykpOwogbWVtY3B5KHN0YXJ0LGVudGVyX3htcyxzaXplb2YoZW50ZXJfeG1zKSk7Cn0KCnN0YXRpYyBjaGFyIGVudGVyX3BtW109ewogMHg1MCwgICAgICAgICAgICAgICAgLyogcHVzaHcgJWF4ICovCiAweDUyLCAgICAgICAgICAgICAgICAvKiBwdXNodyAlZHggKi8KIDB4NTUsICAgICAgICAgICAgICAgIC8qIHB1c2h3ICVicCAqLwogMHg4OSwweEU1LCAgICAgICAgICAgLyogbW92dyAlc3AsJWJwICovCi8qIGdldCByZXR1cm4gQ1MgKi8KIDB4OEIsMHg1NiwweDA4LCAgICAgIC8qIG1vdncgOCglYnApLCVkeCAqLwovKiBqdXN0IGNhbGwgaW50IDMxIGhlcmUgdG8gZ2V0IGludG8gcHJvdGVjdGVkIG1vZGUuLi4gKi8KLyogaXQnbGwgY2hlY2sgd2hldGhlciBpdCB3YXMgY2FsbGVkIGZyb20gZHBtaV9zZWcuLi4gKi8KIDB4Q0QsMHgzMSwgICAgICAgICAgIC8qIGludCAkMHgzMSAqLwovKiB3ZSBhcmUgbm93IGluIHRoZSBjb250ZXh0IG9mIGEgMTYtYml0IHJlbGF5IGNhbGwgKi8KLyogbmVlZCB0byBmaXh1cCBvdXIgc3RhY2s7CiAqIDE2LWJpdCByZWxheSByZXR1cm4gYWRkcmVzcyB3aWxsIGJlIGxvc3QsIGJ1dCB3ZSB3b24ndCB3b3JyeSBxdWl0ZSB5ZXQgKi8KIDB4OEUsMHhEMCwgICAgICAgICAgIC8qIG1vdncgJWF4LCVzcyAqLwogMHg2NiwweDBGLDB4QjcsMHhFNSwgLyogbW92endsICVicCwlZXNwICovCi8qIHNldCByZXR1cm4gQ1MgKi8KIDB4ODksMHg1NiwweDA4LCAgICAgIC8qIG1vdncgJWR4LDgoJWJwKSAqLwogMHg1RCwgICAgICAgICAgICAgICAgLyogcG9wdyAlYnAgKi8KIDB4NUEsICAgICAgICAgICAgICAgIC8qIHBvcHcgJWR4ICovCiAweDU4LCAgICAgICAgICAgICAgICAvKiBwb3B3ICVheCAqLwogMHhDQiAgICAgICAgICAgICAgICAgLyogbHJldCAqLwp9OwoKc3RhdGljIHZvaWQgTVpfSW5pdERQTUkoIExQRE9TVEFTSyBscERvc1Rhc2sgKQp7CiB1bnNpZ25lZCBzaXplPXNpemVvZihlbnRlcl9wbSk7CiBMUEJZVEUgc3RhcnQ9RE9TTUVNX0dldEJsb2NrKGxwRG9zVGFzay0+aE1vZHVsZSxzaXplLCYobHBEb3NUYXNrLT5kcG1pX3NlZykpOwogCiBscERvc1Rhc2stPmRwbWlfc2VsID0gU0VMRUNUT1JfQWxsb2NCbG9jayggc3RhcnQsIHNpemUsIFNFR01FTlRfQ09ERSwgRkFMU0UsIEZBTFNFICk7CgogbWVtY3B5KHN0YXJ0LGVudGVyX3BtLHNpemVvZihlbnRlcl9wbSkpOwp9CgpzdGF0aWMgV09SRCBNWl9Jbml0RW52aXJvbm1lbnQoIExQRE9TVEFTSyBscERvc1Rhc2ssIExQQ1NUUiBlbnYsIExQQ1NUUiBuYW1lICkKewogdW5zaWduZWQgc3o9MDsKIFdPUkQgc2VnOwogTFBTVFIgZW52YmxrOwoKIGlmIChlbnYpIHsKICAvKiBnZXQgc2l6ZSBvZiBlbnZpcm9ubWVudCBibG9jayAqLwogIHdoaWxlIChlbnZbc3orK10pIHN6Kz1zdHJsZW4oZW52K3N6KSsxOwogfSBlbHNlIHN6Kys7CiAvKiBhbGxvY2F0ZSBpdCAqLwogZW52YmxrPURPU01FTV9HZXRCbG9jayhscERvc1Rhc2stPmhNb2R1bGUsc3orc2l6ZW9mKFdPUkQpK3N0cmxlbihuYW1lKSsxLCZzZWcpOwogLyogZmlsbCBpdCAqLwogaWYgKGVudikgewogIG1lbWNweShlbnZibGssZW52LHN6KTsKIH0gZWxzZSBlbnZibGtbMF09MDsKIC8qIERPUyAzLng6IHRoZSBibG9jayBjb250YWlucyAxIGFkZGl0aW9uYWwgc3RyaW5nICovCiAqKFdPUkQqKShlbnZibGsrc3opPTE7CiAvKiBiZWluZyB0aGUgcHJvZ3JhbSBuYW1lIGl0c2VsZiAqLwogc3RyY3B5KGVudmJsaytzeitzaXplb2YoV09SRCksbmFtZSk7CiByZXR1cm4gc2VnOwp9CgpzdGF0aWMgQk9PTCBNWl9Jbml0TWVtb3J5KCBMUERPU1RBU0sgbHBEb3NUYXNrLCBORV9NT0RVTEUgKnBNb2R1bGUgKQp7CiBpbnQgeDsKCiBpZiAobHBEb3NUYXNrLT5pbWdfb2ZzKSByZXR1cm4gVFJVRTsgLyogYWxyZWFkeSBhbGxvY2F0ZWQgKi8KCiAvKiBhbGxvY2F0ZSAxTUIrNjRLIHNoYXJlZCBtZW1vcnkgKi8KIGxwRG9zVGFzay0+aW1nX29mcz1TVEFSVF9PRkZTRVQ7CiNpZmRlZiBNWl9NQVBTRUxGCiBscERvc1Rhc2stPmltZz1WaXJ0dWFsQWxsb2MoTlVMTCwweDExMDAwMCxNRU1fQ09NTUlULFBBR0VfUkVBRFdSSVRFKTsKIC8qIG1ha2Ugc3VyZSBtbWFwIGFjY2VwdHMgaXQgKi8KICgoY2hhciopbHBEb3NUYXNrLT5pbWcpWzB4MTBGRkZGXT0wOwojZWxzZQogdG1wbmFtKGxwRG9zVGFzay0+bW1fbmFtZSk7Ci8qIHN0cmNweShscERvc1Rhc2stPm1tX25hbWUsIi90bXAvbXlkb3NpbWFnZSIpOyAqLwogbHBEb3NUYXNrLT5tbV9mZD1vcGVuKGxwRG9zVGFzay0+bW1fbmFtZSxPX1JEV1J8T19DUkVBVCAvKiB8T19UUlVOQyAqLyxTX0lSVVNSfFNfSVdVU1IpOwogaWYgKGxwRG9zVGFzay0+bW1fZmQ8MCkgRVJSKG1vZHVsZSwiZmlsZSAlcyBjb3VsZCBub3QgYmUgb3BlbmVkXG4iLGxwRG9zVGFzay0+bW1fbmFtZSk7CiAvKiBleHBhbmQgZmlsZSB0byAxTUIrNjRLICovCiBsc2VlayhscERvc1Rhc2stPm1tX2ZkLDB4MTEwMDAwLTEsU0VFS19TRVQpOwogeD0wOyB3cml0ZShscERvc1Rhc2stPm1tX2ZkLCZ4LDEpOwogLyogbWFwIGl0IGluICovCiBscERvc1Rhc2stPmltZz1tbWFwKE5VTEwsMHgxMTAwMDAtU1RBUlRfT0ZGU0VULFBST1RfUkVBRHxQUk9UX1dSSVRFLE1BUF9TSEFSRUQsbHBEb3NUYXNrLT5tbV9mZCwwKTsKI2VuZGlmCiBpZiAobHBEb3NUYXNrLT5pbWc9PShMUFZPSUQpLTEpIHsKICBFUlIobW9kdWxlLCJjb3VsZCBub3QgbWFwIHNoYXJlZCBtZW1vcnksIGVycm9yPSVzXG4iLHN0cmVycm9yKGVycm5vKSk7CiAgcmV0dXJuIEZBTFNFOwogfQogVFJBQ0UobW9kdWxlLCJET1MgVk04NiBpbWFnZSBtYXBwZWQgYXQgJTA4bHhcbiIsKERXT1JEKWxwRG9zVGFzay0+aW1nKTsKIHBNb2R1bGUtPmRvc19pbWFnZT1scERvc1Rhc2stPmltZzsKCiAvKiBpbml0aWFsaXplIHRoZSBtZW1vcnkgKi8KIFRSQUNFKG1vZHVsZSwiSW5pdGlhbGl6aW5nIERPUyBtZW1vcnkgc3RydWN0dXJlc1xuIik7CiBET1NNRU1fSW5pdChscERvc1Rhc2stPmhNb2R1bGUpOwogTVpfSW5pdEhhbmRsZXJzKGxwRG9zVGFzayk7CiBNWl9Jbml0WE1TKGxwRG9zVGFzayk7CiBNWl9Jbml0RFBNSShscERvc1Rhc2spOwogcmV0dXJuIFRSVUU7Cn0KCnN0YXRpYyBCT09MIE1aX0xvYWRJbWFnZSggSEZJTEUgaEZpbGUsIE9GU1RSVUNUICpvZnMsIExQQ1NUUiBjbWRsaW5lLAogICAgICAgICAgICAgICAgICAgICAgICAgIExQQ1NUUiBlbnYsIExQRE9TVEFTSyBscERvc1Rhc2ssIE5FX01PRFVMRSAqcE1vZHVsZSApCnsKIElNQUdFX0RPU19IRUFERVIgbXpfaGVhZGVyOwogRFdPUkQgaW1hZ2Vfc3RhcnQsaW1hZ2Vfc2l6ZSxtaW5fc2l6ZSxtYXhfc2l6ZSxhdmFpbDsKIEJZVEUqcHNwX3N0YXJ0LCpsb2FkX3N0YXJ0OwogaW50IHgsb2xkX2NvbT0wOwogU0VHUFRSIHJlbG9jOwogV09SRCBlbnZfc2VnOwoKIF9sbHNlZWsoaEZpbGUsMCxGSUxFX0JFR0lOKTsKIGlmICgoX2xyZWFkKGhGaWxlLCZtel9oZWFkZXIsc2l6ZW9mKG16X2hlYWRlcikpICE9IHNpemVvZihtel9oZWFkZXIpKSB8fAogICAgIChtel9oZWFkZXIuZV9tYWdpYyAhPSBJTUFHRV9ET1NfU0lHTkFUVVJFKSkgewogIG9sZF9jb209MTsgLyogYXNzdW1lIC5DT00gZmlsZSAqLwogIGltYWdlX3N0YXJ0PTA7CiAgaW1hZ2Vfc2l6ZT1HZXRGaWxlU2l6ZShoRmlsZSxOVUxMKTsKICBtaW5fc2l6ZT0weDEwMDAwOyBtYXhfc2l6ZT0weDEwMDAwMDsKICBtel9oZWFkZXIuZV9jcmxjPTA7CiAgbXpfaGVhZGVyLmVfc3M9MDsgbXpfaGVhZGVyLmVfc3A9MHhGRkZFOwogIG16X2hlYWRlci5lX2NzPTA7IG16X2hlYWRlci5lX2lwPTB4MTAwOwogfSBlbHNlIHsKICAvKiBjYWxjdWxhdGUgbG9hZCBzaXplICovCiAgaW1hZ2Vfc3RhcnQ9bXpfaGVhZGVyLmVfY3Bhcmhkcjw8NDsKICBpbWFnZV9zaXplPW16X2hlYWRlci5lX2NwPDw5OyAvKiBwYWdlcyBhcmUgNTEyIGJ5dGVzICovCiAgaWYgKChtel9oZWFkZXIuZV9jYmxwIT0wKSYmKG16X2hlYWRlci5lX2NibHAhPTQpKSBpbWFnZV9zaXplLT01MTItbXpfaGVhZGVyLmVfY2JscDsKICBpbWFnZV9zaXplLT1pbWFnZV9zdGFydDsKICBtaW5fc2l6ZT1pbWFnZV9zaXplKygoRFdPUkQpbXpfaGVhZGVyLmVfbWluYWxsb2M8PDQpKyhQU1BfU0laRTw8NCk7CiAgbWF4X3NpemU9aW1hZ2Vfc2l6ZSsoKERXT1JEKW16X2hlYWRlci5lX21heGFsbG9jPDw0KSsoUFNQX1NJWkU8PDQpOwogfQoKIE1aX0luaXRNZW1vcnkobHBEb3NUYXNrLHBNb2R1bGUpOwoKIC8qIGFsbG9jYXRlIGVudmlyb25tZW50IGJsb2NrICovCiBlbnZfc2VnPU1aX0luaXRFbnZpcm9ubWVudChscERvc1Rhc2ssZW52LG9mcy0+c3pQYXRoTmFtZSk7CgogLyogYWxsb2NhdGUgbWVtb3J5IGZvciB0aGUgZXhlY3V0YWJsZSAqLwogVFJBQ0UobW9kdWxlLCJBbGxvY2F0aW5nIERPUyBtZW1vcnkgKG1pbj0lbGQsIG1heD0lbGQpXG4iLG1pbl9zaXplLG1heF9zaXplKTsKIGF2YWlsPURPU01FTV9BdmFpbGFibGUobHBEb3NUYXNrLT5oTW9kdWxlKTsKIGlmIChhdmFpbDxtaW5fc2l6ZSkgewogIEVSUihtb2R1bGUsICJpbnN1ZmZpY2llbnQgRE9TIG1lbW9yeVxuIik7CiAgU2V0TGFzdEVycm9yKEVSUk9SX05PVF9FTk9VR0hfTUVNT1JZKTsKICByZXR1cm4gRkFMU0U7CiB9CiBpZiAoYXZhaWw+bWF4X3NpemUpIGF2YWlsPW1heF9zaXplOwogcHNwX3N0YXJ0PURPU01FTV9HZXRCbG9jayhscERvc1Rhc2stPmhNb2R1bGUsYXZhaWwsJmxwRG9zVGFzay0+cHNwX3NlZyk7CiBpZiAoIXBzcF9zdGFydCkgewogIEVSUihtb2R1bGUsICJlcnJvciBhbGxvY2F0aW5nIERPUyBtZW1vcnlcbiIpOwogIFNldExhc3RFcnJvcihFUlJPUl9OT1RfRU5PVUdIX01FTU9SWSk7CiAgcmV0dXJuIEZBTFNFOwogfQogbHBEb3NUYXNrLT5sb2FkX3NlZz1scERvc1Rhc2stPnBzcF9zZWcrKG9sZF9jb20/MDpQU1BfU0laRSk7CiBsb2FkX3N0YXJ0PXBzcF9zdGFydCsoUFNQX1NJWkU8PDQpOwogTVpfSW5pdFBTUChwc3Bfc3RhcnQsIGNtZGxpbmUsIGVudl9zZWcpOwoKIC8qIGxvYWQgZXhlY3V0YWJsZSBpbWFnZSAqLwogVFJBQ0UobW9kdWxlLCJsb2FkaW5nIERPUyAlcyBpbWFnZSwgJTA4bHggYnl0ZXNcbiIsb2xkX2NvbT8iQ09NIjoiRVhFIixpbWFnZV9zaXplKTsKIF9sbHNlZWsoaEZpbGUsaW1hZ2Vfc3RhcnQsRklMRV9CRUdJTik7CiBpZiAoKF9scmVhZChoRmlsZSxsb2FkX3N0YXJ0LGltYWdlX3NpemUpKSAhPSBpbWFnZV9zaXplKSB7CiAgU2V0TGFzdEVycm9yKEVSUk9SX0JBRF9GT1JNQVQpOwogIHJldHVybiBGQUxTRTsKIH0KCiBpZiAobXpfaGVhZGVyLmVfY3JsYykgewogIC8qIGxvYWQgcmVsb2NhdGlvbiB0YWJsZSAqLwogIFRSQUNFKG1vZHVsZSwibG9hZGluZyBET1MgRVhFIHJlbG9jYXRpb24gdGFibGUsICVkIGVudHJpZXNcbiIsbXpfaGVhZGVyLmVfY3JsYyk7CiAgLyogRklYTUU6IGlzIHRoaXMgdG9vIHNsb3cgd2l0aG91dCByZWFkIGJ1ZmZlcmluZz8gKi8KICBfbGxzZWVrKGhGaWxlLG16X2hlYWRlci5lX2xmYXJsYyxGSUxFX0JFR0lOKTsKICBmb3IgKHg9MDsgeDxtel9oZWFkZXIuZV9jcmxjOyB4KyspIHsKICAgaWYgKF9scmVhZChoRmlsZSwmcmVsb2Msc2l6ZW9mKHJlbG9jKSkgIT0gc2l6ZW9mKHJlbG9jKSkgewogICAgU2V0TGFzdEVycm9yKEVSUk9SX0JBRF9GT1JNQVQpOwogICAgcmV0dXJuIEZBTFNFOwogICB9CiAgICooV09SRCopU0VHUFRSMTYobG9hZF9zdGFydCxyZWxvYykrPWxwRG9zVGFzay0+bG9hZF9zZWc7CiAgfQogfQoKIGxwRG9zVGFzay0+aW5pdF9jcz1scERvc1Rhc2stPmxvYWRfc2VnK216X2hlYWRlci5lX2NzOwogbHBEb3NUYXNrLT5pbml0X2lwPW16X2hlYWRlci5lX2lwOwogbHBEb3NUYXNrLT5pbml0X3NzPWxwRG9zVGFzay0+bG9hZF9zZWcrbXpfaGVhZGVyLmVfc3M7CiBscERvc1Rhc2stPmluaXRfc3A9bXpfaGVhZGVyLmVfc3A7CgogVFJBQ0UobW9kdWxlLCJlbnRyeSBwb2ludDogJTA0eDolMDR4XG4iLGxwRG9zVGFzay0+aW5pdF9jcyxscERvc1Rhc2stPmluaXRfaXApOwogcmV0dXJuIFRSVUU7Cn0KCkxQRE9TVEFTSyBNWl9BbGxvY0RQTUlUYXNrKCBITU9EVUxFMTYgaE1vZHVsZSApCnsKIExQRE9TVEFTSyBscERvc1Rhc2sgPSBjYWxsb2MoMSwgc2l6ZW9mKERPU1RBU0spKTsKIE5FX01PRFVMRSAqcE1vZHVsZTsKCiBpZiAobHBEb3NUYXNrKSB7CiAgbHBEb3NUYXNrLT5oTW9kdWxlID0gaE1vZHVsZTsKCiAgcE1vZHVsZSA9IChORV9NT0RVTEUgKilHbG9iYWxMb2NrMTYoaE1vZHVsZSk7CiAgcE1vZHVsZS0+bHBEb3NUYXNrID0gbHBEb3NUYXNrOwogCiAgbHBEb3NUYXNrLT5pbWc9TlVMTDsgbHBEb3NUYXNrLT5tbV9uYW1lWzBdPTA7IGxwRG9zVGFzay0+bW1fZmQ9LTE7CgogIE1aX0luaXRNZW1vcnkobHBEb3NUYXNrLCBwTW9kdWxlKTsKCiAgR2xvYmFsVW5sb2NrMTYoaE1vZHVsZSk7CiB9CiByZXR1cm4gbHBEb3NUYXNrOwp9CgpzdGF0aWMgdm9pZCBNWl9Jbml0VGltZXIoIExQRE9TVEFTSyBscERvc1Rhc2ssIGludCB2ZXIgKQp7CiBpZiAodmVyPDEpIHsKICAvKiBjYW4ndCBtYWtlIHRpbWVyIHRpY2tzICovCiB9IGVsc2UgewogIGludCBmdW5jOwogIHN0cnVjdCB0aW1ldmFsIHRpbTsKCiAgLyogc3RhcnQgZG9zbW9kIHRpbWVyIGF0IDU1SHogKi8KICBmdW5jPURPU01PRF9TRVRfVElNRVI7CiAgdGltLnR2X3NlYz0wOyB0aW0udHZfdXNlYz01NDkyNTsKICB3cml0ZShscERvc1Rhc2stPndyaXRlX3BpcGUsJmZ1bmMsc2l6ZW9mKGZ1bmMpKTsKICB3cml0ZShscERvc1Rhc2stPndyaXRlX3BpcGUsJnRpbSxzaXplb2YodGltKSk7CiB9Cn0KCkJPT0wgTVpfSW5pdFRhc2soIExQRE9TVEFTSyBscERvc1Rhc2sgKQp7CiAgaW50IHdyaXRlX2ZkWzJdLHhfZmQ7CiAgcGlkX3QgY2hpbGQ7CiAgY2hhciAqZm5hbWUsKmZhcmcsYXJnWzE2XSxmcHJvY1s2NF0scGF0aFsyNTZdLCpmcGF0aDsKICBTRUNVUklUWV9BVFRSSUJVVEVTIGF0dHI9e3NpemVvZihhdHRyKSxOVUxMLFRSVUV9OwogIHN0cnVjdCBnZXRfcmVhZF9mZF9yZXF1ZXN0IHJfcmVxOwogIHN0cnVjdCBnZXRfd3JpdGVfZmRfcmVxdWVzdCB3X3JlcTsKCiAgaWYgKCFscERvc1Rhc2spIHJldHVybiBGQUxTRTsKICAvKiBjcmVhdGUgcGlwZXMgKi8KICAvKiB0aGlzIGhhcHBlbnMgaW4gdGhlIHdyb25nIHByb2Nlc3MgY29udGV4dCwgc28gd2UgaGF2ZSB0byBsZXQgdGhlIG5ldyBwcm9jZXNzCiAgICAgaW5oZXJpdCBpdC4uLiAoRklYTUU6IGNhbGwgTVpfSW5pdFRhc2sgaW4gdGhlIHJpZ2h0IHByb2Nlc3MgY29udGV4dCkgKi8KICBpZiAoIUNyZWF0ZVBpcGUoJihscERvc1Rhc2stPmhSZWFkUGlwZSksJihscERvc1Rhc2stPmhYUGlwZSksJmF0dHIsMCkpIHJldHVybiBGQUxTRTsKICBpZiAocGlwZSh3cml0ZV9mZCk8MCkgewogICAgQ2xvc2VIYW5kbGUobHBEb3NUYXNrLT5oUmVhZFBpcGUpOwogICAgQ2xvc2VIYW5kbGUobHBEb3NUYXNrLT5oWFBpcGUpOwogICAgcmV0dXJuIEZBTFNFOwogIH0KICByX3JlcS5oYW5kbGUgPSBscERvc1Rhc2stPmhSZWFkUGlwZTsKICBDTElFTlRfU2VuZFJlcXVlc3QoIFJFUV9HRVRfUkVBRF9GRCwgLTEsIDEsICZyX3JlcSwgc2l6ZW9mKHJfcmVxKSApOwogIENMSUVOVF9XYWl0UmVwbHkoIE5VTEwsICYobHBEb3NUYXNrLT5yZWFkX3BpcGUpLCAwICk7CiAgd19yZXEuaGFuZGxlID0gbHBEb3NUYXNrLT5oWFBpcGU7CiAgQ0xJRU5UX1NlbmRSZXF1ZXN0KCBSRVFfR0VUX1dSSVRFX0ZELCAtMSwgMSwgJndfcmVxLCBzaXplb2Yod19yZXEpICk7CiAgQ0xJRU5UX1dhaXRSZXBseSggTlVMTCwgJnhfZmQsIDAgKTsKCiAgVFJBQ0UobW9kdWxlLCJ3aW4zMiBwaXBlOiByZWFkPSVkLCB3cml0ZT0lZCwgdW5peCBwaXBlOiByZWFkPSVkLCB3cml0ZT0lZFxuIiwKCSAgICAgICBscERvc1Rhc2stPmhSZWFkUGlwZSxscERvc1Rhc2stPmhYUGlwZSxscERvc1Rhc2stPnJlYWRfcGlwZSx4X2ZkKTsKICBUUkFDRShtb2R1bGUsIm91dGJvdW5kIHVuaXggcGlwZTogcmVhZD0lZCwgd3JpdGU9JWQsIHBpZD0lZFxuIix3cml0ZV9mZFswXSx3cml0ZV9mZFsxXSxnZXRwaWQoKSk7CgogIGxwRG9zVGFzay0+d3JpdGVfcGlwZT13cml0ZV9mZFsxXTsKCiAvKiBpZiB3ZSBoYXZlIGEgbWFwcGluZyBmaWxlLCB1c2UgaXQgKi8KIGZuYW1lPWxwRG9zVGFzay0+bW1fbmFtZTsgZmFyZz1OVUxMOwogaWYgKCFmbmFtZVswXSkgewogIC8qIG90aGVyd2lzZSwgbWFwIG91ciBvd24gbWVtb3J5IGltYWdlICovCiAgc3ByaW50ZihmcHJvYywiL3Byb2MvJWQvbWVtIixnZXRwaWQoKSk7CiAgc3ByaW50ZihhcmcsIiVsZCIsKHVuc2lnbmVkIGxvbmcpbHBEb3NUYXNrLT5pbWcpOwogIGZuYW1lPWZwcm9jOyBmYXJnPWFyZzsKIH0KCiAgVFJBQ0UobW9kdWxlLCJMb2FkaW5nIERPUyBWTSBzdXBwb3J0IG1vZHVsZSAoaG1vZHVsZT0lMDR4KVxuIixscERvc1Rhc2stPmhNb2R1bGUpOwogIGlmICgoY2hpbGQ9Zm9yaygpKTwwKSB7CiAgICBjbG9zZSh3cml0ZV9mZFswXSk7CiAgICBjbG9zZShscERvc1Rhc2stPnJlYWRfcGlwZSk7CiAgICBjbG9zZShscERvc1Rhc2stPndyaXRlX3BpcGUpOwogICAgY2xvc2UoeF9mZCk7CiAgICBDbG9zZUhhbmRsZShscERvc1Rhc2stPmhSZWFkUGlwZSk7CiAgICBDbG9zZUhhbmRsZShscERvc1Rhc2stPmhYUGlwZSk7CiAgICByZXR1cm4gRkFMU0U7CiAgfQogaWYgKGNoaWxkIT0wKSB7CiAgLyogcGFyZW50IHByb2Nlc3MgKi8KICBpbnQgcmV0OwoKICBjbG9zZSh3cml0ZV9mZFswXSk7CiAgY2xvc2UoeF9mZCk7CiAgbHBEb3NUYXNrLT50YXNrPWNoaWxkOwogIC8qIHdhaXQgZm9yIGNoaWxkIHByb2Nlc3MgdG8gc2lnbmFsIHJlYWRpbmVzcyAqLwogIGRvIHsKICAgaWYgKHJlYWQobHBEb3NUYXNrLT5yZWFkX3BpcGUsJnJldCxzaXplb2YocmV0KSkhPXNpemVvZihyZXQpKSB7CiAgICBpZiAoKGVycm5vPT1FSU5UUil8fChlcnJubz09RUFHQUlOKSkgY29udGludWU7CiAgICAvKiBmYWlsdXJlICovCiAgICBFUlIobW9kdWxlLCJkb3Ntb2QgaGFzIGZhaWxlZCB0byBpbml0aWFsaXplXG4iKTsKICAgIGlmIChscERvc1Rhc2stPm1tX25hbWVbMF0hPTApIHVubGluayhscERvc1Rhc2stPm1tX25hbWUpOwogICAgcmV0dXJuIEZBTFNFOwogICB9CiAgfSB3aGlsZSAoMCk7CiAgLyogdGhlIGNoaWxkIGhhcyBub3cgbW1hcGVkIHRoZSB0ZW1wIGZpbGUsIGl0J3Mgbm93IHNhZmUgdG8gdW5saW5rLgogICAqIGRvIGl0IGhlcmUgdG8gYXZvaWQgbGVhdmluZyBhIG1lc3MgaW4gL3RtcCBpZi93aGVuIFdpbmUgY3Jhc2hlcy4uLiAqLwogIGlmIChscERvc1Rhc2stPm1tX25hbWVbMF0hPTApIHVubGluayhscERvc1Rhc2stPm1tX25hbWUpOwogIC8qIHN0YXJ0IHNpbXVsYXRlZCBzeXN0ZW0gdGltZXIgKi8KICBNWl9Jbml0VGltZXIobHBEb3NUYXNrLHJldCk7CiAgaWYgKHJldDwyKSB7CiAgICBFUlIobW9kdWxlLCJkb3Ntb2QgdmVyc2lvbiB0b28gb2xkISBQbGVhc2UgaW5zdGFsbCBuZXdlciBkb3Ntb2QgcHJvcGVybHlcbiIpOwogICAgRVJSKG1vZHVsZSwiSWYgeW91IGRvbid0LCB0aGUgbmV3IGRvc21vZCBldmVudCBoYW5kbGluZyBzeXN0ZW0gd2lsbCBub3Qgd29ya1xuIik7CiAgfQogIC8qIGFsbCBzeXN0ZW1zIGFyZSBub3cgZ28gKi8KIH0gZWxzZSB7CiAgLyogY2hpbGQgcHJvY2VzcyAqLwogIGNsb3NlKGxwRG9zVGFzay0+cmVhZF9waXBlKTsKICBjbG9zZShscERvc1Rhc2stPndyaXRlX3BpcGUpOwogIC8qIHB1dCBvdXIgcGlwZXMgc29tZXdoZXJlIGRvc21vZCBjYW4gZmluZCB0aGVtICovCiAgZHVwMih3cml0ZV9mZFswXSwwKTsgLyogc3RkaW4gKi8KICBkdXAyKHhfZmQsMSk7ICAgICAgICAvKiBzdGRvdXQgKi8KICAvKiBlbmFibGUgc2lnbmFscyAqLwogIFNJR05BTF9NYXNrQXN5bmNFdmVudHMoRkFMU0UpOwogIC8qIG5vdyBsb2FkIGRvc21vZCAqLwogIC8qIGNoZWNrIGFyZ3ZbMF0tZGVyaXZlZCBwYXRocyBmaXJzdCwgc2luY2UgdGhlIG5ld2VzdCBkb3Ntb2QgaXMgbW9zdCBsaWtlbHkgdGhlcmUKICAgKiAoYXQgbGVhc3QgaXQgd2FzIG9uY2UgZm9yIEFuZHJlYXMgTW9ociwgc28gSSBkZWNpZGVkIHRvIG1ha2UgaXQgZWFzaWVyIGZvciBoaW0pICovCiAgZnBhdGg9c3RycmNocihzdHJjcHkocGF0aCxPcHRpb25zLmFyZ3YwKSwnLycpOwogIGlmIChmcGF0aCkgewogICBzdHJjcHkoZnBhdGgsIi9kb3Ntb2QiKTsKICAgZXhlY2wocGF0aCxmbmFtZSxmYXJnLE5VTEwpOwogICBzdHJjcHkoZnBhdGgsIi9sb2FkZXIvZG9zL2Rvc21vZCIpOwogICBleGVjbChwYXRoLGZuYW1lLGZhcmcsTlVMTCk7CiAgfQogIC8qIG9rYXksIGl0IHdhc24ndCB0aGVyZSwgdHJ5IGluIHRoZSBwYXRoICovCiAgZXhlY2xwKCJkb3Ntb2QiLGZuYW1lLGZhcmcsTlVMTCk7CiAgLyogbGFzdCBkZXNwZXJhdGUgYXR0ZW1wdHM6IGN1cnJlbnQgZGlyZWN0b3J5ICovCiAgZXhlY2woImRvc21vZCIsZm5hbWUsZmFyZyxOVUxMKTsKICAvKiBhbmQsIGp1c3QgZm9yIGNvbXBsZXRlbmVzcy4uLiAqLwogIGV4ZWNsKCJsb2FkZXIvZG9zL2Rvc21vZCIsZm5hbWUsZmFyZyxOVUxMKTsKICAvKiBpZiBmYWlsdXJlLCBleGl0ICovCiAgRVJSKG1vZHVsZSwiRmFpbGVkIHRvIHNwYXduIGRvc21vZCwgZXJyb3I9JXNcbiIsc3RyZXJyb3IoZXJybm8pKTsKICBleGl0KDEpOwogfQogcmV0dXJuIFRSVUU7Cn0KCkJPT0wgTVpfQ3JlYXRlUHJvY2VzcyggSEZJTEUgaEZpbGUsIE9GU1RSVUNUICpvZnMsIExQQ1NUUiBjbWRsaW5lLCBMUENTVFIgZW52LCAKICAgICAgICAgICAgICAgICAgICAgICBMUFNFQ1VSSVRZX0FUVFJJQlVURVMgcHNhLCBMUFNFQ1VSSVRZX0FUVFJJQlVURVMgdHNhLAogICAgICAgICAgICAgICAgICAgICAgIEJPT0wgaW5oZXJpdCwgTFBTVEFSVFVQSU5GT0Egc3RhcnR1cCwgCiAgICAgICAgICAgICAgICAgICAgICAgTFBQUk9DRVNTX0lORk9STUFUSU9OIGluZm8gKQp7CiBMUERPU1RBU0sgbHBEb3NUYXNrID0gTlVMTDsgLyoga2VlcCBnY2MgZnJvbSBjb21wbGFpbmluZyAqLwogSE1PRFVMRTE2IGhNb2R1bGU7CiBQREIgKnBkYiA9IFBST0NFU1NfQ3VycmVudCgpOwogVERCICpwVGFzayA9IChUREIqKUdsb2JhbExvY2sxNiggR2V0Q3VycmVudFRhc2soKSApOwogTkVfTU9EVUxFICpwTW9kdWxlID0gcFRhc2sgPyBORV9HZXRQdHIoIHBUYXNrLT5oTW9kdWxlICkgOiBOVUxMOwogaW50IGFsbG9jID0gIShwTW9kdWxlICYmIHBNb2R1bGUtPmRvc19pbWFnZSk7CgogaWYgKGFsbG9jICYmIChscERvc1Rhc2sgPSBjYWxsb2MoMSwgc2l6ZW9mKERPU1RBU0spKSkgPT0gTlVMTCkgewogIFNldExhc3RFcnJvcihFUlJPUl9OT1RfRU5PVUdIX01FTU9SWSk7CiAgcmV0dXJuIEZBTFNFOwogfQoKIGlmICgoIWVudikmJnBkYikgZW52ID0gcGRiLT5lbnZfZGItPmVudmlyb247CiBpZiAoYWxsb2MpIHsKICBpZiAoKGhNb2R1bGUgPSBNT0RVTEVfQ3JlYXRlRHVtbXlNb2R1bGUob2ZzLCBOVUxMKSkgPCAzMikgewogICBTZXRMYXN0RXJyb3IoaE1vZHVsZSk7CiAgIHJldHVybiBGQUxTRTsKICB9CiAgbHBEb3NUYXNrLT5oTW9kdWxlID0gaE1vZHVsZTsKCiAgcE1vZHVsZSA9IChORV9NT0RVTEUgKilHbG9iYWxMb2NrMTYoaE1vZHVsZSk7CiAgcE1vZHVsZS0+bHBEb3NUYXNrID0gbHBEb3NUYXNrOwogCiAgbHBEb3NUYXNrLT5pbWc9TlVMTDsgbHBEb3NUYXNrLT5tbV9uYW1lWzBdPTA7IGxwRG9zVGFzay0+bW1fZmQ9LTE7CiB9IGVsc2UgbHBEb3NUYXNrPXBNb2R1bGUtPmxwRG9zVGFzazsKIGlmICghTVpfTG9hZEltYWdlKCBoRmlsZSwgb2ZzLCBjbWRsaW5lLCBlbnYsIGxwRG9zVGFzaywgcE1vZHVsZSApKSB7CiAgaWYgKGFsbG9jKSB7CiAgIGlmIChscERvc1Rhc2stPm1tX25hbWVbMF0hPTApIHsKICAgIGlmIChscERvc1Rhc2stPmltZyE9TlVMTCkgbXVubWFwKGxwRG9zVGFzay0+aW1nLDB4MTEwMDAwLVNUQVJUX09GRlNFVCk7CiAgICBpZiAobHBEb3NUYXNrLT5tbV9mZD49MCkgY2xvc2UobHBEb3NUYXNrLT5tbV9mZCk7CiAgICB1bmxpbmsobHBEb3NUYXNrLT5tbV9uYW1lKTsKICAgfSBlbHNlCiAgICBpZiAobHBEb3NUYXNrLT5pbWchPU5VTEwpIFZpcnR1YWxGcmVlKGxwRG9zVGFzay0+aW1nLDB4MTEwMDAwLE1FTV9SRUxFQVNFKTsKICB9CiAgcmV0dXJuIEZBTFNFOwogfQogaWYgKGFsbG9jKSB7CiAgcE1vZHVsZS0+ZG9zX2ltYWdlID0gbHBEb3NUYXNrLT5pbWc7CiAgaWYgKCFNWl9Jbml0VGFzayggbHBEb3NUYXNrICkpIHsKICAgTVpfS2lsbE1vZHVsZSggbHBEb3NUYXNrICk7CiAgIC8qIEZJWE1FOiBjbGVhbnVwIGhNb2R1bGUgKi8KICAgU2V0TGFzdEVycm9yKEVSUk9SX0dFTl9GQUlMVVJFKTsKICAgcmV0dXJuIEZBTFNFOwogIH0KICBpbmhlcml0ID0gVFJVRTsgLyogYmFkIGhhY2sgZm9yIGluaGVyaXRpbmcgdGhlIENyZWF0ZVBpcGUuLi4gKi8KICBpZiAoIVBST0NFU1NfQ3JlYXRlKCBwTW9kdWxlLCBjbWRsaW5lLCBlbnYsIDAsIDAsIAogICAgICAgICAgICAgICAgICAgICAgIHBzYSwgdHNhLCBpbmhlcml0LCBzdGFydHVwLCBpbmZvICkpCiAgIHJldHVybiBGQUxTRTsKIH0KIHJldHVybiBUUlVFOwp9Cgp2b2lkIE1aX0tpbGxNb2R1bGUoIExQRE9TVEFTSyBscERvc1Rhc2sgKQp7CiAgRE9TRVZFTlQgKmV2ZW50LCpwX2V2ZW50OwogIERPU1NZU1RFTSAqc3lzLCpwX3N5czsKCiAgVFJBQ0UobW9kdWxlLCJraWxsaW5nIERPUyB0YXNrXG4iKTsKICBpZiAobHBEb3NUYXNrLT5tbV9uYW1lWzBdIT0wKSB7CiAgICBtdW5tYXAobHBEb3NUYXNrLT5pbWcsMHgxMTAwMDAtU1RBUlRfT0ZGU0VUKTsKICAgIGNsb3NlKGxwRG9zVGFzay0+bW1fZmQpOwogIH0gZWxzZSBWaXJ0dWFsRnJlZShscERvc1Rhc2stPmltZywweDExMDAwMCxNRU1fUkVMRUFTRSk7CiAgY2xvc2UobHBEb3NUYXNrLT5yZWFkX3BpcGUpOwogIGNsb3NlKGxwRG9zVGFzay0+d3JpdGVfcGlwZSk7CiAgQ2xvc2VIYW5kbGUobHBEb3NUYXNrLT5oUmVhZFBpcGUpOwogIENsb3NlSGFuZGxlKGxwRG9zVGFzay0+aFhQaXBlKTsKICBraWxsKGxwRG9zVGFzay0+dGFzayxTSUdURVJNKTsKLyogZnJlZSBtZW1vcnkgYWxsb2NhdGVkIGZvciBldmVudHMgYW5kIHN5c3RlbXMgKi8KI2RlZmluZSBERlJFRSh2YXIscHZhcixzdmFyKSBcCiAgdmFyID0gbHBEb3NUYXNrLT5zdmFyOyBcCiAgd2hpbGUgKHZhcikgeyBcCiAgICBpZiAodmFyLT5kYXRhKSBmcmVlKHZhci0+ZGF0YSk7IFwKICAgIHB2YXIgPSB2YXItPm5leHQ7IGZyZWUodmFyKTsgdmFyID0gcHZhcjsgXAogIH0KCiAgREZSRUUoZXZlbnQscF9ldmVudCxwZW5kaW5nKQogIERGUkVFKGV2ZW50LHBfZXZlbnQsY3VycmVudCkKICBERlJFRShzeXMscF9zeXMsc3lzKQoKI3VuZGVmIERGUkVFCgojaWYgMAogLyogRklYTUU6IHRoaXMgc2VlbXMgdG8gY3Jhc2ggKi8KIGlmIChscERvc1Rhc2stPmRwbWlfc2VsKQogIFVuTWFwTFMoUFRSX1NFR19PRkZfVE9fU0VHUFRSKGxwRG9zVGFzay0+ZHBtaV9zZWwsMCkpOwojZW5kaWYKfQoKI2Vsc2UgLyogIU1aX1NVUFBPUlRFRCAqLwoKQk9PTCBNWl9DcmVhdGVQcm9jZXNzKCBIRklMRSBoRmlsZSwgT0ZTVFJVQ1QgKm9mcywgTFBDU1RSIGNtZGxpbmUsIExQQ1NUUiBlbnYsIAogICAgICAgICAgICAgICAgICAgICAgIExQU0VDVVJJVFlfQVRUUklCVVRFUyBwc2EsIExQU0VDVVJJVFlfQVRUUklCVVRFUyB0c2EsCiAgICAgICAgICAgICAgICAgICAgICAgQk9PTCBpbmhlcml0LCBMUFNUQVJUVVBJTkZPQSBzdGFydHVwLCAKICAgICAgICAgICAgICAgICAgICAgICBMUFBST0NFU1NfSU5GT1JNQVRJT04gaW5mbyApCnsKIFdBUk4obW9kdWxlLCJET1MgZXhlY3V0YWJsZXMgbm90IHN1cHBvcnRlZCBvbiB0aGlzIGFyY2hpdGVjdHVyZVxuIik7CiBTZXRMYXN0RXJyb3IoRVJST1JfQkFEX0ZPUk1BVCk7CiByZXR1cm4gRkFMU0U7Cn0KCiNlbmRpZgo=