LyoKICogY29tX3JpZ2h0LmMgLS0gcHJvdmlkZSBIZWltZGFsbCAvIEtlcmJlcm9zNGt0aCBjb21fZXJyIGludGVyZmFjZXMKICogCWZvciBiYWNrd2FyZHMgY29tcGF0YmlsaXR5IAogKiAKICogQ29weXJpZ2h0IChjKSAyMDAzIGJ5IFRoZW9kb3JlIFRzJ28KICoKICogVGFrZW4gZnJvbSBsaWIvY29tX2Vyci9lcnJvci5jIGZyb20gS2VyYmVyb3M0a3RoIGRpc3RyaWJ1dGlvbi4KICogCiAqIENvcHlyaWdodCAoYykgMTk5NywgMTk5OCwgMjAwMSBLdW5nbGlnYSBUZWtuaXNrYSBI9mdza29sYW4KICogKFJveWFsIEluc3RpdHV0ZSBvZiBUZWNobm9sb2d5LCBTdG9ja2hvbG0sIFN3ZWRlbikuIAogKiBBbGwgcmlnaHRzIHJlc2VydmVkLiAKICoKICogUmVkaXN0cmlidXRpb24gYW5kIHVzZSBpbiBzb3VyY2UgYW5kIGJpbmFyeSBmb3Jtcywgd2l0aCBvciB3aXRob3V0IAogKiBtb2RpZmljYXRpb24sIGFyZSBwZXJtaXR0ZWQgcHJvdmlkZWQgdGhhdCB0aGUgZm9sbG93aW5nIGNvbmRpdGlvbnMgCiAqIGFyZSBtZXQ6IAogKgogKiAxLiBSZWRpc3RyaWJ1dGlvbnMgb2Ygc291cmNlIGNvZGUgbXVzdCByZXRhaW4gdGhlIGFib3ZlIGNvcHlyaWdodCAKICogICAgbm90aWNlLCB0aGlzIGxpc3Qgb2YgY29uZGl0aW9ucyBhbmQgdGhlIGZvbGxvd2luZyBkaXNjbGFpbWVyLiAKICoKICogMi4gUmVkaXN0cmlidXRpb25zIGluIGJpbmFyeSBmb3JtIG11c3QgcmVwcm9kdWNlIHRoZSBhYm92ZSBjb3B5cmlnaHQgCiAqICAgIG5vdGljZSwgdGhpcyBsaXN0IG9mIGNvbmRpdGlvbnMgYW5kIHRoZSBmb2xsb3dpbmcgZGlzY2xhaW1lciBpbiB0aGUgCiAqICAgIGRvY3VtZW50YXRpb24gYW5kL29yIG90aGVyIG1hdGVyaWFscyBwcm92aWRlZCB3aXRoIHRoZSBkaXN0cmlidXRpb24uIAogKgogKiAzLiBOZWl0aGVyIHRoZSBuYW1lIG9mIHRoZSBJbnN0aXR1dGUgbm9yIHRoZSBuYW1lcyBvZiBpdHMgY29udHJpYnV0b3JzIAogKiAgICBtYXkgYmUgdXNlZCB0byBlbmRvcnNlIG9yIHByb21vdGUgcHJvZHVjdHMgZGVyaXZlZCBmcm9tIHRoaXMgc29mdHdhcmUgCiAqICAgIHdpdGhvdXQgc3BlY2lmaWMgcHJpb3Igd3JpdHRlbiBwZXJtaXNzaW9uLiAKICoKICogVEhJUyBTT0ZUV0FSRSBJUyBQUk9WSURFRCBCWSBUSEUgSU5TVElUVVRFIEFORCBDT05UUklCVVRPUlMgYGBBUyBJUycnIEFORCAKICogQU5ZIEVYUFJFU1MgT1IgSU1QTElFRCBXQVJSQU5USUVTLCBJTkNMVURJTkcsIEJVVCBOT1QgTElNSVRFRCBUTywgVEhFIAogKiBJTVBMSUVEIFdBUlJBTlRJRVMgT0YgTUVSQ0hBTlRBQklMSVRZIEFORCBGSVRORVNTIEZPUiBBIFBBUlRJQ1VMQVIgUFVSUE9TRSAKICogQVJFIERJU0NMQUlNRUQuICBJTiBOTyBFVkVOVCBTSEFMTCBUSEUgSU5TVElUVVRFIE9SIENPTlRSSUJVVE9SUyBCRSBMSUFCTEUgCiAqIEZPUiBBTlkgRElSRUNULCBJTkRJUkVDVCwgSU5DSURFTlRBTCwgU1BFQ0lBTCwgRVhFTVBMQVJZLCBPUiBDT05TRVFVRU5USUFMIAogKiBEQU1BR0VTIChJTkNMVURJTkcsIEJVVCBOT1QgTElNSVRFRCBUTywgUFJPQ1VSRU1FTlQgT0YgU1VCU1RJVFVURSBHT09EUyAKICogT1IgU0VSVklDRVM7IExPU1MgT0YgVVNFLCBEQVRBLCBPUiBQUk9GSVRTOyBPUiBCVVNJTkVTUyBJTlRFUlJVUFRJT04pIAogKiBIT1dFVkVSIENBVVNFRCBBTkQgT04gQU5ZIFRIRU9SWSBPRiBMSUFCSUxJVFksIFdIRVRIRVIgSU4gQ09OVFJBQ1QsIFNUUklDVCAKICogTElBQklMSVRZLCBPUiBUT1JUIChJTkNMVURJTkcgTkVHTElHRU5DRSBPUiBPVEhFUldJU0UpIEFSSVNJTkcgSU4gQU5ZIFdBWSAKICogT1VUIE9GIFRIRSBVU0UgT0YgVEhJUyBTT0ZUV0FSRSwgRVZFTiBJRiBBRFZJU0VEIE9GIFRIRSBQT1NTSUJJTElUWSBPRiAKICogU1VDSCBEQU1BR0UuIAogKi8KCiNpbmNsdWRlIDxzdGRpby5oPgojaW5jbHVkZSA8c3RkbGliLmg+CiNpbmNsdWRlIDxzdHJpbmcuaD4KI2luY2x1ZGUgImNvbV9lcnIuaCIKI2luY2x1ZGUgImVycm9yX3RhYmxlLmgiCgpjb25zdCBjaGFyICoKY29tX3JpZ2h0KHN0cnVjdCBldF9saXN0ICpsaXN0LCBsb25nIGNvZGUpCnsKICAgIHN0cnVjdCBldF9saXN0ICpwOwogICAgZm9yIChwID0gbGlzdDsgcDsgcCA9IHAtPm5leHQpIHsKCWlmIChjb2RlID49IHAtPnRhYmxlLT5iYXNlICYmIGNvZGUgPCBwLT50YWJsZS0+YmFzZSArIHAtPnRhYmxlLT5uX21zZ3MpCgkgICAgcmV0dXJuIHAtPnRhYmxlLT5tc2dzW2NvZGUgLSBwLT50YWJsZS0+YmFzZV07CiAgICB9CiAgICByZXR1cm4gTlVMTDsKfQoKc3RydWN0IGZvb2JhciB7CiAgICBzdHJ1Y3QgZXRfbGlzdCBldGw7CiAgICBzdHJ1Y3QgZXJyb3JfdGFibGUgdGFiOwp9OwoKLyoKICogV2UgcHJvdmlkZSB0aGlzIHJvdXRpbmUgZm9yIGNvbXBhdGliaWxpdHkgd2l0aCBIZWltZGFsbCBnZW5lcmF0ZWQKICogZm9vX2Vyci5jIGZpbGVzLCBidXQgd2UgZG9uJ3QgdXNlIHRoaXMgb3Vyc2VsdmVzIGZvciBmb29fZXJyLmMKICogZmlsZXMgZ2VuZXJhdGVkIGJ5IG91ciBjb21waWxlX2V0LiAgVGhpcyBpcyBzbyBvdXIgZm9vX2Vyci5jCiAqIGZpbGVzIGNhbiBiZSB1c2VkIHdpdGggb2xkZXIgY29tX2VyciBsaWJyYXJpZXMgd2l0aG91dCBydW5uaW5nCiAqIGFmb3VsIG9mIGRlcGVuZGVuY2llcy4KICovCnZvaWQKaW5pdGlhbGl6ZV9lcnJvcl90YWJsZV9yKHN0cnVjdCBldF9saXN0ICoqbGlzdCwgCgkJCSBjb25zdCBjaGFyICoqbWVzc2FnZXMsIAoJCQkgaW50IG51bV9lcnJvcnMsCgkJCSBsb25nIGJhc2UpCnsKICAgIHN0cnVjdCBldF9saXN0ICpldCwgKiplbmQ7CiAgICBzdHJ1Y3QgZXJyb3JfdGFibGUgKnRhYjsKICAgIHN0cnVjdCBmb29iYXIgKmY7CgogICAgZm9yIChlbmQgPSBsaXN0LCBldCA9ICpsaXN0OyBldDsgZW5kID0gJmV0LT5uZXh0LCBldCA9IGV0LT5uZXh0KQogICAgICAgIGlmIChldC0+dGFibGUtPm1zZ3MgPT0gbWVzc2FnZXMpCiAgICAgICAgICAgIHJldHVybjsKICAgIGYgPSBtYWxsb2Moc2l6ZW9mKCpmKSk7CiAgICBpZiAoZiA9PSBOVUxMKQogICAgICAgIHJldHVybjsKICAgIGV0ID0gJmYtPmV0bDsKICAgIGV0LT50YWJsZSA9IHRhYiA9ICZmLT50YWI7CiAgICB0YWItPm1zZ3MgPSBtZXNzYWdlczsKICAgIHRhYi0+bl9tc2dzID0gbnVtX2Vycm9yczsKICAgIHRhYi0+YmFzZSA9IGJhc2U7CiAgICBldC0+bmV4dCA9IE5VTEw7CiAgICAqZW5kID0gZXQ7Cn0KCQkJCgp2b2lkCmZyZWVfZXJyb3JfdGFibGUoc3RydWN0IGV0X2xpc3QgKmV0KQp7CiAgICB3aGlsZShldCl7CglzdHJ1Y3QgZXRfbGlzdCAqcCA9IGV0OwoJZXQgPSBldC0+bmV4dDsKCWZyZWUocCk7CiAgICB9Cn0K