LyoKICogQ29weXJpZ2h0IChjKSAxOTk4LTIwMDQgTGlvbmVsIFVsbWVyCiAqIENvcHlyaWdodCAoYykgMjAwMi0yMDA1IENocmlzdGlhbiBDb3N0YQogKiBDb3B5cmlnaHQgKGMpIDIwMDYgU3RlZmFuIET2c2luZ2VyCiAqCiAqIFRoaXMgbGlicmFyeSBpcyBmcmVlIHNvZnR3YXJlOyB5b3UgY2FuIHJlZGlzdHJpYnV0ZSBpdCBhbmQvb3IKICogbW9kaWZ5IGl0IHVuZGVyIHRoZSB0ZXJtcyBvZiB0aGUgR05VIExlc3NlciBHZW5lcmFsIFB1YmxpYwogKiBMaWNlbnNlIGFzIHB1Ymxpc2hlZCBieSB0aGUgRnJlZSBTb2Z0d2FyZSBGb3VuZGF0aW9uOyBlaXRoZXIKICogdmVyc2lvbiAyLjEgb2YgdGhlIExpY2Vuc2UsIG9yIChhdCB5b3VyIG9wdGlvbikgYW55IGxhdGVyIHZlcnNpb24uCiAqCiAqIFRoaXMgbGlicmFyeSBpcyBkaXN0cmlidXRlZCBpbiB0aGUgaG9wZSB0aGF0IGl0IHdpbGwgYmUgdXNlZnVsLAogKiBidXQgV0lUSE9VVCBBTlkgV0FSUkFOVFk7IHdpdGhvdXQgZXZlbiB0aGUgaW1wbGllZCB3YXJyYW50eSBvZgogKiBNRVJDSEFOVEFCSUxJVFkgb3IgRklUTkVTUyBGT1IgQSBQQVJUSUNVTEFSIFBVUlBPU0UuICBTZWUgdGhlIEdOVQogKiBMZXNzZXIgR2VuZXJhbCBQdWJsaWMgTGljZW5zZSBmb3IgbW9yZSBkZXRhaWxzLgogKgogKiBZb3Ugc2hvdWxkIGhhdmUgcmVjZWl2ZWQgYSBjb3B5IG9mIHRoZSBHTlUgTGVzc2VyIEdlbmVyYWwgUHVibGljCiAqIExpY2Vuc2UgYWxvbmcgd2l0aCB0aGlzIGxpYnJhcnk7IGlmIG5vdCwgd3JpdGUgdG8gdGhlIEZyZWUgU29mdHdhcmUKICogRm91bmRhdGlvbiwgSW5jLiwgNTEgRnJhbmtsaW4gU3QsIEZpZnRoIEZsb29yLCBCb3N0b24sIE1BIDAyMTEwLTEzMDEsIFVTQQogKgogKiBJRGlyZWN0M0REZXZpY2UgaW1wbGVtZW50YXRpb24sIHZlcnNpb24gMSwgMiwgMyBhbmQgNy4gUmVuZGVyaW5nIGlzIHJlbGF5ZWQKICogdG8gV2luZUQzRCwgc29tZSBtaW5pbWFsIERpcmVjdERyYXcgc3BlY2lmaWMgbWFuYWdlbWVudCBpcyBoYW5kbGVkIGhlcmUuCiAqIFRoZSBEaXJlY3QzRERldmljZSBpcyBOT1QgdGhlIHBhcmVudCBvZiB0aGUgV2luZUQzRERldmljZSwgYmVjYXVzZSBkM2QKICogaXMgaW5pdGlhbGl6ZWQgd2hlbiBEaXJlY3REcmF3IGNyZWF0ZXMgdGhlIHByaW1hcnkgc3VyZmFjZS4KICogU29tZSB0eXBlIG1hbmFnZW1lbnQgaXMgbmVjZXNzYXJ5LCBiZWNhdXNlIHNvbWUgRDNEIHR5cGVzIGNoYW5nZWQgYmV0d2VlbgogKiBEM0Q3IGFuZCBEM0Q5LgogKgogKi8KCiNpbmNsdWRlICJjb25maWcuaCIKI2luY2x1ZGUgIndpbmUvcG9ydC5oIgojaW5jbHVkZSAid2luZS9kZWJ1Zy5oIgoKI2luY2x1ZGUgPGFzc2VydC5oPgojaW5jbHVkZSA8c3RkYXJnLmg+CiNpbmNsdWRlIDxzdHJpbmcuaD4KI2luY2x1ZGUgPHN0ZGxpYi5oPgoKI2RlZmluZSBDT0JKTUFDUk9TCgojaW5jbHVkZSAid2luZGVmLmgiCiNpbmNsdWRlICJ3aW5iYXNlLmgiCiNpbmNsdWRlICJ3aW5ubHMuaCIKI2luY2x1ZGUgIndpbmVycm9yLmgiCiNpbmNsdWRlICJ3aW5nZGkuaCIKI2luY2x1ZGUgIndpbmUvZXhjZXB0aW9uLmgiCiNpbmNsdWRlICJleGNwdC5oIgoKI2luY2x1ZGUgImRkcmF3LmgiCiNpbmNsdWRlICJkM2QuaCIKCiNpbmNsdWRlICJkZHJhd19wcml2YXRlLmgiCgpXSU5FX0RFRkFVTFRfREVCVUdfQ0hBTk5FTChkM2Q3KTsKV0lORV9ERUNMQVJFX0RFQlVHX0NIQU5ORUwoZGRyYXdfdGh1bmspOwoKLyogVGhlIGRldmljZSBJRCAqLwpjb25zdCBHVUlEIElJRF9EM0RERVZJQ0VfV2luZUQzRCA9IHsKICAweGFlZjcyZDQzLAogIDB4YjA5YSwKICAweDRiN2IsCiAgeyAweGI3LDB4OTgsMHhjNiwweDhhLDB4NzcsMHgyZCwweDcyLDB4MmEgfQp9OwoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElVbmtub3duIE1ldGhvZHMuIENvbW1vbiBmb3IgVmVyc2lvbiAxLCAyLCAzIGFuZCA3IAogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSURpcmVjdDNERGV2aWNlNzo6UXVlcnlJbnRlcmZhY2UKICoKICogVXNlZCB0byBxdWVyeSBvdGhlciBpbnRlcmZhY2VzIGZyb20gYSBEaXJlY3QzRERldmljZSBpbnRlcmZhY2UuCiAqIEl0IGNhbiByZXR1cm4gaW50ZXJmYWNlIHBvaW50ZXJzIHRvIGFsbCBEaXJlY3QzRERldmljZSB2ZXJzaW9ucyBhcyB3ZWxsCiAqIGFzIElEaXJlY3REcmF3IGFuZCBJRGlyZWN0M0QuIEZvciBhIGxpbmsgdG8gUXVlcnlJbnRlcmZhY2UKICogcnVsZXMgc2VlIGRkcmF3LmMsIElEaXJlY3REcmF3Nzo6UXVlcnlJbnRlcmZhY2UKICoKICogRXhpc3RzIGluIFZlcnNpb24gMSwgMiwgMyBhbmQgNwogKgogKiBQYXJhbXM6CiAqICByZWZpaWQ6IEludGVyZmFjZSBJRCBxdWVyaWVkIGZvcgogKiAgb2JqOiBVc2VkIHRvIHJldHVybiB0aGUgaW50ZXJmYWNlIHBvaW50ZXIKICoKICogUmV0dXJuczoKICogIEQzRF9PSyBvciBFX05PSU5URVJGQUNFCiAqCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIEhSRVNVTFQgV0lOQVBJCklEaXJlY3QzRERldmljZUltcGxfN19RdWVyeUludGVyZmFjZShJRGlyZWN0M0REZXZpY2U3ICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFJFRklJRCByZWZpaWQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2b2lkICoqb2JqKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2U3LCBpZmFjZSk7CiAgICBUUkFDRSgiKCVwKS0+KCVzLCVwKVxuIiwgVGhpcywgZGVidWdzdHJfZ3VpZChyZWZpaWQpLCBvYmopOwoKICAgIC8qIEFjY29yZGluZyB0byBDT00gZG9jcywgaWYgdGhlIFF1ZXJ5SW50ZXJmYWNlIGZhaWxzLCBvYmogc2hvdWxkIGJlIHNldCB0byBOVUxMICovCiAgICAqb2JqID0gTlVMTDsKCiAgICBpZighcmVmaWlkKQogICAgICAgIHJldHVybiBEREVSUl9JTlZBTElEUEFSQU1TOwoKICAgIGlmICggSXNFcXVhbEdVSUQoICZJSURfSVVua25vd24sIHJlZmlpZCApICkKICAgIHsKICAgICAgICAqb2JqID0gSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlNyk7CiAgICB9CgogICAgLyogQ2hlY2sgRGlyZWN0RHJhdyBJbnRlcmZhYwFzICovCiAgICBlbHNlIGlmKCBJc0VxdWFsR1VJRCggJklJRF9JRGlyZWN0RHJhdzcsIHJlZmlpZCApICkKICAgIHsKICAgICAgICAqb2JqID0gSUNPTV9JTlRFUkZBQ0UoVGhpcy0+ZGRyYXcsIElEaXJlY3REcmF3Nyk7CiAgICAgICAgVFJBQ0UoIiglcCkgUmV0dXJuaW5nIElEaXJlY3REcmF3NyBpbnRlcmZhY2UgYXQgJXBcbiIsIFRoaXMsICpvYmopOwogICAgfQogICAgZWxzZSBpZiAoIElzRXF1YWxHVUlEKCAmSUlEX0lEaXJlY3REcmF3NCwgcmVmaWlkICkgKQogICAgewogICAgICAgICpvYmogPSBJQ09NX0lOVEVSRkFDRShUaGlzLT5kZHJhdywgSURpcmVjdERyYXc0KTsKICAgICAgICBUUkFDRSgiKCVwKSBSZXR1cm5pbmcgSURpcmVjdERyYXc0IGludGVyZmFjZSBhdCAlcFxuIiwgVGhpcywgKm9iaik7CiAgICB9CiAgICBlbHNlIGlmICggSXNFcXVhbEdVSUQoICZJSURfSURpcmVjdERyYXcyLCByZWZpaWQgKSApCiAgICB7CiAgICAgICAgKm9iaiA9IElDT01fSU5URVJGQUNFKFRoaXMtPmRkcmF3LCBJRGlyZWN0RHJhdzIpOwogICAgICAgIFRSQUNFKCIoJXApIFJldHVybmluZyBJRGlyZWN0RHJhdzIgaW50ZXJmYWNlIGF0ICVwXG4iLCBUaGlzLCAqb2JqKTsKICAgIH0KICAgIGVsc2UgaWYoIElzRXF1YWxHVUlEKCAmSUlEX0lEaXJlY3REcmF3LCByZWZpaWQgKSApCiAgICB7CiAgICAgICAgKm9iaiA9IElDT01fSU5URVJGQUNFKFRoaXMtPmRkcmF3LCBJRGlyZWN0RHJhdyk7CiAgICAgICAgVFJBQ0UoIiglcCkgUmV0dXJuaW5nIElEaXJlY3REcmF3IGludGVyZmFjZSBhdCAlcFxuIiwgVGhpcywgKm9iaik7CiAgICB9CgogICAgLyogRGlyZWN0M0QgKi8KICAgIGVsc2UgaWYgKCBJc0VxdWFsR1VJRCggJklJRF9JRGlyZWN0M0QgICwgcmVmaWlkICkgKQogICAgewogICAgICAgICpvYmogPSBJQ09NX0lOVEVSRkFDRShUaGlzLT5kZHJhdywgSURpcmVjdDNEKTsKICAgICAgICBUUkFDRSgiKCVwKSBSZXR1cm5pbmcgSURpcmVjdDNEIGludGVyZmFjZSBhdCAlcFxuIiwgVGhpcywgKm9iaik7CiAgICB9CiAgICBlbHNlIGlmICggSXNFcXVhbEdVSUQoICZJSURfSURpcmVjdDNEMiAsIHJlZmlpZCApICkKICAgIHsKICAgICAgICAqb2JqID0gSUNPTV9JTlRFUkZBQ0UoVGhpcy0+ZGRyYXcsIElEaXJlY3QzRDIpOwogICAgICAgIFRSQUNFKCIoJXApIFJldHVybmluZyBJRGlyZWN0M0QyIGludGVyZmFjZSBhdCAlcFxuIiwgVGhpcywgKm9iaik7CiAgICB9CiAgICBlbHNlIGlmICggSXNFcXVhbEdVSUQoICZJSURfSURpcmVjdDNEMyAsIHJlZmlpZCApICkKICAgIHsKICAgICAgICAqb2JqID0gSUNPTV9JTlRFUkZBQ0UoVGhpcy0+ZGRyYXcsIElEaXJlY3QzRDMpOwogICAgICAgIFRSQUNFKCIoJXApIFJldHVybmluZyBJRGlyZWN0M0QzIGludGVyZmFjZSBhdCAlcFxuIiwgVGhpcywgKm9iaik7CiAgICB9CiAgICBlbHNlIGlmICggSXNFcXVhbEdVSUQoICZJSURfSURpcmVjdDNENyAsIHJlZmlpZCApICkKICAgIHsKICAgICAgICAqb2JqID0gSUNPTV9JTlRFUkZBQ0UoVGhpcy0+ZGRyYXcsIElEaXJlY3QzRDcpOwogICAgICAgIFRSQUNFKCIoJXApIFJldHVybmluZyBJRGlyZWN0M0Q3IGludGVyZmFjZSBhdCAlcFxuIiwgVGhpcywgKm9iaik7CiAgICB9CgogICAgLyogRGlyZWN0M0REZXZpY2UgKi8KICAgIGVsc2UgaWYgKCBJc0VxdWFsR1VJRCggJklJRF9JRGlyZWN0M0REZXZpY2UgICwgcmVmaWlkICkgKQogICAgewogICAgICAgICpvYmogPSBJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0REZXZpY2UpOwogICAgICAgIFRSQUNFKCIoJXApIFJldHVybmluZyBJRGlyZWN0M0REZXZpY2UgaW50ZXJmYWNlIGF0ICVwXG4iLCBUaGlzLCAqb2JqKTsKICAgIH0KICAgIGVsc2UgaWYgKCBJc0VxdWFsR1VJRCggJklJRF9JRGlyZWN0M0REZXZpY2UyICAsIHJlZmlpZCApICkgewogICAgICAgICpvYmogPSBJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0REZXZpY2UyKTsKICAgICAgICBUUkFDRSgiKCVwKSBSZXR1cm5pbmcgSURpcmVjdDNERGV2aWNlMiBpbnRlcmZhY2UgYXQgJXBcbiIsIFRoaXMsICpvYmopOwogICAgfQogICAgZWxzZSBpZiAoIElzRXF1YWxHVUlEKCAmSUlEX0lEaXJlY3QzRERldmljZTMgICwgcmVmaWlkICkgKSB7CiAgICAgICAgKm9iaiA9IElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTMpOwogICAgICAgIFRSQUNFKCIoJXApIFJldHVybmluZyBJRGlyZWN0M0REZXZpY2UzIGludGVyZmFjZSBhdCAlcFxuIiwgVGhpcywgKm9iaik7CiAgICB9CiAgICBlbHNlIGlmICggSXNFcXVhbEdVSUQoICZJSURfSURpcmVjdDNERGV2aWNlNyAgLCByZWZpaWQgKSApIHsKICAgICAgICAqb2JqID0gSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlNyk7CiAgICAgICAgVFJBQ0UoIiglcCkgUmV0dXJuaW5nIElEaXJlY3QzRERldmljZTcgaW50ZXJmYWNlIGF0ICVwXG4iLCBUaGlzLCAqb2JqKTsKICAgIH0KCiAgICAvKiBVbmtub3duIGludGVyZmFjZSAqLwogICAgZWxzZQogICAgewogICAgICAgIEVSUigiKCVwKS0+KCVzLCAlcCk6IE5vIGludGVyZmFjZSBmb3VuZCIsIFRoaXMsIGRlYnVnc3RyX2d1aWQocmVmaWlkKSwgb2JqKTsKICAgICAgICByZXR1cm4gRV9OT0lOVEVSRkFDRTsKICAgIH0KCiAgICAvKiBBZGRSZWYgdGhlIHJldHVybmVkIGludGVyZmFjZSAqLwogICAgSVVua25vd25fQWRkUmVmKCAoSVVua25vd24gKikgKm9iaik7CiAgICByZXR1cm4gRDNEX09LOwp9CgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8zX1F1ZXJ5SW50ZXJmYWNlKElEaXJlY3QzRERldmljZTMgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgUkVGSUlEIHJpaWQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2b2lkICoqb2JqKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UzLCBpZmFjZSk7CiAgICBUUkFDRV8oZGRyYXdfdGh1bmspKCIoJXApLT4oJXMsJXApIHRodW5raW5nIHRvIElEaXJlY3QzRERldmljZTcgaW50ZXJmYWNlLlxuIiwgVGhpcywgZGVidWdzdHJfZ3VpZChyaWlkKSwgb2JqKTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2U3X1F1ZXJ5SW50ZXJmYWNlKElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTcpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcmlpZCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIG9iaik7Cn0KCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzJfUXVlcnlJbnRlcmZhY2UoSURpcmVjdDNERGV2aWNlMiAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBSRUZJSUQgcmlpZCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHZvaWQgKipvYmopCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTIsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglcywlcCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlNyBpbnRlcmZhY2UuXG4iLCBUaGlzLCBkZWJ1Z3N0cl9ndWlkKHJpaWQpLCBvYmopOwogICAgcmV0dXJuIElEaXJlY3QzRERldmljZTdfUXVlcnlJbnRlcmZhY2UoSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlNyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICByaWlkLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgb2JqKTsKfQoKc3RhdGljIEhSRVNVTFQgV0lOQVBJClRodW5rX0lEaXJlY3QzRERldmljZUltcGxfMV9RdWVyeUludGVyZmFjZShJRGlyZWN0M0REZXZpY2UgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgUkVGSUlEIHJpaWQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2b2lkICoqb2JwKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglcywlcCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlNyBpbnRlcmZhY2UuXG4iLCBUaGlzLCBkZWJ1Z3N0cl9ndWlkKHJpaWQpLCBvYnApOwogICAgcmV0dXJuIElEaXJlY3QzRERldmljZTdfUXVlcnlJbnRlcmZhY2UoSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlNyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICByaWlkLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgb2JwKTsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTc6OkFkZFJlZgogKgogKiBJbmNyZWFzZXMgdGhlIHJlZmNvdW50Li4uLgogKiBUaGUgbW9zdCBleGNpdGluZyBNZXRob2QsIGRlZmluaXRlbHkKICoKICogRXhpc3RzIGluIFZlcnNpb24gMSwgMiwgMyBhbmQgNwogKgogKiBSZXR1cm5zOgogKiAgVGhlIG5ldyByZWZjb3VudAogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBVTE9ORyBXSU5BUEkKSURpcmVjdDNERGV2aWNlSW1wbF83X0FkZFJlZihJRGlyZWN0M0REZXZpY2U3ICppZmFjZSkKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlNywgaWZhY2UpOwogICAgVUxPTkcgcmVmID0gSW50ZXJsb2NrZWRJbmNyZW1lbnQoJlRoaXMtPnJlZik7CgogICAgVFJBQ0UoIiglcCkgOiBpbmNyZW1lbnRpbmcgZnJvbSAlbHUuXG4iLCBUaGlzLCByZWYgLTEpOwoKICAgIHJldHVybiByZWY7Cn0KCnN0YXRpYyBVTE9ORyBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8zX0FkZFJlZihJRGlyZWN0M0REZXZpY2UzICppZmFjZSkKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlMywgaWZhY2UpOwogICAgVFJBQ0VfKGRkcmF3X3RodW5rKSgiKCVwKS0+KCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlNyBpbnRlcmZhY2UuXG4iLCBUaGlzKTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2U3X0FkZFJlZihJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0REZXZpY2U3KSk7Cn0KCnN0YXRpYyBVTE9ORyBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8yX0FkZFJlZihJRGlyZWN0M0REZXZpY2UyICppZmFjZSkKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlMiwgaWZhY2UpOwogICAgVFJBQ0VfKGRkcmF3X3RodW5rKSgiKCVwKS0+KCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlNyBpbnRlcmZhY2UuXG4iLCBUaGlzKTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2U3X0FkZFJlZihJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0REZXZpY2U3KSk7Cn0KCnN0YXRpYyBVTE9ORyBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8xX0FkZFJlZihJRGlyZWN0M0REZXZpY2UgKmlmYWNlKQp7CiAgICBUUkFDRV8oZGRyYXdfdGh1bmspKCIoJXApLT4oKSB0aHVua2luZyB0byBJRGlyZWN0M0REZXZpY2U3IGludGVyZmFjZS5cbiIsIGlmYWNlKTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2U3X0FkZFJlZihDT01fSU5URVJGQUNFX0NBU1QoSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlLCBJRGlyZWN0M0REZXZpY2U3LCBpZmFjZSkpOwp9CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSURpcmVjdDNERGV2aWNlNzo6UmVsZWFzZQogKgogKiBEZWNyZWFzZXMgdGhlIHJlZmNvdW50IG9mIHRoZSBpbnRlcmZhY2UKICogV2hlbiB0aGUgcmVmY291bnQgaXMgcmVkdWNlZCB0byAwLCB0aGUgb2JqZWN0IGlzIGRlc3Ryb3llZC4KICoKICogRXhpc3RzIGluIFZlcnNpb24gMSwgMiwgMyBhbmQgNwogKgogKiBSZXR1cm5zOmQKICogIFRoZSBuZXcgcmVmY291bnQKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgVUxPTkcgV0lOQVBJCklEaXJlY3QzRERldmljZUltcGxfN19SZWxlYXNlKElEaXJlY3QzRERldmljZTcgKmlmYWNlKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2U3LCBpZmFjZSk7CiAgICBVTE9ORyByZWYgPSBJbnRlcmxvY2tlZERlY3JlbWVudCgmVGhpcy0+cmVmKTsKCiAgICBUUkFDRSgiKCVwKS0+KCkgZGVjcmVtZW50aW5nIGZyb20gJWx1LlxuIiwgVGhpcywgcmVmICsxKTsKCiAgICAvKiBUaGlzIG1ldGhvZCBkb2Vzbid0IGRlc3Ryb3kgdGhlIFdpbmVEM0REZXZpY2UsIGJlY2F1c2UgaXQncyBzdGlsbCBpbiB1c2UgZm9yCiAgICAgKiAyRCByZW5kZXJpbmcuIElEaXJlY3REcmF3U3VyZmFjZTc6OlJlbGVhc2Ugd2lsbCBkZXN0cm95IHRoZSBXaW5lRDNERGV2aWNlCiAgICAgKiB3aGVuIHRoZSByZW5kZXIgdGFyZ2V0IGlzIHJlbGVhc2VkCiAgICAgKi8KICAgIGlmIChyZWYgPT0gMCkKICAgIHsKICAgICAgICBJUGFyZW50ICpJbmRleEJ1ZmZlclBhcmVudDsKICAgICAgICBEV09SRCBpOwoKICAgICAgICAvKiBGcmVlIHRoZSBpbmRleCBidWZmZXIgKi8KICAgICAgICBJV2luZUQzRERldmljZV9TZXRJbmRpY2VzKFRoaXMtPndpbmVEM0REZXZpY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBOVUxMLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgMCk7CiAgICAgICAgSVdpbmVEM0RJbmRleEJ1ZmZlcl9HZXRQYXJlbnQoVGhpcy0+aW5kZXhidWZmZXIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKElVbmtub3duICoqKSAmSW5kZXhCdWZmZXJQYXJlbnQpOwogICAgICAgIElQYXJlbnRfUmVsZWFzZShJbmRleEJ1ZmZlclBhcmVudCk7IC8qIE9uY2UgZm9yIHRoZSBnZXRQYXJlbnQgKi8KICAgICAgICBpZiggSVBhcmVudF9SZWxlYXNlKEluZGV4QnVmZmVyUGFyZW50KSAhPSAwKSAgLyogQW5kIG5vdyB0byBkZXN0cm95IGl0ICovCiAgICAgICAgewogICAgICAgICAgICBFUlIoIiAoJXApIFNvbWV0aGluZyBpcyBzdGlsbCBob2xkaW5nIHRoZSBpbmRleCBidWZmZXIgcGFyZW50ICVwXG4iLCBUaGlzLCBJbmRleEJ1ZmZlclBhcmVudCk7CiAgICAgICAgfQoKICAgICAgICAvKiBSZXN0b3JlIHRoZSByZW5kZXIgdGFyZ2V0cyAqLwogICAgICAgIGlmKFRoaXMtPk9mZlNjcmVlblRhcmdldCkKICAgICAgICB7CiAgICAgICAgICAgIC8qIFRoaXMtPnRhcmdldCBpcyB0aGUgb2Zmc2NyZWVuIHRhcmdldC4KICAgICAgICAgICAgICogVGhpcy0+ZGRyYXctPmQzZF90YXJnZXQgaXMgdGhlIHRhcmdldCB1c2VkIGJ5IEREcmF3CiAgICAgICAgICAgICAqLwogICAgICAgICAgICBUUkFDRSgiKCVwKSBSZWxlYXNlOiBVc2luZyAlcCBhcyBmcm9udCBidWZmZXIsICVwIGFzIGJhY2sgYnVmZmVyXG4iLCBUaGlzLCBUaGlzLT5kZHJhdy0+ZDNkX3RhcmdldCwgTlVMTCk7CiAgICAgICAgICAgIElXaW5lRDNERGV2aWNlX1NldEZyb250QmFja0J1ZmZlcnMoVGhpcy0+d2luZUQzRERldmljZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBUaGlzLT5kZHJhdy0+ZDNkX3RhcmdldC0+V2luZUQzRFN1cmZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgTlVMTCk7CiAgICAgICAgfQoKICAgICAgICAvKiBSZWxlYXNlIHRoZSBXaW5lRDNERGV2aWNlLiBUaGlzIHdvbid0IGRlc3Ryb3kgaXQgKi8KICAgICAgICBpZihJV2luZUQzRERldmljZV9SZWxlYXNlKFRoaXMtPndpbmVEM0REZXZpY2UpIDw9IDApCiAgICAgICAgewogICAgICAgICAgICBFUlIoIiAoJXApIFRoZSB3aW5lRDNEIGRldmljZSAlcCB3YXMgZGVzdHJveWVkIHVuZXhwZWN0YWRlbHkuIFByZXBhcmUgZm9yIHRyb3VibGVcbiIsIFRoaXMsIFRoaXMtPndpbmVEM0REZXZpY2UpOwogICAgICAgIH0KCiAgICAgICAgLyogVGhlIHRleHR1cmUgaGFuZGxlcyBzaG91bGQgYmUgdW5zZXQgYnkgbm93LCBidXQgdGhlcmUgbWlnaHQgYmUgc29tZSBiaXRzCiAgICAgICAgICogbWlzc2luZyBpbiBvdXIgcmVmZXJlbmNlIGNvdW50aW5nKG5lZWRzIHRlc3QpLiBEbyBhIHNhbml0eSBjaGVjawogICAgICAgICAqLwogICAgICAgIGZvcihpID0gMDsgaSA8IFRoaXMtPm51bUhhbmRsZXM7IGkrKykKICAgICAgICB7CiAgICAgICAgICAgIGlmKFRoaXMtPkhhbmRsZXNbaV0ucHRyKQogICAgICAgICAgICB7CiAgICAgICAgICAgICAgICBzd2l0Y2goVGhpcy0+SGFuZGxlc1tpXS50eXBlKQogICAgICAgICAgICAgICAgewogICAgICAgICAgICAgICAgICAgIGNhc2UgRERyYXdIYW5kbGVfVGV4dHVyZToKICAgICAgICAgICAgICAgICAgICB7CiAgICAgICAgICAgICAgICAgICAgICAgIElEaXJlY3REcmF3U3VyZmFjZUltcGwgKnN1cmYgPSAoSURpcmVjdERyYXdTdXJmYWNlSW1wbCAqKSBUaGlzLT5IYW5kbGVzW2ldLnB0cjsKICAgICAgICAgICAgICAgICAgICAgICAgRklYTUUoIlRleHR1cmUgSGFuZGxlICVsZCBub3QgdW5zZXQgcHJvcGVybHlcbiIsIGkgKyAxKTsKICAgICAgICAgICAgICAgICAgICAgICAgc3VyZi0+SGFuZGxlID0gMDsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgYnJlYWs7CgogICAgICAgICAgICAgICAgICAgIGNhc2UgRERyYXdIYW5kbGVfTWF0ZXJpYWw6CiAgICAgICAgICAgICAgICAgICAgewogICAgICAgICAgICAgICAgICAgICAgICBJRGlyZWN0M0RNYXRlcmlhbEltcGwgKm1hdCA9IChJRGlyZWN0M0RNYXRlcmlhbEltcGwgKikgVGhpcy0+SGFuZGxlc1tpXS5wdHI7CiAgICAgICAgICAgICAgICAgICAgICAgIEZJWE1FKCJNYXRlcmlhbCBoYW5kbGUgJWxkIG5vdCB1bnNldCBwcm9wZXJseVxuIiwgaSArIDEpOwogICAgICAgICAgICAgICAgICAgICAgICBtYXQtPkhhbmRsZSA9IDA7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGJyZWFrOwoKICAgICAgICAgICAgICAgICAgICBjYXNlIEREcmF3SGFuZGxlX01hdHJpeDoKICAgICAgICAgICAgICAgICAgICB7CiAgICAgICAgICAgICAgICAgICAgICAgIC8qIE5vIGZpeG1lIGhlcmUgYmVjYXVzZSB0aGlzIG1pZ2h0IGhhcHBlbiBiZWNhdXNlIG9mIHNsb3BweSBhcHBzICovCiAgICAgICAgICAgICAgICAgICAgICAgIFdBUk4oIkxlZnRvdmVyIG1hdHJpeCBoYW5kbGUgJWxkLCBkZWxldGluZ1xuIiwgaSArIDEpOwogICAgICAgICAgICAgICAgICAgICAgICBJRGlyZWN0M0REZXZpY2VfRGVsZXRlTWF0cml4KElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZSksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaSArIDEpOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICBicmVhazsKCiAgICAgICAgICAgICAgICAgICAgZGVmYXVsdDoKICAgICAgICAgICAgICAgICAgICAgICAgRklYTUUoIlVua25vd24gaGFuZGxlICVsZCBub3QgdW5zZXQgcHJvcGVybHlcbiIsIGkgKyAxKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgSGVhcEZyZWUoR2V0UHJvY2Vzc0hlYXAoKSwgMCwgVGhpcy0+SGFuZGxlcyk7CgogICAgICAgIC8qIFJlbGVhc2UgdGhlIHJlbmRlciB0YXJnZXQgYW5kIHRoZSBXaW5lRDNEIHJlbmRlciB0YXJnZXQKICAgICAgICAgKiAoU2VlIElEaXJlY3QzRDc6OkNyZWF0ZURldmljZSBmb3IgbW9yZSBjb21tZW50cyBvbiB0aGlzKQogICAgICAgICAqLwogICAgICAgIElEaXJlY3REcmF3U3VyZmFjZTdfUmVsZWFzZShJQ09NX0lOVEVSRkFDRShUaGlzLT50YXJnZXQsIElEaXJlY3REcmF3U3VyZmFjZTcpKTsKICAgICAgICBJRGlyZWN0RHJhd1N1cmZhY2U3X1JlbGVhc2UoSUNPTV9JTlRFUkZBQ0UoVGhpcy0+ZGRyYXctPmQzZF90YXJnZXQsSURpcmVjdERyYXdTdXJmYWNlNykpOwoKICAgICAgICBUaGlzLT5kZHJhdy0+ZDNkZGV2aWNlID0gTlVMTDsKCiAgICAgICAgLyogTm93IGZyZWUgdGhlIHN0cnVjdHVyZSAqLwogICAgICAgIEhlYXBGcmVlKEdldFByb2Nlc3NIZWFwKCksIDAsIFRoaXMpOwogICAgfQoKICAgIHJldHVybiByZWY7Cn0KCnN0YXRpYyBVTE9ORyBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8zX1JlbGVhc2UoSURpcmVjdDNERGV2aWNlMyAqaWZhY2UpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTMsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPigpIHRodW5raW5nIHRvIElEaXJlY3QzRERldmljZTcgaW50ZXJmYWNlLlxuIiwgVGhpcyk7CiAgICByZXR1cm4gSURpcmVjdDNERGV2aWNlN19SZWxlYXNlKElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTcpKTsKfQoKc3RhdGljIFVMT05HIFdJTkFQSQpUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzJfUmVsZWFzZShJRGlyZWN0M0REZXZpY2UyICppZmFjZSkKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlMiwgaWZhY2UpOwogICAgVFJBQ0VfKGRkcmF3X3RodW5rKSgiKCVwKS0+KCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlNyBpbnRlcmZhY2UuXG4iLCBUaGlzKTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2U3X1JlbGVhc2UoSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlNykpOwp9CgpzdGF0aWMgVUxPTkcgV0lOQVBJClRodW5rX0lEaXJlY3QzRERldmljZUltcGxfMV9SZWxlYXNlKElEaXJlY3QzRERldmljZSAqaWZhY2UpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZSwgaWZhY2UpOwogICAgVFJBQ0VfKGRkcmF3X3RodW5rKSgiKCVwKS0+KCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlNyBpbnRlcmZhY2UuXG4iLCBUaGlzKTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2U3X1JlbGVhc2UoSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlNykpOwp9CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSURpcmVjdDNERGV2aWNlIE1ldGhvZHMKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTo6SW5pdGlhbGl6ZQogKgogKiBJbml0aWFsaXplcyBhIERpcmVjdDNERGV2aWNlLiBUaGlzIGltcGxlbWVudGF0aW9uIGlzIGEgbm8tb3AsIGFzIGFsbAogKiBpbml0aWFsaXphdGlvbiBpcyBkb25lIGF0IGNyZWF0ZSB0aW1lLgogKgogKiBFeGlzdHMgaW4gVmVyc2lvbiAxCiAqCiAqIFBhcmFtZXRlcnM6CiAqICBObyBpZGVhIHdoYXQgdGhleSBtZWFuLCBhcyB0aGUgTVNETiBwYWdlIGlzIGdvbmUKICoKICogUmV0dXJuczogRERfT0sKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKSURpcmVjdDNERGV2aWNlSW1wbF8xX0luaXRpYWxpemUoSURpcmVjdDNERGV2aWNlICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgSURpcmVjdDNEICpEaXJlY3QzRCwgR1VJRCAqZ3VpZCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNEREVWSUNFREVTQyAqRGVzYykKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlLCBpZmFjZSk7CgogICAgLyogSXQgc2hvdWxkbid0IGJlIGNydWNpYWwsIGJ1dCBwcmludCBhIEZJWE1FLCBJJ20gaW50ZXJlc3RlZCBpZgogICAgICogYW55IGdhbWUgY2FsbHMgaXQgYW5kIHdoZW4KICAgICAqLwogICAgRklYTUUoIiglcCktPiglcCwlcCwlcCk6IE5vLW9wIVxuIiwgVGhpcywgRGlyZWN0M0QsIGd1aWQsIERlc2MpOwoKICAgIHJldHVybiBEM0RfT0s7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0REZXZpY2U3OjpHZXRDYXBzCiAqCiAqIFJldHJpZXZlcyB0aGUgZGV2aWNlJ3MgY2FwYWJpbGl0aWVzCiAqCiAqIFRoaXMgaW1wbGVtZW50YXRpb24gaXMgdXNlZCBmb3IgVmVyc2lvbiA3IG9ubHksIHRoZSBvbGRlciB2ZXJzaW9ucyBoYXZlCiAqIHRoZWlyIG93biBpbXBsZW1lbnRhdGlvbi4KICoKICogUGFyYW1ldGVyczoKICogIERlc2M6IFBvaW50ZXIgdG8gYSBEM0RERVZJQ0VERVNDNyBzdHJ1Y3R1cmUgdG8gZmlsbAogKgogKiBSZXR1cm5zOgogKiAgRDNEX09LIG9uIHN1Y2Nlc3MKICogIEQzREVSUl8qIGlmIGEgcHJvYmxlbSBvY2N1cnMuIFNlZSBXaW5lRDNECiAqCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIEhSRVNVTFQgV0lOQVBJCklEaXJlY3QzRERldmljZUltcGxfN19HZXRDYXBzKElEaXJlY3QzRERldmljZTcgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RERVZJQ0VERVNDNyAqRGVzYykKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlNywgaWZhY2UpOwogICAgRDNEREVWSUNFREVTQyBPbGREZXNjOwogICAgVFJBQ0UoIiglcCktPiglcClcbiIsIFRoaXMsIERlc2MpOwoKICAgIC8qIENhbGwgdGhlIHNhbWUgZnVuY3Rpb24gdXNlZCBieSBJRGlyZWN0M0QsIHRoaXMgc2F2ZXMgY29kZSAqLwogICAgcmV0dXJuIElEaXJlY3QzREltcGxfR2V0Q2FwcyhUaGlzLT5kZHJhdy0+d2luZUQzRCwgJk9sZERlc2MsIERlc2MpOwp9CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSURpcmVjdDNERGV2aWNlMzo6R2V0Q2FwcwogKgogKiBSZXRyaWV2ZXMgdGhlIGNhcGFiaWxpdGllcyBvZiB0aGUgaGFyZHdhcmUgZGV2aWNlIGFuZCB0aGUgZW11bGF0aW9uCiAqIGRldmljZS4gRm9yIFdpbmUsIGhhcmR3YXJlIGFuZCBlbXVsYXRpb24gYXJlIHRoZSBzYW1lIChpdCdzIGFsbCBIVykuCiAqCiAqIFRoaXMgaW1wbGVtZW50YXRpb24gaXMgdXNlZCBmb3IgVmVyc2lvbiAxLCAyLCBhbmQgMy4gVmVyc2lvbiA3IGhhcyBpdHMgb3duCiAqCiAqIFBhcmFtZXRlcnM6CiAqICBIV0Rlc2M6IFN0cnVjdHVyZSB0byBmaWxsIHdpdGggdGhlIEhXIGNhcHMKICogIEhlbERlc2M6IFN0cnVjdHVyZSB0byBmaWxsIHdpdGggdGhlIGhhcmRhcmUgZW11bGF0aW9uIGNhcHMKICoKICogUmV0dXJuczoKICogIEQzRF9PSyBvbiBzdWNjZXNzCiAqICBEM0RFUlJfKiBpZiBhIHByb2JsZW0gb2NjdXJzLiBTZWUgV2luZUQzRAogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0REZXZpY2VJbXBsXzNfR2V0Q2FwcyhJRGlyZWN0M0REZXZpY2UzICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNEREVWSUNFREVTQyAqSFdEZXNjLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RERVZJQ0VERVNDICpIZWxEZXNjKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UzLCBpZmFjZSk7CiAgICBEM0RERVZJQ0VERVNDNyBuZXdEZXNjOwogICAgSFJFU1VMVCBocjsKICAgIFRSQUNFKCIoJXApLT4oJXAsJXApXG4iLCBpZmFjZSwgSFdEZXNjLCBIZWxEZXNjKTsKCiAgICBociA9IElEaXJlY3QzREltcGxfR2V0Q2FwcyhUaGlzLT5kZHJhdy0+d2luZUQzRCwgSFdEZXNjLCAmbmV3RGVzYyk7CiAgICBpZihociAhPSBEM0RfT0spIHJldHVybiBocjsKCiAgICAqSGVsRGVzYyA9ICpIV0Rlc2M7CiAgICByZXR1cm4gRDNEX09LOwp9CgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8yX0dldENhcHMoSURpcmVjdDNERGV2aWNlMiAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRERFVklDRURFU0MgKkQzREhXRGV2RGVzYywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNEREVWSUNFREVTQyAqRDNESEVMRGV2RGVzYykKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlMiwgaWZhY2UpOwogICAgVFJBQ0VfKGRkcmF3X3RodW5rKSgiKCVwKS0+KCVwLCVwKSB0aHVua2luZyB0byBJRGlyZWN0M0REZXZpY2UzIGludGVyZmFjZS5cbiIsIFRoaXMsIEQzREhXRGV2RGVzYywgRDNESEVMRGV2RGVzYyk7CiAgICByZXR1cm4gSURpcmVjdDNERGV2aWNlM19HZXRDYXBzKElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTMpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RIV0RldkRlc2MsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzREhFTERldkRlc2MpOwp9CgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8xX0dldENhcHMoSURpcmVjdDNERGV2aWNlICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNEREVWSUNFREVTQyAqRDNESFdEZXZEZXNjLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RERVZJQ0VERVNDICpEM0RIRUxEZXZEZXNjKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglcCwlcCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlMyBpbnRlcmZhY2UuXG4iLCBUaGlzLCBEM0RIV0RldkRlc2MsIEQzREhFTERldkRlc2MpOwogICAgcmV0dXJuIElEaXJlY3QzRERldmljZTNfR2V0Q2FwcyhJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0REZXZpY2UzKSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNESFdEZXZEZXNjLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RIRUxEZXZEZXNjKTsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTI6OlN3YXBUZXh0dXJlSGFuZGxlcwogKgogKiBTd2FwcyB0aGUgdGV4dHVyZSBoYW5kbGVzIG9mIDIgVGV4dHVyZSBpbnRlcmZhY2VzLiBWZXJzaW9uIDEgYW5kIDIKICoKICogUGFyYW1ldGVyczoKICogIFRleDEsIFRleDI6IFRoZSAyIFRleHR1cmVzIHRvIHN3YXAKICoKICogUmV0dXJuczoKICogIEQzRF9PSwogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0REZXZpY2VJbXBsXzJfU3dhcFRleHR1cmVIYW5kbGVzKElEaXJlY3QzRERldmljZTIgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElEaXJlY3QzRFRleHR1cmUyICpUZXgxLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElEaXJlY3QzRFRleHR1cmUyICpUZXgyKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UyLCBpZmFjZSk7CiAgICBEV09SRCBzd2FwOwogICAgSURpcmVjdERyYXdTdXJmYWNlSW1wbCAqc3VyZjEgPSBJQ09NX09CSkVDVChJRGlyZWN0RHJhd1N1cmZhY2VJbXBsLCBJRGlyZWN0M0RUZXh0dXJlMiwgVGV4MSk7CiAgICBJRGlyZWN0RHJhd1N1cmZhY2VJbXBsICpzdXJmMiA9IElDT01fT0JKRUNUKElEaXJlY3REcmF3U3VyZmFjZUltcGwsIElEaXJlY3QzRFRleHR1cmUyLCBUZXgyKTsKICAgIFRSQUNFKCIoJXApLT4oJXAsJXApXG4iLCBUaGlzLCBzdXJmMSwgc3VyZjIpOwoKICAgIFRoaXMtPkhhbmRsZXNbc3VyZjEtPkhhbmRsZSAtIDFdLnB0ciA9IHN1cmYyOwogICAgVGhpcy0+SGFuZGxlc1tzdXJmMi0+SGFuZGxlIC0gMV0ucHRyID0gc3VyZjE7CgogICAgc3dhcCA9IHN1cmYyLT5IYW5kbGU7CiAgICBzdXJmMi0+SGFuZGxlID0gc3VyZjEtPkhhbmRsZTsKICAgIHN1cmYxLT5IYW5kbGUgPSBzd2FwOwoKICAgIHJldHVybiBEM0RfT0s7Cn0KCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzFfU3dhcFRleHR1cmVIYW5kbGVzKElEaXJlY3QzRERldmljZSAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgSURpcmVjdDNEVGV4dHVyZSAqRDNEVGV4MSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBJRGlyZWN0M0RUZXh0dXJlICpEM0RUZXgyKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UyLCBpZmFjZSk7CiAgICBJRGlyZWN0RHJhd1N1cmZhY2VJbXBsICpzdXJmMSA9IElDT01fT0JKRUNUKElEaXJlY3REcmF3U3VyZmFjZUltcGwsIElEaXJlY3QzRFRleHR1cmUsIEQzRFRleDEpOwogICAgSURpcmVjdERyYXdTdXJmYWNlSW1wbCAqc3VyZjIgPSBJQ09NX09CSkVDVChJRGlyZWN0RHJhd1N1cmZhY2VJbXBsLCBJRGlyZWN0M0RUZXh0dXJlLCBEM0RUZXgyKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglcCwlcCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlMiBpbnRlcmZhY2UuXG4iLCBUaGlzLCBzdXJmMSwgc3VyZjIpOwogICAgcmV0dXJuIElEaXJlY3QzRERldmljZTJfU3dhcFRleHR1cmVIYW5kbGVzKElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTIpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElDT01fSU5URVJGQUNFKHN1cmYxLCBJRGlyZWN0M0RUZXh0dXJlMiksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgSUNPTV9JTlRFUkZBQ0Uoc3VyZjIsIElEaXJlY3QzRFRleHR1cmUyKSk7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0REZXZpY2UzOjpHZXRTdGF0cwogKgogKiBUaGlzIG1ldGhvZCBzZWVtcyB0byByZXRyaWV2ZSBzb21lIHN0YXRzIGZyb20gdGhlIGRldmljZS4KICogVGhlIE1TRE4gZG9jdW1lbnRhdGlvbiBkb2Vzbid0IGV4aXN0IGFueSBtb3JlLCBidXQgdGhlIEQzRFNUQVRTCiAqIHN0cnVjdHVyZSBzdWdnZXN0cyB0aGF0IHRoZSBhbW91dCBvZiBkcmF3biBwcmltaXRpdmVzIGFuZCBwcm9jZXNzZWQKICogdmVydGljZXMgaXMgcmV0dXJuZWQuCiAqCiAqIEV4aXN0cyBpbiBWZXJzaW9uIDEsIDIgYW5kIDMKICoKICogUGFyYW1ldGVyczoKICogIFN0YXRzOiBQb2ludGVyIHRvIGEgRDNEU1RBVFMgc3RydWN0dXJlIHRvIGJlIGZpbGxlZAogKgogKiBSZXR1cm5zOgogKiAgRDNEX09LIG9uIHN1Y2Nlc3MKICogIERERVJSX0lOVkFMSURQQVJBTVMgaWYgU3RhdHMgPT0gTlVMTAogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0REZXZpY2VJbXBsXzNfR2V0U3RhdHMoSURpcmVjdDNERGV2aWNlMyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RTVEFUUyAqU3RhdHMpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTMsIGlmYWNlKTsKICAgIEZJWE1FKCIoJXApLT4oJXApOiBTdHViIVxuIiwgVGhpcywgU3RhdHMpOwoKICAgIGlmKCFTdGF0cykKICAgICAgICByZXR1cm4gRERFUlJfSU5WQUxJRFBBUkFNUzsKCiAgICAvKiBGaWxsIHRoZSBTdGF0cyB3aXRoIDAgKi8KICAgIFN0YXRzLT5kd1RyaWFuZ2xlc0RyYXduID0gMDsKICAgIFN0YXRzLT5kd0xpbmVzRHJhd24gPSAwOwogICAgU3RhdHMtPmR3UG9pbnRzRHJhd24gPSAwOwogICAgU3RhdHMtPmR3U3BhbnNEcmF3biA9IDA7CiAgICBTdGF0cy0+ZHdWZXJ0aWNlc1Byb2Nlc3NlZCA9IDA7CgogICAgcmV0dXJuIEQzRF9PSzsKfQoKc3RhdGljIEhSRVNVTFQgV0lOQVBJClRodW5rX0lEaXJlY3QzRERldmljZUltcGxfMl9HZXRTdGF0cyhJRGlyZWN0M0REZXZpY2UyICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRFNUQVRTICpTdGF0cykKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlMiwgaWZhY2UpOwogICAgVFJBQ0VfKGRkcmF3X3RodW5rKSgiKCVwKS0+KCVwKSB0aHVua2luZyB0byBJRGlyZWN0M0REZXZpY2UzIGludGVyZmFjZS5cbiIsIFRoaXMsIFN0YXRzKTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2UzX0dldFN0YXRzKElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTMpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgU3RhdHMpOwp9CgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8xX0dldFN0YXRzKElEaXJlY3QzRERldmljZSAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RTVEFUUyAqU3RhdHMpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZSwgaWZhY2UpOwogICAgVFJBQ0VfKGRkcmF3X3RodW5rKSgiKCVwKS0+KCVwKSB0aHVua2luZyB0byBJRGlyZWN0M0REZXZpY2UzIGludGVyZmFjZS5cbiIsIFRoaXMsIFN0YXRzKTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2UzX0dldFN0YXRzKElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTMpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgU3RhdHMpOwp9CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSURpcmVjdDNERGV2aWNlOjpDcmVhdGVFeGVjdXRlQnVmZmVyCiAqCiAqIENyZWF0ZXMgYW4gSURpcmVjdDNERXhlY3V0ZUJ1ZmZlciwgdXNlZCBmb3IgcmVuZGVyaW5nIHdpdGggYQogKiBEaXJlY3QzRERldmljZS4KICoKICogVmVyc2lvbiAxIG9ubHkuCiAqCiAqIFBhcmFtczoKICogIERlc2M6IEJ1ZmZlciBkZXNjcmlwdGlvbgogKiAgRXhlY3V0ZUJ1ZmZlcjogQWRkcmVzcyB0byByZXR1cm4gdGhlIEludGVyZmFjZSBwb2ludGVyIGF0CiAqICBVbmtPdXRlcjogTXVzdCBiZSBOVUxMLiBCYXNpY2FsbHkgZm9yIGFnZ3JlZ2F0aW9uLCB3aGljaCBkZHJhdyBkb2Vzbid0CiAqICAgICAgICAgICAgc3VwcG9ydAogKgogKiBSZXR1cm5zOgogKiAgQ0xBU1NfRV9OT0FHR1JFR0FUSU9OIGlmIFVua091dGVyICE9IE5VTEwKICogIERERVJSX09VVE9GTUVNT1JZIGlmIHdlIHJhbiBvdXQgb2YgbWVtb3J5CiAqICBEM0RfT0sgb24gc3VjY2VzcwogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0REZXZpY2VJbXBsXzFfQ3JlYXRlRXhlY3V0ZUJ1ZmZlcihJRGlyZWN0M0REZXZpY2UgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RFWEVDVVRFQlVGRkVSREVTQyAqRGVzYywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgSURpcmVjdDNERXhlY3V0ZUJ1ZmZlciAqKkV4ZWN1dGVCdWZmZXIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElVbmtub3duICpVbmtPdXRlcikKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlLCBpZmFjZSk7CiAgICBJRGlyZWN0M0RFeGVjdXRlQnVmZmVySW1wbCogb2JqZWN0OwogICAgVFJBQ0UoIiglcCktPiglcCwlcCwlcCkhXG4iLCBUaGlzLCBEZXNjLCBFeGVjdXRlQnVmZmVyLCBVbmtPdXRlcik7CgogICAgaWYoVW5rT3V0ZXIpCiAgICAgICAgcmV0dXJuIENMQVNTX0VfTk9BR0dSRUdBVElPTjsKCiAgICAvKiBBbGxvY2F0ZSB0aGUgbmV3IEV4ZWN1dGUgQnVmZmVyICovCiAgICBvYmplY3QgPSBIZWFwQWxsb2MoR2V0UHJvY2Vzc0hlYXAoKSwgSEVBUF9aRVJPX01FTU9SWSwgc2l6ZW9mKElEaXJlY3QzREV4ZWN1dGVCdWZmZXJJbXBsKSk7CiAgICBpZighb2JqZWN0KQogICAgewogICAgICAgIEVSUigiT3V0IG9mIG1lbW9yeSB3aGVuIGFsbG9jYXRpbmcgYSBJRGlyZWN0M0RFeGVjdXRlQnVmZmVySW1wbCBzdHJ1Y3R1cmVcbiIpOwogICAgICAgIHJldHVybiBEREVSUl9PVVRPRk1FTU9SWTsKICAgIH0KCiAgICBJQ09NX0lOSVRfSU5URVJGQUNFKG9iamVjdCwgSURpcmVjdDNERXhlY3V0ZUJ1ZmZlciwgSURpcmVjdDNERXhlY3V0ZUJ1ZmZlcl9WdGJsKTsKCiAgICBvYmplY3QtPnJlZiA9IDE7CiAgICBvYmplY3QtPmQzZGRldiA9IFRoaXM7CgogICAgLyogSW5pdGlhbGl6ZXMgbWVtb3J5ICovCiAgICBtZW1jcHkoJm9iamVjdC0+ZGVzYywgRGVzYywgRGVzYy0+ZHdTaXplKTsKCiAgICAvKiBObyBidWZmZXIgZ2l2ZW4gKi8KICAgIGlmICgob2JqZWN0LT5kZXNjLmR3RmxhZ3MgJiBEM0RERUJfTFBEQVRBKSA9PSAwKQogICAgICAgIG9iamVjdC0+ZGVzYy5scERhdGEgPSBOVUxMOwoKICAgIC8qIE5vIGJ1ZmZlciBzaXplIGdpdmVuICovCiAgICBpZiAoKG9iamVjdC0+ZGVzYy5kd0ZsYWdzICYgRDNEREVCX0JVRlNJWkUpID09IDApCiAgICAgICAgb2JqZWN0LT5kZXNjLmR3QnVmZmVyU2l6ZSA9IDA7CgogICAgLyogQ3JlYXRlIGJ1ZmZlciBpZiBhc2tlZCAqLwogICAgaWYgKChvYmplY3QtPmRlc2MubHBEYXRhID09IE5VTEwpICYmIChvYmplY3QtPmRlc2MuZHdCdWZmZXJTaXplID4gMCkpCiAgICB7CiAgICAgICAgb2JqZWN0LT5uZWVkX2ZyZWUgPSBUUlVFOwogICAgICAgIG9iamVjdC0+ZGVzYy5scERhdGEgPSBIZWFwQWxsb2MoR2V0UHJvY2Vzc0hlYXAoKSxIRUFQX1pFUk9fTUVNT1JZLG9iamVjdC0+ZGVzYy5kd0J1ZmZlclNpemUpOwogICAgICAgIGlmKCFvYmplY3QtPmRlc2MubHBEYXRhKQogICAgICAgIHsKICAgICAgICAgICAgRVJSKCJPdXQgb2YgbWVtb3J5IHdoZW4gYWxsb2NhdGluZyB0aGUgZXhlY3V0ZSBidWZmZXIgZGF0YVxuIik7CiAgICAgICAgICAgIEhlYXBGcmVlKEdldFByb2Nlc3NIZWFwKCksIDAsIG9iamVjdCk7CiAgICAgICAgICAgIHJldHVybiBEREVSUl9PVVRPRk1FTU9SWTsKICAgICAgICB9CiAgICB9CiAgICBlbHNlCiAgICB7CiAgICAgICAgb2JqZWN0LT5uZWVkX2ZyZWUgPSBGQUxTRTsKICAgIH0KCiAgICAvKiBObyB2ZXJ0aWNlcyBmb3IgdGhlIG1vbWVudCAqLwogICAgb2JqZWN0LT52ZXJ0ZXhfZGF0YSA9IE5VTEw7CgogICAgb2JqZWN0LT5kZXNjLmR3RmxhZ3MgfD0gRDNEREVCX0xQREFUQTsKCiAgICBvYmplY3QtPmluZGljZXMgPSBOVUxMOwogICAgb2JqZWN0LT5uYl9pbmRpY2VzID0gMDsKCiAgICAqRXhlY3V0ZUJ1ZmZlciA9IElDT01fSU5URVJGQUNFKG9iamVjdCwgSURpcmVjdDNERXhlY3V0ZUJ1ZmZlcik7CgogICAgVFJBQ0UoIiBSZXR1cm5pbmcgSURpcmVjdDNERXhlY3V0ZUJ1ZmZlciBhdCAlcCwgaW1wbGVtZW50YXRpb24gaXMgYXQgJXBcbiIsICpFeGVjdXRlQnVmZmVyLCBvYmplY3QpOwoKICAgIHJldHVybiBEM0RfT0s7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0REZXZpY2U6OkV4ZWN1dGUKICoKICogRXhlY3V0ZXMgYWxsIHRoZSBzdHVmZiBpbiBhbiBleGVjdXRlIGJ1ZmZlci4KICoKICogUGFyYW1zOgogKiAgRXhlY3V0ZUJ1ZmZlcjogVGhlIGJ1ZmZlciB0byBleGVjdXRlCiAqICBWaWV3cG9ydDogVGhlIHZpZXdwb3J0IHVzZWQgZm9yIHJlbmRlcmluZwogKiAgRmxhZ3M6IFNvbWUgZmxhZ3MKICoKICogUmV0dXJuczoKICogIERERVJSX0lOVkFMSURQQVJBTVMgaWYgRXhlY3V0ZUJ1ZmZlciA9PSBOVUxMCiAqICBEM0RfT0sgb24gc3VjZXNzCiAqCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIEhSRVNVTFQgV0lOQVBJCklEaXJlY3QzRERldmljZUltcGxfMV9FeGVjdXRlKElEaXJlY3QzRERldmljZSAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElEaXJlY3QzREV4ZWN1dGVCdWZmZXIgKkV4ZWN1dGVCdWZmZXIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElEaXJlY3QzRFZpZXdwb3J0ICpWaWV3cG9ydCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgRmxhZ3MpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZSwgaWZhY2UpOwogICAgSURpcmVjdDNERXhlY3V0ZUJ1ZmZlckltcGwgKkRpcmVjdDNERXhlY3V0ZUJ1ZmZlckltcGwgPSBJQ09NX09CSkVDVChJRGlyZWN0M0RFeGVjdXRlQnVmZmVySW1wbCwgSURpcmVjdDNERXhlY3V0ZUJ1ZmZlciwgRXhlY3V0ZUJ1ZmZlcik7CiAgICBJRGlyZWN0M0RWaWV3cG9ydEltcGwgKkRpcmVjdDNEVmlld3BvcnRJbXBsID0gSUNPTV9PQkpFQ1QoSURpcmVjdDNEVmlld3BvcnRJbXBsLCBJRGlyZWN0M0RWaWV3cG9ydDMsIFZpZXdwb3J0KTsKCiAgICBUUkFDRSgiKCVwKS0+KCVwLCVwLCUwOGx4KVxuIiwgVGhpcywgRGlyZWN0M0RFeGVjdXRlQnVmZmVySW1wbCwgRGlyZWN0M0RWaWV3cG9ydEltcGwsIEZsYWdzKTsKCiAgICBpZighRGlyZWN0M0RFeGVjdXRlQnVmZmVySW1wbCkKICAgICAgICByZXR1cm4gRERFUlJfSU5WQUxJRFBBUkFNUzsKCiAgICAvKiBFeGVjdXRlLi4uICovCiAgICBJRGlyZWN0M0RFeGVjdXRlQnVmZmVySW1wbF9FeGVjdXRlKERpcmVjdDNERXhlY3V0ZUJ1ZmZlckltcGwsIFRoaXMsIERpcmVjdDNEVmlld3BvcnRJbXBsKTsKCiAgICByZXR1cm4gRDNEX09LOwp9CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSURpcmVjdDNERGV2aWNlMzo6QWRkVmlld3BvcnQKICoKICogQWRkIGEgRGlyZWN0M0RWaWV3cG9ydCB0byB0aGUgZGV2aWNlJ3Mgdmlld3BvcnQgbGlzdC4gVGhlc2Ugdmlld3BvcnRzCiAqIGFyZSB3cmFwcGVkIHRvIElEaXJlY3QzRERldmljZTcgdmlld3BvcnRzIGluIHZpZXdwb3J0LmMKICoKICogRXhpc3RzIGluIFZlcnNpb24gMSwgMiBhbmQgMy4gTm90ZSB0aGF0IElEaXJlY3QzRFZpZXdwb3J0IDEsIDIgYW5kIDMKICogYXJlIHRoZSBzYW1lIGludGVyZmFjZXMuCiAqCiAqIFBhcmFtczoKICogIFZpZXdwb3J0OiBUaGUgdmlld3BvcnQgdG8gYWRkCiAqCiAqIFJldHVybnM6CiAqICBEREVSUl9JTlZBTElEUEFSQU1TIGlmIFZpZXdwb3J0ID09IE5VTEwKICogIEQzRF9PSyBvbiBzdWNjZXNzCiAqCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIEhSRVNVTFQgV0lOQVBJCklEaXJlY3QzRERldmljZUltcGxfM19BZGRWaWV3cG9ydChJRGlyZWN0M0REZXZpY2UzICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElEaXJlY3QzRFZpZXdwb3J0MyAqVmlld3BvcnQpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTMsIGlmYWNlKTsKICAgIElEaXJlY3QzRFZpZXdwb3J0SW1wbCAqdnAgPSBJQ09NX09CSkVDVChJRGlyZWN0M0RWaWV3cG9ydEltcGwsIElEaXJlY3QzRFZpZXdwb3J0MywgVmlld3BvcnQpOwoKICAgIFRSQUNFKCIoJXApLT4oJXApXG4iLCBUaGlzLCB2cCk7CgogICAgLyogU2FuaXR5IGNoZWNrICovCiAgICBpZighdnApCiAgICAgICAgcmV0dXJuIERERVJSX0lOVkFMSURQQVJBTVM7CgogICAgdnAtPm5leHQgPSBUaGlzLT52aWV3cG9ydF9saXN0OwogICAgVGhpcy0+dmlld3BvcnRfbGlzdCA9IHZwOwoKICAgIHJldHVybiBEM0RfT0s7Cn0KCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzJfQWRkVmlld3BvcnQoSURpcmVjdDNERGV2aWNlMiAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBJRGlyZWN0M0RWaWV3cG9ydDIgKkRpcmVjdDNEVmlld3BvcnQyKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UyLCBpZmFjZSk7CiAgICBJRGlyZWN0M0RWaWV3cG9ydEltcGwgKnZwID0gSUNPTV9PQkpFQ1QoSURpcmVjdDNEVmlld3BvcnRJbXBsLCBJRGlyZWN0M0RWaWV3cG9ydDMsIERpcmVjdDNEVmlld3BvcnQyKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglcCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlMyBpbnRlcmZhY2UuXG4iLCBUaGlzLCB2cCk7CiAgICByZXR1cm4gSURpcmVjdDNERGV2aWNlM19BZGRWaWV3cG9ydChJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0REZXZpY2UzKSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElDT01fSU5URVJGQUNFKHZwLCBJRGlyZWN0M0RWaWV3cG9ydDMpKTsKfQoKc3RhdGljIEhSRVNVTFQgV0lOQVBJClRodW5rX0lEaXJlY3QzRERldmljZUltcGxfMV9BZGRWaWV3cG9ydChJRGlyZWN0M0REZXZpY2UgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgSURpcmVjdDNEVmlld3BvcnQgKkRpcmVjdDNEVmlld3BvcnQpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTIsIGlmYWNlKTsKICAgIElEaXJlY3QzRFZpZXdwb3J0SW1wbCAqdnAgPSBJQ09NX09CSkVDVChJRGlyZWN0M0RWaWV3cG9ydEltcGwsIElEaXJlY3QzRFZpZXdwb3J0MywgRGlyZWN0M0RWaWV3cG9ydCk7CiAgICBUUkFDRV8oZGRyYXdfdGh1bmspKCIoJXApLT4oJXApIHRodW5raW5nIHRvIElEaXJlY3QzRERldmljZTMgaW50ZXJmYWNlLlxuIiwgVGhpcywgdnApOwogICAgcmV0dXJuIElEaXJlY3QzRERldmljZTNfQWRkVmlld3BvcnQoSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlMyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBJQ09NX0lOVEVSRkFDRSh2cCwgSURpcmVjdDNEVmlld3BvcnQzKSk7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0REZXZpY2UzOjpEZWxldGVWaWV3cG9ydAogKgogKiBEZWxldGVzIGEgRGlyZWN0M0RWaWV3cG9ydCBmcm9tIHRoZSBkZXZpY2UncyB2aWV3cG9ydCBsaXN0LgogKgogKiBFeGlzdHMgaW4gVmVyc2lvbiAxLCAyIGFuZCAzLiBOb3RlIHRoYXQgYWxsIFZpZXdwb3J0IGludGVyZmFjZSB2ZXJzaW9ucwogKiBhcmUgZXF1YWwuCiAqCiAqIFBhcmFtczoKICogIFZpZXdwb3J0OiBUaGUgdmlld3BvcnQgdG8gZGVsZXRlCiAqCiAqIFJldHVybnM6CiAqICBEM0RfT0sgb24gc3VjY2VzcwogKiAgRERFUlJfSU5WQUxJRFBBUkFNUyBpZiB0aGUgdmlld3BvcnQgd2Fzbid0IGZvdW5kIGluIHRoZSBsaXN0CiAqCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIEhSRVNVTFQgV0lOQVBJCklEaXJlY3QzRERldmljZUltcGxfM19EZWxldGVWaWV3cG9ydChJRGlyZWN0M0REZXZpY2UzICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElEaXJlY3QzRFZpZXdwb3J0MyAqVmlld3BvcnQpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTMsIGlmYWNlKTsKICAgIElEaXJlY3QzRFZpZXdwb3J0SW1wbCAqdnAgPSAoSURpcmVjdDNEVmlld3BvcnRJbXBsICopIFZpZXdwb3J0OwogICAgSURpcmVjdDNEVmlld3BvcnRJbXBsICpjdXJfdmlld3BvcnQsICpwcmV2X3ZpZXdwb3J0ID0gTlVMTDsKCiAgICBUUkFDRSgiKCVwKS0+KCVwKVxuIiwgVGhpcywgdnApOwoKICAgIGN1cl92aWV3cG9ydCA9IFRoaXMtPnZpZXdwb3J0X2xpc3Q7CiAgICB3aGlsZSAoY3VyX3ZpZXdwb3J0ICE9IE5VTEwpCiAgICB7CiAgICAgICAgaWYgKGN1cl92aWV3cG9ydCA9PSB2cCkKICAgICAgICB7CiAgICAgICAgICAgIGlmIChwcmV2X3ZpZXdwb3J0ID09IE5VTEwpIFRoaXMtPnZpZXdwb3J0X2xpc3QgPSBjdXJfdmlld3BvcnQtPm5leHQ7CiAgICAgICAgICAgIGVsc2UgcHJldl92aWV3cG9ydC0+bmV4dCA9IGN1cl92aWV3cG9ydC0+bmV4dDsKICAgICAgICAgICAgLyogVE9ETyA6IGFkZCBkZXNhY3RpdmF0ZSBvZiB0aGUgdmlld3BvcnQgYW5kIGFsbCBhc3NvY2lhdGVkIGxpZ2h0cy4uLiAqLwogICAgICAgICAgICByZXR1cm4gRDNEX09LOwogICAgICAgIH0KICAgICAgICBwcmV2X3ZpZXdwb3J0ID0gY3VyX3ZpZXdwb3J0OwogICAgICAgIGN1cl92aWV3cG9ydCA9IGN1cl92aWV3cG9ydC0+bmV4dDsKICAgIH0KCiAgICByZXR1cm4gRERFUlJfSU5WQUxJRFBBUkFNUzsKfQoKc3RhdGljIEhSRVNVTFQgV0lOQVBJClRodW5rX0lEaXJlY3QzRERldmljZUltcGxfMl9EZWxldGVWaWV3cG9ydChJRGlyZWN0M0REZXZpY2UyICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElEaXJlY3QzRFZpZXdwb3J0MiAqRGlyZWN0M0RWaWV3cG9ydDIpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTIsIGlmYWNlKTsKICAgIElEaXJlY3QzRFZpZXdwb3J0SW1wbCAqdnAgPSBJQ09NX09CSkVDVChJRGlyZWN0M0RWaWV3cG9ydEltcGwsIElEaXJlY3QzRFZpZXdwb3J0MywgRGlyZWN0M0RWaWV3cG9ydDIpOwogICAgVFJBQ0VfKGRkcmF3X3RodW5rKSgiKCVwKS0+KCVwKSB0aHVua2luZyB0byBJRGlyZWN0M0REZXZpY2UzIGludGVyZmFjZS5cbiIsIFRoaXMsIHZwKTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2UzX0RlbGV0ZVZpZXdwb3J0KElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTMpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgSUNPTV9JTlRFUkZBQ0UodnAsIElEaXJlY3QzRFZpZXdwb3J0MykpOwp9CgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8xX0RlbGV0ZVZpZXdwb3J0KElEaXJlY3QzRERldmljZSAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBJRGlyZWN0M0RWaWV3cG9ydCAqRGlyZWN0M0RWaWV3cG9ydDIpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZSwgaWZhY2UpOwogICAgSURpcmVjdDNEVmlld3BvcnRJbXBsICp2cCA9IElDT01fT0JKRUNUKElEaXJlY3QzRFZpZXdwb3J0SW1wbCwgSURpcmVjdDNEVmlld3BvcnQzLCBEaXJlY3QzRFZpZXdwb3J0Mik7CiAgICBUUkFDRV8oZGRyYXdfdGh1bmspKCIoJXApLT4oJXApIHRodW5raW5nIHRvIElEaXJlY3QzRERldmljZTMgaW50ZXJmYWNlLlxuIiwgVGhpcywgdnApOwogICAgcmV0dXJuIElEaXJlY3QzRERldmljZTNfRGVsZXRlVmlld3BvcnQoSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlMyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBJQ09NX0lOVEVSRkFDRSh2cCwgSURpcmVjdDNEVmlld3BvcnQzKSk7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0REZXZpY2UzOjpOZXh0Vmlld3BvcnQKICoKICogUmV0dXJucyBhIHZpZXdwb3J0IGZyb20gdGhlIHZpZXdwb3J0IGxpc3QsIGRlcGVuZGluZyBvbiB0aGUKICogcGFzc2VkIHZpZXdwb3J0IGFuZCB0aGUgZmxhZ3MuCiAqCiAqIEV4aXN0cyBpbiBWZXJzaW9uIDEsIDIgYW5kIDMuIE5vdGUgdGhhdCBhbGwgVmlld3BvcnQgaW50ZXJmYWNlIHZlcnNpb25zCiAqIGFyZSBlcXVhbC4KICoKICogUGFyYW1zOgogKiAgVmlld3BvcnQ6IFZpZXdwb3J0IHRvIHVzZSBmb3IgYmVnaW5uaW5nIHRoZSBzZWFyY2gKICogIEZsYWdzOiBEM0RORVhUX05FWFQsIEQzRE5FWFRfSEVBRCBvciBEM0RORVhUX1RBSUwKICoKICogUmV0dXJuczoKICogIEQzRF9PSyBvbiBzdWNjZXNzCiAqICBEREVSUl9JTlZBTElEUEFSQU1TIGlmIHRoZSBmbGFncyB3ZXJlIHdyb25nLCBvciBWaWV3cG9ydCB3YXMgTlVMTAogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0REZXZpY2VJbXBsXzNfTmV4dFZpZXdwb3J0KElEaXJlY3QzRERldmljZTMgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElEaXJlY3QzRFZpZXdwb3J0MyAqVmlld3BvcnQzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElEaXJlY3QzRFZpZXdwb3J0MyAqKmxwbHBEaXJlY3QzRFZpZXdwb3J0MywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBGbGFncykKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlMywgaWZhY2UpOwogICAgSURpcmVjdDNEVmlld3BvcnRJbXBsICp2cCA9IElDT01fT0JKRUNUKElEaXJlY3QzRFZpZXdwb3J0SW1wbCwgSURpcmVjdDNEVmlld3BvcnQzLCBWaWV3cG9ydDMpOwogICAgSURpcmVjdDNEVmlld3BvcnRJbXBsICpyZXMgPSBOVUxMOwoKICAgIFRSQUNFKCIoJXApLT4oJXAsJXAsJTA4bHgpXG4iLCBUaGlzLCB2cCwgbHBscERpcmVjdDNEVmlld3BvcnQzLCBGbGFncyk7CgogICAgaWYoIXZwKQogICAgewogICAgICAgIHJldHVybiBEREVSUl9JTlZBTElEUEFSQU1TOwogICAgICAgICpscGxwRGlyZWN0M0RWaWV3cG9ydDMgPSBOVUxMOwogICAgfQoKCiAgICBzd2l0Y2ggKEZsYWdzKQogICAgewogICAgICAgIGNhc2UgRDNETkVYVF9ORVhUOgogICAgICAgIHsKICAgICAgICAgICAgcmVzID0gdnAtPm5leHQ7CiAgICAgICAgfQogICAgICAgIGJyZWFrOwogICAgICAgIGNhc2UgRDNETkVYVF9IRUFEOgogICAgICAgIHsKICAgICAgICAgICAgcmVzID0gVGhpcy0+dmlld3BvcnRfbGlzdDsKICAgICAgICB9CiAgICAgICAgYnJlYWs7CiAgICAgICAgY2FzZSBEM0RORVhUX1RBSUw6CiAgICAgICAgewogICAgICAgICAgICBJRGlyZWN0M0RWaWV3cG9ydEltcGwgKmN1cl92aWV3cG9ydCA9IFRoaXMtPnZpZXdwb3J0X2xpc3Q7CiAgICAgICAgICAgIGlmIChjdXJfdmlld3BvcnQgIT0gTlVMTCkKICAgICAgICAgICAgewogICAgICAgICAgICAgICAgd2hpbGUgKGN1cl92aWV3cG9ydC0+bmV4dCAhPSBOVUxMKSBjdXJfdmlld3BvcnQgPSBjdXJfdmlld3BvcnQtPm5leHQ7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmVzID0gY3VyX3ZpZXdwb3J0OwogICAgICAgIH0KICAgICAgICBicmVhazsKICAgICAgICBkZWZhdWx0OgogICAgICAgICAgICAqbHBscERpcmVjdDNEVmlld3BvcnQzID0gTlVMTDsKICAgICAgICAgICAgcmV0dXJuIERERVJSX0lOVkFMSURQQVJBTVM7CiAgICB9CgogICAgKmxwbHBEaXJlY3QzRFZpZXdwb3J0MyA9IElDT01fSU5URVJGQUNFKHJlcywgSURpcmVjdDNEVmlld3BvcnQzKTsKICAgIHJldHVybiBEM0RfT0s7Cn0KCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzJfTmV4dFZpZXdwb3J0KElEaXJlY3QzRERldmljZTIgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElEaXJlY3QzRFZpZXdwb3J0MiAqVmlld3BvcnQyLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElEaXJlY3QzRFZpZXdwb3J0MiAqKmxwbHBEaXJlY3QzRFZpZXdwb3J0MiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBGbGFncykKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlMiwgaWZhY2UpOwogICAgSURpcmVjdDNEVmlld3BvcnRJbXBsICp2cCA9IElDT01fT0JKRUNUKElEaXJlY3QzRFZpZXdwb3J0SW1wbCwgSURpcmVjdDNEVmlld3BvcnQzLCBWaWV3cG9ydDIpOwogICAgSURpcmVjdDNEVmlld3BvcnQzICpyZXM7CiAgICBIUkVTVUxUIGhyOwogICAgVFJBQ0VfKGRkcmF3X3RodW5rKSgiKCVwKS0+KCVwLCVwLCUwOGx4KSB0aHVua2luZyB0byBJRGlyZWN0M0REZXZpY2UzIGludGVyZmFjZS5cbiIsIFRoaXMsIHZwLCBscGxwRGlyZWN0M0RWaWV3cG9ydDIsIEZsYWdzKTsKICAgIGhyID0gSURpcmVjdDNERGV2aWNlM19OZXh0Vmlld3BvcnQoSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlMyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElDT01fSU5URVJGQUNFKHZwLCBJRGlyZWN0M0RWaWV3cG9ydDMpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmcmVzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBGbGFncyk7CiAgICAqbHBscERpcmVjdDNEVmlld3BvcnQyID0gKElEaXJlY3QzRFZpZXdwb3J0MiAqKSBDT01fSU5URVJGQUNFX0NBU1QoSURpcmVjdDNEVmlld3BvcnRJbXBsLCBJRGlyZWN0M0RWaWV3cG9ydDMsIElEaXJlY3QzRFZpZXdwb3J0MywgcmVzKTsKICAgIHJldHVybiBocjsKfQoKc3RhdGljIEhSRVNVTFQgV0lOQVBJClRodW5rX0lEaXJlY3QzRERldmljZUltcGxfMV9OZXh0Vmlld3BvcnQoSURpcmVjdDNERGV2aWNlICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBJRGlyZWN0M0RWaWV3cG9ydCAqVmlld3BvcnQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgSURpcmVjdDNEVmlld3BvcnQgKipscGxwRGlyZWN0M0RWaWV3cG9ydCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBGbGFncykKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlLCBpZmFjZSk7CiAgICBJRGlyZWN0M0RWaWV3cG9ydEltcGwgKnZwID0gSUNPTV9PQkpFQ1QoSURpcmVjdDNEVmlld3BvcnRJbXBsLCBJRGlyZWN0M0RWaWV3cG9ydDMsIFZpZXdwb3J0KTsKICAgIElEaXJlY3QzRFZpZXdwb3J0MyAqcmVzOwogICAgSFJFU1VMVCBocjsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglcCwlcCwlMDhseCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlMyBpbnRlcmZhY2UuXG4iLCBUaGlzLCB2cCwgbHBscERpcmVjdDNEVmlld3BvcnQsIEZsYWdzKTsKICAgIGhyID0gSURpcmVjdDNERGV2aWNlM19OZXh0Vmlld3BvcnQoSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlMyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElDT01fSU5URVJGQUNFKHZwLCBJRGlyZWN0M0RWaWV3cG9ydDMpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmcmVzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBGbGFncyk7CiAgICAqbHBscERpcmVjdDNEVmlld3BvcnQgPSAoSURpcmVjdDNEVmlld3BvcnQgKikgQ09NX0lOVEVSRkFDRV9DQVNUKElEaXJlY3QzRFZpZXdwb3J0SW1wbCwgSURpcmVjdDNEVmlld3BvcnQzLCBJRGlyZWN0M0RWaWV3cG9ydDMsIHJlcyk7CiAgICByZXR1cm4gaHI7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0REZXZpY2U6OlBpY2sKICoKICogRXhlY3V0ZXMgYW4gZXhlY3V0ZSBidWZmZXIgd2l0aG91dCBwZXJmb3JtaW5nIHJlbmRlcmluZy4gSW5zdGVhZCwgYQogKiBsaXN0IG9mIHByaW1pdGl2ZXMgdGhhdCBpbnRlcnNlY3Qgd2l0aCAoeDEseTEpIG9mIHRoZSBwYXNzZWQgcmVjdGFuZ2xlCiAqIGlzIGNyZWF0ZWQuIElEaXJlY3QzRERldmljZTo6R2V0UGlja1JlY29yZHMgY2FuIGJlIHVzZWQgdG8gcmV0cmlldmUKICogdGhpcyBsaXN0LgogKgogKiBWZXJzaW9uIDEgb25seQogKgogKiBQYXJhbXM6CiAqICBFeGVjdXRlQnVmZmVyOiBCdWZmZXIgdG8gZXhlY3V0ZQogKiAgVmlld3BvcnQ6IFZpZXdwb3J0IHRvIHVzZSBmb3IgZXhlY3V0aW9uCiAqICBGbGFnczogTm9uZSBhcmUgZGVmaW5lZCwgYWNjb3JkaW5nIHRvIHRoZSBTREsKICogIFJlY3Q6IFNwZWNpZmllcyB0aGUgY29vcmRpbmF0ZXMgdG8gYmUgcGlja2VkLiBPbmx5IHgxIGFuZCB5MiBhcmUgdXNlZCwKICogICAgICAgIHgyIGFuZCB5MiBhcmUgaWdub3JlZC4KICoKICogUmV0dXJuczoKICogIEQzRF9PSyBiZWNhdXNlIGl0J3MgYSBzdHViCiAqCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIEhSRVNVTFQgV0lOQVBJCklEaXJlY3QzRERldmljZUltcGxfMV9QaWNrKElEaXJlY3QzRERldmljZSAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgIElEaXJlY3QzREV4ZWN1dGVCdWZmZXIgKkV4ZWN1dGVCdWZmZXIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgIElEaXJlY3QzRFZpZXdwb3J0ICpWaWV3cG9ydCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgRmxhZ3MsCiAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRFJFQ1QgKlJlY3QpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZSwgaWZhY2UpOwogICAgSURpcmVjdDNERXhlY3V0ZUJ1ZmZlckltcGwgKmV4ZWNidWYgPSBJQ09NX09CSkVDVChJRGlyZWN0M0RFeGVjdXRlQnVmZmVySW1wbCwgSURpcmVjdDNERXhlY3V0ZUJ1ZmZlciwgRXhlY3V0ZUJ1ZmZlcik7CiAgICBJRGlyZWN0M0RWaWV3cG9ydEltcGwgKnZwID0gSUNPTV9PQkpFQ1QoSURpcmVjdDNEVmlld3BvcnRJbXBsLCBJRGlyZWN0M0RWaWV3cG9ydDMsIFZpZXdwb3J0KTsKICAgIEZJWE1FKCIoJXApLT4oJXAsJXAsJTA4bHgsJXApOiBzdHViIVxuIiwgVGhpcywgZXhlY2J1ZiwgdnAsIEZsYWdzLCBSZWN0KTsKCiAgICByZXR1cm4gRDNEX09LOwp9CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSURpcmVjdDNERGV2aWNlOjpHZXRQaWNrUmVjb3JkcwogKgogKiBSZXRyaWV2ZXMgdGhlIHBpY2sgcmVjb3JkcyBnZW5lcmF0ZWQgYnkgSURpcmVjdDNERGV2aWNlOjpHZXRQaWNrUmVjb3JkcwogKgogKiBWZXJzaW9uIDEgb25seQogKgogKiBQYXJhbXM6CiAqICBDb3VudDogUG9pbnRlciB0byBhIERXT1JEIGNvbnRhaW5pbmcgdGhlIG51bWJlcnMgb2YgcGljayByZWNvcmRzIHRvCiAqICAgICAgICAgcmV0cmlldmUKICogIEQzRFBpY2tSZWM6IEFkZHJlc3MgdG8gc3RvcmUgdGhlIHJlc3VsdGluZyBEM0RQSUNLUkVDT1JEIGFycnkuCiAqCiAqIFJldHVybnM6CiAqICBEM0RfT0ssIGJlY2F1c2UgaXQncyBhIHN0dWIKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKSURpcmVjdDNERGV2aWNlSW1wbF8xX0dldFBpY2tSZWNvcmRzKElEaXJlY3QzRERldmljZSAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCAqQ291bnQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RQSUNLUkVDT1JEICpEM0RQaWNrUmVjKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UsIGlmYWNlKTsKICAgIEZJWE1FKCIoJXApLT4oJXAsJXApOiBzdHViIVxuIiwgVGhpcywgQ291bnQsIEQzRFBpY2tSZWMpOwoKICAgIHJldHVybiBEM0RfT0s7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0REZXZpY2U3OjpFbnVtVGV4dHVyZWZvcm1hdHMKICoKICogRW51bWVyYXRlcyB0aGUgc3VwcG9ydGVkIHRleHR1cmUgZm9ybWF0cy4gSXQgaGFzIGEgbGlzdCBvZiBhbGwgcG9zc2libGUKICogZm9ybWF0cyBhbmQgY2FsbHMgSVdpbmVEM0Q6OkNoZWNrRGV2aWNlRm9ybWF0IGZvciBlYWNoIGZvcm1hdCB0byBzZWUgaWYKICogV2luZUQzRCBzdXBwb3J0cyBpdC4gSWYgc28sIHRoZW4gaXQgaXMgcGFzc2VkIHRvIHRoZSBhcHAuCiAqCiAqIFRoaXMgaXMgZm9yIFZlcnNpb24gNyBhbmQgMywgb2xkZXIgdmVyc2lvbnMgaGF2ZSBhIGRpZmZlcmVudAogKiBjYWxsYmFjayBmdW5jdGlvbiBhbmQgdGhlaXIgb3duIGltcGxlbWVudGF0aW9uCiAqCiAqIFBhcmFtczoKICogIENhbGxiYWNrOiBDYWxsYmFjayB0byBjYWxsIGZvciBlYWNoIGVudW1lcmF0ZWQgZm9ybWF0CiAqICBBcmc6IEFyZ3VtZW50IHRvIHBhc3MgdG8gdGhlIGNhbGxiYWNrCiAqCiAqIFJldHVybnM6CiAqICBEM0RfT0sgb24gc3VjY2VzcwogKiAgRERFUlJfSU5WQUxJRFBBUkFNUyBpZiBDYWxsYmFjayA9PSBOVUxMCiAqCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIEhSRVNVTFQgV0lOQVBJCklEaXJlY3QzRERldmljZUltcGxfN19FbnVtVGV4dHVyZUZvcm1hdHMoSURpcmVjdDNERGV2aWNlNyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgTFBEM0RFTlVNUElYRUxGT1JNQVRTQ0FMTEJBQ0sgQ2FsbGJhY2ssCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdm9pZCAqQXJnKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2U3LCBpZmFjZSk7CiAgICBIUkVTVUxUIGhyOwogICAgaW50IGk7CgogICAgV0lORUQzREZPUk1BVCBGb3JtYXRMaXN0W10gPSB7CiAgICAgICAgLyogMzIgYml0ICovCiAgICAgICAgV0lORUQzREZNVF9BOFI4RzhCOCwKICAgICAgICBXSU5FRDNERk1UX1g4UjhHOEI4LAogICAgICAgIC8qIDI0IGJpdCAqLwogICAgICAgIFdJTkVEM0RGTVRfUjhHOEI4LAogICAgICAgIC8qIDE2IEJpdCAqLwogICAgICAgIFdJTkVEM0RGTVRfQTFSNUc1QjUsCiAgICAgICAgV0lORUQzREZNVF9BNFI0RzRCNCwKICAgICAgICBXSU5FRDNERk1UX1I1RzZCNSwKICAgICAgICBXSU5FRDNERk1UX1gxUjVHNUI1LAogICAgICAgIC8qIDggQml0ICovCiAgICAgICAgV0lORUQzREZNVF9SM0czQjIsCiAgICAgICAgV0lORUQzREZNVF9QOCwKICAgICAgICAvKiBGT1VSQ0MgY29kZXMgKi8KICAgICAgICBXSU5FRDNERk1UX0RYVDEsCiAgICAgICAgV0lORUQzREZNVF9EWFQzLAogICAgICAgIFdJTkVEM0RGTVRfRFhUNSwKICAgIH07CgogICAgVFJBQ0UoIiglcCktPiglcCwlcCk6IFJlbGF5XG4iLCBUaGlzLCBDYWxsYmFjaywgQXJnKTsKCiAgICBpZighQ2FsbGJhY2spCiAgICAgICAgcmV0dXJuIERERVJSX0lOVkFMSURQQVJBTVM7CgogICAgZm9yKGkgPSAwOyBpIDwgc2l6ZW9mKEZvcm1hdExpc3QpIC8gc2l6ZW9mKFdJTkVEM0RGT1JNQVQpOyBpKyspCiAgICB7CiAgICAgICAgaHIgPSBJV2luZUQzRF9DaGVja0RldmljZUZvcm1hdChUaGlzLT5kZHJhdy0+d2luZUQzRCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIDAgLyogQWRhcHRlciAqLywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIDAgLyogRGV2aWNlVHlwZSAqLywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIDAgLyogQWRhcHRlckZvcm1hdCAqLywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIDAgLyogVXNhZ2UgKi8sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAwIC8qIFJlc291cmNlVHlwZSAqLywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEZvcm1hdExpc3RbaV0pOwogICAgICAgIGlmKGhyID09IEQzRF9PSykKICAgICAgICB7CiAgICAgICAgICAgIEREUElYRUxGT1JNQVQgcGZvcm1hdDsKCiAgICAgICAgICAgIG1lbXNldCgmcGZvcm1hdCwgMCwgc2l6ZW9mKHBmb3JtYXQpKTsKICAgICAgICAgICAgcGZvcm1hdC5kd1NpemUgPSBzaXplb2YocGZvcm1hdCk7CiAgICAgICAgICAgIFBpeGVsRm9ybWF0X1dpbmVEM0R0b0REKCZwZm9ybWF0LCBGb3JtYXRMaXN0W2ldKTsKCiAgICAgICAgICAgIFRSQUNFKCJFbnVtZXJhdGluZyBXaW5lRDNERm9ybWF0ICVkXG4iLCBGb3JtYXRMaXN0W2ldKTsKICAgICAgICAgICAgaHIgPSBDYWxsYmFjaygmcGZvcm1hdCwgQXJnKTsKICAgICAgICAgICAgaWYoaHIgIT0gRERFTlVNUkVUX09LKQogICAgICAgICAgICB7CiAgICAgICAgICAgICAgICBUUkFDRSgiRm9ybWF0IGVudW1lcmF0aW9uIGNhbmNlbGxlZCBieSBhcHBsaWNhdGlvblxuIik7CiAgICAgICAgICAgICAgICByZXR1cm4gRDNEX09LOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgfQogICAgVFJBQ0UoIkVuZCBvZiBlbnVtZXJhdGlvblxuIik7CiAgICByZXR1cm4gRDNEX09LOwp9CgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8zX0VudW1UZXh0dXJlRm9ybWF0cyhJRGlyZWN0M0REZXZpY2UzICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBMUEQzREVOVU1QSVhFTEZPUk1BVFNDQUxMQkFDSyBDYWxsYmFjaywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2b2lkICpBcmcpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTMsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglcCwlcCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlNyBpbnRlcmZhY2UuXG4iLCBUaGlzLCBDYWxsYmFjaywgQXJnKTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2U3X0VudW1UZXh0dXJlRm9ybWF0cyhJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0REZXZpY2U3KSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBDYWxsYmFjaywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBBcmcpOwp9CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSURpcmVjdDNERGV2aWNlMjo6RW51bVRleHR1cmVmb3JtYXRzCiAqCiAqIEVudW1UZXh0dXJlRm9ybWF0cyBmb3IgVmVyc2lvbiAxIGFuZCAyLCBzZWUKICogSURpcmVjdDNERGV2aWNlNzo6RW51bVRleHVyZUZvcm1hdHMgZm9yIGEgbW9yZSBkZXRhaWxlZCBkZXNjcmlwdGlvbi4KICoKICogVGhpcyB2ZXJzaW9uIGhhcyBhIGRpZmZlcmVudCBjYWxsYmFjayBhbmQgZG9lcyBub3QgZW51bWVyYXRlIEZvdXJDQwogKiBmb3JtYXRzCiAqCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIEhSRVNVTFQgV0lOQVBJCklEaXJlY3QzRERldmljZUltcGxfMl9FbnVtVGV4dHVyZUZvcm1hdHMoSURpcmVjdDNERGV2aWNlMiAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgTFBEM0RFTlVNVEVYVFVSRUZPUk1BVFNDQUxMQkFDSyBDYWxsYmFjaywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2b2lkICpBcmcpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTIsIGlmYWNlKTsKICAgIEhSRVNVTFQgaHI7CiAgICBpbnQgaTsKCiAgICBXSU5FRDNERk9STUFUIEZvcm1hdExpc3RbXSA9IHsKICAgICAgICAvKiAzMiBiaXQgKi8KICAgICAgICBXSU5FRDNERk1UX0E4UjhHOEI4LAogICAgICAgIFdJTkVEM0RGTVRfWDhSOEc4QjgsCiAgICAgICAgLyogMjQgYml0ICovCiAgICAgICAgV0lORUQzREZNVF9SOEc4QjgsCiAgICAgICAgLyogMTYgQml0ICovCiAgICAgICAgV0lORUQzREZNVF9BMVI1RzVCNSwKICAgICAgICBXSU5FRDNERk1UX0E0UjRHNEI0LAogICAgICAgIFdJTkVEM0RGTVRfUjVHNkI1LAogICAgICAgIFdJTkVEM0RGTVRfWDFSNUc1QjUsCiAgICAgICAgLyogOCBCaXQgKi8KICAgICAgICBXSU5FRDNERk1UX1IzRzNCMiwKICAgICAgICBXSU5FRDNERk1UX1A4LAogICAgICAgIC8qIEZPVVJDQyBjb2RlcyAtIE5vdCBpbiB0aGlzIHZlcnNpb24qLwogICAgfTsKCiAgICBUUkFDRSgiKCVwKS0+KCVwLCVwKTogUmVsYXlcbiIsIFRoaXMsIENhbGxiYWNrLCBBcmcpOwoKICAgIGlmKCFDYWxsYmFjaykKICAgICAgICByZXR1cm4gRERFUlJfSU5WQUxJRFBBUkFNUzsKCiAgICBmb3IoaSA9IDA7IGkgPCBzaXplb2YoRm9ybWF0TGlzdCkgLyBzaXplb2YoV0lORUQzREZPUk1BVCk7IGkrKykKICAgIHsKICAgICAgICBociA9IElXaW5lRDNEX0NoZWNrRGV2aWNlRm9ybWF0KFRoaXMtPmRkcmF3LT53aW5lRDNELAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgMCAvKiBBZGFwdGVyICovLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgMCAvKiBEZXZpY2VUeXBlICovLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgMCAvKiBBZGFwdGVyRm9ybWF0ICovLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgMCAvKiBVc2FnZSAqLywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIDAgLyogUmVzb3VyY2VUeXBlICovLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRm9ybWF0TGlzdFtpXSk7CiAgICAgICAgaWYoaHIgPT0gRDNEX09LKQogICAgICAgIHsKICAgICAgICAgICAgRERTVVJGQUNFREVTQyBzZGVzYzsKCiAgICAgICAgICAgIG1lbXNldCgmc2Rlc2MsIDAsIHNpemVvZihzZGVzYykpOwogICAgICAgICAgICBzZGVzYy5kd1NpemUgPSBzaXplb2Yoc2Rlc2MpOwogICAgICAgICAgICBzZGVzYy5kd0ZsYWdzID0gRERTRF9QSVhFTEZPUk1BVCB8IEREU0RfQ0FQUzsKICAgICAgICAgICAgc2Rlc2MuZGRzQ2Fwcy5kd0NhcHMgPSBERFNDQVBTX1RFWFRVUkU7CiAgICAgICAgICAgIHNkZXNjLmRkcGZQaXhlbEZvcm1hdC5kd1NpemUgPSBzaXplb2Yoc2Rlc2MuZGRwZlBpeGVsRm9ybWF0LmR3U2l6ZSk7CiAgICAgICAgICAgIFBpeGVsRm9ybWF0X1dpbmVEM0R0b0REKCZzZGVzYy5kZHBmUGl4ZWxGb3JtYXQsIEZvcm1hdExpc3RbaV0pOwoKICAgICAgICAgICAgVFJBQ0UoIkVudW1lcmF0aW5nIFdpbmVEM0RGb3JtYXQgJWRcbiIsIEZvcm1hdExpc3RbaV0pOwogICAgICAgICAgICBociA9IENhbGxiYWNrKCZzZGVzYywgQXJnKTsKICAgICAgICAgICAgaWYoaHIgIT0gRERFTlVNUkVUX09LKQogICAgICAgICAgICB7CiAgICAgICAgICAgICAgICBUUkFDRSgiRm9ybWF0IGVudW1lcmF0aW9uIGNhbmNlbGxlZCBieSBhcHBsaWNhdGlvblxuIik7CiAgICAgICAgICAgICAgICByZXR1cm4gRDNEX09LOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgfQogICAgVFJBQ0UoIkVuZCBvZiBlbnVtZXJhdGlvblxuIik7CiAgICByZXR1cm4gRDNEX09LOwp9CgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8xX0VudW1UZXh0dXJlRm9ybWF0cyhJRGlyZWN0M0REZXZpY2UgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIExQRDNERU5VTVRFWFRVUkVGT1JNQVRTQ0FMTEJBQ0sgQ2FsbGJhY2ssCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdm9pZCAqQXJnKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglcCwlcCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlMiBpbnRlcmZhY2UuXG4iLCBUaGlzLCBDYWxsYmFjaywgQXJnKTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2UyX0VudW1UZXh0dXJlRm9ybWF0cyhJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0REZXZpY2UyKSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBDYWxsYmFjaywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBBcmcpOwp9CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSURpcmVjdDNERGV2aWNlOjpDcmVhdGVNYXRyaXgKICoKICogQ3JlYXRlcyBhIG1hdHJpeCBoYW5kbGUuIEEgaGFuZGxlIGlzIGNyZWF0ZWQgYW5kIG1lbW9yeSBmb3IgYSBEM0RNQVRSSVggaXMKICogYWxsb2NhdGVkIGZvciB0aGUgaGFuZGxlLgogKgogKiBWZXJzaW9uIDEgb25seQogKgogKiBQYXJhbXMKICogIEQzRE1hdEhhbmRsZTogQWRkcmVzcyB0byByZXR1cm4gdGhlIGhhbmRsZSBhdAogKgogKiBSZXR1cm5zOgogKiAgRDNEX09LIG9uIHN1Y2Nlc3MKICogIERERVJSX0lOVkFMSURQQVJBTVMgaWYgRDNETWF0SGFuZGxlID0gTlVMTAogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0REZXZpY2VJbXBsXzFfQ3JlYXRlTWF0cml4KElEaXJlY3QzRERldmljZSAqaWZhY2UsIEQzRE1BVFJJWEhBTkRMRSAqRDNETWF0SGFuZGxlKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UsIGlmYWNlKTsKICAgIEQzRE1BVFJJWCAqTWF0cml4OwogICAgVFJBQ0UoIiglcCktPiglcClcbiIsIFRoaXMsIEQzRE1hdEhhbmRsZSk7CgogICAgaWYoIUQzRE1hdEhhbmRsZSkKICAgICAgICByZXR1cm4gRERFUlJfSU5WQUxJRFBBUkFNUzsKCiAgICBNYXRyaXggPSBIZWFwQWxsb2MoR2V0UHJvY2Vzc0hlYXAoKSwgSEVBUF9aRVJPX01FTU9SWSwgc2l6ZW9mKEQzRE1BVFJJWCkpOwogICAgaWYoIU1hdHJpeCkKICAgIHsKICAgICAgICBFUlIoIk91dCBvZiBtZW1vcnkgd2hlbiBhbGxvY2F0aW5nIGEgRDNETUFUUklYXG4iKTsKICAgICAgICByZXR1cm4gRERFUlJfT1VUT0ZNRU1PUlk7CiAgICB9CiAgICAqRDNETWF0SGFuZGxlID0gSURpcmVjdDNERGV2aWNlSW1wbF9DcmVhdGVIYW5kbGUoVGhpcyk7CiAgICBpZighKCpEM0RNYXRIYW5kbGUpKQogICAgewogICAgICAgIEVSUigiRmFpbGVkIHRvIGNyZWF0ZSBhIG1hdHJpeCBoYW5kbGVcbiIpOwogICAgICAgIEhlYXBGcmVlKEdldFByb2Nlc3NIZWFwKCksIDAsIE1hdHJpeCk7CiAgICAgICAgcmV0dXJuIERERVJSX09VVE9GTUVNT1JZOwogICAgfQogICAgVGhpcy0+SGFuZGxlc1soRFdPUkQpICpEM0RNYXRIYW5kbGUgLSAxXS5wdHIgPSBNYXRyaXg7CiAgICBUaGlzLT5IYW5kbGVzWyhEV09SRCkgKkQzRE1hdEhhbmRsZSAtIDFdLnR5cGUgPSBERHJhd0hhbmRsZV9NYXRyaXg7CiAgICBUUkFDRSgiIHJldHVybmluZyBtYXRyaXggaGFuZGxlICVsZFxuIiwgKkQzRE1hdEhhbmRsZSk7CgogICAgcmV0dXJuIEQzRF9PSzsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTo6U2V0TWF0cml4CiAqCiAqIFNldHMgYSBtYXRyaXggZm9yIGEgbWF0cml4IGhhbmRsZS4gVGhlIG1hdHJpeCBpcyBjb3BpZWQgaW50byB0aGUgbWVtb3J5CiAqIGFsbG9jYXRlZCBmb3IgdGhlIGhhbmRsZQogKgogKiBWZXJzaW9uIDEgb25seQogKgogKiBQYXJhbXM6CiAqICBEM0RNYXRIYW5kbGU6IEhhbmRsZSB0byBzZXQgdGhlIG1hdHJpeCB0bwogKiAgRDNETWF0cml4OiBNYXRyaXggdG8gc2V0CiAqCiAqIFJldHVybnM6CiAqICBEM0RfT0sgb24gc3VjY2VzcwogKiAgRERFUlJfSU5WQUxJRFBBUkFNUyBpZiB0aGUgaGFuZGxlIG9mIHRoZSBtYXRyaXggaXMgaW52YWxpZCBvciB0aGUgbWF0cml4CiAqICAgdG8gc2V0IGlzIE5VTEwKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKSURpcmVjdDNERGV2aWNlSW1wbF8xX1NldE1hdHJpeChJRGlyZWN0M0REZXZpY2UgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRE1BVFJJWEhBTkRMRSBEM0RNYXRIYW5kbGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNETUFUUklYICpEM0RNYXRyaXgpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZSwgaWZhY2UpOwogICAgVFJBQ0UoIiglcCktPiglMDhseCwlcClcbiIsIFRoaXMsIChEV09SRCkgRDNETWF0SGFuZGxlLCBEM0RNYXRyaXgpOwoKICAgIGlmKCAoIUQzRE1hdEhhbmRsZSkgfHwgKCFEM0RNYXRyaXgpICkKICAgICAgICByZXR1cm4gRERFUlJfSU5WQUxJRFBBUkFNUzsKCiAgICBpZihEM0RNYXRIYW5kbGUgPiBUaGlzLT5udW1IYW5kbGVzKQogICAgewogICAgICAgIEVSUigiSGFuZGxlICVsZCBvdXQgb2YgcmFuZ2VcbiIsIEQzRE1hdEhhbmRsZSk7CiAgICAgICAgcmV0dXJuIERERVJSX0lOVkFMSURQQVJBTVM7CiAgICB9CiAgICBlbHNlIGlmKFRoaXMtPkhhbmRsZXNbRDNETWF0SGFuZGxlIC0gMV0udHlwZSAhPSBERHJhd0hhbmRsZV9NYXRyaXgpCiAgICB7CiAgICAgICAgRVJSKCJIYW5kbGUgJWxkIGlzIG5vdCBhIG1hdHJpeCBoYW5kbGVcbiIsIEQzRE1hdEhhbmRsZSk7CiAgICAgICAgcmV0dXJuIERERVJSX0lOVkFMSURQQVJBTVM7CiAgICB9CgogICAgaWYgKFRSQUNFX09OKGQzZDcpKQogICAgICAgIGR1bXBfRDNETUFUUklYKEQzRE1hdHJpeCk7CgogICAgKigoRDNETUFUUklYICopIFRoaXMtPkhhbmRsZXNbRDNETWF0SGFuZGxlIC0gMV0ucHRyKSA9ICpEM0RNYXRyaXg7CgogICAgcmV0dXJuIEQzRF9PSzsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTo6U2V0TWF0cml4CiAqCiAqIFJldHVybnMgdGhlIGNvbnRlbnQgb2YgYSBEM0RNQVRSSVggaGFuZGxlCiAqCiAqIFZlcnNpb24gMSBvbmx5CiAqCiAqIFBhcmFtczoKICogIEQzRE1hdEhhbmRsZTogTWF0cml4IGhhbmRsZSB0byByZWFkIHRoZSBjb250ZW50IGZyb20KICogIEQzRE1hdHJpeDogQWRkcmVzcyB0byBzdG9yZSB0aGUgY29udGVudCBhdAogKgogKiBSZXR1cm5zOgogKiAgRDNEX09LIG9uIHN1Y2Nlc3MKICogIERERVJSX0lOVkFMSURQQVJBTVMgaWYgRDNETWF0SGFuZGxlIGlzIGludmFsaWQgb3IgRDNETWF0cml4IGlzIE5VTEwKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKSURpcmVjdDNERGV2aWNlSW1wbF8xX0dldE1hdHJpeChJRGlyZWN0M0REZXZpY2UgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRE1BVFJJWEhBTkRMRSBEM0RNYXRIYW5kbGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNETUFUUklYICpEM0RNYXRyaXgpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZSwgaWZhY2UpOwogICAgVFJBQ0UoIiglcCktPiglMDhseCwlcClcbiIsIFRoaXMsIChEV09SRCkgRDNETWF0SGFuZGxlLCBEM0RNYXRyaXgpOwoKICAgIGlmKCFEM0RNYXRyaXgpCiAgICAgICAgcmV0dXJuIERERVJSX0lOVkFMSURQQVJBTVM7CiAgICBpZighRDNETWF0SGFuZGxlKQogICAgICAgIHJldHVybiBEREVSUl9JTlZBTElEUEFSQU1TOwoKICAgIGlmKEQzRE1hdEhhbmRsZSA+IFRoaXMtPm51bUhhbmRsZXMpCiAgICB7CiAgICAgICAgRVJSKCJIYW5kbGUgJWxkIG91dCBvZiByYW5nZVxuIiwgRDNETWF0SGFuZGxlKTsKICAgICAgICByZXR1cm4gRERFUlJfSU5WQUxJRFBBUkFNUzsKICAgIH0KICAgIGVsc2UgaWYoVGhpcy0+SGFuZGxlc1tEM0RNYXRIYW5kbGUgLSAxXS50eXBlICE9IEREcmF3SGFuZGxlX01hdHJpeCkKICAgIHsKICAgICAgICBFUlIoIkhhbmRsZSAlbGQgaXMgbm90IGEgbWF0cml4IGhhbmRsZVxuIiwgRDNETWF0SGFuZGxlKTsKICAgICAgICByZXR1cm4gRERFUlJfSU5WQUxJRFBBUkFNUzsKICAgIH0KCiAgICAvKiBUaGUgaGFuZGxlIGlzIHNpbXBseSBhIHBvaW50ZXIgdG8gYSBEM0RNQVRSSVggc3RydWN0dXJlICovCiAgICAqRDNETWF0cml4ID0gKigoRDNETUFUUklYICopIFRoaXMtPkhhbmRsZXNbRDNETWF0SGFuZGxlIC0gMV0ucHRyKTsKCiAgICByZXR1cm4gRDNEX09LOwp9CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSURpcmVjdDNERGV2aWNlOjpEZWxldGVNYXRyaXgKICoKICogRGVzdHJveXMgYSBNYXRyaXggaGFuZGxlLiBGcmVlcyB0aGUgbWVtb3J5IGFuZCB1bnNldHMgdGhlIGhhbmRsZSBkYXRhCiAqCiAqIFZlcnNpb24gMSBvbmx5CiAqCiAqIFBhcmFtczoKICogIEQzRE1hdEhhbmRsZTogSGFuZGxlIHRvIGRlc3Ryb3kKICoKICogUmV0dXJuczoKICogIEQzRF9PSyBvbiBzdWNjZXNzCiAqICBEREVSUl9JTlZBTElEUEFSQU1TIGlmIEQzRE1hdEhhbmRsZSBpcyBpbnZhbGlkCiAqCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIEhSRVNVTFQgV0lOQVBJCklEaXJlY3QzRERldmljZUltcGxfMV9EZWxldGVNYXRyaXgoSURpcmVjdDNERGV2aWNlICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RNQVRSSVhIQU5ETEUgRDNETWF0SGFuZGxlKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UsIGlmYWNlKTsKICAgIFRSQUNFKCIoJXApLT4oJTA4bHgpXG4iLCBUaGlzLCAoRFdPUkQpIEQzRE1hdEhhbmRsZSk7CgogICAgaWYoIUQzRE1hdEhhbmRsZSkKICAgICAgICByZXR1cm4gRERFUlJfSU5WQUxJRFBBUkFNUzsKCiAgICBpZihEM0RNYXRIYW5kbGUgPiBUaGlzLT5udW1IYW5kbGVzKQogICAgewogICAgICAgIEVSUigiSGFuZGxlICVsZCBvdXQgb2YgcmFuZ2VcbiIsIEQzRE1hdEhhbmRsZSk7CiAgICAgICAgcmV0dXJuIERERVJSX0lOVkFMSURQQVJBTVM7CiAgICB9CiAgICBlbHNlIGlmKFRoaXMtPkhhbmRsZXNbRDNETWF0SGFuZGxlIC0gMV0udHlwZSAhPSBERHJhd0hhbmRsZV9NYXRyaXgpCiAgICB7CiAgICAgICAgRVJSKCJIYW5kbGUgJWxkIGlzIG5vdCBhIG1hdHJpeCBoYW5kbGVcbiIsIEQzRE1hdEhhbmRsZSk7CiAgICAgICAgcmV0dXJuIERERVJSX0lOVkFMSURQQVJBTVM7CiAgICB9CgogICAgSGVhcEZyZWUoR2V0UHJvY2Vzc0hlYXAoKSwgMCwgVGhpcy0+SGFuZGxlc1tEM0RNYXRIYW5kbGUgLSAxXS5wdHIpOwogICAgVGhpcy0+SGFuZGxlc1tEM0RNYXRIYW5kbGUgLSAxXS5wdHIgPSBOVUxMOwogICAgVGhpcy0+SGFuZGxlc1tEM0RNYXRIYW5kbGUgLSAxXS50eXBlID0gRERyYXdIYW5kbGVfVW5rbm93bjsKCiAgICByZXR1cm4gRDNEX09LOwp9CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSURpcmVjdDNERGV2aWNlNzo6QmVnaW5TY2VuZQogKgogKiBUaGlzIG1ldGhvZCBtdXN0IGJlIGNhbGxlZCBiZWZvcmUgYW55IHJlbmRlcmluZyBpcyBwZXJmb3JtZWQuCiAqIElEaXJlY3QzRERldmljZTo6RW5kU2NlbmUgaGFzIHRvIGJlIGNhbGxlZCBhZnRlciB0aGUgc2NlbmUgaXMgY29tcGxldGUKICoKICogVmVyc2lvbiAxLCAyLCAzIGFuZCA3CiAqCiAqIFJldHVybnM6CiAqICBEM0RfT0sgb24gc3VjY2VzcywgZm9yIGRldGFpbHMgc2VlIElXaW5lRDNERGV2aWNlOjpCZWdpblNjZW5lCiAqCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIEhSRVNVTFQgV0lOQVBJCklEaXJlY3QzRERldmljZUltcGxfN19CZWdpblNjZW5lKElEaXJlY3QzRERldmljZTcgKmlmYWNlKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2U3LCBpZmFjZSk7CiAgICBUUkFDRSgiKCVwKTogUmVsYXlcbiIsIFRoaXMpOwoKICAgIHJldHVybiBJV2luZUQzRERldmljZV9CZWdpblNjZW5lKFRoaXMtPndpbmVEM0REZXZpY2UpOwp9CgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8zX0JlZ2luU2NlbmUoSURpcmVjdDNERGV2aWNlMyAqaWZhY2UpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTMsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPigpIHRodW5raW5nIHRvIElEaXJlY3QzRERldmljZTcgaW50ZXJmYWNlLlxuIiwgVGhpcyk7CiAgICByZXR1cm4gSURpcmVjdDNERGV2aWNlN19CZWdpblNjZW5lKElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTcpKTsKfQoKc3RhdGljIEhSRVNVTFQgV0lOQVBJClRodW5rX0lEaXJlY3QzRERldmljZUltcGxfMl9CZWdpblNjZW5lKElEaXJlY3QzRERldmljZTIgKmlmYWNlKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UyLCBpZmFjZSk7CiAgICBUUkFDRV8oZGRyYXdfdGh1bmspKCIoJXApLT4oKSB0aHVua2luZyB0byBJRGlyZWN0M0REZXZpY2U3IGludGVyZmFjZS5cbiIsIFRoaXMpOwogICAgcmV0dXJuIElEaXJlY3QzRERldmljZTdfQmVnaW5TY2VuZShJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0REZXZpY2U3KSk7Cn0KCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzFfQmVnaW5TY2VuZShJRGlyZWN0M0REZXZpY2UgKmlmYWNlKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPigpIHRodW5raW5nIHRvIElEaXJlY3QzRERldmljZTcgaW50ZXJmYWNlLlxuIiwgVGhpcyk7CiAgICByZXR1cm4gSURpcmVjdDNERGV2aWNlN19CZWdpblNjZW5lKElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTcpKTsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTc6OkVuZFNjZW5lCiAqCiAqIEVuZHMgYSBzY2VuZSB0aGF0IGhhcyBiZWVuIGJlZ3VuIHdpdGggSURpcmVjdDNERGV2aWNlNzo6QmVnaW5TY2VuZS4KICogVGhpcyBtZXRob2QgbXVzdCBiZSBjYWxsZWQgYWZ0ZXIgcmVuZGVyaW5nIGlzIGZpbmlzaGVkLgogKgogKiBWZXJzaW9uIDEsIDIsIDMgYW5kIDcKICoKICogUmV0dXJuczoKICogIEQzRF9PSyBvbiBzdWNjZXNzLCBmb3IgZGV0YWlscyBzZWUgSVdpbmVEM0REZXZpY2U6OkVuZFNjZW5lCiAqCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIEhSRVNVTFQgV0lOQVBJCklEaXJlY3QzRERldmljZUltcGxfN19FbmRTY2VuZShJRGlyZWN0M0REZXZpY2U3ICppZmFjZSkKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlNywgaWZhY2UpOwogICAgVFJBQ0UoIiglcCk6IFJlbGF5XG4iLCBUaGlzKTsKCiAgICBJV2luZUQzRERldmljZV9FbmRTY2VuZShUaGlzLT53aW5lRDNERGV2aWNlKTsKICAgIHJldHVybiBEM0RfT0s7Cn0KCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzNfRW5kU2NlbmUoSURpcmVjdDNERGV2aWNlMyAqaWZhY2UpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTMsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPigpIHRodW5raW5nIHRvIElEaXJlY3QzRERldmljZTcgaW50ZXJmYWNlLlxuIiwgVGhpcyk7CiAgICByZXR1cm4gSURpcmVjdDNERGV2aWNlN19FbmRTY2VuZShJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0REZXZpY2U3KSk7Cn0KCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzJfRW5kU2NlbmUoSURpcmVjdDNERGV2aWNlMiAqaWZhY2UpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTIsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPigpIHRodW5raW5nIHRvIElEaXJlY3QzRERldmljZTcgaW50ZXJmYWNlLlxuIiwgVGhpcyk7CiAgICByZXR1cm4gSURpcmVjdDNERGV2aWNlN19FbmRTY2VuZShJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0REZXZpY2U3KSk7Cn0KCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzFfRW5kU2NlbmUoSURpcmVjdDNERGV2aWNlICppZmFjZSkKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlLCBpZmFjZSk7CiAgICBUUkFDRV8oZGRyYXdfdGh1bmspKCIoJXApLT4oKSB0aHVua2luZyB0byBJRGlyZWN0M0REZXZpY2U3IGludGVyZmFjZS5cbiIsIFRoaXMpOwogICAgcmV0dXJuIElEaXJlY3QzRERldmljZTdfRW5kU2NlbmUoSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlNykpOwp9CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSURpcmVjdDNERGV2aWNlNzo6R2V0RGlyZWN0M0QKICoKICogUmV0dXJucyB0aGUgSURpcmVjdDNEKD0gaW50ZXJmYWNlIHRvIHRoZSBEaXJlY3REcmF3IG9iamVjdCkgdXNlZCB0byBjcmVhdGUKICogdGhpcyBkZXZpY2UuCiAqCiAqIFBhcmFtczoKICogIERpcmVjdDNENzogQWRkcmVzcyB0byBzdG9yZSB0aGUgaW50ZXJmYWNlIHBvaW50ZXIgYXQKICoKICogUmV0dXJuczoKICogIEQzRF9PSyBvbiBzdWNjZXNzCiAqICBEREVSUl9JTlZBTElEUEFSQU1TIGlmIERpcmVjdDNENyA9PSBOVUxMCiAqCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIEhSRVNVTFQgV0lOQVBJCklEaXJlY3QzRERldmljZUltcGxfN19HZXREaXJlY3QzRChJRGlyZWN0M0REZXZpY2U3ICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElEaXJlY3QzRDcgKipEaXJlY3QzRDcpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTcsIGlmYWNlKTsKICAgIFRSQUNFKCIoJXApLT4oJXApXG4iLCBUaGlzLCBEaXJlY3QzRDcpOwoKICAgIGlmKCFEaXJlY3QzRDcpCiAgICAgICAgcmV0dXJuIERERVJSX0lOVkFMSURQQVJBTVM7CgogICAgKkRpcmVjdDNENyA9IElDT01fSU5URVJGQUNFKFRoaXMtPmRkcmF3LCBJRGlyZWN0M0Q3KTsKICAgIElEaXJlY3QzRDdfQWRkUmVmKCpEaXJlY3QzRDcpOwoKICAgIFRSQUNFKCIgcmV0dXJuaW5nIGludGVyZmFjZSAlcFxuIiwgKkRpcmVjdDNENyk7CiAgICByZXR1cm4gRDNEX09LOwp9CgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8zX0dldERpcmVjdDNEKElEaXJlY3QzRERldmljZTMgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgSURpcmVjdDNEMyAqKkRpcmVjdDNEMykKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlMywgaWZhY2UpOwogICAgSFJFU1VMVCByZXQ7CiAgICBJRGlyZWN0M0Q3ICpyZXRfcHRyOwoKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglcCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlNyBpbnRlcmZhY2UuXG4iLCBUaGlzLCBEaXJlY3QzRDMpOwogICAgcmV0ID0gSURpcmVjdDNERGV2aWNlN19HZXREaXJlY3QzRChJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0REZXZpY2U3KSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJnJldF9wdHIpOwogICAgaWYocmV0ICE9IEQzRF9PSykKICAgICAgICByZXR1cm4gcmV0OwogICAgKkRpcmVjdDNEMyA9IENPTV9JTlRFUkZBQ0VfQ0FTVChJRGlyZWN0RHJhd0ltcGwsIElEaXJlY3QzRDcsIElEaXJlY3QzRDMsIHJldF9wdHIpOwogICAgVFJBQ0UoIiByZXR1cm5pbmcgaW50ZXJmYWNlICVwXG4iLCAqRGlyZWN0M0QzKTsKICAgIHJldHVybiBEM0RfT0s7Cn0KCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzJfR2V0RGlyZWN0M0QoSURpcmVjdDNERGV2aWNlMiAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBJRGlyZWN0M0QyICoqRGlyZWN0M0QyKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UyLCBpZmFjZSk7CiAgICBIUkVTVUxUIHJldDsKICAgIElEaXJlY3QzRDcgKnJldF9wdHI7CgogICAgVFJBQ0VfKGRkcmF3X3RodW5rKSgiKCVwKS0+KCVwKSB0aHVua2luZyB0byBJRGlyZWN0M0REZXZpY2U3IGludGVyZmFjZS5cbiIsIFRoaXMsIERpcmVjdDNEMik7CiAgICByZXQgPSBJRGlyZWN0M0REZXZpY2U3X0dldERpcmVjdDNEKElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTcpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmcmV0X3B0cik7CiAgICBpZihyZXQgIT0gRDNEX09LKQogICAgICAgIHJldHVybiByZXQ7CiAgICAqRGlyZWN0M0QyID0gQ09NX0lOVEVSRkFDRV9DQVNUKElEaXJlY3REcmF3SW1wbCwgSURpcmVjdDNENywgSURpcmVjdDNEMiwgcmV0X3B0cik7CiAgICBUUkFDRSgiIHJldHVybmluZyBpbnRlcmZhY2UgJXBcbiIsICpEaXJlY3QzRDIpOwogICAgcmV0dXJuIEQzRF9PSzsKfQoKc3RhdGljIEhSRVNVTFQgV0lOQVBJClRodW5rX0lEaXJlY3QzRERldmljZUltcGxfMV9HZXREaXJlY3QzRChJRGlyZWN0M0REZXZpY2UgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgSURpcmVjdDNEICoqRGlyZWN0M0QpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZSwgaWZhY2UpOwogICAgSFJFU1VMVCByZXQ7CiAgICBJRGlyZWN0M0Q3ICpyZXRfcHRyOwoKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglcCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlNyBpbnRlcmZhY2UuXG4iLCBUaGlzLCBEaXJlY3QzRCk7CiAgICByZXQgPSBJRGlyZWN0M0REZXZpY2U3X0dldERpcmVjdDNEKElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTcpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmcmV0X3B0cik7CiAgICBpZihyZXQgIT0gRDNEX09LKQogICAgICAgIHJldHVybiByZXQ7CiAgICAqRGlyZWN0M0QgPSBDT01fSU5URVJGQUNFX0NBU1QoSURpcmVjdERyYXdJbXBsLCBJRGlyZWN0M0Q3LCBJRGlyZWN0M0QsIHJldF9wdHIpOwogICAgVFJBQ0UoIiByZXR1cm5pbmcgaW50ZXJmYWNlICVwXG4iLCAqRGlyZWN0M0QpOwogICAgcmV0dXJuIEQzRF9PSzsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTM6OlNldEN1cnJlbnRWaWV3cG9ydAogKgogKiBTZXRzIGEgRGlyZWN0M0RWaWV3cG9ydCBhcyB0aGUgY3VycmVudCB2aWV3cG9ydC4KICogRm9yIHRoZSB0aHVua3Mgbm90ZSB0aGF0IGFsbCB2aWV3cG9ydCBpbnRlcmZhY2UgdmVyc2lvbnMgYXJlIGVxdWFsCiAqCiAqIFBhcmFtczoKICogIERpcmVjdDNEVmlld3BvcnQzOiBUaGUgdmlld3BvcnQgdG8gc2V0CiAqCiAqIFZlcnNpb24gMiBhbmQgMwogKgogKiBSZXR1cm5zOgogKiAgRDNEX09LIG9uIHN1Y2Nlc3MKICogIChJcyBhIE5VTEwgdmlld3BvcnQgdmFsaWQ/KQogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0REZXZpY2VJbXBsXzNfU2V0Q3VycmVudFZpZXdwb3J0KElEaXJlY3QzRERldmljZTMgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElEaXJlY3QzRFZpZXdwb3J0MyAqRGlyZWN0M0RWaWV3cG9ydDMpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTMsIGlmYWNlKTsKICAgIElEaXJlY3QzRFZpZXdwb3J0SW1wbCAqdnAgPSBJQ09NX09CSkVDVChJRGlyZWN0M0RWaWV3cG9ydEltcGwsIElEaXJlY3QzRFZpZXdwb3J0MywgRGlyZWN0M0RWaWV3cG9ydDMpOwogICAgVFJBQ0UoIiglcCktPiglcClcbiIsIFRoaXMsIERpcmVjdDNEVmlld3BvcnQzKTsKCiAgICAvKiBEbyBub3RoaW5nIGlmIHRoZSBzcGVjaWZpZWQgdmlld3BvcnQgaXMgdGhlIHNhbWUgYXMgdGhlIGN1cnJlbnQgb25lICovCiAgICBpZiAoVGhpcy0+Y3VycmVudF92aWV3cG9ydCA9PSB2cCApCiAgICAgIHJldHVybiBEM0RfT0s7CgogICAgLyogU2hvdWxkIGNoZWNrIGlmIHRoZSB2aWV3cG9ydCB3YXMgYWRkZWQgb3Igbm90ICovCgogICAgLyogUmVsZWFzZSBwcmV2aW91cyB2aWV3cG9ydCBhbmQgQWRkUmVmIHRoZSBuZXcgb25lICovCiAgICBpZiAoVGhpcy0+Y3VycmVudF92aWV3cG9ydCkKICAgIHsKICAgICAgICBUUkFDRSgiVmlld3BvcnRJbXBsIGlzIGF0ICVwLCBpbnRlcmZhY2UgaXMgYXQgJXBcbiIsIFRoaXMtPmN1cnJlbnRfdmlld3BvcnQsIElDT01fSU5URVJGQUNFKFRoaXMtPmN1cnJlbnRfdmlld3BvcnQsIElEaXJlY3QzRFZpZXdwb3J0MykpOwogICAgICAgIElEaXJlY3QzRFZpZXdwb3J0M19SZWxlYXNlKCBJQ09NX0lOVEVSRkFDRShUaGlzLT5jdXJyZW50X3ZpZXdwb3J0LCBJRGlyZWN0M0RWaWV3cG9ydDMpICk7CiAgICB9CiAgICBJRGlyZWN0M0RWaWV3cG9ydDNfQWRkUmVmKERpcmVjdDNEVmlld3BvcnQzKTsKCiAgICAvKiBTZXQgdGhpcyB2aWV3cG9ydCBhcyB0aGUgY3VycmVudCB2aWV3cG9ydCAqLwogICAgVGhpcy0+Y3VycmVudF92aWV3cG9ydCA9IHZwOwoKICAgIC8qIEFjdGl2YXRlIHRoaXMgdmlld3BvcnQgKi8KICAgIFRoaXMtPmN1cnJlbnRfdmlld3BvcnQtPmFjdGl2ZV9kZXZpY2UgPSBUaGlzOwogICAgVGhpcy0+Y3VycmVudF92aWV3cG9ydC0+YWN0aXZhdGUoVGhpcy0+Y3VycmVudF92aWV3cG9ydCk7CgogICAgcmV0dXJuIEQzRF9PSzsKfQoKc3RhdGljIEhSRVNVTFQgV0lOQVBJClRodW5rX0lEaXJlY3QzRERldmljZUltcGxfMl9TZXRDdXJyZW50Vmlld3BvcnQoSURpcmVjdDNERGV2aWNlMiAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgSURpcmVjdDNEVmlld3BvcnQyICpEaXJlY3QzRFZpZXdwb3J0MikKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlMiwgaWZhY2UpOwogICAgSURpcmVjdDNEVmlld3BvcnRJbXBsICp2cCA9IElDT01fT0JKRUNUKElEaXJlY3QzRFZpZXdwb3J0SW1wbCwgSURpcmVjdDNEVmlld3BvcnQzLCBEaXJlY3QzRFZpZXdwb3J0Mik7CiAgICBUUkFDRV8oZGRyYXdfdGh1bmspKCIoJXApLT4oJXApIHRodW5raW5nIHRvIElEaXJlY3QzRERldmljZTMgaW50ZXJmYWNlLlxuIiwgVGhpcywgdnApOwogICAgcmV0dXJuIElEaXJlY3QzRERldmljZTNfU2V0Q3VycmVudFZpZXdwb3J0KElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTMpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElDT01fSU5URVJGQUNFKHZwLCBJRGlyZWN0M0RWaWV3cG9ydDMpKTsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTM6OkdldEN1cnJlbnRWaWV3cG9ydAogKgogKiBSZXR1cm5zIHRoZSBjdXJyZW50bHkgYWN0aXZlIHZpZXdwb3J0LgogKgogKiBWZXJzaW9uIDIgYW5kIDMKICoKICogUGFyYW1zOgogKiAgRGlyZWN0M0RWaWV3cG9ydDM6IEFkZHJlc3MgdG8gcmV0dXJuIHRoZSBpbnRlcmZhY2UgcG9pbnRlciBhdAogKgogKiBSZXR1cm5zOgogKiAgRDNEX09LIG9uIHN1Y2Nlc3MKICogIERERVJSX0lOVkFMSURQQVJBTVMgaWYgRGlyZWN0M0RWaWV3cG9ydCA9PSBOVUxMCiAqCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIEhSRVNVTFQgV0lOQVBJCklEaXJlY3QzRERldmljZUltcGxfM19HZXRDdXJyZW50Vmlld3BvcnQoSURpcmVjdDNERGV2aWNlMyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgSURpcmVjdDNEVmlld3BvcnQzICoqRGlyZWN0M0RWaWV3cG9ydDMpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTMsIGlmYWNlKTsKICAgIFRSQUNFKCIoJXApLT4oJXApXG4iLCBUaGlzLCBEaXJlY3QzRFZpZXdwb3J0Myk7CgogICAgaWYoIURpcmVjdDNEVmlld3BvcnQzKQogICAgICAgIHJldHVybiBEREVSUl9JTlZBTElEUEFSQU1TOwoKICAgICpEaXJlY3QzRFZpZXdwb3J0MyA9IElDT01fSU5URVJGQUNFKFRoaXMtPmN1cnJlbnRfdmlld3BvcnQsIElEaXJlY3QzRFZpZXdwb3J0Myk7CgogICAgLyogQWRkUmVmIHRoZSByZXR1cm5lZCB2aWV3cG9ydCAqLwogICAgaWYoKkRpcmVjdDNEVmlld3BvcnQzKSBJRGlyZWN0M0RWaWV3cG9ydDNfQWRkUmVmKCpEaXJlY3QzRFZpZXdwb3J0Myk7CgogICAgVFJBQ0UoIiByZXR1cm5pbmcgaW50ZXJmYWNlICVwXG4iLCAqRGlyZWN0M0RWaWV3cG9ydDMpOwoKICAgIHJldHVybiBEM0RfT0s7Cn0KCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzJfR2V0Q3VycmVudFZpZXdwb3J0KElEaXJlY3QzRERldmljZTIgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElEaXJlY3QzRFZpZXdwb3J0MiAqKkRpcmVjdDNEVmlld3BvcnQyKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UzLCBpZmFjZSk7CiAgICBIUkVTVUxUIGhyOwogICAgVFJBQ0VfKGRkcmF3X3RodW5rKSgiKCVwKS0+KCVwKSB0aHVua2luZyB0byBJRGlyZWN0M0REZXZpY2UzIGludGVyZmFjZS5cbiIsIFRoaXMsIERpcmVjdDNEVmlld3BvcnQyKTsKICAgIGhyID0gSURpcmVjdDNERGV2aWNlM19HZXRDdXJyZW50Vmlld3BvcnQoSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlMyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKElEaXJlY3QzRFZpZXdwb3J0MyAqKikgRGlyZWN0M0RWaWV3cG9ydDIpOwogICAgaWYoaHIgIT0gRDNEX09LKSByZXR1cm4gaHI7CiAgICAqRGlyZWN0M0RWaWV3cG9ydDIgPSAoSURpcmVjdDNEVmlld3BvcnQyICopIENPTV9JTlRFUkZBQ0VfQ0FTVChJRGlyZWN0M0RWaWV3cG9ydEltcGwsIElEaXJlY3QzRFZpZXdwb3J0MywgSURpcmVjdDNEVmlld3BvcnQzLCBEaXJlY3QzRFZpZXdwb3J0Mik7CiAgICByZXR1cm4gRDNEX09LOwp9CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSURpcmVjdDNERGV2aWNlNzo6U2V0UmVuZGVyVGFyZ2V0CiAqCiAqIFNldHMgdGhlIHJlbmRlciB0YXJnZXQgZm9yIHRoZSBEaXJlY3QzRERldmljZS4KICogRm9yIHRoZSB0aHVua3Mgbm90ZSB0aGF0IElEaXJlY3REcmF3U3VyZmFjZTcgPT0gSURpcmVjdERyYXdTdXJmYWNlNCBhbmQKICogSURpcmVjdERyYXdTdXJmYWNlMyA9PSBJRGlyZWN0RHJhd1N1cmZhY2UKICoKICogVmVyc2lvbiAyLCAzIGFuZCA3CiAqCiAqIFBhcmFtczoKICogIE5ld1RhcmdldDogUG9pbnRlciB0byBhbiBJRGlyZWN0RHJhd1N1cmZhY2U3IGludGVyZmFjZSB0byBzZXQgYXMgdGhlIG5ldwogKiAgICAgICAgICAgICByZW5kZXIgdGFyZ2V0CiAqICBGbGFnczogU29tZSBmbGFncwogKgogKiBSZXR1cm5zOgogKiAgRDNEX09LIG9uIHN1Y2Nlc3MsIGZvciBkZXRhaWxzIHNlZSBJV2luZUQzRERldmljZTo6U2V0UmVuZGVyVGFyZ2V0CiAqCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIEhSRVNVTFQgV0lOQVBJCklEaXJlY3QzRERldmljZUltcGxfN19TZXRSZW5kZXJUYXJnZXQoSURpcmVjdDNERGV2aWNlNyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgSURpcmVjdERyYXdTdXJmYWNlNyAqTmV3VGFyZ2V0LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIEZsYWdzKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2U3LCBpZmFjZSk7CiAgICBJRGlyZWN0RHJhd1N1cmZhY2VJbXBsICpUYXJnZXQgPSBJQ09NX09CSkVDVChJRGlyZWN0RHJhd1N1cmZhY2VJbXBsLCBJRGlyZWN0RHJhd1N1cmZhY2U3LCBOZXdUYXJnZXQpOwogICAgVFJBQ0UoIiglcCktPiglcCwlMDhseCk6IFJlbGF5XG4iLCBUaGlzLCBOZXdUYXJnZXQsIEZsYWdzKTsKCiAgICAvKiBGbGFnczogTm90IHVzZWQgKi8KCiAgICByZXR1cm4gSVdpbmVEM0REZXZpY2VfU2V0UmVuZGVyVGFyZ2V0KFRoaXMtPndpbmVEM0REZXZpY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIDAsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFRhcmdldCA/IFRhcmdldC0+V2luZUQzRFN1cmZhY2UgOiBOVUxMKTsKfQoKc3RhdGljIEhSRVNVTFQgV0lOQVBJClRodW5rX0lEaXJlY3QzRERldmljZUltcGxfM19TZXRSZW5kZXJUYXJnZXQoSURpcmVjdDNERGV2aWNlMyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgSURpcmVjdERyYXdTdXJmYWNlNCAqTmV3UmVuZGVyVGFyZ2V0LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIEZsYWdzKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UzLCBpZmFjZSk7CiAgICBJRGlyZWN0RHJhd1N1cmZhY2VJbXBsICpUYXJnZXQgPSBJQ09NX09CSkVDVChJRGlyZWN0RHJhd1N1cmZhY2VJbXBsLCBJRGlyZWN0RHJhd1N1cmZhY2U3LCBOZXdSZW5kZXJUYXJnZXQpOwogICAgVFJBQ0VfKGRkcmF3X3RodW5rKSgiKCVwKS0+KCVwLCUwOGx4KSB0aHVua2luZyB0byBJRGlyZWN0M0REZXZpY2U3IGludGVyZmFjZS5cbiIsIFRoaXMsIFRhcmdldCwgRmxhZ3MpOwogICAgcmV0dXJuIElEaXJlY3QzRERldmljZTdfU2V0UmVuZGVyVGFyZ2V0KElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTcpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElDT01fSU5URVJGQUNFKFRhcmdldCwgSURpcmVjdERyYXdTdXJmYWNlNyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRmxhZ3MpOwp9CgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8yX1NldFJlbmRlclRhcmdldChJRGlyZWN0M0REZXZpY2UyICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBJRGlyZWN0RHJhd1N1cmZhY2UgKk5ld1JlbmRlclRhcmdldCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBGbGFncykKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlMiwgaWZhY2UpOwogICAgSURpcmVjdERyYXdTdXJmYWNlSW1wbCAqVGFyZ2V0ID0gSUNPTV9PQkpFQ1QoSURpcmVjdERyYXdTdXJmYWNlSW1wbCwgSURpcmVjdERyYXdTdXJmYWNlMywgTmV3UmVuZGVyVGFyZ2V0KTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglcCwlMDhseCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlNyBpbnRlcmZhY2UuXG4iLCBUaGlzLCBUYXJnZXQsIEZsYWdzKTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2U3X1NldFJlbmRlclRhcmdldChJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0REZXZpY2U3KSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBJQ09NX0lOVEVSRkFDRShUYXJnZXQsIElEaXJlY3REcmF3U3VyZmFjZTcpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEZsYWdzKTsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTc6OkdldFJlbmRlclRhcmdldAogKgogKiBSZXR1cm5zIHRoZSBjdXJyZW50IHJlbmRlciB0YXJnZXQuCiAqIFRoaXMgaXMgaGFuZGxlZCBsb2NhbGx5LCBiZWNhdXNlIHRoZSBXaW5lRDNEIHJlbmRlciB0YXJnZXQncyBwYXJlbnQKICogaXMgYW4gSVBhcmVudAogKgogKiBWZXJzaW9uIDIsIDMgYW5kIDcKICoKICogUGFyYW1zOgogKiAgUmVuZGVyVGFyZ2V0OiBBZGRyZXNzIHRvIHN0b3JlIHRoZSBzdXJmYWNlIGludGVyZmFjZSBwb2ludGVyCiAqCiAqIFJldHVybnM6CiAqICBEM0RfT0sgb24gc3VjY2VzcwogKiAgRERFUlJfSU5WQUxJRFBBUkFNUyBpZiBSZW5kZXJUYXJnZXQgPT0gTlVMTAogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0REZXZpY2VJbXBsXzdfR2V0UmVuZGVyVGFyZ2V0KElEaXJlY3QzRERldmljZTcgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElEaXJlY3REcmF3U3VyZmFjZTcgKipSZW5kZXJUYXJnZXQpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTcsIGlmYWNlKTsKICAgIFRSQUNFKCIoJXApLT4oJXApOiBSZWxheVxuIiwgVGhpcywgUmVuZGVyVGFyZ2V0KTsKCiAgICBpZighUmVuZGVyVGFyZ2V0KQogICAgICAgIHJldHVybiBEREVSUl9JTlZBTElEUEFSQU1TOwoKICAgICpSZW5kZXJUYXJnZXQgPSBJQ09NX0lOVEVSRkFDRShUaGlzLT50YXJnZXQsIElEaXJlY3REcmF3U3VyZmFjZTcpOwogICAgSURpcmVjdERyYXdTdXJmYWNlN19BZGRSZWYoKlJlbmRlclRhcmdldCk7CgogICAgcmV0dXJuIEQzRF9PSzsKfQoKc3RhdGljIEhSRVNVTFQgV0lOQVBJClRodW5rX0lEaXJlY3QzRERldmljZUltcGxfM19HZXRSZW5kZXJUYXJnZXQoSURpcmVjdDNERGV2aWNlMyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgSURpcmVjdERyYXdTdXJmYWNlNCAqKlJlbmRlclRhcmdldCkKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlMywgaWZhY2UpOwogICAgSFJFU1VMVCBocjsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglcCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlNyBpbnRlcmZhY2UuXG4iLCBUaGlzLCBSZW5kZXJUYXJnZXQpOwogICAgaHIgPSBJRGlyZWN0M0REZXZpY2U3X0dldFJlbmRlclRhcmdldChJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0REZXZpY2U3KSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKElEaXJlY3REcmF3U3VyZmFjZTcgKiopIFJlbmRlclRhcmdldCk7CiAgICBpZihociAhPSBEM0RfT0spIHJldHVybiBocjsKICAgICpSZW5kZXJUYXJnZXQgPSAoSURpcmVjdERyYXdTdXJmYWNlNCAqKSBDT01fSU5URVJGQUNFX0NBU1QoSURpcmVjdERyYXdTdXJmYWNlSW1wbCwgSURpcmVjdERyYXdTdXJmYWNlNywgSURpcmVjdERyYXdTdXJmYWNlNywgUmVuZGVyVGFyZ2V0KTsKICAgIHJldHVybiBEM0RfT0s7Cn0KCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzJfR2V0UmVuZGVyVGFyZ2V0KElEaXJlY3QzRERldmljZTIgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElEaXJlY3REcmF3U3VyZmFjZSAqKlJlbmRlclRhcmdldCkKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlMiwgaWZhY2UpOwogICAgSFJFU1VMVCBocjsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglcCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlNyBpbnRlcmZhY2UuXG4iLCBUaGlzLCBSZW5kZXJUYXJnZXQpOwogICAgaHIgPSBJRGlyZWN0M0REZXZpY2U3X0dldFJlbmRlclRhcmdldChJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0REZXZpY2U3KSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKElEaXJlY3REcmF3U3VyZmFjZTcgKiopIFJlbmRlclRhcmdldCk7CiAgICBpZihociAhPSBEM0RfT0spIHJldHVybiBocjsKICAgICpSZW5kZXJUYXJnZXQgPSAoSURpcmVjdERyYXdTdXJmYWNlICopIENPTV9JTlRFUkZBQ0VfQ0FTVChJRGlyZWN0RHJhd1N1cmZhY2VJbXBsLCBJRGlyZWN0RHJhd1N1cmZhY2U3LCBJRGlyZWN0RHJhd1N1cmZhY2UzLCBSZW5kZXJUYXJnZXQpOwogICAgcmV0dXJuIEQzRF9PSzsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTM6OkJlZ2luCiAqCiAqIEJlZ2lucyBhIGRlc2NyaXB0aW9uIGJsb2NrIG9mIHZlcnRpY2VzLiBUaGlzIGlzIHNpbWlsYXIgdG8gZ2xCZWdpbigpCiAqIGFuZCBnbEVuZCgpLiBBZnRlciBhIGNhbGwgdG8gSURpcmVjdDNERGV2aWNlMzo6RW5kLCB0aGUgdmVydGljZXMKICogZGVzY3JpYmVkIHdpdGggSURpcmVjdDNERGV2aWNlOjpWZXJ0ZXggYXJlIGRyYXduLgogKgogKiBWZXJzaW9uIDIgYW5kIDMKICoKICogUGFyYW1zOgogKiAgUHJpbWl0aXZlVHlwZTogVGhlIHR5cGUgb2YgcHJpbWl0aXZlcyB0byBkcmF3CiAqICBWZXJ0ZXhUeXBlRGVzYzogQSBmbGV4aWJsZSB2ZXJ0ZXggZm9ybWF0IGRlc2NyaXB0aW9uIG9mIHRoZSB2ZXJ0aWNlcwogKiAgRmxhZ3M6IFNvbWUgZmxhZ3MuLgogKgogKiBSZXR1cm5zOgogKiAgRDNEX09LIG9uIHN1Y2Nlc3MKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKSURpcmVjdDNERGV2aWNlSW1wbF8zX0JlZ2luKElEaXJlY3QzRERldmljZTMgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNEUFJJTUlUSVZFVFlQRSBQcmltaXRpdmVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgVmVydGV4VHlwZURlc2MsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBGbGFncykKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlMywgaWZhY2UpOwogICAgVFJBQ0UoIiglcCktPiglZCwlbGQsJTA4bHgpXG4iLCBUaGlzLCBQcmltaXRpdmVUeXBlLCBWZXJ0ZXhUeXBlRGVzYywgRmxhZ3MpOwoKICAgIFRoaXMtPnByaW1pdGl2ZV90eXBlID0gUHJpbWl0aXZlVHlwZTsKICAgIFRoaXMtPnZlcnRleF90eXBlID0gVmVydGV4VHlwZURlc2M7CiAgICBUaGlzLT5yZW5kZXJfZmxhZ3MgPSBGbGFnczsKICAgIFRoaXMtPnZlcnRleF9zaXplID0gZ2V0X2ZsZXhpYmxlX3ZlcnRleF9zaXplKFRoaXMtPnZlcnRleF90eXBlKTsKICAgIFRoaXMtPm5iX3ZlcnRpY2VzID0gMDsKCiAgICByZXR1cm4gRDNEX09LOwp9CgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8yX0JlZ2luKElEaXJlY3QzRERldmljZTIgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNEUFJJTUlUSVZFVFlQRSBkM2RwdCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRFZFUlRFWFRZUEUgZHdWZXJ0ZXhUeXBlRGVzYywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIGR3RmxhZ3MpCnsKICAgIERXT1JEIEZWRjsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTIsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcC8lcCktPiglMDh4LCUwOHgsJTA4bHgpOiBUaHVua2luZyB0byBJRGlyZWN0M0REZXZpY2UzXG4iLCBUaGlzLCBpZmFjZSwgZDNkcHQsIGR3VmVydGV4VHlwZURlc2MsIGR3RmxhZ3MpOwoKICAgIHN3aXRjaChkd1ZlcnRleFR5cGVEZXNjKQogICAgewogICAgICAgIGNhc2UgRDNEVlRfVkVSVEVYOiBGVkYgPSBEM0RGVkZfVkVSVEVYOyBicmVhazsKICAgICAgICBjYXNlIEQzRFZUX0xWRVJURVg6IEZWRiA9IEQzREZWRl9MVkVSVEVYOyBicmVhazsKICAgICAgICBjYXNlIEQzRFZUX1RMVkVSVEVYOiBGVkYgPSBEM0RGVkZfVExWRVJURVg7IGJyZWFrOwogICAgICAgIGRlZmF1bHQ6CiAgICAgICAgICAgIEVSUigiVW5leHBlY3RlZCB2ZXJ0ZXggdHlwZSAlZFxuIiwgZHdWZXJ0ZXhUeXBlRGVzYyk7CiAgICAgICAgICAgIHJldHVybiBEREVSUl9JTlZBTElEUEFSQU1TOyAgLyogU2hvdWxkIG5ldmVyIGhhcHBlbiAqLwogICAgfTsKCiAgICByZXR1cm4gSURpcmVjdDNERGV2aWNlM19CZWdpbihJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0REZXZpY2UzKSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGQzZHB0LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRlZGLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZHdGbGFncyk7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0REZXZpY2UzOjpCZWdpbkluZGV4ZWQKICoKICogRHJhd3MgcHJpbWl0aXZlcyBiYXNlZCBvbiB2ZXJ0aWNlcyBpbiBhIHZlcnRleCBhcnJheSB3aGljaCBhcmUgc3BlY2lmaWVkCiAqIGJ5IGluZGljZXMuCiAqCiAqIFZlcnNpb24gMiBhbmQgMwogKgogKiBQYXJhbXM6CiAqICBQcmltaXRpdmVUeXBlOiBQcmltaXRpdmUgdHlwZSB0byBkcmF3CiAqICBWZXJ0ZXhUeXBlOiBBIEZWRiBkZXNjcmlwdGlvbiBvZiB0aGUgdmVydGV4IGZvcm1hdAogKiAgVmVydGljZXM6IHBvaW50ZXIgdG8gYW4gYXJyYXkgY29udGFpbmluZyB0aGUgdmVydGljZXMKICogIE51bVZlcnRpY2VzOiBUaGUgbnVtYmVyIG9mIHZlcnRpY2VzIGluIHRoZSB2ZXJ0ZXggYXJyYXkKICogIEZsYWdzOiBTb21lIGZsYWdzIC4uLgogKgogKiBSZXR1cm5zOgogKiAgRDNEX09LLCBiZWNhdXNlIGl0J3MgYSBzdHViCiAqCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIEhSRVNVTFQgV0lOQVBJCklEaXJlY3QzRERldmljZUltcGxfM19CZWdpbkluZGV4ZWQoSURpcmVjdDNERGV2aWNlMyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNEUFJJTUlUSVZFVFlQRSBQcmltaXRpdmVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIFZlcnRleFR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdm9pZCAqVmVydGljZXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgTnVtVmVydGljZXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgRmxhZ3MpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTMsIGlmYWNlKTsKICAgIEZJWE1FKCIoJXApLT4oJTA4eCwlMDhseCwlcCwlMDhseCwlMDhseCk6IHN0dWIhXG4iLCBUaGlzLCBQcmltaXRpdmVUeXBlLCBWZXJ0ZXhUeXBlLCBWZXJ0aWNlcywgTnVtVmVydGljZXMsIEZsYWdzKTsKICAgIHJldHVybiBEM0RfT0s7Cn0KCgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8yX0JlZ2luSW5kZXhlZChJRGlyZWN0M0REZXZpY2UyICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RQUklNSVRJVkVUWVBFIGQzZHB0UHJpbWl0aXZlVHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RWRVJURVhUWVBFIGQzZHZ0VmVydGV4VHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2b2lkICpscHZWZXJ0aWNlcywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBkd051bVZlcnRpY2VzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIGR3RmxhZ3MpCnsKICAgIERXT1JEIEZWRjsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTIsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcC8lcCktPiglMDh4LCUwOHgsJXAsJTA4bHgsJTA4bHgpOiBUaHVua2luZyB0byBJRGlyZWN0M0REZXZpY2UzXG4iLCBUaGlzLCBpZmFjZSwgZDNkcHRQcmltaXRpdmVUeXBlLCBkM2R2dFZlcnRleFR5cGUsIGxwdlZlcnRpY2VzLCBkd051bVZlcnRpY2VzLCBkd0ZsYWdzKTsKCiAgICBzd2l0Y2goZDNkdnRWZXJ0ZXhUeXBlKQogICAgewogICAgICAgIGNhc2UgRDNEVlRfVkVSVEVYOiBGVkYgPSBEM0RGVkZfVkVSVEVYOyBicmVhazsKICAgICAgICBjYXNlIEQzRFZUX0xWRVJURVg6IEZWRiA9IEQzREZWRl9MVkVSVEVYOyBicmVhazsKICAgICAgICBjYXNlIEQzRFZUX1RMVkVSVEVYOiBGVkYgPSBEM0RGVkZfVExWRVJURVg7IGJyZWFrOwogICAgICAgIGRlZmF1bHQ6CiAgICAgICAgICAgIEVSUigiVW5leHBlY3RlZCB2ZXJ0ZXggdHlwZSAlZFxuIiwgZDNkdnRWZXJ0ZXhUeXBlKTsKICAgICAgICAgICAgcmV0dXJuIERERVJSX0lOVkFMSURQQVJBTVM7ICAvKiBTaG91bGQgbmV2ZXIgaGFwcGVuICovCiAgICB9OwoKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2UzX0JlZ2luSW5kZXhlZChJQ09NX0lOVEVSRkFDRShUaGlzLElEaXJlY3QzRERldmljZTMpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGQzZHB0UHJpbWl0aXZlVHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBGVkYsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgbHB2VmVydGljZXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZHdOdW1WZXJ0aWNlcywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBkd0ZsYWdzKTsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTM6OlZlcnRleAogKgogKiBEcmF3cyBhIHZlcnRleCBhcyBkZXNjcmliZWQgYnkgSURpcmVjdDNERGV2aWNlMzo6QmVnaW4uIEl0IHBsYWNlcyBhbGwKICogZHJhd24gdmVydGljZXMgaW4gYSB2ZXJ0ZXggYnVmZmVyLiBJZiB0aGUgYnVmZmVyIGlzIHRvbyBzbWFsbCwgaXRzCiAqIHNpemUgaXMgaW5jcmVhc2VkLgogKgogKiBWZXJzaW9uIDIgYW5kIDMKICoKICogUGFyYW1zOgogKiAgVmVydGV4OiBQb2ludGVyIHRvIHRoZSB2ZXJ0ZXgKICoKICogUmV0dXJuczoKICogIEQzRF9PSywgb24gc3VjY2VzcwogKiAgRERFUlJfSU5WQUxJRFBBUkFNUyBpZiBWZXJ0ZXggaXMgTlVMTAogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0REZXZpY2VJbXBsXzNfVmVydGV4KElEaXJlY3QzRERldmljZTMgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgIHZvaWQgKlZlcnRleCkKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlMywgaWZhY2UpOwogICAgVFJBQ0UoIiglcCktPiglcClcbiIsIFRoaXMsIFZlcnRleCk7CgogICAgaWYoIVZlcnRleCkKICAgICAgICByZXR1cm4gRERFUlJfSU5WQUxJRFBBUkFNUzsKCiAgICBpZiAoKFRoaXMtPm5iX3ZlcnRpY2VzKzEpKlRoaXMtPnZlcnRleF9zaXplID4gVGhpcy0+YnVmZmVyX3NpemUpCiAgICB7CiAgICAgICAgQllURSAqb2xkX2J1ZmZlcjsKICAgICAgICBUaGlzLT5idWZmZXJfc2l6ZSA9IFRoaXMtPmJ1ZmZlcl9zaXplID8gVGhpcy0+YnVmZmVyX3NpemUgKiAyIDogVGhpcy0+dmVydGV4X3NpemUgKiAzOwogICAgICAgIG9sZF9idWZmZXIgPSBUaGlzLT52ZXJ0ZXhfYnVmZmVyOwogICAgICAgIFRoaXMtPnZlcnRleF9idWZmZXIgPSBIZWFwQWxsb2MoR2V0UHJvY2Vzc0hlYXAoKSwgMCwgVGhpcy0+YnVmZmVyX3NpemUpOwogICAgICAgIGlmIChvbGRfYnVmZmVyKQogICAgICAgIHsKICAgICAgICAgICAgQ29weU1lbW9yeShUaGlzLT52ZXJ0ZXhfYnVmZmVyLCBvbGRfYnVmZmVyLCBUaGlzLT5uYl92ZXJ0aWNlcyAqIFRoaXMtPnZlcnRleF9zaXplKTsKICAgICAgICAgICAgSGVhcEZyZWUoR2V0UHJvY2Vzc0hlYXAoKSwgMCwgb2xkX2J1ZmZlcik7CiAgICAgICAgfQogICAgfQoKICAgIENvcHlNZW1vcnkoVGhpcy0+dmVydGV4X2J1ZmZlciArIFRoaXMtPm5iX3ZlcnRpY2VzKysgKiBUaGlzLT52ZXJ0ZXhfc2l6ZSwgVmVydGV4LCBUaGlzLT52ZXJ0ZXhfc2l6ZSk7CgogICAgcmV0dXJuIEQzRF9PSzsKfQoKc3RhdGljIEhSRVNVTFQgV0lOQVBJClRodW5rX0lEaXJlY3QzRERldmljZUltcGxfMl9WZXJ0ZXgoSURpcmVjdDNERGV2aWNlMiAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdm9pZCAqbHBWZXJ0ZXhUeXBlKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UyLCBpZmFjZSk7CiAgICBUUkFDRV8oZGRyYXdfdGh1bmspKCIoJXApLT4oJXApIHRodW5raW5nIHRvIElEaXJlY3QzRERldmljZTMgaW50ZXJmYWNlLlxuIiwgVGhpcywgbHBWZXJ0ZXhUeXBlKTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2UzX1ZlcnRleChJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0REZXZpY2UzKSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBscFZlcnRleFR5cGUpOwp9CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSURpcmVjdDNERGV2aWNlMzo6SW5kZXgKICoKICogU3BlY2lmaWVzIGFuIGluZGV4IHRvIGEgdmVydGV4IHRvIGJlIGRyYXduLiBUaGUgdmVydGV4IGFycmF5IGhhcyB0bwogKiBiZSBzcGVjaWZpZWQgd2l0aCBCZWdpbkluZGV4ZWQgZmlyc3QuCiAqCiAqIFBhcmFtZXRlcnM6CiAqICBWZXJ0ZXhJbmRleDogVGhlIGluZGV4IG9mIHRoZSB2ZXJ0ZXggdG8gZHJhdwogKgogKiBSZXR1cm5zOgogKiAgRDNEX09LIGJlY2F1c2UgaXQncyBhIHN0dWIKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKSURpcmVjdDNERGV2aWNlSW1wbF8zX0luZGV4KElEaXJlY3QzRERldmljZTMgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgV09SRCBWZXJ0ZXhJbmRleCkKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlMywgaWZhY2UpOwogICAgRklYTUUoIiglcCktPiglMDR4KTogc3R1YiFcbiIsIFRoaXMsIFZlcnRleEluZGV4KTsKICAgIHJldHVybiBEM0RfT0s7Cn0KCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzJfSW5kZXgoSURpcmVjdDNERGV2aWNlMiAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBXT1JEIHdWZXJ0ZXhJbmRleCkKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlMiwgaWZhY2UpOwogICAgVFJBQ0VfKGRkcmF3X3RodW5rKSgiKCVwKS0+KCUwNHgpIHRodW5raW5nIHRvIElEaXJlY3QzRERldmljZTMgaW50ZXJmYWNlLlxuIiwgVGhpcywgd1ZlcnRleEluZGV4KTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2UzX0luZGV4KElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTMpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgd1ZlcnRleEluZGV4KTsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTM6OkVuZAogKgogKiBFbmRzIGEgZHJhdyBiZWd1biB3aXRoIElEaXJlY3QzRERldmljZTM6OkJlZ2luIG9yCiAqIElEaXJlY3QzRERldmljZTo6QmVnaW5JbmRleGVkLiBUaGUgdmVydGljZXMgc3BlY2lmaWVkIHdpdGgKICogSURpcmVjdDNERGV2aWNlOjpWZXJ0ZXggb3IgSURpcmVjdDNERGV2aWNlOjpJbmRleCBhcmUgZHJhd24gdXNpbmcKICogdGhlIElEaXJlY3QzRERldmljZTc6OkRyYXdQcmltaXRpdmUgbWV0aG9kLiBTbyBmYXIgb25seQogKiBub24taW5kZXhlZCBtb2RlIGlzIHN1cHBvcnRlZAogKgogKiBWZXJzaW9uIDIgYW5kIDMKICoKICogUGFyYW1zOgogKiAgRmxhZ3M6IFNvbWUgZmxhZ3MsIGFzIHVzdWFsLiBEb24ndCBrbm93IHdoaWNoIGFyZSBkZWZpbmVkCiAqCiAqIFJldHVybnM6CiAqICBUaGUgcmV0dXJuIHZhbHVlIG9mIElEaXJlY3QzRERldmljZTc6OkRyYXdQcmltaXRpdmUKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKSURpcmVjdDNERGV2aWNlSW1wbF8zX0VuZChJRGlyZWN0M0REZXZpY2UzICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBGbGFncykKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlMywgaWZhY2UpOwogICAgVFJBQ0UoIiglcCktPiglMDhseClcbiIsIFRoaXMsIEZsYWdzKTsKCiAgICByZXR1cm4gSURpcmVjdDNERGV2aWNlN19EcmF3UHJpbWl0aXZlKElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTcpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBUaGlzLT5wcmltaXRpdmVfdHlwZSwgVGhpcy0+dmVydGV4X3R5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFRoaXMtPnZlcnRleF9idWZmZXIsIFRoaXMtPm5iX3ZlcnRpY2VzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBUaGlzLT5yZW5kZXJfZmxhZ3MpOwp9CgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8yX0VuZChJRGlyZWN0M0REZXZpY2UyICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBkd0ZsYWdzKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UyLCBpZmFjZSk7CiAgICBUUkFDRV8oZGRyYXdfdGh1bmspKCIoJXApLT4oJTA4bHgpIHRodW5raW5nIHRvIElEaXJlY3QzRERldmljZTMgaW50ZXJmYWNlLlxuIiwgVGhpcywgZHdGbGFncyk7CiAgICByZXR1cm4gSURpcmVjdDNERGV2aWNlM19FbmQoSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlMyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZHdGbGFncyk7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0REZXZpY2U3OjpHZXRSZW5kZXJTdGF0ZQogKgogKiBSZXR1cm5zIHRoZSB2YWx1ZSBvZiBhIHJlbmRlciBzdGF0ZS4gVGhlIHBvc3NpYmxlIHJlbmRlciBzdGF0ZXMgYXJlCiAqIGRlZmluZWQgaW4gaW5jbHVkZS9kM2R0eXBlcy5oCiAqCiAqIFZlcnNpb24gMiwgMyBhbmQgNwogKgogKiBQYXJhbXM6CiAqICBSZW5kZXJTdGF0ZVR5cGU6IFJlbmRlciBzdGF0ZSB0byByZXR1cm4gdGhlIGN1cnJlbnQgc2V0dGluZyBvZgogKiAgVmFsdWU6IEFkZHJlc3MgdG8gc3RvcmUgdGhlIHZhbHVlIGF0CiAqCiAqIFJldHVybnM6CiAqICBEM0RfT0sgb24gc3VjY2VzcywgZm9yIGRldGFpbHMgc2VlIElXaW5lRDNERGV2aWNlOjpHZXRSZW5kZXJTdGF0ZQogKiAgRERFUlJfSU5WQUxJRFBBUkFNUyBpZiBWYWx1ZSA9PSBOVUxMCiAqCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIEhSRVNVTFQgV0lOQVBJCklEaXJlY3QzRERldmljZUltcGxfN19HZXRSZW5kZXJTdGF0ZShJRGlyZWN0M0REZXZpY2U3ICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRFJFTkRFUlNUQVRFVFlQRSBSZW5kZXJTdGF0ZVR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCAqVmFsdWUpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTcsIGlmYWNlKTsKICAgIFRSQUNFKCIoJXApLT4oJTA4eCwlcCk6IFJlbGF5XG4iLCBUaGlzLCBSZW5kZXJTdGF0ZVR5cGUsIFZhbHVlKTsKCiAgICBpZighVmFsdWUpCiAgICAgICAgcmV0dXJuIERERVJSX0lOVkFMSURQQVJBTVM7CgogICAgcmV0dXJuIElXaW5lRDNERGV2aWNlX0dldFJlbmRlclN0YXRlKFRoaXMtPndpbmVEM0REZXZpY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgUmVuZGVyU3RhdGVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFZhbHVlKTsKfQoKc3RhdGljIEhSRVNVTFQgV0lOQVBJClRodW5rX0lEaXJlY3QzRERldmljZUltcGxfM19HZXRSZW5kZXJTdGF0ZShJRGlyZWN0M0REZXZpY2UzICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRFJFTkRFUlNUQVRFVFlQRSBkd1JlbmRlclN0YXRlVHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEICpscGR3UmVuZGVyU3RhdGUpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTMsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglMDh4LCVwKSB0aHVua2luZyB0byBJRGlyZWN0M0REZXZpY2U3IGludGVyZmFjZS5cbiIsIFRoaXMsIGR3UmVuZGVyU3RhdGVUeXBlLCBscGR3UmVuZGVyU3RhdGUpOwogICAgcmV0dXJuIElEaXJlY3QzRERldmljZTdfR2V0UmVuZGVyU3RhdGUoSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlNyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBkd1JlbmRlclN0YXRlVHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGxwZHdSZW5kZXJTdGF0ZSk7Cn0KCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzJfR2V0UmVuZGVyU3RhdGUoSURpcmVjdDNERGV2aWNlMiAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RSRU5ERVJTVEFURVRZUEUgZHdSZW5kZXJTdGF0ZVR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCAqbHBkd1JlbmRlclN0YXRlKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UyLCBpZmFjZSk7CiAgICBUUkFDRV8oZGRyYXdfdGh1bmspKCIoJXApLT4oJTA4eCwlcCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlNyBpbnRlcmZhY2UuXG4iLCBUaGlzLCBkd1JlbmRlclN0YXRlVHlwZSwgbHBkd1JlbmRlclN0YXRlKTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2U3X0dldFJlbmRlclN0YXRlKElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTcpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZHdSZW5kZXJTdGF0ZVR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBscGR3UmVuZGVyU3RhdGUpOwp9CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSURpcmVjdDNERGV2aWNlNzo6U2V0UmVuZGVyU3RhdGUKICoKICogU2V0cyBhIHJlbmRlciBzdGF0ZS4gVGhlIHBvc3NpYmxlIHJlbmRlciBzdGF0ZXMgYXJlIGRlZmluZWQgaW4KICogaW5jbHVkZS9kM2R0eXBlcy5oCiAqCiAqIFZlcnNpb24gMiwgMyBhbmQgNwogKgogKiBQYXJhbXM6CiAqICBSZW5kZXJTdGF0ZVR5cGU6IFN0YXRlIHRvIHNldAogKiAgVmFsdWU6IFZhbHVlIHRvIGFzc2lnbiB0byB0aGF0IHN0YXRlCiAqCiAqIFJldHVybnM6CiAqICBEM0RfT0sgb24gc3VjY2VzcywKICogIGZvciBkZXRhaWxzIHNlZSBJV2luZUQzRERldmljZTo6U2V0UmVuZGVyU3RhdGUKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKSURpcmVjdDNERGV2aWNlSW1wbF83X1NldFJlbmRlclN0YXRlKElEaXJlY3QzRERldmljZTcgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNEUkVOREVSU1RBVEVUWVBFIFJlbmRlclN0YXRlVHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIFZhbHVlKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2U3LCBpZmFjZSk7CiAgICBUUkFDRSgiKCVwKS0+KCUwOHgsJWxkKTogUmVsYXlcbiIsIFRoaXMsIFJlbmRlclN0YXRlVHlwZSwgVmFsdWUpOwoKICAgIC8qIFNvbWUgcmVuZGVyIHN0YXRlcyBuZWVkIHNwZWNpYWwgY2FyZSAqLwogICAgc3dpdGNoKFJlbmRlclN0YXRlVHlwZSkKICAgIHsKICAgICAgICBjYXNlIEQzRFJFTkRFUlNUQVRFX1RFWFRVUkVIQU5ETEU6CiAgICAgICAgewogICAgICAgICAgICBpZihWYWx1ZSA9PSAwKQogICAgICAgICAgICB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIElXaW5lRDNERGV2aWNlX1NldFRleHR1cmUoVGhpcy0+d2luZUQzRERldmljZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAwLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIE5VTEwpOwogICAgICAgICAgICB9CgogICAgICAgICAgICBpZihWYWx1ZSA+IFRoaXMtPm51bUhhbmRsZXMpCiAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgIEZJWE1FKCJTcGVjaWZpZWQgaGFuZGxlICVsZCBvdXQgb2YgcmFuZ2VcbiIsIFZhbHVlKTsKICAgICAgICAgICAgICAgIHJldHVybiBEREVSUl9JTlZBTElEUEFSQU1TOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmKFRoaXMtPkhhbmRsZXNbVmFsdWUgLSAxXS50eXBlICE9IEREcmF3SGFuZGxlX1RleHR1cmUpCiAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgIEZJWE1FKCJIYW5kbGUgJWxkIGlzbid0IGEgdGV4dHVyZSBoYW5kbGVcbiIsIFZhbHVlKTsKICAgICAgICAgICAgICAgIHJldHVybiBEREVSUl9JTlZBTElEUEFSQU1TOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UKICAgICAgICAgICAgewogICAgICAgICAgICAgICAgSURpcmVjdERyYXdTdXJmYWNlSW1wbCAqc3VyZiA9IChJRGlyZWN0RHJhd1N1cmZhY2VJbXBsICopIFRoaXMtPkhhbmRsZXNbVmFsdWUgLSAxXS5wdHI7CiAgICAgICAgICAgICAgICByZXR1cm4gSVdpbmVEM0REZXZpY2VfU2V0VGV4dHVyZShUaGlzLT53aW5lRDNERGV2aWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgMCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIChJV2luZUQzREJhc2VUZXh0dXJlICopIHN1cmYtPndpbmVEM0RUZXh0dXJlKTsKICAgICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgY2FzZSBEM0RSRU5ERVJTVEFURV9URVhUVVJFTUFHOgogICAgICAgIHsKICAgICAgICAgICAgV0lORUQzRFRFWFRVUkVGSUxURVJUWVBFIHRleF9tYWcgPSBXSU5FRDNEVEVYRl9OT05FOwoKICAgICAgICAgICAgc3dpdGNoICgoRDNEVEVYVFVSRUZJTFRFUikgVmFsdWUpCiAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgIGNhc2UgRDNERklMVEVSX05FQVJFU1Q6CiAgICAgICAgICAgICAgICAgICAgdGV4X21hZyA9IFdJTkVEM0RURVhGX1BPSU5UOwogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgY2FzZSBEM0RGSUxURVJfTElORUFSOgogICAgICAgICAgICAgICAgICAgIHRleF9tYWcgPSBXSU5FRDNEVEVYRl9MSU5FQVI7CiAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICBkZWZhdWx0OgogICAgICAgICAgICAgICAgICAgIEVSUigiVW5oYW5kbGVkIHRleHR1cmUgbWFnICVsZCAhXG4iLFZhbHVlKTsKICAgICAgICAgICAgfQoKICAgICAgICAgICAgcmV0dXJuIElXaW5lRDNERGV2aWNlX1NldFNhbXBsZXJTdGF0ZShUaGlzLT53aW5lRDNERGV2aWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIDAsIFdJTkVEM0RTQU1QX01BR0ZJTFRFUiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB0ZXhfbWFnKTsKICAgICAgICB9CgogICAgICAgIGNhc2UgRDNEUkVOREVSU1RBVEVfVEVYVFVSRU1JTjoKICAgICAgICB7CiAgICAgICAgICAgIFdJTkVEM0RURVhUVVJFRklMVEVSVFlQRSB0ZXhfbWluID0gV0lORUQzRFRFWEZfTk9ORTsKCiAgICAgICAgICAgIHN3aXRjaCAoKEQzRFRFWFRVUkVGSUxURVIpIFZhbHVlKQogICAgICAgICAgICB7CiAgICAgICAgICAgICAgICBjYXNlIEQzREZJTFRFUl9ORUFSRVNUOgogICAgICAgICAgICAgICAgICAgIHRleF9taW4gPSBXSU5FRDNEVEVYRl9QT0lOVDsKICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgIGNhc2UgRDNERklMVEVSX0xJTkVBUjoKICAgICAgICAgICAgICAgICAgICB0ZXhfbWluID0gV0lORUQzRFRFWEZfTElORUFSOwogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgZGVmYXVsdDoKICAgICAgICAgICAgICAgICAgICBFUlIoIlVuaGFuZGxlZCB0ZXh0dXJlIG1hZyAlbGQgIVxuIixWYWx1ZSk7CiAgICAgICAgICAgIH0KCiAgICAgICAgICAgIHJldHVybiBJV2luZUQzRERldmljZV9TZXRTYW1wbGVyU3RhdGUoVGhpcy0+d2luZUQzRERldmljZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAwLCBXSU5FRDNEU0FNUF9NSU5GSUxURVIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdGV4X21pbik7CiAgICAgICAgfQoKICAgICAgICBjYXNlIEQzRFJFTkRFUlNUQVRFX1RFWFRVUkVBRERSRVNTVToKICAgICAgICBjYXNlIEQzRFJFTkRFUlNUQVRFX1RFWFRVUkVBRERSRVNTVjoKICAgICAgICBjYXNlIEQzRFJFTkRFUlNUQVRFX1RFWFRVUkVBRERSRVNTOgogICAgICAgIHsKICAgICAgICAgICAgV0lORUQzRFRFWFRVUkVTVEFHRVNUQVRFVFlQRSBUZXhTdGFnZVN0YXRlVHlwZTsKCiAgICAgICAgICAgIGlmIChSZW5kZXJTdGF0ZVR5cGUgPT0gRDNEUkVOREVSU1RBVEVfVEVYVFVSRUFERFJFU1MpCiAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgIFRleFN0YWdlU3RhdGVUeXBlID0gV0lORUQzRFRTU19BRERSRVNTOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgaWYgKFJlbmRlclN0YXRlVHlwZSA9PSBEM0RSRU5ERVJTVEFURV9URVhUVVJFQUREUkVTU1UpCiAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgIFRleFN0YWdlU3RhdGVUeXBlID0gV0lORUQzRFRTU19BRERSRVNTVTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlCiAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgIFRleFN0YWdlU3RhdGVUeXBlID0gV0lORUQzRFRTU19BRERSRVNTVjsKICAgICAgICAgICAgfQoKICAgICAgICAgICAgcmV0dXJuIElXaW5lRDNERGV2aWNlX1NldFRleHR1cmVTdGFnZVN0YXRlKFRoaXMtPndpbmVEM0REZXZpY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAwLCBUZXhTdGFnZVN0YXRlVHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFZhbHVlKTsKICAgICAgICB9CgogICAgICAgIGNhc2UgRDNEUkVOREVSU1RBVEVfVEVYVFVSRU1BUEJMRU5EOgogICAgICAgIHsKICAgICAgICAgICAgLyogT2xkIHRleHR1cmUgY29tYmluZSBzZXR1cCBzdHlsZSwgc3VwZXJzZWRlZCBieSB0ZXh0dXJlIHN0YWdlIHN0YXRlcwogICAgICAgICAgICAgKiBpbiBEM0Q3LiBJdCBpcyBzYWZlIGZvciB1cyB0byB3cmFwIGl0IHRvIHRleHR1cmUgc3RhZ2Ugc3RhdGVzLgogICAgICAgICAgICAgKi8KICAgICAgICAgICAgc3dpdGNoICggKEQzRFRFWFRVUkVCTEVORCkgVmFsdWUpCiAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgIGNhc2UgRDNEVEJMRU5EX01PRFVMQVRFOgogICAgICAgICAgICAgICAgICAgIElXaW5lRDNERGV2aWNlX1NldFRleHR1cmVTdGFnZVN0YXRlKGlmYWNlLCAwLCBEM0RUU1NfQ09MT1JBUkcxLCBEM0RUQV9URVhUVVJFKTsKICAgICAgICAgICAgICAgICAgICBJV2luZUQzRERldmljZV9TZXRUZXh0dXJlU3RhZ2VTdGF0ZShpZmFjZSwgMCwgRDNEVFNTX0FMUEhBQVJHMSwgRDNEVEFfVEVYVFVSRSk7CiAgICAgICAgICAgICAgICAgICAgSVdpbmVEM0REZXZpY2VfU2V0VGV4dHVyZVN0YWdlU3RhdGUoaWZhY2UsIDAsIEQzRFRTU19DT0xPUkFSRzIsIEQzRFRBX0NVUlJFTlQpOwogICAgICAgICAgICAgICAgICAgIElXaW5lRDNERGV2aWNlX1NldFRleHR1cmVTdGFnZVN0YXRlKGlmYWNlLCAwLCBEM0RUU1NfQ09MT1JPUCwgRDNEVE9QX01PRFVMQVRFKTsKICAgICAgICAgICAgICAgICAgICBJV2luZUQzRERldmljZV9TZXRUZXh0dXJlU3RhZ2VTdGF0ZShpZmFjZSwgMCwgRDNEVFNTX0FMUEhBT1AsIEQzRFRPUF9TRUxFQ1RBUkcxKTsKICAgICAgICAgICAgICAgICAgICBicmVhazsKCiAgICAgICAgICAgICAgICBjYXNlIEQzRFRCTEVORF9NT0RVTEFURUFMUEhBOgogICAgICAgICAgICAgICAgICAgIElXaW5lRDNERGV2aWNlX1NldFRleHR1cmVTdGFnZVN0YXRlKGlmYWNlLCAwLCBEM0RUU1NfQ09MT1JBUkcxLCBEM0RUQV9URVhUVVJFKTsKICAgICAgICAgICAgICAgICAgICBJV2luZUQzRERldmljZV9TZXRUZXh0dXJlU3RhZ2VTdGF0ZShpZmFjZSwgMCwgRDNEVFNTX0FMUEhBQVJHMSwgRDNEVEFfVEVYVFVSRSk7CiAgICAgICAgICAgICAgICAgICAgSVdpbmVEM0REZXZpY2VfU2V0VGV4dHVyZVN0YWdlU3RhdGUoaWZhY2UsIDAsIEQzRFRTU19DT0xPUkFSRzIsIEQzRFRBX0NVUlJFTlQpOwogICAgICAgICAgICAgICAgICAgIElXaW5lRDNERGV2aWNlX1NldFRleHR1cmVTdGFnZVN0YXRlKGlmYWNlLCAwLCBEM0RUU1NfQUxQSEFBUkcyLCBEM0RUQV9DVVJSRU5UKTsKICAgICAgICAgICAgICAgICAgICBJV2luZUQzRERldmljZV9TZXRUZXh0dXJlU3RhZ2VTdGF0ZShpZmFjZSwgMCwgRDNEVFNTX0NPTE9ST1AsIEQzRFRPUF9NT0RVTEFURSk7CiAgICAgICAgICAgICAgICAgICAgSVdpbmVEM0REZXZpY2VfU2V0VGV4dHVyZVN0YWdlU3RhdGUoaWZhY2UsIDAsIEQzRFRTU19BTFBIQU9QLCBEM0RUT1BfTU9EVUxBVEUpOwogICAgICAgICAgICAgICAgICAgIGJyZWFrOwoKICAgICAgICAgICAgICAgIGNhc2UgRDNEVEJMRU5EX0RFQ0FMOgogICAgICAgICAgICAgICAgICAgIElXaW5lRDNERGV2aWNlX1NldFRleHR1cmVTdGFnZVN0YXRlKGlmYWNlLCAwLCBEM0RUU1NfQ09MT1JBUkcxLCBEM0RUQV9URVhUVVJFKTsKICAgICAgICAgICAgICAgICAgICBJV2luZUQzRERldmljZV9TZXRUZXh0dXJlU3RhZ2VTdGF0ZShpZmFjZSwgMCwgRDNEVFNTX0FMUEhBQVJHMSwgRDNEVEFfVEVYVFVSRSk7CiAgICAgICAgICAgICAgICAgICAgSVdpbmVEM0REZXZpY2VfU2V0VGV4dHVyZVN0YWdlU3RhdGUoaWZhY2UsIDAsIEQzRFRTU19DT0xPUk9QLCBEM0RUT1BfU0VMRUNUQVJHMSk7CiAgICAgICAgICAgICAgICAgICAgSVdpbmVEM0REZXZpY2VfU2V0VGV4dHVyZVN0YWdlU3RhdGUoaWZhY2UsIDAsIEQzRFRTU19BTFBIQU9QLCBEM0RUT1BfU0VMRUNUQVJHMSk7CiAgICAgICAgICAgICAgICAgICAgYnJlYWs7CgogICAgICAgICAgICAgICAgY2FzZSBEM0RUQkxFTkRfREVDQUxBTFBIQToKICAgICAgICAgICAgICAgICAgICBJV2luZUQzRERldmljZV9TZXRUZXh0dXJlU3RhZ2VTdGF0ZShpZmFjZSwgMCwgRDNEVFNTX0NPTE9SQVJHMSwgRDNEVEFfVEVYVFVSRSk7CiAgICAgICAgICAgICAgICAgICAgSVdpbmVEM0REZXZpY2VfU2V0VGV4dHVyZVN0YWdlU3RhdGUoaWZhY2UsIDAsIEQzRFRTU19BTFBIQUFSRzEsIEQzRFRBX1RFWFRVUkUpOwogICAgICAgICAgICAgICAgICAgIElXaW5lRDNERGV2aWNlX1NldFRleHR1cmVTdGFnZVN0YXRlKGlmYWNlLCAwLCBEM0RUU1NfQUxQSEFBUkcyLCBEM0RUQV9DVVJSRU5UKTsKICAgICAgICAgICAgICAgICAgICBJV2luZUQzRERldmljZV9TZXRUZXh0dXJlU3RhZ2VTdGF0ZShpZmFjZSwgMCwgRDNEVFNTX0NPTE9ST1AsIEQzRFRPUF9TRUxFQ1RBUkcxKTsKICAgICAgICAgICAgICAgICAgICBJV2luZUQzRERldmljZV9TZXRUZXh0dXJlU3RhZ2VTdGF0ZShpZmFjZSwgMCwgRDNEVFNTX0FMUEhBT1AsIEQzRFRPUF9NT0RVTEFURSk7CiAgICAgICAgICAgICAgICAgICAgYnJlYWs7CgogICAgICAgICAgICAgICAgZGVmYXVsdDoKICAgICAgICAgICAgICAgICAgICBFUlIoIlVuaGFuZGxlZCB0ZXh0dXJlIGVudmlyb25tZW50ICVsZCAhXG4iLFZhbHVlKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHJldHVybiBEM0RfT0s7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgIH0KCiAgICAgICAgZGVmYXVsdDoKICAgICAgICAgICAgcmV0dXJuIElXaW5lRDNERGV2aWNlX1NldFJlbmRlclN0YXRlKFRoaXMtPndpbmVEM0REZXZpY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBSZW5kZXJTdGF0ZVR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBWYWx1ZSk7CiAgICB9Cn0KCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzNfU2V0UmVuZGVyU3RhdGUoSURpcmVjdDNERGV2aWNlMyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RSRU5ERVJTVEFURVRZUEUgUmVuZGVyU3RhdGVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgVmFsdWUpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTMsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglMDh4LCUwOGx4KSB0aHVua2luZyB0byBJRGlyZWN0M0REZXZpY2U3IGludGVyZmFjZS5cbiIsIFRoaXMsIFJlbmRlclN0YXRlVHlwZSwgVmFsdWUpOwogICAgcmV0dXJuIElEaXJlY3QzRERldmljZTdfU2V0UmVuZGVyU3RhdGUoSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlNyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBSZW5kZXJTdGF0ZVR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBWYWx1ZSk7Cn0KCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzJfU2V0UmVuZGVyU3RhdGUoSURpcmVjdDNERGV2aWNlMiAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RSRU5ERVJTVEFURVRZUEUgUmVuZGVyU3RhdGVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgVmFsdWUpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTIsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglMDh4LCUwOGx4KSB0aHVua2luZyB0byBJRGlyZWN0M0REZXZpY2U3IGludGVyZmFjZS5cbiIsIFRoaXMsIFJlbmRlclN0YXRlVHlwZSwgVmFsdWUpOwogICAgcmV0dXJuIElEaXJlY3QzRERldmljZTdfU2V0UmVuZGVyU3RhdGUoSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlNyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBSZW5kZXJTdGF0ZVR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBWYWx1ZSk7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBEaXJlY3QzRERldmljZTM6OlNldExpZ2h0U3RhdGUKICoKICogU2V0cyBhIGxpZ2h0IHN0YXRlIGZvciBEaXJlY3QzRERldmljZTMgYW5kIERpcmVjdDNERGV2aWNlMi4gVGhlCiAqIGxpZ2h0IHN0YXRlcyBhcmUgZm9yd2FyZGVkIHRvIERpcmVjdDNERGV2aWNlNyByZW5kZXIgc3RhdGVzCiAqCiAqIFZlcnNpb24gMiBhbmQgMwogKgogKiBQYXJhbXM6CiAqICBMaWdodFN0YXRlVHlwZTogVGhlIGxpZ2h0IHN0YXRlIHRvIGNoYW5nZQogKiAgVmFsdWU6IFRoZSB2YWx1ZSB0byBhc3NpZ24gdG8gdGhhdCBsaWdodCBzdGF0ZQogKgogKiBSZXR1cm5zOgogKiAgRDNEX09LIG9uIHN1Y2Nlc3MKICogIERERVJSX0lOVkFMSURQQVJBTVMgaWYgdGhlIHBhcmFtZXRlcnMgd2VyZSBpbmNvcnJlY3QKICogIEFsc28gY2hlY2sgSURpcmVjdDNERGV2aWNlNzo6U2V0UmVuZGVyU3RhdGUKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKSURpcmVjdDNERGV2aWNlSW1wbF8zX1NldExpZ2h0U3RhdGUoSURpcmVjdDNERGV2aWNlMyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRExJR0hUU1RBVEVUWVBFIExpZ2h0U3RhdGVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBWYWx1ZSkKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlMywgaWZhY2UpOwoKICAgIFRSQUNFKCIoJXApLT4oJTA4eCwlMDhseClcbiIsIFRoaXMsIExpZ2h0U3RhdGVUeXBlLCBWYWx1ZSk7CgogICAgaWYgKCFMaWdodFN0YXRlVHlwZSAmJiAoTGlnaHRTdGF0ZVR5cGUgPiBEM0RMSUdIVFNUQVRFX0NPTE9SVkVSVEVYKSkKICAgIHsKICAgICAgICBUUkFDRSgiVW5leHBlY3RlZCBMaWdodCBTdGF0ZSBUeXBlXG4iKTsKICAgICAgICByZXR1cm4gRERFUlJfSU5WQUxJRFBBUkFNUzsKICAgIH0KCiAgICBpZiAoTGlnaHRTdGF0ZVR5cGUgPT0gRDNETElHSFRTVEFURV9NQVRFUklBTCAvKiAxICovKQogICAgewogICAgICAgIElEaXJlY3QzRE1hdGVyaWFsSW1wbCAqbWF0OwoKICAgICAgICBpZihWYWx1ZSA9PSAwKSBtYXQgPSBOVUxMOwogICAgICAgIGVsc2UgaWYoVmFsdWUgPiBUaGlzLT5udW1IYW5kbGVzKQogICAgICAgIHsKICAgICAgICAgICAgRVJSKCJNYXRlcmlhbCBoYW5kbGUgb3V0IG9mIHJhbmdlKCVsZClcbiIsIFZhbHVlKTsKICAgICAgICAgICAgcmV0dXJuIERERVJSX0lOVkFMSURQQVJBTVM7CiAgICAgICAgfQogICAgICAgIGVsc2UgaWYoVGhpcy0+SGFuZGxlc1tWYWx1ZSAtIDFdLnR5cGUgIT0gRERyYXdIYW5kbGVfTWF0ZXJpYWwpCiAgICAgICAgewogICAgICAgICAgICBFUlIoIkludmFsaWQgaGFuZGxlICVsZFxuIiwgVmFsdWUpOwogICAgICAgICAgICByZXR1cm4gRERFUlJfSU5WQUxJRFBBUkFNUzsKICAgICAgICB9CiAgICAgICAgZWxzZQogICAgICAgIHsKICAgICAgICAgICAgbWF0ID0gKElEaXJlY3QzRE1hdGVyaWFsSW1wbCAqKSBUaGlzLT5IYW5kbGVzW1ZhbHVlIC0gMV0ucHRyOwogICAgICAgIH0KCiAgICAgICAgaWYgKG1hdCAhPSBOVUxMKQogICAgICAgIHsKICAgICAgICAgICAgVFJBQ0UoIiBhY3RpdmF0aW5nIG1hdGVyaWFsICVwLlxuIiwgbWF0KTsKICAgICAgICAgICAgbWF0LT5hY3RpdmF0ZShtYXQpOwogICAgICAgIH0KICAgICAgICBlbHNlCiAgICAgICAgewogICAgICAgICAgICBGSVhNRSgiIEQzRExJR0hUU1RBVEVfTUFURVJJQUwgY2FsbGVkIHdpdGggTlVMTCBtYXRlcmlhbCAhISFcbiIpOwogICAgICAgIH0KICAgICAgICBUaGlzLT5tYXRlcmlhbCA9IFZhbHVlOwogICAgfQogICAgZWxzZSBpZiAoTGlnaHRTdGF0ZVR5cGUgPT0gRDNETElHSFRTVEFURV9DT0xPUk1PREVMIC8qIDMgKi8pCiAgICB7CiAgICAgICAgc3dpdGNoIChWYWx1ZSkKICAgICAgICB7CiAgICAgICAgICAgIGNhc2UgRDNEQ09MT1JfTU9OTzoKICAgICAgICAgICAgICAgIEVSUigiRERDT0xPUl9NT05PIHNob3VsZCBub3QgaGFwcGVuIVxuIik7CiAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgY2FzZSBEM0RDT0xPUl9SR0I6CiAgICAgICAgICAgICAgICAvKiBXZSBhcmUgYWxyZWFkeSBpbiB0aGlzIG1vZGUgKi8KICAgICAgICAgICAgICAgIFRSQUNFKCJTZXR0aW5nIGNvbG9yIG1vZGVsIHRvIFJHQiAobm8tb3ApLlxuIik7CiAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgZGVmYXVsdDoKICAgICAgICAgICAgICAgIEVSUigiVW5rbm93biBjb2xvciBtb2RlbCFcbiIpOwogICAgICAgICAgICAgICAgcmV0dXJuIERERVJSX0lOVkFMSURQQVJBTVM7CiAgICAgICAgfQogICAgfQogICAgZWxzZQogICAgewogICAgICAgIEQzRFJFTkRFUlNUQVRFVFlQRSByczsKICAgICAgICBzd2l0Y2ggKExpZ2h0U3RhdGVUeXBlKQogICAgICAgIHsKICAgICAgICAgICAgY2FzZSBEM0RMSUdIVFNUQVRFX0FNQklFTlQ6ICAgICAgIC8qIDIgKi8KICAgICAgICAgICAgICAgIHJzID0gRDNEUkVOREVSU1RBVEVfQU1CSUVOVDsKICAgICAgICAgICAgICAgIGJyZWFrOwkJCiAgICAgICAgICAgIGNhc2UgRDNETElHSFRTVEFURV9GT0dNT0RFOiAgICAgICAvKiA0ICovCiAgICAgICAgICAgICAgICBycyA9IEQzRFJFTkRFUlNUQVRFX0ZPR1ZFUlRFWE1PREU7CiAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgY2FzZSBEM0RMSUdIVFNUQVRFX0ZPR1NUQVJUOiAgICAgIC8qIDUgKi8KICAgICAgICAgICAgICAgIHJzID0gRDNEUkVOREVSU1RBVEVfRk9HU1RBUlQ7CiAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgY2FzZSBEM0RMSUdIVFNUQVRFX0ZPR0VORDogICAgICAgIC8qIDYgKi8KICAgICAgICAgICAgICAgIHJzID0gRDNEUkVOREVSU1RBVEVfRk9HRU5EOwogICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIGNhc2UgRDNETElHSFRTVEFURV9GT0dERU5TSVRZOiAgICAvKiA3ICovCiAgICAgICAgICAgICAgICBycyA9IEQzRFJFTkRFUlNUQVRFX0ZPR0RFTlNJVFk7CiAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgY2FzZSBEM0RMSUdIVFNUQVRFX0NPTE9SVkVSVEVYOiAgIC8qIDggKi8KICAgICAgICAgICAgICAgIHJzID0gRDNEUkVOREVSU1RBVEVfQ09MT1JWRVJURVg7CiAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgZGVmYXVsdDoKICAgICAgICAgICAgICAgIEVSUigiVW5rbm93biBEM0RMSUdIVFNUQVRFVFlQRSAlZC5cbiIsIExpZ2h0U3RhdGVUeXBlKTsKICAgICAgICAgICAgICAgIHJldHVybiBEREVSUl9JTlZBTElEUEFSQU1TOwogICAgICAgIH0KCiAgICAgICAgcmV0dXJuIElEaXJlY3QzRERldmljZTdfU2V0UmVuZGVyU3RhdGUoSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlNyksIAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFZhbHVlKTsKICAgIH0KCiAgICByZXR1cm4gRDNEX09LOwp9CgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8yX1NldExpZ2h0U3RhdGUoSURpcmVjdDNERGV2aWNlMiAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRExJR0hUU1RBVEVUWVBFIExpZ2h0U3RhdGVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBWYWx1ZSkKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlMiwgaWZhY2UpOwogICAgVFJBQ0VfKGRkcmF3X3RodW5rKSgiKCVwKS0+KCUwOHgsJTA4bHgpIHRodW5raW5nIHRvIElEaXJlY3QzRERldmljZTMgaW50ZXJmYWNlLlxuIiwgVGhpcywgTGlnaHRTdGF0ZVR5cGUsIFZhbHVlKTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2UzX1NldExpZ2h0U3RhdGUoSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlMyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIExpZ2h0U3RhdGVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBWYWx1ZSk7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0REZXZpY2UzOjpHZXRMaWdodFN0YXRlCiAqCiAqIFJldHVybnMgdGhlIGN1cnJlbnQgc2V0dGluZyBvZiBhIGxpZ2h0IHN0YXRlLiBUaGUgc3RhdGUgaXMgcmVhZCBmcm9tCiAqIHRoZSBEaXJlY3QzRERldmljZTcgcmVuZGVyIHN0YXRlLgogKgogKiBWZXJzaW9uIDIgYW5kIDMKICoKICogUGFyYW1zOgogKiAgTGlnaHRTdGF0ZVR5cGU6IFRoZSBsaWdodCBzdGF0ZSB0byByZXR1cm4KICogIFZhbHVlOiBUaGUgYWRkcmVzcyB0byBzdG9yZSB0aGUgbGlnaHQgc3RhdGUgc2V0dGluZyBhdAogKgogKiBSZXR1cm5zOgogKiAgRDNEX09LIG9uIHN1Y2Nlc3MKICogIEREREVSUl9JTlZBTElEUEFSQU1TIGlmIHRoZSBwYXJhbWV0ZXJzIHdlcmUgaW5jb3JyZWN0CiAqICBBbHNvIHNlZSBJRGlyZWN0M0REZXZpY2U3OjpHZXRSZW5kZXJTdGF0ZQogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0REZXZpY2VJbXBsXzNfR2V0TGlnaHRTdGF0ZShJRGlyZWN0M0REZXZpY2UzICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNETElHSFRTVEFURVRZUEUgTGlnaHRTdGF0ZVR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEICpWYWx1ZSkKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlMywgaWZhY2UpOwoKICAgIFRSQUNFKCIoJXApLT4oJTA4eCwlcClcbiIsIFRoaXMsIExpZ2h0U3RhdGVUeXBlLCBWYWx1ZSk7CgogICAgaWYgKCFMaWdodFN0YXRlVHlwZSAmJiAoTGlnaHRTdGF0ZVR5cGUgPiBEM0RMSUdIVFNUQVRFX0NPTE9SVkVSVEVYKSkKICAgIHsKICAgICAgICBUUkFDRSgiVW5leHBlY3RlZCBMaWdodCBTdGF0ZSBUeXBlXG4iKTsKICAgICAgICByZXR1cm4gRERFUlJfSU5WQUxJRFBBUkFNUzsKICAgIH0KCiAgICBpZighVmFsdWUpCiAgICAgICAgcmV0dXJuIERERVJSX0lOVkFMSURQQVJBTVM7CgogICAgaWYgKExpZ2h0U3RhdGVUeXBlID09IEQzRExJR0hUU1RBVEVfTUFURVJJQUwgLyogMSAqLykKICAgIHsKICAgICAgICAqVmFsdWUgPSBUaGlzLT5tYXRlcmlhbDsKICAgIH0KICAgIGVsc2UgaWYgKExpZ2h0U3RhdGVUeXBlID09IEQzRExJR0hUU1RBVEVfQ09MT1JNT0RFTCAvKiAzICovKQogICAgewogICAgICAgICpWYWx1ZSA9IEQzRENPTE9SX1JHQjsKICAgIH0KICAgIGVsc2UKICAgIHsKICAgICAgICBEM0RSRU5ERVJTVEFURVRZUEUgcnM7CiAgICAgICAgc3dpdGNoIChMaWdodFN0YXRlVHlwZSkKICAgICAgICB7CiAgICAgICAgICAgIGNhc2UgRDNETElHSFRTVEFURV9BTUJJRU5UOiAgICAgICAvKiAyICovCiAgICAgICAgICAgICAgICBycyA9IEQzRFJFTkRFUlNUQVRFX0FNQklFTlQ7CiAgICAgICAgICAgICAgICBicmVhazsJCQogICAgICAgICAgICBjYXNlIEQzRExJR0hUU1RBVEVfRk9HTU9ERTogICAgICAgLyogNCAqLwogICAgICAgICAgICAgICAgcnMgPSBEM0RSRU5ERVJTVEFURV9GT0dWRVJURVhNT0RFOwogICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIGNhc2UgRDNETElHSFRTVEFURV9GT0dTVEFSVDogICAgICAvKiA1ICovCiAgICAgICAgICAgICAgICBycyA9IEQzRFJFTkRFUlNUQVRFX0ZPR1NUQVJUOwogICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIGNhc2UgRDNETElHSFRTVEFURV9GT0dFTkQ6ICAgICAgICAvKiA2ICovCiAgICAgICAgICAgICAgICBycyA9IEQzRFJFTkRFUlNUQVRFX0ZPR0VORDsKICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICBjYXNlIEQzRExJR0hUU1RBVEVfRk9HREVOU0lUWTogICAgLyogNyAqLwogICAgICAgICAgICAgICAgcnMgPSBEM0RSRU5ERVJTVEFURV9GT0dERU5TSVRZOwogICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIGNhc2UgRDNETElHSFRTVEFURV9DT0xPUlZFUlRFWDogICAvKiA4ICovCiAgICAgICAgICAgICAgICBycyA9IEQzRFJFTkRFUlNUQVRFX0NPTE9SVkVSVEVYOwogICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIGRlZmF1bHQ6CiAgICAgICAgICAgICAgICBFUlIoIlVua25vd24gRDNETElHSFRTVEFURVRZUEUgJWQuXG4iLCBMaWdodFN0YXRlVHlwZSk7CiAgICAgICAgICAgICAgICByZXR1cm4gRERFUlJfSU5WQUxJRFBBUkFNUzsKICAgICAgICB9CgogICAgICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2U3X0dldFJlbmRlclN0YXRlKElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTcpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFZhbHVlKTsKICAgIH0KCiAgICByZXR1cm4gRDNEX09LOwp9CgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8yX0dldExpZ2h0U3RhdGUoSURpcmVjdDNERGV2aWNlMiAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRExJR0hUU1RBVEVUWVBFIExpZ2h0U3RhdGVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCAqVmFsdWUpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTIsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglMDh4LCVwKSB0aHVua2luZyB0byBJRGlyZWN0M0REZXZpY2UzIGludGVyZmFjZS5cbiIsIFRoaXMsIExpZ2h0U3RhdGVUeXBlLCBWYWx1ZSk7CiAgICByZXR1cm4gSURpcmVjdDNERGV2aWNlM19HZXRMaWdodFN0YXRlKElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTMpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBMaWdodFN0YXRlVHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgVmFsdWUpOwp9CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSURpcmVjdDNERGV2aWNlNzo6U2V0VHJhbnNmb3JtCiAqCiAqIEFzc2lnbnMgYSBEM0RNQVRSSVggdG8gYSB0cmFuc2Zvcm0gdHlwZS4gVGhlIHRyYW5zZm9ybSB0eXBlcyBhcmUgZGVmaW5lZAogKiBpbiBpbmNsdWRlL2QzZHR5cGVzLmguCiAqIFRoZSBEM0RUUkFOU0ZPUk1TVEFURV9XT1JMRCAoPTEpIGlzIHRyYW5zbGF0ZWQgdG8gRDNEVFNfV09STERNQVRSSVgoMCkKICogKD0yNTUpIGZvciB3aW5lZDNkLCBiZWNhdXNlIHRoZSAxIHRyYW5zZm9ybSBzdGF0ZSB3YXMgcmVtb3ZlZCBpbiBkM2Q4CiAqIGFuZCBXaW5lRDNEIGFscmVhZHkgdW5kZXJzdGFuZHMgdGhlIHJlcGxhY2VtZW50IEQzRFRTX1dPUkxETUFUUklYKDApCiAqCiAqIFZlcnNpb24gMiwgMyBhbmQgNwogKgogKiBQYXJhbXM6CiAqICBUcmFuc2Zvcm1TdGF0ZVR5cGU6IHRyYW5zZm9ybSBzdGF0ZSB0byBzZXQKICogIE1hdHJpeDogTWF0cml4IHRvIGFzc2lnbiB0byB0aGUgc3RhdGUKICoKICogUmV0dXJuczoKICogIEQzRF9PSyBvbiBzdWNjZXNzCiAqICBEREVSUl9JTlZBTElEUEFSQU1TIGlmIE1hdHJpeCA9PSBOVUxMCiAqICBGb3IgZGV0YWlscyBzZWUgSVdpbmVEM0REZXZpY2U6OlNldFRyYW5zZm9ybQogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0REZXZpY2VJbXBsXzdfU2V0VHJhbnNmb3JtKElEaXJlY3QzRERldmljZTcgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRFRSQU5TRk9STVNUQVRFVFlQRSBUcmFuc2Zvcm1TdGF0ZVR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNETUFUUklYICpNYXRyaXgpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTcsIGlmYWNlKTsKICAgIEQzRFRSQU5TRk9STVNUQVRFVFlQRSB0eXBlID0gVHJhbnNmb3JtU3RhdGVUeXBlOwogICAgVFJBQ0UoIiglcCktPiglMDh4LCVwKTogUmVsYXlcbiIsIFRoaXMsIFRyYW5zZm9ybVN0YXRlVHlwZSwgTWF0cml4KTsKCiAgICBpZighTWF0cml4KQogICAgICAgIHJldHVybiBEREVSUl9JTlZBTElEUEFSQU1TOwoKICAgIC8qIEQzRFRSQU5TRk9STVNUQVRFX1dPUkxEIGRvZXNuJ3QgZXhpc3QgaW4gV2luZUQzRCwKICAgICAqIHVzZSBEM0RUU19XT1JMRE1BVFJJWCgwKSBpbnN0ZWFkCiAgICAgKiBEM0RUU19XT1JMRE1BVFJJWChpbmRleCkgaXMgKEQzRFRSQU5TRk9STVNUQVRFVFlQRSkoaW5kZXggKyAyNTYpCiAgICAgKi8KICAgIGlmKFRyYW5zZm9ybVN0YXRlVHlwZSA9PSBEM0RUUkFOU0ZPUk1TVEFURV9XT1JMRCkKICAgICAgICB0eXBlID0gKEQzRFRSQU5TRk9STVNUQVRFVFlQRSkoMCArIDI1Nik7CgogICAgcmV0dXJuIElXaW5lRDNERGV2aWNlX1NldFRyYW5zZm9ybShUaGlzLT53aW5lRDNERGV2aWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB0eXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBNYXRyaXgpOwp9CgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8zX1NldFRyYW5zZm9ybShJRGlyZWN0M0REZXZpY2UzICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RUUkFOU0ZPUk1TVEFURVRZUEUgVHJhbnNmb3JtU3RhdGVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRE1BVFJJWCAqRDNETWF0cml4KQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UzLCBpZmFjZSk7CiAgICBUUkFDRV8oZGRyYXdfdGh1bmspKCIoJXApLT4oJTA4eCwlcCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlNyBpbnRlcmZhY2UuXG4iLCBUaGlzLCBUcmFuc2Zvcm1TdGF0ZVR5cGUsIEQzRE1hdHJpeCk7CiAgICByZXR1cm4gSURpcmVjdDNERGV2aWNlN19TZXRUcmFuc2Zvcm0oSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlNyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgVHJhbnNmb3JtU3RhdGVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRE1hdHJpeCk7Cn0KCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzJfU2V0VHJhbnNmb3JtKElEaXJlY3QzRERldmljZTIgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRFRSQU5TRk9STVNUQVRFVFlQRSBUcmFuc2Zvcm1TdGF0ZVR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNETUFUUklYICpEM0RNYXRyaXgpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTIsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglMDh4LCVwKSB0aHVua2luZyB0byBJRGlyZWN0M0REZXZpY2U3IGludGVyZmFjZS5cbiIsIFRoaXMsIFRyYW5zZm9ybVN0YXRlVHlwZSwgRDNETWF0cml4KTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2U3X1NldFRyYW5zZm9ybShJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0REZXZpY2U3KSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBUcmFuc2Zvcm1TdGF0ZVR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNETWF0cml4KTsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTc6OkdldFRyYW5zZm9ybQogKgogKiBSZXR1cm5zIHRoZSBtYXRyaXggYXNzaWduZWQgdG8gYSB0cmFuc2Zvcm0gc3RhdGUKICogRDNEVFJBTlNGT1JNU1RBVEVfV09STEQgaXMgdHJhbnNsYXRlZCB0byBEM0RUU19XT1JMRE1BVFJJWCgwKSwgc2VlCiAqIFNldFRyYW5zZm9ybQogKgogKiBQYXJhbXM6CiAqICBUcmFuc2Zvcm1TdGF0ZVR5cGU6IFN0YXRlIHRvIHJlYWQgdGhlIG1hdHJpeCBmcm9tCiAqICBNYXRyaXg6IEFkZHJlc3MgdG8gc3RvcmUgdGhlIG1hdHJpeCBhdAogKgogKiBSZXR1cm5zOgogKiAgRDNEX09LIG9uIHN1Y2Nlc3MKICogIERERVJSX0lOVkFMSURQQVJBTVMgaWYgTWF0cml4ID09IE5VTEwKICogIEZvciBkZXRhaWxzLCBzZWUgSVdpbmVEM0REZXZpY2U6OkdldFRyYW5zZm9ybQogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0REZXZpY2VJbXBsXzdfR2V0VHJhbnNmb3JtKElEaXJlY3QzRERldmljZTcgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRFRSQU5TRk9STVNUQVRFVFlQRSBUcmFuc2Zvcm1TdGF0ZVR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNETUFUUklYICpNYXRyaXgpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTcsIGlmYWNlKTsKICAgIEQzRFRSQU5TRk9STVNUQVRFVFlQRSB0eXBlID0gVHJhbnNmb3JtU3RhdGVUeXBlOwogICAgVFJBQ0UoIiglcCktPiglMDh4LCVwKTogUmVsYXlcbiIsIFRoaXMsIFRyYW5zZm9ybVN0YXRlVHlwZSwgTWF0cml4KTsKCiAgICBpZighTWF0cml4KQogICAgICAgIHJldHVybiBEREVSUl9JTlZBTElEUEFSQU1TOwoKICAgIC8qIEQzRFRSQU5TRk9STVNUQVRFX1dPUkxEIGRvZXNuJ3QgZXhpc3QgaW4gV2luZUQzRCwKICAgICAqIHVzZSBEM0RUU19XT1JMRE1BVFJJWCgwKSBpbnN0ZWFkCiAgICAgKiBEM0RUU19XT1JMRE1BVFJJWChpbmRleCkgaXMgKEQzRFRSQU5TRk9STVNUQVRFVFlQRSkoaW5kZXggKyAyNTYpCiAgICAgKi8KICAgIGlmKFRyYW5zZm9ybVN0YXRlVHlwZSA9PSBEM0RUUkFOU0ZPUk1TVEFURV9XT1JMRCkKICAgICAgICB0eXBlID0gKEQzRFRSQU5TRk9STVNUQVRFVFlQRSkoMCArIDI1Nik7CgogICAgcmV0dXJuIElXaW5lRDNERGV2aWNlX0dldFRyYW5zZm9ybShUaGlzLT53aW5lRDNERGV2aWNlLCB0eXBlLCBNYXRyaXgpOwp9CgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8zX0dldFRyYW5zZm9ybShJRGlyZWN0M0REZXZpY2UzICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RUUkFOU0ZPUk1TVEFURVRZUEUgVHJhbnNmb3JtU3RhdGVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRE1BVFJJWCAqRDNETWF0cml4KQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UzLCBpZmFjZSk7CiAgICBUUkFDRV8oZGRyYXdfdGh1bmspKCIoJXApLT4oJTA4eCwlcCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlNyBpbnRlcmZhY2UuXG4iLCBUaGlzLCBUcmFuc2Zvcm1TdGF0ZVR5cGUsIEQzRE1hdHJpeCk7CiAgICByZXR1cm4gSURpcmVjdDNERGV2aWNlN19HZXRUcmFuc2Zvcm0oSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlNyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgVHJhbnNmb3JtU3RhdGVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRE1hdHJpeCk7Cn0KCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzJfR2V0VHJhbnNmb3JtKElEaXJlY3QzRERldmljZTIgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRFRSQU5TRk9STVNUQVRFVFlQRSBUcmFuc2Zvcm1TdGF0ZVR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNETUFUUklYICpEM0RNYXRyaXgpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTIsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglMDh4LCVwKSB0aHVua2luZyB0byBJRGlyZWN0M0REZXZpY2U3IGludGVyZmFjZS5cbiIsIFRoaXMsIFRyYW5zZm9ybVN0YXRlVHlwZSwgRDNETWF0cml4KTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2U3X0dldFRyYW5zZm9ybShJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0REZXZpY2U3KSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBUcmFuc2Zvcm1TdGF0ZVR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNETWF0cml4KTsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTc6Ok11bHRpcGx5VHJhbnNmb3JtCiAqCiAqIE11bHRpcGxpZXMgdGhlIGFscmVhZHktc2V0IHRyYW5zZm9ybSBtYXRyaXggb2YgYSB0cmFuc2Zvcm0gc3RhdGUKICogd2l0aCBhbm90aGVyIG1hdHJpeC4gRm9yIHRoZSB3b3JsZCBtYXRyaXgsIHNlZSBTZXRUcmFuc2Zvcm0KICoKICogVmVyc2lvbiAyLCAzIGFuZCA3CiAqCiAqIFBhcmFtczoKICogIFRyYW5zZm9ybVN0YXRlVHlwZTogVHJhbnNmb3JtIHN0YXRlIHRvIG11bHRpcGx5CiAqICBEM0RNYXRyaXggTWF0cml4IHRvIG11bHRpcGx5IHdpdGguCiAqCiAqIFJldHVybnMKICogIEQzRF9PSyBvbiBzdWNjZXNzCiAqICBEREVSUl9JTlZBTElEUEFSQU1TIGlmIEQzRE1hdHJpeCBpcyBOVUxMCiAqICBGb3IgZGV0YWlscywgc2VlIElXaW5lRDNERGV2aWNlOjpNdWx0aXBseVRyYW5zZm9ybQogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0REZXZpY2VJbXBsXzdfTXVsdGlwbHlUcmFuc2Zvcm0oSURpcmVjdDNERGV2aWNlNyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RUUkFOU0ZPUk1TVEFURVRZUEUgVHJhbnNmb3JtU3RhdGVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNETUFUUklYICpEM0RNYXRyaXgpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTcsIGlmYWNlKTsKICAgIFRSQUNFKCIoJXApLT4oJTA4eCwlcCk6IFJlbGF5XG4iLCBUaGlzLCBUcmFuc2Zvcm1TdGF0ZVR5cGUsIEQzRE1hdHJpeCk7CgogICAgLyogRDNEVFJBTlNGT1JNU1RBVEVfV09STEQgZG9lc24ndCBleGlzdCBpbiBXaW5lRDNELAogICAgICogdXNlIEQzRFRTX1dPUkxETUFUUklYKDApIGluc3RlYWQKICAgICAqIEQzRFRTX1dPUkxETUFUUklYKGluZGV4KSBpcyAoRDNEVFJBTlNGT1JNU1RBVEVUWVBFKShpbmRleCArIDI1NikKICAgICAqLwogICAgaWYoVHJhbnNmb3JtU3RhdGVUeXBlID09IEQzRFRSQU5TRk9STVNUQVRFX1dPUkxEKQogICAgICAgIFRyYW5zZm9ybVN0YXRlVHlwZSA9IChEM0RUUkFOU0ZPUk1TVEFURVRZUEUpKDAgKyAyNTYpOwoKICAgIHJldHVybiBJV2luZUQzRERldmljZV9NdWx0aXBseVRyYW5zZm9ybShUaGlzLT53aW5lRDNERGV2aWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFRyYW5zZm9ybVN0YXRlVHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RNYXRyaXgpOwp9CgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8zX011bHRpcGx5VHJhbnNmb3JtKElEaXJlY3QzRERldmljZTMgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNEVFJBTlNGT1JNU1RBVEVUWVBFIFRyYW5zZm9ybVN0YXRlVHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRE1BVFJJWCAqRDNETWF0cml4KQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UzLCBpZmFjZSk7CiAgICBUUkFDRV8oZGRyYXdfdGh1bmspKCIoJXApLT4oJTA4eCwlcCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlNyBpbnRlcmZhY2UuXG4iLCBUaGlzLCBUcmFuc2Zvcm1TdGF0ZVR5cGUsIEQzRE1hdHJpeCk7CiAgICByZXR1cm4gSURpcmVjdDNERGV2aWNlN19NdWx0aXBseVRyYW5zZm9ybShJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0REZXZpY2U3KSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFRyYW5zZm9ybVN0YXRlVHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRE1hdHJpeCk7Cn0KCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzJfTXVsdGlwbHlUcmFuc2Zvcm0oSURpcmVjdDNERGV2aWNlMiAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RUUkFOU0ZPUk1TVEFURVRZUEUgVHJhbnNmb3JtU3RhdGVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNETUFUUklYICpEM0RNYXRyaXgpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTIsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglMDh4LCVwKSB0aHVua2luZyB0byBJRGlyZWN0M0REZXZpY2U3IGludGVyZmFjZS5cbiIsIFRoaXMsIFRyYW5zZm9ybVN0YXRlVHlwZSwgRDNETWF0cml4KTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2U3X011bHRpcGx5VHJhbnNmb3JtKElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTcpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgVHJhbnNmb3JtU3RhdGVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNETWF0cml4KTsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTc6OkRyYXdQcmltaXRpdmUKICoKICogRHJhd3MgcHJpbWl0aXZlcyBiYXNlZCBvbiB2ZXJ0aWNlcyBpbiBhbiBhcHBsaWNhdGlvbi1wcm92aWRlZCBwb2ludGVyCiAqCiAqIFZlcnNpb24gMiwgMyBhbmQgNy4gVGhlIElEaXJlY3QzRERldmljZTIgdGh1bmsgY29udmVydHMgdGhlIGZpeGVkIHZlcnRleCB0eXBlIGludG8KICogYW4gRlZGIGZvcm1hdCBmb3IgRDNENwogKgogKiBQYXJhbXM6CiAqICBQcmltaXRpdmVUeXBlOiBUaGUgdHlwZSBvZiB0aGUgcHJpbWl0aXZlcyB0byBkcmF3CiAqICBWZXJ0ZXggdHlwZTogRmxleGlibGUgdmVydGV4IGZvcm1hdCB2ZXJ0ZXggZGVzY3JpcHRpb24KICogIFZlcnRpY2VzOiBQb2ludGVyIHRvIHRoZSB2ZXJ0ZXggYXJyYXkKICogIFZlcnRleENvdW50OiBUaGUgbnVtYmVyIG9mIHZlcnRpY2VzIHRvIGRyYXcKICogIEZsYWdzOiBBcyB1c3VhbCBhIGZldyBmbGFncwogKgogKiBSZXR1cm5zOgogKiAgRDNEX09LIG9uIHN1Y2Nlc3MKICogIERERVJSX0lOVkFMSURQQVJBTVMgaWYgVmVydGljZXMgaXMgTlVMTAogKiAgRm9yIGRldGFpbHMsIHNlZSBJV2luZUQzRERldmljZTo6RHJhd1ByaW1pdGl2ZVVQCiAqCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIEhSRVNVTFQgV0lOQVBJCklEaXJlY3QzRERldmljZUltcGxfN19EcmF3UHJpbWl0aXZlKElEaXJlY3QzRERldmljZTcgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RQUklNSVRJVkVUWVBFIFByaW1pdGl2ZVR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIFZlcnRleFR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHZvaWQgKlZlcnRpY2VzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBWZXJ0ZXhDb3VudCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgRmxhZ3MpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTcsIGlmYWNlKTsKICAgIFVJTlQgUHJpbWl0aXZlQ291bnQsIHN0cmlkZTsKICAgIEhSRVNVTFQgaHI7CiAgICBUUkFDRSgiKCVwKS0+KCUwOHgsJTA4bHgsJXAsJTA4bHgsJTA4bHgpOiBSZWxheSFcbiIsIFRoaXMsIFByaW1pdGl2ZVR5cGUsIFZlcnRleFR5cGUsIFZlcnRpY2VzLCBWZXJ0ZXhDb3VudCwgRmxhZ3MpOwoKICAgIGlmKCFWZXJ0aWNlcykKICAgICAgICByZXR1cm4gRERFUlJfSU5WQUxJRFBBUkFNUzsKCiAgICAvKiBHZXQgdGhlIHZlcnRleCBjb3VudCAqLwogICAgc3dpdGNoKFByaW1pdGl2ZVR5cGUpCiAgICB7CiAgICAgIGNhc2UgRDNEUFRfUE9JTlRMSVNUOiAKICAgICAgICBQcmltaXRpdmVDb3VudCA9IFZlcnRleENvdW50OwogICAgICAgIGJyZWFrOwoKICAgICAgY2FzZSBEM0RQVF9MSU5FTElTVDogCiAgICAgICAgUHJpbWl0aXZlQ291bnQgPSBWZXJ0ZXhDb3VudCAvIDI7CiAgICAgICAgYnJlYWs7CgogICAgICBjYXNlIEQzRFBUX0xJTkVTVFJJUDoKICAgICAgICBQcmltaXRpdmVDb3VudCA9IFZlcnRleENvdW50IC0gMTsKICAgICAgICBicmVhazsKCiAgICAgIGNhc2UgRDNEUFRfVFJJQU5HTEVMSVNUOgogICAgICAgIFByaW1pdGl2ZUNvdW50ID0gVmVydGV4Q291bnQgLyAzOwogICAgICAgIGJyZWFrOwoKICAgICAgY2FzZSBEM0RQVF9UUklBTkdMRVNUUklQOgogICAgICAgIFByaW1pdGl2ZUNvdW50ID0gVmVydGV4Q291bnQgLSAyOwogICAgICAgIGJyZWFrOwoKICAgICAgY2FzZSBEM0RQVF9UUklBTkdMRUZBTjoKICAgICAgICBQcmltaXRpdmVDb3VudCA9IFZlcnRleENvdW50IC0gMjsKICAgICAgICBicmVhazsKCiAgICAgIGRlZmF1bHQ6IHJldHVybiBEREVSUl9JTlZBTElEUEFSQU1TOwogICAgfQoKICAgIC8qIEdldCB0aGUgc3RyaWRlICovCiAgICBzdHJpZGUgPSBnZXRfZmxleGlibGVfdmVydGV4X3NpemUoVmVydGV4VHlwZSk7CgogICAgLyogU2V0IHRoZSBGVkYgKi8KICAgIGhyID0gSVdpbmVEM0REZXZpY2VfU2V0RlZGKFRoaXMtPndpbmVEM0REZXZpY2UsIFZlcnRleFR5cGUpOwogICAgaWYoaHIgIT0gRDNEX09LKSByZXR1cm4gaHI7CgogICAgLyogVGhpcyBtZXRob2QgdHJhbnNsYXRlcyB0byB0aGUgdXNlciBwb2ludGVyIGRyYXcgb2YgV2luZUQzRCAqLwogICAgcmV0dXJuIElXaW5lRDNERGV2aWNlX0RyYXdQcmltaXRpdmVVUChUaGlzLT53aW5lRDNERGV2aWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBQcmltaXRpdmVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBQcmltaXRpdmVDb3VudCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgVmVydGljZXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHN0cmlkZSk7Cn0KCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzNfRHJhd1ByaW1pdGl2ZShJRGlyZWN0M0REZXZpY2UzICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNEUFJJTUlUSVZFVFlQRSBQcmltaXRpdmVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBWZXJ0ZXhUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2b2lkICpWZXJ0aWNlcywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgVmVydGV4Q291bnQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIEZsYWdzKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UzLCBpZmFjZSk7CiAgICBUUkFDRV8oZGRyYXdfdGh1bmspKCIoJXApLT4oJTA4eCwlMDhseCwlcCwlMDhseCwlMDhseCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlNyBpbnRlcmZhY2UuXG4iLCBUaGlzLCBQcmltaXRpdmVUeXBlLCBWZXJ0ZXhUeXBlLCBWZXJ0aWNlcywgVmVydGV4Q291bnQsIEZsYWdzKTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2U3X0RyYXdQcmltaXRpdmUoSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlNyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFByaW1pdGl2ZVR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFZlcnRleFR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFZlcnRpY2VzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBWZXJ0ZXhDb3VudCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRmxhZ3MpOwp9CgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8yX0RyYXdQcmltaXRpdmUoSURpcmVjdDNERGV2aWNlMiAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRFBSSU1JVElWRVRZUEUgUHJpbWl0aXZlVHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNEVkVSVEVYVFlQRSBWZXJ0ZXhUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2b2lkICpWZXJ0aWNlcywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgVmVydGV4Q291bnQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIEZsYWdzKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UyLCBpZmFjZSk7CiAgICBEV09SRCBGVkY7CiAgICBUUkFDRV8oZGRyYXdfdGh1bmspKCIoJXApLT4oJTA4eCwlMDh4LCVwLCUwOGx4LCUwOGx4KSB0aHVua2luZyB0byBJRGlyZWN0M0REZXZpY2U3IGludGVyZmFjZS5cbiIsIFRoaXMsIFByaW1pdGl2ZVR5cGUsIFZlcnRleFR5cGUsIFZlcnRpY2VzLCBWZXJ0ZXhDb3VudCwgRmxhZ3MpOwoKICAgIHN3aXRjaChWZXJ0ZXhUeXBlKQogICAgewogICAgICAgIGNhc2UgRDNEVlRfVkVSVEVYOiBGVkYgPSBEM0RGVkZfVkVSVEVYOyBicmVhazsKICAgICAgICBjYXNlIEQzRFZUX0xWRVJURVg6IEZWRiA9IEQzREZWRl9MVkVSVEVYOyBicmVhazsKICAgICAgICBjYXNlIEQzRFZUX1RMVkVSVEVYOiBGVkYgPSBEM0RGVkZfVExWRVJURVg7IGJyZWFrOwogICAgICAgIGRlZmF1bHQ6CiAgICAgICAgICAgIEVSUigiVW5leHBlY3RlZCB2ZXJ0ZXggdHlwZSAlZFxuIiwgVmVydGV4VHlwZSk7CiAgICAgICAgICAgIHJldHVybiBEREVSUl9JTlZBTElEUEFSQU1TOyAgLyogU2hvdWxkIG5ldmVyIGhhcHBlbiAqLwogICAgfQoKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2U3X0RyYXdQcmltaXRpdmUoSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlNyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFByaW1pdGl2ZVR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEZWRiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgVmVydGljZXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFZlcnRleENvdW50LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBGbGFncyk7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0REZXZpY2U3OjpEcmF3SW5kZXhlZFByaW1pdGl2ZQogKgogKiBEcmF3cyB2ZXJ0aWNlcyBmcm9tIGFuIGFwcGxpY2F0aW9uLXByb3ZpZGVkIHBvaW50ZXIsIGJhc2VkIG9uIHRoZSBpbmRleAogKiBudW1iZXJzIGluIGEgV09SRCBhcnJheS4KICoKICogVmVyc2lvbiAyLCAzIGFuZCA3LiBUaGUgdmVyc2lvbiA3IHRodW5rIHRyYW5zbGF0ZXMgdGhlIHZlcnRleCB0eXBlIGludG8KICogYW4gRlZGIGZvcm1hdCBmb3IgRDNENwogKgogKiBQYXJhbXM6CiAqICBQcmltaXRpdmVUeXBlOiBUaGUgcHJpbWl0aXZlIHR5cGUgdG8gZHJhdwogKiAgVmVydGV4VHlwZTogVGhlIEZWRiB2ZXJ0ZXggZGVzY3JpcHRpb24KICogIFZlcnRpY2VzOiBQb2ludGVyIHRvIHRoZSB2ZXJ0ZXggYXJyYXkKICogIFZlcnRleENvdW50OiA/CiAqICBJbmRpY2VzOiBQb2ludGVyIHRvIHRoZSBpbmRleCBhcnJheQogKiAgSW5kZXhDb3VudDogTnVtYmVyIG9mIGluZGljZXMgPSBOdW1iZXIgb2YgdmVydGljZXMgdG8gZHJhdwogKiAgRmxhZ3M6IEFzIHVzdWFsLCBzb21lIGZsYWdzCiAqCiAqIFJldHVybnM6CiAqICBEM0RfT0sgb24gc3VjY2VzcwogKiAgRERFUlJfSU5WQUxJRFBBUkFNUyBpZiBWZXJ0aWNlcyBvciBJbmRpY2VzIGlzIE5VTEwKICogIEZvciBkZXRhaWxzLCBzZWUgSVdpbmVEM0REZXZpY2U6OkRyYXdJbmRleGVkUHJpbWl0aXZlVVAKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKSURpcmVjdDNERGV2aWNlSW1wbF83X0RyYXdJbmRleGVkUHJpbWl0aXZlKElEaXJlY3QzRERldmljZTcgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNEUFJJTUlUSVZFVFlQRSBQcmltaXRpdmVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgVmVydGV4VHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHZvaWQgKlZlcnRpY2VzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgVmVydGV4Q291bnQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBXT1JEICpJbmRpY2VzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgSW5kZXhDb3VudCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIEZsYWdzKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2U3LCBpZmFjZSk7CiAgICBVSU5UIFByaW1pdGl2ZUNvdW50ID0gMDsKICAgIEhSRVNVTFQgaHI7CiAgICBUUkFDRSgiKCVwKS0+KCUwOHgsJTA4bHgsJXAsJTA4bHgsJXAsJTA4bHgsJTA4bHgpOiBSZWxheSFcbiIsIFRoaXMsIFByaW1pdGl2ZVR5cGUsIFZlcnRleFR5cGUsIFZlcnRpY2VzLCBWZXJ0ZXhDb3VudCwgSW5kaWNlcywgSW5kZXhDb3VudCwgRmxhZ3MpOwogICAgLyogR2V0IHRoZSBwcmltaXRpdmUgbnVtYmVyICovCiAgICBzd2l0Y2goUHJpbWl0aXZlVHlwZSkKICAgIHsKICAgICAgY2FzZSBEM0RQVF9QT0lOVExJU1Q6IAogICAgICAgIFByaW1pdGl2ZUNvdW50ID0gSW5kZXhDb3VudDsKICAgICAgICBicmVhazsKCiAgICAgIGNhc2UgRDNEUFRfTElORUxJU1Q6IAogICAgICAgIFByaW1pdGl2ZUNvdW50ID0gSW5kZXhDb3VudCAvIDI7CiAgICAgICAgYnJlYWs7CgogICAgICBjYXNlIEQzRFBUX0xJTkVTVFJJUDoKICAgICAgICBQcmltaXRpdmVDb3VudCA9IEluZGV4Q291bnQgLSAxOwogICAgICAgIGJyZWFrOwoKICAgICAgY2FzZSBEM0RQVF9UUklBTkdMRUxJU1Q6CiAgICAgICAgUHJpbWl0aXZlQ291bnQgPSBJbmRleENvdW50IC8gMzsKICAgICAgICBicmVhazsKCiAgICAgIGNhc2UgRDNEUFRfVFJJQU5HTEVTVFJJUDoKICAgICAgICBQcmltaXRpdmVDb3VudCA9IEluZGV4Q291bnQgLSAyOwogICAgICAgIGJyZWFrOwoKICAgICAgY2FzZSBEM0RQVF9UUklBTkdMRUZBTjoKICAgICAgICBQcmltaXRpdmVDb3VudCA9IEluZGV4Q291bnQgLSAyOwogICAgICAgIGJyZWFrOwoKICAgICAgZGVmYXVsdDogcmV0dXJuIERERVJSX0lOVkFMSURQQVJBTVM7CiAgICB9CgogICAgLyogU2V0IHRoZSBEM0REZXZpY2UncyBGVkYgKi8KICAgIGhyID0gSVdpbmVEM0REZXZpY2VfU2V0RlZGKFRoaXMtPndpbmVEM0REZXZpY2UsIFZlcnRleFR5cGUpOwogICAgaWYoRkFJTEVEKGhyKSkKICAgIHsKICAgICAgICBFUlIoIiAoJXApIFNldHRpbmcgdGhlIEZWRiBmYWlsZWQsIGhyID0gJWx4IVxuIiwgVGhpcywgaHIpOwogICAgICAgIHJldHVybiBocjsKICAgIH0KCiAgICByZXR1cm4gSVdpbmVEM0REZXZpY2VfRHJhd0luZGV4ZWRQcmltaXRpdmVVUChUaGlzLT53aW5lRDNERGV2aWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgUHJpbWl0aXZlVHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIDAgLyogTWluVmVydGV4SW5kZXggKi8sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBWZXJ0ZXhDb3VudCAvKiBVSU5UIE51bVZlcnRleEluZGV4ICovLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgUHJpbWl0aXZlQ291bnQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBJbmRpY2VzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgV0lORUQzREZNVF9JTkRFWDE2LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgVmVydGljZXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBnZXRfZmxleGlibGVfdmVydGV4X3NpemUoVmVydGV4VHlwZSkpOwp9CgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8zX0RyYXdJbmRleGVkUHJpbWl0aXZlKElEaXJlY3QzRERldmljZTMgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNEUFJJTUlUSVZFVFlQRSBQcmltaXRpdmVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgVmVydGV4VHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHZvaWQgKlZlcnRpY2VzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgVmVydGV4Q291bnQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBXT1JEICpJbmRpY2VzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgSW5kZXhDb3VudCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIEZsYWdzKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UzLCBpZmFjZSk7CiAgICBUUkFDRV8oZGRyYXdfdGh1bmspKCIoJXApLT4oJTA4eCwlMDhseCwlcCwlMDhseCwlcCwlMDhseCwlMDhseCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlNyBpbnRlcmZhY2UuXG4iLCBUaGlzLCBQcmltaXRpdmVUeXBlLCBWZXJ0ZXhUeXBlLCBWZXJ0aWNlcywgVmVydGV4Q291bnQsIEluZGljZXMsIEluZGV4Q291bnQsIEZsYWdzKTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2U3X0RyYXdJbmRleGVkUHJpbWl0aXZlKElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTcpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgUHJpbWl0aXZlVHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFZlcnRleFR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBWZXJ0aWNlcywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFZlcnRleENvdW50LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgSW5kaWNlcywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEluZGV4Q291bnQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBGbGFncyk7Cn0KCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzJfRHJhd0luZGV4ZWRQcmltaXRpdmUoSURpcmVjdDNERGV2aWNlMiAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RQUklNSVRJVkVUWVBFIFByaW1pdGl2ZVR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RWRVJURVhUWVBFIFZlcnRleFR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2b2lkICpWZXJ0aWNlcywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIFZlcnRleENvdW50LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgV09SRCAqSW5kaWNlcywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIEluZGV4Q291bnQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBGbGFncykKewogICAgRFdPUkQgRlZGOwogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlMiwgaWZhY2UpOwogICAgVFJBQ0VfKGRkcmF3X3RodW5rKSgiKCVwKS0+KCUwOHgsJTA4eCwlcCwlMDhseCwlcCwlMDhseCwlMDhseCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlNyBpbnRlcmZhY2UuXG4iLCBUaGlzLCBQcmltaXRpdmVUeXBlLCBWZXJ0ZXhUeXBlLCBWZXJ0aWNlcywgVmVydGV4Q291bnQsIEluZGljZXMsIEluZGV4Q291bnQsIEZsYWdzKTsKCiAgICBzd2l0Y2goVmVydGV4VHlwZSkKICAgIHsKICAgICAgICBjYXNlIEQzRFZUX1ZFUlRFWDogRlZGID0gRDNERlZGX1ZFUlRFWDsgYnJlYWs7CiAgICAgICAgY2FzZSBEM0RWVF9MVkVSVEVYOiBGVkYgPSBEM0RGVkZfTFZFUlRFWDsgYnJlYWs7CiAgICAgICAgY2FzZSBEM0RWVF9UTFZFUlRFWDogRlZGID0gRDNERlZGX1RMVkVSVEVYOyBicmVhazsKICAgICAgICBkZWZhdWx0OgogICAgICAgICAgICBFUlIoIlVuZXhwZWN0ZWQgdmVydGV4IHR5cGUgJWRcbiIsIFZlcnRleFR5cGUpOwogICAgICAgICAgICByZXR1cm4gRERFUlJfSU5WQUxJRFBBUkFNUzsgIC8qIFNob3VsZCBuZXZlciBoYXBwZW4gKi8KICAgIH0KCiAgICByZXR1cm4gSURpcmVjdDNERGV2aWNlN19EcmF3SW5kZXhlZFByaW1pdGl2ZShJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0REZXZpY2U3KSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFByaW1pdGl2ZVR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBGVkYsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBWZXJ0aWNlcywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFZlcnRleENvdW50LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgSW5kaWNlcywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEluZGV4Q291bnQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBGbGFncyk7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0REZXZpY2U3OjpTZXRDbGlwU3RhdHVzCiAqCiAqIFNldHMgdGhlIGNsaXAgc3RhdHVzLiBUaGlzIGRlZmluZXMgdGhpbmdzIGFzIGNsaXBwaW5nIGNvbmRpdGlvbnMgYW5kCiAqIHRoZSBleHRlbnRzIG9mIHRoZSBjbGlwcGluZyByZWdpb24uCiAqCiAqIFZlcnNpb24gMiwgMyBhbmQgNwogKgogKiBQYXJhbXM6CiAqICBDbGlwU3RhdHVzOgogKgogKiBSZXR1cm5zOgogKiAgRDNEX09LIGJlY2F1c2UgaXQncyBhIHN0dWIKICogIChEREVSUl9JTlZBTElEUEFSQU1TIGlmIENsaXBTdGF0dXMgPT0gTlVMTCkKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKSURpcmVjdDNERGV2aWNlSW1wbF83X1NldENsaXBTdGF0dXMoSURpcmVjdDNERGV2aWNlNyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRENMSVBTVEFUVVMgKkNsaXBTdGF0dXMpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTcsIGlmYWNlKTsKICAgIEZJWE1FKCIoJXApLT4oJXApOiBTdHViIVxuIiwgVGhpcywgQ2xpcFN0YXR1cyk7CgogICAgLyogRDNEQ0xJUFNUQVRVUyBhbmQgV0lORUQzRENMSVBTVEFUVVMgYXJlIGRpZmZlcmVudC4gSSBkb24ndCBrbm93IGhvdyB0byBjb252ZXJ0IHRoZW0KICAgICAqIFBlcmhhcHMgdGhpcyBuZWVkcyBhIG5ldyBkYXRhIHR5cGUgYW5kIGFuIGFkZGl0aW9uYWwgSVdpbmVEM0REZXZpY2UgbWV0aG9kCiAgICAgKi8KICAgIC8qIHJldHVybiBJV2luZUQzRERldmljZV9TZXRDbGlwU3RhdHVzKFRoaXMtPndpbmVEM0REZXZpY2UsIENsaXBTdGF0dXMpOyovCiAgICByZXR1cm4gRDNEX09LOwp9CgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8zX1NldENsaXBTdGF0dXMoSURpcmVjdDNERGV2aWNlMyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRENMSVBTVEFUVVMgKkNsaXBTdGF0dXMpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTMsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglcCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlNyBpbnRlcmZhY2UuXG4iLCBUaGlzLCBDbGlwU3RhdHVzKTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2U3X1NldENsaXBTdGF0dXMoSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlNyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIENsaXBTdGF0dXMpOwp9CgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8yX1NldENsaXBTdGF0dXMoSURpcmVjdDNERGV2aWNlMiAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRENMSVBTVEFUVVMgKkNsaXBTdGF0dXMpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTIsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglcCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlNyBpbnRlcmZhY2UuXG4iLCBUaGlzLCBDbGlwU3RhdHVzKTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2U3X1NldENsaXBTdGF0dXMoSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlNyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIENsaXBTdGF0dXMpOwp9CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSURpcmVjdDNERGV2aWNlNzo6R2V0Q2xpcFN0YXR1cwogKgogKiBSZXR1cm5zIHRoZSBjbGlwIHN0YXR1cwogKgogKiBQYXJhbXM6CiAqICBDbGlwU3RhdHVzOiBBZGRyZXNzIHRvIHdyaXRlIHRoZSBjbGlwIHN0YXR1cyB0bwogKgogKiBSZXR1cm5zOgogKiAgRDNEX09LIGJlY2F1c2UgaXQncyBhIHN0dWIKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKSURpcmVjdDNERGV2aWNlSW1wbF83X0dldENsaXBTdGF0dXMoSURpcmVjdDNERGV2aWNlNyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRENMSVBTVEFUVVMgKkNsaXBTdGF0dXMpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTcsIGlmYWNlKTsKICAgIEZJWE1FKCIoJXApLT4oJXApOiBTdHViIVxuIiwgVGhpcywgQ2xpcFN0YXR1cyk7CgogICAgLyogRDNEQ0xJUFNUQVRVUyBhbmQgV0lORUQzRENMSVBTVEFUVVMgYXJlIGRpZmZlcmVudC4gSSBkb24ndCBrbm93IGhvdyB0byBjb252ZXJ0IHRoZW0gKi8KICAgIC8qIHJldHVybiBJV2luZUQzRERldmljZV9HZXRDbGlwU3RhdHVzKFRoaXMtPndpbmVEM0REZXZpY2UsIENsaXBTdGF0dXMpOyovCiAgICByZXR1cm4gRDNEX09LOwp9CgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8zX0dldENsaXBTdGF0dXMoSURpcmVjdDNERGV2aWNlMyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRENMSVBTVEFUVVMgKkNsaXBTdGF0dXMpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTMsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglcCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlNyBpbnRlcmZhY2UuXG4iLCBUaGlzLCBDbGlwU3RhdHVzKTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2U3X0dldENsaXBTdGF0dXMoSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlNyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIENsaXBTdGF0dXMpOwp9CgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8yX0dldENsaXBTdGF0dXMoSURpcmVjdDNERGV2aWNlMiAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRENMSVBTVEFUVVMgKkNsaXBTdGF0dXMpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTIsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglcCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlNyBpbnRlcmZhY2UuXG4iLCBUaGlzLCBDbGlwU3RhdHVzKTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2U3X0dldENsaXBTdGF0dXMoSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlNyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIENsaXBTdGF0dXMpOwp9CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSURpcmVjdDNERGV2aWNlOjpEcmF3UHJpbWl0aXZlU3RyaWRlZAogKgogKiBEcmF3cyB2ZXJ0aWNlcyBkZXNjcmliZWQgYnkgYSBEM0REUkFXUFJJTUlUSVZFU1RSSURFRERBVEEgc3RydWN0dXJlLgogKgogKiBWZXJzaW9uIDMgYW5kIDcKICoKICogUGFyYW1zOgogKiAgUHJpbWl0aXZlVHlwZTogVGhlIHByaW1pdGl2ZSB0eXBlIHRvIGRyYXcKICogIFZlcnRleFR5cGU6IFRoZSBGVkYgZGVzY3JpcHRpb24gb2YgdGhlIHZlcnRpY2VzIHRvIGRyYXcgKGZvciB0aGUgc3RyaWRlPz8pCiAqICBEM0REcmF3UHJpbVN0cmlkZURhdGE6IEEgRDNERFJBV1BSSU1JVElWRVNUUklERUREQVRBIHN0cnVjdHVyZSBkZXNjcmliaW5nCiAqICAgICAgICAgICAgICAgICAgICAgICAgIHRoZSB2ZXJ0ZXggZGF0YSBsb2NhdGlvbnMKICogIFZlcnRleENvdW50OiBUaGUgbnVtYmVyIG9mIHZlcnRpY2VzIHRvIGRyYXcKICogIEZsYWdzOiBTb21lIGZsYWdzCiAqCiAqIFJldHVybnM6CiAqICBEM0RfT0ssIGJlY2F1c2UgaXQncyBhIHN0dWIKICogIChEREVSUl9JTlZBTElEUEFSQU1TIGlmIEQzRERyYXdQcmltU3RyaWRlRGF0YSBpcyBOVUxMKQogKiAgKEZvciBkZXRhaWxzLCBzZWUgSVdpbmVEM0REZXZpY2U6OkRyYXdQcmltaXRpdmVTdHJpZGVkKQogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0REZXZpY2VJbXBsXzdfRHJhd1ByaW1pdGl2ZVN0cmlkZWQoSURpcmVjdDNERGV2aWNlNyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RQUklNSVRJVkVUWVBFIFByaW1pdGl2ZVR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBWZXJ0ZXhUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNERFJBV1BSSU1JVElWRVNUUklERUREQVRBICpEM0REcmF3UHJpbVN0cmlkZURhdGEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBWZXJ0ZXhDb3VudCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIEZsYWdzKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2U3LCBpZmFjZSk7CiAgICBXaW5lRGlyZWN0M0RWZXJ0ZXhTdHJpZGVkRGF0YSBXaW5lRDNEU3RyaWRlZDsKICAgIGludCBpOwogICAgVUlOVCBQcmltaXRpdmVDb3VudDsKCiAgICBUUkFDRSgiKCVwKS0+KCUwOHgsJTA4bHgsJXAsJTA4bHgsJTA4bHgpOiBzdHViIVxuIiwgVGhpcywgUHJpbWl0aXZlVHlwZSwgVmVydGV4VHlwZSwgRDNERHJhd1ByaW1TdHJpZGVEYXRhLCBWZXJ0ZXhDb3VudCwgRmxhZ3MpOwoKICAgIC8qIEdldCB0aGUgc3RyaWRlZCBkYXRhIHJpZ2h0LiB0aGUgd2luZWQzZCBzdHJ1Y3R1cmUgaXMgYSBiaXQgYmlnZ2VyCiAgICAgKiBXYXRjaCBvdXQ6IFRoZSBjb250ZW50cyBvZiB0aGUgc3RyaWRlZCBkYXRhIGFyZSBkZXRlcm1pbmVkIGJ5IHRoZSBmdmYsCiAgICAgKiBub3QgYnkgdGhlIG1lbWJlcnMgc2V0IGluIEQzRERyYXdQcmltU3RyaWRlRGF0YS4gU28gaXQncyB2YWxpZAogICAgICogdG8gaGF2ZSBkaWZmdXNlLmxwdkRhdGEgc2V0IHRvIDB4ZGVhZGJlZWYgaWYgdGhlIGRpZmZ1c2UgZmxhZyBpcwogICAgICogbm90IHNldCBpbiB0aGUgZnZmLgogICAgICovCiAgICBpZihWZXJ0ZXhUeXBlICYgRDNERlZGX1BPU0lUSU9OX01BU0spCiAgICB7CiAgICAgICAgbWVtc2V0KCZXaW5lRDNEU3RyaWRlZCwgMCwgc2l6ZW9mKFdpbmVEM0RTdHJpZGVkKSk7CiAgICAgICAgV2luZUQzRFN0cmlkZWQudS5zLnBvc2l0aW9uLmxwRGF0YSA9IEQzRERyYXdQcmltU3RyaWRlRGF0YS0+cG9zaXRpb24ubHB2RGF0YTsKICAgICAgICBXaW5lRDNEU3RyaWRlZC51LnMucG9zaXRpb24uZHdTdHJpZGUgPSBEM0REcmF3UHJpbVN0cmlkZURhdGEtPnBvc2l0aW9uLmR3U3RyaWRlOwogICAgICAgIFdpbmVEM0RTdHJpZGVkLnUucy5wb3NpdGlvbi5kd1R5cGUgPSBXSU5FRDNEREVDTFRZUEVfRkxPQVQzOwogICAgICAgIGlmIChWZXJ0ZXhUeXBlICYgRDNERlZGX1hZWlJIVykKICAgICAgICB7CiAgICAgICAgICAgIFdpbmVEM0RTdHJpZGVkLnUucy5wb3NpdGlvbi5kd1R5cGUgPSBXSU5FRDNEREVDTFRZUEVfRkxPQVQ0OwogICAgICAgICAgICBXaW5lRDNEU3RyaWRlZC51LnMucG9zaXRpb25fdHJhbnNmb3JtZWQgPSBUUlVFOwogICAgICAgIH0gZWxzZQogICAgICAgICAgICBXaW5lRDNEU3RyaWRlZC51LnMucG9zaXRpb25fdHJhbnNmb3JtZWQgPSBGQUxTRTsKICAgIH0KCiAgICBpZihWZXJ0ZXhUeXBlICYgRDNERlZGX05PUk1BTCkKICAgIHsKICAgICAgICBXaW5lRDNEU3RyaWRlZC51LnMubm9ybWFsLmxwRGF0YSA9IEQzRERyYXdQcmltU3RyaWRlRGF0YS0+bm9ybWFsLmxwdkRhdGE7CiAgICAgICAgV2luZUQzRFN0cmlkZWQudS5zLm5vcm1hbC5kd1N0cmlkZSA9IEQzRERyYXdQcmltU3RyaWRlRGF0YS0+bm9ybWFsLmR3U3RyaWRlOwogICAgICAgIFdpbmVEM0RTdHJpZGVkLnUucy5ub3JtYWwuZHdUeXBlID0gV0lORUQzRERFQ0xUWVBFX0ZMT0FUMzsKICAgIH0KCiAgICBpZihWZXJ0ZXhUeXBlICYgRDNERlZGX0RJRkZVU0UpCiAgICB7CiAgICAgICAgV2luZUQzRFN0cmlkZWQudS5zLmRpZmZ1c2UubHBEYXRhID0gRDNERHJhd1ByaW1TdHJpZGVEYXRhLT5kaWZmdXNlLmxwdkRhdGE7CiAgICAgICAgV2luZUQzRFN0cmlkZWQudS5zLmRpZmZ1c2UuZHdTdHJpZGUgPSBEM0REcmF3UHJpbVN0cmlkZURhdGEtPmRpZmZ1c2UuZHdTdHJpZGU7CiAgICAgICAgV2luZUQzRFN0cmlkZWQudS5zLmRpZmZ1c2UuZHdUeXBlID0gV0lORUQzRERFQ0xUWVBFX1NIT1JUNDsKICAgIH0KCiAgICBpZihWZXJ0ZXhUeXBlICYgRDNERlZGX1NQRUNVTEFSKQogICAgewogICAgICAgIFdpbmVEM0RTdHJpZGVkLnUucy5zcGVjdWxhci5scERhdGEgPSBEM0REcmF3UHJpbVN0cmlkZURhdGEtPnNwZWN1bGFyLmxwdkRhdGE7CiAgICAgICAgV2luZUQzRFN0cmlkZWQudS5zLnNwZWN1bGFyLmR3U3RyaWRlID0gRDNERHJhd1ByaW1TdHJpZGVEYXRhLT5zcGVjdWxhci5kd1N0cmlkZTsKICAgICAgICBXaW5lRDNEU3RyaWRlZC51LnMuc3BlY3VsYXIuZHdUeXBlID0gV0lORUQzRERFQ0xUWVBFX1NIT1JUNDsKICAgIH0KCiAgICBmb3IoIGkgPSAwOyBpIDwgR0VUX1RFWENPVU5UX0ZST01fRlZGKFZlcnRleFR5cGUpOyBpKyspCiAgICB7CiAgICAgICAgV2luZUQzRFN0cmlkZWQudS5zLnRleENvb3Jkc1tpXS5scERhdGEgPSBEM0REcmF3UHJpbVN0cmlkZURhdGEtPnRleHR1cmVDb29yZHNbaV0ubHB2RGF0YTsKICAgICAgICBXaW5lRDNEU3RyaWRlZC51LnMudGV4Q29vcmRzW2ldLmR3U3RyaWRlID0gRDNERHJhd1ByaW1TdHJpZGVEYXRhLT50ZXh0dXJlQ29vcmRzW2ldLmR3U3RyaWRlOwogICAgICAgIHN3aXRjaChHRVRfVEVYQ09PUkRfU0laRV9GUk9NX0ZWRihWZXJ0ZXhUeXBlLCBpKSkKICAgICAgICB7CiAgICAgICAgICAgIGNhc2UgMTogV2luZUQzRFN0cmlkZWQudS5zLnRleENvb3Jkc1tpXS5kd1R5cGUgPSBXSU5FRDNEREVDTFRZUEVfRkxPQVQxOyBicmVhazsKICAgICAgICAgICAgY2FzZSAyOiBXaW5lRDNEU3RyaWRlZC51LnMudGV4Q29vcmRzW2ldLmR3VHlwZSA9IFdJTkVEM0RERUNMVFlQRV9GTE9BVDI7IGJyZWFrOwogICAgICAgICAgICBjYXNlIDM6IFdpbmVEM0RTdHJpZGVkLnUucy50ZXhDb29yZHNbaV0uZHdUeXBlID0gV0lORUQzRERFQ0xUWVBFX0ZMT0FUMzsgYnJlYWs7CiAgICAgICAgICAgIGNhc2UgNDogV2luZUQzRFN0cmlkZWQudS5zLnRleENvb3Jkc1tpXS5kd1R5cGUgPSBXSU5FRDNEREVDTFRZUEVfRkxPQVQ0OyBicmVhazsKICAgICAgICAgICAgZGVmYXVsdDogRVJSKCJVbmV4cGVjdGVkIHRleHR1cmUgY29vcmRpbmF0ZSBzaXplICVsZFxuIiwKICAgICAgICAgICAgICAgICAgICAgICAgIEdFVF9URVhDT09SRF9TSVpFX0ZST01fRlZGKFZlcnRleFR5cGUsIGkpKTsKICAgICAgICB9CiAgICB9CgogICAgLyogR2V0IHRoZSBwcmltaXRpdmUgY291bnQgKi8KICAgIHN3aXRjaChQcmltaXRpdmVUeXBlKQogICAgewogICAgICAgIGNhc2UgRDNEUFRfUE9JTlRMSVNUOiAKICAgICAgICAgIFByaW1pdGl2ZUNvdW50ID0gVmVydGV4Q291bnQ7CiAgICAgICAgICBicmVhazsKCiAgICAgICAgY2FzZSBEM0RQVF9MSU5FTElTVDogCiAgICAgICAgICBQcmltaXRpdmVDb3VudCA9IFZlcnRleENvdW50IC8gMjsKICAgICAgICAgIGJyZWFrOwoKICAgICAgICBjYXNlIEQzRFBUX0xJTkVTVFJJUDoKICAgICAgICAgIFByaW1pdGl2ZUNvdW50ID0gVmVydGV4Q291bnQgLSAxOwogICAgICAgICAgYnJlYWs7CgogICAgICAgIGNhc2UgRDNEUFRfVFJJQU5HTEVMSVNUOgogICAgICAgICAgUHJpbWl0aXZlQ291bnQgPSBWZXJ0ZXhDb3VudCAvIDM7CiAgICAgICAgICBicmVhazsKCiAgICAgICAgY2FzZSBEM0RQVF9UUklBTkdMRVNUUklQOgogICAgICAgICAgUHJpbWl0aXZlQ291bnQgPSBWZXJ0ZXhDb3VudCAtIDI7CiAgICAgICAgICBicmVhazsKCiAgICAgICAgY2FzZSBEM0RQVF9UUklBTkdMRUZBTjoKICAgICAgICAgIFByaW1pdGl2ZUNvdW50ID0gVmVydGV4Q291bnQgLSAyOwogICAgICAgICAgYnJlYWs7CgogICAgICAgIGRlZmF1bHQ6IHJldHVybiBEREVSUl9JTlZBTElEUEFSQU1TOwogICAgfQoKICAgIElXaW5lRDNERGV2aWNlX1NldEZWRihUaGlzLT53aW5lRDNERGV2aWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgIFZlcnRleFR5cGUpOwoKICAgIHJldHVybiBJV2luZUQzRERldmljZV9EcmF3UHJpbWl0aXZlU3RyaWRlZChUaGlzLT53aW5lRDNERGV2aWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFByaW1pdGl2ZVR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgUHJpbWl0aXZlQ291bnQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJldpbmVEM0RTdHJpZGVkKTsKfQoKc3RhdGljIEhSRVNVTFQgV0lOQVBJClRodW5rX0lEaXJlY3QzRERldmljZUltcGxfM19EcmF3UHJpbWl0aXZlU3RyaWRlZChJRGlyZWN0M0REZXZpY2UzICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRFBSSU1JVElWRVRZUEUgUHJpbWl0aXZlVHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIFZlcnRleFR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0REUkFXUFJJTUlUSVZFU1RSSURFRERBVEEgKkQzRERyYXdQcmltU3RyaWRlRGF0YSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIFZlcnRleENvdW50LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgRmxhZ3MpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTMsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglMDh4LCUwOGx4LCVwLCUwOGx4LCUwOGx4KSB0aHVua2luZyB0byBJRGlyZWN0M0REZXZpY2U3IGludGVyZmFjZS5cbiIsIFRoaXMsIFByaW1pdGl2ZVR5cGUsIFZlcnRleFR5cGUsIEQzRERyYXdQcmltU3RyaWRlRGF0YSwgVmVydGV4Q291bnQsIEZsYWdzKTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2U3X0RyYXdQcmltaXRpdmVTdHJpZGVkKElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTcpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgUHJpbWl0aXZlVHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFZlcnRleFR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0REcmF3UHJpbVN0cmlkZURhdGEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBWZXJ0ZXhDb3VudCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEZsYWdzKTsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTc6OkRyYXdJbmRleGVkUHJpbWl0aXZlU3RyaWRlZAogKgogKiBEcmF3cyBwcmltaXRpdmVzIHNwZWNpZmllZCBieSBzdHJpZGVkIGRhdGEgbG9jYXRpb25zIGJhc2VkIG9uIGluZGljZXMKICoKICogVmVyc2lvbiAzIGFuZCA3CiAqCiAqIFBhcmFtczoKICogIFByaW1pdGl2ZVR5cGU6CiAqCiAqIFJldHVybnM6CiAqICBEM0RfT0ssIGJlY2F1c2UgaXQncyBhIHN0dWIKICogIChEREVSUl9JTlZBTElEUEFSQU1TIGlmIEQzRERyYXdQcmltU3RyaWRlRGF0YSBpcyBOVUxMKQogKiAgKERERVJSX0lOVkFMSURQQVJBTVMgaWYgSW5kaWNlcyBpcyBOVUxMKQogKiAgKEZvciBtb3JlIGRldGFpbHMsIHNlZSBJV2luZUQzRERldmljZTo6RHJhd0luZGV4ZWRQcmltaXRpdmVTdHJpZGVkKQogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0REZXZpY2VJbXBsXzdfRHJhd0luZGV4ZWRQcmltaXRpdmVTdHJpZGVkKElEaXJlY3QzRERldmljZTcgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRFBSSU1JVElWRVRZUEUgUHJpbWl0aXZlVHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBWZXJ0ZXhUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRERSQVdQUklNSVRJVkVTVFJJREVEREFUQSAqRDNERHJhd1ByaW1TdHJpZGVEYXRhLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIFZlcnRleENvdW50LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFdPUkQgKkluZGljZXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgSW5kZXhDb3VudCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBGbGFncykKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlNywgaWZhY2UpOwogICAgRklYTUUoIiglcCktPiglMDh4LCUwOGx4LCVwLCUwOGx4LCVwLCUwOGx4LCUwOGx4KTogc3R1YiFcbiIsIFRoaXMsIFByaW1pdGl2ZVR5cGUsIFZlcnRleFR5cGUsIEQzRERyYXdQcmltU3RyaWRlRGF0YSwgVmVydGV4Q291bnQsIEluZGljZXMsIEluZGV4Q291bnQsIEZsYWdzKTsKCiAgICAvKiBJJ2xsIGltcGxlbWVudCBpdCBhcyBzb29uIGFzIEkgZmluZCBhIGFwcCB0byB0ZXN0IGl0LgogICAgICogVGhpcyBuZWVkcyBhbiBhZGRpdGlvbmFsIG1ldGhvZCBpbiBJV2luZUQzRERldmljZS4KICAgICAqLwogICAgcmV0dXJuIEQzRF9PSzsKfQoKc3RhdGljIEhSRVNVTFQgV0lOQVBJClRodW5rX0lEaXJlY3QzRERldmljZUltcGxfM19EcmF3SW5kZXhlZFByaW1pdGl2ZVN0cmlkZWQoSURpcmVjdDNERGV2aWNlMyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNEUFJJTUlUSVZFVFlQRSBQcmltaXRpdmVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIFZlcnRleFR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNERFJBV1BSSU1JVElWRVNUUklERUREQVRBICpEM0REcmF3UHJpbVN0cmlkZURhdGEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgVmVydGV4Q291bnQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgV09SRCAqSW5kaWNlcywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBJbmRleENvdW50LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIEZsYWdzKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UzLCBpZmFjZSk7CiAgICBUUkFDRV8oZGRyYXdfdGh1bmspKCIoJXApLT4oJTA4eCwlMDhseCwlcCwlMDhseCwlcCwlMDhseCwlMDhseCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlNyBpbnRlcmZhY2UuXG4iLCBpZmFjZSwgUHJpbWl0aXZlVHlwZSwgVmVydGV4VHlwZSwgRDNERHJhd1ByaW1TdHJpZGVEYXRhLCBWZXJ0ZXhDb3VudCwgSW5kaWNlcywgSW5kZXhDb3VudCwgRmxhZ3MpOwogICAgcmV0dXJuIElEaXJlY3QzRERldmljZTdfRHJhd0luZGV4ZWRQcmltaXRpdmVTdHJpZGVkKElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTcpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFByaW1pdGl2ZVR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgVmVydGV4VHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0REcmF3UHJpbVN0cmlkZURhdGEsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgVmVydGV4Q291bnQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgSW5kaWNlcywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBJbmRleENvdW50LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEZsYWdzKTsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTc6OkRyYXdQcmltaXRpdmVWQgogKgogKiBEcmF3cyBwcmltaXRpdmVzIGZyb20gYSB2ZXJ0ZXggYnVmZmVyIHRvIHRoZSBzY3JlZW4uCiAqCiAqIFZlcnNpb24gMyBhbmQgNwogKgogKiBQYXJhbXM6CiAqICBQcmltaXRpdmVUeXBlOiBUeXBlIG9mIHByaW1pdGl2ZSB0byBiZSByZW5kZXJlZC4KICogIEQzRFZlcnRleEJ1ZjogU291cmNlIFZlcnRleCBCdWZmZXIKICogIFN0YXJ0VmVydGV4OiBJbmRleCBvZiB0aGUgZmlyc3QgdmVydGV4IGZyb20gdGhlIGJ1ZmZlciB0byBiZSByZW5kZXJlZAogKiAgTnVtVmVydGljZXM6IE51bWJlciBvZiB2ZXJ0aWNlcyB0byBiZSByZW5kZXJlZAogKiAgRmxhZ3M6IENhbiBiZSBEM0REUF9XQUlUIHRvIHdhaXQgdW50aWwgcmVuZGVyaW5nIGhhcyBmaW5pc2hlZAogKgogKiBSZXR1cm4gdmFsdWVzCiAqICBEM0RfT0sgb24gc3VjY2VzcwogKiAgRERFUlJfSU5WQUxJRFBBUkFNUyBpZiBEM0RWZXJ0ZXhCdWYgaXMgTlVMTAogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0REZXZpY2VJbXBsXzdfRHJhd1ByaW1pdGl2ZVZCKElEaXJlY3QzRERldmljZTcgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRFBSSU1JVElWRVRZUEUgUHJpbWl0aXZlVHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3ICpEM0RWZXJ0ZXhCdWYsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgU3RhcnRWZXJ0ZXgsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgTnVtVmVydGljZXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgRmxhZ3MpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTcsIGlmYWNlKTsKICAgIElEaXJlY3QzRFZlcnRleEJ1ZmZlckltcGwgKnZiID0gSUNPTV9PQkpFQ1QoSURpcmVjdDNEVmVydGV4QnVmZmVySW1wbCwgSURpcmVjdDNEVmVydGV4QnVmZmVyNywgRDNEVmVydGV4QnVmKTsKICAgIFVJTlQgUHJpbWl0aXZlQ291bnQ7CiAgICBIUkVTVUxUIGhyOwogICAgRFdPUkQgc3RyaWRlOwogICAgV0lORUQzRFZFUlRFWEJVRkZFUl9ERVNDIERlc2M7CgogICAgVFJBQ0UoIiglcCktPiglMDh4LCVwLCUwOGx4LCUwOGx4LCUwOGx4KVxuIiwgVGhpcywgUHJpbWl0aXZlVHlwZSwgRDNEVmVydGV4QnVmLCBTdGFydFZlcnRleCwgTnVtVmVydGljZXMsIEZsYWdzKTsKCiAgICAvKiBTYW5pdHkgY2hlY2tzICovCiAgICBpZighdmIpCiAgICB7CiAgICAgICAgRVJSKCIoJXApIE5vIFZlcnRleCBidWZmZXIgc3BlY2lmaWVkXG4iLCBUaGlzKTsKICAgICAgICByZXR1cm4gRERFUlJfSU5WQUxJRFBBUkFNUzsKICAgIH0KCiAgICAvKiBHZXQgdGhlIHByaW1pdGl2ZSBjb3VudCAqLwogICAgc3dpdGNoKFByaW1pdGl2ZVR5cGUpCiAgICB7CiAgICAgICAgY2FzZSBEM0RQVF9QT0lOVExJU1Q6IAogICAgICAgICAgUHJpbWl0aXZlQ291bnQgPSBOdW1WZXJ0aWNlczsKICAgICAgICAgIGJyZWFrOwoKICAgICAgICBjYXNlIEQzRFBUX0xJTkVMSVNUOiAKICAgICAgICAgIFByaW1pdGl2ZUNvdW50ID0gTnVtVmVydGljZXMgLyAyOwogICAgICAgICAgYnJlYWs7CgogICAgICAgIGNhc2UgRDNEUFRfTElORVNUUklQOgogICAgICAgICAgUHJpbWl0aXZlQ291bnQgPSBOdW1WZXJ0aWNlcyAtIDE7CiAgICAgICAgICBicmVhazsKCiAgICAgICAgY2FzZSBEM0RQVF9UUklBTkdMRUxJU1Q6CiAgICAgICAgICBQcmltaXRpdmVDb3VudCA9IE51bVZlcnRpY2VzIC8gMzsKICAgICAgICAgIGJyZWFrOwoKICAgICAgICBjYXNlIEQzRFBUX1RSSUFOR0xFU1RSSVA6CiAgICAgICAgICBQcmltaXRpdmVDb3VudCA9IE51bVZlcnRpY2VzIC0gMjsKICAgICAgICAgIGJyZWFrOwoKICAgICAgICBjYXNlIEQzRFBUX1RSSUFOR0xFRkFOOgogICAgICAgICAgUHJpbWl0aXZlQ291bnQgPSBOdW1WZXJ0aWNlcyAtIDI7CiAgICAgICAgICBicmVhazsKCiAgICAgICAgZGVmYXVsdDogcmV0dXJuIERERVJSX0lOVkFMSURQQVJBTVM7CiAgICB9CgogICAgLyogR2V0IHRoZSBGVkYgb2YgdGhlIHZlcnRleCBidWZmZXIsIGFuZCBpdHMgc3RyaWRlICovCiAgICBociA9IElXaW5lRDNEVmVydGV4QnVmZmVyX0dldERlc2ModmItPndpbmVEM0RWZXJ0ZXhCdWZmZXIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJkRlc2MpOwogICAgaWYoaHIgIT0gRDNEX09LKQogICAgewogICAgICAgIEVSUigiKCVwKSBJV2luZUQzRFZlcnRleEJ1ZmZlcjo6R2V0RGVzYyBmYWlsZWQgd2l0aCBociA9ICUwOGx4XG4iLCBUaGlzLCBocik7CiAgICAgICAgcmV0dXJuIGhyOwogICAgfQogICAgc3RyaWRlID0gZ2V0X2ZsZXhpYmxlX3ZlcnRleF9zaXplKERlc2MuRlZGKTsKCiAgICBociA9IElXaW5lRDNERGV2aWNlX1NldEZWRihUaGlzLT53aW5lRDNERGV2aWNlLCBEZXNjLkZWRik7CiAgICBpZihGQUlMRUQoaHIpKQogICAgewogICAgICAgIEVSUigiICglcCkgU2V0dGluZyB0aGUgRlZGIGZhaWxlZCwgaHIgPSAlbHghXG4iLCBUaGlzLCBocik7CiAgICAgICAgcmV0dXJuIGhyOwogICAgfQoKICAgIC8qIFNldCB0aGUgdmVydGV4IHN0cmVhbSBzb3VyY2UgKi8KICAgIGhyID0gSVdpbmVEM0REZXZpY2VfU2V0U3RyZWFtU291cmNlKFRoaXMtPndpbmVEM0REZXZpY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAwIC8qIFN0cmVhbU51bWJlciAqLywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHZiLT53aW5lRDNEVmVydGV4QnVmZmVyLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgMCAvKiBTdGFydFZlcnRleCAtIHdlIHBhc3MgdGhpcyB0byBEcmF3UHJpbWl0aXZlICovLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc3RyaWRlKTsKICAgIGlmKGhyICE9IEQzRF9PSykKICAgIHsKICAgICAgICBFUlIoIiglcCkgSURpcmVjdDNERGV2aWNlOjpTZXRTdHJlYW1Tb3VyY2UgZmFpbGVkIHdpdGggaHIgPSAlMDhseFxuIiwgVGhpcywgaHIpOwogICAgICAgIHJldHVybiBocjsKICAgIH0KCiAgICAvKiBOb3cgZHJhdyB0aGUgcHJpbWl0aXZlcyAqLwogICAgcmV0dXJuIElXaW5lRDNERGV2aWNlX0RyYXdQcmltaXRpdmUoVGhpcy0+d2luZUQzRERldmljZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFByaW1pdGl2ZVR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBTdGFydFZlcnRleCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFByaW1pdGl2ZUNvdW50KTsKfQoKc3RhdGljIEhSRVNVTFQgV0lOQVBJClRodW5rX0lEaXJlY3QzRERldmljZUltcGxfM19EcmF3UHJpbWl0aXZlVkIoSURpcmVjdDNERGV2aWNlMyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNEUFJJTUlUSVZFVFlQRSBQcmltaXRpdmVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElEaXJlY3QzRFZlcnRleEJ1ZmZlciAqRDNEVmVydGV4QnVmLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIFN0YXJ0VmVydGV4LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIE51bVZlcnRpY2VzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIEZsYWdzKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UzLCBpZmFjZSk7CiAgICBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXJJbXBsICp2YiA9IElDT01fT0JKRUNUKElEaXJlY3QzRFZlcnRleEJ1ZmZlckltcGwsIElEaXJlY3QzRFZlcnRleEJ1ZmZlciwgRDNEVmVydGV4QnVmKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglMDh4LCVwLCUwOGx4LCUwOGx4LCUwOGx4KSB0aHVua2luZyB0byBJRGlyZWN0M0REZXZpY2U3IGludGVyZmFjZS5cbiIsIFRoaXMsICBQcmltaXRpdmVUeXBlLCB2YiwgU3RhcnRWZXJ0ZXgsIE51bVZlcnRpY2VzLCBGbGFncyk7CiAgICByZXR1cm4gSURpcmVjdDNERGV2aWNlN19EcmF3UHJpbWl0aXZlVkIoSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlNyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgUHJpbWl0aXZlVHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBJQ09NX0lOVEVSRkFDRSh2YiwgSURpcmVjdDNEVmVydGV4QnVmZmVyNyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgU3RhcnRWZXJ0ZXgsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgTnVtVmVydGljZXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRmxhZ3MpOwp9CgoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTc6OkRyYXdJbmRleGVkUHJpbWl0aXZlVkIKICoKICogRHJhd3MgcHJpbWl0aXZlcyBmcm9tIGEgdmVydGV4IGJ1ZmZlciB0byB0aGUgc2NyZWVuCiAqCiAqIFBhcmFtczoKICogIFByaW1pdGl2ZVR5cGU6IFR5cGUgb2YgcHJpbWl0aXZlIHRvIGJlIHJlbmRlcmVkLgogKiAgRDNEVmVydGV4QnVmOiBTb3VyY2UgVmVydGV4IEJ1ZmZlcgogKiAgU3RhcnRWZXJ0ZXg6IEluZGV4IG9mIHRoZSBmaXJzdCB2ZXJ0ZXggZnJvbSB0aGUgYnVmZmVyIHRvIGJlIHJlbmRlcmVkCiAqICBOdW1WZXJ0aWNlczogTnVtYmVyIG9mIHZlcnRpY2VzIHRvIGJlIHJlbmRlcmVkCiAqICBJbmRpY2VzOiBBcnJheSBvZiBEV09SRHMgdXNlZCB0byBpbmRleCBpbnRvIHRoZSBWZXJ0aWNlcwogKiAgSW5kZXhDb3VudDogTnVtYmVyIG9mIGluZGljZXMgaW4gSW5kaWNlcwogKiAgRmxhZ3M6IENhbiBiZSBEM0REUF9XQUlUIHRvIHdhaXQgdW50aWwgcmVuZGVyaW5nIGhhcyBmaW5pc2hlZAogKgogKiBSZXR1cm4gdmFsdWVzCiAqCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIEhSRVNVTFQgV0lOQVBJCklEaXJlY3QzRERldmljZUltcGxfN19EcmF3SW5kZXhlZFByaW1pdGl2ZVZCKElEaXJlY3QzRERldmljZTcgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RQUklNSVRJVkVUWVBFIFByaW1pdGl2ZVR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElEaXJlY3QzRFZlcnRleEJ1ZmZlcjcgKkQzRFZlcnRleEJ1ZiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgU3RhcnRWZXJ0ZXgsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIE51bVZlcnRpY2VzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBXT1JEICpJbmRpY2VzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBJbmRleENvdW50LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBGbGFncykKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlNywgaWZhY2UpOwogICAgSURpcmVjdDNEVmVydGV4QnVmZmVySW1wbCAqdmIgPSBJQ09NX09CSkVDVChJRGlyZWN0M0RWZXJ0ZXhCdWZmZXJJbXBsLCBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXI3LCBEM0RWZXJ0ZXhCdWYpOwogICAgRFdPUkQgc3RyaWRlOwogICAgVUlOVCBQcmltaXRpdmVDb3VudDsKICAgIFdPUkQgKkxvY2tlZEluZGljZXM7CiAgICBIUkVTVUxUIGhyOwogICAgV0lORUQzRFZFUlRFWEJVRkZFUl9ERVNDIERlc2M7CgogICAgVFJBQ0UoIiglcCktPiglMDh4LCVwLCVsZCwlbGQsJXAsJWxkLCUwOGx4KVxuIiwgVGhpcywgUHJpbWl0aXZlVHlwZSwgdmIsIFN0YXJ0VmVydGV4LCBOdW1WZXJ0aWNlcywgSW5kaWNlcywgSW5kZXhDb3VudCwgRmxhZ3MpOwoKICAgIC8qIFN0ZXBzOgogICAgICogMSkgQ2FsY3VsYXRlIHNvbWUgdGhpbmdzOiBWZXJ0ZXggY291bnQgLT4gUHJpbWl0aXZlIGNvdW50LCBzdHJpZGUsIC4uLgogICAgICogMikgVXBsb2FkIHRoZSBJbmRpY2VzIHRvIHRoZSBpbmRleCBidWZmZXIKICAgICAqIDMpIFNldCB0aGUgaW5kZXggc291cmNlCiAgICAgKiA0KSBTZXQgdGhlIFZlcnRleCBCdWZmZXIgYXMgdGhlIFN0cmVhbSBzb3VyY2UKICAgICAqIDUpIENhbGwgSVdpbmVEM0REZXZpY2U6OkRyYXdJbmRleGVkUHJpbWl0aXZlCiAgICAgKi8KCiAgICAvKiBHZXQgdGhlIHByaW1pdGl2ZSBjb3VudCAqLwogICAgc3dpdGNoKFByaW1pdGl2ZVR5cGUpCiAgICB7CiAgICAgICAgY2FzZSBEM0RQVF9QT0lOVExJU1Q6IAogICAgICAgICAgUHJpbWl0aXZlQ291bnQgPSBJbmRleENvdW50OwogICAgICAgICAgYnJlYWs7CgogICAgICAgIGNhc2UgRDNEUFRfTElORUxJU1Q6IAogICAgICAgICAgUHJpbWl0aXZlQ291bnQgPSBJbmRleENvdW50IC8gMjsKICAgICAgICAgIGJyZWFrOwoKICAgICAgICBjYXNlIEQzRFBUX0xJTkVTVFJJUDoKICAgICAgICAgIFByaW1pdGl2ZUNvdW50ID0gSW5kZXhDb3VudCAtIDE7CiAgICAgICAgICBicmVhazsKCiAgICAgICAgY2FzZSBEM0RQVF9UUklBTkdMRUxJU1Q6CiAgICAgICAgICBQcmltaXRpdmVDb3VudCA9IEluZGV4Q291bnQgLyAzOwogICAgICAgICAgYnJlYWs7CgogICAgICAgIGNhc2UgRDNEUFRfVFJJQU5HTEVTVFJJUDoKICAgICAgICAgIFByaW1pdGl2ZUNvdW50ID0gSW5kZXhDb3VudCAtIDI7CiAgICAgICAgICBicmVhazsKCiAgICAgICAgY2FzZSBEM0RQVF9UUklBTkdMRUZBTjoKICAgICAgICAgIFByaW1pdGl2ZUNvdW50ID0gSW5kZXhDb3VudCAtIDI7CiAgICAgICAgICBicmVhazsKCiAgICAgICAgZGVmYXVsdDogcmV0dXJuIERERVJSX0lOVkFMSURQQVJBTVM7CiAgICB9CgogICAgLyogR2V0IHRoZSBGVkYgb2YgdGhlIHZlcnRleCBidWZmZXIsIGFuZCBpdHMgc3RyaWRlICovCiAgICBociA9IElXaW5lRDNEVmVydGV4QnVmZmVyX0dldERlc2ModmItPndpbmVEM0RWZXJ0ZXhCdWZmZXIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJkRlc2MpOwogICAgaWYoaHIgIT0gRDNEX09LKQogICAgewogICAgICAgIEVSUigiKCVwKSBJV2luZUQzRFZlcnRleEJ1ZmZlcjo6R2V0RGVzYyBmYWlsZWQgd2l0aCBociA9ICUwOGx4XG4iLCBUaGlzLCBocik7CiAgICAgICAgcmV0dXJuIGhyOwogICAgfQogICAgc3RyaWRlID0gZ2V0X2ZsZXhpYmxlX3ZlcnRleF9zaXplKERlc2MuRlZGKTsKICAgIFRSQUNFKCJWZXJ0ZXggYnVmZmVyIEZWRiA9ICUwOGx4LCBzdHJpZGU9JWxkXG4iLCBEZXNjLkZWRiwgc3RyaWRlKTsKCiAgICBociA9IElXaW5lRDNERGV2aWNlX1NldEZWRihUaGlzLT53aW5lRDNERGV2aWNlLCBEZXNjLkZWRik7CiAgICBpZihGQUlMRUQoaHIpKQogICAgewogICAgICAgIEVSUigiICglcCkgU2V0dGluZyB0aGUgRlZGIGZhaWxlZCwgaHIgPSAlbHghXG4iLCBUaGlzLCBocik7CiAgICAgICAgcmV0dXJuIGhyOwogICAgfQoKICAgIC8qIGNvcHkgdGhlIGluZGV4IHN0cmVhbSBpbnRvIHRoZSBpbmRleCBidWZmZXIuCiAgICAgKiBBIG5ldyBJV2luZUQzRERldmljZSBtZXRob2QgY291bGQgYmUgY3JlYXRlZAogICAgICogd2hpY2ggdGFrZXMgYW4gdXNlciBwb2ludGVyIGNvbnRhaW5pbmcgdGhlIGluZGljZXMKICAgICAqIG9yIGEgU2V0RGF0YS1NZXRob2QgZm9yIHRoZSBpbmRleCBidWZmZXIsIHdoaWNoCiAgICAgKiBvdmVycmlkZXMgdGhlIGluZGV4IGJ1ZmZlciBkYXRhIHdpdGggb3VyIHBvaW50ZXIuCiAgICAgKi8KICAgIGhyID0gSVdpbmVEM0RJbmRleEJ1ZmZlcl9Mb2NrKFRoaXMtPmluZGV4YnVmZmVyLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgMCAvKiBPZmZTZXRUb0xvY2sgKi8sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAwIC8qIFNpemVUb0xvY2sgLSBkb2Vzbid0IG1hdHRlciAqLywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIChCWVRFICoqKSAmTG9ja2VkSW5kaWNlcywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIDAgLyogRmxhZ3MgKi8pOwogICAgYXNzZXJ0KEluZGV4Q291bnQgPCAweDEwMDAwMCk7CiAgICBpZihociAhPSBEM0RfT0spCiAgICB7CiAgICAgICAgRVJSKCIoJXApIElXaW5lRDNESW5kZXhCdWZmZXI6OkxvY2sgZmFpbGVkIHdpdGggaHIgPSAlMDhseFxuIiwgVGhpcywgaHIpOwogICAgICAgIHJldHVybiBocjsKICAgIH0KICAgIG1lbWNweShMb2NrZWRJbmRpY2VzLCBJbmRpY2VzLCBJbmRleENvdW50ICogc2l6ZW9mKFdPUkQpKTsKICAgIGhyID0gSVdpbmVEM0RJbmRleEJ1ZmZlcl9VbmxvY2soVGhpcy0+aW5kZXhidWZmZXIpOwogICAgaWYoaHIgIT0gRDNEX09LKQogICAgewogICAgICAgIEVSUigiKCVwKSBJV2luZUQzREluZGV4QnVmZmVyOjpVbmxvY2sgZmFpbGVkIHdpdGggaHIgPSAlMDhseFxuIiwgVGhpcywgaHIpOwogICAgICAgIHJldHVybiBocjsKICAgIH0KCiAgICAvKiBTZXQgdGhlIGluZGV4IHN0cmVhbSAqLwogICAgaHIgPSBJV2luZUQzRERldmljZV9TZXRJbmRpY2VzKFRoaXMtPndpbmVEM0REZXZpY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgVGhpcy0+aW5kZXhidWZmZXIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgMCk7CgogICAgLyogU2V0IHRoZSB2ZXJ0ZXggc3RyZWFtIHNvdXJjZSAqLwogICAgaHIgPSBJV2luZUQzRERldmljZV9TZXRTdHJlYW1Tb3VyY2UoVGhpcy0+d2luZUQzRERldmljZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIDAgLyogU3RyZWFtTnVtYmVyICovLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdmItPndpbmVEM0RWZXJ0ZXhCdWZmZXIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAwIC8qIG9mZnNldCwgd2UgcGFzcyB0aGlzIHRvIERyYXdJbmRleGVkUHJpbWl0aXZlICovLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc3RyaWRlKTsKICAgIGlmKGhyICE9IEQzRF9PSykKICAgIHsKICAgICAgICBFUlIoIiglcCkgSURpcmVjdDNERGV2aWNlOjpTZXRTdHJlYW1Tb3VyY2UgZmFpbGVkIHdpdGggaHIgPSAlMDhseFxuIiwgVGhpcywgaHIpOwogICAgICAgIHJldHVybiBocjsKICAgIH0KCgogICAgaHIgPSBJV2luZUQzRERldmljZV9EcmF3SW5kZXhlZFByaW1pdGl2ZShUaGlzLT53aW5lRDNERGV2aWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBQcmltaXRpdmVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBTdGFydFZlcnRleCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgMCAvKiBtaW5JbmRleCAqLywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgTnVtVmVydGljZXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIDAgLyogU3RhcnRJbmRleCAqLywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgUHJpbWl0aXZlQ291bnQpOwoKICAgIHJldHVybiBEM0RfT0s7Cn0KCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzNfRHJhd0luZGV4ZWRQcmltaXRpdmVWQihJRGlyZWN0M0REZXZpY2UzICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNEUFJJTUlUSVZFVFlQRSBQcmltaXRpdmVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBJRGlyZWN0M0RWZXJ0ZXhCdWZmZXIgKkQzRFZlcnRleEJ1ZiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgV09SRCAqSW5kaWNlcywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgSW5kZXhDb3VudCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgRmxhZ3MpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTMsIGlmYWNlKTsKICAgIElEaXJlY3QzRFZlcnRleEJ1ZmZlckltcGwgKlZCID0gSUNPTV9PQkpFQ1QoSURpcmVjdDNEVmVydGV4QnVmZmVySW1wbCwgSURpcmVjdDNEVmVydGV4QnVmZmVyLCBEM0RWZXJ0ZXhCdWYpOwogICAgVFJBQ0VfKGRkcmF3X3RodW5rKSgiKCVwKS0+KCUwOHgsJXAsJXAsJTA4bHgsJTA4bHgpIHRodW5raW5nIHRvIElEaXJlY3QzRERldmljZTcgaW50ZXJmYWNlLlxuIiwgVGhpcywgUHJpbWl0aXZlVHlwZSwgVkIsIEluZGljZXMsIEluZGV4Q291bnQsIEZsYWdzKTsKCiAgICByZXR1cm4gSURpcmVjdDNERGV2aWNlN19EcmF3SW5kZXhlZFByaW1pdGl2ZVZCKElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTcpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBQcmltaXRpdmVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBJQ09NX0lOVEVSRkFDRShWQiwgSURpcmVjdDNEVmVydGV4QnVmZmVyNyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIDAsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEluZGV4Q291bnQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEluZGljZXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEluZGV4Q291bnQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEZsYWdzKTsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTc6OkNvbXB1dGVTcGhlcmVWaXNpYmlsaXR5CiAqCiAqIENhbGN1bGF0ZXMgdGhlIHZpc2liaWxpdHkgb2Ygc3BoZXJlcyBpbiB0aGUgY3VycmVudCB2aWV3cG9ydC4gVGhlIHNwaGVyZXMKICogYXJlIHBhc3NlZCBpbiB0aGUgQ2VudGVycyBhbmQgUmFkaWkgYXJyYXlzLCB0aGUgcmVzdWx0cyBhcmUgcGFzc2VkIGJhY2sKICogaW4gdGhlIFJldHVyblZhbHVlcyBhcnJheS4gUmV0dXJuIHZhbHVlcyBhcmUgZWl0aGVyIGNvbXBsZXRlbHkgdmlzaWJsZSwKICogcGFydGlhbGx5IHZpc2libGUgb3IgY29tcGxldGVseSBpbnZpc2libGUuCiAqIFRoZSByZXR1cm4gdmFsdWUgY29uc2lzdCBvZiBhIGNvbWJpbmF0aW9uIG9mIEQzRENMSVBfKiBmbGFncywgb3IgaXQncwogKiAwIGlmIHRoZSBzcGhlcmUgaXMgY29tcGxldGVseSB2aXNpYmxlKGFjY29yZGluZyB0byB0aGUgU0RLLCBub3QgY2hlY2tlZCkKICoKICogU291bmRzIGxpa2UgYW4gb3ZlcmRvc2Ugb2YgbWF0aCA7KQogKgogKiBWZXJzaW9uIDMgYW5kIDcKICoKICogUGFyYW1zOgogKiAgQ2VudGVyczogQXJyYXkgY29udGFpbmluZyB0aGUgc3BoZXJlIGNlbnRlcnMKICogIFJhZGlpOiBBcnJheSBjb250YWluaW5nIHRoZSBzcGhlcmUgcmFkaWkKICogIE51bVNwaGVyZXM6IFRoZSBudW1iZXIgb2YgY2VudGVycyBhbmQgcmFkaWkgaW4gdGhlIGFycmF5cwogKiAgRmxhZ3M6IFNvbWUgZmxhZ3MKICogIFJldHVyblZhbHVlczogQXJyYXkgdG8gd3JpdGUgdGhlIHJlc3VsdHMgdG8KICoKICogUmV0dXJuczoKICogIEQzRF9PSyBiZWNhdXNlIGl0J3MgYSBzdHViCiAqICAoRERFUlJfSU5WQUxJRFBBUkFNUyBpZiBDZW50ZXJzLCBSYWRpaSBvciBSZXR1cm5WYWx1ZXMgYXJlIE5VTEwpCiAqICAoRDNERVJSX0lOVkFMSURNQVRSSVggaWYgdGhlIGNvbWJpbmVkIHdvcmxkLCB2aWV3IGFuZCBwcm9qIG1hdHJpeAogKiAgaXMgc2luZ3VsYXIpCiAqCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIEhSRVNVTFQgV0lOQVBJCklEaXJlY3QzRERldmljZUltcGxfN19Db21wdXRlU3BoZXJlVmlzaWJpbGl0eShJRGlyZWN0M0REZXZpY2U3ICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRFZFQ1RPUiAqQ2VudGVycywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRFZBTFVFICpSYWRpaSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIE51bVNwaGVyZXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBGbGFncywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEICpSZXR1cm5WYWx1ZXMpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTcsIGlmYWNlKTsKICAgIEZJWE1FKCIoJXApLT4oJXAsJXAsJTA4bHgsJTA4bHgsJXApOiBzdHViIVxuIiwgVGhpcywgQ2VudGVycywgUmFkaWksIE51bVNwaGVyZXMsIEZsYWdzLCBSZXR1cm5WYWx1ZXMpOwoKICAgIC8qIHRoZSBEaXJlY3RYIDcgc2RrIHNheXMgdGhhdCB0aGUgdmlzaWJpbGl0eSBpcyBjb21wdXRlZCBieQogICAgICogYmFjay10cmFuc2Zvcm1pbmcgdGhlIHZpZXdpbmcgZnJ1c3R1bSB0byBtb2RlbCBzcGFjZQogICAgICogdXNpbmcgdGhlIGludmVyc2Ugb2YgdGhlIGNvbWJpbmVkIHdvcmxkLCB2aWV3IGFuZCBwcm9qZWN0aW9uCiAgICAgKiBtYXRyaXguIElmIHRoZSBtYXRyaXggY2FuJ3QgYmUgcmV2ZXJzZWQsIEQzREVSUl9JTlZBTElETUFUUklYCiAgICAgKiBpcyByZXR1cm5lZC4KICAgICAqCiAgICAgKiBCYXNpYyBpbXBsZW1lbnRhdGlvbiBpZGVhOgogICAgICogMSkgQ2hlY2sgaWYgdGhlIGNlbnRlciBpcyBpbiB0aGUgdmlld2luZyBmcnVzdHVtCiAgICAgKiAyKSBDdXQgdGhlIHNwaGVyZSB3aXRoIHRoZSBwbGFuZXMgb2YgdGhlIHZpZXdpbmcKICAgICAqICAgIGZydXN0dW0KICAgICAqCiAgICAgKiAtPkNlbnRlciBpbnNpZGUgdGhlIGZydXN0dW0sIG5vIGludGVyc2VjdGlvbnM6CiAgICAgKiAgICBGdWxseSB2aXNpYmxlCiAgICAgKiAtPkNlbnRlciBvdXRzaWRlIHRoZSBmcnVzdHVtLCBubyBpbnRlcnNlY3Rpb25zOgogICAgICogICAgTm90IHZpc2libGUKICAgICAqIC0+U29tZSBpbnRlcnNlY3Rpb25zOiBQYXJ0aWFsbHkgdmlzaWJsZQogICAgICoKICAgICAqIEltcGxlbWVudCB0aGlzIGNhbGwgaW4gV2luZUQzRC4gRWl0aGVyIGltcGxlbWVudCB0aGUKICAgICAqIG1hdHJpeCBhbmQgdmVjdG9yIHN0dWZmIGluIFdpbmVEM0QsIG9yIHVzZSBzb21lIGV4dGVybmFsCiAgICAgKiBtYXRoIGxpYnJhcnkuCiAgICAgKi8KCiAgICByZXR1cm4gRDNEX09LOwp9CgpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8zX0NvbXB1dGVTcGhlcmVWaXNpYmlsaXR5KElEaXJlY3QzRERldmljZTMgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNEVkVDVE9SICpDZW50ZXJzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNEVkFMVUUgKlJhZGlpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgTnVtU3BoZXJlcywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIEZsYWdzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgKlJldHVyblZhbHVlcykKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlMywgaWZhY2UpOwogICAgVFJBQ0VfKGRkcmF3X3RodW5rKSgiKCVwKS0+KCVwLCVwLCUwOGx4LCUwOGx4LCVwKSB0aHVua2luZyB0byBJRGlyZWN0M0REZXZpY2U3IGludGVyZmFjZS5cbiIsIFRoaXMsIENlbnRlcnMsIFJhZGlpLCBOdW1TcGhlcmVzLCBGbGFncywgUmV0dXJuVmFsdWVzKTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2U3X0NvbXB1dGVTcGhlcmVWaXNpYmlsaXR5KElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTcpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgQ2VudGVycywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFJhZGlpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgTnVtU3BoZXJlcywKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEZsYWdzLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgUmV0dXJuVmFsdWVzKTsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTc6OkdldFRleHR1cmUKICoKICogUmV0dXJucyB0aGUgdGV4dHVyZSBpbnRlcmZhY2UgaGFuZGxlIGFzc2lnbmVkIHRvIGEgdGV4dHVyZSBzdGFnZS4KICogVGhlIHJldHVybmVkIHRleHR1cmUgaXMgQWRkUmVmZWQuIFRoaXMgaXMgdGFrZW4gZnJvbSBvbGQgZGRyYXcsCiAqIG5vdCBjaGVja2VkIGluIFdpbmRvd3MuCiAqCiAqIFZlcnNpb24gMyBhbmQgNwogKgogKiBQYXJhbXM6CiAqICBTdGFnZTogVGV4dHVyZSBzdGFnZSB0byByZWFkIHRoZSB0ZXh0dXJlIGZyb20KICogIFRleHR1cmU6IEFkZHJlc3MgdG8gc3RvcmUgdGhlIGludGVyZmFjZSBwb2ludGVyIGF0CiAqCiAqIFJldHVybnM6CiAqICBEM0RfT0sgb24gc3VjY2VzcwogKiAgRERFUlJfSU5WQUxJRFBBUkFNUyBpZiBUZXh0dXJlIGlzIE5VTEwKICogIEZvciBkZXRhaWxzLCBzZWUgSVdpbmVEM0REZXZpY2U6OkdldFRleHR1cmUKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKSURpcmVjdDNERGV2aWNlSW1wbF83X0dldFRleHR1cmUoSURpcmVjdDNERGV2aWNlNyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIFN0YWdlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBJRGlyZWN0RHJhd1N1cmZhY2U3ICoqVGV4dHVyZSkKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlNywgaWZhY2UpOwogICAgSVdpbmVEM0RCYXNlVGV4dHVyZSAqU3VyZjsKICAgIEhSRVNVTFQgaHI7CiAgICBUUkFDRSgiKCVwKS0+KCVsZCwlcCk6IFJlbGF5XG4iLCBUaGlzLCBTdGFnZSwgVGV4dHVyZSk7CgogICAgaWYoIVRleHR1cmUpCiAgICB7CiAgICAgICAgVFJBQ0UoIlRleHR1cmUgPT0gTlVMTCwgZmFpbGluZyB3aXRoIERERVJSX0lOVkFMSURQQVJBTVNcbiIpOwogICAgICAgIHJldHVybiBEREVSUl9JTlZBTElEUEFSQU1TOwogICAgfQoKICAgIGhyID0gSVdpbmVEM0REZXZpY2VfR2V0VGV4dHVyZShUaGlzLT53aW5lRDNERGV2aWNlLCBTdGFnZSwgKElXaW5lRDNEQmFzZVRleHR1cmUgKiopICZTdXJmKTsKICAgIGlmKCAoaHIgIT0gRDNEX09LKSB8fCAoIVN1cmYpICkgCiAgICB7CiAgICAgICAgKlRleHR1cmUgPSBOVUxMOwogICAgICAgIHJldHVybiBocjsKICAgIH0KCiAgICAvKiBHZXRQYXJlbnQgQWRkUmVmKClzLCB3aGljaCBpcyBwZXJmZWN0bHkgT0suCiAgICAgKiBXZSBoYXZlIHBhc3NlZCB0aGUgSURpcmVjdERyYXdTdXJmYWNlNyBpbnRlcmZhY2UgdG8gV2luZUQzRCwgc28gdGhhdCdzIE9LIHRvby4KICAgICAqLwogICAgcmV0dXJuIElXaW5lRDNEQmFzZVRleHR1cmVfR2V0UGFyZW50KFN1cmYsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKElVbmtub3duICoqKSBUZXh0dXJlKTsKfQoKc3RhdGljIEhSRVNVTFQgV0lOQVBJClRodW5rX0lEaXJlY3QzRERldmljZUltcGxfM19HZXRUZXh0dXJlKElEaXJlY3QzRERldmljZTMgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBTdGFnZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgSURpcmVjdDNEVGV4dHVyZTIgKipUZXh0dXJlMikKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlMywgaWZhY2UpOwogICAgSFJFU1VMVCByZXQ7CiAgICBJRGlyZWN0RHJhd1N1cmZhY2U3ICpyZXRfdmFsOwoKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglbGQsJXApIHRodW5raW5nIHRvIElEaXJlY3QzRERldmljZTcgaW50ZXJmYWNlLlxuIiwgVGhpcywgU3RhZ2UsIFRleHR1cmUyKTsKICAgIHJldCA9IElEaXJlY3QzRERldmljZTdfR2V0VGV4dHVyZShJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0REZXZpY2U3KSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBTdGFnZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAmcmV0X3ZhbCk7CgogICAgKlRleHR1cmUyID0gQ09NX0lOVEVSRkFDRV9DQVNUKElEaXJlY3REcmF3U3VyZmFjZUltcGwsIElEaXJlY3REcmF3U3VyZmFjZTcsIElEaXJlY3QzRFRleHR1cmUyLCByZXRfdmFsKTsKCiAgICBUUkFDRV8oZGRyYXdfdGh1bmspKCIgcmV0dXJuaW5nIGludGVyZmFjZSAlcC5cbiIsICpUZXh0dXJlMik7CgogICAgcmV0dXJuIHJldDsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTc6OlNldFRleHR1cmUKICoKICogQXNzaWducyBhIHRleHR1cmUgdG8gYSB0ZXh0dXJlIHN0YWdlLiBJcyB0aGUgdGV4dHVyZSBBZGRSZWYtZWQ/CiAqCiAqIFZlcnNpb24gMyBhbmQgNwogKgogKiBQYXJhbXM6CiAqICBTdGFnZTogVGhlIHN0YWdlIHRvIGFzc2lnbiB0aGUgdGV4dHVyZSB0bwogKiAgVGV4dHVyZTogSW50ZXJmYWNlIHBvaW50ZXIgdG8gdGhlIHRleHR1cmUgc3VyZmFjZQogKgogKiBSZXR1cm5zCiAqIEQzRF9PSyBvbiBzdWNjZXNzCiAqIEZvciBkZXRhaWxzLCBzZWUgSVdpbmVEM0REZXZpY2U6OlNldFRleHR1cmUKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKSURpcmVjdDNERGV2aWNlSW1wbF83X1NldFRleHR1cmUoSURpcmVjdDNERGV2aWNlNyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIFN0YWdlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBJRGlyZWN0RHJhd1N1cmZhY2U3ICpUZXh0dXJlKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2U3LCBpZmFjZSk7CiAgICBJRGlyZWN0RHJhd1N1cmZhY2VJbXBsICpzdXJmID0gSUNPTV9PQkpFQ1QoSURpcmVjdERyYXdTdXJmYWNlSW1wbCwgSURpcmVjdERyYXdTdXJmYWNlNywgVGV4dHVyZSk7CiAgICBUUkFDRSgiKCVwKS0+KCUwOGx4LCVwKTogUmVsYXkhXG4iLCBUaGlzLCBTdGFnZSwgc3VyZik7CgogICAgLyogVGV4dHVyZSBtYXkgYmUgTlVMTCBoZXJlICovCiAgICByZXR1cm4gSVdpbmVEM0REZXZpY2VfU2V0VGV4dHVyZShUaGlzLT53aW5lRDNERGV2aWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgU3RhZ2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzdXJmID8gKElXaW5lRDNEQmFzZVRleHR1cmUgKiApIHN1cmYtPndpbmVEM0RUZXh0dXJlIDogTlVMTCk7Cn0KCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzNfU2V0VGV4dHVyZShJRGlyZWN0M0REZXZpY2UzICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgU3RhZ2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElEaXJlY3QzRFRleHR1cmUyICpUZXh0dXJlMikKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlMywgaWZhY2UpOwogICAgSURpcmVjdERyYXdTdXJmYWNlSW1wbCAqdGV4ID0gSUNPTV9PQkpFQ1QoSURpcmVjdERyYXdTdXJmYWNlSW1wbCwgSURpcmVjdDNEVGV4dHVyZTIsIFRleHR1cmUyKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglbGQsJXApIHRodW5raW5nIHRvIElEaXJlY3QzRERldmljZTcgaW50ZXJmYWNlLlxuIiwgVGhpcywgU3RhZ2UsIHRleCk7CiAgICByZXR1cm4gSURpcmVjdDNERGV2aWNlN19TZXRUZXh0dXJlKElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTcpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBTdGFnZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgSUNPTV9JTlRFUkZBQ0UodGV4LCBJRGlyZWN0RHJhd1N1cmZhY2U3KSk7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0REZXZpY2U3OjpHZXRUZXh0dXJlU3RhZ2VTdGF0ZQogKgogKiBSZXRyaWV2ZXMgYSBzdGF0ZSBmcm9tIGEgdGV4dHVyZSBzdGFnZS4KICoKICogVmVyc2lvbiAzIGFuZCA3CiAqCiAqIFBhcmFtczoKICogIFN0YWdlOiBUaGUgc3RhZ2UgdG8gcmV0cmlldmUgdGhlIHN0YXRlIGZyb20KICogIFRleFN0YWdlU3RhdGVUeXBlOiBUaGUgc3RhdGUgdHlwZSB0byByZXRyaWV2ZQogKiAgU3RhdGU6IEFkZHJlc3MgdG8gc3RvcmUgdGhlIHN0YXRlJ3MgdmFsdWUgYXQKICoKICogUmV0dXJuczoKICogIEQzRF9PSyBvbiBzdWNjZXNzCiAqICBEREVSUl9JTlZBTElEUEFSQU1TIGlmIFN0YXRlIGlzIE5VTEwKICogIEZvciBkZXRhaWxzLCBzZWUgSVdpbmVEM0REZXZpY2U6OkdldFRleHR1cmVTdGFnZVN0YXRlCiAqCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIEhSRVNVTFQgV0lOQVBJCklEaXJlY3QzRERldmljZUltcGxfN19HZXRUZXh0dXJlU3RhZ2VTdGF0ZShJRGlyZWN0M0REZXZpY2U3ICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIFN0YWdlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNEVEVYVFVSRVNUQUdFU1RBVEVUWVBFIFRleFN0YWdlU3RhdGVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgKlN0YXRlKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2U3LCBpZmFjZSk7CiAgICBUUkFDRSgiKCVwKS0+KCUwOGx4LCUwOHgsJXApOiBSZWxheSFcbiIsIFRoaXMsIFN0YWdlLCBUZXhTdGFnZVN0YXRlVHlwZSwgU3RhdGUpOwoKICAgIGlmKCFTdGF0ZSkKICAgICAgICByZXR1cm4gRERFUlJfSU5WQUxJRFBBUkFNUzsKCiAgICByZXR1cm4gSVdpbmVEM0REZXZpY2VfR2V0VGV4dHVyZVN0YWdlU3RhdGUoVGhpcy0+d2luZUQzRERldmljZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBTdGFnZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBUZXhTdGFnZVN0YXRlVHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBTdGF0ZSk7Cn0KCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzNfR2V0VGV4dHVyZVN0YWdlU3RhdGUoSURpcmVjdDNERGV2aWNlMyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBTdGFnZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRFRFWFRVUkVTVEFHRVNUQVRFVFlQRSBUZXhTdGFnZVN0YXRlVHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEICpTdGF0ZSkKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlMywgaWZhY2UpOwogICAgVFJBQ0VfKGRkcmF3X3RodW5rKSgiKCVwKS0+KCUwOGx4LCUwOHgsJXApIHRodW5raW5nIHRvIElEaXJlY3QzRERldmljZTcgaW50ZXJmYWNlLlxuIiwgVGhpcywgU3RhZ2UsIFRleFN0YWdlU3RhdGVUeXBlLCBTdGF0ZSk7CiAgICByZXR1cm4gSURpcmVjdDNERGV2aWNlN19HZXRUZXh0dXJlU3RhZ2VTdGF0ZShJQ09NX0lOVEVSRkFDRShUaGlzLCBJRGlyZWN0M0REZXZpY2U3KSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFN0YWdlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgVGV4U3RhZ2VTdGF0ZVR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBTdGF0ZSk7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0REZXZpY2U3OjpTZXRUZXh0dXJlU3RhZ2VTdGF0ZQogKgogKiBTZXRzIGEgdGV4dHVyZSBzdGFnZSBzdGF0ZS4gU29tZSBzdGFnZSB0eXBlcyBuZWVkIHRvIGJlIGhhbmRsZWQgc3BlY2lhbGx5LAogKiBiZWNhdXNlIHRoZXkgZG8gbm90IGV4aXN0IGluIFdpbmVEM0QgYW5kIHdlcmUgbW92ZWQgdG8gYW5vdGhlciBwbGFjZQogKgogKiBWZXJzaW9uIDMgYW5kIDcKICoKICogUGFyYW1zOgogKiAgU3RhZ2U6IFRoZSBzdGFnZSB0byBtb2RpZnkKICogIFRleFN0YWdlU3RhdGVUeXBlOiBUaGUgc3RhdGUgdG8gY2hhbmdlCiAqICBTdGF0ZTogVGhlIG5ldyB2YWx1ZSBmb3IgdGhlIHN0YXRlCiAqCiAqIFJldHVybnM6CiAqICBEM0RfT0sgb24gc3VjY2VzcwogKiAgRm9yIGRldGFpbHMsIHNlZSBJV2luZUQzRERldmljZTo6U2V0VGV4dHVyZVN0YWdlU3RhdGUKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKSURpcmVjdDNERGV2aWNlSW1wbF83X1NldFRleHR1cmVTdGFnZVN0YXRlKElEaXJlY3QzRERldmljZTcgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgU3RhZ2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RURVhUVVJFU1RBR0VTVEFURVRZUEUgVGV4U3RhZ2VTdGF0ZVR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBTdGF0ZSkKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlNywgaWZhY2UpOwogICAgVFJBQ0UoIiglcCktPiglMDhseCwlMDh4LCUwOGx4KTogUmVsYXkhXG4iLCBUaGlzLCBTdGFnZSwgVGV4U3RhZ2VTdGF0ZVR5cGUsIFN0YXRlKTsKICAgIHN3aXRjaChUZXhTdGFnZVN0YXRlVHlwZSkKICAgIHsKICAgICAgICAvKiBNaXBmaWx0ZXIgaXMgYSBzYW1wbGVyIHN0YXRlIHdpdGggZGlmZmVyZW50IHZhbHVlcyAqLwogICAgICAgIGNhc2UgRDNEVFNTX01JUEZJTFRFUjoKICAgICAgICB7CiAgICAgICAgICAgIFdJTkVEM0RURVhUVVJFRklMVEVSVFlQRSB2YWx1ZTsKICAgICAgICAgICAgc3dpdGNoKFN0YXRlKQogICAgICAgICAgICB7CiAgICAgICAgICAgICAgICBjYXNlIEQzRFRGUF9OT05FOiB2YWx1ZSA9IFdJTkVEM0RURVhGX05PTkU7IGJyZWFrOwogICAgICAgICAgICAgICAgY2FzZSBEM0RURlBfUE9JTlQ6IHZhbHVlID0gV0lORUQzRFRFWEZfUE9JTlQ7IGJyZWFrOwogICAgICAgICAgICAgICAgY2FzZSAwOiAvKiBVbmNoZWNrZWQgKi8KICAgICAgICAgICAgICAgIGNhc2UgRDNEVEZQX0xJTkVBUjogdmFsdWUgPSBXSU5FRDNEVEVYRl9MSU5FQVI7IGJyZWFrOwogICAgICAgICAgICAgICAgZGVmYXVsdDoKICAgICAgICAgICAgICAgICAgICBFUlIoIlVuZXhwZWN0ZWQgbWlwZmlsdGVyIHZhbHVlICVsZFxuIiwgU3RhdGUpOwogICAgICAgICAgICAgICAgICAgIHZhbHVlID0gV0lORUQzRFRFWEZfTk9ORTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gSVdpbmVEM0REZXZpY2VfU2V0U2FtcGxlclN0YXRlKFRoaXMtPndpbmVEM0REZXZpY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgU3RhZ2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgV0lORUQzRFNBTVBfTUlQRklMVEVSLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHZhbHVlKTsKICAgICAgICB9CgogICAgICAgIC8qIE1pbmZpbHRlciBpcyBhIHNhbXBsZXIgc3RhdGUgdG9vLCBlcXVhbCB2YWx1ZXMgKi8KICAgICAgICBjYXNlIEQzRFRTU19NSU5GSUxURVI6CiAgICAgICAgICAgIHJldHVybiBJV2luZUQzRERldmljZV9TZXRTYW1wbGVyU3RhdGUoVGhpcy0+d2luZUQzRERldmljZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBTdGFnZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBXSU5FRDNEU0FNUF9NSU5GSUxURVIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgU3RhdGUpOwogICAgICAgIC8qIFNhbWUgZm9yIE1BR0ZJTFRFUiAqLwogICAgICAgIGNhc2UgRDNEVFNTX01BR0ZJTFRFUjoKICAgICAgICAgICAgcmV0dXJuIElXaW5lRDNERGV2aWNlX1NldFNhbXBsZXJTdGF0ZShUaGlzLT53aW5lRDNERGV2aWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFN0YWdlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFdJTkVEM0RTQU1QX01BR0ZJTFRFUiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBTdGF0ZSk7CgogICAgICAgIGRlZmF1bHQ6CgogICAgICAgICAgICByZXR1cm4gSVdpbmVEM0REZXZpY2VfU2V0VGV4dHVyZVN0YWdlU3RhdGUoVGhpcy0+d2luZUQzRERldmljZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgU3RhZ2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFRleFN0YWdlU3RhdGVUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBTdGF0ZSk7CiAgICB9Cn0KCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzNfU2V0VGV4dHVyZVN0YWdlU3RhdGUoSURpcmVjdDNERGV2aWNlMyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBTdGFnZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRFRFWFRVUkVTVEFHRVNUQVRFVFlQRSBUZXhTdGFnZVN0YXRlVHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIFN0YXRlKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2UzLCBpZmFjZSk7CiAgICBUUkFDRV8oZGRyYXdfdGh1bmspKCIoJXApLT4oJTA4bHgsJTA4eCwlMDhseCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlNyBpbnRlcmZhY2UuXG4iLCBUaGlzLCBTdGFnZSwgVGV4U3RhZ2VTdGF0ZVR5cGUsIFN0YXRlKTsKICAgIHJldHVybiBJRGlyZWN0M0REZXZpY2U3X1NldFRleHR1cmVTdGFnZVN0YXRlKElDT01fSU5URVJGQUNFKFRoaXMsIElEaXJlY3QzRERldmljZTcpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgU3RhZ2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBUZXhTdGFnZVN0YXRlVHlwZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFN0YXRlKTsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTc6OlZhbGlkYXRlRGV2aWNlCiAqCiAqIFNESzogIlJlcG9ydHMgdGhlIGRldmljZSdzIGFiaWxpdHkgdG8gcmVuZGVyIHRoZSBjdXJyZW50bHkgc2V0CiAqIHRleHR1cmUtYmxlbmRpbmcgb3BlcmF0aW9ucyBpbiBhIHNpbmdsZSBwYXNzIi4gV2hhdGV2ZXIgdGhhdCBtZWFucwogKiBleGFjdGx5Li4uCiAqCiAqIFZlcnNpb24gMyBhbmQgNwogKgogKiBQYXJhbXM6CiAqICBOdW1QYXNzZXM6IEFkZHJlc3MgdG8gd3JpdGUgdGhlIG51bWJlciBvZiBuZWNlc3NhcnkgcGFzc2VzIGZvciB0aGUKICogICAgICAgICAgICAgZGVzaXJlZCBlZmZlY3QgdG8uCiAqCiAqIFJldHVybnM6CiAqICBEM0RfT0sgb24gc3VjY2VzcwogKiAgU2VlIElXaW5lRDNERGV2aWNlOjpWYWxpZGF0ZURldmljZSBmb3IgbW9yZSBkZXRhaWxzCiAqCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIEhSRVNVTFQgV0lOQVBJCklEaXJlY3QzRERldmljZUltcGxfN19WYWxpZGF0ZURldmljZShJRGlyZWN0M0REZXZpY2U3ICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEICpOdW1QYXNzZXMpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTcsIGlmYWNlKTsKICAgIFRSQUNFKCIoJXApLT4oJXApOiBSZWxheVxuIiwgVGhpcywgTnVtUGFzc2VzKTsKCiAgICByZXR1cm4gSVdpbmVEM0REZXZpY2VfVmFsaWRhdGVEZXZpY2UoVGhpcy0+d2luZUQzRERldmljZSwgTnVtUGFzc2VzKTsKfQoKc3RhdGljIEhSRVNVTFQgV0lOQVBJClRodW5rX0lEaXJlY3QzRERldmljZUltcGxfM19WYWxpZGF0ZURldmljZShJRGlyZWN0M0REZXZpY2UzICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEICpQYXNzZXMpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTMsIGlmYWNlKTsKICAgIFRSQUNFXyhkZHJhd190aHVuaykoIiglcCktPiglcCkgdGh1bmtpbmcgdG8gSURpcmVjdDNERGV2aWNlNyBpbnRlcmZhY2UuXG4iLCBUaGlzLCBQYXNzZXMpOwogICAgcmV0dXJuIElEaXJlY3QzRERldmljZTdfVmFsaWRhdGVEZXZpY2UoSUNPTV9JTlRFUkZBQ0UoVGhpcywgSURpcmVjdDNERGV2aWNlNyksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBQYXNzZXMpOwp9CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSURpcmVjdDNERGV2aWNlNzo6Q2xlYXIKICoKICogRmlsbHMgdGhlIHJlbmRlciB0YXJnZXQsIHRoZSB6IGJ1ZmZlciBhbmQgdGhlIHN0ZW5jaWwgYnVmZmVyIHdpdGggYQogKiBjbGVhciBjb2xvciAvIHZhbHVlCiAqCiAqIFZlcnNpb24gNyBvbmx5CiAqCiAqIFBhcmFtczoKICogIENvdW50OiBOdW1iZXIgb2YgcmVjdGFuZ2xlcyBpbiBSZWN0cyBtdXN0IGJlIDAgaWYgUmVjdHMgaXMgTlVMTAogKiAgUmVjdHM6IFJlY3RhbmdsZXMgdG8gY2xlYXIuIElmIE5VTEwsIHRoZSB3aG9sZSBzdXJmYWNlIGlzIGNsZWFyZWQKICogIEZsYWdzOiBTb21lIGZsYWdzLCBhcyB1c3VhbAogKiAgQ29sb3I6IENsZWFyIGNvbG9yIGZvciB0aGUgcmVuZGVyIHRhcmdldAogKiAgWjogQ2xlYXIgdmFsdWUgZm9yIHRoZSBaIGJ1ZmZlcgogKiAgU3RlbmNpbDogQ2xlYXIgdmFsdWUgdG8gc3RvcmUgaW4gZWFjaCBzdGVuY2lsIGJ1ZmZlciBlbnRyeQogKgogKiBSZXR1cm5zOgogKiAgRDNEX09LIG9uIHN1Y2Nlc3MKICogIEZvciBkZXRhaWxzLCBzZWUgSVdpbmVEM0REZXZpY2U6OkNsZWFyCiAqCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIEhSRVNVTFQgV0lOQVBJCklEaXJlY3QzRERldmljZUltcGxfN19DbGVhcihJRGlyZWN0M0REZXZpY2U3ICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIENvdW50LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNEUkVDVCAqUmVjdHMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBGbGFncywKICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRENPTE9SIENvbG9yLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNEVkFMVUUgWiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIFN0ZW5jaWwpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTcsIGlmYWNlKTsKICAgIFRSQUNFKCIoJXApLT4oJTA4bHgsJXAsJTA4bHgsJTA4bHgsJWYsJTA4bHgpOiBSZWxheVxuIiwgVGhpcywgQ291bnQsIFJlY3RzLCBGbGFncywgKERXT1JEKSBDb2xvciwgWiwgU3RlbmNpbCk7CgogICAgcmV0dXJuIElXaW5lRDNERGV2aWNlX0NsZWFyKFRoaXMtPndpbmVEM0REZXZpY2UsIENvdW50LCBSZWN0cywgRmxhZ3MsIENvbG9yLCBaLCBTdGVuY2lsKTsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTc6OlNldFZpZXdwb3J0CiAqCiAqIFNldHMgdGhlIGN1cnJlbnQgdmlld3BvcnQuCiAqCiAqIFZlcnNpb24gNyBvbmx5LCBidXQgSURpcmVjdDNEVmlld3BvcnQgdXNlcyB0aGlzIGNhbGwgZm9yIG9sZGVyCiAqIHZlcnNpb25zCiAqCiAqIFBhcmFtczoKICogIERhdGE6IFRoZSBuZXcgdmlld3BvcnQgdG8gc2V0CiAqCiAqIFJldHVybnM6CiAqICBEM0RfT0sgb24gc3VjY2VzcwogKiAgRERFUlJfSU5WQUxJRFBBUkFNUyBpZiBEYXRhIGlzIE5VTEwKICogIEZvciBtb3JlIGRldGFpbHMsIHNlZSBJV2luZURERGV2aWNlOjpTZXRWaWV3cG9ydAogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0REZXZpY2VJbXBsXzdfU2V0Vmlld3BvcnQoSURpcmVjdDNERGV2aWNlNyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RWSUVXUE9SVDcgKkRhdGEpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTcsIGlmYWNlKTsKICAgIFRSQUNFKCIoJXApLT4oJXApIFJlbGF5IVxuIiwgVGhpcywgRGF0YSk7CgogICAgaWYoIURhdGEpCiAgICAgICAgcmV0dXJuIERERVJSX0lOVkFMSURQQVJBTVM7CgogICAgcmV0dXJuIElXaW5lRDNERGV2aWNlX1NldFZpZXdwb3J0KFRoaXMtPndpbmVEM0REZXZpY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRGF0YSk7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0REZXZpY2U6OkdldFZpZXdwb3J0CiAqCiAqIFJldHVybnMgdGhlIGN1cnJlbnQgdmlld3BvcnQKICoKICogVmVyc2lvbiA3CiAqCiAqIFBhcmFtczoKICogIERhdGE6IEQzRDdWaWV3cG9ydCBzdHJ1Y3R1cmUgdG8gd3JpdGUgdGhlIHZpZXdwb3J0IGluZm9ybWF0aW9uIHRvCiAqCiAqIFJldHVybnM6CiAqICBEM0RfT0sgb24gc3VjY2VzcwogKiAgRERFUlJfSU5WQUxJRFBBUkFNUyBpZiBEYXRhIGlzIE5VTEwKICogIEZvciBtb3JlIGRldGFpbHMsIHNlZSBJV2luZUQzRERldmljZTo6R2V0Vmlld3BvcnQKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKSURpcmVjdDNERGV2aWNlSW1wbF83X0dldFZpZXdwb3J0KElEaXJlY3QzRERldmljZTcgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNEVklFV1BPUlQ3ICpEYXRhKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2U3LCBpZmFjZSk7CiAgICBIUkVTVUxUIGhyOwogICAgVFJBQ0UoIiglcCktPiglcCkgUmVsYXkhXG4iLCBUaGlzLCBEYXRhKTsKCiAgICBpZighRGF0YSkKICAgICAgICByZXR1cm4gRERFUlJfSU5WQUxJRFBBUkFNUzsKCiAgICBociA9IElXaW5lRDNERGV2aWNlX0dldFZpZXdwb3J0KFRoaXMtPndpbmVEM0REZXZpY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERhdGEpOwogICAgcmV0dXJuIGhyX2RkcmF3X2Zyb21fd2luZWQzZChocik7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0REZXZpY2U3OjpTZXRNYXRlcmlhbAogKgogKiBTZXRzIHRoZSBNYXRlcmlhbAogKgogKiBWZXJzaW9uIDcKICoKICogUGFyYW1zOgogKiAgTWF0OiBUaGUgbWF0ZXJpYWwgdG8gc2V0CiAqCiAqIFJldHVybnM6CiAqICBEM0RfT0sgb24gc3VjY2VzcwogKiAgRERFUlJfSU5WQUxJRFBBUkFNUyBpZiBNYXQgaXMgTlVMTC4KICogIEZvciBtb3JlIGRldGFpbHMsIHNlZSBJV2luZUQzRERldmljZTo6U2V0TWF0ZXJpYWwKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKSURpcmVjdDNERGV2aWNlSW1wbF83X1NldE1hdGVyaWFsKElEaXJlY3QzRERldmljZTcgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNETUFURVJJQUw3ICpNYXQpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTcsIGlmYWNlKTsKICAgIEhSRVNVTFQgaHI7CiAgICBUUkFDRSgiKCVwKS0+KCVwKTogUmVsYXkhXG4iLCBUaGlzLCBNYXQpOwoKICAgIGhyID0gSVdpbmVEM0REZXZpY2VfU2V0TWF0ZXJpYWwoVGhpcy0+d2luZUQzRERldmljZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgTWF0KTsKICAgIHJldHVybiBocl9kZHJhd19mcm9tX3dpbmVkM2QoaHIpOwp9CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSURpcmVjdDNERGV2aWNlNzo6R2V0TWF0ZXJpYWwKICoKICogUmV0dXJucyB0aGUgY3VycmVudCBtYXRlcmlhbAogKgogKiBWZXJzaW9uIDcKICoKICogUGFyYW1zOgogKiAgTWF0OiBEM0RNQVRFUklBTDcgc3RydWN0dXJlIHRvIHdyaXRlIHRoZSBtYXRlcmlhbCBwYXJhbWV0ZXJzIHRvCiAqCiAqIFJldHVybnM6CiAqICBEM0RfT0sgb24gc3VjY2VzcwogKiAgRERFUlJfSU5WQUxJRFBBUkFNUyBpZiBNYXQgaXMgTlVMTAogKiAgRm9yIG1vcmUgZGV0YWlscywgc2VlIElXaW5lRDNERGV2aWNlOjpHZXRNYXRlcmlhbAogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0REZXZpY2VJbXBsXzdfR2V0TWF0ZXJpYWwoSURpcmVjdDNERGV2aWNlNyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RNQVRFUklBTDcgKk1hdCkKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlNywgaWZhY2UpOwogICAgSFJFU1VMVCBocjsKICAgIFRSQUNFKCIoJXApLT4oJXApOiBSZWxheSFcbiIsIFRoaXMsIE1hdCk7CgogICAgaHIgPSBJV2luZUQzRERldmljZV9HZXRNYXRlcmlhbChUaGlzLT53aW5lRDNERGV2aWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBNYXQpOwogICAgcmV0dXJuIGhyX2RkcmF3X2Zyb21fd2luZWQzZChocik7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0REZXZpY2U3OjpTZXRMaWdodAogKgogKiBBc3NpZ25zIGEgbGlnaHQgdG8gYSBsaWdodCBpbmRleCwgYnV0IGRvZXNuJ3QgYWN0aXZhdGUgaXQgeWV0LgogKgogKiBWZXJzaW9uIDcsIElEaXJlY3QzRExpZ2h0IHVzZXMgdGhpcyBtZXRob2QgZm9yIG9sZGVyIHZlcnNpb25zCiAqCiAqIFBhcmFtczoKICogIExpZ2h0SW5kZXg6IFRoZSBpbmRleCBvZiB0aGUgbmV3IGxpZ2h0CiAqICBMaWdodDogQSBEM0RMSUdIVDcgc3RydWN0dXJlIGRlc2NyaWJpbmcgdGhlIGxpZ2h0CiAqCiAqIFJldHVybnM6CiAqICBEM0RfT0sgb24gc3VjY2VzcwogKiAgRm9yIG1vcmUgZGV0YWlscywgc2VlIElXaW5lRDNERGV2aWNlOjpTZXRMaWdodAogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0REZXZpY2VJbXBsXzdfU2V0TGlnaHQoSURpcmVjdDNERGV2aWNlNyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBMaWdodEluZGV4LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRDNETElHSFQ3ICpMaWdodCkKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlNywgaWZhY2UpOwogICAgSFJFU1VMVCBocjsKICAgIFRSQUNFKCIoJXApLT4oJTA4bHgsJXApOiBSZWxheSFcbiIsIFRoaXMsIExpZ2h0SW5kZXgsIExpZ2h0KTsKCiAgICBociA9IElXaW5lRDNERGV2aWNlX1NldExpZ2h0KFRoaXMtPndpbmVEM0REZXZpY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIExpZ2h0SW5kZXgsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIExpZ2h0KTsKICAgIHJldHVybiBocl9kZHJhd19mcm9tX3dpbmVkM2QoaHIpOwp9CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSURpcmVjdDNERGV2aWNlNzo6R2V0TGlnaHQKICoKICogUmV0dXJucyB0aGUgbGlnaHQgYXNzaWduZWQgdG8gYSBsaWdodCBpbmRleAogKgogKiBQYXJhbXM6CiAqICBMaWdodDogU3RydWN0dXJlIHRvIHdyaXRlIHRoZSBsaWdodCBpbmZvcm1hdGlvbiB0bwogKgogKiBSZXR1cm5zOgogKiAgRDNEX09LIG9uIHN1Y2Nlc3MKICogIERERVJSX0lOVkFMSURQQVJBTVMgaWYgTGlnaHQgaXMgTlVMTAogKiAgRm9yIGRldGFpbHMsIHNlZSBJV2luZUQzRERldmljZTo6R2V0TGlnaHQKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKSURpcmVjdDNERGV2aWNlSW1wbF83X0dldExpZ2h0KElEaXJlY3QzRERldmljZTcgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgTGlnaHRJbmRleCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRExJR0hUNyAqTGlnaHQpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTcsIGlmYWNlKTsKICAgIEhSRVNVTFQgcmM7CiAgICBUUkFDRSgiKCVwKS0+KCUwOGx4LCVwKTogUmVsYXkhXG4iLCBUaGlzLCBMaWdodEluZGV4LCBMaWdodCk7CgogICAgcmMgPSAgSVdpbmVEM0REZXZpY2VfR2V0TGlnaHQoVGhpcy0+d2luZUQzRERldmljZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIExpZ2h0SW5kZXgsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBMaWdodCk7CgogICAgLyogVHJhbnNsYXRlIHRoZSByZXN1bHQuIFdpbmVEM0QgcmV0dXJucyBvdGhlciB2YWx1ZXMgdGhhbiBEM0Q3ICovCiAgICByZXR1cm4gaHJfZGRyYXdfZnJvbV93aW5lZDNkKHJjKTsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTc6OkJlZ2luU3RhdGVCbG9jawogKgogKiBCZWdpbnMgcmVjb3JkaW5nIHRvIGEgc3RhdGVibG9jawogKgogKiBWZXJzaW9uIDcKICoKICogUmV0dXJuczoKICogIEQzRF9PSyBvbiBzdWNjZXNzCiAqICBGb3IgZGV0YWlscyBzZWUgSVdpbmVEM0REZXZpY2U6OkJlZ2luU3RhdGVCbG9jawogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0REZXZpY2VJbXBsXzdfQmVnaW5TdGF0ZUJsb2NrKElEaXJlY3QzRERldmljZTcgKmlmYWNlKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2U3LCBpZmFjZSk7CiAgICBIUkVTVUxUIGhyOwogICAgVFJBQ0UoIiglcCktPigpOiBSZWxheSFcbiIsIFRoaXMpOwoKICAgIGhyID0gSVdpbmVEM0REZXZpY2VfQmVnaW5TdGF0ZUJsb2NrKFRoaXMtPndpbmVEM0REZXZpY2UpOwogICAgcmV0dXJuIGhyX2RkcmF3X2Zyb21fd2luZWQzZChocik7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0REZXZpY2U3OjpFbmRTdGF0ZUJsb2NrCiAqCiAqIFN0b3BzIHJlY29yZGluZyB0byBhIHN0YXRlIGJsb2NrIGFuZCByZXR1cm5zIHRoZSBjcmVhdGVkIHN0YXRlYmxvY2sKICogaGFuZGxlLiBUaGUgZDNkNyBzdGF0ZWJsb2NrIGhhbmRsZXMgYXJlIHRoZSBpbnRlcmZhY2UgcG9pbnRlcnMgb2YgdGhlCiAqIElXaW5lRDNEU3RhdGVCbG9jayBpbnRlcmZhY2UKICoKICogVmVyc2lvbiA3CiAqCiAqIFBhcmFtczoKICogIEJsb2NrSGFuZGxlOiBBZGRyZXNzIHRvIHN0b3JlIHRoZSBzdGF0ZWJsb2NrJ3MgaGFuZGxlIHRvCiAqCiAqIFJldHVybnM6CiAqICBEM0RfT0sgb24gc3VjY2VzcwogKiAgRERFUlJfSU5WQUxJRFBBUkFNUyBpZiBCbG9ja0hhbmRsZSBpcyBOVUxMCiAqICBTZWUgSVdpbmVEM0REZXZpY2U6OkVuZFN0YXRlQmxvY2sgZm9yIG1vcmUgZGV0YWlscwogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0REZXZpY2VJbXBsXzdfRW5kU3RhdGVCbG9jayhJRGlyZWN0M0REZXZpY2U3ICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgKkJsb2NrSGFuZGxlKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2U3LCBpZmFjZSk7CiAgICBIUkVTVUxUIGhyOwogICAgVFJBQ0UoIiglcCktPiglcCk6IFJlbGF5IVxuIiwgVGhpcywgQmxvY2tIYW5kbGUpOwoKICAgIGlmKCFCbG9ja0hhbmRsZSkKICAgICAgICByZXR1cm4gRERFUlJfSU5WQUxJRFBBUkFNUzsKCiAgICBociA9IElXaW5lRDNERGV2aWNlX0VuZFN0YXRlQmxvY2soVGhpcy0+d2luZUQzRERldmljZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAoSVdpbmVEM0RTdGF0ZUJsb2NrICoqKSBCbG9ja0hhbmRsZSk7CiAgICByZXR1cm4gaHJfZGRyYXdfZnJvbV93aW5lZDNkKGhyKTsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTc6OlByZUxvYWQKICoKICogQWxsb3dzIHRoZSBhcHAgdG8gc2lnbmFsIHRoYXQgYSB0ZXh0dXJlIHdpbGwgYmUgdXNlZCBzb29uLCB0byBhbGxvdwogKiB0aGUgRGlyZWN0M0REZXZpY2UgdG8gbG9hZCBpdCB0byB0aGUgdmlkZW8gY2FyZCBpbiB0aGUgbWVhbnRpbWUuCiAqCiAqIFZlcnNpb24gNwogKgogKiBQYXJhbXM6CiAqICBUZXh0dXJlOiBUaGUgdGV4dHVyZSB0byBwcmVsb2FkCiAqCiAqIFJldHVybnM6CiAqICBEM0RfT0sgb24gc3VjY2VzcwogKiAgRERFUlJfSU5WQUxJRFBBUkFNUyBpZiBUZXh0dXJlIGlzIE5VTEwKICogIFNlZSBJV2luZUQzRFN1cmZhY2U6OlByZUxvYWQgZm9yIGRldGFpbHMKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKSURpcmVjdDNERGV2aWNlSW1wbF83X1ByZUxvYWQoSURpcmVjdDNERGV2aWNlNyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIElEaXJlY3REcmF3U3VyZmFjZTcgKlRleHR1cmUpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTcsIGlmYWNlKTsKICAgIElEaXJlY3REcmF3U3VyZmFjZUltcGwgKnN1cmYgPSBJQ09NX09CSkVDVChJRGlyZWN0RHJhd1N1cmZhY2VJbXBsLCBJRGlyZWN0RHJhd1N1cmZhY2U3LCBUZXh0dXJlKTsKCiAgICBUUkFDRSgiKCVwKS0+KCVwKTogUmVsYXkhXG4iLCBUaGlzLCBzdXJmKTsKCiAgICBpZighVGV4dHVyZSkKICAgICAgICByZXR1cm4gRERFUlJfSU5WQUxJRFBBUkFNUzsKCiAgICBJV2luZUQzRFN1cmZhY2VfUHJlTG9hZChzdXJmLT5XaW5lRDNEU3VyZmFjZSk7CiAgICByZXR1cm4gRDNEX09LOwp9CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSURpcmVjdDNERGV2aWNlNzo6QXBwbHlTdGF0ZUJsb2NrCiAqCiAqIEFjdGl2YXRlcyB0aGUgc3RhdGUgc3RvcmVkIGluIGEgc3RhdGUgYmxvY2sgaGFuZGxlLgogKgogKiBQYXJhbXM6CiAqICBCbG9ja0hhbmRsZTogVGhlIHN0YXRlYmxvY2sgaGFuZGxlIHRvIGFjdGl2YXRlCiAqCiAqIFJldHVybnM6CiAqICBEM0RfT0sgb24gc3VjY2VzcwogKiAgRDNERVJSX0lOVkFMSURTVEFURUJMT0NLIGlmIEJsb2NrSGFuZGxlIGlzIE5VTEwKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKSURpcmVjdDNERGV2aWNlSW1wbF83X0FwcGx5U3RhdGVCbG9jayhJRGlyZWN0M0REZXZpY2U3ICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBCbG9ja0hhbmRsZSkKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlNywgaWZhY2UpOwogICAgSFJFU1VMVCBocjsKICAgIFRSQUNFKCIoJXApLT4oJTA4bHgpOiBSZWxheSFcbiIsIFRoaXMsIEJsb2NrSGFuZGxlKTsKCiAgICBpZighQmxvY2tIYW5kbGUpCiAgICAgICAgcmV0dXJuIEQzREVSUl9JTlZBTElEU1RBVEVCTE9DSzsKCiAgICBociA9IElXaW5lRDNEU3RhdGVCbG9ja19BcHBseSgoSVdpbmVEM0RTdGF0ZUJsb2NrICopIEJsb2NrSGFuZGxlKTsKICAgIHJldHVybiBocl9kZHJhd19mcm9tX3dpbmVkM2QoaHIpOwp9CgovKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioKICogSURpcmVjdDNERGV2aWNlNzo6Q2FwdHVyZVN0YXRlQmxvY2sKICoKICogVXBkYXRlcyBhIHN0YXRlYmxvY2sncyB2YWx1ZXMgdG8gdGhlIHZhbHVlcyBjdXJyZW50bHkgc2V0IGZvciB0aGUgZGV2aWNlCiAqCiAqIFZlcnNpb24gNwogKgogKiBQYXJhbXM6CiAqICBCbG9ja0hhbmRsZTogU3RhdGVibG9jayB0byB1cGRhdGUKICoKICogUmV0dXJuczoKICogIEQzRF9PSyBvbiBzdWNjZXNzCiAqICBEM0RFUlJfSU5WQUxJRFNUQVRFQkxPQ0sgaWYgQmxvY2tIYW5kbGUgaXMgTlVMTAogKiAgU2VlIElXaW5lRDNERGV2aWNlOjpDYXB0dXJlU3RhdGVCbG9jayBmb3IgbW9yZSBkZXRhaWxzCiAqCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIEhSRVNVTFQgV0lOQVBJCklEaXJlY3QzRERldmljZUltcGxfN19DYXB0dXJlU3RhdGVCbG9jayhJRGlyZWN0M0REZXZpY2U3ICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIEJsb2NrSGFuZGxlKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2U3LCBpZmFjZSk7CiAgICBIUkVTVUxUIGhyOwogICAgVFJBQ0UoIiglcCktPiglMDhseCk6IFJlbGF5IVxuIiwgVGhpcywgQmxvY2tIYW5kbGUpOwoKICAgIGlmKEJsb2NrSGFuZGxlID09IDApCiAgICAgICAgcmV0dXJuIEQzREVSUl9JTlZBTElEU1RBVEVCTE9DSzsKCiAgICBociA9IElXaW5lRDNEU3RhdGVCbG9ja19DYXB0dXJlKChJV2luZUQzRFN0YXRlQmxvY2sgKikgQmxvY2tIYW5kbGUpOwogICAgcmV0dXJuIGhyX2RkcmF3X2Zyb21fd2luZWQzZChocik7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0REZXZpY2U3OjpEZWxldGVTdGF0ZUJsb2NrCiAqCiAqIERlbGV0ZXMgYSBzdGF0ZWJsb2NrIGhhbmRsZS4gVGhpcyBtZWFucyByZWxlYXNpbmcgdGhlIFdpbmVEM0RTdGF0ZUJsb2NrCiAqCiAqIFZlcnNpb24gNwogKgogKiBQYXJhbXM6CiAqICBCbG9ja0hhbmRsZTogU3RhdGVibG9jayBoYW5kbGUgdG8gZGVsZXRlCiAqCiAqIFJldHVybnM6CiAqICBEM0RfT0sgb24gc3VjY2VzcwogKiAgRDNERVJSX0lOVkFMSURTVEFURUJMT0NLIGlmIEJsb2NrSGFuZGxlIGlzIDAKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKSURpcmVjdDNERGV2aWNlSW1wbF83X0RlbGV0ZVN0YXRlQmxvY2soSURpcmVjdDNERGV2aWNlNyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIEJsb2NrSGFuZGxlKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2U3LCBpZmFjZSk7CiAgICBUUkFDRSgiKCVwKS0+KCUwOGx4KTogUmVsYXkhXG4iLCBUaGlzLCBCbG9ja0hhbmRsZSk7CgogICAgaWYoQmxvY2tIYW5kbGUgPT0gMCkKICAgICAgICByZXR1cm4gRDNERVJSX0lOVkFMSURTVEFURUJMT0NLOwoKICAgIElXaW5lRDNEU3RhdGVCbG9ja19SZWxlYXNlKChJV2luZUQzRFN0YXRlQmxvY2sgKikgQmxvY2tIYW5kbGUpOwoKICAgIHJldHVybiBEM0RfT0s7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0REZXZpY2U3OjpDcmVhdGVTdGF0ZUJsb2NrCiAqCiAqIENyZWF0ZXMgYSBuZXcgc3RhdGUgYmxvY2sgaGFuZGxlLgogKgogKiBWZXJzaW9uIDcKICoKICogUGFyYW1zOgogKiAgVHlwZTogVGhlIHN0YXRlIGJsb2NrIHR5cGUKICogIEJsb2NrSGFuZGxlOiBBZGRyZXNzIHRvIHdyaXRlIHRoZSBjcmVhdGVkIGhhbmRsZSB0bwogKgogKiBSZXR1cm5zOgogKiAgIEQzRF9PSyBvbiBzdWNjZXNzCiAqICAgRERFUlJfSU5WQUxJRFBBUkFNUyBpZiBCbG9ja0hhbmRsZSBpcyBOVUxMCiAqCiAqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKi8Kc3RhdGljIEhSRVNVTFQgV0lOQVBJCklEaXJlY3QzRERldmljZUltcGxfN19DcmVhdGVTdGF0ZUJsb2NrKElEaXJlY3QzRERldmljZTcgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RTVEFURUJMT0NLVFlQRSBUeXBlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCAqQmxvY2tIYW5kbGUpCnsKICAgIElDT01fVEhJU19GUk9NKElEaXJlY3QzRERldmljZUltcGwsIElEaXJlY3QzRERldmljZTcsIGlmYWNlKTsKICAgIEhSRVNVTFQgaHI7CiAgICBUUkFDRSgiKCVwKS0+KCUwOHgsJXApIVxuIiwgVGhpcywgVHlwZSwgQmxvY2tIYW5kbGUpOwoKICAgIGlmKCFCbG9ja0hhbmRsZSkKICAgICAgICByZXR1cm4gRERFUlJfSU5WQUxJRFBBUkFNUzsKCiAgICAvKiBUaGUgRDNEU1RBVEVCTE9DS1RZUEUgZW51bSBpcyBmaW5lIGhlcmUgKi8KICAgIGhyID0gSVdpbmVEM0REZXZpY2VfQ3JlYXRlU3RhdGVCbG9jayhUaGlzLT53aW5lRDNERGV2aWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKElXaW5lRDNEU3RhdGVCbG9jayAqKikgQmxvY2tIYW5kbGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgTlVMTCAvKiBQYXJlbnQsIGhvcGUgdGhhdCB3b3JrcyAqLyk7CiAgICByZXR1cm4gaHJfZGRyYXdfZnJvbV93aW5lZDNkKGhyKTsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTc6OkxvYWQKICoKICogTG9hZHMgYSByZWN0YW5ndWxhciBhcmVhIGZyb20gdGhlIHNvdXJjZSBpbnRvIHRoZSBkZXN0aW5hdGlvbiB0ZXh0dXJlLgogKiBJdCBjYW4gYWxzbyBjb3B5IHRoZSBzb3VyY2UgdG8gdGhlIGZhY2VzIG9mIGEgY3ViaWMgZW52aXJvbm1lbnQgbWFwCiAqCiAqIFZlcnNpb24gNwogKgogKiBQYXJhbXM6CiAqICBEZXN0VGV4OiBEZXN0aW5hdGlvbiB0ZXh0dXJlCiAqICBEZXN0UG9pbnQ6IFBvaW50IGluIHRoZSBkZXN0aW5hdGlvbiB3aGVyZSB0aGUgc291cmNlIGltYWdlIHNob3VsZCBiZQogKiAgICAgICAgICAgICB3cml0dGVuIHRvCiAqICBTcmNUZXg6IFNvdXJjZSB0ZXh0dXJlCiAqICBTcmNSZWN0OiBTb3VyY2UgcmVjdGFuZ2xlCiAqICBGbGFnczogU29tZSBmbGFncwogKgogKiBSZXR1cm5zOgogKiAgRDNEX09LIG9uIHN1Y2Nlc3MKICogIERERVJSX0lOVkFMSURQQVJBTVMgaWYgRGVzdFRleCBvciBTcmNUZXggYXJlIE5VTEwKICogIFNlZSBJRGlyZWN0M0RUZXh0dXJlMjo6TG9hZCBmb3IgZGV0YWlscwogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0REZXZpY2VJbXBsXzdfTG9hZChJRGlyZWN0M0REZXZpY2U3ICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgSURpcmVjdERyYXdTdXJmYWNlNyAqRGVzdFRleCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgUE9JTlQgKkRlc3RQb2ludCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgSURpcmVjdERyYXdTdXJmYWNlNyAqU3JjVGV4LAogICAgICAgICAgICAgICAgICAgICAgICAgICBSRUNUICpTcmNSZWN0LAogICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBGbGFncykKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlNywgaWZhY2UpOwogICAgSURpcmVjdERyYXdTdXJmYWNlSW1wbCAqZGVzdCA9IElDT01fT0JKRUNUKElEaXJlY3REcmF3U3VyZmFjZUltcGwsIElEaXJlY3REcmF3U3VyZmFjZTcsIERlc3RUZXgpOwogICAgSURpcmVjdERyYXdTdXJmYWNlSW1wbCAqc3JjID0gSUNPTV9PQkpFQ1QoSURpcmVjdERyYXdTdXJmYWNlSW1wbCwgSURpcmVjdERyYXdTdXJmYWNlNywgU3JjVGV4KTsKICAgIEZJWE1FKCIoJXApLT4oJXAsJXAsJXAsJXAsJTA4bHgpOiBQYXJ0aWFsbHkgSW1wbGVtZW50ZWQhXG4iLCBUaGlzLCBkZXN0LCBEZXN0UG9pbnQsIHNyYywgU3JjUmVjdCwgRmxhZ3MpOwoKICAgIGlmKCAoIXNyYykgfHwgKCFkZXN0KSApCiAgICAgICAgcmV0dXJuIERERVJSX0lOVkFMSURQQVJBTVM7CgogICAgSURpcmVjdDNEVGV4dHVyZTJfTG9hZChJQ09NX0lOVEVSRkFDRShkZXN0LCBJRGlyZWN0M0RUZXh0dXJlMiksCiAgICAgICAgICAgICAgICAgICAgICAgICAgIElDT01fSU5URVJGQUNFKHNyYywgSURpcmVjdDNEVGV4dHVyZTIpKTsKICAgIHJldHVybiBEM0RfT0s7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0REZXZpY2U3OjpMaWdodEVuYWJsZQogKgogKiBFbmFibGVzIG9yIGRpc2FibGVzIGEgbGlnaHQKICoKICogVmVyc2lvbiA3LCBJRGlyZWN0M0RMaWdodCB1c2VzIHRoaXMgbWV0aG9kIHRvby4KICoKICogUGFyYW1zOgogKiAgTGlnaHRJbmRleDogVGhlIGluZGV4IG9mIHRoZSBsaWdodCB0byBlbmFibGUgLyBkaXNhYmxlCiAqICBFbmFibGU6IEVuYWJsZSBvciBkaXNhYmxlIHRoZSBsaWdodAogKgogKiBSZXR1cm5zOgogKiAgRDNEX09LIG9uIHN1Y2Nlc3MKICogIEZvciBtb3JlIGRldGFpbHMsIHNlZSBJV2luZUQzRERldmljZTo6U2V0TGlnaHRFbmFibGUKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKSURpcmVjdDNERGV2aWNlSW1wbF83X0xpZ2h0RW5hYmxlKElEaXJlY3QzRERldmljZTcgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgTGlnaHRJbmRleCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEJPT0wgRW5hYmxlKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2U3LCBpZmFjZSk7CiAgICBIUkVTVUxUIGhyOwogICAgVFJBQ0UoIiglcCktPiglMDhseCwlZCk6IFJlbGF5IVxuIiwgVGhpcywgTGlnaHRJbmRleCwgRW5hYmxlKTsKCiAgICBociA9IElXaW5lRDNERGV2aWNlX1NldExpZ2h0RW5hYmxlKFRoaXMtPndpbmVEM0REZXZpY2UsIExpZ2h0SW5kZXgsIEVuYWJsZSk7CiAgICByZXR1cm4gaHJfZGRyYXdfZnJvbV93aW5lZDNkKGhyKTsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTc6OkdldExpZ2h0RW5hYmxlCiAqCiAqIFJldHJpZXZlcyBpZiB0aGUgbGlnaHQgd2l0aCB0aGUgZ2l2ZW4gaW5kZXggaXMgZW5hYmxlZCBvciBub3QKICoKICogVmVyc2lvbiA3CiAqCiAqIFBhcmFtczoKICogIExpZ2h0SW5kZXg6IEluZGV4IG9mIGRlc2lyZWQgbGlnaHQKICogIEVuYWJsZTogUG9pbnRlciB0byBhIEJPT0wgd2hpY2ggY29udGFpbnMgdGhlIHJlc3VsdAogKgogKiBSZXR1cm5zOgogKiAgRDNEX09LIG9uIHN1Y2Nlc3MKICogIERERVJSX0lOVkFMSURQQVJBTVMgaWYgRW5hYmxlIGlzIE5VTEwKICogIFNlZSBJV2luZUQzRERldmljZTo6R2V0TGlnaHRFbmFibGUgZm9yIG1vcmUgZGV0YWlscwogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0REZXZpY2VJbXBsXzdfR2V0TGlnaHRFbmFibGUoSURpcmVjdDNERGV2aWNlNyAqaWZhY2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBMaWdodEluZGV4LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgQk9PTCogRW5hYmxlKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2U3LCBpZmFjZSk7CiAgICBIUkVTVUxUIGhyOwogICAgVFJBQ0UoIiglcCktPiglMDhseCwlcCk6IFJlbGF5XG4iLCBUaGlzLCBMaWdodEluZGV4LCBFbmFibGUpOwoKICAgIGlmKCFFbmFibGUpCiAgICAgICAgcmV0dXJuIERERVJSX0lOVkFMSURQQVJBTVM7CgogICAgaHIgPSBJV2luZUQzRERldmljZV9HZXRMaWdodEVuYWJsZShUaGlzLT53aW5lRDNERGV2aWNlLCBMaWdodEluZGV4LCBFbmFibGUpOwogICAgcmV0dXJuIGhyX2RkcmF3X2Zyb21fd2luZWQzZChocik7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0REZXZpY2U3OjpTZXRDbGlwUGxhbmUKICoKICogU2V0cyBjdXN0b20gY2xpcHBpbmcgcGxhbmUKICoKICogVmVyc2lvbiA3CiAqCiAqIFBhcmFtczoKICogIEluZGV4OiBUaGUgaW5kZXggb2YgdGhlIGNsaXBwaW5nIHBsYW5lCiAqICBQbGFuZUVxdWF0aW9uOiBBbiBlcXVhdGlvbiBkZWZpbmluZyB0aGUgY2xpcHBpbmcgcGxhbmUKICoKICogUmV0dXJuczoKICogIEQzRF9PSyBvbiBzdWNjZXNzCiAqICBEREVSUl9JTlZBTElEUEFSQU1TIGlmIFBsYW5lRXF1YXRpb24gaXMgTlVMTAogKiAgU2VlIElXaW5lRDNERGV2aWNlOjpTZXRDbGlwUGxhbmUgZm9yIG1vcmUgZGV0YWlscwogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0REZXZpY2VJbXBsXzdfU2V0Q2xpcFBsYW5lKElEaXJlY3QzRERldmljZTcgKmlmYWNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERXT1JEIEluZGV4LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEQzRFZBTFVFKiBQbGFuZUVxdWF0aW9uKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2U3LCBpZmFjZSk7CiAgICBUUkFDRSgiKCVwKS0+KCUwOGx4LCVwKTogUmVsYXkhXG4iLCBUaGlzLCBJbmRleCwgUGxhbmVFcXVhdGlvbik7CgogICAgaWYoIVBsYW5lRXF1YXRpb24pCiAgICAgICAgcmV0dXJuIERERVJSX0lOVkFMSURQQVJBTVM7CgogICAgcmV0dXJuIElXaW5lRDNERGV2aWNlX1NldENsaXBQbGFuZShUaGlzLT53aW5lRDNERGV2aWNlLCBJbmRleCwgUGxhbmVFcXVhdGlvbik7Cn0KCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0REZXZpY2U3OjpHZXRDbGlwUGxhbmUKICoKICogUmV0dXJucyB0aGUgY2xpcHBpbmcgcGxhbmUgd2l0aCBhIHNwZWNpZmljIGluZGV4CiAqCiAqIFBhcmFtczoKICogIEluZGV4OiBUaGUgaW5kZXggb2YgdGhlIGRlc2lyZWQgcGxhbmUKICogIFBsYW5lRXF1YXRpb246IEFkZHJlc3MgdG8gc3RvcmUgdGhlIHBsYW5lIGVxdWF0aW9uIHRvCiAqCiAqIFJldHVybnM6CiAqICBEM0RfT0sgb24gc3VjY2VzcwogKiAgRERFUlJfSU5WQUxJRFBBUkFNUyBpZiBQbGFuZUVxdWF0aW9uIGlzIE5VTEwKICogIFNlZSBJV2luZUQzRERldmljZTo6R2V0Q2xpcFBsYW5lIGZvciBtb3JlIGRldGFpbHMKICoKICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqLwpzdGF0aWMgSFJFU1VMVCBXSU5BUEkKSURpcmVjdDNERGV2aWNlSW1wbF83X0dldENsaXBQbGFuZShJRGlyZWN0M0REZXZpY2U3ICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBJbmRleCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEM0RWQUxVRSogUGxhbmVFcXVhdGlvbikKewogICAgSUNPTV9USElTX0ZST00oSURpcmVjdDNERGV2aWNlSW1wbCwgSURpcmVjdDNERGV2aWNlNywgaWZhY2UpOwogICAgVFJBQ0UoIiglcCktPiglbGQsJXApOiBSZWxheSFcbiIsIFRoaXMsIEluZGV4LCBQbGFuZUVxdWF0aW9uKTsKCiAgICBpZighUGxhbmVFcXVhdGlvbikKICAgICAgICByZXR1cm4gRERFUlJfSU5WQUxJRFBBUkFNUzsKCiAgICByZXR1cm4gSVdpbmVEM0REZXZpY2VfR2V0Q2xpcFBsYW5lKFRoaXMtPndpbmVEM0REZXZpY2UsIEluZGV4LCBQbGFuZUVxdWF0aW9uKTsKfQoKLyoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqCiAqIElEaXJlY3QzRERldmljZTc6OkdldEluZm8KICoKICogUmV0cmlldmVzIHNvbWUgaW5mb3JtYXRpb24gYWJvdXQgdGhlIGRldmljZS4gVGhlIERpcmVjdFggc2RrIHNheXMgdGhhdAogKiB0aGlzIHZlcnNpb24gcmV0dXJucyBTX0ZBTFNFIGZvciBhbGwgcmV0YWlsIGJ1aWxkcyBvZiBEaXJlY3RYLCB0aGF0J3Mgd2hhdAogKiB0aGlzIGltcGxlbWVudGF0aW9uIGRvZXMuCiAqCiAqIFBhcmFtczoKICogIERldkluZm9JRDogSW5mb3JtYXRpb24gdHlwZSByZXF1ZXN0ZWQKICogIERldkluZm9TdHJ1Y3Q6IFBvaW50ZXIgdG8gYSBzdHJ1Y3R1cmUgdG8gc3RvcmUgdGhlIGluZm8gdG8KICogIFNpemU6IFNpemUgb2YgdGhlIHN0cnVjdHVyZQogKgogKiBSZXR1cm5zOgogKiAgU19GQUxTRSwgYmVjYXVzZSBpdCdzIGEgbm9uLWRlYnVnIGRyaXZlcgogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCnN0YXRpYyBIUkVTVUxUIFdJTkFQSQpJRGlyZWN0M0REZXZpY2VJbXBsXzdfR2V0SW5mbyhJRGlyZWN0M0REZXZpY2U3ICppZmFjZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRFdPUkQgRGV2SW5mb0lELAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2b2lkICpEZXZJbmZvU3RydWN0LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICBEV09SRCBTaXplKQp7CiAgICBJQ09NX1RISVNfRlJPTShJRGlyZWN0M0REZXZpY2VJbXBsLCBJRGlyZWN0M0REZXZpY2U3LCBpZmFjZSk7CiAgICBUUkFDRSgiKCVwKS0+KCUwOGx4LCVwLCUwOGx4KVxuIiwgVGhpcywgRGV2SW5mb0lELCBEZXZJbmZvU3RydWN0LCBTaXplKTsKCiAgICBpZiAoVFJBQ0VfT04oZDNkNykpCiAgICB7CiAgICAgICAgVFJBQ0UoIiBpbmZvIHJlcXVlc3RlZCA6ICIpOwogICAgICAgIHN3aXRjaCAoRGV2SW5mb0lEKQogICAgICAgIHsKICAgICAgICAgICAgY2FzZSBEM0RERVZJTkZPSURfVEVYVFVSRU1BTkFHRVI6IFRSQUNFKCJEM0RERVZJTkZPSURfVEVYVFVSRU1BTkFHRVJcbiIpOyBicmVhazsKICAgICAgICAgICAgY2FzZSBEM0RERVZJTkZPSURfRDNEVEVYVFVSRU1BTkFHRVI6IFRSQUNFKCJEM0RERVZJTkZPSURfRDNEVEVYVFVSRU1BTkFHRVJcbiIpOyBicmVhazsKICAgICAgICAgICAgY2FzZSBEM0RERVZJTkZPSURfVEVYVFVSSU5HOiBUUkFDRSgiRDNEREVWSU5GT0lEX1RFWFRVUklOR1xuIik7IGJyZWFrOwogICAgICAgICAgICBkZWZhdWx0OiBFUlIoIiBpbnZhbGlkIGZsYWcgISEhXG4iKTsgcmV0dXJuIERERVJSX0lOVkFMSURQQVJBTVM7CiAgICAgICAgfQogICAgfQoKICAgIHJldHVybiBTX0ZBTFNFOyAvKiBBY2NvcmRpbmcgdG8gTVNETiwgdGhpcyBpcyB2YWxpZCBmb3IgYSBub24tZGVidWcgZHJpdmVyICovCn0KCmNvbnN0IElEaXJlY3QzRERldmljZTdWdGJsIElEaXJlY3QzRERldmljZTdfVnRibCA9CnsKICAgIC8qKiogSVVua25vd24gTWV0aG9kcyAqKiovCiAgICBJRGlyZWN0M0REZXZpY2VJbXBsXzdfUXVlcnlJbnRlcmZhY2UsCiAgICBJRGlyZWN0M0REZXZpY2VJbXBsXzdfQWRkUmVmLAogICAgSURpcmVjdDNERGV2aWNlSW1wbF83X1JlbGVhc2UsCiAgICAvKioqIElEaXJlY3QzRERldmljZTcgKioqLwogICAgSURpcmVjdDNERGV2aWNlSW1wbF83X0dldENhcHMsCiAgICBJRGlyZWN0M0REZXZpY2VJbXBsXzdfRW51bVRleHR1cmVGb3JtYXRzLAogICAgSURpcmVjdDNERGV2aWNlSW1wbF83X0JlZ2luU2NlbmUsCiAgICBJRGlyZWN0M0REZXZpY2VJbXBsXzdfRW5kU2NlbmUsCiAgICBJRGlyZWN0M0REZXZpY2VJbXBsXzdfR2V0RGlyZWN0M0QsCiAgICBJRGlyZWN0M0REZXZpY2VJbXBsXzdfU2V0UmVuZGVyVGFyZ2V0LAogICAgSURpcmVjdDNERGV2aWNlSW1wbF83X0dldFJlbmRlclRhcmdldCwKICAgIElEaXJlY3QzRERldmljZUltcGxfN19DbGVhciwKICAgIElEaXJlY3QzRERldmljZUltcGxfN19TZXRUcmFuc2Zvcm0sCiAgICBJRGlyZWN0M0REZXZpY2VJbXBsXzdfR2V0VHJhbnNmb3JtLAogICAgSURpcmVjdDNERGV2aWNlSW1wbF83X1NldFZpZXdwb3J0LAogICAgSURpcmVjdDNERGV2aWNlSW1wbF83X011bHRpcGx5VHJhbnNmb3JtLAogICAgSURpcmVjdDNERGV2aWNlSW1wbF83X0dldFZpZXdwb3J0LAogICAgSURpcmVjdDNERGV2aWNlSW1wbF83X1NldE1hdGVyaWFsLAogICAgSURpcmVjdDNERGV2aWNlSW1wbF83X0dldE1hdGVyaWFsLAogICAgSURpcmVjdDNERGV2aWNlSW1wbF83X1NldExpZ2h0LAogICAgSURpcmVjdDNERGV2aWNlSW1wbF83X0dldExpZ2h0LAogICAgSURpcmVjdDNERGV2aWNlSW1wbF83X1NldFJlbmRlclN0YXRlLAogICAgSURpcmVjdDNERGV2aWNlSW1wbF83X0dldFJlbmRlclN0YXRlLAogICAgSURpcmVjdDNERGV2aWNlSW1wbF83X0JlZ2luU3RhdGVCbG9jaywKICAgIElEaXJlY3QzRERldmljZUltcGxfN19FbmRTdGF0ZUJsb2NrLAogICAgSURpcmVjdDNERGV2aWNlSW1wbF83X1ByZUxvYWQsCiAgICBJRGlyZWN0M0REZXZpY2VJbXBsXzdfRHJhd1ByaW1pdGl2ZSwKICAgIElEaXJlY3QzRERldmljZUltcGxfN19EcmF3SW5kZXhlZFByaW1pdGl2ZSwKICAgIElEaXJlY3QzRERldmljZUltcGxfN19TZXRDbGlwU3RhdHVzLAogICAgSURpcmVjdDNERGV2aWNlSW1wbF83X0dldENsaXBTdGF0dXMsCiAgICBJRGlyZWN0M0REZXZpY2VJbXBsXzdfRHJhd1ByaW1pdGl2ZVN0cmlkZWQsCiAgICBJRGlyZWN0M0REZXZpY2VJbXBsXzdfRHJhd0luZGV4ZWRQcmltaXRpdmVTdHJpZGVkLAogICAgSURpcmVjdDNERGV2aWNlSW1wbF83X0RyYXdQcmltaXRpdmVWQiwKICAgIElEaXJlY3QzRERldmljZUltcGxfN19EcmF3SW5kZXhlZFByaW1pdGl2ZVZCLAogICAgSURpcmVjdDNERGV2aWNlSW1wbF83X0NvbXB1dGVTcGhlcmVWaXNpYmlsaXR5LAogICAgSURpcmVjdDNERGV2aWNlSW1wbF83X0dldFRleHR1cmUsCiAgICBJRGlyZWN0M0REZXZpY2VJbXBsXzdfU2V0VGV4dHVyZSwKICAgIElEaXJlY3QzRERldmljZUltcGxfN19HZXRUZXh0dXJlU3RhZ2VTdGF0ZSwKICAgIElEaXJlY3QzRERldmljZUltcGxfN19TZXRUZXh0dXJlU3RhZ2VTdGF0ZSwKICAgIElEaXJlY3QzRERldmljZUltcGxfN19WYWxpZGF0ZURldmljZSwKICAgIElEaXJlY3QzRERldmljZUltcGxfN19BcHBseVN0YXRlQmxvY2ssCiAgICBJRGlyZWN0M0REZXZpY2VJbXBsXzdfQ2FwdHVyZVN0YXRlQmxvY2ssCiAgICBJRGlyZWN0M0REZXZpY2VJbXBsXzdfRGVsZXRlU3RhdGVCbG9jaywKICAgIElEaXJlY3QzRERldmljZUltcGxfN19DcmVhdGVTdGF0ZUJsb2NrLAogICAgSURpcmVjdDNERGV2aWNlSW1wbF83X0xvYWQsCiAgICBJRGlyZWN0M0REZXZpY2VJbXBsXzdfTGlnaHRFbmFibGUsCiAgICBJRGlyZWN0M0REZXZpY2VJbXBsXzdfR2V0TGlnaHRFbmFibGUsCiAgICBJRGlyZWN0M0REZXZpY2VJbXBsXzdfU2V0Q2xpcFBsYW5lLAogICAgSURpcmVjdDNERGV2aWNlSW1wbF83X0dldENsaXBQbGFuZSwKICAgIElEaXJlY3QzRERldmljZUltcGxfN19HZXRJbmZvCn07Cgpjb25zdCBJRGlyZWN0M0REZXZpY2UzVnRibCBJRGlyZWN0M0REZXZpY2UzX1Z0YmwgPQp7CiAgICAvKioqIElVbmtub3duIE1ldGhvZHMgKioqLwogICAgVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8zX1F1ZXJ5SW50ZXJmYWNlLAogICAgVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8zX0FkZFJlZiwKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfM19SZWxlYXNlLAogICAgLyoqKiBJRGlyZWN0M0REZXZpY2UzICoqKi8KICAgIElEaXJlY3QzRERldmljZUltcGxfM19HZXRDYXBzLAogICAgSURpcmVjdDNERGV2aWNlSW1wbF8zX0dldFN0YXRzLAogICAgSURpcmVjdDNERGV2aWNlSW1wbF8zX0FkZFZpZXdwb3J0LAogICAgSURpcmVjdDNERGV2aWNlSW1wbF8zX0RlbGV0ZVZpZXdwb3J0LAogICAgSURpcmVjdDNERGV2aWNlSW1wbF8zX05leHRWaWV3cG9ydCwKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfM19FbnVtVGV4dHVyZUZvcm1hdHMsCiAgICBUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzNfQmVnaW5TY2VuZSwKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfM19FbmRTY2VuZSwKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfM19HZXREaXJlY3QzRCwKICAgIElEaXJlY3QzRERldmljZUltcGxfM19TZXRDdXJyZW50Vmlld3BvcnQsCiAgICBJRGlyZWN0M0REZXZpY2VJbXBsXzNfR2V0Q3VycmVudFZpZXdwb3J0LAogICAgVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8zX1NldFJlbmRlclRhcmdldCwKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfM19HZXRSZW5kZXJUYXJnZXQsCiAgICBJRGlyZWN0M0REZXZpY2VJbXBsXzNfQmVnaW4sCiAgICBJRGlyZWN0M0REZXZpY2VJbXBsXzNfQmVnaW5JbmRleGVkLAogICAgSURpcmVjdDNERGV2aWNlSW1wbF8zX1ZlcnRleCwKICAgIElEaXJlY3QzRERldmljZUltcGxfM19JbmRleCwKICAgIElEaXJlY3QzRERldmljZUltcGxfM19FbmQsCiAgICBUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzNfR2V0UmVuZGVyU3RhdGUsCiAgICBUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzNfU2V0UmVuZGVyU3RhdGUsCiAgICBJRGlyZWN0M0REZXZpY2VJbXBsXzNfR2V0TGlnaHRTdGF0ZSwKICAgIElEaXJlY3QzRERldmljZUltcGxfM19TZXRMaWdodFN0YXRlLAogICAgVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8zX1NldFRyYW5zZm9ybSwKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfM19HZXRUcmFuc2Zvcm0sCiAgICBUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzNfTXVsdGlwbHlUcmFuc2Zvcm0sCiAgICBUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzNfRHJhd1ByaW1pdGl2ZSwKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfM19EcmF3SW5kZXhlZFByaW1pdGl2ZSwKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfM19TZXRDbGlwU3RhdHVzLAogICAgVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8zX0dldENsaXBTdGF0dXMsCiAgICBUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzNfRHJhd1ByaW1pdGl2ZVN0cmlkZWQsCiAgICBUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzNfRHJhd0luZGV4ZWRQcmltaXRpdmVTdHJpZGVkLAogICAgVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8zX0RyYXdQcmltaXRpdmVWQiwKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfM19EcmF3SW5kZXhlZFByaW1pdGl2ZVZCLAogICAgVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8zX0NvbXB1dGVTcGhlcmVWaXNpYmlsaXR5LAogICAgVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8zX0dldFRleHR1cmUsCiAgICBUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzNfU2V0VGV4dHVyZSwKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfM19HZXRUZXh0dXJlU3RhZ2VTdGF0ZSwKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfM19TZXRUZXh0dXJlU3RhZ2VTdGF0ZSwKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfM19WYWxpZGF0ZURldmljZQp9OwoKY29uc3QgSURpcmVjdDNERGV2aWNlMlZ0YmwgSURpcmVjdDNERGV2aWNlMl9WdGJsID0KewogICAgLyoqKiBJVW5rbm93biBNZXRob2RzICoqKi8KICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfMl9RdWVyeUludGVyZmFjZSwKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfMl9BZGRSZWYsCiAgICBUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzJfUmVsZWFzZSwKICAgIC8qKiogSURpcmVjdDNERGV2aWNlMiAqKiovCiAgICBUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzJfR2V0Q2FwcywKICAgIElEaXJlY3QzRERldmljZUltcGxfMl9Td2FwVGV4dHVyZUhhbmRsZXMsCiAgICBUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzJfR2V0U3RhdHMsCiAgICBUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzJfQWRkVmlld3BvcnQsCiAgICBUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzJfRGVsZXRlVmlld3BvcnQsCiAgICBUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzJfTmV4dFZpZXdwb3J0LAogICAgSURpcmVjdDNERGV2aWNlSW1wbF8yX0VudW1UZXh0dXJlRm9ybWF0cywKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfMl9CZWdpblNjZW5lLAogICAgVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8yX0VuZFNjZW5lLAogICAgVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8yX0dldERpcmVjdDNELAogICAgVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8yX1NldEN1cnJlbnRWaWV3cG9ydCwKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfMl9HZXRDdXJyZW50Vmlld3BvcnQsCiAgICBUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzJfU2V0UmVuZGVyVGFyZ2V0LAogICAgVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8yX0dldFJlbmRlclRhcmdldCwKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfMl9CZWdpbiwKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfMl9CZWdpbkluZGV4ZWQsCiAgICBUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzJfVmVydGV4LAogICAgVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8yX0luZGV4LAogICAgVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8yX0VuZCwKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfMl9HZXRSZW5kZXJTdGF0ZSwKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfMl9TZXRSZW5kZXJTdGF0ZSwKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfMl9HZXRMaWdodFN0YXRlLAogICAgVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8yX1NldExpZ2h0U3RhdGUsCiAgICBUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzJfU2V0VHJhbnNmb3JtLAogICAgVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8yX0dldFRyYW5zZm9ybSwKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfMl9NdWx0aXBseVRyYW5zZm9ybSwKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfMl9EcmF3UHJpbWl0aXZlLAogICAgVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8yX0RyYXdJbmRleGVkUHJpbWl0aXZlLAogICAgVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8yX1NldENsaXBTdGF0dXMsCiAgICBUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzJfR2V0Q2xpcFN0YXR1cwp9OwoKY29uc3QgSURpcmVjdDNERGV2aWNlVnRibCBJRGlyZWN0M0REZXZpY2UxX1Z0YmwgPQp7CiAgICAvKioqIElVbmtub3duIE1ldGhvZHMgKioqLwogICAgVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8xX1F1ZXJ5SW50ZXJmYWNlLAogICAgVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8xX0FkZFJlZiwKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfMV9SZWxlYXNlLAogICAgLyoqKiBJRGlyZWN0M0REZXZpY2UxICoqKi8KICAgIElEaXJlY3QzRERldmljZUltcGxfMV9Jbml0aWFsaXplLAogICAgVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8xX0dldENhcHMsCiAgICBUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzFfU3dhcFRleHR1cmVIYW5kbGVzLAogICAgSURpcmVjdDNERGV2aWNlSW1wbF8xX0NyZWF0ZUV4ZWN1dGVCdWZmZXIsCiAgICBUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzFfR2V0U3RhdHMsCiAgICBJRGlyZWN0M0REZXZpY2VJbXBsXzFfRXhlY3V0ZSwKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfMV9BZGRWaWV3cG9ydCwKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfMV9EZWxldGVWaWV3cG9ydCwKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfMV9OZXh0Vmlld3BvcnQsCiAgICBJRGlyZWN0M0REZXZpY2VJbXBsXzFfUGljaywKICAgIElEaXJlY3QzRERldmljZUltcGxfMV9HZXRQaWNrUmVjb3JkcywKICAgIFRodW5rX0lEaXJlY3QzRERldmljZUltcGxfMV9FbnVtVGV4dHVyZUZvcm1hdHMsCiAgICBJRGlyZWN0M0REZXZpY2VJbXBsXzFfQ3JlYXRlTWF0cml4LAogICAgSURpcmVjdDNERGV2aWNlSW1wbF8xX1NldE1hdHJpeCwKICAgIElEaXJlY3QzRERldmljZUltcGxfMV9HZXRNYXRyaXgsCiAgICBJRGlyZWN0M0REZXZpY2VJbXBsXzFfRGVsZXRlTWF0cml4LAogICAgVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8xX0VuZFNjZW5lLAogICAgVGh1bmtfSURpcmVjdDNERGV2aWNlSW1wbF8xX0JlZ2luU2NlbmUsCiAgICBUaHVua19JRGlyZWN0M0REZXZpY2VJbXBsXzFfR2V0RGlyZWN0M0QKfTsKCi8qKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogKiBJRGlyZWN0M0REZXZpY2VJbXBsX0NyZWF0ZUhhbmRsZQogKgogKiBOb3QgY2FsbGVkIGZyb20gdGhlIFZUYWJsZQogKgogKiBTb21lIG9sZGVyIGludGVyZmFjZSB2ZXJzaW9ucyBvcGVyYXRlIHdpdGggaGFuZGxlcywgd2hpY2ggYXJlIGJhc2ljYWxseQogKiBEV09SRHMgd2hpY2ggaWRlbnRpZnkgYW4gaW50ZXJmYWNlLCBmb3IgZXhhbXBsZQogKiBJRGlyZWN0M0REZXZpY2U6OlNldFJlbmRlclN0YXRlIHdpdGggRElSRUNUM0RSRU5ERVJTVEFURV9URVhUVVJFSEFORExFCiAqCiAqIFRob3NlIGhhbmRsZSBjb3VsZCBiZSBqdXN0IGNhc3RzIHRvIHRoZSBpbnRlcmZhY2UgcG9pbnRlcnMgb3IgdmljZSB2ZXJzYSwKICogYnV0IHRoYXQgaXMgbm90IDY0IGJpdCBzYWZlIGFuZCB3b3VsZCBtZWFuIGJsaW5kbHkgZGVyZWZlcmluZyBhIERXT1JECiAqIHBhc3NlZCBieSB0aGUgYXBwLiBJbnN0ZWFkIHRoZXJlIGlzIGEgZHluYW1pYyBhcnJheSBpbiB0aGUgZGV2aWNlIHdoaWNoCiAqIGtlZXBzIGEgRFdPUkQgdG8gcG9pbnRlciBpbmZvcm1hdGlvbiBhbmQgYSB0eXBlIGZvciB0aGUgaGFuZGxlLgogKgogKiBCYXNpY2FsbHkgdGhpcyBhcnJheSBvbmx5IGdyb3dzLCB3aGVuIGEgaGFuZGxlIGlzIGZyZWVkIGl0cyBwb2ludGVyIGlzCiAqIGp1c3Qgc2V0IHRvIE5VTEwuIFRoZXJlIHdpbGwgYmUgbXVjaCBtb3JlIHJlYWRzIGZyb20gdGhlIGFycmF5IHRoYW4KICogaW5zZXJ0aW9uIG9wZXJhdGlvbnMsIHNvIGEgZHluYW1pYyBhcnJheSBpcyBmaW5lLgogKgogKiBQYXJhbXM6CiAqICBUaGlzOiBEM0REZXZpY2UgaW1wbGVtZW50YXRpb24gZm9yIHdoaWNoIHRoaXMgaGFuZGxlIHNob3VsZCBiZSBjcmVhdGVkCiAqCiAqIFJldHVybnM6CiAqICBBIGZyZWUgaGFuZGxlIG9uIHN1Y2Nlc3MKICogIDAgb24gZmFpbHVyZQogKgogKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCkRXT1JECklEaXJlY3QzRERldmljZUltcGxfQ3JlYXRlSGFuZGxlKElEaXJlY3QzRERldmljZUltcGwgKlRoaXMpCnsKICAgIERXT1JEIGk7CiAgICBzdHJ1Y3QgSGFuZGxlRW50cnkgKm9sZEhhbmRsZXMgPSBUaGlzLT5IYW5kbGVzOwoKICAgIFRSQUNFKCIoJXApXG4iLCBUaGlzKTsKCiAgICBmb3IoaSA9IDA7IGkgPCBUaGlzLT5udW1IYW5kbGVzOyBpKyspCiAgICB7CiAgICAgICAgaWYoVGhpcy0+SGFuZGxlc1tpXS5wdHIgPT0gTlVMTCAmJgogICAgICAgICAgIFRoaXMtPkhhbmRsZXNbaV0udHlwZSA9PSBERHJhd0hhbmRsZV9Vbmtub3duKQogICAgICAgIHsKICAgICAgICAgICAgVFJBQ0UoIlJldXNpbmcgZnJlZWQgaGFuZGxlICVsZFxuIiwgaSArIDEpOwogICAgICAgICAgICByZXR1cm4gaSArIDE7CiAgICAgICAgfQogICAgfQoKICAgIFRSQUNFKCJHcm93aW5nIHRoZSBoYW5kbGUgYXJyYXlcbiIpOwoKICAgIFRoaXMtPm51bUhhbmRsZXMrKzsKICAgIFRoaXMtPkhhbmRsZXMgPSBIZWFwQWxsb2MoR2V0UHJvY2Vzc0hlYXAoKSwgMCwgc2l6ZW9mKHN0cnVjdCBIYW5kbGVFbnRyeSkgKiBUaGlzLT5udW1IYW5kbGVzKTsKICAgIGlmKCFUaGlzLT5IYW5kbGVzKQogICAgewogICAgICAgIEVSUigiT3V0IG9mIG1lbW9yeVxuIik7CiAgICAgICAgVGhpcy0+SGFuZGxlcyA9IG9sZEhhbmRsZXM7CiAgICAgICAgVGhpcy0+bnVtSGFuZGxlcy0tOwogICAgICAgIHJldHVybiAwOwogICAgfQogICAgaWYob2xkSGFuZGxlcykKICAgIHsKICAgICAgICBtZW1jcHkoVGhpcy0+SGFuZGxlcywgb2xkSGFuZGxlcywgKFRoaXMtPm51bUhhbmRsZXMgLSAxKSAqIHNpemVvZihzdHJ1Y3QgSGFuZGxlRW50cnkpKTsKICAgICAgICBIZWFwRnJlZShHZXRQcm9jZXNzSGVhcCgpLCAwLCBvbGRIYW5kbGVzKTsKICAgIH0KCiAgICBUUkFDRSgiUmV0dXJuaW5nICVsZFxuIiwgVGhpcy0+bnVtSGFuZGxlcyk7CiAgICByZXR1cm4gVGhpcy0+bnVtSGFuZGxlczsKfQo=