LyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqCiAqIENvcHlyaWdodCAyMDA2LTIwMDggVHVuZ3N0ZW4gR3JhcGhpY3MsIEluYy4sIENlZGFyIFBhcmssIFRYLiwgVVNBLgogKiBBbGwgUmlnaHRzIFJlc2VydmVkLgogKiBDb3B5cmlnaHQgMjAwOSBWTXdhcmUsIEluYy4sIFBhbG8gQWx0bywgQ0EuLCBVU0EuCiAqIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCiAqCiAqIFBlcm1pc3Npb24gaXMgaGVyZWJ5IGdyYW50ZWQsIGZyZWUgb2YgY2hhcmdlLCB0byBhbnkgcGVyc29uIG9idGFpbmluZyBhCiAqIGNvcHkgb2YgdGhpcyBzb2Z0d2FyZSBhbmQgYXNzb2NpYXRlZCBkb2N1bWVudGF0aW9uIGZpbGVzICh0aGUKICogIlNvZnR3YXJlIiksIHRvIGRlYWwgaW4gdGhlIFNvZnR3YXJlIHdpdGhvdXQgcmVzdHJpY3Rpb24sIGluY2x1ZGluZwogKiB3aXRob3V0IGxpbWl0YXRpb24gdGhlIHJpZ2h0cyB0byB1c2UsIGNvcHksIG1vZGlmeSwgbWVyZ2UsIHB1Ymxpc2gsCiAqIGRpc3RyaWJ1dGUsIHN1YiBsaWNlbnNlLCBhbmQvb3Igc2VsbCBjb3BpZXMgb2YgdGhlIFNvZnR3YXJlLCBhbmQgdG8KICogcGVybWl0IHBlcnNvbnMgdG8gd2hvbSB0aGUgU29mdHdhcmUgaXMgZnVybmlzaGVkIHRvIGRvIHNvLCBzdWJqZWN0IHRvCiAqIHRoZSBmb2xsb3dpbmcgY29uZGl0aW9uczoKICoKICogVGhlIGFib3ZlIGNvcHlyaWdodCBub3RpY2UgYW5kIHRoaXMgcGVybWlzc2lvbiBub3RpY2UgKGluY2x1ZGluZyB0aGUKICogbmV4dCBwYXJhZ3JhcGgpIHNoYWxsIGJlIGluY2x1ZGVkIGluIGFsbCBjb3BpZXMgb3Igc3Vic3RhbnRpYWwgcG9ydGlvbnMKICogb2YgdGhlIFNvZnR3YXJlLgogKgogKiBUSEUgU09GVFdBUkUgSVMgUFJPVklERUQgIkFTIElTIiwgV0lUSE9VVCBXQVJSQU5UWSBPRiBBTlkgS0lORCwgRVhQUkVTUyBPUgogKiBJTVBMSUVELCBJTkNMVURJTkcgQlVUIE5PVCBMSU1JVEVEIFRPIFRIRSBXQVJSQU5USUVTIE9GIE1FUkNIQU5UQUJJTElUWSwKICogRklUTkVTUyBGT1IgQSBQQVJUSUNVTEFSIFBVUlBPU0UgQU5EIE5PTi1JTkZSSU5HRU1FTlQuIElOIE5PIEVWRU5UIFNIQUxMCiAqIFRIRSBDT1BZUklHSFQgSE9MREVSUywgQVVUSE9SUyBBTkQvT1IgSVRTIFNVUFBMSUVSUyBCRSBMSUFCTEUgRk9SIEFOWSBDTEFJTSwKICogREFNQUdFUyBPUiBPVEhFUiBMSUFCSUxJVFksIFdIRVRIRVIgSU4gQU4gQUNUSU9OIE9GIENPTlRSQUNULCBUT1JUIE9SCiAqIE9USEVSV0lTRSwgQVJJU0lORyBGUk9NLCBPVVQgT0YgT1IgSU4gQ09OTkVDVElPTiBXSVRIIFRIRSBTT0ZUV0FSRSBPUiBUSEUKICogVVNFIE9SIE9USEVSIERFQUxJTkdTIElOIFRIRSBTT0ZUV0FSRS4KICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwoKLyoKICogR2VuZXJpYyBzaW1wbGUgbWVtb3J5IG1hbmFnZXIgaW1wbGVtZW50YXRpb24uIEludGVuZGVkIHRvIGJlIHVzZWQgYXMgYSBiYXNlCiAqIGNsYXNzIGltcGxlbWVudGF0aW9uIGZvciBtb3JlIGFkdmFuY2VkIG1lbW9yeSBtYW5hZ2Vycy4KICoKICogTm90ZSB0aGF0IHRoZSBhbGdvcml0aG0gdXNlZCBpcyBxdWl0ZSBzaW1wbGUgYW5kIHRoZXJlIG1pZ2h0IGJlIHN1YnN0YW50aWFsCiAqIHBlcmZvcm1hbmNlIGdhaW5zIGlmIGEgc21hcnRlciBmcmVlIGxpc3QgaXMgaW1wbGVtZW50ZWQuIEN1cnJlbnRseSBpdCBpcyBqdXN0IGFuCiAqIHVub3JkZXJlZCBzdGFjayBvZiBmcmVlIHJlZ2lvbnMuIFRoaXMgY291bGQgZWFzaWx5IGJlIGltcHJvdmVkIGlmIGFuIFJCLXRyZWUKICogaXMgdXNlZCBpbnN0ZWFkLiBBdCBsZWFzdCBpZiB3ZSBleHBlY3QgaGVhdnkgZnJhZ21lbnRhdGlvbi4KICogTm90ZSB0aGF0IHRoaXMgaW1wbGVtZW50YXRpb24gaXMgbW9yZSBvciBsZXNzIGlkZW50aWNhbCB0byB0aGUgZHJtIGNvcmUgbWFuYWdlcgogKiBpbiB0aGUgbGludXgga2VybmVsLgogKgogKiBBdXRob3JzOgogKiBUaG9tYXMgSGVsbHN0cvZtIDx0aG9tYXMtYXQtdHVuZ3N0ZW5ncmFwaGljcy1kb3QtY29tPgogKi8KCiNpZmRlZiBIQVZFX0NPTkZJR19ICiNpbmNsdWRlICJjb25maWcuaCIKI2VuZGlmCgojaW5jbHVkZSAid3NibV9tbS5oIgojaW5jbHVkZSA8ZXJybm8uaD4KI2luY2x1ZGUgPHN0ZGxpYi5oPgoKdW5zaWduZWQgbG9uZwp3c2JtTU1UYWlsU3BhY2Uoc3RydWN0IF9Xc2JtTU0gKm1tKQp7CiAgICBzdHJ1Y3QgX1dzYm1MaXN0SGVhZCAqdGFpbF9ub2RlOwogICAgc3RydWN0IF9Xc2JtTU1Ob2RlICplbnRyeTsKCiAgICB0YWlsX25vZGUgPSBtbS0+bWxfZW50cnkucHJldjsKICAgIGVudHJ5ID0gV1NCTUxJU1RFTlRSWSh0YWlsX25vZGUsIHN0cnVjdCBfV3NibU1NTm9kZSwgbWxfZW50cnkpOwoKICAgIGlmICghZW50cnktPmZyZWUpCglyZXR1cm4gMDsKCiAgICByZXR1cm4gZW50cnktPnNpemU7Cn0KCmludAp3c2JtTU1SZW1vdmVTcGFjZUZyb21UYWlsKHN0cnVjdCBfV3NibU1NICptbSwgdW5zaWduZWQgbG9uZyBzaXplKQp7CiAgICBzdHJ1Y3QgX1dzYm1MaXN0SGVhZCAqdGFpbF9ub2RlOwogICAgc3RydWN0IF9Xc2JtTU1Ob2RlICplbnRyeTsKCiAgICB0YWlsX25vZGUgPSBtbS0+bWxfZW50cnkucHJldjsKICAgIGVudHJ5ID0gV1NCTUxJU1RFTlRSWSh0YWlsX25vZGUsIHN0cnVjdCBfV3NibU1NTm9kZSwgbWxfZW50cnkpOwoKICAgIGlmICghZW50cnktPmZyZWUpCglyZXR1cm4gLUVOT01FTTsKCiAgICBpZiAoZW50cnktPnNpemUgPD0gc2l6ZSkKCXJldHVybiAtRU5PTUVNOwoKICAgIGVudHJ5LT5zaXplIC09IHNpemU7CiAgICByZXR1cm4gMDsKfQoKc3RhdGljIGludAp3c2JtTU1DcmVhdGVUYWlsTm9kZShzdHJ1Y3QgX1dzYm1NTSAqbW0sCgkJICAgICB1bnNpZ25lZCBsb25nIHN0YXJ0LCB1bnNpZ25lZCBsb25nIHNpemUpCnsKICAgIHN0cnVjdCBfV3NibU1NTm9kZSAqY2hpbGQ7CgogICAgY2hpbGQgPSAoc3RydWN0IF9Xc2JtTU1Ob2RlICopbWFsbG9jKHNpemVvZigqY2hpbGQpKTsKICAgIGlmICghY2hpbGQpCglyZXR1cm4gLUVOT01FTTsKCiAgICBjaGlsZC0+ZnJlZSA9IDE7CiAgICBjaGlsZC0+c2l6ZSA9IHNpemU7CiAgICBjaGlsZC0+c3RhcnQgPSBzdGFydDsKICAgIGNoaWxkLT5tbSA9IG1tOwoKICAgIFdTQk1MSVNUQUREVEFJTCgmY2hpbGQtPm1sX2VudHJ5LCAmbW0tPm1sX2VudHJ5KTsKICAgIFdTQk1MSVNUQUREVEFJTCgmY2hpbGQtPmZsX2VudHJ5LCAmbW0tPmZsX2VudHJ5KTsKCiAgICByZXR1cm4gMDsKfQoKc3RhdGljIHN0cnVjdCBfV3NibU1NTm9kZSAqCndzYm1NTVNwbGl0QXRTdGFydChzdHJ1Y3QgX1dzYm1NTU5vZGUgKnBhcmVudCwgdW5zaWduZWQgbG9uZyBzaXplKQp7CiAgICBzdHJ1Y3QgX1dzYm1NTU5vZGUgKmNoaWxkOwoKICAgIGNoaWxkID0gKHN0cnVjdCBfV3NibU1NTm9kZSAqKW1hbGxvYyhzaXplb2YoKmNoaWxkKSk7CiAgICBpZiAoIWNoaWxkKQoJcmV0dXJuIE5VTEw7CgogICAgV1NCTUlOSVRMSVNUSEVBRCgmY2hpbGQtPmZsX2VudHJ5KTsKCiAgICBjaGlsZC0+ZnJlZSA9IDA7CiAgICBjaGlsZC0+c2l6ZSA9IHNpemU7CiAgICBjaGlsZC0+c3RhcnQgPSBwYXJlbnQtPnN0YXJ0OwogICAgY2hpbGQtPm1tID0gcGFyZW50LT5tbTsKCiAgICBXU0JNTElTVEFERFRBSUwoJmNoaWxkLT5tbF9lbnRyeSwgJnBhcmVudC0+bWxfZW50cnkpOwogICAgV1NCTUlOSVRMSVNUSEVBRCgmY2hpbGQtPmZsX2VudHJ5KTsKCiAgICBwYXJlbnQtPnNpemUgLT0gc2l6ZTsKICAgIHBhcmVudC0+c3RhcnQgKz0gc2l6ZTsKICAgIHJldHVybiBjaGlsZDsKfQoKc3RydWN0IF9Xc2JtTU1Ob2RlICoKd3NibU1NR2V0QmxvY2soc3RydWN0IF9Xc2JtTU1Ob2RlICpwYXJlbnQsCgkgICAgICAgdW5zaWduZWQgbG9uZyBzaXplLCB1bnNpZ25lZCBhbGlnbm1lbnQpCnsKCiAgICBzdHJ1Y3QgX1dzYm1NTU5vZGUgKmFsaWduX3NwbGl0b2ZmID0gTlVMTDsKICAgIHN0cnVjdCBfV3NibU1NTm9kZSAqY2hpbGQ7CiAgICB1bnNpZ25lZCB0bXAgPSAwOwoKICAgIGlmIChhbGlnbm1lbnQpCgl0bXAgPSBwYXJlbnQtPnN0YXJ0ICUgYWxpZ25tZW50OwoKICAgIGlmICh0bXApIHsKCWFsaWduX3NwbGl0b2ZmID0gd3NibU1NU3BsaXRBdFN0YXJ0KHBhcmVudCwgYWxpZ25tZW50IC0gdG1wKTsKCWlmICghYWxpZ25fc3BsaXRvZmYpCgkgICAgcmV0dXJuIE5VTEw7CiAgICB9CgogICAgaWYgKHBhcmVudC0+c2l6ZSA9PSBzaXplKSB7CglXU0JNTElTVERFTElOSVQoJnBhcmVudC0+ZmxfZW50cnkpOwoJcGFyZW50LT5mcmVlID0gMDsKCXJldHVybiBwYXJlbnQ7CiAgICB9IGVsc2UgewoJY2hpbGQgPSB3c2JtTU1TcGxpdEF0U3RhcnQocGFyZW50LCBzaXplKTsKICAgIH0KCiAgICBpZiAoYWxpZ25fc3BsaXRvZmYpCgl3c2JtTU1QdXRCbG9jayhhbGlnbl9zcGxpdG9mZik7CgogICAgcmV0dXJuIGNoaWxkOwp9CgovKgogKiBQdXQgYSBibG9jay4gTWVyZ2Ugd2l0aCB0aGUgcHJldmlvdXMgYW5kIC8gb3IgbmV4dCBibG9jayBpZiB0aGV5IGFyZSBmcmVlLgogKiBPdGhlcndpc2UgYWRkIHRvIHRoZSBmcmVlIHN0YWNrLgogKi8KCnZvaWQKd3NibU1NUHV0QmxvY2soc3RydWN0IF9Xc2JtTU1Ob2RlICpjdXIpCnsKCiAgICBzdHJ1Y3QgX1dzYm1NTSAqbW0gPSBjdXItPm1tOwogICAgc3RydWN0IF9Xc2JtTGlzdEhlYWQgKmN1cl9oZWFkID0gJmN1ci0+bWxfZW50cnk7CiAgICBzdHJ1Y3QgX1dzYm1MaXN0SGVhZCAqcm9vdF9oZWFkID0gJm1tLT5tbF9lbnRyeTsKICAgIHN0cnVjdCBfV3NibU1NTm9kZSAqcHJldl9ub2RlID0gTlVMTDsKICAgIHN0cnVjdCBfV3NibU1NTm9kZSAqbmV4dF9ub2RlOwoKICAgIGludCBtZXJnZWQgPSAwOwoKICAgIGlmIChjdXJfaGVhZC0+cHJldiAhPSByb290X2hlYWQpIHsKCXByZXZfbm9kZSA9CgkgICAgV1NCTUxJU1RFTlRSWShjdXJfaGVhZC0+cHJldiwgc3RydWN0IF9Xc2JtTU1Ob2RlLCBtbF9lbnRyeSk7CglpZiAocHJldl9ub2RlLT5mcmVlKSB7CgkgICAgcHJldl9ub2RlLT5zaXplICs9IGN1ci0+c2l6ZTsKCSAgICBtZXJnZWQgPSAxOwoJfQogICAgfQogICAgaWYgKGN1cl9oZWFkLT5uZXh0ICE9IHJvb3RfaGVhZCkgewoJbmV4dF9ub2RlID0KCSAgICBXU0JNTElTVEVOVFJZKGN1cl9oZWFkLT5uZXh0LCBzdHJ1Y3QgX1dzYm1NTU5vZGUsIG1sX2VudHJ5KTsKCWlmIChuZXh0X25vZGUtPmZyZWUpIHsKCSAgICBpZiAobWVyZ2VkKSB7CgkJcHJldl9ub2RlLT5zaXplICs9IG5leHRfbm9kZS0+c2l6ZTsKCQlXU0JNTElTVERFTCgmbmV4dF9ub2RlLT5tbF9lbnRyeSk7CgkJV1NCTUxJU1RERUwoJm5leHRfbm9kZS0+ZmxfZW50cnkpOwoJCWZyZWUobmV4dF9ub2RlKTsKCSAgICB9IGVsc2UgewoJCW5leHRfbm9kZS0+c2l6ZSArPSBjdXItPnNpemU7CgkJbmV4dF9ub2RlLT5zdGFydCA9IGN1ci0+c3RhcnQ7CgkJbWVyZ2VkID0gMTsKCSAgICB9Cgl9CiAgICB9CiAgICBpZiAoIW1lcmdlZCkgewoJY3VyLT5mcmVlID0gMTsKCVdTQk1MSVNUQUREKCZjdXItPmZsX2VudHJ5LCAmbW0tPmZsX2VudHJ5KTsKICAgIH0gZWxzZSB7CglXU0JNTElTVERFTCgmY3VyLT5tbF9lbnRyeSk7CglmcmVlKGN1cik7CiAgICB9Cn0KCnN0cnVjdCBfV3NibU1NTm9kZSAqCndzYm1NTVNlYXJjaEZyZWUoY29uc3Qgc3RydWN0IF9Xc2JtTU0gKm1tLAoJCSB1bnNpZ25lZCBsb25nIHNpemUsIHVuc2lnbmVkIGFsaWdubWVudCwgaW50IGJlc3RfbWF0Y2gpCnsKICAgIHN0cnVjdCBfV3NibUxpc3RIZWFkICpsaXN0OwogICAgY29uc3Qgc3RydWN0IF9Xc2JtTGlzdEhlYWQgKmZyZWVfc3RhY2sgPSAmbW0tPmZsX2VudHJ5OwogICAgc3RydWN0IF9Xc2JtTU1Ob2RlICplbnRyeTsKICAgIHN0cnVjdCBfV3NibU1NTm9kZSAqYmVzdDsKICAgIHVuc2lnbmVkIGxvbmcgYmVzdF9zaXplOwogICAgdW5zaWduZWQgd2FzdGVkOwoKICAgIGJlc3QgPSBOVUxMOwogICAgYmVzdF9zaXplID0gfjBVTDsKCiAgICBXU0JNTElTVEZPUkVBQ0gobGlzdCwgZnJlZV9zdGFjaykgewoJZW50cnkgPSBXU0JNTElTVEVOVFJZKGxpc3QsIHN0cnVjdCBfV3NibU1NTm9kZSwgZmxfZW50cnkpOwoKCXdhc3RlZCA9IDA7CgoJaWYgKGVudHJ5LT5zaXplIDwgc2l6ZSkKCSAgICBjb250aW51ZTsKCglpZiAoYWxpZ25tZW50KSB7CgkgICAgcmVnaXN0ZXIgdW5zaWduZWQgdG1wID0gZW50cnktPnN0YXJ0ICUgYWxpZ25tZW50OwoKCSAgICBpZiAodG1wKQoJCXdhc3RlZCArPSBhbGlnbm1lbnQgLSB0bXA7Cgl9CgoJaWYgKGVudHJ5LT5zaXplID49IHNpemUgKyB3YXN0ZWQpIHsKCSAgICBpZiAoIWJlc3RfbWF0Y2gpCgkJcmV0dXJuIGVudHJ5OwoJICAgIGlmIChzaXplIDwgYmVzdF9zaXplKSB7CgkJYmVzdCA9IGVudHJ5OwoJCWJlc3Rfc2l6ZSA9IGVudHJ5LT5zaXplOwoJICAgIH0KCX0KICAgIH0KCiAgICByZXR1cm4gYmVzdDsKfQoKaW50CndzYm1NTWNsZWFuKHN0cnVjdCBfV3NibU1NICptbSkKewogICAgc3RydWN0IF9Xc2JtTGlzdEhlYWQgKmhlYWQgPSAmbW0tPm1sX2VudHJ5OwoKICAgIHJldHVybiAoaGVhZC0+bmV4dC0+bmV4dCA9PSBoZWFkKTsKfQoKaW50CndzYm1NTWluaXQoc3RydWN0IF9Xc2JtTU0gKm1tLCB1bnNpZ25lZCBsb25nIHN0YXJ0LCB1bnNpZ25lZCBsb25nIHNpemUpCnsKICAgIFdTQk1JTklUTElTVEhFQUQoJm1tLT5tbF9lbnRyeSk7CiAgICBXU0JNSU5JVExJU1RIRUFEKCZtbS0+ZmxfZW50cnkpOwoKICAgIHJldHVybiB3c2JtTU1DcmVhdGVUYWlsTm9kZShtbSwgc3RhcnQsIHNpemUpOwp9Cgp2b2lkCndzYm1NTXRha2Vkb3duKHN0cnVjdCBfV3NibU1NICptbSkKewogICAgc3RydWN0IF9Xc2JtTGlzdEhlYWQgKmJub2RlID0gbW0tPmZsX2VudHJ5Lm5leHQ7CiAgICBzdHJ1Y3QgX1dzYm1NTU5vZGUgKmVudHJ5OwoKICAgIGVudHJ5ID0gV1NCTUxJU1RFTlRSWShibm9kZSwgc3RydWN0IF9Xc2JtTU1Ob2RlLCBmbF9lbnRyeSk7CgogICAgaWYgKGVudHJ5LT5tbF9lbnRyeS5uZXh0ICE9ICZtbS0+bWxfZW50cnkgfHwKCWVudHJ5LT5mbF9lbnRyeS5uZXh0ICE9ICZtbS0+ZmxfZW50cnkpIHsKCXJldHVybjsKICAgIH0KCiAgICBXU0JNTElTVERFTCgmZW50cnktPmZsX2VudHJ5KTsKICAgIFdTQk1MSVNUREVMKCZlbnRyeS0+bWxfZW50cnkpOwogICAgZnJlZShlbnRyeSk7Cn0K