LyogRGlyZWN0M0QgVmVydGV4IEJ1ZmZlcgogKiBDb3B5cmlnaHQgKGMpIDIwMDIgTGlvbmVsIFVMTUVSCiAqIENvcHlyaWdodCAoYykgMjAwNiBTdGVmYW4gRNZTSU5HRVIKICoKICogVGhpcyBmaWxlIGNvbnRhaW5zIHRoZSBpbXBsZW1lbnRhdGlvbiBvZiBEaXJlY3QzRFZlcnRleEJ1ZmZlciBDT00gb2JqZWN0CiAqCiAqIFRoaXMgbGlicmFyeSBpcyBmcmVlIHNvZnR3YXJlOyB5b3UgY2FuIHJlZGlzdHJpYnV0ZSBpdCBhbmQvb3IKICogbW9kaWZ5IGl0IHVuZGVyIHRoZSB0ZXJtcyBvZiB0aGUgR05VIExlc3NlciBHZW5lcmFsIFB1YmxpYwogKiBMaWNlbnNlIGFzIHB1Ymxpc2hlZCBieSB0aGUgRnJlZSBTb2Z0d2FyZSBGb3VuZGF0aW9uOyBlaXRoZXIKICogdmVyc2lvbiAyLjEgb2YgdGhlIExpY2Vuc2UsIG9yIChhdCB5b3VyIG9wdGlvbikgYW55IGxhdGVyIHZlcnNpb24uCiAqCiAqIFRoaXMgbGlicmFyeSBpcyBkaXN0cmlidXRlZCBpbiB0aGUgaG9wZSB0aGF0IGl0IHdpbGwgYmUgdXNlZnVsLAogKiBidXQgV0lUSE9VVCBBTlkgV0FSUkFOVFk7IHdpdGhvdXQgZXZlbiB0aGUgaW1wbGllZCB3YXJyYW50eSBvZgogKiBNRVJDSEFOVEFCSUxJVFkgb3IgRklUTkVTUyBGT1IgQSBQQVJUSUNVTEFSIFBVUlBPU0UuICBTZWUgdGhlIEdOVQogKiBMZXNzZXIgR2VuZXJhbCBQdWJsaWMgTGljZW5zZSBmb3IgbW9yZSBkZXRhaWxzLgogKgogKiBZb3Ugc2hvdWxkIGhhdmUgcmVjZWl2ZWQgYSBjb3B5IG9mIHRoZSBHTlUgTGVzc2VyIEdlbmVyYWwgUHVibGljCiAqIExpY2Vuc2UgYWxvbmcgd2l0aCB0aGlzIGxpYnJhcnk7IGlmIG5vdCwgd3JpdGUgdG8gdGhlIEZyZWUgU29mdHdhcmUKICogRm91bmRhdGlvbiwgSW5jLiwgNTEgRnJhbmtsaW4gU3QsIEZpZnRoIEZsb29yLCBCb3N0b24sIE1BIDAyMTEwLTEzMDEsIFVTQQogKi8KCiNpbmNsdWRlICJjb25maWcuaCIKI2luY2x1ZGUgIndpbmUvcG9ydC5oIgojaW5jbHVkZSAid2luZS9kZWJ1Zy5oIgoKI2luY2x1ZGUgPGFzc2VydC5oPgojaW5jbHVkZSA8c3RkYXJnLmg+CiNpbmNsdWRlIDxzdHJpbmcuaD4KI2luY2x1ZGUgPHN0ZGxpYi5oPgoKI2RlZmluZSBDT0JKTUFDUk9TCgojaW5jbHVkZSAid2luZGVmLmgiCiNpbmNsdWRlICJ3aW5iYXNlLmgiCiNpbmNsdWRlICJ3aW5ubHMuaCIKI2luY2x1ZGUgIndpbmVycm9yLmgiCiNpbmNsdWRlICJ3aW5nZGkuaCIKI2luY2x1ZGUgIndpbmUvZXhjZXB0aW9uLmgiCiNpbmNsdWRlICJleGNwdC5oIgoKI2luY2x1ZGUgImRkcmF3LmgiCiNpbmNsdWRlICJkM2QuaCIKCiNpbmNsdWRlICJkZHJhd19wcml2YXRlLmgiCgpXSU5FX0RFRkFVTFRfREVCVUdfQ0hBTk5FTChkM2Q3KTsKV0lORV9ERUNMQVJFX0RFQlVHX0NIQU5ORUwoZGRyYXdfdGh1bmspOwoKCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJVW5rbm93biBNZXRob2RzCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3OjpRdWVyeUludGVyZmFjZQogKgogKiBUaGUgUXVlcnlJbnRlcmZhY2UgTWV0aG9kIGZvciBWZXJ0ZXggQnVmZmVycwogKiBGb3IgYSBsaW5rIHRvIFF1ZXJ5SW50ZXJmYWNlIHJ1bGVzLCBzZWUgSURpcmVjdERyYXc3OjpRdWVyeUludGVyZmFjZQogKgogKiBQYXJhbXMKICogIHJpaWQ6IFF1ZXJ5aWVkIEludGVyZmFjZSBpZAogKiAgb2JqOiBBZGRyZXNzIHRvIHJldHVybiB0aGUgaW50ZXJmYWNlIHBvaW50ZXIKICoKICogUmV0dXJuczoKICogIFNfT0sgb24gc3VjY2VzcwogKiAgRV9OT0lOVEVSRkFDRSBpZiB0aGUgaW50ZXJmYWNlIHdhc24ndCBmb3VuZAogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0RWZXJ0ZXhCdWZmZXJJbXBsX1F1ZXJ5SW50ZXJmYWNlKElEaXJlY3QzRFZlcnRleEJ1ZmZlcjcgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFJFRklJRCByaWlkLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHZvaWQgICoqb2JqKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0RWZXJ0ZXhCdWZmZXJJbXBsLCBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3LCBpZmFjZSk7CiAgICBUUkFDRSgiKCVwKS0+KCVzLCVwKVxuIiwgVGhpcywgZGVidWdzdHJfZ3VpZChyaWlkKSwgb2JqKTsKCiAgICAvKiBCeSBkZWZhdWx0LCBzZXQgdGhlIG9iamVjdCBwb2ludGVyIHRvIE5VTEwgKi8KICAgICpvYmogPSBOVUxMOwoKICAgIGlmICggSXNFcXVhbEdVSUQoICZJSURfSVVua25vd24sICByaWlkICkgKQogICAgewogICAgICAgIElEaXJlY3QzRFZlcnRleEJ1ZmZlcjdfQWRkUmVmKElDT01fSU5URVJGQUNFKFRoaXMsSURpcmVjdDNEVmVydGV4QnVmZmVyNykpOwogICAgICAgICpvYmogPSBpZmFjZTsKICAgICAgICBUUkFDRSgiICBDcmVhdGluZyBJVW5rbm93biBpbnRlcmZhY2UgYXQgJXAuXG4iLCAqb2JqKTsKICAgICAgICByZXR1cm4gU19PSzsKICAgIH0KICAgIGlmICggSXNFcXVhbEdVSUQoICZJSURfSURpcmVjdDNEVmVydGV4QnVmZmVyLCByaWlkICkgKQogICAgewogICAgICAgIElEaXJlY3QzRFZlcnRleEJ1ZmZlcjdfQWRkUmVmKElDT01fSU5URVJGQUNFKFRoaXMsSURpcmVjdDNEVmVydGV4QnVmZmVyNykpOwogICAgICAgICpvYmogPSBJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXIpOwogICAgICAgIFRSQUNFKCIgIENyZWF0aW5nIElEaXJlY3QzRFZlcnRleEJ1ZmZlciBpbnRlcmZhY2UgJXBcbiIsICpvYmopOwogICAgICAgIHJldHVybiBTX09LOwogICAgfQogICAgaWYgKCBJc0VxdWFsR1VJRCggJklJRF9JRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3LCByaWlkICkgKQogICAgewogICAgICAgIElEaXJlY3QzRFZlcnRleEJ1ZmZlcjdfQWRkUmVmKElDT01fSU5URVJGQUNFKFRoaXMsSURpcmVjdDNEVmVydGV4QnVmZmVyNykpOwogICAgICAgICpvYmogPSBJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3KTsKICAgICAgICBUUkFDRSgiICBDcmVhdGluZyBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3IGludGVyZmFjZSAlcFxuIiwgKm9iaik7CiAgICAgICAgcmV0dXJuIFNfT0s7CiAgICB9CiAgICBGSVhNRSgiKCVwKTogaW50ZXJmYWNlIGZvciBJSUQgJXMgTk9UIGZvdW5kIVxuIiwgVGhpcywgZGVidWdzdHJfZ3VpZChyaWlkKSk7CiAgICByZXR1cm4gRV9OT0lOVEVSRkFDRTsKfQoKc3RhdGljIEhSRVNVTFQgV0lOQVBJClRodW5rX0lEaXJlY3QzRFZlcnRleEJ1ZmZlckltcGxfMV9RdWVyeUludGVyZmFjZShJRGlyZWN0M0RWZXJ0ZXhCdWZmZXIgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgUkVGSUlEIHJpaWQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2b2lkICoqb2JqKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0RWZXJ0ZXhCdWZmZXJJbXBsLCBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXIsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglcywlcCkgdGh1bmtpbmcgdG8gSURpcmVjdDNEVmVydGV4QnVmZmVyNyBpbnRlcmZhY2UuXG4iLCBUaGlzLCBkZWJ1Z3N0cl9ndWlkKHJpaWQpLCBvYmopOwoKICAgIHJldHVybiBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3X1F1ZXJ5SW50ZXJmYWNlKElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRFZlcnRleEJ1ZmZlcjcpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcmlpZCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIG9iaik7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3OjpBZGRSZWYKICoKICogQWRkUmVmIGZvciBWZXJ0ZXggQnVmZmVycwogKgogKiBSZXR1cm5zOgogKiAgVGhlIG5ldyByZWZjb3VudAogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBVTE9ORyBXSU5BUEkKSURpcmVjdDNEVmVydGV4QnVmZmVySW1wbF9BZGRSZWYoSURpcmVjdDNEVmVydGV4QnVmZmVyNyAqaWZhY2UpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRFZlcnRleEJ1ZmZlckltcGwsIElEaXJlY3QzRFZlcnRleEJ1ZmZlcjcsIGlmYWNlKTsKICAgIFVMT05HIHJlZiA9IEludGVybG9ja2VkSW5jcmVtZW50KCZUaGlzLT5yZWYpOwoKICAgIFRSQUNFKCIoJXAvJXApLT4oKSBpbmNyZW1lbnRpbmcgZnJvbSAlbHUuXG4iLCBUaGlzLCBpZmFjZSwgcmVmIC0gMSk7CgogICAgcmV0dXJuIHJlZjsKfQoKc3RhdGljIFVMT05HIFdJTkFQSQpUaHVua19JRGlyZWN0M0RWZXJ0ZXhCdWZmZXJJbXBsXzFfQWRkUmVmKElEaXJlY3QzRFZlcnRleEJ1ZmZlciAqaWZhY2UpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRFZlcnRleEJ1ZmZlckltcGwsIElEaXJlY3QzRFZlcnRleEJ1ZmZlciwgaWZhY2UpOwogICAgVFJBQ0VfKGRkcmF3X3RodW5rKSgiKCVwKS0+KCkgdGh1bmtpbmcgdG8gSURpcmVjdDNEVmVydGV4QnVmZmVyNyBpbnRlcmZhY2UuXG4iLCBUaGlzKTsKCiAgICByZXR1cm4gSURpcmVjdDNEVmVydGV4QnVmZmVyN19BZGRSZWYoSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNEVmVydGV4QnVmZmVyNykpOwp9CgoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRFZlcnRleEJ1ZmZlcjc6OlJlbGVhc2UKICoKICogUmVsZWFzZSBmb3IgVmVydGV4IEJ1ZmZlcnMKICoKICogUmV0dXJuczoKICogIFRoZSBuZXcgcmVmY291bnQKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgVUxPTkcgV0lOQVBJCklEaXJlY3QzRFZlcnRleEJ1ZmZlckltcGxfUmVsZWFzZShJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3ICppZmFjZSkKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNEVmVydGV4QnVmZmVySW1wbCwgSURpcmVjdDNEVmVydGV4QnVmZmVyNywgaWZhY2UpOwogICAgVUxPTkcgcmVmID0gSW50ZXJsb2NrZWREZWNyZW1lbnQoJlRoaXMtPnJlZik7CgogICAgVFJBQ0UoIiglcCktPigpIGRlY3JlbWVudGluZyBmcm9tICVsdS5cbiIsIFRoaXMsIHJlZiArIDEpOwoKICAgIGlmIChyZWYgPT0gMCkKICAgIHsKICAgICAgICBJV2luZUQzRFZlcnRleEJ1ZmZlcl9SZWxlYXNlKFRoaXMtPndpbmVEM0RWZXJ0ZXhCdWZmZXIpOwogICAgICAgIEhlYXBGcmVlKEdldFByb2Nlc3NIZWFwKCksIDAsIFRoaXMpOwogICAgICAgIHJldHVybiAwOwogICAgfQogICAgcmV0dXJuIHJlZjsKfQoKc3RhdGljIFVMT05HIFdJTkFQSQpUaHVua19JRGlyZWN0M0RWZXJ0ZXhCdWZmZXJJbXBsXzFfUmVsZWFzZShJRGlyZWN0M0RWZXJ0ZXhCdWZmZXIgKmlmYWNlKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0RWZXJ0ZXhCdWZmZXJJbXBsLCBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXIsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPigpIHRodW5raW5nIHRvIElEaXJlY3QzRFZlcnRleEJ1ZmZlcjcgaW50ZXJmYWNlLlxuIiwgVGhpcyk7CgogICAgcmV0dXJuIElEaXJlY3QzRFZlcnRleEJ1ZmZlcjdfUmVsZWFzZShJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3KSk7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXIgTWV0aG9kcwogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSURpcmVjdDNEVmVydGV4QnVmZmVyNzo6TG9jawogKgogKiBMb2NrcyB0aGUgdmVydGV4IGJ1ZmZlciBhbmQgcmV0dXJucyBhIHBvaW50ZXIgdG8gdGhlIHZlcnRleCBkYXRhCiAqIExvY2tpbmcgdmVydGV4IGJ1ZmZlcnMgaXMgc2ltaWxhciB0byBsb2NraW5nIHN1cmZhY2VzLCBiZWNhdXNlIFdpbmRvd3MKICogdXNlcyBzdXJmYWNlcyB0byBzdG9yZSB2ZXJ0ZXggZGF0YSBpbnRlcm5hbGx5IChBY2NvcmRpbmcgdG8gdGhlIERYIHNkaykKICoKICogUGFyYW1zOgogKiAgRmxhZ3M6IExvY2tpbmcgZmxhZ3MuIFJlbGV2YW50IGhlcmUgYXJlIERETE9DS19SRUFET05MWSwgRERMT0NLX1dSSVRFT05MWSwKICogICAgICAgICBERExPQ0tfRElTQ0FSRENPTlRFTlRTIGFuZCBERExPQ0tfTk9PVkVSV1JJVEUuCiAqICBEYXRhOiAgUmV0dXJucyBhIHBvaW50ZXIgdG8gdGhlIHZlcnRleCBkYXRhCiAqICBTaXplOiAgUmV0dXJucyB0aGUgc2l6ZSBvZiB0aGUgYnVmZmVyIGlmIG5vdCBOVUxMCiAqCiAqIFJldHVybnM6CiAqICBEM0RfT0sgb24gc3VjY2VzcwogKiAgRERFUlJfSU5WQUxJRFBBUkFNUyBpZiBEYXRhIGlzIE5VTEwKICogIEQzREVSUl9WRVJURVhCVUZGRVJPUFRJTUlaRUQgaWYgY2FsbGVkIG9uIGFuIG9wdGltaXplZCBidWZmZXIoV2luZUQzRCkKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKSURpcmVjdDNEVmVydGV4QnVmZmVySW1wbF9Mb2NrKElEaXJlY3QzRFZlcnRleEJ1ZmZlcjcgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgRmxhZ3MsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2b2lkICoqRGF0YSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEICpTaXplKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0RWZXJ0ZXhCdWZmZXJJbXBsLCBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3LCBpZmFjZSk7CiAgICBXSU5FRDNEVkVSVEVYQlVGRkVSX0RFU0MgRGVzYzsKICAgIEhSRVNVTFQgaHI7CiAgICBUUkFDRSgiKCVwKS0+KCUwOGx4LCVwLCVwKVxuIiwgVGhpcywgRmxhZ3MsIERhdGEsIFNpemUpOwoKICAgIGlmKFNpemUpCiAgICB7CiAgICAgICAgLyogR2V0IHRoZSBzaXplLCBmb3IgcmV0dXJuaW5nIGl0LCBhbmQgZm9yIGxvY2tpbmcgKi8KICAgICAgICBociA9IElXaW5lRDNEVmVydGV4QnVmZmVyX0dldERlc2MoVGhpcy0+d2luZUQzRFZlcnRleEJ1ZmZlciwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJkRlc2MpOwogICAgICAgIGlmKGhyICE9IEQzRF9PSykKICAgICAgICB7CiAgICAgICAgICAgIEVSUigiKCVwKSBJV2luZUQzRFZlcnRleEJ1ZmZlcjo6R2V0RGVzYyBmYWlsZWQgd2l0aCBocj0lMDhseFxuIiwgVGhpcywgaHIpOwogICAgICAgICAgICByZXR1cm4gaHI7CiAgICAgICAgfQogICAgICAgICpTaXplID0gRGVzYy5TaXplOwogICAgfQoKICAgIHJldHVybiBJV2luZUQzRFZlcnRleEJ1ZmZlcl9Mb2NrKFRoaXMtPndpbmVEM0RWZXJ0ZXhCdWZmZXIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAwIC8qIE9mZnNldFRvTG9jayAqLywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIDAgLyogU2l6ZVRvTG9jaywgMCA9PSBGdWxsIGxvY2sgKi8sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAoQllURSAqKikgRGF0YSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEZsYWdzKTsKfQoKc3RhdGljIEhSRVNVTFQgV0lOQVBJClRodW5rX0lEaXJlY3QzRFZlcnRleEJ1ZmZlckltcGxfMV9Mb2NrKElEaXJlY3QzRFZlcnRleEJ1ZmZlciAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIEZsYWdzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2b2lkICoqRGF0YSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgKlNpemUpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRFZlcnRleEJ1ZmZlckltcGwsIElEaXJlY3QzRFZlcnRleEJ1ZmZlciwgaWZhY2UpOwogICAgVFJBQ0VfKGRkcmF3X3RodW5rKSgiKCVwKS0+KCUwOGx4LCVwLCVwKSB0aHVua2luZyB0byBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3IGludGVyZmFjZS5cbiIsIFRoaXMsIEZsYWdzLCBEYXRhLCBTaXplKTsKCiAgICByZXR1cm4gSURpcmVjdDNEVmVydGV4QnVmZmVyN19Mb2NrKElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRFZlcnRleEJ1ZmZlcjcpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBGbGFncywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRGF0YSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgU2l6ZSk7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3OjpVbmxvY2sKICoKICogVW5sb2NrcyBhIHZlcnRleCBCdWZmZXIKICoKICogUmV0dXJuczoKICogIEQzRF9PSyBvbiBzdWNjZXNzCiAqCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIEhSRVNVTFQgV0lOQVBJCklEaXJlY3QzRFZlcnRleEJ1ZmZlckltcGxfVW5sb2NrKElEaXJlY3QzRFZlcnRleEJ1ZmZlcjcgKmlmYWNlKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0RWZXJ0ZXhCdWZmZXJJbXBsLCBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3LCBpZmFjZSk7CiAgICBUUkFDRSgiKCVwKS0+KClcbiIsIFRoaXMpOwoKICAgIC8qIFRoaXMgaXMgZWFzeSA6KSAqLwogICAgcmV0dXJuIElXaW5lRDNEVmVydGV4QnVmZmVyX1VubG9jayhUaGlzLT53aW5lRDNEVmVydGV4QnVmZmVyKTsKfQoKc3RhdGljIEhSRVNVTFQgV0lOQVBJClRodW5rX0lEaXJlY3QzRFZlcnRleEJ1ZmZlckltcGxfMV9VbmxvY2soSURpcmVjdDNEVmVydGV4QnVmZmVyICppZmFjZSkKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNEVmVydGV4QnVmZmVySW1wbCwgSURpcmVjdDNEVmVydGV4QnVmZmVyLCBpZmFjZSk7CiAgICBUUkFDRV8oZGRyYXdfdGh1bmspKCIoJXApLT4oKSB0aHVua2luZyB0byBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3IGludGVyZmFjZS5cbiIsIFRoaXMpOwoKICAgIHJldHVybiBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3X1VubG9jayhJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3KSk7Cn0KCgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSURpcmVjdDNEVmVydGV4QnVmZmVyNzo6UHJvY2Vzc1ZlcnRpY2VzCiAqCiAqIFByb2Nlc3NlcyB1bnRyYW5zZm9ybWVkIFZlcnRpY2VzIGludG8gYSB0cmFuc2Zvcm1lZCBvciBvcHRpbWl6ZWQgdmVydGV4CiAqIGJ1ZmZlci4gSXQgY2FuIGFsc28gcGVyZm9ybSBvdGhlciBvcGVyYXRpb25zLCBzdWNoIGFzIGxpZ2h0aW5nIG9yIGNsaXBwaW5nCiAqCiAqIFBhcmFtcwogKiAgVmVydGV4T3A6IE9wZXJhdGlvbihzKSB0byBwZXJmb3JtOiBEM0RWT1BfQ0xJUCwgX0VYVEVOVFMsIF9MSUdIVCwgX1RSQU5TRk9STQogKiAgRGVzdEluZGV4OiBJbmRleCBpbiB0aGUgZGVzdGluYXRpb24gYnVmZmVyKFRoaXMpLCB3aGVyZSB0aGUgdmVydGljZXMgYXJlCiAqICAgICAgICAgICAgIHBsYWNlZAogKiAgQ291bnQ6IE51bWJlciBvZiBWZXJ0aWNlcyBpbiB0aGUgU291cmNlIGJ1ZmZlciB0byBwcm9jZXNzCiAqICBTcmNCdWZmZXI6IFNvdXJjZSB2ZXJ0ZXggYnVmZmVyCiAqICBTcmNJbmRleDogSW5kZXggb2YgdGhlIGZpcnN0IHZlcnRleCBpbiB0aGUgc3JjIGJ1ZmZlciB0byBwcm9jZXNzCiAqICBEM0REZXZpY2U6IERldmljZSB0byB1c2UgZm9yIHRyYW5zZm9ybWF0aW9uCiAqICBGbGFnczogMCBmb3IgZGVmYXVsdCwgRDNEUFZfRE9OT1RDT1BZREFUQSB0byBwcmV2ZW50IGNvcHlpbmcKICogICAgICAgICB1bmNoYW5lZCB2ZXJ0aWNlcwogKgogKiBSZXR1cm5zOgogKiAgRDNEX09LIG9uIHN1Y2Nlc3MKICogIERERVJSX0lOVkFMSURQQVJBTVMgSWYgRDNEVk9QX1RSQU5TRk9STSB3YXNuJ3QgcGFzc2VkCiAqCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIEhSRVNVTFQgV0lOQVBJCklEaXJlY3QzRFZlcnRleEJ1ZmZlckltcGxfUHJvY2Vzc1ZlcnRpY2VzKElEaXJlY3QzRFZlcnRleEJ1ZmZlcjcgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBWZXJ0ZXhPcCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgRGVzdEluZGV4LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBDb3VudCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgSURpcmVjdDNEVmVydGV4QnVmZmVyNyAqU3JjQnVmZmVyLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBTcmNJbmRleCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgSURpcmVjdDNERGV2aWNlNyAqRDNERGV2aWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBGbGFncykKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNEVmVydGV4QnVmZmVySW1wbCwgSURpcmVjdDNEVmVydGV4QnVmZmVyNywgaWZhY2UpOwogICAgSURpcmVjdDNEVmVydGV4QnVmZmVySW1wbCAqU3JjID0gSUNPTV9PQkpFQ1QoSURpcmVjdDNEVmVydGV4QnVmZmVySW1wbCwgSURpcmVjdDNEVmVydGV4QnVmZmVyNywgU3JjQnVmZmVyKTsKICAgIElEaXJlY3QzRERldmljZUltcGwgKkQzRCA9IElDT01fT0JKRUNUKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTcsIEQzRERldmljZSk7CiAgICBCT09MIG9sZENsaXAsIGRvQ2xpcDsKICAgIEhSRVNVTFQgaHI7CgogICAgVFJBQ0UoIiglcCktPiglMDhseCwlbGQsJWxkLCVwLCVsZCwlcCwlMDhseClcbiIsIFRoaXMsIFZlcnRleE9wLCBEZXN0SW5kZXgsIENvdW50LCBTcmMsIFNyY0luZGV4LCBEM0QsIEZsYWdzKTsKCiAgICAvKiBWZXJ0ZXggb3BlcmF0aW9uczoKICAgICAqIEQzRFZPUF9DTElQOiBDbGlwcyB2ZXJ0aWNlcyBvdXRzaWRlIHRoZSB2aWV3aW5nIGZydXN0cnVtLiBOZWVkcyBjbGlwcGluZyBpbmZvcm1hdGlvbgogICAgICogaW4gdGhlIHZlcnRleCBidWZmZXIgKEJ1ZmZlciBtYXkgbm90IGJlIGNyZWF0ZWQgd2l0aCBEM0RWQkNBUFNfRE9OT1RDTElQKQogICAgICogRDNEVk9QX0VYVEVOVFM6IENhdXNlcyB0aGUgc2NyZWVuIGV4dGVudHMgdG8gYmUgdXBkYXRlZCB3aGVuIHJlbmRlcmluZyB0aGUgdmVydGljZXMKICAgICAqIEQzRFZPUF9MSUdIVDogTGlnaHRzIHRoZSB2ZXJ0aWNlcwogICAgICogRDNEVk9QX1RSQU5TRk9STTogVHJhbnNmb3JtIHRoZSB2ZXJ0aWNlcy4gVGhpcyBmbGFnIGlzIG5lY2Vzc2FyeQogICAgICoKICAgICAqIFdpbmVEM0Qgb25seSB0cmFuc2Zvcm1zIGFuZCBjbGlwcyB0aGUgdmVydGljZXMgYnkgbm93LCBzbyBFWFRFTlRTIGFuZCBMSUdIVAogICAgICogYXJlIG5vdCBpbXBsZW1lbnRlZC4gQ2xpcHBpbmcgaXMgZGlzYWJsZWQgQVRNLCBiZWNhdXNlIG9mIHVuc3VyZSBjb25kaXRpb25zLgogICAgICovCiAgICBpZiggIShWZXJ0ZXhPcCAmIEQzRFZPUF9UUkFOU0ZPUk0pICkgcmV0dXJuIERERVJSX0lOVkFMSURQQVJBTVM7CgogICAgLyogV2luZUQzRCBkb2Vzbid0IGtub3cgZDNkNyB2ZXJ0ZXggb3BlcmF0aW9uLCBpdCB1c2VzCiAgICAgKiByZW5kZXIgc3RhdGVzIGluc3RlYWQuIFNldCB0aGUgcmVuZGVyIHN0YXRlcyBhY2NvcmRpbmcgdG8KICAgICAqIHRoZSB2ZXJ0ZXggb3BzCiAgICAgKi8KICAgIGRvQ2xpcCA9IFZlcnRleE9wICYgRDNEVk9QX0NMSVAgPyBUUlVFIDogRkFMU0U7CiAgICBJV2luZUQzRERldmljZV9HZXRSZW5kZXJTdGF0ZShEM0QtPndpbmVEM0REZXZpY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBXSU5FRDNEUlNfQ0xJUFBJTkcsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAoRFdPUkQgKikgJm9sZENsaXApOwogICAgaWYoZG9DbGlwICE9IG9sZENsaXApCiAgICB7CiAgICAgICAgSVdpbmVEM0REZXZpY2VfU2V0UmVuZGVyU3RhdGUoRDNELT53aW5lRDNERGV2aWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFdJTkVEM0RSU19DTElQUElORywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBkb0NsaXApOwogICAgfQoKCiAgICBociA9IElXaW5lRDNERGV2aWNlX1Byb2Nlc3NWZXJ0aWNlcyhEM0QtPndpbmVEM0REZXZpY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBTcmNJbmRleCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERlc3RJbmRleCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIENvdW50LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgVGhpcy0+d2luZUQzRFZlcnRleEJ1ZmZlciwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFNyYy0+d2luZUQzRFZlcnRleEJ1ZmZlciwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEZsYWdzKTsKCiAgICAvKiBSZXN0b3JlIHRoZSBzdGF0ZXMgaWYgbmVlZGVkICovCiAgICBpZihkb0NsaXAgIT0gb2xkQ2xpcCkKICAgICAgICBJV2luZUQzRERldmljZV9TZXRSZW5kZXJTdGF0ZShEM0QtPndpbmVEM0REZXZpY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgV0lORUQzRFJTX0NMSVBQSU5HLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIG9sZENsaXApOwogICAgcmV0dXJuIGhyOwp9CgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNEVmVydGV4QnVmZmVySW1wbF8xX1Byb2Nlc3NWZXJ0aWNlcyhJRGlyZWN0M0RWZXJ0ZXhCdWZmZXIgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIFZlcnRleE9wLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIERlc3RJbmRleCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBDb3VudCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXIgKlNyY0J1ZmZlciwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBTcmNJbmRleCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBJRGlyZWN0M0REZXZpY2UzICpEM0REZXZpY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgRmxhZ3MpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRFZlcnRleEJ1ZmZlckltcGwsIElEaXJlY3QzRFZlcnRleEJ1ZmZlciwgaWZhY2UpOwogICAgSURpcmVjdDNEVmVydGV4QnVmZmVySW1wbCAqU3JjID0gSUNPTV9PQkpFQ1QoSURpcmVjdDNEVmVydGV4QnVmZmVySW1wbCwgSURpcmVjdDNEVmVydGV4QnVmZmVyLCBTcmNCdWZmZXIpOwogICAgSURpcmVjdDNERGV2aWNlSW1wbCAqRDNEID0gSUNPTV9PQkpFQ1QoSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlMywgRDNERGV2aWNlKTsKCiAgICBUUkFDRV8oZGRyYXdfdGh1bmspKCIoJXApLT4oJTA4bHgsJTA4bHgsJTA4bHgsJXAsJTA4bHgsJXAsJTA4bHgpIHRodW5raW5nIHRvIElEaXJlY3QzRFZlcnRleEJ1ZmZlcjcgaW50ZXJmYWNlLlxuIiwgVGhpcywgVmVydGV4T3AsIERlc3RJbmRleCwgQ291bnQsIFNyYywgU3JjSW5kZXgsIEQzRCwgRmxhZ3MpOwoKICAgIHJldHVybiBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3X1Byb2Nlc3NWZXJ0aWNlcyhJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3KSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBWZXJ0ZXhPcCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEZXN0SW5kZXgsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgQ291bnQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgSUNPTV9JTlRFUkZBQ0UoU3JjLCBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3KSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBTcmNJbmRleCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBJQ09NX0lOVEVSRkFDRShEM0QsIElEaXJlY3QzRERldmljZTcpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEZsYWdzKTsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRFZlcnRleEJ1ZmZlcjc6OkdldFZlcnRleEJ1ZmZlckRlc2MKICoKICogUmV0dXJucyB0aGUgZGVzY3JpcHRpb24gb2YgYSB2ZXJ0ZXggYnVmZmVyCiAqCiAqIFBhcmFtczoKICogIERlc2M6IEFkZHJlc3MgdG8gd3JpdGUgdGhlIGRlc2NyaXB0aW9uIHRvCiAqCiAqIFJldHVybnMKICogIERERVJSX0lOVkFMSURQQVJBTVMgaWYgRGVzYyBpcyBOVUxMCiAqICBEM0RfT0sgb24gc3VjY2VzcwogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0RWZXJ0ZXhCdWZmZXJJbXBsX0dldFZlcnRleEJ1ZmZlckRlc2MoSURpcmVjdDNEVmVydGV4QnVmZmVyNyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RWRVJURVhCVUZGRVJERVNDICpEZXNjKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0RWZXJ0ZXhCdWZmZXJJbXBsLCBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3LCBpZmFjZSk7CiAgICBXSU5FRDNEVkVSVEVYQlVGRkVSX0RFU0MgV0Rlc2M7CiAgICBIUkVTVUxUIGhyOwogICAgRFdPUkQgc2l6ZTsKICAgIFRSQUNFKCIoJXApLT4oJXApXG4iLCBUaGlzLCBEZXNjKTsKCiAgICBpZighRGVzYykgcmV0dXJuIERERVJSX0lOVkFMSURQQVJBTVM7CgogICAgaHIgPSBJV2luZUQzRFZlcnRleEJ1ZmZlcl9HZXREZXNjKFRoaXMtPndpbmVEM0RWZXJ0ZXhCdWZmZXIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJldEZXNjKTsKICAgIGlmKGhyICE9IEQzRF9PSykKICAgIHsKICAgICAgICBFUlIoIiglcCkgSVdpbmVEM0RWZXJ0ZXhCdWZmZXI6OkdldERlc2MgZmFpbGVkIHdpdGggaHI9JTA4bHhcbiIsIFRoaXMsIGhyKTsKICAgICAgICByZXR1cm4gaHI7CiAgICB9CgogICAgLyogQ2xlYXIgdGhlIHJldHVybiB2YWx1ZSBvZiBnYXJiYWdlICovCiAgICBzaXplID0gRGVzYy0+ZHdTaXplOwogICAgbWVtc2V0KERlc2MsIDAsIHNpemUpOwoKICAgIC8qIE5vdyBmaWxsIHRoZSBEZXNjIHN0cnVjdHVyZSAqLwogICAgRGVzYy0+ZHdTaXplID0gc2l6ZTsKICAgIERlc2MtPmR3Q2FwcyA9IFRoaXMtPkNhcHM7CiAgICBEZXNjLT5kd0ZWRiA9IFdEZXNjLkZWRjsKICAgIERlc2MtPmR3TnVtVmVydGljZXMgPSBXRGVzYy5TaXplIC8gZ2V0X2ZsZXhpYmxlX3ZlcnRleF9zaXplKFdEZXNjLkZWRik7CgogICAgcmV0dXJuIEQzRF9PSzsKfQoKc3RhdGljIEhSRVNVTFQgV0lOQVBJClRodW5rX0lEaXJlY3QzRFZlcnRleEJ1ZmZlckltcGxfMV9HZXRWZXJ0ZXhCdWZmZXJEZXNjKElEaXJlY3QzRFZlcnRleEJ1ZmZlciAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRFZFUlRFWEJVRkZFUkRFU0MgKkRlc2MpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRFZlcnRleEJ1ZmZlckltcGwsIElEaXJlY3QzRFZlcnRleEJ1ZmZlciwgaWZhY2UpOwogICAgVFJBQ0VfKGRkcmF3X3RodW5rKSgiKCVwKS0+KCVwKSB0aHVua2luZyB0byBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3IGludGVyZmFjZS5cbiIsIFRoaXMsIERlc2MpOwoKICAgIHJldHVybiBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3X0dldFZlcnRleEJ1ZmZlckRlc2MoSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNEVmVydGV4QnVmZmVyNyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERlc2MpOwp9CgoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRFZlcnRleEJ1ZmZlcjc6Ok9wdGltaXplCiAqCiAqIENvbnZlcnRzIGFuIHVub3B0aW1pemVkIHZlcnRleCBidWZmZXIgaW50byBhbiBvcHRpbWl6ZWQgYnVmZmVyCiAqCiAqIFBhcmFtczoKICogIEQzRERldmljZTogRGV2aWNlIGZvciB3aGljaCB0aGlzIGJ1ZmZlciBpcyBvcHRpbWl6ZWQKICogIEZsYWdzOiBOb3QgdXNlZCwgc2hvdWxkIGJlIHNldCB0byAwCiAqCiAqIFJldHVybnMKICogIEQzRF9PSywgYmVjYXVzZSBpdCdzIGEgc3R1YgogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0RWZXJ0ZXhCdWZmZXJJbXBsX09wdGltaXplKElEaXJlY3QzRFZlcnRleEJ1ZmZlcjcgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElEaXJlY3QzRERldmljZTcgKkQzRERldmljZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBGbGFncykKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNEVmVydGV4QnVmZmVySW1wbCwgSURpcmVjdDNEVmVydGV4QnVmZmVyNywgaWZhY2UpOwogICAgSURpcmVjdDNERGV2aWNlSW1wbCAqRDNEID0gSUNPTV9PQkpFQ1QoSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlNywgRDNERGV2aWNlKTsKICAgIEZJWE1FKCIoJXApLT4oJXAsJTA4bHgpOiBzdHViIVxuIiwgVGhpcywgRDNELCBGbGFncyk7CgogICAgLyogV2UgY291bGQgZm9yd2FyZCB0aGlzIGNhbGwgdG8gV2luZUQzRCBhbmQgdGFrZSBhZHZhbnRhZ2UKICAgICAqIG9mIGl0IG9uY2Ugd2UgdXNlIE9wZW5HTCB2ZXJ0ZXggYnVmZmVycwogICAgICovCiAgICBUaGlzLT5DYXBzIHw9IEQzRFZCQ0FQU19PUFRJTUlaRUQ7CgogICAgcmV0dXJuIEREX09LOwp9CgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNEVmVydGV4QnVmZmVySW1wbF8xX09wdGltaXplKElEaXJlY3QzRFZlcnRleEJ1ZmZlciAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBJRGlyZWN0M0REZXZpY2UzICpEM0REZXZpY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBGbGFncykKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNEVmVydGV4QnVmZmVySW1wbCwgSURpcmVjdDNEVmVydGV4QnVmZmVyLCBpZmFjZSk7CiAgICBJRGlyZWN0M0REZXZpY2VJbXBsICpEM0QgPSBJQ09NX09CSkVDVChJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UzLCBEM0REZXZpY2UpOwogICAgVFJBQ0VfKGRkcmF3X3RodW5rKSgiKCVwKS0+KCVwLCUwOGx4KSB0aHVua2luZyB0byBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3IGludGVyZmFjZS5cbiIsIFRoaXMsIEQzRCwgRmxhZ3MpOwoKICAgIHJldHVybiBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3X09wdGltaXplKElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRFZlcnRleEJ1ZmZlcjcpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgSUNPTV9JTlRFUkZBQ0UoRDNELCBJRGlyZWN0M0REZXZpY2U3KSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEZsYWdzKTsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRFZlcnRleEJ1ZmZlcjc6OlByb2Nlc3NWZXJ0aWNlc1N0cmlkZWQKICoKICogVGhpcyBtZXRob2QgcHJvY2Vzc2VzIHVudHJhbnNmb3JtZWQgc3RyaWRlZCB2ZXJ0aWNlcyBpbnRvIGEgcHJvY2Vzc2VkCiAqIG9yIG9wdGltaXplZCB2ZXJ0ZXggYnVmZmVyLgogKgogKiBGb3IgbW9yZSBkZXRhaWxzIG9uIHRoZSBwYXJhbWV0ZXJzLCBzZWUKICogSURpcmVjdDNEVmVydGV4QnVmZmVyNzo6UHJvY2Vzc1ZlcnRpY2VzCiAqCiAqIFBhcmFtczoKICogIFZlcnRleE9wOiBPcGVyYXRpb25zIHRvIHBlcmZvcm0KICogIERlc3RJbmRleDogRGVzdGluYXRpb24gaW5kZXggdG8gd3JpdGUgdGhlIHZlcnRpY2VzIHRvCiAqICBDb3VudDogTnVtYmVyIG9mIGlucHV0IHZlcnRpY2VzCiAqICBTdHJpZGVEYXRhOiBBcnJheSBjb250YWluaW5nIHRoZSBpbnB1dCB2ZXJ0aWNlcwogKiAgVmVydGV4VHlwZURlc2M6IFZlcnRleCBEZXNjcmlwdGlvbiBvciBzb3VyY2UgaW5kZXg/Pz8/Pz8/Pz8KICogIEQzRERldmljZTogSURpcmVjdDNERGV2aWNlNyB0byB1c2UgZm9yIHByb2Nlc3NpbmcKICogIEZsYWdzOiBDYW4gYmUgRDNEUFZfRE9OT1RDT1BZREFUQSB0byBhdm9pZCBjb3B5aW5nIHVubW9kaWZpZWQgdmVydGljZXMKICoKICogUmV0dXJucwogKiAgRDNEX09LIG9uIHN1Y2Nlc3MsIG9yIERERVJSXyoKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKSURpcmVjdDNEVmVydGV4QnVmZmVySW1wbF9Qcm9jZXNzVmVydGljZXNTdHJpZGVkKElEaXJlY3QzRFZlcnRleEJ1ZmZlcjcgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgVmVydGV4T3AsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBEZXN0SW5kZXgsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBDb3VudCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRERSQVdQUklNSVRJVkVTVFJJREVEREFUQSAqU3RyaWRlRGF0YSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIFZlcnRleFR5cGVEZXNjLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgSURpcmVjdDNERGV2aWNlNyAqRDNERGV2aWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgRmxhZ3MpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRFZlcnRleEJ1ZmZlckltcGwsIElEaXJlY3QzRFZlcnRleEJ1ZmZlcjcsIGlmYWNlKTsKICAgIElEaXJlY3QzRERldmljZUltcGwgKkQzRCA9IElDT01fT0JKRUNUKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTcsIEQzRERldmljZSk7CiAgICBGSVhNRSgiKCVwKS0+KCUwOGx4LCUwOGx4LCUwOGx4LCVwLCUwOGx4LCVwLCUwOGx4KTogc3R1YiFcbiIsIFRoaXMsIFZlcnRleE9wLCBEZXN0SW5kZXgsIENvdW50LCBTdHJpZGVEYXRhLCBWZXJ0ZXhUeXBlRGVzYywgRDNELCBGbGFncyk7CiAgICByZXR1cm4gRERfT0s7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBUaGUgVlRhYmxlcwogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCgpjb25zdCBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3VnRibCBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3X1Z0YmwgPQp7CiAgICAvKioqIElVbmtub3duIE1ldGhvZHMgKioqLwogICAgSURpcmVjdDNEVmVydGV4QnVmZmVySW1wbF9RdWVyeUludGVyZmFjZSwKICAgIElEaXJlY3QzRFZlcnRleEJ1ZmZlckltcGxfQWRkUmVmLAogICAgSURpcmVjdDNEVmVydGV4QnVmZmVySW1wbF9SZWxlYXNlLAogICAgLyoqKiBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXIgTWV0aG9kcyAqKiovCiAgICBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXJJbXBsX0xvY2ssCiAgICBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXJJbXBsX1VubG9jaywKICAgIElEaXJlY3QzRFZlcnRleEJ1ZmZlckltcGxfUHJvY2Vzc1ZlcnRpY2VzLAogICAgSURpcmVjdDNEVmVydGV4QnVmZmVySW1wbF9HZXRWZXJ0ZXhCdWZmZXJEZXNjLAogICAgSURpcmVjdDNEVmVydGV4QnVmZmVySW1wbF9PcHRpbWl6ZSwKICAgIC8qKiogSURpcmVjdDNEVmVydGV4QnVmZmVyNyBNZXRob2RzICoqKi8KICAgIElEaXJlY3QzRFZlcnRleEJ1ZmZlckltcGxfUHJvY2Vzc1ZlcnRpY2VzU3RyaWRlZAp9OwoKY29uc3QgSURpcmVjdDNEVmVydGV4QnVmZmVyVnRibCBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXIxX1Z0YmwgPQp7CiAgICAvKioqIElVbmtub3duIE1ldGhvZHMgKioqLwogICAgVGh1bmtfSURpcmVjdDNEVmVydGV4QnVmZmVySW1wbF8xX1F1ZXJ5SW50ZXJmYWNlLAogICAgVGh1bmtfSURpcmVjdDNEVmVydGV4QnVmZmVySW1wbF8xX0FkZFJlZiwKICAgIFRodW5rX0lEaXJlY3QzRFZlcnRleEJ1ZmZlckltcGxfMV9SZWxlYXNlLAogICAgLyoqKiBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXIgTWV0aG9kcyAqKiovCiAgICBUaHVua19JRGlyZWN0M0RWZXJ0ZXhCdWZmZXJJbXBsXzFfTG9jaywKICAgIFRodW5rX0lEaXJlY3QzRFZlcnRleEJ1ZmZlckltcGxfMV9VbmxvY2ssCiAgICBUaHVua19JRGlyZWN0M0RWZXJ0ZXhCdWZmZXJJbXBsXzFfUHJvY2Vzc1ZlcnRpY2VzLAogICAgVGh1bmtfSURpcmVjdDNEVmVydGV4QnVmZmVySW1wbF8xX0dldFZlcnRleEJ1ZmZlckRlc2MsCiAgICBUaHVua19JRGlyZWN0M0RWZXJ0ZXhCdWZmZXJJbXBsXzFfT3B0aW1pemUKfTsK