LyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiAgICAgICAgICAgICAgICAKICogRmlsZW5hbWU6ICAgICAgYWN0aXN5cy5jCiAqIFZlcnNpb246ICAgICAgIDEuMQogKiBEZXNjcmlwdGlvbjogICBJbXBsZW1lbnRhdGlvbiBmb3IgdGhlIEFDVGlTWVMgSVItMjIwTCBhbmQgSVItMjIwTCsgCiAqICAgICAgICAgICAgICAgIGRvbmdsZXMKICogU3RhdHVzOiAgICAgICAgQmV0YS4KICogQXV0aG9yczogICAgICAgRGFnIEJyYXR0bGkgPGRhZ2JAY3MudWl0Lm5vPiAoaW5pdGlhbGx5KQogKgkJICBKZWFuIFRvdXJyaWxoZXMgPGp0QGhwbC5ocC5jb20+IChuZXcgdmVyc2lvbikKICoJCSAgTWFydGluIERpZWhsIDxtYWRAbWRpZWhsLmRlPiAobmV3IHZlcnNpb24gZm9yIHNpcl9kZXYpCiAqIENyZWF0ZWQgYXQ6ICAgIFdlZCBPY3QgMjEgMjA6MDI6MzUgMTk5OAogKiBNb2RpZmllZCBhdDogICBTdW4gT2N0IDI3IDIyOjAyOjEzIDIwMDIKICogTW9kaWZpZWQgYnk6ICAgTWFydGluIERpZWhsIDxtYWRAbWRpZWhsLmRlPgogKiAKICogICAgIENvcHlyaWdodCAoYykgMTk5OC0xOTk5IERhZyBCcmF0dGxpLCBBbGwgUmlnaHRzIFJlc2VydmVkLgogKiAgICAgQ29weXJpZ2h0IChjKSAxOTk5IEplYW4gVG91cnJpbGhlcwogKiAgICAgQ29weXJpZ2h0IChjKSAyMDAyIE1hcnRpbiBEaWVobAogKiAgICAgIAogKiAgICAgVGhpcyBwcm9ncmFtIGlzIGZyZWUgc29mdHdhcmU7IHlvdSBjYW4gcmVkaXN0cmlidXRlIGl0IGFuZC9vciAKICogICAgIG1vZGlmeSBpdCB1bmRlciB0aGUgdGVybXMgb2YgdGhlIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlIGFzIAogKiAgICAgcHVibGlzaGVkIGJ5IHRoZSBGcmVlIFNvZnR3YXJlIEZvdW5kYXRpb247IGVpdGhlciB2ZXJzaW9uIDIgb2YgCiAqICAgICB0aGUgTGljZW5zZSwgb3IgKGF0IHlvdXIgb3B0aW9uKSBhbnkgbGF0ZXIgdmVyc2lvbi4KICogIAogKiAgICAgTmVpdGhlciBEYWcgQnJhdHRsaSBub3IgVW5pdmVyc2l0eSBvZiBUcm9tc/ggYWRtaXQgbGlhYmlsaXR5IG5vcgogKiAgICAgcHJvdmlkZSB3YXJyYW50eSBmb3IgYW55IG9mIHRoaXMgc29mdHdhcmUuIFRoaXMgbWF0ZXJpYWwgaXMgCiAqICAgICBwcm92aWRlZCAiQVMtSVMiIGFuZCBhdCBubyBjaGFyZ2UuCiAqICAgICAKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwoKLyoKICogQ2hhbmdlbG9nCiAqCiAqIDAuOCAtPiAwLjk5OTkgLSBKZWFuCiAqCW8gTmV3IGluaXRpYWxpc2F0aW9uIHByb2NlZHVyZSA6IG11Y2ggc2FmZXIgYW5kIGNvcnJlY3QKICoJbyBOZXcgcHJvY2VkdXJlIHRoZSBjaGFuZ2Ugc3BlZWQgOiBtdWNoIGZhc3RlciBhbmQgc2ltcGxlcgogKglvIE90aGVyIGNsZWFudXBzICYgY29tbWVudHMKICoJVGhhbmtzIHRvIExpY2hlbiBXYW5nIEAgQWN0aXN5cyBmb3IgaGlzIGV4Y2VsbGVudCBoZWxwLi4uCiAqCiAqIDEuMCAtPiAxLjEgLSBNYXJ0aW4gRGllaGwKICoJbW9kaWZpZWQgZm9yIG5ldyBzaXIgaW5mcmFzdHJ1Y3R1cmUKICovCgojaW5jbHVkZSA8bGludXgvbW9kdWxlLmg+CiNpbmNsdWRlIDxsaW51eC9kZWxheS5oPgojaW5jbHVkZSA8bGludXgvaW5pdC5oPgoKI2luY2x1ZGUgPG5ldC9pcmRhL2lyZGEuaD4KCiNpbmNsdWRlICJzaXItZGV2LmgiCgovKiAKICogRGVmaW5lIHRoZSB0aW1pbmcgb2YgdGhlIHB1bHNlcyB3ZSBzZW5kIHRvIHRoZSBkb25nbGUgKHRvIHJlc2V0IGl0LCBhbmQKICogdG8gdG9nZ2xlIHNwZWVkcykuIEJhc2ljYWxseSwgdGhlIGxpbWl0IGhlcmUgaXMgdGhlIHByb3BhZ2F0aW9uIHNwZWVkIG9mCiAqIHRoZSBzaWduYWxzIHRocm91Z2ggdGhlIHNlcmlhbCBwb3J0LCB0aGUgZG9uZ2xlIGJlaW5nIG11Y2ggZmFzdGVyLiAgQW55CiAqIHNlcmlhbCBwb3J0IHN1cHBvcnQgMTE1IGtiL3MsIHNvIHdlIGFyZSBzdXJlIHRoYXQgcHVsc2VzIDguNSB1cyB3aWRlIGNhbgogKiBnbyB0aHJvdWdoIGNsZWFubHkgLiBJZiB5b3UgYXJlIG9uIHRoZSB3aWxkIHNpZGUsIHlvdSBjYW4gdHJ5IHRvIGxvd2VyCiAqIHRoaXMgdmFsdWUgKEFjdGlzeXMgcmVjb21tZW5kZWQgbWUgMiB1cywgYW5kIDAgdXMgd29yayBmb3IgbWUgb24gYSBQMjMzISkKICovCiNkZWZpbmUgTUlOX0RFTEFZIDEwCS8qIDEwIHVzIHRvIGJlIG9uIHRoZSBjb25zZXJ2YXRpdmUgc2lkZSAqLwoKc3RhdGljIGludCBhY3Rpc3lzX29wZW4oc3RydWN0IHNpcl9kZXYgKik7CnN0YXRpYyBpbnQgYWN0aXN5c19jbG9zZShzdHJ1Y3Qgc2lyX2RldiAqKTsKc3RhdGljIGludCBhY3Rpc3lzX2NoYW5nZV9zcGVlZChzdHJ1Y3Qgc2lyX2RldiAqLCB1bnNpZ25lZCk7CnN0YXRpYyBpbnQgYWN0aXN5c19yZXNldChzdHJ1Y3Qgc2lyX2RldiAqKTsKCi8qIFRoZXNlIGFyZSB0aGUgYmF1ZHJhdGVzIHN1cHBvcnRlZCwgaW4gdGhlIG9yZGVyIGF2YWlsYWJsZSAqLwovKiBOb3RlIDogdGhlIDIyMEwgZG9lc24ndCBzdXBwb3J0IDM4NDAwLCBidXQgd2Ugd2lsbCBmaXggdGhhdCBiZWxvdyAqLwpzdGF0aWMgdW5zaWduZWQgYmF1ZF9yYXRlc1tdID0geyA5NjAwLCAxOTIwMCwgNTc2MDAsIDExNTIwMCwgMzg0MDAgfTsKCiNkZWZpbmUgTUFYX1NQRUVEUyAoc2l6ZW9mKGJhdWRfcmF0ZXMpL3NpemVvZihiYXVkX3JhdGVzWzBdKSkKCnN0YXRpYyBzdHJ1Y3QgZG9uZ2xlX2RyaXZlciBhY3QyMjBsID0gewoJLm93bmVyCQk9IFRISVNfTU9EVUxFLAoJLmRyaXZlcl9uYW1lCT0gIkFjdGlzeXMgQUNULTIyMEwiLAoJLnR5cGUJCT0gSVJEQV9BQ1RJU1lTX0RPTkdMRSwKCS5vcGVuCQk9IGFjdGlzeXNfb3BlbiwKCS5jbG9zZQkJPSBhY3Rpc3lzX2Nsb3NlLAoJLnJlc2V0CQk9IGFjdGlzeXNfcmVzZXQsCgkuc2V0X3NwZWVkCT0gYWN0aXN5c19jaGFuZ2Vfc3BlZWQsCn07CgpzdGF0aWMgc3RydWN0IGRvbmdsZV9kcml2ZXIgYWN0MjIwbF9wbHVzID0gewoJLm93bmVyCQk9IFRISVNfTU9EVUxFLAoJLmRyaXZlcl9uYW1lCT0gIkFjdGlzeXMgQUNULTIyMEwrIiwKCS50eXBlCQk9IElSREFfQUNUSVNZU19QTFVTX0RPTkdMRSwKCS5vcGVuCQk9IGFjdGlzeXNfb3BlbiwKCS5jbG9zZQkJPSBhY3Rpc3lzX2Nsb3NlLAoJLnJlc2V0CQk9IGFjdGlzeXNfcmVzZXQsCgkuc2V0X3NwZWVkCT0gYWN0aXN5c19jaGFuZ2Vfc3BlZWQsCn07CgpzdGF0aWMgaW50IF9faW5pdCBhY3Rpc3lzX3Npcl9pbml0KHZvaWQpCnsKCWludCByZXQ7CgoJLyogRmlyc3QsIHJlZ2lzdGVyIGFuIEFjdGlzeXMgMjIwTCBkb25nbGUgKi8KCXJldCA9IGlyZGFfcmVnaXN0ZXJfZG9uZ2xlKCZhY3QyMjBsKTsKCWlmIChyZXQgPCAwKQoJCXJldHVybiByZXQ7CgoJLyogTm93LCByZWdpc3RlciBhbiBBY3Rpc3lzIDIyMEwrIGRvbmdsZSAqLwoJcmV0ID0gaXJkYV9yZWdpc3Rlcl9kb25nbGUoJmFjdDIyMGxfcGx1cyk7CglpZiAocmV0IDwgMCkgewoJCWlyZGFfdW5yZWdpc3Rlcl9kb25nbGUoJmFjdDIyMGwpOwoJCXJldHVybiByZXQ7Cgl9CglyZXR1cm4gMDsKfQoKc3RhdGljIHZvaWQgX19leGl0IGFjdGlzeXNfc2lyX2NsZWFudXAodm9pZCkKewoJLyogV2UgaGF2ZSB0byByZW1vdmUgYm90aCBkb25nbGVzICovCglpcmRhX3VucmVnaXN0ZXJfZG9uZ2xlKCZhY3QyMjBsX3BsdXMpOwoJaXJkYV91bnJlZ2lzdGVyX2RvbmdsZSgmYWN0MjIwbCk7Cn0KCnN0YXRpYyBpbnQgYWN0aXN5c19vcGVuKHN0cnVjdCBzaXJfZGV2ICpkZXYpCnsKCXN0cnVjdCBxb3NfaW5mbyAqcW9zID0gJmRldi0+cW9zOwoKCXNpcmRldl9zZXRfZHRyX3J0cyhkZXYsIFRSVUUsIFRSVUUpOwoKCS8qIFNldCB0aGUgc3BlZWRzIHdlIGNhbiBhY2NlcHQgKi8KCXFvcy0+YmF1ZF9yYXRlLmJpdHMgJj0gSVJfOTYwMHxJUl8xOTIwMHxJUl8zODQwMHxJUl81NzYwMHxJUl8xMTUyMDA7CgoJLyogUmVtb3ZlIHN1cHBvcnQgZm9yIDM4NDAwIGlmIHRoaXMgaXMgbm90IGEgMjIwTCsgZG9uZ2xlICovCglpZiAoZGV2LT5kb25nbGVfZHJ2LT50eXBlID09IElSREFfQUNUSVNZU19ET05HTEUpCgkJcW9zLT5iYXVkX3JhdGUuYml0cyAmPSB+SVJfMzg0MDA7CgoJcW9zLT5taW5fdHVybl90aW1lLmJpdHMgPSAweDdmOyAvKiBOZWVkcyAwLjAxIG1zICovCglpcmRhX3Fvc19iaXRzX3RvX3ZhbHVlKHFvcyk7CgoJLyogaXJkYSB0aHJlYWQgd2FpdHMgNTAgbXNlYyBmb3IgcG93ZXIgc2V0dGxpbmcgKi8KCglyZXR1cm4gMDsKfQoKc3RhdGljIGludCBhY3Rpc3lzX2Nsb3NlKHN0cnVjdCBzaXJfZGV2ICpkZXYpCnsKCS8qIFBvd2VyIG9mZiB0aGUgZG9uZ2xlICovCglzaXJkZXZfc2V0X2R0cl9ydHMoZGV2LCBGQUxTRSwgRkFMU0UpOwoKCXJldHVybiAwOwp9CgovKgogKiBGdW5jdGlvbiBhY3Rpc3lzX2NoYW5nZV9zcGVlZCAodGFzaykKICoKICogICAgQ2hhbmdlIHNwZWVkIG9mIHRoZSBBQ1RpU1lTIElSLTIyMEwgYW5kIElSLTIyMEwrIHR5cGUgSXJEQSBkb25nbGVzLgogKiAgICBUbyBjeWNsZSB0aHJvdWdoIHRoZSBhdmFpbGFibGUgYmF1ZCByYXRlcywgcHVsc2UgUlRTIGxvdyBmb3IgYSBmZXcgdXMuCiAqCiAqCUZpcnN0LCB3ZSByZXNldCB0aGUgZG9uZ2xlIHRvIGFsd2F5cyBzdGFydCBmcm9tIGEga25vd24gc3RhdGUuCiAqCVRoZW4sIHdlIGN5Y2xlIHRocm91Z2ggdGhlIHNwZWVkcyBieSBwdWxzaW5nIFJUUyBsb3cgYW5kIHRoZW4gdXAuCiAqCVRoZSBkb25nbGUgYWxsb3cgdXMgdG8gcHVsc2UgcXVpdGUgZmFzdCwgc2Ugd2UgY2FuIHNldCBzcGVlZCBpbiBvbmUgZ28sCiAqIHdoaWNoIGlzIG11c3QgZmFzdGVyICggPCAxMDAgdXMpIGFuZCBsZXNzIGNvbXBsZXggdGhhbiB3aGF0IGlzIGZvdW5kCiAqIGluIHNvbWUgb3RoZXIgZG9uZ2xlIGRyaXZlcnMuLi4KICoJTm90ZSB0aGF0IGV2ZW4gaWYgdGhlIG5ldyBzcGVlZCBpcyB0aGUgc2FtZSBhcyB0aGUgY3VycmVudCBzcGVlZCwKICogd2UgcmVhc3NlcnQgdGhlIHNwZWVkLiBUaGlzIG1ha2Ugc3VyZSB0aGF0IHRoaW5ncyBhcmUgYWxsIHJpZ2h0LAogKiBhbmQgaXQncyBmYXN0IGFueXdheS4uLgogKglCeSB0aGUgd2F5LCB0aGlzIGZ1bmN0aW9uIHdpbGwgd29yayBmb3IgYm90aCB0eXBlIG9mIGRvbmdsZXMsCiAqIGJlY2F1c2UgdGhlIGFkZGl0aW9uYWwgc3BlZWQgaXMgYXQgdGhlIGVuZCBvZiB0aGUgc2VxdWVuY2UuLi4KICovCnN0YXRpYyBpbnQgYWN0aXN5c19jaGFuZ2Vfc3BlZWQoc3RydWN0IHNpcl9kZXYgKmRldiwgdW5zaWduZWQgc3BlZWQpCnsKCWludCByZXQgPSAwOwoJaW50IGkgPSAwOwoKICAgICAgICBJUkRBX0RFQlVHKDQsICIlcygpLCBzcGVlZD0lZCAod2FzICVkKVxuIiwgX19GVU5DVElPTl9fLAogICAgICAgIAlzcGVlZCwgZGV2LT5zcGVlZCk7CgoJLyogZG9uZ2xlIHdhcyBhbHJlYWR5IHJlc2V0dGVkIGZyb20gaXJkYV9yZXF1ZXN0IHN0YXRlIG1hY2hpbmUsCgkgKiB3ZSBhcmUgaW4ga25vd24gc3RhdGUgKGRvbmdsZSBkZWZhdWx0KQoJICovCgoJLyogCgkgKiBOb3csIHdlIGNhbiBzZXQgdGhlIHNwZWVkIHJlcXVlc3RlZC4gU2VuZCBSVFMgcHVsc2VzIHVudGlsIHdlCiAgICAgICAgICogcmVhY2ggdGhlIHRhcmdldCBzcGVlZCAKCSAqLwoJZm9yIChpID0gMDsgaSA8IE1BWF9TUEVFRFM7IGkrKykgewoJCWlmIChzcGVlZCA9PSBiYXVkX3JhdGVzW2ldKSB7CgkJCWRldi0+c3BlZWQgPSBzcGVlZDsKCQkJYnJlYWs7CgkJfQoJCS8qIFNldCBSVFMgbG93IGZvciAxMCB1cyAqLwoJCXNpcmRldl9zZXRfZHRyX3J0cyhkZXYsIFRSVUUsIEZBTFNFKTsKCQl1ZGVsYXkoTUlOX0RFTEFZKTsKCgkJLyogU2V0IFJUUyBoaWdoIGZvciAxMCB1cyAqLwoJCXNpcmRldl9zZXRfZHRyX3J0cyhkZXYsIFRSVUUsIFRSVUUpOwoJCXVkZWxheShNSU5fREVMQVkpOwoJfQoKCS8qIENoZWNrIGlmIGxpZmUgaXMgc3dlZXQuLi4gKi8KCWlmIChpID49IE1BWF9TUEVFRFMpIHsKCQlhY3Rpc3lzX3Jlc2V0KGRldik7CgkJcmV0ID0gLUVJTlZBTDsgIC8qIFRoaXMgc2hvdWxkIG5vdCBoYXBwZW4gKi8KCX0KCgkvKiBCYXN0YSBsYXZvcm8sIG9uIHNlIGNhc3NlIGQnaWNpLi4uICovCglyZXR1cm4gcmV0Owp9CgovKgogKiBGdW5jdGlvbiBhY3Rpc3lzX3Jlc2V0ICh0YXNrKQogKgogKiAgICAgIFJlc2V0IHRoZSBBY3Rpc3lzIHR5cGUgZG9uZ2xlLiBXYXJuaW5nLCB0aGlzIGZ1bmN0aW9uIG11c3Qgb25seSBiZQogKiAgICAgIGNhbGxlZCB3aXRoIGEgcHJvY2VzcyBjb250ZXh0IQogKgogKiBXZSBuZWVkIHRvIGRvIHR3byB0aGluZ3MgaW4gdGhpcyBmdW5jdGlvbiA6CiAqCW8gZmlyc3QgbWFrZSBzdXJlIHRoYXQgdGhlIGRvbmdsZSBpcyBpbiBhIHN0YXRlIHdoZXJlIGl0IGNhbiBvcGVyYXRlCiAqCW8gc2Vjb25kIHB1dCB0aGUgZG9uZ2xlIGluIGEga25vdyBzdGF0ZQogKgogKglUaGUgZG9uZ2xlIGlzIHBvd2VyZWQgb2YgdGhlIFJUUyBhbmQgRFRSIGxpbmVzLiBJbiB0aGUgZG9uZ2xlLCB0aGVyZQogKiBpcyBhIGJpZyBjYXBhY2l0b3IgdG8gYWNjb21tb2RhdGUgdGhlIGN1cnJlbnQgc3Bpa2VzLiBUaGlzIGNhcGFjaXRvcgogKiB0YWtlcyBhIGxlYXN0IDUwIG1zIHRvIGJlIGNoYXJnZWQuIEluIHRoZW9yeSwgdGhlIEJpb3Mgc2V0IHRob3NlIGxpbmVzCiAqIHVwLCBzbyBieSB0aGUgdGltZSB3ZSBhcnJpdmUgaGVyZSB3ZSBzaG91bGQgYmUgc2V0LiBJdCBkb2Vzbid0IGh1cnQKICogdG8gYmUgb24gdGhlIGNvbnNlcnZhdGl2ZSBzaWRlLCBzbyB3ZSB3aWxsIHdhaXQuLi4KICogPE1hcnRpbiA6IG1vdmUgYWJvdmUgY29tbWVudCB0byBpcmRhX2NvbmZpZ19mc20+CiAqCVRoZW4sIHdlIHNldCB0aGUgc3BlZWQgdG8gOTYwMCBiL3MgdG8gZ2V0IGluIGEga25vd24gc3RhdGUgKHNlZSBpbgogKiBjaGFuZ2Vfc3BlZWQgZm9yIGRldGFpbHMpLiBJdCBpcyBuZWVkZWQgYmVjYXVzZSB0aGUgSXJEQSBzdGFjawogKiBoYXMgdHJpZWQgdG8gc2V0IHRoZSBzcGVlZCBpbW1lZGlhdGVseSBhZnRlciBvdXIgZmlyc3QgcmV0dXJuLAogKiBzbyBiZWZvcmUgd2UgY2FuIGJlIHN1cmUgdGhlIGRvbmdsZSBpcyB1cCBhbmQgcnVubmluZy4KICovCgpzdGF0aWMgaW50IGFjdGlzeXNfcmVzZXQoc3RydWN0IHNpcl9kZXYgKmRldikKewoJLyogUmVzZXQgdGhlIGRvbmdsZSA6IHNldCBEVFIgbG93IGZvciAxMCB1cyAqLwoJc2lyZGV2X3NldF9kdHJfcnRzKGRldiwgRkFMU0UsIFRSVUUpOwoJdWRlbGF5KE1JTl9ERUxBWSk7CgoJLyogR28gYmFjayB0byBub3JtYWwgbW9kZSAqLwoJc2lyZGV2X3NldF9kdHJfcnRzKGRldiwgVFJVRSwgVFJVRSk7CgkKCWRldi0+c3BlZWQgPSA5NjAwOwkvKiBUaGF0J3MgdGhlIGRlZmF1bHQgKi8KCglyZXR1cm4gMDsKfQoKTU9EVUxFX0FVVEhPUigiRGFnIEJyYXR0bGkgPGRhZ2JAY3MudWl0Lm5vPiAtIEplYW4gVG91cnJpbGhlcyA8anRAaHBsLmhwLmNvbT4iKTsKTU9EVUxFX0RFU0NSSVBUSU9OKCJBQ1RpU1lTIElSLTIyMEwgYW5kIElSLTIyMEwrIGRvbmdsZSBkcml2ZXIiKTsJCk1PRFVMRV9MSUNFTlNFKCJHUEwiKTsKTU9EVUxFX0FMSUFTKCJpcmRhLWRvbmdsZS0yIik7IC8qIElSREFfQUNUSVNZU19ET05HTEUgKi8KTU9EVUxFX0FMSUFTKCJpcmRhLWRvbmdsZS0zIik7IC8qIElSREFfQUNUSVNZU19QTFVTX0RPTkdMRSAqLwoKbW9kdWxlX2luaXQoYWN0aXN5c19zaXJfaW5pdCk7Cm1vZHVsZV9leGl0KGFjdGlzeXNfc2lyX2NsZWFudXApOwo=