#! /usr/bin/python3 -s

# The MIT License (MIT)
#
# Copyright (c) 2019 Caian Benedicto <caian@ggaunicamp.com>
#
# Permission is hereby granted, free of charge, to any person obtaining a copy
# of this software and associated documentation files (the "Software"), to
# deal in the Software without restriction, including without limitation the
# rights to use, copy, modify, merge, publish, distribute, sublicense,
# and/or sell copies of the Software, and to permit persons to whom the
# Software is furnished to do so, subject to the following conditions:
#
# The above copyright notice and this permission notice shall be included in
# all copies or substantial portions of the Software.
#
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
# THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
# IN THE SOFTWARE.

import sys, os, base64

_apis = {
    'c': {
        'spitz.h': 'LyoKICogVGhlIE1JVCBMaWNlbnNlIChNSVQpCiAqCiAqIENvcHlyaWdodCAoYykgMjAxNSBDYWlhbiBCZW5lZGljdG8gPGNhaWFuQGdnYXVuaWNhbXAuY29tPgogKiBDb3B5cmlnaHQgKGMpIDIwMTQgSWFuIExpdSBSb2RyaWd1ZXMgPGlhbi5saXVAZ2dhdW5pY2FtcC5jb20+CiAqCiAqIFBlcm1pc3Npb24gaXMgaGVyZWJ5IGdyYW50ZWQsIGZyZWUgb2YgY2hhcmdlLCB0byBhbnkgcGVyc29uIG9idGFpbmluZyBhIGNvcHkgCiAqIG9mIHRoaXMgc29mdHdhcmUgYW5kIGFzc29jaWF0ZWQgZG9jdW1lbnRhdGlvbiBmaWxlcyAodGhlICJTb2Z0d2FyZSIpLCB0byAKICogZGVhbCBpbiB0aGUgU29mdHdhcmUgd2l0aG91dCByZXN0cmljdGlvbiwgaW5jbHVkaW5nIHdpdGhvdXQgbGltaXRhdGlvbiB0aGUgCiAqIHJpZ2h0cyB0byB1c2UsIGNvcHksIG1vZGlmeSwgbWVyZ2UsIHB1Ymxpc2gsIGRpc3RyaWJ1dGUsIHN1YmxpY2Vuc2UsIAogKiBhbmQvb3Igc2VsbCBjb3BpZXMgb2YgdGhlIFNvZnR3YXJlLCBhbmQgdG8gcGVybWl0IHBlcnNvbnMgdG8gd2hvbSB0aGUgCiAqIFNvZnR3YXJlIGlzIGZ1cm5pc2hlZCB0byBkbyBzbywgc3ViamVjdCB0byB0aGUgZm9sbG93aW5nIGNvbmRpdGlvbnM6CiAqIAogKiBUaGUgYWJvdmUgY29weXJpZ2h0IG5vdGljZSBhbmQgdGhpcyBwZXJtaXNzaW9uIG5vdGljZSBzaGFsbCBiZSBpbmNsdWRlZCBpbiAKICogYWxsIGNvcGllcyBvciBzdWJzdGFudGlhbCBwb3J0aW9ucyBvZiB0aGUgU29mdHdhcmUuCiAqIAogKiBUSEUgU09GVFdBUkUgSVMgUFJPVklERUQgIkFTIElTIiwgV0lUSE9VVCBXQVJSQU5UWSBPRiBBTlkgS0lORCwgRVhQUkVTUyBPUiAKICogSU1QTElFRCwgSU5DTFVESU5HIEJVVCBOT1QgTElNSVRFRCBUTyBUSEUgV0FSUkFOVElFUyBPRiBNRVJDSEFOVEFCSUxJVFksIAogKiBGSVRORVNTIEZPUiBBIFBBUlRJQ1VMQVIgUFVSUE9TRSBBTkQgTk9OSU5GUklOR0VNRU5ULiBJTiBOTyBFVkVOVCBTSEFMTCAKICogVEhFIEFVVEhPUlMgT1IgQ09QWVJJR0hUIEhPTERFUlMgQkUgTElBQkxFIEZPUiBBTlkgQ0xBSU0sIERBTUFHRVMgT1IgT1RIRVIgCiAqIExJQUJJTElUWSwgV0hFVEhFUiBJTiBBTiBBQ1RJT04gT0YgQ09OVFJBQ1QsIFRPUlQgT1IgT1RIRVJXSVNFLCBBUklTSU5HIAogKiBGUk9NLCBPVVQgT0YgT1IgSU4gQ09OTkVDVElPTiBXSVRIIFRIRSBTT0ZUV0FSRSBPUiBUSEUgVVNFIE9SIE9USEVSIERFQUxJTkdTIAogKiBJTiBUSEUgU09GVFdBUkUuCiAqLwoKI2lmbmRlZiBfX1NQSVRaX0hfXwojZGVmaW5lIF9fU1BJVFpfSF9fCgojaWZkZWYgX19jcGx1c3BsdXMKZXh0ZXJuICJDIiB7CiNlbmRpZgoKIC8qIFB5dGhvbiB2ZXJzaW9uIG9mIHNwaXRzIHVzZXMgY2RlY2wgY2FsbGluZyBjb252ZW50aW9uICovCgovKiBUaGUgc2l6ZSB1c2VkIHRvIHBhc3MgbWVzc2FnZXMgaXMgNjQgYml0ICovCgp0eXBlZGVmIGxvbmcgbG9uZyBpbnQgc3BpdHNzaXplX3Q7Cgp0eXBlZGVmIGNvbnN0IHZvaWQqIHNwaXRzY3R4X3Q7CgovKiBSdW5uZXIgY2FsbGJhY2sgdGhhdCBleGVjdXRlcyB0aGUgdGFzayBkaXN0cmlidXRpb24gYW5kIGNvbW1pdHRpbmcgKi8KCnR5cGVkZWYgaW50ICgqc3BpdHpydW5fdCkoaW50LCBjb25zdCBjaGFyKiosIGNvbnN0IHZvaWQqLCBzcGl0c3NpemVfdCwgCiAgICBjb25zdCB2b2lkKiosIHNwaXRzc2l6ZV90Kik7CgovKiBQdXNoZXIgY2FsbGJhY2sgdGhhdCBwZXJmb3JtcyByZXN1bHQgc3VibWlzc2lvbiBmcm9tIGEgd29ya2VyICovCgp0eXBlZGVmIHZvaWQgKCpzcGl0c3B1c2hfdCkoY29uc3Qgdm9pZCosIHNwaXRzc2l6ZV90LCBzcGl0c2N0eF90KTsKCi8qIFNwaXRzIG1haW4gKi8KCmludCBzcGl0c19tYWluKGludCBhcmdjLCBjb25zdCBjaGFyKiBhcmd2W10sIHNwaXR6cnVuX3QgcnVuKTsKCi8qIEpvYiBNYW5hZ2VyICovCgp2b2lkKiBzcGl0c19qb2JfbWFuYWdlcl9uZXcoaW50IGFyZ2MsIGNvbnN0IGNoYXIgKmFyZ3ZbXSwKICAgIGNvbnN0IHZvaWQqIGpvYmluZm8sIHNwaXRzc2l6ZV90IGpvYmluZm9zeik7CgppbnQgc3BpdHNfam9iX21hbmFnZXJfbmV4dF90YXNrKHZvaWQgKnVzZXJfZGF0YSwgCiAgICBzcGl0c3B1c2hfdCBwdXNoX3Rhc2ssIHNwaXRzY3R4X3Qgam1jdHgpOwoKdm9pZCBzcGl0c19qb2JfbWFuYWdlcl9maW5hbGl6ZSh2b2lkICp1c2VyX2RhdGEpOwoKLyogV29ya2VyICovCgp2b2lkKiBzcGl0c193b3JrZXJfbmV3KGludCBhcmdjLCBjb25zdCBjaGFyICphcmd2W10pOwoKaW50IHNwaXRzX3dvcmtlcl9ydW4odm9pZCAqdXNlcl9kYXRhLCBjb25zdCB2b2lkKiB0YXNrLCAKICAgIHNwaXRzc2l6ZV90IHRhc2tzeiwgc3BpdHNwdXNoX3QgcHVzaF9yZXN1bHQsIAogICAgc3BpdHNjdHhfdCB0YXNrY3R4KTsKCnZvaWQgc3BpdHNfd29ya2VyX2ZpbmFsaXplKHZvaWQgKnVzZXJfZGF0YSk7CgovKiBDb21taXR0ZXIgKi8KCnZvaWQqIHNwaXRzX2NvbW1pdHRlcl9uZXcoaW50IGFyZ2MsIGNvbnN0IGNoYXIgKmFyZ3ZbXSwKICAgIGNvbnN0IHZvaWQqIGpvYmluZm8sIHNwaXRzc2l6ZV90IGpvYmluZm9zeik7CgppbnQgc3BpdHNfY29tbWl0dGVyX2NvbW1pdF9waXQodm9pZCAqdXNlcl9kYXRhLAogICAgY29uc3Qgdm9pZCogcmVzdWx0LCBzcGl0c3NpemVfdCByZXN1bHRzeik7CgppbnQgc3BpdHNfY29tbWl0dGVyX2NvbW1pdF9qb2Iodm9pZCAqdXNlcl9kYXRhLAogICAgc3BpdHNwdXNoX3QgcHVzaF9maW5hbF9yZXN1bHQsIHNwaXRzY3R4X3Qgam9iY3R4KTsKCnZvaWQgc3BpdHNfY29tbWl0dGVyX2ZpbmFsaXplKHZvaWQgKnVzZXJfZGF0YSk7CgojaWZkZWYgX19jcGx1c3BsdXMKfQojZW5kaWYKCiNlbmRpZiAvKiBfX1NQSVRaX0hfXyAqLwo='
    },
    'cpp': {
        'spitz.h': 'LyoKICogVGhlIE1JVCBMaWNlbnNlIChNSVQpCiAqCiAqIENvcHlyaWdodCAoYykgMjAxNSBDYWlhbiBCZW5lZGljdG8gPGNhaWFuQGdnYXVuaWNhbXAuY29tPgogKiBDb3B5cmlnaHQgKGMpIDIwMTQgSWFuIExpdSBSb2RyaWd1ZXMgPGlhbi5saXVAZ2dhdW5pY2FtcC5jb20+CiAqCiAqIFBlcm1pc3Npb24gaXMgaGVyZWJ5IGdyYW50ZWQsIGZyZWUgb2YgY2hhcmdlLCB0byBhbnkgcGVyc29uIG9idGFpbmluZyBhIGNvcHkgCiAqIG9mIHRoaXMgc29mdHdhcmUgYW5kIGFzc29jaWF0ZWQgZG9jdW1lbnRhdGlvbiBmaWxlcyAodGhlICJTb2Z0d2FyZSIpLCB0byAKICogZGVhbCBpbiB0aGUgU29mdHdhcmUgd2l0aG91dCByZXN0cmljdGlvbiwgaW5jbHVkaW5nIHdpdGhvdXQgbGltaXRhdGlvbiB0aGUgCiAqIHJpZ2h0cyB0byB1c2UsIGNvcHksIG1vZGlmeSwgbWVyZ2UsIHB1Ymxpc2gsIGRpc3RyaWJ1dGUsIHN1YmxpY2Vuc2UsIAogKiBhbmQvb3Igc2VsbCBjb3BpZXMgb2YgdGhlIFNvZnR3YXJlLCBhbmQgdG8gcGVybWl0IHBlcnNvbnMgdG8gd2hvbSB0aGUgCiAqIFNvZnR3YXJlIGlzIGZ1cm5pc2hlZCB0byBkbyBzbywgc3ViamVjdCB0byB0aGUgZm9sbG93aW5nIGNvbmRpdGlvbnM6CiAqIAogKiBUaGUgYWJvdmUgY29weXJpZ2h0IG5vdGljZSBhbmQgdGhpcyBwZXJtaXNzaW9uIG5vdGljZSBzaGFsbCBiZSBpbmNsdWRlZCBpbiAKICogYWxsIGNvcGllcyBvciBzdWJzdGFudGlhbCBwb3J0aW9ucyBvZiB0aGUgU29mdHdhcmUuCiAqIAogKiBUSEUgU09GVFdBUkUgSVMgUFJPVklERUQgIkFTIElTIiwgV0lUSE9VVCBXQVJSQU5UWSBPRiBBTlkgS0lORCwgRVhQUkVTUyBPUiAKICogSU1QTElFRCwgSU5DTFVESU5HIEJVVCBOT1QgTElNSVRFRCBUTyBUSEUgV0FSUkFOVElFUyBPRiBNRVJDSEFOVEFCSUxJVFksIAogKiBGSVRORVNTIEZPUiBBIFBBUlRJQ1VMQVIgUFVSUE9TRSBBTkQgTk9OSU5GUklOR0VNRU5ULiBJTiBOTyBFVkVOVCBTSEFMTCAKICogVEhFIEFVVEhPUlMgT1IgQ09QWVJJR0hUIEhPTERFUlMgQkUgTElBQkxFIEZPUiBBTlkgQ0xBSU0sIERBTUFHRVMgT1IgT1RIRVIgCiAqIExJQUJJTElUWSwgV0hFVEhFUiBJTiBBTiBBQ1RJT04gT0YgQ09OVFJBQ1QsIFRPUlQgT1IgT1RIRVJXSVNFLCBBUklTSU5HIAogKiBGUk9NLCBPVVQgT0YgT1IgSU4gQ09OTkVDVElPTiBXSVRIIFRIRSBTT0ZUV0FSRSBPUiBUSEUgVVNFIE9SIE9USEVSIERFQUxJTkdTIAogKiBJTiBUSEUgU09GVFdBUkUuCiAqLwoKI2lmbmRlZiBfX1NQSVRaX0hfXwojZGVmaW5lIF9fU1BJVFpfSF9fCgojaWZkZWYgX19jcGx1c3BsdXMKZXh0ZXJuICJDIiB7CiNlbmRpZgoKIC8qIFB5dGhvbiB2ZXJzaW9uIG9mIHNwaXRzIHVzZXMgY2RlY2wgY2FsbGluZyBjb252ZW50aW9uICovCgovKiBUaGUgc2l6ZSB1c2VkIHRvIHBhc3MgbWVzc2FnZXMgaXMgNjQgYml0ICovCgp0eXBlZGVmIGxvbmcgbG9uZyBpbnQgc3BpdHNzaXplX3Q7Cgp0eXBlZGVmIGNvbnN0IHZvaWQqIHNwaXRzY3R4X3Q7CgovKiBSdW5uZXIgY2FsbGJhY2sgdGhhdCBleGVjdXRlcyB0aGUgdGFzayBkaXN0cmlidXRpb24gYW5kIGNvbW1pdHRpbmcgKi8KCnR5cGVkZWYgaW50ICgqc3BpdHpydW5fdCkoaW50LCBjb25zdCBjaGFyKiosIGNvbnN0IHZvaWQqLCBzcGl0c3NpemVfdCwgCiAgICBjb25zdCB2b2lkKiosIHNwaXRzc2l6ZV90Kik7CgovKiBQdXNoZXIgY2FsbGJhY2sgdGhhdCBwZXJmb3JtcyByZXN1bHQgc3VibWlzc2lvbiBmcm9tIGEgd29ya2VyICovCgp0eXBlZGVmIHZvaWQgKCpzcGl0c3B1c2hfdCkoY29uc3Qgdm9pZCosIHNwaXRzc2l6ZV90LCBzcGl0c2N0eF90KTsKCi8qIFNwaXRzIG1haW4gKi8KCmludCBzcGl0c19tYWluKGludCBhcmdjLCBjb25zdCBjaGFyKiBhcmd2W10sIHNwaXR6cnVuX3QgcnVuKTsKCi8qIEpvYiBNYW5hZ2VyICovCgp2b2lkKiBzcGl0c19qb2JfbWFuYWdlcl9uZXcoaW50IGFyZ2MsIGNvbnN0IGNoYXIgKmFyZ3ZbXSwKICAgIGNvbnN0IHZvaWQqIGpvYmluZm8sIHNwaXRzc2l6ZV90IGpvYmluZm9zeik7CgppbnQgc3BpdHNfam9iX21hbmFnZXJfbmV4dF90YXNrKHZvaWQgKnVzZXJfZGF0YSwgCiAgICBzcGl0c3B1c2hfdCBwdXNoX3Rhc2ssIHNwaXRzY3R4X3Qgam1jdHgpOwoKdm9pZCBzcGl0c19qb2JfbWFuYWdlcl9maW5hbGl6ZSh2b2lkICp1c2VyX2RhdGEpOwoKLyogV29ya2VyICovCgp2b2lkKiBzcGl0c193b3JrZXJfbmV3KGludCBhcmdjLCBjb25zdCBjaGFyICphcmd2W10pOwoKaW50IHNwaXRzX3dvcmtlcl9ydW4odm9pZCAqdXNlcl9kYXRhLCBjb25zdCB2b2lkKiB0YXNrLCAKICAgIHNwaXRzc2l6ZV90IHRhc2tzeiwgc3BpdHNwdXNoX3QgcHVzaF9yZXN1bHQsIAogICAgc3BpdHNjdHhfdCB0YXNrY3R4KTsKCnZvaWQgc3BpdHNfd29ya2VyX2ZpbmFsaXplKHZvaWQgKnVzZXJfZGF0YSk7CgovKiBDb21taXR0ZXIgKi8KCnZvaWQqIHNwaXRzX2NvbW1pdHRlcl9uZXcoaW50IGFyZ2MsIGNvbnN0IGNoYXIgKmFyZ3ZbXSwKICAgIGNvbnN0IHZvaWQqIGpvYmluZm8sIHNwaXRzc2l6ZV90IGpvYmluZm9zeik7CgppbnQgc3BpdHNfY29tbWl0dGVyX2NvbW1pdF9waXQodm9pZCAqdXNlcl9kYXRhLAogICAgY29uc3Qgdm9pZCogcmVzdWx0LCBzcGl0c3NpemVfdCByZXN1bHRzeik7CgppbnQgc3BpdHNfY29tbWl0dGVyX2NvbW1pdF9qb2Iodm9pZCAqdXNlcl9kYXRhLAogICAgc3BpdHNwdXNoX3QgcHVzaF9maW5hbF9yZXN1bHQsIHNwaXRzY3R4X3Qgam9iY3R4KTsKCnZvaWQgc3BpdHNfY29tbWl0dGVyX2ZpbmFsaXplKHZvaWQgKnVzZXJfZGF0YSk7CgojaWZkZWYgX19jcGx1c3BsdXMKfQojZW5kaWYKCiNlbmRpZiAvKiBfX1NQSVRaX0hfXyAqLwo=',
        'spitz.hpp': 'LyoKICogVGhlIE1JVCBMaWNlbnNlIChNSVQpCiAqCiAqIENvcHlyaWdodCAoYykgMjAxNSBDYWlhbiBCZW5lZGljdG8gPGNhaWFuQGdnYXVuaWNhbXAuY29tPgogKiBDb3B5cmlnaHQgKGMpIDIwMTQgSWFuIExpdSBSb2RyaWd1ZXMgPGlhbi5saXVAZ2dhdW5pY2FtcC5jb20+CiAqCiAqIFBlcm1pc3Npb24gaXMgaGVyZWJ5IGdyYW50ZWQsIGZyZWUgb2YgY2hhcmdlLCB0byBhbnkgcGVyc29uIG9idGFpbmluZyBhIGNvcHkKICogb2YgdGhpcyBzb2Z0d2FyZSBhbmQgYXNzb2NpYXRlZCBkb2N1bWVudGF0aW9uIGZpbGVzICh0aGUgIlNvZnR3YXJlIiksIHRvCiAqIGRlYWwgaW4gdGhlIFNvZnR3YXJlIHdpdGhvdXQgcmVzdHJpY3Rpb24sIGluY2x1ZGluZyB3aXRob3V0IGxpbWl0YXRpb24gdGhlCiAqIHJpZ2h0cyB0byB1c2UsIGNvcHksIG1vZGlmeSwgbWVyZ2UsIHB1Ymxpc2gsIGRpc3RyaWJ1dGUsIHN1YmxpY2Vuc2UsCiAqIGFuZC9vciBzZWxsIGNvcGllcyBvZiB0aGUgU29mdHdhcmUsIGFuZCB0byBwZXJtaXQgcGVyc29ucyB0byB3aG9tIHRoZQogKiBTb2Z0d2FyZSBpcyBmdXJuaXNoZWQgdG8gZG8gc28sIHN1YmplY3QgdG8gdGhlIGZvbGxvd2luZyBjb25kaXRpb25zOgogKgogKiBUaGUgYWJvdmUgY29weXJpZ2h0IG5vdGljZSBhbmQgdGhpcyBwZXJtaXNzaW9uIG5vdGljZSBzaGFsbCBiZSBpbmNsdWRlZCBpbgogKiBhbGwgY29waWVzIG9yIHN1YnN0YW50aWFsIHBvcnRpb25zIG9mIHRoZSBTb2Z0d2FyZS4KICoKICogVEhFIFNPRlRXQVJFIElTIFBST1ZJREVEICJBUyBJUyIsIFdJVEhPVVQgV0FSUkFOVFkgT0YgQU5ZIEtJTkQsIEVYUFJFU1MgT1IKICogSU1QTElFRCwgSU5DTFVESU5HIEJVVCBOT1QgTElNSVRFRCBUTyBUSEUgV0FSUkFOVElFUyBPRiBNRVJDSEFOVEFCSUxJVFksCiAqIEZJVE5FU1MgRk9SIEEgUEFSVElDVUxBUiBQVVJQT1NFIEFORCBOT05JTkZSSU5HRU1FTlQuIElOIE5PIEVWRU5UIFNIQUxMCiAqIFRIRSBBVVRIT1JTIE9SIENPUFlSSUdIVCBIT0xERVJTIEJFIExJQUJMRSBGT1IgQU5ZIENMQUlNLCBEQU1BR0VTIE9SIE9USEVSCiAqIExJQUJJTElUWSwgV0hFVEhFUiBJTiBBTiBBQ1RJT04gT0YgQ09OVFJBQ1QsIFRPUlQgT1IgT1RIRVJXSVNFLCBBUklTSU5HCiAqIEZST00sIE9VVCBPRiBPUiBJTiBDT05ORUNUSU9OIFdJVEggVEhFIFNPRlRXQVJFIE9SIFRIRSBVU0UgT1IgT1RIRVIgREVBTElOR1MKICogSU4gVEhFIFNPRlRXQVJFLgogKi8KCiNpZm5kZWYgX19TUElUWl9DUFBfXwojZGVmaW5lIF9fU1BJVFpfQ1BQX18KCiNpbmNsdWRlICJzcGl0ei5oIgojaW5jbHVkZSAic3RyZWFtLmhwcCIKCiNpbmNsdWRlIDxpb3N0cmVhbT4KCm5hbWVzcGFjZSBzcGl0eiB7CgogICAgY2xhc3MgcHVzaGVyCiAgICB7CiAgICBwcml2YXRlOgogICAgICAgIHNwaXRzcHVzaF90IHB1c2hmOwogICAgICAgIHNwaXRzY3R4X3QgY3R4OwoKICAgIHB1YmxpYzoKICAgICAgICBwdXNoZXIoc3BpdHNwdXNoX3QgcHVzaGYsIHNwaXRzY3R4X3QgY3R4KSA6CiAgICAgICAgICAgIHB1c2hmKHB1c2hmKSwgY3R4KGN0eCkKICAgICAgICB7CiAgICAgICAgfQoKICAgICAgICB2b2lkIHB1c2goY29uc3Qgb3N0cmVhbSYgcCkgY29uc3QKICAgICAgICB7CiAgICAgICAgICAgIHRoaXMtPnB1c2hmKHAuZGF0YSgpLCBwLnBvcygpLCB0aGlzLT5jdHgpOwogICAgICAgIH0KCiAgICAgICAgdm9pZCBwdXNoKGNvbnN0IHZvaWQqIHAsIHNwaXRzc2l6ZV90IHMpIGNvbnN0CiAgICAgICAgewogICAgICAgICAgICB0aGlzLT5wdXNoZihwLCBzLCB0aGlzLT5jdHgpOwogICAgICAgIH0KICAgIH07CgogICAgY2xhc3MgcnVubmVyCiAgICB7CiAgICBwcml2YXRlOgogICAgICAgIHNwaXR6cnVuX3QgcnVuZjsKCiAgICBwdWJsaWM6CiAgICAgICAgcnVubmVyKHNwaXR6cnVuX3QgcnVuZikgOiBydW5mKHJ1bmYpCiAgICAgICAgewogICAgICAgIH0KCiAgICAgICAgaW50IHJ1bihpbnQgYXJnYywgY29uc3QgY2hhcioqIGFyZ3YpIGNvbnN0CiAgICAgICAgewogICAgICAgICAgICBvc3RyZWFtIGo7CiAgICAgICAgICAgIGlzdHJlYW0gcjsKICAgICAgICAgICAgcmV0dXJuIHJ1bihhcmdjLCBhcmd2LCBqLCByKTsKICAgICAgICB9CgogICAgICAgIGludCBydW4oaW50IGFyZ2MsIGNvbnN0IGNoYXIqKiBhcmd2LCBpc3RyZWFtJiBmaW5hbF9yZXN1bHQpIGNvbnN0CiAgICAgICAgewogICAgICAgICAgICBvc3RyZWFtIGo7CiAgICAgICAgICAgIHJldHVybiBydW4oYXJnYywgYXJndiwgaiwgZmluYWxfcmVzdWx0KTsKICAgICAgICB9CgogICAgICAgIGludCBydW4oaW50IGFyZ2MsIGNvbnN0IGNoYXIqKiBhcmd2LCBvc3RyZWFtJiBqb2JpbmZvKSBjb25zdAogICAgICAgIHsKICAgICAgICAgICAgaXN0cmVhbSByOwogICAgICAgICAgICByZXR1cm4gcnVuKGFyZ2MsIGFyZ3YsIGpvYmluZm8sIHIpOwogICAgICAgIH0KCiAgICAgICAgaW50IHJ1bihpbnQgYXJnYywgY29uc3QgY2hhcioqIGFyZ3YsIG9zdHJlYW0mIGpvYmluZm8sCiAgICAgICAgICAgIGlzdHJlYW0mIGZpbmFsX3Jlc3VsdCkgY29uc3QKICAgICAgICB7CiAgICAgICAgICAgIGNvbnN0IHZvaWQqIHBmaW5hbF9yZXN1bHQ7CiAgICAgICAgICAgIHNwaXRzc2l6ZV90IHBmaW5hbF9yZXN1bHRfc2l6ZTsKICAgICAgICAgICAgY29uc3Qgdm9pZCogcGpvYmluZm8gPSBqb2JpbmZvLmRhdGEoKTsKICAgICAgICAgICAgc3BpdHNzaXplX3QgcGpvYmluZm9fc2l6ZSA9IGpvYmluZm8ucG9zKCk7CiAgICAgICAgICAgIGludCByID0gdGhpcy0+cnVuZihhcmdjLCBhcmd2LCBwam9iaW5mbywgcGpvYmluZm9fc2l6ZSwKICAgICAgICAgICAgICAgICZwZmluYWxfcmVzdWx0LCAmcGZpbmFsX3Jlc3VsdF9zaXplKTsKICAgICAgICAgICAgZmluYWxfcmVzdWx0ID0gaXN0cmVhbShwZmluYWxfcmVzdWx0LCBwZmluYWxfcmVzdWx0X3NpemUpOwogICAgICAgICAgICByZXR1cm4gcjsKICAgICAgICB9CiAgICB9OwoKICAgIGNsYXNzIHNwaXR6X21haW4KICAgIHsKICAgIHB1YmxpYzoKICAgICAgICB2aXJ0dWFsIGludCBtYWluKGludCBhcmdjLCBjb25zdCBjaGFyKiBhcmd2W10sIGNvbnN0IHJ1bm5lciYgcnVubmVyKQogICAgICAgIHsKICAgICAgICAgICAgcmV0dXJuIHJ1bm5lci5ydW4oYXJnYywgYXJndik7CiAgICAgICAgfQogICAgICAgIHZpcnR1YWwgfnNwaXR6X21haW4oKXsgfQogICAgfTsKCiAgICBjbGFzcyBqb2JfbWFuYWdlcgogICAgewogICAgcHVibGljOgogICAgICAgIHZpcnR1YWwgYm9vbCBuZXh0X3Rhc2soY29uc3QgcHVzaGVyJiB0YXNrKSA9IDA7CiAgICAgICAgdmlydHVhbCB+am9iX21hbmFnZXIoKSB7IH0KICAgIH07CgogICAgY2xhc3Mgd29ya2VyCiAgICB7CiAgICBwdWJsaWM6CiAgICAgICAgdmlydHVhbCBpbnQgcnVuKGlzdHJlYW0mIHRhc2ssIGNvbnN0IHB1c2hlciYgcmVzdWx0KSA9IDA7CiAgICAgICAgdmlydHVhbCB+d29ya2VyKCkgeyB9CiAgICB9OwoKICAgIGNsYXNzIGNvbW1pdHRlcgogICAgewogICAgcHVibGljOgogICAgICAgIHZpcnR1YWwgaW50IGNvbW1pdF90YXNrKGlzdHJlYW0mIHJlc3VsdCkgPSAwOwogICAgICAgIHZpcnR1YWwgaW50IGNvbW1pdF9qb2IoY29uc3QgcHVzaGVyJiBmaW5hbF9yZXN1bHQpIHsKICAgICAgICAgICAgZmluYWxfcmVzdWx0LnB1c2goTlVMTCwgMCk7CiAgICAgICAgICAgIHJldHVybiAwOwogICAgICAgIH0KICAgICAgICB2aXJ0dWFsIH5jb21taXR0ZXIoKSB7IH0KICAgIH07CgogICAgY2xhc3MgZmFjdG9yeQogICAgewogICAgcHVibGljOgogICAgICAgIHZpcnR1YWwgc3BpdHpfbWFpbiAqY3JlYXRlX3NwaXR6X21haW4oKSB7IHJldHVybiBuZXcgc3BpdHpfbWFpbigpOyB9CiAgICAgICAgdmlydHVhbCBqb2JfbWFuYWdlciAqY3JlYXRlX2pvYl9tYW5hZ2VyKGludCwgY29uc3QgY2hhciAqW10sIGlzdHJlYW0mKSA9IDA7CiAgICAgICAgdmlydHVhbCB3b3JrZXIgKmNyZWF0ZV93b3JrZXIoaW50LCBjb25zdCBjaGFyICpbXSkgPSAwOwogICAgICAgIHZpcnR1YWwgY29tbWl0dGVyICpjcmVhdGVfY29tbWl0dGVyKGludCwgY29uc3QgY2hhciAqW10sIGlzdHJlYW0mKSA9IDA7CiAgICB9Owp9OwoKZXh0ZXJuIHNwaXR6OjpmYWN0b3J5ICpzcGl0el9mYWN0b3J5OwoKI2lmZGVmIFNQSVRaX0VOVFJZX1BPSU5UCgpleHRlcm4gIkMiIGludCBzcGl0c19tYWluKGludCBhcmdjLCBjb25zdCBjaGFyKiBhcmd2W10sIHNwaXR6cnVuX3QgcnVuKQp7CiAgICBzcGl0ejo6c3BpdHpfbWFpbiAqc20gPSBzcGl0el9mYWN0b3J5LT5jcmVhdGVfc3BpdHpfbWFpbigpOwogICAgc3BpdHo6OnJ1bm5lciBydW5uZXIocnVuKTsKCiAgICBpbnQgciA9IHNtLT5tYWluKGFyZ2MsIGFyZ3YsIHJ1bm5lcik7CgogICAgZGVsZXRlIHNtOwoKICAgIHJldHVybiByOwp9CgpleHRlcm4gIkMiIHZvaWQgKnNwaXRzX2pvYl9tYW5hZ2VyX25ldyhpbnQgYXJnYywgY29uc3QgY2hhciAqYXJndltdLAogICAgY29uc3Qgdm9pZCogam9iaW5mbywgc3BpdHNzaXplX3Qgam9iaW5mb3N6KQp7CiAgICBzcGl0ejo6aXN0cmVhbSBqaShqb2JpbmZvLCBqb2JpbmZvc3opOwogICAgc3BpdHo6OmpvYl9tYW5hZ2VyICpqbSA9IHNwaXR6X2ZhY3RvcnktPmNyZWF0ZV9qb2JfbWFuYWdlcihhcmdjLCBhcmd2LCBqaSk7CiAgICByZXR1cm4gcmVpbnRlcnByZXRfY2FzdDx2b2lkKj4oam0pOwp9CgpleHRlcm4gIkMiIGludCBzcGl0c19qb2JfbWFuYWdlcl9uZXh0X3Rhc2sodm9pZCAqdXNlcl9kYXRhLAogICAgc3BpdHNwdXNoX3QgcHVzaF90YXNrLCBzcGl0c2N0eF90IGptY3R4KQp7CiAgICBjbGFzcyBzcGl0ejo6am9iX21hbmFnZXIgKmptID0gcmVpbnRlcnByZXRfY2FzdAogICAgICAgIDxzcGl0ejo6am9iX21hbmFnZXIqPih1c2VyX2RhdGEpOwoKICAgIHNwaXR6OjpwdXNoZXIgdGFzayhwdXNoX3Rhc2ssIGptY3R4KTsKICAgIHJldHVybiBqbS0+bmV4dF90YXNrKHRhc2spID8gMSA6IDA7Cn0KCmV4dGVybiAiQyIgdm9pZCBzcGl0c19qb2JfbWFuYWdlcl9maW5hbGl6ZSh2b2lkICp1c2VyX2RhdGEpCnsKICAgIGNsYXNzIHNwaXR6Ojpqb2JfbWFuYWdlciAqam0gPSByZWludGVycHJldF9jYXN0CiAgICAgICAgPHNwaXR6Ojpqb2JfbWFuYWdlcio+KHVzZXJfZGF0YSk7CgogICAgZGVsZXRlIGptOwp9CgpleHRlcm4gIkMiIHZvaWQgKnNwaXRzX3dvcmtlcl9uZXcoaW50IGFyZ2MsIGNvbnN0IGNoYXIgKiphcmd2KQp7CiAgICBzcGl0ejo6d29ya2VyICp3ID0gc3BpdHpfZmFjdG9yeS0+Y3JlYXRlX3dvcmtlcihhcmdjLCBhcmd2KTsKICAgIHJldHVybiByZWludGVycHJldF9jYXN0PHZvaWQqPih3KTsKfQoKZXh0ZXJuICJDIiBpbnQgc3BpdHNfd29ya2VyX3J1bih2b2lkICp1c2VyX2RhdGEsIGNvbnN0IHZvaWQqIHRhc2ssCiAgICBzcGl0c3NpemVfdCB0YXNrc3osIHNwaXRzcHVzaF90IHB1c2hfcmVzdWx0LAogICAgc3BpdHNjdHhfdCB0YXNrY3R4KQp7CiAgICBzcGl0ejo6d29ya2VyICp3ID0gcmVpbnRlcnByZXRfY2FzdAogICAgICAgIDxzcGl0ejo6d29ya2VyKj4odXNlcl9kYXRhKTsKCiAgICBzcGl0ejo6aXN0cmVhbSBzdGFzayh0YXNrLCB0YXNrc3opOwogICAgc3BpdHo6OnB1c2hlciByZXN1bHQocHVzaF9yZXN1bHQsIHRhc2tjdHgpOwoKICAgIHJldHVybiB3LT5ydW4oc3Rhc2ssIHJlc3VsdCk7Cn0KCmV4dGVybiAiQyIgdm9pZCBzcGl0c193b3JrZXJfZmluYWxpemUodm9pZCAqdXNlcl9kYXRhKQp7CiAgICBzcGl0ejo6d29ya2VyICp3ID0gcmVpbnRlcnByZXRfY2FzdAogICAgICAgIDxzcGl0ejo6d29ya2VyKj4odXNlcl9kYXRhKTsKCiAgICBkZWxldGUgdzsKfQoKZXh0ZXJuICJDIiB2b2lkICpzcGl0c19jb21taXR0ZXJfbmV3KGludCBhcmdjLCBjb25zdCBjaGFyICphcmd2W10sCiAgICBjb25zdCB2b2lkKiBqb2JpbmZvLCBzcGl0c3NpemVfdCBqb2JpbmZvc3opCnsKICAgIHNwaXR6Ojppc3RyZWFtIGppKGpvYmluZm8sIGpvYmluZm9zeik7CiAgICBzcGl0ejo6Y29tbWl0dGVyICpjbyA9IHNwaXR6X2ZhY3RvcnktPmNyZWF0ZV9jb21taXR0ZXIoYXJnYywgYXJndiwgamkpOwogICAgcmV0dXJuIHJlaW50ZXJwcmV0X2Nhc3Q8dm9pZCo+KGNvKTsKfQoKZXh0ZXJuICJDIiBpbnQgc3BpdHNfY29tbWl0dGVyX2NvbW1pdF9waXQodm9pZCAqdXNlcl9kYXRhLAogICAgY29uc3Qgdm9pZCogcmVzdWx0LCBzcGl0c3NpemVfdCByZXN1bHRzeikKewogICAgc3BpdHo6OmNvbW1pdHRlciAqY28gPSByZWludGVycHJldF9jYXN0CiAgICAgICAgPHNwaXR6Ojpjb21taXR0ZXIqPih1c2VyX2RhdGEpOwoKICAgIHNwaXR6Ojppc3RyZWFtIHNyZXN1bHQocmVzdWx0LCByZXN1bHRzeik7CiAgICByZXR1cm4gY28tPmNvbW1pdF90YXNrKHNyZXN1bHQpOwp9CgpleHRlcm4gIkMiIGludCBzcGl0c19jb21taXR0ZXJfY29tbWl0X2pvYih2b2lkICp1c2VyX2RhdGEsCiAgICBzcGl0c3B1c2hfdCBwdXNoX2ZpbmFsX3Jlc3VsdCwgc3BpdHNjdHhfdCBqb2JjdHgpCnsKICAgIHNwaXR6Ojpjb21taXR0ZXIgKmNvID0gcmVpbnRlcnByZXRfY2FzdAogICAgICAgIDxzcGl0ejo6Y29tbWl0dGVyKj4odXNlcl9kYXRhKTsKCiAgICBzcGl0ejo6cHVzaGVyIGZpbmFsX3Jlc3VsdChwdXNoX2ZpbmFsX3Jlc3VsdCwgam9iY3R4KTsKICAgIHJldHVybiBjby0+Y29tbWl0X2pvYihmaW5hbF9yZXN1bHQpOwp9CgpleHRlcm4gIkMiIHZvaWQgc3BpdHNfY29tbWl0dGVyX2ZpbmFsaXplKHZvaWQgKnVzZXJfZGF0YSkKewogICAgc3BpdHo6OmNvbW1pdHRlciAqY28gPSByZWludGVycHJldF9jYXN0CiAgICAgICAgPHNwaXR6Ojpjb21taXR0ZXIqPih1c2VyX2RhdGEpOwoKICAgIGRlbGV0ZSBjbzsKfQoKI2lmZGVmIFNQSVRaX1NFUklBTF9ERUJVRwojaW5jbHVkZSA8dmVjdG9yPgojaW5jbHVkZSA8YWxnb3JpdGhtPgojaW5jbHVkZSA8aW9zdHJlYW0+CiNpbmNsdWRlIDxjc3RkbGliPgojaW5jbHVkZSA8ZnN0cmVhbT4KI2luY2x1ZGUgPHNzdHJlYW0+CiNpbmNsdWRlIDxzdGRpbnQuaD4KCnN0YXRpYyB2b2lkIHNwaXR6X2RlYnVnX3B1c2hlcihjb25zdCB2b2lkKiBwZGF0YSwKICAgIHNwaXRzc2l6ZV90IHNpemUsIHNwaXRzY3R4X3QgY3R4KQp7CiAgICBzdGQ6OnZlY3Rvcjx1aW50OF90PiogdiA9IHJlaW50ZXJwcmV0X2Nhc3Q8c3RkOjp2ZWN0b3I8dWludDhfdD4qPgogICAgICAoY29uc3RfY2FzdDx2b2lkKj4oY3R4KSk7CgogICAgaWYgKHYtPnNpemUoKSAhPSAwKSB7CiAgICAgICAgc3RkOjpjZXJyIDw8ICJbU1BJVFpdIFB1c2ggY2FsbGVkIG1vcmUgdGhhbiBvbmNlISIgPDwgc3RkOjplbmRsOwogICAgfQoKICAgIHYtPnB1c2hfYmFjaygxKTsKCiAgICBzdGQ6OmNvcHkocmVpbnRlcnByZXRfY2FzdDxjb25zdCB1aW50OF90Kj4ocGRhdGEpLAogICAgICAgIHJlaW50ZXJwcmV0X2Nhc3Q8Y29uc3QgdWludDhfdCo+KHBkYXRhKSArIHNpemUsCiAgICAgICAgc3RkOjpiYWNrX2luc2VydGVyKCp2KSk7Cn0KCnN0YXRpYyBpbnQgc3BpdHpfZGVidWdfcnVubmVyKGludCBhcmdjLCBjb25zdCBjaGFyKiogYXJndiwKICAgIGNvbnN0IHZvaWQqIHBqb2JpbmZvLCBzcGl0c3NpemVfdCBqb2JpbmZvc3osCiAgICBjb25zdCB2b2lkKiogcGZpbmFsX3Jlc3VsdCwgc3BpdHNzaXplX3QqIHBmaW5hbF9yZXN1bHRzeikKewogICAgdm9pZCogam0gPSBzcGl0c19qb2JfbWFuYWdlcl9uZXcoYXJnYywgYXJndiwgcGpvYmluZm8sIGpvYmluZm9zeik7CiAgICB2b2lkKiBjbyA9IHNwaXRzX2NvbW1pdHRlcl9uZXcoYXJnYywgYXJndiwgcGpvYmluZm8sIGpvYmluZm9zeik7CiAgICB2b2lkKiB3ayA9IHNwaXRzX3dvcmtlcl9uZXcoYXJnYywgYXJndik7CgogICAgc3RhdGljIGludDY0X3QgamlkID0gMDsKICAgIGludDY0X3QgdGlkID0gMDsKCiAgICBpbnQgcjEgPSAwLCByMiA9IDAsIHIzID0gMDsKCiAgICBzdGQ6OnZlY3RvcjxpbnQ4X3Q+IHRhc2s7CiAgICBzdGQ6OnZlY3RvcjxpbnQ4X3Q+IHJlc3VsdDsKICAgIHN0ZDo6dmVjdG9yPGludDhfdD4qIGZpbmFsX3Jlc3VsdCA9IG5ldyBzdGQ6OnZlY3RvcjxpbnQ4X3Q+KCk7CgogICAgd2hpbGUodHJ1ZSkgewogICAgICAgIHRhc2suY2xlYXIoKTsKICAgICAgICBzdGQ6OmNlcnIgPDwgIltTUElUWl0gR2VuZXJhdGluZyB0YXNrICIgPDwgdGlkIDw8ICIuLi4iIDw8IHN0ZDo6ZW5kbDsKICAgICAgICBpZighc3BpdHNfam9iX21hbmFnZXJfbmV4dF90YXNrKGptLCBzcGl0el9kZWJ1Z19wdXNoZXIsICZ0YXNrKSkKICAgICAgICAgICAgYnJlYWs7CgogICAgICAgIGlmICh0YXNrLnNpemUoKSA9PSAwKSB7CiAgICAgICAgICAgIHN0ZDo6Y2VyciA8PCAiW1NQSVRaXSBUYXNrIG1hbmFnZXIgZGlkbid0IHB1c2ggYSB0YXNrISIKICAgICAgICAgICAgICAgIDw8IHN0ZDo6ZW5kbDsKICAgICAgICAgICAgZXhpdCgxKTsKICAgICAgICB9CgogICAgICAgIHJlc3VsdC5jbGVhcigpOwogICAgICAgIHN0ZDo6Y2VyciA8PCAiW1NQSVRaXSBFeGVjdXRpbmcgdGFzayAiIDw8IHRpZCA8PCAiLi4uIiA8PCBzdGQ6OmVuZGw7CiAgICAgICAgcjEgPSBzcGl0c193b3JrZXJfcnVuKHdrLCB0YXNrLmRhdGEoKSsxLCB0YXNrLnNpemUoKS0xLAogICAgICAgICAgICBzcGl0el9kZWJ1Z19wdXNoZXIsICZyZXN1bHQpOwoKICAgICAgICBpZiAocjEgIT0gMCkgewogICAgICAgICAgICBzdGQ6OmNlcnIgPDwgIltTUElUWl0gVGFzayAiIDw8IHRpZCA8PCAiIGZhaWxlZCB0byBleGVjdXRlISIKICAgICAgICAgICAgICAgIDw8IHN0ZDo6ZW5kbDsKICAgICAgICAgICAgZ290byBkdW1wX3Rhc2tfYW5kX2V4aXQ7CiAgICAgICAgfQoKICAgICAgICBpZiAodGFzay5zaXplKCkgPT0gMCkgewogICAgICAgICAgICBzdGQ6OmNlcnIgPDwgIltTUElUWl0gV29ya2VyIGRpZG4ndCBwdXNoIGEgcmVzdWx0ISIKICAgICAgICAgICAgICAgIDw8IHN0ZDo6ZW5kbDsKICAgICAgICAgICAgZ290byBkdW1wX3Rhc2tfYW5kX2V4aXQ7CiAgICAgICAgfQoKICAgICAgICBzdGQ6OmNlcnIgPDwgIltTUElUWl0gQ29tbWl0dGluZyB0YXNrICIgPDwgdGlkIDw8ICIuLi4iIDw8IHN0ZDo6ZW5kbDsKICAgICAgICByMiA9IHNwaXRzX2NvbW1pdHRlcl9jb21taXRfcGl0KGNvLCByZXN1bHQuZGF0YSgpKzEsIHJlc3VsdC5zaXplKCktMSk7CgogICAgICAgIGlmIChyMiAhPSAwKSB7CiAgICAgICAgICAgIHN0ZDo6Y2VyciA8PCAiW1NQSVRaXSBUYXNrICIgPDwgdGlkIDw8ICIgZmFpbGVkIHRvIGNvbW1pdCEiCiAgICAgICAgICAgICAgICA8PCBzdGQ6OmVuZGw7CiAgICAgICAgICAgIGdvdG8gZHVtcF9yZXN1bHRfYW5kX2V4aXQ7CiAgICAgICAgfQogICAgICAgIHRpZCsrOwogICAgfQogICAgc3RkOjpjZXJyIDw8ICJbU1BJVFpdIEZpbmlzaGVkIHByb2Nlc3NpbmcgdGFza3MuIiA8PCBzdGQ6OmVuZGw7CgogICAgZmluYWxfcmVzdWx0LT5jbGVhcigpOwogICAgc3RkOjpjZXJyIDw8ICJbU1BJVFpdIENvbW1pdHRpbmcgam9iICIgPDwgamlkIDw8ICIuLi4iIDw8IHN0ZDo6ZW5kbDsKICAgIHIzID0gc3BpdHNfY29tbWl0dGVyX2NvbW1pdF9qb2IoY28sIHNwaXR6X2RlYnVnX3B1c2hlciwgZmluYWxfcmVzdWx0KTsKCiAgICBpZiAocjMgIT0gMCkgewogICAgICAgIHN0ZDo6Y2VyciA8PCAiW1NQSVRaXSBKb2IgIiA8PCBqaWQgPDwgIiBmYWlsZWQgdG8gY29tbWl0ISIKICAgICAgICAgICAgPDwgc3RkOjplbmRsOwogICAgICAgIGV4aXQoMSk7CiAgICB9CgogICAgaWYgKGZpbmFsX3Jlc3VsdC0+c2l6ZSgpIDw9IDEpIHsKICAgICAgICAqcGZpbmFsX3Jlc3VsdCA9IE5VTEw7CiAgICAgICAgKnBmaW5hbF9yZXN1bHRzeiA9IDA7CiAgICB9IGVsc2UgewogICAgICAgICpwZmluYWxfcmVzdWx0ID0gZmluYWxfcmVzdWx0LT5kYXRhKCkrMTsKICAgICAgICAqcGZpbmFsX3Jlc3VsdHN6ID0gZmluYWxfcmVzdWx0LT5zaXplKCktMTsKICAgIH0KCiAgICBzdGQ6OmNlcnIgPDwgIltTUElUWl0gRmluYWxpemluZyB0YXNrIG1hbmFnZXIuLi4iIDw8IHN0ZDo6ZW5kbDsKICAgIHNwaXRzX2pvYl9tYW5hZ2VyX2ZpbmFsaXplKGptKTsKCiAgICBzdGQ6OmNlcnIgPDwgIltTUElUWl0gRmluYWxpemluZyBjb21taXR0ZXIuLi4iIDw8IHN0ZDo6ZW5kbDsKICAgIHNwaXRzX2NvbW1pdHRlcl9maW5hbGl6ZShjbyk7CgogICAgc3RkOjpjZXJyIDw8ICJbU1BJVFpdIEZpbmFsaXppbmcgd29ya2VyLi4uIiA8PCBzdGQ6OmVuZGw7CiAgICBzcGl0c193b3JrZXJfZmluYWxpemUod2spOwoKICAgIHN0ZDo6Y2VyciA8PCAiW1NQSVRaXSBKb2IgIiA8PCBqaWQgPDwgIiBjb21wbGV0ZWQuIiA8PCBzdGQ6OmVuZGw7CiAgICBqaWQrKzsKCiAgICByZXR1cm4gMDsKCmR1bXBfcmVzdWx0X2FuZF9leGl0OgogICAgewogICAgICAgIHN0ZDo6Y2VyciA8PCAiW1NQSVRaXSBHZW5lcmF0aW5nIHJlc3VsdCBkdW1wIGZvciB0YXNrICIKICAgICAgICAgICAgPDwgdGlkIDw8ICIuLi4iIDw8IHN0ZDo6ZW5kbDsKICAgICAgICBzdGQ6OnN0cmluZ3N0cmVhbSBzczsKICAgICAgICBzcyA8PCAicmVzdWx0LSIgPDwgdGlkIDw8ICIuZHVtcCI7CiAgICAgICAgc3RkOjpvZnN0cmVhbSByZXNmaWxlKHNzLnN0cigpLmNfc3RyKCksIHN0ZDo6b2ZzdHJlYW06OmJpbmFyeSk7CiAgICAgICAgcmVzZmlsZS53cml0ZShyZWludGVycHJldF9jYXN0PGNvbnN0IGNoYXIqPihyZXN1bHQuZGF0YSgpKzEpLAogICAgICAgICAgICByZXN1bHQuc2l6ZSgpLTEpOwogICAgICAgIHJlc2ZpbGUuY2xvc2UoKTsKICAgICAgICBzdGQ6OmNlcnIgPDwgIltTUElUWl0gUmVzdWx0IGR1bXAgZ2VuZXJhdGVkIGFzICIgPDwgc3Muc3RyKCkgPDwKICAgICAgICAgICAgIiBbIiA8PCAocmVzdWx0LnNpemUoKS0xKSA8PCAiIGJ5dGVzXS4gIiA8PCBzdGQ6OmVuZGw7CiAgICB9CmR1bXBfdGFza19hbmRfZXhpdDoKICAgIHsKICAgICAgICBzdGQ6OmNlcnIgPDwgIltTUElUWl0gR2VuZXJhdGluZyB0YXNrIGR1bXAgZm9yIHRhc2sgIgogICAgICAgICAgICA8PCB0aWQgPDwgIi4uLiIgPDwgc3RkOjplbmRsOwogICAgICAgIHN0ZDo6c3RyaW5nc3RyZWFtIHNzOwogICAgICAgIHNzIDw8ICJ0YXNrLSIgPDwgdGlkIDw8ICIuZHVtcCI7CiAgICAgICAgc3RkOjpvZnN0cmVhbSB0YXNrZmlsZShzcy5zdHIoKS5jX3N0cigpLCBzdGQ6Om9mc3RyZWFtOjpiaW5hcnkpOwogICAgICAgIHRhc2tmaWxlLndyaXRlKHJlaW50ZXJwcmV0X2Nhc3Q8Y29uc3QgY2hhcio+KHRhc2suZGF0YSgpKzEpLAogICAgICAgICAgICB0YXNrLnNpemUoKS0xKTsKICAgICAgICB0YXNrZmlsZS5jbG9zZSgpOwogICAgICAgIHN0ZDo6Y2VyciA8PCAiW1NQSVRaXSBUYXNrIGR1bXAgZ2VuZXJhdGVkIGFzICIgPDwgc3Muc3RyKCkgPDwKICAgICAgICAgICAgIiBbIiA8PCAodGFzay5zaXplKCktMSkgPDwgIiBieXRlc10uICIgPDwgc3RkOjplbmRsOwogICAgfQogICAgZXhpdCgxKTsKfQoKaW50IG1haW4oaW50IGFyZ2MsIGNvbnN0IGNoYXIqKiBhcmd2KQp7CiAgICBzdGQ6OmNlcnIgPDwgIltTUElUWl0gRW50ZXJpbmcgZGVidWcgbW9kZS4uLiIgPDwgc3RkOjplbmRsOwogICAgc3BpdHNfbWFpbihhcmdjLCBhcmd2LCBzcGl0el9kZWJ1Z19ydW5uZXIpOwogICAgc3RkOjpjZXJyIDw8ICJbU1BJVFpdIFNwaXR6IGZpbmlzaGVkLiIgPDwgc3RkOjplbmRsOwp9CiNlbmRpZgoKI2VuZGlmCgojZW5kaWYgLyogX19TUElUWl9DUFBfXyAqLwoKLy8gdmltOmZ0PWNwcDpzdz0yOmV0OnN0YQo=',
        'stream.hpp' : 'LyoKICogVGhlIE1JVCBMaWNlbnNlIChNSVQpCiAqCiAqIENvcHlyaWdodCAoYykgMjAxNSBDYWlhbiBCZW5lZGljdG8gPGNhaWFuQGdnYXVuaWNhbXAuY29tPgogKiBDb3B5cmlnaHQgKGMpIDIwMTQgSWFuIExpdSBSb2RyaWd1ZXMgPGlhbi5saXVAZ2dhdW5pY2FtcC5jb20+CiAqCiAqIFBlcm1pc3Npb24gaXMgaGVyZWJ5IGdyYW50ZWQsIGZyZWUgb2YgY2hhcmdlLCB0byBhbnkgcGVyc29uIG9idGFpbmluZyBhIGNvcHkKICogb2YgdGhpcyBzb2Z0d2FyZSBhbmQgYXNzb2NpYXRlZCBkb2N1bWVudGF0aW9uIGZpbGVzICh0aGUgIlNvZnR3YXJlIiksIHRvCiAqIGRlYWwgaW4gdGhlIFNvZnR3YXJlIHdpdGhvdXQgcmVzdHJpY3Rpb24sIGluY2x1ZGluZyB3aXRob3V0IGxpbWl0YXRpb24gdGhlCiAqIHJpZ2h0cyB0byB1c2UsIGNvcHksIG1vZGlmeSwgbWVyZ2UsIHB1Ymxpc2gsIGRpc3RyaWJ1dGUsIHN1YmxpY2Vuc2UsCiAqIGFuZC9vciBzZWxsIGNvcGllcyBvZiB0aGUgU29mdHdhcmUsIGFuZCB0byBwZXJtaXQgcGVyc29ucyB0byB3aG9tIHRoZQogKiBTb2Z0d2FyZSBpcyBmdXJuaXNoZWQgdG8gZG8gc28sIHN1YmplY3QgdG8gdGhlIGZvbGxvd2luZyBjb25kaXRpb25zOgogKgogKiBUaGUgYWJvdmUgY29weXJpZ2h0IG5vdGljZSBhbmQgdGhpcyBwZXJtaXNzaW9uIG5vdGljZSBzaGFsbCBiZSBpbmNsdWRlZCBpbgogKiBhbGwgY29waWVzIG9yIHN1YnN0YW50aWFsIHBvcnRpb25zIG9mIHRoZSBTb2Z0d2FyZS4KICoKICogVEhFIFNPRlRXQVJFIElTIFBST1ZJREVEICJBUyBJUyIsIFdJVEhPVVQgV0FSUkFOVFkgT0YgQU5ZIEtJTkQsIEVYUFJFU1MgT1IKICogSU1QTElFRCwgSU5DTFVESU5HIEJVVCBOT1QgTElNSVRFRCBUTyBUSEUgV0FSUkFOVElFUyBPRiBNRVJDSEFOVEFCSUxJVFksCiAqIEZJVE5FU1MgRk9SIEEgUEFSVElDVUxBUiBQVVJQT1NFIEFORCBOT05JTkZSSU5HRU1FTlQuIElOIE5PIEVWRU5UIFNIQUxMCiAqIFRIRSBBVVRIT1JTIE9SIENPUFlSSUdIVCBIT0xERVJTIEJFIExJQUJMRSBGT1IgQU5ZIENMQUlNLCBEQU1BR0VTIE9SIE9USEVSCiAqIExJQUJJTElUWSwgV0hFVEhFUiBJTiBBTiBBQ1RJT04gT0YgQ09OVFJBQ1QsIFRPUlQgT1IgT1RIRVJXSVNFLCBBUklTSU5HCiAqIEZST00sIE9VVCBPRiBPUiBJTiBDT05ORUNUSU9OIFdJVEggVEhFIFNPRlRXQVJFIE9SIFRIRSBVU0UgT1IgT1RIRVIgREVBTElOR1MKICogSU4gVEhFIFNPRlRXQVJFLgogKi8KCiNpZm5kZWYgX19TUElUWl9DUFBfU1RSRUFNX0hQUF9fCiNkZWZpbmUgX19TUElUWl9DUFBfU1RSRUFNX0hQUF9fCgojaW5jbHVkZSA8c3RkaW50Lmg+CiNpbmNsdWRlIDxhcnBhL2luZXQuaD4KCiNpbmNsdWRlIDx2ZWN0b3I+CiNpbmNsdWRlIDxzdHJpbmc+CiNpbmNsdWRlIDxzc3RyZWFtPgojaW5jbHVkZSA8aXRlcmF0b3I+CiNpbmNsdWRlIDxleGNlcHRpb24+CiNpbmNsdWRlIDxhbGdvcml0aG0+CgpuYW1lc3BhY2Ugc3BpdHogewoKICAgIGNsYXNzIG9zdHJlYW0KICAgIHsKICAgIHByaXZhdGU6CiAgICAgICAgc3RkOjp2ZWN0b3I8Y2hhcj4gcGRhdGE7CgogICAgICAgIHN0YXRpYyB1aW50NjRfdCBzcGl0el9odG9ubGwodWludDY0X3QgeCkKICAgICAgICB7CiAgICAgICAgICAgIGlmIChodG9ucygxKSA9PSAxKQogICAgICAgICAgICAgICAgcmV0dXJuIHg7CiAgICAgICAgICAgIHVpbnQzMl90IGxvID0gc3RhdGljX2Nhc3Q8dWludDMyX3Q+KCh4ICYgMHhGRkZGRkZGRjAwMDAwMDAwKSA+PiAzMik7CiAgICAgICAgICAgIHVpbnQzMl90IGhpID0gc3RhdGljX2Nhc3Q8dWludDMyX3Q+KHggJiAweDAwMDAwMDAwRkZGRkZGRkYpOwogICAgICAgICAgICB1aW50NjRfdCBubG8gPSBodG9ubChsbyk7CiAgICAgICAgICAgIHVpbnQ2NF90IG5oaSA9IGh0b25sKGhpKTsKICAgICAgICAgICAgcmV0dXJuIG5oaSA8PCAzMiB8IG5sbzsKICAgICAgICB9CgogICAgICAgIHRlbXBsYXRlPHR5cGVuYW1lIFQ+IHZvaWQgcHVzaF9iYWNrKGNvbnN0IFQmIHYpCiAgICAgICAgewogICAgICAgICAgICBzaXplX3QgcyA9IHRoaXMtPnBkYXRhLnNpemUoKTsKICAgICAgICAgICAgdGhpcy0+cGRhdGEucmVzaXplKHMgKyBzaXplb2YoVCkpOwogICAgICAgICAgICAqcmVpbnRlcnByZXRfY2FzdDxUKj4odGhpcy0+cGRhdGEuZGF0YSgpICsgcykgPSB2OwogICAgICAgIH0KCiAgICAgICAgdGVtcGxhdGU8dHlwZW5hbWUgVD4gdWludDE2X3QgaHRvbjE2KGNvbnN0IFQmIHYpCiAgICAgICAgewogICAgICAgICAgICBjb25zdCBjaGFyKiBwID0gcmVpbnRlcnByZXRfY2FzdDxjb25zdCBjaGFyKj4oJnYpOwogICAgICAgICAgICByZXR1cm4gaHRvbnMoKnJlaW50ZXJwcmV0X2Nhc3Q8Y29uc3QgdWludDE2X3QqPihwKSk7CiAgICAgICAgfQoKICAgICAgICB0ZW1wbGF0ZTx0eXBlbmFtZSBUPiB1aW50MzJfdCBodG9uMzIoY29uc3QgVCYgdikKICAgICAgICB7CiAgICAgICAgICAgIGNvbnN0IGNoYXIqIHAgPSByZWludGVycHJldF9jYXN0PGNvbnN0IGNoYXIqPigmdik7CiAgICAgICAgICAgIHJldHVybiBodG9ubCgqcmVpbnRlcnByZXRfY2FzdDxjb25zdCB1aW50MzJfdCo+KHApKTsKICAgICAgICB9CgogICAgICAgIHRlbXBsYXRlPHR5cGVuYW1lIFQ+IHVpbnQ2NF90IGh0b242NChjb25zdCBUJiB2KQogICAgICAgIHsKICAgICAgICAgICAgY29uc3QgY2hhciogcCA9IHJlaW50ZXJwcmV0X2Nhc3Q8Y29uc3QgY2hhcio+KCZ2KTsKICAgICAgICAgICAgcmV0dXJuIHNwaXR6X2h0b25sbCgqcmVpbnRlcnByZXRfY2FzdDxjb25zdCB1aW50NjRfdCo+KHApKTsKICAgICAgICB9CgogICAgcHVibGljOgogICAgICAgIG9zdHJlYW0oKSA6IHBkYXRhKCkgeyB9CgogICAgICAgIHZvaWQgd3JpdGVfYm9vbChjb25zdCBib29sJiB2KSB7IHB1c2hfYmFjaygoY2hhcikodiA/IDEgOiAwKSk7IH0KICAgICAgICB2b2lkIHdyaXRlX2NoYXIoY29uc3QgaW50OF90JiB2KSB7IHB1c2hfYmFjayh2KTsgfQogICAgICAgIHZvaWQgd3JpdGVfYnl0ZShjb25zdCB1aW50OF90JiB2KSB7IHB1c2hfYmFjayh2KTsgfQogICAgICAgIHZvaWQgd3JpdGVfZmxvYXQoY29uc3QgZmxvYXQmIHYpIHsgcHVzaF9iYWNrKGh0b24zMih2KSk7IH0KICAgICAgICB2b2lkIHdyaXRlX2RvdWJsZShjb25zdCBkb3VibGUmIHYpIHsgcHVzaF9iYWNrKGh0b242NCh2KSk7IH0KICAgICAgICB2b2lkIHdyaXRlX3Nob3J0KGNvbnN0IGludDE2X3QmIHYpIHsgcHVzaF9iYWNrKGh0b24xNih2KSk7IH0KICAgICAgICB2b2lkIHdyaXRlX3VzaG9ydChjb25zdCB1aW50MTZfdCYgdikgeyBwdXNoX2JhY2soaHRvbjE2KHYpKTsgfQogICAgICAgIHZvaWQgd3JpdGVfaW50KGNvbnN0IGludDMyX3QmIHYpIHsgcHVzaF9iYWNrKGh0b24zMih2KSk7IH0KICAgICAgICB2b2lkIHdyaXRlX3VpbnQoY29uc3QgdWludDMyX3QmIHYpIHsgcHVzaF9iYWNrKGh0b24zMih2KSk7IH0KICAgICAgICB2b2lkIHdyaXRlX2xvbmdsb25nKGNvbnN0IGludDY0X3QmIHYpIHsgcHVzaF9iYWNrKGh0b242NCh2KSk7IH0KICAgICAgICB2b2lkIHdyaXRlX3Vsb25nbG9uZyhjb25zdCB1aW50NjRfdCYgdikgeyBwdXNoX2JhY2soaHRvbjY0KHYpKTsgfQogICAgICAgIHZvaWQgd3JpdGVfc3RyaW5nKGNvbnN0IHN0ZDo6c3RyaW5nJiB2KQogICAgICAgIHsKICAgICAgICAgICAgY29uc3QgY2hhciAqcCA9IHYuY19zdHIoKTsKICAgICAgICAgICAgZG8geyB3cml0ZV9jaGFyKCpwKTsgfQogICAgICAgICAgICB3aGlsZSAoKnArKyk7CiAgICAgICAgfQogICAgICAgIHZvaWQgd3JpdGVfZGF0YShjb25zdCB2b2lkKiBwZGF0YSwgc2l6ZV90IHNpemUpCiAgICAgICAgewogICAgICAgICAgICBzdGQ6OmNvcHkocmVpbnRlcnByZXRfY2FzdDxjb25zdCBjaGFyKj4ocGRhdGEpLAogICAgICAgICAgICAgICAgcmVpbnRlcnByZXRfY2FzdDxjb25zdCBjaGFyKj4ocGRhdGEpICsgc2l6ZSwKICAgICAgICAgICAgICAgIHN0ZDo6YmFja19pbnNlcnRlcih0aGlzLT5wZGF0YSkpOwogICAgICAgIH0KCiAgICAgICAgb3N0cmVhbSYgb3BlcmF0b3I8PChjb25zdCBmbG9hdCYgdikgICAgICAgeyB3cml0ZV9mbG9hdCh2KTsgcmV0dXJuICp0aGlzOyB9CiAgICAgICAgb3N0cmVhbSYgb3BlcmF0b3I8PChjb25zdCBkb3VibGUmIHYpICAgICAgeyB3cml0ZV9kb3VibGUodik7IHJldHVybiAqdGhpczsgfQogICAgICAgIG9zdHJlYW0mIG9wZXJhdG9yPDwoY29uc3QgaW50OF90JiB2KSAgICAgIHsgd3JpdGVfY2hhcih2KTsgcmV0dXJuICp0aGlzOyB9CiAgICAgICAgb3N0cmVhbSYgb3BlcmF0b3I8PChjb25zdCBpbnQxNl90JiB2KSAgICAgeyB3cml0ZV9zaG9ydCh2KTsgcmV0dXJuICp0aGlzOyB9CiAgICAgICAgb3N0cmVhbSYgb3BlcmF0b3I8PChjb25zdCBpbnQ2NF90JiB2KSAgICAgeyB3cml0ZV9sb25nbG9uZyh2KTsgcmV0dXJuICp0aGlzOyB9CiAgICAgICAgb3N0cmVhbSYgb3BlcmF0b3I8PChjb25zdCB1aW50OF90JiB2KSAgICAgeyB3cml0ZV9ieXRlKHYpOyByZXR1cm4gKnRoaXM7IH0KICAgICAgICBvc3RyZWFtJiBvcGVyYXRvcjw8KGNvbnN0IHVpbnQxNl90JiB2KSAgICB7IHdyaXRlX3VzaG9ydCh2KTsgcmV0dXJuICp0aGlzOyB9CiAgICAgICAgb3N0cmVhbSYgb3BlcmF0b3I8PChjb25zdCB1aW50MzJfdCYgdikgICAgeyB3cml0ZV91aW50KHYpOyByZXR1cm4gKnRoaXM7IH0KICAgICAgICBvc3RyZWFtJiBvcGVyYXRvcjw8KGNvbnN0IHVpbnQ2NF90JiB2KSAgICB7IHdyaXRlX3Vsb25nbG9uZyh2KTsgcmV0dXJuICp0aGlzOyB9CiAgICAgICAgb3N0cmVhbSYgb3BlcmF0b3I8PChjb25zdCBpbnQmIHYpICAgICAgICAgeyB3cml0ZV9pbnQodik7IHJldHVybiAqdGhpczsgfQogICAgICAgIG9zdHJlYW0mIG9wZXJhdG9yPDwoY29uc3QgYm9vbCYgdikgICAgICAgIHsgd3JpdGVfYm9vbCh2KTsgcmV0dXJuICp0aGlzOyB9CiAgICAgICAgb3N0cmVhbSYgb3BlcmF0b3I8PChjb25zdCBzdGQ6OnN0cmluZyYgdikgeyB3cml0ZV9zdHJpbmcodik7IHJldHVybiAqdGhpczsgfQoKICAgICAgICBzaXplX3QgcG9zKCkgY29uc3QKICAgICAgICB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLT5wZGF0YS5zaXplKCk7CiAgICAgICAgfQoKICAgICAgICBjb25zdCB2b2lkKiBkYXRhKCkgY29uc3QKICAgICAgICB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLT5wZGF0YS5kYXRhKCk7CiAgICAgICAgfQogICAgfTsKCiAgICBjbGFzcyBpc3RyZWFtCiAgICB7CiAgICBwcml2YXRlOgogICAgICAgIGNvbnN0IGNoYXIqIHBkYXRhOwogICAgICAgIHNpemVfdCBzeiwgcG9zOwoKICAgICAgICBzdGF0aWMgdWludDY0X3Qgc3BpdHpfbnRvaGxsKHVpbnQ2NF90IHgpCiAgICAgICAgewogICAgICAgICAgICBpZiAobnRvaHMoMSkgPT0gMSkKICAgICAgICAgICAgICAgIHJldHVybiB4OwogICAgICAgICAgICB1aW50MzJfdCBsbyA9IHN0YXRpY19jYXN0PHVpbnQzMl90PigoeCAmIDB4RkZGRkZGRkYwMDAwMDAwMCkgPj4gMzIpOwogICAgICAgICAgICB1aW50MzJfdCBoaSA9IHN0YXRpY19jYXN0PHVpbnQzMl90Pih4ICYgMHgwMDAwMDAwMEZGRkZGRkZGKTsKICAgICAgICAgICAgdWludDY0X3QgbmxvID0gaHRvbmwobG8pOwogICAgICAgICAgICB1aW50NjRfdCBuaGkgPSBodG9ubChoaSk7CiAgICAgICAgICAgIHJldHVybiBuaGkgPDwgMzIgfCBubG87CiAgICAgICAgfQoKICAgICAgICBjaGFyIGdldDEoKQogICAgICAgIHsKICAgICAgICAgICAgZW5zdXJlX3NpemUoMSk7CiAgICAgICAgICAgIHVpbnQ4X3QgdiA9ICoodGhpcy0+cGRhdGEgKyB0aGlzLT5wb3MpOwogICAgICAgICAgICB0aGlzLT5wb3MgKz0gMTsKICAgICAgICAgICAgcmV0dXJuIHY7CiAgICAgICAgfQoKICAgICAgICB1aW50MTZfdCBnZXQyKCkKICAgICAgICB7CiAgICAgICAgICAgIGVuc3VyZV9zaXplKDIpOwogICAgICAgICAgICB1aW50MTZfdCB2ID0gKigoY29uc3QgdWludDE2X3QqKSh0aGlzLT5wZGF0YSArIHRoaXMtPnBvcykpOwogICAgICAgICAgICB0aGlzLT5wb3MgKz0gMjsKICAgICAgICAgICAgcmV0dXJuIG50b2hzKHYpOwogICAgICAgIH0KCiAgICAgICAgdWludDMyX3QgZ2V0NCgpCiAgICAgICAgewogICAgICAgICAgICBlbnN1cmVfc2l6ZSg0KTsKICAgICAgICAgICAgdWludDMyX3QgdiA9ICooKGNvbnN0IHVpbnQzMl90KikodGhpcy0+cGRhdGEgKyB0aGlzLT5wb3MpKTsKICAgICAgICAgICAgdGhpcy0+cG9zICs9IDQ7CiAgICAgICAgICAgIHJldHVybiBudG9obCh2KTsKICAgICAgICB9CgogICAgICAgIHVpbnQ2NF90IGdldDgoKQogICAgICAgIHsKICAgICAgICAgICAgZW5zdXJlX3NpemUoOCk7CiAgICAgICAgICAgIHVpbnQ2NF90IHYgPSAqKChjb25zdCB1aW50NjRfdCopKHRoaXMtPnBkYXRhICsgdGhpcy0+cG9zKSk7CiAgICAgICAgICAgIHRoaXMtPnBvcyArPSA4OwogICAgICAgICAgICByZXR1cm4gc3BpdHpfbnRvaGxsKHYpOwogICAgICAgIH0KCiAgICAgICAgdGVtcGxhdGU8dHlwZW5hbWUgVD4gVCBnZXRfYXMoKQogICAgICAgIHsKICAgICAgICAgICAgZW5zdXJlX3NpemUoc2l6ZW9mKFQpKTsKICAgICAgICAgICAgVCB2ID0gKnJlaW50ZXJwcmV0X2Nhc3Q8Y29uc3QgVCo+KHRoaXMtPnBkYXRhICsgdGhpcy0+cG9zKTsKICAgICAgICAgICAgdGhpcy0+cG9zICs9IHNpemVvZihUKTsKICAgICAgICAgICAgcmV0dXJuIHY7CiAgICAgICAgfQoKICAgICAgICB2b2lkIGVuc3VyZV9zaXplKHNpemVfdCBuKQogICAgICAgIHsKICAgICAgICAgICAgaWYgKHRoaXMtPnN6IC0gdGhpcy0+cG9zIDwgbikKICAgICAgICAgICAgICAgIHRocm93IHN0ZDo6ZXhjZXB0aW9uKCk7CiAgICAgICAgfQoKICAgIHB1YmxpYzoKICAgICAgICBpc3RyZWFtKCkgOgogICAgICAgICAgICBwZGF0YShyZWludGVycHJldF9jYXN0PGNvbnN0IGNoYXIqPigwKSksCiAgICAgICAgICAgIHN6KDApLAogICAgICAgICAgICBwb3MoMCkKICAgICAgICB7CiAgICAgICAgfQoKICAgICAgICBpc3RyZWFtKGNvbnN0IHZvaWQgKmRhdGEsIGNvbnN0IHNpemVfdCYgc2l6ZSkgOgogICAgICAgICAgICBwZGF0YShyZWludGVycHJldF9jYXN0PGNvbnN0IGNoYXIqPihkYXRhKSksCiAgICAgICAgICAgIHN6KHNpemUpLAogICAgICAgICAgICBwb3MoMCkKICAgICAgICB7CiAgICAgICAgfQoKICAgICAgICBib29sIHJlYWRfYm9vbCgpIHsgdWludDhfdCB2ID0gZ2V0MSgpOyByZXR1cm4gdiA/IHRydWUgOiBmYWxzZTsgfQogICAgICAgIGludDhfdCByZWFkX2NoYXIoKSB7IHJldHVybiBnZXQxKCk7IH0KICAgICAgICB1aW50OF90IHJlYWRfYnl0ZSgpIHsgY2hhciB2ID0gZ2V0MSgpOyByZXR1cm4gKigoaW50OF90Kikmdik7IH0KICAgICAgICBmbG9hdCByZWFkX2Zsb2F0KCkgeyB1aW50MzJfdCB2ID0gZ2V0NCgpOyByZXR1cm4gKigoZmxvYXQqKShjaGFyKikmdik7IH0KICAgICAgICBkb3VibGUgcmVhZF9kb3VibGUoKSB7IHVpbnQ2NF90IHYgPSBnZXQ4KCk7IHJldHVybiAqKChkb3VibGUqKShjaGFyKikmdik7IH0KICAgICAgICBpbnQxNl90IHJlYWRfc2hvcnQoKSB7IHVpbnQxNl90IHYgPSBnZXQyKCk7IHJldHVybiAqKChpbnQxNl90KikoY2hhciopJnYpOyB9CiAgICAgICAgdWludDE2X3QgcmVhZF91c2hvcnQoKSB7IHJldHVybiBnZXQyKCk7IH0KICAgICAgICBpbnQzMl90IHJlYWRfaW50KCkgeyB1aW50MzJfdCB2ID0gZ2V0NCgpOyByZXR1cm4gKigoaW50MzJfdCopKGNoYXIqKSZ2KTsgfQogICAgICAgIHVpbnQzMl90IHJlYWRfdWludCgpIHsgcmV0dXJuIGdldDQoKTsgfQogICAgICAgIGludDY0X3QgcmVhZF9sb25nbG9uZygpIHsgdWludDY0X3QgdiA9IGdldDgoKTsgcmV0dXJuICooKGludDY0X3QqKShjaGFyKikmdik7IH0KICAgICAgICB1aW50NjRfdCByZWFkX3Vsb25nbG9uZygpIHsgcmV0dXJuIGdldDgoKTsgfQogICAgICAgIHN0ZDo6c3RyaW5nIHJlYWRfc3RyaW5nKCkKICAgICAgICB7CiAgICAgICAgICAgIHN0ZDo6c3RyaW5nc3RyZWFtIHNzOwogICAgICAgICAgICBjaGFyIGM7CiAgICAgICAgICAgIHdoaWxlKChjID0gcmVhZF9jaGFyKCkpKQogICAgICAgICAgICAgICAgc3MgPDwgYzsKICAgICAgICAgICAgcmV0dXJuIHNzLnN0cigpOwogICAgICAgIH0KICAgICAgICB2b2lkIHJlYWRfZGF0YSh2b2lkKiBwZGF0YSwgc2l6ZV90IHNpemUpCiAgICAgICAgewogICAgICAgICAgICBlbnN1cmVfc2l6ZShzaXplKTsKCiAgICAgICAgICAgIHN0ZDo6Y29weSh0aGlzLT5wZGF0YSArIHRoaXMtPnBvcywgdGhpcy0+cGRhdGEgKyB0aGlzLT5wb3MgKyBzaXplLAogICAgICAgICAgICAgICAgcmVpbnRlcnByZXRfY2FzdDxjaGFyKj4ocGRhdGEpKTsKCiAgICAgICAgICAgIHRoaXMtPnBvcyArPSBzaXplOwogICAgICAgIH0KCiAgICAgICAgaXN0cmVhbSYgb3BlcmF0b3I+PihmbG9hdCYgdikgICAgICAgeyB2ID0gcmVhZF9mbG9hdCgpOyByZXR1cm4gKnRoaXM7IH0KICAgICAgICBpc3RyZWFtJiBvcGVyYXRvcj4+KGRvdWJsZSYgdikgICAgICB7IHYgPSByZWFkX2RvdWJsZSgpOyByZXR1cm4gKnRoaXM7IH0KICAgICAgICBpc3RyZWFtJiBvcGVyYXRvcj4+KGludDhfdCYgdikgICAgICB7IHYgPSByZWFkX2NoYXIoKTsgcmV0dXJuICp0aGlzOyB9CiAgICAgICAgaXN0cmVhbSYgb3BlcmF0b3I+PihpbnQxNl90JiB2KSAgICAgeyB2ID0gcmVhZF9zaG9ydCgpOyByZXR1cm4gKnRoaXM7IH0KICAgICAgICBpc3RyZWFtJiBvcGVyYXRvcj4+KGludDY0X3QmIHYpICAgICB7IHYgPSByZWFkX2xvbmdsb25nKCk7IHJldHVybiAqdGhpczsgfQogICAgICAgIGlzdHJlYW0mIG9wZXJhdG9yPj4odWludDhfdCYgdikgICAgIHsgdiA9IHJlYWRfYnl0ZSgpOyByZXR1cm4gKnRoaXM7IH0KICAgICAgICBpc3RyZWFtJiBvcGVyYXRvcj4+KHVpbnQxNl90JiB2KSAgICB7IHYgPSByZWFkX3VzaG9ydCgpOyByZXR1cm4gKnRoaXM7IH0KICAgICAgICBpc3RyZWFtJiBvcGVyYXRvcj4+KHVpbnQzMl90JiB2KSAgICB7IHYgPSByZWFkX3VpbnQoKTsgcmV0dXJuICp0aGlzOyB9CiAgICAgICAgaXN0cmVhbSYgb3BlcmF0b3I+Pih1aW50NjRfdCYgdikgICAgeyB2ID0gcmVhZF91bG9uZ2xvbmcoKTsgcmV0dXJuICp0aGlzOyB9CiAgICAgICAgaXN0cmVhbSYgb3BlcmF0b3I+PihpbnQmIHYpICAgICAgICAgeyB2ID0gcmVhZF9pbnQoKTsgcmV0dXJuICp0aGlzOyB9CiAgICAgICAgaXN0cmVhbSYgb3BlcmF0b3I+Pihib29sJiB2KSAgICAgICAgeyB2ID0gcmVhZF9ib29sKCk7IHJldHVybiAqdGhpczsgfQogICAgICAgIGlzdHJlYW0mIG9wZXJhdG9yPj4oc3RkOjpzdHJpbmcmIHYpIHsgdiA9IHJlYWRfc3RyaW5nKCk7IHJldHVybiAqdGhpczsgfQoKICAgICAgICBzaXplX3Qgc2l6ZSgpIGNvbnN0CiAgICAgICAgewogICAgICAgICAgICByZXR1cm4gdGhpcy0+c3o7CiAgICAgICAgfQoKICAgICAgICBib29sIGhhc19kYXRhKCkgY29uc3QKICAgICAgICB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLT5wb3MgPCB0aGlzLT5zejsKICAgICAgICB9CiAgICB9Owp9OwoKI2VuZGlmIC8qIF9fU1BJVFpfQ1BQX1NUUkVBTV9IUFBfXyAqLwo='
    }
}

def render_api(name):
    """"""
    if name not in _apis:
        sys.stderr.write("Error: Unknown API '%s'!\n" % name)
        exit(1)
    destdir = 'spitz'
    if not os.path.exists(destdir):
        print("Creating '%s'..." % destdir)
        os.makedirs(destdir)
    for filename, blob in sorted(_apis[name].items()):
        filepath = os.path.join(destdir, filename)
        if os.path.exists(filepath):
            sys.stderr.write("Error: The file '%s' already exists!\n" % filepath)
            exit(1)
        print("Creating '%s'..." % filepath)
        fblob = open(filepath, 'wb')
        fblob.write(base64.b64decode(blob))
    print("Done.")


if __name__ == '__main__':
    if len(sys.argv) != 2:
        print('USAGE: spitz-examples example_name')
        print('Available examples:')
        for name in sorted(_apis.keys()):
            print('  %s' % name)
        exit(1)
    render_api(sys.argv[1])
