diff --git a/.nvmrc b/.nvmrc new file mode 100644 index 0000000..2bd5a0a --- /dev/null +++ b/.nvmrc @@ -0,0 +1 @@ +22 diff --git a/distros/safari/api-keys/api-keys.build.js b/distros/safari/api-keys/api-keys.build.js index 49aba0e..795e2f6 100644 --- a/distros/safari/api-keys/api-keys.build.js +++ b/distros/safari/api-keys/api-keys.build.js @@ -1,12 +1,493 @@ -(()=>{var r=typeof browser<"u"?browser:typeof chrome<"u"?chrome:null;if(!r)throw new Error("browser-polyfill: No extension API namespace found (neither browser nor chrome).");var d=typeof browser>"u"&&typeof chrome<"u";function y(e,t){return(...a)=>{try{let s=t.apply(e,a);if(s&&typeof s.then=="function")return s}catch{}return new Promise((s,o)=>{t.apply(e,[...a,(...c)=>{r.runtime&&r.runtime.lastError?o(new Error(r.runtime.lastError.message)):s(c.length<=1?c[0]:c)}])})}}var u={};u.runtime={sendMessage(...e){return d?y(r.runtime,r.runtime.sendMessage)(...e):r.runtime.sendMessage(...e)},onMessage:r.runtime.onMessage,getURL(e){return r.runtime.getURL(e)},openOptionsPage(){return d?y(r.runtime,r.runtime.openOptionsPage)():r.runtime.openOptionsPage()},get id(){return r.runtime.id}};u.storage={local:{get(...e){return d?y(r.storage.local,r.storage.local.get)(...e):r.storage.local.get(...e)},set(...e){return d?y(r.storage.local,r.storage.local.set)(...e):r.storage.local.set(...e)},clear(...e){return d?y(r.storage.local,r.storage.local.clear)(...e):r.storage.local.clear(...e)},remove(...e){return d?y(r.storage.local,r.storage.local.remove)(...e):r.storage.local.remove(...e)}},sync:r.storage?.sync?{get(...e){return d?y(r.storage.sync,r.storage.sync.get)(...e):r.storage.sync.get(...e)},set(...e){return d?y(r.storage.sync,r.storage.sync.set)(...e):r.storage.sync.set(...e)},remove(...e){return d?y(r.storage.sync,r.storage.sync.remove)(...e):r.storage.sync.remove(...e)},clear(...e){return d?y(r.storage.sync,r.storage.sync.clear)(...e):r.storage.sync.clear(...e)},getBytesInUse(...e){return r.storage.sync.getBytesInUse?d?y(r.storage.sync,r.storage.sync.getBytesInUse)(...e):r.storage.sync.getBytesInUse(...e):Promise.resolve(0)}}:null,onChanged:r.storage?.onChanged||null};u.tabs={create(...e){return d?y(r.tabs,r.tabs.create)(...e):r.tabs.create(...e)},query(...e){return d?y(r.tabs,r.tabs.query)(...e):r.tabs.query(...e)},remove(...e){return d?y(r.tabs,r.tabs.remove)(...e):r.tabs.remove(...e)},update(...e){return d?y(r.tabs,r.tabs.update)(...e):r.tabs.update(...e)},get(...e){return d?y(r.tabs,r.tabs.get)(...e):r.tabs.get(...e)},getCurrent(...e){return d?y(r.tabs,r.tabs.getCurrent)(...e):r.tabs.getCurrent(...e)},sendMessage(...e){return d?y(r.tabs,r.tabs.sendMessage)(...e):r.tabs.sendMessage(...e)}};u.alarms=r.alarms?{create(...e){let t=r.alarms.create(...e);return t&&typeof t.then=="function"?t:Promise.resolve()},clear(...e){return d?y(r.alarms,r.alarms.clear)(...e):r.alarms.clear(...e)},onAlarm:r.alarms.onAlarm}:null;var D=102400,J=8192,ee=512,te="_chunk:",V="_sync_meta",_="platformSyncEnabled";var E={P1_PROFILES:1,P2_SETTINGS:2,P3_APIKEYS:3,P4_VAULT:4},B=u.storage.local,K=null;function ne(e,t){let a=[];for(let o=0;o{let{hosts:k,...f}=c;return f}),o=JSON.stringify(s);t.push({key:"profiles",jsonString:o,priority:E.P1_PROFILES,size:o.length})}if(e.profileIndex!=null){let s=JSON.stringify(e.profileIndex);t.push({key:"profileIndex",jsonString:s,priority:E.P1_PROFILES,size:s.length})}if(e.isEncrypted!=null){let s=JSON.stringify(e.isEncrypted);t.push({key:"isEncrypted",jsonString:s,priority:E.P1_PROFILES,size:s.length})}let a=["autoLockMinutes","version","protocol_handler",_];for(let s of a)if(e[s]!=null){let o=JSON.stringify(e[s]);t.push({key:s,jsonString:o,priority:E.P2_SETTINGS,size:o.length})}for(let s of Object.keys(e))if(s.startsWith("feature:")){let o=JSON.stringify(e[s]);t.push({key:s,jsonString:o,priority:E.P2_SETTINGS,size:o.length})}if(e.apiKeyVault){let s=JSON.stringify(e.apiKeyVault);t.push({key:"apiKeyVault",jsonString:s,priority:E.P3_APIKEYS,size:s.length})}if(e.vaultDocs&&typeof e.vaultDocs=="object"){let s=Object.values(e.vaultDocs).sort((o,c)=>(c.updatedAt||0)-(o.updatedAt||0));for(let o of s){let c=`vaultDoc:${o.path}`,k=JSON.stringify(o);t.push({key:c,jsonString:k,priority:E.P4_VAULT,size:k.length})}}return t}async function se(){if(!(!u.storage.sync||!await ae()))try{let t=await re();t.sort((S,g)=>S.priority-g.priority);let a=0,s=0,o={},c=[],k=!1;for(let S of t){if(k)break;let g=ne(S.key,S.jsonString),m=0;for(let b of g)m+=b.key.length+(typeof b.value=="string"?b.value.length:JSON.stringify(b.value).length);if((a+m>D-500||s+g.length>ee-5)&&!(S.priority<=E.P3_APIKEYS)){k=!0;break}for(let b of g)o[b.key]=b.value,c.push(b.key);a+=m,s+=g.length}let f={lastWrittenAt:Date.now(),keys:c};o[V]=JSON.stringify(f),await u.storage.sync.set(o);try{let S=await u.storage.sync.get(null),g=Object.keys(S).filter(m=>m!==V&&!c.includes(m));g.length>0&&await u.storage.sync.remove(g)}catch{}}catch{}}function q(){u.storage.sync&&(K&&clearTimeout(K),K=setTimeout(()=>{K=null,se()},2e3))}async function ae(){return(await B.get({[_]:!0}))[_]}var Y=u.storage.local,P="apiKeyVault",F={keys:{},syncEnabled:!0,eventId:null,relayCreatedAt:null,syncStatus:"synced"};async function w(){let e=await Y.get({[P]:F});return{...F,...e[P]}}async function I(e){await Y.set({[P]:e}),q()}async function C(){return w()}async function j(e,t,a){let s=await w(),o=Math.floor(Date.now()/1e3),c=s.keys[e];return s.keys[e]={id:e,label:t,secret:a,createdAt:c?.createdAt||o,updatedAt:o,profileScope:c?.profileScope??null},await I(s),s.keys[e]}async function z(e){let t=await w();delete t.keys[e],await I(t)}async function x(){let e=await w();return Object.values(e.keys).sort((t,a)=>t.label.toLowerCase().localeCompare(a.label.toLowerCase()))}async function H(e){let t=await w();t.syncEnabled=e,await I(t)}async function G(){return(await w()).syncEnabled}async function A(e,t=null,a=null){let s=await w();s.syncStatus=e,t!==null&&(s.eventId=t),a!==null&&(s.relayCreatedAt=a),await I(s)}async function W(){return(await w()).keys}async function O(e){let t=await w();for(let[a,s]of Object.entries(e))t.keys[a]=s;await I(t)}var n={keys:[],newLabel:"",newSecret:"",editingId:null,editLabel:"",editSecret:"",copiedId:null,revealedId:null,syncEnabled:!0,globalSyncStatus:"idle",syncError:"",saving:!1,toast:"",relayInfo:{read:[],write:[]}};function l(e){return document.getElementById(e)}function L(){return n.relayInfo.read.length>0||n.relayInfo.write.length>0}function oe(){return[...n.keys].sort((e,t)=>e.label.toLowerCase().localeCompare(t.label.toLowerCase()))}function ie(e){return e?e.length<=8?"\u2022".repeat(e.length):e.slice(0,4)+"\u2022".repeat(4)+e.slice(-4):""}function v(e){n.toast=e,p(),setTimeout(()=>{n.toast="",p()},2e3)}function ce(e){return e==="idle"?"bg-green-500":e==="syncing"?"bg-yellow-500 animate-pulse":"bg-red-500"}function le(){return n.globalSyncStatus==="syncing"?"Syncing...":n.globalSyncStatus==="error"?n.syncError:n.syncEnabled?"Synced":"Local only"}function p(){let e=l("sync-dot"),t=l("sync-text"),a=l("sync-btn"),s=l("sync-toggle"),o=l("key-count");e&&(e.className=`inline-block w-3 h-3 rounded-full ${ce(n.globalSyncStatus)}`),t&&(t.textContent=le()),a&&(a.disabled=n.globalSyncStatus==="syncing"||!L()||!n.syncEnabled),s&&(s.checked=n.syncEnabled),o&&(o.textContent=n.keys.length+" key"+(n.keys.length!==1?"s":""));let c=l("key-table-container"),k=l("no-keys"),f=l("key-table-body");if(c&&(c.style.display=n.keys.length>0?"block":"none"),k&&(k.style.display=n.keys.length===0?"block":"none"),f){let Q=oe();f.innerHTML=Q.map(i=>{if(n.editingId===i.id)return` +(() => { + // src/utilities/browser-polyfill.js + var _browser = typeof browser !== "undefined" ? browser : typeof chrome !== "undefined" ? chrome : null; + if (!_browser) { + throw new Error("browser-polyfill: No extension API namespace found (neither browser nor chrome)."); + } + var isChrome = typeof browser === "undefined" && typeof chrome !== "undefined"; + function promisify(context, method) { + return (...args) => { + try { + const result = method.apply(context, args); + if (result && typeof result.then === "function") { + return result; + } + } catch (_) { + } + return new Promise((resolve, reject) => { + method.apply(context, [ + ...args, + (...cbArgs) => { + if (_browser.runtime && _browser.runtime.lastError) { + reject(new Error(_browser.runtime.lastError.message)); + } else { + resolve(cbArgs.length <= 1 ? cbArgs[0] : cbArgs); + } + } + ]); + }); + }; + } + var api = {}; + api.runtime = { + /** + * sendMessage – always returns a Promise. + */ + sendMessage(...args) { + if (!isChrome) { + return _browser.runtime.sendMessage(...args); + } + return promisify(_browser.runtime, _browser.runtime.sendMessage)(...args); + }, + /** + * onMessage – thin wrapper so callers use a consistent reference. + * The listener signature is (message, sender, sendResponse). + * On Chrome the listener can return `true` to keep the channel open, + * or return a Promise (MV3). Safari / Firefox expect a Promise return. + */ + onMessage: _browser.runtime.onMessage, + /** + * getURL – synchronous on all browsers. + */ + getURL(path) { + return _browser.runtime.getURL(path); + }, + /** + * openOptionsPage + */ + openOptionsPage() { + if (!isChrome) { + return _browser.runtime.openOptionsPage(); + } + return promisify(_browser.runtime, _browser.runtime.openOptionsPage)(); + }, + /** + * Expose the id for convenience. + */ + get id() { + return _browser.runtime.id; + } + }; + api.storage = { + local: { + get(...args) { + if (!isChrome) { + return _browser.storage.local.get(...args); + } + return promisify(_browser.storage.local, _browser.storage.local.get)(...args); + }, + set(...args) { + if (!isChrome) { + return _browser.storage.local.set(...args); + } + return promisify(_browser.storage.local, _browser.storage.local.set)(...args); + }, + clear(...args) { + if (!isChrome) { + return _browser.storage.local.clear(...args); + } + return promisify(_browser.storage.local, _browser.storage.local.clear)(...args); + }, + remove(...args) { + if (!isChrome) { + return _browser.storage.local.remove(...args); + } + return promisify(_browser.storage.local, _browser.storage.local.remove)(...args); + } + }, + // --- storage.sync ---------------------------------------------------------- + // Null when the browser doesn't support sync (older Safari, etc.) + sync: _browser.storage?.sync ? { + get(...args) { + if (!isChrome) { + return _browser.storage.sync.get(...args); + } + return promisify(_browser.storage.sync, _browser.storage.sync.get)(...args); + }, + set(...args) { + if (!isChrome) { + return _browser.storage.sync.set(...args); + } + return promisify(_browser.storage.sync, _browser.storage.sync.set)(...args); + }, + remove(...args) { + if (!isChrome) { + return _browser.storage.sync.remove(...args); + } + return promisify(_browser.storage.sync, _browser.storage.sync.remove)(...args); + }, + clear(...args) { + if (!isChrome) { + return _browser.storage.sync.clear(...args); + } + return promisify(_browser.storage.sync, _browser.storage.sync.clear)(...args); + }, + getBytesInUse(...args) { + if (!_browser.storage.sync.getBytesInUse) { + return Promise.resolve(0); + } + if (!isChrome) { + return _browser.storage.sync.getBytesInUse(...args); + } + return promisify(_browser.storage.sync, _browser.storage.sync.getBytesInUse)(...args); + } + } : null, + // --- storage.onChanged ----------------------------------------------------- + onChanged: _browser.storage?.onChanged || null + }; + api.tabs = { + create(...args) { + if (!isChrome) { + return _browser.tabs.create(...args); + } + return promisify(_browser.tabs, _browser.tabs.create)(...args); + }, + query(...args) { + if (!isChrome) { + return _browser.tabs.query(...args); + } + return promisify(_browser.tabs, _browser.tabs.query)(...args); + }, + remove(...args) { + if (!isChrome) { + return _browser.tabs.remove(...args); + } + return promisify(_browser.tabs, _browser.tabs.remove)(...args); + }, + update(...args) { + if (!isChrome) { + return _browser.tabs.update(...args); + } + return promisify(_browser.tabs, _browser.tabs.update)(...args); + }, + get(...args) { + if (!isChrome) { + return _browser.tabs.get(...args); + } + return promisify(_browser.tabs, _browser.tabs.get)(...args); + }, + getCurrent(...args) { + if (!isChrome) { + return _browser.tabs.getCurrent(...args); + } + return promisify(_browser.tabs, _browser.tabs.getCurrent)(...args); + }, + sendMessage(...args) { + if (!isChrome) { + return _browser.tabs.sendMessage(...args); + } + return promisify(_browser.tabs, _browser.tabs.sendMessage)(...args); + } + }; + api.alarms = _browser.alarms ? { + create(...args) { + const result = _browser.alarms.create(...args); + return result && typeof result.then === "function" ? result : Promise.resolve(); + }, + clear(...args) { + if (!isChrome) { + return _browser.alarms.clear(...args); + } + return promisify(_browser.alarms, _browser.alarms.clear)(...args); + }, + onAlarm: _browser.alarms.onAlarm + } : null; + + // src/utilities/sync-manager.js + var SYNC_QUOTA = 102400; + var MAX_ITEM = 8192; + var MAX_ITEMS = 512; + var CHUNK_PREFIX = "_chunk:"; + var SYNC_META_KEY = "_sync_meta"; + var LOCAL_ENABLED_KEY = "platformSyncEnabled"; + var PRIORITY = { + P1_PROFILES: 1, + P2_SETTINGS: 2, + P3_APIKEYS: 3, + P4_VAULT: 4 + }; + var storage = api.storage.local; + var pushTimer = null; + function chunkValue(key, jsonString) { + const chunks = []; + for (let i = 0; i < jsonString.length; i += MAX_ITEM - 100) { + chunks.push(jsonString.slice(i, i + MAX_ITEM - 100)); + } + if (chunks.length === 1) { + return [{ key, value: jsonString }]; + } + const entries = []; + for (let i = 0; i < chunks.length; i++) { + entries.push({ key: `${CHUNK_PREFIX}${key}:${i}`, value: chunks[i] }); + } + entries.push({ key, value: JSON.stringify({ __chunked: true, count: chunks.length }) }); + return entries; + } + async function buildSyncPayload() { + const all = await storage.get(null); + const entries = []; + if (all.profiles) { + const cleanProfiles = all.profiles.map((p) => { + const { hosts, ...rest } = p; + return rest; + }); + const json = JSON.stringify(cleanProfiles); + entries.push({ key: "profiles", jsonString: json, priority: PRIORITY.P1_PROFILES, size: json.length }); + } + if (all.profileIndex != null) { + const json = JSON.stringify(all.profileIndex); + entries.push({ key: "profileIndex", jsonString: json, priority: PRIORITY.P1_PROFILES, size: json.length }); + } + const settingsKeys = ["autoLockMinutes", "version", "protocol_handler", LOCAL_ENABLED_KEY]; + for (const k of settingsKeys) { + if (all[k] != null) { + const json = JSON.stringify(all[k]); + entries.push({ key: k, jsonString: json, priority: PRIORITY.P2_SETTINGS, size: json.length }); + } + } + for (const k of Object.keys(all)) { + if (k.startsWith("feature:")) { + const json = JSON.stringify(all[k]); + entries.push({ key: k, jsonString: json, priority: PRIORITY.P2_SETTINGS, size: json.length }); + } + } + if (all.apiKeyVault) { + const json = JSON.stringify(all.apiKeyVault); + entries.push({ key: "apiKeyVault", jsonString: json, priority: PRIORITY.P3_APIKEYS, size: json.length }); + } + if (all.vaultDocs && typeof all.vaultDocs === "object") { + const docs = Object.values(all.vaultDocs).sort((a, b) => (b.updatedAt || 0) - (a.updatedAt || 0)); + for (const doc of docs) { + const docKey = `vaultDoc:${doc.path}`; + const json = JSON.stringify(doc); + entries.push({ key: docKey, jsonString: json, priority: PRIORITY.P4_VAULT, size: json.length }); + } + } + return entries; + } + async function pushToSync() { + if (!api.storage.sync) return; + const enabled = await isSyncEnabled(); + if (!enabled) return; + try { + const entries = await buildSyncPayload(); + entries.sort((a, b) => a.priority - b.priority); + let usedBytes = 0; + let usedItems = 0; + const syncPayload = {}; + const allSyncKeys = []; + let budgetExhausted = false; + for (const entry of entries) { + if (budgetExhausted) break; + const chunks = chunkValue(entry.key, entry.jsonString); + let entrySize = 0; + for (const c of chunks) { + entrySize += c.key.length + (typeof c.value === "string" ? c.value.length : JSON.stringify(c.value).length); + } + if (usedBytes + entrySize > SYNC_QUOTA - 500 || usedItems + chunks.length > MAX_ITEMS - 5) { + if (entry.priority <= PRIORITY.P3_APIKEYS) { + } else { + console.warn(`[SyncManager] Budget exhausted at priority ${entry.priority}, skipping remaining entries`); + budgetExhausted = true; + break; + } + } + for (const c of chunks) { + syncPayload[c.key] = c.value; + allSyncKeys.push(c.key); + } + usedBytes += entrySize; + usedItems += chunks.length; + } + const meta = { + lastWrittenAt: Date.now(), + keys: allSyncKeys + }; + syncPayload[SYNC_META_KEY] = JSON.stringify(meta); + await api.storage.sync.set(syncPayload); + try { + const existing = await api.storage.sync.get(null); + const orphanKeys = Object.keys(existing).filter( + (k) => k !== SYNC_META_KEY && !allSyncKeys.includes(k) + ); + if (orphanKeys.length > 0) { + await api.storage.sync.remove(orphanKeys); + } + } catch { + } + console.log(`[SyncManager] Pushed ${allSyncKeys.length} entries (${usedBytes} bytes) to sync storage`); + } catch (e) { + console.error("[SyncManager] pushToSync error:", e); + } + } + function scheduleSyncPush() { + if (!api.storage.sync) return; + if (pushTimer) clearTimeout(pushTimer); + pushTimer = setTimeout(() => { + pushTimer = null; + pushToSync(); + }, 2e3); + } + async function isSyncEnabled() { + const data = await storage.get({ [LOCAL_ENABLED_KEY]: true }); + return data[LOCAL_ENABLED_KEY]; + } + + // src/utilities/api-key-store.js + var storage2 = api.storage.local; + var STORAGE_KEY = "apiKeyVault"; + var DEFAULT_STORE = { + keys: {}, + syncEnabled: true, + eventId: null, + relayCreatedAt: null, + syncStatus: "synced" + }; + async function getStore() { + const data = await storage2.get({ [STORAGE_KEY]: DEFAULT_STORE }); + return { ...DEFAULT_STORE, ...data[STORAGE_KEY] }; + } + async function setStore(store) { + await storage2.set({ [STORAGE_KEY]: store }); + scheduleSyncPush(); + } + async function getApiKeyStore() { + return getStore(); + } + async function saveApiKey(id, label, secret) { + const store = await getStore(); + const now = Math.floor(Date.now() / 1e3); + const existing = store.keys[id]; + store.keys[id] = { + id, + label, + secret, + createdAt: existing?.createdAt || now, + updatedAt: now, + profileScope: existing?.profileScope ?? null + }; + await setStore(store); + return store.keys[id]; + } + async function deleteApiKey(id) { + const store = await getStore(); + delete store.keys[id]; + await setStore(store); + } + async function listApiKeys() { + const store = await getStore(); + return Object.values(store.keys).sort( + (a, b) => a.label.toLowerCase().localeCompare(b.label.toLowerCase()) + ); + } + async function setSyncEnabled(enabled) { + const store = await getStore(); + store.syncEnabled = enabled; + await setStore(store); + } + async function isSyncEnabled2() { + const store = await getStore(); + return store.syncEnabled; + } + async function updateStoreSyncState(syncStatus, eventId = null, relayCreatedAt = null) { + const store = await getStore(); + store.syncStatus = syncStatus; + if (eventId !== null) store.eventId = eventId; + if (relayCreatedAt !== null) store.relayCreatedAt = relayCreatedAt; + await setStore(store); + } + async function exportStore() { + const store = await getStore(); + return store.keys; + } + async function importStore(keys) { + const store = await getStore(); + for (const [id, key] of Object.entries(keys)) { + store.keys[id] = key; + } + await setStore(store); + } + + // src/api-keys/api-keys.js + var state = { + keys: [], + newLabel: "", + newSecret: "", + editingId: null, + editLabel: "", + editSecret: "", + copiedId: null, + revealedId: null, + syncEnabled: true, + globalSyncStatus: "idle", + syncError: "", + saving: false, + toast: "", + relayInfo: { read: [], write: [] } + }; + function $(id) { + return document.getElementById(id); + } + function hasRelays() { + return state.relayInfo.read.length > 0 || state.relayInfo.write.length > 0; + } + function sortedKeys() { + return [...state.keys].sort( + (a, b) => a.label.toLowerCase().localeCompare(b.label.toLowerCase()) + ); + } + function maskSecret(secret) { + if (!secret) return ""; + if (secret.length <= 8) return "\u2022".repeat(secret.length); + return secret.slice(0, 4) + "\u2022".repeat(4) + secret.slice(-4); + } + function showToast(msg) { + state.toast = msg; + render(); + setTimeout(() => { + state.toast = ""; + render(); + }, 2e3); + } + function syncStatusClass(status) { + if (status === "idle") return "bg-green-500"; + if (status === "syncing") return "bg-yellow-500 animate-pulse"; + return "bg-red-500"; + } + function syncStatusText() { + if (state.globalSyncStatus === "syncing") return "Syncing..."; + if (state.globalSyncStatus === "error") return state.syncError; + return state.syncEnabled ? "Synced" : "Local only"; + } + function render() { + const syncDot = $("sync-dot"); + const syncText = $("sync-text"); + const syncBtn = $("sync-btn"); + const syncToggle = $("sync-toggle"); + const keyCount = $("key-count"); + if (syncDot) syncDot.className = `inline-block w-3 h-3 rounded-full ${syncStatusClass(state.globalSyncStatus)}`; + if (syncText) syncText.textContent = syncStatusText(); + if (syncBtn) syncBtn.disabled = state.globalSyncStatus === "syncing" || !hasRelays() || !state.syncEnabled; + if (syncToggle) syncToggle.checked = state.syncEnabled; + if (keyCount) keyCount.textContent = state.keys.length + " key" + (state.keys.length !== 1 ? "s" : ""); + const keyTableContainer = $("key-table-container"); + const noKeysMsg = $("no-keys"); + const keyTableBody = $("key-table-body"); + if (keyTableContainer) keyTableContainer.style.display = state.keys.length > 0 ? "block" : "none"; + if (noKeysMsg) noKeysMsg.style.display = state.keys.length === 0 ? "block" : "none"; + if (keyTableBody) { + const sorted = sortedKeys(); + keyTableBody.innerHTML = sorted.map((key) => { + if (state.editingId === key.id) { + return ` @@ -15,8 +496,8 @@ class="input text-xs font-mono w-full" autocomplete="off" spellcheck="false" - data-edit-secret="${i.id}" - value="${X(n.editSecret)}" + data-edit-secret="${key.id}" + value="${escapeAttr(state.editSecret)}" /> @@ -24,17 +505,311 @@ - `;let h=n.revealedId===i.id?N(i.secret):N(ie(i.secret)),Z=n.copiedId===i.id?"Copied!":"Copy";return` + `; + } + const displaySecret = state.revealedId === key.id ? escapeHtml(key.secret) : escapeHtml(maskSecret(key.secret)); + const copyLabel = state.copiedId === key.id ? "Copied!" : "Copy"; + return ` - ${N(i.label)} + ${escapeHtml(key.label)} - ${h} + ${displaySecret} - - + + - `}).join(""),f.querySelectorAll('[data-action="start-edit"]').forEach(i=>{i.addEventListener("click",()=>de(i.dataset.keyId))}),f.querySelectorAll('[data-action="toggle-reveal"]').forEach(i=>{i.addEventListener("click",()=>{n.revealedId=n.revealedId===i.dataset.keyId?null:i.dataset.keyId,p()})}),f.querySelectorAll('[data-action="copy-secret"]').forEach(i=>{i.addEventListener("click",()=>fe(i.dataset.keyId))}),f.querySelectorAll('[data-action="delete-key"]').forEach(i=>{i.addEventListener("click",()=>ye(i.dataset.keyId))}),f.querySelectorAll('[data-action="save-edit"]').forEach(i=>{i.addEventListener("click",$)}),f.querySelectorAll('[data-action="cancel-edit"]').forEach(i=>{i.addEventListener("click",R)}),f.querySelectorAll("[data-edit-label]").forEach(i=>{i.addEventListener("input",h=>{n.editLabel=h.target.value}),i.addEventListener("keyup",h=>{h.key==="Enter"&&$(),h.key==="Escape"&&R()})}),f.querySelectorAll("[data-edit-secret]").forEach(i=>{i.addEventListener("input",h=>{n.editSecret=h.target.value}),i.addEventListener("keyup",h=>{h.key==="Enter"&&$(),h.key==="Escape"&&R()})})}let S=l("new-label"),g=l("new-secret"),m=l("add-key-btn");S&&document.activeElement!==S&&(S.value=n.newLabel),g&&document.activeElement!==g&&(g.value=n.newSecret),m&&(m.disabled=n.saving||n.newLabel.trim().length===0||n.newSecret.trim().length===0,m.textContent=n.saving?"Saving...":"Save");let b=l("toast");b&&(b.textContent=n.toast,b.style.display=n.toast?"block":"none")}function N(e){let t=document.createElement("div");return t.textContent=e,t.innerHTML}function X(e){return e.replace(/&/g,"&").replace(/"/g,""").replace(//g,">")}async function ue(){let e=n.newLabel.trim(),t=n.newSecret.trim();if(!e||!t)return;n.saving=!0,p();let a=crypto.randomUUID();await j(a,e,t),n.keys=await x(),n.newLabel="",n.newSecret="",n.syncEnabled&&L()&&await M(),n.saving=!1,v("Key added")}function de(e){let t=n.keys.find(a=>a.id===e);t&&(n.editingId=t.id,n.editLabel=t.label,n.editSecret=t.secret,p())}async function $(){if(!n.editingId)return;let e=n.editLabel.trim(),t=n.editSecret.trim();!e||!t||(await j(n.editingId,e,t),n.keys=await x(),n.editingId=null,n.editLabel="",n.editSecret="",n.syncEnabled&&L()&&await M(),v("Key updated"))}function R(){n.editingId=null,n.editLabel="",n.editSecret="",p()}async function ye(e){let t=n.keys.find(a=>a.id===e);t&&confirm(`Delete "${t.label}"?`)&&(await z(e),n.keys=await x(),n.syncEnabled&&L()&&await M(),v("Key deleted"))}async function fe(e){let t=n.keys.find(a=>a.id===e);t&&(await navigator.clipboard.writeText(t.secret),n.copiedId=e,p(),setTimeout(()=>{n.copiedId=null,p()},2e3),setTimeout(()=>{navigator.clipboard.writeText("").catch(()=>{})},3e4))}async function M(){try{let e=await C(),t=await u.runtime.sendMessage({kind:"apikeys.publish",payload:{keys:e.keys}});return t.success&&await A("synced",t.eventId,t.createdAt),t}catch(e){return await A("local-only"),{success:!1,error:e.message}}}async function U(){n.globalSyncStatus="syncing",n.syncError="",p();try{let e=await u.runtime.sendMessage({kind:"apikeys.fetch"});if(!e.success){n.globalSyncStatus="error",n.syncError=e.error||"Sync failed",p();return}if(e.keys){let t=await C(),a=t.keys;Object.keys(a).length===0?await O(e.keys):(!t.relayCreatedAt||e.createdAt>t.relayCreatedAt)&&await O(e.keys),await A("synced",e.eventId,e.createdAt),n.keys=await x()}n.globalSyncStatus="idle"}catch(e){n.globalSyncStatus="error",n.syncError=e.message||"Sync failed"}p()}async function pe(){await H(n.syncEnabled),n.syncEnabled&&L()&&await U()}async function ge(){let e=await W(),t=JSON.stringify(e,null,2),a=await u.runtime.sendMessage({kind:"apikeys.encrypt",payload:{plainText:t}});if(!a.success){v("Export failed: "+(a.error||"unknown"));return}let s=new Blob([JSON.stringify({encrypted:!0,data:a.cipherText})],{type:"application/json"}),o=URL.createObjectURL(s),c=document.createElement("a");c.href=o,c.download="nostrkey-api-keys-backup.json",c.click(),URL.revokeObjectURL(o),v("Exported")}async function be(e){let t=e.target.files?.[0];if(t){try{let a=await t.text(),s=JSON.parse(a),o;if(s.encrypted&&s.data){let c=await u.runtime.sendMessage({kind:"apikeys.decrypt",payload:{cipherText:s.data}});if(!c.success){v("Decrypt failed: "+(c.error||"unknown"));return}o=JSON.parse(c.plainText)}else o=s;await O(o),n.keys=await x(),n.syncEnabled&&L()&&await M(),v("Imported "+Object.keys(o).length+" keys")}catch(a){v("Import failed: "+a.message)}e.target.value=""}}function Se(){l("sync-btn")?.addEventListener("click",U),l("add-key-btn")?.addEventListener("click",ue),l("export-btn")?.addEventListener("click",ge),l("import-file")?.addEventListener("change",be),l("close-btn")?.addEventListener("click",()=>window.close()),l("sync-toggle")?.addEventListener("change",e=>{n.syncEnabled=e.target.checked,pe()}),l("new-label")?.addEventListener("input",e=>{n.newLabel=e.target.value,p()}),l("new-secret")?.addEventListener("input",e=>{n.newSecret=e.target.value,p()})}async function he(){let e=await u.runtime.sendMessage({kind:"isEncrypted"}),t=l("vault-locked-gate"),a=l("vault-main-content");if(!e){t&&(t.style.display="block"),a&&(a.style.display="none"),l("gate-security-btn")?.addEventListener("click",()=>{let o=u.runtime.getURL("security/security.html");window.open(o,"nostrkey-options")});return}t&&(t.style.display="none"),a&&(a.style.display="block");let s=await u.runtime.sendMessage({kind:"vault.getRelays"});n.relayInfo=s||{read:[],write:[]},n.syncEnabled=await G(),n.keys=await x(),Se(),p(),n.syncEnabled&&L()&&await U()}document.addEventListener("DOMContentLoaded",he);})(); + `; + }).join(""); + keyTableBody.querySelectorAll('[data-action="start-edit"]').forEach((el) => { + el.addEventListener("click", () => startEdit(el.dataset.keyId)); + }); + keyTableBody.querySelectorAll('[data-action="toggle-reveal"]').forEach((el) => { + el.addEventListener("click", () => { + state.revealedId = state.revealedId === el.dataset.keyId ? null : el.dataset.keyId; + render(); + }); + }); + keyTableBody.querySelectorAll('[data-action="copy-secret"]').forEach((el) => { + el.addEventListener("click", () => copySecret(el.dataset.keyId)); + }); + keyTableBody.querySelectorAll('[data-action="delete-key"]').forEach((el) => { + el.addEventListener("click", () => deleteKey(el.dataset.keyId)); + }); + keyTableBody.querySelectorAll('[data-action="save-edit"]').forEach((el) => { + el.addEventListener("click", saveEdit); + }); + keyTableBody.querySelectorAll('[data-action="cancel-edit"]').forEach((el) => { + el.addEventListener("click", cancelEdit); + }); + keyTableBody.querySelectorAll("[data-edit-label]").forEach((el) => { + el.addEventListener("input", (e) => { + state.editLabel = e.target.value; + }); + el.addEventListener("keyup", (e) => { + if (e.key === "Enter") saveEdit(); + if (e.key === "Escape") cancelEdit(); + }); + }); + keyTableBody.querySelectorAll("[data-edit-secret]").forEach((el) => { + el.addEventListener("input", (e) => { + state.editSecret = e.target.value; + }); + el.addEventListener("keyup", (e) => { + if (e.key === "Enter") saveEdit(); + if (e.key === "Escape") cancelEdit(); + }); + }); + } + const newLabelInput = $("new-label"); + const newSecretInput = $("new-secret"); + const addKeyBtn = $("add-key-btn"); + if (newLabelInput && document.activeElement !== newLabelInput) newLabelInput.value = state.newLabel; + if (newSecretInput && document.activeElement !== newSecretInput) newSecretInput.value = state.newSecret; + if (addKeyBtn) { + addKeyBtn.disabled = state.saving || state.newLabel.trim().length === 0 || state.newSecret.trim().length === 0; + addKeyBtn.textContent = state.saving ? "Saving..." : "Save"; + } + const toast = $("toast"); + if (toast) { + toast.textContent = state.toast; + toast.style.display = state.toast ? "block" : "none"; + } + } + function escapeHtml(str) { + const div = document.createElement("div"); + div.textContent = str; + return div.innerHTML; + } + function escapeAttr(str) { + return str.replace(/&/g, "&").replace(/"/g, """).replace(//g, ">"); + } + async function addKey() { + const label = state.newLabel.trim(); + const secret = state.newSecret.trim(); + if (!label || !secret) return; + state.saving = true; + render(); + const id = crypto.randomUUID(); + await saveApiKey(id, label, secret); + state.keys = await listApiKeys(); + state.newLabel = ""; + state.newSecret = ""; + if (state.syncEnabled && hasRelays()) { + await publishToRelay(); + } + state.saving = false; + showToast("Key added"); + } + function startEdit(id) { + const key = state.keys.find((k) => k.id === id); + if (!key) return; + state.editingId = key.id; + state.editLabel = key.label; + state.editSecret = key.secret; + render(); + } + async function saveEdit() { + if (!state.editingId) return; + const label = state.editLabel.trim(); + const secret = state.editSecret.trim(); + if (!label || !secret) return; + await saveApiKey(state.editingId, label, secret); + state.keys = await listApiKeys(); + state.editingId = null; + state.editLabel = ""; + state.editSecret = ""; + if (state.syncEnabled && hasRelays()) { + await publishToRelay(); + } + showToast("Key updated"); + } + function cancelEdit() { + state.editingId = null; + state.editLabel = ""; + state.editSecret = ""; + render(); + } + async function deleteKey(id) { + const key = state.keys.find((k) => k.id === id); + if (!key) return; + if (!confirm(`Delete "${key.label}"?`)) return; + await deleteApiKey(id); + state.keys = await listApiKeys(); + if (state.syncEnabled && hasRelays()) { + await publishToRelay(); + } + showToast("Key deleted"); + } + async function copySecret(id) { + const key = state.keys.find((k) => k.id === id); + if (!key) return; + await navigator.clipboard.writeText(key.secret); + state.copiedId = id; + render(); + setTimeout(() => { + state.copiedId = null; + render(); + }, 2e3); + setTimeout(() => { + navigator.clipboard.writeText("").catch(() => { + }); + }, 3e4); + } + async function publishToRelay() { + try { + const store = await getApiKeyStore(); + const result = await api.runtime.sendMessage({ + kind: "apikeys.publish", + payload: { keys: store.keys } + }); + if (result.success) { + await updateStoreSyncState("synced", result.eventId, result.createdAt); + } + return result; + } catch (e) { + await updateStoreSyncState("local-only"); + return { success: false, error: e.message }; + } + } + async function syncAll() { + state.globalSyncStatus = "syncing"; + state.syncError = ""; + render(); + try { + const result = await api.runtime.sendMessage({ kind: "apikeys.fetch" }); + if (!result.success) { + state.globalSyncStatus = "error"; + state.syncError = result.error || "Sync failed"; + render(); + return; + } + if (result.keys) { + const store = await getApiKeyStore(); + const localKeys = store.keys; + const localCount = Object.keys(localKeys).length; + if (localCount === 0) { + await importStore(result.keys); + } else if (!store.relayCreatedAt || result.createdAt > store.relayCreatedAt) { + await importStore(result.keys); + } + await updateStoreSyncState("synced", result.eventId, result.createdAt); + state.keys = await listApiKeys(); + } + state.globalSyncStatus = "idle"; + } catch (e) { + state.globalSyncStatus = "error"; + state.syncError = e.message || "Sync failed"; + } + render(); + } + async function toggleSync() { + await setSyncEnabled(state.syncEnabled); + if (state.syncEnabled && hasRelays()) { + await syncAll(); + } + } + async function exportKeys() { + const keys = await exportStore(); + const plainText = JSON.stringify(keys, null, 2); + const result = await api.runtime.sendMessage({ + kind: "apikeys.encrypt", + payload: { plainText } + }); + if (!result.success) { + showToast("Export failed: " + (result.error || "unknown")); + return; + } + const blob = new Blob( + [JSON.stringify({ encrypted: true, data: result.cipherText })], + { type: "application/json" } + ); + const url = URL.createObjectURL(blob); + const a = document.createElement("a"); + a.href = url; + a.download = "nostrkey-api-keys-backup.json"; + a.click(); + URL.revokeObjectURL(url); + showToast("Exported"); + } + async function importKeys(event) { + const file = event.target.files?.[0]; + if (!file) return; + try { + const text = await file.text(); + const parsed = JSON.parse(text); + let keys; + if (parsed.encrypted && parsed.data) { + const result = await api.runtime.sendMessage({ + kind: "apikeys.decrypt", + payload: { cipherText: parsed.data } + }); + if (!result.success) { + showToast("Decrypt failed: " + (result.error || "unknown")); + return; + } + keys = JSON.parse(result.plainText); + } else { + keys = parsed; + } + await importStore(keys); + state.keys = await listApiKeys(); + if (state.syncEnabled && hasRelays()) { + await publishToRelay(); + } + showToast("Imported " + Object.keys(keys).length + " keys"); + } catch (e) { + showToast("Import failed: " + e.message); + } + event.target.value = ""; + } + function bindEvents() { + $("sync-btn")?.addEventListener("click", syncAll); + $("add-key-btn")?.addEventListener("click", addKey); + $("export-btn")?.addEventListener("click", exportKeys); + $("import-file")?.addEventListener("change", importKeys); + $("close-btn")?.addEventListener("click", () => window.close()); + $("sync-toggle")?.addEventListener("change", (e) => { + state.syncEnabled = e.target.checked; + toggleSync(); + }); + $("new-label")?.addEventListener("input", (e) => { + state.newLabel = e.target.value; + render(); + }); + $("new-secret")?.addEventListener("input", (e) => { + state.newSecret = e.target.value; + render(); + }); + } + async function init() { + const isEncrypted = await api.runtime.sendMessage({ kind: "isEncrypted" }); + const gate = $("vault-locked-gate"); + const main = $("vault-main-content"); + if (!isEncrypted) { + if (gate) gate.style.display = "block"; + if (main) main.style.display = "none"; + $("gate-security-btn")?.addEventListener("click", () => { + const url = api.runtime.getURL("security/security.html"); + window.open(url, "nostrkey-options"); + }); + return; + } + if (gate) gate.style.display = "none"; + if (main) main.style.display = "block"; + const relays = await api.runtime.sendMessage({ kind: "vault.getRelays" }); + state.relayInfo = relays || { read: [], write: [] }; + state.syncEnabled = await isSyncEnabled2(); + state.keys = await listApiKeys(); + bindEvents(); + render(); + if (state.syncEnabled && hasRelays()) { + await syncAll(); + } + } + document.addEventListener("DOMContentLoaded", init); +})(); +//# sourceMappingURL=data:application/json;base64,ewogICJ2ZXJzaW9uIjogMywKICAic291cmNlcyI6IFsiLi4vLi4vLi4vc3JjL3V0aWxpdGllcy9icm93c2VyLXBvbHlmaWxsLmpzIiwgIi4uLy4uLy4uL3NyYy91dGlsaXRpZXMvc3luYy1tYW5hZ2VyLmpzIiwgIi4uLy4uLy4uL3NyYy91dGlsaXRpZXMvYXBpLWtleS1zdG9yZS5qcyIsICIuLi8uLi8uLi9zcmMvYXBpLWtleXMvYXBpLWtleXMuanMiXSwKICAic291cmNlc0NvbnRlbnQiOiBbIi8qKlxuICogQnJvd3NlciBBUEkgY29tcGF0aWJpbGl0eSBsYXllciBmb3IgQ2hyb21lIC8gU2FmYXJpIC8gRmlyZWZveC5cbiAqXG4gKiBTYWZhcmkgYW5kIEZpcmVmb3ggZXhwb3NlIGBicm93c2VyLipgIChQcm9taXNlLWJhc2VkLCBXZWJFeHRlbnNpb24gc3RhbmRhcmQpLlxuICogQ2hyb21lIGV4cG9zZXMgYGNocm9tZS4qYCAoY2FsbGJhY2stYmFzZWQgaGlzdG9yaWNhbGx5LCBidXQgTVYzIHN1cHBvcnRzXG4gKiBwcm9taXNlcyBvbiBtb3N0IEFQSXMpLiBJbiBhIHNlcnZpY2Utd29ya2VyIGNvbnRleHQgYGJyb3dzZXJgIGlzIHVuZGVmaW5lZFxuICogb24gQ2hyb21lLCBzbyB3ZSBub3JtYWxpc2UgZXZlcnl0aGluZyBoZXJlLlxuICpcbiAqIFVzYWdlOiAgaW1wb3J0IHsgYXBpIH0gZnJvbSAnLi91dGlsaXRpZXMvYnJvd3Nlci1wb2x5ZmlsbCc7XG4gKiAgICAgICAgIGFwaS5ydW50aW1lLnNlbmRNZXNzYWdlKC4uLilcbiAqXG4gKiBUaGUgZXhwb3J0ZWQgYGFwaWAgb2JqZWN0IG1pcnJvcnMgdGhlIHN1YnNldCBvZiB0aGUgV2ViRXh0ZW5zaW9uIEFQSSB0aGF0XG4gKiBOb3N0cktleSBhY3R1YWxseSB1c2VzLCB3aXRoIGV2ZXJ5IG1ldGhvZCByZXR1cm5pbmcgYSBQcm9taXNlLlxuICovXG5cbi8vIERldGVjdCB3aGljaCBnbG9iYWwgbmFtZXNwYWNlIGlzIGF2YWlsYWJsZS5cbmNvbnN0IF9icm93c2VyID1cbiAgICB0eXBlb2YgYnJvd3NlciAhPT0gJ3VuZGVmaW5lZCcgPyBicm93c2VyIDpcbiAgICB0eXBlb2YgY2hyb21lICAhPT0gJ3VuZGVmaW5lZCcgPyBjaHJvbWUgIDpcbiAgICBudWxsO1xuXG5pZiAoIV9icm93c2VyKSB7XG4gICAgdGhyb3cgbmV3IEVycm9yKCdicm93c2VyLXBvbHlmaWxsOiBObyBleHRlbnNpb24gQVBJIG5hbWVzcGFjZSBmb3VuZCAobmVpdGhlciBicm93c2VyIG5vciBjaHJvbWUpLicpO1xufVxuXG4vKipcbiAqIFRydWUgd2hlbiBydW5uaW5nIG9uIENocm9tZSAob3IgYW55IENocm9taXVtLWJhc2VkIGJyb3dzZXIgdGhhdCBvbmx5XG4gKiBleHBvc2VzIHRoZSBgY2hyb21lYCBuYW1lc3BhY2UpLlxuICovXG5jb25zdCBpc0Nocm9tZSA9IHR5cGVvZiBicm93c2VyID09PSAndW5kZWZpbmVkJyAmJiB0eXBlb2YgY2hyb21lICE9PSAndW5kZWZpbmVkJztcblxuLyoqXG4gKiBXcmFwIGEgQ2hyb21lIGNhbGxiYWNrLXN0eWxlIG1ldGhvZCBzbyBpdCByZXR1cm5zIGEgUHJvbWlzZS5cbiAqIElmIHRoZSBtZXRob2QgYWxyZWFkeSByZXR1cm5zIGEgcHJvbWlzZSAoTVYzKSB3ZSBqdXN0IHBhc3MgdGhyb3VnaC5cbiAqL1xuZnVuY3Rpb24gcHJvbWlzaWZ5KGNvbnRleHQsIG1ldGhvZCkge1xuICAgIHJldHVybiAoLi4uYXJncykgPT4ge1xuICAgICAgICAvLyBNVjMgQ2hyb21lIEFQSXMgcmV0dXJuIHByb21pc2VzIHdoZW4gbm8gY2FsbGJhY2sgaXMgc3VwcGxpZWQuXG4gICAgICAgIC8vIFdlIHRyeSB0aGUgcHJvbWlzZSBwYXRoIGZpcnN0OyBpZiB0aGUgcnVudGltZSBzaWduYWxzIGFuIGVycm9yXG4gICAgICAgIC8vIHZpYSBjaHJvbWUucnVudGltZS5sYXN0RXJyb3IgaW5zaWRlIGEgY2FsbGJhY2sgd2UgY2F0Y2ggdGhhdCB0b28uXG4gICAgICAgIHRyeSB7XG4gICAgICAgICAgICBjb25zdCByZXN1bHQgPSBtZXRob2QuYXBwbHkoY29udGV4dCwgYXJncyk7XG4gICAgICAgICAgICBpZiAocmVzdWx0ICYmIHR5cGVvZiByZXN1bHQudGhlbiA9PT0gJ2Z1bmN0aW9uJykge1xuICAgICAgICAgICAgICAgIHJldHVybiByZXN1bHQ7XG4gICAgICAgICAgICB9XG4gICAgICAgIH0gY2F0Y2ggKF8pIHtcbiAgICAgICAgICAgIC8vIGZhbGwgdGhyb3VnaCB0byBjYWxsYmFjayB3cmFwcGluZ1xuICAgICAgICB9XG5cbiAgICAgICAgcmV0dXJuIG5ldyBQcm9taXNlKChyZXNvbHZlLCByZWplY3QpID0+IHtcbiAgICAgICAgICAgIG1ldGhvZC5hcHBseShjb250ZXh0LCBbXG4gICAgICAgICAgICAgICAgLi4uYXJncyxcbiAgICAgICAgICAgICAgICAoLi4uY2JBcmdzKSA9PiB7XG4gICAgICAgICAgICAgICAgICAgIGlmIChfYnJvd3Nlci5ydW50aW1lICYmIF9icm93c2VyLnJ1bnRpbWUubGFzdEVycm9yKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICByZWplY3QobmV3IEVycm9yKF9icm93c2VyLnJ1bnRpbWUubGFzdEVycm9yLm1lc3NhZ2UpKTtcbiAgICAgICAgICAgICAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICAgICAgICAgICAgICAgIHJlc29sdmUoY2JBcmdzLmxlbmd0aCA8PSAxID8gY2JBcmdzWzBdIDogY2JBcmdzKTtcbiAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgIH0sXG4gICAgICAgICAgICBdKTtcbiAgICAgICAgfSk7XG4gICAgfTtcbn1cblxuLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG4vLyBCdWlsZCB0aGUgdW5pZmllZCBgYXBpYCBvYmplY3Rcbi8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLVxuXG5jb25zdCBhcGkgPSB7fTtcblxuLy8gLS0tIHJ1bnRpbWUgLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG5hcGkucnVudGltZSA9IHtcbiAgICAvKipcbiAgICAgKiBzZW5kTWVzc2FnZSBcdTIwMTMgYWx3YXlzIHJldHVybnMgYSBQcm9taXNlLlxuICAgICAqL1xuICAgIHNlbmRNZXNzYWdlKC4uLmFyZ3MpIHtcbiAgICAgICAgaWYgKCFpc0Nocm9tZSkge1xuICAgICAgICAgICAgcmV0dXJuIF9icm93c2VyLnJ1bnRpbWUuc2VuZE1lc3NhZ2UoLi4uYXJncyk7XG4gICAgICAgIH1cbiAgICAgICAgcmV0dXJuIHByb21pc2lmeShfYnJvd3Nlci5ydW50aW1lLCBfYnJvd3Nlci5ydW50aW1lLnNlbmRNZXNzYWdlKSguLi5hcmdzKTtcbiAgICB9LFxuXG4gICAgLyoqXG4gICAgICogb25NZXNzYWdlIFx1MjAxMyB0aGluIHdyYXBwZXIgc28gY2FsbGVycyB1c2UgYSBjb25zaXN0ZW50IHJlZmVyZW5jZS5cbiAgICAgKiBUaGUgbGlzdGVuZXIgc2lnbmF0dXJlIGlzIChtZXNzYWdlLCBzZW5kZXIsIHNlbmRSZXNwb25zZSkuXG4gICAgICogT24gQ2hyb21lIHRoZSBsaXN0ZW5lciBjYW4gcmV0dXJuIGB0cnVlYCB0byBrZWVwIHRoZSBjaGFubmVsIG9wZW4sXG4gICAgICogb3IgcmV0dXJuIGEgUHJvbWlzZSAoTVYzKS4gIFNhZmFyaSAvIEZpcmVmb3ggZXhwZWN0IGEgUHJvbWlzZSByZXR1cm4uXG4gICAgICovXG4gICAgb25NZXNzYWdlOiBfYnJvd3Nlci5ydW50aW1lLm9uTWVzc2FnZSxcblxuICAgIC8qKlxuICAgICAqIGdldFVSTCBcdTIwMTMgc3luY2hyb25vdXMgb24gYWxsIGJyb3dzZXJzLlxuICAgICAqL1xuICAgIGdldFVSTChwYXRoKSB7XG4gICAgICAgIHJldHVybiBfYnJvd3Nlci5ydW50aW1lLmdldFVSTChwYXRoKTtcbiAgICB9LFxuXG4gICAgLyoqXG4gICAgICogb3Blbk9wdGlvbnNQYWdlXG4gICAgICovXG4gICAgb3Blbk9wdGlvbnNQYWdlKCkge1xuICAgICAgICBpZiAoIWlzQ2hyb21lKSB7XG4gICAgICAgICAgICByZXR1cm4gX2Jyb3dzZXIucnVudGltZS5vcGVuT3B0aW9uc1BhZ2UoKTtcbiAgICAgICAgfVxuICAgICAgICByZXR1cm4gcHJvbWlzaWZ5KF9icm93c2VyLnJ1bnRpbWUsIF9icm93c2VyLnJ1bnRpbWUub3Blbk9wdGlvbnNQYWdlKSgpO1xuICAgIH0sXG5cbiAgICAvKipcbiAgICAgKiBFeHBvc2UgdGhlIGlkIGZvciBjb252ZW5pZW5jZS5cbiAgICAgKi9cbiAgICBnZXQgaWQoKSB7XG4gICAgICAgIHJldHVybiBfYnJvd3Nlci5ydW50aW1lLmlkO1xuICAgIH0sXG59O1xuXG4vLyAtLS0gc3RvcmFnZS5sb2NhbCAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cbmFwaS5zdG9yYWdlID0ge1xuICAgIGxvY2FsOiB7XG4gICAgICAgIGdldCguLi5hcmdzKSB7XG4gICAgICAgICAgICBpZiAoIWlzQ2hyb21lKSB7XG4gICAgICAgICAgICAgICAgcmV0dXJuIF9icm93c2VyLnN0b3JhZ2UubG9jYWwuZ2V0KC4uLmFyZ3MpO1xuICAgICAgICAgICAgfVxuICAgICAgICAgICAgcmV0dXJuIHByb21pc2lmeShfYnJvd3Nlci5zdG9yYWdlLmxvY2FsLCBfYnJvd3Nlci5zdG9yYWdlLmxvY2FsLmdldCkoLi4uYXJncyk7XG4gICAgICAgIH0sXG4gICAgICAgIHNldCguLi5hcmdzKSB7XG4gICAgICAgICAgICBpZiAoIWlzQ2hyb21lKSB7XG4gICAgICAgICAgICAgICAgcmV0dXJuIF9icm93c2VyLnN0b3JhZ2UubG9jYWwuc2V0KC4uLmFyZ3MpO1xuICAgICAgICAgICAgfVxuICAgICAgICAgICAgcmV0dXJuIHByb21pc2lmeShfYnJvd3Nlci5zdG9yYWdlLmxvY2FsLCBfYnJvd3Nlci5zdG9yYWdlLmxvY2FsLnNldCkoLi4uYXJncyk7XG4gICAgICAgIH0sXG4gICAgICAgIGNsZWFyKC4uLmFyZ3MpIHtcbiAgICAgICAgICAgIGlmICghaXNDaHJvbWUpIHtcbiAgICAgICAgICAgICAgICByZXR1cm4gX2Jyb3dzZXIuc3RvcmFnZS5sb2NhbC5jbGVhciguLi5hcmdzKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICAgIHJldHVybiBwcm9taXNpZnkoX2Jyb3dzZXIuc3RvcmFnZS5sb2NhbCwgX2Jyb3dzZXIuc3RvcmFnZS5sb2NhbC5jbGVhcikoLi4uYXJncyk7XG4gICAgICAgIH0sXG4gICAgICAgIHJlbW92ZSguLi5hcmdzKSB7XG4gICAgICAgICAgICBpZiAoIWlzQ2hyb21lKSB7XG4gICAgICAgICAgICAgICAgcmV0dXJuIF9icm93c2VyLnN0b3JhZ2UubG9jYWwucmVtb3ZlKC4uLmFyZ3MpO1xuICAgICAgICAgICAgfVxuICAgICAgICAgICAgcmV0dXJuIHByb21pc2lmeShfYnJvd3Nlci5zdG9yYWdlLmxvY2FsLCBfYnJvd3Nlci5zdG9yYWdlLmxvY2FsLnJlbW92ZSkoLi4uYXJncyk7XG4gICAgICAgIH0sXG4gICAgfSxcblxuICAgIC8vIC0tLSBzdG9yYWdlLnN5bmMgLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLVxuICAgIC8vIE51bGwgd2hlbiB0aGUgYnJvd3NlciBkb2Vzbid0IHN1cHBvcnQgc3luYyAob2xkZXIgU2FmYXJpLCBldGMuKVxuICAgIHN5bmM6IF9icm93c2VyLnN0b3JhZ2U/LnN5bmMgPyB7XG4gICAgICAgIGdldCguLi5hcmdzKSB7XG4gICAgICAgICAgICBpZiAoIWlzQ2hyb21lKSB7XG4gICAgICAgICAgICAgICAgcmV0dXJuIF9icm93c2VyLnN0b3JhZ2Uuc3luYy5nZXQoLi4uYXJncyk7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgICByZXR1cm4gcHJvbWlzaWZ5KF9icm93c2VyLnN0b3JhZ2Uuc3luYywgX2Jyb3dzZXIuc3RvcmFnZS5zeW5jLmdldCkoLi4uYXJncyk7XG4gICAgICAgIH0sXG4gICAgICAgIHNldCguLi5hcmdzKSB7XG4gICAgICAgICAgICBpZiAoIWlzQ2hyb21lKSB7XG4gICAgICAgICAgICAgICAgcmV0dXJuIF9icm93c2VyLnN0b3JhZ2Uuc3luYy5zZXQoLi4uYXJncyk7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgICByZXR1cm4gcHJvbWlzaWZ5KF9icm93c2VyLnN0b3JhZ2Uuc3luYywgX2Jyb3dzZXIuc3RvcmFnZS5zeW5jLnNldCkoLi4uYXJncyk7XG4gICAgICAgIH0sXG4gICAgICAgIHJlbW92ZSguLi5hcmdzKSB7XG4gICAgICAgICAgICBpZiAoIWlzQ2hyb21lKSB7XG4gICAgICAgICAgICAgICAgcmV0dXJuIF9icm93c2VyLnN0b3JhZ2Uuc3luYy5yZW1vdmUoLi4uYXJncyk7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgICByZXR1cm4gcHJvbWlzaWZ5KF9icm93c2VyLnN0b3JhZ2Uuc3luYywgX2Jyb3dzZXIuc3RvcmFnZS5zeW5jLnJlbW92ZSkoLi4uYXJncyk7XG4gICAgICAgIH0sXG4gICAgICAgIGNsZWFyKC4uLmFyZ3MpIHtcbiAgICAgICAgICAgIGlmICghaXNDaHJvbWUpIHtcbiAgICAgICAgICAgICAgICByZXR1cm4gX2Jyb3dzZXIuc3RvcmFnZS5zeW5jLmNsZWFyKC4uLmFyZ3MpO1xuICAgICAgICAgICAgfVxuICAgICAgICAgICAgcmV0dXJuIHByb21pc2lmeShfYnJvd3Nlci5zdG9yYWdlLnN5bmMsIF9icm93c2VyLnN0b3JhZ2Uuc3luYy5jbGVhcikoLi4uYXJncyk7XG4gICAgICAgIH0sXG4gICAgICAgIGdldEJ5dGVzSW5Vc2UoLi4uYXJncykge1xuICAgICAgICAgICAgaWYgKCFfYnJvd3Nlci5zdG9yYWdlLnN5bmMuZ2V0Qnl0ZXNJblVzZSkge1xuICAgICAgICAgICAgICAgIC8vIFNhZmFyaSBkb2Vzbid0IHN1cHBvcnQgZ2V0Qnl0ZXNJblVzZSBcdTIwMTQgcmV0dXJuIDBcbiAgICAgICAgICAgICAgICByZXR1cm4gUHJvbWlzZS5yZXNvbHZlKDApO1xuICAgICAgICAgICAgfVxuICAgICAgICAgICAgaWYgKCFpc0Nocm9tZSkge1xuICAgICAgICAgICAgICAgIHJldHVybiBfYnJvd3Nlci5zdG9yYWdlLnN5bmMuZ2V0Qnl0ZXNJblVzZSguLi5hcmdzKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICAgIHJldHVybiBwcm9taXNpZnkoX2Jyb3dzZXIuc3RvcmFnZS5zeW5jLCBfYnJvd3Nlci5zdG9yYWdlLnN5bmMuZ2V0Qnl0ZXNJblVzZSkoLi4uYXJncyk7XG4gICAgICAgIH0sXG4gICAgfSA6IG51bGwsXG5cbiAgICAvLyAtLS0gc3RvcmFnZS5vbkNoYW5nZWQgLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cbiAgICBvbkNoYW5nZWQ6IF9icm93c2VyLnN0b3JhZ2U/Lm9uQ2hhbmdlZCB8fCBudWxsLFxufTtcblxuLy8gLS0tIHRhYnMgLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG5hcGkudGFicyA9IHtcbiAgICBjcmVhdGUoLi4uYXJncykge1xuICAgICAgICBpZiAoIWlzQ2hyb21lKSB7XG4gICAgICAgICAgICByZXR1cm4gX2Jyb3dzZXIudGFicy5jcmVhdGUoLi4uYXJncyk7XG4gICAgICAgIH1cbiAgICAgICAgcmV0dXJuIHByb21pc2lmeShfYnJvd3Nlci50YWJzLCBfYnJvd3Nlci50YWJzLmNyZWF0ZSkoLi4uYXJncyk7XG4gICAgfSxcbiAgICBxdWVyeSguLi5hcmdzKSB7XG4gICAgICAgIGlmICghaXNDaHJvbWUpIHtcbiAgICAgICAgICAgIHJldHVybiBfYnJvd3Nlci50YWJzLnF1ZXJ5KC4uLmFyZ3MpO1xuICAgICAgICB9XG4gICAgICAgIHJldHVybiBwcm9taXNpZnkoX2Jyb3dzZXIudGFicywgX2Jyb3dzZXIudGFicy5xdWVyeSkoLi4uYXJncyk7XG4gICAgfSxcbiAgICByZW1vdmUoLi4uYXJncykge1xuICAgICAgICBpZiAoIWlzQ2hyb21lKSB7XG4gICAgICAgICAgICByZXR1cm4gX2Jyb3dzZXIudGFicy5yZW1vdmUoLi4uYXJncyk7XG4gICAgICAgIH1cbiAgICAgICAgcmV0dXJuIHByb21pc2lmeShfYnJvd3Nlci50YWJzLCBfYnJvd3Nlci50YWJzLnJlbW92ZSkoLi4uYXJncyk7XG4gICAgfSxcbiAgICB1cGRhdGUoLi4uYXJncykge1xuICAgICAgICBpZiAoIWlzQ2hyb21lKSB7XG4gICAgICAgICAgICByZXR1cm4gX2Jyb3dzZXIudGFicy51cGRhdGUoLi4uYXJncyk7XG4gICAgICAgIH1cbiAgICAgICAgcmV0dXJuIHByb21pc2lmeShfYnJvd3Nlci50YWJzLCBfYnJvd3Nlci50YWJzLnVwZGF0ZSkoLi4uYXJncyk7XG4gICAgfSxcbiAgICBnZXQoLi4uYXJncykge1xuICAgICAgICBpZiAoIWlzQ2hyb21lKSB7XG4gICAgICAgICAgICByZXR1cm4gX2Jyb3dzZXIudGFicy5nZXQoLi4uYXJncyk7XG4gICAgICAgIH1cbiAgICAgICAgcmV0dXJuIHByb21pc2lmeShfYnJvd3Nlci50YWJzLCBfYnJvd3Nlci50YWJzLmdldCkoLi4uYXJncyk7XG4gICAgfSxcbiAgICBnZXRDdXJyZW50KC4uLmFyZ3MpIHtcbiAgICAgICAgaWYgKCFpc0Nocm9tZSkge1xuICAgICAgICAgICAgcmV0dXJuIF9icm93c2VyLnRhYnMuZ2V0Q3VycmVudCguLi5hcmdzKTtcbiAgICAgICAgfVxuICAgICAgICByZXR1cm4gcHJvbWlzaWZ5KF9icm93c2VyLnRhYnMsIF9icm93c2VyLnRhYnMuZ2V0Q3VycmVudCkoLi4uYXJncyk7XG4gICAgfSxcbiAgICBzZW5kTWVzc2FnZSguLi5hcmdzKSB7XG4gICAgICAgIGlmICghaXNDaHJvbWUpIHtcbiAgICAgICAgICAgIHJldHVybiBfYnJvd3Nlci50YWJzLnNlbmRNZXNzYWdlKC4uLmFyZ3MpO1xuICAgICAgICB9XG4gICAgICAgIHJldHVybiBwcm9taXNpZnkoX2Jyb3dzZXIudGFicywgX2Jyb3dzZXIudGFicy5zZW5kTWVzc2FnZSkoLi4uYXJncyk7XG4gICAgfSxcbn07XG5cbi8vIC0tLSBhbGFybXMgLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLVxuLy8gY2hyb21lLmFsYXJtcyBzdXJ2aXZlcyBNVjMgc2VydmljZS13b3JrZXIgZXZpY3Rpb247IHNldFRpbWVvdXQgZG9lcyBub3QuXG5hcGkuYWxhcm1zID0gX2Jyb3dzZXIuYWxhcm1zID8ge1xuICAgIGNyZWF0ZSguLi5hcmdzKSB7XG4gICAgICAgIC8vIGFsYXJtcy5jcmVhdGUgaXMgc3luY2hyb25vdXMgb24gQ2hyb21lLCByZXR1cm5zIFByb21pc2Ugb24gRmlyZWZveC9TYWZhcmlcbiAgICAgICAgY29uc3QgcmVzdWx0ID0gX2Jyb3dzZXIuYWxhcm1zLmNyZWF0ZSguLi5hcmdzKTtcbiAgICAgICAgcmV0dXJuIHJlc3VsdCAmJiB0eXBlb2YgcmVzdWx0LnRoZW4gPT09ICdmdW5jdGlvbicgPyByZXN1bHQgOiBQcm9taXNlLnJlc29sdmUoKTtcbiAgICB9LFxuICAgIGNsZWFyKC4uLmFyZ3MpIHtcbiAgICAgICAgaWYgKCFpc0Nocm9tZSkge1xuICAgICAgICAgICAgcmV0dXJuIF9icm93c2VyLmFsYXJtcy5jbGVhciguLi5hcmdzKTtcbiAgICAgICAgfVxuICAgICAgICByZXR1cm4gcHJvbWlzaWZ5KF9icm93c2VyLmFsYXJtcywgX2Jyb3dzZXIuYWxhcm1zLmNsZWFyKSguLi5hcmdzKTtcbiAgICB9LFxuICAgIG9uQWxhcm06IF9icm93c2VyLmFsYXJtcy5vbkFsYXJtLFxufSA6IG51bGw7XG5cbmV4cG9ydCB7IGFwaSwgaXNDaHJvbWUgfTtcbiIsICIvKipcbiAqIFN5bmMgTWFuYWdlciBcdTIwMTQgUGxhdGZvcm0gc3luYyB2aWEgc3RvcmFnZS5zeW5jIChDaHJvbWUgXHUyMTkyIEdvb2dsZSwgU2FmYXJpIFx1MjE5MiBpQ2xvdWQpXG4gKlxuICogQXJjaGl0ZWN0dXJlOlxuICogICBXcml0ZTogYXBwIFx1MjE5MiBzdG9yYWdlLmxvY2FsIFx1MjE5MiBzY2hlZHVsZVN5bmNQdXNoKCkgXHUyMTkyIHN0b3JhZ2Uuc3luY1xuICogICBSZWFkOiAgcHVsbEZyb21TeW5jKCkgb24gc3RhcnR1cCBcdTIxOTIgbWVyZ2UgaW50byBzdG9yYWdlLmxvY2FsXG4gKiAgIExpc3Rlbjogc3RvcmFnZS5vbkNoYW5nZWQoXCJzeW5jXCIpIFx1MjE5MiBtZXJnZSByZW1vdGUgY2hhbmdlcyBpbnRvIGxvY2FsXG4gKlxuICogc3RvcmFnZS5sb2NhbCByZW1haW5zIHRoZSBzb3VyY2Ugb2YgdHJ1dGguIHN0b3JhZ2Uuc3luYyBpcyBhIGJlc3QtZWZmb3J0IG1pcnJvci5cbiAqL1xuXG5pbXBvcnQgeyBhcGkgfSBmcm9tICcuL2Jyb3dzZXItcG9seWZpbGwnO1xuXG4vLyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cbi8vIENvbnN0YW50c1xuLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG5jb25zdCBTWU5DX1FVT1RBID0gMTAyXzQwMDsgICAgICAgLy8gMTAwIEtCIHRvdGFsXG5jb25zdCBNQVhfSVRFTSA9IDhfMTkyOyAgICAgICAgICAgLy8gOCBLQiBwZXIgaXRlbVxuY29uc3QgTUFYX0lURU1TID0gNTEyO1xuY29uc3QgQ0hVTktfUFJFRklYID0gJ19jaHVuazonO1xuY29uc3QgU1lOQ19NRVRBX0tFWSA9ICdfc3luY19tZXRhJztcbmNvbnN0IExPQ0FMX0VOQUJMRURfS0VZID0gJ3BsYXRmb3JtU3luY0VuYWJsZWQnO1xuXG4vLyBLZXlzIHRoYXQgc2hvdWxkIG5ldmVyIGJlIHN5bmNlZFxuY29uc3QgRVhDTFVERURfS0VZUyA9IFtcbiAgICAnYnVua2VyU2Vzc2lvbnMnLFxuICAgICdpZ25vcmVJbnN0YWxsSG9vaycsXG4gICAgJ3Bhc3N3b3JkSGFzaCcsXG4gICAgJ3Bhc3N3b3JkU2FsdCcsXG5dO1xuXG4vLyBQcmlvcml0eSB0aWVycyBmb3IgYnVkZ2V0IGFsbG9jYXRpb25cbmNvbnN0IFBSSU9SSVRZID0ge1xuICAgIFAxX1BST0ZJTEVTOiAxLFxuICAgIFAyX1NFVFRJTkdTOiAyLFxuICAgIFAzX0FQSUtFWVM6IDMsXG4gICAgUDRfVkFVTFQ6IDQsXG59O1xuXG5jb25zdCBzdG9yYWdlID0gYXBpLnN0b3JhZ2UubG9jYWw7XG5sZXQgcHVzaFRpbWVyID0gbnVsbDtcblxuLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG4vLyBDaHVua2luZyBoZWxwZXJzXG4vLyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cblxuLyoqXG4gKiBTcGxpdCBhIEpTT04tc2VyaWFsaXNlZCB2YWx1ZSBpbnRvIDw9OEtCIGNodW5rcy5cbiAqIFJldHVybnMgYW4gYXJyYXkgb2YgeyBrZXksIHZhbHVlIH0gcGFpcnMgcmVhZHkgZm9yIHN0b3JhZ2Uuc3luYy5zZXQoKS5cbiAqL1xuZnVuY3Rpb24gY2h1bmtWYWx1ZShrZXksIGpzb25TdHJpbmcpIHtcbiAgICBjb25zdCBjaHVua3MgPSBbXTtcbiAgICBmb3IgKGxldCBpID0gMDsgaSA8IGpzb25TdHJpbmcubGVuZ3RoOyBpICs9IE1BWF9JVEVNIC0gMTAwKSB7XG4gICAgICAgIC8vIFJlc2VydmUgfjEwMCBieXRlcyBmb3IgdGhlIGtleSBvdmVyaGVhZCBpbiB0aGUgc3RvcmVkIGl0ZW1cbiAgICAgICAgY2h1bmtzLnB1c2goanNvblN0cmluZy5zbGljZShpLCBpICsgTUFYX0lURU0gLSAxMDApKTtcbiAgICB9XG4gICAgaWYgKGNodW5rcy5sZW5ndGggPT09IDEpIHtcbiAgICAgICAgLy8gRml0cyBpbiBhIHNpbmdsZSBpdGVtIFx1MjAxNCBzdG9yZSBkaXJlY3RseVxuICAgICAgICByZXR1cm4gW3sga2V5LCB2YWx1ZToganNvblN0cmluZyB9XTtcbiAgICB9XG4gICAgLy8gTXVsdGlwbGUgY2h1bmtzXG4gICAgY29uc3QgZW50cmllcyA9IFtdO1xuICAgIGZvciAobGV0IGkgPSAwOyBpIDwgY2h1bmtzLmxlbmd0aDsgaSsrKSB7XG4gICAgICAgIGVudHJpZXMucHVzaCh7IGtleTogYCR7Q0hVTktfUFJFRklYfSR7a2V5fToke2l9YCwgdmFsdWU6IGNodW5rc1tpXSB9KTtcbiAgICB9XG4gICAgLy8gU3RvcmUgYSBtZXRhZGF0YSBlbnRyeSBzbyB3ZSBrbm93IGhvdyBtYW55IGNodW5rcyB0aGVyZSBhcmVcbiAgICBlbnRyaWVzLnB1c2goeyBrZXksIHZhbHVlOiBKU09OLnN0cmluZ2lmeSh7IF9fY2h1bmtlZDogdHJ1ZSwgY291bnQ6IGNodW5rcy5sZW5ndGggfSkgfSk7XG4gICAgcmV0dXJuIGVudHJpZXM7XG59XG5cbi8qKlxuICogUmVhc3NlbWJsZSBjaHVua2VkIGRhdGEgZnJvbSBhIHN5bmMgZGF0YSBvYmplY3QuXG4gKiBSZXR1cm5zIHRoZSBwYXJzZWQgSlNPTiB2YWx1ZSwgb3IgbnVsbCBvbiBlcnJvci5cbiAqL1xuZnVuY3Rpb24gcmVhc3NlbWJsZUZyb21TeW5jRGF0YShrZXksIHN5bmNEYXRhKSB7XG4gICAgdHJ5IHtcbiAgICAgICAgY29uc3QgbWV0YSA9IHR5cGVvZiBzeW5jRGF0YVtrZXldID09PSAnc3RyaW5nJyA/IEpTT04ucGFyc2Uoc3luY0RhdGFba2V5XSkgOiBzeW5jRGF0YVtrZXldO1xuICAgICAgICBpZiAoIW1ldGEgfHwgIW1ldGEuX19jaHVua2VkKSB7XG4gICAgICAgICAgICAvLyBOb3QgY2h1bmtlZCBcdTIwMTQgcGFyc2UgZGlyZWN0bHlcbiAgICAgICAgICAgIHJldHVybiB0eXBlb2Ygc3luY0RhdGFba2V5XSA9PT0gJ3N0cmluZycgPyBKU09OLnBhcnNlKHN5bmNEYXRhW2tleV0pIDogc3luY0RhdGFba2V5XTtcbiAgICAgICAgfVxuICAgICAgICBsZXQgY29tYmluZWQgPSAnJztcbiAgICAgICAgZm9yIChsZXQgaSA9IDA7IGkgPCBtZXRhLmNvdW50OyBpKyspIHtcbiAgICAgICAgICAgIGNvbnN0IGNodW5rS2V5ID0gYCR7Q0hVTktfUFJFRklYfSR7a2V5fToke2l9YDtcbiAgICAgICAgICAgIGlmIChzeW5jRGF0YVtjaHVua0tleV0gPT0gbnVsbCkgcmV0dXJuIG51bGw7XG4gICAgICAgICAgICBjb21iaW5lZCArPSBzeW5jRGF0YVtjaHVua0tleV07XG4gICAgICAgIH1cbiAgICAgICAgcmV0dXJuIEpTT04ucGFyc2UoY29tYmluZWQpO1xuICAgIH0gY2F0Y2gge1xuICAgICAgICByZXR1cm4gbnVsbDtcbiAgICB9XG59XG5cbi8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLVxuLy8gQnVpbGQgc3luYyBwYXlsb2FkXG4vLyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cblxuLyoqXG4gKiBSZWFkIGFsbCBsb2NhbCBkYXRhIGFuZCBidWlsZCBhIHByaW9yaXRpc2VkIGxpc3Qgb2YgZW50cmllcyB0byBzeW5jLlxuICogUmV0dXJucyB7IGVudHJpZXM6IFt7IGtleSwganNvblN0cmluZywgcHJpb3JpdHksIHNpemUgfV0sIHRvdGFsU2l6ZSB9XG4gKi9cbmFzeW5jIGZ1bmN0aW9uIGJ1aWxkU3luY1BheWxvYWQoKSB7XG4gICAgY29uc3QgYWxsID0gYXdhaXQgc3RvcmFnZS5nZXQobnVsbCk7XG4gICAgY29uc3QgZW50cmllcyA9IFtdO1xuXG4gICAgLy8gUDE6IFByb2ZpbGVzIChzdHJpcCBgaG9zdHNgIHRvIHNhdmUgc3BhY2UpICsgcHJvZmlsZUluZGV4XG4gICAgaWYgKGFsbC5wcm9maWxlcykge1xuICAgICAgICBjb25zdCBjbGVhblByb2ZpbGVzID0gYWxsLnByb2ZpbGVzLm1hcChwID0+IHtcbiAgICAgICAgICAgIGNvbnN0IHsgaG9zdHMsIC4uLnJlc3QgfSA9IHA7XG4gICAgICAgICAgICByZXR1cm4gcmVzdDtcbiAgICAgICAgfSk7XG4gICAgICAgIGNvbnN0IGpzb24gPSBKU09OLnN0cmluZ2lmeShjbGVhblByb2ZpbGVzKTtcbiAgICAgICAgZW50cmllcy5wdXNoKHsga2V5OiAncHJvZmlsZXMnLCBqc29uU3RyaW5nOiBqc29uLCBwcmlvcml0eTogUFJJT1JJVFkuUDFfUFJPRklMRVMsIHNpemU6IGpzb24ubGVuZ3RoIH0pO1xuICAgIH1cbiAgICBpZiAoYWxsLnByb2ZpbGVJbmRleCAhPSBudWxsKSB7XG4gICAgICAgIGNvbnN0IGpzb24gPSBKU09OLnN0cmluZ2lmeShhbGwucHJvZmlsZUluZGV4KTtcbiAgICAgICAgZW50cmllcy5wdXNoKHsga2V5OiAncHJvZmlsZUluZGV4JywganNvblN0cmluZzoganNvbiwgcHJpb3JpdHk6IFBSSU9SSVRZLlAxX1BST0ZJTEVTLCBzaXplOiBqc29uLmxlbmd0aCB9KTtcbiAgICB9XG4gICAgLy8gTk9URTogYGlzRW5jcnlwdGVkYCBpcyBpbnRlbnRpb25hbGx5IE5PVCBzeW5jZWQuIFRoZSBwYXNzd29yZCB2ZXJpZmllclxuICAgIC8vIChwYXNzd29yZEhhc2gvcGFzc3dvcmRTYWx0KSBpcyBleGNsdWRlZCBmcm9tIHN5bmMgZm9yIHNlY3VyaXR5LCBzbyBhIGRldmljZVxuICAgIC8vIHRoYXQgcmVjZWl2ZWQgaXNFbmNyeXB0ZWQ9dHJ1ZSB3aXRoIG5vIGhhc2ggd291bGQgYmUgcGVybWFuZW50bHkgbG9ja2VkIG91dFxuICAgIC8vIChjaGVja1Bhc3N3b3JkIGFsd2F5cyBmYWlscykuIEVuY3J5cHRpb24gc3RhdGUgaXMgc3RyaWN0bHkgZGV2aWNlLWxvY2FsLlxuXG4gICAgLy8gUDI6IFNldHRpbmdzXG4gICAgY29uc3Qgc2V0dGluZ3NLZXlzID0gWydhdXRvTG9ja01pbnV0ZXMnLCAndmVyc2lvbicsICdwcm90b2NvbF9oYW5kbGVyJywgTE9DQUxfRU5BQkxFRF9LRVldO1xuICAgIGZvciAoY29uc3QgayBvZiBzZXR0aW5nc0tleXMpIHtcbiAgICAgICAgaWYgKGFsbFtrXSAhPSBudWxsKSB7XG4gICAgICAgICAgICBjb25zdCBqc29uID0gSlNPTi5zdHJpbmdpZnkoYWxsW2tdKTtcbiAgICAgICAgICAgIGVudHJpZXMucHVzaCh7IGtleTogaywganNvblN0cmluZzoganNvbiwgcHJpb3JpdHk6IFBSSU9SSVRZLlAyX1NFVFRJTkdTLCBzaXplOiBqc29uLmxlbmd0aCB9KTtcbiAgICAgICAgfVxuICAgIH1cbiAgICAvLyBGZWF0dXJlIGZsYWdzXG4gICAgZm9yIChjb25zdCBrIG9mIE9iamVjdC5rZXlzKGFsbCkpIHtcbiAgICAgICAgaWYgKGsuc3RhcnRzV2l0aCgnZmVhdHVyZTonKSkge1xuICAgICAgICAgICAgY29uc3QganNvbiA9IEpTT04uc3RyaW5naWZ5KGFsbFtrXSk7XG4gICAgICAgICAgICBlbnRyaWVzLnB1c2goeyBrZXk6IGssIGpzb25TdHJpbmc6IGpzb24sIHByaW9yaXR5OiBQUklPUklUWS5QMl9TRVRUSU5HUywgc2l6ZToganNvbi5sZW5ndGggfSk7XG4gICAgICAgIH1cbiAgICB9XG5cbiAgICAvLyBQMzogQVBJIGtleSB2YXVsdFxuICAgIGlmIChhbGwuYXBpS2V5VmF1bHQpIHtcbiAgICAgICAgY29uc3QganNvbiA9IEpTT04uc3RyaW5naWZ5KGFsbC5hcGlLZXlWYXVsdCk7XG4gICAgICAgIGVudHJpZXMucHVzaCh7IGtleTogJ2FwaUtleVZhdWx0JywganNvblN0cmluZzoganNvbiwgcHJpb3JpdHk6IFBSSU9SSVRZLlAzX0FQSUtFWVMsIHNpemU6IGpzb24ubGVuZ3RoIH0pO1xuICAgIH1cblxuICAgIC8vIFA0OiBWYXVsdCBkb2NzIChpbmRpdmlkdWFsbHksIG5ld2VzdCBmaXJzdClcbiAgICBpZiAoYWxsLnZhdWx0RG9jcyAmJiB0eXBlb2YgYWxsLnZhdWx0RG9jcyA9PT0gJ29iamVjdCcpIHtcbiAgICAgICAgY29uc3QgZG9jcyA9IE9iamVjdC52YWx1ZXMoYWxsLnZhdWx0RG9jcykuc29ydCgoYSwgYikgPT4gKGIudXBkYXRlZEF0IHx8IDApIC0gKGEudXBkYXRlZEF0IHx8IDApKTtcbiAgICAgICAgZm9yIChjb25zdCBkb2Mgb2YgZG9jcykge1xuICAgICAgICAgICAgY29uc3QgZG9jS2V5ID0gYHZhdWx0RG9jOiR7ZG9jLnBhdGh9YDtcbiAgICAgICAgICAgIGNvbnN0IGpzb24gPSBKU09OLnN0cmluZ2lmeShkb2MpO1xuICAgICAgICAgICAgZW50cmllcy5wdXNoKHsga2V5OiBkb2NLZXksIGpzb25TdHJpbmc6IGpzb24sIHByaW9yaXR5OiBQUklPUklUWS5QNF9WQVVMVCwgc2l6ZToganNvbi5sZW5ndGggfSk7XG4gICAgICAgIH1cbiAgICB9XG5cbiAgICByZXR1cm4gZW50cmllcztcbn1cblxuLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG4vLyBQdXNoIHRvIHN5bmNcbi8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLVxuXG5hc3luYyBmdW5jdGlvbiBwdXNoVG9TeW5jKCkge1xuICAgIGlmICghYXBpLnN0b3JhZ2Uuc3luYykgcmV0dXJuO1xuXG4gICAgY29uc3QgZW5hYmxlZCA9IGF3YWl0IGlzU3luY0VuYWJsZWQoKTtcbiAgICBpZiAoIWVuYWJsZWQpIHJldHVybjtcblxuICAgIHRyeSB7XG4gICAgICAgIGNvbnN0IGVudHJpZXMgPSBhd2FpdCBidWlsZFN5bmNQYXlsb2FkKCk7XG5cbiAgICAgICAgLy8gU29ydCBieSBwcmlvcml0eSAoYXNjZW5kaW5nID0gbW9zdCBpbXBvcnRhbnQgZmlyc3QpXG4gICAgICAgIGVudHJpZXMuc29ydCgoYSwgYikgPT4gYS5wcmlvcml0eSAtIGIucHJpb3JpdHkpO1xuXG4gICAgICAgIC8vIEJ1aWxkIHRoZSBzeW5jIHBheWxvYWQgcmVzcGVjdGluZyBidWRnZXRcbiAgICAgICAgbGV0IHVzZWRCeXRlcyA9IDA7XG4gICAgICAgIGxldCB1c2VkSXRlbXMgPSAwO1xuICAgICAgICBjb25zdCBzeW5jUGF5bG9hZCA9IHt9O1xuICAgICAgICBjb25zdCBhbGxTeW5jS2V5cyA9IFtdO1xuICAgICAgICBsZXQgYnVkZ2V0RXhoYXVzdGVkID0gZmFsc2U7XG5cbiAgICAgICAgZm9yIChjb25zdCBlbnRyeSBvZiBlbnRyaWVzKSB7XG4gICAgICAgICAgICBpZiAoYnVkZ2V0RXhoYXVzdGVkKSBicmVhaztcblxuICAgICAgICAgICAgY29uc3QgY2h1bmtzID0gY2h1bmtWYWx1ZShlbnRyeS5rZXksIGVudHJ5Lmpzb25TdHJpbmcpO1xuICAgICAgICAgICAgbGV0IGVudHJ5U2l6ZSA9IDA7XG4gICAgICAgICAgICBmb3IgKGNvbnN0IGMgb2YgY2h1bmtzKSB7XG4gICAgICAgICAgICAgICAgZW50cnlTaXplICs9IGMua2V5Lmxlbmd0aCArICh0eXBlb2YgYy52YWx1ZSA9PT0gJ3N0cmluZycgPyBjLnZhbHVlLmxlbmd0aCA6IEpTT04uc3RyaW5naWZ5KGMudmFsdWUpLmxlbmd0aCk7XG4gICAgICAgICAgICB9XG5cbiAgICAgICAgICAgIGlmICh1c2VkQnl0ZXMgKyBlbnRyeVNpemUgPiBTWU5DX1FVT1RBIC0gNTAwIHx8IHVzZWRJdGVtcyArIGNodW5rcy5sZW5ndGggPiBNQVhfSVRFTVMgLSA1KSB7XG4gICAgICAgICAgICAgICAgaWYgKGVudHJ5LnByaW9yaXR5IDw9IFBSSU9SSVRZLlAzX0FQSUtFWVMpIHtcbiAgICAgICAgICAgICAgICAgICAgLy8gQ3JpdGljYWwgZGF0YSBcdTIwMTQgdHJ5IGFueXdheSwgbGV0IHRoZSBBUEkgdGhyb3cgaWYgdHJ1bHkgb3ZlclxuICAgICAgICAgICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgICAgICAgICAgIGNvbnNvbGUud2FybihgW1N5bmNNYW5hZ2VyXSBCdWRnZXQgZXhoYXVzdGVkIGF0IHByaW9yaXR5ICR7ZW50cnkucHJpb3JpdHl9LCBza2lwcGluZyByZW1haW5pbmcgZW50cmllc2ApO1xuICAgICAgICAgICAgICAgICAgICBidWRnZXRFeGhhdXN0ZWQgPSB0cnVlO1xuICAgICAgICAgICAgICAgICAgICBicmVhaztcbiAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICB9XG5cbiAgICAgICAgICAgIGZvciAoY29uc3QgYyBvZiBjaHVua3MpIHtcbiAgICAgICAgICAgICAgICBzeW5jUGF5bG9hZFtjLmtleV0gPSBjLnZhbHVlO1xuICAgICAgICAgICAgICAgIGFsbFN5bmNLZXlzLnB1c2goYy5rZXkpO1xuICAgICAgICAgICAgfVxuICAgICAgICAgICAgdXNlZEJ5dGVzICs9IGVudHJ5U2l6ZTtcbiAgICAgICAgICAgIHVzZWRJdGVtcyArPSBjaHVua3MubGVuZ3RoO1xuICAgICAgICB9XG5cbiAgICAgICAgLy8gQWRkIHN5bmMgbWV0YWRhdGFcbiAgICAgICAgY29uc3QgbWV0YSA9IHtcbiAgICAgICAgICAgIGxhc3RXcml0dGVuQXQ6IERhdGUubm93KCksXG4gICAgICAgICAgICBrZXlzOiBhbGxTeW5jS2V5cyxcbiAgICAgICAgfTtcbiAgICAgICAgc3luY1BheWxvYWRbU1lOQ19NRVRBX0tFWV0gPSBKU09OLnN0cmluZ2lmeShtZXRhKTtcblxuICAgICAgICAvLyBXcml0ZSB0byBzeW5jIHN0b3JhZ2VcbiAgICAgICAgYXdhaXQgYXBpLnN0b3JhZ2Uuc3luYy5zZXQoc3luY1BheWxvYWQpO1xuXG4gICAgICAgIC8vIENsZWFuIG9ycGhhbmVkIGNodW5rczogcmVhZCBleGlzdGluZyBzeW5jIGtleXMgYW5kIHJlbW92ZSBhbnkgbm90IGluIG91ciBwYXlsb2FkXG4gICAgICAgIHRyeSB7XG4gICAgICAgICAgICBjb25zdCBleGlzdGluZyA9IGF3YWl0IGFwaS5zdG9yYWdlLnN5bmMuZ2V0KG51bGwpO1xuICAgICAgICAgICAgY29uc3Qgb3JwaGFuS2V5cyA9IE9iamVjdC5rZXlzKGV4aXN0aW5nKS5maWx0ZXIoayA9PlxuICAgICAgICAgICAgICAgIGsgIT09IFNZTkNfTUVUQV9LRVkgJiYgIWFsbFN5bmNLZXlzLmluY2x1ZGVzKGspXG4gICAgICAgICAgICApO1xuICAgICAgICAgICAgaWYgKG9ycGhhbktleXMubGVuZ3RoID4gMCkge1xuICAgICAgICAgICAgICAgIGF3YWl0IGFwaS5zdG9yYWdlLnN5bmMucmVtb3ZlKG9ycGhhbktleXMpO1xuICAgICAgICAgICAgfVxuICAgICAgICB9IGNhdGNoIHtcbiAgICAgICAgICAgIC8vIE5vbi1jcml0aWNhbCBjbGVhbnVwXG4gICAgICAgIH1cblxuICAgICAgICBjb25zb2xlLmxvZyhgW1N5bmNNYW5hZ2VyXSBQdXNoZWQgJHthbGxTeW5jS2V5cy5sZW5ndGh9IGVudHJpZXMgKCR7dXNlZEJ5dGVzfSBieXRlcykgdG8gc3luYyBzdG9yYWdlYCk7XG4gICAgfSBjYXRjaCAoZSkge1xuICAgICAgICBjb25zb2xlLmVycm9yKCdbU3luY01hbmFnZXJdIHB1c2hUb1N5bmMgZXJyb3I6JywgZSk7XG4gICAgICAgIC8vIExvY2FsIHN0b3JhZ2UgaXMgdW5hZmZlY3RlZCBcdTIwMTQgZ3JhY2VmdWwgZGVncmFkYXRpb25cbiAgICB9XG59XG5cbi8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLVxuLy8gUHVsbCBmcm9tIHN5bmNcbi8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLVxuXG4vKipcbiAqIFJlYWQgYWxsIGRhdGEgZnJvbSBzeW5jIHN0b3JhZ2UgYW5kIHJldHVybiBhcyBhIHBsYWluIG9iamVjdCB3aXRoXG4gKiByZWFzc2VtYmxlZCBjaHVua2VkIHZhbHVlcy5cbiAqL1xuYXN5bmMgZnVuY3Rpb24gcHVsbEZyb21TeW5jKCkge1xuICAgIGlmICghYXBpLnN0b3JhZ2Uuc3luYykgcmV0dXJuIG51bGw7XG5cbiAgICB0cnkge1xuICAgICAgICBjb25zdCByYXcgPSBhd2FpdCBhcGkuc3RvcmFnZS5zeW5jLmdldChudWxsKTtcbiAgICAgICAgaWYgKCFyYXcgfHwgT2JqZWN0LmtleXMocmF3KS5sZW5ndGggPT09IDApIHJldHVybiBudWxsO1xuXG4gICAgICAgIGNvbnN0IG1ldGFTdHIgPSByYXdbU1lOQ19NRVRBX0tFWV07XG4gICAgICAgIGlmICghbWV0YVN0cikgcmV0dXJuIG51bGw7XG5cbiAgICAgICAgbGV0IG1ldGE7XG4gICAgICAgIHRyeSB7IG1ldGEgPSBKU09OLnBhcnNlKG1ldGFTdHIpOyB9IGNhdGNoIHsgcmV0dXJuIG51bGw7IH1cblxuICAgICAgICBjb25zdCByZXN1bHQgPSB7fTtcbiAgICAgICAgLy8gQ29sbGVjdCB0aGUgbm9uLWNodW5rLCBub24tbWV0YSBrZXlzXG4gICAgICAgIGNvbnN0IGRhdGFLZXlzID0gbWV0YS5rZXlzLmZpbHRlcihrID0+ICFrLnN0YXJ0c1dpdGgoQ0hVTktfUFJFRklYKSAmJiBrICE9PSBTWU5DX01FVEFfS0VZKTtcblxuICAgICAgICBmb3IgKGNvbnN0IGtleSBvZiBkYXRhS2V5cykge1xuICAgICAgICAgICAgY29uc3QgdmFsdWUgPSByZWFzc2VtYmxlRnJvbVN5bmNEYXRhKGtleSwgcmF3KTtcbiAgICAgICAgICAgIGlmICh2YWx1ZSAhPSBudWxsKSB7XG4gICAgICAgICAgICAgICAgcmVzdWx0W2tleV0gPSB2YWx1ZTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgfVxuXG4gICAgICAgIHJlc3VsdC5fc3luY01ldGEgPSBtZXRhO1xuICAgICAgICByZXR1cm4gcmVzdWx0O1xuICAgIH0gY2F0Y2ggKGUpIHtcbiAgICAgICAgY29uc29sZS5lcnJvcignW1N5bmNNYW5hZ2VyXSBwdWxsRnJvbVN5bmMgZXJyb3I6JywgZSk7XG4gICAgICAgIHJldHVybiBudWxsO1xuICAgIH1cbn1cblxuLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG4vLyBNZXJnZSBsb2dpY1xuLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG5cbi8qKlxuICogTWVyZ2Ugc3luYyBkYXRhIGludG8gbG9jYWwgc3RvcmFnZSB3aXRoIGNvbmZsaWN0IHJlc29sdXRpb24uXG4gKi9cbi8qKlxuICogQ29tcGFyZSB0d28gZG90dGVkIHZlcnNpb24gc3RyaW5ncyBudW1lcmljYWxseSwgY29tcG9uZW50IGJ5IGNvbXBvbmVudC5cbiAqIFJldHVybnMgLTEgaWYgYSA8IGIsIDAgaWYgZXF1YWwsIDEgaWYgYSA+IGIuIE5vbi1udW1lcmljIC8gbWlzc2luZ1xuICogY29tcG9uZW50cyBhcmUgdHJlYXRlZCBhcyAwIChlLmcuICcxLjYnID09PSAnMS42LjAnKS5cbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGNvbXBhcmVTZW12ZXIoYSwgYikge1xuICAgIGNvbnN0IHBhID0gU3RyaW5nKGEpLnNwbGl0KCcuJyk7XG4gICAgY29uc3QgcGIgPSBTdHJpbmcoYikuc3BsaXQoJy4nKTtcbiAgICBjb25zdCBsZW4gPSBNYXRoLm1heChwYS5sZW5ndGgsIHBiLmxlbmd0aCk7XG4gICAgZm9yIChsZXQgaSA9IDA7IGkgPCBsZW47IGkrKykge1xuICAgICAgICBjb25zdCBuYSA9IHBhcnNlSW50KHBhW2ldLCAxMCkgfHwgMDtcbiAgICAgICAgY29uc3QgbmIgPSBwYXJzZUludChwYltpXSwgMTApIHx8IDA7XG4gICAgICAgIGlmIChuYSA+IG5iKSByZXR1cm4gMTtcbiAgICAgICAgaWYgKG5hIDwgbmIpIHJldHVybiAtMTtcbiAgICB9XG4gICAgcmV0dXJuIDA7XG59XG5cbmFzeW5jIGZ1bmN0aW9uIG1lcmdlSW50b0xvY2FsKHN5bmNEYXRhKSB7XG4gICAgaWYgKCFzeW5jRGF0YSkgcmV0dXJuO1xuXG4gICAgY29uc3QgbG9jYWwgPSBhd2FpdCBzdG9yYWdlLmdldChudWxsKTtcbiAgICBjb25zdCB7IHVwZGF0ZXMsIGNoYW5nZWQgfSA9IGNvbXB1dGVNZXJnZVVwZGF0ZXMobG9jYWwsIHN5bmNEYXRhKTtcblxuICAgIGlmIChjaGFuZ2VkKSB7XG4gICAgICAgIGF3YWl0IHN0b3JhZ2Uuc2V0KHVwZGF0ZXMpO1xuICAgICAgICBjb25zb2xlLmxvZygnW1N5bmNNYW5hZ2VyXSBNZXJnZWQgc3luYyBkYXRhIGludG8gbG9jYWw6JywgT2JqZWN0LmtleXModXBkYXRlcykpO1xuICAgIH1cbn1cblxuLyoqXG4gKiBQdXJlIG1lcmdlOiBnaXZlbiB0aGUgY3VycmVudCBsb2NhbCBzdGF0ZSBhbmQgYW4gaW5jb21pbmcgc3luYyBwYXlsb2FkLFxuICogY29tcHV0ZSB0aGUgc3RvcmFnZSB1cGRhdGVzIHRvIGFwcGx5LiBObyBJL08gXHUyMDE0IGV4cG9ydGVkIHNvIHRoZSBtZXJnZSBydWxlc1xuICogKGZyZXNoLWluc3RhbGwgZGV0ZWN0aW9uLCBwdWJrZXkta2V5ZWQgcHJvZmlsZSBtYXRjaGluZywgZW5jcnlwdGlvbi1zdGF0ZVxuICogZXhjbHVzaW9uKSBjYW4gYmUgcmVncmVzc2lvbi10ZXN0ZWQgZGlyZWN0bHkuXG4gKlxuICogQHJldHVybnMge3sgdXBkYXRlczogT2JqZWN0LCBjaGFuZ2VkOiBib29sZWFuIH19XG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBjb21wdXRlTWVyZ2VVcGRhdGVzKGxvY2FsLCBzeW5jRGF0YSkge1xuICAgIGNvbnN0IHVwZGF0ZXMgPSB7fTtcbiAgICBsZXQgY2hhbmdlZCA9IGZhbHNlO1xuICAgIGlmICghc3luY0RhdGEpIHJldHVybiB7IHVwZGF0ZXMsIGNoYW5nZWQgfTtcblxuICAgIC8vIERldGVjdCBmcmVzaCBpbnN0YWxsOiBubyBwcm9maWxlcywgb3Igb25seSBwcm9maWxlKHMpIHRoYXQgY2Fycnkgbm9cbiAgICAvLyBpZGVudGl0eSBhdCBhbGwgKG5vIHByaXZhdGUga2V5LCBubyBjYWNoZWQgcHVia2V5LCBub3QgYSBidW5rZXIvcmVtb3RlXG4gICAgLy8gc2lnbmVyKS4gQSBidW5rZXIgcHJvZmlsZSBsZWdpdGltYXRlbHkgaGFzIHByaXZLZXk6JycgYnV0IElTIGEgcmVhbFxuICAgIC8vIGlkZW50aXR5IFx1MjAxNCBpdCBtdXN0IG5vdCBiZSB0cmVhdGVkIGFzIGEgYmxhbmsgaW5zdGFsbCBhbmQgd2lwZWQuXG4gICAgY29uc3QgaGFzSWRlbnRpdHkgPSAocCkgPT5cbiAgICAgICAgISEocC5wcml2S2V5IHx8IHAucHViS2V5IHx8IHAudHlwZSA9PT0gJ2J1bmtlcicgfHwgcC5idW5rZXJVcmwgfHwgcC5yZW1vdGVQdWJrZXkpO1xuICAgIGNvbnN0IGlzRnJlc2ggPSAhbG9jYWwucHJvZmlsZXMgfHxcbiAgICAgICAgbG9jYWwucHJvZmlsZXMubGVuZ3RoID09PSAwIHx8XG4gICAgICAgICFsb2NhbC5wcm9maWxlcy5zb21lKGhhc0lkZW50aXR5KTtcblxuICAgIC8vIC0tLSBQcm9maWxlcyAoUDEpIC0tLVxuICAgIGlmIChzeW5jRGF0YS5wcm9maWxlcykge1xuICAgICAgICBpZiAoaXNGcmVzaCkge1xuICAgICAgICAgICAgLy8gRnJlc2ggaW5zdGFsbCBcdTIwMTQgYWRvcHQgc3luYyBwcm9maWxlcyBlbnRpcmVseVxuICAgICAgICAgICAgdXBkYXRlcy5wcm9maWxlcyA9IHN5bmNEYXRhLnByb2ZpbGVzO1xuICAgICAgICAgICAgY2hhbmdlZCA9IHRydWU7XG4gICAgICAgIH0gZWxzZSBpZiAobG9jYWwucHJvZmlsZXMpIHtcbiAgICAgICAgICAgIC8vIE1hdGNoIHByb2ZpbGVzIGJ5IHB1YmtleSAoc3RhYmxlIGlkZW50aXR5KSwgTk9UIGFycmF5IGluZGV4IFx1MjAxNFxuICAgICAgICAgICAgLy8gcmVvcmRlcmluZyBvciBpbnNlcnRpbmcgYSBwcm9maWxlIG9uIG9uZSBkZXZpY2UgbXVzdCBuZXZlciBjYXVzZVxuICAgICAgICAgICAgLy8gb25lIGlkZW50aXR5J3Mga2V5IG1hdGVyaWFsIHRvIG92ZXJ3cml0ZSBhbiB1bnJlbGF0ZWQgcHJvZmlsZS5cbiAgICAgICAgICAgIGNvbnN0IG1lcmdlZCA9IFsuLi5sb2NhbC5wcm9maWxlc107XG4gICAgICAgICAgICBjb25zdCBpbmRleEJ5UHVia2V5ID0gbmV3IE1hcCgpO1xuICAgICAgICAgICAgbWVyZ2VkLmZvckVhY2goKHAsIGkpID0+IHsgaWYgKHAucHViS2V5KSBpbmRleEJ5UHVia2V5LnNldChwLnB1YktleSwgaSk7IH0pO1xuXG4gICAgICAgICAgICBmb3IgKGNvbnN0IHN5bmNQcm9maWxlIG9mIHN5bmNEYXRhLnByb2ZpbGVzKSB7XG4gICAgICAgICAgICAgICAgY29uc3QgbG9jYWxJZHggPSBzeW5jUHJvZmlsZS5wdWJLZXkgIT0gbnVsbFxuICAgICAgICAgICAgICAgICAgICA/IGluZGV4QnlQdWJrZXkuZ2V0KHN5bmNQcm9maWxlLnB1YktleSlcbiAgICAgICAgICAgICAgICAgICAgOiB1bmRlZmluZWQ7XG5cbiAgICAgICAgICAgICAgICBpZiAobG9jYWxJZHggPT09IHVuZGVmaW5lZCkge1xuICAgICAgICAgICAgICAgICAgICAvLyBObyBsb2NhbCBwcm9maWxlIHdpdGggdGhpcyBwdWJrZXkgXHUyMDE0IGl0J3MgYSBuZXcgb25lIGZyb20gc3luYy5cbiAgICAgICAgICAgICAgICAgICAgLy8gKFByb2ZpbGVzIHdpdGhvdXQgYSBwdWJrZXkgY2FuJ3QgYmUgc2FmZWx5IG1hdGNoZWQsIHNvIHdlIGFkZFxuICAgICAgICAgICAgICAgICAgICAvLyByYXRoZXIgdGhhbiByaXNrIGNsb2JiZXJpbmcgYW4gdW5yZWxhdGVkIGxvY2FsIHByb2ZpbGUuKVxuICAgICAgICAgICAgICAgICAgICBtZXJnZWQucHVzaChzeW5jUHJvZmlsZSk7XG4gICAgICAgICAgICAgICAgICAgIGlmIChzeW5jUHJvZmlsZS5wdWJLZXkpIGluZGV4QnlQdWJrZXkuc2V0KHN5bmNQcm9maWxlLnB1YktleSwgbWVyZ2VkLmxlbmd0aCAtIDEpO1xuICAgICAgICAgICAgICAgICAgICBjaGFuZ2VkID0gdHJ1ZTtcbiAgICAgICAgICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgICAgICAgICBjb25zdCBsb2NhbFByb2ZpbGUgPSBtZXJnZWRbbG9jYWxJZHhdO1xuICAgICAgICAgICAgICAgICAgICBjb25zdCBzeW5jVGltZSA9IHN5bmNQcm9maWxlLnVwZGF0ZWRBdCB8fCAwO1xuICAgICAgICAgICAgICAgICAgICBjb25zdCBsb2NhbFRpbWUgPSBsb2NhbFByb2ZpbGUudXBkYXRlZEF0IHx8IDA7XG4gICAgICAgICAgICAgICAgICAgIGlmIChzeW5jVGltZSA+IGxvY2FsVGltZSkge1xuICAgICAgICAgICAgICAgICAgICAgICAgLy8gU3luYyBpcyBuZXdlciBcdTIwMTQgbWVyZ2UgYnV0IHByZXNlcnZlIGxvY2FsIGhvc3RzXG4gICAgICAgICAgICAgICAgICAgICAgICBtZXJnZWRbbG9jYWxJZHhdID0geyAuLi5zeW5jUHJvZmlsZSwgaG9zdHM6IGxvY2FsUHJvZmlsZS5ob3N0cyB8fCB7fSB9O1xuICAgICAgICAgICAgICAgICAgICAgICAgY2hhbmdlZCA9IHRydWU7XG4gICAgICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICB9XG4gICAgICAgICAgICBpZiAoY2hhbmdlZCkgdXBkYXRlcy5wcm9maWxlcyA9IG1lcmdlZDtcbiAgICAgICAgfVxuICAgIH1cblxuICAgIC8vIC0tLSBQcm9maWxlIGluZGV4IChQMSkgLS0tXG4gICAgaWYgKHN5bmNEYXRhLnByb2ZpbGVJbmRleCAhPSBudWxsICYmIGlzRnJlc2gpIHtcbiAgICAgICAgdXBkYXRlcy5wcm9maWxlSW5kZXggPSBzeW5jRGF0YS5wcm9maWxlSW5kZXg7XG4gICAgICAgIGNoYW5nZWQgPSB0cnVlO1xuICAgIH1cblxuICAgIC8vIC0tLSBFbmNyeXB0aW9uIHN0YXRlIChQMSkgLS0tXG4gICAgLy8gSW50ZW50aW9uYWxseSBOT1QgbWVyZ2VkIGZyb20gc3luYy4gU2VlIGJ1aWxkU3luY1BheWxvYWQoKTogdGhlIHBhc3N3b3JkXG4gICAgLy8gdmVyaWZpZXIgaXMgbmV2ZXIgc3luY2VkLCBzbyB0cnVzdGluZyBhIHN5bmNlZCBpc0VuY3J5cHRlZD10cnVlIHdvdWxkIGxvY2tcbiAgICAvLyB0aGUgdXNlciBvdXQgcGVybWFuZW50bHkuIEVuY3J5cHRpb24gc3RhdGUgc3RheXMgZGV2aWNlLWxvY2FsLlxuXG4gICAgLy8gLS0tIFNldHRpbmdzIChQMikgXHUyMDE0IGxhc3Qtd3JpdGUtd2lucyAtLS1cbiAgICBjb25zdCBzeW5jTWV0YSA9IHN5bmNEYXRhLl9zeW5jTWV0YSB8fCB7fTtcbiAgICBjb25zdCBzZXR0aW5nc0tleXMgPSBbJ2F1dG9Mb2NrTWludXRlcycsICd2ZXJzaW9uJywgJ3Byb3RvY29sX2hhbmRsZXInLCBMT0NBTF9FTkFCTEVEX0tFWV07XG4gICAgZm9yIChjb25zdCBrZXkgb2Ygc2V0dGluZ3NLZXlzKSB7XG4gICAgICAgIGlmIChzeW5jRGF0YVtrZXldICE9IG51bGwgJiYgc3luY0RhdGFba2V5XSAhPT0gbG9jYWxba2V5XSkge1xuICAgICAgICAgICAgLy8gRm9yIHZlcnNpb24sIG9ubHkgYWNjZXB0IGhpZ2hlci4gQ29tcGFyZSBudW1lcmljYWxseSBwZXIgc2VtdmVyXG4gICAgICAgICAgICAvLyBjb21wb25lbnQgXHUyMDE0IGEgc3RyaW5nIGA8PWAgbWFrZXMgJzEuMTAuMCcgPD0gJzEuOS4wJyAoc28gYSBnZW51aW5lbHlcbiAgICAgICAgICAgIC8vIG5ld2VyIGJ1aWxkIGZyb20gc3luYyB3b3VsZCBiZSB3cm9uZ2x5IHJlamVjdGVkKS5cbiAgICAgICAgICAgIGlmIChrZXkgPT09ICd2ZXJzaW9uJyAmJiBsb2NhbC52ZXJzaW9uICYmIGNvbXBhcmVTZW12ZXIoc3luY0RhdGEudmVyc2lvbiwgbG9jYWwudmVyc2lvbikgPD0gMCkgY29udGludWU7XG4gICAgICAgICAgICB1cGRhdGVzW2tleV0gPSBzeW5jRGF0YVtrZXldO1xuICAgICAgICAgICAgY2hhbmdlZCA9IHRydWU7XG4gICAgICAgIH1cbiAgICB9XG4gICAgLy8gRmVhdHVyZSBmbGFnc1xuICAgIGZvciAoY29uc3Qga2V5IG9mIE9iamVjdC5rZXlzKHN5bmNEYXRhKSkge1xuICAgICAgICBpZiAoa2V5LnN0YXJ0c1dpdGgoJ2ZlYXR1cmU6JykgJiYgc3luY0RhdGFba2V5XSAhPT0gbG9jYWxba2V5XSkge1xuICAgICAgICAgICAgdXBkYXRlc1trZXldID0gc3luY0RhdGFba2V5XTtcbiAgICAgICAgICAgIGNoYW5nZWQgPSB0cnVlO1xuICAgICAgICB9XG4gICAgfVxuXG4gICAgLy8gLS0tIEFQSSBLZXkgVmF1bHQgKFAzKSAtLS1cbiAgICBpZiAoc3luY0RhdGEuYXBpS2V5VmF1bHQpIHtcbiAgICAgICAgaWYgKCFsb2NhbC5hcGlLZXlWYXVsdCB8fCBpc0ZyZXNoKSB7XG4gICAgICAgICAgICB1cGRhdGVzLmFwaUtleVZhdWx0ID0gc3luY0RhdGEuYXBpS2V5VmF1bHQ7XG4gICAgICAgICAgICBjaGFuZ2VkID0gdHJ1ZTtcbiAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICAgIC8vIE1lcmdlIGluZGl2aWR1YWwga2V5cyBieSB1cGRhdGVkQXRcbiAgICAgICAgICAgIGNvbnN0IGxvY2FsS2V5cyA9IGxvY2FsLmFwaUtleVZhdWx0LmtleXMgfHwge307XG4gICAgICAgICAgICBjb25zdCBzeW5jS2V5cyA9IHN5bmNEYXRhLmFwaUtleVZhdWx0LmtleXMgfHwge307XG4gICAgICAgICAgICBjb25zdCBtZXJnZWQgPSB7IC4uLmxvY2FsS2V5cyB9O1xuICAgICAgICAgICAgZm9yIChjb25zdCBbaWQsIHN5bmNLZXldIG9mIE9iamVjdC5lbnRyaWVzKHN5bmNLZXlzKSkge1xuICAgICAgICAgICAgICAgIGNvbnN0IGxvY2FsS2V5ID0gbWVyZ2VkW2lkXTtcbiAgICAgICAgICAgICAgICBpZiAoIWxvY2FsS2V5IHx8IChzeW5jS2V5LnVwZGF0ZWRBdCB8fCAwKSA+IChsb2NhbEtleS51cGRhdGVkQXQgfHwgMCkpIHtcbiAgICAgICAgICAgICAgICAgICAgbWVyZ2VkW2lkXSA9IHN5bmNLZXk7XG4gICAgICAgICAgICAgICAgICAgIGNoYW5nZWQgPSB0cnVlO1xuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgIH1cbiAgICAgICAgICAgIGlmIChjaGFuZ2VkKSB7XG4gICAgICAgICAgICAgICAgdXBkYXRlcy5hcGlLZXlWYXVsdCA9IHsgLi4ubG9jYWwuYXBpS2V5VmF1bHQsIGtleXM6IG1lcmdlZCB9O1xuICAgICAgICAgICAgfVxuICAgICAgICB9XG4gICAgfVxuXG4gICAgLy8gLS0tIFZhdWx0IGRvY3MgKFA0KSAtLS1cbiAgICBjb25zdCBsb2NhbERvY3MgPSBsb2NhbC52YXVsdERvY3MgfHwge307XG4gICAgbGV0IGRvY3NDaGFuZ2VkID0gZmFsc2U7XG4gICAgY29uc3QgbWVyZ2VkRG9jcyA9IHsgLi4ubG9jYWxEb2NzIH07XG4gICAgZm9yIChjb25zdCBrZXkgb2YgT2JqZWN0LmtleXMoc3luY0RhdGEpKSB7XG4gICAgICAgIGlmICgha2V5LnN0YXJ0c1dpdGgoJ3ZhdWx0RG9jOicpKSBjb250aW51ZTtcbiAgICAgICAgY29uc3QgZG9jID0gc3luY0RhdGFba2V5XTtcbiAgICAgICAgaWYgKCFkb2MgfHwgIWRvYy5wYXRoKSBjb250aW51ZTtcbiAgICAgICAgY29uc3QgbG9jYWxEb2MgPSBtZXJnZWREb2NzW2RvYy5wYXRoXTtcbiAgICAgICAgaWYgKCFsb2NhbERvYyB8fCAoZG9jLnVwZGF0ZWRBdCB8fCAwKSA+IChsb2NhbERvYy51cGRhdGVkQXQgfHwgMCkpIHtcbiAgICAgICAgICAgIG1lcmdlZERvY3NbZG9jLnBhdGhdID0gZG9jO1xuICAgICAgICAgICAgZG9jc0NoYW5nZWQgPSB0cnVlO1xuICAgICAgICB9XG4gICAgfVxuICAgIGlmIChkb2NzQ2hhbmdlZCkge1xuICAgICAgICB1cGRhdGVzLnZhdWx0RG9jcyA9IG1lcmdlZERvY3M7XG4gICAgICAgIGNoYW5nZWQgPSB0cnVlO1xuICAgIH1cblxuICAgIHJldHVybiB7IHVwZGF0ZXMsIGNoYW5nZWQgfTtcbn1cblxuLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG4vLyBEZWJvdW5jZWQgcHVzaFxuLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG5cbi8qKlxuICogU2NoZWR1bGUgYSBzeW5jIHB1c2ggd2l0aCBhIDItc2Vjb25kIGRlYm91bmNlLlxuICogRXhwb3J0ZWQgZm9yIHVzZSBieSBzdG9yZXMgYW5kIHRoZSBzdG9yYWdlIGludGVyY2VwdG9yLlxuICovXG5leHBvcnQgZnVuY3Rpb24gc2NoZWR1bGVTeW5jUHVzaCgpIHtcbiAgICBpZiAoIWFwaS5zdG9yYWdlLnN5bmMpIHJldHVybjtcbiAgICBpZiAocHVzaFRpbWVyKSBjbGVhclRpbWVvdXQocHVzaFRpbWVyKTtcbiAgICBwdXNoVGltZXIgPSBzZXRUaW1lb3V0KCgpID0+IHtcbiAgICAgICAgcHVzaFRpbWVyID0gbnVsbDtcbiAgICAgICAgcHVzaFRvU3luYygpO1xuICAgIH0sIDIwMDApO1xufVxuXG4vLyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cbi8vIEVuYWJsZSAvIGRpc2FibGVcbi8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLVxuXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gaXNTeW5jRW5hYmxlZCgpIHtcbiAgICBjb25zdCBkYXRhID0gYXdhaXQgc3RvcmFnZS5nZXQoeyBbTE9DQUxfRU5BQkxFRF9LRVldOiB0cnVlIH0pO1xuICAgIHJldHVybiBkYXRhW0xPQ0FMX0VOQUJMRURfS0VZXTtcbn1cblxuZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIHNldFN5bmNFbmFibGVkKGVuYWJsZWQpIHtcbiAgICBhd2FpdCBzdG9yYWdlLnNldCh7IFtMT0NBTF9FTkFCTEVEX0tFWV06IGVuYWJsZWQgfSk7XG4gICAgaWYgKGVuYWJsZWQpIHtcbiAgICAgICAgc2NoZWR1bGVTeW5jUHVzaCgpO1xuICAgIH1cbn1cblxuLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG4vLyBJbml0aWFsaXNhdGlvblxuLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG5cbi8qKlxuICogQ2FsbGVkIG9uY2Ugb24gc3RhcnR1cCAoZnJvbSBiYWNrZ3JvdW5kLmpzKS5cbiAqIFB1bGxzIGZyb20gc3luYywgbWVyZ2VzLCB0aGVuIGxpc3RlbnMgZm9yIHJlbW90ZSBjaGFuZ2VzLlxuICovXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gaW5pdFN5bmMoKSB7XG4gICAgaWYgKCFhcGkuc3RvcmFnZS5zeW5jKSB7XG4gICAgICAgIGNvbnNvbGUubG9nKCdbU3luY01hbmFnZXJdIHN0b3JhZ2Uuc3luYyBub3QgYXZhaWxhYmxlIFx1MjAxNCBza2lwcGluZycpO1xuICAgICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgY29uc3QgZW5hYmxlZCA9IGF3YWl0IGlzU3luY0VuYWJsZWQoKTtcbiAgICBpZiAoIWVuYWJsZWQpIHtcbiAgICAgICAgY29uc29sZS5sb2coJ1tTeW5jTWFuYWdlcl0gUGxhdGZvcm0gc3luYyBkaXNhYmxlZCcpO1xuICAgICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgLy8gUHVsbCArIG1lcmdlXG4gICAgdHJ5IHtcbiAgICAgICAgY29uc3Qgc3luY0RhdGEgPSBhd2FpdCBwdWxsRnJvbVN5bmMoKTtcbiAgICAgICAgaWYgKHN5bmNEYXRhKSB7XG4gICAgICAgICAgICBhd2FpdCBtZXJnZUludG9Mb2NhbChzeW5jRGF0YSk7XG4gICAgICAgICAgICBjb25zb2xlLmxvZygnW1N5bmNNYW5hZ2VyXSBJbml0aWFsIHB1bGwrbWVyZ2UgY29tcGxldGUnKTtcbiAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICAgIGNvbnNvbGUubG9nKCdbU3luY01hbmFnZXJdIE5vIHN5bmMgZGF0YSBmb3VuZCBcdTIwMTQgZnJlc2ggc3luYycpO1xuICAgICAgICB9XG4gICAgfSBjYXRjaCAoZSkge1xuICAgICAgICBjb25zb2xlLmVycm9yKCdbU3luY01hbmFnZXJdIEluaXRpYWwgcHVsbCBmYWlsZWQ6JywgZSk7XG4gICAgfVxuXG4gICAgLy8gTGlzdGVuIGZvciByZW1vdGUgY2hhbmdlc1xuICAgIGlmIChhcGkuc3RvcmFnZS5vbkNoYW5nZWQpIHtcbiAgICAgICAgYXBpLnN0b3JhZ2Uub25DaGFuZ2VkLmFkZExpc3RlbmVyKChjaGFuZ2VzLCBhcmVhTmFtZSkgPT4ge1xuICAgICAgICAgICAgaWYgKGFyZWFOYW1lICE9PSAnc3luYycpIHJldHVybjtcbiAgICAgICAgICAgIGNvbnNvbGUubG9nKCdbU3luY01hbmFnZXJdIFJlbW90ZSBzeW5jIGNoYW5nZSBkZXRlY3RlZCcpO1xuICAgICAgICAgICAgLy8gUmUtcHVsbCBhbmQgbWVyZ2UgdGhlIGZ1bGwgc3luYyBkYXRhIHRvIGhhbmRsZSBjaHVua2VkIHZhbHVlcyBjb3JyZWN0bHlcbiAgICAgICAgICAgIHB1bGxGcm9tU3luYygpLnRoZW4oc3luY0RhdGEgPT4ge1xuICAgICAgICAgICAgICAgIGlmIChzeW5jRGF0YSkgbWVyZ2VJbnRvTG9jYWwoc3luY0RhdGEpO1xuICAgICAgICAgICAgfSkuY2F0Y2goZSA9PiB7XG4gICAgICAgICAgICAgICAgY29uc29sZS5lcnJvcignW1N5bmNNYW5hZ2VyXSBSZW1vdGUgbWVyZ2UgZXJyb3I6JywgZSk7XG4gICAgICAgICAgICB9KTtcbiAgICAgICAgfSk7XG4gICAgfVxuXG4gICAgLy8gRG8gYW4gaW5pdGlhbCBwdXNoIHNvIGxvY2FsIGRhdGEgaXMgbWlycm9yZWRcbiAgICBzY2hlZHVsZVN5bmNQdXNoKCk7XG59XG4iLCAiLyoqXG4gKiBBUEkgS2V5IFN0b3JlIFx1MjAxNCBMb2NhbCBjYWNoZSBmb3IgZW5jcnlwdGVkIEFQSSBrZXlzXG4gKlxuICogU3RvcmFnZSBzY2hlbWEgaW4gYnJvd3Nlci5zdG9yYWdlLmxvY2FsOlxuICogICBhcGlLZXlWYXVsdDoge1xuICogICAgIGtleXM6IHtcbiAqICAgICAgIFwiPHV1aWQ+XCI6IHsgaWQsIGxhYmVsLCBzZWNyZXQsIGNyZWF0ZWRBdCwgdXBkYXRlZEF0LCBwcm9maWxlU2NvcGUgfVxuICogICAgIH0sXG4gKiAgICAgc3luY0VuYWJsZWQ6IHRydWUsXG4gKiAgICAgZXZlbnRJZDogbnVsbCxcbiAqICAgICByZWxheUNyZWF0ZWRBdDogbnVsbCxcbiAqICAgICBzeW5jU3RhdHVzOiBcInN5bmNlZFwiICAgIC8vIHN5bmNlZCB8IGxvY2FsLW9ubHkgfCBjb25mbGljdFxuICogICB9XG4gKlxuICogcHJvZmlsZVNjb3BlOiBudWxsIChhbGwgcHJvZmlsZXMpIHwgbnVtYmVyW10gKHNwZWNpZmljIHByb2ZpbGUgaW5kaWNlcylcbiAqL1xuXG5pbXBvcnQgeyBhcGkgfSBmcm9tICcuL2Jyb3dzZXItcG9seWZpbGwnO1xuaW1wb3J0IHsgc2NoZWR1bGVTeW5jUHVzaCB9IGZyb20gJy4vc3luYy1tYW5hZ2VyJztcblxuY29uc3Qgc3RvcmFnZSA9IGFwaS5zdG9yYWdlLmxvY2FsO1xuY29uc3QgU1RPUkFHRV9LRVkgPSAnYXBpS2V5VmF1bHQnO1xuXG5jb25zdCBERUZBVUxUX1NUT1JFID0ge1xuICAgIGtleXM6IHt9LFxuICAgIHN5bmNFbmFibGVkOiB0cnVlLFxuICAgIGV2ZW50SWQ6IG51bGwsXG4gICAgcmVsYXlDcmVhdGVkQXQ6IG51bGwsXG4gICAgc3luY1N0YXR1czogJ3N5bmNlZCcsXG59O1xuXG5hc3luYyBmdW5jdGlvbiBnZXRTdG9yZSgpIHtcbiAgICBjb25zdCBkYXRhID0gYXdhaXQgc3RvcmFnZS5nZXQoeyBbU1RPUkFHRV9LRVldOiBERUZBVUxUX1NUT1JFIH0pO1xuICAgIHJldHVybiB7IC4uLkRFRkFVTFRfU1RPUkUsIC4uLmRhdGFbU1RPUkFHRV9LRVldIH07XG59XG5cbmFzeW5jIGZ1bmN0aW9uIHNldFN0b3JlKHN0b3JlKSB7XG4gICAgYXdhaXQgc3RvcmFnZS5zZXQoeyBbU1RPUkFHRV9LRVldOiBzdG9yZSB9KTtcbiAgICBzY2hlZHVsZVN5bmNQdXNoKCk7XG59XG5cbi8qKlxuICogR2V0IHRoZSBmdWxsIEFQSSBrZXkgc3RvcmUgb2JqZWN0LlxuICovXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gZ2V0QXBpS2V5U3RvcmUoKSB7XG4gICAgcmV0dXJuIGdldFN0b3JlKCk7XG59XG5cbi8qKlxuICogR2V0IGEgc2luZ2xlIEFQSSBrZXkgYnkgaWQuXG4gKiBAcGFyYW0ge3N0cmluZ30gaWRcbiAqIEByZXR1cm5zIHtQcm9taXNlPE9iamVjdHxudWxsPn1cbiAqL1xuZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIGdldEFwaUtleShpZCkge1xuICAgIGNvbnN0IHN0b3JlID0gYXdhaXQgZ2V0U3RvcmUoKTtcbiAgICByZXR1cm4gc3RvcmUua2V5c1tpZF0gfHwgbnVsbDtcbn1cblxuLyoqXG4gKiBVcHNlcnQgYW4gQVBJIGtleS4gQ3JlYXRlcyBpZiBuZXcsIHVwZGF0ZXMgaWYgZXhpc3RpbmcuXG4gKiBAcGFyYW0ge3N0cmluZ30gaWQgLSBVVUlEXG4gKiBAcGFyYW0ge3N0cmluZ30gbGFiZWxcbiAqIEBwYXJhbSB7c3RyaW5nfSBzZWNyZXRcbiAqL1xuZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIHNhdmVBcGlLZXkoaWQsIGxhYmVsLCBzZWNyZXQpIHtcbiAgICBjb25zdCBzdG9yZSA9IGF3YWl0IGdldFN0b3JlKCk7XG4gICAgY29uc3Qgbm93ID0gTWF0aC5mbG9vcihEYXRlLm5vdygpIC8gMTAwMCk7XG4gICAgY29uc3QgZXhpc3RpbmcgPSBzdG9yZS5rZXlzW2lkXTtcbiAgICBzdG9yZS5rZXlzW2lkXSA9IHtcbiAgICAgICAgaWQsXG4gICAgICAgIGxhYmVsLFxuICAgICAgICBzZWNyZXQsXG4gICAgICAgIGNyZWF0ZWRBdDogZXhpc3Rpbmc/LmNyZWF0ZWRBdCB8fCBub3csXG4gICAgICAgIHVwZGF0ZWRBdDogbm93LFxuICAgICAgICBwcm9maWxlU2NvcGU6IGV4aXN0aW5nPy5wcm9maWxlU2NvcGUgPz8gbnVsbCxcbiAgICB9O1xuICAgIGF3YWl0IHNldFN0b3JlKHN0b3JlKTtcbiAgICByZXR1cm4gc3RvcmUua2V5c1tpZF07XG59XG5cbi8qKlxuICogRGVsZXRlIGFuIEFQSSBrZXkgYnkgaWQuXG4gKi9cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBkZWxldGVBcGlLZXkoaWQpIHtcbiAgICBjb25zdCBzdG9yZSA9IGF3YWl0IGdldFN0b3JlKCk7XG4gICAgZGVsZXRlIHN0b3JlLmtleXNbaWRdO1xuICAgIGF3YWl0IHNldFN0b3JlKHN0b3JlKTtcbn1cblxuLyoqXG4gKiBMaXN0IGFsbCBBUEkga2V5cyBzb3J0ZWQgYnkgbGFiZWwgKGNhc2UtaW5zZW5zaXRpdmUpLlxuICogQHJldHVybnMge1Byb21pc2U8QXJyYXk+fVxuICovXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gbGlzdEFwaUtleXMoKSB7XG4gICAgY29uc3Qgc3RvcmUgPSBhd2FpdCBnZXRTdG9yZSgpO1xuICAgIHJldHVybiBPYmplY3QudmFsdWVzKHN0b3JlLmtleXMpLnNvcnQoKGEsIGIpID0+XG4gICAgICAgIGEubGFiZWwudG9Mb3dlckNhc2UoKS5sb2NhbGVDb21wYXJlKGIubGFiZWwudG9Mb3dlckNhc2UoKSksXG4gICAgKTtcbn1cblxuLyoqXG4gKiBTZXQgdGhlIHJlbGF5IHN5bmMgdG9nZ2xlLlxuICovXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gc2V0U3luY0VuYWJsZWQoZW5hYmxlZCkge1xuICAgIGNvbnN0IHN0b3JlID0gYXdhaXQgZ2V0U3RvcmUoKTtcbiAgICBzdG9yZS5zeW5jRW5hYmxlZCA9IGVuYWJsZWQ7XG4gICAgYXdhaXQgc2V0U3RvcmUoc3RvcmUpO1xufVxuXG4vKipcbiAqIENoZWNrIGlmIHJlbGF5IHN5bmMgaXMgZW5hYmxlZC5cbiAqL1xuZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIGlzU3luY0VuYWJsZWQoKSB7XG4gICAgY29uc3Qgc3RvcmUgPSBhd2FpdCBnZXRTdG9yZSgpO1xuICAgIHJldHVybiBzdG9yZS5zeW5jRW5hYmxlZDtcbn1cblxuLyoqXG4gKiBVcGRhdGUgc3luYyBzdGF0ZSBhZnRlciBhIHJlbGF5IG9wZXJhdGlvbi5cbiAqL1xuZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIHVwZGF0ZVN0b3JlU3luY1N0YXRlKHN5bmNTdGF0dXMsIGV2ZW50SWQgPSBudWxsLCByZWxheUNyZWF0ZWRBdCA9IG51bGwpIHtcbiAgICBjb25zdCBzdG9yZSA9IGF3YWl0IGdldFN0b3JlKCk7XG4gICAgc3RvcmUuc3luY1N0YXR1cyA9IHN5bmNTdGF0dXM7XG4gICAgaWYgKGV2ZW50SWQgIT09IG51bGwpIHN0b3JlLmV2ZW50SWQgPSBldmVudElkO1xuICAgIGlmIChyZWxheUNyZWF0ZWRBdCAhPT0gbnVsbCkgc3RvcmUucmVsYXlDcmVhdGVkQXQgPSByZWxheUNyZWF0ZWRBdDtcbiAgICBhd2FpdCBzZXRTdG9yZShzdG9yZSk7XG59XG5cbi8qKlxuICogRXhwb3J0IHRoZSBrZXlzIG9iamVjdCAoZm9yIGVuY3J5cHRlZCBiYWNrdXApLlxuICogQHJldHVybnMge1Byb21pc2U8T2JqZWN0Pn0gTWFwIG9mIGlkIC0+IGtleSBkYXRhXG4gKi9cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBleHBvcnRTdG9yZSgpIHtcbiAgICBjb25zdCBzdG9yZSA9IGF3YWl0IGdldFN0b3JlKCk7XG4gICAgcmV0dXJuIHN0b3JlLmtleXM7XG59XG5cbi8qKlxuICogSW1wb3J0IGtleXMgaW50byB0aGUgc3RvcmUgKG1lcmdlIFx1MjAxNCBleGlzdGluZyBrZXlzIHdpdGggc2FtZSBpZCBhcmUgb3ZlcndyaXR0ZW4pLlxuICogQHBhcmFtIHtPYmplY3R9IGtleXMgLSBNYXAgb2YgaWQgLT4geyBpZCwgbGFiZWwsIHNlY3JldCwgY3JlYXRlZEF0LCB1cGRhdGVkQXQgfVxuICovXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gaW1wb3J0U3RvcmUoa2V5cykge1xuICAgIGNvbnN0IHN0b3JlID0gYXdhaXQgZ2V0U3RvcmUoKTtcbiAgICBmb3IgKGNvbnN0IFtpZCwga2V5XSBvZiBPYmplY3QuZW50cmllcyhrZXlzKSkge1xuICAgICAgICBzdG9yZS5rZXlzW2lkXSA9IGtleTtcbiAgICB9XG4gICAgYXdhaXQgc2V0U3RvcmUoc3RvcmUpO1xufVxuIiwgImltcG9ydCB7IGFwaSB9IGZyb20gJy4uL3V0aWxpdGllcy9icm93c2VyLXBvbHlmaWxsJztcbmltcG9ydCB7XG4gICAgZ2V0QXBpS2V5U3RvcmUsXG4gICAgc2F2ZUFwaUtleSxcbiAgICBkZWxldGVBcGlLZXksXG4gICAgbGlzdEFwaUtleXMsXG4gICAgc2V0U3luY0VuYWJsZWQsXG4gICAgaXNTeW5jRW5hYmxlZCxcbiAgICB1cGRhdGVTdG9yZVN5bmNTdGF0ZSxcbiAgICBleHBvcnRTdG9yZSxcbiAgICBpbXBvcnRTdG9yZSxcbn0gZnJvbSAnLi4vdXRpbGl0aWVzL2FwaS1rZXktc3RvcmUnO1xuXG5jb25zdCBzdGF0ZSA9IHtcbiAgICBrZXlzOiBbXSxcbiAgICBuZXdMYWJlbDogJycsXG4gICAgbmV3U2VjcmV0OiAnJyxcbiAgICBlZGl0aW5nSWQ6IG51bGwsXG4gICAgZWRpdExhYmVsOiAnJyxcbiAgICBlZGl0U2VjcmV0OiAnJyxcbiAgICBjb3BpZWRJZDogbnVsbCxcbiAgICByZXZlYWxlZElkOiBudWxsLFxuICAgIHN5bmNFbmFibGVkOiB0cnVlLFxuICAgIGdsb2JhbFN5bmNTdGF0dXM6ICdpZGxlJyxcbiAgICBzeW5jRXJyb3I6ICcnLFxuICAgIHNhdmluZzogZmFsc2UsXG4gICAgdG9hc3Q6ICcnLFxuICAgIHJlbGF5SW5mbzogeyByZWFkOiBbXSwgd3JpdGU6IFtdIH0sXG59O1xuXG5mdW5jdGlvbiAkKGlkKSB7IHJldHVybiBkb2N1bWVudC5nZXRFbGVtZW50QnlJZChpZCk7IH1cblxuZnVuY3Rpb24gaGFzUmVsYXlzKCkge1xuICAgIHJldHVybiBzdGF0ZS5yZWxheUluZm8ucmVhZC5sZW5ndGggPiAwIHx8IHN0YXRlLnJlbGF5SW5mby53cml0ZS5sZW5ndGggPiAwO1xufVxuXG5mdW5jdGlvbiBzb3J0ZWRLZXlzKCkge1xuICAgIHJldHVybiBbLi4uc3RhdGUua2V5c10uc29ydCgoYSwgYikgPT5cbiAgICAgICAgYS5sYWJlbC50b0xvd2VyQ2FzZSgpLmxvY2FsZUNvbXBhcmUoYi5sYWJlbC50b0xvd2VyQ2FzZSgpKSxcbiAgICApO1xufVxuXG5mdW5jdGlvbiBtYXNrU2VjcmV0KHNlY3JldCkge1xuICAgIGlmICghc2VjcmV0KSByZXR1cm4gJyc7XG4gICAgaWYgKHNlY3JldC5sZW5ndGggPD0gOCkgcmV0dXJuICdcXHUyMDIyJy5yZXBlYXQoc2VjcmV0Lmxlbmd0aCk7XG4gICAgcmV0dXJuIHNlY3JldC5zbGljZSgwLCA0KSArICdcXHUyMDIyJy5yZXBlYXQoNCkgKyBzZWNyZXQuc2xpY2UoLTQpO1xufVxuXG5mdW5jdGlvbiBzaG93VG9hc3QobXNnKSB7XG4gICAgc3RhdGUudG9hc3QgPSBtc2c7XG4gICAgcmVuZGVyKCk7XG4gICAgc2V0VGltZW91dCgoKSA9PiB7IHN0YXRlLnRvYXN0ID0gJyc7IHJlbmRlcigpOyB9LCAyMDAwKTtcbn1cblxuZnVuY3Rpb24gc3luY1N0YXR1c0NsYXNzKHN0YXR1cykge1xuICAgIGlmIChzdGF0dXMgPT09ICdpZGxlJykgcmV0dXJuICdiZy1ncmVlbi01MDAnO1xuICAgIGlmIChzdGF0dXMgPT09ICdzeW5jaW5nJykgcmV0dXJuICdiZy15ZWxsb3ctNTAwIGFuaW1hdGUtcHVsc2UnO1xuICAgIHJldHVybiAnYmctcmVkLTUwMCc7XG59XG5cbmZ1bmN0aW9uIHN5bmNTdGF0dXNUZXh0KCkge1xuICAgIGlmIChzdGF0ZS5nbG9iYWxTeW5jU3RhdHVzID09PSAnc3luY2luZycpIHJldHVybiAnU3luY2luZy4uLic7XG4gICAgaWYgKHN0YXRlLmdsb2JhbFN5bmNTdGF0dXMgPT09ICdlcnJvcicpIHJldHVybiBzdGF0ZS5zeW5jRXJyb3I7XG4gICAgcmV0dXJuIHN0YXRlLnN5bmNFbmFibGVkID8gJ1N5bmNlZCcgOiAnTG9jYWwgb25seSc7XG59XG5cbi8vIC0tLSBSZW5kZXIgLS0tXG5cbmZ1bmN0aW9uIHJlbmRlcigpIHtcbiAgICAvLyBTeW5jIGJhclxuICAgIGNvbnN0IHN5bmNEb3QgPSAkKCdzeW5jLWRvdCcpO1xuICAgIGNvbnN0IHN5bmNUZXh0ID0gJCgnc3luYy10ZXh0Jyk7XG4gICAgY29uc3Qgc3luY0J0biA9ICQoJ3N5bmMtYnRuJyk7XG4gICAgY29uc3Qgc3luY1RvZ2dsZSA9ICQoJ3N5bmMtdG9nZ2xlJyk7XG4gICAgY29uc3Qga2V5Q291bnQgPSAkKCdrZXktY291bnQnKTtcblxuICAgIGlmIChzeW5jRG90KSBzeW5jRG90LmNsYXNzTmFtZSA9IGBpbmxpbmUtYmxvY2sgdy0zIGgtMyByb3VuZGVkLWZ1bGwgJHtzeW5jU3RhdHVzQ2xhc3Moc3RhdGUuZ2xvYmFsU3luY1N0YXR1cyl9YDtcbiAgICBpZiAoc3luY1RleHQpIHN5bmNUZXh0LnRleHRDb250ZW50ID0gc3luY1N0YXR1c1RleHQoKTtcbiAgICBpZiAoc3luY0J0bikgc3luY0J0bi5kaXNhYmxlZCA9IHN0YXRlLmdsb2JhbFN5bmNTdGF0dXMgPT09ICdzeW5jaW5nJyB8fCAhaGFzUmVsYXlzKCkgfHwgIXN0YXRlLnN5bmNFbmFibGVkO1xuICAgIGlmIChzeW5jVG9nZ2xlKSBzeW5jVG9nZ2xlLmNoZWNrZWQgPSBzdGF0ZS5zeW5jRW5hYmxlZDtcbiAgICBpZiAoa2V5Q291bnQpIGtleUNvdW50LnRleHRDb250ZW50ID0gc3RhdGUua2V5cy5sZW5ndGggKyAnIGtleScgKyAoc3RhdGUua2V5cy5sZW5ndGggIT09IDEgPyAncycgOiAnJyk7XG5cbiAgICAvLyBLZXkgdGFibGVcbiAgICBjb25zdCBrZXlUYWJsZUNvbnRhaW5lciA9ICQoJ2tleS10YWJsZS1jb250YWluZXInKTtcbiAgICBjb25zdCBub0tleXNNc2cgPSAkKCduby1rZXlzJyk7XG4gICAgY29uc3Qga2V5VGFibGVCb2R5ID0gJCgna2V5LXRhYmxlLWJvZHknKTtcblxuICAgIGlmIChrZXlUYWJsZUNvbnRhaW5lcikga2V5VGFibGVDb250YWluZXIuc3R5bGUuZGlzcGxheSA9IHN0YXRlLmtleXMubGVuZ3RoID4gMCA/ICdibG9jaycgOiAnbm9uZSc7XG4gICAgaWYgKG5vS2V5c01zZykgbm9LZXlzTXNnLnN0eWxlLmRpc3BsYXkgPSBzdGF0ZS5rZXlzLmxlbmd0aCA9PT0gMCA/ICdibG9jaycgOiAnbm9uZSc7XG5cbiAgICBpZiAoa2V5VGFibGVCb2R5KSB7XG4gICAgICAgIGNvbnN0IHNvcnRlZCA9IHNvcnRlZEtleXMoKTtcbiAgICAgICAga2V5VGFibGVCb2R5LmlubmVySFRNTCA9IHNvcnRlZC5tYXAoa2V5ID0+IHtcbiAgICAgICAgICAgIGlmIChzdGF0ZS5lZGl0aW5nSWQgPT09IGtleS5pZCkge1xuICAgICAgICAgICAgICAgIHJldHVybiBgXG4gICAgICAgICAgICAgICAgICAgIDx0ciBjbGFzcz1cImJvcmRlci1iIGJvcmRlci1tb25va2FpLWJnLWxpZ2h0ZXIgaG92ZXI6YmctbW9ub2thaS1iZy1saWdodGVyXCI+XG4gICAgICAgICAgICAgICAgICAgICAgICA8dGQgY2xhc3M9XCJwLTJcIj5cbiAgICAgICAgICAgICAgICAgICAgICAgICAgICA8aW5wdXRcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdHlwZT1cInRleHRcIlxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBjbGFzcz1cImlucHV0IHRleHQtc20gdy1mdWxsXCJcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgYXV0b2NvbXBsZXRlPVwib2ZmXCJcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZGF0YS1lZGl0LWxhYmVsPVwiJHtrZXkuaWR9XCJcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdmFsdWU9XCIke2VzY2FwZUF0dHIoc3RhdGUuZWRpdExhYmVsKX1cIlxuICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8+XG4gICAgICAgICAgICAgICAgICAgICAgICA8L3RkPlxuICAgICAgICAgICAgICAgICAgICAgICAgPHRkIGNsYXNzPVwicC0yIGZvbnQtbW9ubyB0ZXh0LXhzXCI+XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgPGlucHV0XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHR5cGU9XCJ0ZXh0XCJcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY2xhc3M9XCJpbnB1dCB0ZXh0LXhzIGZvbnQtbW9ubyB3LWZ1bGxcIlxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBhdXRvY29tcGxldGU9XCJvZmZcIlxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzcGVsbGNoZWNrPVwiZmFsc2VcIlxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBkYXRhLWVkaXQtc2VjcmV0PVwiJHtrZXkuaWR9XCJcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdmFsdWU9XCIke2VzY2FwZUF0dHIoc3RhdGUuZWRpdFNlY3JldCl9XCJcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAvPlxuICAgICAgICAgICAgICAgICAgICAgICAgPC90ZD5cbiAgICAgICAgICAgICAgICAgICAgICAgIDx0ZCBjbGFzcz1cInAtMiB0ZXh0LXJpZ2h0IHdoaXRlc3BhY2Utbm93cmFwXCI+XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgPGJ1dHRvbiBjbGFzcz1cImJ1dHRvbiB0ZXh0LXhzXCIgZGF0YS1hY3Rpb249XCJzYXZlLWVkaXRcIj5TYXZlPC9idXR0b24+XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgPGJ1dHRvbiBjbGFzcz1cImJ1dHRvbiB0ZXh0LXhzXCIgZGF0YS1hY3Rpb249XCJjYW5jZWwtZWRpdFwiPkNhbmNlbDwvYnV0dG9uPlxuICAgICAgICAgICAgICAgICAgICAgICAgPC90ZD5cbiAgICAgICAgICAgICAgICAgICAgPC90cj5cbiAgICAgICAgICAgICAgICBgO1xuICAgICAgICAgICAgfVxuICAgICAgICAgICAgY29uc3QgZGlzcGxheVNlY3JldCA9IHN0YXRlLnJldmVhbGVkSWQgPT09IGtleS5pZCA/IGVzY2FwZUh0bWwoa2V5LnNlY3JldCkgOiBlc2NhcGVIdG1sKG1hc2tTZWNyZXQoa2V5LnNlY3JldCkpO1xuICAgICAgICAgICAgY29uc3QgY29weUxhYmVsID0gc3RhdGUuY29waWVkSWQgPT09IGtleS5pZCA/ICdDb3BpZWQhJyA6ICdDb3B5JztcbiAgICAgICAgICAgIHJldHVybiBgXG4gICAgICAgICAgICAgICAgPHRyIGNsYXNzPVwiYm9yZGVyLWIgYm9yZGVyLW1vbm9rYWktYmctbGlnaHRlciBob3ZlcjpiZy1tb25va2FpLWJnLWxpZ2h0ZXJcIj5cbiAgICAgICAgICAgICAgICAgICAgPHRkIGNsYXNzPVwicC0yXCI+XG4gICAgICAgICAgICAgICAgICAgICAgICA8c3BhbiBjbGFzcz1cImN1cnNvci1wb2ludGVyIGhvdmVyOnVuZGVybGluZVwiIGRhdGEtYWN0aW9uPVwic3RhcnQtZWRpdFwiIGRhdGEta2V5LWlkPVwiJHtrZXkuaWR9XCI+JHtlc2NhcGVIdG1sKGtleS5sYWJlbCl9PC9zcGFuPlxuICAgICAgICAgICAgICAgICAgICA8L3RkPlxuICAgICAgICAgICAgICAgICAgICA8dGQgY2xhc3M9XCJwLTIgZm9udC1tb25vIHRleHQteHNcIj5cbiAgICAgICAgICAgICAgICAgICAgICAgIDxzcGFuIGNsYXNzPVwiY3Vyc29yLXBvaW50ZXJcIiBkYXRhLWFjdGlvbj1cInRvZ2dsZS1yZXZlYWxcIiBkYXRhLWtleS1pZD1cIiR7a2V5LmlkfVwiPiR7ZGlzcGxheVNlY3JldH08L3NwYW4+XG4gICAgICAgICAgICAgICAgICAgIDwvdGQ+XG4gICAgICAgICAgICAgICAgICAgIDx0ZCBjbGFzcz1cInAtMiB0ZXh0LXJpZ2h0IHdoaXRlc3BhY2Utbm93cmFwXCI+XG4gICAgICAgICAgICAgICAgICAgICAgICA8YnV0dG9uIGNsYXNzPVwiYnV0dG9uIHRleHQteHNcIiBkYXRhLWFjdGlvbj1cImNvcHktc2VjcmV0XCIgZGF0YS1rZXktaWQ9XCIke2tleS5pZH1cIj4ke2NvcHlMYWJlbH08L2J1dHRvbj5cbiAgICAgICAgICAgICAgICAgICAgICAgIDxidXR0b24gY2xhc3M9XCJidXR0b24gdGV4dC14c1wiIGRhdGEtYWN0aW9uPVwiZGVsZXRlLWtleVwiIGRhdGEta2V5LWlkPVwiJHtrZXkuaWR9XCI+RGVsPC9idXR0b24+XG4gICAgICAgICAgICAgICAgICAgIDwvdGQ+XG4gICAgICAgICAgICAgICAgPC90cj5cbiAgICAgICAgICAgIGA7XG4gICAgICAgIH0pLmpvaW4oJycpO1xuXG4gICAgICAgIC8vIEJpbmQgdGFibGUgZXZlbnRzXG4gICAgICAgIGtleVRhYmxlQm9keS5xdWVyeVNlbGVjdG9yQWxsKCdbZGF0YS1hY3Rpb249XCJzdGFydC1lZGl0XCJdJykuZm9yRWFjaChlbCA9PiB7XG4gICAgICAgICAgICBlbC5hZGRFdmVudExpc3RlbmVyKCdjbGljaycsICgpID0+IHN0YXJ0RWRpdChlbC5kYXRhc2V0LmtleUlkKSk7XG4gICAgICAgIH0pO1xuICAgICAgICBrZXlUYWJsZUJvZHkucXVlcnlTZWxlY3RvckFsbCgnW2RhdGEtYWN0aW9uPVwidG9nZ2xlLXJldmVhbFwiXScpLmZvckVhY2goZWwgPT4ge1xuICAgICAgICAgICAgZWwuYWRkRXZlbnRMaXN0ZW5lcignY2xpY2snLCAoKSA9PiB7XG4gICAgICAgICAgICAgICAgc3RhdGUucmV2ZWFsZWRJZCA9IHN0YXRlLnJldmVhbGVkSWQgPT09IGVsLmRhdGFzZXQua2V5SWQgPyBudWxsIDogZWwuZGF0YXNldC5rZXlJZDtcbiAgICAgICAgICAgICAgICByZW5kZXIoKTtcbiAgICAgICAgICAgIH0pO1xuICAgICAgICB9KTtcbiAgICAgICAga2V5VGFibGVCb2R5LnF1ZXJ5U2VsZWN0b3JBbGwoJ1tkYXRhLWFjdGlvbj1cImNvcHktc2VjcmV0XCJdJykuZm9yRWFjaChlbCA9PiB7XG4gICAgICAgICAgICBlbC5hZGRFdmVudExpc3RlbmVyKCdjbGljaycsICgpID0+IGNvcHlTZWNyZXQoZWwuZGF0YXNldC5rZXlJZCkpO1xuICAgICAgICB9KTtcbiAgICAgICAga2V5VGFibGVCb2R5LnF1ZXJ5U2VsZWN0b3JBbGwoJ1tkYXRhLWFjdGlvbj1cImRlbGV0ZS1rZXlcIl0nKS5mb3JFYWNoKGVsID0+IHtcbiAgICAgICAgICAgIGVsLmFkZEV2ZW50TGlzdGVuZXIoJ2NsaWNrJywgKCkgPT4gZGVsZXRlS2V5KGVsLmRhdGFzZXQua2V5SWQpKTtcbiAgICAgICAgfSk7XG4gICAgICAgIGtleVRhYmxlQm9keS5xdWVyeVNlbGVjdG9yQWxsKCdbZGF0YS1hY3Rpb249XCJzYXZlLWVkaXRcIl0nKS5mb3JFYWNoKGVsID0+IHtcbiAgICAgICAgICAgIGVsLmFkZEV2ZW50TGlzdGVuZXIoJ2NsaWNrJywgc2F2ZUVkaXQpO1xuICAgICAgICB9KTtcbiAgICAgICAga2V5VGFibGVCb2R5LnF1ZXJ5U2VsZWN0b3JBbGwoJ1tkYXRhLWFjdGlvbj1cImNhbmNlbC1lZGl0XCJdJykuZm9yRWFjaChlbCA9PiB7XG4gICAgICAgICAgICBlbC5hZGRFdmVudExpc3RlbmVyKCdjbGljaycsIGNhbmNlbEVkaXQpO1xuICAgICAgICB9KTtcblxuICAgICAgICAvLyBCaW5kIGVkaXQgaW5wdXQgZXZlbnRzXG4gICAgICAgIGtleVRhYmxlQm9keS5xdWVyeVNlbGVjdG9yQWxsKCdbZGF0YS1lZGl0LWxhYmVsXScpLmZvckVhY2goZWwgPT4ge1xuICAgICAgICAgICAgZWwuYWRkRXZlbnRMaXN0ZW5lcignaW5wdXQnLCAoZSkgPT4geyBzdGF0ZS5lZGl0TGFiZWwgPSBlLnRhcmdldC52YWx1ZTsgfSk7XG4gICAgICAgICAgICBlbC5hZGRFdmVudExpc3RlbmVyKCdrZXl1cCcsIChlKSA9PiB7XG4gICAgICAgICAgICAgICAgaWYgKGUua2V5ID09PSAnRW50ZXInKSBzYXZlRWRpdCgpO1xuICAgICAgICAgICAgICAgIGlmIChlLmtleSA9PT0gJ0VzY2FwZScpIGNhbmNlbEVkaXQoKTtcbiAgICAgICAgICAgIH0pO1xuICAgICAgICB9KTtcbiAgICAgICAga2V5VGFibGVCb2R5LnF1ZXJ5U2VsZWN0b3JBbGwoJ1tkYXRhLWVkaXQtc2VjcmV0XScpLmZvckVhY2goZWwgPT4ge1xuICAgICAgICAgICAgZWwuYWRkRXZlbnRMaXN0ZW5lcignaW5wdXQnLCAoZSkgPT4geyBzdGF0ZS5lZGl0U2VjcmV0ID0gZS50YXJnZXQudmFsdWU7IH0pO1xuICAgICAgICAgICAgZWwuYWRkRXZlbnRMaXN0ZW5lcigna2V5dXAnLCAoZSkgPT4ge1xuICAgICAgICAgICAgICAgIGlmIChlLmtleSA9PT0gJ0VudGVyJykgc2F2ZUVkaXQoKTtcbiAgICAgICAgICAgICAgICBpZiAoZS5rZXkgPT09ICdFc2NhcGUnKSBjYW5jZWxFZGl0KCk7XG4gICAgICAgICAgICB9KTtcbiAgICAgICAgfSk7XG4gICAgfVxuXG4gICAgLy8gQWRkIGtleSBmb3JtXG4gICAgY29uc3QgbmV3TGFiZWxJbnB1dCA9ICQoJ25ldy1sYWJlbCcpO1xuICAgIGNvbnN0IG5ld1NlY3JldElucHV0ID0gJCgnbmV3LXNlY3JldCcpO1xuICAgIGNvbnN0IGFkZEtleUJ0biA9ICQoJ2FkZC1rZXktYnRuJyk7XG5cbiAgICBpZiAobmV3TGFiZWxJbnB1dCAmJiBkb2N1bWVudC5hY3RpdmVFbGVtZW50ICE9PSBuZXdMYWJlbElucHV0KSBuZXdMYWJlbElucHV0LnZhbHVlID0gc3RhdGUubmV3TGFiZWw7XG4gICAgaWYgKG5ld1NlY3JldElucHV0ICYmIGRvY3VtZW50LmFjdGl2ZUVsZW1lbnQgIT09IG5ld1NlY3JldElucHV0KSBuZXdTZWNyZXRJbnB1dC52YWx1ZSA9IHN0YXRlLm5ld1NlY3JldDtcbiAgICBpZiAoYWRkS2V5QnRuKSB7XG4gICAgICAgIGFkZEtleUJ0bi5kaXNhYmxlZCA9IHN0YXRlLnNhdmluZyB8fCBzdGF0ZS5uZXdMYWJlbC50cmltKCkubGVuZ3RoID09PSAwIHx8IHN0YXRlLm5ld1NlY3JldC50cmltKCkubGVuZ3RoID09PSAwO1xuICAgICAgICBhZGRLZXlCdG4udGV4dENvbnRlbnQgPSBzdGF0ZS5zYXZpbmcgPyAnU2F2aW5nLi4uJyA6ICdTYXZlJztcbiAgICB9XG5cbiAgICAvLyBUb2FzdFxuICAgIGNvbnN0IHRvYXN0ID0gJCgndG9hc3QnKTtcbiAgICBpZiAodG9hc3QpIHtcbiAgICAgICAgdG9hc3QudGV4dENvbnRlbnQgPSBzdGF0ZS50b2FzdDtcbiAgICAgICAgdG9hc3Quc3R5bGUuZGlzcGxheSA9IHN0YXRlLnRvYXN0ID8gJ2Jsb2NrJyA6ICdub25lJztcbiAgICB9XG59XG5cbmZ1bmN0aW9uIGVzY2FwZUh0bWwoc3RyKSB7XG4gICAgY29uc3QgZGl2ID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnZGl2Jyk7XG4gICAgZGl2LnRleHRDb250ZW50ID0gc3RyO1xuICAgIHJldHVybiBkaXYuaW5uZXJIVE1MO1xufVxuXG5mdW5jdGlvbiBlc2NhcGVBdHRyKHN0cikge1xuICAgIHJldHVybiBzdHIucmVwbGFjZSgvJi9nLCAnJmFtcDsnKS5yZXBsYWNlKC9cIi9nLCAnJnF1b3Q7JykucmVwbGFjZSgvPC9nLCAnJmx0OycpLnJlcGxhY2UoLz4vZywgJyZndDsnKTtcbn1cblxuLy8gLS0tIENSVUQgLS0tXG5cbmFzeW5jIGZ1bmN0aW9uIGFkZEtleSgpIHtcbiAgICBjb25zdCBsYWJlbCA9IHN0YXRlLm5ld0xhYmVsLnRyaW0oKTtcbiAgICBjb25zdCBzZWNyZXQgPSBzdGF0ZS5uZXdTZWNyZXQudHJpbSgpO1xuICAgIGlmICghbGFiZWwgfHwgIXNlY3JldCkgcmV0dXJuO1xuXG4gICAgc3RhdGUuc2F2aW5nID0gdHJ1ZTtcbiAgICByZW5kZXIoKTtcblxuICAgIGNvbnN0IGlkID0gY3J5cHRvLnJhbmRvbVVVSUQoKTtcbiAgICBhd2FpdCBzYXZlQXBpS2V5KGlkLCBsYWJlbCwgc2VjcmV0KTtcbiAgICBzdGF0ZS5rZXlzID0gYXdhaXQgbGlzdEFwaUtleXMoKTtcbiAgICBzdGF0ZS5uZXdMYWJlbCA9ICcnO1xuICAgIHN0YXRlLm5ld1NlY3JldCA9ICcnO1xuXG4gICAgaWYgKHN0YXRlLnN5bmNFbmFibGVkICYmIGhhc1JlbGF5cygpKSB7XG4gICAgICAgIGF3YWl0IHB1Ymxpc2hUb1JlbGF5KCk7XG4gICAgfVxuXG4gICAgc3RhdGUuc2F2aW5nID0gZmFsc2U7XG4gICAgc2hvd1RvYXN0KCdLZXkgYWRkZWQnKTtcbn1cblxuZnVuY3Rpb24gc3RhcnRFZGl0KGlkKSB7XG4gICAgY29uc3Qga2V5ID0gc3RhdGUua2V5cy5maW5kKGsgPT4gay5pZCA9PT0gaWQpO1xuICAgIGlmICgha2V5KSByZXR1cm47XG4gICAgc3RhdGUuZWRpdGluZ0lkID0ga2V5LmlkO1xuICAgIHN0YXRlLmVkaXRMYWJlbCA9IGtleS5sYWJlbDtcbiAgICBzdGF0ZS5lZGl0U2VjcmV0ID0ga2V5LnNlY3JldDtcbiAgICByZW5kZXIoKTtcbn1cblxuYXN5bmMgZnVuY3Rpb24gc2F2ZUVkaXQoKSB7XG4gICAgaWYgKCFzdGF0ZS5lZGl0aW5nSWQpIHJldHVybjtcbiAgICBjb25zdCBsYWJlbCA9IHN0YXRlLmVkaXRMYWJlbC50cmltKCk7XG4gICAgY29uc3Qgc2VjcmV0ID0gc3RhdGUuZWRpdFNlY3JldC50cmltKCk7XG4gICAgaWYgKCFsYWJlbCB8fCAhc2VjcmV0KSByZXR1cm47XG5cbiAgICBhd2FpdCBzYXZlQXBpS2V5KHN0YXRlLmVkaXRpbmdJZCwgbGFiZWwsIHNlY3JldCk7XG4gICAgc3RhdGUua2V5cyA9IGF3YWl0IGxpc3RBcGlLZXlzKCk7XG4gICAgc3RhdGUuZWRpdGluZ0lkID0gbnVsbDtcbiAgICBzdGF0ZS5lZGl0TGFiZWwgPSAnJztcbiAgICBzdGF0ZS5lZGl0U2VjcmV0ID0gJyc7XG5cbiAgICBpZiAoc3RhdGUuc3luY0VuYWJsZWQgJiYgaGFzUmVsYXlzKCkpIHtcbiAgICAgICAgYXdhaXQgcHVibGlzaFRvUmVsYXkoKTtcbiAgICB9XG5cbiAgICBzaG93VG9hc3QoJ0tleSB1cGRhdGVkJyk7XG59XG5cbmZ1bmN0aW9uIGNhbmNlbEVkaXQoKSB7XG4gICAgc3RhdGUuZWRpdGluZ0lkID0gbnVsbDtcbiAgICBzdGF0ZS5lZGl0TGFiZWwgPSAnJztcbiAgICBzdGF0ZS5lZGl0U2VjcmV0ID0gJyc7XG4gICAgcmVuZGVyKCk7XG59XG5cbmFzeW5jIGZ1bmN0aW9uIGRlbGV0ZUtleShpZCkge1xuICAgIGNvbnN0IGtleSA9IHN0YXRlLmtleXMuZmluZChrID0+IGsuaWQgPT09IGlkKTtcbiAgICBpZiAoIWtleSkgcmV0dXJuO1xuICAgIGlmICghY29uZmlybShgRGVsZXRlIFwiJHtrZXkubGFiZWx9XCI/YCkpIHJldHVybjtcblxuICAgIGF3YWl0IGRlbGV0ZUFwaUtleShpZCk7XG4gICAgc3RhdGUua2V5cyA9IGF3YWl0IGxpc3RBcGlLZXlzKCk7XG5cbiAgICBpZiAoc3RhdGUuc3luY0VuYWJsZWQgJiYgaGFzUmVsYXlzKCkpIHtcbiAgICAgICAgYXdhaXQgcHVibGlzaFRvUmVsYXkoKTtcbiAgICB9XG5cbiAgICBzaG93VG9hc3QoJ0tleSBkZWxldGVkJyk7XG59XG5cbi8vIC0tLSBDbGlwYm9hcmQgLS0tXG5cbmFzeW5jIGZ1bmN0aW9uIGNvcHlTZWNyZXQoaWQpIHtcbiAgICBjb25zdCBrZXkgPSBzdGF0ZS5rZXlzLmZpbmQoayA9PiBrLmlkID09PSBpZCk7XG4gICAgaWYgKCFrZXkpIHJldHVybjtcbiAgICBhd2FpdCBuYXZpZ2F0b3IuY2xpcGJvYXJkLndyaXRlVGV4dChrZXkuc2VjcmV0KTtcbiAgICBzdGF0ZS5jb3BpZWRJZCA9IGlkO1xuICAgIHJlbmRlcigpO1xuICAgIHNldFRpbWVvdXQoKCkgPT4geyBzdGF0ZS5jb3BpZWRJZCA9IG51bGw7IHJlbmRlcigpOyB9LCAyMDAwKTtcbiAgICBzZXRUaW1lb3V0KCgpID0+IHtcbiAgICAgICAgbmF2aWdhdG9yLmNsaXBib2FyZC53cml0ZVRleHQoJycpLmNhdGNoKCgpID0+IHt9KTtcbiAgICB9LCAzMDAwMCk7XG59XG5cbi8vIC0tLSBTeW5jIC0tLVxuXG5hc3luYyBmdW5jdGlvbiBwdWJsaXNoVG9SZWxheSgpIHtcbiAgICB0cnkge1xuICAgICAgICBjb25zdCBzdG9yZSA9IGF3YWl0IGdldEFwaUtleVN0b3JlKCk7XG4gICAgICAgIGNvbnN0IHJlc3VsdCA9IGF3YWl0IGFwaS5ydW50aW1lLnNlbmRNZXNzYWdlKHtcbiAgICAgICAgICAgIGtpbmQ6ICdhcGlrZXlzLnB1Ymxpc2gnLFxuICAgICAgICAgICAgcGF5bG9hZDogeyBrZXlzOiBzdG9yZS5rZXlzIH0sXG4gICAgICAgIH0pO1xuICAgICAgICBpZiAocmVzdWx0LnN1Y2Nlc3MpIHtcbiAgICAgICAgICAgIGF3YWl0IHVwZGF0ZVN0b3JlU3luY1N0YXRlKCdzeW5jZWQnLCByZXN1bHQuZXZlbnRJZCwgcmVzdWx0LmNyZWF0ZWRBdCk7XG4gICAgICAgIH1cbiAgICAgICAgcmV0dXJuIHJlc3VsdDtcbiAgICB9IGNhdGNoIChlKSB7XG4gICAgICAgIGF3YWl0IHVwZGF0ZVN0b3JlU3luY1N0YXRlKCdsb2NhbC1vbmx5Jyk7XG4gICAgICAgIHJldHVybiB7IHN1Y2Nlc3M6IGZhbHNlLCBlcnJvcjogZS5tZXNzYWdlIH07XG4gICAgfVxufVxuXG5hc3luYyBmdW5jdGlvbiBzeW5jQWxsKCkge1xuICAgIHN0YXRlLmdsb2JhbFN5bmNTdGF0dXMgPSAnc3luY2luZyc7XG4gICAgc3RhdGUuc3luY0Vycm9yID0gJyc7XG4gICAgcmVuZGVyKCk7XG5cbiAgICB0cnkge1xuICAgICAgICBjb25zdCByZXN1bHQgPSBhd2FpdCBhcGkucnVudGltZS5zZW5kTWVzc2FnZSh7IGtpbmQ6ICdhcGlrZXlzLmZldGNoJyB9KTtcblxuICAgICAgICBpZiAoIXJlc3VsdC5zdWNjZXNzKSB7XG4gICAgICAgICAgICBzdGF0ZS5nbG9iYWxTeW5jU3RhdHVzID0gJ2Vycm9yJztcbiAgICAgICAgICAgIHN0YXRlLnN5bmNFcnJvciA9IHJlc3VsdC5lcnJvciB8fCAnU3luYyBmYWlsZWQnO1xuICAgICAgICAgICAgcmVuZGVyKCk7XG4gICAgICAgICAgICByZXR1cm47XG4gICAgICAgIH1cblxuICAgICAgICBpZiAocmVzdWx0LmtleXMpIHtcbiAgICAgICAgICAgIGNvbnN0IHN0b3JlID0gYXdhaXQgZ2V0QXBpS2V5U3RvcmUoKTtcbiAgICAgICAgICAgIGNvbnN0IGxvY2FsS2V5cyA9IHN0b3JlLmtleXM7XG4gICAgICAgICAgICBjb25zdCBsb2NhbENvdW50ID0gT2JqZWN0LmtleXMobG9jYWxLZXlzKS5sZW5ndGg7XG5cbiAgICAgICAgICAgIGlmIChsb2NhbENvdW50ID09PSAwKSB7XG4gICAgICAgICAgICAgICAgYXdhaXQgaW1wb3J0U3RvcmUocmVzdWx0LmtleXMpO1xuICAgICAgICAgICAgfSBlbHNlIGlmICghc3RvcmUucmVsYXlDcmVhdGVkQXQgfHwgcmVzdWx0LmNyZWF0ZWRBdCA+IHN0b3JlLnJlbGF5Q3JlYXRlZEF0KSB7XG4gICAgICAgICAgICAgICAgYXdhaXQgaW1wb3J0U3RvcmUocmVzdWx0LmtleXMpO1xuICAgICAgICAgICAgfVxuXG4gICAgICAgICAgICBhd2FpdCB1cGRhdGVTdG9yZVN5bmNTdGF0ZSgnc3luY2VkJywgcmVzdWx0LmV2ZW50SWQsIHJlc3VsdC5jcmVhdGVkQXQpO1xuICAgICAgICAgICAgc3RhdGUua2V5cyA9IGF3YWl0IGxpc3RBcGlLZXlzKCk7XG4gICAgICAgIH1cblxuICAgICAgICBzdGF0ZS5nbG9iYWxTeW5jU3RhdHVzID0gJ2lkbGUnO1xuICAgIH0gY2F0Y2ggKGUpIHtcbiAgICAgICAgc3RhdGUuZ2xvYmFsU3luY1N0YXR1cyA9ICdlcnJvcic7XG4gICAgICAgIHN0YXRlLnN5bmNFcnJvciA9IGUubWVzc2FnZSB8fCAnU3luYyBmYWlsZWQnO1xuICAgIH1cblxuICAgIHJlbmRlcigpO1xufVxuXG5hc3luYyBmdW5jdGlvbiB0b2dnbGVTeW5jKCkge1xuICAgIGF3YWl0IHNldFN5bmNFbmFibGVkKHN0YXRlLnN5bmNFbmFibGVkKTtcbiAgICBpZiAoc3RhdGUuc3luY0VuYWJsZWQgJiYgaGFzUmVsYXlzKCkpIHtcbiAgICAgICAgYXdhaXQgc3luY0FsbCgpO1xuICAgIH1cbn1cblxuLy8gLS0tIEltcG9ydCAvIEV4cG9ydCAtLS1cblxuYXN5bmMgZnVuY3Rpb24gZXhwb3J0S2V5cygpIHtcbiAgICBjb25zdCBrZXlzID0gYXdhaXQgZXhwb3J0U3RvcmUoKTtcbiAgICBjb25zdCBwbGFpblRleHQgPSBKU09OLnN0cmluZ2lmeShrZXlzLCBudWxsLCAyKTtcblxuICAgIGNvbnN0IHJlc3VsdCA9IGF3YWl0IGFwaS5ydW50aW1lLnNlbmRNZXNzYWdlKHtcbiAgICAgICAga2luZDogJ2FwaWtleXMuZW5jcnlwdCcsXG4gICAgICAgIHBheWxvYWQ6IHsgcGxhaW5UZXh0IH0sXG4gICAgfSk7XG5cbiAgICBpZiAoIXJlc3VsdC5zdWNjZXNzKSB7XG4gICAgICAgIHNob3dUb2FzdCgnRXhwb3J0IGZhaWxlZDogJyArIChyZXN1bHQuZXJyb3IgfHwgJ3Vua25vd24nKSk7XG4gICAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICBjb25zdCBibG9iID0gbmV3IEJsb2IoXG4gICAgICAgIFtKU09OLnN0cmluZ2lmeSh7IGVuY3J5cHRlZDogdHJ1ZSwgZGF0YTogcmVzdWx0LmNpcGhlclRleHQgfSldLFxuICAgICAgICB7IHR5cGU6ICdhcHBsaWNhdGlvbi9qc29uJyB9LFxuICAgICk7XG4gICAgY29uc3QgdXJsID0gVVJMLmNyZWF0ZU9iamVjdFVSTChibG9iKTtcbiAgICBjb25zdCBhID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnYScpO1xuICAgIGEuaHJlZiA9IHVybDtcbiAgICBhLmRvd25sb2FkID0gJ25vc3Rya2V5LWFwaS1rZXlzLWJhY2t1cC5qc29uJztcbiAgICBhLmNsaWNrKCk7XG4gICAgVVJMLnJldm9rZU9iamVjdFVSTCh1cmwpO1xuICAgIHNob3dUb2FzdCgnRXhwb3J0ZWQnKTtcbn1cblxuYXN5bmMgZnVuY3Rpb24gaW1wb3J0S2V5cyhldmVudCkge1xuICAgIGNvbnN0IGZpbGUgPSBldmVudC50YXJnZXQuZmlsZXM/LlswXTtcbiAgICBpZiAoIWZpbGUpIHJldHVybjtcblxuICAgIHRyeSB7XG4gICAgICAgIGNvbnN0IHRleHQgPSBhd2FpdCBmaWxlLnRleHQoKTtcbiAgICAgICAgY29uc3QgcGFyc2VkID0gSlNPTi5wYXJzZSh0ZXh0KTtcblxuICAgICAgICBsZXQga2V5cztcbiAgICAgICAgaWYgKHBhcnNlZC5lbmNyeXB0ZWQgJiYgcGFyc2VkLmRhdGEpIHtcbiAgICAgICAgICAgIGNvbnN0IHJlc3VsdCA9IGF3YWl0IGFwaS5ydW50aW1lLnNlbmRNZXNzYWdlKHtcbiAgICAgICAgICAgICAgICBraW5kOiAnYXBpa2V5cy5kZWNyeXB0JyxcbiAgICAgICAgICAgICAgICBwYXlsb2FkOiB7IGNpcGhlclRleHQ6IHBhcnNlZC5kYXRhIH0sXG4gICAgICAgICAgICB9KTtcbiAgICAgICAgICAgIGlmICghcmVzdWx0LnN1Y2Nlc3MpIHtcbiAgICAgICAgICAgICAgICBzaG93VG9hc3QoJ0RlY3J5cHQgZmFpbGVkOiAnICsgKHJlc3VsdC5lcnJvciB8fCAndW5rbm93bicpKTtcbiAgICAgICAgICAgICAgICByZXR1cm47XG4gICAgICAgICAgICB9XG4gICAgICAgICAgICBrZXlzID0gSlNPTi5wYXJzZShyZXN1bHQucGxhaW5UZXh0KTtcbiAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICAgIGtleXMgPSBwYXJzZWQ7XG4gICAgICAgIH1cblxuICAgICAgICBhd2FpdCBpbXBvcnRTdG9yZShrZXlzKTtcbiAgICAgICAgc3RhdGUua2V5cyA9IGF3YWl0IGxpc3RBcGlLZXlzKCk7XG5cbiAgICAgICAgaWYgKHN0YXRlLnN5bmNFbmFibGVkICYmIGhhc1JlbGF5cygpKSB7XG4gICAgICAgICAgICBhd2FpdCBwdWJsaXNoVG9SZWxheSgpO1xuICAgICAgICB9XG5cbiAgICAgICAgc2hvd1RvYXN0KCdJbXBvcnRlZCAnICsgT2JqZWN0LmtleXMoa2V5cykubGVuZ3RoICsgJyBrZXlzJyk7XG4gICAgfSBjYXRjaCAoZSkge1xuICAgICAgICBzaG93VG9hc3QoJ0ltcG9ydCBmYWlsZWQ6ICcgKyBlLm1lc3NhZ2UpO1xuICAgIH1cblxuICAgIGV2ZW50LnRhcmdldC52YWx1ZSA9ICcnO1xufVxuXG4vLyAtLS0gRXZlbnQgYmluZGluZyAtLS1cblxuZnVuY3Rpb24gYmluZEV2ZW50cygpIHtcbiAgICAkKCdzeW5jLWJ0bicpPy5hZGRFdmVudExpc3RlbmVyKCdjbGljaycsIHN5bmNBbGwpO1xuICAgICQoJ2FkZC1rZXktYnRuJyk/LmFkZEV2ZW50TGlzdGVuZXIoJ2NsaWNrJywgYWRkS2V5KTtcbiAgICAkKCdleHBvcnQtYnRuJyk/LmFkZEV2ZW50TGlzdGVuZXIoJ2NsaWNrJywgZXhwb3J0S2V5cyk7XG4gICAgJCgnaW1wb3J0LWZpbGUnKT8uYWRkRXZlbnRMaXN0ZW5lcignY2hhbmdlJywgaW1wb3J0S2V5cyk7XG4gICAgJCgnY2xvc2UtYnRuJyk/LmFkZEV2ZW50TGlzdGVuZXIoJ2NsaWNrJywgKCkgPT4gd2luZG93LmNsb3NlKCkpO1xuXG4gICAgJCgnc3luYy10b2dnbGUnKT8uYWRkRXZlbnRMaXN0ZW5lcignY2hhbmdlJywgKGUpID0+IHtcbiAgICAgICAgc3RhdGUuc3luY0VuYWJsZWQgPSBlLnRhcmdldC5jaGVja2VkO1xuICAgICAgICB0b2dnbGVTeW5jKCk7XG4gICAgfSk7XG5cbiAgICAkKCduZXctbGFiZWwnKT8uYWRkRXZlbnRMaXN0ZW5lcignaW5wdXQnLCAoZSkgPT4ge1xuICAgICAgICBzdGF0ZS5uZXdMYWJlbCA9IGUudGFyZ2V0LnZhbHVlO1xuICAgICAgICByZW5kZXIoKTtcbiAgICB9KTtcblxuICAgICQoJ25ldy1zZWNyZXQnKT8uYWRkRXZlbnRMaXN0ZW5lcignaW5wdXQnLCAoZSkgPT4ge1xuICAgICAgICBzdGF0ZS5uZXdTZWNyZXQgPSBlLnRhcmdldC52YWx1ZTtcbiAgICAgICAgcmVuZGVyKCk7XG4gICAgfSk7XG59XG5cbmFzeW5jIGZ1bmN0aW9uIGluaXQoKSB7XG4gICAgLy8gR2F0ZTogcmVxdWlyZSBtYXN0ZXIgcGFzc3dvcmQgYmVmb3JlIGFsbG93aW5nIGFjY2Vzc1xuICAgIGNvbnN0IGlzRW5jcnlwdGVkID0gYXdhaXQgYXBpLnJ1bnRpbWUuc2VuZE1lc3NhZ2UoeyBraW5kOiAnaXNFbmNyeXB0ZWQnIH0pO1xuICAgIGNvbnN0IGdhdGUgPSAkKCd2YXVsdC1sb2NrZWQtZ2F0ZScpO1xuICAgIGNvbnN0IG1haW4gPSAkKCd2YXVsdC1tYWluLWNvbnRlbnQnKTtcblxuICAgIGlmICghaXNFbmNyeXB0ZWQpIHtcbiAgICAgICAgaWYgKGdhdGUpIGdhdGUuc3R5bGUuZGlzcGxheSA9ICdibG9jayc7XG4gICAgICAgIGlmIChtYWluKSBtYWluLnN0eWxlLmRpc3BsYXkgPSAnbm9uZSc7XG4gICAgICAgICQoJ2dhdGUtc2VjdXJpdHktYnRuJyk/LmFkZEV2ZW50TGlzdGVuZXIoJ2NsaWNrJywgKCkgPT4ge1xuICAgICAgICAgICAgY29uc3QgdXJsID0gYXBpLnJ1bnRpbWUuZ2V0VVJMKCdzZWN1cml0eS9zZWN1cml0eS5odG1sJyk7XG4gICAgICAgICAgICB3aW5kb3cub3Blbih1cmwsICdub3N0cmtleS1vcHRpb25zJyk7XG4gICAgICAgIH0pO1xuICAgICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgaWYgKGdhdGUpIGdhdGUuc3R5bGUuZGlzcGxheSA9ICdub25lJztcbiAgICBpZiAobWFpbikgbWFpbi5zdHlsZS5kaXNwbGF5ID0gJ2Jsb2NrJztcblxuICAgIGNvbnN0IHJlbGF5cyA9IGF3YWl0IGFwaS5ydW50aW1lLnNlbmRNZXNzYWdlKHsga2luZDogJ3ZhdWx0LmdldFJlbGF5cycgfSk7XG4gICAgc3RhdGUucmVsYXlJbmZvID0gcmVsYXlzIHx8IHsgcmVhZDogW10sIHdyaXRlOiBbXSB9O1xuICAgIHN0YXRlLnN5bmNFbmFibGVkID0gYXdhaXQgaXNTeW5jRW5hYmxlZCgpO1xuICAgIHN0YXRlLmtleXMgPSBhd2FpdCBsaXN0QXBpS2V5cygpO1xuXG4gICAgYmluZEV2ZW50cygpO1xuICAgIHJlbmRlcigpO1xuXG4gICAgaWYgKHN0YXRlLnN5bmNFbmFibGVkICYmIGhhc1JlbGF5cygpKSB7XG4gICAgICAgIGF3YWl0IHN5bmNBbGwoKTtcbiAgICB9XG59XG5cbmRvY3VtZW50LmFkZEV2ZW50TGlzdGVuZXIoJ0RPTUNvbnRlbnRMb2FkZWQnLCBpbml0KTtcbiJdLAogICJtYXBwaW5ncyI6ICI7O0FBZ0JBLE1BQU0sV0FDRixPQUFPLFlBQVksY0FBYyxVQUNqQyxPQUFPLFdBQVksY0FBYyxTQUNqQztBQUVKLE1BQUksQ0FBQyxV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 diff --git a/distros/safari/background.build.js b/distros/safari/background.build.js index aff78a2..52b15bd 100644 --- a/distros/safari/background.build.js +++ b/distros/safari/background.build.js @@ -1,5 +1,7172 @@ -(()=>{var Qa=Object.create;var kn=Object.defineProperty;var ec=Object.getOwnPropertyDescriptor;var tc=Object.getOwnPropertyNames;var rc=Object.getPrototypeOf,nc=Object.prototype.hasOwnProperty;var oc=(t,e)=>()=>(t&&(e=t(t=0)),e);var bt=(t,e)=>()=>(e||t((e={exports:{}}).exports,e),e.exports),An=(t,e)=>{for(var r in e)kn(t,r,{get:e[r],enumerable:!0})},ic=(t,e,r,n)=>{if(e&&typeof e=="object"||typeof e=="function")for(let o of tc(e))!nc.call(t,o)&&o!==r&&kn(t,o,{get:()=>e[o],enumerable:!(n=ec(e,o))||n.enumerable});return t};var er=(t,e,r)=>(r=t!=null?Qa(rc(t)):{},ic(e||!t||!t.__esModule?kn(r,"default",{value:t,enumerable:!0}):r,t));var R,b=oc(()=>{R={env:{NODE_ENV:"production",LOG_LEVEL:"warn"},browser:!0,version:"",stdout:null,stderr:null,nextTick:function(t){var e=Array.prototype.slice.call(arguments,1);Promise.resolve().then(function(){t.apply(null,e)})}}});var es=bt((kd,Qi)=>{"use strict";b();function _c(t){try{return JSON.stringify(t)}catch{return'"[Circular]"'}}Qi.exports=Lc;function Lc(t,e,r){var n=r&&r.stringify||_c,o=1;if(typeof t=="object"&&t!==null){var i=e.length+o;if(i===1)return t;var s=new Array(i);s[0]=n(t);for(var a=1;a-1?u:0,t.charCodeAt(d+1)){case 100:case 102:if(f>=c||e[f]==null)break;u=c||e[f]==null)break;u=c||e[f]===void 0)break;u",u=d+2,d++;break}l+=n(e[f]),u=d+2,d++;break;case 115:if(f>=c)break;u{"use strict";b();var ts=es();Mr.exports=rt;var cr=jc().console||{},Uc={mapHttpRequest:Dr,mapHttpResponse:Dr,wrapRequestSerializer:Jn,wrapResponseSerializer:Jn,wrapErrorSerializer:Jn,req:Dr,res:Dr,err:ns,errWithCause:ns};function ht(t,e){return t==="silent"?1/0:e.levels.values[t]}var eo=Symbol("pino.logFuncs"),Xn=Symbol("pino.hierarchy"),Pc={error:"log",fatal:"error",warn:"error",info:"log",debug:"log",trace:"log"};function rs(t,e){let r={logger:e,parent:t[Xn]};e[Xn]=r}function Rc(t,e,r){let n={};e.forEach(o=>{n[o]=r[o]?r[o]:cr[o]||cr[Pc[o]||"log"]||Vt}),t[eo]=n}function Cc(t,e){return Array.isArray(t)?t.filter(function(n){return n!=="!stdSerializers.err"}):t===!0?Object.keys(e):!1}function rt(t){t=t||{},t.browser=t.browser||{};let e=t.browser.transmit;if(e&&typeof e.send!="function")throw Error("pino: transmit option must have a send function");let r=t.browser.write||cr;t.browser.write&&(t.browser.asObject=!0);let n=t.serializers||{},o=Cc(t.browser.serialize,n),i=t.browser.serialize;Array.isArray(t.browser.serialize)&&t.browser.serialize.indexOf("!stdSerializers.err")>-1&&(i=!1);let s=Object.keys(t.customLevels||{}),a=["error","fatal","warn","info","debug","trace"].concat(s);typeof r=="function"&&a.forEach(function(p){r[p]=r}),(t.enabled===!1||t.browser.disabled)&&(t.level="silent");let c=t.level||"info",l=Object.create(r);l.log||(l.log=Vt),Rc(l,a,r),rs({},l),Object.defineProperty(l,"levelVal",{get:u}),Object.defineProperty(l,"level",{get:h,set:d});let f={transmit:e,serialize:o,asObject:t.browser.asObject,asObjectBindingsOnly:t.browser.asObjectBindingsOnly,formatters:t.browser.formatters,reportCaller:t.browser.reportCaller,levels:a,timestamp:Fc(t),messageKey:t.messageKey||"msg",onChild:t.onChild||Vt};l.levels=Oc(t),l.level=c,l.isLevelEnabled=function(p){return this.levels.values[p]?this.levels.values[p]>=this.levels.values[this.level]:!1},l.setMaxListeners=l.getMaxListeners=l.emit=l.addListener=l.on=l.prependListener=l.once=l.prependOnceListener=l.removeListener=l.removeAllListeners=l.listeners=l.listenerCount=l.eventNames=l.write=l.flush=Vt,l.serializers=n,l._serialize=o,l._stdErrSerialize=i,l.child=function(...p){return y.call(this,f,...p)},e&&(l._logEvent=Qn());function u(){return ht(this.level,this)}function h(){return this._level}function d(p){if(p!=="silent"&&!this.levels.values[p])throw Error("unknown level "+p);this._level=p,At(this,f,l,"error"),At(this,f,l,"fatal"),At(this,f,l,"warn"),At(this,f,l,"info"),At(this,f,l,"debug"),At(this,f,l,"trace"),s.forEach(w=>{At(this,f,l,w)})}function y(p,w,k){if(!w)throw new Error("missing bindings for child Pino");k=k||{},o&&w.serializers&&(k.serializers=w.serializers);let O=k.serializers;if(o&&O){var D=Object.assign({},n,O),H=t.browser.serialize===!0?Object.keys(D):o;delete w.serializers,to([w],H,D,this._stdErrSerialize)}function X(q){this._childLevel=(q._childLevel|0)+1,this.bindings=w,D&&(this.serializers=D,this._serialize=H),e&&(this._logEvent=Qn([].concat(q._logEvent.bindings,w)))}X.prototype=this;let M=new X(this);return rs(this,M),M.child=function(...q){return y.call(this,p,...q)},M.level=k.level||this.level,p.onChild(M),M}return l}function Oc(t){let e=t.customLevels||{},r=Object.assign({},rt.levels.values,e),n=Object.assign({},rt.levels.labels,Nc(e));return{values:r,labels:n}}function Nc(t){let e={};return Object.keys(t).forEach(function(r){e[t[r]]=r}),e}rt.levels={values:{fatal:60,error:50,warn:40,info:30,debug:20,trace:10},labels:{10:"trace",20:"debug",30:"info",40:"warn",50:"error",60:"fatal"}};rt.stdSerializers=Uc;rt.stdTimeFunctions=Object.assign({},{nullTime:is,epochTime:ss,unixTime:$c,isoTime:qc});function Dc(t){let e=[];t.bindings&&e.push(t.bindings);let r=t[Xn];for(;r.parent;)r=r.parent,r.logger.bindings&&e.push(r.logger.bindings);return e.reverse()}function At(t,e,r,n){if(Object.defineProperty(t,n,{value:ht(t.level,r)>ht(n,r)?Vt:r[eo][n],writable:!0,enumerable:!0,configurable:!0}),t[n]===Vt){if(!e.transmit)return;let i=e.transmit.level||t.level,s=ht(i,r);if(ht(n,r)0&&u[0]&&typeof u[0]=="object")try{let h=os();h&&(u[0].caller=h)}catch{}o.call(c,...u)}else{if(e.reportCaller)try{let u=os();u&&a.push(u)}catch{}o.apply(c,a)}if(e.transmit){let u=e.transmit.level||t._level,h=ht(u,r),d=ht(n,r);if(du}=o.formatters||{},a=r.slice(),c=a[0],l={},f=(t._childLevel|0)+1;if(f<1&&(f=1),n&&(l.time=n),i){let u=i(e,t.levels.values[e]);Object.assign(l,u)}else l.level=t.levels.values[e];if(o.asObjectBindingsOnly){if(c!==null&&typeof c=="object")for(;f--&&typeof a[0]=="object";)Object.assign(l,a.shift());return[s(l),...a]}else{if(c!==null&&typeof c=="object"){for(;f--&&typeof a[0]=="object";)Object.assign(l,a.shift());c=a.length?ts(a.shift(),a):void 0}else typeof c=="string"&&(c=ts(a.shift(),a));return c!==void 0&&(l[o.messageKey]=c),[s(l)]}}function to(t,e,r,n){for(let o in t)if(n&&t[o]instanceof Error)t[o]=rt.stdSerializers.err(t[o]);else if(typeof t[o]=="object"&&!Array.isArray(t[o])&&e)for(let i in t[o])e.indexOf(i)>-1&&i in r&&(t[o][i]=r[i](t[o][i]))}function Vc(t,e,r,n=!1){let o=e.send,i=e.ts,s=e.methodLevel,a=e.methodValue,c=e.val,l=t._logEvent.bindings;n||to(r,t._serialize||Object.keys(t.serializers),t.serializers,t._stdErrSerialize===void 0?!0:t._stdErrSerialize),t._logEvent.ts=i,t._logEvent.messages=r.filter(function(f){return l.indexOf(f)===-1}),t._logEvent.level.label=s,t._logEvent.level.value=a,o(s,t._logEvent,c),t._logEvent=Qn(l)}function Qn(t){return{ts:0,messages:[],bindings:t||[],level:{label:"",value:0}}}function ns(t){let e={type:t.constructor.name,msg:t.message,stack:t.stack};for(let r in t)e[r]===void 0&&(e[r]=t[r]);return e}function Fc(t){return typeof t.timestamp=="function"?t.timestamp:t.timestamp===!1?is:ss}function Dr(){return{}}function Jn(t){return t}function Vt(){}function is(){return!1}function ss(){return Date.now()}function $c(){return Math.round(Date.now()/1e3)}function qc(){return new Date(Date.now()).toISOString()}function jc(){function t(e){return typeof e<"u"&&e}try{return typeof globalThis<"u"||Object.defineProperty(Object.prototype,"globalThis",{get:function(){return delete Object.prototype.globalThis,this.globalThis=this},configurable:!0}),globalThis}catch{return t(self)||t(window)||t(this)||{}}}Mr.exports.default=rt;Mr.exports.pino=rt;function os(){let t=new Error().stack;if(!t)return null;let e=t.split(` -`);for(let r=1;r{b();us.exports={}});var bs=bt($t=>{"use strict";b();Object.defineProperty($t,"__esModule",{value:!0});$t.bech32m=$t.bech32=void 0;var Vr="qpzry9x8gf2tvdw0s3jn54khce6mua7l",ms={};for(let t=0;t>25;return(t&33554431)<<5^-(e>>0&1)&996825010^-(e>>1&1)&642813549^-(e>>2&1)&513874426^-(e>>3&1)&1027748829^-(e>>4&1)&705979059}function gs(t){let e=1;for(let r=0;r126)return"Invalid prefix ("+t+")";e=Ft(e)^n>>5}e=Ft(e);for(let r=0;r=r;)i-=r,a.push(o>>i&s);if(n)i>0&&a.push(o<=e)return"Excess padding";if(o<c)throw new TypeError("Exceeds length limit");s=s.toLowerCase();let l=gs(s);if(typeof l=="string")throw new Error(l);let f=s+"1";for(let u=0;u>5!==0)throw new Error("Non 5-bit word");l=Ft(l)^h,f+=Vr.charAt(h)}for(let u=0;u<6;++u)l=Ft(l);l^=e;for(let u=0;u<6;++u){let h=l>>(5-u)*5&31;f+=Vr.charAt(h)}return f}function n(s,a){if(a=a||90,s.length<8)return s+" too short";if(s.length>a)return"Exceeds length limit";let c=s.toLowerCase(),l=s.toUpperCase();if(s!==c&&s!==l)return"Mixed-case string "+s;s=c;let f=s.lastIndexOf("1");if(f===-1)return"No separator character for "+s;if(f===0)return"Missing prefix for "+s;let u=s.slice(0,f),h=s.slice(f+1);if(h.length<6)return"Data too short";let d=gs(u);if(typeof d=="string")return d;let y=[];for(let p=0;p=h.length)&&y.push(k)}return d!==e?"Invalid checksum for "+s:{prefix:u,words:y}}function o(s,a){let c=n(s,a);if(typeof c=="object")return c}function i(s,a){let c=n(s,a);if(typeof c=="object")return c;throw new Error(c)}return{decodeUnsafe:o,decode:i,encode:r,toWords:tl,fromWordsUnsafe:rl,fromWords:nl}}$t.bech32=ws("bech32");$t.bech32m=ws("bech32m")});var vs=bt(Fr=>{"use strict";b();Fr.byteLength=il;Fr.toByteArray=al;Fr.fromByteArray=ul;var ze=[],Ce=[],ol=typeof Uint8Array<"u"?Uint8Array:Array,ao="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";for(Bt=0,xs=ao.length;Bt0)throw new Error("Invalid string. Length must be a multiple of 4");var r=t.indexOf("=");r===-1&&(r=e);var n=r===e?0:4-r%4;return[r,n]}function il(t){var e=Es(t),r=e[0],n=e[1];return(r+n)*3/4-n}function sl(t,e,r){return(e+r)*3/4-r}function al(t){var e,r=Es(t),n=r[0],o=r[1],i=new ol(sl(t,n,o)),s=0,a=o>0?n-4:n,c;for(c=0;c>16&255,i[s++]=e>>8&255,i[s++]=e&255;return o===2&&(e=Ce[t.charCodeAt(c)]<<2|Ce[t.charCodeAt(c+1)]>>4,i[s++]=e&255),o===1&&(e=Ce[t.charCodeAt(c)]<<10|Ce[t.charCodeAt(c+1)]<<4|Ce[t.charCodeAt(c+2)]>>2,i[s++]=e>>8&255,i[s++]=e&255),i}function cl(t){return ze[t>>18&63]+ze[t>>12&63]+ze[t>>6&63]+ze[t&63]}function ll(t,e,r){for(var n,o=[],i=e;ia?a:s+i));return n===1?(e=t[r-1],o.push(ze[e>>2]+ze[e<<4&63]+"==")):n===2&&(e=(t[r-2]<<8)+t[r-1],o.push(ze[e>>10]+ze[e>>4&63]+ze[e<<2&63]+"=")),o.join("")}});var ks=bt(co=>{b();co.read=function(t,e,r,n,o){var i,s,a=o*8-n-1,c=(1<>1,f=-7,u=r?o-1:0,h=r?-1:1,d=t[e+u];for(u+=h,i=d&(1<<-f)-1,d>>=-f,f+=a;f>0;i=i*256+t[e+u],u+=h,f-=8);for(s=i&(1<<-f)-1,i>>=-f,f+=n;f>0;s=s*256+t[e+u],u+=h,f-=8);if(i===0)i=1-l;else{if(i===c)return s?NaN:(d?-1:1)*(1/0);s=s+Math.pow(2,n),i=i-l}return(d?-1:1)*s*Math.pow(2,i-n)};co.write=function(t,e,r,n,o,i){var s,a,c,l=i*8-o-1,f=(1<>1,h=o===23?Math.pow(2,-24)-Math.pow(2,-77):0,d=n?0:i-1,y=n?1:-1,p=e<0||e===0&&1/e<0?1:0;for(e=Math.abs(e),isNaN(e)||e===1/0?(a=isNaN(e)?1:0,s=f):(s=Math.floor(Math.log(e)/Math.LN2),e*(c=Math.pow(2,-s))<1&&(s--,c*=2),s+u>=1?e+=h/c:e+=h*Math.pow(2,1-u),e*c>=2&&(s++,c/=2),s+u>=f?(a=0,s=f):s+u>=1?(a=(e*c-1)*Math.pow(2,o),s=s+u):(a=e*Math.pow(2,u-1)*Math.pow(2,o),s=0));o>=8;t[r+d]=a&255,d+=y,a/=256,o-=8);for(s=s<0;t[r+d]=s&255,d+=y,s/=256,l-=8);t[r+d-y]|=p*128}});var Ks=bt(Wt=>{"use strict";b();var lo=vs(),jt=ks(),As=typeof Symbol=="function"&&typeof Symbol.for=="function"?Symbol.for("nodejs.util.inspect.custom"):null;Wt.Buffer=g;Wt.SlowBuffer=gl;Wt.INSPECT_MAX_BYTES=50;var $r=2147483647;Wt.kMaxLength=$r;g.TYPED_ARRAY_SUPPORT=fl();!g.TYPED_ARRAY_SUPPORT&&typeof console<"u";function fl(){try{let t=new Uint8Array(1),e={foo:function(){return 42}};return Object.setPrototypeOf(e,Uint8Array.prototype),Object.setPrototypeOf(t,e),t.foo()===42}catch{return!1}}Object.defineProperty(g.prototype,"parent",{enumerable:!0,get:function(){if(g.isBuffer(this))return this.buffer}});Object.defineProperty(g.prototype,"offset",{enumerable:!0,get:function(){if(g.isBuffer(this))return this.byteOffset}});function nt(t){if(t>$r)throw new RangeError('The value "'+t+'" is invalid for option "size"');let e=new Uint8Array(t);return Object.setPrototypeOf(e,g.prototype),e}function g(t,e,r){if(typeof t=="number"){if(typeof e=="string")throw new TypeError('The "string" argument must be of type string. Received type number');return po(t)}return Ts(t,e,r)}g.poolSize=8192;function Ts(t,e,r){if(typeof t=="string")return hl(t,e);if(ArrayBuffer.isView(t))return pl(t);if(t==null)throw new TypeError("The first argument must be one of type string, Buffer, ArrayBuffer, Array, or Array-like Object. Received type "+typeof t);if(We(t,ArrayBuffer)||t&&We(t.buffer,ArrayBuffer)||typeof SharedArrayBuffer<"u"&&(We(t,SharedArrayBuffer)||t&&We(t.buffer,SharedArrayBuffer)))return fo(t,e,r);if(typeof t=="number")throw new TypeError('The "value" argument must not be of type number. Received type number');let n=t.valueOf&&t.valueOf();if(n!=null&&n!==t)return g.from(n,e,r);let o=yl(t);if(o)return o;if(typeof Symbol<"u"&&Symbol.toPrimitive!=null&&typeof t[Symbol.toPrimitive]=="function")return g.from(t[Symbol.toPrimitive]("string"),e,r);throw new TypeError("The first argument must be one of type string, Buffer, ArrayBuffer, Array, or Array-like Object. Received type "+typeof t)}g.from=function(t,e,r){return Ts(t,e,r)};Object.setPrototypeOf(g.prototype,Uint8Array.prototype);Object.setPrototypeOf(g,Uint8Array);function _s(t){if(typeof t!="number")throw new TypeError('"size" argument must be of type number');if(t<0)throw new RangeError('The value "'+t+'" is invalid for option "size"')}function dl(t,e,r){return _s(t),t<=0?nt(t):e!==void 0?typeof r=="string"?nt(t).fill(e,r):nt(t).fill(e):nt(t)}g.alloc=function(t,e,r){return dl(t,e,r)};function po(t){return _s(t),nt(t<0?0:yo(t)|0)}g.allocUnsafe=function(t){return po(t)};g.allocUnsafeSlow=function(t){return po(t)};function hl(t,e){if((typeof e!="string"||e==="")&&(e="utf8"),!g.isEncoding(e))throw new TypeError("Unknown encoding: "+e);let r=Ls(t,e)|0,n=nt(r),o=n.write(t,e);return o!==r&&(n=n.slice(0,o)),n}function uo(t){let e=t.length<0?0:yo(t.length)|0,r=nt(e);for(let n=0;n=$r)throw new RangeError("Attempt to allocate Buffer larger than maximum size: 0x"+$r.toString(16)+" bytes");return t|0}function gl(t){return+t!=t&&(t=0),g.alloc(+t)}g.isBuffer=function(e){return e!=null&&e._isBuffer===!0&&e!==g.prototype};g.compare=function(e,r){if(We(e,Uint8Array)&&(e=g.from(e,e.offset,e.byteLength)),We(r,Uint8Array)&&(r=g.from(r,r.offset,r.byteLength)),!g.isBuffer(e)||!g.isBuffer(r))throw new TypeError('The "buf1", "buf2" arguments must be one of type Buffer or Uint8Array');if(e===r)return 0;let n=e.length,o=r.length;for(let i=0,s=Math.min(n,o);io.length?(g.isBuffer(s)||(s=g.from(s)),s.copy(o,i)):Uint8Array.prototype.set.call(o,s,i);else if(g.isBuffer(s))s.copy(o,i);else throw new TypeError('"list" argument must be an Array of Buffers');i+=s.length}return o};function Ls(t,e){if(g.isBuffer(t))return t.length;if(ArrayBuffer.isView(t)||We(t,ArrayBuffer))return t.byteLength;if(typeof t!="string")throw new TypeError('The "string" argument must be one of type string, Buffer, or ArrayBuffer. Received type '+typeof t);let r=t.length,n=arguments.length>2&&arguments[2]===!0;if(!n&&r===0)return 0;let o=!1;for(;;)switch(e){case"ascii":case"latin1":case"binary":return r;case"utf8":case"utf-8":return ho(t).length;case"ucs2":case"ucs-2":case"utf16le":case"utf-16le":return r*2;case"hex":return r>>>1;case"base64":return Hs(t).length;default:if(o)return n?-1:ho(t).length;e=(""+e).toLowerCase(),o=!0}}g.byteLength=Ls;function ml(t,e,r){let n=!1;if((e===void 0||e<0)&&(e=0),e>this.length||((r===void 0||r>this.length)&&(r=this.length),r<=0)||(r>>>=0,e>>>=0,r<=e))return"";for(t||(t="utf8");;)switch(t){case"hex":return Il(this,e,r);case"utf8":case"utf-8":return Ps(this,e,r);case"ascii":return Bl(this,e,r);case"latin1":case"binary":return Sl(this,e,r);case"base64":return kl(this,e,r);case"ucs2":case"ucs-2":case"utf16le":case"utf-16le":return Tl(this,e,r);default:if(n)throw new TypeError("Unknown encoding: "+t);t=(t+"").toLowerCase(),n=!0}}g.prototype._isBuffer=!0;function St(t,e,r){let n=t[e];t[e]=t[r],t[r]=n}g.prototype.swap16=function(){let e=this.length;if(e%2!==0)throw new RangeError("Buffer size must be a multiple of 16-bits");for(let r=0;rr&&(e+=" ... "),""};As&&(g.prototype[As]=g.prototype.inspect);g.prototype.compare=function(e,r,n,o,i){if(We(e,Uint8Array)&&(e=g.from(e,e.offset,e.byteLength)),!g.isBuffer(e))throw new TypeError('The "target" argument must be one of type Buffer or Uint8Array. Received type '+typeof e);if(r===void 0&&(r=0),n===void 0&&(n=e?e.length:0),o===void 0&&(o=0),i===void 0&&(i=this.length),r<0||n>e.length||o<0||i>this.length)throw new RangeError("out of range index");if(o>=i&&r>=n)return 0;if(o>=i)return-1;if(r>=n)return 1;if(r>>>=0,n>>>=0,o>>>=0,i>>>=0,this===e)return 0;let s=i-o,a=n-r,c=Math.min(s,a),l=this.slice(o,i),f=e.slice(r,n);for(let u=0;u2147483647?r=2147483647:r<-2147483648&&(r=-2147483648),r=+r,mo(r)&&(r=o?0:t.length-1),r<0&&(r=t.length+r),r>=t.length){if(o)return-1;r=t.length-1}else if(r<0)if(o)r=0;else return-1;if(typeof e=="string"&&(e=g.from(e,n)),g.isBuffer(e))return e.length===0?-1:Bs(t,e,r,n,o);if(typeof e=="number")return e=e&255,typeof Uint8Array.prototype.indexOf=="function"?o?Uint8Array.prototype.indexOf.call(t,e,r):Uint8Array.prototype.lastIndexOf.call(t,e,r):Bs(t,[e],r,n,o);throw new TypeError("val must be string, number or Buffer")}function Bs(t,e,r,n,o){let i=1,s=t.length,a=e.length;if(n!==void 0&&(n=String(n).toLowerCase(),n==="ucs2"||n==="ucs-2"||n==="utf16le"||n==="utf-16le")){if(t.length<2||e.length<2)return-1;i=2,s/=2,a/=2,r/=2}function c(f,u){return i===1?f[u]:f.readUInt16BE(u*i)}let l;if(o){let f=-1;for(l=r;ls&&(r=s-a),l=r;l>=0;l--){let f=!0;for(let u=0;uo&&(n=o)):n=o;let i=e.length;n>i/2&&(n=i/2);let s;for(s=0;s>>0,isFinite(n)?(n=n>>>0,o===void 0&&(o="utf8")):(o=n,n=void 0);else throw new Error("Buffer.write(string, encoding, offset[, length]) is no longer supported");let i=this.length-r;if((n===void 0||n>i)&&(n=i),e.length>0&&(n<0||r<0)||r>this.length)throw new RangeError("Attempt to write outside buffer bounds");o||(o="utf8");let s=!1;for(;;)switch(o){case"hex":return wl(this,e,r,n);case"utf8":case"utf-8":return bl(this,e,r,n);case"ascii":case"latin1":case"binary":return xl(this,e,r,n);case"base64":return El(this,e,r,n);case"ucs2":case"ucs-2":case"utf16le":case"utf-16le":return vl(this,e,r,n);default:if(s)throw new TypeError("Unknown encoding: "+o);o=(""+o).toLowerCase(),s=!0}};g.prototype.toJSON=function(){return{type:"Buffer",data:Array.prototype.slice.call(this._arr||this,0)}};function kl(t,e,r){return e===0&&r===t.length?lo.fromByteArray(t):lo.fromByteArray(t.slice(e,r))}function Ps(t,e,r){r=Math.min(t.length,r);let n=[],o=e;for(;o239?4:i>223?3:i>191?2:1;if(o+a<=r){let c,l,f,u;switch(a){case 1:i<128&&(s=i);break;case 2:c=t[o+1],(c&192)===128&&(u=(i&31)<<6|c&63,u>127&&(s=u));break;case 3:c=t[o+1],l=t[o+2],(c&192)===128&&(l&192)===128&&(u=(i&15)<<12|(c&63)<<6|l&63,u>2047&&(u<55296||u>57343)&&(s=u));break;case 4:c=t[o+1],l=t[o+2],f=t[o+3],(c&192)===128&&(l&192)===128&&(f&192)===128&&(u=(i&15)<<18|(c&63)<<12|(l&63)<<6|f&63,u>65535&&u<1114112&&(s=u))}}s===null?(s=65533,a=1):s>65535&&(s-=65536,n.push(s>>>10&1023|55296),s=56320|s&1023),n.push(s),o+=a}return Al(n)}var Ss=4096;function Al(t){let e=t.length;if(e<=Ss)return String.fromCharCode.apply(String,t);let r="",n=0;for(;nn)&&(r=n);let o="";for(let i=e;in&&(e=n),r<0?(r+=n,r<0&&(r=0)):r>n&&(r=n),rr)throw new RangeError("Trying to access beyond buffer length")}g.prototype.readUintLE=g.prototype.readUIntLE=function(e,r,n){e=e>>>0,r=r>>>0,n||le(e,r,this.length);let o=this[e],i=1,s=0;for(;++s>>0,r=r>>>0,n||le(e,r,this.length);let o=this[e+--r],i=1;for(;r>0&&(i*=256);)o+=this[e+--r]*i;return o};g.prototype.readUint8=g.prototype.readUInt8=function(e,r){return e=e>>>0,r||le(e,1,this.length),this[e]};g.prototype.readUint16LE=g.prototype.readUInt16LE=function(e,r){return e=e>>>0,r||le(e,2,this.length),this[e]|this[e+1]<<8};g.prototype.readUint16BE=g.prototype.readUInt16BE=function(e,r){return e=e>>>0,r||le(e,2,this.length),this[e]<<8|this[e+1]};g.prototype.readUint32LE=g.prototype.readUInt32LE=function(e,r){return e=e>>>0,r||le(e,4,this.length),(this[e]|this[e+1]<<8|this[e+2]<<16)+this[e+3]*16777216};g.prototype.readUint32BE=g.prototype.readUInt32BE=function(e,r){return e=e>>>0,r||le(e,4,this.length),this[e]*16777216+(this[e+1]<<16|this[e+2]<<8|this[e+3])};g.prototype.readBigUInt64LE=yt(function(e){e=e>>>0,zt(e,"offset");let r=this[e],n=this[e+7];(r===void 0||n===void 0)&&ur(e,this.length-8);let o=r+this[++e]*2**8+this[++e]*2**16+this[++e]*2**24,i=this[++e]+this[++e]*2**8+this[++e]*2**16+n*2**24;return BigInt(o)+(BigInt(i)<>>0,zt(e,"offset");let r=this[e],n=this[e+7];(r===void 0||n===void 0)&&ur(e,this.length-8);let o=r*2**24+this[++e]*2**16+this[++e]*2**8+this[++e],i=this[++e]*2**24+this[++e]*2**16+this[++e]*2**8+n;return(BigInt(o)<>>0,r=r>>>0,n||le(e,r,this.length);let o=this[e],i=1,s=0;for(;++s=i&&(o-=Math.pow(2,8*r)),o};g.prototype.readIntBE=function(e,r,n){e=e>>>0,r=r>>>0,n||le(e,r,this.length);let o=r,i=1,s=this[e+--o];for(;o>0&&(i*=256);)s+=this[e+--o]*i;return i*=128,s>=i&&(s-=Math.pow(2,8*r)),s};g.prototype.readInt8=function(e,r){return e=e>>>0,r||le(e,1,this.length),this[e]&128?(255-this[e]+1)*-1:this[e]};g.prototype.readInt16LE=function(e,r){e=e>>>0,r||le(e,2,this.length);let n=this[e]|this[e+1]<<8;return n&32768?n|4294901760:n};g.prototype.readInt16BE=function(e,r){e=e>>>0,r||le(e,2,this.length);let n=this[e+1]|this[e]<<8;return n&32768?n|4294901760:n};g.prototype.readInt32LE=function(e,r){return e=e>>>0,r||le(e,4,this.length),this[e]|this[e+1]<<8|this[e+2]<<16|this[e+3]<<24};g.prototype.readInt32BE=function(e,r){return e=e>>>0,r||le(e,4,this.length),this[e]<<24|this[e+1]<<16|this[e+2]<<8|this[e+3]};g.prototype.readBigInt64LE=yt(function(e){e=e>>>0,zt(e,"offset");let r=this[e],n=this[e+7];(r===void 0||n===void 0)&&ur(e,this.length-8);let o=this[e+4]+this[e+5]*2**8+this[e+6]*2**16+(n<<24);return(BigInt(o)<>>0,zt(e,"offset");let r=this[e],n=this[e+7];(r===void 0||n===void 0)&&ur(e,this.length-8);let o=(r<<24)+this[++e]*2**16+this[++e]*2**8+this[++e];return(BigInt(o)<>>0,r||le(e,4,this.length),jt.read(this,e,!0,23,4)};g.prototype.readFloatBE=function(e,r){return e=e>>>0,r||le(e,4,this.length),jt.read(this,e,!1,23,4)};g.prototype.readDoubleLE=function(e,r){return e=e>>>0,r||le(e,8,this.length),jt.read(this,e,!0,52,8)};g.prototype.readDoubleBE=function(e,r){return e=e>>>0,r||le(e,8,this.length),jt.read(this,e,!1,52,8)};function ve(t,e,r,n,o,i){if(!g.isBuffer(t))throw new TypeError('"buffer" argument must be a Buffer instance');if(e>o||et.length)throw new RangeError("Index out of range")}g.prototype.writeUintLE=g.prototype.writeUIntLE=function(e,r,n,o){if(e=+e,r=r>>>0,n=n>>>0,!o){let a=Math.pow(2,8*n)-1;ve(this,e,r,n,a,0)}let i=1,s=0;for(this[r]=e&255;++s>>0,n=n>>>0,!o){let a=Math.pow(2,8*n)-1;ve(this,e,r,n,a,0)}let i=n-1,s=1;for(this[r+i]=e&255;--i>=0&&(s*=256);)this[r+i]=e/s&255;return r+n};g.prototype.writeUint8=g.prototype.writeUInt8=function(e,r,n){return e=+e,r=r>>>0,n||ve(this,e,r,1,255,0),this[r]=e&255,r+1};g.prototype.writeUint16LE=g.prototype.writeUInt16LE=function(e,r,n){return e=+e,r=r>>>0,n||ve(this,e,r,2,65535,0),this[r]=e&255,this[r+1]=e>>>8,r+2};g.prototype.writeUint16BE=g.prototype.writeUInt16BE=function(e,r,n){return e=+e,r=r>>>0,n||ve(this,e,r,2,65535,0),this[r]=e>>>8,this[r+1]=e&255,r+2};g.prototype.writeUint32LE=g.prototype.writeUInt32LE=function(e,r,n){return e=+e,r=r>>>0,n||ve(this,e,r,4,4294967295,0),this[r+3]=e>>>24,this[r+2]=e>>>16,this[r+1]=e>>>8,this[r]=e&255,r+4};g.prototype.writeUint32BE=g.prototype.writeUInt32BE=function(e,r,n){return e=+e,r=r>>>0,n||ve(this,e,r,4,4294967295,0),this[r]=e>>>24,this[r+1]=e>>>16,this[r+2]=e>>>8,this[r+3]=e&255,r+4};function Rs(t,e,r,n,o){Ms(e,n,o,t,r,7);let i=Number(e&BigInt(4294967295));t[r++]=i,i=i>>8,t[r++]=i,i=i>>8,t[r++]=i,i=i>>8,t[r++]=i;let s=Number(e>>BigInt(32)&BigInt(4294967295));return t[r++]=s,s=s>>8,t[r++]=s,s=s>>8,t[r++]=s,s=s>>8,t[r++]=s,r}function Cs(t,e,r,n,o){Ms(e,n,o,t,r,7);let i=Number(e&BigInt(4294967295));t[r+7]=i,i=i>>8,t[r+6]=i,i=i>>8,t[r+5]=i,i=i>>8,t[r+4]=i;let s=Number(e>>BigInt(32)&BigInt(4294967295));return t[r+3]=s,s=s>>8,t[r+2]=s,s=s>>8,t[r+1]=s,s=s>>8,t[r]=s,r+8}g.prototype.writeBigUInt64LE=yt(function(e,r=0){return Rs(this,e,r,BigInt(0),BigInt("0xffffffffffffffff"))});g.prototype.writeBigUInt64BE=yt(function(e,r=0){return Cs(this,e,r,BigInt(0),BigInt("0xffffffffffffffff"))});g.prototype.writeIntLE=function(e,r,n,o){if(e=+e,r=r>>>0,!o){let c=Math.pow(2,8*n-1);ve(this,e,r,n,c-1,-c)}let i=0,s=1,a=0;for(this[r]=e&255;++i>0)-a&255;return r+n};g.prototype.writeIntBE=function(e,r,n,o){if(e=+e,r=r>>>0,!o){let c=Math.pow(2,8*n-1);ve(this,e,r,n,c-1,-c)}let i=n-1,s=1,a=0;for(this[r+i]=e&255;--i>=0&&(s*=256);)e<0&&a===0&&this[r+i+1]!==0&&(a=1),this[r+i]=(e/s>>0)-a&255;return r+n};g.prototype.writeInt8=function(e,r,n){return e=+e,r=r>>>0,n||ve(this,e,r,1,127,-128),e<0&&(e=255+e+1),this[r]=e&255,r+1};g.prototype.writeInt16LE=function(e,r,n){return e=+e,r=r>>>0,n||ve(this,e,r,2,32767,-32768),this[r]=e&255,this[r+1]=e>>>8,r+2};g.prototype.writeInt16BE=function(e,r,n){return e=+e,r=r>>>0,n||ve(this,e,r,2,32767,-32768),this[r]=e>>>8,this[r+1]=e&255,r+2};g.prototype.writeInt32LE=function(e,r,n){return e=+e,r=r>>>0,n||ve(this,e,r,4,2147483647,-2147483648),this[r]=e&255,this[r+1]=e>>>8,this[r+2]=e>>>16,this[r+3]=e>>>24,r+4};g.prototype.writeInt32BE=function(e,r,n){return e=+e,r=r>>>0,n||ve(this,e,r,4,2147483647,-2147483648),e<0&&(e=4294967295+e+1),this[r]=e>>>24,this[r+1]=e>>>16,this[r+2]=e>>>8,this[r+3]=e&255,r+4};g.prototype.writeBigInt64LE=yt(function(e,r=0){return Rs(this,e,r,-BigInt("0x8000000000000000"),BigInt("0x7fffffffffffffff"))});g.prototype.writeBigInt64BE=yt(function(e,r=0){return Cs(this,e,r,-BigInt("0x8000000000000000"),BigInt("0x7fffffffffffffff"))});function Os(t,e,r,n,o,i){if(r+n>t.length)throw new RangeError("Index out of range");if(r<0)throw new RangeError("Index out of range")}function Ns(t,e,r,n,o){return e=+e,r=r>>>0,o||Os(t,e,r,4,34028234663852886e22,-34028234663852886e22),jt.write(t,e,r,n,23,4),r+4}g.prototype.writeFloatLE=function(e,r,n){return Ns(this,e,r,!0,n)};g.prototype.writeFloatBE=function(e,r,n){return Ns(this,e,r,!1,n)};function Ds(t,e,r,n,o){return e=+e,r=r>>>0,o||Os(t,e,r,8,17976931348623157e292,-17976931348623157e292),jt.write(t,e,r,n,52,8),r+8}g.prototype.writeDoubleLE=function(e,r,n){return Ds(this,e,r,!0,n)};g.prototype.writeDoubleBE=function(e,r,n){return Ds(this,e,r,!1,n)};g.prototype.copy=function(e,r,n,o){if(!g.isBuffer(e))throw new TypeError("argument should be a Buffer");if(n||(n=0),!o&&o!==0&&(o=this.length),r>=e.length&&(r=e.length),r||(r=0),o>0&&o=this.length)throw new RangeError("Index out of range");if(o<0)throw new RangeError("sourceEnd out of bounds");o>this.length&&(o=this.length),e.length-r>>0,n=n===void 0?this.length:n>>>0,e||(e=0);let i;if(typeof e=="number")for(i=r;i2**32?o=Is(String(r)):typeof r=="bigint"&&(o=String(r),(r>BigInt(2)**BigInt(32)||r<-(BigInt(2)**BigInt(32)))&&(o=Is(o)),o+="n"),n+=` It must be ${e}. Received ${o}`,n},RangeError);function Is(t){let e="",r=t.length,n=t[0]==="-"?1:0;for(;r>=n+4;r-=3)e=`_${t.slice(r-3,r)}${e}`;return`${t.slice(0,r)}${e}`}function _l(t,e,r){zt(e,"offset"),(t[e]===void 0||t[e+r]===void 0)&&ur(e,t.length-(r+1))}function Ms(t,e,r,n,o,i){if(t>r||t3?e===0||e===BigInt(0)?a=`>= 0${s} and < 2${s} ** ${(i+1)*8}${s}`:a=`>= -(2${s} ** ${(i+1)*8-1}${s}) and < 2 ** ${(i+1)*8-1}${s}`:a=`>= ${e}${s} and <= ${r}${s}`,new qt.ERR_OUT_OF_RANGE("value",a,t)}_l(n,o,i)}function zt(t,e){if(typeof t!="number")throw new qt.ERR_INVALID_ARG_TYPE(e,"number",t)}function ur(t,e,r){throw Math.floor(t)!==t?(zt(t,r),new qt.ERR_OUT_OF_RANGE(r||"offset","an integer",t)):e<0?new qt.ERR_BUFFER_OUT_OF_BOUNDS:new qt.ERR_OUT_OF_RANGE(r||"offset",`>= ${r?1:0} and <= ${e}`,t)}var Ll=/[^+/0-9A-Za-z-_]/g;function Ul(t){if(t=t.split("=")[0],t=t.trim().replace(Ll,""),t.length<2)return"";for(;t.length%4!==0;)t=t+"=";return t}function ho(t,e){e=e||1/0;let r,n=t.length,o=null,i=[];for(let s=0;s55295&&r<57344){if(!o){if(r>56319){(e-=3)>-1&&i.push(239,191,189);continue}else if(s+1===n){(e-=3)>-1&&i.push(239,191,189);continue}o=r;continue}if(r<56320){(e-=3)>-1&&i.push(239,191,189),o=r;continue}r=(o-55296<<10|r-56320)+65536}else o&&(e-=3)>-1&&i.push(239,191,189);if(o=null,r<128){if((e-=1)<0)break;i.push(r)}else if(r<2048){if((e-=2)<0)break;i.push(r>>6|192,r&63|128)}else if(r<65536){if((e-=3)<0)break;i.push(r>>12|224,r>>6&63|128,r&63|128)}else if(r<1114112){if((e-=4)<0)break;i.push(r>>18|240,r>>12&63|128,r>>6&63|128,r&63|128)}else throw new Error("Invalid code point")}return i}function Pl(t){let e=[];for(let r=0;r>8,o=r%256,i.push(o),i.push(n);return i}function Hs(t){return lo.toByteArray(Ul(t))}function qr(t,e,r,n){let o;for(o=0;o=e.length||o>=t.length);++o)e[o+r]=t[o];return o}function We(t,e){return t instanceof e||t!=null&&t.constructor!=null&&t.constructor.name!=null&&t.constructor.name===e.name}function mo(t){return t!==t}var Cl=(function(){let t="0123456789abcdef",e=new Array(256);for(let r=0;r<16;++r){let n=r*16;for(let o=0;o<16;++o)e[n+o]=t[r]+t[o]}return e})();function yt(t){return typeof BigInt>"u"?Ol:t}function Ol(){throw new Error("BigInt not supported")}});b();b();b();b();var di;(function(t){t[t.SET_METADATA=0]="SET_METADATA",t[t.TEXT_NOTE=1]="TEXT_NOTE",t[t.RECOMMEND_SERVER=2]="RECOMMEND_SERVER",t[t.CONTACTS=3]="CONTACTS",t[t.ENCRYPTED_DIRECT_MESSAGE=4]="ENCRYPTED_DIRECT_MESSAGE",t[t.EVENT_DELETION=5]="EVENT_DELETION",t[t.REPOST=6]="REPOST",t[t.REACTION=7]="REACTION",t[t.CHANNEL_CREATION=40]="CHANNEL_CREATION",t[t.CHANNEL_METADATA=41]="CHANNEL_METADATA",t[t.CHANNEL_MESSAGE=42]="CHANNEL_MESSAGE",t[t.CHANNEL_HIDE_MESSAGE=43]="CHANNEL_HIDE_MESSAGE",t[t.CHANNEL_MUTE_USER=44]="CHANNEL_MUTE_USER",t[t.AUTH=22242]="AUTH",t[t.AUTH_RESPONSE=22243]="AUTH_RESPONSE"})(di||(di={}));var Er;(function(t){t.EVENT="EVENT",t.NOTICE="NOTICE",t.OK="OK",t.EOSE="EOSE",t.REQ="REQ",t.CLOSE="CLOSE",t.AUTH="AUTH"})(Er||(Er={}));b();b();b();b();var vr;(function(t){t.CONNECT="connect",t.PING="ping",t.GET_PUBLIC_KEY="get_public_key",t.SIGN_EVENT="sign_event",t.NIP04_ENCRYPT="nip04_encrypt",t.NIP04_DECRYPT="nip04_decrypt",t.NIP44_ENCRYPT="nip44_encrypt",t.NIP44_DECRYPT="nip44_decrypt",t.GET_RELAYS="get_relays"})(vr||(vr={}));var Bn;(function(t){t[t.SET_METADATA=0]="SET_METADATA",t[t.TEXT_NOTE=1]="TEXT_NOTE",t[t.RECOMMEND_SERVER=2]="RECOMMEND_SERVER",t[t.CONTACT_LIST=3]="CONTACT_LIST",t[t.ENCRYPTED_DIRECT_MESSAGE=4]="ENCRYPTED_DIRECT_MESSAGE",t[t.DELETE=5]="DELETE",t[t.REPOST=6]="REPOST",t[t.REACTION=7]="REACTION",t[t.BADGE_AWARD=8]="BADGE_AWARD",t[t.CHANNEL_CREATE=40]="CHANNEL_CREATE",t[t.CHANNEL_METADATA=41]="CHANNEL_METADATA",t[t.CHANNEL_MESSAGE=42]="CHANNEL_MESSAGE",t[t.CHANNEL_HIDE_MESSAGE=43]="CHANNEL_HIDE_MESSAGE",t[t.CHANNEL_MUTE_USER=44]="CHANNEL_MUTE_USER",t[t.CHANNEL_RESERVE=45]="CHANNEL_RESERVE",t[t.REPORTING=1984]="REPORTING",t[t.ZAP_REQUEST=9734]="ZAP_REQUEST",t[t.ZAP=9735]="ZAP",t[t.MUTE_LIST=1e4]="MUTE_LIST",t[t.PIN_LIST=10001]="PIN_LIST",t[t.RELAY_LIST_METADATA=10002]="RELAY_LIST_METADATA",t[t.CLIENT_AUTH=22242]="CLIENT_AUTH",t[t.AUTH_RESPONSE=22243]="AUTH_RESPONSE",t[t.NOSTR_CONNECT=24133]="NOSTR_CONNECT",t[t.CATEGORIZED_PEOPLE=3e4]="CATEGORIZED_PEOPLE",t[t.CATEGORIZED_BOOKMARKS=30001]="CATEGORIZED_BOOKMARKS",t[t.PROFILE_BADGES=30008]="PROFILE_BADGES",t[t.BADGE_DEFINITION=30009]="BADGE_DEFINITION",t[t.LONG_FORM=30023]="LONG_FORM",t[t.APPLICATION_SPECIFIC=30078]="APPLICATION_SPECIFIC"})(Bn||(Bn={}));b();b();b();b();b();function tr(t){return t instanceof Uint8Array||ArrayBuffer.isView(t)&&t.constructor.name==="Uint8Array"}function te(t,e=""){if(!Number.isSafeInteger(t)||t<0){let r=e&&`"${e}" `;throw new Error(`${r}expected integer >= 0, got ${t}`)}}function F(t,e,r=""){let n=tr(t),o=t?.length,i=e!==void 0;if(!n||i&&o!==e){let s=r&&`"${r}" `,a=i?` of length ${e}`:"",c=n?`length=${o}`:`type=${typeof t}`;throw new Error(s+"expected Uint8Array"+a+", got "+c)}return t}function Qe(t){if(typeof t!="function"||typeof t.create!="function")throw new Error("Hash must wrapped by utils.createHasher");te(t.outputLen),te(t.blockLen)}function Ot(t,e=!0){if(t.destroyed)throw new Error("Hash instance has been destroyed");if(e&&t.finished)throw new Error("Hash#digest() has already been called")}function pi(t,e){F(t,void 0,"digestInto() output");let r=e.outputLen;if(t.length='+r)}function kr(t){return new Uint32Array(t.buffer,t.byteOffset,Math.floor(t.byteLength/4))}function Be(...t){for(let e=0;e>>e}function j(t,e){return t<>>32-e>>>0}var sc=new Uint8Array(new Uint32Array([287454020]).buffer)[0]===68;function ac(t){return t<<24&4278190080|t<<8&16711680|t>>>8&65280|t>>>24&255}function cc(t){for(let e=0;et:cc,yi=typeof Uint8Array.from([]).toHex=="function"&&typeof Uint8Array.fromHex=="function",lc=Array.from({length:256},(t,e)=>e.toString(16).padStart(2,"0"));function Ee(t){if(F(t),yi)return t.toHex();let e="";for(let r=0;r=Xe._0&&t<=Xe._9)return t-Xe._0;if(t>=Xe.A&&t<=Xe.F)return t-(Xe.A-10);if(t>=Xe.a&&t<=Xe.f)return t-(Xe.a-10)}function oe(t){if(typeof t!="string")throw new Error("hex string expected, got "+typeof t);if(yi)return Uint8Array.fromHex(t);let e=t.length,r=e/2;if(e%2)throw new Error("hex string expected, got unpadded hex of length "+e);let n=new Uint8Array(r);for(let o=0,i=0;ot(i).update(o).digest(),n=t(void 0);return r.outputLen=n.outputLen,r.blockLen=n.blockLen,r.create=o=>t(o),Object.assign(r,e),Object.freeze(r)}function ge(t=32){let e=typeof globalThis=="object"?globalThis.crypto:null;if(typeof e?.getRandomValues!="function")throw new Error("crypto.getRandomValues must be defined");return e.getRandomValues(new Uint8Array(t))}var mi=t=>({oid:Uint8Array.from([6,9,96,134,72,1,101,3,4,2,t])});function wi(t,e,r){return t&e^~t&r}function bi(t,e,r){return t&e^t&r^e&r}var Br=class{blockLen;outputLen;padOffset;isLE;buffer;view;finished=!1;length=0;pos=0;destroyed=!1;constructor(e,r,n,o){this.blockLen=e,this.outputLen=r,this.padOffset=n,this.isLE=o,this.buffer=new Uint8Array(e),this.view=Nt(this.buffer)}update(e){Ot(this),F(e);let{view:r,buffer:n,blockLen:o}=this,i=e.length;for(let s=0;so-s&&(this.process(n,0),s=0);for(let u=s;uf.length)throw new Error("_sha2: outputLen bigger than state");for(let u=0;u>>3,p=Ke(d,17)^Ke(d,19)^d>>>10;ut[u]=p+ut[u-7]+y+ut[u-16]|0}let{A:n,B:o,C:i,D:s,E:a,F:c,G:l,H:f}=this;for(let u=0;u<64;u++){let h=Ke(a,6)^Ke(a,11)^Ke(a,25),d=f+h+wi(a,c,l)+fc[u]+ut[u]|0,p=(Ke(n,2)^Ke(n,13)^Ke(n,22))+bi(n,o,i)|0;f=l,l=c,c=a,a=s+d|0,s=i,i=o,o=n,n=d+p|0}n=n+this.A|0,o=o+this.B|0,i=i+this.C|0,s=s+this.D|0,a=a+this.E|0,c=c+this.F|0,l=l+this.G|0,f=f+this.H|0,this.set(n,o,i,s,a,c,l,f)}roundClean(){Be(ut)}destroy(){this.set(0,0,0,0,0,0,0,0),Be(this.buffer)}},_n=class extends Tn{A=et[0]|0;B=et[1]|0;C=et[2]|0;D=et[3]|0;E=et[4]|0;F=et[5]|0;G=et[6]|0;H=et[7]|0;constructor(){super(32)}};var pe=gi(()=>new _n,mi(1));b();b();var Un=BigInt(0),Ln=BigInt(1);function rr(t,e=""){if(typeof t!="boolean"){let r=e&&`"${e}" `;throw new Error(r+"expected boolean, got type="+typeof t)}return t}function xi(t){if(typeof t=="bigint"){if(!Sr(t))throw new Error("positive bigint expected, got "+t)}else te(t);return t}function nr(t){let e=xi(t).toString(16);return e.length&1?"0"+e:e}function Ei(t){if(typeof t!="string")throw new Error("hex string expected, got "+typeof t);return t===""?Un:BigInt("0x"+t)}function ft(t){return Ei(Ee(t))}function Pn(t){return Ei(Ee(dc(F(t)).reverse()))}function Ir(t,e){te(e),t=xi(t);let r=oe(t.toString(16).padStart(e*2,"0"));if(r.length!==e)throw new Error("number too large");return r}function Rn(t,e){return Ir(t,e).reverse()}function dc(t){return Uint8Array.from(t)}function vi(t){return Uint8Array.from(t,(e,r)=>{let n=e.charCodeAt(0);if(e.length!==1||n>127)throw new Error(`string contains non-ASCII character "${t[r]}" with code ${n} at position ${r}`);return n})}var Sr=t=>typeof t=="bigint"&&Un<=t;function hc(t,e,r){return Sr(t)&&Sr(e)&&Sr(r)&&e<=t&&tUn;t>>=Ln,e+=1);return e}var or=t=>(Ln<new Uint8Array(w),o=Uint8Array.of(),i=Uint8Array.of(0),s=Uint8Array.of(1),a=1e3,c=n(t),l=n(t),f=0,u=()=>{c.fill(1),l.fill(0),f=0},h=(...w)=>r(l,ie(c,...w)),d=(w=o)=>{l=h(i,w),c=h(),w.length!==0&&(l=h(s,w),c=h())},y=()=>{if(f++>=a)throw new Error("drbg: tried max amount of iterations");let w=0,k=[];for(;w{u(),d(w);let O;for(;!(O=k(y()));)d();return u(),O}}function ir(t,e={},r={}){if(!t||typeof t!="object")throw new Error("expected valid options object");function n(i,s,a){let c=t[i];if(a&&c===void 0)return;let l=typeof c;if(l!==s||c===null)throw new Error(`param "${i}" is invalid: expected ${s}, got ${l}`)}let o=(i,s)=>Object.entries(i).forEach(([a,c])=>n(a,c,s));o(e,!1),o(r,!0)}function On(t){let e=new WeakMap;return(r,...n)=>{let o=e.get(r);if(o!==void 0)return o;let i=t(r,...n);return e.set(r,i),i}}b();var me=BigInt(0),ye=BigInt(1),xt=BigInt(2),Ii=BigInt(3),Ti=BigInt(4),_i=BigInt(5),pc=BigInt(7),Li=BigInt(8),yc=BigInt(9),Ui=BigInt(16);function Ve(t,e){let r=t%e;return r>=me?r:e+r}function Se(t,e,r){let n=t;for(;e-- >me;)n*=n,n%=r;return n}function Bi(t,e){if(t===me)throw new Error("invert: expected non-zero number");if(e<=me)throw new Error("invert: expected positive modulus, got "+e);let r=Ve(t,e),n=e,o=me,i=ye,s=ye,a=me;for(;r!==me;){let l=n/r,f=n%r,u=o-s*l,h=i-a*l;n=r,r=f,o=s,i=a,s=u,a=h}if(n!==ye)throw new Error("invert: does not exist");return Ve(o,e)}function Dn(t,e,r){if(!t.eql(t.sqr(e),r))throw new Error("Cannot find square root")}function Pi(t,e){let r=(t.ORDER+ye)/Ti,n=t.pow(e,r);return Dn(t,n,e),n}function gc(t,e){let r=(t.ORDER-_i)/Li,n=t.mul(e,xt),o=t.pow(n,r),i=t.mul(e,o),s=t.mul(t.mul(i,xt),o),a=t.mul(i,t.sub(s,t.ONE));return Dn(t,a,e),a}function mc(t){let e=Dt(t),r=Ri(t),n=r(e,e.neg(e.ONE)),o=r(e,n),i=r(e,e.neg(n)),s=(t+pc)/Ui;return(a,c)=>{let l=a.pow(c,s),f=a.mul(l,n),u=a.mul(l,o),h=a.mul(l,i),d=a.eql(a.sqr(f),c),y=a.eql(a.sqr(u),c);l=a.cmov(l,f,d),f=a.cmov(h,u,y);let p=a.eql(a.sqr(f),c),w=a.cmov(l,f,p);return Dn(a,w,c),w}}function Ri(t){if(t1e3)throw new Error("Cannot find square root: probably non-prime P");if(r===1)return Pi;let i=o.pow(n,e),s=(e+ye)/xt;return function(c,l){if(c.is0(l))return l;if(Si(c,l)!==1)throw new Error("Cannot find square root");let f=r,u=c.mul(c.ONE,i),h=c.pow(l,e),d=c.pow(l,s);for(;!c.eql(h,c.ONE);){if(c.is0(h))return c.ZERO;let y=1,p=c.sqr(h);for(;!c.eql(p,c.ONE);)if(y++,p=c.sqr(p),y===f)throw new Error("Cannot find square root");let w=ye<(n[o]="function",n),e);return ir(t,r),t}function xc(t,e,r){if(rme;)r&ye&&(n=t.mul(n,o)),o=t.sqr(o),r>>=ye;return n}function Tr(t,e,r=!1){let n=new Array(e.length).fill(r?t.ZERO:void 0),o=e.reduce((s,a,c)=>t.is0(a)?s:(n[c]=s,t.mul(s,a)),t.ONE),i=t.inv(o);return e.reduceRight((s,a,c)=>t.is0(a)?s:(n[c]=t.mul(s,n[c]),t.mul(s,a)),i),n}function Si(t,e){let r=(t.ORDER-ye)/xt,n=t.pow(e,r),o=t.eql(n,t.ONE),i=t.eql(n,t.ZERO),s=t.eql(n,t.neg(t.ONE));if(!o&&!i&&!s)throw new Error("invalid Legendre symbol result");return o?1:i?0:-1}function Ec(t,e){e!==void 0&&te(e);let r=e!==void 0?e:t.toString(2).length,n=Math.ceil(r/8);return{nBitLength:r,nByteLength:n}}var Nn=class{ORDER;BITS;BYTES;isLE;ZERO=me;ONE=ye;_lengths;_sqrt;_mod;constructor(e,r={}){if(e<=me)throw new Error("invalid field: expected ORDER > 0, got "+e);let n;this.isLE=!1,r!=null&&typeof r=="object"&&(typeof r.BITS=="number"&&(n=r.BITS),typeof r.sqrt=="function"&&(this.sqrt=r.sqrt),typeof r.isLE=="boolean"&&(this.isLE=r.isLE),r.allowedLengths&&(this._lengths=r.allowedLengths?.slice()),typeof r.modFromBytes=="boolean"&&(this._mod=r.modFromBytes));let{nBitLength:o,nByteLength:i}=Ec(e,n);if(i>2048)throw new Error("invalid field: expected ORDER of <= 2048 bytes");this.ORDER=e,this.BITS=o,this.BYTES=i,this._sqrt=void 0,Object.preventExtensions(this)}create(e){return Ve(e,this.ORDER)}isValid(e){if(typeof e!="bigint")throw new Error("invalid field element: expected bigint, got "+typeof e);return me<=e&&eo)throw new Error("Field.fromBytes: expected "+n+" bytes, got "+e.length);let l=new Uint8Array(o);l.set(e,i?0:l.length-e.length),e=l}if(e.length!==o)throw new Error("Field.fromBytes: expected "+o+" bytes, got "+e.length);let c=i?Pn(e):ft(e);if(a&&(c=Ve(c,s)),!r&&!this.isValid(c))throw new Error("invalid field element: outside of range 0..ORDER");return c}invertBatch(e){return Tr(this,e)}cmov(e,r,n){return n?r:e}};function Dt(t,e={}){return new Nn(t,e)}function Ci(t){if(typeof t!="bigint")throw new Error("field order must be bigint");let e=t.toString(2).length;return Math.ceil(e/8)}function Hn(t){let e=Ci(t);return e+Math.ceil(e/2)}function _r(t,e,r=!1){F(t);let n=t.length,o=Ci(e),i=Hn(e);if(n<16||n1024)throw new Error("expected "+i+"-1024 bytes of input, got "+n);let s=r?Pn(t):ft(t),a=Ve(s,e-ye)+ye;return r?Rn(a,o):Ir(a,o)}var Mt=BigInt(0),Et=BigInt(1);function sr(t,e){let r=e.negate();return t?r:e}function $n(t,e){let r=Tr(t.Fp,e.map(n=>n.Z));return e.map((n,o)=>t.fromAffine(n.toAffine(r[o])))}function Mi(t,e){if(!Number.isSafeInteger(t)||t<=0||t>e)throw new Error("invalid window size, expected [1.."+e+"], got W="+t)}function Kn(t,e){Mi(t,e);let r=Math.ceil(e/t)+1,n=2**(t-1),o=2**t,i=or(t),s=BigInt(t);return{windows:r,windowSize:n,mask:i,maxNumber:o,shiftBy:s}}function Oi(t,e,r){let{windowSize:n,mask:o,maxNumber:i,shiftBy:s}=r,a=Number(t&o),c=t>>s;a>n&&(a-=i,c+=Et);let l=e*n,f=l+Math.abs(a)-1,u=a===0,h=a<0,d=e%2!==0;return{nextN:c,offset:f,isZero:u,isNeg:h,isNegF:d,offsetF:l}}var Vn=new WeakMap,Hi=new WeakMap;function Fn(t){return Hi.get(t)||1}function Ni(t){if(t!==Mt)throw new Error("invalid wNAF")}var Lr=class{BASE;ZERO;Fn;bits;constructor(e,r){this.BASE=e.BASE,this.ZERO=e.ZERO,this.Fn=e.Fn,this.bits=r}_unsafeLadder(e,r,n=this.ZERO){let o=e;for(;r>Mt;)r&Et&&(n=n.add(o)),o=o.double(),r>>=Et;return n}precomputeWindow(e,r){let{windows:n,windowSize:o}=Kn(r,this.bits),i=[],s=e,a=s;for(let c=0;cMt||n>Mt;)r&Et&&(i=i.add(o)),n&Et&&(s=s.add(o)),o=o.double(),r>>=Et,n>>=Et;return{p1:i,p2:s}}function Di(t,e,r){if(e){if(e.ORDER!==t)throw new Error("Field.ORDER must match order: Fp == p, Fn == n");return Mn(e),e}else return Dt(t,{isLE:r})}function Vi(t,e,r={},n){if(n===void 0&&(n=t==="edwards"),!e||typeof e!="object")throw new Error(`expected valid ${t} CURVE object`);for(let c of["p","n","h"]){let l=e[c];if(!(typeof l=="bigint"&&l>Mt))throw new Error(`CURVE.${c} must be positive bigint`)}let o=Di(e.p,r.Fp,n),i=Di(e.n,r.Fn,n),a=["Gx","Gy","a",t==="weierstrass"?"b":"d"];for(let c of a)if(!o.isValid(e[c]))throw new Error(`CURVE.${c} must be valid field element of CURVE.Fp`);return e=Object.freeze(Object.assign({},e)),{CURVE:e,Fp:o,Fn:i}}function Ur(t,e){return function(n){let o=t(n);return{secretKey:o,publicKey:e(o)}}}b();b();var Pr=class{oHash;iHash;blockLen;outputLen;finished=!1;destroyed=!1;constructor(e,r){if(Qe(e),F(r,void 0,"key"),this.iHash=e.create(),typeof this.iHash.update!="function")throw new Error("Expected instance of class which extends utils.Hash");this.blockLen=this.iHash.blockLen,this.outputLen=this.iHash.outputLen;let n=this.blockLen,o=new Uint8Array(n);o.set(r.length>n?e.create().update(r).digest():r);for(let i=0;inew Pr(t,e).update(r).digest();Fe.create=(t,e)=>new Pr(t,e);var Fi=(t,e)=>(t+(t>=0?e:-e)/$i)/e;function vc(t,e,r){let[[n,o],[i,s]]=e,a=Fi(s*t,r),c=Fi(-o*t,r),l=t-a*n-c*i,f=-a*o-c*s,u=l=d||f=d)throw new Error("splitScalar (endomorphism): failed, k="+t);return{k1neg:u,k1:l,k2neg:h,k2:f}}function jn(t){if(!["compact","recovered","der"].includes(t))throw new Error('Signature format must be "compact", "recovered", or "der"');return t}function qn(t,e){let r={};for(let n of Object.keys(e))r[n]=t[n]===void 0?e[n]:t[n];return rr(r.lowS,"lowS"),rr(r.prehash,"prehash"),r.format!==void 0&&jn(r.format),r}var zn=class extends Error{constructor(e=""){super(e)}},dt={Err:zn,_tlv:{encode:(t,e)=>{let{Err:r}=dt;if(t<0||t>256)throw new r("tlv.encode: wrong tag");if(e.length&1)throw new r("tlv.encode: unpadded data");let n=e.length/2,o=nr(n);if(o.length/2&128)throw new r("tlv.encode: long form length too big");let i=n>127?nr(o.length/2|128):"";return nr(t)+i+o+e},decode(t,e){let{Err:r}=dt,n=0;if(t<0||t>256)throw new r("tlv.encode: wrong tag");if(e.length<2||e[n++]!==t)throw new r("tlv.decode: wrong tlv");let o=e[n++],i=!!(o&128),s=0;if(!i)s=o;else{let c=o&127;if(!c)throw new r("tlv.decode(long): indefinite length not supported");if(c>4)throw new r("tlv.decode(long): byte length is too big");let l=e.subarray(n,n+c);if(l.length!==c)throw new r("tlv.decode: length bytes not complete");if(l[0]===0)throw new r("tlv.decode(long): zero leftmost byte");for(let f of l)s=s<<8|f;if(n+=c,s<128)throw new r("tlv.decode(long): not minimal encoding")}let a=e.subarray(n,n+s);if(a.length!==s)throw new r("tlv.decode: wrong value length");return{v:a,l:e.subarray(n+s)}}},_int:{encode(t){let{Err:e}=dt;if(t{let{X:x,Y:m,Z:A}=P;if(n.eql(A,n.ONE))return{x,y:m};let S=P.is0();E==null&&(E=S?n.ONE:n.inv(A));let I=n.mul(x,E),v=n.mul(m,E),B=n.mul(A,E);if(S)return{x:n.ZERO,y:n.ZERO};if(!n.eql(B,n.ONE))throw new Error("invZ was invalid");return{x:I,y:v}}),q=On(P=>{if(P.is0()){if(e.allowInfinityPoint&&!n.is0(P.Y))return;throw new Error("bad point: ZERO")}let{x:E,y:x}=P.toAffine();if(!n.isValid(E)||!n.isValid(x))throw new Error("bad point: x or y not field elements");if(!w(E,x))throw new Error("bad point: equation left != right");if(!P.isTorsionFree())throw new Error("bad point: not in prime-order subgroup");return!0});function G(P,E,x,m,A){return x=new C(n.mul(x.X,P),x.Y,x.Z),E=sr(m,E),x=sr(A,x),E.add(x)}class C{static BASE=new C(i.Gx,i.Gy,n.ONE);static ZERO=new C(n.ZERO,n.ONE,n.ZERO);static Fp=n;static Fn=o;X;Y;Z;constructor(E,x,m){this.X=D("x",E),this.Y=D("y",x,!0),this.Z=D("z",m),Object.freeze(this)}static CURVE(){return i}static fromAffine(E){let{x,y:m}=E||{};if(!E||!n.isValid(x)||!n.isValid(m))throw new Error("invalid affine point");if(E instanceof C)throw new Error("projective point not allowed");return n.is0(x)&&n.is0(m)?C.ZERO:new C(x,m,n.ONE)}static fromBytes(E){let x=C.fromAffine(y(F(E,void 0,"point")));return x.assertValidity(),x}static fromHex(E){return C.fromBytes(oe(E))}get x(){return this.toAffine().x}get y(){return this.toAffine().y}precompute(E=8,x=!0){return K.createCache(this,E),x||this.multiply(Rr),this}assertValidity(){q(this)}hasEvenY(){let{y:E}=this.toAffine();if(!n.isOdd)throw new Error("Field doesn't support isOdd");return!n.isOdd(E)}equals(E){H(E);let{X:x,Y:m,Z:A}=this,{X:S,Y:I,Z:v}=E,B=n.eql(n.mul(x,v),n.mul(S,A)),T=n.eql(n.mul(m,v),n.mul(I,A));return B&&T}negate(){return new C(this.X,n.neg(this.Y),this.Z)}double(){let{a:E,b:x}=i,m=n.mul(x,Rr),{X:A,Y:S,Z:I}=this,v=n.ZERO,B=n.ZERO,T=n.ZERO,L=n.mul(A,A),Y=n.mul(S,S),z=n.mul(I,I),V=n.mul(A,S);return V=n.add(V,V),T=n.mul(A,I),T=n.add(T,T),v=n.mul(E,T),B=n.mul(m,z),B=n.add(v,B),v=n.sub(Y,B),B=n.add(Y,B),B=n.mul(v,B),v=n.mul(V,v),T=n.mul(m,T),z=n.mul(E,z),V=n.sub(L,z),V=n.mul(E,V),V=n.add(V,T),T=n.add(L,L),L=n.add(T,L),L=n.add(L,z),L=n.mul(L,V),B=n.add(B,L),z=n.mul(S,I),z=n.add(z,z),L=n.mul(z,V),v=n.sub(v,L),T=n.mul(z,Y),T=n.add(T,T),T=n.add(T,T),new C(v,B,T)}add(E){H(E);let{X:x,Y:m,Z:A}=this,{X:S,Y:I,Z:v}=E,B=n.ZERO,T=n.ZERO,L=n.ZERO,Y=i.a,z=n.mul(i.b,Rr),V=n.mul(x,S),Z=n.mul(m,I),ee=n.mul(A,v),fe=n.add(x,m),J=n.add(S,I);fe=n.mul(fe,J),J=n.add(V,Z),fe=n.sub(fe,J),J=n.add(x,A);let he=n.add(S,v);return J=n.mul(J,he),he=n.add(V,ee),J=n.sub(J,he),he=n.add(m,A),B=n.add(I,v),he=n.mul(he,B),B=n.add(Z,ee),he=n.sub(he,B),L=n.mul(Y,J),B=n.mul(z,ee),L=n.add(B,L),B=n.sub(Z,L),L=n.add(Z,L),T=n.mul(B,L),Z=n.add(V,V),Z=n.add(Z,V),ee=n.mul(Y,ee),J=n.mul(z,J),Z=n.add(Z,ee),ee=n.sub(V,ee),ee=n.mul(Y,ee),J=n.add(J,ee),V=n.mul(Z,J),T=n.add(T,V),V=n.mul(he,J),B=n.mul(fe,B),B=n.sub(B,V),V=n.mul(fe,Z),L=n.mul(he,L),L=n.add(L,V),new C(B,T,L)}subtract(E){return this.add(E.negate())}is0(){return this.equals(C.ZERO)}multiply(E){let{endo:x}=e;if(!o.isValidNot0(E))throw new Error("invalid scalar: out of range");let m,A,S=I=>K.cached(this,I,v=>$n(C,v));if(x){let{k1neg:I,k1:v,k2neg:B,k2:T}=X(E),{p:L,f:Y}=S(v),{p:z,f:V}=S(T);A=Y.add(V),m=G(x.beta,L,z,I,B)}else{let{p:I,f:v}=S(E);m=I,A=v}return $n(C,[m,A])[0]}multiplyUnsafe(E){let{endo:x}=e,m=this;if(!o.isValid(E))throw new Error("invalid scalar: out of range");if(E===tt||m.is0())return C.ZERO;if(E===Ht)return m;if(K.hasCache(this))return this.multiply(E);if(x){let{k1neg:A,k1:S,k2neg:I,k2:v}=X(E),{p1:B,p2:T}=Ki(C,m,S,v);return G(x.beta,B,T,A,I)}else return K.unsafe(m,E)}toAffine(E){return M(this,E)}isTorsionFree(){let{isTorsionFree:E}=e;return s===Ht?!0:E?E(C,this):K.unsafe(this,a).is0()}clearCofactor(){let{clearCofactor:E}=e;return s===Ht?this:E?E(C,this):this.multiplyUnsafe(s)}isSmallOrder(){return this.multiplyUnsafe(s).is0()}toBytes(E=!0){return rr(E,"isCompressed"),this.assertValidity(),d(C,this,E)}toHex(E=!0){return Ee(this.toBytes(E))}toString(){return``}}let $=o.BITS,K=new Lr(C,e.endo?Math.ceil($/2):$);return C.BASE.precompute(8),C}function ji(t){return Uint8Array.of(t?2:3)}function zi(t,e){return{secretKey:e.BYTES,publicKey:1+t.BYTES,publicKeyUncompressed:1+2*t.BYTES,publicKeyHasPrefix:!0,signature:2*e.BYTES}}function Ac(t,e={}){let{Fn:r}=t,n=e.randomBytes||ge,o=Object.assign(zi(t.Fp,r),{seed:Hn(r.ORDER)});function i(d){try{let y=r.fromBytes(d);return r.isValidNot0(y)}catch{return!1}}function s(d,y){let{publicKey:p,publicKeyUncompressed:w}=o;try{let k=d.length;return y===!0&&k!==p||y===!1&&k!==w?!1:!!t.fromBytes(d)}catch{return!1}}function a(d=n(o.seed)){return _r(F(d,o.seed,"seed"),r.ORDER)}function c(d,y=!0){return t.BASE.multiply(r.fromBytes(d)).toBytes(y)}function l(d){let{secretKey:y,publicKey:p,publicKeyUncompressed:w}=o;if(!tr(d)||"_lengths"in r&&r._lengths||y===p)return;let k=F(d,void 0,"key").length;return k===p||k===w}function f(d,y,p=!0){if(l(d)===!0)throw new Error("first arg must be private key");if(l(y)===!1)throw new Error("second arg must be public key");let w=r.fromBytes(d);return t.fromBytes(y).multiply(w).toBytes(p)}let u={isValidSecretKey:i,isValidPublicKey:s,randomSecretKey:a},h=Ur(a,c);return Object.freeze({getPublicKey:c,getSharedSecret:f,keygen:h,Point:t,utils:u,lengths:o})}function Wi(t,e,r={}){Qe(e),ir(r,{},{hmac:"function",lowS:"boolean",randomBytes:"function",bits2int:"function",bits2int_modN:"function"}),r=Object.assign({},r);let n=r.randomBytes||ge,o=r.hmac||((x,m)=>Fe(e,x,m)),{Fp:i,Fn:s}=t,{ORDER:a,BITS:c}=s,{keygen:l,getPublicKey:f,getSharedSecret:u,utils:h,lengths:d}=Ac(t,r),y={prehash:!0,lowS:typeof r.lowS=="boolean"?r.lowS:!0,format:"compact",extraEntropy:!1},p=a*$i>Ht;return x>m}function k(x,m){if(!s.isValidNot0(m))throw new Error(`invalid signature ${x}: out of range 1..Point.Fn.ORDER`);return m}function O(){if(p)throw new Error('"recovered" sig type is not supported for cofactor >2 curves')}function D(x,m){jn(m);let A=d.signature,S=m==="compact"?A:m==="recovered"?A+1:void 0;return F(x,S)}class H{r;s;recovery;constructor(m,A,S){if(this.r=k("r",m),this.s=k("s",A),S!=null){if(O(),![0,1,2,3].includes(S))throw new Error("invalid recovery id");this.recovery=S}Object.freeze(this)}static fromBytes(m,A=y.format){D(m,A);let S;if(A==="der"){let{r:T,s:L}=dt.toSig(F(m));return new H(T,L)}A==="recovered"&&(S=m[0],A="compact",m=m.subarray(1));let I=d.signature/2,v=m.subarray(0,I),B=m.subarray(I,I*2);return new H(s.fromBytes(v),s.fromBytes(B),S)}static fromHex(m,A){return this.fromBytes(oe(m),A)}assertRecovery(){let{recovery:m}=this;if(m==null)throw new Error("invalid recovery id: must be present");return m}addRecoveryBit(m){return new H(this.r,this.s,m)}recoverPublicKey(m){let{r:A,s:S}=this,I=this.assertRecovery(),v=I===2||I===3?A+a:A;if(!i.isValid(v))throw new Error("invalid recovery id: sig.r+curve.n != R.x");let B=i.toBytes(v),T=t.fromBytes(ie(ji((I&1)===0),B)),L=s.inv(v),Y=M(F(m,void 0,"msgHash")),z=s.create(-Y*L),V=s.create(S*L),Z=t.BASE.multiplyUnsafe(z).add(T.multiplyUnsafe(V));if(Z.is0())throw new Error("invalid recovery: point at infinify");return Z.assertValidity(),Z}hasHighS(){return w(this.s)}toBytes(m=y.format){if(jn(m),m==="der")return oe(dt.hexFromSig(this));let{r:A,s:S}=this,I=s.toBytes(A),v=s.toBytes(S);return m==="recovered"?(O(),ie(Uint8Array.of(this.assertRecovery()),I,v)):ie(I,v)}toHex(m){return Ee(this.toBytes(m))}}let X=r.bits2int||function(m){if(m.length>8192)throw new Error("input is too large");let A=ft(m),S=m.length*8-c;return S>0?A>>BigInt(S):A},M=r.bits2int_modN||function(m){return s.create(X(m))},q=or(c);function G(x){return ki("num < 2^"+c,x,tt,q),s.toBytes(x)}function C(x,m){return F(x,void 0,"message"),m?F(e(x),void 0,"prehashed message"):x}function $(x,m,A){let{lowS:S,prehash:I,extraEntropy:v}=qn(A,y);x=C(x,I);let B=M(x),T=s.fromBytes(m);if(!s.isValidNot0(T))throw new Error("invalid private key");let L=[G(T),G(B)];if(v!=null&&v!==!1){let Z=v===!0?n(d.secretKey):v;L.push(F(Z,void 0,"extraEntropy"))}let Y=ie(...L),z=B;function V(Z){let ee=X(Z);if(!s.isValidNot0(ee))return;let fe=s.inv(ee),J=t.BASE.multiply(ee).toAffine(),he=s.create(J.x);if(he===tt)return;let xr=s.create(fe*s.create(z+he*T));if(xr===tt)return;let ui=(J.x===he?0:2)|Number(J.y&Ht),fi=xr;return S&&w(xr)&&(fi=s.neg(xr),ui^=1),new H(he,fi,p?void 0:ui)}return{seed:Y,k2sig:V}}function K(x,m,A={}){let{seed:S,k2sig:I}=$(x,m,A);return Ai(e.outputLen,s.BYTES,o)(S,I).toBytes(A.format)}function P(x,m,A,S={}){let{lowS:I,prehash:v,format:B}=qn(S,y);if(A=F(A,void 0,"publicKey"),m=C(m,v),!tr(x)){let T=x instanceof H?", use sig.toBytes()":"";throw new Error("verify expects Uint8Array signature"+T)}D(x,B);try{let T=H.fromBytes(x,B),L=t.fromBytes(A);if(I&&T.hasHighS())return!1;let{r:Y,s:z}=T,V=M(m),Z=s.inv(z),ee=s.create(V*Z),fe=s.create(Y*Z),J=t.BASE.multiplyUnsafe(ee).add(L.multiplyUnsafe(fe));return J.is0()?!1:s.create(J.x)===Y}catch{return!1}}function E(x,m,A={}){let{prehash:S}=qn(A,y);return m=C(m,S),H.fromBytes(x,"recovered").recoverPublicKey(m).toBytes()}return Object.freeze({keygen:l,getPublicKey:f,getSharedSecret:u,utils:h,lengths:d,Point:t,sign:K,verify:P,recoverPublicKey:E,Signature:H,hash:e})}var Nr={p:BigInt("0xfffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2f"),n:BigInt("0xfffffffffffffffffffffffffffffffebaaedce6af48a03bbfd25e8cd0364141"),h:BigInt(1),a:BigInt(0),b:BigInt(7),Gx:BigInt("0x79be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798"),Gy:BigInt("0x483ada7726a3c4655da4fbfc0e1108a8fd17b448a68554199c47d08ffb10d4b8")},Bc={beta:BigInt("0x7ae96a2b657c07106e64479eac3434e99cf0497512f58995c1396c28719501ee"),basises:[[BigInt("0x3086d221a7d46bcde86c90e49284eb15"),-BigInt("0xe4437ed6010e88286f547fa90abfe4c3")],[BigInt("0x114ca50f7a8e2f3f657c1108d9d44cfd8"),BigInt("0x3086d221a7d46bcde86c90e49284eb15")]]},Sc=BigInt(0),Wn=BigInt(2);function Ic(t){let e=Nr.p,r=BigInt(3),n=BigInt(6),o=BigInt(11),i=BigInt(22),s=BigInt(23),a=BigInt(44),c=BigInt(88),l=t*t*t%e,f=l*l*t%e,u=Se(f,r,e)*f%e,h=Se(u,r,e)*f%e,d=Se(h,Wn,e)*l%e,y=Se(d,o,e)*d%e,p=Se(y,i,e)*y%e,w=Se(p,a,e)*p%e,k=Se(w,c,e)*w%e,O=Se(k,a,e)*p%e,D=Se(O,r,e)*f%e,H=Se(D,s,e)*y%e,X=Se(H,n,e)*l%e,M=Se(X,Wn,e);if(!Cr.eql(Cr.sqr(M),t))throw new Error("Cannot find square root");return M}var Cr=Dt(Nr.p,{sqrt:Ic}),vt=qi(Nr,{Fp:Cr,endo:Bc}),kt=Wi(vt,pe),Gi={};function Or(t,...e){let r=Gi[t];if(r===void 0){let n=pe(vi(t));r=ie(n,n),Gi[t]=r}return pe(ie(r,...e))}var Yn=t=>t.toBytes(!0).slice(1),Zn=t=>t%Wn===Sc;function Gn(t){let{Fn:e,BASE:r}=vt,n=e.fromBytes(t),o=r.multiply(n);return{scalar:Zn(o.y)?n:e.neg(n),bytes:Yn(o)}}function Zi(t){let e=Cr;if(!e.isValidNot0(t))throw new Error("invalid x: Fail if x \u2265 p");let r=e.create(t*t),n=e.create(r*t+BigInt(7)),o=e.sqrt(n);Zn(o)||(o=e.neg(o));let i=vt.fromAffine({x:t,y:o});return i.assertValidity(),i}var ar=ft;function Ji(...t){return vt.Fn.create(ar(Or("BIP0340/challenge",...t)))}function Yi(t){return Gn(t).bytes}function Tc(t,e,r=ge(32)){let{Fn:n}=vt,o=F(t,void 0,"message"),{bytes:i,scalar:s}=Gn(e),a=F(r,32,"auxRand"),c=n.toBytes(s^ar(Or("BIP0340/aux",a))),l=Or("BIP0340/nonce",c,i,o),{bytes:f,scalar:u}=Gn(l),h=Ji(f,i,o),d=new Uint8Array(64);if(d.set(f,0),d.set(n.toBytes(n.create(u+h*s)),32),!Xi(d,o,i))throw new Error("sign: Invalid signature produced");return d}function Xi(t,e,r){let{Fp:n,Fn:o,BASE:i}=vt,s=F(t,64,"signature"),a=F(e,void 0,"message"),c=F(r,32,"publicKey");try{let l=Zi(ar(c)),f=ar(s.subarray(0,32));if(!n.isValidNot0(f))return!1;let u=ar(s.subarray(32,64));if(!o.isValidNot0(u))return!1;let h=Ji(o.toBytes(f),Yn(l),a),d=i.multiplyUnsafe(u).add(l.multiplyUnsafe(o.neg(h))),{x:y,y:p}=d.toAffine();return!(d.is0()||!Zn(p)||y!==f)}catch{return!1}}var Kt=(()=>{let r=(n=ge(48))=>_r(n,Nr.n);return{keygen:Ur(r,Yi),getPublicKey:Yi,sign:Tc,verify:Xi,Point:vt,utils:{randomSecretKey:r,taggedHash:Or,lift_x:Zi,pointToBytes:Yn},lengths:{secretKey:32,publicKey:32,publicKeyHasPrefix:!1,signature:64,seed:48}}})();b();var ls=er(as()),cs;(function(t){t[t.DEBUG=0]="DEBUG",t[t.INFO=1]="INFO",t[t.WARN=2]="WARN",t[t.ERROR=3]="ERROR"})(cs||(cs={}));var Ie=(0,ls.default)({name:"nostr-crypto-utils",level:R.env.LOG_LEVEL||"info",transport:void 0,formatters:{level:t=>({level:t.toUpperCase()}),log:t=>{if(t&&typeof t=="object"&&"err"in t){let e={...t};if(e.err instanceof Error){let r=e.err;e.err={message:r.message,stack:r.stack,name:r.name}}return e}return t}}});b();function zc(t){try{return!!t.match(/^[A-Za-z0-9+/]*={0,2}$/)}catch{return!1}}function Hr(t){let e="";for(let r=0;r{if(typeof window<"u"&&window.crypto)return window.crypto;if(typeof globalThis<"u"&&globalThis.crypto)return globalThis.crypto;try{let t=await Promise.resolve().then(()=>er(ro()));if(t.webcrypto)return t.webcrypto}catch{Ie.debug("Node crypto not available")}throw new Error("No WebCrypto implementation available")},no=class{cryptoInstance=null;initPromise;constructor(){this.initPromise=this.initialize()}async initialize(){this.cryptoInstance=await Wc()}async ensureInitialized(){if(await this.initPromise,!this.cryptoInstance)throw new Error("Crypto implementation not initialized");return this.cryptoInstance}async getSubtle(){return(await this.ensureInitialized()).subtle}async getRandomValues(e){return(await this.ensureInitialized()).getRandomValues(e)}},Md=new no,Gc=Kt.sign,Yc=Kt.verify;async function oo(){let t=ge(32),e=Ee(t);t.fill(0);let r=await fs(e);return{privateKey:e,publicKey:r}}async function fs(t){try{let e=oe(t),r=Kt.getPublicKey(e);return{hex:Ee(r),bytes:r}}catch(e){throw Ie.error({error:e},"Failed to get public key"),e}}function Zc(t){return t instanceof Uint8Array?Ee(t):t}async function ds(t,e){try{let r=Zc(e),n=JSON.stringify([0,t.pubkey,t.created_at,t.kind,t.tags,t.content]),o=pe(new TextEncoder().encode(n)),i=oe(r),s=Kt.sign(o,i);return{...t,id:Ee(o),sig:Ee(s)}}catch(r){throw Ie.error({error:r},"Failed to sign event"),r}}function Pe(t){let e=t instanceof Uint8Array?t:oe(t),r=Kt.getPublicKey(e);return Ee(r)}async function Re(t,e){let r=t.pubkey||Pe(e),n=t.created_at||Math.floor(Date.now()/1e3),o={kind:t.kind||1,created_at:n,tags:t.tags||[],content:t.content||"",pubkey:r};return ds(o,e)}b();b();b();b();var pt={};An(pt,{computeSharedSecret:()=>ys,decryptMessage:()=>ps,encryptMessage:()=>hs,generateSharedSecret:()=>ys});b();var Qc=async()=>{if(typeof window<"u"&&window.crypto)return window.crypto;if(typeof globalThis<"u"&&globalThis.crypto)return globalThis.crypto;try{let t=await Promise.resolve().then(()=>er(ro()));if(t.webcrypto)return t.webcrypto}catch{Ie.debug("Node crypto not available")}throw new Error("No WebCrypto implementation available")},io=class{cryptoInstance=null;initPromise;constructor(){this.initPromise=this.initialize()}async initialize(){this.cryptoInstance=await Qc()}async ensureInitialized(){if(await this.initPromise,!this.cryptoInstance)throw new Error("Crypto implementation not initialized");return this.cryptoInstance}async getSubtle(){return(await this.ensureInitialized()).subtle}async getRandomValues(e){return(await this.ensureInitialized()).getRandomValues(e)}},lr=new io;async function hs(t,e,r){try{if(!t||!e||!r)throw new Error("Invalid input parameters");if(!/^[0-9a-f]{64}$/i.test(e))throw new Error("Invalid private key format");let n=r.startsWith("02")||r.startsWith("03")?r:"02"+r,o=kt.getSharedSecret(oe(e),oe(n)),i=o.slice(1,33),s=await(await lr.getSubtle()).importKey("raw",i.buffer,{name:"AES-CBC",length:256},!1,["encrypt"]);i.fill(0),o.fill(0);let a=new Uint8Array(16);await lr.getRandomValues(a);let c=new TextEncoder().encode(t),l=await(await lr.getSubtle()).encrypt({name:"AES-CBC",iv:a},s,c.buffer),f=Hr(new Uint8Array(l)),u=Hr(a);return f+"?iv="+u}catch(n){throw Ie.error({error:n},"Failed to encrypt message"),n}}async function ps(t,e,r){try{if(!t||!e||!r)throw new Error("Invalid input parameters");if(!/^[0-9a-f]{64}$/i.test(e))throw new Error("Invalid private key format");let n=r.startsWith("02")||r.startsWith("03")?r:"02"+r,o=kt.getSharedSecret(oe(e),oe(n)),i=o.slice(1,33),s=await(await lr.getSubtle()).importKey("raw",i.buffer,{name:"AES-CBC",length:256},!1,["decrypt"]);i.fill(0),o.fill(0);let a,c;if(t.includes("?iv=")){let[f,u]=t.split("?iv=");c=Kr(f),a=Kr(u)}else{let f=oe(t);a=f.slice(0,16),c=f.slice(16)}let l=await(await lr.getSubtle()).decrypt({name:"AES-CBC",iv:a},s,c.buffer);return new TextDecoder().decode(l)}catch(n){throw Ie.error({error:n},"Failed to decrypt message"),n}}function ys(t,e){try{if(!t||!e)throw new Error("Invalid input parameters");if(!/^[0-9a-f]{64}$/i.test(t))throw new Error("Invalid private key format");let r=e.startsWith("02")||e.startsWith("03")?e:"02"+e;return{sharedSecret:kt.getSharedSecret(oe(t),oe(r)).slice(1,33)}}catch(r){throw Ie.error({error:r},"Failed to generate shared secret"),r}}b();var Te={};An(Te,{decode:()=>ql,naddrEncode:()=>Fl,neventEncode:()=>Vl,noteEncode:()=>Hl,nprofileEncode:()=>Kl,npubEncode:()=>Dl,nrelayEncode:()=>$l,nsecEncode:()=>Ml});b();var we=er(bs()),Oe=er(Ks()),Nl=["npub","nsec","note","nprofile","nevent","naddr","nrelay"],Ge={SPECIAL:0,RELAY:1,AUTHOR:2,KIND:3,IDENTIFIER:4};function Dl(t){Ye(t,64);let e=Oe.Buffer.from(t,"hex"),r=we.bech32.toWords(e);return we.bech32.encode("npub",r,1e3)}function Ml(t){Ye(t,64);let e=Oe.Buffer.from(t,"hex"),r=we.bech32.toWords(e);return we.bech32.encode("nsec",r,1e3)}function Hl(t){Ye(t,64);let e=Oe.Buffer.from(t,"hex"),r=we.bech32.toWords(e);return we.bech32.encode("note",r,1e3)}function Kl(t,e){Ye(t,64),e&&e.forEach(Gt);let r=wo({type:"nprofile",data:t,relays:e});return we.bech32.encode("nprofile",r,1e3)}function Vl(t,e,r,n){if(Ye(t,64),e&&e.forEach(Gt),r&&Ye(r,64),n!==void 0&&!Number.isInteger(n))throw new Error("Invalid event kind");let o=wo({type:"nevent",data:t,relays:e,author:r,kind:n});return we.bech32.encode("nevent",o,1e3)}function Fl(t,e,r,n){if(Ye(t,64),!Number.isInteger(e))throw new Error("Invalid event kind");if(!r)throw new Error("Identifier is required");n&&n.forEach(Gt);let o=wo({type:"naddr",data:t,kind:e,identifier:r,relays:n});return we.bech32.encode("naddr",o,1e3)}function $l(t){Gt(t);let e=Oe.Buffer.from(t,"utf8"),r=we.bech32.toWords(e);return we.bech32.encode("nrelay",r,1e3)}function ql(t){if(!t.includes("1"))throw new Error("Invalid bech32 string");let e=t.split("1")[0].toLowerCase();if(!Nl.includes(e))throw new Error("Unknown prefix");try{let r=we.bech32.decode(t,1e3),n=Oe.Buffer.from(we.bech32.fromWords(r.words)),o,i;switch(r.prefix){case"npub":case"nsec":case"note":return Ye(n.toString("hex"),64),{type:r.prefix,data:n.toString("hex")};case"nrelay":return o=n.toString("utf8"),Gt(o),{type:"nrelay",data:o};case"nprofile":case"nevent":case"naddr":return i=jl(r.prefix,n),i;default:throw new Error("Unknown prefix")}}catch(r){throw r instanceof Error?r:new Error("Invalid bech32 string")}}function Ye(t,e){if(!/^[0-9a-fA-F]+$/.test(t))throw new Error("Invalid hex string");if(e&&t.length!==e)throw new Error(`Invalid hex string length (expected ${e})`)}function Gt(t){try{let e=new URL(t);if(!["ws:","wss:"].includes(e.protocol))throw new Error("Invalid relay URL protocol")}catch{throw new Error("Invalid relay URL")}}function wo(t){let e=[],r=Oe.Buffer.from(t.data,"hex");if(e.push(Ge.SPECIAL,r.length),e.push(...r),t.relays?.length)for(let n of t.relays){let o=Oe.Buffer.from(n,"utf8");e.push(Ge.RELAY,o.length),e.push(...o)}if(t.author){let n=Oe.Buffer.from(t.author,"hex");e.push(Ge.AUTHOR,n.length),e.push(...n)}if(t.kind!==void 0){let n=Oe.Buffer.alloc(4);n.writeUInt32BE(t.kind),e.push(Ge.KIND,n.length),e.push(...n)}if(t.identifier){let n=Oe.Buffer.from(t.identifier,"utf8");e.push(Ge.IDENTIFIER,n.length),e.push(...n)}return we.bech32.toWords(Oe.Buffer.from(e))}function jl(t,e){let r={type:t,data:"",relays:[]},n=0,o;for(;ne.length)throw new Error("Invalid TLV data");let a=e.slice(n+2,n+2+s);switch(i){case Ge.SPECIAL:r.data=a.toString("hex"),Ye(r.data,64);break;case Ge.RELAY:o=a.toString("utf8"),Gt(o),r.relays=r.relays||[],r.relays.push(o);break;case Ge.AUTHOR:r.author=a.toString("hex"),Ye(r.author,64);break;case Ge.KIND:r.kind=a.readUInt32BE();break;case Ge.IDENTIFIER:r.identifier=a.toString("utf8");break;default:break}n+=2+s}return r}b();var st={};An(st,{calcPaddedLen:()=>tn,decrypt:()=>Do,encrypt:()=>No,getConversationKey:()=>Oo,v2:()=>ke});b();b();b();b();function Wl(t){return t instanceof Uint8Array||ArrayBuffer.isView(t)&&t.constructor.name==="Uint8Array"}function jr(t){if(typeof t!="boolean")throw new Error(`boolean expected, not ${t}`)}function zr(t){if(!Number.isSafeInteger(t)||t<0)throw new Error("positive integer expected, got "+t)}function ue(t,e,r=""){let n=Wl(t),o=t?.length,i=e!==void 0;if(!n||i&&o!==e){let s=r&&`"${r}" `,a=i?` of length ${e}`:"",c=n?`length=${o}`:`type=${typeof t}`;throw new Error(s+"expected Uint8Array"+a+", got "+c)}return t}function bo(t,e=!0){if(t.destroyed)throw new Error("Hash instance has been destroyed");if(e&&t.finished)throw new Error("Hash#digest() has already been called")}function Vs(t,e){ue(t,void 0,"output");let r=e.outputLen;if(t.length{function r(n,...o){if(ue(n,void 0,"key"),!Yl)throw new Error("Non little-endian hardware is not yet supported");if(t.nonceLength!==void 0){let f=o[0];ue(f,t.varSizeNonce?void 0:t.nonceLength,"nonce")}let i=t.tagLength;i&&o[1]!==void 0&&ue(o[1],void 0,"AAD");let s=e(n,...o),a=(f,u)=>{if(u!==void 0){if(f!==2)throw new Error("cipher output not supported");ue(u,void 0,"output")}},c=!1;return{encrypt(f,u){if(c)throw new Error("cannot encrypt() twice with same key + nonce");return c=!0,ue(f),a(s.encrypt.length,u),s.encrypt(f,u)},decrypt(f,u){if(ue(f),i&&f.lengthUint8Array.from(t.split(""),e=>e.charCodeAt(0)),Jl=js("expand 16-byte k"),Xl=js("expand 32-byte k"),Ql=ot(Jl),eu=ot(Xl);function U(t,e){return t<>>32-e}function vo(t){return t.byteOffset%4===0}var Gr=64,tu=16,zs=2**32-1,qs=Uint32Array.of();function ru(t,e,r,n,o,i,s,a){let c=o.length,l=new Uint8Array(Gr),f=ot(l),u=vo(o)&&vo(i),h=u?ot(o):qs,d=u?ot(i):qs;for(let y=0;y=zs)throw new Error("arx: counter overflow");let p=Math.min(Gr,c-y);if(u&&p===Gr){let w=y/4;if(y%4!==0)throw new Error("arx: invalid block position");for(let k=0,O;k{ue(a,void 0,"key"),ue(c,void 0,"nonce"),ue(l,void 0,"data");let h=l.length;if(f===void 0&&(f=new Uint8Array(h)),ue(f,void 0,"output"),zr(u),u<0||u>=zs)throw new Error("arx: counter overflow");if(f.length>>13|n<<3)&8191,this.r[2]=(n>>>10|o<<6)&7939,this.r[3]=(o>>>7|i<<9)&8191,this.r[4]=(i>>>4|s<<12)&255,this.r[5]=s>>>1&8190,this.r[6]=(s>>>14|a<<2)&8191,this.r[7]=(a>>>11|c<<5)&8065,this.r[8]=(c>>>8|l<<8)&8191,this.r[9]=l>>>5&127;for(let f=0;f<8;f++)this.pad[f]=de(e,16+2*f)}process(e,r,n=!1){let o=n?0:2048,{h:i,r:s}=this,a=s[0],c=s[1],l=s[2],f=s[3],u=s[4],h=s[5],d=s[6],y=s[7],p=s[8],w=s[9],k=de(e,r+0),O=de(e,r+2),D=de(e,r+4),H=de(e,r+6),X=de(e,r+8),M=de(e,r+10),q=de(e,r+12),G=de(e,r+14),C=i[0]+(k&8191),$=i[1]+((k>>>13|O<<3)&8191),K=i[2]+((O>>>10|D<<6)&8191),P=i[3]+((D>>>7|H<<9)&8191),E=i[4]+((H>>>4|X<<12)&8191),x=i[5]+(X>>>1&8191),m=i[6]+((X>>>14|M<<2)&8191),A=i[7]+((M>>>11|q<<5)&8191),S=i[8]+((q>>>8|G<<8)&8191),I=i[9]+(G>>>5|o),v=0,B=v+C*a+$*(5*w)+K*(5*p)+P*(5*y)+E*(5*d);v=B>>>13,B&=8191,B+=x*(5*h)+m*(5*u)+A*(5*f)+S*(5*l)+I*(5*c),v+=B>>>13,B&=8191;let T=v+C*c+$*a+K*(5*w)+P*(5*p)+E*(5*y);v=T>>>13,T&=8191,T+=x*(5*d)+m*(5*h)+A*(5*u)+S*(5*f)+I*(5*l),v+=T>>>13,T&=8191;let L=v+C*l+$*c+K*a+P*(5*w)+E*(5*p);v=L>>>13,L&=8191,L+=x*(5*y)+m*(5*d)+A*(5*h)+S*(5*u)+I*(5*f),v+=L>>>13,L&=8191;let Y=v+C*f+$*l+K*c+P*a+E*(5*w);v=Y>>>13,Y&=8191,Y+=x*(5*p)+m*(5*y)+A*(5*d)+S*(5*h)+I*(5*u),v+=Y>>>13,Y&=8191;let z=v+C*u+$*f+K*l+P*c+E*a;v=z>>>13,z&=8191,z+=x*(5*w)+m*(5*p)+A*(5*y)+S*(5*d)+I*(5*h),v+=z>>>13,z&=8191;let V=v+C*h+$*u+K*f+P*l+E*c;v=V>>>13,V&=8191,V+=x*a+m*(5*w)+A*(5*p)+S*(5*y)+I*(5*d),v+=V>>>13,V&=8191;let Z=v+C*d+$*h+K*u+P*f+E*l;v=Z>>>13,Z&=8191,Z+=x*c+m*a+A*(5*w)+S*(5*p)+I*(5*y),v+=Z>>>13,Z&=8191;let ee=v+C*y+$*d+K*h+P*u+E*f;v=ee>>>13,ee&=8191,ee+=x*l+m*c+A*a+S*(5*w)+I*(5*p),v+=ee>>>13,ee&=8191;let fe=v+C*p+$*y+K*d+P*h+E*u;v=fe>>>13,fe&=8191,fe+=x*f+m*l+A*c+S*a+I*(5*w),v+=fe>>>13,fe&=8191;let J=v+C*w+$*p+K*y+P*d+E*h;v=J>>>13,J&=8191,J+=x*u+m*f+A*l+S*c+I*a,v+=J>>>13,J&=8191,v=(v<<2)+v|0,v=v+B|0,B=v&8191,v=v>>>13,T+=v,i[0]=B,i[1]=T,i[2]=L,i[3]=Y,i[4]=z,i[5]=V,i[6]=Z,i[7]=ee,i[8]=fe,i[9]=J}finalize(){let{h:e,pad:r}=this,n=new Uint16Array(10),o=e[1]>>>13;e[1]&=8191;for(let a=2;a<10;a++)e[a]+=o,o=e[a]>>>13,e[a]&=8191;e[0]+=o*5,o=e[0]>>>13,e[0]&=8191,e[1]+=o,o=e[1]>>>13,e[1]&=8191,e[2]+=o,n[0]=e[0]+5,o=n[0]>>>13,n[0]&=8191;for(let a=1;a<10;a++)n[a]=e[a]+o,o=n[a]>>>13,n[a]&=8191;n[9]-=8192;let i=(o^1)-1;for(let a=0;a<10;a++)n[a]&=i;i=~i;for(let a=0;a<10;a++)e[a]=e[a]&i|n[a];e[0]=(e[0]|e[1]<<13)&65535,e[1]=(e[1]>>>3|e[2]<<10)&65535,e[2]=(e[2]>>>6|e[3]<<7)&65535,e[3]=(e[3]>>>9|e[4]<<4)&65535,e[4]=(e[4]>>>12|e[5]<<1|e[6]<<14)&65535,e[5]=(e[6]>>>2|e[7]<<11)&65535,e[6]=(e[7]>>>5|e[8]<<8)&65535,e[7]=(e[8]>>>8|e[9]<<5)&65535;let s=e[0]+r[0];e[0]=s&65535;for(let a=1;a<8;a++)s=(e[a]+r[a]|0)+(s>>>16)|0,e[a]=s&65535;it(n)}update(e){bo(this),ue(e),e=Yt(e);let{buffer:r,blockLen:n}=this,o=e.length;for(let i=0;i>>0,e[i++]=n[s]>>>8;return e}digest(){let{buffer:e,outputLen:r}=this;this.digestInto(e);let n=e.slice(0,r);return this.destroy(),n}};function nu(t){let e=(n,o)=>t(o).update(n).digest(),r=t(new Uint8Array(32));return e.outputLen=r.outputLen,e.blockLen=r.blockLen,e.create=n=>t(n),e}var Ws=nu(t=>new Ao(t));function Zs(t,e,r,n,o,i=20){let s=t[0],a=t[1],c=t[2],l=t[3],f=e[0],u=e[1],h=e[2],d=e[3],y=e[4],p=e[5],w=e[6],k=e[7],O=o,D=r[0],H=r[1],X=r[2],M=s,q=a,G=c,C=l,$=f,K=u,P=h,E=d,x=y,m=p,A=w,S=k,I=O,v=D,B=H,T=X;for(let Y=0;Y{t.update(e);let r=e.length%16;r&&t.update(su.subarray(r))},au=new Uint8Array(32);function Ys(t,e,r,n,o){o!==void 0&&ue(o,void 0,"AAD");let i=t(e,r,au),s=$s(n.length,o?o.length:0,!0),a=Ws.create(i);o&&Gs(a,o),Gs(a,n),a.update(s);let c=a.digest();return it(i,s),c}var Js=t=>(e,r,n)=>({encrypt(i,s){let a=i.length;s=Eo(a+16,s,!1),s.set(i);let c=s.subarray(0,-16);t(e,r,c,c,1);let l=Ys(t,e,r,c,n);return s.set(l,a),it(l),s},decrypt(i,s){s=Eo(i.length-16,s,!1);let a=i.subarray(0,-16),c=i.subarray(-16),l=Ys(t,e,r,a,n);if(!Wr(c,l))throw new Error("invalid tag");return s.set(i.subarray(0,-16)),t(e,r,s,s,1),it(l),s}}),Vh=xo({blockSize:64,nonceLength:12,tagLength:16},Js(Yr)),Bo=xo({blockSize:64,nonceLength:24,tagLength:16},Js(iu));b();function Qs(t,e,r){return Qe(t),r===void 0&&(r=new Uint8Array(t.outputLen)),Fe(t,r,e)}var So=Uint8Array.of(0),Xs=Uint8Array.of();function ea(t,e,r,n=32){Qe(t),te(n,"length");let o=t.outputLen;if(n>255*o)throw new Error("Length must be <= 255*HashLen");let i=Math.ceil(n/o);r===void 0?r=Xs:F(r,void 0,"info");let s=new Uint8Array(i*o),a=Fe.create(t,e),c=a._cloneInto(),l=new Uint8Array(a.outputLen);for(let f=0;ftypeof r=="string"):e.every(r=>Number.isSafeInteger(r)):!1}function ia(t){if(typeof t!="function")throw new Error("function expected");return!0}function It(t,e){if(typeof e!="string")throw new Error(`${t}: string expected`);return!0}function Jt(t){if(!Number.isSafeInteger(t))throw new Error(`invalid integer: ${t}`)}function Jr(t){if(!Array.isArray(t))throw new Error("array expected")}function Xr(t,e){if(!oa(!0,e))throw new Error(`${t}: array of strings expected`)}function _o(t,e){if(!oa(!1,e))throw new Error(`${t}: array of numbers expected`)}function Lo(...t){let e=i=>i,r=(i,s)=>a=>i(s(a)),n=t.map(i=>i.encode).reduceRight(r,e),o=t.map(i=>i.decode).reduce(r,e);return{encode:n,decode:o}}function Uo(t){let e=typeof t=="string"?t.split(""):t,r=e.length;Xr("alphabet",e);let n=new Map(e.map((o,i)=>[o,i]));return{encode:o=>(Jr(o),o.map(i=>{if(!Number.isSafeInteger(i)||i<0||i>=r)throw new Error(`alphabet.encode: digit index outside alphabet "${i}". Allowed: ${t}`);return e[i]})),decode:o=>(Jr(o),o.map(i=>{It("alphabet.decode",i);let s=n.get(i);if(s===void 0)throw new Error(`Unknown letter: "${i}". Allowed: ${t}`);return s}))}}function Po(t=""){return It("join",t),{encode:e=>(Xr("join.decode",e),e.join(t)),decode:e=>(It("join.decode",e),e.split(t))}}function sa(t,e="="){return Jt(t),It("padding",e),{encode(r){for(Xr("padding.encode",r);r.length*t%8;)r.push(e);return r},decode(r){Xr("padding.decode",r);let n=r.length;if(n*t%8)throw new Error("padding: invalid, string should have whole number of bytes");for(;n>0&&r[n-1]===e;n--)if((n-1)*t%8===0)throw new Error("padding: invalid, string has too much padding");return r.slice(0,n)}}}function Io(t,e,r){if(e<2)throw new Error(`convertRadix: invalid from=${e}, base cannot be less than 2`);if(r<2)throw new Error(`convertRadix: invalid to=${r}, base cannot be less than 2`);if(Jr(t),!t.length)return[];let n=0,o=[],i=Array.from(t,a=>{if(Jt(a),a<0||a>=e)throw new Error(`invalid integer: ${a}`);return a}),s=i.length;for(;;){let a=0,c=!0;for(let l=n;le===0?t:aa(e,t%e),Qr=(t,e)=>t+(e-aa(t,e)),Zr=(()=>{let t=[];for(let e=0;e<40;e++)t.push(2**e);return t})();function en(t,e,r,n){if(Jr(t),e<=0||e>32)throw new Error(`convertRadix2: wrong from=${e}`);if(r<=0||r>32)throw new Error(`convertRadix2: wrong to=${r}`);if(Qr(e,r)>32)throw new Error(`convertRadix2: carry overflow from=${e} to=${r} carryBits=${Qr(e,r)}`);let o=0,i=0,s=Zr[e],a=Zr[r]-1,c=[];for(let l of t){if(Jt(l),l>=s)throw new Error(`convertRadix2: invalid data word=${l} from=${e}`);if(o=o<32)throw new Error(`convertRadix2: carry overflow pos=${i} from=${e}`);for(i+=e;i>=r;i-=r)c.push((o>>i-r&a)>>>0);let f=Zr[i];if(f===void 0)throw new Error("invalid carry");o&=f-1}if(o=o<=e)throw new Error("Excess padding");if(!n&&o>0)throw new Error(`Non-zero padding: ${o}`);return n&&i>0&&c.push(o>>>0),c}function lu(t){Jt(t);let e=2**8;return{encode:r=>{if(!Zt(r))throw new Error("radix.encode input should be Uint8Array");return Io(Array.from(r),e,t)},decode:r=>(_o("radix.decode",r),Uint8Array.from(Io(r,t,e)))}}function Ro(t,e=!1){if(Jt(t),t<=0||t>32)throw new Error("radix2: bits should be in (0..32]");if(Qr(8,t)>32||Qr(t,8)>32)throw new Error("radix2: carry overflow");return{encode:r=>{if(!Zt(r))throw new Error("radix2.encode input should be Uint8Array");return en(Array.from(r),8,t,!e)},decode:r=>(_o("radix2.decode",r),Uint8Array.from(en(r,t,8,e)))}}function ta(t){return ia(t),function(...e){try{return t.apply(null,e)}catch{}}}function uu(t,e){return Jt(t),ia(e),{encode(r){if(!Zt(r))throw new Error("checksum.encode: input should be Uint8Array");let n=e(r).slice(0,t),o=new Uint8Array(r.length+t);return o.set(r),o.set(n,r.length),o},decode(r){if(!Zt(r))throw new Error("checksum.decode: input should be Uint8Array");let n=r.slice(0,-t),o=r.slice(-t),i=e(n).slice(0,t);for(let s=0;s{It("base64",t);let r=e?/^[A-Za-z0-9=_-]+$/:/^[A-Za-z0-9=+/]+$/,n=e?"base64url":"base64";if(t.length>0&&!r.test(t))throw new Error("invalid base64");return Uint8Array.fromBase64(t,{alphabet:n,lastChunkHandling:"strict"})},Co=fu?{encode(t){return cu(t),t.toBase64()},decode(t){return du(t,!1)}}:Lo(Ro(6),Uo("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"),sa(6),Po(""));var To=Lo(Uo("qpzry9x8gf2tvdw0s3jn54khce6mua7l"),Po("")),ra=[996825010,642813549,513874426,1027748829,705979059];function fr(t){let e=t>>25,r=(t&33554431)<<5;for(let n=0;n>n&1)===1&&(r^=ra[n]);return r}function na(t,e,r=1){let n=t.length,o=1;for(let i=0;i126)throw new Error(`Invalid prefix (${t})`);o=fr(o)^s>>5}o=fr(o);for(let i=0;id)throw new TypeError(`Length ${p} exceeds limit ${d}`);let w=u.toLowerCase(),k=na(w,h,e);return`${w}1${To.encode(h)}${k}`}function a(u,h=90){It("bech32.decode input",u);let d=u.length;if(d<8||h!==!1&&d>h)throw new TypeError(`invalid string length: ${d} (${u}). Expected (8..${h})`);let y=u.toLowerCase();if(u!==y&&u!==u.toUpperCase())throw new Error("String must be lowercase or uppercase");let p=y.lastIndexOf("1");if(p===0||p===-1)throw new Error('Letter "1" must be present between prefix and data only');let w=y.slice(0,p),k=y.slice(p+1);if(k.length<6)throw new Error("Data must be at least 6 characters long");let O=To.decode(k).slice(0,-6),D=na(w,O,e);if(!k.endsWith(D))throw new Error(`Invalid checksum in ${u}: expected "${D}"`);return{prefix:w,words:O}}let c=ta(a);function l(u){let{prefix:h,words:d}=a(u,!1);return{prefix:h,words:d,bytes:n(d)}}function f(u,h){return s(u,o(h))}return{encode:s,decode:a,encodeFromBytes:f,decodeToBytes:l,decodeUnsafe:c,fromWords:n,fromWordsUnsafe:i,toWords:o}}var hr=hu("bech32");var ca=new TextEncoder,pu=new TextDecoder,la=1,ua=65535;function tn(t){if(!Number.isSafeInteger(t)||t<1)throw new Error("expected positive integer");if(t<=32)return 32;let e=1<ua)throw new Error("invalid plaintext length: must be between 1 and 65535 bytes");let n=new Uint8Array(2);new DataView(n.buffer).setUint16(0,r,!1);let o=new Uint8Array(tn(r)-r);return ie(n,e,o)}function gu(t){let e=new DataView(t.buffer,t.byteOffset).getUint16(0,!1),r=t.subarray(2,2+e);if(eua||r.length!==e||t.length!==2+tn(e))throw new Error("invalid padding");return pu.decode(r)}function Oo(t,e){let n=kt.getSharedSecret(t,oe("02"+e)).subarray(1,33);return Qs(pe,n,ca.encode("nip44-v2"))}function fa(t,e){let r=ea(pe,t,e,76);return{chacha_key:r.subarray(0,32),chacha_nonce:r.subarray(32,44),hmac_key:r.subarray(44,76)}}function No(t,e,r=ge(32)){let{chacha_key:n,chacha_nonce:o,hmac_key:i}=fa(e,r),s=yu(t),a=Yr(n,o,s),c=Fe(pe,i,ie(r,a));return Co.encode(ie(new Uint8Array([2]),r,a,c))}function Do(t,e){let r=Co.decode(t),n=r[0];if(n!==2)throw new Error(`unknown encryption version: ${n}`);if(r.length<99||r.length>65603)throw new Error("invalid payload size");let o=r.subarray(1,33),i=r.subarray(33,r.length-32),s=r.subarray(r.length-32),{chacha_key:a,chacha_nonce:c,hmac_key:l}=fa(e,o),f=Fe(pe,l,ie(o,i));if(!Wr(s,f))throw new Error("invalid MAC");let u=Yr(a,c,i);return gu(u)}var ke={utils:{getConversationKey:Oo,calcPaddedLen:tn},encrypt:No,decrypt:Do};b();b();b();b();function bu(t,e,r,n){Qe(t);let o=Ar({dkLen:32,asyncTick:10},n),{c:i,dkLen:s,asyncTick:a}=o;if(te(i,"c"),te(s,"dkLen"),te(a,"asyncTick"),i<1)throw new Error("iterations (c) must be >= 1");let c=In(e,"password"),l=In(r,"salt"),f=new Uint8Array(s),u=Fe.create(t,c),h=u._cloneInto().update(l);return{c:i,dkLen:s,asyncTick:a,DK:f,PRF:u,PRFSalt:h}}function xu(t,e,r,n,o){return t.destroy(),e.destroy(),n&&n.destroy(),Be(o),r}function Mo(t,e,r,n){let{c:o,dkLen:i,DK:s,PRF:a,PRFSalt:c}=bu(t,e,r,n),l,f=new Uint8Array(4),u=Nt(f),h=new Uint8Array(a.outputLen);for(let d=1,y=0;y0&&(s+=16),da(r,i,t,e+=16,r,s)}function Eu(t,e,r){let n=Ar({dkLen:32,asyncTick:10,maxmem:1073742848},r),{N:o,r:i,p:s,dkLen:a,asyncTick:c,maxmem:l,onProgress:f}=n;if(te(o,"N"),te(i,"r"),te(s,"p"),te(a,"dkLen"),te(c,"asyncTick"),te(l,"maxmem"),f!==void 0&&typeof f!="function")throw new Error("progressCb must be a function");let u=128*i,h=u/4,d=Math.pow(2,32);if(o<=1||(o&o-1)!==0||o>d)throw new Error('"N" expected a power of 2, and 2^1 <= N <= 2^32');if(s<1||s>(d-1)*32/u)throw new Error('"p" expected integer 1..((2^32 - 1) * 32) / (128 * r)');if(a<1||a>(d-1)*32)throw new Error('"dkLen" expected integer 1..(2^32 - 1) * 32');if(u*(o+s)>l)throw new Error('"maxmem" limit was hit, expected 128*r*(N+p) <= "maxmem"='+l);let p=Mo(pe,t,e,{c:1,dkLen:u*s}),w=kr(p),k=kr(new Uint8Array(u*o)),O=kr(new Uint8Array(u)),D=()=>{};if(f){let H=2*o*s,X=Math.max(Math.floor(H/1e4),1),M=0;D=()=>{M++,f&&(!(M%X)||M===H)&&f(M/H)}}return{N:o,r:i,p:s,dkLen:a,blockSize32:h,V:k,B32:w,B:p,tmp:O,blockMixCb:D,asyncTick:c}}function vu(t,e,r,n,o){let i=Mo(pe,t,r,{c:1,dkLen:e});return Be(r,n,o),i}function Ko(t,e,r){let{N:n,r:o,p:i,dkLen:s,blockSize32:a,V:c,B32:l,B:f,tmp:u,blockMixCb:h}=Eu(t,e,r);Sn(l);for(let d=0;d>>0;for(let k=0;ke.toString(16).padStart(2,"0")).join("")}b();b();var Au=t=>t[0]==="\u3042\u3044\u3053\u304F\u3057\u3093";function Bu(t){if(typeof t!="string")throw new TypeError("invalid mnemonic type: "+typeof t);return t.normalize("NFKD")}function Su(t){let e=Bu(t),r=e.split(" ");if(![12,15,18,21,24].includes(r.length))throw new Error("Invalid mnemonic");return{nfkd:e,words:r}}function ya(t){if(F(t),![16,20,24,28,32].includes(t.length))throw new Error("invalid entropy length")}var Iu=t=>{let e=8-t.length/4;return new Uint8Array([pe(t)[0]>>e<{if(typeof e!="string")throw new Error("wordlist: non-string element: "+e)}),dr.chain(dr.checksum(1,Iu),dr.radix2(11,!0),dr.alphabet(t))}function Vo(t,e){let{words:r}=Su(t),n=ga(e).decode(r);return ya(n),n}function ma(t,e){return ya(t),ga(e).encode(t).join(Au(e)?"\u3000":" ")}function wa(t,e){try{Vo(t,e)}catch{return!1}return!0}b();var rn=`abandon +(() => { + var __create = Object.create; + var __defProp = Object.defineProperty; + var __getOwnPropDesc = Object.getOwnPropertyDescriptor; + var __getOwnPropNames = Object.getOwnPropertyNames; + var __getProtoOf = Object.getPrototypeOf; + var __hasOwnProp = Object.prototype.hasOwnProperty; + var __esm = (fn, res) => function __init() { + return fn && (res = (0, fn[__getOwnPropNames(fn)[0]])(fn = 0)), res; + }; + var __commonJS = (cb, mod2) => function __require() { + return mod2 || (0, cb[__getOwnPropNames(cb)[0]])((mod2 = { exports: {} }).exports, mod2), mod2.exports; + }; + var __export = (target, all) => { + for (var name in all) + __defProp(target, name, { get: all[name], enumerable: true }); + }; + var __copyProps = (to, from, except, desc) => { + if (from && typeof from === "object" || typeof from === "function") { + for (let key of __getOwnPropNames(from)) + if (!__hasOwnProp.call(to, key) && key !== except) + __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable }); + } + return to; + }; + var __toESM = (mod2, isNodeMode, target) => (target = mod2 != null ? __create(__getProtoOf(mod2)) : {}, __copyProps( + // If the importer is in node compatibility mode or this is not an ESM + // file that has been converted to a CommonJS file using a Babel- + // compatible transform (i.e. "__esModule" has not been set), then set + // "default" to the CommonJS "module.exports" for node compatibility. + isNodeMode || !mod2 || !mod2.__esModule ? __defProp(target, "default", { value: mod2, enumerable: true }) : target, + mod2 + )); + + // src/shims/process.js + var process; + var init_process = __esm({ + "src/shims/process.js"() { + process = { + env: { NODE_ENV: "production", LOG_LEVEL: "warn" }, + browser: true, + version: "", + stdout: null, + stderr: null, + nextTick: function(fn) { + var args = Array.prototype.slice.call(arguments, 1); + Promise.resolve().then(function() { + fn.apply(null, args); + }); + } + }; + } + }); + + // node_modules/quick-format-unescaped/index.js + var require_quick_format_unescaped = __commonJS({ + "node_modules/quick-format-unescaped/index.js"(exports, module) { + "use strict"; + init_process(); + function tryStringify(o) { + try { + return JSON.stringify(o); + } catch (e) { + return '"[Circular]"'; + } + } + module.exports = format; + function format(f, args, opts) { + var ss = opts && opts.stringify || tryStringify; + var offset = 1; + if (typeof f === "object" && f !== null) { + var len = args.length + offset; + if (len === 1) return f; + var objects = new Array(len); + objects[0] = ss(f); + for (var index = 1; index < len; index++) { + objects[index] = ss(args[index]); + } + return objects.join(" "); + } + if (typeof f !== "string") { + return f; + } + var argLen = args.length; + if (argLen === 0) return f; + var str = ""; + var a = 1 - offset; + var lastPos = -1; + var flen = f && f.length || 0; + for (var i = 0; i < flen; ) { + if (f.charCodeAt(i) === 37 && i + 1 < flen) { + lastPos = lastPos > -1 ? lastPos : 0; + switch (f.charCodeAt(i + 1)) { + case 100: + // 'd' + case 102: + if (a >= argLen) + break; + if (args[a] == null) break; + if (lastPos < i) + str += f.slice(lastPos, i); + str += Number(args[a]); + lastPos = i + 2; + i++; + break; + case 105: + if (a >= argLen) + break; + if (args[a] == null) break; + if (lastPos < i) + str += f.slice(lastPos, i); + str += Math.floor(Number(args[a])); + lastPos = i + 2; + i++; + break; + case 79: + // 'O' + case 111: + // 'o' + case 106: + if (a >= argLen) + break; + if (args[a] === void 0) break; + if (lastPos < i) + str += f.slice(lastPos, i); + var type = typeof args[a]; + if (type === "string") { + str += "'" + args[a] + "'"; + lastPos = i + 2; + i++; + break; + } + if (type === "function") { + str += args[a].name || ""; + lastPos = i + 2; + i++; + break; + } + str += ss(args[a]); + lastPos = i + 2; + i++; + break; + case 115: + if (a >= argLen) + break; + if (lastPos < i) + str += f.slice(lastPos, i); + str += String(args[a]); + lastPos = i + 2; + i++; + break; + case 37: + if (lastPos < i) + str += f.slice(lastPos, i); + str += "%"; + lastPos = i + 2; + i++; + a--; + break; + } + ++a; + } + ++i; + } + if (lastPos === -1) + return f; + else if (lastPos < flen) { + str += f.slice(lastPos); + } + return str; + } + } + }); + + // node_modules/pino/browser.js + var require_browser = __commonJS({ + "node_modules/pino/browser.js"(exports, module) { + "use strict"; + init_process(); + var format = require_quick_format_unescaped(); + module.exports = pino2; + var _console = pfGlobalThisOrFallback().console || {}; + var stdSerializers = { + mapHttpRequest: mock, + mapHttpResponse: mock, + wrapRequestSerializer: passthrough, + wrapResponseSerializer: passthrough, + wrapErrorSerializer: passthrough, + req: mock, + res: mock, + err: asErrValue, + errWithCause: asErrValue + }; + function levelToValue(level, logger2) { + return level === "silent" ? Infinity : logger2.levels.values[level]; + } + var baseLogFunctionSymbol = /* @__PURE__ */ Symbol("pino.logFuncs"); + var hierarchySymbol = /* @__PURE__ */ Symbol("pino.hierarchy"); + var logFallbackMap = { + error: "log", + fatal: "error", + warn: "error", + info: "log", + debug: "log", + trace: "log" + }; + function appendChildLogger(parentLogger, childLogger) { + const newEntry = { + logger: childLogger, + parent: parentLogger[hierarchySymbol] + }; + childLogger[hierarchySymbol] = newEntry; + } + function setupBaseLogFunctions(logger2, levels, proto) { + const logFunctions = {}; + levels.forEach((level) => { + logFunctions[level] = proto[level] ? proto[level] : _console[level] || _console[logFallbackMap[level] || "log"] || noop; + }); + logger2[baseLogFunctionSymbol] = logFunctions; + } + function shouldSerialize(serialize, serializers) { + if (Array.isArray(serialize)) { + const hasToFilter = serialize.filter(function(k) { + return k !== "!stdSerializers.err"; + }); + return hasToFilter; + } else if (serialize === true) { + return Object.keys(serializers); + } + return false; + } + function pino2(opts) { + opts = opts || {}; + opts.browser = opts.browser || {}; + const transmit2 = opts.browser.transmit; + if (transmit2 && typeof transmit2.send !== "function") { + throw Error("pino: transmit option must have a send function"); + } + const proto = opts.browser.write || _console; + if (opts.browser.write) opts.browser.asObject = true; + const serializers = opts.serializers || {}; + const serialize = shouldSerialize(opts.browser.serialize, serializers); + let stdErrSerialize = opts.browser.serialize; + if (Array.isArray(opts.browser.serialize) && opts.browser.serialize.indexOf("!stdSerializers.err") > -1) stdErrSerialize = false; + const customLevels = Object.keys(opts.customLevels || {}); + const levels = ["error", "fatal", "warn", "info", "debug", "trace"].concat(customLevels); + if (typeof proto === "function") { + levels.forEach(function(level2) { + proto[level2] = proto; + }); + } + if (opts.enabled === false || opts.browser.disabled) opts.level = "silent"; + const level = opts.level || "info"; + const logger2 = Object.create(proto); + if (!logger2.log) logger2.log = noop; + setupBaseLogFunctions(logger2, levels, proto); + appendChildLogger({}, logger2); + Object.defineProperty(logger2, "levelVal", { + get: getLevelVal + }); + Object.defineProperty(logger2, "level", { + get: getLevel, + set: setLevel + }); + const setOpts = { + transmit: transmit2, + serialize, + asObject: opts.browser.asObject, + asObjectBindingsOnly: opts.browser.asObjectBindingsOnly, + formatters: opts.browser.formatters, + reportCaller: opts.browser.reportCaller, + levels, + timestamp: getTimeFunction(opts), + messageKey: opts.messageKey || "msg", + onChild: opts.onChild || noop + }; + logger2.levels = getLevels(opts); + logger2.level = level; + logger2.isLevelEnabled = function(level2) { + if (!this.levels.values[level2]) { + return false; + } + return this.levels.values[level2] >= this.levels.values[this.level]; + }; + logger2.setMaxListeners = logger2.getMaxListeners = logger2.emit = logger2.addListener = logger2.on = logger2.prependListener = logger2.once = logger2.prependOnceListener = logger2.removeListener = logger2.removeAllListeners = logger2.listeners = logger2.listenerCount = logger2.eventNames = logger2.write = logger2.flush = noop; + logger2.serializers = serializers; + logger2._serialize = serialize; + logger2._stdErrSerialize = stdErrSerialize; + logger2.child = function(...args) { + return child.call(this, setOpts, ...args); + }; + if (transmit2) logger2._logEvent = createLogEventShape(); + function getLevelVal() { + return levelToValue(this.level, this); + } + function getLevel() { + return this._level; + } + function setLevel(level2) { + if (level2 !== "silent" && !this.levels.values[level2]) { + throw Error("unknown level " + level2); + } + this._level = level2; + set(this, setOpts, logger2, "error"); + set(this, setOpts, logger2, "fatal"); + set(this, setOpts, logger2, "warn"); + set(this, setOpts, logger2, "info"); + set(this, setOpts, logger2, "debug"); + set(this, setOpts, logger2, "trace"); + customLevels.forEach((level3) => { + set(this, setOpts, logger2, level3); + }); + } + function child(setOpts2, bindings, childOptions) { + if (!bindings) { + throw new Error("missing bindings for child Pino"); + } + childOptions = childOptions || {}; + if (serialize && bindings.serializers) { + childOptions.serializers = bindings.serializers; + } + const childOptionsSerializers = childOptions.serializers; + if (serialize && childOptionsSerializers) { + var childSerializers = Object.assign({}, serializers, childOptionsSerializers); + var childSerialize = opts.browser.serialize === true ? Object.keys(childSerializers) : serialize; + delete bindings.serializers; + applySerializers([bindings], childSerialize, childSerializers, this._stdErrSerialize); + } + function Child(parent) { + this._childLevel = (parent._childLevel | 0) + 1; + this.bindings = bindings; + if (childSerializers) { + this.serializers = childSerializers; + this._serialize = childSerialize; + } + if (transmit2) { + this._logEvent = createLogEventShape( + [].concat(parent._logEvent.bindings, bindings) + ); + } + } + Child.prototype = this; + const newLogger = new Child(this); + appendChildLogger(this, newLogger); + newLogger.child = function(...args) { + return child.call(this, setOpts2, ...args); + }; + newLogger.level = childOptions.level || this.level; + setOpts2.onChild(newLogger); + return newLogger; + } + return logger2; + } + function getLevels(opts) { + const customLevels = opts.customLevels || {}; + const values = Object.assign({}, pino2.levels.values, customLevels); + const labels = Object.assign({}, pino2.levels.labels, invertObject(customLevels)); + return { + values, + labels + }; + } + function invertObject(obj) { + const inverted = {}; + Object.keys(obj).forEach(function(key) { + inverted[obj[key]] = key; + }); + return inverted; + } + pino2.levels = { + values: { + fatal: 60, + error: 50, + warn: 40, + info: 30, + debug: 20, + trace: 10 + }, + labels: { + 10: "trace", + 20: "debug", + 30: "info", + 40: "warn", + 50: "error", + 60: "fatal" + } + }; + pino2.stdSerializers = stdSerializers; + pino2.stdTimeFunctions = Object.assign({}, { nullTime, epochTime, unixTime, isoTime }); + function getBindingChain(logger2) { + const bindings = []; + if (logger2.bindings) { + bindings.push(logger2.bindings); + } + let hierarchy = logger2[hierarchySymbol]; + while (hierarchy.parent) { + hierarchy = hierarchy.parent; + if (hierarchy.logger.bindings) { + bindings.push(hierarchy.logger.bindings); + } + } + return bindings.reverse(); + } + function set(self2, opts, rootLogger, level) { + Object.defineProperty(self2, level, { + value: levelToValue(self2.level, rootLogger) > levelToValue(level, rootLogger) ? noop : rootLogger[baseLogFunctionSymbol][level], + writable: true, + enumerable: true, + configurable: true + }); + if (self2[level] === noop) { + if (!opts.transmit) return; + const transmitLevel = opts.transmit.level || self2.level; + const transmitValue = levelToValue(transmitLevel, rootLogger); + const methodValue = levelToValue(level, rootLogger); + if (methodValue < transmitValue) return; + } + self2[level] = createWrap(self2, opts, rootLogger, level); + const bindings = getBindingChain(self2); + if (bindings.length === 0) { + return; + } + self2[level] = prependBindingsInArguments(bindings, self2[level]); + } + function prependBindingsInArguments(bindings, logFunc) { + return function() { + return logFunc.apply(this, [...bindings, ...arguments]); + }; + } + function createWrap(self2, opts, rootLogger, level) { + return /* @__PURE__ */ (function(write) { + return function LOG() { + const ts = opts.timestamp(); + const args = new Array(arguments.length); + const proto = Object.getPrototypeOf && Object.getPrototypeOf(this) === _console ? _console : this; + for (var i = 0; i < args.length; i++) args[i] = arguments[i]; + var argsIsSerialized = false; + if (opts.serialize) { + applySerializers(args, this._serialize, this.serializers, this._stdErrSerialize); + argsIsSerialized = true; + } + if (opts.asObject || opts.formatters) { + const out = asObject(this, level, args, ts, opts); + if (opts.reportCaller && out && out.length > 0 && out[0] && typeof out[0] === "object") { + try { + const caller = getCallerLocation(); + if (caller) out[0].caller = caller; + } catch (e) { + } + } + write.call(proto, ...out); + } else { + if (opts.reportCaller) { + try { + const caller = getCallerLocation(); + if (caller) args.push(caller); + } catch (e) { + } + } + write.apply(proto, args); + } + if (opts.transmit) { + const transmitLevel = opts.transmit.level || self2._level; + const transmitValue = levelToValue(transmitLevel, rootLogger); + const methodValue = levelToValue(level, rootLogger); + if (methodValue < transmitValue) return; + transmit(this, { + ts, + methodLevel: level, + methodValue, + transmitLevel, + transmitValue: rootLogger.levels.values[opts.transmit.level || self2._level], + send: opts.transmit.send, + val: levelToValue(self2._level, rootLogger) + }, args, argsIsSerialized); + } + }; + })(self2[baseLogFunctionSymbol][level]); + } + function asObject(logger2, level, args, ts, opts) { + const { + level: levelFormatter, + log: logObjectFormatter = (obj) => obj + } = opts.formatters || {}; + const argsCloned = args.slice(); + let msg = argsCloned[0]; + const logObject = {}; + let lvl = (logger2._childLevel | 0) + 1; + if (lvl < 1) lvl = 1; + if (ts) { + logObject.time = ts; + } + if (levelFormatter) { + const formattedLevel = levelFormatter(level, logger2.levels.values[level]); + Object.assign(logObject, formattedLevel); + } else { + logObject.level = logger2.levels.values[level]; + } + if (opts.asObjectBindingsOnly) { + if (msg !== null && typeof msg === "object") { + while (lvl-- && typeof argsCloned[0] === "object") { + Object.assign(logObject, argsCloned.shift()); + } + } + const formattedLogObject = logObjectFormatter(logObject); + return [formattedLogObject, ...argsCloned]; + } else { + if (msg !== null && typeof msg === "object") { + while (lvl-- && typeof argsCloned[0] === "object") { + Object.assign(logObject, argsCloned.shift()); + } + msg = argsCloned.length ? format(argsCloned.shift(), argsCloned) : void 0; + } else if (typeof msg === "string") msg = format(argsCloned.shift(), argsCloned); + if (msg !== void 0) logObject[opts.messageKey] = msg; + const formattedLogObject = logObjectFormatter(logObject); + return [formattedLogObject]; + } + } + function applySerializers(args, serialize, serializers, stdErrSerialize) { + for (const i in args) { + if (stdErrSerialize && args[i] instanceof Error) { + args[i] = pino2.stdSerializers.err(args[i]); + } else if (typeof args[i] === "object" && !Array.isArray(args[i]) && serialize) { + for (const k in args[i]) { + if (serialize.indexOf(k) > -1 && k in serializers) { + args[i][k] = serializers[k](args[i][k]); + } + } + } + } + } + function transmit(logger2, opts, args, argsIsSerialized = false) { + const send = opts.send; + const ts = opts.ts; + const methodLevel = opts.methodLevel; + const methodValue = opts.methodValue; + const val = opts.val; + const bindings = logger2._logEvent.bindings; + if (!argsIsSerialized) { + applySerializers( + args, + logger2._serialize || Object.keys(logger2.serializers), + logger2.serializers, + logger2._stdErrSerialize === void 0 ? true : logger2._stdErrSerialize + ); + } + logger2._logEvent.ts = ts; + logger2._logEvent.messages = args.filter(function(arg) { + return bindings.indexOf(arg) === -1; + }); + logger2._logEvent.level.label = methodLevel; + logger2._logEvent.level.value = methodValue; + send(methodLevel, logger2._logEvent, val); + logger2._logEvent = createLogEventShape(bindings); + } + function createLogEventShape(bindings) { + return { + ts: 0, + messages: [], + bindings: bindings || [], + level: { label: "", value: 0 } + }; + } + function asErrValue(err) { + const obj = { + type: err.constructor.name, + msg: err.message, + stack: err.stack + }; + for (const key in err) { + if (obj[key] === void 0) { + obj[key] = err[key]; + } + } + return obj; + } + function getTimeFunction(opts) { + if (typeof opts.timestamp === "function") { + return opts.timestamp; + } + if (opts.timestamp === false) { + return nullTime; + } + return epochTime; + } + function mock() { + return {}; + } + function passthrough(a) { + return a; + } + function noop() { + } + function nullTime() { + return false; + } + function epochTime() { + return Date.now(); + } + function unixTime() { + return Math.round(Date.now() / 1e3); + } + function isoTime() { + return new Date(Date.now()).toISOString(); + } + function pfGlobalThisOrFallback() { + function defd(o) { + return typeof o !== "undefined" && o; + } + try { + if (typeof globalThis !== "undefined") return globalThis; + Object.defineProperty(Object.prototype, "globalThis", { + get: function() { + delete Object.prototype.globalThis; + return this.globalThis = this; + }, + configurable: true + }); + return globalThis; + } catch (e) { + return defd(self) || defd(window) || defd(this) || {}; + } + } + module.exports.default = pino2; + module.exports.pino = pino2; + function getCallerLocation() { + const stack = new Error().stack; + if (!stack) return null; + const lines = stack.split("\n"); + for (let i = 1; i < lines.length; i++) { + const l = lines[i].trim(); + if (/(^at\s+)?(createWrap|LOG|set\s*\(|asObject|Object\.apply|Function\.apply)/.test(l)) continue; + if (l.indexOf("browser.js") !== -1) continue; + if (l.indexOf("node:internal") !== -1) continue; + if (l.indexOf("node_modules") !== -1) continue; + let m = l.match(/\((.*?):(\d+):(\d+)\)/); + if (!m) m = l.match(/at\s+(.*?):(\d+):(\d+)/); + if (m) { + const file = m[1]; + const line = m[2]; + const col = m[3]; + return file + ":" + line + ":" + col; + } + } + return null; + } + } + }); + + // node-stub:crypto + var require_crypto = __commonJS({ + "node-stub:crypto"(exports, module) { + init_process(); + module.exports = {}; + } + }); + + // node_modules/bech32/dist/index.js + var require_dist = __commonJS({ + "node_modules/bech32/dist/index.js"(exports) { + "use strict"; + init_process(); + Object.defineProperty(exports, "__esModule", { value: true }); + exports.bech32m = exports.bech32 = void 0; + var ALPHABET = "qpzry9x8gf2tvdw0s3jn54khce6mua7l"; + var ALPHABET_MAP = {}; + for (let z = 0; z < ALPHABET.length; z++) { + const x = ALPHABET.charAt(z); + ALPHABET_MAP[x] = z; + } + function polymodStep(pre) { + const b = pre >> 25; + return (pre & 33554431) << 5 ^ -(b >> 0 & 1) & 996825010 ^ -(b >> 1 & 1) & 642813549 ^ -(b >> 2 & 1) & 513874426 ^ -(b >> 3 & 1) & 1027748829 ^ -(b >> 4 & 1) & 705979059; + } + function prefixChk(prefix) { + let chk = 1; + for (let i = 0; i < prefix.length; ++i) { + const c = prefix.charCodeAt(i); + if (c < 33 || c > 126) + return "Invalid prefix (" + prefix + ")"; + chk = polymodStep(chk) ^ c >> 5; + } + chk = polymodStep(chk); + for (let i = 0; i < prefix.length; ++i) { + const v = prefix.charCodeAt(i); + chk = polymodStep(chk) ^ v & 31; + } + return chk; + } + function convert(data, inBits, outBits, pad2) { + let value = 0; + let bits = 0; + const maxV = (1 << outBits) - 1; + const result = []; + for (let i = 0; i < data.length; ++i) { + value = value << inBits | data[i]; + bits += inBits; + while (bits >= outBits) { + bits -= outBits; + result.push(value >> bits & maxV); + } + } + if (pad2) { + if (bits > 0) { + result.push(value << outBits - bits & maxV); + } + } else { + if (bits >= inBits) + return "Excess padding"; + if (value << outBits - bits & maxV) + return "Non-zero padding"; + } + return result; + } + function toWords(bytes) { + return convert(bytes, 8, 5, true); + } + function fromWordsUnsafe(words) { + const res = convert(words, 5, 8, false); + if (Array.isArray(res)) + return res; + } + function fromWords(words) { + const res = convert(words, 5, 8, false); + if (Array.isArray(res)) + return res; + throw new Error(res); + } + function getLibraryFromEncoding(encoding) { + let ENCODING_CONST; + if (encoding === "bech32") { + ENCODING_CONST = 1; + } else { + ENCODING_CONST = 734539939; + } + function encode(prefix, words, LIMIT) { + LIMIT = LIMIT || 90; + if (prefix.length + 7 + words.length > LIMIT) + throw new TypeError("Exceeds length limit"); + prefix = prefix.toLowerCase(); + let chk = prefixChk(prefix); + if (typeof chk === "string") + throw new Error(chk); + let result = prefix + "1"; + for (let i = 0; i < words.length; ++i) { + const x = words[i]; + if (x >> 5 !== 0) + throw new Error("Non 5-bit word"); + chk = polymodStep(chk) ^ x; + result += ALPHABET.charAt(x); + } + for (let i = 0; i < 6; ++i) { + chk = polymodStep(chk); + } + chk ^= ENCODING_CONST; + for (let i = 0; i < 6; ++i) { + const v = chk >> (5 - i) * 5 & 31; + result += ALPHABET.charAt(v); + } + return result; + } + function __decode(str, LIMIT) { + LIMIT = LIMIT || 90; + if (str.length < 8) + return str + " too short"; + if (str.length > LIMIT) + return "Exceeds length limit"; + const lowered = str.toLowerCase(); + const uppered = str.toUpperCase(); + if (str !== lowered && str !== uppered) + return "Mixed-case string " + str; + str = lowered; + const split = str.lastIndexOf("1"); + if (split === -1) + return "No separator character for " + str; + if (split === 0) + return "Missing prefix for " + str; + const prefix = str.slice(0, split); + const wordChars = str.slice(split + 1); + if (wordChars.length < 6) + return "Data too short"; + let chk = prefixChk(prefix); + if (typeof chk === "string") + return chk; + const words = []; + for (let i = 0; i < wordChars.length; ++i) { + const c = wordChars.charAt(i); + const v = ALPHABET_MAP[c]; + if (v === void 0) + return "Unknown character " + c; + chk = polymodStep(chk) ^ v; + if (i + 6 >= wordChars.length) + continue; + words.push(v); + } + if (chk !== ENCODING_CONST) + return "Invalid checksum for " + str; + return { prefix, words }; + } + function decodeUnsafe(str, LIMIT) { + const res = __decode(str, LIMIT); + if (typeof res === "object") + return res; + } + function decode2(str, LIMIT) { + const res = __decode(str, LIMIT); + if (typeof res === "object") + return res; + throw new Error(res); + } + return { + decodeUnsafe, + decode: decode2, + encode, + toWords, + fromWordsUnsafe, + fromWords + }; + } + exports.bech32 = getLibraryFromEncoding("bech32"); + exports.bech32m = getLibraryFromEncoding("bech32m"); + } + }); + + // node_modules/base64-js/index.js + var require_base64_js = __commonJS({ + "node_modules/base64-js/index.js"(exports) { + "use strict"; + init_process(); + exports.byteLength = byteLength; + exports.toByteArray = toByteArray; + exports.fromByteArray = fromByteArray; + var lookup = []; + var revLookup = []; + var Arr = typeof Uint8Array !== "undefined" ? Uint8Array : Array; + var code = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"; + for (i = 0, len = code.length; i < len; ++i) { + lookup[i] = code[i]; + revLookup[code.charCodeAt(i)] = i; + } + var i; + var len; + revLookup["-".charCodeAt(0)] = 62; + revLookup["_".charCodeAt(0)] = 63; + function getLens(b64) { + var len2 = b64.length; + if (len2 % 4 > 0) { + throw new Error("Invalid string. Length must be a multiple of 4"); + } + var validLen = b64.indexOf("="); + if (validLen === -1) validLen = len2; + var placeHoldersLen = validLen === len2 ? 0 : 4 - validLen % 4; + return [validLen, placeHoldersLen]; + } + function byteLength(b64) { + var lens = getLens(b64); + var validLen = lens[0]; + var placeHoldersLen = lens[1]; + return (validLen + placeHoldersLen) * 3 / 4 - placeHoldersLen; + } + function _byteLength(b64, validLen, placeHoldersLen) { + return (validLen + placeHoldersLen) * 3 / 4 - placeHoldersLen; + } + function toByteArray(b64) { + var tmp; + var lens = getLens(b64); + var validLen = lens[0]; + var placeHoldersLen = lens[1]; + var arr = new Arr(_byteLength(b64, validLen, placeHoldersLen)); + var curByte = 0; + var len2 = placeHoldersLen > 0 ? validLen - 4 : validLen; + var i2; + for (i2 = 0; i2 < len2; i2 += 4) { + tmp = revLookup[b64.charCodeAt(i2)] << 18 | revLookup[b64.charCodeAt(i2 + 1)] << 12 | revLookup[b64.charCodeAt(i2 + 2)] << 6 | revLookup[b64.charCodeAt(i2 + 3)]; + arr[curByte++] = tmp >> 16 & 255; + arr[curByte++] = tmp >> 8 & 255; + arr[curByte++] = tmp & 255; + } + if (placeHoldersLen === 2) { + tmp = revLookup[b64.charCodeAt(i2)] << 2 | revLookup[b64.charCodeAt(i2 + 1)] >> 4; + arr[curByte++] = tmp & 255; + } + if (placeHoldersLen === 1) { + tmp = revLookup[b64.charCodeAt(i2)] << 10 | revLookup[b64.charCodeAt(i2 + 1)] << 4 | revLookup[b64.charCodeAt(i2 + 2)] >> 2; + arr[curByte++] = tmp >> 8 & 255; + arr[curByte++] = tmp & 255; + } + return arr; + } + function tripletToBase64(num2) { + return lookup[num2 >> 18 & 63] + lookup[num2 >> 12 & 63] + lookup[num2 >> 6 & 63] + lookup[num2 & 63]; + } + function encodeChunk(uint8, start, end) { + var tmp; + var output = []; + for (var i2 = start; i2 < end; i2 += 3) { + tmp = (uint8[i2] << 16 & 16711680) + (uint8[i2 + 1] << 8 & 65280) + (uint8[i2 + 2] & 255); + output.push(tripletToBase64(tmp)); + } + return output.join(""); + } + function fromByteArray(uint8) { + var tmp; + var len2 = uint8.length; + var extraBytes = len2 % 3; + var parts = []; + var maxChunkLength = 16383; + for (var i2 = 0, len22 = len2 - extraBytes; i2 < len22; i2 += maxChunkLength) { + parts.push(encodeChunk(uint8, i2, i2 + maxChunkLength > len22 ? len22 : i2 + maxChunkLength)); + } + if (extraBytes === 1) { + tmp = uint8[len2 - 1]; + parts.push( + lookup[tmp >> 2] + lookup[tmp << 4 & 63] + "==" + ); + } else if (extraBytes === 2) { + tmp = (uint8[len2 - 2] << 8) + uint8[len2 - 1]; + parts.push( + lookup[tmp >> 10] + lookup[tmp >> 4 & 63] + lookup[tmp << 2 & 63] + "=" + ); + } + return parts.join(""); + } + } + }); + + // node_modules/ieee754/index.js + var require_ieee754 = __commonJS({ + "node_modules/ieee754/index.js"(exports) { + init_process(); + exports.read = function(buffer, offset, isLE3, mLen, nBytes) { + var e, m; + var eLen = nBytes * 8 - mLen - 1; + var eMax = (1 << eLen) - 1; + var eBias = eMax >> 1; + var nBits = -7; + var i = isLE3 ? nBytes - 1 : 0; + var d = isLE3 ? -1 : 1; + var s = buffer[offset + i]; + i += d; + e = s & (1 << -nBits) - 1; + s >>= -nBits; + nBits += eLen; + for (; nBits > 0; e = e * 256 + buffer[offset + i], i += d, nBits -= 8) { + } + m = e & (1 << -nBits) - 1; + e >>= -nBits; + nBits += mLen; + for (; nBits > 0; m = m * 256 + buffer[offset + i], i += d, nBits -= 8) { + } + if (e === 0) { + e = 1 - eBias; + } else if (e === eMax) { + return m ? NaN : (s ? -1 : 1) * Infinity; + } else { + m = m + Math.pow(2, mLen); + e = e - eBias; + } + return (s ? -1 : 1) * m * Math.pow(2, e - mLen); + }; + exports.write = function(buffer, value, offset, isLE3, mLen, nBytes) { + var e, m, c; + var eLen = nBytes * 8 - mLen - 1; + var eMax = (1 << eLen) - 1; + var eBias = eMax >> 1; + var rt = mLen === 23 ? Math.pow(2, -24) - Math.pow(2, -77) : 0; + var i = isLE3 ? 0 : nBytes - 1; + var d = isLE3 ? 1 : -1; + var s = value < 0 || value === 0 && 1 / value < 0 ? 1 : 0; + value = Math.abs(value); + if (isNaN(value) || value === Infinity) { + m = isNaN(value) ? 1 : 0; + e = eMax; + } else { + e = Math.floor(Math.log(value) / Math.LN2); + if (value * (c = Math.pow(2, -e)) < 1) { + e--; + c *= 2; + } + if (e + eBias >= 1) { + value += rt / c; + } else { + value += rt * Math.pow(2, 1 - eBias); + } + if (value * c >= 2) { + e++; + c /= 2; + } + if (e + eBias >= eMax) { + m = 0; + e = eMax; + } else if (e + eBias >= 1) { + m = (value * c - 1) * Math.pow(2, mLen); + e = e + eBias; + } else { + m = value * Math.pow(2, eBias - 1) * Math.pow(2, mLen); + e = 0; + } + } + for (; mLen >= 8; buffer[offset + i] = m & 255, i += d, m /= 256, mLen -= 8) { + } + e = e << mLen | m; + eLen += mLen; + for (; eLen > 0; buffer[offset + i] = e & 255, i += d, e /= 256, eLen -= 8) { + } + buffer[offset + i - d] |= s * 128; + }; + } + }); + + // node_modules/buffer/index.js + var require_buffer = __commonJS({ + "node_modules/buffer/index.js"(exports) { + "use strict"; + init_process(); + var base642 = require_base64_js(); + var ieee754 = require_ieee754(); + var customInspectSymbol = typeof Symbol === "function" && typeof Symbol["for"] === "function" ? Symbol["for"]("nodejs.util.inspect.custom") : null; + exports.Buffer = Buffer3; + exports.SlowBuffer = SlowBuffer; + exports.INSPECT_MAX_BYTES = 50; + var K_MAX_LENGTH = 2147483647; + exports.kMaxLength = K_MAX_LENGTH; + Buffer3.TYPED_ARRAY_SUPPORT = typedArraySupport(); + if (!Buffer3.TYPED_ARRAY_SUPPORT && typeof console !== "undefined" && typeof console.error === "function") { + console.error( + "This browser lacks typed array (Uint8Array) support which is required by `buffer` v5.x. Use `buffer` v4.x if you require old browser support." + ); + } + function typedArraySupport() { + try { + const arr = new Uint8Array(1); + const proto = { foo: function() { + return 42; + } }; + Object.setPrototypeOf(proto, Uint8Array.prototype); + Object.setPrototypeOf(arr, proto); + return arr.foo() === 42; + } catch (e) { + return false; + } + } + Object.defineProperty(Buffer3.prototype, "parent", { + enumerable: true, + get: function() { + if (!Buffer3.isBuffer(this)) return void 0; + return this.buffer; + } + }); + Object.defineProperty(Buffer3.prototype, "offset", { + enumerable: true, + get: function() { + if (!Buffer3.isBuffer(this)) return void 0; + return this.byteOffset; + } + }); + function createBuffer(length) { + if (length > K_MAX_LENGTH) { + throw new RangeError('The value "' + length + '" is invalid for option "size"'); + } + const buf = new Uint8Array(length); + Object.setPrototypeOf(buf, Buffer3.prototype); + return buf; + } + function Buffer3(arg, encodingOrOffset, length) { + if (typeof arg === "number") { + if (typeof encodingOrOffset === "string") { + throw new TypeError( + 'The "string" argument must be of type string. Received type number' + ); + } + return allocUnsafe(arg); + } + return from(arg, encodingOrOffset, length); + } + Buffer3.poolSize = 8192; + function from(value, encodingOrOffset, length) { + if (typeof value === "string") { + return fromString(value, encodingOrOffset); + } + if (ArrayBuffer.isView(value)) { + return fromArrayView(value); + } + if (value == null) { + throw new TypeError( + "The first argument must be one of type string, Buffer, ArrayBuffer, Array, or Array-like Object. Received type " + typeof value + ); + } + if (isInstance(value, ArrayBuffer) || value && isInstance(value.buffer, ArrayBuffer)) { + return fromArrayBuffer(value, encodingOrOffset, length); + } + if (typeof SharedArrayBuffer !== "undefined" && (isInstance(value, SharedArrayBuffer) || value && isInstance(value.buffer, SharedArrayBuffer))) { + return fromArrayBuffer(value, encodingOrOffset, length); + } + if (typeof value === "number") { + throw new TypeError( + 'The "value" argument must not be of type number. Received type number' + ); + } + const valueOf = value.valueOf && value.valueOf(); + if (valueOf != null && valueOf !== value) { + return Buffer3.from(valueOf, encodingOrOffset, length); + } + const b = fromObject(value); + if (b) return b; + if (typeof Symbol !== "undefined" && Symbol.toPrimitive != null && typeof value[Symbol.toPrimitive] === "function") { + return Buffer3.from(value[Symbol.toPrimitive]("string"), encodingOrOffset, length); + } + throw new TypeError( + "The first argument must be one of type string, Buffer, ArrayBuffer, Array, or Array-like Object. Received type " + typeof value + ); + } + Buffer3.from = function(value, encodingOrOffset, length) { + return from(value, encodingOrOffset, length); + }; + Object.setPrototypeOf(Buffer3.prototype, Uint8Array.prototype); + Object.setPrototypeOf(Buffer3, Uint8Array); + function assertSize(size) { + if (typeof size !== "number") { + throw new TypeError('"size" argument must be of type number'); + } else if (size < 0) { + throw new RangeError('The value "' + size + '" is invalid for option "size"'); + } + } + function alloc(size, fill, encoding) { + assertSize(size); + if (size <= 0) { + return createBuffer(size); + } + if (fill !== void 0) { + return typeof encoding === "string" ? createBuffer(size).fill(fill, encoding) : createBuffer(size).fill(fill); + } + return createBuffer(size); + } + Buffer3.alloc = function(size, fill, encoding) { + return alloc(size, fill, encoding); + }; + function allocUnsafe(size) { + assertSize(size); + return createBuffer(size < 0 ? 0 : checked(size) | 0); + } + Buffer3.allocUnsafe = function(size) { + return allocUnsafe(size); + }; + Buffer3.allocUnsafeSlow = function(size) { + return allocUnsafe(size); + }; + function fromString(string, encoding) { + if (typeof encoding !== "string" || encoding === "") { + encoding = "utf8"; + } + if (!Buffer3.isEncoding(encoding)) { + throw new TypeError("Unknown encoding: " + encoding); + } + const length = byteLength(string, encoding) | 0; + let buf = createBuffer(length); + const actual = buf.write(string, encoding); + if (actual !== length) { + buf = buf.slice(0, actual); + } + return buf; + } + function fromArrayLike(array) { + const length = array.length < 0 ? 0 : checked(array.length) | 0; + const buf = createBuffer(length); + for (let i = 0; i < length; i += 1) { + buf[i] = array[i] & 255; + } + return buf; + } + function fromArrayView(arrayView) { + if (isInstance(arrayView, Uint8Array)) { + const copy = new Uint8Array(arrayView); + return fromArrayBuffer(copy.buffer, copy.byteOffset, copy.byteLength); + } + return fromArrayLike(arrayView); + } + function fromArrayBuffer(array, byteOffset, length) { + if (byteOffset < 0 || array.byteLength < byteOffset) { + throw new RangeError('"offset" is outside of buffer bounds'); + } + if (array.byteLength < byteOffset + (length || 0)) { + throw new RangeError('"length" is outside of buffer bounds'); + } + let buf; + if (byteOffset === void 0 && length === void 0) { + buf = new Uint8Array(array); + } else if (length === void 0) { + buf = new Uint8Array(array, byteOffset); + } else { + buf = new Uint8Array(array, byteOffset, length); + } + Object.setPrototypeOf(buf, Buffer3.prototype); + return buf; + } + function fromObject(obj) { + if (Buffer3.isBuffer(obj)) { + const len = checked(obj.length) | 0; + const buf = createBuffer(len); + if (buf.length === 0) { + return buf; + } + obj.copy(buf, 0, 0, len); + return buf; + } + if (obj.length !== void 0) { + if (typeof obj.length !== "number" || numberIsNaN(obj.length)) { + return createBuffer(0); + } + return fromArrayLike(obj); + } + if (obj.type === "Buffer" && Array.isArray(obj.data)) { + return fromArrayLike(obj.data); + } + } + function checked(length) { + if (length >= K_MAX_LENGTH) { + throw new RangeError("Attempt to allocate Buffer larger than maximum size: 0x" + K_MAX_LENGTH.toString(16) + " bytes"); + } + return length | 0; + } + function SlowBuffer(length) { + if (+length != length) { + length = 0; + } + return Buffer3.alloc(+length); + } + Buffer3.isBuffer = function isBuffer(b) { + return b != null && b._isBuffer === true && b !== Buffer3.prototype; + }; + Buffer3.compare = function compare(a, b) { + if (isInstance(a, Uint8Array)) a = Buffer3.from(a, a.offset, a.byteLength); + if (isInstance(b, Uint8Array)) b = Buffer3.from(b, b.offset, b.byteLength); + if (!Buffer3.isBuffer(a) || !Buffer3.isBuffer(b)) { + throw new TypeError( + 'The "buf1", "buf2" arguments must be one of type Buffer or Uint8Array' + ); + } + if (a === b) return 0; + let x = a.length; + let y = b.length; + for (let i = 0, len = Math.min(x, y); i < len; ++i) { + if (a[i] !== b[i]) { + x = a[i]; + y = b[i]; + break; + } + } + if (x < y) return -1; + if (y < x) return 1; + return 0; + }; + Buffer3.isEncoding = function isEncoding(encoding) { + switch (String(encoding).toLowerCase()) { + case "hex": + case "utf8": + case "utf-8": + case "ascii": + case "latin1": + case "binary": + case "base64": + case "ucs2": + case "ucs-2": + case "utf16le": + case "utf-16le": + return true; + default: + return false; + } + }; + Buffer3.concat = function concat(list, length) { + if (!Array.isArray(list)) { + throw new TypeError('"list" argument must be an Array of Buffers'); + } + if (list.length === 0) { + return Buffer3.alloc(0); + } + let i; + if (length === void 0) { + length = 0; + for (i = 0; i < list.length; ++i) { + length += list[i].length; + } + } + const buffer = Buffer3.allocUnsafe(length); + let pos = 0; + for (i = 0; i < list.length; ++i) { + let buf = list[i]; + if (isInstance(buf, Uint8Array)) { + if (pos + buf.length > buffer.length) { + if (!Buffer3.isBuffer(buf)) buf = Buffer3.from(buf); + buf.copy(buffer, pos); + } else { + Uint8Array.prototype.set.call( + buffer, + buf, + pos + ); + } + } else if (!Buffer3.isBuffer(buf)) { + throw new TypeError('"list" argument must be an Array of Buffers'); + } else { + buf.copy(buffer, pos); + } + pos += buf.length; + } + return buffer; + }; + function byteLength(string, encoding) { + if (Buffer3.isBuffer(string)) { + return string.length; + } + if (ArrayBuffer.isView(string) || isInstance(string, ArrayBuffer)) { + return string.byteLength; + } + if (typeof string !== "string") { + throw new TypeError( + 'The "string" argument must be one of type string, Buffer, or ArrayBuffer. Received type ' + typeof string + ); + } + const len = string.length; + const mustMatch = arguments.length > 2 && arguments[2] === true; + if (!mustMatch && len === 0) return 0; + let loweredCase = false; + for (; ; ) { + switch (encoding) { + case "ascii": + case "latin1": + case "binary": + return len; + case "utf8": + case "utf-8": + return utf8ToBytes3(string).length; + case "ucs2": + case "ucs-2": + case "utf16le": + case "utf-16le": + return len * 2; + case "hex": + return len >>> 1; + case "base64": + return base64ToBytes2(string).length; + default: + if (loweredCase) { + return mustMatch ? -1 : utf8ToBytes3(string).length; + } + encoding = ("" + encoding).toLowerCase(); + loweredCase = true; + } + } + } + Buffer3.byteLength = byteLength; + function slowToString(encoding, start, end) { + let loweredCase = false; + if (start === void 0 || start < 0) { + start = 0; + } + if (start > this.length) { + return ""; + } + if (end === void 0 || end > this.length) { + end = this.length; + } + if (end <= 0) { + return ""; + } + end >>>= 0; + start >>>= 0; + if (end <= start) { + return ""; + } + if (!encoding) encoding = "utf8"; + while (true) { + switch (encoding) { + case "hex": + return hexSlice(this, start, end); + case "utf8": + case "utf-8": + return utf8Slice(this, start, end); + case "ascii": + return asciiSlice(this, start, end); + case "latin1": + case "binary": + return latin1Slice(this, start, end); + case "base64": + return base64Slice(this, start, end); + case "ucs2": + case "ucs-2": + case "utf16le": + case "utf-16le": + return utf16leSlice(this, start, end); + default: + if (loweredCase) throw new TypeError("Unknown encoding: " + encoding); + encoding = (encoding + "").toLowerCase(); + loweredCase = true; + } + } + } + Buffer3.prototype._isBuffer = true; + function swap(b, n, m) { + const i = b[n]; + b[n] = b[m]; + b[m] = i; + } + Buffer3.prototype.swap16 = function swap16() { + const len = this.length; + if (len % 2 !== 0) { + throw new RangeError("Buffer size must be a multiple of 16-bits"); + } + for (let i = 0; i < len; i += 2) { + swap(this, i, i + 1); + } + return this; + }; + Buffer3.prototype.swap32 = function swap32() { + const len = this.length; + if (len % 4 !== 0) { + throw new RangeError("Buffer size must be a multiple of 32-bits"); + } + for (let i = 0; i < len; i += 4) { + swap(this, i, i + 3); + swap(this, i + 1, i + 2); + } + return this; + }; + Buffer3.prototype.swap64 = function swap64() { + const len = this.length; + if (len % 8 !== 0) { + throw new RangeError("Buffer size must be a multiple of 64-bits"); + } + for (let i = 0; i < len; i += 8) { + swap(this, i, i + 7); + swap(this, i + 1, i + 6); + swap(this, i + 2, i + 5); + swap(this, i + 3, i + 4); + } + return this; + }; + Buffer3.prototype.toString = function toString() { + const length = this.length; + if (length === 0) return ""; + if (arguments.length === 0) return utf8Slice(this, 0, length); + return slowToString.apply(this, arguments); + }; + Buffer3.prototype.toLocaleString = Buffer3.prototype.toString; + Buffer3.prototype.equals = function equals(b) { + if (!Buffer3.isBuffer(b)) throw new TypeError("Argument must be a Buffer"); + if (this === b) return true; + return Buffer3.compare(this, b) === 0; + }; + Buffer3.prototype.inspect = function inspect() { + let str = ""; + const max = exports.INSPECT_MAX_BYTES; + str = this.toString("hex", 0, max).replace(/(.{2})/g, "$1 ").trim(); + if (this.length > max) str += " ... "; + return ""; + }; + if (customInspectSymbol) { + Buffer3.prototype[customInspectSymbol] = Buffer3.prototype.inspect; + } + Buffer3.prototype.compare = function compare(target, start, end, thisStart, thisEnd) { + if (isInstance(target, Uint8Array)) { + target = Buffer3.from(target, target.offset, target.byteLength); + } + if (!Buffer3.isBuffer(target)) { + throw new TypeError( + 'The "target" argument must be one of type Buffer or Uint8Array. Received type ' + typeof target + ); + } + if (start === void 0) { + start = 0; + } + if (end === void 0) { + end = target ? target.length : 0; + } + if (thisStart === void 0) { + thisStart = 0; + } + if (thisEnd === void 0) { + thisEnd = this.length; + } + if (start < 0 || end > target.length || thisStart < 0 || thisEnd > this.length) { + throw new RangeError("out of range index"); + } + if (thisStart >= thisEnd && start >= end) { + return 0; + } + if (thisStart >= thisEnd) { + return -1; + } + if (start >= end) { + return 1; + } + start >>>= 0; + end >>>= 0; + thisStart >>>= 0; + thisEnd >>>= 0; + if (this === target) return 0; + let x = thisEnd - thisStart; + let y = end - start; + const len = Math.min(x, y); + const thisCopy = this.slice(thisStart, thisEnd); + const targetCopy = target.slice(start, end); + for (let i = 0; i < len; ++i) { + if (thisCopy[i] !== targetCopy[i]) { + x = thisCopy[i]; + y = targetCopy[i]; + break; + } + } + if (x < y) return -1; + if (y < x) return 1; + return 0; + }; + function bidirectionalIndexOf(buffer, val, byteOffset, encoding, dir) { + if (buffer.length === 0) return -1; + if (typeof byteOffset === "string") { + encoding = byteOffset; + byteOffset = 0; + } else if (byteOffset > 2147483647) { + byteOffset = 2147483647; + } else if (byteOffset < -2147483648) { + byteOffset = -2147483648; + } + byteOffset = +byteOffset; + if (numberIsNaN(byteOffset)) { + byteOffset = dir ? 0 : buffer.length - 1; + } + if (byteOffset < 0) byteOffset = buffer.length + byteOffset; + if (byteOffset >= buffer.length) { + if (dir) return -1; + else byteOffset = buffer.length - 1; + } else if (byteOffset < 0) { + if (dir) byteOffset = 0; + else return -1; + } + if (typeof val === "string") { + val = Buffer3.from(val, encoding); + } + if (Buffer3.isBuffer(val)) { + if (val.length === 0) { + return -1; + } + return arrayIndexOf(buffer, val, byteOffset, encoding, dir); + } else if (typeof val === "number") { + val = val & 255; + if (typeof Uint8Array.prototype.indexOf === "function") { + if (dir) { + return Uint8Array.prototype.indexOf.call(buffer, val, byteOffset); + } else { + return Uint8Array.prototype.lastIndexOf.call(buffer, val, byteOffset); + } + } + return arrayIndexOf(buffer, [val], byteOffset, encoding, dir); + } + throw new TypeError("val must be string, number or Buffer"); + } + function arrayIndexOf(arr, val, byteOffset, encoding, dir) { + let indexSize = 1; + let arrLength = arr.length; + let valLength = val.length; + if (encoding !== void 0) { + encoding = String(encoding).toLowerCase(); + if (encoding === "ucs2" || encoding === "ucs-2" || encoding === "utf16le" || encoding === "utf-16le") { + if (arr.length < 2 || val.length < 2) { + return -1; + } + indexSize = 2; + arrLength /= 2; + valLength /= 2; + byteOffset /= 2; + } + } + function read(buf, i2) { + if (indexSize === 1) { + return buf[i2]; + } else { + return buf.readUInt16BE(i2 * indexSize); + } + } + let i; + if (dir) { + let foundIndex = -1; + for (i = byteOffset; i < arrLength; i++) { + if (read(arr, i) === read(val, foundIndex === -1 ? 0 : i - foundIndex)) { + if (foundIndex === -1) foundIndex = i; + if (i - foundIndex + 1 === valLength) return foundIndex * indexSize; + } else { + if (foundIndex !== -1) i -= i - foundIndex; + foundIndex = -1; + } + } + } else { + if (byteOffset + valLength > arrLength) byteOffset = arrLength - valLength; + for (i = byteOffset; i >= 0; i--) { + let found = true; + for (let j = 0; j < valLength; j++) { + if (read(arr, i + j) !== read(val, j)) { + found = false; + break; + } + } + if (found) return i; + } + } + return -1; + } + Buffer3.prototype.includes = function includes(val, byteOffset, encoding) { + return this.indexOf(val, byteOffset, encoding) !== -1; + }; + Buffer3.prototype.indexOf = function indexOf(val, byteOffset, encoding) { + return bidirectionalIndexOf(this, val, byteOffset, encoding, true); + }; + Buffer3.prototype.lastIndexOf = function lastIndexOf(val, byteOffset, encoding) { + return bidirectionalIndexOf(this, val, byteOffset, encoding, false); + }; + function hexWrite(buf, string, offset, length) { + offset = Number(offset) || 0; + const remaining = buf.length - offset; + if (!length) { + length = remaining; + } else { + length = Number(length); + if (length > remaining) { + length = remaining; + } + } + const strLen = string.length; + if (length > strLen / 2) { + length = strLen / 2; + } + let i; + for (i = 0; i < length; ++i) { + const parsed = parseInt(string.substr(i * 2, 2), 16); + if (numberIsNaN(parsed)) return i; + buf[offset + i] = parsed; + } + return i; + } + function utf8Write(buf, string, offset, length) { + return blitBuffer(utf8ToBytes3(string, buf.length - offset), buf, offset, length); + } + function asciiWrite(buf, string, offset, length) { + return blitBuffer(asciiToBytes2(string), buf, offset, length); + } + function base64Write(buf, string, offset, length) { + return blitBuffer(base64ToBytes2(string), buf, offset, length); + } + function ucs2Write(buf, string, offset, length) { + return blitBuffer(utf16leToBytes(string, buf.length - offset), buf, offset, length); + } + Buffer3.prototype.write = function write(string, offset, length, encoding) { + if (offset === void 0) { + encoding = "utf8"; + length = this.length; + offset = 0; + } else if (length === void 0 && typeof offset === "string") { + encoding = offset; + length = this.length; + offset = 0; + } else if (isFinite(offset)) { + offset = offset >>> 0; + if (isFinite(length)) { + length = length >>> 0; + if (encoding === void 0) encoding = "utf8"; + } else { + encoding = length; + length = void 0; + } + } else { + throw new Error( + "Buffer.write(string, encoding, offset[, length]) is no longer supported" + ); + } + const remaining = this.length - offset; + if (length === void 0 || length > remaining) length = remaining; + if (string.length > 0 && (length < 0 || offset < 0) || offset > this.length) { + throw new RangeError("Attempt to write outside buffer bounds"); + } + if (!encoding) encoding = "utf8"; + let loweredCase = false; + for (; ; ) { + switch (encoding) { + case "hex": + return hexWrite(this, string, offset, length); + case "utf8": + case "utf-8": + return utf8Write(this, string, offset, length); + case "ascii": + case "latin1": + case "binary": + return asciiWrite(this, string, offset, length); + case "base64": + return base64Write(this, string, offset, length); + case "ucs2": + case "ucs-2": + case "utf16le": + case "utf-16le": + return ucs2Write(this, string, offset, length); + default: + if (loweredCase) throw new TypeError("Unknown encoding: " + encoding); + encoding = ("" + encoding).toLowerCase(); + loweredCase = true; + } + } + }; + Buffer3.prototype.toJSON = function toJSON() { + return { + type: "Buffer", + data: Array.prototype.slice.call(this._arr || this, 0) + }; + }; + function base64Slice(buf, start, end) { + if (start === 0 && end === buf.length) { + return base642.fromByteArray(buf); + } else { + return base642.fromByteArray(buf.slice(start, end)); + } + } + function utf8Slice(buf, start, end) { + end = Math.min(buf.length, end); + const res = []; + let i = start; + while (i < end) { + const firstByte = buf[i]; + let codePoint = null; + let bytesPerSequence = firstByte > 239 ? 4 : firstByte > 223 ? 3 : firstByte > 191 ? 2 : 1; + if (i + bytesPerSequence <= end) { + let secondByte, thirdByte, fourthByte, tempCodePoint; + switch (bytesPerSequence) { + case 1: + if (firstByte < 128) { + codePoint = firstByte; + } + break; + case 2: + secondByte = buf[i + 1]; + if ((secondByte & 192) === 128) { + tempCodePoint = (firstByte & 31) << 6 | secondByte & 63; + if (tempCodePoint > 127) { + codePoint = tempCodePoint; + } + } + break; + case 3: + secondByte = buf[i + 1]; + thirdByte = buf[i + 2]; + if ((secondByte & 192) === 128 && (thirdByte & 192) === 128) { + tempCodePoint = (firstByte & 15) << 12 | (secondByte & 63) << 6 | thirdByte & 63; + if (tempCodePoint > 2047 && (tempCodePoint < 55296 || tempCodePoint > 57343)) { + codePoint = tempCodePoint; + } + } + break; + case 4: + secondByte = buf[i + 1]; + thirdByte = buf[i + 2]; + fourthByte = buf[i + 3]; + if ((secondByte & 192) === 128 && (thirdByte & 192) === 128 && (fourthByte & 192) === 128) { + tempCodePoint = (firstByte & 15) << 18 | (secondByte & 63) << 12 | (thirdByte & 63) << 6 | fourthByte & 63; + if (tempCodePoint > 65535 && tempCodePoint < 1114112) { + codePoint = tempCodePoint; + } + } + } + } + if (codePoint === null) { + codePoint = 65533; + bytesPerSequence = 1; + } else if (codePoint > 65535) { + codePoint -= 65536; + res.push(codePoint >>> 10 & 1023 | 55296); + codePoint = 56320 | codePoint & 1023; + } + res.push(codePoint); + i += bytesPerSequence; + } + return decodeCodePointsArray(res); + } + var MAX_ARGUMENTS_LENGTH = 4096; + function decodeCodePointsArray(codePoints) { + const len = codePoints.length; + if (len <= MAX_ARGUMENTS_LENGTH) { + return String.fromCharCode.apply(String, codePoints); + } + let res = ""; + let i = 0; + while (i < len) { + res += String.fromCharCode.apply( + String, + codePoints.slice(i, i += MAX_ARGUMENTS_LENGTH) + ); + } + return res; + } + function asciiSlice(buf, start, end) { + let ret = ""; + end = Math.min(buf.length, end); + for (let i = start; i < end; ++i) { + ret += String.fromCharCode(buf[i] & 127); + } + return ret; + } + function latin1Slice(buf, start, end) { + let ret = ""; + end = Math.min(buf.length, end); + for (let i = start; i < end; ++i) { + ret += String.fromCharCode(buf[i]); + } + return ret; + } + function hexSlice(buf, start, end) { + const len = buf.length; + if (!start || start < 0) start = 0; + if (!end || end < 0 || end > len) end = len; + let out = ""; + for (let i = start; i < end; ++i) { + out += hexSliceLookupTable[buf[i]]; + } + return out; + } + function utf16leSlice(buf, start, end) { + const bytes = buf.slice(start, end); + let res = ""; + for (let i = 0; i < bytes.length - 1; i += 2) { + res += String.fromCharCode(bytes[i] + bytes[i + 1] * 256); + } + return res; + } + Buffer3.prototype.slice = function slice(start, end) { + const len = this.length; + start = ~~start; + end = end === void 0 ? len : ~~end; + if (start < 0) { + start += len; + if (start < 0) start = 0; + } else if (start > len) { + start = len; + } + if (end < 0) { + end += len; + if (end < 0) end = 0; + } else if (end > len) { + end = len; + } + if (end < start) end = start; + const newBuf = this.subarray(start, end); + Object.setPrototypeOf(newBuf, Buffer3.prototype); + return newBuf; + }; + function checkOffset(offset, ext, length) { + if (offset % 1 !== 0 || offset < 0) throw new RangeError("offset is not uint"); + if (offset + ext > length) throw new RangeError("Trying to access beyond buffer length"); + } + Buffer3.prototype.readUintLE = Buffer3.prototype.readUIntLE = function readUIntLE(offset, byteLength2, noAssert) { + offset = offset >>> 0; + byteLength2 = byteLength2 >>> 0; + if (!noAssert) checkOffset(offset, byteLength2, this.length); + let val = this[offset]; + let mul = 1; + let i = 0; + while (++i < byteLength2 && (mul *= 256)) { + val += this[offset + i] * mul; + } + return val; + }; + Buffer3.prototype.readUintBE = Buffer3.prototype.readUIntBE = function readUIntBE(offset, byteLength2, noAssert) { + offset = offset >>> 0; + byteLength2 = byteLength2 >>> 0; + if (!noAssert) { + checkOffset(offset, byteLength2, this.length); + } + let val = this[offset + --byteLength2]; + let mul = 1; + while (byteLength2 > 0 && (mul *= 256)) { + val += this[offset + --byteLength2] * mul; + } + return val; + }; + Buffer3.prototype.readUint8 = Buffer3.prototype.readUInt8 = function readUInt8(offset, noAssert) { + offset = offset >>> 0; + if (!noAssert) checkOffset(offset, 1, this.length); + return this[offset]; + }; + Buffer3.prototype.readUint16LE = Buffer3.prototype.readUInt16LE = function readUInt16LE(offset, noAssert) { + offset = offset >>> 0; + if (!noAssert) checkOffset(offset, 2, this.length); + return this[offset] | this[offset + 1] << 8; + }; + Buffer3.prototype.readUint16BE = Buffer3.prototype.readUInt16BE = function readUInt16BE(offset, noAssert) { + offset = offset >>> 0; + if (!noAssert) checkOffset(offset, 2, this.length); + return this[offset] << 8 | this[offset + 1]; + }; + Buffer3.prototype.readUint32LE = Buffer3.prototype.readUInt32LE = function readUInt32LE(offset, noAssert) { + offset = offset >>> 0; + if (!noAssert) checkOffset(offset, 4, this.length); + return (this[offset] | this[offset + 1] << 8 | this[offset + 2] << 16) + this[offset + 3] * 16777216; + }; + Buffer3.prototype.readUint32BE = Buffer3.prototype.readUInt32BE = function readUInt32BE(offset, noAssert) { + offset = offset >>> 0; + if (!noAssert) checkOffset(offset, 4, this.length); + return this[offset] * 16777216 + (this[offset + 1] << 16 | this[offset + 2] << 8 | this[offset + 3]); + }; + Buffer3.prototype.readBigUInt64LE = defineBigIntMethod(function readBigUInt64LE(offset) { + offset = offset >>> 0; + validateNumber(offset, "offset"); + const first = this[offset]; + const last = this[offset + 7]; + if (first === void 0 || last === void 0) { + boundsError(offset, this.length - 8); + } + const lo = first + this[++offset] * 2 ** 8 + this[++offset] * 2 ** 16 + this[++offset] * 2 ** 24; + const hi = this[++offset] + this[++offset] * 2 ** 8 + this[++offset] * 2 ** 16 + last * 2 ** 24; + return BigInt(lo) + (BigInt(hi) << BigInt(32)); + }); + Buffer3.prototype.readBigUInt64BE = defineBigIntMethod(function readBigUInt64BE(offset) { + offset = offset >>> 0; + validateNumber(offset, "offset"); + const first = this[offset]; + const last = this[offset + 7]; + if (first === void 0 || last === void 0) { + boundsError(offset, this.length - 8); + } + const hi = first * 2 ** 24 + this[++offset] * 2 ** 16 + this[++offset] * 2 ** 8 + this[++offset]; + const lo = this[++offset] * 2 ** 24 + this[++offset] * 2 ** 16 + this[++offset] * 2 ** 8 + last; + return (BigInt(hi) << BigInt(32)) + BigInt(lo); + }); + Buffer3.prototype.readIntLE = function readIntLE(offset, byteLength2, noAssert) { + offset = offset >>> 0; + byteLength2 = byteLength2 >>> 0; + if (!noAssert) checkOffset(offset, byteLength2, this.length); + let val = this[offset]; + let mul = 1; + let i = 0; + while (++i < byteLength2 && (mul *= 256)) { + val += this[offset + i] * mul; + } + mul *= 128; + if (val >= mul) val -= Math.pow(2, 8 * byteLength2); + return val; + }; + Buffer3.prototype.readIntBE = function readIntBE(offset, byteLength2, noAssert) { + offset = offset >>> 0; + byteLength2 = byteLength2 >>> 0; + if (!noAssert) checkOffset(offset, byteLength2, this.length); + let i = byteLength2; + let mul = 1; + let val = this[offset + --i]; + while (i > 0 && (mul *= 256)) { + val += this[offset + --i] * mul; + } + mul *= 128; + if (val >= mul) val -= Math.pow(2, 8 * byteLength2); + return val; + }; + Buffer3.prototype.readInt8 = function readInt8(offset, noAssert) { + offset = offset >>> 0; + if (!noAssert) checkOffset(offset, 1, this.length); + if (!(this[offset] & 128)) return this[offset]; + return (255 - this[offset] + 1) * -1; + }; + Buffer3.prototype.readInt16LE = function readInt16LE(offset, noAssert) { + offset = offset >>> 0; + if (!noAssert) checkOffset(offset, 2, this.length); + const val = this[offset] | this[offset + 1] << 8; + return val & 32768 ? val | 4294901760 : val; + }; + Buffer3.prototype.readInt16BE = function readInt16BE(offset, noAssert) { + offset = offset >>> 0; + if (!noAssert) checkOffset(offset, 2, this.length); + const val = this[offset + 1] | this[offset] << 8; + return val & 32768 ? val | 4294901760 : val; + }; + Buffer3.prototype.readInt32LE = function readInt32LE(offset, noAssert) { + offset = offset >>> 0; + if (!noAssert) checkOffset(offset, 4, this.length); + return this[offset] | this[offset + 1] << 8 | this[offset + 2] << 16 | this[offset + 3] << 24; + }; + Buffer3.prototype.readInt32BE = function readInt32BE(offset, noAssert) { + offset = offset >>> 0; + if (!noAssert) checkOffset(offset, 4, this.length); + return this[offset] << 24 | this[offset + 1] << 16 | this[offset + 2] << 8 | this[offset + 3]; + }; + Buffer3.prototype.readBigInt64LE = defineBigIntMethod(function readBigInt64LE(offset) { + offset = offset >>> 0; + validateNumber(offset, "offset"); + const first = this[offset]; + const last = this[offset + 7]; + if (first === void 0 || last === void 0) { + boundsError(offset, this.length - 8); + } + const val = this[offset + 4] + this[offset + 5] * 2 ** 8 + this[offset + 6] * 2 ** 16 + (last << 24); + return (BigInt(val) << BigInt(32)) + BigInt(first + this[++offset] * 2 ** 8 + this[++offset] * 2 ** 16 + this[++offset] * 2 ** 24); + }); + Buffer3.prototype.readBigInt64BE = defineBigIntMethod(function readBigInt64BE(offset) { + offset = offset >>> 0; + validateNumber(offset, "offset"); + const first = this[offset]; + const last = this[offset + 7]; + if (first === void 0 || last === void 0) { + boundsError(offset, this.length - 8); + } + const val = (first << 24) + // Overflow + this[++offset] * 2 ** 16 + this[++offset] * 2 ** 8 + this[++offset]; + return (BigInt(val) << BigInt(32)) + BigInt(this[++offset] * 2 ** 24 + this[++offset] * 2 ** 16 + this[++offset] * 2 ** 8 + last); + }); + Buffer3.prototype.readFloatLE = function readFloatLE(offset, noAssert) { + offset = offset >>> 0; + if (!noAssert) checkOffset(offset, 4, this.length); + return ieee754.read(this, offset, true, 23, 4); + }; + Buffer3.prototype.readFloatBE = function readFloatBE(offset, noAssert) { + offset = offset >>> 0; + if (!noAssert) checkOffset(offset, 4, this.length); + return ieee754.read(this, offset, false, 23, 4); + }; + Buffer3.prototype.readDoubleLE = function readDoubleLE(offset, noAssert) { + offset = offset >>> 0; + if (!noAssert) checkOffset(offset, 8, this.length); + return ieee754.read(this, offset, true, 52, 8); + }; + Buffer3.prototype.readDoubleBE = function readDoubleBE(offset, noAssert) { + offset = offset >>> 0; + if (!noAssert) checkOffset(offset, 8, this.length); + return ieee754.read(this, offset, false, 52, 8); + }; + function checkInt(buf, value, offset, ext, max, min) { + if (!Buffer3.isBuffer(buf)) throw new TypeError('"buffer" argument must be a Buffer instance'); + if (value > max || value < min) throw new RangeError('"value" argument is out of bounds'); + if (offset + ext > buf.length) throw new RangeError("Index out of range"); + } + Buffer3.prototype.writeUintLE = Buffer3.prototype.writeUIntLE = function writeUIntLE(value, offset, byteLength2, noAssert) { + value = +value; + offset = offset >>> 0; + byteLength2 = byteLength2 >>> 0; + if (!noAssert) { + const maxBytes = Math.pow(2, 8 * byteLength2) - 1; + checkInt(this, value, offset, byteLength2, maxBytes, 0); + } + let mul = 1; + let i = 0; + this[offset] = value & 255; + while (++i < byteLength2 && (mul *= 256)) { + this[offset + i] = value / mul & 255; + } + return offset + byteLength2; + }; + Buffer3.prototype.writeUintBE = Buffer3.prototype.writeUIntBE = function writeUIntBE(value, offset, byteLength2, noAssert) { + value = +value; + offset = offset >>> 0; + byteLength2 = byteLength2 >>> 0; + if (!noAssert) { + const maxBytes = Math.pow(2, 8 * byteLength2) - 1; + checkInt(this, value, offset, byteLength2, maxBytes, 0); + } + let i = byteLength2 - 1; + let mul = 1; + this[offset + i] = value & 255; + while (--i >= 0 && (mul *= 256)) { + this[offset + i] = value / mul & 255; + } + return offset + byteLength2; + }; + Buffer3.prototype.writeUint8 = Buffer3.prototype.writeUInt8 = function writeUInt8(value, offset, noAssert) { + value = +value; + offset = offset >>> 0; + if (!noAssert) checkInt(this, value, offset, 1, 255, 0); + this[offset] = value & 255; + return offset + 1; + }; + Buffer3.prototype.writeUint16LE = Buffer3.prototype.writeUInt16LE = function writeUInt16LE(value, offset, noAssert) { + value = +value; + offset = offset >>> 0; + if (!noAssert) checkInt(this, value, offset, 2, 65535, 0); + this[offset] = value & 255; + this[offset + 1] = value >>> 8; + return offset + 2; + }; + Buffer3.prototype.writeUint16BE = Buffer3.prototype.writeUInt16BE = function writeUInt16BE(value, offset, noAssert) { + value = +value; + offset = offset >>> 0; + if (!noAssert) checkInt(this, value, offset, 2, 65535, 0); + this[offset] = value >>> 8; + this[offset + 1] = value & 255; + return offset + 2; + }; + Buffer3.prototype.writeUint32LE = Buffer3.prototype.writeUInt32LE = function writeUInt32LE(value, offset, noAssert) { + value = +value; + offset = offset >>> 0; + if (!noAssert) checkInt(this, value, offset, 4, 4294967295, 0); + this[offset + 3] = value >>> 24; + this[offset + 2] = value >>> 16; + this[offset + 1] = value >>> 8; + this[offset] = value & 255; + return offset + 4; + }; + Buffer3.prototype.writeUint32BE = Buffer3.prototype.writeUInt32BE = function writeUInt32BE(value, offset, noAssert) { + value = +value; + offset = offset >>> 0; + if (!noAssert) checkInt(this, value, offset, 4, 4294967295, 0); + this[offset] = value >>> 24; + this[offset + 1] = value >>> 16; + this[offset + 2] = value >>> 8; + this[offset + 3] = value & 255; + return offset + 4; + }; + function wrtBigUInt64LE(buf, value, offset, min, max) { + checkIntBI(value, min, max, buf, offset, 7); + let lo = Number(value & BigInt(4294967295)); + buf[offset++] = lo; + lo = lo >> 8; + buf[offset++] = lo; + lo = lo >> 8; + buf[offset++] = lo; + lo = lo >> 8; + buf[offset++] = lo; + let hi = Number(value >> BigInt(32) & BigInt(4294967295)); + buf[offset++] = hi; + hi = hi >> 8; + buf[offset++] = hi; + hi = hi >> 8; + buf[offset++] = hi; + hi = hi >> 8; + buf[offset++] = hi; + return offset; + } + function wrtBigUInt64BE(buf, value, offset, min, max) { + checkIntBI(value, min, max, buf, offset, 7); + let lo = Number(value & BigInt(4294967295)); + buf[offset + 7] = lo; + lo = lo >> 8; + buf[offset + 6] = lo; + lo = lo >> 8; + buf[offset + 5] = lo; + lo = lo >> 8; + buf[offset + 4] = lo; + let hi = Number(value >> BigInt(32) & BigInt(4294967295)); + buf[offset + 3] = hi; + hi = hi >> 8; + buf[offset + 2] = hi; + hi = hi >> 8; + buf[offset + 1] = hi; + hi = hi >> 8; + buf[offset] = hi; + return offset + 8; + } + Buffer3.prototype.writeBigUInt64LE = defineBigIntMethod(function writeBigUInt64LE(value, offset = 0) { + return wrtBigUInt64LE(this, value, offset, BigInt(0), BigInt("0xffffffffffffffff")); + }); + Buffer3.prototype.writeBigUInt64BE = defineBigIntMethod(function writeBigUInt64BE(value, offset = 0) { + return wrtBigUInt64BE(this, value, offset, BigInt(0), BigInt("0xffffffffffffffff")); + }); + Buffer3.prototype.writeIntLE = function writeIntLE(value, offset, byteLength2, noAssert) { + value = +value; + offset = offset >>> 0; + if (!noAssert) { + const limit = Math.pow(2, 8 * byteLength2 - 1); + checkInt(this, value, offset, byteLength2, limit - 1, -limit); + } + let i = 0; + let mul = 1; + let sub = 0; + this[offset] = value & 255; + while (++i < byteLength2 && (mul *= 256)) { + if (value < 0 && sub === 0 && this[offset + i - 1] !== 0) { + sub = 1; + } + this[offset + i] = (value / mul >> 0) - sub & 255; + } + return offset + byteLength2; + }; + Buffer3.prototype.writeIntBE = function writeIntBE(value, offset, byteLength2, noAssert) { + value = +value; + offset = offset >>> 0; + if (!noAssert) { + const limit = Math.pow(2, 8 * byteLength2 - 1); + checkInt(this, value, offset, byteLength2, limit - 1, -limit); + } + let i = byteLength2 - 1; + let mul = 1; + let sub = 0; + this[offset + i] = value & 255; + while (--i >= 0 && (mul *= 256)) { + if (value < 0 && sub === 0 && this[offset + i + 1] !== 0) { + sub = 1; + } + this[offset + i] = (value / mul >> 0) - sub & 255; + } + return offset + byteLength2; + }; + Buffer3.prototype.writeInt8 = function writeInt8(value, offset, noAssert) { + value = +value; + offset = offset >>> 0; + if (!noAssert) checkInt(this, value, offset, 1, 127, -128); + if (value < 0) value = 255 + value + 1; + this[offset] = value & 255; + return offset + 1; + }; + Buffer3.prototype.writeInt16LE = function writeInt16LE(value, offset, noAssert) { + value = +value; + offset = offset >>> 0; + if (!noAssert) checkInt(this, value, offset, 2, 32767, -32768); + this[offset] = value & 255; + this[offset + 1] = value >>> 8; + return offset + 2; + }; + Buffer3.prototype.writeInt16BE = function writeInt16BE(value, offset, noAssert) { + value = +value; + offset = offset >>> 0; + if (!noAssert) checkInt(this, value, offset, 2, 32767, -32768); + this[offset] = value >>> 8; + this[offset + 1] = value & 255; + return offset + 2; + }; + Buffer3.prototype.writeInt32LE = function writeInt32LE(value, offset, noAssert) { + value = +value; + offset = offset >>> 0; + if (!noAssert) checkInt(this, value, offset, 4, 2147483647, -2147483648); + this[offset] = value & 255; + this[offset + 1] = value >>> 8; + this[offset + 2] = value >>> 16; + this[offset + 3] = value >>> 24; + return offset + 4; + }; + Buffer3.prototype.writeInt32BE = function writeInt32BE(value, offset, noAssert) { + value = +value; + offset = offset >>> 0; + if (!noAssert) checkInt(this, value, offset, 4, 2147483647, -2147483648); + if (value < 0) value = 4294967295 + value + 1; + this[offset] = value >>> 24; + this[offset + 1] = value >>> 16; + this[offset + 2] = value >>> 8; + this[offset + 3] = value & 255; + return offset + 4; + }; + Buffer3.prototype.writeBigInt64LE = defineBigIntMethod(function writeBigInt64LE(value, offset = 0) { + return wrtBigUInt64LE(this, value, offset, -BigInt("0x8000000000000000"), BigInt("0x7fffffffffffffff")); + }); + Buffer3.prototype.writeBigInt64BE = defineBigIntMethod(function writeBigInt64BE(value, offset = 0) { + return wrtBigUInt64BE(this, value, offset, -BigInt("0x8000000000000000"), BigInt("0x7fffffffffffffff")); + }); + function checkIEEE754(buf, value, offset, ext, max, min) { + if (offset + ext > buf.length) throw new RangeError("Index out of range"); + if (offset < 0) throw new RangeError("Index out of range"); + } + function writeFloat(buf, value, offset, littleEndian, noAssert) { + value = +value; + offset = offset >>> 0; + if (!noAssert) { + checkIEEE754(buf, value, offset, 4, 34028234663852886e22, -34028234663852886e22); + } + ieee754.write(buf, value, offset, littleEndian, 23, 4); + return offset + 4; + } + Buffer3.prototype.writeFloatLE = function writeFloatLE(value, offset, noAssert) { + return writeFloat(this, value, offset, true, noAssert); + }; + Buffer3.prototype.writeFloatBE = function writeFloatBE(value, offset, noAssert) { + return writeFloat(this, value, offset, false, noAssert); + }; + function writeDouble(buf, value, offset, littleEndian, noAssert) { + value = +value; + offset = offset >>> 0; + if (!noAssert) { + checkIEEE754(buf, value, offset, 8, 17976931348623157e292, -17976931348623157e292); + } + ieee754.write(buf, value, offset, littleEndian, 52, 8); + return offset + 8; + } + Buffer3.prototype.writeDoubleLE = function writeDoubleLE(value, offset, noAssert) { + return writeDouble(this, value, offset, true, noAssert); + }; + Buffer3.prototype.writeDoubleBE = function writeDoubleBE(value, offset, noAssert) { + return writeDouble(this, value, offset, false, noAssert); + }; + Buffer3.prototype.copy = function copy(target, targetStart, start, end) { + if (!Buffer3.isBuffer(target)) throw new TypeError("argument should be a Buffer"); + if (!start) start = 0; + if (!end && end !== 0) end = this.length; + if (targetStart >= target.length) targetStart = target.length; + if (!targetStart) targetStart = 0; + if (end > 0 && end < start) end = start; + if (end === start) return 0; + if (target.length === 0 || this.length === 0) return 0; + if (targetStart < 0) { + throw new RangeError("targetStart out of bounds"); + } + if (start < 0 || start >= this.length) throw new RangeError("Index out of range"); + if (end < 0) throw new RangeError("sourceEnd out of bounds"); + if (end > this.length) end = this.length; + if (target.length - targetStart < end - start) { + end = target.length - targetStart + start; + } + const len = end - start; + if (this === target && typeof Uint8Array.prototype.copyWithin === "function") { + this.copyWithin(targetStart, start, end); + } else { + Uint8Array.prototype.set.call( + target, + this.subarray(start, end), + targetStart + ); + } + return len; + }; + Buffer3.prototype.fill = function fill(val, start, end, encoding) { + if (typeof val === "string") { + if (typeof start === "string") { + encoding = start; + start = 0; + end = this.length; + } else if (typeof end === "string") { + encoding = end; + end = this.length; + } + if (encoding !== void 0 && typeof encoding !== "string") { + throw new TypeError("encoding must be a string"); + } + if (typeof encoding === "string" && !Buffer3.isEncoding(encoding)) { + throw new TypeError("Unknown encoding: " + encoding); + } + if (val.length === 1) { + const code = val.charCodeAt(0); + if (encoding === "utf8" && code < 128 || encoding === "latin1") { + val = code; + } + } + } else if (typeof val === "number") { + val = val & 255; + } else if (typeof val === "boolean") { + val = Number(val); + } + if (start < 0 || this.length < start || this.length < end) { + throw new RangeError("Out of range index"); + } + if (end <= start) { + return this; + } + start = start >>> 0; + end = end === void 0 ? this.length : end >>> 0; + if (!val) val = 0; + let i; + if (typeof val === "number") { + for (i = start; i < end; ++i) { + this[i] = val; + } + } else { + const bytes = Buffer3.isBuffer(val) ? val : Buffer3.from(val, encoding); + const len = bytes.length; + if (len === 0) { + throw new TypeError('The value "' + val + '" is invalid for argument "value"'); + } + for (i = 0; i < end - start; ++i) { + this[i + start] = bytes[i % len]; + } + } + return this; + }; + var errors = {}; + function E(sym, getMessage, Base) { + errors[sym] = class NodeError extends Base { + constructor() { + super(); + Object.defineProperty(this, "message", { + value: getMessage.apply(this, arguments), + writable: true, + configurable: true + }); + this.name = `${this.name} [${sym}]`; + this.stack; + delete this.name; + } + get code() { + return sym; + } + set code(value) { + Object.defineProperty(this, "code", { + configurable: true, + enumerable: true, + value, + writable: true + }); + } + toString() { + return `${this.name} [${sym}]: ${this.message}`; + } + }; + } + E( + "ERR_BUFFER_OUT_OF_BOUNDS", + function(name) { + if (name) { + return `${name} is outside of buffer bounds`; + } + return "Attempt to access memory outside buffer bounds"; + }, + RangeError + ); + E( + "ERR_INVALID_ARG_TYPE", + function(name, actual) { + return `The "${name}" argument must be of type number. Received type ${typeof actual}`; + }, + TypeError + ); + E( + "ERR_OUT_OF_RANGE", + function(str, range, input) { + let msg = `The value of "${str}" is out of range.`; + let received = input; + if (Number.isInteger(input) && Math.abs(input) > 2 ** 32) { + received = addNumericalSeparator(String(input)); + } else if (typeof input === "bigint") { + received = String(input); + if (input > BigInt(2) ** BigInt(32) || input < -(BigInt(2) ** BigInt(32))) { + received = addNumericalSeparator(received); + } + received += "n"; + } + msg += ` It must be ${range}. Received ${received}`; + return msg; + }, + RangeError + ); + function addNumericalSeparator(val) { + let res = ""; + let i = val.length; + const start = val[0] === "-" ? 1 : 0; + for (; i >= start + 4; i -= 3) { + res = `_${val.slice(i - 3, i)}${res}`; + } + return `${val.slice(0, i)}${res}`; + } + function checkBounds(buf, offset, byteLength2) { + validateNumber(offset, "offset"); + if (buf[offset] === void 0 || buf[offset + byteLength2] === void 0) { + boundsError(offset, buf.length - (byteLength2 + 1)); + } + } + function checkIntBI(value, min, max, buf, offset, byteLength2) { + if (value > max || value < min) { + const n = typeof min === "bigint" ? "n" : ""; + let range; + if (byteLength2 > 3) { + if (min === 0 || min === BigInt(0)) { + range = `>= 0${n} and < 2${n} ** ${(byteLength2 + 1) * 8}${n}`; + } else { + range = `>= -(2${n} ** ${(byteLength2 + 1) * 8 - 1}${n}) and < 2 ** ${(byteLength2 + 1) * 8 - 1}${n}`; + } + } else { + range = `>= ${min}${n} and <= ${max}${n}`; + } + throw new errors.ERR_OUT_OF_RANGE("value", range, value); + } + checkBounds(buf, offset, byteLength2); + } + function validateNumber(value, name) { + if (typeof value !== "number") { + throw new errors.ERR_INVALID_ARG_TYPE(name, "number", value); + } + } + function boundsError(value, length, type) { + if (Math.floor(value) !== value) { + validateNumber(value, type); + throw new errors.ERR_OUT_OF_RANGE(type || "offset", "an integer", value); + } + if (length < 0) { + throw new errors.ERR_BUFFER_OUT_OF_BOUNDS(); + } + throw new errors.ERR_OUT_OF_RANGE( + type || "offset", + `>= ${type ? 1 : 0} and <= ${length}`, + value + ); + } + var INVALID_BASE64_RE = /[^+/0-9A-Za-z-_]/g; + function base64clean(str) { + str = str.split("=")[0]; + str = str.trim().replace(INVALID_BASE64_RE, ""); + if (str.length < 2) return ""; + while (str.length % 4 !== 0) { + str = str + "="; + } + return str; + } + function utf8ToBytes3(string, units) { + units = units || Infinity; + let codePoint; + const length = string.length; + let leadSurrogate = null; + const bytes = []; + for (let i = 0; i < length; ++i) { + codePoint = string.charCodeAt(i); + if (codePoint > 55295 && codePoint < 57344) { + if (!leadSurrogate) { + if (codePoint > 56319) { + if ((units -= 3) > -1) bytes.push(239, 191, 189); + continue; + } else if (i + 1 === length) { + if ((units -= 3) > -1) bytes.push(239, 191, 189); + continue; + } + leadSurrogate = codePoint; + continue; + } + if (codePoint < 56320) { + if ((units -= 3) > -1) bytes.push(239, 191, 189); + leadSurrogate = codePoint; + continue; + } + codePoint = (leadSurrogate - 55296 << 10 | codePoint - 56320) + 65536; + } else if (leadSurrogate) { + if ((units -= 3) > -1) bytes.push(239, 191, 189); + } + leadSurrogate = null; + if (codePoint < 128) { + if ((units -= 1) < 0) break; + bytes.push(codePoint); + } else if (codePoint < 2048) { + if ((units -= 2) < 0) break; + bytes.push( + codePoint >> 6 | 192, + codePoint & 63 | 128 + ); + } else if (codePoint < 65536) { + if ((units -= 3) < 0) break; + bytes.push( + codePoint >> 12 | 224, + codePoint >> 6 & 63 | 128, + codePoint & 63 | 128 + ); + } else if (codePoint < 1114112) { + if ((units -= 4) < 0) break; + bytes.push( + codePoint >> 18 | 240, + codePoint >> 12 & 63 | 128, + codePoint >> 6 & 63 | 128, + codePoint & 63 | 128 + ); + } else { + throw new Error("Invalid code point"); + } + } + return bytes; + } + function asciiToBytes2(str) { + const byteArray = []; + for (let i = 0; i < str.length; ++i) { + byteArray.push(str.charCodeAt(i) & 255); + } + return byteArray; + } + function utf16leToBytes(str, units) { + let c, hi, lo; + const byteArray = []; + for (let i = 0; i < str.length; ++i) { + if ((units -= 2) < 0) break; + c = str.charCodeAt(i); + hi = c >> 8; + lo = c % 256; + byteArray.push(lo); + byteArray.push(hi); + } + return byteArray; + } + function base64ToBytes2(str) { + return base642.toByteArray(base64clean(str)); + } + function blitBuffer(src, dst, offset, length) { + let i; + for (i = 0; i < length; ++i) { + if (i + offset >= dst.length || i >= src.length) break; + dst[i + offset] = src[i]; + } + return i; + } + function isInstance(obj, type) { + return obj instanceof type || obj != null && obj.constructor != null && obj.constructor.name != null && obj.constructor.name === type.name; + } + function numberIsNaN(obj) { + return obj !== obj; + } + var hexSliceLookupTable = (function() { + const alphabet2 = "0123456789abcdef"; + const table = new Array(256); + for (let i = 0; i < 16; ++i) { + const i16 = i * 16; + for (let j = 0; j < 16; ++j) { + table[i16 + j] = alphabet2[i] + alphabet2[j]; + } + } + return table; + })(); + function defineBigIntMethod(fn) { + return typeof BigInt === "undefined" ? BufferBigIntNotDefined : fn; + } + function BufferBigIntNotDefined() { + throw new Error("BigInt not supported"); + } + } + }); + + // src/background.js + init_process(); + + // node_modules/nostr-crypto-utils/dist/esm/index.js + init_process(); + + // node_modules/nostr-crypto-utils/dist/esm/types/index.js + init_process(); + + // node_modules/nostr-crypto-utils/dist/esm/types/base.js + init_process(); + var NostrEventKind; + (function(NostrEventKind3) { + NostrEventKind3[NostrEventKind3["SET_METADATA"] = 0] = "SET_METADATA"; + NostrEventKind3[NostrEventKind3["TEXT_NOTE"] = 1] = "TEXT_NOTE"; + NostrEventKind3[NostrEventKind3["RECOMMEND_SERVER"] = 2] = "RECOMMEND_SERVER"; + NostrEventKind3[NostrEventKind3["CONTACTS"] = 3] = "CONTACTS"; + NostrEventKind3[NostrEventKind3["ENCRYPTED_DIRECT_MESSAGE"] = 4] = "ENCRYPTED_DIRECT_MESSAGE"; + NostrEventKind3[NostrEventKind3["EVENT_DELETION"] = 5] = "EVENT_DELETION"; + NostrEventKind3[NostrEventKind3["REPOST"] = 6] = "REPOST"; + NostrEventKind3[NostrEventKind3["REACTION"] = 7] = "REACTION"; + NostrEventKind3[NostrEventKind3["CHANNEL_CREATION"] = 40] = "CHANNEL_CREATION"; + NostrEventKind3[NostrEventKind3["CHANNEL_METADATA"] = 41] = "CHANNEL_METADATA"; + NostrEventKind3[NostrEventKind3["CHANNEL_MESSAGE"] = 42] = "CHANNEL_MESSAGE"; + NostrEventKind3[NostrEventKind3["CHANNEL_HIDE_MESSAGE"] = 43] = "CHANNEL_HIDE_MESSAGE"; + NostrEventKind3[NostrEventKind3["CHANNEL_MUTE_USER"] = 44] = "CHANNEL_MUTE_USER"; + NostrEventKind3[NostrEventKind3["AUTH"] = 22242] = "AUTH"; + NostrEventKind3[NostrEventKind3["AUTH_RESPONSE"] = 22243] = "AUTH_RESPONSE"; + })(NostrEventKind || (NostrEventKind = {})); + var NostrMessageType; + (function(NostrMessageType2) { + NostrMessageType2["EVENT"] = "EVENT"; + NostrMessageType2["NOTICE"] = "NOTICE"; + NostrMessageType2["OK"] = "OK"; + NostrMessageType2["EOSE"] = "EOSE"; + NostrMessageType2["REQ"] = "REQ"; + NostrMessageType2["CLOSE"] = "CLOSE"; + NostrMessageType2["AUTH"] = "AUTH"; + })(NostrMessageType || (NostrMessageType = {})); + + // node_modules/nostr-crypto-utils/dist/esm/types/protocol.js + init_process(); + + // node_modules/nostr-crypto-utils/dist/esm/types/messages.js + init_process(); + + // node_modules/nostr-crypto-utils/dist/esm/types/guards.js + init_process(); + + // node_modules/nostr-crypto-utils/dist/esm/types/nip46.js + init_process(); + var Nip46Method; + (function(Nip46Method2) { + Nip46Method2["CONNECT"] = "connect"; + Nip46Method2["PING"] = "ping"; + Nip46Method2["GET_PUBLIC_KEY"] = "get_public_key"; + Nip46Method2["SIGN_EVENT"] = "sign_event"; + Nip46Method2["NIP04_ENCRYPT"] = "nip04_encrypt"; + Nip46Method2["NIP04_DECRYPT"] = "nip04_decrypt"; + Nip46Method2["NIP44_ENCRYPT"] = "nip44_encrypt"; + Nip46Method2["NIP44_DECRYPT"] = "nip44_decrypt"; + Nip46Method2["GET_RELAYS"] = "get_relays"; + })(Nip46Method || (Nip46Method = {})); + + // node_modules/nostr-crypto-utils/dist/esm/types/index.js + var NostrEventKind2; + (function(NostrEventKind3) { + NostrEventKind3[NostrEventKind3["SET_METADATA"] = 0] = "SET_METADATA"; + NostrEventKind3[NostrEventKind3["TEXT_NOTE"] = 1] = "TEXT_NOTE"; + NostrEventKind3[NostrEventKind3["RECOMMEND_SERVER"] = 2] = "RECOMMEND_SERVER"; + NostrEventKind3[NostrEventKind3["CONTACT_LIST"] = 3] = "CONTACT_LIST"; + NostrEventKind3[NostrEventKind3["ENCRYPTED_DIRECT_MESSAGE"] = 4] = "ENCRYPTED_DIRECT_MESSAGE"; + NostrEventKind3[NostrEventKind3["DELETE"] = 5] = "DELETE"; + NostrEventKind3[NostrEventKind3["REPOST"] = 6] = "REPOST"; + NostrEventKind3[NostrEventKind3["REACTION"] = 7] = "REACTION"; + NostrEventKind3[NostrEventKind3["BADGE_AWARD"] = 8] = "BADGE_AWARD"; + NostrEventKind3[NostrEventKind3["CHANNEL_CREATE"] = 40] = "CHANNEL_CREATE"; + NostrEventKind3[NostrEventKind3["CHANNEL_METADATA"] = 41] = "CHANNEL_METADATA"; + NostrEventKind3[NostrEventKind3["CHANNEL_MESSAGE"] = 42] = "CHANNEL_MESSAGE"; + NostrEventKind3[NostrEventKind3["CHANNEL_HIDE_MESSAGE"] = 43] = "CHANNEL_HIDE_MESSAGE"; + NostrEventKind3[NostrEventKind3["CHANNEL_MUTE_USER"] = 44] = "CHANNEL_MUTE_USER"; + NostrEventKind3[NostrEventKind3["CHANNEL_RESERVE"] = 45] = "CHANNEL_RESERVE"; + NostrEventKind3[NostrEventKind3["REPORTING"] = 1984] = "REPORTING"; + NostrEventKind3[NostrEventKind3["ZAP_REQUEST"] = 9734] = "ZAP_REQUEST"; + NostrEventKind3[NostrEventKind3["ZAP"] = 9735] = "ZAP"; + NostrEventKind3[NostrEventKind3["MUTE_LIST"] = 1e4] = "MUTE_LIST"; + NostrEventKind3[NostrEventKind3["PIN_LIST"] = 10001] = "PIN_LIST"; + NostrEventKind3[NostrEventKind3["RELAY_LIST_METADATA"] = 10002] = "RELAY_LIST_METADATA"; + NostrEventKind3[NostrEventKind3["CLIENT_AUTH"] = 22242] = "CLIENT_AUTH"; + NostrEventKind3[NostrEventKind3["AUTH_RESPONSE"] = 22243] = "AUTH_RESPONSE"; + NostrEventKind3[NostrEventKind3["NOSTR_CONNECT"] = 24133] = "NOSTR_CONNECT"; + NostrEventKind3[NostrEventKind3["CATEGORIZED_PEOPLE"] = 3e4] = "CATEGORIZED_PEOPLE"; + NostrEventKind3[NostrEventKind3["CATEGORIZED_BOOKMARKS"] = 30001] = "CATEGORIZED_BOOKMARKS"; + NostrEventKind3[NostrEventKind3["PROFILE_BADGES"] = 30008] = "PROFILE_BADGES"; + NostrEventKind3[NostrEventKind3["BADGE_DEFINITION"] = 30009] = "BADGE_DEFINITION"; + NostrEventKind3[NostrEventKind3["LONG_FORM"] = 30023] = "LONG_FORM"; + NostrEventKind3[NostrEventKind3["APPLICATION_SPECIFIC"] = 30078] = "APPLICATION_SPECIFIC"; + })(NostrEventKind2 || (NostrEventKind2 = {})); + + // node_modules/nostr-crypto-utils/dist/esm/crypto.js + init_process(); + + // node_modules/@noble/curves/secp256k1.js + init_process(); + + // node_modules/@noble/hashes/sha2.js + init_process(); + + // node_modules/@noble/hashes/_md.js + init_process(); + + // node_modules/@noble/hashes/utils.js + init_process(); + function isBytes(a) { + return a instanceof Uint8Array || ArrayBuffer.isView(a) && a.constructor.name === "Uint8Array"; + } + function anumber(n, title = "") { + if (!Number.isSafeInteger(n) || n < 0) { + const prefix = title && `"${title}" `; + throw new Error(`${prefix}expected integer >= 0, got ${n}`); + } + } + function abytes(value, length, title = "") { + const bytes = isBytes(value); + const len = value?.length; + const needsLen = length !== void 0; + if (!bytes || needsLen && len !== length) { + const prefix = title && `"${title}" `; + const ofLen = needsLen ? ` of length ${length}` : ""; + const got = bytes ? `length=${len}` : `type=${typeof value}`; + throw new Error(prefix + "expected Uint8Array" + ofLen + ", got " + got); + } + return value; + } + function ahash(h) { + if (typeof h !== "function" || typeof h.create !== "function") + throw new Error("Hash must wrapped by utils.createHasher"); + anumber(h.outputLen); + anumber(h.blockLen); + } + function aexists(instance, checkFinished = true) { + if (instance.destroyed) + throw new Error("Hash instance has been destroyed"); + if (checkFinished && instance.finished) + throw new Error("Hash#digest() has already been called"); + } + function aoutput(out, instance) { + abytes(out, void 0, "digestInto() output"); + const min = instance.outputLen; + if (out.length < min) { + throw new Error('"digestInto() output" expected to be of length >=' + min); + } + } + function u32(arr) { + return new Uint32Array(arr.buffer, arr.byteOffset, Math.floor(arr.byteLength / 4)); + } + function clean(...arrays) { + for (let i = 0; i < arrays.length; i++) { + arrays[i].fill(0); + } + } + function createView(arr) { + return new DataView(arr.buffer, arr.byteOffset, arr.byteLength); + } + function rotr(word, shift) { + return word << 32 - shift | word >>> shift; + } + function rotl(word, shift) { + return word << shift | word >>> 32 - shift >>> 0; + } + var isLE = /* @__PURE__ */ (() => new Uint8Array(new Uint32Array([287454020]).buffer)[0] === 68)(); + function byteSwap(word) { + return word << 24 & 4278190080 | word << 8 & 16711680 | word >>> 8 & 65280 | word >>> 24 & 255; + } + function byteSwap32(arr) { + for (let i = 0; i < arr.length; i++) { + arr[i] = byteSwap(arr[i]); + } + return arr; + } + var swap32IfBE = isLE ? (u) => u : byteSwap32; + var hasHexBuiltin = /* @__PURE__ */ (() => ( + // @ts-ignore + typeof Uint8Array.from([]).toHex === "function" && typeof Uint8Array.fromHex === "function" + ))(); + var hexes = /* @__PURE__ */ Array.from({ length: 256 }, (_, i) => i.toString(16).padStart(2, "0")); + function bytesToHex(bytes) { + abytes(bytes); + if (hasHexBuiltin) + return bytes.toHex(); + let hex = ""; + for (let i = 0; i < bytes.length; i++) { + hex += hexes[bytes[i]]; + } + return hex; + } + var asciis = { _0: 48, _9: 57, A: 65, F: 70, a: 97, f: 102 }; + function asciiToBase16(ch) { + if (ch >= asciis._0 && ch <= asciis._9) + return ch - asciis._0; + if (ch >= asciis.A && ch <= asciis.F) + return ch - (asciis.A - 10); + if (ch >= asciis.a && ch <= asciis.f) + return ch - (asciis.a - 10); + return; + } + function hexToBytes(hex) { + if (typeof hex !== "string") + throw new Error("hex string expected, got " + typeof hex); + if (hasHexBuiltin) + return Uint8Array.fromHex(hex); + const hl = hex.length; + const al = hl / 2; + if (hl % 2) + throw new Error("hex string expected, got unpadded hex of length " + hl); + const array = new Uint8Array(al); + for (let ai = 0, hi = 0; ai < al; ai++, hi += 2) { + const n1 = asciiToBase16(hex.charCodeAt(hi)); + const n2 = asciiToBase16(hex.charCodeAt(hi + 1)); + if (n1 === void 0 || n2 === void 0) { + const char = hex[hi] + hex[hi + 1]; + throw new Error('hex string expected, got non-hex character "' + char + '" at index ' + hi); + } + array[ai] = n1 * 16 + n2; + } + return array; + } + function utf8ToBytes(str) { + if (typeof str !== "string") + throw new Error("string expected"); + return new Uint8Array(new TextEncoder().encode(str)); + } + function kdfInputToBytes(data, errorTitle = "") { + if (typeof data === "string") + return utf8ToBytes(data); + return abytes(data, void 0, errorTitle); + } + function concatBytes(...arrays) { + let sum = 0; + for (let i = 0; i < arrays.length; i++) { + const a = arrays[i]; + abytes(a); + sum += a.length; + } + const res = new Uint8Array(sum); + for (let i = 0, pad2 = 0; i < arrays.length; i++) { + const a = arrays[i]; + res.set(a, pad2); + pad2 += a.length; + } + return res; + } + function checkOpts(defaults, opts) { + if (opts !== void 0 && {}.toString.call(opts) !== "[object Object]") + throw new Error("options must be object or undefined"); + const merged = Object.assign(defaults, opts); + return merged; + } + function createHasher(hashCons, info = {}) { + const hashC = (msg, opts) => hashCons(opts).update(msg).digest(); + const tmp = hashCons(void 0); + hashC.outputLen = tmp.outputLen; + hashC.blockLen = tmp.blockLen; + hashC.create = (opts) => hashCons(opts); + Object.assign(hashC, info); + return Object.freeze(hashC); + } + function randomBytes(bytesLength = 32) { + const cr = typeof globalThis === "object" ? globalThis.crypto : null; + if (typeof cr?.getRandomValues !== "function") + throw new Error("crypto.getRandomValues must be defined"); + return cr.getRandomValues(new Uint8Array(bytesLength)); + } + var oidNist = (suffix) => ({ + oid: Uint8Array.from([6, 9, 96, 134, 72, 1, 101, 3, 4, 2, suffix]) + }); + + // node_modules/@noble/hashes/_md.js + function Chi(a, b, c) { + return a & b ^ ~a & c; + } + function Maj(a, b, c) { + return a & b ^ a & c ^ b & c; + } + var HashMD = class { + blockLen; + outputLen; + padOffset; + isLE; + // For partial updates less than block size + buffer; + view; + finished = false; + length = 0; + pos = 0; + destroyed = false; + constructor(blockLen, outputLen, padOffset, isLE3) { + this.blockLen = blockLen; + this.outputLen = outputLen; + this.padOffset = padOffset; + this.isLE = isLE3; + this.buffer = new Uint8Array(blockLen); + this.view = createView(this.buffer); + } + update(data) { + aexists(this); + abytes(data); + const { view, buffer, blockLen } = this; + const len = data.length; + for (let pos = 0; pos < len; ) { + const take = Math.min(blockLen - this.pos, len - pos); + if (take === blockLen) { + const dataView = createView(data); + for (; blockLen <= len - pos; pos += blockLen) + this.process(dataView, pos); + continue; + } + buffer.set(data.subarray(pos, pos + take), this.pos); + this.pos += take; + pos += take; + if (this.pos === blockLen) { + this.process(view, 0); + this.pos = 0; + } + } + this.length += data.length; + this.roundClean(); + return this; + } + digestInto(out) { + aexists(this); + aoutput(out, this); + this.finished = true; + const { buffer, view, blockLen, isLE: isLE3 } = this; + let { pos } = this; + buffer[pos++] = 128; + clean(this.buffer.subarray(pos)); + if (this.padOffset > blockLen - pos) { + this.process(view, 0); + pos = 0; + } + for (let i = pos; i < blockLen; i++) + buffer[i] = 0; + view.setBigUint64(blockLen - 8, BigInt(this.length * 8), isLE3); + this.process(view, 0); + const oview = createView(out); + const len = this.outputLen; + if (len % 4) + throw new Error("_sha2: outputLen must be aligned to 32bit"); + const outLen = len / 4; + const state = this.get(); + if (outLen > state.length) + throw new Error("_sha2: outputLen bigger than state"); + for (let i = 0; i < outLen; i++) + oview.setUint32(4 * i, state[i], isLE3); + } + digest() { + const { buffer, outputLen } = this; + this.digestInto(buffer); + const res = buffer.slice(0, outputLen); + this.destroy(); + return res; + } + _cloneInto(to) { + to ||= new this.constructor(); + to.set(...this.get()); + const { blockLen, buffer, length, finished, destroyed, pos } = this; + to.destroyed = destroyed; + to.finished = finished; + to.length = length; + to.pos = pos; + if (length % blockLen) + to.buffer.set(buffer); + return to; + } + clone() { + return this._cloneInto(); + } + }; + var SHA256_IV = /* @__PURE__ */ Uint32Array.from([ + 1779033703, + 3144134277, + 1013904242, + 2773480762, + 1359893119, + 2600822924, + 528734635, + 1541459225 + ]); + + // node_modules/@noble/hashes/sha2.js + var SHA256_K = /* @__PURE__ */ Uint32Array.from([ + 1116352408, + 1899447441, + 3049323471, + 3921009573, + 961987163, + 1508970993, + 2453635748, + 2870763221, + 3624381080, + 310598401, + 607225278, + 1426881987, + 1925078388, + 2162078206, + 2614888103, + 3248222580, + 3835390401, + 4022224774, + 264347078, + 604807628, + 770255983, + 1249150122, + 1555081692, + 1996064986, + 2554220882, + 2821834349, + 2952996808, + 3210313671, + 3336571891, + 3584528711, + 113926993, + 338241895, + 666307205, + 773529912, + 1294757372, + 1396182291, + 1695183700, + 1986661051, + 2177026350, + 2456956037, + 2730485921, + 2820302411, + 3259730800, + 3345764771, + 3516065817, + 3600352804, + 4094571909, + 275423344, + 430227734, + 506948616, + 659060556, + 883997877, + 958139571, + 1322822218, + 1537002063, + 1747873779, + 1955562222, + 2024104815, + 2227730452, + 2361852424, + 2428436474, + 2756734187, + 3204031479, + 3329325298 + ]); + var SHA256_W = /* @__PURE__ */ new Uint32Array(64); + var SHA2_32B = class extends HashMD { + constructor(outputLen) { + super(64, outputLen, 8, false); + } + get() { + const { A, B, C, D, E, F, G, H } = this; + return [A, B, C, D, E, F, G, H]; + } + // prettier-ignore + set(A, B, C, D, E, F, G, H) { + this.A = A | 0; + this.B = B | 0; + this.C = C | 0; + this.D = D | 0; + this.E = E | 0; + this.F = F | 0; + this.G = G | 0; + this.H = H | 0; + } + process(view, offset) { + for (let i = 0; i < 16; i++, offset += 4) + SHA256_W[i] = view.getUint32(offset, false); + for (let i = 16; i < 64; i++) { + const W15 = SHA256_W[i - 15]; + const W2 = SHA256_W[i - 2]; + const s0 = rotr(W15, 7) ^ rotr(W15, 18) ^ W15 >>> 3; + const s1 = rotr(W2, 17) ^ rotr(W2, 19) ^ W2 >>> 10; + SHA256_W[i] = s1 + SHA256_W[i - 7] + s0 + SHA256_W[i - 16] | 0; + } + let { A, B, C, D, E, F, G, H } = this; + for (let i = 0; i < 64; i++) { + const sigma1 = rotr(E, 6) ^ rotr(E, 11) ^ rotr(E, 25); + const T1 = H + sigma1 + Chi(E, F, G) + SHA256_K[i] + SHA256_W[i] | 0; + const sigma0 = rotr(A, 2) ^ rotr(A, 13) ^ rotr(A, 22); + const T2 = sigma0 + Maj(A, B, C) | 0; + H = G; + G = F; + F = E; + E = D + T1 | 0; + D = C; + C = B; + B = A; + A = T1 + T2 | 0; + } + A = A + this.A | 0; + B = B + this.B | 0; + C = C + this.C | 0; + D = D + this.D | 0; + E = E + this.E | 0; + F = F + this.F | 0; + G = G + this.G | 0; + H = H + this.H | 0; + this.set(A, B, C, D, E, F, G, H); + } + roundClean() { + clean(SHA256_W); + } + destroy() { + this.set(0, 0, 0, 0, 0, 0, 0, 0); + clean(this.buffer); + } + }; + var _SHA256 = class extends SHA2_32B { + // We cannot use array here since array allows indexing by variable + // which means optimizer/compiler cannot use registers. + A = SHA256_IV[0] | 0; + B = SHA256_IV[1] | 0; + C = SHA256_IV[2] | 0; + D = SHA256_IV[3] | 0; + E = SHA256_IV[4] | 0; + F = SHA256_IV[5] | 0; + G = SHA256_IV[6] | 0; + H = SHA256_IV[7] | 0; + constructor() { + super(32); + } + }; + var sha256 = /* @__PURE__ */ createHasher( + () => new _SHA256(), + /* @__PURE__ */ oidNist(1) + ); + + // node_modules/@noble/curves/abstract/curve.js + init_process(); + + // node_modules/@noble/curves/utils.js + init_process(); + var _0n = /* @__PURE__ */ BigInt(0); + var _1n = /* @__PURE__ */ BigInt(1); + function abool(value, title = "") { + if (typeof value !== "boolean") { + const prefix = title && `"${title}" `; + throw new Error(prefix + "expected boolean, got type=" + typeof value); + } + return value; + } + function abignumber(n) { + if (typeof n === "bigint") { + if (!isPosBig(n)) + throw new Error("positive bigint expected, got " + n); + } else + anumber(n); + return n; + } + function numberToHexUnpadded(num2) { + const hex = abignumber(num2).toString(16); + return hex.length & 1 ? "0" + hex : hex; + } + function hexToNumber(hex) { + if (typeof hex !== "string") + throw new Error("hex string expected, got " + typeof hex); + return hex === "" ? _0n : BigInt("0x" + hex); + } + function bytesToNumberBE(bytes) { + return hexToNumber(bytesToHex(bytes)); + } + function bytesToNumberLE(bytes) { + return hexToNumber(bytesToHex(copyBytes(abytes(bytes)).reverse())); + } + function numberToBytesBE(n, len) { + anumber(len); + n = abignumber(n); + const res = hexToBytes(n.toString(16).padStart(len * 2, "0")); + if (res.length !== len) + throw new Error("number too large"); + return res; + } + function numberToBytesLE(n, len) { + return numberToBytesBE(n, len).reverse(); + } + function copyBytes(bytes) { + return Uint8Array.from(bytes); + } + function asciiToBytes(ascii) { + return Uint8Array.from(ascii, (c, i) => { + const charCode = c.charCodeAt(0); + if (c.length !== 1 || charCode > 127) { + throw new Error(`string contains non-ASCII character "${ascii[i]}" with code ${charCode} at position ${i}`); + } + return charCode; + }); + } + var isPosBig = (n) => typeof n === "bigint" && _0n <= n; + function inRange(n, min, max) { + return isPosBig(n) && isPosBig(min) && isPosBig(max) && min <= n && n < max; + } + function aInRange(title, n, min, max) { + if (!inRange(n, min, max)) + throw new Error("expected valid " + title + ": " + min + " <= n < " + max + ", got " + n); + } + function bitLen(n) { + let len; + for (len = 0; n > _0n; n >>= _1n, len += 1) + ; + return len; + } + var bitMask = (n) => (_1n << BigInt(n)) - _1n; + function createHmacDrbg(hashLen, qByteLen, hmacFn) { + anumber(hashLen, "hashLen"); + anumber(qByteLen, "qByteLen"); + if (typeof hmacFn !== "function") + throw new Error("hmacFn must be a function"); + const u8n = (len) => new Uint8Array(len); + const NULL = Uint8Array.of(); + const byte0 = Uint8Array.of(0); + const byte1 = Uint8Array.of(1); + const _maxDrbgIters = 1e3; + let v = u8n(hashLen); + let k = u8n(hashLen); + let i = 0; + const reset = () => { + v.fill(1); + k.fill(0); + i = 0; + }; + const h = (...msgs) => hmacFn(k, concatBytes(v, ...msgs)); + const reseed = (seed = NULL) => { + k = h(byte0, seed); + v = h(); + if (seed.length === 0) + return; + k = h(byte1, seed); + v = h(); + }; + const gen = () => { + if (i++ >= _maxDrbgIters) + throw new Error("drbg: tried max amount of iterations"); + let len = 0; + const out = []; + while (len < qByteLen) { + v = h(); + const sl = v.slice(); + out.push(sl); + len += v.length; + } + return concatBytes(...out); + }; + const genUntil = (seed, pred) => { + reset(); + reseed(seed); + let res = void 0; + while (!(res = pred(gen()))) + reseed(); + reset(); + return res; + }; + return genUntil; + } + function validateObject(object, fields = {}, optFields = {}) { + if (!object || typeof object !== "object") + throw new Error("expected valid options object"); + function checkField(fieldName, expectedType, isOpt) { + const val = object[fieldName]; + if (isOpt && val === void 0) + return; + const current = typeof val; + if (current !== expectedType || val === null) + throw new Error(`param "${fieldName}" is invalid: expected ${expectedType}, got ${current}`); + } + const iter = (f, isOpt) => Object.entries(f).forEach(([k, v]) => checkField(k, v, isOpt)); + iter(fields, false); + iter(optFields, true); + } + function memoized(fn) { + const map = /* @__PURE__ */ new WeakMap(); + return (arg, ...args) => { + const val = map.get(arg); + if (val !== void 0) + return val; + const computed = fn(arg, ...args); + map.set(arg, computed); + return computed; + }; + } + + // node_modules/@noble/curves/abstract/modular.js + init_process(); + var _0n2 = /* @__PURE__ */ BigInt(0); + var _1n2 = /* @__PURE__ */ BigInt(1); + var _2n = /* @__PURE__ */ BigInt(2); + var _3n = /* @__PURE__ */ BigInt(3); + var _4n = /* @__PURE__ */ BigInt(4); + var _5n = /* @__PURE__ */ BigInt(5); + var _7n = /* @__PURE__ */ BigInt(7); + var _8n = /* @__PURE__ */ BigInt(8); + var _9n = /* @__PURE__ */ BigInt(9); + var _16n = /* @__PURE__ */ BigInt(16); + function mod(a, b) { + const result = a % b; + return result >= _0n2 ? result : b + result; + } + function pow2(x, power, modulo) { + let res = x; + while (power-- > _0n2) { + res *= res; + res %= modulo; + } + return res; + } + function invert(number, modulo) { + if (number === _0n2) + throw new Error("invert: expected non-zero number"); + if (modulo <= _0n2) + throw new Error("invert: expected positive modulus, got " + modulo); + let a = mod(number, modulo); + let b = modulo; + let x = _0n2, y = _1n2, u = _1n2, v = _0n2; + while (a !== _0n2) { + const q = b / a; + const r = b % a; + const m = x - u * q; + const n = y - v * q; + b = a, a = r, x = u, y = v, u = m, v = n; + } + const gcd2 = b; + if (gcd2 !== _1n2) + throw new Error("invert: does not exist"); + return mod(x, modulo); + } + function assertIsSquare(Fp, root, n) { + if (!Fp.eql(Fp.sqr(root), n)) + throw new Error("Cannot find square root"); + } + function sqrt3mod4(Fp, n) { + const p1div4 = (Fp.ORDER + _1n2) / _4n; + const root = Fp.pow(n, p1div4); + assertIsSquare(Fp, root, n); + return root; + } + function sqrt5mod8(Fp, n) { + const p5div8 = (Fp.ORDER - _5n) / _8n; + const n2 = Fp.mul(n, _2n); + const v = Fp.pow(n2, p5div8); + const nv = Fp.mul(n, v); + const i = Fp.mul(Fp.mul(nv, _2n), v); + const root = Fp.mul(nv, Fp.sub(i, Fp.ONE)); + assertIsSquare(Fp, root, n); + return root; + } + function sqrt9mod16(P) { + const Fp_ = Field(P); + const tn = tonelliShanks(P); + const c1 = tn(Fp_, Fp_.neg(Fp_.ONE)); + const c2 = tn(Fp_, c1); + const c3 = tn(Fp_, Fp_.neg(c1)); + const c4 = (P + _7n) / _16n; + return (Fp, n) => { + let tv1 = Fp.pow(n, c4); + let tv2 = Fp.mul(tv1, c1); + const tv3 = Fp.mul(tv1, c2); + const tv4 = Fp.mul(tv1, c3); + const e1 = Fp.eql(Fp.sqr(tv2), n); + const e2 = Fp.eql(Fp.sqr(tv3), n); + tv1 = Fp.cmov(tv1, tv2, e1); + tv2 = Fp.cmov(tv4, tv3, e2); + const e3 = Fp.eql(Fp.sqr(tv2), n); + const root = Fp.cmov(tv1, tv2, e3); + assertIsSquare(Fp, root, n); + return root; + }; + } + function tonelliShanks(P) { + if (P < _3n) + throw new Error("sqrt is not defined for small field"); + let Q = P - _1n2; + let S = 0; + while (Q % _2n === _0n2) { + Q /= _2n; + S++; + } + let Z = _2n; + const _Fp = Field(P); + while (FpLegendre(_Fp, Z) === 1) { + if (Z++ > 1e3) + throw new Error("Cannot find square root: probably non-prime P"); + } + if (S === 1) + return sqrt3mod4; + let cc = _Fp.pow(Z, Q); + const Q1div2 = (Q + _1n2) / _2n; + return function tonelliSlow(Fp, n) { + if (Fp.is0(n)) + return n; + if (FpLegendre(Fp, n) !== 1) + throw new Error("Cannot find square root"); + let M = S; + let c = Fp.mul(Fp.ONE, cc); + let t = Fp.pow(n, Q); + let R = Fp.pow(n, Q1div2); + while (!Fp.eql(t, Fp.ONE)) { + if (Fp.is0(t)) + return Fp.ZERO; + let i = 1; + let t_tmp = Fp.sqr(t); + while (!Fp.eql(t_tmp, Fp.ONE)) { + i++; + t_tmp = Fp.sqr(t_tmp); + if (i === M) + throw new Error("Cannot find square root"); + } + const exponent = _1n2 << BigInt(M - i - 1); + const b = Fp.pow(c, exponent); + M = i; + c = Fp.sqr(b); + t = Fp.mul(t, c); + R = Fp.mul(R, b); + } + return R; + }; + } + function FpSqrt(P) { + if (P % _4n === _3n) + return sqrt3mod4; + if (P % _8n === _5n) + return sqrt5mod8; + if (P % _16n === _9n) + return sqrt9mod16(P); + return tonelliShanks(P); + } + var FIELD_FIELDS = [ + "create", + "isValid", + "is0", + "neg", + "inv", + "sqrt", + "sqr", + "eql", + "add", + "sub", + "mul", + "pow", + "div", + "addN", + "subN", + "mulN", + "sqrN" + ]; + function validateField(field) { + const initial = { + ORDER: "bigint", + BYTES: "number", + BITS: "number" + }; + const opts = FIELD_FIELDS.reduce((map, val) => { + map[val] = "function"; + return map; + }, initial); + validateObject(field, opts); + return field; + } + function FpPow(Fp, num2, power) { + if (power < _0n2) + throw new Error("invalid exponent, negatives unsupported"); + if (power === _0n2) + return Fp.ONE; + if (power === _1n2) + return num2; + let p = Fp.ONE; + let d = num2; + while (power > _0n2) { + if (power & _1n2) + p = Fp.mul(p, d); + d = Fp.sqr(d); + power >>= _1n2; + } + return p; + } + function FpInvertBatch(Fp, nums, passZero = false) { + const inverted = new Array(nums.length).fill(passZero ? Fp.ZERO : void 0); + const multipliedAcc = nums.reduce((acc, num2, i) => { + if (Fp.is0(num2)) + return acc; + inverted[i] = acc; + return Fp.mul(acc, num2); + }, Fp.ONE); + const invertedAcc = Fp.inv(multipliedAcc); + nums.reduceRight((acc, num2, i) => { + if (Fp.is0(num2)) + return acc; + inverted[i] = Fp.mul(acc, inverted[i]); + return Fp.mul(acc, num2); + }, invertedAcc); + return inverted; + } + function FpLegendre(Fp, n) { + const p1mod2 = (Fp.ORDER - _1n2) / _2n; + const powered = Fp.pow(n, p1mod2); + const yes = Fp.eql(powered, Fp.ONE); + const zero = Fp.eql(powered, Fp.ZERO); + const no = Fp.eql(powered, Fp.neg(Fp.ONE)); + if (!yes && !zero && !no) + throw new Error("invalid Legendre symbol result"); + return yes ? 1 : zero ? 0 : -1; + } + function nLength(n, nBitLength) { + if (nBitLength !== void 0) + anumber(nBitLength); + const _nBitLength = nBitLength !== void 0 ? nBitLength : n.toString(2).length; + const nByteLength = Math.ceil(_nBitLength / 8); + return { nBitLength: _nBitLength, nByteLength }; + } + var _Field = class { + ORDER; + BITS; + BYTES; + isLE; + ZERO = _0n2; + ONE = _1n2; + _lengths; + _sqrt; + // cached sqrt + _mod; + constructor(ORDER, opts = {}) { + if (ORDER <= _0n2) + throw new Error("invalid field: expected ORDER > 0, got " + ORDER); + let _nbitLength = void 0; + this.isLE = false; + if (opts != null && typeof opts === "object") { + if (typeof opts.BITS === "number") + _nbitLength = opts.BITS; + if (typeof opts.sqrt === "function") + this.sqrt = opts.sqrt; + if (typeof opts.isLE === "boolean") + this.isLE = opts.isLE; + if (opts.allowedLengths) + this._lengths = opts.allowedLengths?.slice(); + if (typeof opts.modFromBytes === "boolean") + this._mod = opts.modFromBytes; + } + const { nBitLength, nByteLength } = nLength(ORDER, _nbitLength); + if (nByteLength > 2048) + throw new Error("invalid field: expected ORDER of <= 2048 bytes"); + this.ORDER = ORDER; + this.BITS = nBitLength; + this.BYTES = nByteLength; + this._sqrt = void 0; + Object.preventExtensions(this); + } + create(num2) { + return mod(num2, this.ORDER); + } + isValid(num2) { + if (typeof num2 !== "bigint") + throw new Error("invalid field element: expected bigint, got " + typeof num2); + return _0n2 <= num2 && num2 < this.ORDER; + } + is0(num2) { + return num2 === _0n2; + } + // is valid and invertible + isValidNot0(num2) { + return !this.is0(num2) && this.isValid(num2); + } + isOdd(num2) { + return (num2 & _1n2) === _1n2; + } + neg(num2) { + return mod(-num2, this.ORDER); + } + eql(lhs, rhs) { + return lhs === rhs; + } + sqr(num2) { + return mod(num2 * num2, this.ORDER); + } + add(lhs, rhs) { + return mod(lhs + rhs, this.ORDER); + } + sub(lhs, rhs) { + return mod(lhs - rhs, this.ORDER); + } + mul(lhs, rhs) { + return mod(lhs * rhs, this.ORDER); + } + pow(num2, power) { + return FpPow(this, num2, power); + } + div(lhs, rhs) { + return mod(lhs * invert(rhs, this.ORDER), this.ORDER); + } + // Same as above, but doesn't normalize + sqrN(num2) { + return num2 * num2; + } + addN(lhs, rhs) { + return lhs + rhs; + } + subN(lhs, rhs) { + return lhs - rhs; + } + mulN(lhs, rhs) { + return lhs * rhs; + } + inv(num2) { + return invert(num2, this.ORDER); + } + sqrt(num2) { + if (!this._sqrt) + this._sqrt = FpSqrt(this.ORDER); + return this._sqrt(this, num2); + } + toBytes(num2) { + return this.isLE ? numberToBytesLE(num2, this.BYTES) : numberToBytesBE(num2, this.BYTES); + } + fromBytes(bytes, skipValidation = false) { + abytes(bytes); + const { _lengths: allowedLengths, BYTES, isLE: isLE3, ORDER, _mod: modFromBytes } = this; + if (allowedLengths) { + if (!allowedLengths.includes(bytes.length) || bytes.length > BYTES) { + throw new Error("Field.fromBytes: expected " + allowedLengths + " bytes, got " + bytes.length); + } + const padded = new Uint8Array(BYTES); + padded.set(bytes, isLE3 ? 0 : padded.length - bytes.length); + bytes = padded; + } + if (bytes.length !== BYTES) + throw new Error("Field.fromBytes: expected " + BYTES + " bytes, got " + bytes.length); + let scalar = isLE3 ? bytesToNumberLE(bytes) : bytesToNumberBE(bytes); + if (modFromBytes) + scalar = mod(scalar, ORDER); + if (!skipValidation) { + if (!this.isValid(scalar)) + throw new Error("invalid field element: outside of range 0..ORDER"); + } + return scalar; + } + // TODO: we don't need it here, move out to separate fn + invertBatch(lst) { + return FpInvertBatch(this, lst); + } + // We can't move this out because Fp6, Fp12 implement it + // and it's unclear what to return in there. + cmov(a, b, condition) { + return condition ? b : a; + } + }; + function Field(ORDER, opts = {}) { + return new _Field(ORDER, opts); + } + function getFieldBytesLength(fieldOrder) { + if (typeof fieldOrder !== "bigint") + throw new Error("field order must be bigint"); + const bitLength = fieldOrder.toString(2).length; + return Math.ceil(bitLength / 8); + } + function getMinHashLength(fieldOrder) { + const length = getFieldBytesLength(fieldOrder); + return length + Math.ceil(length / 2); + } + function mapHashToField(key, fieldOrder, isLE3 = false) { + abytes(key); + const len = key.length; + const fieldLen = getFieldBytesLength(fieldOrder); + const minLen = getMinHashLength(fieldOrder); + if (len < 16 || len < minLen || len > 1024) + throw new Error("expected " + minLen + "-1024 bytes of input, got " + len); + const num2 = isLE3 ? bytesToNumberLE(key) : bytesToNumberBE(key); + const reduced = mod(num2, fieldOrder - _1n2) + _1n2; + return isLE3 ? numberToBytesLE(reduced, fieldLen) : numberToBytesBE(reduced, fieldLen); + } + + // node_modules/@noble/curves/abstract/curve.js + var _0n3 = /* @__PURE__ */ BigInt(0); + var _1n3 = /* @__PURE__ */ BigInt(1); + function negateCt(condition, item) { + const neg = item.negate(); + return condition ? neg : item; + } + function normalizeZ(c, points) { + const invertedZs = FpInvertBatch(c.Fp, points.map((p) => p.Z)); + return points.map((p, i) => c.fromAffine(p.toAffine(invertedZs[i]))); + } + function validateW(W, bits) { + if (!Number.isSafeInteger(W) || W <= 0 || W > bits) + throw new Error("invalid window size, expected [1.." + bits + "], got W=" + W); + } + function calcWOpts(W, scalarBits) { + validateW(W, scalarBits); + const windows = Math.ceil(scalarBits / W) + 1; + const windowSize = 2 ** (W - 1); + const maxNumber = 2 ** W; + const mask = bitMask(W); + const shiftBy = BigInt(W); + return { windows, windowSize, mask, maxNumber, shiftBy }; + } + function calcOffsets(n, window2, wOpts) { + const { windowSize, mask, maxNumber, shiftBy } = wOpts; + let wbits = Number(n & mask); + let nextN = n >> shiftBy; + if (wbits > windowSize) { + wbits -= maxNumber; + nextN += _1n3; + } + const offsetStart = window2 * windowSize; + const offset = offsetStart + Math.abs(wbits) - 1; + const isZero = wbits === 0; + const isNeg = wbits < 0; + const isNegF = window2 % 2 !== 0; + const offsetF = offsetStart; + return { nextN, offset, isZero, isNeg, isNegF, offsetF }; + } + var pointPrecomputes = /* @__PURE__ */ new WeakMap(); + var pointWindowSizes = /* @__PURE__ */ new WeakMap(); + function getW(P) { + return pointWindowSizes.get(P) || 1; + } + function assert0(n) { + if (n !== _0n3) + throw new Error("invalid wNAF"); + } + var wNAF = class { + BASE; + ZERO; + Fn; + bits; + // Parametrized with a given Point class (not individual point) + constructor(Point, bits) { + this.BASE = Point.BASE; + this.ZERO = Point.ZERO; + this.Fn = Point.Fn; + this.bits = bits; + } + // non-const time multiplication ladder + _unsafeLadder(elm, n, p = this.ZERO) { + let d = elm; + while (n > _0n3) { + if (n & _1n3) + p = p.add(d); + d = d.double(); + n >>= _1n3; + } + return p; + } + /** + * Creates a wNAF precomputation window. Used for caching. + * Default window size is set by `utils.precompute()` and is equal to 8. + * Number of precomputed points depends on the curve size: + * 2^(𝑊−1) * (Math.ceil(𝑛 / 𝑊) + 1), where: + * - 𝑊 is the window size + * - 𝑛 is the bitlength of the curve order. + * For a 256-bit curve and window size 8, the number of precomputed points is 128 * 33 = 4224. + * @param point Point instance + * @param W window size + * @returns precomputed point tables flattened to a single array + */ + precomputeWindow(point, W) { + const { windows, windowSize } = calcWOpts(W, this.bits); + const points = []; + let p = point; + let base = p; + for (let window2 = 0; window2 < windows; window2++) { + base = p; + points.push(base); + for (let i = 1; i < windowSize; i++) { + base = base.add(p); + points.push(base); + } + p = base.double(); + } + return points; + } + /** + * Implements ec multiplication using precomputed tables and w-ary non-adjacent form. + * More compact implementation: + * https://github.com/paulmillr/noble-secp256k1/blob/47cb1669b6e506ad66b35fe7d76132ae97465da2/index.ts#L502-L541 + * @returns real and fake (for const-time) points + */ + wNAF(W, precomputes, n) { + if (!this.Fn.isValid(n)) + throw new Error("invalid scalar"); + let p = this.ZERO; + let f = this.BASE; + const wo = calcWOpts(W, this.bits); + for (let window2 = 0; window2 < wo.windows; window2++) { + const { nextN, offset, isZero, isNeg, isNegF, offsetF } = calcOffsets(n, window2, wo); + n = nextN; + if (isZero) { + f = f.add(negateCt(isNegF, precomputes[offsetF])); + } else { + p = p.add(negateCt(isNeg, precomputes[offset])); + } + } + assert0(n); + return { p, f }; + } + /** + * Implements ec unsafe (non const-time) multiplication using precomputed tables and w-ary non-adjacent form. + * @param acc accumulator point to add result of multiplication + * @returns point + */ + wNAFUnsafe(W, precomputes, n, acc = this.ZERO) { + const wo = calcWOpts(W, this.bits); + for (let window2 = 0; window2 < wo.windows; window2++) { + if (n === _0n3) + break; + const { nextN, offset, isZero, isNeg } = calcOffsets(n, window2, wo); + n = nextN; + if (isZero) { + continue; + } else { + const item = precomputes[offset]; + acc = acc.add(isNeg ? item.negate() : item); + } + } + assert0(n); + return acc; + } + getPrecomputes(W, point, transform) { + let comp = pointPrecomputes.get(point); + if (!comp) { + comp = this.precomputeWindow(point, W); + if (W !== 1) { + if (typeof transform === "function") + comp = transform(comp); + pointPrecomputes.set(point, comp); + } + } + return comp; + } + cached(point, scalar, transform) { + const W = getW(point); + return this.wNAF(W, this.getPrecomputes(W, point, transform), scalar); + } + unsafe(point, scalar, transform, prev) { + const W = getW(point); + if (W === 1) + return this._unsafeLadder(point, scalar, prev); + return this.wNAFUnsafe(W, this.getPrecomputes(W, point, transform), scalar, prev); + } + // We calculate precomputes for elliptic curve point multiplication + // using windowed method. This specifies window size and + // stores precomputed values. Usually only base point would be precomputed. + createCache(P, W) { + validateW(W, this.bits); + pointWindowSizes.set(P, W); + pointPrecomputes.delete(P); + } + hasCache(elm) { + return getW(elm) !== 1; + } + }; + function mulEndoUnsafe(Point, point, k1, k2) { + let acc = point; + let p1 = Point.ZERO; + let p2 = Point.ZERO; + while (k1 > _0n3 || k2 > _0n3) { + if (k1 & _1n3) + p1 = p1.add(acc); + if (k2 & _1n3) + p2 = p2.add(acc); + acc = acc.double(); + k1 >>= _1n3; + k2 >>= _1n3; + } + return { p1, p2 }; + } + function createField(order, field, isLE3) { + if (field) { + if (field.ORDER !== order) + throw new Error("Field.ORDER must match order: Fp == p, Fn == n"); + validateField(field); + return field; + } else { + return Field(order, { isLE: isLE3 }); + } + } + function createCurveFields(type, CURVE, curveOpts = {}, FpFnLE) { + if (FpFnLE === void 0) + FpFnLE = type === "edwards"; + if (!CURVE || typeof CURVE !== "object") + throw new Error(`expected valid ${type} CURVE object`); + for (const p of ["p", "n", "h"]) { + const val = CURVE[p]; + if (!(typeof val === "bigint" && val > _0n3)) + throw new Error(`CURVE.${p} must be positive bigint`); + } + const Fp = createField(CURVE.p, curveOpts.Fp, FpFnLE); + const Fn = createField(CURVE.n, curveOpts.Fn, FpFnLE); + const _b = type === "weierstrass" ? "b" : "d"; + const params = ["Gx", "Gy", "a", _b]; + for (const p of params) { + if (!Fp.isValid(CURVE[p])) + throw new Error(`CURVE.${p} must be valid field element of CURVE.Fp`); + } + CURVE = Object.freeze(Object.assign({}, CURVE)); + return { CURVE, Fp, Fn }; + } + function createKeygen(randomSecretKey, getPublicKey2) { + return function keygen(seed) { + const secretKey = randomSecretKey(seed); + return { secretKey, publicKey: getPublicKey2(secretKey) }; + }; + } + + // node_modules/@noble/curves/abstract/weierstrass.js + init_process(); + + // node_modules/@noble/hashes/hmac.js + init_process(); + var _HMAC = class { + oHash; + iHash; + blockLen; + outputLen; + finished = false; + destroyed = false; + constructor(hash, key) { + ahash(hash); + abytes(key, void 0, "key"); + this.iHash = hash.create(); + if (typeof this.iHash.update !== "function") + throw new Error("Expected instance of class which extends utils.Hash"); + this.blockLen = this.iHash.blockLen; + this.outputLen = this.iHash.outputLen; + const blockLen = this.blockLen; + const pad2 = new Uint8Array(blockLen); + pad2.set(key.length > blockLen ? hash.create().update(key).digest() : key); + for (let i = 0; i < pad2.length; i++) + pad2[i] ^= 54; + this.iHash.update(pad2); + this.oHash = hash.create(); + for (let i = 0; i < pad2.length; i++) + pad2[i] ^= 54 ^ 92; + this.oHash.update(pad2); + clean(pad2); + } + update(buf) { + aexists(this); + this.iHash.update(buf); + return this; + } + digestInto(out) { + aexists(this); + abytes(out, this.outputLen, "output"); + this.finished = true; + this.iHash.digestInto(out); + this.oHash.update(out); + this.oHash.digestInto(out); + this.destroy(); + } + digest() { + const out = new Uint8Array(this.oHash.outputLen); + this.digestInto(out); + return out; + } + _cloneInto(to) { + to ||= Object.create(Object.getPrototypeOf(this), {}); + const { oHash, iHash, finished, destroyed, blockLen, outputLen } = this; + to = to; + to.finished = finished; + to.destroyed = destroyed; + to.blockLen = blockLen; + to.outputLen = outputLen; + to.oHash = oHash._cloneInto(to.oHash); + to.iHash = iHash._cloneInto(to.iHash); + return to; + } + clone() { + return this._cloneInto(); + } + destroy() { + this.destroyed = true; + this.oHash.destroy(); + this.iHash.destroy(); + } + }; + var hmac = (hash, key, message) => new _HMAC(hash, key).update(message).digest(); + hmac.create = (hash, key) => new _HMAC(hash, key); + + // node_modules/@noble/curves/abstract/weierstrass.js + var divNearest = (num2, den) => (num2 + (num2 >= 0 ? den : -den) / _2n2) / den; + function _splitEndoScalar(k, basis, n) { + const [[a1, b1], [a2, b2]] = basis; + const c1 = divNearest(b2 * k, n); + const c2 = divNearest(-b1 * k, n); + let k1 = k - c1 * a1 - c2 * a2; + let k2 = -c1 * b1 - c2 * b2; + const k1neg = k1 < _0n4; + const k2neg = k2 < _0n4; + if (k1neg) + k1 = -k1; + if (k2neg) + k2 = -k2; + const MAX_NUM = bitMask(Math.ceil(bitLen(n) / 2)) + _1n4; + if (k1 < _0n4 || k1 >= MAX_NUM || k2 < _0n4 || k2 >= MAX_NUM) { + throw new Error("splitScalar (endomorphism): failed, k=" + k); + } + return { k1neg, k1, k2neg, k2 }; + } + function validateSigFormat(format) { + if (!["compact", "recovered", "der"].includes(format)) + throw new Error('Signature format must be "compact", "recovered", or "der"'); + return format; + } + function validateSigOpts(opts, def) { + const optsn = {}; + for (let optName of Object.keys(def)) { + optsn[optName] = opts[optName] === void 0 ? def[optName] : opts[optName]; + } + abool(optsn.lowS, "lowS"); + abool(optsn.prehash, "prehash"); + if (optsn.format !== void 0) + validateSigFormat(optsn.format); + return optsn; + } + var DERErr = class extends Error { + constructor(m = "") { + super(m); + } + }; + var DER = { + // asn.1 DER encoding utils + Err: DERErr, + // Basic building block is TLV (Tag-Length-Value) + _tlv: { + encode: (tag, data) => { + const { Err: E } = DER; + if (tag < 0 || tag > 256) + throw new E("tlv.encode: wrong tag"); + if (data.length & 1) + throw new E("tlv.encode: unpadded data"); + const dataLen = data.length / 2; + const len = numberToHexUnpadded(dataLen); + if (len.length / 2 & 128) + throw new E("tlv.encode: long form length too big"); + const lenLen = dataLen > 127 ? numberToHexUnpadded(len.length / 2 | 128) : ""; + const t = numberToHexUnpadded(tag); + return t + lenLen + len + data; + }, + // v - value, l - left bytes (unparsed) + decode(tag, data) { + const { Err: E } = DER; + let pos = 0; + if (tag < 0 || tag > 256) + throw new E("tlv.encode: wrong tag"); + if (data.length < 2 || data[pos++] !== tag) + throw new E("tlv.decode: wrong tlv"); + const first = data[pos++]; + const isLong = !!(first & 128); + let length = 0; + if (!isLong) + length = first; + else { + const lenLen = first & 127; + if (!lenLen) + throw new E("tlv.decode(long): indefinite length not supported"); + if (lenLen > 4) + throw new E("tlv.decode(long): byte length is too big"); + const lengthBytes = data.subarray(pos, pos + lenLen); + if (lengthBytes.length !== lenLen) + throw new E("tlv.decode: length bytes not complete"); + if (lengthBytes[0] === 0) + throw new E("tlv.decode(long): zero leftmost byte"); + for (const b of lengthBytes) + length = length << 8 | b; + pos += lenLen; + if (length < 128) + throw new E("tlv.decode(long): not minimal encoding"); + } + const v = data.subarray(pos, pos + length); + if (v.length !== length) + throw new E("tlv.decode: wrong value length"); + return { v, l: data.subarray(pos + length) }; + } + }, + // https://crypto.stackexchange.com/a/57734 Leftmost bit of first byte is 'negative' flag, + // since we always use positive integers here. It must always be empty: + // - add zero byte if exists + // - if next byte doesn't have a flag, leading zero is not allowed (minimal encoding) + _int: { + encode(num2) { + const { Err: E } = DER; + if (num2 < _0n4) + throw new E("integer: negative integers are not allowed"); + let hex = numberToHexUnpadded(num2); + if (Number.parseInt(hex[0], 16) & 8) + hex = "00" + hex; + if (hex.length & 1) + throw new E("unexpected DER parsing assertion: unpadded hex"); + return hex; + }, + decode(data) { + const { Err: E } = DER; + if (data[0] & 128) + throw new E("invalid signature integer: negative"); + if (data[0] === 0 && !(data[1] & 128)) + throw new E("invalid signature integer: unnecessary leading zero"); + return bytesToNumberBE(data); + } + }, + toSig(bytes) { + const { Err: E, _int: int, _tlv: tlv } = DER; + const data = abytes(bytes, void 0, "signature"); + const { v: seqBytes, l: seqLeftBytes } = tlv.decode(48, data); + if (seqLeftBytes.length) + throw new E("invalid signature: left bytes after parsing"); + const { v: rBytes, l: rLeftBytes } = tlv.decode(2, seqBytes); + const { v: sBytes, l: sLeftBytes } = tlv.decode(2, rLeftBytes); + if (sLeftBytes.length) + throw new E("invalid signature: left bytes after parsing"); + return { r: int.decode(rBytes), s: int.decode(sBytes) }; + }, + hexFromSig(sig) { + const { _tlv: tlv, _int: int } = DER; + const rs = tlv.encode(2, int.encode(sig.r)); + const ss = tlv.encode(2, int.encode(sig.s)); + const seq = rs + ss; + return tlv.encode(48, seq); + } + }; + var _0n4 = BigInt(0); + var _1n4 = BigInt(1); + var _2n2 = BigInt(2); + var _3n2 = BigInt(3); + var _4n2 = BigInt(4); + function weierstrass(params, extraOpts = {}) { + const validated = createCurveFields("weierstrass", params, extraOpts); + const { Fp, Fn } = validated; + let CURVE = validated.CURVE; + const { h: cofactor, n: CURVE_ORDER } = CURVE; + validateObject(extraOpts, {}, { + allowInfinityPoint: "boolean", + clearCofactor: "function", + isTorsionFree: "function", + fromBytes: "function", + toBytes: "function", + endo: "object" + }); + const { endo } = extraOpts; + if (endo) { + if (!Fp.is0(CURVE.a) || typeof endo.beta !== "bigint" || !Array.isArray(endo.basises)) { + throw new Error('invalid endo: expected "beta": bigint and "basises": array'); + } + } + const lengths = getWLengths(Fp, Fn); + function assertCompressionIsSupported() { + if (!Fp.isOdd) + throw new Error("compression is not supported: Field does not have .isOdd()"); + } + function pointToBytes2(_c, point, isCompressed) { + const { x, y } = point.toAffine(); + const bx = Fp.toBytes(x); + abool(isCompressed, "isCompressed"); + if (isCompressed) { + assertCompressionIsSupported(); + const hasEvenY = !Fp.isOdd(y); + return concatBytes(pprefix(hasEvenY), bx); + } else { + return concatBytes(Uint8Array.of(4), bx, Fp.toBytes(y)); + } + } + function pointFromBytes(bytes) { + abytes(bytes, void 0, "Point"); + const { publicKey: comp, publicKeyUncompressed: uncomp } = lengths; + const length = bytes.length; + const head = bytes[0]; + const tail = bytes.subarray(1); + if (length === comp && (head === 2 || head === 3)) { + const x = Fp.fromBytes(tail); + if (!Fp.isValid(x)) + throw new Error("bad point: is not on curve, wrong x"); + const y2 = weierstrassEquation(x); + let y; + try { + y = Fp.sqrt(y2); + } catch (sqrtError) { + const err = sqrtError instanceof Error ? ": " + sqrtError.message : ""; + throw new Error("bad point: is not on curve, sqrt error" + err); + } + assertCompressionIsSupported(); + const evenY = Fp.isOdd(y); + const evenH = (head & 1) === 1; + if (evenH !== evenY) + y = Fp.neg(y); + return { x, y }; + } else if (length === uncomp && head === 4) { + const L = Fp.BYTES; + const x = Fp.fromBytes(tail.subarray(0, L)); + const y = Fp.fromBytes(tail.subarray(L, L * 2)); + if (!isValidXY(x, y)) + throw new Error("bad point: is not on curve"); + return { x, y }; + } else { + throw new Error(`bad point: got length ${length}, expected compressed=${comp} or uncompressed=${uncomp}`); + } + } + const encodePoint = extraOpts.toBytes || pointToBytes2; + const decodePoint = extraOpts.fromBytes || pointFromBytes; + function weierstrassEquation(x) { + const x2 = Fp.sqr(x); + const x3 = Fp.mul(x2, x); + return Fp.add(Fp.add(x3, Fp.mul(x, CURVE.a)), CURVE.b); + } + function isValidXY(x, y) { + const left = Fp.sqr(y); + const right = weierstrassEquation(x); + return Fp.eql(left, right); + } + if (!isValidXY(CURVE.Gx, CURVE.Gy)) + throw new Error("bad curve params: generator point"); + const _4a3 = Fp.mul(Fp.pow(CURVE.a, _3n2), _4n2); + const _27b2 = Fp.mul(Fp.sqr(CURVE.b), BigInt(27)); + if (Fp.is0(Fp.add(_4a3, _27b2))) + throw new Error("bad curve params: a or b"); + function acoord(title, n, banZero = false) { + if (!Fp.isValid(n) || banZero && Fp.is0(n)) + throw new Error(`bad point coordinate ${title}`); + return n; + } + function aprjpoint(other) { + if (!(other instanceof Point)) + throw new Error("Weierstrass Point expected"); + } + function splitEndoScalarN(k) { + if (!endo || !endo.basises) + throw new Error("no endo"); + return _splitEndoScalar(k, endo.basises, Fn.ORDER); + } + const toAffineMemo = memoized((p, iz) => { + const { X, Y, Z } = p; + if (Fp.eql(Z, Fp.ONE)) + return { x: X, y: Y }; + const is0 = p.is0(); + if (iz == null) + iz = is0 ? Fp.ONE : Fp.inv(Z); + const x = Fp.mul(X, iz); + const y = Fp.mul(Y, iz); + const zz = Fp.mul(Z, iz); + if (is0) + return { x: Fp.ZERO, y: Fp.ZERO }; + if (!Fp.eql(zz, Fp.ONE)) + throw new Error("invZ was invalid"); + return { x, y }; + }); + const assertValidMemo = memoized((p) => { + if (p.is0()) { + if (extraOpts.allowInfinityPoint && !Fp.is0(p.Y)) + return; + throw new Error("bad point: ZERO"); + } + const { x, y } = p.toAffine(); + if (!Fp.isValid(x) || !Fp.isValid(y)) + throw new Error("bad point: x or y not field elements"); + if (!isValidXY(x, y)) + throw new Error("bad point: equation left != right"); + if (!p.isTorsionFree()) + throw new Error("bad point: not in prime-order subgroup"); + return true; + }); + function finishEndo(endoBeta, k1p, k2p, k1neg, k2neg) { + k2p = new Point(Fp.mul(k2p.X, endoBeta), k2p.Y, k2p.Z); + k1p = negateCt(k1neg, k1p); + k2p = negateCt(k2neg, k2p); + return k1p.add(k2p); + } + class Point { + // base / generator point + static BASE = new Point(CURVE.Gx, CURVE.Gy, Fp.ONE); + // zero / infinity / identity point + static ZERO = new Point(Fp.ZERO, Fp.ONE, Fp.ZERO); + // 0, 1, 0 + // math field + static Fp = Fp; + // scalar field + static Fn = Fn; + X; + Y; + Z; + /** Does NOT validate if the point is valid. Use `.assertValidity()`. */ + constructor(X, Y, Z) { + this.X = acoord("x", X); + this.Y = acoord("y", Y, true); + this.Z = acoord("z", Z); + Object.freeze(this); + } + static CURVE() { + return CURVE; + } + /** Does NOT validate if the point is valid. Use `.assertValidity()`. */ + static fromAffine(p) { + const { x, y } = p || {}; + if (!p || !Fp.isValid(x) || !Fp.isValid(y)) + throw new Error("invalid affine point"); + if (p instanceof Point) + throw new Error("projective point not allowed"); + if (Fp.is0(x) && Fp.is0(y)) + return Point.ZERO; + return new Point(x, y, Fp.ONE); + } + static fromBytes(bytes) { + const P = Point.fromAffine(decodePoint(abytes(bytes, void 0, "point"))); + P.assertValidity(); + return P; + } + static fromHex(hex) { + return Point.fromBytes(hexToBytes(hex)); + } + get x() { + return this.toAffine().x; + } + get y() { + return this.toAffine().y; + } + /** + * + * @param windowSize + * @param isLazy true will defer table computation until the first multiplication + * @returns + */ + precompute(windowSize = 8, isLazy = true) { + wnaf.createCache(this, windowSize); + if (!isLazy) + this.multiply(_3n2); + return this; + } + // TODO: return `this` + /** A point on curve is valid if it conforms to equation. */ + assertValidity() { + assertValidMemo(this); + } + hasEvenY() { + const { y } = this.toAffine(); + if (!Fp.isOdd) + throw new Error("Field doesn't support isOdd"); + return !Fp.isOdd(y); + } + /** Compare one point to another. */ + equals(other) { + aprjpoint(other); + const { X: X1, Y: Y1, Z: Z1 } = this; + const { X: X2, Y: Y2, Z: Z2 } = other; + const U1 = Fp.eql(Fp.mul(X1, Z2), Fp.mul(X2, Z1)); + const U2 = Fp.eql(Fp.mul(Y1, Z2), Fp.mul(Y2, Z1)); + return U1 && U2; + } + /** Flips point to one corresponding to (x, -y) in Affine coordinates. */ + negate() { + return new Point(this.X, Fp.neg(this.Y), this.Z); + } + // Renes-Costello-Batina exception-free doubling formula. + // There is 30% faster Jacobian formula, but it is not complete. + // https://eprint.iacr.org/2015/1060, algorithm 3 + // Cost: 8M + 3S + 3*a + 2*b3 + 15add. + double() { + const { a, b } = CURVE; + const b3 = Fp.mul(b, _3n2); + const { X: X1, Y: Y1, Z: Z1 } = this; + let X3 = Fp.ZERO, Y3 = Fp.ZERO, Z3 = Fp.ZERO; + let t0 = Fp.mul(X1, X1); + let t1 = Fp.mul(Y1, Y1); + let t2 = Fp.mul(Z1, Z1); + let t3 = Fp.mul(X1, Y1); + t3 = Fp.add(t3, t3); + Z3 = Fp.mul(X1, Z1); + Z3 = Fp.add(Z3, Z3); + X3 = Fp.mul(a, Z3); + Y3 = Fp.mul(b3, t2); + Y3 = Fp.add(X3, Y3); + X3 = Fp.sub(t1, Y3); + Y3 = Fp.add(t1, Y3); + Y3 = Fp.mul(X3, Y3); + X3 = Fp.mul(t3, X3); + Z3 = Fp.mul(b3, Z3); + t2 = Fp.mul(a, t2); + t3 = Fp.sub(t0, t2); + t3 = Fp.mul(a, t3); + t3 = Fp.add(t3, Z3); + Z3 = Fp.add(t0, t0); + t0 = Fp.add(Z3, t0); + t0 = Fp.add(t0, t2); + t0 = Fp.mul(t0, t3); + Y3 = Fp.add(Y3, t0); + t2 = Fp.mul(Y1, Z1); + t2 = Fp.add(t2, t2); + t0 = Fp.mul(t2, t3); + X3 = Fp.sub(X3, t0); + Z3 = Fp.mul(t2, t1); + Z3 = Fp.add(Z3, Z3); + Z3 = Fp.add(Z3, Z3); + return new Point(X3, Y3, Z3); + } + // Renes-Costello-Batina exception-free addition formula. + // There is 30% faster Jacobian formula, but it is not complete. + // https://eprint.iacr.org/2015/1060, algorithm 1 + // Cost: 12M + 0S + 3*a + 3*b3 + 23add. + add(other) { + aprjpoint(other); + const { X: X1, Y: Y1, Z: Z1 } = this; + const { X: X2, Y: Y2, Z: Z2 } = other; + let X3 = Fp.ZERO, Y3 = Fp.ZERO, Z3 = Fp.ZERO; + const a = CURVE.a; + const b3 = Fp.mul(CURVE.b, _3n2); + let t0 = Fp.mul(X1, X2); + let t1 = Fp.mul(Y1, Y2); + let t2 = Fp.mul(Z1, Z2); + let t3 = Fp.add(X1, Y1); + let t4 = Fp.add(X2, Y2); + t3 = Fp.mul(t3, t4); + t4 = Fp.add(t0, t1); + t3 = Fp.sub(t3, t4); + t4 = Fp.add(X1, Z1); + let t5 = Fp.add(X2, Z2); + t4 = Fp.mul(t4, t5); + t5 = Fp.add(t0, t2); + t4 = Fp.sub(t4, t5); + t5 = Fp.add(Y1, Z1); + X3 = Fp.add(Y2, Z2); + t5 = Fp.mul(t5, X3); + X3 = Fp.add(t1, t2); + t5 = Fp.sub(t5, X3); + Z3 = Fp.mul(a, t4); + X3 = Fp.mul(b3, t2); + Z3 = Fp.add(X3, Z3); + X3 = Fp.sub(t1, Z3); + Z3 = Fp.add(t1, Z3); + Y3 = Fp.mul(X3, Z3); + t1 = Fp.add(t0, t0); + t1 = Fp.add(t1, t0); + t2 = Fp.mul(a, t2); + t4 = Fp.mul(b3, t4); + t1 = Fp.add(t1, t2); + t2 = Fp.sub(t0, t2); + t2 = Fp.mul(a, t2); + t4 = Fp.add(t4, t2); + t0 = Fp.mul(t1, t4); + Y3 = Fp.add(Y3, t0); + t0 = Fp.mul(t5, t4); + X3 = Fp.mul(t3, X3); + X3 = Fp.sub(X3, t0); + t0 = Fp.mul(t3, t1); + Z3 = Fp.mul(t5, Z3); + Z3 = Fp.add(Z3, t0); + return new Point(X3, Y3, Z3); + } + subtract(other) { + return this.add(other.negate()); + } + is0() { + return this.equals(Point.ZERO); + } + /** + * Constant time multiplication. + * Uses wNAF method. Windowed method may be 10% faster, + * but takes 2x longer to generate and consumes 2x memory. + * Uses precomputes when available. + * Uses endomorphism for Koblitz curves. + * @param scalar by which the point would be multiplied + * @returns New point + */ + multiply(scalar) { + const { endo: endo2 } = extraOpts; + if (!Fn.isValidNot0(scalar)) + throw new Error("invalid scalar: out of range"); + let point, fake; + const mul = (n) => wnaf.cached(this, n, (p) => normalizeZ(Point, p)); + if (endo2) { + const { k1neg, k1, k2neg, k2 } = splitEndoScalarN(scalar); + const { p: k1p, f: k1f } = mul(k1); + const { p: k2p, f: k2f } = mul(k2); + fake = k1f.add(k2f); + point = finishEndo(endo2.beta, k1p, k2p, k1neg, k2neg); + } else { + const { p, f } = mul(scalar); + point = p; + fake = f; + } + return normalizeZ(Point, [point, fake])[0]; + } + /** + * Non-constant-time multiplication. Uses double-and-add algorithm. + * It's faster, but should only be used when you don't care about + * an exposed secret key e.g. sig verification, which works over *public* keys. + */ + multiplyUnsafe(sc) { + const { endo: endo2 } = extraOpts; + const p = this; + if (!Fn.isValid(sc)) + throw new Error("invalid scalar: out of range"); + if (sc === _0n4 || p.is0()) + return Point.ZERO; + if (sc === _1n4) + return p; + if (wnaf.hasCache(this)) + return this.multiply(sc); + if (endo2) { + const { k1neg, k1, k2neg, k2 } = splitEndoScalarN(sc); + const { p1, p2 } = mulEndoUnsafe(Point, p, k1, k2); + return finishEndo(endo2.beta, p1, p2, k1neg, k2neg); + } else { + return wnaf.unsafe(p, sc); + } + } + /** + * Converts Projective point to affine (x, y) coordinates. + * @param invertedZ Z^-1 (inverted zero) - optional, precomputation is useful for invertBatch + */ + toAffine(invertedZ) { + return toAffineMemo(this, invertedZ); + } + /** + * Checks whether Point is free of torsion elements (is in prime subgroup). + * Always torsion-free for cofactor=1 curves. + */ + isTorsionFree() { + const { isTorsionFree } = extraOpts; + if (cofactor === _1n4) + return true; + if (isTorsionFree) + return isTorsionFree(Point, this); + return wnaf.unsafe(this, CURVE_ORDER).is0(); + } + clearCofactor() { + const { clearCofactor } = extraOpts; + if (cofactor === _1n4) + return this; + if (clearCofactor) + return clearCofactor(Point, this); + return this.multiplyUnsafe(cofactor); + } + isSmallOrder() { + return this.multiplyUnsafe(cofactor).is0(); + } + toBytes(isCompressed = true) { + abool(isCompressed, "isCompressed"); + this.assertValidity(); + return encodePoint(Point, this, isCompressed); + } + toHex(isCompressed = true) { + return bytesToHex(this.toBytes(isCompressed)); + } + toString() { + return ``; + } + } + const bits = Fn.BITS; + const wnaf = new wNAF(Point, extraOpts.endo ? Math.ceil(bits / 2) : bits); + Point.BASE.precompute(8); + return Point; + } + function pprefix(hasEvenY) { + return Uint8Array.of(hasEvenY ? 2 : 3); + } + function getWLengths(Fp, Fn) { + return { + secretKey: Fn.BYTES, + publicKey: 1 + Fp.BYTES, + publicKeyUncompressed: 1 + 2 * Fp.BYTES, + publicKeyHasPrefix: true, + signature: 2 * Fn.BYTES + }; + } + function ecdh(Point, ecdhOpts = {}) { + const { Fn } = Point; + const randomBytes_ = ecdhOpts.randomBytes || randomBytes; + const lengths = Object.assign(getWLengths(Point.Fp, Fn), { seed: getMinHashLength(Fn.ORDER) }); + function isValidSecretKey(secretKey) { + try { + const num2 = Fn.fromBytes(secretKey); + return Fn.isValidNot0(num2); + } catch (error) { + return false; + } + } + function isValidPublicKey(publicKey, isCompressed) { + const { publicKey: comp, publicKeyUncompressed } = lengths; + try { + const l = publicKey.length; + if (isCompressed === true && l !== comp) + return false; + if (isCompressed === false && l !== publicKeyUncompressed) + return false; + return !!Point.fromBytes(publicKey); + } catch (error) { + return false; + } + } + function randomSecretKey(seed = randomBytes_(lengths.seed)) { + return mapHashToField(abytes(seed, lengths.seed, "seed"), Fn.ORDER); + } + function getPublicKey2(secretKey, isCompressed = true) { + return Point.BASE.multiply(Fn.fromBytes(secretKey)).toBytes(isCompressed); + } + function isProbPub(item) { + const { secretKey, publicKey, publicKeyUncompressed } = lengths; + if (!isBytes(item)) + return void 0; + if ("_lengths" in Fn && Fn._lengths || secretKey === publicKey) + return void 0; + const l = abytes(item, void 0, "key").length; + return l === publicKey || l === publicKeyUncompressed; + } + function getSharedSecret(secretKeyA, publicKeyB, isCompressed = true) { + if (isProbPub(secretKeyA) === true) + throw new Error("first arg must be private key"); + if (isProbPub(publicKeyB) === false) + throw new Error("second arg must be public key"); + const s = Fn.fromBytes(secretKeyA); + const b = Point.fromBytes(publicKeyB); + return b.multiply(s).toBytes(isCompressed); + } + const utils2 = { + isValidSecretKey, + isValidPublicKey, + randomSecretKey + }; + const keygen = createKeygen(randomSecretKey, getPublicKey2); + return Object.freeze({ getPublicKey: getPublicKey2, getSharedSecret, keygen, Point, utils: utils2, lengths }); + } + function ecdsa(Point, hash, ecdsaOpts = {}) { + ahash(hash); + validateObject(ecdsaOpts, {}, { + hmac: "function", + lowS: "boolean", + randomBytes: "function", + bits2int: "function", + bits2int_modN: "function" + }); + ecdsaOpts = Object.assign({}, ecdsaOpts); + const randomBytes3 = ecdsaOpts.randomBytes || randomBytes; + const hmac2 = ecdsaOpts.hmac || ((key, msg) => hmac(hash, key, msg)); + const { Fp, Fn } = Point; + const { ORDER: CURVE_ORDER, BITS: fnBits } = Fn; + const { keygen, getPublicKey: getPublicKey2, getSharedSecret, utils: utils2, lengths } = ecdh(Point, ecdsaOpts); + const defaultSigOpts = { + prehash: true, + lowS: typeof ecdsaOpts.lowS === "boolean" ? ecdsaOpts.lowS : true, + format: "compact", + extraEntropy: false + }; + const hasLargeCofactor = CURVE_ORDER * _2n2 < Fp.ORDER; + function isBiggerThanHalfOrder(number) { + const HALF = CURVE_ORDER >> _1n4; + return number > HALF; + } + function validateRS(title, num2) { + if (!Fn.isValidNot0(num2)) + throw new Error(`invalid signature ${title}: out of range 1..Point.Fn.ORDER`); + return num2; + } + function assertSmallCofactor() { + if (hasLargeCofactor) + throw new Error('"recovered" sig type is not supported for cofactor >2 curves'); + } + function validateSigLength(bytes, format) { + validateSigFormat(format); + const size = lengths.signature; + const sizer = format === "compact" ? size : format === "recovered" ? size + 1 : void 0; + return abytes(bytes, sizer); + } + class Signature { + r; + s; + recovery; + constructor(r, s, recovery) { + this.r = validateRS("r", r); + this.s = validateRS("s", s); + if (recovery != null) { + assertSmallCofactor(); + if (![0, 1, 2, 3].includes(recovery)) + throw new Error("invalid recovery id"); + this.recovery = recovery; + } + Object.freeze(this); + } + static fromBytes(bytes, format = defaultSigOpts.format) { + validateSigLength(bytes, format); + let recid; + if (format === "der") { + const { r: r2, s: s2 } = DER.toSig(abytes(bytes)); + return new Signature(r2, s2); + } + if (format === "recovered") { + recid = bytes[0]; + format = "compact"; + bytes = bytes.subarray(1); + } + const L = lengths.signature / 2; + const r = bytes.subarray(0, L); + const s = bytes.subarray(L, L * 2); + return new Signature(Fn.fromBytes(r), Fn.fromBytes(s), recid); + } + static fromHex(hex, format) { + return this.fromBytes(hexToBytes(hex), format); + } + assertRecovery() { + const { recovery } = this; + if (recovery == null) + throw new Error("invalid recovery id: must be present"); + return recovery; + } + addRecoveryBit(recovery) { + return new Signature(this.r, this.s, recovery); + } + recoverPublicKey(messageHash) { + const { r, s } = this; + const recovery = this.assertRecovery(); + const radj = recovery === 2 || recovery === 3 ? r + CURVE_ORDER : r; + if (!Fp.isValid(radj)) + throw new Error("invalid recovery id: sig.r+curve.n != R.x"); + const x = Fp.toBytes(radj); + const R = Point.fromBytes(concatBytes(pprefix((recovery & 1) === 0), x)); + const ir = Fn.inv(radj); + const h = bits2int_modN(abytes(messageHash, void 0, "msgHash")); + const u1 = Fn.create(-h * ir); + const u2 = Fn.create(s * ir); + const Q = Point.BASE.multiplyUnsafe(u1).add(R.multiplyUnsafe(u2)); + if (Q.is0()) + throw new Error("invalid recovery: point at infinify"); + Q.assertValidity(); + return Q; + } + // Signatures should be low-s, to prevent malleability. + hasHighS() { + return isBiggerThanHalfOrder(this.s); + } + toBytes(format = defaultSigOpts.format) { + validateSigFormat(format); + if (format === "der") + return hexToBytes(DER.hexFromSig(this)); + const { r, s } = this; + const rb = Fn.toBytes(r); + const sb = Fn.toBytes(s); + if (format === "recovered") { + assertSmallCofactor(); + return concatBytes(Uint8Array.of(this.assertRecovery()), rb, sb); + } + return concatBytes(rb, sb); + } + toHex(format) { + return bytesToHex(this.toBytes(format)); + } + } + const bits2int = ecdsaOpts.bits2int || function bits2int_def(bytes) { + if (bytes.length > 8192) + throw new Error("input is too large"); + const num2 = bytesToNumberBE(bytes); + const delta = bytes.length * 8 - fnBits; + return delta > 0 ? num2 >> BigInt(delta) : num2; + }; + const bits2int_modN = ecdsaOpts.bits2int_modN || function bits2int_modN_def(bytes) { + return Fn.create(bits2int(bytes)); + }; + const ORDER_MASK = bitMask(fnBits); + function int2octets(num2) { + aInRange("num < 2^" + fnBits, num2, _0n4, ORDER_MASK); + return Fn.toBytes(num2); + } + function validateMsgAndHash(message, prehash) { + abytes(message, void 0, "message"); + return prehash ? abytes(hash(message), void 0, "prehashed message") : message; + } + function prepSig(message, secretKey, opts) { + const { lowS, prehash, extraEntropy } = validateSigOpts(opts, defaultSigOpts); + message = validateMsgAndHash(message, prehash); + const h1int = bits2int_modN(message); + const d = Fn.fromBytes(secretKey); + if (!Fn.isValidNot0(d)) + throw new Error("invalid private key"); + const seedArgs = [int2octets(d), int2octets(h1int)]; + if (extraEntropy != null && extraEntropy !== false) { + const e = extraEntropy === true ? randomBytes3(lengths.secretKey) : extraEntropy; + seedArgs.push(abytes(e, void 0, "extraEntropy")); + } + const seed = concatBytes(...seedArgs); + const m = h1int; + function k2sig(kBytes) { + const k = bits2int(kBytes); + if (!Fn.isValidNot0(k)) + return; + const ik = Fn.inv(k); + const q = Point.BASE.multiply(k).toAffine(); + const r = Fn.create(q.x); + if (r === _0n4) + return; + const s = Fn.create(ik * Fn.create(m + r * d)); + if (s === _0n4) + return; + let recovery = (q.x === r ? 0 : 2) | Number(q.y & _1n4); + let normS = s; + if (lowS && isBiggerThanHalfOrder(s)) { + normS = Fn.neg(s); + recovery ^= 1; + } + return new Signature(r, normS, hasLargeCofactor ? void 0 : recovery); + } + return { seed, k2sig }; + } + function sign(message, secretKey, opts = {}) { + const { seed, k2sig } = prepSig(message, secretKey, opts); + const drbg = createHmacDrbg(hash.outputLen, Fn.BYTES, hmac2); + const sig = drbg(seed, k2sig); + return sig.toBytes(opts.format); + } + function verify(signature, message, publicKey, opts = {}) { + const { lowS, prehash, format } = validateSigOpts(opts, defaultSigOpts); + publicKey = abytes(publicKey, void 0, "publicKey"); + message = validateMsgAndHash(message, prehash); + if (!isBytes(signature)) { + const end = signature instanceof Signature ? ", use sig.toBytes()" : ""; + throw new Error("verify expects Uint8Array signature" + end); + } + validateSigLength(signature, format); + try { + const sig = Signature.fromBytes(signature, format); + const P = Point.fromBytes(publicKey); + if (lowS && sig.hasHighS()) + return false; + const { r, s } = sig; + const h = bits2int_modN(message); + const is = Fn.inv(s); + const u1 = Fn.create(h * is); + const u2 = Fn.create(r * is); + const R = Point.BASE.multiplyUnsafe(u1).add(P.multiplyUnsafe(u2)); + if (R.is0()) + return false; + const v = Fn.create(R.x); + return v === r; + } catch (e) { + return false; + } + } + function recoverPublicKey(signature, message, opts = {}) { + const { prehash } = validateSigOpts(opts, defaultSigOpts); + message = validateMsgAndHash(message, prehash); + return Signature.fromBytes(signature, "recovered").recoverPublicKey(message).toBytes(); + } + return Object.freeze({ + keygen, + getPublicKey: getPublicKey2, + getSharedSecret, + utils: utils2, + lengths, + Point, + sign, + verify, + recoverPublicKey, + Signature, + hash + }); + } + + // node_modules/@noble/curves/secp256k1.js + var secp256k1_CURVE = { + p: BigInt("0xfffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2f"), + n: BigInt("0xfffffffffffffffffffffffffffffffebaaedce6af48a03bbfd25e8cd0364141"), + h: BigInt(1), + a: BigInt(0), + b: BigInt(7), + Gx: BigInt("0x79be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798"), + Gy: BigInt("0x483ada7726a3c4655da4fbfc0e1108a8fd17b448a68554199c47d08ffb10d4b8") + }; + var secp256k1_ENDO = { + beta: BigInt("0x7ae96a2b657c07106e64479eac3434e99cf0497512f58995c1396c28719501ee"), + basises: [ + [BigInt("0x3086d221a7d46bcde86c90e49284eb15"), -BigInt("0xe4437ed6010e88286f547fa90abfe4c3")], + [BigInt("0x114ca50f7a8e2f3f657c1108d9d44cfd8"), BigInt("0x3086d221a7d46bcde86c90e49284eb15")] + ] + }; + var _0n5 = /* @__PURE__ */ BigInt(0); + var _2n3 = /* @__PURE__ */ BigInt(2); + function sqrtMod(y) { + const P = secp256k1_CURVE.p; + const _3n3 = BigInt(3), _6n = BigInt(6), _11n = BigInt(11), _22n = BigInt(22); + const _23n = BigInt(23), _44n = BigInt(44), _88n = BigInt(88); + const b2 = y * y * y % P; + const b3 = b2 * b2 * y % P; + const b6 = pow2(b3, _3n3, P) * b3 % P; + const b9 = pow2(b6, _3n3, P) * b3 % P; + const b11 = pow2(b9, _2n3, P) * b2 % P; + const b22 = pow2(b11, _11n, P) * b11 % P; + const b44 = pow2(b22, _22n, P) * b22 % P; + const b88 = pow2(b44, _44n, P) * b44 % P; + const b176 = pow2(b88, _88n, P) * b88 % P; + const b220 = pow2(b176, _44n, P) * b44 % P; + const b223 = pow2(b220, _3n3, P) * b3 % P; + const t1 = pow2(b223, _23n, P) * b22 % P; + const t2 = pow2(t1, _6n, P) * b2 % P; + const root = pow2(t2, _2n3, P); + if (!Fpk1.eql(Fpk1.sqr(root), y)) + throw new Error("Cannot find square root"); + return root; + } + var Fpk1 = Field(secp256k1_CURVE.p, { sqrt: sqrtMod }); + var Pointk1 = /* @__PURE__ */ weierstrass(secp256k1_CURVE, { + Fp: Fpk1, + endo: secp256k1_ENDO + }); + var secp256k1 = /* @__PURE__ */ ecdsa(Pointk1, sha256); + var TAGGED_HASH_PREFIXES = {}; + function taggedHash(tag, ...messages) { + let tagP = TAGGED_HASH_PREFIXES[tag]; + if (tagP === void 0) { + const tagH = sha256(asciiToBytes(tag)); + tagP = concatBytes(tagH, tagH); + TAGGED_HASH_PREFIXES[tag] = tagP; + } + return sha256(concatBytes(tagP, ...messages)); + } + var pointToBytes = (point) => point.toBytes(true).slice(1); + var hasEven = (y) => y % _2n3 === _0n5; + function schnorrGetExtPubKey(priv) { + const { Fn, BASE } = Pointk1; + const d_ = Fn.fromBytes(priv); + const p = BASE.multiply(d_); + const scalar = hasEven(p.y) ? d_ : Fn.neg(d_); + return { scalar, bytes: pointToBytes(p) }; + } + function lift_x(x) { + const Fp = Fpk1; + if (!Fp.isValidNot0(x)) + throw new Error("invalid x: Fail if x \u2265 p"); + const xx = Fp.create(x * x); + const c = Fp.create(xx * x + BigInt(7)); + let y = Fp.sqrt(c); + if (!hasEven(y)) + y = Fp.neg(y); + const p = Pointk1.fromAffine({ x, y }); + p.assertValidity(); + return p; + } + var num = bytesToNumberBE; + function challenge(...args) { + return Pointk1.Fn.create(num(taggedHash("BIP0340/challenge", ...args))); + } + function schnorrGetPublicKey(secretKey) { + return schnorrGetExtPubKey(secretKey).bytes; + } + function schnorrSign(message, secretKey, auxRand = randomBytes(32)) { + const { Fn } = Pointk1; + const m = abytes(message, void 0, "message"); + const { bytes: px, scalar: d } = schnorrGetExtPubKey(secretKey); + const a = abytes(auxRand, 32, "auxRand"); + const t = Fn.toBytes(d ^ num(taggedHash("BIP0340/aux", a))); + const rand = taggedHash("BIP0340/nonce", t, px, m); + const { bytes: rx, scalar: k } = schnorrGetExtPubKey(rand); + const e = challenge(rx, px, m); + const sig = new Uint8Array(64); + sig.set(rx, 0); + sig.set(Fn.toBytes(Fn.create(k + e * d)), 32); + if (!schnorrVerify(sig, m, px)) + throw new Error("sign: Invalid signature produced"); + return sig; + } + function schnorrVerify(signature, message, publicKey) { + const { Fp, Fn, BASE } = Pointk1; + const sig = abytes(signature, 64, "signature"); + const m = abytes(message, void 0, "message"); + const pub = abytes(publicKey, 32, "publicKey"); + try { + const P = lift_x(num(pub)); + const r = num(sig.subarray(0, 32)); + if (!Fp.isValidNot0(r)) + return false; + const s = num(sig.subarray(32, 64)); + if (!Fn.isValidNot0(s)) + return false; + const e = challenge(Fn.toBytes(r), pointToBytes(P), m); + const R = BASE.multiplyUnsafe(s).add(P.multiplyUnsafe(Fn.neg(e))); + const { x, y } = R.toAffine(); + if (R.is0() || !hasEven(y) || x !== r) + return false; + return true; + } catch (error) { + return false; + } + } + var schnorr = /* @__PURE__ */ (() => { + const size = 32; + const seedLength = 48; + const randomSecretKey = (seed = randomBytes(seedLength)) => { + return mapHashToField(seed, secp256k1_CURVE.n); + }; + return { + keygen: createKeygen(randomSecretKey, schnorrGetPublicKey), + getPublicKey: schnorrGetPublicKey, + sign: schnorrSign, + verify: schnorrVerify, + Point: Pointk1, + utils: { + randomSecretKey, + taggedHash, + lift_x, + pointToBytes + }, + lengths: { + secretKey: size, + publicKey: size, + publicKeyHasPrefix: false, + signature: size * 2, + seed: seedLength + } + }; + })(); + + // node_modules/nostr-crypto-utils/dist/esm/utils/logger.js + init_process(); + var import_pino = __toESM(require_browser()); + var LogLevel; + (function(LogLevel2) { + LogLevel2[LogLevel2["DEBUG"] = 0] = "DEBUG"; + LogLevel2[LogLevel2["INFO"] = 1] = "INFO"; + LogLevel2[LogLevel2["WARN"] = 2] = "WARN"; + LogLevel2[LogLevel2["ERROR"] = 3] = "ERROR"; + })(LogLevel || (LogLevel = {})); + var logger = (0, import_pino.default)({ + name: "nostr-crypto-utils", + level: process.env.LOG_LEVEL || "info", + transport: true ? { + target: "pino-pretty", + options: { + colorize: true, + translateTime: "HH:MM:ss", + ignore: "pid,hostname" + } + } : void 0, + formatters: { + level: (label) => { + return { level: label.toUpperCase() }; + }, + log: (obj) => { + if (obj && typeof obj === "object" && "err" in obj) { + const newObj = { ...obj }; + if (newObj.err instanceof Error) { + const err = newObj.err; + newObj.err = { + message: err.message, + stack: err.stack, + name: err.name + }; + } + return newObj; + } + return obj; + } + } + }); + + // node_modules/nostr-crypto-utils/dist/esm/encoding/base64.js + init_process(); + function isValidBase64(base642) { + try { + return Boolean(base642.match(/^[A-Za-z0-9+/]*={0,2}$/)); + } catch { + return false; + } + } + function bytesToBase64(bytes) { + let binary = ""; + for (let i = 0; i < bytes.length; i++) { + binary += String.fromCharCode(bytes[i]); + } + return btoa(binary); + } + function base64ToBytes(base642) { + if (!isValidBase64(base642)) { + throw new Error("Invalid base64 string"); + } + const binary = atob(base642); + const bytes = new Uint8Array(binary.length); + for (let i = 0; i < binary.length; i++) { + bytes[i] = binary.charCodeAt(i); + } + return bytes; + } + + // node_modules/nostr-crypto-utils/dist/esm/crypto.js + var getCrypto = async () => { + if (typeof window !== "undefined" && window.crypto) { + return window.crypto; + } + if (typeof globalThis !== "undefined" && globalThis.crypto) { + return globalThis.crypto; + } + try { + const cryptoModule = await Promise.resolve().then(() => __toESM(require_crypto())); + if (cryptoModule.webcrypto) { + return cryptoModule.webcrypto; + } + } catch { + logger.debug("Node crypto not available"); + } + throw new Error("No WebCrypto implementation available"); + }; + var CustomCrypto = class { + cryptoInstance = null; + initPromise; + constructor() { + this.initPromise = this.initialize(); + } + async initialize() { + this.cryptoInstance = await getCrypto(); + } + async ensureInitialized() { + await this.initPromise; + if (!this.cryptoInstance) { + throw new Error("Crypto implementation not initialized"); + } + return this.cryptoInstance; + } + async getSubtle() { + const crypto2 = await this.ensureInitialized(); + return crypto2.subtle; + } + async getRandomValues(array) { + const crypto2 = await this.ensureInitialized(); + return crypto2.getRandomValues(array); + } + }; + var customCrypto = new CustomCrypto(); + var signSchnorr = schnorr.sign; + var verifySchnorrSignature = schnorr.verify; + async function generateKeyPair() { + const privateKeyBytes = randomBytes(32); + const privateKey = bytesToHex(privateKeyBytes); + privateKeyBytes.fill(0); + const publicKey = await getPublicKey(privateKey); + return { + privateKey, + publicKey + }; + } + async function getPublicKey(privateKey) { + try { + const privateKeyBytes = hexToBytes(privateKey); + const publicKeyBytes = schnorr.getPublicKey(privateKeyBytes); + return { + hex: bytesToHex(publicKeyBytes), + bytes: publicKeyBytes + }; + } catch (error) { + logger.error({ error }, "Failed to get public key"); + throw error; + } + } + function normalizePrivateKey(privateKey) { + if (privateKey instanceof Uint8Array) { + return bytesToHex(privateKey); + } + return privateKey; + } + async function signEvent(event, privateKey) { + try { + const privateKeyHex = normalizePrivateKey(privateKey); + const serialized = JSON.stringify([ + 0, + event.pubkey, + event.created_at, + event.kind, + event.tags, + event.content + ]); + const eventHash = sha256(new TextEncoder().encode(serialized)); + const privateKeyBytes = hexToBytes(privateKeyHex); + const signatureBytes = schnorr.sign(eventHash, privateKeyBytes); + return { + ...event, + id: bytesToHex(eventHash), + sig: bytesToHex(signatureBytes) + }; + } catch (error) { + logger.error({ error }, "Failed to sign event"); + throw error; + } + } + function getPublicKeySync(privateKey) { + const privateKeyBytes = privateKey instanceof Uint8Array ? privateKey : hexToBytes(privateKey); + const publicKeyBytes = schnorr.getPublicKey(privateKeyBytes); + return bytesToHex(publicKeyBytes); + } + async function finalizeEvent(event, privateKey) { + const pubkey = event.pubkey || getPublicKeySync(privateKey); + const timestamp = event.created_at || Math.floor(Date.now() / 1e3); + const fullEvent = { + kind: event.kind || 1, + created_at: timestamp, + tags: event.tags || [], + content: event.content || "", + pubkey + }; + return signEvent(fullEvent, privateKey); + } + + // node_modules/nostr-crypto-utils/dist/esm/validation/index.js + init_process(); + + // node_modules/nostr-crypto-utils/dist/esm/event/index.js + init_process(); + + // node_modules/nostr-crypto-utils/dist/esm/event/creation.js + init_process(); + + // node_modules/nostr-crypto-utils/dist/esm/event/signing.js + init_process(); + + // node_modules/nostr-crypto-utils/dist/esm/nips/nip-04.js + var nip_04_exports = {}; + __export(nip_04_exports, { + computeSharedSecret: () => generateSharedSecret, + decryptMessage: () => decryptMessage, + encryptMessage: () => encryptMessage, + generateSharedSecret: () => generateSharedSecret + }); + init_process(); + var getCrypto2 = async () => { + if (typeof window !== "undefined" && window.crypto) { + return window.crypto; + } + if (typeof globalThis !== "undefined" && globalThis.crypto) { + return globalThis.crypto; + } + try { + const cryptoModule = await Promise.resolve().then(() => __toESM(require_crypto())); + if (cryptoModule.webcrypto) { + return cryptoModule.webcrypto; + } + } catch { + logger.debug("Node crypto not available"); + } + throw new Error("No WebCrypto implementation available"); + }; + var CryptoImplementation = class { + cryptoInstance = null; + initPromise; + constructor() { + this.initPromise = this.initialize(); + } + async initialize() { + this.cryptoInstance = await getCrypto2(); + } + async ensureInitialized() { + await this.initPromise; + if (!this.cryptoInstance) { + throw new Error("Crypto implementation not initialized"); + } + return this.cryptoInstance; + } + async getSubtle() { + const crypto2 = await this.ensureInitialized(); + return crypto2.subtle; + } + async getRandomValues(array) { + const crypto2 = await this.ensureInitialized(); + return crypto2.getRandomValues(array); + } + }; + var cryptoImpl = new CryptoImplementation(); + async function encryptMessage(message, senderPrivKey, recipientPubKey) { + try { + if (!message || !senderPrivKey || !recipientPubKey) { + throw new Error("Invalid input parameters"); + } + if (!/^[0-9a-f]{64}$/i.test(senderPrivKey)) { + throw new Error("Invalid private key format"); + } + const pubKeyHex = recipientPubKey.startsWith("02") || recipientPubKey.startsWith("03") ? recipientPubKey : "02" + recipientPubKey; + const sharedPoint = secp256k1.getSharedSecret(hexToBytes(senderPrivKey), hexToBytes(pubKeyHex)); + const sharedX = sharedPoint.slice(1, 33); + const sharedKey = await (await cryptoImpl.getSubtle()).importKey("raw", sharedX.buffer, { name: "AES-CBC", length: 256 }, false, ["encrypt"]); + sharedX.fill(0); + sharedPoint.fill(0); + const iv = new Uint8Array(16); + await cryptoImpl.getRandomValues(iv); + const encoded = new TextEncoder().encode(message); + const encrypted = await (await cryptoImpl.getSubtle()).encrypt({ name: "AES-CBC", iv }, sharedKey, encoded.buffer); + const ciphertextBase64 = bytesToBase64(new Uint8Array(encrypted)); + const ivBase64 = bytesToBase64(iv); + return ciphertextBase64 + "?iv=" + ivBase64; + } catch (error) { + logger.error({ error }, "Failed to encrypt message"); + throw error; + } + } + async function decryptMessage(encryptedMessage, recipientPrivKey, senderPubKey) { + try { + if (!encryptedMessage || !recipientPrivKey || !senderPubKey) { + throw new Error("Invalid input parameters"); + } + if (!/^[0-9a-f]{64}$/i.test(recipientPrivKey)) { + throw new Error("Invalid private key format"); + } + const pubKeyHex = senderPubKey.startsWith("02") || senderPubKey.startsWith("03") ? senderPubKey : "02" + senderPubKey; + const sharedPoint = secp256k1.getSharedSecret(hexToBytes(recipientPrivKey), hexToBytes(pubKeyHex)); + const sharedX = sharedPoint.slice(1, 33); + const sharedKey = await (await cryptoImpl.getSubtle()).importKey("raw", sharedX.buffer, { name: "AES-CBC", length: 256 }, false, ["decrypt"]); + sharedX.fill(0); + sharedPoint.fill(0); + let iv; + let ciphertext; + if (encryptedMessage.includes("?iv=")) { + const [ciphertextBase64, ivBase64] = encryptedMessage.split("?iv="); + ciphertext = base64ToBytes(ciphertextBase64); + iv = base64ToBytes(ivBase64); + } else { + const encrypted = hexToBytes(encryptedMessage); + iv = encrypted.slice(0, 16); + ciphertext = encrypted.slice(16); + } + const decrypted = await (await cryptoImpl.getSubtle()).decrypt({ name: "AES-CBC", iv }, sharedKey, ciphertext.buffer); + return new TextDecoder().decode(decrypted); + } catch (error) { + logger.error({ error }, "Failed to decrypt message"); + throw error; + } + } + function generateSharedSecret(privateKey, publicKey) { + try { + if (!privateKey || !publicKey) { + throw new Error("Invalid input parameters"); + } + if (!/^[0-9a-f]{64}$/i.test(privateKey)) { + throw new Error("Invalid private key format"); + } + const pubKeyHex = publicKey.startsWith("02") || publicKey.startsWith("03") ? publicKey : "02" + publicKey; + const sharedPoint = secp256k1.getSharedSecret(hexToBytes(privateKey), hexToBytes(pubKeyHex)); + return { sharedSecret: sharedPoint.slice(1, 33) }; + } catch (error) { + logger.error({ error }, "Failed to generate shared secret"); + throw error; + } + } + + // node_modules/nostr-crypto-utils/dist/esm/nips/nip-01.js + init_process(); + + // node_modules/nostr-crypto-utils/dist/esm/nips/nip-19.js + var nip_19_exports = {}; + __export(nip_19_exports, { + decode: () => decode, + naddrEncode: () => naddrEncode, + neventEncode: () => neventEncode, + noteEncode: () => noteEncode, + nprofileEncode: () => nprofileEncode, + npubEncode: () => npubEncode, + nrelayEncode: () => nrelayEncode, + nsecEncode: () => nsecEncode + }); + init_process(); + var import_bech32 = __toESM(require_dist()); + var import_buffer = __toESM(require_buffer()); + var VALID_PREFIXES = ["npub", "nsec", "note", "nprofile", "nevent", "naddr", "nrelay"]; + var TLV_TYPES = { + SPECIAL: 0, + // Main data (hex) + RELAY: 1, + // Relay URL (utf8) + AUTHOR: 2, + // Author pubkey (hex) + KIND: 3, + // Event kind (uint8) + IDENTIFIER: 4 + // Identifier (utf8) + }; + function npubEncode(pubkey) { + validateHexString(pubkey, 64); + const data = import_buffer.Buffer.from(pubkey, "hex"); + const words = import_bech32.bech32.toWords(data); + return import_bech32.bech32.encode("npub", words, 1e3); + } + function nsecEncode(privkey) { + validateHexString(privkey, 64); + const data = import_buffer.Buffer.from(privkey, "hex"); + const words = import_bech32.bech32.toWords(data); + return import_bech32.bech32.encode("nsec", words, 1e3); + } + function noteEncode(eventId) { + validateHexString(eventId, 64); + const data = import_buffer.Buffer.from(eventId, "hex"); + const words = import_bech32.bech32.toWords(data); + return import_bech32.bech32.encode("note", words, 1e3); + } + function nprofileEncode(pubkey, relays) { + validateHexString(pubkey, 64); + if (relays) { + relays.forEach(validateRelayUrl); + } + const data = encodeTLV({ + type: "nprofile", + data: pubkey, + relays + }); + return import_bech32.bech32.encode("nprofile", data, 1e3); + } + function neventEncode(eventId, relays, author, kind) { + validateHexString(eventId, 64); + if (relays) { + relays.forEach(validateRelayUrl); + } + if (author) { + validateHexString(author, 64); + } + if (kind !== void 0 && !Number.isInteger(kind)) { + throw new Error("Invalid event kind"); + } + const data = encodeTLV({ + type: "nevent", + data: eventId, + relays, + author, + kind + }); + return import_bech32.bech32.encode("nevent", data, 1e3); + } + function naddrEncode(pubkey, kind, identifier, relays) { + validateHexString(pubkey, 64); + if (!Number.isInteger(kind)) { + throw new Error("Invalid event kind"); + } + if (!identifier) { + throw new Error("Identifier is required"); + } + if (relays) { + relays.forEach(validateRelayUrl); + } + const data = encodeTLV({ + type: "naddr", + data: pubkey, + kind, + identifier, + relays + }); + return import_bech32.bech32.encode("naddr", data, 1e3); + } + function nrelayEncode(url) { + validateRelayUrl(url); + const data = import_buffer.Buffer.from(url, "utf8"); + const words = import_bech32.bech32.toWords(data); + return import_bech32.bech32.encode("nrelay", words, 1e3); + } + function decode(str) { + if (!str.includes("1")) { + throw new Error("Invalid bech32 string"); + } + const prefix = str.split("1")[0].toLowerCase(); + if (!VALID_PREFIXES.includes(prefix)) { + throw new Error("Unknown prefix"); + } + try { + const decoded = import_bech32.bech32.decode(str, 1e3); + const data = import_buffer.Buffer.from(import_bech32.bech32.fromWords(decoded.words)); + let url; + let decodedData; + switch (decoded.prefix) { + case "npub": + case "nsec": + case "note": + validateHexString(data.toString("hex"), 64); + return { + type: decoded.prefix, + data: data.toString("hex") + }; + case "nrelay": + url = data.toString("utf8"); + validateRelayUrl(url); + return { + type: "nrelay", + data: url + }; + case "nprofile": + case "nevent": + case "naddr": + decodedData = decodeTLV(decoded.prefix, data); + return decodedData; + default: + throw new Error("Unknown prefix"); + } + } catch (error) { + if (error instanceof Error) { + throw error; + } + throw new Error("Invalid bech32 string"); + } + } + function validateHexString(str, length) { + if (!/^[0-9a-fA-F]+$/.test(str)) { + throw new Error("Invalid hex string"); + } + if (length && str.length !== length) { + throw new Error(`Invalid hex string length (expected ${length})`); + } + } + function validateRelayUrl(url) { + try { + const parsed = new URL(url); + if (!["ws:", "wss:"].includes(parsed.protocol)) { + throw new Error("Invalid relay URL protocol"); + } + } catch { + throw new Error("Invalid relay URL"); + } + } + function encodeTLV(data) { + const result = []; + const bytes = import_buffer.Buffer.from(data.data, "hex"); + result.push(TLV_TYPES.SPECIAL, bytes.length); + result.push(...bytes); + if (data.relays?.length) { + for (const relay of data.relays) { + const relayBytes = import_buffer.Buffer.from(relay, "utf8"); + result.push(TLV_TYPES.RELAY, relayBytes.length); + result.push(...relayBytes); + } + } + if (data.author) { + const authorBytes = import_buffer.Buffer.from(data.author, "hex"); + result.push(TLV_TYPES.AUTHOR, authorBytes.length); + result.push(...authorBytes); + } + if (data.kind !== void 0) { + const kindBytes = import_buffer.Buffer.alloc(4); + kindBytes.writeUInt32BE(data.kind); + result.push(TLV_TYPES.KIND, kindBytes.length); + result.push(...kindBytes); + } + if (data.identifier) { + const identifierBytes = import_buffer.Buffer.from(data.identifier, "utf8"); + result.push(TLV_TYPES.IDENTIFIER, identifierBytes.length); + result.push(...identifierBytes); + } + return import_bech32.bech32.toWords(import_buffer.Buffer.from(result)); + } + function decodeTLV(prefix, data) { + const result = { + type: prefix, + data: "", + relays: [] + }; + let i = 0; + let relay; + while (i < data.length) { + const type = data[i]; + const length = data[i + 1]; + if (i + 2 + length > data.length) { + throw new Error("Invalid TLV data"); + } + const value = data.slice(i + 2, i + 2 + length); + switch (type) { + case TLV_TYPES.SPECIAL: + result.data = value.toString("hex"); + validateHexString(result.data, 64); + break; + case TLV_TYPES.RELAY: + relay = value.toString("utf8"); + validateRelayUrl(relay); + result.relays = result.relays || []; + result.relays.push(relay); + break; + case TLV_TYPES.AUTHOR: + result.author = value.toString("hex"); + validateHexString(result.author, 64); + break; + case TLV_TYPES.KIND: + result.kind = value.readUInt32BE(); + break; + case TLV_TYPES.IDENTIFIER: + result.identifier = value.toString("utf8"); + break; + default: + break; + } + i += 2 + length; + } + return result; + } + + // node_modules/nostr-crypto-utils/dist/esm/nips/nip-26.js + init_process(); + + // node_modules/nostr-crypto-utils/dist/esm/nips/nip-44.js + var nip_44_exports = {}; + __export(nip_44_exports, { + calcPaddedLen: () => calcPaddedLen, + decrypt: () => decrypt, + encrypt: () => encrypt, + getConversationKey: () => getConversationKey, + v2: () => v2 + }); + init_process(); + + // node_modules/@noble/ciphers/chacha.js + init_process(); + + // node_modules/@noble/ciphers/_arx.js + init_process(); + + // node_modules/@noble/ciphers/utils.js + init_process(); + function isBytes2(a) { + return a instanceof Uint8Array || ArrayBuffer.isView(a) && a.constructor.name === "Uint8Array"; + } + function abool2(b) { + if (typeof b !== "boolean") + throw new Error(`boolean expected, not ${b}`); + } + function anumber2(n) { + if (!Number.isSafeInteger(n) || n < 0) + throw new Error("positive integer expected, got " + n); + } + function abytes2(value, length, title = "") { + const bytes = isBytes2(value); + const len = value?.length; + const needsLen = length !== void 0; + if (!bytes || needsLen && len !== length) { + const prefix = title && `"${title}" `; + const ofLen = needsLen ? ` of length ${length}` : ""; + const got = bytes ? `length=${len}` : `type=${typeof value}`; + throw new Error(prefix + "expected Uint8Array" + ofLen + ", got " + got); + } + return value; + } + function aexists2(instance, checkFinished = true) { + if (instance.destroyed) + throw new Error("Hash instance has been destroyed"); + if (checkFinished && instance.finished) + throw new Error("Hash#digest() has already been called"); + } + function aoutput2(out, instance) { + abytes2(out, void 0, "output"); + const min = instance.outputLen; + if (out.length < min) { + throw new Error("digestInto() expects output buffer of length at least " + min); + } + } + function u322(arr) { + return new Uint32Array(arr.buffer, arr.byteOffset, Math.floor(arr.byteLength / 4)); + } + function clean2(...arrays) { + for (let i = 0; i < arrays.length; i++) { + arrays[i].fill(0); + } + } + function createView2(arr) { + return new DataView(arr.buffer, arr.byteOffset, arr.byteLength); + } + var isLE2 = /* @__PURE__ */ (() => new Uint8Array(new Uint32Array([287454020]).buffer)[0] === 68)(); + function checkOpts2(defaults, opts) { + if (opts == null || typeof opts !== "object") + throw new Error("options must be defined"); + const merged = Object.assign(defaults, opts); + return merged; + } + function equalBytes(a, b) { + if (a.length !== b.length) + return false; + let diff = 0; + for (let i = 0; i < a.length; i++) + diff |= a[i] ^ b[i]; + return diff === 0; + } + var wrapCipher = /* @__NO_SIDE_EFFECTS__ */ (params, constructor) => { + function wrappedCipher(key, ...args) { + abytes2(key, void 0, "key"); + if (!isLE2) + throw new Error("Non little-endian hardware is not yet supported"); + if (params.nonceLength !== void 0) { + const nonce = args[0]; + abytes2(nonce, params.varSizeNonce ? void 0 : params.nonceLength, "nonce"); + } + const tagl = params.tagLength; + if (tagl && args[1] !== void 0) + abytes2(args[1], void 0, "AAD"); + const cipher = constructor(key, ...args); + const checkOutput = (fnLength, output) => { + if (output !== void 0) { + if (fnLength !== 2) + throw new Error("cipher output not supported"); + abytes2(output, void 0, "output"); + } + }; + let called = false; + const wrCipher = { + encrypt(data, output) { + if (called) + throw new Error("cannot encrypt() twice with same key + nonce"); + called = true; + abytes2(data); + checkOutput(cipher.encrypt.length, output); + return cipher.encrypt(data, output); + }, + decrypt(data, output) { + abytes2(data); + if (tagl && data.length < tagl) + throw new Error('"ciphertext" expected length bigger than tagLength=' + tagl); + checkOutput(cipher.decrypt.length, output); + return cipher.decrypt(data, output); + } + }; + return wrCipher; + } + Object.assign(wrappedCipher, params); + return wrappedCipher; + }; + function getOutput(expectedLength, out, onlyAligned = true) { + if (out === void 0) + return new Uint8Array(expectedLength); + if (out.length !== expectedLength) + throw new Error('"output" expected Uint8Array of length ' + expectedLength + ", got: " + out.length); + if (onlyAligned && !isAligned32(out)) + throw new Error("invalid output, must be aligned"); + return out; + } + function u64Lengths(dataLength, aadLength, isLE3) { + abool2(isLE3); + const num2 = new Uint8Array(16); + const view = createView2(num2); + view.setBigUint64(0, BigInt(aadLength), isLE3); + view.setBigUint64(8, BigInt(dataLength), isLE3); + return num2; + } + function isAligned32(bytes) { + return bytes.byteOffset % 4 === 0; + } + function copyBytes2(bytes) { + return Uint8Array.from(bytes); + } + + // node_modules/@noble/ciphers/_arx.js + var encodeStr = (str) => Uint8Array.from(str.split(""), (c) => c.charCodeAt(0)); + var sigma16 = encodeStr("expand 16-byte k"); + var sigma32 = encodeStr("expand 32-byte k"); + var sigma16_32 = u322(sigma16); + var sigma32_32 = u322(sigma32); + function rotl2(a, b) { + return a << b | a >>> 32 - b; + } + function isAligned322(b) { + return b.byteOffset % 4 === 0; + } + var BLOCK_LEN = 64; + var BLOCK_LEN32 = 16; + var MAX_COUNTER = 2 ** 32 - 1; + var U32_EMPTY = Uint32Array.of(); + function runCipher(core, sigma, key, nonce, data, output, counter, rounds) { + const len = data.length; + const block = new Uint8Array(BLOCK_LEN); + const b32 = u322(block); + const isAligned = isAligned322(data) && isAligned322(output); + const d32 = isAligned ? u322(data) : U32_EMPTY; + const o32 = isAligned ? u322(output) : U32_EMPTY; + for (let pos = 0; pos < len; counter++) { + core(sigma, key, nonce, b32, counter, rounds); + if (counter >= MAX_COUNTER) + throw new Error("arx: counter overflow"); + const take = Math.min(BLOCK_LEN, len - pos); + if (isAligned && take === BLOCK_LEN) { + const pos32 = pos / 4; + if (pos % 4 !== 0) + throw new Error("arx: invalid block position"); + for (let j = 0, posj; j < BLOCK_LEN32; j++) { + posj = pos32 + j; + o32[posj] = d32[posj] ^ b32[j]; + } + pos += BLOCK_LEN; + continue; + } + for (let j = 0, posj; j < take; j++) { + posj = pos + j; + output[posj] = data[posj] ^ block[j]; + } + pos += take; + } + } + function createCipher(core, opts) { + const { allowShortKeys, extendNonceFn, counterLength, counterRight, rounds } = checkOpts2({ allowShortKeys: false, counterLength: 8, counterRight: false, rounds: 20 }, opts); + if (typeof core !== "function") + throw new Error("core must be a function"); + anumber2(counterLength); + anumber2(rounds); + abool2(counterRight); + abool2(allowShortKeys); + return (key, nonce, data, output, counter = 0) => { + abytes2(key, void 0, "key"); + abytes2(nonce, void 0, "nonce"); + abytes2(data, void 0, "data"); + const len = data.length; + if (output === void 0) + output = new Uint8Array(len); + abytes2(output, void 0, "output"); + anumber2(counter); + if (counter < 0 || counter >= MAX_COUNTER) + throw new Error("arx: counter overflow"); + if (output.length < len) + throw new Error(`arx: output (${output.length}) is shorter than data (${len})`); + const toClean = []; + let l = key.length; + let k; + let sigma; + if (l === 32) { + toClean.push(k = copyBytes2(key)); + sigma = sigma32_32; + } else if (l === 16 && allowShortKeys) { + k = new Uint8Array(32); + k.set(key); + k.set(key, 16); + sigma = sigma16_32; + toClean.push(k); + } else { + abytes2(key, 32, "arx key"); + throw new Error("invalid key size"); + } + if (!isAligned322(nonce)) + toClean.push(nonce = copyBytes2(nonce)); + const k32 = u322(k); + if (extendNonceFn) { + if (nonce.length !== 24) + throw new Error(`arx: extended nonce must be 24 bytes`); + extendNonceFn(sigma, k32, u322(nonce.subarray(0, 16)), k32); + nonce = nonce.subarray(16); + } + const nonceNcLen = 16 - counterLength; + if (nonceNcLen !== nonce.length) + throw new Error(`arx: nonce must be ${nonceNcLen} or 16 bytes`); + if (nonceNcLen !== 12) { + const nc = new Uint8Array(12); + nc.set(nonce, counterRight ? 0 : 12 - nonce.length); + nonce = nc; + toClean.push(nonce); + } + const n32 = u322(nonce); + runCipher(core, sigma, k32, n32, data, output, counter, rounds); + clean2(...toClean); + return output; + }; + } + + // node_modules/@noble/ciphers/_poly1305.js + init_process(); + function u8to16(a, i) { + return a[i++] & 255 | (a[i++] & 255) << 8; + } + var Poly1305 = class { + blockLen = 16; + outputLen = 16; + buffer = new Uint8Array(16); + r = new Uint16Array(10); + // Allocating 1 array with .subarray() here is slower than 3 + h = new Uint16Array(10); + pad = new Uint16Array(8); + pos = 0; + finished = false; + // Can be speed-up using BigUint64Array, at the cost of complexity + constructor(key) { + key = copyBytes2(abytes2(key, 32, "key")); + const t0 = u8to16(key, 0); + const t1 = u8to16(key, 2); + const t2 = u8to16(key, 4); + const t3 = u8to16(key, 6); + const t4 = u8to16(key, 8); + const t5 = u8to16(key, 10); + const t6 = u8to16(key, 12); + const t7 = u8to16(key, 14); + this.r[0] = t0 & 8191; + this.r[1] = (t0 >>> 13 | t1 << 3) & 8191; + this.r[2] = (t1 >>> 10 | t2 << 6) & 7939; + this.r[3] = (t2 >>> 7 | t3 << 9) & 8191; + this.r[4] = (t3 >>> 4 | t4 << 12) & 255; + this.r[5] = t4 >>> 1 & 8190; + this.r[6] = (t4 >>> 14 | t5 << 2) & 8191; + this.r[7] = (t5 >>> 11 | t6 << 5) & 8065; + this.r[8] = (t6 >>> 8 | t7 << 8) & 8191; + this.r[9] = t7 >>> 5 & 127; + for (let i = 0; i < 8; i++) + this.pad[i] = u8to16(key, 16 + 2 * i); + } + process(data, offset, isLast = false) { + const hibit = isLast ? 0 : 1 << 11; + const { h, r } = this; + const r0 = r[0]; + const r1 = r[1]; + const r2 = r[2]; + const r3 = r[3]; + const r4 = r[4]; + const r5 = r[5]; + const r6 = r[6]; + const r7 = r[7]; + const r8 = r[8]; + const r9 = r[9]; + const t0 = u8to16(data, offset + 0); + const t1 = u8to16(data, offset + 2); + const t2 = u8to16(data, offset + 4); + const t3 = u8to16(data, offset + 6); + const t4 = u8to16(data, offset + 8); + const t5 = u8to16(data, offset + 10); + const t6 = u8to16(data, offset + 12); + const t7 = u8to16(data, offset + 14); + let h0 = h[0] + (t0 & 8191); + let h1 = h[1] + ((t0 >>> 13 | t1 << 3) & 8191); + let h2 = h[2] + ((t1 >>> 10 | t2 << 6) & 8191); + let h3 = h[3] + ((t2 >>> 7 | t3 << 9) & 8191); + let h4 = h[4] + ((t3 >>> 4 | t4 << 12) & 8191); + let h5 = h[5] + (t4 >>> 1 & 8191); + let h6 = h[6] + ((t4 >>> 14 | t5 << 2) & 8191); + let h7 = h[7] + ((t5 >>> 11 | t6 << 5) & 8191); + let h8 = h[8] + ((t6 >>> 8 | t7 << 8) & 8191); + let h9 = h[9] + (t7 >>> 5 | hibit); + let c = 0; + let d0 = c + h0 * r0 + h1 * (5 * r9) + h2 * (5 * r8) + h3 * (5 * r7) + h4 * (5 * r6); + c = d0 >>> 13; + d0 &= 8191; + d0 += h5 * (5 * r5) + h6 * (5 * r4) + h7 * (5 * r3) + h8 * (5 * r2) + h9 * (5 * r1); + c += d0 >>> 13; + d0 &= 8191; + let d1 = c + h0 * r1 + h1 * r0 + h2 * (5 * r9) + h3 * (5 * r8) + h4 * (5 * r7); + c = d1 >>> 13; + d1 &= 8191; + d1 += h5 * (5 * r6) + h6 * (5 * r5) + h7 * (5 * r4) + h8 * (5 * r3) + h9 * (5 * r2); + c += d1 >>> 13; + d1 &= 8191; + let d2 = c + h0 * r2 + h1 * r1 + h2 * r0 + h3 * (5 * r9) + h4 * (5 * r8); + c = d2 >>> 13; + d2 &= 8191; + d2 += h5 * (5 * r7) + h6 * (5 * r6) + h7 * (5 * r5) + h8 * (5 * r4) + h9 * (5 * r3); + c += d2 >>> 13; + d2 &= 8191; + let d3 = c + h0 * r3 + h1 * r2 + h2 * r1 + h3 * r0 + h4 * (5 * r9); + c = d3 >>> 13; + d3 &= 8191; + d3 += h5 * (5 * r8) + h6 * (5 * r7) + h7 * (5 * r6) + h8 * (5 * r5) + h9 * (5 * r4); + c += d3 >>> 13; + d3 &= 8191; + let d4 = c + h0 * r4 + h1 * r3 + h2 * r2 + h3 * r1 + h4 * r0; + c = d4 >>> 13; + d4 &= 8191; + d4 += h5 * (5 * r9) + h6 * (5 * r8) + h7 * (5 * r7) + h8 * (5 * r6) + h9 * (5 * r5); + c += d4 >>> 13; + d4 &= 8191; + let d5 = c + h0 * r5 + h1 * r4 + h2 * r3 + h3 * r2 + h4 * r1; + c = d5 >>> 13; + d5 &= 8191; + d5 += h5 * r0 + h6 * (5 * r9) + h7 * (5 * r8) + h8 * (5 * r7) + h9 * (5 * r6); + c += d5 >>> 13; + d5 &= 8191; + let d6 = c + h0 * r6 + h1 * r5 + h2 * r4 + h3 * r3 + h4 * r2; + c = d6 >>> 13; + d6 &= 8191; + d6 += h5 * r1 + h6 * r0 + h7 * (5 * r9) + h8 * (5 * r8) + h9 * (5 * r7); + c += d6 >>> 13; + d6 &= 8191; + let d7 = c + h0 * r7 + h1 * r6 + h2 * r5 + h3 * r4 + h4 * r3; + c = d7 >>> 13; + d7 &= 8191; + d7 += h5 * r2 + h6 * r1 + h7 * r0 + h8 * (5 * r9) + h9 * (5 * r8); + c += d7 >>> 13; + d7 &= 8191; + let d8 = c + h0 * r8 + h1 * r7 + h2 * r6 + h3 * r5 + h4 * r4; + c = d8 >>> 13; + d8 &= 8191; + d8 += h5 * r3 + h6 * r2 + h7 * r1 + h8 * r0 + h9 * (5 * r9); + c += d8 >>> 13; + d8 &= 8191; + let d9 = c + h0 * r9 + h1 * r8 + h2 * r7 + h3 * r6 + h4 * r5; + c = d9 >>> 13; + d9 &= 8191; + d9 += h5 * r4 + h6 * r3 + h7 * r2 + h8 * r1 + h9 * r0; + c += d9 >>> 13; + d9 &= 8191; + c = (c << 2) + c | 0; + c = c + d0 | 0; + d0 = c & 8191; + c = c >>> 13; + d1 += c; + h[0] = d0; + h[1] = d1; + h[2] = d2; + h[3] = d3; + h[4] = d4; + h[5] = d5; + h[6] = d6; + h[7] = d7; + h[8] = d8; + h[9] = d9; + } + finalize() { + const { h, pad: pad2 } = this; + const g = new Uint16Array(10); + let c = h[1] >>> 13; + h[1] &= 8191; + for (let i = 2; i < 10; i++) { + h[i] += c; + c = h[i] >>> 13; + h[i] &= 8191; + } + h[0] += c * 5; + c = h[0] >>> 13; + h[0] &= 8191; + h[1] += c; + c = h[1] >>> 13; + h[1] &= 8191; + h[2] += c; + g[0] = h[0] + 5; + c = g[0] >>> 13; + g[0] &= 8191; + for (let i = 1; i < 10; i++) { + g[i] = h[i] + c; + c = g[i] >>> 13; + g[i] &= 8191; + } + g[9] -= 1 << 13; + let mask = (c ^ 1) - 1; + for (let i = 0; i < 10; i++) + g[i] &= mask; + mask = ~mask; + for (let i = 0; i < 10; i++) + h[i] = h[i] & mask | g[i]; + h[0] = (h[0] | h[1] << 13) & 65535; + h[1] = (h[1] >>> 3 | h[2] << 10) & 65535; + h[2] = (h[2] >>> 6 | h[3] << 7) & 65535; + h[3] = (h[3] >>> 9 | h[4] << 4) & 65535; + h[4] = (h[4] >>> 12 | h[5] << 1 | h[6] << 14) & 65535; + h[5] = (h[6] >>> 2 | h[7] << 11) & 65535; + h[6] = (h[7] >>> 5 | h[8] << 8) & 65535; + h[7] = (h[8] >>> 8 | h[9] << 5) & 65535; + let f = h[0] + pad2[0]; + h[0] = f & 65535; + for (let i = 1; i < 8; i++) { + f = (h[i] + pad2[i] | 0) + (f >>> 16) | 0; + h[i] = f & 65535; + } + clean2(g); + } + update(data) { + aexists2(this); + abytes2(data); + data = copyBytes2(data); + const { buffer, blockLen } = this; + const len = data.length; + for (let pos = 0; pos < len; ) { + const take = Math.min(blockLen - this.pos, len - pos); + if (take === blockLen) { + for (; blockLen <= len - pos; pos += blockLen) + this.process(data, pos); + continue; + } + buffer.set(data.subarray(pos, pos + take), this.pos); + this.pos += take; + pos += take; + if (this.pos === blockLen) { + this.process(buffer, 0, false); + this.pos = 0; + } + } + return this; + } + destroy() { + clean2(this.h, this.r, this.buffer, this.pad); + } + digestInto(out) { + aexists2(this); + aoutput2(out, this); + this.finished = true; + const { buffer, h } = this; + let { pos } = this; + if (pos) { + buffer[pos++] = 1; + for (; pos < 16; pos++) + buffer[pos] = 0; + this.process(buffer, 0, true); + } + this.finalize(); + let opos = 0; + for (let i = 0; i < 8; i++) { + out[opos++] = h[i] >>> 0; + out[opos++] = h[i] >>> 8; + } + return out; + } + digest() { + const { buffer, outputLen } = this; + this.digestInto(buffer); + const res = buffer.slice(0, outputLen); + this.destroy(); + return res; + } + }; + function wrapConstructorWithKey(hashCons) { + const hashC = (msg, key) => hashCons(key).update(msg).digest(); + const tmp = hashCons(new Uint8Array(32)); + hashC.outputLen = tmp.outputLen; + hashC.blockLen = tmp.blockLen; + hashC.create = (key) => hashCons(key); + return hashC; + } + var poly1305 = /* @__PURE__ */ (() => wrapConstructorWithKey((key) => new Poly1305(key)))(); + + // node_modules/@noble/ciphers/chacha.js + function chachaCore(s, k, n, out, cnt, rounds = 20) { + let y00 = s[0], y01 = s[1], y02 = s[2], y03 = s[3], y04 = k[0], y05 = k[1], y06 = k[2], y07 = k[3], y08 = k[4], y09 = k[5], y10 = k[6], y11 = k[7], y12 = cnt, y13 = n[0], y14 = n[1], y15 = n[2]; + let x00 = y00, x01 = y01, x02 = y02, x03 = y03, x04 = y04, x05 = y05, x06 = y06, x07 = y07, x08 = y08, x09 = y09, x10 = y10, x11 = y11, x12 = y12, x13 = y13, x14 = y14, x15 = y15; + for (let r = 0; r < rounds; r += 2) { + x00 = x00 + x04 | 0; + x12 = rotl2(x12 ^ x00, 16); + x08 = x08 + x12 | 0; + x04 = rotl2(x04 ^ x08, 12); + x00 = x00 + x04 | 0; + x12 = rotl2(x12 ^ x00, 8); + x08 = x08 + x12 | 0; + x04 = rotl2(x04 ^ x08, 7); + x01 = x01 + x05 | 0; + x13 = rotl2(x13 ^ x01, 16); + x09 = x09 + x13 | 0; + x05 = rotl2(x05 ^ x09, 12); + x01 = x01 + x05 | 0; + x13 = rotl2(x13 ^ x01, 8); + x09 = x09 + x13 | 0; + x05 = rotl2(x05 ^ x09, 7); + x02 = x02 + x06 | 0; + x14 = rotl2(x14 ^ x02, 16); + x10 = x10 + x14 | 0; + x06 = rotl2(x06 ^ x10, 12); + x02 = x02 + x06 | 0; + x14 = rotl2(x14 ^ x02, 8); + x10 = x10 + x14 | 0; + x06 = rotl2(x06 ^ x10, 7); + x03 = x03 + x07 | 0; + x15 = rotl2(x15 ^ x03, 16); + x11 = x11 + x15 | 0; + x07 = rotl2(x07 ^ x11, 12); + x03 = x03 + x07 | 0; + x15 = rotl2(x15 ^ x03, 8); + x11 = x11 + x15 | 0; + x07 = rotl2(x07 ^ x11, 7); + x00 = x00 + x05 | 0; + x15 = rotl2(x15 ^ x00, 16); + x10 = x10 + x15 | 0; + x05 = rotl2(x05 ^ x10, 12); + x00 = x00 + x05 | 0; + x15 = rotl2(x15 ^ x00, 8); + x10 = x10 + x15 | 0; + x05 = rotl2(x05 ^ x10, 7); + x01 = x01 + x06 | 0; + x12 = rotl2(x12 ^ x01, 16); + x11 = x11 + x12 | 0; + x06 = rotl2(x06 ^ x11, 12); + x01 = x01 + x06 | 0; + x12 = rotl2(x12 ^ x01, 8); + x11 = x11 + x12 | 0; + x06 = rotl2(x06 ^ x11, 7); + x02 = x02 + x07 | 0; + x13 = rotl2(x13 ^ x02, 16); + x08 = x08 + x13 | 0; + x07 = rotl2(x07 ^ x08, 12); + x02 = x02 + x07 | 0; + x13 = rotl2(x13 ^ x02, 8); + x08 = x08 + x13 | 0; + x07 = rotl2(x07 ^ x08, 7); + x03 = x03 + x04 | 0; + x14 = rotl2(x14 ^ x03, 16); + x09 = x09 + x14 | 0; + x04 = rotl2(x04 ^ x09, 12); + x03 = x03 + x04 | 0; + x14 = rotl2(x14 ^ x03, 8); + x09 = x09 + x14 | 0; + x04 = rotl2(x04 ^ x09, 7); + } + let oi = 0; + out[oi++] = y00 + x00 | 0; + out[oi++] = y01 + x01 | 0; + out[oi++] = y02 + x02 | 0; + out[oi++] = y03 + x03 | 0; + out[oi++] = y04 + x04 | 0; + out[oi++] = y05 + x05 | 0; + out[oi++] = y06 + x06 | 0; + out[oi++] = y07 + x07 | 0; + out[oi++] = y08 + x08 | 0; + out[oi++] = y09 + x09 | 0; + out[oi++] = y10 + x10 | 0; + out[oi++] = y11 + x11 | 0; + out[oi++] = y12 + x12 | 0; + out[oi++] = y13 + x13 | 0; + out[oi++] = y14 + x14 | 0; + out[oi++] = y15 + x15 | 0; + } + function hchacha(s, k, i, out) { + let x00 = s[0], x01 = s[1], x02 = s[2], x03 = s[3], x04 = k[0], x05 = k[1], x06 = k[2], x07 = k[3], x08 = k[4], x09 = k[5], x10 = k[6], x11 = k[7], x12 = i[0], x13 = i[1], x14 = i[2], x15 = i[3]; + for (let r = 0; r < 20; r += 2) { + x00 = x00 + x04 | 0; + x12 = rotl2(x12 ^ x00, 16); + x08 = x08 + x12 | 0; + x04 = rotl2(x04 ^ x08, 12); + x00 = x00 + x04 | 0; + x12 = rotl2(x12 ^ x00, 8); + x08 = x08 + x12 | 0; + x04 = rotl2(x04 ^ x08, 7); + x01 = x01 + x05 | 0; + x13 = rotl2(x13 ^ x01, 16); + x09 = x09 + x13 | 0; + x05 = rotl2(x05 ^ x09, 12); + x01 = x01 + x05 | 0; + x13 = rotl2(x13 ^ x01, 8); + x09 = x09 + x13 | 0; + x05 = rotl2(x05 ^ x09, 7); + x02 = x02 + x06 | 0; + x14 = rotl2(x14 ^ x02, 16); + x10 = x10 + x14 | 0; + x06 = rotl2(x06 ^ x10, 12); + x02 = x02 + x06 | 0; + x14 = rotl2(x14 ^ x02, 8); + x10 = x10 + x14 | 0; + x06 = rotl2(x06 ^ x10, 7); + x03 = x03 + x07 | 0; + x15 = rotl2(x15 ^ x03, 16); + x11 = x11 + x15 | 0; + x07 = rotl2(x07 ^ x11, 12); + x03 = x03 + x07 | 0; + x15 = rotl2(x15 ^ x03, 8); + x11 = x11 + x15 | 0; + x07 = rotl2(x07 ^ x11, 7); + x00 = x00 + x05 | 0; + x15 = rotl2(x15 ^ x00, 16); + x10 = x10 + x15 | 0; + x05 = rotl2(x05 ^ x10, 12); + x00 = x00 + x05 | 0; + x15 = rotl2(x15 ^ x00, 8); + x10 = x10 + x15 | 0; + x05 = rotl2(x05 ^ x10, 7); + x01 = x01 + x06 | 0; + x12 = rotl2(x12 ^ x01, 16); + x11 = x11 + x12 | 0; + x06 = rotl2(x06 ^ x11, 12); + x01 = x01 + x06 | 0; + x12 = rotl2(x12 ^ x01, 8); + x11 = x11 + x12 | 0; + x06 = rotl2(x06 ^ x11, 7); + x02 = x02 + x07 | 0; + x13 = rotl2(x13 ^ x02, 16); + x08 = x08 + x13 | 0; + x07 = rotl2(x07 ^ x08, 12); + x02 = x02 + x07 | 0; + x13 = rotl2(x13 ^ x02, 8); + x08 = x08 + x13 | 0; + x07 = rotl2(x07 ^ x08, 7); + x03 = x03 + x04 | 0; + x14 = rotl2(x14 ^ x03, 16); + x09 = x09 + x14 | 0; + x04 = rotl2(x04 ^ x09, 12); + x03 = x03 + x04 | 0; + x14 = rotl2(x14 ^ x03, 8); + x09 = x09 + x14 | 0; + x04 = rotl2(x04 ^ x09, 7); + } + let oi = 0; + out[oi++] = x00; + out[oi++] = x01; + out[oi++] = x02; + out[oi++] = x03; + out[oi++] = x12; + out[oi++] = x13; + out[oi++] = x14; + out[oi++] = x15; + } + var chacha20 = /* @__PURE__ */ createCipher(chachaCore, { + counterRight: false, + counterLength: 4, + allowShortKeys: false + }); + var xchacha20 = /* @__PURE__ */ createCipher(chachaCore, { + counterRight: false, + counterLength: 8, + extendNonceFn: hchacha, + allowShortKeys: false + }); + var ZEROS16 = /* @__PURE__ */ new Uint8Array(16); + var updatePadded = (h, msg) => { + h.update(msg); + const leftover = msg.length % 16; + if (leftover) + h.update(ZEROS16.subarray(leftover)); + }; + var ZEROS32 = /* @__PURE__ */ new Uint8Array(32); + function computeTag(fn, key, nonce, ciphertext, AAD) { + if (AAD !== void 0) + abytes2(AAD, void 0, "AAD"); + const authKey = fn(key, nonce, ZEROS32); + const lengths = u64Lengths(ciphertext.length, AAD ? AAD.length : 0, true); + const h = poly1305.create(authKey); + if (AAD) + updatePadded(h, AAD); + updatePadded(h, ciphertext); + h.update(lengths); + const res = h.digest(); + clean2(authKey, lengths); + return res; + } + var _poly1305_aead = (xorStream) => (key, nonce, AAD) => { + const tagLength = 16; + return { + encrypt(plaintext, output) { + const plength = plaintext.length; + output = getOutput(plength + tagLength, output, false); + output.set(plaintext); + const oPlain = output.subarray(0, -tagLength); + xorStream(key, nonce, oPlain, oPlain, 1); + const tag = computeTag(xorStream, key, nonce, oPlain, AAD); + output.set(tag, plength); + clean2(tag); + return output; + }, + decrypt(ciphertext, output) { + output = getOutput(ciphertext.length - tagLength, output, false); + const data = ciphertext.subarray(0, -tagLength); + const passedTag = ciphertext.subarray(-tagLength); + const tag = computeTag(xorStream, key, nonce, data, AAD); + if (!equalBytes(passedTag, tag)) + throw new Error("invalid tag"); + output.set(ciphertext.subarray(0, -tagLength)); + xorStream(key, nonce, output, output, 1); + clean2(tag); + return output; + } + }; + }; + var chacha20poly1305 = /* @__PURE__ */ wrapCipher({ blockSize: 64, nonceLength: 12, tagLength: 16 }, _poly1305_aead(chacha20)); + var xchacha20poly1305 = /* @__PURE__ */ wrapCipher({ blockSize: 64, nonceLength: 24, tagLength: 16 }, _poly1305_aead(xchacha20)); + + // node_modules/@noble/hashes/hkdf.js + init_process(); + function extract(hash, ikm, salt) { + ahash(hash); + if (salt === void 0) + salt = new Uint8Array(hash.outputLen); + return hmac(hash, salt, ikm); + } + var HKDF_COUNTER = /* @__PURE__ */ Uint8Array.of(0); + var EMPTY_BUFFER = /* @__PURE__ */ Uint8Array.of(); + function expand(hash, prk, info, length = 32) { + ahash(hash); + anumber(length, "length"); + const olen = hash.outputLen; + if (length > 255 * olen) + throw new Error("Length must be <= 255*HashLen"); + const blocks = Math.ceil(length / olen); + if (info === void 0) + info = EMPTY_BUFFER; + else + abytes(info, void 0, "info"); + const okm = new Uint8Array(blocks * olen); + const HMAC = hmac.create(hash, prk); + const HMACTmp = HMAC._cloneInto(); + const T = new Uint8Array(HMAC.outputLen); + for (let counter = 0; counter < blocks; counter++) { + HKDF_COUNTER[0] = counter + 1; + HMACTmp.update(counter === 0 ? EMPTY_BUFFER : T).update(info).update(HKDF_COUNTER).digestInto(T); + okm.set(T, olen * counter); + HMAC._cloneInto(HMACTmp); + } + HMAC.destroy(); + HMACTmp.destroy(); + clean(T, HKDF_COUNTER); + return okm.slice(0, length); + } + + // node_modules/@scure/base/index.js + init_process(); + function isBytes3(a) { + return a instanceof Uint8Array || ArrayBuffer.isView(a) && a.constructor.name === "Uint8Array"; + } + function abytes3(b) { + if (!isBytes3(b)) + throw new Error("Uint8Array expected"); + } + function isArrayOf(isString, arr) { + if (!Array.isArray(arr)) + return false; + if (arr.length === 0) + return true; + if (isString) { + return arr.every((item) => typeof item === "string"); + } else { + return arr.every((item) => Number.isSafeInteger(item)); + } + } + function afn(input) { + if (typeof input !== "function") + throw new Error("function expected"); + return true; + } + function astr(label, input) { + if (typeof input !== "string") + throw new Error(`${label}: string expected`); + return true; + } + function anumber3(n) { + if (!Number.isSafeInteger(n)) + throw new Error(`invalid integer: ${n}`); + } + function aArr(input) { + if (!Array.isArray(input)) + throw new Error("array expected"); + } + function astrArr(label, input) { + if (!isArrayOf(true, input)) + throw new Error(`${label}: array of strings expected`); + } + function anumArr(label, input) { + if (!isArrayOf(false, input)) + throw new Error(`${label}: array of numbers expected`); + } + // @__NO_SIDE_EFFECTS__ + function chain(...args) { + const id = (a) => a; + const wrap2 = (a, b) => (c) => a(b(c)); + const encode = args.map((x) => x.encode).reduceRight(wrap2, id); + const decode2 = args.map((x) => x.decode).reduce(wrap2, id); + return { encode, decode: decode2 }; + } + // @__NO_SIDE_EFFECTS__ + function alphabet(letters) { + const lettersA = typeof letters === "string" ? letters.split("") : letters; + const len = lettersA.length; + astrArr("alphabet", lettersA); + const indexes = new Map(lettersA.map((l, i) => [l, i])); + return { + encode: (digits) => { + aArr(digits); + return digits.map((i) => { + if (!Number.isSafeInteger(i) || i < 0 || i >= len) + throw new Error(`alphabet.encode: digit index outside alphabet "${i}". Allowed: ${letters}`); + return lettersA[i]; + }); + }, + decode: (input) => { + aArr(input); + return input.map((letter) => { + astr("alphabet.decode", letter); + const i = indexes.get(letter); + if (i === void 0) + throw new Error(`Unknown letter: "${letter}". Allowed: ${letters}`); + return i; + }); + } + }; + } + // @__NO_SIDE_EFFECTS__ + function join(separator = "") { + astr("join", separator); + return { + encode: (from) => { + astrArr("join.decode", from); + return from.join(separator); + }, + decode: (to) => { + astr("join.decode", to); + return to.split(separator); + } + }; + } + // @__NO_SIDE_EFFECTS__ + function padding(bits, chr = "=") { + anumber3(bits); + astr("padding", chr); + return { + encode(data) { + astrArr("padding.encode", data); + while (data.length * bits % 8) + data.push(chr); + return data; + }, + decode(input) { + astrArr("padding.decode", input); + let end = input.length; + if (end * bits % 8) + throw new Error("padding: invalid, string should have whole number of bytes"); + for (; end > 0 && input[end - 1] === chr; end--) { + const last = end - 1; + const byte = last * bits; + if (byte % 8 === 0) + throw new Error("padding: invalid, string has too much padding"); + } + return input.slice(0, end); + } + }; + } + function convertRadix(data, from, to) { + if (from < 2) + throw new Error(`convertRadix: invalid from=${from}, base cannot be less than 2`); + if (to < 2) + throw new Error(`convertRadix: invalid to=${to}, base cannot be less than 2`); + aArr(data); + if (!data.length) + return []; + let pos = 0; + const res = []; + const digits = Array.from(data, (d) => { + anumber3(d); + if (d < 0 || d >= from) + throw new Error(`invalid integer: ${d}`); + return d; + }); + const dlen = digits.length; + while (true) { + let carry = 0; + let done = true; + for (let i = pos; i < dlen; i++) { + const digit = digits[i]; + const fromCarry = from * carry; + const digitBase = fromCarry + digit; + if (!Number.isSafeInteger(digitBase) || fromCarry / from !== carry || digitBase - digit !== fromCarry) { + throw new Error("convertRadix: carry overflow"); + } + const div = digitBase / to; + carry = digitBase % to; + const rounded = Math.floor(div); + digits[i] = rounded; + if (!Number.isSafeInteger(rounded) || rounded * to + carry !== digitBase) + throw new Error("convertRadix: carry overflow"); + if (!done) + continue; + else if (!rounded) + pos = i; + else + done = false; + } + res.push(carry); + if (done) + break; + } + for (let i = 0; i < data.length - 1 && data[i] === 0; i++) + res.push(0); + return res.reverse(); + } + var gcd = (a, b) => b === 0 ? a : gcd(b, a % b); + var radix2carry = /* @__NO_SIDE_EFFECTS__ */ (from, to) => from + (to - gcd(from, to)); + var powers = /* @__PURE__ */ (() => { + let res = []; + for (let i = 0; i < 40; i++) + res.push(2 ** i); + return res; + })(); + function convertRadix2(data, from, to, padding2) { + aArr(data); + if (from <= 0 || from > 32) + throw new Error(`convertRadix2: wrong from=${from}`); + if (to <= 0 || to > 32) + throw new Error(`convertRadix2: wrong to=${to}`); + if (/* @__PURE__ */ radix2carry(from, to) > 32) { + throw new Error(`convertRadix2: carry overflow from=${from} to=${to} carryBits=${/* @__PURE__ */ radix2carry(from, to)}`); + } + let carry = 0; + let pos = 0; + const max = powers[from]; + const mask = powers[to] - 1; + const res = []; + for (const n of data) { + anumber3(n); + if (n >= max) + throw new Error(`convertRadix2: invalid data word=${n} from=${from}`); + carry = carry << from | n; + if (pos + from > 32) + throw new Error(`convertRadix2: carry overflow pos=${pos} from=${from}`); + pos += from; + for (; pos >= to; pos -= to) + res.push((carry >> pos - to & mask) >>> 0); + const pow = powers[pos]; + if (pow === void 0) + throw new Error("invalid carry"); + carry &= pow - 1; + } + carry = carry << to - pos & mask; + if (!padding2 && pos >= from) + throw new Error("Excess padding"); + if (!padding2 && carry > 0) + throw new Error(`Non-zero padding: ${carry}`); + if (padding2 && pos > 0) + res.push(carry >>> 0); + return res; + } + // @__NO_SIDE_EFFECTS__ + function radix(num2) { + anumber3(num2); + const _256 = 2 ** 8; + return { + encode: (bytes) => { + if (!isBytes3(bytes)) + throw new Error("radix.encode input should be Uint8Array"); + return convertRadix(Array.from(bytes), _256, num2); + }, + decode: (digits) => { + anumArr("radix.decode", digits); + return Uint8Array.from(convertRadix(digits, num2, _256)); + } + }; + } + // @__NO_SIDE_EFFECTS__ + function radix2(bits, revPadding = false) { + anumber3(bits); + if (bits <= 0 || bits > 32) + throw new Error("radix2: bits should be in (0..32]"); + if (/* @__PURE__ */ radix2carry(8, bits) > 32 || /* @__PURE__ */ radix2carry(bits, 8) > 32) + throw new Error("radix2: carry overflow"); + return { + encode: (bytes) => { + if (!isBytes3(bytes)) + throw new Error("radix2.encode input should be Uint8Array"); + return convertRadix2(Array.from(bytes), 8, bits, !revPadding); + }, + decode: (digits) => { + anumArr("radix2.decode", digits); + return Uint8Array.from(convertRadix2(digits, bits, 8, revPadding)); + } + }; + } + function unsafeWrapper(fn) { + afn(fn); + return function(...args) { + try { + return fn.apply(null, args); + } catch (e) { + } + }; + } + function checksum(len, fn) { + anumber3(len); + afn(fn); + return { + encode(data) { + if (!isBytes3(data)) + throw new Error("checksum.encode: input should be Uint8Array"); + const sum = fn(data).slice(0, len); + const res = new Uint8Array(data.length + len); + res.set(data); + res.set(sum, data.length); + return res; + }, + decode(data) { + if (!isBytes3(data)) + throw new Error("checksum.decode: input should be Uint8Array"); + const payload = data.slice(0, -len); + const oldChecksum = data.slice(-len); + const newChecksum = fn(payload).slice(0, len); + for (let i = 0; i < len; i++) + if (newChecksum[i] !== oldChecksum[i]) + throw new Error("Invalid checksum"); + return payload; + } + }; + } + var utils = { + alphabet, + chain, + checksum, + convertRadix, + convertRadix2, + radix, + radix2, + join, + padding + }; + var hasBase64Builtin = /* @__PURE__ */ (() => typeof Uint8Array.from([]).toBase64 === "function" && typeof Uint8Array.fromBase64 === "function")(); + var decodeBase64Builtin = (s, isUrl) => { + astr("base64", s); + const re = isUrl ? /^[A-Za-z0-9=_-]+$/ : /^[A-Za-z0-9=+/]+$/; + const alphabet2 = isUrl ? "base64url" : "base64"; + if (s.length > 0 && !re.test(s)) + throw new Error("invalid base64"); + return Uint8Array.fromBase64(s, { alphabet: alphabet2, lastChunkHandling: "strict" }); + }; + var base64 = hasBase64Builtin ? { + encode(b) { + abytes3(b); + return b.toBase64(); + }, + decode(s) { + return decodeBase64Builtin(s, false); + } + } : /* @__PURE__ */ chain(/* @__PURE__ */ radix2(6), /* @__PURE__ */ alphabet("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"), /* @__PURE__ */ padding(6), /* @__PURE__ */ join("")); + var BECH_ALPHABET = /* @__PURE__ */ chain(/* @__PURE__ */ alphabet("qpzry9x8gf2tvdw0s3jn54khce6mua7l"), /* @__PURE__ */ join("")); + var POLYMOD_GENERATORS = [996825010, 642813549, 513874426, 1027748829, 705979059]; + function bech32Polymod(pre) { + const b = pre >> 25; + let chk = (pre & 33554431) << 5; + for (let i = 0; i < POLYMOD_GENERATORS.length; i++) { + if ((b >> i & 1) === 1) + chk ^= POLYMOD_GENERATORS[i]; + } + return chk; + } + function bechChecksum(prefix, words, encodingConst = 1) { + const len = prefix.length; + let chk = 1; + for (let i = 0; i < len; i++) { + const c = prefix.charCodeAt(i); + if (c < 33 || c > 126) + throw new Error(`Invalid prefix (${prefix})`); + chk = bech32Polymod(chk) ^ c >> 5; + } + chk = bech32Polymod(chk); + for (let i = 0; i < len; i++) + chk = bech32Polymod(chk) ^ prefix.charCodeAt(i) & 31; + for (let v of words) + chk = bech32Polymod(chk) ^ v; + for (let i = 0; i < 6; i++) + chk = bech32Polymod(chk); + chk ^= encodingConst; + return BECH_ALPHABET.encode(convertRadix2([chk % powers[30]], 30, 5, false)); + } + // @__NO_SIDE_EFFECTS__ + function genBech32(encoding) { + const ENCODING_CONST = encoding === "bech32" ? 1 : 734539939; + const _words = /* @__PURE__ */ radix2(5); + const fromWords = _words.decode; + const toWords = _words.encode; + const fromWordsUnsafe = unsafeWrapper(fromWords); + function encode(prefix, words, limit = 90) { + astr("bech32.encode prefix", prefix); + if (isBytes3(words)) + words = Array.from(words); + anumArr("bech32.encode", words); + const plen = prefix.length; + if (plen === 0) + throw new TypeError(`Invalid prefix length ${plen}`); + const actualLength = plen + 7 + words.length; + if (limit !== false && actualLength > limit) + throw new TypeError(`Length ${actualLength} exceeds limit ${limit}`); + const lowered = prefix.toLowerCase(); + const sum = bechChecksum(lowered, words, ENCODING_CONST); + return `${lowered}1${BECH_ALPHABET.encode(words)}${sum}`; + } + function decode2(str, limit = 90) { + astr("bech32.decode input", str); + const slen = str.length; + if (slen < 8 || limit !== false && slen > limit) + throw new TypeError(`invalid string length: ${slen} (${str}). Expected (8..${limit})`); + const lowered = str.toLowerCase(); + if (str !== lowered && str !== str.toUpperCase()) + throw new Error(`String must be lowercase or uppercase`); + const sepIndex = lowered.lastIndexOf("1"); + if (sepIndex === 0 || sepIndex === -1) + throw new Error(`Letter "1" must be present between prefix and data only`); + const prefix = lowered.slice(0, sepIndex); + const data = lowered.slice(sepIndex + 1); + if (data.length < 6) + throw new Error("Data must be at least 6 characters long"); + const words = BECH_ALPHABET.decode(data).slice(0, -6); + const sum = bechChecksum(prefix, words, ENCODING_CONST); + if (!data.endsWith(sum)) + throw new Error(`Invalid checksum in ${str}: expected "${sum}"`); + return { prefix, words }; + } + const decodeUnsafe = unsafeWrapper(decode2); + function decodeToBytes(str) { + const { prefix, words } = decode2(str, false); + return { prefix, words, bytes: fromWords(words) }; + } + function encodeFromBytes(prefix, bytes) { + return encode(prefix, toWords(bytes)); + } + return { + encode, + decode: decode2, + encodeFromBytes, + decodeToBytes, + decodeUnsafe, + fromWords, + fromWordsUnsafe, + toWords + }; + } + var bech322 = /* @__PURE__ */ genBech32("bech32"); + + // node_modules/nostr-crypto-utils/dist/esm/nips/nip-44.js + var utf8Encoder = new TextEncoder(); + var utf8Decoder = new TextDecoder(); + var minPlaintextSize = 1; + var maxPlaintextSize = 65535; + function calcPaddedLen(len) { + if (!Number.isSafeInteger(len) || len < 1) + throw new Error("expected positive integer"); + if (len <= 32) + return 32; + const nextPower = 1 << Math.floor(Math.log2(len - 1)) + 1; + const chunk = nextPower <= 256 ? 32 : nextPower / 8; + return chunk * (Math.floor((len - 1) / chunk) + 1); + } + function pad(plaintext) { + const unpadded = utf8Encoder.encode(plaintext); + const unpaddedLen = unpadded.length; + if (unpaddedLen < minPlaintextSize || unpaddedLen > maxPlaintextSize) + throw new Error("invalid plaintext length: must be between 1 and 65535 bytes"); + const prefix = new Uint8Array(2); + new DataView(prefix.buffer).setUint16(0, unpaddedLen, false); + const suffix = new Uint8Array(calcPaddedLen(unpaddedLen) - unpaddedLen); + return concatBytes(prefix, unpadded, suffix); + } + function unpad(padded) { + const unpaddedLen = new DataView(padded.buffer, padded.byteOffset).getUint16(0, false); + const unpadded = padded.subarray(2, 2 + unpaddedLen); + if (unpaddedLen < minPlaintextSize || unpaddedLen > maxPlaintextSize || unpadded.length !== unpaddedLen || padded.length !== 2 + calcPaddedLen(unpaddedLen)) { + throw new Error("invalid padding"); + } + return utf8Decoder.decode(unpadded); + } + function getConversationKey(privkeyA, pubkeyB) { + const sharedPoint = secp256k1.getSharedSecret(privkeyA, hexToBytes("02" + pubkeyB)); + const sharedX = sharedPoint.subarray(1, 33); + return extract(sha256, sharedX, utf8Encoder.encode("nip44-v2")); + } + function getMessageKeys(conversationKey, nonce) { + const keys = expand(sha256, conversationKey, nonce, 76); + return { + chacha_key: keys.subarray(0, 32), + chacha_nonce: keys.subarray(32, 44), + hmac_key: keys.subarray(44, 76) + }; + } + function encrypt(plaintext, conversationKey, nonce = randomBytes(32)) { + const { chacha_key, chacha_nonce, hmac_key } = getMessageKeys(conversationKey, nonce); + const padded = pad(plaintext); + const ciphertext = chacha20(chacha_key, chacha_nonce, padded); + const mac = hmac(sha256, hmac_key, concatBytes(nonce, ciphertext)); + return base64.encode(concatBytes(new Uint8Array([2]), nonce, ciphertext, mac)); + } + function decrypt(payload, conversationKey) { + const data = base64.decode(payload); + const version = data[0]; + if (version !== 2) + throw new Error(`unknown encryption version: ${version}`); + if (data.length < 99 || data.length > 65603) + throw new Error("invalid payload size"); + const nonce = data.subarray(1, 33); + const ciphertext = data.subarray(33, data.length - 32); + const mac = data.subarray(data.length - 32); + const { chacha_key, chacha_nonce, hmac_key } = getMessageKeys(conversationKey, nonce); + const expectedMac = hmac(sha256, hmac_key, concatBytes(nonce, ciphertext)); + if (!equalBytes(mac, expectedMac)) + throw new Error("invalid MAC"); + const padded = chacha20(chacha_key, chacha_nonce, ciphertext); + return unpad(padded); + } + var v2 = { + utils: { + getConversationKey, + calcPaddedLen + }, + encrypt, + decrypt + }; + + // node_modules/nostr-crypto-utils/dist/esm/nips/nip-46.js + init_process(); + + // node_modules/nostr-crypto-utils/dist/esm/nips/nip-49.js + init_process(); + + // node_modules/@noble/hashes/scrypt.js + init_process(); + + // node_modules/@noble/hashes/pbkdf2.js + init_process(); + function pbkdf2Init(hash, _password, _salt, _opts) { + ahash(hash); + const opts = checkOpts({ dkLen: 32, asyncTick: 10 }, _opts); + const { c, dkLen, asyncTick } = opts; + anumber(c, "c"); + anumber(dkLen, "dkLen"); + anumber(asyncTick, "asyncTick"); + if (c < 1) + throw new Error("iterations (c) must be >= 1"); + const password = kdfInputToBytes(_password, "password"); + const salt = kdfInputToBytes(_salt, "salt"); + const DK = new Uint8Array(dkLen); + const PRF = hmac.create(hash, password); + const PRFSalt = PRF._cloneInto().update(salt); + return { c, dkLen, asyncTick, DK, PRF, PRFSalt }; + } + function pbkdf2Output(PRF, PRFSalt, DK, prfW, u) { + PRF.destroy(); + PRFSalt.destroy(); + if (prfW) + prfW.destroy(); + clean(u); + return DK; + } + function pbkdf2(hash, password, salt, opts) { + const { c, dkLen, DK, PRF, PRFSalt } = pbkdf2Init(hash, password, salt, opts); + let prfW; + const arr = new Uint8Array(4); + const view = createView(arr); + const u = new Uint8Array(PRF.outputLen); + for (let ti = 1, pos = 0; pos < dkLen; ti++, pos += PRF.outputLen) { + const Ti = DK.subarray(pos, pos + PRF.outputLen); + view.setInt32(0, ti, false); + (prfW = PRFSalt._cloneInto(prfW)).update(arr).digestInto(u); + Ti.set(u.subarray(0, Ti.length)); + for (let ui = 1; ui < c; ui++) { + PRF._cloneInto(prfW).update(u).digestInto(u); + for (let i = 0; i < Ti.length; i++) + Ti[i] ^= u[i]; + } + } + return pbkdf2Output(PRF, PRFSalt, DK, prfW, u); + } + + // node_modules/@noble/hashes/scrypt.js + function XorAndSalsa(prev, pi, input, ii, out, oi) { + let y00 = prev[pi++] ^ input[ii++], y01 = prev[pi++] ^ input[ii++]; + let y02 = prev[pi++] ^ input[ii++], y03 = prev[pi++] ^ input[ii++]; + let y04 = prev[pi++] ^ input[ii++], y05 = prev[pi++] ^ input[ii++]; + let y06 = prev[pi++] ^ input[ii++], y07 = prev[pi++] ^ input[ii++]; + let y08 = prev[pi++] ^ input[ii++], y09 = prev[pi++] ^ input[ii++]; + let y10 = prev[pi++] ^ input[ii++], y11 = prev[pi++] ^ input[ii++]; + let y12 = prev[pi++] ^ input[ii++], y13 = prev[pi++] ^ input[ii++]; + let y14 = prev[pi++] ^ input[ii++], y15 = prev[pi++] ^ input[ii++]; + let x00 = y00, x01 = y01, x02 = y02, x03 = y03, x04 = y04, x05 = y05, x06 = y06, x07 = y07, x08 = y08, x09 = y09, x10 = y10, x11 = y11, x12 = y12, x13 = y13, x14 = y14, x15 = y15; + for (let i = 0; i < 8; i += 2) { + x04 ^= rotl(x00 + x12 | 0, 7); + x08 ^= rotl(x04 + x00 | 0, 9); + x12 ^= rotl(x08 + x04 | 0, 13); + x00 ^= rotl(x12 + x08 | 0, 18); + x09 ^= rotl(x05 + x01 | 0, 7); + x13 ^= rotl(x09 + x05 | 0, 9); + x01 ^= rotl(x13 + x09 | 0, 13); + x05 ^= rotl(x01 + x13 | 0, 18); + x14 ^= rotl(x10 + x06 | 0, 7); + x02 ^= rotl(x14 + x10 | 0, 9); + x06 ^= rotl(x02 + x14 | 0, 13); + x10 ^= rotl(x06 + x02 | 0, 18); + x03 ^= rotl(x15 + x11 | 0, 7); + x07 ^= rotl(x03 + x15 | 0, 9); + x11 ^= rotl(x07 + x03 | 0, 13); + x15 ^= rotl(x11 + x07 | 0, 18); + x01 ^= rotl(x00 + x03 | 0, 7); + x02 ^= rotl(x01 + x00 | 0, 9); + x03 ^= rotl(x02 + x01 | 0, 13); + x00 ^= rotl(x03 + x02 | 0, 18); + x06 ^= rotl(x05 + x04 | 0, 7); + x07 ^= rotl(x06 + x05 | 0, 9); + x04 ^= rotl(x07 + x06 | 0, 13); + x05 ^= rotl(x04 + x07 | 0, 18); + x11 ^= rotl(x10 + x09 | 0, 7); + x08 ^= rotl(x11 + x10 | 0, 9); + x09 ^= rotl(x08 + x11 | 0, 13); + x10 ^= rotl(x09 + x08 | 0, 18); + x12 ^= rotl(x15 + x14 | 0, 7); + x13 ^= rotl(x12 + x15 | 0, 9); + x14 ^= rotl(x13 + x12 | 0, 13); + x15 ^= rotl(x14 + x13 | 0, 18); + } + out[oi++] = y00 + x00 | 0; + out[oi++] = y01 + x01 | 0; + out[oi++] = y02 + x02 | 0; + out[oi++] = y03 + x03 | 0; + out[oi++] = y04 + x04 | 0; + out[oi++] = y05 + x05 | 0; + out[oi++] = y06 + x06 | 0; + out[oi++] = y07 + x07 | 0; + out[oi++] = y08 + x08 | 0; + out[oi++] = y09 + x09 | 0; + out[oi++] = y10 + x10 | 0; + out[oi++] = y11 + x11 | 0; + out[oi++] = y12 + x12 | 0; + out[oi++] = y13 + x13 | 0; + out[oi++] = y14 + x14 | 0; + out[oi++] = y15 + x15 | 0; + } + function BlockMix(input, ii, out, oi, r) { + let head = oi + 0; + let tail = oi + 16 * r; + for (let i = 0; i < 16; i++) + out[tail + i] = input[ii + (2 * r - 1) * 16 + i]; + for (let i = 0; i < r; i++, head += 16, ii += 16) { + XorAndSalsa(out, tail, input, ii, out, head); + if (i > 0) + tail += 16; + XorAndSalsa(out, head, input, ii += 16, out, tail); + } + } + function scryptInit(password, salt, _opts) { + const opts = checkOpts({ + dkLen: 32, + asyncTick: 10, + maxmem: 1024 ** 3 + 1024 + }, _opts); + const { N, r, p, dkLen, asyncTick, maxmem, onProgress } = opts; + anumber(N, "N"); + anumber(r, "r"); + anumber(p, "p"); + anumber(dkLen, "dkLen"); + anumber(asyncTick, "asyncTick"); + anumber(maxmem, "maxmem"); + if (onProgress !== void 0 && typeof onProgress !== "function") + throw new Error("progressCb must be a function"); + const blockSize = 128 * r; + const blockSize32 = blockSize / 4; + const pow32 = Math.pow(2, 32); + if (N <= 1 || (N & N - 1) !== 0 || N > pow32) + throw new Error('"N" expected a power of 2, and 2^1 <= N <= 2^32'); + if (p < 1 || p > (pow32 - 1) * 32 / blockSize) + throw new Error('"p" expected integer 1..((2^32 - 1) * 32) / (128 * r)'); + if (dkLen < 1 || dkLen > (pow32 - 1) * 32) + throw new Error('"dkLen" expected integer 1..(2^32 - 1) * 32'); + const memUsed = blockSize * (N + p); + if (memUsed > maxmem) + throw new Error('"maxmem" limit was hit, expected 128*r*(N+p) <= "maxmem"=' + maxmem); + const B = pbkdf2(sha256, password, salt, { c: 1, dkLen: blockSize * p }); + const B32 = u32(B); + const V = u32(new Uint8Array(blockSize * N)); + const tmp = u32(new Uint8Array(blockSize)); + let blockMixCb = () => { + }; + if (onProgress) { + const totalBlockMix = 2 * N * p; + const callbackPer = Math.max(Math.floor(totalBlockMix / 1e4), 1); + let blockMixCnt = 0; + blockMixCb = () => { + blockMixCnt++; + if (onProgress && (!(blockMixCnt % callbackPer) || blockMixCnt === totalBlockMix)) + onProgress(blockMixCnt / totalBlockMix); + }; + } + return { N, r, p, dkLen, blockSize32, V, B32, B, tmp, blockMixCb, asyncTick }; + } + function scryptOutput(password, dkLen, B, V, tmp) { + const res = pbkdf2(sha256, password, B, { c: 1, dkLen }); + clean(B, V, tmp); + return res; + } + function scrypt(password, salt, opts) { + const { N, r, p, dkLen, blockSize32, V, B32, B, tmp, blockMixCb } = scryptInit(password, salt, opts); + swap32IfBE(B32); + for (let pi = 0; pi < p; pi++) { + const Pi = blockSize32 * pi; + for (let i = 0; i < blockSize32; i++) + V[i] = B32[Pi + i]; + for (let i = 0, pos = 0; i < N - 1; i++) { + BlockMix(V, pos, V, pos += blockSize32, r); + blockMixCb(); + } + BlockMix(V, (N - 1) * blockSize32, B32, Pi, r); + blockMixCb(); + for (let i = 0; i < N; i++) { + const j = (B32[Pi + blockSize32 - 16] & N - 1) >>> 0; + for (let k = 0; k < blockSize32; k++) + tmp[k] = B32[Pi + k] ^ V[j * blockSize32 + k]; + BlockMix(tmp, 0, B32, Pi, r); + blockMixCb(); + } + } + swap32IfBE(B32); + return scryptOutput(password, dkLen, B, V, tmp); + } + + // node_modules/nostr-crypto-utils/dist/esm/nips/nip-49.js + function encrypt2(sec, password, logn = 16, ksb = 2) { + const salt = randomBytes(16); + const n = 2 ** logn; + const normalizedPassword = password.normalize("NFKC"); + const key = scrypt(normalizedPassword, salt, { N: n, r: 8, p: 1, dkLen: 32 }); + const nonce = randomBytes(24); + const aad = Uint8Array.from([ksb]); + const cipher = xchacha20poly1305(key, nonce, aad); + const ciphertext = cipher.encrypt(sec); + const payload = concatBytes(Uint8Array.from([2]), Uint8Array.from([logn]), salt, nonce, aad, ciphertext); + const words = bech322.toWords(payload); + return bech322.encode("ncryptsec", words, 200); + } + function decrypt2(ncryptsec, password) { + const { prefix, words } = bech322.decode(ncryptsec, 200); + if (prefix !== "ncryptsec") + throw new Error("invalid ncryptsec prefix"); + const data = new Uint8Array(bech322.fromWords(words)); + const version = data[0]; + if (version !== 2) + throw new Error(`unknown ncryptsec version: ${version}`); + const logn = data[1]; + const salt = data.subarray(2, 18); + const nonce = data.subarray(18, 42); + const ksb = data[42]; + const ciphertext = data.subarray(43); + const n = 2 ** logn; + const normalizedPassword = password.normalize("NFKC"); + const key = scrypt(normalizedPassword, salt, { N: n, r: 8, p: 1, dkLen: 32 }); + const aad = Uint8Array.from([ksb]); + const cipher = xchacha20poly1305(key, nonce, aad); + return cipher.decrypt(ciphertext); + } + + // node_modules/nostr-crypto-utils/dist/esm/utils/encoding.js + init_process(); + function hexToBytes2(hex) { + const bytes = new Uint8Array(hex.length / 2); + for (let i = 0; i < hex.length; i += 2) { + bytes[i / 2] = parseInt(hex.slice(i, i + 2), 16); + } + return bytes; + } + function bytesToHex3(bytes) { + return Array.from(bytes).map((b) => b.toString(16).padStart(2, "0")).join(""); + } + + // src/utilities/seedphrase.js + init_process(); + + // node_modules/@scure/bip39/index.js + init_process(); + var isJapanese = (wordlist2) => wordlist2[0] === "\u3042\u3044\u3053\u304F\u3057\u3093"; + function nfkd(str) { + if (typeof str !== "string") + throw new TypeError("invalid mnemonic type: " + typeof str); + return str.normalize("NFKD"); + } + function normalize(str) { + const norm = nfkd(str); + const words = norm.split(" "); + if (![12, 15, 18, 21, 24].includes(words.length)) + throw new Error("Invalid mnemonic"); + return { nfkd: norm, words }; + } + function aentropy(ent) { + abytes(ent); + if (![16, 20, 24, 28, 32].includes(ent.length)) + throw new Error("invalid entropy length"); + } + var calcChecksum = (entropy) => { + const bitsLeft = 8 - entropy.length / 4; + return new Uint8Array([sha256(entropy)[0] >> bitsLeft << bitsLeft]); + }; + function getCoder(wordlist2) { + if (!Array.isArray(wordlist2) || wordlist2.length !== 2048 || typeof wordlist2[0] !== "string") + throw new Error("Wordlist: expected array of 2048 strings"); + wordlist2.forEach((i) => { + if (typeof i !== "string") + throw new Error("wordlist: non-string element: " + i); + }); + return utils.chain(utils.checksum(1, calcChecksum), utils.radix2(11, true), utils.alphabet(wordlist2)); + } + function mnemonicToEntropy(mnemonic, wordlist2) { + const { words } = normalize(mnemonic); + const entropy = getCoder(wordlist2).decode(words); + aentropy(entropy); + return entropy; + } + function entropyToMnemonic(entropy, wordlist2) { + aentropy(entropy); + const words = getCoder(wordlist2).encode(entropy); + return words.join(isJapanese(wordlist2) ? "\u3000" : " "); + } + function validateMnemonic(mnemonic, wordlist2) { + try { + mnemonicToEntropy(mnemonic, wordlist2); + } catch (e) { + return false; + } + return true; + } + + // node_modules/@scure/bip39/wordlists/english.js + init_process(); + var wordlist = `abandon ability able about @@ -2046,8 +9213,3552 @@ youth zebra zero zone -zoo`.split(` -`);function ba(t){let e=at(t);return ma(e,rn)}function xa(t){let e=Vo(t.trim().toLowerCase(),rn),r=Ae(e),n=Pe(r);return{hexKey:r,pubKey:n}}function Fo(t){try{return wa(t.trim().toLowerCase(),rn)}catch{return!1}}b();async function nn(){let t=await oo();return{privateKey:t.privateKey,publicKey:t.publicKey.hex}}b();var ly=new Error("timeout while waiting for mutex to become available"),uy=new Error("mutex already locked"),Tu=new Error("request for lock canceled"),_u=function(t,e,r,n){function o(i){return i instanceof r?i:new r(function(s){s(i)})}return new(r||(r=Promise))(function(i,s){function a(f){try{l(n.next(f))}catch(u){s(u)}}function c(f){try{l(n.throw(f))}catch(u){s(u)}}function l(f){f.done?i(f.value):o(f.value).then(a,c)}l((n=n.apply(t,e||[])).next())})},$o=class{constructor(e,r=Tu){this._value=e,this._cancelError=r,this._queue=[],this._weightedWaiters=[]}acquire(e=1,r=0){if(e<=0)throw new Error(`invalid weight ${e}: must be positive`);return new Promise((n,o)=>{let i={resolve:n,reject:o,weight:e,priority:r},s=Ea(this._queue,a=>r<=a.priority);s===-1&&e<=this._value?this._dispatchItem(i):this._queue.splice(s+1,0,i)})}runExclusive(e){return _u(this,arguments,void 0,function*(r,n=1,o=0){let[i,s]=yield this.acquire(n,o);try{return yield r(i)}finally{s()}})}waitForUnlock(e=1,r=0){if(e<=0)throw new Error(`invalid weight ${e}: must be positive`);return this._couldLockImmediately(e,r)?Promise.resolve():new Promise(n=>{this._weightedWaiters[e-1]||(this._weightedWaiters[e-1]=[]),Lu(this._weightedWaiters[e-1],{resolve:n,priority:r})})}isLocked(){return this._value<=0}getValue(){return this._value}setValue(e){this._value=e,this._dispatchQueue()}release(e=1){if(e<=0)throw new Error(`invalid weight ${e}: must be positive`);this._value+=e,this._dispatchQueue()}cancel(){this._queue.forEach(e=>e.reject(this._cancelError)),this._queue=[]}_dispatchQueue(){for(this._drainUnlockWaiters();this._queue.length>0&&this._queue[0].weight<=this._value;)this._dispatchItem(this._queue.shift()),this._drainUnlockWaiters()}_dispatchItem(e){let r=this._value;this._value-=e.weight,e.resolve([r,this._newReleaser(e.weight)])}_newReleaser(e){let r=!1;return()=>{r||(r=!0,this.release(e))}}_drainUnlockWaiters(){if(this._queue.length===0)for(let e=this._value;e>0;e--){let r=this._weightedWaiters[e-1];r&&(r.forEach(n=>n.resolve()),this._weightedWaiters[e-1]=[])}else{let e=this._queue[0].priority;for(let r=this._value;r>0;r--){let n=this._weightedWaiters[r-1];if(!n)continue;let o=n.findIndex(i=>i.priority<=e);(o===-1?n:n.splice(0,o)).forEach((i=>i.resolve()))}}}_couldLockImmediately(e,r){return(this._queue.length===0||this._queue[0].prioritye.priority<=n.priority);t.splice(r+1,0,e)}function Ea(t,e){for(let r=t.length-1;r>=0;r--)if(e(t[r]))return r;return-1}var Uu=function(t,e,r,n){function o(i){return i instanceof r?i:new r(function(s){s(i)})}return new(r||(r=Promise))(function(i,s){function a(f){try{l(n.next(f))}catch(u){s(u)}}function c(f){try{l(n.throw(f))}catch(u){s(u)}}function l(f){f.done?i(f.value):o(f.value).then(a,c)}l((n=n.apply(t,e||[])).next())})},pr=class{constructor(e){this._semaphore=new $o(1,e)}acquire(){return Uu(this,arguments,void 0,function*(e=0){let[,r]=yield this._semaphore.acquire(1,e);return r})}runExclusive(e,r=0){return this._semaphore.runExclusive(()=>e(),1,r)}isLocked(){return this._semaphore.isLocked()}waitForUnlock(e=0){return this._semaphore.waitForUnlock(1,e)}release(){this._semaphore.isLocked()&&this._semaphore.release()}cancel(){return this._semaphore.cancel()}};b();b();var _=typeof browser<"u"?browser:typeof chrome<"u"?chrome:null;if(!_)throw new Error("browser-polyfill: No extension API namespace found (neither browser nor chrome).");var ae=typeof browser>"u"&&typeof chrome<"u";function ce(t,e){return(...r)=>{try{let n=e.apply(t,r);if(n&&typeof n.then=="function")return n}catch{}return new Promise((n,o)=>{e.apply(t,[...r,(...i)=>{_.runtime&&_.runtime.lastError?o(new Error(_.runtime.lastError.message)):n(i.length<=1?i[0]:i)}])})}}var N={};N.runtime={sendMessage(...t){return ae?ce(_.runtime,_.runtime.sendMessage)(...t):_.runtime.sendMessage(...t)},onMessage:_.runtime.onMessage,getURL(t){return _.runtime.getURL(t)},openOptionsPage(){return ae?ce(_.runtime,_.runtime.openOptionsPage)():_.runtime.openOptionsPage()},get id(){return _.runtime.id}};N.storage={local:{get(...t){return ae?ce(_.storage.local,_.storage.local.get)(...t):_.storage.local.get(...t)},set(...t){return ae?ce(_.storage.local,_.storage.local.set)(...t):_.storage.local.set(...t)},clear(...t){return ae?ce(_.storage.local,_.storage.local.clear)(...t):_.storage.local.clear(...t)},remove(...t){return ae?ce(_.storage.local,_.storage.local.remove)(...t):_.storage.local.remove(...t)}},sync:_.storage?.sync?{get(...t){return ae?ce(_.storage.sync,_.storage.sync.get)(...t):_.storage.sync.get(...t)},set(...t){return ae?ce(_.storage.sync,_.storage.sync.set)(...t):_.storage.sync.set(...t)},remove(...t){return ae?ce(_.storage.sync,_.storage.sync.remove)(...t):_.storage.sync.remove(...t)},clear(...t){return ae?ce(_.storage.sync,_.storage.sync.clear)(...t):_.storage.sync.clear(...t)},getBytesInUse(...t){return _.storage.sync.getBytesInUse?ae?ce(_.storage.sync,_.storage.sync.getBytesInUse)(...t):_.storage.sync.getBytesInUse(...t):Promise.resolve(0)}}:null,onChanged:_.storage?.onChanged||null};N.tabs={create(...t){return ae?ce(_.tabs,_.tabs.create)(...t):_.tabs.create(...t)},query(...t){return ae?ce(_.tabs,_.tabs.query)(...t):_.tabs.query(...t)},remove(...t){return ae?ce(_.tabs,_.tabs.remove)(...t):_.tabs.remove(...t)},update(...t){return ae?ce(_.tabs,_.tabs.update)(...t):_.tabs.update(...t)},get(...t){return ae?ce(_.tabs,_.tabs.get)(...t):_.tabs.get(...t)},getCurrent(...t){return ae?ce(_.tabs,_.tabs.getCurrent)(...t):_.tabs.getCurrent(...t)},sendMessage(...t){return ae?ce(_.tabs,_.tabs.sendMessage)(...t):_.tabs.sendMessage(...t)}};N.alarms=_.alarms?{create(...t){let e=_.alarms.create(...t);return e&&typeof e.then=="function"?e:Promise.resolve()},clear(...t){return ae?ce(_.alarms,_.alarms.clear)(...t):_.alarms.clear(...t)},onAlarm:_.alarms.onAlarm}:null;b();function gt(t){let e=new Uint8Array(t),r="";for(let n=0;ne.some(r=>t instanceof r),Ta,_a;function Ru(){return Ta||(Ta=[IDBDatabase,IDBObjectStore,IDBIndex,IDBCursor,IDBTransaction])}function Cu(){return _a||(_a=[IDBCursor.prototype.advance,IDBCursor.prototype.continue,IDBCursor.prototype.continuePrimaryKey])}var Jo=new WeakMap,Go=new WeakMap,ln=new WeakMap;function Ou(t){let e=new Promise((r,n)=>{let o=()=>{t.removeEventListener("success",i),t.removeEventListener("error",s)},i=()=>{r(_t(t.result)),o()},s=()=>{n(t.error),o()};t.addEventListener("success",i),t.addEventListener("error",s)});return ln.set(e,t),e}function Nu(t){if(Jo.has(t))return;let e=new Promise((r,n)=>{let o=()=>{t.removeEventListener("complete",i),t.removeEventListener("error",s),t.removeEventListener("abort",s)},i=()=>{r(),o()},s=()=>{n(t.error||new DOMException("AbortError","AbortError")),o()};t.addEventListener("complete",i),t.addEventListener("error",s),t.addEventListener("abort",s)});Jo.set(t,e)}var Xo={get(t,e,r){if(t instanceof IDBTransaction){if(e==="done")return Jo.get(t);if(e==="store")return r.objectStoreNames[1]?void 0:r.objectStore(r.objectStoreNames[0])}return _t(t[e])},set(t,e,r){return t[e]=r,!0},has(t,e){return t instanceof IDBTransaction&&(e==="done"||e==="store")?!0:e in t}};function Ra(t){Xo=t(Xo)}function Du(t){return Cu().includes(t)?function(...e){return t.apply(Qo(this),e),_t(this.request)}:function(...e){return _t(t.apply(Qo(this),e))}}function Mu(t){return typeof t=="function"?Du(t):(t instanceof IDBTransaction&&Nu(t),Zo(t,Ru())?new Proxy(t,Xo):t)}function _t(t){if(t instanceof IDBRequest)return Ou(t);if(Go.has(t))return Go.get(t);let e=Mu(t);return e!==t&&(Go.set(t,e),ln.set(e,t)),e}var Qo=t=>ln.get(t);function Ca(t,e,{blocked:r,upgrade:n,blocking:o,terminated:i}={}){let s=indexedDB.open(t,e),a=_t(s);return n&&s.addEventListener("upgradeneeded",c=>{n(_t(s.result),c.oldVersion,c.newVersion,_t(s.transaction),c)}),r&&s.addEventListener("blocked",c=>r(c.oldVersion,c.newVersion,c)),a.then(c=>{i&&c.addEventListener("close",()=>i()),o&&c.addEventListener("versionchange",l=>o(l.oldVersion,l.newVersion,l))}).catch(()=>{}),a}var Hu=["get","getKey","getAll","getAllKeys","count"],Ku=["put","add","delete","clear"],Yo=new Map;function La(t,e){if(!(t instanceof IDBDatabase&&!(e in t)&&typeof e=="string"))return;if(Yo.get(e))return Yo.get(e);let r=e.replace(/FromIndex$/,""),n=e!==r,o=Ku.includes(r);if(!(r in(n?IDBIndex:IDBObjectStore).prototype)||!(o||Hu.includes(r)))return;let i=async function(s,...a){let c=this.transaction(s,o?"readwrite":"readonly"),l=c.store;return n&&(l=l.index(a.shift())),(await Promise.all([l[r](...a),o&&c.done]))[0]};return Yo.set(e,i),i}Ra(t=>({...t,get:(e,r,n)=>La(e,r)||t.get(e,r,n),has:(e,r)=>!!La(e,r)||t.has(e,r)}));var Vu=["continue","continuePrimaryKey","advance"],Ua={},ei=new WeakMap,Oa=new WeakMap,Fu={get(t,e){if(!Vu.includes(e))return t[e];let r=Ua[e];return r||(r=Ua[e]=function(...n){ei.set(this,Oa.get(this)[e](...n))}),r}};async function*$u(...t){let e=this;if(e instanceof IDBCursor||(e=await e.openCursor(...t)),!e)return;e=e;let r=new Proxy(e,Fu);for(Oa.set(r,e),ln.set(r,Qo(e));e;)yield r,e=await(ei.get(r)||e.continue()),ei.delete(r)}function Pa(t,e){return e===Symbol.asyncIterator&&Zo(t,[IDBIndex,IDBObjectStore,IDBCursor])||e==="iterate"&&Zo(t,[IDBIndex,IDBObjectStore])}Ra(t=>({...t,get(e,r,n){return Pa(e,r)?$u:t.get(e,r,n)},has(e,r){return Pa(e,r)||t.has(e,r)}}));async function qu(){return await Ca("events",1,{upgrade(t){let e=t.createObjectStore("events",{keyPath:"event.id"});e.createIndex("pubkey","event.pubkey"),e.createIndex("created_at","event.created_at"),e.createIndex("kind","event.kind"),e.createIndex("host","metadata.host")}})}async function Na(t){return(await qu()).put("events",t)}b();var ju=102400,Da=8192,zu=512,ti="_chunk:",fn="_sync_meta",dn="platformSyncEnabled";var mt={P1_PROFILES:1,P2_SETTINGS:2,P3_APIKEYS:3,P4_VAULT:4},hn=N.storage.local,un=null;function Wu(t,e){let r=[];for(let o=0;o{let{hosts:s,...a}=i;return a}),o=JSON.stringify(n);e.push({key:"profiles",jsonString:o,priority:mt.P1_PROFILES,size:o.length})}if(t.profileIndex!=null){let n=JSON.stringify(t.profileIndex);e.push({key:"profileIndex",jsonString:n,priority:mt.P1_PROFILES,size:n.length})}if(t.isEncrypted!=null){let n=JSON.stringify(t.isEncrypted);e.push({key:"isEncrypted",jsonString:n,priority:mt.P1_PROFILES,size:n.length})}let r=["autoLockMinutes","version","protocol_handler",dn];for(let n of r)if(t[n]!=null){let o=JSON.stringify(t[n]);e.push({key:n,jsonString:o,priority:mt.P2_SETTINGS,size:o.length})}for(let n of Object.keys(t))if(n.startsWith("feature:")){let o=JSON.stringify(t[n]);e.push({key:n,jsonString:o,priority:mt.P2_SETTINGS,size:o.length})}if(t.apiKeyVault){let n=JSON.stringify(t.apiKeyVault);e.push({key:"apiKeyVault",jsonString:n,priority:mt.P3_APIKEYS,size:n.length})}if(t.vaultDocs&&typeof t.vaultDocs=="object"){let n=Object.values(t.vaultDocs).sort((o,i)=>(i.updatedAt||0)-(o.updatedAt||0));for(let o of n){let i=`vaultDoc:${o.path}`,s=JSON.stringify(o);e.push({key:i,jsonString:s,priority:mt.P4_VAULT,size:s.length})}}return e}async function Zu(){if(!(!N.storage.sync||!await Ka()))try{let e=await Yu();e.sort((c,l)=>c.priority-l.priority);let r=0,n=0,o={},i=[],s=!1;for(let c of e){if(s)break;let l=Wu(c.key,c.jsonString),f=0;for(let u of l)f+=u.key.length+(typeof u.value=="string"?u.value.length:JSON.stringify(u.value).length);if((r+f>ju-500||n+l.length>zu-5)&&!(c.priority<=mt.P3_APIKEYS)){s=!0;break}for(let u of l)o[u.key]=u.value,i.push(u.key);r+=f,n+=l.length}let a={lastWrittenAt:Date.now(),keys:i};o[fn]=JSON.stringify(a),await N.storage.sync.set(o);try{let c=await N.storage.sync.get(null),l=Object.keys(c).filter(f=>f!==fn&&!i.includes(f));l.length>0&&await N.storage.sync.remove(l)}catch{}}catch{}}async function Ma(){if(!N.storage.sync)return null;try{let t=await N.storage.sync.get(null);if(!t||Object.keys(t).length===0)return null;let e=t[fn];if(!e)return null;let r;try{r=JSON.parse(e)}catch{return null}let n={},o=r.keys.filter(i=>!i.startsWith(ti)&&i!==fn);for(let i of o){let s=Gu(i,t);s!=null&&(n[i]=s)}return n._syncMeta=r,n}catch{return null}}async function Ha(t){if(!t)return;let e=await hn.get(null),r={},n=!1,o=!e.profiles||e.profiles.length===0||e.profiles.length===1&&!e.profiles[0].privKey;if(t.profiles){if(o)r.profiles=t.profiles,n=!0;else if(e.profiles){let f=[...e.profiles];for(let u=0;u=f.length)f.push(h),n=!0;else{let d=f[u],y=h.updatedAt||0,p=d.updatedAt||0;y>p&&(f[u]={...h,hosts:d.hosts||{}},n=!0)}}n&&(r.profiles=f)}}t.profileIndex!=null&&o&&(r.profileIndex=t.profileIndex,n=!0),t.isEncrypted===!0&&!e.isEncrypted&&(r.isEncrypted=!0,n=!0);let i=t._syncMeta||{},s=["autoLockMinutes","version","protocol_handler",dn];for(let f of s)if(t[f]!=null&&t[f]!==e[f]){if(f==="version"&&e.version&&t.version<=e.version)continue;r[f]=t[f],n=!0}for(let f of Object.keys(t))f.startsWith("feature:")&&t[f]!==e[f]&&(r[f]=t[f],n=!0);if(t.apiKeyVault)if(!e.apiKeyVault||o)r.apiKeyVault=t.apiKeyVault,n=!0;else{let f=e.apiKeyVault.keys||{},u=t.apiKeyVault.keys||{},h={...f};for(let[d,y]of Object.entries(u)){let p=h[d];(!p||(y.updatedAt||0)>(p.updatedAt||0))&&(h[d]=y,n=!0)}n&&(r.apiKeyVault={...e.apiKeyVault,keys:h})}let a=e.vaultDocs||{},c=!1,l={...a};for(let f of Object.keys(t)){if(!f.startsWith("vaultDoc:"))continue;let u=t[f];if(!u||!u.path)continue;let h=l[u.path];(!h||(u.updatedAt||0)>(h.updatedAt||0))&&(l[u.path]=u,c=!0)}c&&(r.vaultDocs=l,n=!0),n&&await hn.set(r)}function ri(){N.storage.sync&&(un&&clearTimeout(un),un=setTimeout(()=>{un=null,Zu()},2e3))}async function Ka(){return(await hn.get({[dn]:!0}))[dn]}async function Va(){if(!(!N.storage.sync||!await Ka())){try{let e=await Ma();e&&await Ha(e)}catch{}N.storage.onChanged&&N.storage.onChanged.addListener((e,r)=>{r==="sync"&&Ma().then(n=>{n&&Ha(n)}).catch(n=>{})}),ri()}}b();var gr=N.storage.local,_e=t=>{},Le=new Map;function Fa(t){if(!t.startsWith("bunker://"))throw new Error("Invalid bunker URL: must start with bunker://");let e=new URL(t),r=e.hostname||e.pathname.replace("//","");if(!/^[0-9a-f]{64}$/i.test(r))throw new Error("Invalid bunker URL: pubkey must be 64 hex characters");let n=e.searchParams.getAll("relay");if(n.length===0)throw new Error("Invalid bunker URL: at least one relay is required");for(let i of n)try{let s=new URL(i);if(s.protocol!=="wss:"&&s.protocol!=="ws:")throw new Error(`Invalid relay protocol: ${s.protocol}`)}catch{throw new Error(`Invalid relay URL: ${i}`)}let o=e.searchParams.get("secret")||null;return{remotePubkey:r,relays:n,secret:o}}var Lt=class{constructor(e){this.url=e,this.ws=null,this.subscriptions=new Map,this.eoseCallbacks=new Map,this.connected=!1,this.reconnectTimer=null,this.reconnectAttempts=0,this.maxReconnectAttempts=5}connect(){return new Promise((e,r)=>{try{this.ws=new WebSocket(this.url)}catch(o){r(new Error(`Failed to create WebSocket: ${o.message}`));return}let n=setTimeout(()=>{this.ws?.close(),r(new Error(`Connection timeout: ${this.url}`))},1e4);this.ws.onopen=()=>{clearTimeout(n),this.connected=!0,this.reconnectAttempts=0,_e(`Connected to ${this.url}`),e()},this.ws.onerror=o=>{clearTimeout(n),_e(`WebSocket error: ${this.url}`),r(new Error(`WebSocket error: ${this.url}`))},this.ws.onclose=()=>{this.connected=!1,_e(`Disconnected from ${this.url}`),this.scheduleReconnect()},this.ws.onmessage=o=>{try{let i=JSON.parse(o.data);this.handleMessage(i)}catch(i){_e(`Failed to parse message: ${i.message}`)}}})}handleMessage(e){let[r,n,...o]=e;if(r==="EVENT"&&n&&o[0]){let i=o[0],s=this.subscriptions.get(n);s&&s(i)}else if(r==="EOSE"&&n){let i=this.eoseCallbacks.get(n);i&&(this.eoseCallbacks.delete(n),i())}else r==="OK"||r==="NOTICE"&&_e(`Relay notice: ${o[0]}`)}subscribe(e,r,n,o=null){if(!this.connected||!this.ws)throw new Error("Not connected");this.subscriptions.set(e,n),o&&this.eoseCallbacks.set(e,o),this.ws.send(JSON.stringify(["REQ",e,...r]))}unsubscribe(e){this.ws&&this.connected&&this.ws.send(JSON.stringify(["CLOSE",e])),this.subscriptions.delete(e),this.eoseCallbacks.delete(e)}publish(e){if(!this.connected||!this.ws)throw new Error("Not connected");this.ws.send(JSON.stringify(["EVENT",e]))}scheduleReconnect(){if(this.reconnectAttempts>=this.maxReconnectAttempts){_e(`Max reconnect attempts reached for ${this.url}`);return}let e=Math.min(1e3*Math.pow(2,this.reconnectAttempts),3e4);this.reconnectAttempts++,this.reconnectTimer=setTimeout(()=>{_e(`Reconnecting to ${this.url} (attempt ${this.reconnectAttempts})`),this.connect().catch(()=>{})},e)}close(){clearTimeout(this.reconnectTimer),this.maxReconnectAttempts=0,this.subscriptions.clear(),this.eoseCallbacks.clear(),this.ws&&(this.ws.close(),this.ws=null),this.connected=!1}},pn=class{constructor({remotePubkey:e,relays:r,secret:n}){this.remotePubkey=e,this.relayUrls=r,this.secret=n,this.sessionPrivkey=null,this.sessionPubkey=null,this.conversationKey=null,this.relays=[],this.pendingRequests=new Map,this.connected=!1,this.subId=`nostrkey-${crypto.randomUUID().slice(0,8)}`}async init(){if(this.sessionPrivkey)return;let e=await nn();this.sessionPrivkey=at(e.privateKey),this.sessionPubkey=e.publicKey,this.conversationKey=ke.utils.getConversationKey(this.sessionPrivkey,this.remotePubkey)}async connect(){await this.init();let e=this.relayUrls.map(o=>{let i=new Lt(o);return i.connect().then(()=>(this.relays.push(i),i))}),n=(await Promise.allSettled(e)).filter(o=>o.status==="fulfilled");if(n.length===0)throw new Error("Failed to connect to any relay");_e(`Connected to ${n.length}/${this.relayUrls.length} relays`);for(let o of this.relays)o.subscribe(this.subId,[{kinds:[24133],"#p":[this.sessionPubkey]}],i=>this.handleResponse(i));this.connected=!0,this.secret?await this.sendRequest("connect",[this.remotePubkey,this.secret]):await this.sendRequest("connect",[this.remotePubkey])}handleResponse(e){if(e.pubkey!==this.remotePubkey){_e(`Ignoring event from unknown pubkey: ${e.pubkey}`);return}try{let r=ke.decrypt(e.content,this.conversationKey),n=JSON.parse(r);_e(`Response: ${n.id} -> ${n.result?"ok":n.error}`);let o=this.pendingRequests.get(n.id);o&&(this.pendingRequests.delete(n.id),n.error?o.reject(new Error(n.error)):o.resolve(n.result))}catch(r){_e(`Failed to handle response: ${r.message}`)}}async sendRequest(e,r=[]){if(!this.connected&&e!=="connect")throw new Error("Not connected to bunker");let n=crypto.randomUUID(),o=JSON.stringify({id:n,method:e,params:r}),i=ke.encrypt(o,this.conversationKey),s=await Re({kind:24133,content:i,tags:[["p",this.remotePubkey]],created_at:Math.floor(Date.now()/1e3)},this.sessionPrivkey);for(let a of this.relays)try{a.publish(s)}catch(c){_e(`Failed to publish to ${a.url}: ${c.message}`)}return new Promise((a,c)=>{let l=setTimeout(()=>{this.pendingRequests.delete(n),c(new Error(`Request timeout: ${e}`))},3e4);this.pendingRequests.set(n,{resolve:f=>{clearTimeout(l),a(f)},reject:f=>{clearTimeout(l),c(f)}})})}async getPublicKey(){return await this.sendRequest("get_public_key")}async signEvent(e){let r=await this.sendRequest("sign_event",[JSON.stringify(e)]);return JSON.parse(r)}async nip04Encrypt(e,r){return await this.sendRequest("nip04_encrypt",[e,r])}async nip04Decrypt(e,r){return await this.sendRequest("nip04_decrypt",[e,r])}async nip44Encrypt(e,r){return await this.sendRequest("nip44_encrypt",[e,r])}async nip44Decrypt(e,r){return await this.sendRequest("nip44_decrypt",[e,r])}async ping(){return await this.sendRequest("ping")}getSessionInfo(){return{remotePubkey:this.remotePubkey,relayUrls:this.relayUrls,secret:this.secret,sessionPrivkey:Ae(this.sessionPrivkey),sessionPubkey:this.sessionPubkey}}disconnect(){for(let e of this.relays)e.unsubscribe(this.subId),e.close();this.relays=[],this.pendingRequests.clear(),this.connected=!1,_e("Disconnected from bunker")}};function Ju(t){let e=new pn({remotePubkey:t.remotePubkey,relays:t.relayUrls,secret:t.secret});return e.sessionPrivkey=at(t.sessionPrivkey),e.sessionPubkey=t.sessionPubkey,e.conversationKey=ke.utils.getConversationKey(e.sessionPrivkey,e.remotePubkey),e}async function De(t){if(Le.has(t)){let o=Le.get(t);if(o.connected)return o;o.disconnect(),Le.delete(t)}let r=(await gr.get({bunkerSessions:{}})).bunkerSessions?.[t];if(!r)throw new Error("No bunker session configured for this profile");let n=Ju(r);return await n.connect(),Le.set(t,n),n}async function $a(t,e){Le.has(t)&&(Le.get(t).disconnect(),Le.delete(t));let r=Fa(e),n=new pn(r);await n.connect();let i=(await gr.get({bunkerSessions:{}})).bunkerSessions||{};return i[t]=n.getSessionInfo(),await gr.set({bunkerSessions:i}),Le.set(t,n),n}async function qa(t){Le.has(t)&&(Le.get(t).disconnect(),Le.delete(t));let r=(await gr.get({bunkerSessions:{}})).bunkerSessions||{};delete r[t],await gr.set({bunkerSessions:r})}function ja(t){return Le.has(t)&&Le.get(t).connected}function za(t){try{return Fa(t),{valid:!0,error:null}}catch(e){return{valid:!1,error:e.message}}}b();var qe=t=>{},yn=class{constructor({relayUrls:e,userPubkey:r,secret:n}){this.relayUrls=e,this.userPubkey=r,this.secret=n,this.relays=[],this.authenticatedClients=new Set,this.subId=`bunker-srv-${crypto.randomUUID().slice(0,8)}`,this.active=!1,this._getPrivKey=null}async start({getPrivKey:e}){this._getPrivKey=e;let r=this.relayUrls.map(i=>{let s=new Lt(i);return s.connect().then(()=>(this.relays.push(s),s))}),o=(await Promise.allSettled(r)).filter(i=>i.status==="fulfilled");if(o.length===0)throw new Error("Failed to connect to any relay");qe(`Connected to ${o.length}/${this.relayUrls.length} relays`);for(let i of this.relays)i.subscribe(this.subId,[{kinds:[24133],"#p":[this.userPubkey],since:Math.floor(Date.now()/1e3)-5}],s=>this._handleRequest(s));this.active=!0,qe("Bunker server started")}stop(){for(let e of this.relays)e.unsubscribe(this.subId),e.close();this.relays=[],this.authenticatedClients.clear(),this.active=!1,this._getPrivKey=null,qe("Bunker server stopped")}getConnectionString(){let e=this.relayUrls.map(r=>`relay=${encodeURIComponent(r)}`).join("&");return`bunker://${this.userPubkey}?${e}&secret=${this.secret}`}async _handleRequest(e){let r=e.pubkey,n;try{n=await this._getPrivKey()}catch(u){qe(`Cannot get private key (locked?): ${u.message}`);return}let o;try{o=ke.utils.getConversationKey(n,r)}catch(u){qe(`Failed to derive conversation key: ${u.message}`);return}let i;try{let u=ke.decrypt(e.content,o);i=JSON.parse(u)}catch(u){qe(`Failed to decrypt request: ${u.message}`);return}let{id:s,method:a,params:c}=i;if(qe(`Request: ${a} (id=${s}) from ${r.slice(0,8)}...`),a!=="connect"&&!this.authenticatedClients.has(r)){await this._sendResponse(n,r,o,{id:s,result:null,error:"Unauthorized: send connect first"});return}let l=null,f=null;try{switch(a){case"connect":{let u=c[1];this.secret&&u!==this.secret?f="Invalid secret":(this.authenticatedClients.add(r),l="ack",qe(`Client authenticated: ${r.slice(0,8)}...`));break}case"get_public_key":l=this.userPubkey;break;case"sign_event":{let u=JSON.parse(c[0]),h=await Re(u,n);l=JSON.stringify(h);break}case"nip44_encrypt":{let u=c[0],h=c[1],d=ke.utils.getConversationKey(n,u);l=ke.encrypt(h,d);break}case"nip44_decrypt":{let u=c[0],h=c[1],d=ke.utils.getConversationKey(n,u);l=ke.decrypt(h,d);break}case"nip04_encrypt":{let u=c[0],h=c[1];l=await pt.encryptMessage(h,Ae(n),u);break}case"nip04_decrypt":{let u=c[0],h=c[1];l=await pt.decryptMessage(h,Ae(n),u);break}case"ping":l="pong";break;default:f=`Unsupported method: ${a}`}}catch(u){f=u.message,qe(`Error handling ${a}: ${u.message}`)}await this._sendResponse(n,r,o,{id:s,result:l,error:f})}async _sendResponse(e,r,n,o){let i=ke.encrypt(JSON.stringify(o),n),s=await Re({kind:24133,content:i,tags:[["p",r]],created_at:Math.floor(Date.now()/1e3)},e);for(let a of this.relays)try{a.publish(s)}catch(c){qe(`Failed to publish response to ${a.url}: ${c.message}`)}qe(`Response sent: ${o.id} ${o.error?"ERROR":"OK"}`)}};b();var gn="nostrkey:",Xu="nostrkey";function ni(t,e){return{kind:30078,content:e,tags:[["d",`${gn}${t}`],["client",Xu]],created_at:Math.floor(Date.now()/1e3)}}function oi(t,e){return{kind:5,content:"vault document deleted",tags:[["e",t],["a",`30078::${gn}${e}`]],created_at:Math.floor(Date.now()/1e3)}}function Wa(t){return{kinds:[30078],authors:[t]}}function Ga(t){if(t.kind!==30078)return null;let e=t.tags?.find(n=>n[0]==="d");if(!e||!e[1]?.startsWith(gn))return null;let r=e[1].slice(gn.length);return r?{path:r,content:t.content,createdAt:t.created_at,eventId:t.id}:null}var mn=N.storage.local,re={get:(...t)=>mn.get(...t),set:(...t)=>{let e=mn.set(...t);return e.then(()=>ri()).catch(()=>{}),e},clear:(...t)=>mn.clear(...t),remove:(...t)=>mn.remove(...t)},W=t=>{},xe={},He={mutex:new pr,release:null,tabId:null},Ct={total:0,processed:0},Je=null;function Q(t,e){e().then(r=>t(r)).catch(r=>{t(void 0)})}var ii=new Map,Qu=5,ef=1e4;function tf(t){let e=Date.now(),r=ii.get(t)||[];return r=r.filter(n=>e-n=Qu?(ii.set(t,r),!0):(r.push(e),ii.set(t,r),!1)}var be=new Map,lt=null,Pt=null,Ue=!0,Me=!1,Qt=900*1e3,Rt=null,wt=!1,wr=!0,mr=0,wn=0,Ya=new Map;(async()=>{W("[STARTUP] Reading persisted state...");let t=await re.get({autoLockMinutes:15,isEncrypted:!1,passwordHash:null,nostrAccessWhileLocked:!1,blockCrossOriginFrames:!0});W(`[STARTUP] isEncrypted=${t.isEncrypted}, passwordHash=${t.passwordHash?"EXISTS":"null"}, autoLockMinutes=${t.autoLockMinutes}`),Qt=t.autoLockMinutes*60*1e3,!t.isEncrypted&&t.passwordHash&&(W("[STARTUP] Self-healing: passwordHash exists but isEncrypted=false \u2192 fixing"),await re.set({isEncrypted:!0}),t.isEncrypted=!0),Me=t.isEncrypted,wt=!!t.nostrAccessWhileLocked,wr=t.blockCrossOriginFrames!==!1,Ue=Me,W(`[STARTUP] Final state: encryptionEnabled=${Me}, locked=${Ue}`);try{await Va(),W("[STARTUP] Platform sync initialized")}catch(e){W(`[STARTUP] Platform sync init error (non-fatal): ${e.message}`)}try{if(typeof browser<"u"&&browser.runtime.sendNativeMessage){let e=await browser.runtime.sendNativeMessage("com.nostrkey.Extension",{action:"getSharedProfiles"});if(e&&e.profiles&&e.profiles.length>0){let r=await re.get({profiles:[]}),n=rf(r.profiles,e.profiles);n.changed&&(await re.set({profiles:n.profiles}),W(`[STARTUP] Merged ${e.profiles.length} shared profile(s) from iOS app`))}}}catch(e){W(`[STARTUP] Shared profiles check skipped: ${e.message}`)}})();function rf(t,e){let r=!1,n=[...t];for(let o of e){if(!o.pubKey)continue;let i=n.findIndex(s=>s.pubKey===o.pubKey);if(i===-1)n.push({name:o.name||"Shared Profile",privKey:o.privKey||"",pubKey:o.pubKey,hosts:{},relays:o.relays||[],type:"local",updatedAt:o.lastSyncedAt?new Date(o.lastSyncedAt).getTime():Date.now()}),r=!0;else{let s=n[i],a=s.updatedAt||0,c=o.lastSyncedAt?new Date(o.lastSyncedAt).getTime():0;c>a&&o.privKey&&!s.privKey&&(n[i]={...s,privKey:o.privKey,name:o.name||s.name,relays:o.relays||s.relays,updatedAt:c},r=!0)}}return{profiles:n,changed:r}}var ai="nostrkey-auto-lock";function Ut(){if(Rt&&(clearTimeout(Rt),Rt=null),Ue||Qt<=0){N.alarms?.clear(ai).catch(()=>{});return}N.alarms?N.alarms.create(ai,{delayInMinutes:Qt/6e4}):Rt=setTimeout(()=>{li()},Qt)}N.alarms?.onAlarm&&N.alarms.onAlarm.addListener(t=>{t.name===ai&&li()});var Za=new pr;async function li(){let t=await Za.acquire();try{wt||be.clear(),lt=null,Pt=null,Ue=!0,Rt&&(clearTimeout(Rt),Rt=null),W(`Session locked. Keys retained: ${wt&&be.size>0}`)}finally{t()}}async function si(t){let e=await Za.acquire();try{let r=Date.now();if(r=3){let a=3e4*Math.pow(2,Math.floor((mr-3)/3));wn=Date.now()+a,W(`[SECURITY] ${mr} failed attempts. Cooldown: ${a/1e3}s`)}return{success:!1,error:"Invalid password"}}mr=0,wn=0;let o=await $e(),i=!1;for(let a=0;a{if(W(t),nf.has(t.kind)&&!of(e))return W(`[SECURITY] Blocked ${t.kind} from non-extension sender`),r({success:!1,error:"Unauthorized sender"}),!0;let n=crypto.randomUUID(),o;switch(t.kind){case"closePrompt":return He.release?.(),r(!0),!0;case"allowed":return Ut(),ci(t),r(!0),!0;case"denied":return En(t),r(!0),!0;case"generatePrivateKey":return(async()=>{try{let i=await af();r(i)}catch{r(null)}})(),!0;case"savePrivateKey":return Ut(),uf(t.payload);case"getNpub":return(async()=>{try{let i=await ff(t.payload);r(i)}catch{r(null)}})(),!0;case"getNsec":return Ut(),(async()=>{try{let i=await Xa(t.payload);r(i)}catch{r(null)}})(),!0;case"calcPubKey":return r(Pe(t.payload)),!0;case"npubEncode":return r(Te.npubEncode(t.payload)),!0;case"copy":return typeof navigator<"u"&&navigator.clipboard?.writeText?navigator.clipboard.writeText(t.payload).then(()=>r(!0)).catch(()=>r(!1)):r(!1),!0;case"isLocked":return(async()=>{try{let i=await Ja();W(`[isLocked] Sending response: ${i}`),r(i)}catch(i){W(`[isLocked] Error: ${i.message}`),r(!1)}})(),!0;case"isEncrypted":return(async()=>{try{let i=await re.get({isEncrypted:!1,passwordHash:null});W(`[isEncrypted] storage: isEncrypted=${i.isEncrypted}, passwordHash=${i.passwordHash?"EXISTS":"null"}`),!i.isEncrypted&&i.passwordHash&&(W("[isEncrypted] Self-healing: passwordHash exists but flag=false"),await re.set({isEncrypted:!0}),i.isEncrypted=!0),Me=i.isEncrypted,W(`[isEncrypted] Sending response: ${Me}`),r(Me)}catch(i){W(`[isEncrypted] Error: ${i.message}`),r(!1)}})(),!0;case"hasEncryptedData":return(async()=>{try{let i=await re.get({passwordHash:null,profiles:[]}),s=!!i.passwordHash,a=0;if(W(`[hasEncryptedData] passwordHash=${s}, profiles=${Array.isArray(i.profiles)?i.profiles.length:"not-array"}`),Array.isArray(i.profiles))for(let l=0;l0;W(`[hasEncryptedData] Result: found=${c}, hasPasswordHash=${s}, encryptedProfiles=${a}`),c&&!Me&&(W("[hasEncryptedData] Self-healing: setting isEncrypted=true, locked=true"),await re.set({isEncrypted:!0}),Me=!0,Ue=!0),r({found:c,hasPasswordHash:s,encryptedProfiles:a})}catch{r({found:!1,hasPasswordHash:!1,encryptedProfiles:0})}})(),!0;case"unlock":return Q(r,()=>si(t.payload)),!0;case"lock":return li().then(()=>r(!0)),!0;case"setPassword":return(async()=>{try{await lf(),await Ba(t.payload),Me=!0;let i=await si(t.payload);N.runtime.sendMessage({kind:"passwordStateChanged",hasPassword:!0}).catch(()=>{}),N.runtime.sendMessage({kind:"backupNeeded"}).catch(()=>{}),r(i)}catch(i){r({success:!1,error:i.message})}})(),!0;case"changePassword":return(async()=>{try{let{oldPassword:i,newPassword:s}=t.payload;if(!await cn(i)){r({success:!1,error:"Invalid current password"});return}await Sa(i,s);let c=await si(s);N.runtime.sendMessage({kind:"passwordStateChanged",hasPassword:!0}).catch(()=>{}),N.runtime.sendMessage({kind:"backupNeeded"}).catch(()=>{}),r(c)}catch(i){r({success:!1,error:i.message})}})(),!0;case"removePassword":return(async()=>{try{await Aa(t.payload),be.clear(),lt=null,Pt=null,Ue=!1,Me=!1,N.runtime.sendMessage({kind:"passwordStateChanged",hasPassword:!1}).catch(()=>{}),r({success:!0})}catch(i){r({success:!1,error:i.message})}})(),!0;case"resetAllData":return(async()=>{try{await re.clear(),be.clear(),lt=null,Pt=null,Ue=!1,Me=!1,wt=!1,wr=!0,await re.set({profiles:[{name:"Default Nostr Profile",privKey:"",pubKey:""}],profileIndex:0,isEncrypted:!1,passwordHash:null,passwordSalt:null}),N.runtime.sendMessage({kind:"dataReset"}).catch(()=>{}),r({success:!0})}catch(i){r({success:!1,error:i.message})}})(),!0;case"setAutoLockTimeout":{let i=[0,5,15,30,60,90,180],s=Number(t.payload);return i.includes(s)?(Qt=s*60*1e3,re.set({autoLockMinutes:s}),Ut(),r(!0),!0):(r(!1),!0)}case"getAutoLockTimeout":return Q(r,async()=>{let{autoLockMinutes:i}=await re.get({autoLockMinutes:15});return i}),!0;case"resetAutoLock":return Ut(),r(!0),!0;case"getNostrAccessWhileLocked":return r(wt),!0;case"setNostrAccessWhileLocked":return wt=!!t.payload,re.set({nostrAccessWhileLocked:!!t.payload}),!t.payload&&Ue&&be.clear(),r(!0),!0;case"getBlockCrossOriginFrames":return r(wr),!0;case"setBlockCrossOriginFrames":return wr=!!t.payload,re.set({blockCrossOriginFrames:!!t.payload}),r(!0),!0;case"getActiveProfileInfo":return(async()=>{try{let i=await ne(),a=(await $e())[i];if(!a){W("[getActiveProfileInfo] No profile found at index "+i),r({name:"Unknown",npub:"",hasKeys:!1});return}let c="";a.type==="bunker"&&a.remotePubkey?c=Te.npubEncode(a.remotePubkey):a.pubKey&&(c=Te.npubEncode(a.pubKey));let l={name:a.name||"Unnamed Profile",npub:c,hasKeys:be.has(i),isBunker:a.type==="bunker"};W("[getActiveProfileInfo] Sending: "+JSON.stringify(l)),r(l)}catch(i){W("[getActiveProfileInfo] Error: "+i.message),r({name:"Error",npub:"",hasKeys:!1})}})(),!0;case"ncryptsec.decrypt":return Q(r,async()=>{try{let{ncryptsec:i,password:s}=t.payload;return{success:!0,hexKey:Ae(pa(i,s))}}catch(i){return{success:!1,error:i.message||"Decryption failed"}}}),!0;case"ncryptsec.encrypt":return Q(r,async()=>{try{let{profileIndex:i,password:s}=t.payload,a=await se(i);if(a?.type==="bunker")return{success:!1,error:"Cannot export bunker profile as ncryptsec"};let c=await br(i,a);return{success:!0,ncryptsec:ha(at(c),s)}}catch(i){return{success:!1,error:i.message||"Encryption failed"}}}),!0;case"seedPhrase.fromKey":return Q(r,async()=>{try{let i=t.payload,s=await se(i);if(s?.type==="bunker")return{success:!1,error:"Cannot export bunker profile as seed phrase"};let a=await br(i,s);return{success:!0,seedPhrase:ba(a)}}catch(i){return{success:!1,error:i.message||"Failed to generate seed phrase"}}}),!0;case"seedPhrase.toKey":return Q(r,async()=>{try{let{hexKey:i,pubKey:s}=xa(t.payload);return{success:!0,hexKey:i,pubKey:s}}catch(i){return{success:!1,error:i.message||"Invalid seed phrase"}}}),!0;case"seedPhrase.validate":return r(Fo(t.payload)),!0;case"getProfileType":return Q(r,async()=>{let i=t.payload??await ne();return(await se(i))?.type||"local"}),!0;case"bunker.connect":return Q(r,async()=>{try{let{profileIndex:i,bunkerUrl:s}=t.payload,c=await(await $a(i,s)).getPublicKey(),l=await $e();return l[i].remotePubkey=c,l[i].bunkerUrl=s,await re.set({profiles:l}),{success:!0,remotePubkey:c}}catch(i){return{success:!1,error:i.message}}}),!0;case"bunker.disconnect":return Q(r,async()=>{try{let i=t.payload;return await qa(i),{success:!0}}catch(i){return{success:!1,error:i.message}}}),!0;case"bunker.status":return Q(r,async()=>{let i=t.payload??await ne();return{connected:ja(i)}}),!0;case"bunker.ping":return Q(r,async()=>{try{let i=t.payload??await ne();return{success:!0,result:await(await De(i)).ping()}}catch(i){return{success:!1,error:i.message}}}),!0;case"bunker.validateUrl":return r(za(t.payload)),!0;case"bunkerServer.start":return Q(r,async()=>{try{Je&&(Je.stop(),Je=null);let i=await ct(),s=t.payload?.relayUrls||["wss://relay.nostrkey.com"],a=crypto.randomUUID().replace(/-/g,"").slice(0,16),c=new yn({relayUrls:s,userPubkey:i,secret:a});return await c.start({getPrivKey:je}),Je=c,{success:!0,uri:c.getConnectionString()}}catch(i){return{success:!1,error:i.message}}}),!0;case"bunkerServer.stop":return Q(r,async()=>(Je&&(Je.stop(),Je=null),{success:!0})),!0;case"bunkerServer.status":return r({active:!!Je?.active,uri:Je?.getConnectionString()||null,clientCount:Je?.authenticatedClients.size||0}),!0;case"vault.publish":return Q(r,async()=>{try{let{path:i,content:s}=t.payload,a=await ct(),c=await bn({pubKey:a,plainText:s}),l=ni(i,c),f=await ne(),u=await se(f),h;if(u.type==="bunker")h=await(await De(f)).signEvent(l);else{let d=await je();h=await Re(l,d)}return await Xt("write",async d=>{for(let y of d)try{y.publish(h)}catch{}}),{success:!0,eventId:h.id,createdAt:h.created_at}}catch(i){return{success:!1,error:i.message}}}),!0;case"vault.fetch":return Q(r,async()=>{try{let i=await ct(),s=Wa(i),a=[];await Xt("read",async u=>{let h=u.map(d=>new Promise(y=>{let p=`vault-${crypto.randomUUID().slice(0,8)}`,w=setTimeout(()=>{try{d.unsubscribe(p)}catch{}y()},15e3);d.subscribe(p,[s],k=>{a.push(k)},()=>{clearTimeout(w);try{d.unsubscribe(p)}catch{}y()})}));await Promise.all(h)});let c=new Map;for(let u of a){let h=Ga(u);if(!h)continue;let d=c.get(h.path);(!d||h.createdAt>d.createdAt)&&c.set(h.path,{event:u,parsed:h})}let l=[],f=await ct();for(let{event:u,parsed:h}of c.values())try{let d=await xn({pubKey:f,cipherText:u.content});l.push({path:h.path,content:d,createdAt:h.createdAt,eventId:h.eventId})}catch{}return{success:!0,documents:l}}catch(i){return{success:!1,error:i.message}}}),!0;case"vault.delete":return Q(r,async()=>{try{let{path:i,eventId:s}=t.payload,a=oi(s,i),c=await ne(),l=await se(c),f;if(l.type==="bunker")f=await(await De(c)).signEvent(a);else{let u=await je();f=await Re(a,u)}return await Xt("write",async u=>{for(let h of u)try{h.publish(f)}catch{}}),{success:!0}}catch(i){return{success:!1,error:i.message}}}),!0;case"vault.getRelays":return Q(r,async()=>{try{let s=(await vn()).relays||[],a=s.filter(l=>l.read).map(l=>l.url),c=s.filter(l=>l.write).map(l=>l.url);return{read:a,write:c}}catch{return{read:[],write:[]}}}),!0;case"apikeys.publish":return Q(r,async()=>{try{let{keys:i}=t.payload,s=await ct(),a=JSON.stringify(i),c=await bn({pubKey:s,plainText:a}),l=ni("vault/api-keys",c),f=await ne(),u=await se(f),h;if(u.type==="bunker")h=await(await De(f)).signEvent(l);else{let d=await je();h=await Re(l,d)}return await Xt("write",async d=>{for(let y of d)try{y.publish(h)}catch{}}),{success:!0,eventId:h.id,createdAt:h.created_at}}catch(i){return{success:!1,error:i.message}}}),!0;case"apikeys.fetch":return Q(r,async()=>{try{let i=await ct(),s={kinds:[30078],authors:[i],"#d":["nostrkey:vault/api-keys"]},a=[];await Xt("read",async u=>{let h=u.map(d=>new Promise(y=>{let p=`apikeys-${crypto.randomUUID().slice(0,8)}`,w=setTimeout(()=>{try{d.unsubscribe(p)}catch{}y()},15e3);d.subscribe(p,[s],k=>{a.push(k)},()=>{clearTimeout(w);try{d.unsubscribe(p)}catch{}y()})}));await Promise.all(h)});let c=null;for(let u of a)(!c||u.created_at>c.created_at)&&(c=u);if(!c)return{success:!0,keys:null,eventId:null,createdAt:null};let l=await xn({pubKey:i,cipherText:c.content});return{success:!0,keys:JSON.parse(l),eventId:c.id,createdAt:c.created_at}}catch(i){return{success:!1,error:i.message}}}),!0;case"apikeys.delete":return Q(r,async()=>{try{let{eventId:i}=t.payload,s=oi(i,"vault/api-keys"),a=await ne(),c=await se(a),l;if(c.type==="bunker")l=await(await De(a)).signEvent(s);else{let f=await je();l=await Re(s,f)}return await Xt("write",async f=>{for(let u of f)try{u.publish(l)}catch{}}),{success:!0}}catch(i){return{success:!1,error:i.message}}}),!0;case"apikeys.encrypt":return Q(r,async()=>{try{let{plainText:i}=t.payload,s=await ct();return{success:!0,cipherText:await bn({pubKey:s,plainText:i})}}catch(i){return{success:!1,error:i.message}}}),!0;case"apikeys.decrypt":return Q(r,async()=>{try{let{cipherText:i}=t.payload,s=await ct();return{success:!0,plainText:await xn({pubKey:s,cipherText:i})}}catch(i){return{success:!1,error:i.message}}}),!0;case"backup.export":return Q(r,async()=>{if(!lt)return{success:!1,error:"Extension must be unlocked to create a backup"};let i=await re.get({profiles:[],profileIndex:0,isEncrypted:!1,passwordHash:null,passwordSalt:null,apiKeyVault:null,vaultDocs:null,nostrAccessWhileLocked:!1,blockCrossOriginFrames:!0,autoLockMinutes:15,version:null}),s=JSON.stringify(i),a=await qo(s,lt,Pt),c=N.runtime.getManifest?.()?.version||"unknown";return{success:!0,envelope:{format:"nostrkey-backup",version:1,createdAt:new Date().toISOString(),extensionVersion:c,profileCount:Array.isArray(i.profiles)?i.profiles.length:0,payload:JSON.parse(a)}}}),!0;case"backup.import":return Q(r,async()=>{try{let{envelope:i,password:s}=t.payload;if(!i||i.format!=="nostrkey-backup")return{success:!1,error:"Not a valid NostrKey backup file"};if(typeof i.version!="number"||i.version>1)return{success:!1,error:"Backup version not supported. Update NostrKey and try again."};let a=JSON.stringify(i.payload),c;try{c=await Tt(a,s)}catch{return{success:!1,error:"Wrong password \u2014 could not decrypt backup"}}let l=JSON.parse(c);await re.set(l),Me=!!l.isEncrypted,Ue=!1;let f=crypto.getRandomValues(new Uint8Array(16));if(lt=await yr(s,f),Pt=f,wt=l.nostrAccessWhileLocked!==!1,wr=l.blockCrossOriginFrames!==!1,typeof l.autoLockMinutes=="number"&&(Qt=l.autoLockMinutes*60*1e3),be.clear(),Array.isArray(l.profiles))for(let h=0;h{let{protocol_handler:i}=await re.get(["protocol_handler"]);if(!i)return!1;let{url:s}=t.payload,a=s.split("nostr:")[1];if(!a)return!1;try{let c=Te.decode(a),{type:l,data:f}=c,u={raw:a,hrp:l,hex:l==="naddr"?c.author||a:f||a,p_or_e:{npub:"p",note:"e",nprofile:"p",nevent:"e",naddr:"a"}[l]||"",u_or_n:{npub:"u",note:"n",nprofile:"u",nevent:"n",naddr:"n"}[l]||"",relay0:c.relays?.[0]||"",relay1:c.relays?.[1]||"",relay2:c.relays?.[2]||""},h=i;for(let[d,y]of Object.entries(u))h=h.replace(new RegExp(`\\{ *${d} *\\}`,"g"),y);return h}catch{return!1}}),!0;case"getPubKey":case"signEvent":case"nip04.encrypt":case"nip04.decrypt":case"nip44.encrypt":case"nip44.decrypt":case"getRelays":case"addRelay":case"exportProfile":return xe[n]=r,Object.keys(xe).length===1&&(Ct={total:0,processed:0}),Ct.total++,cf(n,t),setTimeout(()=>{xe[n]&&En({payload:n,origKind:t.kind,host:t.host}),He.release?.()},1e4),!0;default:return!1}});async function sf(){if(He.tabId!==null)try{await N.tabs.get(He.tabId)}catch{He.release?.(),He.tabId=null}}async function af(){return(await nn()).privateKey}async function cf(t,{kind:e,host:r,payload:n}){if(r){let p=Date.now(),w=Ya.get(r)||{count:0,resetAt:p+6e4};if(p>w.resetAt&&(w.count=0,w.resetAt=p+6e4),w.count++,Ya.set(r,w),w.count>5){W(`[SECURITY] Rate limited ${r} \u2014 ${w.count} requests in 60s`);let k=xe[t];delete xe[t],k?.({error:"rate_limited",message:"Too many requests. Please wait a moment."});return}}let o=await ne();if(!((await se(o))?.type==="bunker")&&(e!=="getPubKey"&&e!=="getRelays"&&e!=="addRelay"&&e!=="exportProfile")&&await Ja()&&!(wt&&be.has(o))){let w=be.size===0;try{let[O]=await N.tabs.query({active:!0,currentWindow:!0});O?.id&&N.tabs.sendMessage(O.id,{kind:"showLockedSheet",firstUnlock:w}).catch(()=>{})}catch{}let k=xe[t];delete xe[t],k?.({error:"locked",message:"Extension is locked. Please unlock with your master password."});return}if(tf(r)){let p=xe[t];delete xe[t],p?.({error:"rate_limited",message:"Too many requests. Please wait."}),W(`Rate limited: ${r}`);return}await sf(),He.release=await He.mutex.acquire(),Ct.processed++;let c=Ct.processed,l=Ct.total,f=e==="signEvent"?`signEvent:${n.kind}`:e,u=await ka(r,f);if(u==="allow"){ci({payload:t,origKind:e,event:n,remember:!1,host:r}),He.release();return}if(u==="deny"){En({payload:t,origKind:e,host:r}),He.release();return}try{let[p]=await N.tabs.query({active:!0,currentWindow:!0});if(p?.id){let w=await N.tabs.sendMessage(p.id,{kind:"showPermissionSheet",host:r,permissionKind:e,queuePosition:c,queueTotal:l});if(w){w.allowed?ci({payload:t,origKind:e,event:n,remember:w.remember,host:r}):En({payload:t,origKind:e,event:n,remember:w.remember,host:r}),He.release();return}}}catch(p){W("Bottom sheet unavailable, falling back to tab:",p.message)}let h=new URLSearchParams({uuid:t,kind:e,host:r,payload:JSON.stringify(n||!1),queuePosition:c,queueTotal:l}),d=await N.tabs.getCurrent(),y=await N.tabs.create({url:N.runtime.getURL(`permission/permission.html?${h.toString()}`),openerTabId:d?.id});return He.tabId=y.id,!0}function ci({payload:t,origKind:e,event:r,remember:n,host:o}){let i=xe[t];if(delete xe[t],Object.keys(xe).length===0&&(Ct={total:0,processed:0}),n){let s=e==="signEvent"?`signEvent:${r.kind}`:e;zo(o,s,"allow")}if(i){let s=a=>{W(`Error in ${e}: ${a.message}`),i({error:"bunker_error",message:a.message})};switch(e){case"getPubKey":ct().then(a=>i(a)).catch(s);break;case"signEvent":df(r,o).then(a=>i(a)).catch(s);break;case"nip04.encrypt":hf(r).then(a=>i(a)).catch(s);break;case"nip04.decrypt":pf(r).then(a=>i(a)).catch(s);break;case"nip44.encrypt":bn(r).then(a=>i(a)).catch(s);break;case"nip44.decrypt":xn(r).then(a=>i(a)).catch(s);break;case"getRelays":yf().then(a=>i(a)).catch(s);break;case"addRelay":gf(r.url).then(a=>i(a)).catch(s);break;case"exportProfile":mf().then(a=>i(a)).catch(s);break}}}function En({origKind:t,host:e,payload:r,remember:n,event:o}){let i=xe[r];if(delete xe[r],Object.keys(xe).length===0&&(Ct={total:0,processed:0}),n){let s=t==="signEvent"?`signEvent:${o.kind}`:t;zo(e,s,"deny")}return i?.(void 0),!1}async function lf(){let t=await $e(),e=!1;for(let r=0;r=o.length)throw new Error("Invalid profile index");let i=Pe(n);return o[t].pubKey=i,await Wo()&<?(o[t].privKey=await qo(n,lt,Pt),be.set(t,n)):o[t].privKey=n,await re.set({profiles:o}),!0}async function Xa(t){let e=await se(t);if(e.type==="bunker")return null;let r=await br(t,e);return Te.nsecEncode(r)}async function ff(t){let e=await se(t);if(!e)return null;if(e.type==="bunker")return e.remotePubkey?Te.npubEncode(e.remotePubkey):null;if(e.pubKey)return Te.npubEncode(e.pubKey);try{let r=await br(t,e);if(!r||typeof r!="string"||r.length!==64)return null;let n=Pe(r);return Te.npubEncode(n)}catch{return null}}async function br(t,e){if(Ze(e.privKey)){if(be.has(t))return be.get(t);throw new Error("Extension is locked \u2014 cannot access private key")}return e.privKey}async function je(){let t=await ne(),e=await vn(),r=await br(t,e);return at(r)}async function ct(){let t=await ne(),e=await se(t);if(e.type==="bunker"){if(e.remotePubkey)return e.remotePubkey;let i=await(await De(t)).getPublicKey(),s=await an("profiles");return s[t].remotePubkey=i,await re.set({profiles:s}),i}if(e.pubKey)return e.pubKey;let r=await je();return Pe(Ae(r))}async function vn(){let t=await ne();return(await an("profiles"))[t]}async function df(t,e){t=JSON.parse(JSON.stringify(t));let r=await ne();if((await se(r)).type==="bunker")t=await(await De(r)).signEvent(t);else{let o=await je();t=await Re(t,o)}return Na({event:t,metadata:{host:e,signed_at:Math.round(Date.now()/1e3)}}),t}async function hf({pubKey:t,plainText:e}){let r=await ne();if((await se(r)).type==="bunker")return(await De(r)).nip04Encrypt(t,e);let o=await je();return pt.encryptMessage(e,Ae(o),t)}async function pf({pubKey:t,cipherText:e}){let r=await ne();if((await se(r)).type==="bunker")return(await De(r)).nip04Decrypt(t,e);let o=await je();return pt.decryptMessage(e,Ae(o),t)}async function bn({pubKey:t,plainText:e}){let r=await ne();if((await se(r)).type==="bunker")return(await De(r)).nip44Encrypt(t,e);let o=await je(),i=st.v2.utils.getConversationKey(o,t);return st.v2.encrypt(e,i)}async function xn({pubKey:t,cipherText:e}){let r=await ne();if((await se(r)).type==="bunker")return(await De(r)).nip44Decrypt(t,e);let o=await je(),i=st.v2.utils.getConversationKey(o,t);return st.v2.decrypt(e,i)}async function yf(){let e=(await vn()).relays,r={};return e.forEach(n=>{let{url:o,read:i,write:s}=n;r[o]={read:i,write:s}}),r}async function gf(t){let e;try{e=new URL(t)}catch{throw new Error("Invalid URL")}if(e.protocol!=="wss:")throw new Error("Must be a wss:// URL");let r=await $e(),n=await ne(),o=r[n];return o.relays||(o.relays=[]),o.relays.some(i=>i.url===e.href)?{success:!0,message:"Relay already exists"}:(o.relays.push({url:e.href,read:!0,write:!0}),o.updatedAt=Math.floor(Date.now()/1e3),await re.set({profiles:r}),{success:!0,message:"Relay added"})}async function mf(){let t=await ne(),e=await se(t);if(!e)throw new Error("No active profile");if(e.type==="bunker")return{name:e.name,type:"bunker",bunkerUrl:e.bunkerUrl||"",exportedAt:new Date().toISOString(),source:"NostrKey"};let r="";e.pubKey&&(r=Te.npubEncode(e.pubKey));let n="";try{n=await Xa(t)}catch{throw new Error("Cannot export while locked. Please unlock first.")}return{name:e.name,npub:r,nsec:n,relays:(e.relays||[]).map(o=>o.url),exportedAt:new Date().toISOString(),source:"NostrKey"}}async function Xt(t,e){let o=((await vn()).relays||[]).filter(a=>t==="read"?a.read:a.write).map(a=>a.url);if(o.length===0)throw new Error("No relays configured");let i=[],s=o.map(async a=>{let c=new Lt(a);try{await c.connect(),i.push(c)}catch{}});if(await Promise.allSettled(s),i.length===0)throw new Error("Failed to connect to any relay");try{await e(i)}finally{for(let a of i)a.close()}}})(); +zoo`.split("\n"); + + // src/utilities/seedphrase.js + function keyToSeedPhrase(hexKey) { + const bytes = hexToBytes2(hexKey); + return entropyToMnemonic(bytes, wordlist); + } + function seedPhraseToKey(phrase) { + const entropy = mnemonicToEntropy(phrase.trim().toLowerCase(), wordlist); + const hexKey = bytesToHex3(entropy); + const pubKey = getPublicKeySync(hexKey); + return { hexKey, pubKey }; + } + function isValidSeedPhrase(phrase) { + try { + return validateMnemonic(phrase.trim().toLowerCase(), wordlist); + } catch { + return false; + } + } + + // src/utilities/keys.js + init_process(); + async function generateKeyPair2() { + const keyPair = await generateKeyPair(); + return { + privateKey: keyPair.privateKey, + publicKey: keyPair.publicKey.hex + }; + } + + // node_modules/async-mutex/index.mjs + init_process(); + var E_TIMEOUT = new Error("timeout while waiting for mutex to become available"); + var E_ALREADY_LOCKED = new Error("mutex already locked"); + var E_CANCELED = new Error("request for lock canceled"); + var __awaiter$2 = function(thisArg, _arguments, P, generator) { + function adopt(value) { + return value instanceof P ? value : new P(function(resolve) { + resolve(value); + }); + } + return new (P || (P = Promise))(function(resolve, reject) { + function fulfilled(value) { + try { + step(generator.next(value)); + } catch (e) { + reject(e); + } + } + function rejected(value) { + try { + step(generator["throw"](value)); + } catch (e) { + reject(e); + } + } + function step(result) { + result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); + } + step((generator = generator.apply(thisArg, _arguments || [])).next()); + }); + }; + var Semaphore = class { + constructor(_value, _cancelError = E_CANCELED) { + this._value = _value; + this._cancelError = _cancelError; + this._queue = []; + this._weightedWaiters = []; + } + acquire(weight = 1, priority = 0) { + if (weight <= 0) + throw new Error(`invalid weight ${weight}: must be positive`); + return new Promise((resolve, reject) => { + const task = { resolve, reject, weight, priority }; + const i = findIndexFromEnd(this._queue, (other) => priority <= other.priority); + if (i === -1 && weight <= this._value) { + this._dispatchItem(task); + } else { + this._queue.splice(i + 1, 0, task); + } + }); + } + runExclusive(callback_1) { + return __awaiter$2(this, arguments, void 0, function* (callback, weight = 1, priority = 0) { + const [value, release] = yield this.acquire(weight, priority); + try { + return yield callback(value); + } finally { + release(); + } + }); + } + waitForUnlock(weight = 1, priority = 0) { + if (weight <= 0) + throw new Error(`invalid weight ${weight}: must be positive`); + if (this._couldLockImmediately(weight, priority)) { + return Promise.resolve(); + } else { + return new Promise((resolve) => { + if (!this._weightedWaiters[weight - 1]) + this._weightedWaiters[weight - 1] = []; + insertSorted(this._weightedWaiters[weight - 1], { resolve, priority }); + }); + } + } + isLocked() { + return this._value <= 0; + } + getValue() { + return this._value; + } + setValue(value) { + this._value = value; + this._dispatchQueue(); + } + release(weight = 1) { + if (weight <= 0) + throw new Error(`invalid weight ${weight}: must be positive`); + this._value += weight; + this._dispatchQueue(); + } + cancel() { + this._queue.forEach((entry) => entry.reject(this._cancelError)); + this._queue = []; + } + _dispatchQueue() { + this._drainUnlockWaiters(); + while (this._queue.length > 0 && this._queue[0].weight <= this._value) { + this._dispatchItem(this._queue.shift()); + this._drainUnlockWaiters(); + } + } + _dispatchItem(item) { + const previousValue = this._value; + this._value -= item.weight; + item.resolve([previousValue, this._newReleaser(item.weight)]); + } + _newReleaser(weight) { + let called = false; + return () => { + if (called) + return; + called = true; + this.release(weight); + }; + } + _drainUnlockWaiters() { + if (this._queue.length === 0) { + for (let weight = this._value; weight > 0; weight--) { + const waiters = this._weightedWaiters[weight - 1]; + if (!waiters) + continue; + waiters.forEach((waiter) => waiter.resolve()); + this._weightedWaiters[weight - 1] = []; + } + } else { + const queuedPriority = this._queue[0].priority; + for (let weight = this._value; weight > 0; weight--) { + const waiters = this._weightedWaiters[weight - 1]; + if (!waiters) + continue; + const i = waiters.findIndex((waiter) => waiter.priority <= queuedPriority); + (i === -1 ? waiters : waiters.splice(0, i)).forEach(((waiter) => waiter.resolve())); + } + } + } + _couldLockImmediately(weight, priority) { + return (this._queue.length === 0 || this._queue[0].priority < priority) && weight <= this._value; + } + }; + function insertSorted(a, v) { + const i = findIndexFromEnd(a, (other) => v.priority <= other.priority); + a.splice(i + 1, 0, v); + } + function findIndexFromEnd(a, predicate) { + for (let i = a.length - 1; i >= 0; i--) { + if (predicate(a[i])) { + return i; + } + } + return -1; + } + var __awaiter$1 = function(thisArg, _arguments, P, generator) { + function adopt(value) { + return value instanceof P ? value : new P(function(resolve) { + resolve(value); + }); + } + return new (P || (P = Promise))(function(resolve, reject) { + function fulfilled(value) { + try { + step(generator.next(value)); + } catch (e) { + reject(e); + } + } + function rejected(value) { + try { + step(generator["throw"](value)); + } catch (e) { + reject(e); + } + } + function step(result) { + result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); + } + step((generator = generator.apply(thisArg, _arguments || [])).next()); + }); + }; + var Mutex = class { + constructor(cancelError) { + this._semaphore = new Semaphore(1, cancelError); + } + acquire() { + return __awaiter$1(this, arguments, void 0, function* (priority = 0) { + const [, releaser] = yield this._semaphore.acquire(1, priority); + return releaser; + }); + } + runExclusive(callback, priority = 0) { + return this._semaphore.runExclusive(() => callback(), 1, priority); + } + isLocked() { + return this._semaphore.isLocked(); + } + waitForUnlock(priority = 0) { + return this._semaphore.waitForUnlock(1, priority); + } + release() { + if (this._semaphore.isLocked()) + this._semaphore.release(); + } + cancel() { + return this._semaphore.cancel(); + } + }; + + // src/utilities/utils.js + init_process(); + + // src/utilities/browser-polyfill.js + init_process(); + var _browser = typeof browser !== "undefined" ? browser : typeof chrome !== "undefined" ? chrome : null; + if (!_browser) { + throw new Error("browser-polyfill: No extension API namespace found (neither browser nor chrome)."); + } + var isChrome = typeof browser === "undefined" && typeof chrome !== "undefined"; + function promisify(context, method) { + return (...args) => { + try { + const result = method.apply(context, args); + if (result && typeof result.then === "function") { + return result; + } + } catch (_) { + } + return new Promise((resolve, reject) => { + method.apply(context, [ + ...args, + (...cbArgs) => { + if (_browser.runtime && _browser.runtime.lastError) { + reject(new Error(_browser.runtime.lastError.message)); + } else { + resolve(cbArgs.length <= 1 ? cbArgs[0] : cbArgs); + } + } + ]); + }); + }; + } + var api = {}; + api.runtime = { + /** + * sendMessage – always returns a Promise. + */ + sendMessage(...args) { + if (!isChrome) { + return _browser.runtime.sendMessage(...args); + } + return promisify(_browser.runtime, _browser.runtime.sendMessage)(...args); + }, + /** + * onMessage – thin wrapper so callers use a consistent reference. + * The listener signature is (message, sender, sendResponse). + * On Chrome the listener can return `true` to keep the channel open, + * or return a Promise (MV3). Safari / Firefox expect a Promise return. + */ + onMessage: _browser.runtime.onMessage, + /** + * getURL – synchronous on all browsers. + */ + getURL(path) { + return _browser.runtime.getURL(path); + }, + /** + * openOptionsPage + */ + openOptionsPage() { + if (!isChrome) { + return _browser.runtime.openOptionsPage(); + } + return promisify(_browser.runtime, _browser.runtime.openOptionsPage)(); + }, + /** + * Expose the id for convenience. + */ + get id() { + return _browser.runtime.id; + } + }; + api.storage = { + local: { + get(...args) { + if (!isChrome) { + return _browser.storage.local.get(...args); + } + return promisify(_browser.storage.local, _browser.storage.local.get)(...args); + }, + set(...args) { + if (!isChrome) { + return _browser.storage.local.set(...args); + } + return promisify(_browser.storage.local, _browser.storage.local.set)(...args); + }, + clear(...args) { + if (!isChrome) { + return _browser.storage.local.clear(...args); + } + return promisify(_browser.storage.local, _browser.storage.local.clear)(...args); + }, + remove(...args) { + if (!isChrome) { + return _browser.storage.local.remove(...args); + } + return promisify(_browser.storage.local, _browser.storage.local.remove)(...args); + } + }, + // --- storage.sync ---------------------------------------------------------- + // Null when the browser doesn't support sync (older Safari, etc.) + sync: _browser.storage?.sync ? { + get(...args) { + if (!isChrome) { + return _browser.storage.sync.get(...args); + } + return promisify(_browser.storage.sync, _browser.storage.sync.get)(...args); + }, + set(...args) { + if (!isChrome) { + return _browser.storage.sync.set(...args); + } + return promisify(_browser.storage.sync, _browser.storage.sync.set)(...args); + }, + remove(...args) { + if (!isChrome) { + return _browser.storage.sync.remove(...args); + } + return promisify(_browser.storage.sync, _browser.storage.sync.remove)(...args); + }, + clear(...args) { + if (!isChrome) { + return _browser.storage.sync.clear(...args); + } + return promisify(_browser.storage.sync, _browser.storage.sync.clear)(...args); + }, + getBytesInUse(...args) { + if (!_browser.storage.sync.getBytesInUse) { + return Promise.resolve(0); + } + if (!isChrome) { + return _browser.storage.sync.getBytesInUse(...args); + } + return promisify(_browser.storage.sync, _browser.storage.sync.getBytesInUse)(...args); + } + } : null, + // --- storage.onChanged ----------------------------------------------------- + onChanged: _browser.storage?.onChanged || null + }; + api.tabs = { + create(...args) { + if (!isChrome) { + return _browser.tabs.create(...args); + } + return promisify(_browser.tabs, _browser.tabs.create)(...args); + }, + query(...args) { + if (!isChrome) { + return _browser.tabs.query(...args); + } + return promisify(_browser.tabs, _browser.tabs.query)(...args); + }, + remove(...args) { + if (!isChrome) { + return _browser.tabs.remove(...args); + } + return promisify(_browser.tabs, _browser.tabs.remove)(...args); + }, + update(...args) { + if (!isChrome) { + return _browser.tabs.update(...args); + } + return promisify(_browser.tabs, _browser.tabs.update)(...args); + }, + get(...args) { + if (!isChrome) { + return _browser.tabs.get(...args); + } + return promisify(_browser.tabs, _browser.tabs.get)(...args); + }, + getCurrent(...args) { + if (!isChrome) { + return _browser.tabs.getCurrent(...args); + } + return promisify(_browser.tabs, _browser.tabs.getCurrent)(...args); + }, + sendMessage(...args) { + if (!isChrome) { + return _browser.tabs.sendMessage(...args); + } + return promisify(_browser.tabs, _browser.tabs.sendMessage)(...args); + } + }; + api.alarms = _browser.alarms ? { + create(...args) { + const result = _browser.alarms.create(...args); + return result && typeof result.then === "function" ? result : Promise.resolve(); + }, + clear(...args) { + if (!isChrome) { + return _browser.alarms.clear(...args); + } + return promisify(_browser.alarms, _browser.alarms.clear)(...args); + }, + onAlarm: _browser.alarms.onAlarm + } : null; + + // src/utilities/crypto.js + init_process(); + var PBKDF2_ITERATIONS = 6e5; + var SALT_BYTES = 16; + var IV_BYTES = 12; + function arrayBufferToBase64(buffer) { + const bytes = new Uint8Array(buffer); + let binary = ""; + for (let i = 0; i < bytes.length; i++) { + binary += String.fromCharCode(bytes[i]); + } + return btoa(binary); + } + function base64ToArrayBuffer(base642) { + const binary = atob(base642); + const bytes = new Uint8Array(binary.length); + for (let i = 0; i < binary.length; i++) { + bytes[i] = binary.charCodeAt(i); + } + return bytes.buffer; + } + async function deriveKey(password, salt) { + const enc = new TextEncoder(); + const keyMaterial = await crypto.subtle.importKey( + "raw", + enc.encode(password), + "PBKDF2", + false, + ["deriveKey"] + ); + return crypto.subtle.deriveKey( + { + name: "PBKDF2", + salt: salt instanceof Uint8Array ? salt : new Uint8Array(salt), + iterations: PBKDF2_ITERATIONS, + hash: "SHA-256" + }, + keyMaterial, + { name: "AES-GCM", length: 256 }, + false, + ["encrypt", "decrypt"] + ); + } + async function encryptWithKey(plaintext, key, salt) { + const iv = crypto.getRandomValues(new Uint8Array(IV_BYTES)); + const enc = new TextEncoder(); + const ciphertext = await crypto.subtle.encrypt( + { name: "AES-GCM", iv }, + key, + enc.encode(plaintext) + ); + return JSON.stringify({ + salt: arrayBufferToBase64(salt), + iv: arrayBufferToBase64(iv), + ciphertext: arrayBufferToBase64(ciphertext) + }); + } + async function encrypt4(plaintext, password) { + const salt = crypto.getRandomValues(new Uint8Array(SALT_BYTES)); + const iv = crypto.getRandomValues(new Uint8Array(IV_BYTES)); + const key = await deriveKey(password, salt); + const enc = new TextEncoder(); + const ciphertext = await crypto.subtle.encrypt( + { name: "AES-GCM", iv }, + key, + enc.encode(plaintext) + ); + return JSON.stringify({ + salt: arrayBufferToBase64(salt), + iv: arrayBufferToBase64(iv), + ciphertext: arrayBufferToBase64(ciphertext) + }); + } + async function decrypt4(encryptedData, password) { + const { salt, iv, ciphertext } = JSON.parse(encryptedData); + const saltBuf = new Uint8Array(base64ToArrayBuffer(salt)); + const ivBuf = new Uint8Array(base64ToArrayBuffer(iv)); + const ctBuf = base64ToArrayBuffer(ciphertext); + const key = await deriveKey(password, saltBuf); + const plainBuf = await crypto.subtle.decrypt( + { name: "AES-GCM", iv: ivBuf }, + key, + ctBuf + ); + const dec = new TextDecoder(); + return dec.decode(plainBuf); + } + async function hashPassword(password, salt) { + if (!salt) { + salt = crypto.getRandomValues(new Uint8Array(SALT_BYTES)); + } else if (typeof salt === "string") { + salt = new Uint8Array(base64ToArrayBuffer(salt)); + } + const enc = new TextEncoder(); + const keyMaterial = await crypto.subtle.importKey( + "raw", + enc.encode(password), + "PBKDF2", + false, + ["deriveBits"] + ); + const hashBits = await crypto.subtle.deriveBits( + { + name: "PBKDF2", + salt, + iterations: PBKDF2_ITERATIONS, + hash: "SHA-256" + }, + keyMaterial, + 256 + ); + return { + hash: arrayBufferToBase64(hashBits), + salt: arrayBufferToBase64(salt) + }; + } + async function verifyPassword(password, storedHash, storedSalt) { + const { hash } = await hashPassword(password, storedSalt); + return hash === storedHash; + } + + // src/utilities/utils.js + var storage = api.storage.local; + var RECOMMENDED_RELAYS = [ + new URL("wss://relay.damus.io"), + new URL("wss://relay.primal.net"), + new URL("wss://relay.snort.social"), + new URL("wss://relay.getalby.com/v1"), + new URL("wss://nos.lol") + ]; + async function getProfiles() { + let profiles = await storage.get({ profiles: [] }); + return profiles.profiles; + } + async function getProfile(index) { + let profiles = await getProfiles(); + return profiles[index]; + } + async function getProfileIndex() { + const index = await storage.get({ profileIndex: 0 }); + return index.profileIndex; + } + async function get(item) { + return (await storage.get(item))[item]; + } + async function getPermission(host, action) { + let index = await getProfileIndex(); + let profile = await getProfile(index); + return profile?.hosts?.[host]?.[action] || "ask"; + } + async function setPermission(host, action, perm, index = null) { + let profiles = await getProfiles(); + if (index == null) { + index = await getProfileIndex(); + } + let profile = profiles[index]; + let newPerms = profile.hosts[host] || {}; + newPerms = { ...newPerms, [action]: perm }; + profile.hosts[host] = newPerms; + profile.updatedAt = Math.floor(Date.now() / 1e3); + profiles[index] = profile; + await storage.set({ profiles }); + } + async function isEncrypted() { + const data = await storage.get({ isEncrypted: false, passwordHash: null, profiles: [] }); + if (data.isEncrypted) return true; + if (data.passwordHash) { + await storage.set({ isEncrypted: true }); + return true; + } + for (const profile of data.profiles) { + if (isEncryptedBlob(profile.privKey)) { + await storage.set({ isEncrypted: true }); + return true; + } + } + return false; + } + async function setPasswordHash(password) { + const { hash, salt } = await hashPassword(password); + await storage.set({ + passwordHash: hash, + passwordSalt: salt, + isEncrypted: true + }); + } + async function checkPassword(password) { + const data = await storage.get({ + passwordHash: null, + passwordSalt: null + }); + if (!data.passwordHash || !data.passwordSalt) return false; + return verifyPassword(password, data.passwordHash, data.passwordSalt); + } + async function removePasswordProtection(password) { + const valid = await checkPassword(password); + if (!valid) throw new Error("Invalid password"); + let profiles = await getProfiles(); + for (let i = 0; i < profiles.length; i++) { + if (profiles[i].type === "bunker") continue; + if (isEncryptedBlob(profiles[i].privKey)) { + profiles[i].privKey = await decrypt4(profiles[i].privKey, password); + } + } + await storage.set({ + profiles, + isEncrypted: false, + passwordHash: null, + passwordSalt: null + }); + } + async function encryptAllKeys(password) { + let profiles = await getProfiles(); + for (let i = 0; i < profiles.length; i++) { + if (profiles[i].type === "bunker") continue; + if (!isEncryptedBlob(profiles[i].privKey)) { + profiles[i].privKey = await encrypt4(profiles[i].privKey, password); + } + } + await setPasswordHash(password); + await storage.set({ profiles }); + } + async function changePasswordForKeys(oldPassword, newPassword) { + let profiles = await getProfiles(); + for (let i = 0; i < profiles.length; i++) { + if (profiles[i].type === "bunker") continue; + let hex = profiles[i].privKey; + if (isEncryptedBlob(hex)) { + hex = await decrypt4(hex, oldPassword); + } + profiles[i].privKey = await encrypt4(hex, newPassword); + } + const { hash, salt } = await hashPassword(newPassword); + await storage.set({ + profiles, + passwordHash: hash, + passwordSalt: salt, + isEncrypted: true + }); + } + async function getDecryptedPrivKey(profile, password) { + if (profile.type === "bunker") return ""; + if (isEncryptedBlob(profile.privKey)) { + return decrypt4(profile.privKey, password); + } + return profile.privKey; + } + function isEncryptedBlob(value) { + if (typeof value !== "string") return false; + try { + const parsed = JSON.parse(value); + return !!(parsed.salt && parsed.iv && parsed.ciphertext); + } catch { + return false; + } + } + + // src/utilities/db.js + init_process(); + + // node_modules/idb/build/index.js + init_process(); + var instanceOfAny = (object, constructors) => constructors.some((c) => object instanceof c); + var idbProxyableTypes; + var cursorAdvanceMethods; + function getIdbProxyableTypes() { + return idbProxyableTypes || (idbProxyableTypes = [ + IDBDatabase, + IDBObjectStore, + IDBIndex, + IDBCursor, + IDBTransaction + ]); + } + function getCursorAdvanceMethods() { + return cursorAdvanceMethods || (cursorAdvanceMethods = [ + IDBCursor.prototype.advance, + IDBCursor.prototype.continue, + IDBCursor.prototype.continuePrimaryKey + ]); + } + var transactionDoneMap = /* @__PURE__ */ new WeakMap(); + var transformCache = /* @__PURE__ */ new WeakMap(); + var reverseTransformCache = /* @__PURE__ */ new WeakMap(); + function promisifyRequest(request) { + const promise = new Promise((resolve, reject) => { + const unlisten = () => { + request.removeEventListener("success", success); + request.removeEventListener("error", error); + }; + const success = () => { + resolve(wrap(request.result)); + unlisten(); + }; + const error = () => { + reject(request.error); + unlisten(); + }; + request.addEventListener("success", success); + request.addEventListener("error", error); + }); + reverseTransformCache.set(promise, request); + return promise; + } + function cacheDonePromiseForTransaction(tx) { + if (transactionDoneMap.has(tx)) + return; + const done = new Promise((resolve, reject) => { + const unlisten = () => { + tx.removeEventListener("complete", complete2); + tx.removeEventListener("error", error); + tx.removeEventListener("abort", error); + }; + const complete2 = () => { + resolve(); + unlisten(); + }; + const error = () => { + reject(tx.error || new DOMException("AbortError", "AbortError")); + unlisten(); + }; + tx.addEventListener("complete", complete2); + tx.addEventListener("error", error); + tx.addEventListener("abort", error); + }); + transactionDoneMap.set(tx, done); + } + var idbProxyTraps = { + get(target, prop, receiver) { + if (target instanceof IDBTransaction) { + if (prop === "done") + return transactionDoneMap.get(target); + if (prop === "store") { + return receiver.objectStoreNames[1] ? void 0 : receiver.objectStore(receiver.objectStoreNames[0]); + } + } + return wrap(target[prop]); + }, + set(target, prop, value) { + target[prop] = value; + return true; + }, + has(target, prop) { + if (target instanceof IDBTransaction && (prop === "done" || prop === "store")) { + return true; + } + return prop in target; + } + }; + function replaceTraps(callback) { + idbProxyTraps = callback(idbProxyTraps); + } + function wrapFunction(func) { + if (getCursorAdvanceMethods().includes(func)) { + return function(...args) { + func.apply(unwrap(this), args); + return wrap(this.request); + }; + } + return function(...args) { + return wrap(func.apply(unwrap(this), args)); + }; + } + function transformCachableValue(value) { + if (typeof value === "function") + return wrapFunction(value); + if (value instanceof IDBTransaction) + cacheDonePromiseForTransaction(value); + if (instanceOfAny(value, getIdbProxyableTypes())) + return new Proxy(value, idbProxyTraps); + return value; + } + function wrap(value) { + if (value instanceof IDBRequest) + return promisifyRequest(value); + if (transformCache.has(value)) + return transformCache.get(value); + const newValue = transformCachableValue(value); + if (newValue !== value) { + transformCache.set(value, newValue); + reverseTransformCache.set(newValue, value); + } + return newValue; + } + var unwrap = (value) => reverseTransformCache.get(value); + function openDB(name, version, { blocked, upgrade, blocking, terminated } = {}) { + const request = indexedDB.open(name, version); + const openPromise = wrap(request); + if (upgrade) { + request.addEventListener("upgradeneeded", (event) => { + upgrade(wrap(request.result), event.oldVersion, event.newVersion, wrap(request.transaction), event); + }); + } + if (blocked) { + request.addEventListener("blocked", (event) => blocked( + // Casting due to https://github.com/microsoft/TypeScript-DOM-lib-generator/pull/1405 + event.oldVersion, + event.newVersion, + event + )); + } + openPromise.then((db) => { + if (terminated) + db.addEventListener("close", () => terminated()); + if (blocking) { + db.addEventListener("versionchange", (event) => blocking(event.oldVersion, event.newVersion, event)); + } + }).catch(() => { + }); + return openPromise; + } + var readMethods = ["get", "getKey", "getAll", "getAllKeys", "count"]; + var writeMethods = ["put", "add", "delete", "clear"]; + var cachedMethods = /* @__PURE__ */ new Map(); + function getMethod(target, prop) { + if (!(target instanceof IDBDatabase && !(prop in target) && typeof prop === "string")) { + return; + } + if (cachedMethods.get(prop)) + return cachedMethods.get(prop); + const targetFuncName = prop.replace(/FromIndex$/, ""); + const useIndex = prop !== targetFuncName; + const isWrite = writeMethods.includes(targetFuncName); + if ( + // Bail if the target doesn't exist on the target. Eg, getAll isn't in Edge. + !(targetFuncName in (useIndex ? IDBIndex : IDBObjectStore).prototype) || !(isWrite || readMethods.includes(targetFuncName)) + ) { + return; + } + const method = async function(storeName, ...args) { + const tx = this.transaction(storeName, isWrite ? "readwrite" : "readonly"); + let target2 = tx.store; + if (useIndex) + target2 = target2.index(args.shift()); + return (await Promise.all([ + target2[targetFuncName](...args), + isWrite && tx.done + ]))[0]; + }; + cachedMethods.set(prop, method); + return method; + } + replaceTraps((oldTraps) => ({ + ...oldTraps, + get: (target, prop, receiver) => getMethod(target, prop) || oldTraps.get(target, prop, receiver), + has: (target, prop) => !!getMethod(target, prop) || oldTraps.has(target, prop) + })); + var advanceMethodProps = ["continue", "continuePrimaryKey", "advance"]; + var methodMap = {}; + var advanceResults = /* @__PURE__ */ new WeakMap(); + var ittrProxiedCursorToOriginalProxy = /* @__PURE__ */ new WeakMap(); + var cursorIteratorTraps = { + get(target, prop) { + if (!advanceMethodProps.includes(prop)) + return target[prop]; + let cachedFunc = methodMap[prop]; + if (!cachedFunc) { + cachedFunc = methodMap[prop] = function(...args) { + advanceResults.set(this, ittrProxiedCursorToOriginalProxy.get(this)[prop](...args)); + }; + } + return cachedFunc; + } + }; + async function* iterate(...args) { + let cursor = this; + if (!(cursor instanceof IDBCursor)) { + cursor = await cursor.openCursor(...args); + } + if (!cursor) + return; + cursor = cursor; + const proxiedCursor = new Proxy(cursor, cursorIteratorTraps); + ittrProxiedCursorToOriginalProxy.set(proxiedCursor, cursor); + reverseTransformCache.set(proxiedCursor, unwrap(cursor)); + while (cursor) { + yield proxiedCursor; + cursor = await (advanceResults.get(proxiedCursor) || cursor.continue()); + advanceResults.delete(proxiedCursor); + } + } + function isIteratorProp(target, prop) { + return prop === Symbol.asyncIterator && instanceOfAny(target, [IDBIndex, IDBObjectStore, IDBCursor]) || prop === "iterate" && instanceOfAny(target, [IDBIndex, IDBObjectStore]); + } + replaceTraps((oldTraps) => ({ + ...oldTraps, + get(target, prop, receiver) { + if (isIteratorProp(target, prop)) + return iterate; + return oldTraps.get(target, prop, receiver); + }, + has(target, prop) { + return isIteratorProp(target, prop) || oldTraps.has(target, prop); + } + })); + + // src/utilities/db.js + async function openEventsDb() { + return await openDB("events", 1, { + upgrade(db) { + const events = db.createObjectStore("events", { + keyPath: "event.id" + }); + events.createIndex("pubkey", "event.pubkey"); + events.createIndex("created_at", "event.created_at"); + events.createIndex("kind", "event.kind"); + events.createIndex("host", "metadata.host"); + } + }); + } + async function saveEvent(event) { + let db = await openEventsDb(); + return db.put("events", event); + } + + // src/utilities/sync-manager.js + init_process(); + var SYNC_QUOTA = 102400; + var MAX_ITEM = 8192; + var MAX_ITEMS = 512; + var CHUNK_PREFIX = "_chunk:"; + var SYNC_META_KEY = "_sync_meta"; + var LOCAL_ENABLED_KEY = "platformSyncEnabled"; + var PRIORITY = { + P1_PROFILES: 1, + P2_SETTINGS: 2, + P3_APIKEYS: 3, + P4_VAULT: 4 + }; + var storage2 = api.storage.local; + var pushTimer = null; + function chunkValue(key, jsonString) { + const chunks = []; + for (let i = 0; i < jsonString.length; i += MAX_ITEM - 100) { + chunks.push(jsonString.slice(i, i + MAX_ITEM - 100)); + } + if (chunks.length === 1) { + return [{ key, value: jsonString }]; + } + const entries = []; + for (let i = 0; i < chunks.length; i++) { + entries.push({ key: `${CHUNK_PREFIX}${key}:${i}`, value: chunks[i] }); + } + entries.push({ key, value: JSON.stringify({ __chunked: true, count: chunks.length }) }); + return entries; + } + function reassembleFromSyncData(key, syncData) { + try { + const meta = typeof syncData[key] === "string" ? JSON.parse(syncData[key]) : syncData[key]; + if (!meta || !meta.__chunked) { + return typeof syncData[key] === "string" ? JSON.parse(syncData[key]) : syncData[key]; + } + let combined = ""; + for (let i = 0; i < meta.count; i++) { + const chunkKey = `${CHUNK_PREFIX}${key}:${i}`; + if (syncData[chunkKey] == null) return null; + combined += syncData[chunkKey]; + } + return JSON.parse(combined); + } catch { + return null; + } + } + async function buildSyncPayload() { + const all = await storage2.get(null); + const entries = []; + if (all.profiles) { + const cleanProfiles = all.profiles.map((p) => { + const { hosts, ...rest } = p; + return rest; + }); + const json = JSON.stringify(cleanProfiles); + entries.push({ key: "profiles", jsonString: json, priority: PRIORITY.P1_PROFILES, size: json.length }); + } + if (all.profileIndex != null) { + const json = JSON.stringify(all.profileIndex); + entries.push({ key: "profileIndex", jsonString: json, priority: PRIORITY.P1_PROFILES, size: json.length }); + } + const settingsKeys = ["autoLockMinutes", "version", "protocol_handler", LOCAL_ENABLED_KEY]; + for (const k of settingsKeys) { + if (all[k] != null) { + const json = JSON.stringify(all[k]); + entries.push({ key: k, jsonString: json, priority: PRIORITY.P2_SETTINGS, size: json.length }); + } + } + for (const k of Object.keys(all)) { + if (k.startsWith("feature:")) { + const json = JSON.stringify(all[k]); + entries.push({ key: k, jsonString: json, priority: PRIORITY.P2_SETTINGS, size: json.length }); + } + } + if (all.apiKeyVault) { + const json = JSON.stringify(all.apiKeyVault); + entries.push({ key: "apiKeyVault", jsonString: json, priority: PRIORITY.P3_APIKEYS, size: json.length }); + } + if (all.vaultDocs && typeof all.vaultDocs === "object") { + const docs = Object.values(all.vaultDocs).sort((a, b) => (b.updatedAt || 0) - (a.updatedAt || 0)); + for (const doc of docs) { + const docKey = `vaultDoc:${doc.path}`; + const json = JSON.stringify(doc); + entries.push({ key: docKey, jsonString: json, priority: PRIORITY.P4_VAULT, size: json.length }); + } + } + return entries; + } + async function pushToSync() { + if (!api.storage.sync) return; + const enabled = await isSyncEnabled(); + if (!enabled) return; + try { + const entries = await buildSyncPayload(); + entries.sort((a, b) => a.priority - b.priority); + let usedBytes = 0; + let usedItems = 0; + const syncPayload = {}; + const allSyncKeys = []; + let budgetExhausted = false; + for (const entry of entries) { + if (budgetExhausted) break; + const chunks = chunkValue(entry.key, entry.jsonString); + let entrySize = 0; + for (const c of chunks) { + entrySize += c.key.length + (typeof c.value === "string" ? c.value.length : JSON.stringify(c.value).length); + } + if (usedBytes + entrySize > SYNC_QUOTA - 500 || usedItems + chunks.length > MAX_ITEMS - 5) { + if (entry.priority <= PRIORITY.P3_APIKEYS) { + } else { + console.warn(`[SyncManager] Budget exhausted at priority ${entry.priority}, skipping remaining entries`); + budgetExhausted = true; + break; + } + } + for (const c of chunks) { + syncPayload[c.key] = c.value; + allSyncKeys.push(c.key); + } + usedBytes += entrySize; + usedItems += chunks.length; + } + const meta = { + lastWrittenAt: Date.now(), + keys: allSyncKeys + }; + syncPayload[SYNC_META_KEY] = JSON.stringify(meta); + await api.storage.sync.set(syncPayload); + try { + const existing = await api.storage.sync.get(null); + const orphanKeys = Object.keys(existing).filter( + (k) => k !== SYNC_META_KEY && !allSyncKeys.includes(k) + ); + if (orphanKeys.length > 0) { + await api.storage.sync.remove(orphanKeys); + } + } catch { + } + console.log(`[SyncManager] Pushed ${allSyncKeys.length} entries (${usedBytes} bytes) to sync storage`); + } catch (e) { + console.error("[SyncManager] pushToSync error:", e); + } + } + async function pullFromSync() { + if (!api.storage.sync) return null; + try { + const raw = await api.storage.sync.get(null); + if (!raw || Object.keys(raw).length === 0) return null; + const metaStr = raw[SYNC_META_KEY]; + if (!metaStr) return null; + let meta; + try { + meta = JSON.parse(metaStr); + } catch { + return null; + } + const result = {}; + const dataKeys = meta.keys.filter((k) => !k.startsWith(CHUNK_PREFIX) && k !== SYNC_META_KEY); + for (const key of dataKeys) { + const value = reassembleFromSyncData(key, raw); + if (value != null) { + result[key] = value; + } + } + result._syncMeta = meta; + return result; + } catch (e) { + console.error("[SyncManager] pullFromSync error:", e); + return null; + } + } + function compareSemver(a, b) { + const pa = String(a).split("."); + const pb = String(b).split("."); + const len = Math.max(pa.length, pb.length); + for (let i = 0; i < len; i++) { + const na = parseInt(pa[i], 10) || 0; + const nb = parseInt(pb[i], 10) || 0; + if (na > nb) return 1; + if (na < nb) return -1; + } + return 0; + } + async function mergeIntoLocal(syncData) { + if (!syncData) return; + const local = await storage2.get(null); + const { updates, changed } = computeMergeUpdates(local, syncData); + if (changed) { + await storage2.set(updates); + console.log("[SyncManager] Merged sync data into local:", Object.keys(updates)); + } + } + function computeMergeUpdates(local, syncData) { + const updates = {}; + let changed = false; + if (!syncData) return { updates, changed }; + const hasIdentity = (p) => !!(p.privKey || p.pubKey || p.type === "bunker" || p.bunkerUrl || p.remotePubkey); + const isFresh = !local.profiles || local.profiles.length === 0 || !local.profiles.some(hasIdentity); + if (syncData.profiles) { + if (isFresh) { + updates.profiles = syncData.profiles; + changed = true; + } else if (local.profiles) { + const merged = [...local.profiles]; + const indexByPubkey = /* @__PURE__ */ new Map(); + merged.forEach((p, i) => { + if (p.pubKey) indexByPubkey.set(p.pubKey, i); + }); + for (const syncProfile of syncData.profiles) { + const localIdx = syncProfile.pubKey != null ? indexByPubkey.get(syncProfile.pubKey) : void 0; + if (localIdx === void 0) { + merged.push(syncProfile); + if (syncProfile.pubKey) indexByPubkey.set(syncProfile.pubKey, merged.length - 1); + changed = true; + } else { + const localProfile = merged[localIdx]; + const syncTime = syncProfile.updatedAt || 0; + const localTime = localProfile.updatedAt || 0; + if (syncTime > localTime) { + merged[localIdx] = { ...syncProfile, hosts: localProfile.hosts || {} }; + changed = true; + } + } + } + if (changed) updates.profiles = merged; + } + } + if (syncData.profileIndex != null && isFresh) { + updates.profileIndex = syncData.profileIndex; + changed = true; + } + const syncMeta = syncData._syncMeta || {}; + const settingsKeys = ["autoLockMinutes", "version", "protocol_handler", LOCAL_ENABLED_KEY]; + for (const key of settingsKeys) { + if (syncData[key] != null && syncData[key] !== local[key]) { + if (key === "version" && local.version && compareSemver(syncData.version, local.version) <= 0) continue; + updates[key] = syncData[key]; + changed = true; + } + } + for (const key of Object.keys(syncData)) { + if (key.startsWith("feature:") && syncData[key] !== local[key]) { + updates[key] = syncData[key]; + changed = true; + } + } + if (syncData.apiKeyVault) { + if (!local.apiKeyVault || isFresh) { + updates.apiKeyVault = syncData.apiKeyVault; + changed = true; + } else { + const localKeys = local.apiKeyVault.keys || {}; + const syncKeys = syncData.apiKeyVault.keys || {}; + const merged = { ...localKeys }; + for (const [id, syncKey] of Object.entries(syncKeys)) { + const localKey = merged[id]; + if (!localKey || (syncKey.updatedAt || 0) > (localKey.updatedAt || 0)) { + merged[id] = syncKey; + changed = true; + } + } + if (changed) { + updates.apiKeyVault = { ...local.apiKeyVault, keys: merged }; + } + } + } + const localDocs = local.vaultDocs || {}; + let docsChanged = false; + const mergedDocs = { ...localDocs }; + for (const key of Object.keys(syncData)) { + if (!key.startsWith("vaultDoc:")) continue; + const doc = syncData[key]; + if (!doc || !doc.path) continue; + const localDoc = mergedDocs[doc.path]; + if (!localDoc || (doc.updatedAt || 0) > (localDoc.updatedAt || 0)) { + mergedDocs[doc.path] = doc; + docsChanged = true; + } + } + if (docsChanged) { + updates.vaultDocs = mergedDocs; + changed = true; + } + return { updates, changed }; + } + function scheduleSyncPush() { + if (!api.storage.sync) return; + if (pushTimer) clearTimeout(pushTimer); + pushTimer = setTimeout(() => { + pushTimer = null; + pushToSync(); + }, 2e3); + } + async function isSyncEnabled() { + const data = await storage2.get({ [LOCAL_ENABLED_KEY]: true }); + return data[LOCAL_ENABLED_KEY]; + } + async function initSync() { + if (!api.storage.sync) { + console.log("[SyncManager] storage.sync not available \u2014 skipping"); + return; + } + const enabled = await isSyncEnabled(); + if (!enabled) { + console.log("[SyncManager] Platform sync disabled"); + return; + } + try { + const syncData = await pullFromSync(); + if (syncData) { + await mergeIntoLocal(syncData); + console.log("[SyncManager] Initial pull+merge complete"); + } else { + console.log("[SyncManager] No sync data found \u2014 fresh sync"); + } + } catch (e) { + console.error("[SyncManager] Initial pull failed:", e); + } + if (api.storage.onChanged) { + api.storage.onChanged.addListener((changes, areaName) => { + if (areaName !== "sync") return; + console.log("[SyncManager] Remote sync change detected"); + pullFromSync().then((syncData) => { + if (syncData) mergeIntoLocal(syncData); + }).catch((e) => { + console.error("[SyncManager] Remote merge error:", e); + }); + }); + } + scheduleSyncPush(); + } + + // src/utilities/nip46.js + init_process(); + var storage3 = api.storage.local; + var log = (msg) => console.log("NIP-46: ", msg); + var sessions = /* @__PURE__ */ new Map(); + function parseBunkerUrl(url) { + if (!url.startsWith("bunker://")) { + throw new Error("Invalid bunker URL: must start with bunker://"); + } + const parsed = new URL(url); + const remotePubkey = parsed.hostname || parsed.pathname.replace("//", ""); + if (!/^[0-9a-f]{64}$/i.test(remotePubkey)) { + throw new Error("Invalid bunker URL: pubkey must be 64 hex characters"); + } + const relays = parsed.searchParams.getAll("relay"); + if (relays.length === 0) { + throw new Error("Invalid bunker URL: at least one relay is required"); + } + for (const relay of relays) { + try { + const r = new URL(relay); + if (r.protocol !== "wss:" && r.protocol !== "ws:") { + throw new Error(`Invalid relay protocol: ${r.protocol}`); + } + } catch (e) { + throw new Error(`Invalid relay URL: ${relay}`); + } + } + const secret = parsed.searchParams.get("secret") || null; + return { remotePubkey, relays, secret }; + } + var RelayConnection = class { + constructor(url) { + this.url = url; + this.ws = null; + this.subscriptions = /* @__PURE__ */ new Map(); + this.eoseCallbacks = /* @__PURE__ */ new Map(); + this.connected = false; + this.reconnectTimer = null; + this.reconnectAttempts = 0; + this.maxReconnectAttempts = 5; + } + connect() { + return new Promise((resolve, reject) => { + try { + this.ws = new WebSocket(this.url); + } catch (e) { + reject(new Error(`Failed to create WebSocket: ${e.message}`)); + return; + } + const timeout = setTimeout(() => { + this.ws?.close(); + reject(new Error(`Connection timeout: ${this.url}`)); + }, 1e4); + this.ws.onopen = () => { + clearTimeout(timeout); + this.connected = true; + this.reconnectAttempts = 0; + log(`Connected to ${this.url}`); + resolve(); + }; + this.ws.onerror = (err) => { + clearTimeout(timeout); + log(`WebSocket error: ${this.url}`); + reject(new Error(`WebSocket error: ${this.url}`)); + }; + this.ws.onclose = () => { + this.connected = false; + log(`Disconnected from ${this.url}`); + this.scheduleReconnect(); + }; + this.ws.onmessage = (msg) => { + try { + const data = JSON.parse(msg.data); + this.handleMessage(data); + } catch (e) { + log(`Failed to parse message: ${e.message}`); + } + }; + }); + } + handleMessage(data) { + const [type, subId, ...rest] = data; + if (type === "EVENT" && subId && rest[0]) { + const event = rest[0]; + const handler = this.subscriptions.get(subId); + if (handler) { + handler(event); + } + } else if (type === "EOSE" && subId) { + const eoseHandler = this.eoseCallbacks.get(subId); + if (eoseHandler) { + this.eoseCallbacks.delete(subId); + eoseHandler(); + } + } else if (type === "OK") { + } else if (type === "NOTICE") { + log(`Relay notice: ${rest[0]}`); + } + } + subscribe(subId, filters, onEvent, onEose = null) { + if (!this.connected || !this.ws) { + throw new Error("Not connected"); + } + this.subscriptions.set(subId, onEvent); + if (onEose) { + this.eoseCallbacks.set(subId, onEose); + } + this.ws.send(JSON.stringify(["REQ", subId, ...filters])); + } + unsubscribe(subId) { + if (this.ws && this.connected) { + this.ws.send(JSON.stringify(["CLOSE", subId])); + } + this.subscriptions.delete(subId); + this.eoseCallbacks.delete(subId); + } + publish(event) { + if (!this.connected || !this.ws) { + throw new Error("Not connected"); + } + this.ws.send(JSON.stringify(["EVENT", event])); + } + scheduleReconnect() { + if (this.reconnectAttempts >= this.maxReconnectAttempts) { + log(`Max reconnect attempts reached for ${this.url}`); + return; + } + const delay = Math.min(1e3 * Math.pow(2, this.reconnectAttempts), 3e4); + this.reconnectAttempts++; + this.reconnectTimer = setTimeout(() => { + log(`Reconnecting to ${this.url} (attempt ${this.reconnectAttempts})`); + this.connect().catch(() => { + }); + }, delay); + } + close() { + clearTimeout(this.reconnectTimer); + this.maxReconnectAttempts = 0; + this.subscriptions.clear(); + this.eoseCallbacks.clear(); + if (this.ws) { + this.ws.close(); + this.ws = null; + } + this.connected = false; + } + }; + var BunkerSession = class { + constructor({ remotePubkey, relays, secret }) { + this.remotePubkey = remotePubkey; + this.relayUrls = relays; + this.secret = secret; + this.sessionPrivkey = null; + this.sessionPubkey = null; + this.conversationKey = null; + this.relays = []; + this.pendingRequests = /* @__PURE__ */ new Map(); + this.connected = false; + this.subId = `nostrkey-${crypto.randomUUID().slice(0, 8)}`; + } + /** + * Initialize the ephemeral session keypair (async) + */ + async init() { + if (this.sessionPrivkey) return; + const keyPair = await generateKeyPair2(); + this.sessionPrivkey = hexToBytes2(keyPair.privateKey); + this.sessionPubkey = keyPair.publicKey; + this.conversationKey = v2.utils.getConversationKey( + this.sessionPrivkey, + this.remotePubkey + ); + } + /** + * Connect to all relays and subscribe for responses + */ + async connect() { + await this.init(); + const connections = this.relayUrls.map((url) => { + const relay = new RelayConnection(url); + return relay.connect().then(() => { + this.relays.push(relay); + return relay; + }); + }); + const results = await Promise.allSettled(connections); + const connected = results.filter((r) => r.status === "fulfilled"); + if (connected.length === 0) { + throw new Error("Failed to connect to any relay"); + } + log(`Connected to ${connected.length}/${this.relayUrls.length} relays`); + for (const relay of this.relays) { + relay.subscribe( + this.subId, + [{ kinds: [24133], "#p": [this.sessionPubkey] }], + (event) => this.handleResponse(event) + ); + } + this.connected = true; + if (this.secret) { + await this.sendRequest("connect", [this.remotePubkey, this.secret]); + } else { + await this.sendRequest("connect", [this.remotePubkey]); + } + } + /** + * Handle an incoming NIP-46 response event + */ + handleResponse(event) { + if (event.pubkey !== this.remotePubkey) { + log(`Ignoring event from unknown pubkey: ${event.pubkey}`); + return; + } + try { + const plaintext = v2.decrypt(event.content, this.conversationKey); + const response = JSON.parse(plaintext); + log(`Response: ${response.id} -> ${response.result ? "ok" : response.error}`); + const pending = this.pendingRequests.get(response.id); + if (pending) { + this.pendingRequests.delete(response.id); + if (response.error) { + pending.reject(new Error(response.error)); + } else { + pending.resolve(response.result); + } + } + } catch (e) { + log(`Failed to handle response: ${e.message}`); + } + } + /** + * Send an encrypted NIP-46 request to the bunker + */ + async sendRequest(method, params = []) { + if (!this.connected && method !== "connect") { + throw new Error("Not connected to bunker"); + } + const id = crypto.randomUUID(); + const request = JSON.stringify({ id, method, params }); + const encrypted = v2.encrypt(request, this.conversationKey); + const event = await finalizeEvent({ + kind: 24133, + content: encrypted, + tags: [["p", this.remotePubkey]], + created_at: Math.floor(Date.now() / 1e3) + }, this.sessionPrivkey); + for (const relay of this.relays) { + try { + relay.publish(event); + } catch (e) { + log(`Failed to publish to ${relay.url}: ${e.message}`); + } + } + return new Promise((resolve, reject) => { + const timeout = setTimeout(() => { + this.pendingRequests.delete(id); + reject(new Error(`Request timeout: ${method}`)); + }, 3e4); + this.pendingRequests.set(id, { + resolve: (result) => { + clearTimeout(timeout); + resolve(result); + }, + reject: (error) => { + clearTimeout(timeout); + reject(error); + } + }); + }); + } + /** + * NIP-46 Methods + */ + async getPublicKey() { + return await this.sendRequest("get_public_key"); + } + async signEvent(event) { + const result = await this.sendRequest("sign_event", [JSON.stringify(event)]); + return JSON.parse(result); + } + async nip04Encrypt(thirdPartyPubkey, plaintext) { + return await this.sendRequest("nip04_encrypt", [thirdPartyPubkey, plaintext]); + } + async nip04Decrypt(thirdPartyPubkey, ciphertext) { + return await this.sendRequest("nip04_decrypt", [thirdPartyPubkey, ciphertext]); + } + async nip44Encrypt(thirdPartyPubkey, plaintext) { + return await this.sendRequest("nip44_encrypt", [thirdPartyPubkey, plaintext]); + } + async nip44Decrypt(thirdPartyPubkey, ciphertext) { + return await this.sendRequest("nip44_decrypt", [thirdPartyPubkey, ciphertext]); + } + async ping() { + return await this.sendRequest("ping"); + } + /** + * Get session info for persistence + */ + getSessionInfo() { + return { + remotePubkey: this.remotePubkey, + relayUrls: this.relayUrls, + secret: this.secret, + sessionPrivkey: bytesToHex3(this.sessionPrivkey), + sessionPubkey: this.sessionPubkey + }; + } + /** + * Disconnect from all relays + */ + disconnect() { + for (const relay of this.relays) { + relay.unsubscribe(this.subId); + relay.close(); + } + this.relays = []; + this.pendingRequests.clear(); + this.connected = false; + log("Disconnected from bunker"); + } + }; + function restoreSession(sessionInfo) { + const session = new BunkerSession({ + remotePubkey: sessionInfo.remotePubkey, + relays: sessionInfo.relayUrls, + secret: sessionInfo.secret + }); + session.sessionPrivkey = hexToBytes2(sessionInfo.sessionPrivkey); + session.sessionPubkey = sessionInfo.sessionPubkey; + session.conversationKey = v2.utils.getConversationKey( + session.sessionPrivkey, + session.remotePubkey + ); + return session; + } + async function getOrCreateSession(profileIndex) { + if (sessions.has(profileIndex)) { + const session2 = sessions.get(profileIndex); + if (session2.connected) { + return session2; + } + session2.disconnect(); + sessions.delete(profileIndex); + } + const data = await storage3.get({ bunkerSessions: {} }); + const sessionInfo = data.bunkerSessions?.[profileIndex]; + if (!sessionInfo) { + throw new Error("No bunker session configured for this profile"); + } + const session = restoreSession(sessionInfo); + await session.connect(); + sessions.set(profileIndex, session); + return session; + } + async function createSession(profileIndex, bunkerUrl) { + if (sessions.has(profileIndex)) { + sessions.get(profileIndex).disconnect(); + sessions.delete(profileIndex); + } + const config = parseBunkerUrl(bunkerUrl); + const session = new BunkerSession(config); + await session.connect(); + const data = await storage3.get({ bunkerSessions: {} }); + const bunkerSessions = data.bunkerSessions || {}; + bunkerSessions[profileIndex] = session.getSessionInfo(); + await storage3.set({ bunkerSessions }); + sessions.set(profileIndex, session); + return session; + } + async function disconnectSession(profileIndex) { + if (sessions.has(profileIndex)) { + sessions.get(profileIndex).disconnect(); + sessions.delete(profileIndex); + } + const data = await storage3.get({ bunkerSessions: {} }); + const bunkerSessions = data.bunkerSessions || {}; + delete bunkerSessions[profileIndex]; + await storage3.set({ bunkerSessions }); + } + function isSessionActive(profileIndex) { + return sessions.has(profileIndex) && sessions.get(profileIndex).connected; + } + function validateBunkerUrl(url) { + try { + parseBunkerUrl(url); + return { valid: true, error: null }; + } catch (e) { + return { valid: false, error: e.message }; + } + } + + // src/utilities/bunker-server.js + init_process(); + var log2 = (msg) => console.log("BunkerServer: ", msg); + var BunkerServer = class { + /** + * @param {Object} opts + * @param {string[]} opts.relayUrls - relay URLs to connect to + * @param {string} opts.userPubkey - hex pubkey of the local user + * @param {string} opts.secret - shared secret for connect handshake + */ + constructor({ relayUrls, userPubkey, secret }) { + this.relayUrls = relayUrls; + this.userPubkey = userPubkey; + this.secret = secret; + this.relays = []; + this.authenticatedClients = /* @__PURE__ */ new Set(); + this.subId = `bunker-srv-${crypto.randomUUID().slice(0, 8)}`; + this.active = false; + this._getPrivKey = null; + } + /** + * Start the bunker server. + * @param {Object} opts + * @param {Function} opts.getPrivKey - async () => Uint8Array (user's private key) + */ + async start({ getPrivKey: getPrivKey2 }) { + this._getPrivKey = getPrivKey2; + const connections = this.relayUrls.map((url) => { + const relay = new RelayConnection(url); + return relay.connect().then(() => { + this.relays.push(relay); + return relay; + }); + }); + const results = await Promise.allSettled(connections); + const connected = results.filter((r) => r.status === "fulfilled"); + if (connected.length === 0) { + throw new Error("Failed to connect to any relay"); + } + log2(`Connected to ${connected.length}/${this.relayUrls.length} relays`); + for (const relay of this.relays) { + relay.subscribe( + this.subId, + [{ kinds: [24133], "#p": [this.userPubkey], since: Math.floor(Date.now() / 1e3) - 5 }], + (event) => this._handleRequest(event) + ); + } + this.active = true; + log2("Bunker server started"); + } + /** + * Stop the bunker server. + */ + stop() { + for (const relay of this.relays) { + relay.unsubscribe(this.subId); + relay.close(); + } + this.relays = []; + this.authenticatedClients.clear(); + this.active = false; + this._getPrivKey = null; + log2("Bunker server stopped"); + } + /** + * Generate the bunker:// connection string. + */ + getConnectionString() { + const relayParams = this.relayUrls.map((u) => `relay=${encodeURIComponent(u)}`).join("&"); + return `bunker://${this.userPubkey}?${relayParams}&secret=${this.secret}`; + } + /** + * Handle an incoming NIP-46 request event. + */ + async _handleRequest(event) { + const clientPubkey = event.pubkey; + let privKey; + try { + privKey = await this._getPrivKey(); + } catch (e) { + log2(`Cannot get private key (locked?): ${e.message}`); + return; + } + let conversationKey; + try { + conversationKey = v2.utils.getConversationKey(privKey, clientPubkey); + } catch (e) { + log2(`Failed to derive conversation key: ${e.message}`); + return; + } + let request; + try { + const plaintext = v2.decrypt(event.content, conversationKey); + request = JSON.parse(plaintext); + } catch (e) { + log2(`Failed to decrypt request: ${e.message}`); + return; + } + const { id, method, params } = request; + log2(`Request: ${method} (id=${id}) from ${clientPubkey.slice(0, 8)}...`); + if (method !== "connect" && !this.authenticatedClients.has(clientPubkey)) { + await this._sendResponse(privKey, clientPubkey, conversationKey, { + id, + result: null, + error: "Unauthorized: send connect first" + }); + return; + } + let result = null; + let error = null; + try { + switch (method) { + case "connect": { + const clientSecret = params[1]; + if (!this.secret || clientSecret !== this.secret) { + error = "Invalid secret"; + } else { + this.authenticatedClients.add(clientPubkey); + result = "ack"; + log2(`Client authenticated: ${clientPubkey.slice(0, 8)}...`); + } + break; + } + case "get_public_key": + result = this.userPubkey; + break; + case "sign_event": { + const unsigned = JSON.parse(params[0]); + const signed = await finalizeEvent(unsigned, privKey); + result = JSON.stringify(signed); + break; + } + case "nip44_encrypt": { + const thirdPartyPubkey = params[0]; + const plaintext = params[1]; + const ck = v2.utils.getConversationKey(privKey, thirdPartyPubkey); + result = v2.encrypt(plaintext, ck); + break; + } + case "nip44_decrypt": { + const thirdPartyPubkey = params[0]; + const ciphertext = params[1]; + const ck = v2.utils.getConversationKey(privKey, thirdPartyPubkey); + result = v2.decrypt(ciphertext, ck); + break; + } + case "nip04_encrypt": { + const thirdPartyPubkey = params[0]; + const plaintext = params[1]; + result = await nip_04_exports.encryptMessage(plaintext, bytesToHex3(privKey), thirdPartyPubkey); + break; + } + case "nip04_decrypt": { + const thirdPartyPubkey = params[0]; + const ciphertext = params[1]; + result = await nip_04_exports.decryptMessage(ciphertext, bytesToHex3(privKey), thirdPartyPubkey); + break; + } + case "ping": + result = "pong"; + break; + default: + error = `Unsupported method: ${method}`; + } + } catch (e) { + error = e.message; + log2(`Error handling ${method}: ${e.message}`); + } + await this._sendResponse(privKey, clientPubkey, conversationKey, { id, result, error }); + } + /** + * Encrypt and publish a NIP-46 response. + */ + async _sendResponse(privKey, clientPubkey, conversationKey, response) { + const encrypted = v2.encrypt(JSON.stringify(response), conversationKey); + const event = await finalizeEvent({ + kind: 24133, + content: encrypted, + tags: [["p", clientPubkey]], + created_at: Math.floor(Date.now() / 1e3) + }, privKey); + for (const relay of this.relays) { + try { + relay.publish(event); + } catch (e) { + log2(`Failed to publish response to ${relay.url}: ${e.message}`); + } + } + log2(`Response sent: ${response.id} ${response.error ? "ERROR" : "OK"}`); + } + }; + + // src/utilities/nip78.js + init_process(); + var KIND_APP_DATA = 30078; + var KIND_DELETION = 5; + var DTAG_PREFIX = "nostrkey:"; + var CLIENT_TAG = "nostrkey"; + function buildVaultEvent(path, encryptedContent) { + return { + kind: KIND_APP_DATA, + content: encryptedContent, + tags: [ + ["d", `${DTAG_PREFIX}${path}`], + ["client", CLIENT_TAG] + ], + created_at: Math.floor(Date.now() / 1e3) + }; + } + function buildVaultDeletion(eventId, path) { + return { + kind: KIND_DELETION, + content: "vault document deleted", + tags: [ + ["e", eventId], + ["a", `${KIND_APP_DATA}::${DTAG_PREFIX}${path}`] + ], + created_at: Math.floor(Date.now() / 1e3) + }; + } + function buildVaultFilter(pubkey) { + return { + kinds: [KIND_APP_DATA], + authors: [pubkey] + }; + } + function parseVaultEvent(event) { + if (event.kind !== KIND_APP_DATA) return null; + const dTag = event.tags?.find((t) => t[0] === "d"); + if (!dTag || !dTag[1]?.startsWith(DTAG_PREFIX)) return null; + const path = dTag[1].slice(DTAG_PREFIX.length); + if (!path) return null; + return { + path, + content: event.content, + createdAt: event.created_at, + eventId: event.id + }; + } + + // src/background.js + var _rawStorage = api.storage.local; + var storage4 = { + get: (...args) => _rawStorage.get(...args), + set: (...args) => { + const result = _rawStorage.set(...args); + result.then(() => scheduleSyncPush()).catch(() => { + }); + return result; + }, + clear: (...args) => _rawStorage.clear(...args), + remove: (...args) => _rawStorage.remove(...args) + }; + var log3 = (msg) => console.log("Background: ", msg); + var validations = {}; + var prompt = { mutex: new Mutex(), release: null, tabId: null }; + var pendingQueue = { total: 0, processed: 0 }; + var activeBunkerServer = null; + function reply(sendResponse, fn) { + fn().then((r) => sendResponse(r)).catch((e) => { + console.error("reply() error:", e); + sendResponse(void 0); + }); + } + var rateLimits = /* @__PURE__ */ new Map(); + var RATE_LIMIT_MAX = 5; + var RATE_LIMIT_WINDOW = 1e4; + function isRateLimited(host) { + const now = Date.now(); + let timestamps = rateLimits.get(host) || []; + timestamps = timestamps.filter((t) => now - t < RATE_LIMIT_WINDOW); + if (timestamps.length >= RATE_LIMIT_MAX) { + rateLimits.set(host, timestamps); + return true; + } + timestamps.push(now); + rateLimits.set(host, timestamps); + return false; + } + var sessionKeys = /* @__PURE__ */ new Map(); + var sessionCryptoKey = null; + var sessionKeySalt = null; + var locked = true; + var encryptionEnabled = false; + var autoLockTimeout = 15 * 60 * 1e3; + var autoLockTimer = null; + var nostrAccessWhileLocked = false; + var blockCrossOriginFrames = true; + var unlockAttempts = 0; + var unlockCooldownUntil = 0; + var permissionRateMap = /* @__PURE__ */ new Map(); + (async () => { + log3("[STARTUP] Reading persisted state..."); + const data = await storage4.get({ autoLockMinutes: 15, isEncrypted: false, passwordHash: null, nostrAccessWhileLocked: false, blockCrossOriginFrames: true }); + log3(`[STARTUP] isEncrypted=${data.isEncrypted}, passwordHash=${data.passwordHash ? "EXISTS" : "null"}, autoLockMinutes=${data.autoLockMinutes}`); + autoLockTimeout = data.autoLockMinutes * 60 * 1e3; + if (!data.isEncrypted && data.passwordHash) { + log3("[STARTUP] Self-healing: passwordHash exists but isEncrypted=false \u2192 fixing"); + await storage4.set({ isEncrypted: true }); + data.isEncrypted = true; + } + if (data.isEncrypted && !data.passwordHash) { + const { profiles = [] } = await storage4.get({ profiles: [] }); + const hasEncryptedBlob = profiles.some((p) => isEncryptedBlob(p.privKey)); + if (!hasEncryptedBlob) { + log3("[STARTUP] Lockout recovery: isEncrypted=true with no passwordHash and no encrypted blobs \u2192 clearing bogus encryption flag"); + await storage4.set({ isEncrypted: false }); + data.isEncrypted = false; + } + } + encryptionEnabled = data.isEncrypted; + nostrAccessWhileLocked = !!data.nostrAccessWhileLocked; + blockCrossOriginFrames = data.blockCrossOriginFrames !== false; + locked = encryptionEnabled; + log3(`[STARTUP] Final state: encryptionEnabled=${encryptionEnabled}, locked=${locked}`); + try { + await initSync(); + log3("[STARTUP] Platform sync initialized"); + } catch (e) { + log3(`[STARTUP] Platform sync init error (non-fatal): ${e.message}`); + } + try { + if (typeof browser !== "undefined" && browser.runtime.sendNativeMessage) { + const response = await browser.runtime.sendNativeMessage( + "com.nostrkey.Extension", + { action: "getSharedProfiles" } + ); + if (response && response.profiles && response.profiles.length > 0) { + const local = await storage4.get({ profiles: [] }); + const merged = mergeSharedProfiles(local.profiles, response.profiles); + if (merged.changed) { + await storage4.set({ profiles: merged.profiles }); + log3(`[STARTUP] Merged ${response.profiles.length} shared profile(s) from iOS app`); + } + } + } + } catch (e) { + log3(`[STARTUP] Shared profiles check skipped: ${e.message}`); + } + })(); + function mergeSharedProfiles(localProfiles, sharedProfiles) { + let changed = false; + const profiles = [...localProfiles]; + for (const shared of sharedProfiles) { + if (!shared.pubKey) continue; + const localIndex = profiles.findIndex((p) => p.pubKey === shared.pubKey); + if (localIndex === -1) { + profiles.push({ + name: shared.name || "Shared Profile", + privKey: shared.privKey || "", + pubKey: shared.pubKey, + hosts: {}, + relays: shared.relays || [], + type: "local", + updatedAt: shared.lastSyncedAt ? new Date(shared.lastSyncedAt).getTime() : Date.now() + }); + changed = true; + } else { + const local = profiles[localIndex]; + const localTime = local.updatedAt || 0; + const sharedTime = shared.lastSyncedAt ? new Date(shared.lastSyncedAt).getTime() : 0; + if (sharedTime > localTime && shared.privKey && !local.privKey) { + profiles[localIndex] = { + ...local, + privKey: shared.privKey, + name: shared.name || local.name, + relays: shared.relays || local.relays, + updatedAt: sharedTime + }; + changed = true; + } + } + } + return { profiles, changed }; + } + var AUTO_LOCK_ALARM = "nostrkey-auto-lock"; + function resetAutoLock() { + if (autoLockTimer) { + clearTimeout(autoLockTimer); + autoLockTimer = null; + } + if (locked || autoLockTimeout <= 0) { + api.alarms?.clear(AUTO_LOCK_ALARM).catch(() => { + }); + return; + } + if (api.alarms) { + api.alarms.create(AUTO_LOCK_ALARM, { delayInMinutes: autoLockTimeout / 6e4 }); + } else { + autoLockTimer = setTimeout(() => { + lockSession(); + }, autoLockTimeout); + } + } + if (api.alarms?.onAlarm) { + api.alarms.onAlarm.addListener((alarm) => { + if (alarm.name === AUTO_LOCK_ALARM) { + lockSession(); + } + }); + } + var sessionMutex = new Mutex(); + async function lockSession() { + const release = await sessionMutex.acquire(); + try { + if (!nostrAccessWhileLocked) { + sessionKeys.clear(); + } + sessionCryptoKey = null; + sessionKeySalt = null; + locked = true; + if (autoLockTimer) { + clearTimeout(autoLockTimer); + autoLockTimer = null; + } + log3(`Session locked. Keys retained: ${nostrAccessWhileLocked && sessionKeys.size > 0}`); + } finally { + release(); + } + } + async function unlockSession(password) { + const release = await sessionMutex.acquire(); + try { + const now = Date.now(); + if (now < unlockCooldownUntil) { + const waitSec = Math.ceil((unlockCooldownUntil - now) / 1e3); + return { success: false, error: `Too many attempts. Try again in ${waitSec} seconds.` }; + } + const valid = await checkPassword(password); + if (!valid) { + unlockAttempts++; + if (unlockAttempts >= 3) { + const cooldownMs = 3e4 * Math.pow(2, Math.floor((unlockAttempts - 3) / 3)); + unlockCooldownUntil = Date.now() + cooldownMs; + log3(`[SECURITY] ${unlockAttempts} failed attempts. Cooldown: ${cooldownMs / 1e3}s`); + } + return { success: false, error: "Invalid password" }; + } + unlockAttempts = 0; + unlockCooldownUntil = 0; + const profiles = await getProfiles(); + let needsSave = false; + for (let i = 0; i < profiles.length; i++) { + if (profiles[i].type === "bunker") continue; + const hex = await getDecryptedPrivKey(profiles[i], password); + sessionKeys.set(i, hex); + if (!profiles[i].pubKey && hex) { + try { + profiles[i].pubKey = getPublicKeySync(hex); + needsSave = true; + } catch (e) { + console.error(`Failed to cache pubKey for profile ${i}:`, e); + } + } + } + if (needsSave) { + await storage4.set({ profiles }); + } + const salt = crypto.getRandomValues(new Uint8Array(16)); + sessionCryptoKey = await deriveKey(password, salt); + sessionKeySalt = salt; + locked = false; + resetAutoLock(); + log3("Session unlocked."); + return { success: true }; + } finally { + release(); + } + } + async function checkLockState() { + const encrypted = await isEncrypted(); + log3(`[checkLockState] isEncrypted()=${encrypted}, locked=${locked}`); + if (!encrypted) { + locked = false; + return false; + } + return locked; + } + var SENSITIVE_KINDS = /* @__PURE__ */ new Set([ + "setPassword", + "changePassword", + "removePassword", + "resetAllData", + "setAutoLockTimeout", + "setNostrAccessWhileLocked", + "setBlockCrossOriginFrames", + "backup.export", + "backup.import", + "unlock", + // Starting/stopping the NIP-46 bunker exposes the user's key for remote + // signing and returns the secret-bearing connection string. It must be a + // deliberate in-extension action — never triggerable by a web page via + // window.nostr.nip46.startBunker(). + "bunkerServer.start", + "bunkerServer.stop" + ]); + function isExtensionSender(sender) { + if (sender.id !== api.runtime.id) return false; + if (sender.tab) { + const extOrigin = `chrome-extension://${api.runtime.id}`; + const url = sender.tab.url || sender.url || ""; + return url.startsWith(extOrigin) || url.startsWith("moz-extension://"); + } + return true; + } + api.runtime.onMessage.addListener((message, _sender, sendResponse) => { + log3(message); + if (SENSITIVE_KINDS.has(message.kind) && !isExtensionSender(_sender)) { + log3(`[SECURITY] Blocked ${message.kind} from non-extension sender`); + sendResponse({ success: false, error: "Unauthorized sender" }); + return true; + } + let uuid = crypto.randomUUID(); + let sr; + switch (message.kind) { + // General + case "closePrompt": + prompt.release?.(); + sendResponse(true); + return true; + case "allowed": + resetAutoLock(); + complete(message); + sendResponse(true); + return true; + case "denied": + deny(message); + sendResponse(true); + return true; + case "generatePrivateKey": + (async () => { + try { + const result = await generatePrivateKey_(); + sendResponse(result); + } catch (e) { + console.error("generatePrivateKey error:", e); + sendResponse(null); + } + })(); + return true; + // Keep message channel open for async sendResponse + case "savePrivateKey": + resetAutoLock(); + (async () => { + try { + await savePrivateKey(message.payload); + sendResponse({ success: true }); + } catch (e) { + console.error("savePrivateKey error:", e); + sendResponse({ success: false, error: e.message || "Failed to save key" }); + } + })(); + return true; + case "getNpub": + (async () => { + try { + const result = await getNpub(message.payload); + sendResponse(result); + } catch (e) { + console.error("getNpub error:", e); + sendResponse(null); + } + })(); + return true; + case "getNsec": + resetAutoLock(); + (async () => { + try { + const result = await getNsec(message.payload); + sendResponse(result); + } catch (e) { + console.error("getNsec error:", e); + sendResponse(null); + } + })(); + return true; + case "calcPubKey": + sendResponse(getPublicKeySync(message.payload)); + return true; + case "npubEncode": + sendResponse(nip_19_exports.npubEncode(message.payload)); + return true; + case "copy": + if (typeof navigator !== "undefined" && navigator.clipboard?.writeText) { + navigator.clipboard.writeText(message.payload).then(() => sendResponse(true)).catch(() => sendResponse(false)); + } else { + sendResponse(false); + } + return true; + // --- Master password / lock handlers --- + // NOTE: These use sendResponse + return true (callback pattern) because + // Chrome MV3 does not reliably deliver Promise-return values from + // onMessage listeners to sendMessage callers. + case "isLocked": + (async () => { + try { + const result = await checkLockState(); + log3(`[isLocked] Sending response: ${result}`); + sendResponse(result); + } catch (e) { + log3(`[isLocked] Error: ${e.message}`); + sendResponse(false); + } + })(); + return true; + case "isEncrypted": + (async () => { + try { + const data = await storage4.get({ isEncrypted: false, passwordHash: null }); + log3(`[isEncrypted] storage: isEncrypted=${data.isEncrypted}, passwordHash=${data.passwordHash ? "EXISTS" : "null"}`); + if (!data.isEncrypted && data.passwordHash) { + log3("[isEncrypted] Self-healing: passwordHash exists but flag=false"); + await storage4.set({ isEncrypted: true }); + data.isEncrypted = true; + } + encryptionEnabled = data.isEncrypted; + log3(`[isEncrypted] Sending response: ${encryptionEnabled}`); + sendResponse(encryptionEnabled); + } catch (e) { + log3(`[isEncrypted] Error: ${e.message}`); + sendResponse(false); + } + })(); + return true; + case "hasEncryptedData": + (async () => { + try { + const data = await storage4.get({ passwordHash: null, profiles: [] }); + const hasPasswordHash = !!data.passwordHash; + let encryptedProfiles = 0; + log3(`[hasEncryptedData] passwordHash=${hasPasswordHash}, profiles=${Array.isArray(data.profiles) ? data.profiles.length : "not-array"}`); + if (Array.isArray(data.profiles)) { + for (let i = 0; i < data.profiles.length; i++) { + const p = data.profiles[i]; + const isEnc = p.privKey ? isEncryptedBlob(p.privKey) : false; + log3(`[hasEncryptedData] profile[${i}] name="${p.name}" privKey=${p.privKey ? isEnc ? "ENCRYPTED" : "PLAINTEXT" : "EMPTY"}`); + if (isEnc) encryptedProfiles++; + } + } + const found = hasPasswordHash || encryptedProfiles > 0; + log3(`[hasEncryptedData] Result: found=${found}, hasPasswordHash=${hasPasswordHash}, encryptedProfiles=${encryptedProfiles}`); + if (found && !encryptionEnabled) { + log3("[hasEncryptedData] Self-healing: setting isEncrypted=true, locked=true"); + await storage4.set({ isEncrypted: true }); + encryptionEnabled = true; + locked = true; + } + sendResponse({ found, hasPasswordHash, encryptedProfiles }); + } catch (e) { + console.error("hasEncryptedData error:", e); + sendResponse({ found: false, hasPasswordHash: false, encryptedProfiles: 0 }); + } + })(); + return true; + case "unlock": + reply(sendResponse, () => unlockSession(message.payload)); + return true; + case "lock": + lockSession().then(() => sendResponse(true)); + return true; + case "setPassword": + (async () => { + try { + await cachePubKeysForAllProfiles(); + await encryptAllKeys(message.payload); + encryptionEnabled = true; + const result = await unlockSession(message.payload); + api.runtime.sendMessage({ kind: "passwordStateChanged", hasPassword: true }).catch(() => { + }); + api.runtime.sendMessage({ kind: "backupNeeded" }).catch(() => { + }); + sendResponse(result); + } catch (e) { + sendResponse({ success: false, error: e.message }); + } + })(); + return true; + case "changePassword": + (async () => { + try { + const { oldPassword, newPassword } = message.payload; + const valid = await checkPassword(oldPassword); + if (!valid) { + sendResponse({ success: false, error: "Invalid current password" }); + return; + } + await changePasswordForKeys(oldPassword, newPassword); + const result = await unlockSession(newPassword); + api.runtime.sendMessage({ kind: "passwordStateChanged", hasPassword: true }).catch(() => { + }); + api.runtime.sendMessage({ kind: "backupNeeded" }).catch(() => { + }); + sendResponse(result); + } catch (e) { + sendResponse({ success: false, error: e.message }); + } + })(); + return true; + case "removePassword": + (async () => { + try { + await removePasswordProtection(message.payload); + sessionKeys.clear(); + sessionCryptoKey = null; + sessionKeySalt = null; + locked = false; + encryptionEnabled = false; + api.runtime.sendMessage({ kind: "passwordStateChanged", hasPassword: false }).catch(() => { + }); + sendResponse({ success: true }); + } catch (e) { + sendResponse({ success: false, error: e.message }); + } + })(); + return true; + case "resetAllData": + (async () => { + try { + await storage4.clear(); + sessionKeys.clear(); + sessionCryptoKey = null; + sessionKeySalt = null; + locked = false; + encryptionEnabled = false; + nostrAccessWhileLocked = false; + blockCrossOriginFrames = true; + await storage4.set({ + profiles: [{ name: "Default Nostr Profile", privKey: "", pubKey: "" }], + profileIndex: 0, + isEncrypted: false, + passwordHash: null, + passwordSalt: null + }); + api.runtime.sendMessage({ kind: "dataReset" }).catch(() => { + }); + sendResponse({ success: true }); + } catch (e) { + sendResponse({ success: false, error: e.message }); + } + })(); + return true; + case "setAutoLockTimeout": { + const ALLOWED_LOCK_MINUTES = [0, 5, 15, 30, 60, 90, 180]; + const mins = Number(message.payload); + if (!ALLOWED_LOCK_MINUTES.includes(mins)) { + sendResponse(false); + return true; + } + autoLockTimeout = mins * 60 * 1e3; + storage4.set({ autoLockMinutes: mins }); + resetAutoLock(); + sendResponse(true); + return true; + } + case "getAutoLockTimeout": + reply(sendResponse, async () => { + const { autoLockMinutes } = await storage4.get({ autoLockMinutes: 15 }); + return autoLockMinutes; + }); + return true; + case "resetAutoLock": + resetAutoLock(); + sendResponse(true); + return true; + // --- Nostr access while locked --- + case "getNostrAccessWhileLocked": + sendResponse(nostrAccessWhileLocked); + return true; + case "setNostrAccessWhileLocked": + nostrAccessWhileLocked = !!message.payload; + storage4.set({ nostrAccessWhileLocked: !!message.payload }); + if (!message.payload && locked) { + sessionKeys.clear(); + } + sendResponse(true); + return true; + case "getBlockCrossOriginFrames": + sendResponse(blockCrossOriginFrames); + return true; + case "setBlockCrossOriginFrames": + blockCrossOriginFrames = !!message.payload; + storage4.set({ blockCrossOriginFrames: !!message.payload }); + sendResponse(true); + return true; + case "getActiveProfileInfo": + (async () => { + try { + const pi = await getProfileIndex(); + const profiles = await getProfiles(); + const profile = profiles[pi]; + if (!profile) { + log3("[getActiveProfileInfo] No profile found at index " + pi); + sendResponse({ name: "Unknown", npub: "", hasKeys: false }); + return; + } + let npub = ""; + if (profile.type === "bunker" && profile.remotePubkey) { + npub = nip_19_exports.npubEncode(profile.remotePubkey); + } else if (profile.pubKey) { + npub = nip_19_exports.npubEncode(profile.pubKey); + } + const result = { + name: profile.name || "Unnamed Profile", + npub, + hasKeys: sessionKeys.has(pi), + isBunker: profile.type === "bunker" + }; + log3("[getActiveProfileInfo] Sending: " + JSON.stringify(result)); + sendResponse(result); + } catch (e) { + log3("[getActiveProfileInfo] Error: " + e.message); + sendResponse({ name: "Error", npub: "", hasKeys: false }); + } + })(); + return true; + // --- NIP-49 ncryptsec handlers --- + case "ncryptsec.decrypt": + reply(sendResponse, async () => { + try { + const { ncryptsec, password } = message.payload; + const hexKey = bytesToHex3(decrypt2(ncryptsec, password)); + return { success: true, hexKey }; + } catch (e) { + return { success: false, error: e.message || "Decryption failed" }; + } + }); + return true; + case "ncryptsec.encrypt": + reply(sendResponse, async () => { + try { + const { profileIndex: ei, password } = message.payload; + const profile = await getProfile(ei); + if (profile?.type === "bunker") { + return { success: false, error: "Cannot export bunker profile as ncryptsec" }; + } + const hexKey = await getPlaintextPrivKey(ei, profile); + const ncryptsec = encrypt2(hexToBytes2(hexKey), password); + return { success: true, ncryptsec }; + } catch (e) { + return { success: false, error: e.message || "Encryption failed" }; + } + }); + return true; + // --- BIP39 Seed Phrase handlers --- + case "seedPhrase.fromKey": + reply(sendResponse, async () => { + try { + const ei = message.payload; + const profile = await getProfile(ei); + if (profile?.type === "bunker") { + return { success: false, error: "Cannot export bunker profile as seed phrase" }; + } + const hexKey = await getPlaintextPrivKey(ei, profile); + const seedPhrase = keyToSeedPhrase(hexKey); + return { success: true, seedPhrase }; + } catch (e) { + return { success: false, error: e.message || "Failed to generate seed phrase" }; + } + }); + return true; + case "seedPhrase.toKey": + reply(sendResponse, async () => { + try { + const { hexKey, pubKey } = seedPhraseToKey(message.payload); + return { success: true, hexKey, pubKey }; + } catch (e) { + return { success: false, error: e.message || "Invalid seed phrase" }; + } + }); + return true; + case "seedPhrase.validate": + sendResponse(isValidSeedPhrase(message.payload)); + return true; + // --- NIP-46 Bunker handlers --- + case "getProfileType": + reply(sendResponse, async () => { + const pi = message.payload ?? await getProfileIndex(); + const profile = await getProfile(pi); + return profile?.type || "local"; + }); + return true; + case "bunker.connect": + reply(sendResponse, async () => { + try { + const { profileIndex: bi, bunkerUrl } = message.payload; + const session = await createSession(bi, bunkerUrl); + const remotePubkey = await session.getPublicKey(); + const profiles = await getProfiles(); + profiles[bi].remotePubkey = remotePubkey; + profiles[bi].bunkerUrl = bunkerUrl; + await storage4.set({ profiles }); + return { success: true, remotePubkey }; + } catch (e) { + return { success: false, error: e.message }; + } + }); + return true; + case "bunker.disconnect": + reply(sendResponse, async () => { + try { + const bi = message.payload; + await disconnectSession(bi); + return { success: true }; + } catch (e) { + return { success: false, error: e.message }; + } + }); + return true; + case "bunker.status": + reply(sendResponse, async () => { + const bi = message.payload ?? await getProfileIndex(); + return { connected: isSessionActive(bi) }; + }); + return true; + case "bunker.ping": + reply(sendResponse, async () => { + try { + const bi = message.payload ?? await getProfileIndex(); + const session = await getOrCreateSession(bi); + const result = await session.ping(); + return { success: true, result }; + } catch (e) { + return { success: false, error: e.message }; + } + }); + return true; + case "bunker.validateUrl": + sendResponse(validateBunkerUrl(message.payload)); + return true; + // --- Bunker Server handlers (extension acts as NIP-46 signer) --- + case "bunkerServer.start": + reply(sendResponse, async () => { + try { + if (activeBunkerServer) { + activeBunkerServer.stop(); + activeBunkerServer = null; + } + const pubkey = await getPubKey(); + const relayUrls = message.payload?.relayUrls || ["wss://relay.nostrkey.com"]; + const secret = crypto.randomUUID().replace(/-/g, "").slice(0, 16); + const server = new BunkerServer({ relayUrls, userPubkey: pubkey, secret }); + await server.start({ getPrivKey }); + activeBunkerServer = server; + return { success: true, uri: server.getConnectionString() }; + } catch (e) { + return { success: false, error: e.message }; + } + }); + return true; + case "bunkerServer.stop": + reply(sendResponse, async () => { + if (activeBunkerServer) { + activeBunkerServer.stop(); + activeBunkerServer = null; + } + return { success: true }; + }); + return true; + case "bunkerServer.status": + sendResponse({ + active: !!activeBunkerServer?.active, + uri: activeBunkerServer?.getConnectionString() || null, + clientCount: activeBunkerServer?.authenticatedClients.size || 0 + }); + return true; + // --- Vault handlers --- + case "vault.publish": + reply(sendResponse, async () => { + try { + const { path, content } = message.payload; + const pubkey = await getPubKey(); + const encrypted = await nip44Encrypt({ pubKey: pubkey, plainText: content }); + const unsigned = buildVaultEvent(path, encrypted); + const pi = await getProfileIndex(); + const profile = await getProfile(pi); + let signed; + if (profile.type === "bunker") { + const session = await getOrCreateSession(pi); + signed = await session.signEvent(unsigned); + } else { + const sk = await getPrivKey(); + signed = await finalizeEvent(unsigned, sk); + } + await withRelays("write", async (relays) => { + for (const relay of relays) { + try { + relay.publish(signed); + } catch (_) { + } + } + }); + return { success: true, eventId: signed.id, createdAt: signed.created_at }; + } catch (e) { + return { success: false, error: e.message }; + } + }); + return true; + case "vault.fetch": + reply(sendResponse, async () => { + try { + const pubkey = await getPubKey(); + const filter = buildVaultFilter(pubkey); + const allEvents = []; + await withRelays("read", async (relays) => { + const perRelay = relays.map((relay) => new Promise((resolve) => { + const subId = `vault-${crypto.randomUUID().slice(0, 8)}`; + const timeout = setTimeout(() => { + try { + relay.unsubscribe(subId); + } catch (_) { + } + resolve(); + }, 15e3); + relay.subscribe( + subId, + [filter], + (event) => { + allEvents.push(event); + }, + () => { + clearTimeout(timeout); + try { + relay.unsubscribe(subId); + } catch (_) { + } + resolve(); + } + ); + })); + await Promise.all(perRelay); + }); + const byDtag = /* @__PURE__ */ new Map(); + for (const event of allEvents) { + const parsed = parseVaultEvent(event); + if (!parsed) continue; + const existing = byDtag.get(parsed.path); + if (!existing || parsed.createdAt > existing.createdAt) { + byDtag.set(parsed.path, { event, parsed }); + } + } + const documents = []; + const pubkey_ = await getPubKey(); + for (const { event, parsed } of byDtag.values()) { + try { + const decrypted = await nip44Decrypt({ pubKey: pubkey_, cipherText: event.content }); + documents.push({ + path: parsed.path, + content: decrypted, + createdAt: parsed.createdAt, + eventId: parsed.eventId + }); + } catch (_) { + } + } + return { success: true, documents }; + } catch (e) { + return { success: false, error: e.message }; + } + }); + return true; + case "vault.delete": + reply(sendResponse, async () => { + try { + const { path, eventId } = message.payload; + const unsigned = buildVaultDeletion(eventId, path); + const pi = await getProfileIndex(); + const profile = await getProfile(pi); + let signed; + if (profile.type === "bunker") { + const session = await getOrCreateSession(pi); + signed = await session.signEvent(unsigned); + } else { + const sk = await getPrivKey(); + signed = await finalizeEvent(unsigned, sk); + } + await withRelays("write", async (relays) => { + for (const relay of relays) { + try { + relay.publish(signed); + } catch (_) { + } + } + }); + return { success: true }; + } catch (e) { + return { success: false, error: e.message }; + } + }); + return true; + case "vault.getRelays": + reply(sendResponse, async () => { + try { + const profile = await currentProfile(); + const relays = profile.relays || []; + const read = relays.filter((r) => r.read).map((r) => r.url); + const write = relays.filter((r) => r.write).map((r) => r.url); + return { read, write }; + } catch (e) { + return { read: [], write: [] }; + } + }); + return true; + // --- API Key Vault handlers --- + case "apikeys.publish": + reply(sendResponse, async () => { + try { + const { keys } = message.payload; + const pubkey = await getPubKey(); + const plainText = JSON.stringify(keys); + const encrypted = await nip44Encrypt({ pubKey: pubkey, plainText }); + const unsigned = buildVaultEvent("vault/api-keys", encrypted); + const pi = await getProfileIndex(); + const profile = await getProfile(pi); + let signed; + if (profile.type === "bunker") { + const session = await getOrCreateSession(pi); + signed = await session.signEvent(unsigned); + } else { + const sk = await getPrivKey(); + signed = await finalizeEvent(unsigned, sk); + } + await withRelays("write", async (relays) => { + for (const relay of relays) { + try { + relay.publish(signed); + } catch (_) { + } + } + }); + return { success: true, eventId: signed.id, createdAt: signed.created_at }; + } catch (e) { + return { success: false, error: e.message }; + } + }); + return true; + case "apikeys.fetch": + reply(sendResponse, async () => { + try { + const pubkey = await getPubKey(); + const filter = { + kinds: [30078], + authors: [pubkey], + "#d": ["nostrkey:vault/api-keys"] + }; + const allEvents = []; + await withRelays("read", async (relays) => { + const perRelay = relays.map((relay) => new Promise((resolve) => { + const subId = `apikeys-${crypto.randomUUID().slice(0, 8)}`; + const timeout = setTimeout(() => { + try { + relay.unsubscribe(subId); + } catch (_) { + } + resolve(); + }, 15e3); + relay.subscribe( + subId, + [filter], + (event) => { + allEvents.push(event); + }, + () => { + clearTimeout(timeout); + try { + relay.unsubscribe(subId); + } catch (_) { + } + resolve(); + } + ); + })); + await Promise.all(perRelay); + }); + let latest = null; + for (const event of allEvents) { + if (!latest || event.created_at > latest.created_at) { + latest = event; + } + } + if (!latest) { + return { success: true, keys: null, eventId: null, createdAt: null }; + } + const decrypted = await nip44Decrypt({ pubKey: pubkey, cipherText: latest.content }); + const keys = JSON.parse(decrypted); + return { success: true, keys, eventId: latest.id, createdAt: latest.created_at }; + } catch (e) { + return { success: false, error: e.message }; + } + }); + return true; + case "apikeys.delete": + reply(sendResponse, async () => { + try { + const { eventId } = message.payload; + const unsigned = buildVaultDeletion(eventId, "vault/api-keys"); + const pi = await getProfileIndex(); + const profile = await getProfile(pi); + let signed; + if (profile.type === "bunker") { + const session = await getOrCreateSession(pi); + signed = await session.signEvent(unsigned); + } else { + const sk = await getPrivKey(); + signed = await finalizeEvent(unsigned, sk); + } + await withRelays("write", async (relays) => { + for (const relay of relays) { + try { + relay.publish(signed); + } catch (_) { + } + } + }); + return { success: true }; + } catch (e) { + return { success: false, error: e.message }; + } + }); + return true; + case "apikeys.encrypt": + reply(sendResponse, async () => { + try { + const { plainText } = message.payload; + const pubkey = await getPubKey(); + const cipherText = await nip44Encrypt({ pubKey: pubkey, plainText }); + return { success: true, cipherText }; + } catch (e) { + return { success: false, error: e.message }; + } + }); + return true; + case "apikeys.decrypt": + reply(sendResponse, async () => { + try { + const { cipherText } = message.payload; + const pubkey = await getPubKey(); + const plainText = await nip44Decrypt({ pubKey: pubkey, cipherText }); + return { success: true, plainText }; + } catch (e) { + return { success: false, error: e.message }; + } + }); + return true; + // --- Encrypted vault backup / restore --- + case "backup.export": + reply(sendResponse, async () => { + const password = message.payload?.password; + if (typeof password !== "string" || password.length < 8) { + return { success: false, error: "A backup password of at least 8 characters is required" }; + } + const data = await storage4.get({ + profiles: [], + profileIndex: 0, + isEncrypted: false, + passwordHash: null, + passwordSalt: null, + apiKeyVault: null, + vaultDocs: null, + nostrAccessWhileLocked: false, + blockCrossOriginFrames: true, + autoLockMinutes: 15, + version: null + }); + const plaintext = JSON.stringify(data); + const encrypted = await encrypt4(plaintext, password); + const version = api.runtime.getManifest?.()?.version || "unknown"; + return { + success: true, + envelope: { + format: "nostrkey-backup", + version: 1, + createdAt: (/* @__PURE__ */ new Date()).toISOString(), + extensionVersion: version, + profileCount: Array.isArray(data.profiles) ? data.profiles.length : 0, + payload: JSON.parse(encrypted) + } + }; + }); + return true; + case "backup.import": + reply(sendResponse, async () => { + try { + const { envelope, password } = message.payload; + if (!envelope || envelope.format !== "nostrkey-backup") { + return { success: false, error: "Not a valid NostrKey backup file" }; + } + if (typeof envelope.version !== "number" || envelope.version > 1) { + return { success: false, error: "Backup version not supported. Update NostrKey and try again." }; + } + const payloadStr = JSON.stringify(envelope.payload); + let plaintext; + try { + plaintext = await decrypt4(payloadStr, password); + } catch (_) { + return { success: false, error: "Wrong password \u2014 could not decrypt backup" }; + } + const data = JSON.parse(plaintext); + await storage4.set(data); + encryptionEnabled = !!data.isEncrypted; + locked = false; + const importSalt = crypto.getRandomValues(new Uint8Array(16)); + sessionCryptoKey = await deriveKey(password, importSalt); + sessionKeySalt = importSalt; + nostrAccessWhileLocked = data.nostrAccessWhileLocked !== false; + blockCrossOriginFrames = data.blockCrossOriginFrames !== false; + if (typeof data.autoLockMinutes === "number") { + autoLockTimeout = data.autoLockMinutes * 60 * 1e3; + } + sessionKeys.clear(); + if (Array.isArray(data.profiles)) { + for (let i = 0; i < data.profiles.length; i++) { + const p = data.profiles[i]; + if (p.type === "bunker" || !p.privKey) continue; + if (isEncryptedBlob(p.privKey)) { + try { + const hex = await decrypt4(p.privKey, password); + sessionKeys.set(i, hex); + } catch (_) { + } + } else { + sessionKeys.set(i, p.privKey); + } + } + } + resetAutoLock(); + const profileCount = Array.isArray(data.profiles) ? data.profiles.length : 0; + return { success: true, profileCount }; + } catch (e) { + return { success: false, error: e.message || "Restore failed" }; + } + }); + return true; + // nostr: protocol URL handler — no key access needed, no permission prompt + case "replaceURL": + reply(sendResponse, async () => { + const { protocol_handler } = await storage4.get(["protocol_handler"]); + if (!protocol_handler) return false; + const { url } = message.payload; + const raw = url.split("nostr:")[1]; + if (!raw) return false; + try { + const decoded = nip_19_exports.decode(raw); + const { type, data } = decoded; + const replacements = { + raw, + hrp: type, + hex: type === "naddr" ? decoded.author || raw : data || raw, + p_or_e: { npub: "p", note: "e", nprofile: "p", nevent: "e", naddr: "a" }[type] || "", + u_or_n: { npub: "u", note: "n", nprofile: "u", nevent: "n", naddr: "n" }[type] || "", + relay0: decoded.relays?.[0] || "", + relay1: decoded.relays?.[1] || "", + relay2: decoded.relays?.[2] || "" + }; + let result = protocol_handler; + for (const [pattern, value] of Object.entries(replacements)) { + result = result.replace(new RegExp(`\\{ *${pattern} *\\}`, "g"), value); + } + return result; + } catch { + return false; + } + }); + return true; + // window.nostr + case "getPubKey": + case "signEvent": + case "nip04.encrypt": + case "nip04.decrypt": + case "nip44.encrypt": + case "nip44.decrypt": + case "getRelays": + case "addRelay": + case "exportProfile": + validations[uuid] = sendResponse; + if (Object.keys(validations).length === 1) { + pendingQueue = { total: 0, processed: 0 }; + } + pendingQueue.total++; + ask(uuid, message); + setTimeout(() => { + if (validations[uuid]) { + deny({ payload: uuid, origKind: message.kind, host: message.host }); + } + prompt.release?.(); + }, 1e4); + return true; + default: + return false; + } + }); + async function forceRelease() { + if (prompt.tabId !== null) { + try { + await api.tabs.get(prompt.tabId); + } catch (error) { + prompt.release?.(); + prompt.tabId = null; + } + } + } + async function generatePrivateKey_() { + const keyPair = await generateKeyPair2(); + return keyPair.privateKey; + } + async function ask(uuid, { kind, host, payload }) { + if (host) { + const now = Date.now(); + const rateEntry = permissionRateMap.get(host) || { count: 0, resetAt: now + 6e4 }; + if (now > rateEntry.resetAt) { + rateEntry.count = 0; + rateEntry.resetAt = now + 6e4; + } + rateEntry.count++; + permissionRateMap.set(host, rateEntry); + if (rateEntry.count > 5) { + log3(`[SECURITY] Rate limited ${host} \u2014 ${rateEntry.count} requests in 60s`); + const sendResponse = validations[uuid]; + delete validations[uuid]; + sendResponse?.({ error: "rate_limited", message: "Too many requests. Please wait a moment." }); + return; + } + } + const pi = await getProfileIndex(); + const profile = await getProfile(pi); + const isBunker = profile?.type === "bunker"; + const needsPrivateKey = kind !== "getPubKey" && kind !== "getRelays" && kind !== "addRelay" && kind !== "exportProfile"; + if (!isBunker && needsPrivateKey) { + const isLocked = await checkLockState(); + if (isLocked) { + if (!(nostrAccessWhileLocked && sessionKeys.has(pi))) { + const isFirstUnlock = sessionKeys.size === 0; + try { + const [activeTab] = await api.tabs.query({ active: true, currentWindow: true }); + if (activeTab?.id) { + api.tabs.sendMessage(activeTab.id, { kind: "showLockedSheet", firstUnlock: isFirstUnlock }).catch(() => { + }); + } + } catch (_) { + } + const sendResponse = validations[uuid]; + delete validations[uuid]; + sendResponse?.({ error: "locked", message: "Extension is locked. Please unlock with your master password." }); + return; + } + } + } + if (isRateLimited(host)) { + const sendResponse = validations[uuid]; + delete validations[uuid]; + sendResponse?.({ error: "rate_limited", message: "Too many requests. Please wait." }); + log3(`Rate limited: ${host}`); + return; + } + await forceRelease(); + prompt.release = await prompt.mutex.acquire(); + pendingQueue.processed++; + const queuePosition = pendingQueue.processed; + const queueTotal = pendingQueue.total; + let mKind = kind === "signEvent" ? `signEvent:${payload.kind}` : kind; + let permission = await getPermission(host, mKind); + if (permission === "allow") { + complete({ + payload: uuid, + origKind: kind, + event: payload, + remember: false, + host + }); + prompt.release(); + return; + } + if (permission === "deny") { + deny({ payload: uuid, origKind: kind, host }); + prompt.release(); + return; + } + try { + const [activeTab] = await api.tabs.query({ active: true, currentWindow: true }); + if (activeTab?.id) { + const result = await api.tabs.sendMessage(activeTab.id, { + kind: "showPermissionSheet", + host, + permissionKind: kind, + queuePosition, + queueTotal + }); + if (result) { + if (result.allowed) { + complete({ + payload: uuid, + origKind: kind, + event: payload, + remember: result.remember, + host + }); + } else { + deny({ + payload: uuid, + origKind: kind, + event: payload, + remember: result.remember, + host + }); + } + prompt.release(); + return; + } + } + } catch (e) { + log3("Bottom sheet unavailable, falling back to tab:", e.message); + } + let qs = new URLSearchParams({ + uuid, + kind, + host, + payload: JSON.stringify(payload || false), + queuePosition, + queueTotal + }); + let tab = await api.tabs.getCurrent(); + let p = await api.tabs.create({ + url: api.runtime.getURL(`permission/permission.html?${qs.toString()}`), + openerTabId: tab?.id + }); + prompt.tabId = p.id; + return true; + } + function complete({ payload, origKind, event, remember, host }) { + const sendResponse = validations[payload]; + delete validations[payload]; + if (Object.keys(validations).length === 0) { + pendingQueue = { total: 0, processed: 0 }; + } + if (remember) { + let mKind = origKind === "signEvent" ? `signEvent:${event.kind}` : origKind; + setPermission(host, mKind, "allow"); + } + if (sendResponse) { + const onError = (e) => { + log3(`Error in ${origKind}: ${e.message}`); + sendResponse({ error: "bunker_error", message: e.message }); + }; + switch (origKind) { + case "getPubKey": + getPubKey().then((pk) => sendResponse(pk)).catch(onError); + break; + case "signEvent": + signEvent_(event, host).then((e) => sendResponse(e)).catch(onError); + break; + case "nip04.encrypt": + nip04Encrypt(event).then((e) => sendResponse(e)).catch(onError); + break; + case "nip04.decrypt": + nip04Decrypt(event).then((e) => sendResponse(e)).catch(onError); + break; + case "nip44.encrypt": + nip44Encrypt(event).then((e) => sendResponse(e)).catch(onError); + break; + case "nip44.decrypt": + nip44Decrypt(event).then((e) => sendResponse(e)).catch(onError); + break; + case "getRelays": + getRelays().then((e) => sendResponse(e)).catch(onError); + break; + case "addRelay": + addRelay(event.url).then((e) => sendResponse(e)).catch(onError); + break; + case "exportProfile": + exportProfileData().then((e) => sendResponse(e)).catch(onError); + break; + } + } + } + function deny({ origKind, host, payload, remember, event }) { + const sendResponse = validations[payload]; + delete validations[payload]; + if (Object.keys(validations).length === 0) { + pendingQueue = { total: 0, processed: 0 }; + } + if (remember) { + let mKind = origKind === "signEvent" ? `signEvent:${event.kind}` : origKind; + setPermission(host, mKind, "deny"); + } + sendResponse?.(void 0); + return false; + } + async function cachePubKeysForAllProfiles() { + const profiles = await getProfiles(); + let updated = false; + for (let i = 0; i < profiles.length; i++) { + const profile = profiles[i]; + if (profile.type === "bunker") continue; + if (profile.pubKey) continue; + if (!profile.privKey || isEncryptedBlob(profile.privKey)) continue; + try { + const pubKey = getPublicKeySync(profile.privKey); + profiles[i].pubKey = pubKey; + updated = true; + } catch (e) { + console.error(`Failed to cache pubKey for profile ${i}:`, e); + } + } + if (updated) { + await storage4.set({ profiles }); + } + } + async function savePrivateKey([index, privKey]) { + const profile = await getProfile(index); + if (profile?.type === "bunker") { + throw new Error("Cannot set private key on a bunker profile"); + } + if (typeof privKey !== "string" || privKey.length === 0) { + throw new Error("Invalid private key: must be a non-empty string"); + } + let hexKey; + if (privKey.startsWith("nsec")) { + try { + hexKey = nip_19_exports.decode(privKey).data; + } catch (e) { + throw new Error("Invalid nsec key"); + } + } else { + hexKey = privKey; + } + if (!/^[0-9a-f]{64}$/i.test(hexKey)) { + throw new Error("Invalid private key: must be 64 hex characters or valid nsec"); + } + let profiles = await get("profiles"); + if (!profiles || index < 0 || index >= profiles.length) { + throw new Error("Invalid profile index"); + } + const pubKey = getPublicKeySync(hexKey); + profiles[index].pubKey = pubKey; + const encrypted = await isEncrypted(); + if (encrypted) { + if (!sessionCryptoKey) { + throw new Error("Extension is locked \u2014 unlock before saving a key"); + } + profiles[index].privKey = await encryptWithKey(hexKey, sessionCryptoKey, sessionKeySalt); + sessionKeys.set(index, hexKey); + } else { + profiles[index].privKey = hexKey; + } + await storage4.set({ profiles }); + return true; + } + async function getNsec(index) { + let profile = await getProfile(index); + if (profile.type === "bunker") return null; + let hexKey = await getPlaintextPrivKey(index, profile); + let nsec = nip_19_exports.nsecEncode(hexKey); + return nsec; + } + async function getNpub(index) { + let profile = await getProfile(index); + if (!profile) return null; + if (profile.type === "bunker") { + if (profile.remotePubkey) return nip_19_exports.npubEncode(profile.remotePubkey); + return null; + } + if (profile.pubKey) { + return nip_19_exports.npubEncode(profile.pubKey); + } + try { + let hexKey = await getPlaintextPrivKey(index, profile); + if (!hexKey || typeof hexKey !== "string" || hexKey.length !== 64) { + return null; + } + let pubKey = getPublicKeySync(hexKey); + let npub = nip_19_exports.npubEncode(pubKey); + return npub; + } catch (e) { + console.error("getNpub error:", e); + return null; + } + } + async function getPlaintextPrivKey(index, profile) { + if (isEncryptedBlob(profile.privKey)) { + if (sessionKeys.has(index)) { + const cached = sessionKeys.get(index); + if (!profile.pubKey || getPublicKeySync(cached) === profile.pubKey) { + return cached; + } + sessionKeys.delete(index); + } + throw new Error("Extension is locked \u2014 cannot access private key"); + } + return profile.privKey; + } + async function getPrivKey() { + let index = await getProfileIndex(); + let profile = await currentProfile(); + let hexKey = await getPlaintextPrivKey(index, profile); + return hexToBytes2(hexKey); + } + async function getPubKey() { + let pi = await getProfileIndex(); + let profile = await getProfile(pi); + if (profile.type === "bunker") { + if (profile.remotePubkey) return profile.remotePubkey; + const session = await getOrCreateSession(pi); + const pubkey = await session.getPublicKey(); + const profiles = await get("profiles"); + profiles[pi].remotePubkey = pubkey; + await storage4.set({ profiles }); + return pubkey; + } + if (profile.pubKey) return profile.pubKey; + let privKey = await getPrivKey(); + let pubKey = getPublicKeySync(bytesToHex3(privKey)); + return pubKey; + } + async function currentProfile() { + let index = await getProfileIndex(); + let profiles = await get("profiles"); + return profiles[index]; + } + async function signEvent_(event, host) { + event = JSON.parse(JSON.stringify(event)); + const pi = await getProfileIndex(); + const profile = await getProfile(pi); + if (profile.type === "bunker") { + const session = await getOrCreateSession(pi); + event = await session.signEvent(event); + } else { + let sk = await getPrivKey(); + event = await finalizeEvent(event, sk); + } + saveEvent({ + event, + metadata: { host, signed_at: Math.round(Date.now() / 1e3) } + }); + return event; + } + async function nip04Encrypt({ pubKey, plainText }) { + const pi = await getProfileIndex(); + const profile = await getProfile(pi); + if (profile.type === "bunker") { + const session = await getOrCreateSession(pi); + return session.nip04Encrypt(pubKey, plainText); + } + let privKey = await getPrivKey(); + return nip_04_exports.encryptMessage(plainText, bytesToHex3(privKey), pubKey); + } + async function nip04Decrypt({ pubKey, cipherText }) { + const pi = await getProfileIndex(); + const profile = await getProfile(pi); + if (profile.type === "bunker") { + const session = await getOrCreateSession(pi); + return session.nip04Decrypt(pubKey, cipherText); + } + let privKey = await getPrivKey(); + return nip_04_exports.decryptMessage(cipherText, bytesToHex3(privKey), pubKey); + } + async function nip44Encrypt({ pubKey, plainText }) { + const pi = await getProfileIndex(); + const profile = await getProfile(pi); + if (profile.type === "bunker") { + const session = await getOrCreateSession(pi); + return session.nip44Encrypt(pubKey, plainText); + } + let privKey = await getPrivKey(); + let conversationKey = nip_44_exports.v2.utils.getConversationKey(privKey, pubKey); + return nip_44_exports.v2.encrypt(plainText, conversationKey); + } + async function nip44Decrypt({ pubKey, cipherText }) { + const pi = await getProfileIndex(); + const profile = await getProfile(pi); + if (profile.type === "bunker") { + const session = await getOrCreateSession(pi); + return session.nip44Decrypt(pubKey, cipherText); + } + let privKey = await getPrivKey(); + let conversationKey = nip_44_exports.v2.utils.getConversationKey(privKey, pubKey); + return nip_44_exports.v2.decrypt(cipherText, conversationKey); + } + async function getRelays() { + let profile = await currentProfile(); + let relays = profile.relays; + let relayObj = {}; + relays.forEach((relay) => { + let { url, read, write } = relay; + relayObj[url] = { read, write }; + }); + return relayObj; + } + async function addRelay(url) { + let parsed; + try { + parsed = new URL(url); + } catch { + throw new Error("Invalid URL"); + } + if (parsed.protocol !== "wss:") { + throw new Error("Must be a wss:// URL"); + } + let profiles = await getProfiles(); + let pi = await getProfileIndex(); + let profile = profiles[pi]; + if (!profile.relays) profile.relays = []; + if (profile.relays.some((r) => r.url === parsed.href)) { + return { success: true, message: "Relay already exists" }; + } + profile.relays.push({ url: parsed.href, read: true, write: true }); + profile.updatedAt = Math.floor(Date.now() / 1e3); + await storage4.set({ profiles }); + return { success: true, message: "Relay added" }; + } + async function exportProfileData() { + let pi = await getProfileIndex(); + let profile = await getProfile(pi); + if (!profile) throw new Error("No active profile"); + if (profile.type === "bunker") { + return { + name: profile.name, + type: "bunker", + bunkerUrl: profile.bunkerUrl || "", + exportedAt: (/* @__PURE__ */ new Date()).toISOString(), + source: "NostrKey" + }; + } + let npub = ""; + if (profile.pubKey) { + npub = nip_19_exports.npubEncode(profile.pubKey); + } + let nsec = ""; + try { + nsec = await getNsec(pi); + } catch { + throw new Error("Cannot export while locked. Please unlock first."); + } + return { + name: profile.name, + npub, + nsec, + relays: (profile.relays || []).map((r) => r.url), + exportedAt: (/* @__PURE__ */ new Date()).toISOString(), + source: "NostrKey" + }; + } + async function withRelays(mode, callback) { + const profile = await currentProfile(); + const relayList = profile.relays || []; + const urls = relayList.filter((r) => mode === "read" ? r.read : r.write).map((r) => r.url); + if (urls.length === 0) { + throw new Error("No relays configured"); + } + const connections = []; + const connectPromises = urls.map(async (url) => { + const relay = new RelayConnection(url); + try { + await relay.connect(); + connections.push(relay); + } catch (_) { + } + }); + await Promise.allSettled(connectPromises); + if (connections.length === 0) { + throw new Error("Failed to connect to any relay"); + } + try { + await callback(connections); + } finally { + for (const relay of connections) { + relay.close(); + } + } + } +})(); /*! Bundled license information: ieee754/index.js: @@ -2080,3 +12791,4 @@ buffer/index.js: @scure/bip39/index.js: (*! scure-bip39 - MIT License (c) 2022 Patricio Palladino, Paul Miller (paulmillr.com) *) */ +//# sourceMappingURL=data:application/json;base64,ewogICJ2ZXJzaW9uIjogMywKICAic291cmNlcyI6IFsiLi4vLi4vc3JjL3NoaW1zL3Byb2Nlc3MuanMiLCAiLi4vLi4vbm9kZV9tb2R1bGVzL3F1aWNrLWZvcm1hdC11bmVzY2FwZWQvaW5kZXguanMiLCAiLi4vLi4vbm9kZV9tb2R1bGVzL3Bpbm8vYnJvd3Nlci5qcyIsICJub2RlLXN0dWI6Y3J5cHRvIiwgIi4uLy4uL25vZGVfbW9kdWxlcy9iZWNoMzIvZGlzdC9pbmRleC5qcyIsICIuLi8uLi9ub2RlX21vZHVsZXMvYmFzZTY0LWpzL2luZGV4LmpzIiwgIi4uLy4uL25vZGVfbW9kdWxlcy9pZWVlNzU0L2luZGV4LmpzIiwgIi4uLy4uL25vZGVfbW9kdWxlcy9idWZmZXIvaW5kZXguanMiLCAiLi4vLi4vc3JjL2JhY2tncm91bmQuanMiLCAiLi4vLi4vbm9kZV9tb2R1bGVzL25vc3RyLWNyeXB0by11dGlscy9zcmMvaW5kZXgudHMiLCAiLi4vLi4vbm9kZV9tb2R1bGVzL25vc3RyLWNyeXB0by11dGlscy9zcmMvdHlwZXMvaW5kZXgudHMiLCAiLi4vLi4vbm9kZV9tb2R1bGVzL25vc3RyLWNyeXB0by11dGlscy9zcmMvdHlwZXMvYmFzZS50cyIsICIuLi8uLi9ub2RlX21vZHVsZXMvbm9zdHItY3J5cHRvLXV0aWxzL3NyYy90eXBlcy9wcm90b2NvbC50cyIsICIuLi8uLi9ub2RlX21vZHVsZXMvbm9zdHItY3J5cHRvLXV0aWxzL2Rpc3QvZXNtL3R5cGVzL21lc3NhZ2VzLmpzIiwgIi4uLy4uL25vZGVfbW9kdWxlcy9ub3N0ci1jcnlwdG8tdXRpbHMvc3JjL3R5cGVzL2d1YXJkcy50cyIsICIuLi8uLi9ub2RlX21vZHVsZXMvbm9zdHItY3J5cHRvLXV0aWxzL3NyYy90eXBlcy9uaXA0Ni50cyIsICIuLi8uLi9ub2RlX21vZHVsZXMvbm9zdHItY3J5cHRvLXV0aWxzL3NyYy9jcnlwdG8udHMiLCAiLi4vLi4vbm9kZV9tb2R1bGVzL0Bub2JsZS9jdXJ2ZXMvc3JjL3NlY3AyNTZrMS50cyIsICIuLi8uLi9ub2RlX21vZHVsZXMvQG5vYmxlL2hhc2hlcy9zcmMvc2hhMi50cyIsICIuLi8uLi9ub2RlX21vZHVsZXMvQG5vYmxlL2hhc2hlcy9zcmMvX21kLnRzIiwgIi4uLy4uL25vZGVfbW9kdWxlcy9Abm9ibGUvaGFzaGVzL3NyYy91dGlscy50cyIsICIuLi8uLi9ub2RlX21vZHVsZXMvQG5vYmxlL2N1cnZlcy9zcmMvYWJzdHJhY3QvY3VydmUudHMiLCAiLi4vLi4vbm9kZV9tb2R1bGVzL0Bub2JsZS9jdXJ2ZXMvc3JjL3V0aWxzLnRzIiwgIi4uLy4uL25vZGVfbW9kdWxlcy9Abm9ibGUvY3VydmVzL3NyYy9hYnN0cmFjdC9tb2R1bGFyLnRzIiwgIi4uLy4uL25vZGVfbW9kdWxlcy9Abm9ibGUvY3VydmVzL3NyYy9hYnN0cmFjdC93ZWllcnN0cmFzcy50cyIsICIuLi8uLi9ub2RlX21vZHVsZXMvQG5vYmxlL2hhc2hlcy9zcmMvaG1hYy50cyIsICIuLi8uLi9ub2RlX21vZHVsZXMvbm9zdHItY3J5cHRvLXV0aWxzL3NyYy91dGlscy9sb2dnZXIudHMiLCAiLi4vLi4vbm9kZV9tb2R1bGVzL25vc3RyLWNyeXB0by11dGlscy9zcmMvZW5jb2RpbmcvYmFzZTY0LnRzIiwgIi4uLy4uL25vZGVfbW9kdWxlcy9ub3N0ci1jcnlwdG8tdXRpbHMvc3JjL3ZhbGlkYXRpb24vaW5kZXgudHMiLCAiLi4vLi4vbm9kZV9tb2R1bGVzL25vc3RyLWNyeXB0by11dGlscy9zcmMvZXZlbnQvaW5kZXgudHMiLCAiLi4vLi4vbm9kZV9tb2R1bGVzL25vc3RyLWNyeXB0by11dGlscy9zcmMvZXZlbnQvY3JlYXRpb24udHMiLCAiLi4vLi4vbm9kZV9tb2R1bGVzL25vc3RyLWNyeXB0by11dGlscy9zcmMvZXZlbnQvc2lnbmluZy50cyIsICIuLi8uLi9ub2RlX21vZHVsZXMvbm9zdHItY3J5cHRvLXV0aWxzL3NyYy9uaXBzL25pcC0wNC50cyIsICIuLi8uLi9ub2RlX21vZHVsZXMvbm9zdHItY3J5cHRvLXV0aWxzL3NyYy9uaXBzL25pcC0wMS50cyIsICIuLi8uLi9ub2RlX21vZHVsZXMvbm9zdHItY3J5cHRvLXV0aWxzL3NyYy9uaXBzL25pcC0xOS50cyIsICIuLi8uLi9ub2RlX21vZHVsZXMvbm9zdHItY3J5cHRvLXV0aWxzL3NyYy9uaXBzL25pcC0yNi50cyIsICIuLi8uLi9ub2RlX21vZHVsZXMvbm9zdHItY3J5cHRvLXV0aWxzL3NyYy9uaXBzL25pcC00NC50cyIsICIuLi8uLi9ub2RlX21vZHVsZXMvQG5vYmxlL2NpcGhlcnMvc3JjL2NoYWNoYS50cyIsICIuLi8uLi9ub2RlX21vZHVsZXMvQG5vYmxlL2NpcGhlcnMvc3JjL19hcngudHMiLCAiLi4vLi4vbm9kZV9tb2R1bGVzL0Bub2JsZS9jaXBoZXJzL3NyYy91dGlscy50cyIsICIuLi8uLi9ub2RlX21vZHVsZXMvQG5vYmxlL2NpcGhlcnMvc3JjL19wb2x5MTMwNS50cyIsICIuLi8uLi9ub2RlX21vZHVsZXMvQG5vYmxlL2hhc2hlcy9zcmMvaGtkZi50cyIsICIuLi8uLi9ub2RlX21vZHVsZXMvQHNjdXJlL2Jhc2UvaW5kZXgudHMiLCAiLi4vLi4vbm9kZV9tb2R1bGVzL25vc3RyLWNyeXB0by11dGlscy9zcmMvbmlwcy9uaXAtNDYudHMiLCAiLi4vLi4vbm9kZV9tb2R1bGVzL25vc3RyLWNyeXB0by11dGlscy9zcmMvbmlwcy9uaXAtNDkudHMiLCAiLi4vLi4vbm9kZV9tb2R1bGVzL0Bub2JsZS9oYXNoZXMvc3JjL3NjcnlwdC50cyIsICIuLi8uLi9ub2RlX21vZHVsZXMvQG5vYmxlL2hhc2hlcy9zcmMvcGJrZGYyLnRzIiwgIi4uLy4uL25vZGVfbW9kdWxlcy9ub3N0ci1jcnlwdG8tdXRpbHMvc3JjL3V0aWxzL2VuY29kaW5nLnRzIiwgIi4uLy4uL3NyYy91dGlsaXRpZXMvc2VlZHBocmFzZS5qcyIsICIuLi8uLi9ub2RlX21vZHVsZXMvQHNjdXJlL2JpcDM5L2luZGV4LmpzIiwgIi4uLy4uL25vZGVfbW9kdWxlcy9Ac2N1cmUvYmlwMzkvd29yZGxpc3RzL2VuZ2xpc2guanMiLCAiLi4vLi4vc3JjL3V0aWxpdGllcy9rZXlzLmpzIiwgIi4uLy4uL25vZGVfbW9kdWxlcy9hc3luYy1tdXRleC9pbmRleC5tanMiLCAiLi4vLi4vc3JjL3V0aWxpdGllcy91dGlscy5qcyIsICIuLi8uLi9zcmMvdXRpbGl0aWVzL2Jyb3dzZXItcG9seWZpbGwuanMiLCAiLi4vLi4vc3JjL3V0aWxpdGllcy9jcnlwdG8uanMiLCAiLi4vLi4vc3JjL3V0aWxpdGllcy9kYi5qcyIsICIuLi8uLi9ub2RlX21vZHVsZXMvaWRiL2J1aWxkL2luZGV4LmpzIiwgIi4uLy4uL3NyYy91dGlsaXRpZXMvc3luYy1tYW5hZ2VyLmpzIiwgIi4uLy4uL3NyYy91dGlsaXRpZXMvbmlwNDYuanMiLCAiLi4vLi4vc3JjL3V0aWxpdGllcy9idW5rZXItc2VydmVyLmpzIiwgIi4uLy4uL3NyYy91dGlsaXRpZXMvbmlwNzguanMiXSwKICAic291cmNlc0NvbnRlbnQiOiBbIi8qKlxuICogTWluaW1hbCBwcm9jZXNzIHNoaW0gZm9yIGJyb3dzZXIgY29udGV4dC5cbiAqIE5vZGUuanMgbGlicmFyaWVzIGJ1bmRsZWQgdmlhIG5vc3RyLWNyeXB0by11dGlscyAoY3J5cHRvLWJyb3dzZXJpZnksXG4gKiByZWFkYWJsZS1zdHJlYW0sIGV0Yy4pIHJlZmVyZW5jZSB0aGUgZ2xvYmFsIGBwcm9jZXNzYCBvYmplY3QuXG4gKiBUaGlzIHByb3ZpZGVzIGp1c3QgZW5vdWdoIGZvciB0aGVtIHRvIHdvcmsgaW4gYSBicm93c2VyIGV4dGVuc2lvbi5cbiAqL1xuZXhwb3J0IHZhciBwcm9jZXNzID0ge1xuICAgIGVudjogeyBOT0RFX0VOVjogJ3Byb2R1Y3Rpb24nLCBMT0dfTEVWRUw6ICd3YXJuJyB9LFxuICAgIGJyb3dzZXI6IHRydWUsXG4gICAgdmVyc2lvbjogJycsXG4gICAgc3Rkb3V0OiBudWxsLFxuICAgIHN0ZGVycjogbnVsbCxcbiAgICBuZXh0VGljazogZnVuY3Rpb24gKGZuKSB7XG4gICAgICAgIHZhciBhcmdzID0gQXJyYXkucHJvdG90eXBlLnNsaWNlLmNhbGwoYXJndW1lbnRzLCAxKTtcbiAgICAgICAgUHJvbWlzZS5yZXNvbHZlKCkudGhlbihmdW5jdGlvbiAoKSB7IGZuLmFwcGx5KG51bGwsIGFyZ3MpOyB9KTtcbiAgICB9LFxufTtcbiIsICIndXNlIHN0cmljdCdcbmZ1bmN0aW9uIHRyeVN0cmluZ2lmeSAobykge1xuICB0cnkgeyByZXR1cm4gSlNPTi5zdHJpbmdpZnkobykgfSBjYXRjaChlKSB7IHJldHVybiAnXCJbQ2lyY3VsYXJdXCInIH1cbn1cblxubW9kdWxlLmV4cG9ydHMgPSBmb3JtYXRcblxuZnVuY3Rpb24gZm9ybWF0KGYsIGFyZ3MsIG9wdHMpIHtcbiAgdmFyIHNzID0gKG9wdHMgJiYgb3B0cy5zdHJpbmdpZnkpIHx8IHRyeVN0cmluZ2lmeVxuICB2YXIgb2Zmc2V0ID0gMVxuICBpZiAodHlwZW9mIGYgPT09ICdvYmplY3QnICYmIGYgIT09IG51bGwpIHtcbiAgICB2YXIgbGVuID0gYXJncy5sZW5ndGggKyBvZmZzZXRcbiAgICBpZiAobGVuID09PSAxKSByZXR1cm4gZlxuICAgIHZhciBvYmplY3RzID0gbmV3IEFycmF5KGxlbilcbiAgICBvYmplY3RzWzBdID0gc3MoZilcbiAgICBmb3IgKHZhciBpbmRleCA9IDE7IGluZGV4IDwgbGVuOyBpbmRleCsrKSB7XG4gICAgICBvYmplY3RzW2luZGV4XSA9IHNzKGFyZ3NbaW5kZXhdKVxuICAgIH1cbiAgICByZXR1cm4gb2JqZWN0cy5qb2luKCcgJylcbiAgfVxuICBpZiAodHlwZW9mIGYgIT09ICdzdHJpbmcnKSB7XG4gICAgcmV0dXJuIGZcbiAgfVxuICB2YXIgYXJnTGVuID0gYXJncy5sZW5ndGhcbiAgaWYgKGFyZ0xlbiA9PT0gMCkgcmV0dXJuIGZcbiAgdmFyIHN0ciA9ICcnXG4gIHZhciBhID0gMSAtIG9mZnNldFxuICB2YXIgbGFzdFBvcyA9IC0xXG4gIHZhciBmbGVuID0gKGYgJiYgZi5sZW5ndGgpIHx8IDBcbiAgZm9yICh2YXIgaSA9IDA7IGkgPCBmbGVuOykge1xuICAgIGlmIChmLmNoYXJDb2RlQXQoaSkgPT09IDM3ICYmIGkgKyAxIDwgZmxlbikge1xuICAgICAgbGFzdFBvcyA9IGxhc3RQb3MgPiAtMSA/IGxhc3RQb3MgOiAwXG4gICAgICBzd2l0Y2ggKGYuY2hhckNvZGVBdChpICsgMSkpIHtcbiAgICAgICAgY2FzZSAxMDA6IC8vICdkJ1xuICAgICAgICBjYXNlIDEwMjogLy8gJ2YnXG4gICAgICAgICAgaWYgKGEgPj0gYXJnTGVuKVxuICAgICAgICAgICAgYnJlYWtcbiAgICAgICAgICBpZiAoYXJnc1thXSA9PSBudWxsKSAgYnJlYWtcbiAgICAgICAgICBpZiAobGFzdFBvcyA8IGkpXG4gICAgICAgICAgICBzdHIgKz0gZi5zbGljZShsYXN0UG9zLCBpKVxuICAgICAgICAgIHN0ciArPSBOdW1iZXIoYXJnc1thXSlcbiAgICAgICAgICBsYXN0UG9zID0gaSArIDJcbiAgICAgICAgICBpKytcbiAgICAgICAgICBicmVha1xuICAgICAgICBjYXNlIDEwNTogLy8gJ2knXG4gICAgICAgICAgaWYgKGEgPj0gYXJnTGVuKVxuICAgICAgICAgICAgYnJlYWtcbiAgICAgICAgICBpZiAoYXJnc1thXSA9PSBudWxsKSAgYnJlYWtcbiAgICAgICAgICBpZiAobGFzdFBvcyA8IGkpXG4gICAgICAgICAgICBzdHIgKz0gZi5zbGljZShsYXN0UG9zLCBpKVxuICAgICAgICAgIHN0ciArPSBNYXRoLmZsb29yKE51bWJlcihhcmdzW2FdKSlcbiAgICAgICAgICBsYXN0UG9zID0gaSArIDJcbiAgICAgICAgICBpKytcbiAgICAgICAgICBicmVha1xuICAgICAgICBjYXNlIDc5OiAvLyAnTydcbiAgICAgICAgY2FzZSAxMTE6IC8vICdvJ1xuICAgICAgICBjYXNlIDEwNjogLy8gJ2onXG4gICAgICAgICAgaWYgKGEgPj0gYXJnTGVuKVxuICAgICAgICAgICAgYnJlYWtcbiAgICAgICAgICBpZiAoYXJnc1thXSA9PT0gdW5kZWZpbmVkKSBicmVha1xuICAgICAgICAgIGlmIChsYXN0UG9zIDwgaSlcbiAgICAgICAgICAgIHN0ciArPSBmLnNsaWNlKGxhc3RQb3MsIGkpXG4gICAgICAgICAgdmFyIHR5cGUgPSB0eXBlb2YgYXJnc1thXVxuICAgICAgICAgIGlmICh0eXBlID09PSAnc3RyaW5nJykge1xuICAgICAgICAgICAgc3RyICs9ICdcXCcnICsgYXJnc1thXSArICdcXCcnXG4gICAgICAgICAgICBsYXN0UG9zID0gaSArIDJcbiAgICAgICAgICAgIGkrK1xuICAgICAgICAgICAgYnJlYWtcbiAgICAgICAgICB9XG4gICAgICAgICAgaWYgKHR5cGUgPT09ICdmdW5jdGlvbicpIHtcbiAgICAgICAgICAgIHN0ciArPSBhcmdzW2FdLm5hbWUgfHwgJzxhbm9ueW1vdXM+J1xuICAgICAgICAgICAgbGFzdFBvcyA9IGkgKyAyXG4gICAgICAgICAgICBpKytcbiAgICAgICAgICAgIGJyZWFrXG4gICAgICAgICAgfVxuICAgICAgICAgIHN0ciArPSBzcyhhcmdzW2FdKVxuICAgICAgICAgIGxhc3RQb3MgPSBpICsgMlxuICAgICAgICAgIGkrK1xuICAgICAgICAgIGJyZWFrXG4gICAgICAgIGNhc2UgMTE1OiAvLyAncydcbiAgICAgICAgICBpZiAoYSA+PSBhcmdMZW4pXG4gICAgICAgICAgICBicmVha1xuICAgICAgICAgIGlmIChsYXN0UG9zIDwgaSlcbiAgICAgICAgICAgIHN0ciArPSBmLnNsaWNlKGxhc3RQb3MsIGkpXG4gICAgICAgICAgc3RyICs9IFN0cmluZyhhcmdzW2FdKVxuICAgICAgICAgIGxhc3RQb3MgPSBpICsgMlxuICAgICAgICAgIGkrK1xuICAgICAgICAgIGJyZWFrXG4gICAgICAgIGNhc2UgMzc6IC8vICclJ1xuICAgICAgICAgIGlmIChsYXN0UG9zIDwgaSlcbiAgICAgICAgICAgIHN0ciArPSBmLnNsaWNlKGxhc3RQb3MsIGkpXG4gICAgICAgICAgc3RyICs9ICclJ1xuICAgICAgICAgIGxhc3RQb3MgPSBpICsgMlxuICAgICAgICAgIGkrK1xuICAgICAgICAgIGEtLVxuICAgICAgICAgIGJyZWFrXG4gICAgICB9XG4gICAgICArK2FcbiAgICB9XG4gICAgKytpXG4gIH1cbiAgaWYgKGxhc3RQb3MgPT09IC0xKVxuICAgIHJldHVybiBmXG4gIGVsc2UgaWYgKGxhc3RQb3MgPCBmbGVuKSB7XG4gICAgc3RyICs9IGYuc2xpY2UobGFzdFBvcylcbiAgfVxuXG4gIHJldHVybiBzdHJcbn1cbiIsICIndXNlIHN0cmljdCdcblxuY29uc3QgZm9ybWF0ID0gcmVxdWlyZSgncXVpY2stZm9ybWF0LXVuZXNjYXBlZCcpXG5cbm1vZHVsZS5leHBvcnRzID0gcGlub1xuXG5jb25zdCBfY29uc29sZSA9IHBmR2xvYmFsVGhpc09yRmFsbGJhY2soKS5jb25zb2xlIHx8IHt9XG5jb25zdCBzdGRTZXJpYWxpemVycyA9IHtcbiAgbWFwSHR0cFJlcXVlc3Q6IG1vY2ssXG4gIG1hcEh0dHBSZXNwb25zZTogbW9jayxcbiAgd3JhcFJlcXVlc3RTZXJpYWxpemVyOiBwYXNzdGhyb3VnaCxcbiAgd3JhcFJlc3BvbnNlU2VyaWFsaXplcjogcGFzc3Rocm91Z2gsXG4gIHdyYXBFcnJvclNlcmlhbGl6ZXI6IHBhc3N0aHJvdWdoLFxuICByZXE6IG1vY2ssXG4gIHJlczogbW9jayxcbiAgZXJyOiBhc0VyclZhbHVlLFxuICBlcnJXaXRoQ2F1c2U6IGFzRXJyVmFsdWVcbn1cbmZ1bmN0aW9uIGxldmVsVG9WYWx1ZSAobGV2ZWwsIGxvZ2dlcikge1xuICByZXR1cm4gbGV2ZWwgPT09ICdzaWxlbnQnXG4gICAgPyBJbmZpbml0eVxuICAgIDogbG9nZ2VyLmxldmVscy52YWx1ZXNbbGV2ZWxdXG59XG5jb25zdCBiYXNlTG9nRnVuY3Rpb25TeW1ib2wgPSBTeW1ib2woJ3Bpbm8ubG9nRnVuY3MnKVxuY29uc3QgaGllcmFyY2h5U3ltYm9sID0gU3ltYm9sKCdwaW5vLmhpZXJhcmNoeScpXG5cbmNvbnN0IGxvZ0ZhbGxiYWNrTWFwID0ge1xuICBlcnJvcjogJ2xvZycsXG4gIGZhdGFsOiAnZXJyb3InLFxuICB3YXJuOiAnZXJyb3InLFxuICBpbmZvOiAnbG9nJyxcbiAgZGVidWc6ICdsb2cnLFxuICB0cmFjZTogJ2xvZydcbn1cblxuZnVuY3Rpb24gYXBwZW5kQ2hpbGRMb2dnZXIgKHBhcmVudExvZ2dlciwgY2hpbGRMb2dnZXIpIHtcbiAgY29uc3QgbmV3RW50cnkgPSB7XG4gICAgbG9nZ2VyOiBjaGlsZExvZ2dlcixcbiAgICBwYXJlbnQ6IHBhcmVudExvZ2dlcltoaWVyYXJjaHlTeW1ib2xdXG4gIH1cbiAgY2hpbGRMb2dnZXJbaGllcmFyY2h5U3ltYm9sXSA9IG5ld0VudHJ5XG59XG5cbmZ1bmN0aW9uIHNldHVwQmFzZUxvZ0Z1bmN0aW9ucyAobG9nZ2VyLCBsZXZlbHMsIHByb3RvKSB7XG4gIGNvbnN0IGxvZ0Z1bmN0aW9ucyA9IHt9XG4gIGxldmVscy5mb3JFYWNoKGxldmVsID0+IHtcbiAgICBsb2dGdW5jdGlvbnNbbGV2ZWxdID0gcHJvdG9bbGV2ZWxdID8gcHJvdG9bbGV2ZWxdIDogKF9jb25zb2xlW2xldmVsXSB8fCBfY29uc29sZVtsb2dGYWxsYmFja01hcFtsZXZlbF0gfHwgJ2xvZyddIHx8IG5vb3ApXG4gIH0pXG4gIGxvZ2dlcltiYXNlTG9nRnVuY3Rpb25TeW1ib2xdID0gbG9nRnVuY3Rpb25zXG59XG5cbmZ1bmN0aW9uIHNob3VsZFNlcmlhbGl6ZSAoc2VyaWFsaXplLCBzZXJpYWxpemVycykge1xuICBpZiAoQXJyYXkuaXNBcnJheShzZXJpYWxpemUpKSB7XG4gICAgY29uc3QgaGFzVG9GaWx0ZXIgPSBzZXJpYWxpemUuZmlsdGVyKGZ1bmN0aW9uIChrKSB7XG4gICAgICByZXR1cm4gayAhPT0gJyFzdGRTZXJpYWxpemVycy5lcnInXG4gICAgfSlcbiAgICByZXR1cm4gaGFzVG9GaWx0ZXJcbiAgfSBlbHNlIGlmIChzZXJpYWxpemUgPT09IHRydWUpIHtcbiAgICByZXR1cm4gT2JqZWN0LmtleXMoc2VyaWFsaXplcnMpXG4gIH1cblxuICByZXR1cm4gZmFsc2Vcbn1cblxuZnVuY3Rpb24gcGlubyAob3B0cykge1xuICBvcHRzID0gb3B0cyB8fCB7fVxuICBvcHRzLmJyb3dzZXIgPSBvcHRzLmJyb3dzZXIgfHwge31cblxuICBjb25zdCB0cmFuc21pdCA9IG9wdHMuYnJvd3Nlci50cmFuc21pdFxuICBpZiAodHJhbnNtaXQgJiYgdHlwZW9mIHRyYW5zbWl0LnNlbmQgIT09ICdmdW5jdGlvbicpIHsgdGhyb3cgRXJyb3IoJ3Bpbm86IHRyYW5zbWl0IG9wdGlvbiBtdXN0IGhhdmUgYSBzZW5kIGZ1bmN0aW9uJykgfVxuXG4gIGNvbnN0IHByb3RvID0gb3B0cy5icm93c2VyLndyaXRlIHx8IF9jb25zb2xlXG4gIGlmIChvcHRzLmJyb3dzZXIud3JpdGUpIG9wdHMuYnJvd3Nlci5hc09iamVjdCA9IHRydWVcbiAgY29uc3Qgc2VyaWFsaXplcnMgPSBvcHRzLnNlcmlhbGl6ZXJzIHx8IHt9XG4gIGNvbnN0IHNlcmlhbGl6ZSA9IHNob3VsZFNlcmlhbGl6ZShvcHRzLmJyb3dzZXIuc2VyaWFsaXplLCBzZXJpYWxpemVycylcbiAgbGV0IHN0ZEVyclNlcmlhbGl6ZSA9IG9wdHMuYnJvd3Nlci5zZXJpYWxpemVcblxuICBpZiAoXG4gICAgQXJyYXkuaXNBcnJheShvcHRzLmJyb3dzZXIuc2VyaWFsaXplKSAmJlxuICAgIG9wdHMuYnJvd3Nlci5zZXJpYWxpemUuaW5kZXhPZignIXN0ZFNlcmlhbGl6ZXJzLmVycicpID4gLTFcbiAgKSBzdGRFcnJTZXJpYWxpemUgPSBmYWxzZVxuXG4gIGNvbnN0IGN1c3RvbUxldmVscyA9IE9iamVjdC5rZXlzKG9wdHMuY3VzdG9tTGV2ZWxzIHx8IHt9KVxuICBjb25zdCBsZXZlbHMgPSBbJ2Vycm9yJywgJ2ZhdGFsJywgJ3dhcm4nLCAnaW5mbycsICdkZWJ1ZycsICd0cmFjZSddLmNvbmNhdChjdXN0b21MZXZlbHMpXG5cbiAgaWYgKHR5cGVvZiBwcm90byA9PT0gJ2Z1bmN0aW9uJykge1xuICAgIGxldmVscy5mb3JFYWNoKGZ1bmN0aW9uIChsZXZlbCkge1xuICAgICAgcHJvdG9bbGV2ZWxdID0gcHJvdG9cbiAgICB9KVxuICB9XG4gIGlmIChvcHRzLmVuYWJsZWQgPT09IGZhbHNlIHx8IG9wdHMuYnJvd3Nlci5kaXNhYmxlZCkgb3B0cy5sZXZlbCA9ICdzaWxlbnQnXG4gIGNvbnN0IGxldmVsID0gb3B0cy5sZXZlbCB8fCAnaW5mbydcbiAgY29uc3QgbG9nZ2VyID0gT2JqZWN0LmNyZWF0ZShwcm90bylcbiAgaWYgKCFsb2dnZXIubG9nKSBsb2dnZXIubG9nID0gbm9vcFxuXG4gIHNldHVwQmFzZUxvZ0Z1bmN0aW9ucyhsb2dnZXIsIGxldmVscywgcHJvdG8pXG4gIC8vIHNldHVwIHJvb3QgaGllcmFyY2h5IGVudHJ5XG4gIGFwcGVuZENoaWxkTG9nZ2VyKHt9LCBsb2dnZXIpXG5cbiAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGxvZ2dlciwgJ2xldmVsVmFsJywge1xuICAgIGdldDogZ2V0TGV2ZWxWYWxcbiAgfSlcbiAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGxvZ2dlciwgJ2xldmVsJywge1xuICAgIGdldDogZ2V0TGV2ZWwsXG4gICAgc2V0OiBzZXRMZXZlbFxuICB9KVxuXG4gIGNvbnN0IHNldE9wdHMgPSB7XG4gICAgdHJhbnNtaXQsXG4gICAgc2VyaWFsaXplLFxuICAgIGFzT2JqZWN0OiBvcHRzLmJyb3dzZXIuYXNPYmplY3QsXG4gICAgYXNPYmplY3RCaW5kaW5nc09ubHk6IG9wdHMuYnJvd3Nlci5hc09iamVjdEJpbmRpbmdzT25seSxcbiAgICBmb3JtYXR0ZXJzOiBvcHRzLmJyb3dzZXIuZm9ybWF0dGVycyxcbiAgICByZXBvcnRDYWxsZXI6IG9wdHMuYnJvd3Nlci5yZXBvcnRDYWxsZXIsXG4gICAgbGV2ZWxzLFxuICAgIHRpbWVzdGFtcDogZ2V0VGltZUZ1bmN0aW9uKG9wdHMpLFxuICAgIG1lc3NhZ2VLZXk6IG9wdHMubWVzc2FnZUtleSB8fCAnbXNnJyxcbiAgICBvbkNoaWxkOiBvcHRzLm9uQ2hpbGQgfHwgbm9vcFxuICB9XG4gIGxvZ2dlci5sZXZlbHMgPSBnZXRMZXZlbHMob3B0cylcbiAgbG9nZ2VyLmxldmVsID0gbGV2ZWxcblxuICBsb2dnZXIuaXNMZXZlbEVuYWJsZWQgPSBmdW5jdGlvbiAobGV2ZWwpIHtcbiAgICBpZiAoIXRoaXMubGV2ZWxzLnZhbHVlc1tsZXZlbF0pIHtcbiAgICAgIHJldHVybiBmYWxzZVxuICAgIH1cblxuICAgIHJldHVybiB0aGlzLmxldmVscy52YWx1ZXNbbGV2ZWxdID49IHRoaXMubGV2ZWxzLnZhbHVlc1t0aGlzLmxldmVsXVxuICB9XG4gIGxvZ2dlci5zZXRNYXhMaXN0ZW5lcnMgPSBsb2dnZXIuZ2V0TWF4TGlzdGVuZXJzID1cbiAgbG9nZ2VyLmVtaXQgPSBsb2dnZXIuYWRkTGlzdGVuZXIgPSBsb2dnZXIub24gPVxuICBsb2dnZXIucHJlcGVuZExpc3RlbmVyID0gbG9nZ2VyLm9uY2UgPVxuICBsb2dnZXIucHJlcGVuZE9uY2VMaXN0ZW5lciA9IGxvZ2dlci5yZW1vdmVMaXN0ZW5lciA9XG4gIGxvZ2dlci5yZW1vdmVBbGxMaXN0ZW5lcnMgPSBsb2dnZXIubGlzdGVuZXJzID1cbiAgbG9nZ2VyLmxpc3RlbmVyQ291bnQgPSBsb2dnZXIuZXZlbnROYW1lcyA9XG4gIGxvZ2dlci53cml0ZSA9IGxvZ2dlci5mbHVzaCA9IG5vb3BcbiAgbG9nZ2VyLnNlcmlhbGl6ZXJzID0gc2VyaWFsaXplcnNcbiAgbG9nZ2VyLl9zZXJpYWxpemUgPSBzZXJpYWxpemVcbiAgbG9nZ2VyLl9zdGRFcnJTZXJpYWxpemUgPSBzdGRFcnJTZXJpYWxpemVcbiAgbG9nZ2VyLmNoaWxkID0gZnVuY3Rpb24gKC4uLmFyZ3MpIHsgcmV0dXJuIGNoaWxkLmNhbGwodGhpcywgc2V0T3B0cywgLi4uYXJncykgfVxuXG4gIGlmICh0cmFuc21pdCkgbG9nZ2VyLl9sb2dFdmVudCA9IGNyZWF0ZUxvZ0V2ZW50U2hhcGUoKVxuXG4gIGZ1bmN0aW9uIGdldExldmVsVmFsICgpIHtcbiAgICByZXR1cm4gbGV2ZWxUb1ZhbHVlKHRoaXMubGV2ZWwsIHRoaXMpXG4gIH1cblxuICBmdW5jdGlvbiBnZXRMZXZlbCAoKSB7XG4gICAgcmV0dXJuIHRoaXMuX2xldmVsXG4gIH1cbiAgZnVuY3Rpb24gc2V0TGV2ZWwgKGxldmVsKSB7XG4gICAgaWYgKGxldmVsICE9PSAnc2lsZW50JyAmJiAhdGhpcy5sZXZlbHMudmFsdWVzW2xldmVsXSkge1xuICAgICAgdGhyb3cgRXJyb3IoJ3Vua25vd24gbGV2ZWwgJyArIGxldmVsKVxuICAgIH1cbiAgICB0aGlzLl9sZXZlbCA9IGxldmVsXG5cbiAgICBzZXQodGhpcywgc2V0T3B0cywgbG9nZ2VyLCAnZXJyb3InKSAvLyA8LS0gbXVzdCBzdGF5IGZpcnN0XG4gICAgc2V0KHRoaXMsIHNldE9wdHMsIGxvZ2dlciwgJ2ZhdGFsJylcbiAgICBzZXQodGhpcywgc2V0T3B0cywgbG9nZ2VyLCAnd2FybicpXG4gICAgc2V0KHRoaXMsIHNldE9wdHMsIGxvZ2dlciwgJ2luZm8nKVxuICAgIHNldCh0aGlzLCBzZXRPcHRzLCBsb2dnZXIsICdkZWJ1ZycpXG4gICAgc2V0KHRoaXMsIHNldE9wdHMsIGxvZ2dlciwgJ3RyYWNlJylcblxuICAgIGN1c3RvbUxldmVscy5mb3JFYWNoKChsZXZlbCkgPT4ge1xuICAgICAgc2V0KHRoaXMsIHNldE9wdHMsIGxvZ2dlciwgbGV2ZWwpXG4gICAgfSlcbiAgfVxuXG4gIGZ1bmN0aW9uIGNoaWxkIChzZXRPcHRzLCBiaW5kaW5ncywgY2hpbGRPcHRpb25zKSB7XG4gICAgaWYgKCFiaW5kaW5ncykge1xuICAgICAgdGhyb3cgbmV3IEVycm9yKCdtaXNzaW5nIGJpbmRpbmdzIGZvciBjaGlsZCBQaW5vJylcbiAgICB9XG4gICAgY2hpbGRPcHRpb25zID0gY2hpbGRPcHRpb25zIHx8IHt9XG4gICAgaWYgKHNlcmlhbGl6ZSAmJiBiaW5kaW5ncy5zZXJpYWxpemVycykge1xuICAgICAgY2hpbGRPcHRpb25zLnNlcmlhbGl6ZXJzID0gYmluZGluZ3Muc2VyaWFsaXplcnNcbiAgICB9XG4gICAgY29uc3QgY2hpbGRPcHRpb25zU2VyaWFsaXplcnMgPSBjaGlsZE9wdGlvbnMuc2VyaWFsaXplcnNcbiAgICBpZiAoc2VyaWFsaXplICYmIGNoaWxkT3B0aW9uc1NlcmlhbGl6ZXJzKSB7XG4gICAgICB2YXIgY2hpbGRTZXJpYWxpemVycyA9IE9iamVjdC5hc3NpZ24oe30sIHNlcmlhbGl6ZXJzLCBjaGlsZE9wdGlvbnNTZXJpYWxpemVycylcbiAgICAgIHZhciBjaGlsZFNlcmlhbGl6ZSA9IG9wdHMuYnJvd3Nlci5zZXJpYWxpemUgPT09IHRydWVcbiAgICAgICAgPyBPYmplY3Qua2V5cyhjaGlsZFNlcmlhbGl6ZXJzKVxuICAgICAgICA6IHNlcmlhbGl6ZVxuICAgICAgZGVsZXRlIGJpbmRpbmdzLnNlcmlhbGl6ZXJzXG4gICAgICBhcHBseVNlcmlhbGl6ZXJzKFtiaW5kaW5nc10sIGNoaWxkU2VyaWFsaXplLCBjaGlsZFNlcmlhbGl6ZXJzLCB0aGlzLl9zdGRFcnJTZXJpYWxpemUpXG4gICAgfVxuICAgIGZ1bmN0aW9uIENoaWxkIChwYXJlbnQpIHtcbiAgICAgIHRoaXMuX2NoaWxkTGV2ZWwgPSAocGFyZW50Ll9jaGlsZExldmVsIHwgMCkgKyAxXG5cbiAgICAgIC8vIG1ha2Ugc3VyZSBiaW5kaW5ncyBhcmUgYXZhaWxhYmxlIGluIHRoZSBgc2V0YCBmdW5jdGlvblxuICAgICAgdGhpcy5iaW5kaW5ncyA9IGJpbmRpbmdzXG5cbiAgICAgIGlmIChjaGlsZFNlcmlhbGl6ZXJzKSB7XG4gICAgICAgIHRoaXMuc2VyaWFsaXplcnMgPSBjaGlsZFNlcmlhbGl6ZXJzXG4gICAgICAgIHRoaXMuX3NlcmlhbGl6ZSA9IGNoaWxkU2VyaWFsaXplXG4gICAgICB9XG4gICAgICBpZiAodHJhbnNtaXQpIHtcbiAgICAgICAgdGhpcy5fbG9nRXZlbnQgPSBjcmVhdGVMb2dFdmVudFNoYXBlKFxuICAgICAgICAgIFtdLmNvbmNhdChwYXJlbnQuX2xvZ0V2ZW50LmJpbmRpbmdzLCBiaW5kaW5ncylcbiAgICAgICAgKVxuICAgICAgfVxuICAgIH1cbiAgICBDaGlsZC5wcm90b3R5cGUgPSB0aGlzXG4gICAgY29uc3QgbmV3TG9nZ2VyID0gbmV3IENoaWxkKHRoaXMpXG5cbiAgICAvLyBtdXN0IGhhcHBlbiBiZWZvcmUgdGhlIGxldmVsIGlzIGFzc2lnbmVkXG4gICAgYXBwZW5kQ2hpbGRMb2dnZXIodGhpcywgbmV3TG9nZ2VyKVxuICAgIG5ld0xvZ2dlci5jaGlsZCA9IGZ1bmN0aW9uICguLi5hcmdzKSB7IHJldHVybiBjaGlsZC5jYWxsKHRoaXMsIHNldE9wdHMsIC4uLmFyZ3MpIH1cbiAgICAvLyByZXF1aXJlZCB0byBhY3R1YWxseSBpbml0aWFsaXplIHRoZSBsb2dnZXIgZnVuY3Rpb25zIGZvciBhbnkgZ2l2ZW4gY2hpbGRcbiAgICBuZXdMb2dnZXIubGV2ZWwgPSBjaGlsZE9wdGlvbnMubGV2ZWwgfHwgdGhpcy5sZXZlbCAvLyBhbGxvdyBsZXZlbCB0byBiZSBzZXQgYnkgY2hpbGRPcHRpb25zXG4gICAgc2V0T3B0cy5vbkNoaWxkKG5ld0xvZ2dlcilcblxuICAgIHJldHVybiBuZXdMb2dnZXJcbiAgfVxuICByZXR1cm4gbG9nZ2VyXG59XG5cbmZ1bmN0aW9uIGdldExldmVscyAob3B0cykge1xuICBjb25zdCBjdXN0b21MZXZlbHMgPSBvcHRzLmN1c3RvbUxldmVscyB8fCB7fVxuXG4gIGNvbnN0IHZhbHVlcyA9IE9iamVjdC5hc3NpZ24oe30sIHBpbm8ubGV2ZWxzLnZhbHVlcywgY3VzdG9tTGV2ZWxzKVxuICBjb25zdCBsYWJlbHMgPSBPYmplY3QuYXNzaWduKHt9LCBwaW5vLmxldmVscy5sYWJlbHMsIGludmVydE9iamVjdChjdXN0b21MZXZlbHMpKVxuXG4gIHJldHVybiB7XG4gICAgdmFsdWVzLFxuICAgIGxhYmVsc1xuICB9XG59XG5cbmZ1bmN0aW9uIGludmVydE9iamVjdCAob2JqKSB7XG4gIGNvbnN0IGludmVydGVkID0ge31cbiAgT2JqZWN0LmtleXMob2JqKS5mb3JFYWNoKGZ1bmN0aW9uIChrZXkpIHtcbiAgICBpbnZlcnRlZFtvYmpba2V5XV0gPSBrZXlcbiAgfSlcbiAgcmV0dXJuIGludmVydGVkXG59XG5cbnBpbm8ubGV2ZWxzID0ge1xuICB2YWx1ZXM6IHtcbiAgICBmYXRhbDogNjAsXG4gICAgZXJyb3I6IDUwLFxuICAgIHdhcm46IDQwLFxuICAgIGluZm86IDMwLFxuICAgIGRlYnVnOiAyMCxcbiAgICB0cmFjZTogMTBcbiAgfSxcbiAgbGFiZWxzOiB7XG4gICAgMTA6ICd0cmFjZScsXG4gICAgMjA6ICdkZWJ1ZycsXG4gICAgMzA6ICdpbmZvJyxcbiAgICA0MDogJ3dhcm4nLFxuICAgIDUwOiAnZXJyb3InLFxuICAgIDYwOiAnZmF0YWwnXG4gIH1cbn1cblxucGluby5zdGRTZXJpYWxpemVycyA9IHN0ZFNlcmlhbGl6ZXJzXG5waW5vLnN0ZFRpbWVGdW5jdGlvbnMgPSBPYmplY3QuYXNzaWduKHt9LCB7IG51bGxUaW1lLCBlcG9jaFRpbWUsIHVuaXhUaW1lLCBpc29UaW1lIH0pXG5cbmZ1bmN0aW9uIGdldEJpbmRpbmdDaGFpbiAobG9nZ2VyKSB7XG4gIGNvbnN0IGJpbmRpbmdzID0gW11cbiAgaWYgKGxvZ2dlci5iaW5kaW5ncykge1xuICAgIGJpbmRpbmdzLnB1c2gobG9nZ2VyLmJpbmRpbmdzKVxuICB9XG5cbiAgLy8gdHJhdmVyc2UgdXAgdGhlIHRyZWUgdG8gZ2V0IGFsbCBiaW5kaW5nc1xuICBsZXQgaGllcmFyY2h5ID0gbG9nZ2VyW2hpZXJhcmNoeVN5bWJvbF1cbiAgd2hpbGUgKGhpZXJhcmNoeS5wYXJlbnQpIHtcbiAgICBoaWVyYXJjaHkgPSBoaWVyYXJjaHkucGFyZW50XG4gICAgaWYgKGhpZXJhcmNoeS5sb2dnZXIuYmluZGluZ3MpIHtcbiAgICAgIGJpbmRpbmdzLnB1c2goaGllcmFyY2h5LmxvZ2dlci5iaW5kaW5ncylcbiAgICB9XG4gIH1cblxuICByZXR1cm4gYmluZGluZ3MucmV2ZXJzZSgpXG59XG5cbmZ1bmN0aW9uIHNldCAoc2VsZiwgb3B0cywgcm9vdExvZ2dlciwgbGV2ZWwpIHtcbiAgLy8gb3ZlcnJpZGUgdGhlIGN1cnJlbnQgbG9nIGZ1bmN0aW9ucyB3aXRoIGVpdGhlciBgbm9vcGAgb3IgdGhlIGJhc2UgbG9nIGZ1bmN0aW9uXG4gIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShzZWxmLCBsZXZlbCwge1xuICAgIHZhbHVlOiAobGV2ZWxUb1ZhbHVlKHNlbGYubGV2ZWwsIHJvb3RMb2dnZXIpID4gbGV2ZWxUb1ZhbHVlKGxldmVsLCByb290TG9nZ2VyKVxuICAgICAgPyBub29wXG4gICAgICA6IHJvb3RMb2dnZXJbYmFzZUxvZ0Z1bmN0aW9uU3ltYm9sXVtsZXZlbF0pLFxuICAgIHdyaXRhYmxlOiB0cnVlLFxuICAgIGVudW1lcmFibGU6IHRydWUsXG4gICAgY29uZmlndXJhYmxlOiB0cnVlXG4gIH0pXG5cbiAgaWYgKHNlbGZbbGV2ZWxdID09PSBub29wKSB7XG4gICAgaWYgKCFvcHRzLnRyYW5zbWl0KSByZXR1cm5cblxuICAgIGNvbnN0IHRyYW5zbWl0TGV2ZWwgPSBvcHRzLnRyYW5zbWl0LmxldmVsIHx8IHNlbGYubGV2ZWxcbiAgICBjb25zdCB0cmFuc21pdFZhbHVlID0gbGV2ZWxUb1ZhbHVlKHRyYW5zbWl0TGV2ZWwsIHJvb3RMb2dnZXIpXG4gICAgY29uc3QgbWV0aG9kVmFsdWUgPSBsZXZlbFRvVmFsdWUobGV2ZWwsIHJvb3RMb2dnZXIpXG4gICAgaWYgKG1ldGhvZFZhbHVlIDwgdHJhbnNtaXRWYWx1ZSkgcmV0dXJuXG4gIH1cblxuICAvLyBtYWtlIHN1cmUgdGhlIGxvZyBmb3JtYXQgaXMgY29ycmVjdFxuICBzZWxmW2xldmVsXSA9IGNyZWF0ZVdyYXAoc2VsZiwgb3B0cywgcm9vdExvZ2dlciwgbGV2ZWwpXG5cbiAgLy8gcHJlcGVuZCBiaW5kaW5ncyBpZiBpdCBpcyBub3QgdGhlIHJvb3QgbG9nZ2VyXG4gIGNvbnN0IGJpbmRpbmdzID0gZ2V0QmluZGluZ0NoYWluKHNlbGYpXG4gIGlmIChiaW5kaW5ncy5sZW5ndGggPT09IDApIHtcbiAgICAvLyBlYXJseSBleGl0IGluIGNhc2UgZm9yIHJvb3RMb2dnZXJcbiAgICByZXR1cm5cbiAgfVxuICBzZWxmW2xldmVsXSA9IHByZXBlbmRCaW5kaW5nc0luQXJndW1lbnRzKGJpbmRpbmdzLCBzZWxmW2xldmVsXSlcbn1cblxuZnVuY3Rpb24gcHJlcGVuZEJpbmRpbmdzSW5Bcmd1bWVudHMgKGJpbmRpbmdzLCBsb2dGdW5jKSB7XG4gIHJldHVybiBmdW5jdGlvbiAoKSB7XG4gICAgcmV0dXJuIGxvZ0Z1bmMuYXBwbHkodGhpcywgWy4uLmJpbmRpbmdzLCAuLi5hcmd1bWVudHNdKVxuICB9XG59XG5cbmZ1bmN0aW9uIGNyZWF0ZVdyYXAgKHNlbGYsIG9wdHMsIHJvb3RMb2dnZXIsIGxldmVsKSB7XG4gIHJldHVybiAoZnVuY3Rpb24gKHdyaXRlKSB7XG4gICAgcmV0dXJuIGZ1bmN0aW9uIExPRyAoKSB7XG4gICAgICBjb25zdCB0cyA9IG9wdHMudGltZXN0YW1wKClcbiAgICAgIGNvbnN0IGFyZ3MgPSBuZXcgQXJyYXkoYXJndW1lbnRzLmxlbmd0aClcbiAgICAgIGNvbnN0IHByb3RvID0gKE9iamVjdC5nZXRQcm90b3R5cGVPZiAmJiBPYmplY3QuZ2V0UHJvdG90eXBlT2YodGhpcykgPT09IF9jb25zb2xlKSA/IF9jb25zb2xlIDogdGhpc1xuICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCBhcmdzLmxlbmd0aDsgaSsrKSBhcmdzW2ldID0gYXJndW1lbnRzW2ldXG5cbiAgICAgIHZhciBhcmdzSXNTZXJpYWxpemVkID0gZmFsc2VcbiAgICAgIGlmIChvcHRzLnNlcmlhbGl6ZSkge1xuICAgICAgICBhcHBseVNlcmlhbGl6ZXJzKGFyZ3MsIHRoaXMuX3NlcmlhbGl6ZSwgdGhpcy5zZXJpYWxpemVycywgdGhpcy5fc3RkRXJyU2VyaWFsaXplKVxuICAgICAgICBhcmdzSXNTZXJpYWxpemVkID0gdHJ1ZVxuICAgICAgfVxuICAgICAgaWYgKG9wdHMuYXNPYmplY3QgfHwgb3B0cy5mb3JtYXR0ZXJzKSB7XG4gICAgICAgIGNvbnN0IG91dCA9IGFzT2JqZWN0KHRoaXMsIGxldmVsLCBhcmdzLCB0cywgb3B0cylcbiAgICAgICAgaWYgKG9wdHMucmVwb3J0Q2FsbGVyICYmIG91dCAmJiBvdXQubGVuZ3RoID4gMCAmJiBvdXRbMF0gJiYgdHlwZW9mIG91dFswXSA9PT0gJ29iamVjdCcpIHtcbiAgICAgICAgICB0cnkge1xuICAgICAgICAgICAgY29uc3QgY2FsbGVyID0gZ2V0Q2FsbGVyTG9jYXRpb24oKVxuICAgICAgICAgICAgaWYgKGNhbGxlcikgb3V0WzBdLmNhbGxlciA9IGNhbGxlclxuICAgICAgICAgIH0gY2F0Y2ggKGUpIHt9XG4gICAgICAgIH1cbiAgICAgICAgd3JpdGUuY2FsbChwcm90bywgLi4ub3V0KVxuICAgICAgfSBlbHNlIHtcbiAgICAgICAgaWYgKG9wdHMucmVwb3J0Q2FsbGVyKSB7XG4gICAgICAgICAgdHJ5IHtcbiAgICAgICAgICAgIGNvbnN0IGNhbGxlciA9IGdldENhbGxlckxvY2F0aW9uKClcbiAgICAgICAgICAgIGlmIChjYWxsZXIpIGFyZ3MucHVzaChjYWxsZXIpXG4gICAgICAgICAgfSBjYXRjaCAoZSkge31cbiAgICAgICAgfVxuICAgICAgICB3cml0ZS5hcHBseShwcm90bywgYXJncylcbiAgICAgIH1cblxuICAgICAgaWYgKG9wdHMudHJhbnNtaXQpIHtcbiAgICAgICAgY29uc3QgdHJhbnNtaXRMZXZlbCA9IG9wdHMudHJhbnNtaXQubGV2ZWwgfHwgc2VsZi5fbGV2ZWxcbiAgICAgICAgY29uc3QgdHJhbnNtaXRWYWx1ZSA9IGxldmVsVG9WYWx1ZSh0cmFuc21pdExldmVsLCByb290TG9nZ2VyKVxuICAgICAgICBjb25zdCBtZXRob2RWYWx1ZSA9IGxldmVsVG9WYWx1ZShsZXZlbCwgcm9vdExvZ2dlcilcbiAgICAgICAgaWYgKG1ldGhvZFZhbHVlIDwgdHJhbnNtaXRWYWx1ZSkgcmV0dXJuXG4gICAgICAgIHRyYW5zbWl0KHRoaXMsIHtcbiAgICAgICAgICB0cyxcbiAgICAgICAgICBtZXRob2RMZXZlbDogbGV2ZWwsXG4gICAgICAgICAgbWV0aG9kVmFsdWUsXG4gICAgICAgICAgdHJhbnNtaXRMZXZlbCxcbiAgICAgICAgICB0cmFuc21pdFZhbHVlOiByb290TG9nZ2VyLmxldmVscy52YWx1ZXNbb3B0cy50cmFuc21pdC5sZXZlbCB8fCBzZWxmLl9sZXZlbF0sXG4gICAgICAgICAgc2VuZDogb3B0cy50cmFuc21pdC5zZW5kLFxuICAgICAgICAgIHZhbDogbGV2ZWxUb1ZhbHVlKHNlbGYuX2xldmVsLCByb290TG9nZ2VyKVxuICAgICAgICB9LCBhcmdzLCBhcmdzSXNTZXJpYWxpemVkKVxuICAgICAgfVxuICAgIH1cbiAgfSkoc2VsZltiYXNlTG9nRnVuY3Rpb25TeW1ib2xdW2xldmVsXSlcbn1cblxuZnVuY3Rpb24gYXNPYmplY3QgKGxvZ2dlciwgbGV2ZWwsIGFyZ3MsIHRzLCBvcHRzKSB7XG4gIGNvbnN0IHtcbiAgICBsZXZlbDogbGV2ZWxGb3JtYXR0ZXIsXG4gICAgbG9nOiBsb2dPYmplY3RGb3JtYXR0ZXIgPSAob2JqKSA9PiBvYmpcbiAgfSA9IG9wdHMuZm9ybWF0dGVycyB8fCB7fVxuICBjb25zdCBhcmdzQ2xvbmVkID0gYXJncy5zbGljZSgpXG4gIGxldCBtc2cgPSBhcmdzQ2xvbmVkWzBdXG4gIGNvbnN0IGxvZ09iamVjdCA9IHt9XG5cbiAgbGV0IGx2bCA9IChsb2dnZXIuX2NoaWxkTGV2ZWwgfCAwKSArIDFcbiAgaWYgKGx2bCA8IDEpIGx2bCA9IDFcblxuICBpZiAodHMpIHtcbiAgICBsb2dPYmplY3QudGltZSA9IHRzXG4gIH1cblxuICBpZiAobGV2ZWxGb3JtYXR0ZXIpIHtcbiAgICBjb25zdCBmb3JtYXR0ZWRMZXZlbCA9IGxldmVsRm9ybWF0dGVyKGxldmVsLCBsb2dnZXIubGV2ZWxzLnZhbHVlc1tsZXZlbF0pXG4gICAgT2JqZWN0LmFzc2lnbihsb2dPYmplY3QsIGZvcm1hdHRlZExldmVsKVxuICB9IGVsc2Uge1xuICAgIGxvZ09iamVjdC5sZXZlbCA9IGxvZ2dlci5sZXZlbHMudmFsdWVzW2xldmVsXVxuICB9XG5cbiAgaWYgKG9wdHMuYXNPYmplY3RCaW5kaW5nc09ubHkpIHtcbiAgICBpZiAobXNnICE9PSBudWxsICYmIHR5cGVvZiBtc2cgPT09ICdvYmplY3QnKSB7XG4gICAgICB3aGlsZSAobHZsLS0gJiYgdHlwZW9mIGFyZ3NDbG9uZWRbMF0gPT09ICdvYmplY3QnKSB7XG4gICAgICAgIE9iamVjdC5hc3NpZ24obG9nT2JqZWN0LCBhcmdzQ2xvbmVkLnNoaWZ0KCkpXG4gICAgICB9XG4gICAgfVxuXG4gICAgY29uc3QgZm9ybWF0dGVkTG9nT2JqZWN0ID0gbG9nT2JqZWN0Rm9ybWF0dGVyKGxvZ09iamVjdClcbiAgICByZXR1cm4gW2Zvcm1hdHRlZExvZ09iamVjdCwgLi4uYXJnc0Nsb25lZF1cbiAgfSBlbHNlIHtcbiAgICAvLyBkZWxpYmVyYXRlLCBjYXRjaGluZyBvYmplY3RzLCBhcnJheXNcbiAgICBpZiAobXNnICE9PSBudWxsICYmIHR5cGVvZiBtc2cgPT09ICdvYmplY3QnKSB7XG4gICAgICB3aGlsZSAobHZsLS0gJiYgdHlwZW9mIGFyZ3NDbG9uZWRbMF0gPT09ICdvYmplY3QnKSB7XG4gICAgICAgIE9iamVjdC5hc3NpZ24obG9nT2JqZWN0LCBhcmdzQ2xvbmVkLnNoaWZ0KCkpXG4gICAgICB9XG4gICAgICBtc2cgPSBhcmdzQ2xvbmVkLmxlbmd0aCA/IGZvcm1hdChhcmdzQ2xvbmVkLnNoaWZ0KCksIGFyZ3NDbG9uZWQpIDogdW5kZWZpbmVkXG4gICAgfSBlbHNlIGlmICh0eXBlb2YgbXNnID09PSAnc3RyaW5nJykgbXNnID0gZm9ybWF0KGFyZ3NDbG9uZWQuc2hpZnQoKSwgYXJnc0Nsb25lZClcbiAgICBpZiAobXNnICE9PSB1bmRlZmluZWQpIGxvZ09iamVjdFtvcHRzLm1lc3NhZ2VLZXldID0gbXNnXG5cbiAgICBjb25zdCBmb3JtYXR0ZWRMb2dPYmplY3QgPSBsb2dPYmplY3RGb3JtYXR0ZXIobG9nT2JqZWN0KVxuICAgIHJldHVybiBbZm9ybWF0dGVkTG9nT2JqZWN0XVxuICB9XG59XG5cbmZ1bmN0aW9uIGFwcGx5U2VyaWFsaXplcnMgKGFyZ3MsIHNlcmlhbGl6ZSwgc2VyaWFsaXplcnMsIHN0ZEVyclNlcmlhbGl6ZSkge1xuICBmb3IgKGNvbnN0IGkgaW4gYXJncykge1xuICAgIGlmIChzdGRFcnJTZXJpYWxpemUgJiYgYXJnc1tpXSBpbnN0YW5jZW9mIEVycm9yKSB7XG4gICAgICBhcmdzW2ldID0gcGluby5zdGRTZXJpYWxpemVycy5lcnIoYXJnc1tpXSlcbiAgICB9IGVsc2UgaWYgKHR5cGVvZiBhcmdzW2ldID09PSAnb2JqZWN0JyAmJiAhQXJyYXkuaXNBcnJheShhcmdzW2ldKSAmJiBzZXJpYWxpemUpIHtcbiAgICAgIGZvciAoY29uc3QgayBpbiBhcmdzW2ldKSB7XG4gICAgICAgIGlmIChzZXJpYWxpemUuaW5kZXhPZihrKSA+IC0xICYmIGsgaW4gc2VyaWFsaXplcnMpIHtcbiAgICAgICAgICBhcmdzW2ldW2tdID0gc2VyaWFsaXplcnNba10oYXJnc1tpXVtrXSlcbiAgICAgICAgfVxuICAgICAgfVxuICAgIH1cbiAgfVxufVxuXG5mdW5jdGlvbiB0cmFuc21pdCAobG9nZ2VyLCBvcHRzLCBhcmdzLCBhcmdzSXNTZXJpYWxpemVkID0gZmFsc2UpIHtcbiAgY29uc3Qgc2VuZCA9IG9wdHMuc2VuZFxuICBjb25zdCB0cyA9IG9wdHMudHNcbiAgY29uc3QgbWV0aG9kTGV2ZWwgPSBvcHRzLm1ldGhvZExldmVsXG4gIGNvbnN0IG1ldGhvZFZhbHVlID0gb3B0cy5tZXRob2RWYWx1ZVxuICBjb25zdCB2YWwgPSBvcHRzLnZhbFxuICBjb25zdCBiaW5kaW5ncyA9IGxvZ2dlci5fbG9nRXZlbnQuYmluZGluZ3NcblxuICBpZiAoIWFyZ3NJc1NlcmlhbGl6ZWQpIHtcbiAgICBhcHBseVNlcmlhbGl6ZXJzKFxuICAgICAgYXJncyxcbiAgICAgIGxvZ2dlci5fc2VyaWFsaXplIHx8IE9iamVjdC5rZXlzKGxvZ2dlci5zZXJpYWxpemVycyksXG4gICAgICBsb2dnZXIuc2VyaWFsaXplcnMsXG4gICAgICBsb2dnZXIuX3N0ZEVyclNlcmlhbGl6ZSA9PT0gdW5kZWZpbmVkID8gdHJ1ZSA6IGxvZ2dlci5fc3RkRXJyU2VyaWFsaXplXG4gICAgKVxuICB9XG5cbiAgbG9nZ2VyLl9sb2dFdmVudC50cyA9IHRzXG4gIGxvZ2dlci5fbG9nRXZlbnQubWVzc2FnZXMgPSBhcmdzLmZpbHRlcihmdW5jdGlvbiAoYXJnKSB7XG4gICAgLy8gYmluZGluZ3MgY2FuIG9ubHkgYmUgb2JqZWN0cywgc28gcmVmZXJlbmNlIGVxdWFsaXR5IGNoZWNrIHZpYSBpbmRleE9mIGlzIGZpbmVcbiAgICByZXR1cm4gYmluZGluZ3MuaW5kZXhPZihhcmcpID09PSAtMVxuICB9KVxuXG4gIGxvZ2dlci5fbG9nRXZlbnQubGV2ZWwubGFiZWwgPSBtZXRob2RMZXZlbFxuICBsb2dnZXIuX2xvZ0V2ZW50LmxldmVsLnZhbHVlID0gbWV0aG9kVmFsdWVcblxuICBzZW5kKG1ldGhvZExldmVsLCBsb2dnZXIuX2xvZ0V2ZW50LCB2YWwpXG5cbiAgbG9nZ2VyLl9sb2dFdmVudCA9IGNyZWF0ZUxvZ0V2ZW50U2hhcGUoYmluZGluZ3MpXG59XG5cbmZ1bmN0aW9uIGNyZWF0ZUxvZ0V2ZW50U2hhcGUgKGJpbmRpbmdzKSB7XG4gIHJldHVybiB7XG4gICAgdHM6IDAsXG4gICAgbWVzc2FnZXM6IFtdLFxuICAgIGJpbmRpbmdzOiBiaW5kaW5ncyB8fCBbXSxcbiAgICBsZXZlbDogeyBsYWJlbDogJycsIHZhbHVlOiAwIH1cbiAgfVxufVxuXG5mdW5jdGlvbiBhc0VyclZhbHVlIChlcnIpIHtcbiAgY29uc3Qgb2JqID0ge1xuICAgIHR5cGU6IGVyci5jb25zdHJ1Y3Rvci5uYW1lLFxuICAgIG1zZzogZXJyLm1lc3NhZ2UsXG4gICAgc3RhY2s6IGVyci5zdGFja1xuICB9XG4gIGZvciAoY29uc3Qga2V5IGluIGVycikge1xuICAgIGlmIChvYmpba2V5XSA9PT0gdW5kZWZpbmVkKSB7XG4gICAgICBvYmpba2V5XSA9IGVycltrZXldXG4gICAgfVxuICB9XG4gIHJldHVybiBvYmpcbn1cblxuZnVuY3Rpb24gZ2V0VGltZUZ1bmN0aW9uIChvcHRzKSB7XG4gIGlmICh0eXBlb2Ygb3B0cy50aW1lc3RhbXAgPT09ICdmdW5jdGlvbicpIHtcbiAgICByZXR1cm4gb3B0cy50aW1lc3RhbXBcbiAgfVxuICBpZiAob3B0cy50aW1lc3RhbXAgPT09IGZhbHNlKSB7XG4gICAgcmV0dXJuIG51bGxUaW1lXG4gIH1cbiAgcmV0dXJuIGVwb2NoVGltZVxufVxuXG5mdW5jdGlvbiBtb2NrICgpIHsgcmV0dXJuIHt9IH1cbmZ1bmN0aW9uIHBhc3N0aHJvdWdoIChhKSB7IHJldHVybiBhIH1cbmZ1bmN0aW9uIG5vb3AgKCkge31cblxuZnVuY3Rpb24gbnVsbFRpbWUgKCkgeyByZXR1cm4gZmFsc2UgfVxuZnVuY3Rpb24gZXBvY2hUaW1lICgpIHsgcmV0dXJuIERhdGUubm93KCkgfVxuZnVuY3Rpb24gdW5peFRpbWUgKCkgeyByZXR1cm4gTWF0aC5yb3VuZChEYXRlLm5vdygpIC8gMTAwMC4wKSB9XG5mdW5jdGlvbiBpc29UaW1lICgpIHsgcmV0dXJuIG5ldyBEYXRlKERhdGUubm93KCkpLnRvSVNPU3RyaW5nKCkgfSAvLyB1c2luZyBEYXRlLm5vdygpIGZvciB0ZXN0YWJpbGl0eVxuXG4vKiBlc2xpbnQtZGlzYWJsZSAqL1xuLyogaXN0YW5idWwgaWdub3JlIG5leHQgKi9cbmZ1bmN0aW9uIHBmR2xvYmFsVGhpc09yRmFsbGJhY2sgKCkge1xuICBmdW5jdGlvbiBkZWZkIChvKSB7IHJldHVybiB0eXBlb2YgbyAhPT0gJ3VuZGVmaW5lZCcgJiYgbyB9XG4gIHRyeSB7XG4gICAgaWYgKHR5cGVvZiBnbG9iYWxUaGlzICE9PSAndW5kZWZpbmVkJykgcmV0dXJuIGdsb2JhbFRoaXNcbiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoT2JqZWN0LnByb3RvdHlwZSwgJ2dsb2JhbFRoaXMnLCB7XG4gICAgICBnZXQ6IGZ1bmN0aW9uICgpIHtcbiAgICAgICAgZGVsZXRlIE9iamVjdC5wcm90b3R5cGUuZ2xvYmFsVGhpc1xuICAgICAgICByZXR1cm4gKHRoaXMuZ2xvYmFsVGhpcyA9IHRoaXMpXG4gICAgICB9LFxuICAgICAgY29uZmlndXJhYmxlOiB0cnVlXG4gICAgfSlcbiAgICByZXR1cm4gZ2xvYmFsVGhpc1xuICB9IGNhdGNoIChlKSB7XG4gICAgcmV0dXJuIGRlZmQoc2VsZikgfHwgZGVmZCh3aW5kb3cpIHx8IGRlZmQodGhpcykgfHwge31cbiAgfVxufVxuLyogZXNsaW50LWVuYWJsZSAqL1xuXG5tb2R1bGUuZXhwb3J0cy5kZWZhdWx0ID0gcGlub1xubW9kdWxlLmV4cG9ydHMucGlubyA9IHBpbm9cblxuLy8gQXR0ZW1wdCB0byBleHRyYWN0IHRoZSB1c2VyIGNhbGxzaXRlIChmaWxlOmxpbmU6Y29sdW1uKVxuLyogaXN0YW5idWwgaWdub3JlIG5leHQgKi9cbmZ1bmN0aW9uIGdldENhbGxlckxvY2F0aW9uICgpIHtcbiAgY29uc3Qgc3RhY2sgPSAobmV3IEVycm9yKCkpLnN0YWNrXG4gIGlmICghc3RhY2spIHJldHVybiBudWxsXG4gIGNvbnN0IGxpbmVzID0gc3RhY2suc3BsaXQoJ1xcbicpXG4gIGZvciAobGV0IGkgPSAxOyBpIDwgbGluZXMubGVuZ3RoOyBpKyspIHtcbiAgICBjb25zdCBsID0gbGluZXNbaV0udHJpbSgpXG4gICAgLy8gc2tpcCBmcmFtZXMgZnJvbSB0aGlzIGZpbGUgYW5kIGludGVybmFsc1xuICAgIGlmICgvKF5hdFxccyspPyhjcmVhdGVXcmFwfExPR3xzZXRcXHMqXFwofGFzT2JqZWN0fE9iamVjdFxcLmFwcGx5fEZ1bmN0aW9uXFwuYXBwbHkpLy50ZXN0KGwpKSBjb250aW51ZVxuICAgIGlmIChsLmluZGV4T2YoJ2Jyb3dzZXIuanMnKSAhPT0gLTEpIGNvbnRpbnVlXG4gICAgaWYgKGwuaW5kZXhPZignbm9kZTppbnRlcm5hbCcpICE9PSAtMSkgY29udGludWVcbiAgICBpZiAobC5pbmRleE9mKCdub2RlX21vZHVsZXMnKSAhPT0gLTEpIGNvbnRpbnVlXG4gICAgLy8gdHJ5IGZvcm1hdHMgbGlrZTogYXQgZnVuYyAoZmlsZTpsaW5lOmNvbCkgb3IgYXQgZmlsZTpsaW5lOmNvbFxuICAgIGxldCBtID0gbC5tYXRjaCgvXFwoKC4qPyk6KFxcZCspOihcXGQrKVxcKS8pXG4gICAgaWYgKCFtKSBtID0gbC5tYXRjaCgvYXRcXHMrKC4qPyk6KFxcZCspOihcXGQrKS8pXG4gICAgaWYgKG0pIHtcbiAgICAgIGNvbnN0IGZpbGUgPSBtWzFdXG4gICAgICBjb25zdCBsaW5lID0gbVsyXVxuICAgICAgY29uc3QgY29sID0gbVszXVxuICAgICAgcmV0dXJuIGZpbGUgKyAnOicgKyBsaW5lICsgJzonICsgY29sXG4gICAgfVxuICB9XG4gIHJldHVybiBudWxsXG59XG4iLCAibW9kdWxlLmV4cG9ydHMgPSB7fTsiLCAiJ3VzZSBzdHJpY3QnO1xuT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsIFwiX19lc01vZHVsZVwiLCB7IHZhbHVlOiB0cnVlIH0pO1xuZXhwb3J0cy5iZWNoMzJtID0gZXhwb3J0cy5iZWNoMzIgPSB2b2lkIDA7XG5jb25zdCBBTFBIQUJFVCA9ICdxcHpyeTl4OGdmMnR2ZHcwczNqbjU0a2hjZTZtdWE3bCc7XG5jb25zdCBBTFBIQUJFVF9NQVAgPSB7fTtcbmZvciAobGV0IHogPSAwOyB6IDwgQUxQSEFCRVQubGVuZ3RoOyB6KyspIHtcbiAgICBjb25zdCB4ID0gQUxQSEFCRVQuY2hhckF0KHopO1xuICAgIEFMUEhBQkVUX01BUFt4XSA9IHo7XG59XG5mdW5jdGlvbiBwb2x5bW9kU3RlcChwcmUpIHtcbiAgICBjb25zdCBiID0gcHJlID4+IDI1O1xuICAgIHJldHVybiAoKChwcmUgJiAweDFmZmZmZmYpIDw8IDUpIF5cbiAgICAgICAgKC0oKGIgPj4gMCkgJiAxKSAmIDB4M2I2YTU3YjIpIF5cbiAgICAgICAgKC0oKGIgPj4gMSkgJiAxKSAmIDB4MjY1MDhlNmQpIF5cbiAgICAgICAgKC0oKGIgPj4gMikgJiAxKSAmIDB4MWVhMTE5ZmEpIF5cbiAgICAgICAgKC0oKGIgPj4gMykgJiAxKSAmIDB4M2Q0MjMzZGQpIF5cbiAgICAgICAgKC0oKGIgPj4gNCkgJiAxKSAmIDB4MmExNDYyYjMpKTtcbn1cbmZ1bmN0aW9uIHByZWZpeENoayhwcmVmaXgpIHtcbiAgICBsZXQgY2hrID0gMTtcbiAgICBmb3IgKGxldCBpID0gMDsgaSA8IHByZWZpeC5sZW5ndGg7ICsraSkge1xuICAgICAgICBjb25zdCBjID0gcHJlZml4LmNoYXJDb2RlQXQoaSk7XG4gICAgICAgIGlmIChjIDwgMzMgfHwgYyA+IDEyNilcbiAgICAgICAgICAgIHJldHVybiAnSW52YWxpZCBwcmVmaXggKCcgKyBwcmVmaXggKyAnKSc7XG4gICAgICAgIGNoayA9IHBvbHltb2RTdGVwKGNoaykgXiAoYyA+PiA1KTtcbiAgICB9XG4gICAgY2hrID0gcG9seW1vZFN0ZXAoY2hrKTtcbiAgICBmb3IgKGxldCBpID0gMDsgaSA8IHByZWZpeC5sZW5ndGg7ICsraSkge1xuICAgICAgICBjb25zdCB2ID0gcHJlZml4LmNoYXJDb2RlQXQoaSk7XG4gICAgICAgIGNoayA9IHBvbHltb2RTdGVwKGNoaykgXiAodiAmIDB4MWYpO1xuICAgIH1cbiAgICByZXR1cm4gY2hrO1xufVxuZnVuY3Rpb24gY29udmVydChkYXRhLCBpbkJpdHMsIG91dEJpdHMsIHBhZCkge1xuICAgIGxldCB2YWx1ZSA9IDA7XG4gICAgbGV0IGJpdHMgPSAwO1xuICAgIGNvbnN0IG1heFYgPSAoMSA8PCBvdXRCaXRzKSAtIDE7XG4gICAgY29uc3QgcmVzdWx0ID0gW107XG4gICAgZm9yIChsZXQgaSA9IDA7IGkgPCBkYXRhLmxlbmd0aDsgKytpKSB7XG4gICAgICAgIHZhbHVlID0gKHZhbHVlIDw8IGluQml0cykgfCBkYXRhW2ldO1xuICAgICAgICBiaXRzICs9IGluQml0cztcbiAgICAgICAgd2hpbGUgKGJpdHMgPj0gb3V0Qml0cykge1xuICAgICAgICAgICAgYml0cyAtPSBvdXRCaXRzO1xuICAgICAgICAgICAgcmVzdWx0LnB1c2goKHZhbHVlID4+IGJpdHMpICYgbWF4Vik7XG4gICAgICAgIH1cbiAgICB9XG4gICAgaWYgKHBhZCkge1xuICAgICAgICBpZiAoYml0cyA+IDApIHtcbiAgICAgICAgICAgIHJlc3VsdC5wdXNoKCh2YWx1ZSA8PCAob3V0Qml0cyAtIGJpdHMpKSAmIG1heFYpO1xuICAgICAgICB9XG4gICAgfVxuICAgIGVsc2Uge1xuICAgICAgICBpZiAoYml0cyA+PSBpbkJpdHMpXG4gICAgICAgICAgICByZXR1cm4gJ0V4Y2VzcyBwYWRkaW5nJztcbiAgICAgICAgaWYgKCh2YWx1ZSA8PCAob3V0Qml0cyAtIGJpdHMpKSAmIG1heFYpXG4gICAgICAgICAgICByZXR1cm4gJ05vbi16ZXJvIHBhZGRpbmcnO1xuICAgIH1cbiAgICByZXR1cm4gcmVzdWx0O1xufVxuZnVuY3Rpb24gdG9Xb3JkcyhieXRlcykge1xuICAgIHJldHVybiBjb252ZXJ0KGJ5dGVzLCA4LCA1LCB0cnVlKTtcbn1cbmZ1bmN0aW9uIGZyb21Xb3Jkc1Vuc2FmZSh3b3Jkcykge1xuICAgIGNvbnN0IHJlcyA9IGNvbnZlcnQod29yZHMsIDUsIDgsIGZhbHNlKTtcbiAgICBpZiAoQXJyYXkuaXNBcnJheShyZXMpKVxuICAgICAgICByZXR1cm4gcmVzO1xufVxuZnVuY3Rpb24gZnJvbVdvcmRzKHdvcmRzKSB7XG4gICAgY29uc3QgcmVzID0gY29udmVydCh3b3JkcywgNSwgOCwgZmFsc2UpO1xuICAgIGlmIChBcnJheS5pc0FycmF5KHJlcykpXG4gICAgICAgIHJldHVybiByZXM7XG4gICAgdGhyb3cgbmV3IEVycm9yKHJlcyk7XG59XG5mdW5jdGlvbiBnZXRMaWJyYXJ5RnJvbUVuY29kaW5nKGVuY29kaW5nKSB7XG4gICAgbGV0IEVOQ09ESU5HX0NPTlNUO1xuICAgIGlmIChlbmNvZGluZyA9PT0gJ2JlY2gzMicpIHtcbiAgICAgICAgRU5DT0RJTkdfQ09OU1QgPSAxO1xuICAgIH1cbiAgICBlbHNlIHtcbiAgICAgICAgRU5DT0RJTkdfQ09OU1QgPSAweDJiYzgzMGEzO1xuICAgIH1cbiAgICBmdW5jdGlvbiBlbmNvZGUocHJlZml4LCB3b3JkcywgTElNSVQpIHtcbiAgICAgICAgTElNSVQgPSBMSU1JVCB8fCA5MDtcbiAgICAgICAgaWYgKHByZWZpeC5sZW5ndGggKyA3ICsgd29yZHMubGVuZ3RoID4gTElNSVQpXG4gICAgICAgICAgICB0aHJvdyBuZXcgVHlwZUVycm9yKCdFeGNlZWRzIGxlbmd0aCBsaW1pdCcpO1xuICAgICAgICBwcmVmaXggPSBwcmVmaXgudG9Mb3dlckNhc2UoKTtcbiAgICAgICAgLy8gZGV0ZXJtaW5lIGNoayBtb2RcbiAgICAgICAgbGV0IGNoayA9IHByZWZpeENoayhwcmVmaXgpO1xuICAgICAgICBpZiAodHlwZW9mIGNoayA9PT0gJ3N0cmluZycpXG4gICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoY2hrKTtcbiAgICAgICAgbGV0IHJlc3VsdCA9IHByZWZpeCArICcxJztcbiAgICAgICAgZm9yIChsZXQgaSA9IDA7IGkgPCB3b3Jkcy5sZW5ndGg7ICsraSkge1xuICAgICAgICAgICAgY29uc3QgeCA9IHdvcmRzW2ldO1xuICAgICAgICAgICAgaWYgKHggPj4gNSAhPT0gMClcbiAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoJ05vbiA1LWJpdCB3b3JkJyk7XG4gICAgICAgICAgICBjaGsgPSBwb2x5bW9kU3RlcChjaGspIF4geDtcbiAgICAgICAgICAgIHJlc3VsdCArPSBBTFBIQUJFVC5jaGFyQXQoeCk7XG4gICAgICAgIH1cbiAgICAgICAgZm9yIChsZXQgaSA9IDA7IGkgPCA2OyArK2kpIHtcbiAgICAgICAgICAgIGNoayA9IHBvbHltb2RTdGVwKGNoayk7XG4gICAgICAgIH1cbiAgICAgICAgY2hrIF49IEVOQ09ESU5HX0NPTlNUO1xuICAgICAgICBmb3IgKGxldCBpID0gMDsgaSA8IDY7ICsraSkge1xuICAgICAgICAgICAgY29uc3QgdiA9IChjaGsgPj4gKCg1IC0gaSkgKiA1KSkgJiAweDFmO1xuICAgICAgICAgICAgcmVzdWx0ICs9IEFMUEhBQkVULmNoYXJBdCh2KTtcbiAgICAgICAgfVxuICAgICAgICByZXR1cm4gcmVzdWx0O1xuICAgIH1cbiAgICBmdW5jdGlvbiBfX2RlY29kZShzdHIsIExJTUlUKSB7XG4gICAgICAgIExJTUlUID0gTElNSVQgfHwgOTA7XG4gICAgICAgIGlmIChzdHIubGVuZ3RoIDwgOClcbiAgICAgICAgICAgIHJldHVybiBzdHIgKyAnIHRvbyBzaG9ydCc7XG4gICAgICAgIGlmIChzdHIubGVuZ3RoID4gTElNSVQpXG4gICAgICAgICAgICByZXR1cm4gJ0V4Y2VlZHMgbGVuZ3RoIGxpbWl0JztcbiAgICAgICAgLy8gZG9uJ3QgYWxsb3cgbWl4ZWQgY2FzZVxuICAgICAgICBjb25zdCBsb3dlcmVkID0gc3RyLnRvTG93ZXJDYXNlKCk7XG4gICAgICAgIGNvbnN0IHVwcGVyZWQgPSBzdHIudG9VcHBlckNhc2UoKTtcbiAgICAgICAgaWYgKHN0ciAhPT0gbG93ZXJlZCAmJiBzdHIgIT09IHVwcGVyZWQpXG4gICAgICAgICAgICByZXR1cm4gJ01peGVkLWNhc2Ugc3RyaW5nICcgKyBzdHI7XG4gICAgICAgIHN0ciA9IGxvd2VyZWQ7XG4gICAgICAgIGNvbnN0IHNwbGl0ID0gc3RyLmxhc3RJbmRleE9mKCcxJyk7XG4gICAgICAgIGlmIChzcGxpdCA9PT0gLTEpXG4gICAgICAgICAgICByZXR1cm4gJ05vIHNlcGFyYXRvciBjaGFyYWN0ZXIgZm9yICcgKyBzdHI7XG4gICAgICAgIGlmIChzcGxpdCA9PT0gMClcbiAgICAgICAgICAgIHJldHVybiAnTWlzc2luZyBwcmVmaXggZm9yICcgKyBzdHI7XG4gICAgICAgIGNvbnN0IHByZWZpeCA9IHN0ci5zbGljZSgwLCBzcGxpdCk7XG4gICAgICAgIGNvbnN0IHdvcmRDaGFycyA9IHN0ci5zbGljZShzcGxpdCArIDEpO1xuICAgICAgICBpZiAod29yZENoYXJzLmxlbmd0aCA8IDYpXG4gICAgICAgICAgICByZXR1cm4gJ0RhdGEgdG9vIHNob3J0JztcbiAgICAgICAgbGV0IGNoayA9IHByZWZpeENoayhwcmVmaXgpO1xuICAgICAgICBpZiAodHlwZW9mIGNoayA9PT0gJ3N0cmluZycpXG4gICAgICAgICAgICByZXR1cm4gY2hrO1xuICAgICAgICBjb25zdCB3b3JkcyA9IFtdO1xuICAgICAgICBmb3IgKGxldCBpID0gMDsgaSA8IHdvcmRDaGFycy5sZW5ndGg7ICsraSkge1xuICAgICAgICAgICAgY29uc3QgYyA9IHdvcmRDaGFycy5jaGFyQXQoaSk7XG4gICAgICAgICAgICBjb25zdCB2ID0gQUxQSEFCRVRfTUFQW2NdO1xuICAgICAgICAgICAgaWYgKHYgPT09IHVuZGVmaW5lZClcbiAgICAgICAgICAgICAgICByZXR1cm4gJ1Vua25vd24gY2hhcmFjdGVyICcgKyBjO1xuICAgICAgICAgICAgY2hrID0gcG9seW1vZFN0ZXAoY2hrKSBeIHY7XG4gICAgICAgICAgICAvLyBub3QgaW4gdGhlIGNoZWNrc3VtP1xuICAgICAgICAgICAgaWYgKGkgKyA2ID49IHdvcmRDaGFycy5sZW5ndGgpXG4gICAgICAgICAgICAgICAgY29udGludWU7XG4gICAgICAgICAgICB3b3Jkcy5wdXNoKHYpO1xuICAgICAgICB9XG4gICAgICAgIGlmIChjaGsgIT09IEVOQ09ESU5HX0NPTlNUKVxuICAgICAgICAgICAgcmV0dXJuICdJbnZhbGlkIGNoZWNrc3VtIGZvciAnICsgc3RyO1xuICAgICAgICByZXR1cm4geyBwcmVmaXgsIHdvcmRzIH07XG4gICAgfVxuICAgIGZ1bmN0aW9uIGRlY29kZVVuc2FmZShzdHIsIExJTUlUKSB7XG4gICAgICAgIGNvbnN0IHJlcyA9IF9fZGVjb2RlKHN0ciwgTElNSVQpO1xuICAgICAgICBpZiAodHlwZW9mIHJlcyA9PT0gJ29iamVjdCcpXG4gICAgICAgICAgICByZXR1cm4gcmVzO1xuICAgIH1cbiAgICBmdW5jdGlvbiBkZWNvZGUoc3RyLCBMSU1JVCkge1xuICAgICAgICBjb25zdCByZXMgPSBfX2RlY29kZShzdHIsIExJTUlUKTtcbiAgICAgICAgaWYgKHR5cGVvZiByZXMgPT09ICdvYmplY3QnKVxuICAgICAgICAgICAgcmV0dXJuIHJlcztcbiAgICAgICAgdGhyb3cgbmV3IEVycm9yKHJlcyk7XG4gICAgfVxuICAgIHJldHVybiB7XG4gICAgICAgIGRlY29kZVVuc2FmZSxcbiAgICAgICAgZGVjb2RlLFxuICAgICAgICBlbmNvZGUsXG4gICAgICAgIHRvV29yZHMsXG4gICAgICAgIGZyb21Xb3Jkc1Vuc2FmZSxcbiAgICAgICAgZnJvbVdvcmRzLFxuICAgIH07XG59XG5leHBvcnRzLmJlY2gzMiA9IGdldExpYnJhcnlGcm9tRW5jb2RpbmcoJ2JlY2gzMicpO1xuZXhwb3J0cy5iZWNoMzJtID0gZ2V0TGlicmFyeUZyb21FbmNvZGluZygnYmVjaDMybScpO1xuIiwgIid1c2Ugc3RyaWN0J1xuXG5leHBvcnRzLmJ5dGVMZW5ndGggPSBieXRlTGVuZ3RoXG5leHBvcnRzLnRvQnl0ZUFycmF5ID0gdG9CeXRlQXJyYXlcbmV4cG9ydHMuZnJvbUJ5dGVBcnJheSA9IGZyb21CeXRlQXJyYXlcblxudmFyIGxvb2t1cCA9IFtdXG52YXIgcmV2TG9va3VwID0gW11cbnZhciBBcnIgPSB0eXBlb2YgVWludDhBcnJheSAhPT0gJ3VuZGVmaW5lZCcgPyBVaW50OEFycmF5IDogQXJyYXlcblxudmFyIGNvZGUgPSAnQUJDREVGR0hJSktMTU5PUFFSU1RVVldYWVphYmNkZWZnaGlqa2xtbm9wcXJzdHV2d3h5ejAxMjM0NTY3ODkrLydcbmZvciAodmFyIGkgPSAwLCBsZW4gPSBjb2RlLmxlbmd0aDsgaSA8IGxlbjsgKytpKSB7XG4gIGxvb2t1cFtpXSA9IGNvZGVbaV1cbiAgcmV2TG9va3VwW2NvZGUuY2hhckNvZGVBdChpKV0gPSBpXG59XG5cbi8vIFN1cHBvcnQgZGVjb2RpbmcgVVJMLXNhZmUgYmFzZTY0IHN0cmluZ3MsIGFzIE5vZGUuanMgZG9lcy5cbi8vIFNlZTogaHR0cHM6Ly9lbi53aWtpcGVkaWEub3JnL3dpa2kvQmFzZTY0I1VSTF9hcHBsaWNhdGlvbnNcbnJldkxvb2t1cFsnLScuY2hhckNvZGVBdCgwKV0gPSA2MlxucmV2TG9va3VwWydfJy5jaGFyQ29kZUF0KDApXSA9IDYzXG5cbmZ1bmN0aW9uIGdldExlbnMgKGI2NCkge1xuICB2YXIgbGVuID0gYjY0Lmxlbmd0aFxuXG4gIGlmIChsZW4gJSA0ID4gMCkge1xuICAgIHRocm93IG5ldyBFcnJvcignSW52YWxpZCBzdHJpbmcuIExlbmd0aCBtdXN0IGJlIGEgbXVsdGlwbGUgb2YgNCcpXG4gIH1cblxuICAvLyBUcmltIG9mZiBleHRyYSBieXRlcyBhZnRlciBwbGFjZWhvbGRlciBieXRlcyBhcmUgZm91bmRcbiAgLy8gU2VlOiBodHRwczovL2dpdGh1Yi5jb20vYmVhdGdhbW1pdC9iYXNlNjQtanMvaXNzdWVzLzQyXG4gIHZhciB2YWxpZExlbiA9IGI2NC5pbmRleE9mKCc9JylcbiAgaWYgKHZhbGlkTGVuID09PSAtMSkgdmFsaWRMZW4gPSBsZW5cblxuICB2YXIgcGxhY2VIb2xkZXJzTGVuID0gdmFsaWRMZW4gPT09IGxlblxuICAgID8gMFxuICAgIDogNCAtICh2YWxpZExlbiAlIDQpXG5cbiAgcmV0dXJuIFt2YWxpZExlbiwgcGxhY2VIb2xkZXJzTGVuXVxufVxuXG4vLyBiYXNlNjQgaXMgNC8zICsgdXAgdG8gdHdvIGNoYXJhY3RlcnMgb2YgdGhlIG9yaWdpbmFsIGRhdGFcbmZ1bmN0aW9uIGJ5dGVMZW5ndGggKGI2NCkge1xuICB2YXIgbGVucyA9IGdldExlbnMoYjY0KVxuICB2YXIgdmFsaWRMZW4gPSBsZW5zWzBdXG4gIHZhciBwbGFjZUhvbGRlcnNMZW4gPSBsZW5zWzFdXG4gIHJldHVybiAoKHZhbGlkTGVuICsgcGxhY2VIb2xkZXJzTGVuKSAqIDMgLyA0KSAtIHBsYWNlSG9sZGVyc0xlblxufVxuXG5mdW5jdGlvbiBfYnl0ZUxlbmd0aCAoYjY0LCB2YWxpZExlbiwgcGxhY2VIb2xkZXJzTGVuKSB7XG4gIHJldHVybiAoKHZhbGlkTGVuICsgcGxhY2VIb2xkZXJzTGVuKSAqIDMgLyA0KSAtIHBsYWNlSG9sZGVyc0xlblxufVxuXG5mdW5jdGlvbiB0b0J5dGVBcnJheSAoYjY0KSB7XG4gIHZhciB0bXBcbiAgdmFyIGxlbnMgPSBnZXRMZW5zKGI2NClcbiAgdmFyIHZhbGlkTGVuID0gbGVuc1swXVxuICB2YXIgcGxhY2VIb2xkZXJzTGVuID0gbGVuc1sxXVxuXG4gIHZhciBhcnIgPSBuZXcgQXJyKF9ieXRlTGVuZ3RoKGI2NCwgdmFsaWRMZW4sIHBsYWNlSG9sZGVyc0xlbikpXG5cbiAgdmFyIGN1ckJ5dGUgPSAwXG5cbiAgLy8gaWYgdGhlcmUgYXJlIHBsYWNlaG9sZGVycywgb25seSBnZXQgdXAgdG8gdGhlIGxhc3QgY29tcGxldGUgNCBjaGFyc1xuICB2YXIgbGVuID0gcGxhY2VIb2xkZXJzTGVuID4gMFxuICAgID8gdmFsaWRMZW4gLSA0XG4gICAgOiB2YWxpZExlblxuXG4gIHZhciBpXG4gIGZvciAoaSA9IDA7IGkgPCBsZW47IGkgKz0gNCkge1xuICAgIHRtcCA9XG4gICAgICAocmV2TG9va3VwW2I2NC5jaGFyQ29kZUF0KGkpXSA8PCAxOCkgfFxuICAgICAgKHJldkxvb2t1cFtiNjQuY2hhckNvZGVBdChpICsgMSldIDw8IDEyKSB8XG4gICAgICAocmV2TG9va3VwW2I2NC5jaGFyQ29kZUF0KGkgKyAyKV0gPDwgNikgfFxuICAgICAgcmV2TG9va3VwW2I2NC5jaGFyQ29kZUF0KGkgKyAzKV1cbiAgICBhcnJbY3VyQnl0ZSsrXSA9ICh0bXAgPj4gMTYpICYgMHhGRlxuICAgIGFycltjdXJCeXRlKytdID0gKHRtcCA+PiA4KSAmIDB4RkZcbiAgICBhcnJbY3VyQnl0ZSsrXSA9IHRtcCAmIDB4RkZcbiAgfVxuXG4gIGlmIChwbGFjZUhvbGRlcnNMZW4gPT09IDIpIHtcbiAgICB0bXAgPVxuICAgICAgKHJldkxvb2t1cFtiNjQuY2hhckNvZGVBdChpKV0gPDwgMikgfFxuICAgICAgKHJldkxvb2t1cFtiNjQuY2hhckNvZGVBdChpICsgMSldID4+IDQpXG4gICAgYXJyW2N1ckJ5dGUrK10gPSB0bXAgJiAweEZGXG4gIH1cblxuICBpZiAocGxhY2VIb2xkZXJzTGVuID09PSAxKSB7XG4gICAgdG1wID1cbiAgICAgIChyZXZMb29rdXBbYjY0LmNoYXJDb2RlQXQoaSldIDw8IDEwKSB8XG4gICAgICAocmV2TG9va3VwW2I2NC5jaGFyQ29kZUF0KGkgKyAxKV0gPDwgNCkgfFxuICAgICAgKHJldkxvb2t1cFtiNjQuY2hhckNvZGVBdChpICsgMildID4+IDIpXG4gICAgYXJyW2N1ckJ5dGUrK10gPSAodG1wID4+IDgpICYgMHhGRlxuICAgIGFycltjdXJCeXRlKytdID0gdG1wICYgMHhGRlxuICB9XG5cbiAgcmV0dXJuIGFyclxufVxuXG5mdW5jdGlvbiB0cmlwbGV0VG9CYXNlNjQgKG51bSkge1xuICByZXR1cm4gbG9va3VwW251bSA+PiAxOCAmIDB4M0ZdICtcbiAgICBsb29rdXBbbnVtID4+IDEyICYgMHgzRl0gK1xuICAgIGxvb2t1cFtudW0gPj4gNiAmIDB4M0ZdICtcbiAgICBsb29rdXBbbnVtICYgMHgzRl1cbn1cblxuZnVuY3Rpb24gZW5jb2RlQ2h1bmsgKHVpbnQ4LCBzdGFydCwgZW5kKSB7XG4gIHZhciB0bXBcbiAgdmFyIG91dHB1dCA9IFtdXG4gIGZvciAodmFyIGkgPSBzdGFydDsgaSA8IGVuZDsgaSArPSAzKSB7XG4gICAgdG1wID1cbiAgICAgICgodWludDhbaV0gPDwgMTYpICYgMHhGRjAwMDApICtcbiAgICAgICgodWludDhbaSArIDFdIDw8IDgpICYgMHhGRjAwKSArXG4gICAgICAodWludDhbaSArIDJdICYgMHhGRilcbiAgICBvdXRwdXQucHVzaCh0cmlwbGV0VG9CYXNlNjQodG1wKSlcbiAgfVxuICByZXR1cm4gb3V0cHV0LmpvaW4oJycpXG59XG5cbmZ1bmN0aW9uIGZyb21CeXRlQXJyYXkgKHVpbnQ4KSB7XG4gIHZhciB0bXBcbiAgdmFyIGxlbiA9IHVpbnQ4Lmxlbmd0aFxuICB2YXIgZXh0cmFCeXRlcyA9IGxlbiAlIDMgLy8gaWYgd2UgaGF2ZSAxIGJ5dGUgbGVmdCwgcGFkIDIgYnl0ZXNcbiAgdmFyIHBhcnRzID0gW11cbiAgdmFyIG1heENodW5rTGVuZ3RoID0gMTYzODMgLy8gbXVzdCBiZSBtdWx0aXBsZSBvZiAzXG5cbiAgLy8gZ28gdGhyb3VnaCB0aGUgYXJyYXkgZXZlcnkgdGhyZWUgYnl0ZXMsIHdlJ2xsIGRlYWwgd2l0aCB0cmFpbGluZyBzdHVmZiBsYXRlclxuICBmb3IgKHZhciBpID0gMCwgbGVuMiA9IGxlbiAtIGV4dHJhQnl0ZXM7IGkgPCBsZW4yOyBpICs9IG1heENodW5rTGVuZ3RoKSB7XG4gICAgcGFydHMucHVzaChlbmNvZGVDaHVuayh1aW50OCwgaSwgKGkgKyBtYXhDaHVua0xlbmd0aCkgPiBsZW4yID8gbGVuMiA6IChpICsgbWF4Q2h1bmtMZW5ndGgpKSlcbiAgfVxuXG4gIC8vIHBhZCB0aGUgZW5kIHdpdGggemVyb3MsIGJ1dCBtYWtlIHN1cmUgdG8gbm90IGZvcmdldCB0aGUgZXh0cmEgYnl0ZXNcbiAgaWYgKGV4dHJhQnl0ZXMgPT09IDEpIHtcbiAgICB0bXAgPSB1aW50OFtsZW4gLSAxXVxuICAgIHBhcnRzLnB1c2goXG4gICAgICBsb29rdXBbdG1wID4+IDJdICtcbiAgICAgIGxvb2t1cFsodG1wIDw8IDQpICYgMHgzRl0gK1xuICAgICAgJz09J1xuICAgIClcbiAgfSBlbHNlIGlmIChleHRyYUJ5dGVzID09PSAyKSB7XG4gICAgdG1wID0gKHVpbnQ4W2xlbiAtIDJdIDw8IDgpICsgdWludDhbbGVuIC0gMV1cbiAgICBwYXJ0cy5wdXNoKFxuICAgICAgbG9va3VwW3RtcCA+PiAxMF0gK1xuICAgICAgbG9va3VwWyh0bXAgPj4gNCkgJiAweDNGXSArXG4gICAgICBsb29rdXBbKHRtcCA8PCAyKSAmIDB4M0ZdICtcbiAgICAgICc9J1xuICAgIClcbiAgfVxuXG4gIHJldHVybiBwYXJ0cy5qb2luKCcnKVxufVxuIiwgIi8qISBpZWVlNzU0LiBCU0QtMy1DbGF1c2UgTGljZW5zZS4gRmVyb3NzIEFib3VraGFkaWplaCA8aHR0cHM6Ly9mZXJvc3Mub3JnL29wZW5zb3VyY2U+ICovXG5leHBvcnRzLnJlYWQgPSBmdW5jdGlvbiAoYnVmZmVyLCBvZmZzZXQsIGlzTEUsIG1MZW4sIG5CeXRlcykge1xuICB2YXIgZSwgbVxuICB2YXIgZUxlbiA9IChuQnl0ZXMgKiA4KSAtIG1MZW4gLSAxXG4gIHZhciBlTWF4ID0gKDEgPDwgZUxlbikgLSAxXG4gIHZhciBlQmlhcyA9IGVNYXggPj4gMVxuICB2YXIgbkJpdHMgPSAtN1xuICB2YXIgaSA9IGlzTEUgPyAobkJ5dGVzIC0gMSkgOiAwXG4gIHZhciBkID0gaXNMRSA/IC0xIDogMVxuICB2YXIgcyA9IGJ1ZmZlcltvZmZzZXQgKyBpXVxuXG4gIGkgKz0gZFxuXG4gIGUgPSBzICYgKCgxIDw8ICgtbkJpdHMpKSAtIDEpXG4gIHMgPj49ICgtbkJpdHMpXG4gIG5CaXRzICs9IGVMZW5cbiAgZm9yICg7IG5CaXRzID4gMDsgZSA9IChlICogMjU2KSArIGJ1ZmZlcltvZmZzZXQgKyBpXSwgaSArPSBkLCBuQml0cyAtPSA4KSB7fVxuXG4gIG0gPSBlICYgKCgxIDw8ICgtbkJpdHMpKSAtIDEpXG4gIGUgPj49ICgtbkJpdHMpXG4gIG5CaXRzICs9IG1MZW5cbiAgZm9yICg7IG5CaXRzID4gMDsgbSA9IChtICogMjU2KSArIGJ1ZmZlcltvZmZzZXQgKyBpXSwgaSArPSBkLCBuQml0cyAtPSA4KSB7fVxuXG4gIGlmIChlID09PSAwKSB7XG4gICAgZSA9IDEgLSBlQmlhc1xuICB9IGVsc2UgaWYgKGUgPT09IGVNYXgpIHtcbiAgICByZXR1cm4gbSA/IE5hTiA6ICgocyA/IC0xIDogMSkgKiBJbmZpbml0eSlcbiAgfSBlbHNlIHtcbiAgICBtID0gbSArIE1hdGgucG93KDIsIG1MZW4pXG4gICAgZSA9IGUgLSBlQmlhc1xuICB9XG4gIHJldHVybiAocyA/IC0xIDogMSkgKiBtICogTWF0aC5wb3coMiwgZSAtIG1MZW4pXG59XG5cbmV4cG9ydHMud3JpdGUgPSBmdW5jdGlvbiAoYnVmZmVyLCB2YWx1ZSwgb2Zmc2V0LCBpc0xFLCBtTGVuLCBuQnl0ZXMpIHtcbiAgdmFyIGUsIG0sIGNcbiAgdmFyIGVMZW4gPSAobkJ5dGVzICogOCkgLSBtTGVuIC0gMVxuICB2YXIgZU1heCA9ICgxIDw8IGVMZW4pIC0gMVxuICB2YXIgZUJpYXMgPSBlTWF4ID4+IDFcbiAgdmFyIHJ0ID0gKG1MZW4gPT09IDIzID8gTWF0aC5wb3coMiwgLTI0KSAtIE1hdGgucG93KDIsIC03NykgOiAwKVxuICB2YXIgaSA9IGlzTEUgPyAwIDogKG5CeXRlcyAtIDEpXG4gIHZhciBkID0gaXNMRSA/IDEgOiAtMVxuICB2YXIgcyA9IHZhbHVlIDwgMCB8fCAodmFsdWUgPT09IDAgJiYgMSAvIHZhbHVlIDwgMCkgPyAxIDogMFxuXG4gIHZhbHVlID0gTWF0aC5hYnModmFsdWUpXG5cbiAgaWYgKGlzTmFOKHZhbHVlKSB8fCB2YWx1ZSA9PT0gSW5maW5pdHkpIHtcbiAgICBtID0gaXNOYU4odmFsdWUpID8gMSA6IDBcbiAgICBlID0gZU1heFxuICB9IGVsc2Uge1xuICAgIGUgPSBNYXRoLmZsb29yKE1hdGgubG9nKHZhbHVlKSAvIE1hdGguTE4yKVxuICAgIGlmICh2YWx1ZSAqIChjID0gTWF0aC5wb3coMiwgLWUpKSA8IDEpIHtcbiAgICAgIGUtLVxuICAgICAgYyAqPSAyXG4gICAgfVxuICAgIGlmIChlICsgZUJpYXMgPj0gMSkge1xuICAgICAgdmFsdWUgKz0gcnQgLyBjXG4gICAgfSBlbHNlIHtcbiAgICAgIHZhbHVlICs9IHJ0ICogTWF0aC5wb3coMiwgMSAtIGVCaWFzKVxuICAgIH1cbiAgICBpZiAodmFsdWUgKiBjID49IDIpIHtcbiAgICAgIGUrK1xuICAgICAgYyAvPSAyXG4gICAgfVxuXG4gICAgaWYgKGUgKyBlQmlhcyA+PSBlTWF4KSB7XG4gICAgICBtID0gMFxuICAgICAgZSA9IGVNYXhcbiAgICB9IGVsc2UgaWYgKGUgKyBlQmlhcyA+PSAxKSB7XG4gICAgICBtID0gKCh2YWx1ZSAqIGMpIC0gMSkgKiBNYXRoLnBvdygyLCBtTGVuKVxuICAgICAgZSA9IGUgKyBlQmlhc1xuICAgIH0gZWxzZSB7XG4gICAgICBtID0gdmFsdWUgKiBNYXRoLnBvdygyLCBlQmlhcyAtIDEpICogTWF0aC5wb3coMiwgbUxlbilcbiAgICAgIGUgPSAwXG4gICAgfVxuICB9XG5cbiAgZm9yICg7IG1MZW4gPj0gODsgYnVmZmVyW29mZnNldCArIGldID0gbSAmIDB4ZmYsIGkgKz0gZCwgbSAvPSAyNTYsIG1MZW4gLT0gOCkge31cblxuICBlID0gKGUgPDwgbUxlbikgfCBtXG4gIGVMZW4gKz0gbUxlblxuICBmb3IgKDsgZUxlbiA+IDA7IGJ1ZmZlcltvZmZzZXQgKyBpXSA9IGUgJiAweGZmLCBpICs9IGQsIGUgLz0gMjU2LCBlTGVuIC09IDgpIHt9XG5cbiAgYnVmZmVyW29mZnNldCArIGkgLSBkXSB8PSBzICogMTI4XG59XG4iLCAiLyohXG4gKiBUaGUgYnVmZmVyIG1vZHVsZSBmcm9tIG5vZGUuanMsIGZvciB0aGUgYnJvd3Nlci5cbiAqXG4gKiBAYXV0aG9yICAgRmVyb3NzIEFib3VraGFkaWplaCA8aHR0cHM6Ly9mZXJvc3Mub3JnPlxuICogQGxpY2Vuc2UgIE1JVFxuICovXG4vKiBlc2xpbnQtZGlzYWJsZSBuby1wcm90byAqL1xuXG4ndXNlIHN0cmljdCdcblxuY29uc3QgYmFzZTY0ID0gcmVxdWlyZSgnYmFzZTY0LWpzJylcbmNvbnN0IGllZWU3NTQgPSByZXF1aXJlKCdpZWVlNzU0JylcbmNvbnN0IGN1c3RvbUluc3BlY3RTeW1ib2wgPVxuICAodHlwZW9mIFN5bWJvbCA9PT0gJ2Z1bmN0aW9uJyAmJiB0eXBlb2YgU3ltYm9sWydmb3InXSA9PT0gJ2Z1bmN0aW9uJykgLy8gZXNsaW50LWRpc2FibGUtbGluZSBkb3Qtbm90YXRpb25cbiAgICA/IFN5bWJvbFsnZm9yJ10oJ25vZGVqcy51dGlsLmluc3BlY3QuY3VzdG9tJykgLy8gZXNsaW50LWRpc2FibGUtbGluZSBkb3Qtbm90YXRpb25cbiAgICA6IG51bGxcblxuZXhwb3J0cy5CdWZmZXIgPSBCdWZmZXJcbmV4cG9ydHMuU2xvd0J1ZmZlciA9IFNsb3dCdWZmZXJcbmV4cG9ydHMuSU5TUEVDVF9NQVhfQllURVMgPSA1MFxuXG5jb25zdCBLX01BWF9MRU5HVEggPSAweDdmZmZmZmZmXG5leHBvcnRzLmtNYXhMZW5ndGggPSBLX01BWF9MRU5HVEhcblxuLyoqXG4gKiBJZiBgQnVmZmVyLlRZUEVEX0FSUkFZX1NVUFBPUlRgOlxuICogICA9PT0gdHJ1ZSAgICBVc2UgVWludDhBcnJheSBpbXBsZW1lbnRhdGlvbiAoZmFzdGVzdClcbiAqICAgPT09IGZhbHNlICAgUHJpbnQgd2FybmluZyBhbmQgcmVjb21tZW5kIHVzaW5nIGBidWZmZXJgIHY0Lnggd2hpY2ggaGFzIGFuIE9iamVjdFxuICogICAgICAgICAgICAgICBpbXBsZW1lbnRhdGlvbiAobW9zdCBjb21wYXRpYmxlLCBldmVuIElFNilcbiAqXG4gKiBCcm93c2VycyB0aGF0IHN1cHBvcnQgdHlwZWQgYXJyYXlzIGFyZSBJRSAxMCssIEZpcmVmb3ggNCssIENocm9tZSA3KywgU2FmYXJpIDUuMSssXG4gKiBPcGVyYSAxMS42KywgaU9TIDQuMisuXG4gKlxuICogV2UgcmVwb3J0IHRoYXQgdGhlIGJyb3dzZXIgZG9lcyBub3Qgc3VwcG9ydCB0eXBlZCBhcnJheXMgaWYgdGhlIGFyZSBub3Qgc3ViY2xhc3NhYmxlXG4gKiB1c2luZyBfX3Byb3RvX18uIEZpcmVmb3ggNC0yOSBsYWNrcyBzdXBwb3J0IGZvciBhZGRpbmcgbmV3IHByb3BlcnRpZXMgdG8gYFVpbnQ4QXJyYXlgXG4gKiAoU2VlOiBodHRwczovL2J1Z3ppbGxhLm1vemlsbGEub3JnL3Nob3dfYnVnLmNnaT9pZD02OTU0MzgpLiBJRSAxMCBsYWNrcyBzdXBwb3J0XG4gKiBmb3IgX19wcm90b19fIGFuZCBoYXMgYSBidWdneSB0eXBlZCBhcnJheSBpbXBsZW1lbnRhdGlvbi5cbiAqL1xuQnVmZmVyLlRZUEVEX0FSUkFZX1NVUFBPUlQgPSB0eXBlZEFycmF5U3VwcG9ydCgpXG5cbmlmICghQnVmZmVyLlRZUEVEX0FSUkFZX1NVUFBPUlQgJiYgdHlwZW9mIGNvbnNvbGUgIT09ICd1bmRlZmluZWQnICYmXG4gICAgdHlwZW9mIGNvbnNvbGUuZXJyb3IgPT09ICdmdW5jdGlvbicpIHtcbiAgY29uc29sZS5lcnJvcihcbiAgICAnVGhpcyBicm93c2VyIGxhY2tzIHR5cGVkIGFycmF5IChVaW50OEFycmF5KSBzdXBwb3J0IHdoaWNoIGlzIHJlcXVpcmVkIGJ5ICcgK1xuICAgICdgYnVmZmVyYCB2NS54LiBVc2UgYGJ1ZmZlcmAgdjQueCBpZiB5b3UgcmVxdWlyZSBvbGQgYnJvd3NlciBzdXBwb3J0LidcbiAgKVxufVxuXG5mdW5jdGlvbiB0eXBlZEFycmF5U3VwcG9ydCAoKSB7XG4gIC8vIENhbiB0eXBlZCBhcnJheSBpbnN0YW5jZXMgY2FuIGJlIGF1Z21lbnRlZD9cbiAgdHJ5IHtcbiAgICBjb25zdCBhcnIgPSBuZXcgVWludDhBcnJheSgxKVxuICAgIGNvbnN0IHByb3RvID0geyBmb286IGZ1bmN0aW9uICgpIHsgcmV0dXJuIDQyIH0gfVxuICAgIE9iamVjdC5zZXRQcm90b3R5cGVPZihwcm90bywgVWludDhBcnJheS5wcm90b3R5cGUpXG4gICAgT2JqZWN0LnNldFByb3RvdHlwZU9mKGFyciwgcHJvdG8pXG4gICAgcmV0dXJuIGFyci5mb28oKSA9PT0gNDJcbiAgfSBjYXRjaCAoZSkge1xuICAgIHJldHVybiBmYWxzZVxuICB9XG59XG5cbk9iamVjdC5kZWZpbmVQcm9wZXJ0eShCdWZmZXIucHJvdG90eXBlLCAncGFyZW50Jywge1xuICBlbnVtZXJhYmxlOiB0cnVlLFxuICBnZXQ6IGZ1bmN0aW9uICgpIHtcbiAgICBpZiAoIUJ1ZmZlci5pc0J1ZmZlcih0aGlzKSkgcmV0dXJuIHVuZGVmaW5lZFxuICAgIHJldHVybiB0aGlzLmJ1ZmZlclxuICB9XG59KVxuXG5PYmplY3QuZGVmaW5lUHJvcGVydHkoQnVmZmVyLnByb3RvdHlwZSwgJ29mZnNldCcsIHtcbiAgZW51bWVyYWJsZTogdHJ1ZSxcbiAgZ2V0OiBmdW5jdGlvbiAoKSB7XG4gICAgaWYgKCFCdWZmZXIuaXNCdWZmZXIodGhpcykpIHJldHVybiB1bmRlZmluZWRcbiAgICByZXR1cm4gdGhpcy5ieXRlT2Zmc2V0XG4gIH1cbn0pXG5cbmZ1bmN0aW9uIGNyZWF0ZUJ1ZmZlciAobGVuZ3RoKSB7XG4gIGlmIChsZW5ndGggPiBLX01BWF9MRU5HVEgpIHtcbiAgICB0aHJvdyBuZXcgUmFuZ2VFcnJvcignVGhlIHZhbHVlIFwiJyArIGxlbmd0aCArICdcIiBpcyBpbnZhbGlkIGZvciBvcHRpb24gXCJzaXplXCInKVxuICB9XG4gIC8vIFJldHVybiBhbiBhdWdtZW50ZWQgYFVpbnQ4QXJyYXlgIGluc3RhbmNlXG4gIGNvbnN0IGJ1ZiA9IG5ldyBVaW50OEFycmF5KGxlbmd0aClcbiAgT2JqZWN0LnNldFByb3RvdHlwZU9mKGJ1ZiwgQnVmZmVyLnByb3RvdHlwZSlcbiAgcmV0dXJuIGJ1ZlxufVxuXG4vKipcbiAqIFRoZSBCdWZmZXIgY29uc3RydWN0b3IgcmV0dXJucyBpbnN0YW5jZXMgb2YgYFVpbnQ4QXJyYXlgIHRoYXQgaGF2ZSB0aGVpclxuICogcHJvdG90eXBlIGNoYW5nZWQgdG8gYEJ1ZmZlci5wcm90b3R5cGVgLiBGdXJ0aGVybW9yZSwgYEJ1ZmZlcmAgaXMgYSBzdWJjbGFzcyBvZlxuICogYFVpbnQ4QXJyYXlgLCBzbyB0aGUgcmV0dXJuZWQgaW5zdGFuY2VzIHdpbGwgaGF2ZSBhbGwgdGhlIG5vZGUgYEJ1ZmZlcmAgbWV0aG9kc1xuICogYW5kIHRoZSBgVWludDhBcnJheWAgbWV0aG9kcy4gU3F1YXJlIGJyYWNrZXQgbm90YXRpb24gd29ya3MgYXMgZXhwZWN0ZWQgLS0gaXRcbiAqIHJldHVybnMgYSBzaW5nbGUgb2N0ZXQuXG4gKlxuICogVGhlIGBVaW50OEFycmF5YCBwcm90b3R5cGUgcmVtYWlucyB1bm1vZGlmaWVkLlxuICovXG5cbmZ1bmN0aW9uIEJ1ZmZlciAoYXJnLCBlbmNvZGluZ09yT2Zmc2V0LCBsZW5ndGgpIHtcbiAgLy8gQ29tbW9uIGNhc2UuXG4gIGlmICh0eXBlb2YgYXJnID09PSAnbnVtYmVyJykge1xuICAgIGlmICh0eXBlb2YgZW5jb2RpbmdPck9mZnNldCA9PT0gJ3N0cmluZycpIHtcbiAgICAgIHRocm93IG5ldyBUeXBlRXJyb3IoXG4gICAgICAgICdUaGUgXCJzdHJpbmdcIiBhcmd1bWVudCBtdXN0IGJlIG9mIHR5cGUgc3RyaW5nLiBSZWNlaXZlZCB0eXBlIG51bWJlcidcbiAgICAgIClcbiAgICB9XG4gICAgcmV0dXJuIGFsbG9jVW5zYWZlKGFyZylcbiAgfVxuICByZXR1cm4gZnJvbShhcmcsIGVuY29kaW5nT3JPZmZzZXQsIGxlbmd0aClcbn1cblxuQnVmZmVyLnBvb2xTaXplID0gODE5MiAvLyBub3QgdXNlZCBieSB0aGlzIGltcGxlbWVudGF0aW9uXG5cbmZ1bmN0aW9uIGZyb20gKHZhbHVlLCBlbmNvZGluZ09yT2Zmc2V0LCBsZW5ndGgpIHtcbiAgaWYgKHR5cGVvZiB2YWx1ZSA9PT0gJ3N0cmluZycpIHtcbiAgICByZXR1cm4gZnJvbVN0cmluZyh2YWx1ZSwgZW5jb2RpbmdPck9mZnNldClcbiAgfVxuXG4gIGlmIChBcnJheUJ1ZmZlci5pc1ZpZXcodmFsdWUpKSB7XG4gICAgcmV0dXJuIGZyb21BcnJheVZpZXcodmFsdWUpXG4gIH1cblxuICBpZiAodmFsdWUgPT0gbnVsbCkge1xuICAgIHRocm93IG5ldyBUeXBlRXJyb3IoXG4gICAgICAnVGhlIGZpcnN0IGFyZ3VtZW50IG11c3QgYmUgb25lIG9mIHR5cGUgc3RyaW5nLCBCdWZmZXIsIEFycmF5QnVmZmVyLCBBcnJheSwgJyArXG4gICAgICAnb3IgQXJyYXktbGlrZSBPYmplY3QuIFJlY2VpdmVkIHR5cGUgJyArICh0eXBlb2YgdmFsdWUpXG4gICAgKVxuICB9XG5cbiAgaWYgKGlzSW5zdGFuY2UodmFsdWUsIEFycmF5QnVmZmVyKSB8fFxuICAgICAgKHZhbHVlICYmIGlzSW5zdGFuY2UodmFsdWUuYnVmZmVyLCBBcnJheUJ1ZmZlcikpKSB7XG4gICAgcmV0dXJuIGZyb21BcnJheUJ1ZmZlcih2YWx1ZSwgZW5jb2RpbmdPck9mZnNldCwgbGVuZ3RoKVxuICB9XG5cbiAgaWYgKHR5cGVvZiBTaGFyZWRBcnJheUJ1ZmZlciAhPT0gJ3VuZGVmaW5lZCcgJiZcbiAgICAgIChpc0luc3RhbmNlKHZhbHVlLCBTaGFyZWRBcnJheUJ1ZmZlcikgfHxcbiAgICAgICh2YWx1ZSAmJiBpc0luc3RhbmNlKHZhbHVlLmJ1ZmZlciwgU2hhcmVkQXJyYXlCdWZmZXIpKSkpIHtcbiAgICByZXR1cm4gZnJvbUFycmF5QnVmZmVyKHZhbHVlLCBlbmNvZGluZ09yT2Zmc2V0LCBsZW5ndGgpXG4gIH1cblxuICBpZiAodHlwZW9mIHZhbHVlID09PSAnbnVtYmVyJykge1xuICAgIHRocm93IG5ldyBUeXBlRXJyb3IoXG4gICAgICAnVGhlIFwidmFsdWVcIiBhcmd1bWVudCBtdXN0IG5vdCBiZSBvZiB0eXBlIG51bWJlci4gUmVjZWl2ZWQgdHlwZSBudW1iZXInXG4gICAgKVxuICB9XG5cbiAgY29uc3QgdmFsdWVPZiA9IHZhbHVlLnZhbHVlT2YgJiYgdmFsdWUudmFsdWVPZigpXG4gIGlmICh2YWx1ZU9mICE9IG51bGwgJiYgdmFsdWVPZiAhPT0gdmFsdWUpIHtcbiAgICByZXR1cm4gQnVmZmVyLmZyb20odmFsdWVPZiwgZW5jb2RpbmdPck9mZnNldCwgbGVuZ3RoKVxuICB9XG5cbiAgY29uc3QgYiA9IGZyb21PYmplY3QodmFsdWUpXG4gIGlmIChiKSByZXR1cm4gYlxuXG4gIGlmICh0eXBlb2YgU3ltYm9sICE9PSAndW5kZWZpbmVkJyAmJiBTeW1ib2wudG9QcmltaXRpdmUgIT0gbnVsbCAmJlxuICAgICAgdHlwZW9mIHZhbHVlW1N5bWJvbC50b1ByaW1pdGl2ZV0gPT09ICdmdW5jdGlvbicpIHtcbiAgICByZXR1cm4gQnVmZmVyLmZyb20odmFsdWVbU3ltYm9sLnRvUHJpbWl0aXZlXSgnc3RyaW5nJyksIGVuY29kaW5nT3JPZmZzZXQsIGxlbmd0aClcbiAgfVxuXG4gIHRocm93IG5ldyBUeXBlRXJyb3IoXG4gICAgJ1RoZSBmaXJzdCBhcmd1bWVudCBtdXN0IGJlIG9uZSBvZiB0eXBlIHN0cmluZywgQnVmZmVyLCBBcnJheUJ1ZmZlciwgQXJyYXksICcgK1xuICAgICdvciBBcnJheS1saWtlIE9iamVjdC4gUmVjZWl2ZWQgdHlwZSAnICsgKHR5cGVvZiB2YWx1ZSlcbiAgKVxufVxuXG4vKipcbiAqIEZ1bmN0aW9uYWxseSBlcXVpdmFsZW50IHRvIEJ1ZmZlcihhcmcsIGVuY29kaW5nKSBidXQgdGhyb3dzIGEgVHlwZUVycm9yXG4gKiBpZiB2YWx1ZSBpcyBhIG51bWJlci5cbiAqIEJ1ZmZlci5mcm9tKHN0clssIGVuY29kaW5nXSlcbiAqIEJ1ZmZlci5mcm9tKGFycmF5KVxuICogQnVmZmVyLmZyb20oYnVmZmVyKVxuICogQnVmZmVyLmZyb20oYXJyYXlCdWZmZXJbLCBieXRlT2Zmc2V0WywgbGVuZ3RoXV0pXG4gKiovXG5CdWZmZXIuZnJvbSA9IGZ1bmN0aW9uICh2YWx1ZSwgZW5jb2RpbmdPck9mZnNldCwgbGVuZ3RoKSB7XG4gIHJldHVybiBmcm9tKHZhbHVlLCBlbmNvZGluZ09yT2Zmc2V0LCBsZW5ndGgpXG59XG5cbi8vIE5vdGU6IENoYW5nZSBwcm90b3R5cGUgKmFmdGVyKiBCdWZmZXIuZnJvbSBpcyBkZWZpbmVkIHRvIHdvcmthcm91bmQgQ2hyb21lIGJ1Zzpcbi8vIGh0dHBzOi8vZ2l0aHViLmNvbS9mZXJvc3MvYnVmZmVyL3B1bGwvMTQ4XG5PYmplY3Quc2V0UHJvdG90eXBlT2YoQnVmZmVyLnByb3RvdHlwZSwgVWludDhBcnJheS5wcm90b3R5cGUpXG5PYmplY3Quc2V0UHJvdG90eXBlT2YoQnVmZmVyLCBVaW50OEFycmF5KVxuXG5mdW5jdGlvbiBhc3NlcnRTaXplIChzaXplKSB7XG4gIGlmICh0eXBlb2Ygc2l6ZSAhPT0gJ251bWJlcicpIHtcbiAgICB0aHJvdyBuZXcgVHlwZUVycm9yKCdcInNpemVcIiBhcmd1bWVudCBtdXN0IGJlIG9mIHR5cGUgbnVtYmVyJylcbiAgfSBlbHNlIGlmIChzaXplIDwgMCkge1xuICAgIHRocm93IG5ldyBSYW5nZUVycm9yKCdUaGUgdmFsdWUgXCInICsgc2l6ZSArICdcIiBpcyBpbnZhbGlkIGZvciBvcHRpb24gXCJzaXplXCInKVxuICB9XG59XG5cbmZ1bmN0aW9uIGFsbG9jIChzaXplLCBmaWxsLCBlbmNvZGluZykge1xuICBhc3NlcnRTaXplKHNpemUpXG4gIGlmIChzaXplIDw9IDApIHtcbiAgICByZXR1cm4gY3JlYXRlQnVmZmVyKHNpemUpXG4gIH1cbiAgaWYgKGZpbGwgIT09IHVuZGVmaW5lZCkge1xuICAgIC8vIE9ubHkgcGF5IGF0dGVudGlvbiB0byBlbmNvZGluZyBpZiBpdCdzIGEgc3RyaW5nLiBUaGlzXG4gICAgLy8gcHJldmVudHMgYWNjaWRlbnRhbGx5IHNlbmRpbmcgaW4gYSBudW1iZXIgdGhhdCB3b3VsZFxuICAgIC8vIGJlIGludGVycHJldGVkIGFzIGEgc3RhcnQgb2Zmc2V0LlxuICAgIHJldHVybiB0eXBlb2YgZW5jb2RpbmcgPT09ICdzdHJpbmcnXG4gICAgICA/IGNyZWF0ZUJ1ZmZlcihzaXplKS5maWxsKGZpbGwsIGVuY29kaW5nKVxuICAgICAgOiBjcmVhdGVCdWZmZXIoc2l6ZSkuZmlsbChmaWxsKVxuICB9XG4gIHJldHVybiBjcmVhdGVCdWZmZXIoc2l6ZSlcbn1cblxuLyoqXG4gKiBDcmVhdGVzIGEgbmV3IGZpbGxlZCBCdWZmZXIgaW5zdGFuY2UuXG4gKiBhbGxvYyhzaXplWywgZmlsbFssIGVuY29kaW5nXV0pXG4gKiovXG5CdWZmZXIuYWxsb2MgPSBmdW5jdGlvbiAoc2l6ZSwgZmlsbCwgZW5jb2RpbmcpIHtcbiAgcmV0dXJuIGFsbG9jKHNpemUsIGZpbGwsIGVuY29kaW5nKVxufVxuXG5mdW5jdGlvbiBhbGxvY1Vuc2FmZSAoc2l6ZSkge1xuICBhc3NlcnRTaXplKHNpemUpXG4gIHJldHVybiBjcmVhdGVCdWZmZXIoc2l6ZSA8IDAgPyAwIDogY2hlY2tlZChzaXplKSB8IDApXG59XG5cbi8qKlxuICogRXF1aXZhbGVudCB0byBCdWZmZXIobnVtKSwgYnkgZGVmYXVsdCBjcmVhdGVzIGEgbm9uLXplcm8tZmlsbGVkIEJ1ZmZlciBpbnN0YW5jZS5cbiAqICovXG5CdWZmZXIuYWxsb2NVbnNhZmUgPSBmdW5jdGlvbiAoc2l6ZSkge1xuICByZXR1cm4gYWxsb2NVbnNhZmUoc2l6ZSlcbn1cbi8qKlxuICogRXF1aXZhbGVudCB0byBTbG93QnVmZmVyKG51bSksIGJ5IGRlZmF1bHQgY3JlYXRlcyBhIG5vbi16ZXJvLWZpbGxlZCBCdWZmZXIgaW5zdGFuY2UuXG4gKi9cbkJ1ZmZlci5hbGxvY1Vuc2FmZVNsb3cgPSBmdW5jdGlvbiAoc2l6ZSkge1xuICByZXR1cm4gYWxsb2NVbnNhZmUoc2l6ZSlcbn1cblxuZnVuY3Rpb24gZnJvbVN0cmluZyAoc3RyaW5nLCBlbmNvZGluZykge1xuICBpZiAodHlwZW9mIGVuY29kaW5nICE9PSAnc3RyaW5nJyB8fCBlbmNvZGluZyA9PT0gJycpIHtcbiAgICBlbmNvZGluZyA9ICd1dGY4J1xuICB9XG5cbiAgaWYgKCFCdWZmZXIuaXNFbmNvZGluZyhlbmNvZGluZykpIHtcbiAgICB0aHJvdyBuZXcgVHlwZUVycm9yKCdVbmtub3duIGVuY29kaW5nOiAnICsgZW5jb2RpbmcpXG4gIH1cblxuICBjb25zdCBsZW5ndGggPSBieXRlTGVuZ3RoKHN0cmluZywgZW5jb2RpbmcpIHwgMFxuICBsZXQgYnVmID0gY3JlYXRlQnVmZmVyKGxlbmd0aClcblxuICBjb25zdCBhY3R1YWwgPSBidWYud3JpdGUoc3RyaW5nLCBlbmNvZGluZylcblxuICBpZiAoYWN0dWFsICE9PSBsZW5ndGgpIHtcbiAgICAvLyBXcml0aW5nIGEgaGV4IHN0cmluZywgZm9yIGV4YW1wbGUsIHRoYXQgY29udGFpbnMgaW52YWxpZCBjaGFyYWN0ZXJzIHdpbGxcbiAgICAvLyBjYXVzZSBldmVyeXRoaW5nIGFmdGVyIHRoZSBmaXJzdCBpbnZhbGlkIGNoYXJhY3RlciB0byBiZSBpZ25vcmVkLiAoZS5nLlxuICAgIC8vICdhYnh4Y2QnIHdpbGwgYmUgdHJlYXRlZCBhcyAnYWInKVxuICAgIGJ1ZiA9IGJ1Zi5zbGljZSgwLCBhY3R1YWwpXG4gIH1cblxuICByZXR1cm4gYnVmXG59XG5cbmZ1bmN0aW9uIGZyb21BcnJheUxpa2UgKGFycmF5KSB7XG4gIGNvbnN0IGxlbmd0aCA9IGFycmF5Lmxlbmd0aCA8IDAgPyAwIDogY2hlY2tlZChhcnJheS5sZW5ndGgpIHwgMFxuICBjb25zdCBidWYgPSBjcmVhdGVCdWZmZXIobGVuZ3RoKVxuICBmb3IgKGxldCBpID0gMDsgaSA8IGxlbmd0aDsgaSArPSAxKSB7XG4gICAgYnVmW2ldID0gYXJyYXlbaV0gJiAyNTVcbiAgfVxuICByZXR1cm4gYnVmXG59XG5cbmZ1bmN0aW9uIGZyb21BcnJheVZpZXcgKGFycmF5Vmlldykge1xuICBpZiAoaXNJbnN0YW5jZShhcnJheVZpZXcsIFVpbnQ4QXJyYXkpKSB7XG4gICAgY29uc3QgY29weSA9IG5ldyBVaW50OEFycmF5KGFycmF5VmlldylcbiAgICByZXR1cm4gZnJvbUFycmF5QnVmZmVyKGNvcHkuYnVmZmVyLCBjb3B5LmJ5dGVPZmZzZXQsIGNvcHkuYnl0ZUxlbmd0aClcbiAgfVxuICByZXR1cm4gZnJvbUFycmF5TGlrZShhcnJheVZpZXcpXG59XG5cbmZ1bmN0aW9uIGZyb21BcnJheUJ1ZmZlciAoYXJyYXksIGJ5dGVPZmZzZXQsIGxlbmd0aCkge1xuICBpZiAoYnl0ZU9mZnNldCA8IDAgfHwgYXJyYXkuYnl0ZUxlbmd0aCA8IGJ5dGVPZmZzZXQpIHtcbiAgICB0aHJvdyBuZXcgUmFuZ2VFcnJvcignXCJvZmZzZXRcIiBpcyBvdXRzaWRlIG9mIGJ1ZmZlciBib3VuZHMnKVxuICB9XG5cbiAgaWYgKGFycmF5LmJ5dGVMZW5ndGggPCBieXRlT2Zmc2V0ICsgKGxlbmd0aCB8fCAwKSkge1xuICAgIHRocm93IG5ldyBSYW5nZUVycm9yKCdcImxlbmd0aFwiIGlzIG91dHNpZGUgb2YgYnVmZmVyIGJvdW5kcycpXG4gIH1cblxuICBsZXQgYnVmXG4gIGlmIChieXRlT2Zmc2V0ID09PSB1bmRlZmluZWQgJiYgbGVuZ3RoID09PSB1bmRlZmluZWQpIHtcbiAgICBidWYgPSBuZXcgVWludDhBcnJheShhcnJheSlcbiAgfSBlbHNlIGlmIChsZW5ndGggPT09IHVuZGVmaW5lZCkge1xuICAgIGJ1ZiA9IG5ldyBVaW50OEFycmF5KGFycmF5LCBieXRlT2Zmc2V0KVxuICB9IGVsc2Uge1xuICAgIGJ1ZiA9IG5ldyBVaW50OEFycmF5KGFycmF5LCBieXRlT2Zmc2V0LCBsZW5ndGgpXG4gIH1cblxuICAvLyBSZXR1cm4gYW4gYXVnbWVudGVkIGBVaW50OEFycmF5YCBpbnN0YW5jZVxuICBPYmplY3Quc2V0UHJvdG90eXBlT2YoYnVmLCBCdWZmZXIucHJvdG90eXBlKVxuXG4gIHJldHVybiBidWZcbn1cblxuZnVuY3Rpb24gZnJvbU9iamVjdCAob2JqKSB7XG4gIGlmIChCdWZmZXIuaXNCdWZmZXIob2JqKSkge1xuICAgIGNvbnN0IGxlbiA9IGNoZWNrZWQob2JqLmxlbmd0aCkgfCAwXG4gICAgY29uc3QgYnVmID0gY3JlYXRlQnVmZmVyKGxlbilcblxuICAgIGlmIChidWYubGVuZ3RoID09PSAwKSB7XG4gICAgICByZXR1cm4gYnVmXG4gICAgfVxuXG4gICAgb2JqLmNvcHkoYnVmLCAwLCAwLCBsZW4pXG4gICAgcmV0dXJuIGJ1ZlxuICB9XG5cbiAgaWYgKG9iai5sZW5ndGggIT09IHVuZGVmaW5lZCkge1xuICAgIGlmICh0eXBlb2Ygb2JqLmxlbmd0aCAhPT0gJ251bWJlcicgfHwgbnVtYmVySXNOYU4ob2JqLmxlbmd0aCkpIHtcbiAgICAgIHJldHVybiBjcmVhdGVCdWZmZXIoMClcbiAgICB9XG4gICAgcmV0dXJuIGZyb21BcnJheUxpa2Uob2JqKVxuICB9XG5cbiAgaWYgKG9iai50eXBlID09PSAnQnVmZmVyJyAmJiBBcnJheS5pc0FycmF5KG9iai5kYXRhKSkge1xuICAgIHJldHVybiBmcm9tQXJyYXlMaWtlKG9iai5kYXRhKVxuICB9XG59XG5cbmZ1bmN0aW9uIGNoZWNrZWQgKGxlbmd0aCkge1xuICAvLyBOb3RlOiBjYW5ub3QgdXNlIGBsZW5ndGggPCBLX01BWF9MRU5HVEhgIGhlcmUgYmVjYXVzZSB0aGF0IGZhaWxzIHdoZW5cbiAgLy8gbGVuZ3RoIGlzIE5hTiAod2hpY2ggaXMgb3RoZXJ3aXNlIGNvZXJjZWQgdG8gemVyby4pXG4gIGlmIChsZW5ndGggPj0gS19NQVhfTEVOR1RIKSB7XG4gICAgdGhyb3cgbmV3IFJhbmdlRXJyb3IoJ0F0dGVtcHQgdG8gYWxsb2NhdGUgQnVmZmVyIGxhcmdlciB0aGFuIG1heGltdW0gJyArXG4gICAgICAgICAgICAgICAgICAgICAgICAgJ3NpemU6IDB4JyArIEtfTUFYX0xFTkdUSC50b1N0cmluZygxNikgKyAnIGJ5dGVzJylcbiAgfVxuICByZXR1cm4gbGVuZ3RoIHwgMFxufVxuXG5mdW5jdGlvbiBTbG93QnVmZmVyIChsZW5ndGgpIHtcbiAgaWYgKCtsZW5ndGggIT0gbGVuZ3RoKSB7IC8vIGVzbGludC1kaXNhYmxlLWxpbmUgZXFlcWVxXG4gICAgbGVuZ3RoID0gMFxuICB9XG4gIHJldHVybiBCdWZmZXIuYWxsb2MoK2xlbmd0aClcbn1cblxuQnVmZmVyLmlzQnVmZmVyID0gZnVuY3Rpb24gaXNCdWZmZXIgKGIpIHtcbiAgcmV0dXJuIGIgIT0gbnVsbCAmJiBiLl9pc0J1ZmZlciA9PT0gdHJ1ZSAmJlxuICAgIGIgIT09IEJ1ZmZlci5wcm90b3R5cGUgLy8gc28gQnVmZmVyLmlzQnVmZmVyKEJ1ZmZlci5wcm90b3R5cGUpIHdpbGwgYmUgZmFsc2Vcbn1cblxuQnVmZmVyLmNvbXBhcmUgPSBmdW5jdGlvbiBjb21wYXJlIChhLCBiKSB7XG4gIGlmIChpc0luc3RhbmNlKGEsIFVpbnQ4QXJyYXkpKSBhID0gQnVmZmVyLmZyb20oYSwgYS5vZmZzZXQsIGEuYnl0ZUxlbmd0aClcbiAgaWYgKGlzSW5zdGFuY2UoYiwgVWludDhBcnJheSkpIGIgPSBCdWZmZXIuZnJvbShiLCBiLm9mZnNldCwgYi5ieXRlTGVuZ3RoKVxuICBpZiAoIUJ1ZmZlci5pc0J1ZmZlcihhKSB8fCAhQnVmZmVyLmlzQnVmZmVyKGIpKSB7XG4gICAgdGhyb3cgbmV3IFR5cGVFcnJvcihcbiAgICAgICdUaGUgXCJidWYxXCIsIFwiYnVmMlwiIGFyZ3VtZW50cyBtdXN0IGJlIG9uZSBvZiB0eXBlIEJ1ZmZlciBvciBVaW50OEFycmF5J1xuICAgIClcbiAgfVxuXG4gIGlmIChhID09PSBiKSByZXR1cm4gMFxuXG4gIGxldCB4ID0gYS5sZW5ndGhcbiAgbGV0IHkgPSBiLmxlbmd0aFxuXG4gIGZvciAobGV0IGkgPSAwLCBsZW4gPSBNYXRoLm1pbih4LCB5KTsgaSA8IGxlbjsgKytpKSB7XG4gICAgaWYgKGFbaV0gIT09IGJbaV0pIHtcbiAgICAgIHggPSBhW2ldXG4gICAgICB5ID0gYltpXVxuICAgICAgYnJlYWtcbiAgICB9XG4gIH1cblxuICBpZiAoeCA8IHkpIHJldHVybiAtMVxuICBpZiAoeSA8IHgpIHJldHVybiAxXG4gIHJldHVybiAwXG59XG5cbkJ1ZmZlci5pc0VuY29kaW5nID0gZnVuY3Rpb24gaXNFbmNvZGluZyAoZW5jb2RpbmcpIHtcbiAgc3dpdGNoIChTdHJpbmcoZW5jb2RpbmcpLnRvTG93ZXJDYXNlKCkpIHtcbiAgICBjYXNlICdoZXgnOlxuICAgIGNhc2UgJ3V0ZjgnOlxuICAgIGNhc2UgJ3V0Zi04JzpcbiAgICBjYXNlICdhc2NpaSc6XG4gICAgY2FzZSAnbGF0aW4xJzpcbiAgICBjYXNlICdiaW5hcnknOlxuICAgIGNhc2UgJ2Jhc2U2NCc6XG4gICAgY2FzZSAndWNzMic6XG4gICAgY2FzZSAndWNzLTInOlxuICAgIGNhc2UgJ3V0ZjE2bGUnOlxuICAgIGNhc2UgJ3V0Zi0xNmxlJzpcbiAgICAgIHJldHVybiB0cnVlXG4gICAgZGVmYXVsdDpcbiAgICAgIHJldHVybiBmYWxzZVxuICB9XG59XG5cbkJ1ZmZlci5jb25jYXQgPSBmdW5jdGlvbiBjb25jYXQgKGxpc3QsIGxlbmd0aCkge1xuICBpZiAoIUFycmF5LmlzQXJyYXkobGlzdCkpIHtcbiAgICB0aHJvdyBuZXcgVHlwZUVycm9yKCdcImxpc3RcIiBhcmd1bWVudCBtdXN0IGJlIGFuIEFycmF5IG9mIEJ1ZmZlcnMnKVxuICB9XG5cbiAgaWYgKGxpc3QubGVuZ3RoID09PSAwKSB7XG4gICAgcmV0dXJuIEJ1ZmZlci5hbGxvYygwKVxuICB9XG5cbiAgbGV0IGlcbiAgaWYgKGxlbmd0aCA9PT0gdW5kZWZpbmVkKSB7XG4gICAgbGVuZ3RoID0gMFxuICAgIGZvciAoaSA9IDA7IGkgPCBsaXN0Lmxlbmd0aDsgKytpKSB7XG4gICAgICBsZW5ndGggKz0gbGlzdFtpXS5sZW5ndGhcbiAgICB9XG4gIH1cblxuICBjb25zdCBidWZmZXIgPSBCdWZmZXIuYWxsb2NVbnNhZmUobGVuZ3RoKVxuICBsZXQgcG9zID0gMFxuICBmb3IgKGkgPSAwOyBpIDwgbGlzdC5sZW5ndGg7ICsraSkge1xuICAgIGxldCBidWYgPSBsaXN0W2ldXG4gICAgaWYgKGlzSW5zdGFuY2UoYnVmLCBVaW50OEFycmF5KSkge1xuICAgICAgaWYgKHBvcyArIGJ1Zi5sZW5ndGggPiBidWZmZXIubGVuZ3RoKSB7XG4gICAgICAgIGlmICghQnVmZmVyLmlzQnVmZmVyKGJ1ZikpIGJ1ZiA9IEJ1ZmZlci5mcm9tKGJ1ZilcbiAgICAgICAgYnVmLmNvcHkoYnVmZmVyLCBwb3MpXG4gICAgICB9IGVsc2Uge1xuICAgICAgICBVaW50OEFycmF5LnByb3RvdHlwZS5zZXQuY2FsbChcbiAgICAgICAgICBidWZmZXIsXG4gICAgICAgICAgYnVmLFxuICAgICAgICAgIHBvc1xuICAgICAgICApXG4gICAgICB9XG4gICAgfSBlbHNlIGlmICghQnVmZmVyLmlzQnVmZmVyKGJ1ZikpIHtcbiAgICAgIHRocm93IG5ldyBUeXBlRXJyb3IoJ1wibGlzdFwiIGFyZ3VtZW50IG11c3QgYmUgYW4gQXJyYXkgb2YgQnVmZmVycycpXG4gICAgfSBlbHNlIHtcbiAgICAgIGJ1Zi5jb3B5KGJ1ZmZlciwgcG9zKVxuICAgIH1cbiAgICBwb3MgKz0gYnVmLmxlbmd0aFxuICB9XG4gIHJldHVybiBidWZmZXJcbn1cblxuZnVuY3Rpb24gYnl0ZUxlbmd0aCAoc3RyaW5nLCBlbmNvZGluZykge1xuICBpZiAoQnVmZmVyLmlzQnVmZmVyKHN0cmluZykpIHtcbiAgICByZXR1cm4gc3RyaW5nLmxlbmd0aFxuICB9XG4gIGlmIChBcnJheUJ1ZmZlci5pc1ZpZXcoc3RyaW5nKSB8fCBpc0luc3RhbmNlKHN0cmluZywgQXJyYXlCdWZmZXIpKSB7XG4gICAgcmV0dXJuIHN0cmluZy5ieXRlTGVuZ3RoXG4gIH1cbiAgaWYgKHR5cGVvZiBzdHJpbmcgIT09ICdzdHJpbmcnKSB7XG4gICAgdGhyb3cgbmV3IFR5cGVFcnJvcihcbiAgICAgICdUaGUgXCJzdHJpbmdcIiBhcmd1bWVudCBtdXN0IGJlIG9uZSBvZiB0eXBlIHN0cmluZywgQnVmZmVyLCBvciBBcnJheUJ1ZmZlci4gJyArXG4gICAgICAnUmVjZWl2ZWQgdHlwZSAnICsgdHlwZW9mIHN0cmluZ1xuICAgIClcbiAgfVxuXG4gIGNvbnN0IGxlbiA9IHN0cmluZy5sZW5ndGhcbiAgY29uc3QgbXVzdE1hdGNoID0gKGFyZ3VtZW50cy5sZW5ndGggPiAyICYmIGFyZ3VtZW50c1syXSA9PT0gdHJ1ZSlcbiAgaWYgKCFtdXN0TWF0Y2ggJiYgbGVuID09PSAwKSByZXR1cm4gMFxuXG4gIC8vIFVzZSBhIGZvciBsb29wIHRvIGF2b2lkIHJlY3Vyc2lvblxuICBsZXQgbG93ZXJlZENhc2UgPSBmYWxzZVxuICBmb3IgKDs7KSB7XG4gICAgc3dpdGNoIChlbmNvZGluZykge1xuICAgICAgY2FzZSAnYXNjaWknOlxuICAgICAgY2FzZSAnbGF0aW4xJzpcbiAgICAgIGNhc2UgJ2JpbmFyeSc6XG4gICAgICAgIHJldHVybiBsZW5cbiAgICAgIGNhc2UgJ3V0ZjgnOlxuICAgICAgY2FzZSAndXRmLTgnOlxuICAgICAgICByZXR1cm4gdXRmOFRvQnl0ZXMoc3RyaW5nKS5sZW5ndGhcbiAgICAgIGNhc2UgJ3VjczInOlxuICAgICAgY2FzZSAndWNzLTInOlxuICAgICAgY2FzZSAndXRmMTZsZSc6XG4gICAgICBjYXNlICd1dGYtMTZsZSc6XG4gICAgICAgIHJldHVybiBsZW4gKiAyXG4gICAgICBjYXNlICdoZXgnOlxuICAgICAgICByZXR1cm4gbGVuID4+PiAxXG4gICAgICBjYXNlICdiYXNlNjQnOlxuICAgICAgICByZXR1cm4gYmFzZTY0VG9CeXRlcyhzdHJpbmcpLmxlbmd0aFxuICAgICAgZGVmYXVsdDpcbiAgICAgICAgaWYgKGxvd2VyZWRDYXNlKSB7XG4gICAgICAgICAgcmV0dXJuIG11c3RNYXRjaCA/IC0xIDogdXRmOFRvQnl0ZXMoc3RyaW5nKS5sZW5ndGggLy8gYXNzdW1lIHV0ZjhcbiAgICAgICAgfVxuICAgICAgICBlbmNvZGluZyA9ICgnJyArIGVuY29kaW5nKS50b0xvd2VyQ2FzZSgpXG4gICAgICAgIGxvd2VyZWRDYXNlID0gdHJ1ZVxuICAgIH1cbiAgfVxufVxuQnVmZmVyLmJ5dGVMZW5ndGggPSBieXRlTGVuZ3RoXG5cbmZ1bmN0aW9uIHNsb3dUb1N0cmluZyAoZW5jb2RpbmcsIHN0YXJ0LCBlbmQpIHtcbiAgbGV0IGxvd2VyZWRDYXNlID0gZmFsc2VcblxuICAvLyBObyBuZWVkIHRvIHZlcmlmeSB0aGF0IFwidGhpcy5sZW5ndGggPD0gTUFYX1VJTlQzMlwiIHNpbmNlIGl0J3MgYSByZWFkLW9ubHlcbiAgLy8gcHJvcGVydHkgb2YgYSB0eXBlZCBhcnJheS5cblxuICAvLyBUaGlzIGJlaGF2ZXMgbmVpdGhlciBsaWtlIFN0cmluZyBub3IgVWludDhBcnJheSBpbiB0aGF0IHdlIHNldCBzdGFydC9lbmRcbiAgLy8gdG8gdGhlaXIgdXBwZXIvbG93ZXIgYm91bmRzIGlmIHRoZSB2YWx1ZSBwYXNzZWQgaXMgb3V0IG9mIHJhbmdlLlxuICAvLyB1bmRlZmluZWQgaXMgaGFuZGxlZCBzcGVjaWFsbHkgYXMgcGVyIEVDTUEtMjYyIDZ0aCBFZGl0aW9uLFxuICAvLyBTZWN0aW9uIDEzLjMuMy43IFJ1bnRpbWUgU2VtYW50aWNzOiBLZXllZEJpbmRpbmdJbml0aWFsaXphdGlvbi5cbiAgaWYgKHN0YXJ0ID09PSB1bmRlZmluZWQgfHwgc3RhcnQgPCAwKSB7XG4gICAgc3RhcnQgPSAwXG4gIH1cbiAgLy8gUmV0dXJuIGVhcmx5IGlmIHN0YXJ0ID4gdGhpcy5sZW5ndGguIERvbmUgaGVyZSB0byBwcmV2ZW50IHBvdGVudGlhbCB1aW50MzJcbiAgLy8gY29lcmNpb24gZmFpbCBiZWxvdy5cbiAgaWYgKHN0YXJ0ID4gdGhpcy5sZW5ndGgpIHtcbiAgICByZXR1cm4gJydcbiAgfVxuXG4gIGlmIChlbmQgPT09IHVuZGVmaW5lZCB8fCBlbmQgPiB0aGlzLmxlbmd0aCkge1xuICAgIGVuZCA9IHRoaXMubGVuZ3RoXG4gIH1cblxuICBpZiAoZW5kIDw9IDApIHtcbiAgICByZXR1cm4gJydcbiAgfVxuXG4gIC8vIEZvcmNlIGNvZXJjaW9uIHRvIHVpbnQzMi4gVGhpcyB3aWxsIGFsc28gY29lcmNlIGZhbHNleS9OYU4gdmFsdWVzIHRvIDAuXG4gIGVuZCA+Pj49IDBcbiAgc3RhcnQgPj4+PSAwXG5cbiAgaWYgKGVuZCA8PSBzdGFydCkge1xuICAgIHJldHVybiAnJ1xuICB9XG5cbiAgaWYgKCFlbmNvZGluZykgZW5jb2RpbmcgPSAndXRmOCdcblxuICB3aGlsZSAodHJ1ZSkge1xuICAgIHN3aXRjaCAoZW5jb2RpbmcpIHtcbiAgICAgIGNhc2UgJ2hleCc6XG4gICAgICAgIHJldHVybiBoZXhTbGljZSh0aGlzLCBzdGFydCwgZW5kKVxuXG4gICAgICBjYXNlICd1dGY4JzpcbiAgICAgIGNhc2UgJ3V0Zi04JzpcbiAgICAgICAgcmV0dXJuIHV0ZjhTbGljZSh0aGlzLCBzdGFydCwgZW5kKVxuXG4gICAgICBjYXNlICdhc2NpaSc6XG4gICAgICAgIHJldHVybiBhc2NpaVNsaWNlKHRoaXMsIHN0YXJ0LCBlbmQpXG5cbiAgICAgIGNhc2UgJ2xhdGluMSc6XG4gICAgICBjYXNlICdiaW5hcnknOlxuICAgICAgICByZXR1cm4gbGF0aW4xU2xpY2UodGhpcywgc3RhcnQsIGVuZClcblxuICAgICAgY2FzZSAnYmFzZTY0JzpcbiAgICAgICAgcmV0dXJuIGJhc2U2NFNsaWNlKHRoaXMsIHN0YXJ0LCBlbmQpXG5cbiAgICAgIGNhc2UgJ3VjczInOlxuICAgICAgY2FzZSAndWNzLTInOlxuICAgICAgY2FzZSAndXRmMTZsZSc6XG4gICAgICBjYXNlICd1dGYtMTZsZSc6XG4gICAgICAgIHJldHVybiB1dGYxNmxlU2xpY2UodGhpcywgc3RhcnQsIGVuZClcblxuICAgICAgZGVmYXVsdDpcbiAgICAgICAgaWYgKGxvd2VyZWRDYXNlKSB0aHJvdyBuZXcgVHlwZUVycm9yKCdVbmtub3duIGVuY29kaW5nOiAnICsgZW5jb2RpbmcpXG4gICAgICAgIGVuY29kaW5nID0gKGVuY29kaW5nICsgJycpLnRvTG93ZXJDYXNlKClcbiAgICAgICAgbG93ZXJlZENhc2UgPSB0cnVlXG4gICAgfVxuICB9XG59XG5cbi8vIFRoaXMgcHJvcGVydHkgaXMgdXNlZCBieSBgQnVmZmVyLmlzQnVmZmVyYCAoYW5kIHRoZSBgaXMtYnVmZmVyYCBucG0gcGFja2FnZSlcbi8vIHRvIGRldGVjdCBhIEJ1ZmZlciBpbnN0YW5jZS4gSXQncyBub3QgcG9zc2libGUgdG8gdXNlIGBpbnN0YW5jZW9mIEJ1ZmZlcmBcbi8vIHJlbGlhYmx5IGluIGEgYnJvd3NlcmlmeSBjb250ZXh0IGJlY2F1c2UgdGhlcmUgY291bGQgYmUgbXVsdGlwbGUgZGlmZmVyZW50XG4vLyBjb3BpZXMgb2YgdGhlICdidWZmZXInIHBhY2thZ2UgaW4gdXNlLiBUaGlzIG1ldGhvZCB3b3JrcyBldmVuIGZvciBCdWZmZXJcbi8vIGluc3RhbmNlcyB0aGF0IHdlcmUgY3JlYXRlZCBmcm9tIGFub3RoZXIgY29weSBvZiB0aGUgYGJ1ZmZlcmAgcGFja2FnZS5cbi8vIFNlZTogaHR0cHM6Ly9naXRodWIuY29tL2Zlcm9zcy9idWZmZXIvaXNzdWVzLzE1NFxuQnVmZmVyLnByb3RvdHlwZS5faXNCdWZmZXIgPSB0cnVlXG5cbmZ1bmN0aW9uIHN3YXAgKGIsIG4sIG0pIHtcbiAgY29uc3QgaSA9IGJbbl1cbiAgYltuXSA9IGJbbV1cbiAgYlttXSA9IGlcbn1cblxuQnVmZmVyLnByb3RvdHlwZS5zd2FwMTYgPSBmdW5jdGlvbiBzd2FwMTYgKCkge1xuICBjb25zdCBsZW4gPSB0aGlzLmxlbmd0aFxuICBpZiAobGVuICUgMiAhPT0gMCkge1xuICAgIHRocm93IG5ldyBSYW5nZUVycm9yKCdCdWZmZXIgc2l6ZSBtdXN0IGJlIGEgbXVsdGlwbGUgb2YgMTYtYml0cycpXG4gIH1cbiAgZm9yIChsZXQgaSA9IDA7IGkgPCBsZW47IGkgKz0gMikge1xuICAgIHN3YXAodGhpcywgaSwgaSArIDEpXG4gIH1cbiAgcmV0dXJuIHRoaXNcbn1cblxuQnVmZmVyLnByb3RvdHlwZS5zd2FwMzIgPSBmdW5jdGlvbiBzd2FwMzIgKCkge1xuICBjb25zdCBsZW4gPSB0aGlzLmxlbmd0aFxuICBpZiAobGVuICUgNCAhPT0gMCkge1xuICAgIHRocm93IG5ldyBSYW5nZUVycm9yKCdCdWZmZXIgc2l6ZSBtdXN0IGJlIGEgbXVsdGlwbGUgb2YgMzItYml0cycpXG4gIH1cbiAgZm9yIChsZXQgaSA9IDA7IGkgPCBsZW47IGkgKz0gNCkge1xuICAgIHN3YXAodGhpcywgaSwgaSArIDMpXG4gICAgc3dhcCh0aGlzLCBpICsgMSwgaSArIDIpXG4gIH1cbiAgcmV0dXJuIHRoaXNcbn1cblxuQnVmZmVyLnByb3RvdHlwZS5zd2FwNjQgPSBmdW5jdGlvbiBzd2FwNjQgKCkge1xuICBjb25zdCBsZW4gPSB0aGlzLmxlbmd0aFxuICBpZiAobGVuICUgOCAhPT0gMCkge1xuICAgIHRocm93IG5ldyBSYW5nZUVycm9yKCdCdWZmZXIgc2l6ZSBtdXN0IGJlIGEgbXVsdGlwbGUgb2YgNjQtYml0cycpXG4gIH1cbiAgZm9yIChsZXQgaSA9IDA7IGkgPCBsZW47IGkgKz0gOCkge1xuICAgIHN3YXAodGhpcywgaSwgaSArIDcpXG4gICAgc3dhcCh0aGlzLCBpICsgMSwgaSArIDYpXG4gICAgc3dhcCh0aGlzLCBpICsgMiwgaSArIDUpXG4gICAgc3dhcCh0aGlzLCBpICsgMywgaSArIDQpXG4gIH1cbiAgcmV0dXJuIHRoaXNcbn1cblxuQnVmZmVyLnByb3RvdHlwZS50b1N0cmluZyA9IGZ1bmN0aW9uIHRvU3RyaW5nICgpIHtcbiAgY29uc3QgbGVuZ3RoID0gdGhpcy5sZW5ndGhcbiAgaWYgKGxlbmd0aCA9PT0gMCkgcmV0dXJuICcnXG4gIGlmIChhcmd1bWVudHMubGVuZ3RoID09PSAwKSByZXR1cm4gdXRmOFNsaWNlKHRoaXMsIDAsIGxlbmd0aClcbiAgcmV0dXJuIHNsb3dUb1N0cmluZy5hcHBseSh0aGlzLCBhcmd1bWVudHMpXG59XG5cbkJ1ZmZlci5wcm90b3R5cGUudG9Mb2NhbGVTdHJpbmcgPSBCdWZmZXIucHJvdG90eXBlLnRvU3RyaW5nXG5cbkJ1ZmZlci5wcm90b3R5cGUuZXF1YWxzID0gZnVuY3Rpb24gZXF1YWxzIChiKSB7XG4gIGlmICghQnVmZmVyLmlzQnVmZmVyKGIpKSB0aHJvdyBuZXcgVHlwZUVycm9yKCdBcmd1bWVudCBtdXN0IGJlIGEgQnVmZmVyJylcbiAgaWYgKHRoaXMgPT09IGIpIHJldHVybiB0cnVlXG4gIHJldHVybiBCdWZmZXIuY29tcGFyZSh0aGlzLCBiKSA9PT0gMFxufVxuXG5CdWZmZXIucHJvdG90eXBlLmluc3BlY3QgPSBmdW5jdGlvbiBpbnNwZWN0ICgpIHtcbiAgbGV0IHN0ciA9ICcnXG4gIGNvbnN0IG1heCA9IGV4cG9ydHMuSU5TUEVDVF9NQVhfQllURVNcbiAgc3RyID0gdGhpcy50b1N0cmluZygnaGV4JywgMCwgbWF4KS5yZXBsYWNlKC8oLnsyfSkvZywgJyQxICcpLnRyaW0oKVxuICBpZiAodGhpcy5sZW5ndGggPiBtYXgpIHN0ciArPSAnIC4uLiAnXG4gIHJldHVybiAnPEJ1ZmZlciAnICsgc3RyICsgJz4nXG59XG5pZiAoY3VzdG9tSW5zcGVjdFN5bWJvbCkge1xuICBCdWZmZXIucHJvdG90eXBlW2N1c3RvbUluc3BlY3RTeW1ib2xdID0gQnVmZmVyLnByb3RvdHlwZS5pbnNwZWN0XG59XG5cbkJ1ZmZlci5wcm90b3R5cGUuY29tcGFyZSA9IGZ1bmN0aW9uIGNvbXBhcmUgKHRhcmdldCwgc3RhcnQsIGVuZCwgdGhpc1N0YXJ0LCB0aGlzRW5kKSB7XG4gIGlmIChpc0luc3RhbmNlKHRhcmdldCwgVWludDhBcnJheSkpIHtcbiAgICB0YXJnZXQgPSBCdWZmZXIuZnJvbSh0YXJnZXQsIHRhcmdldC5vZmZzZXQsIHRhcmdldC5ieXRlTGVuZ3RoKVxuICB9XG4gIGlmICghQnVmZmVyLmlzQnVmZmVyKHRhcmdldCkpIHtcbiAgICB0aHJvdyBuZXcgVHlwZUVycm9yKFxuICAgICAgJ1RoZSBcInRhcmdldFwiIGFyZ3VtZW50IG11c3QgYmUgb25lIG9mIHR5cGUgQnVmZmVyIG9yIFVpbnQ4QXJyYXkuICcgK1xuICAgICAgJ1JlY2VpdmVkIHR5cGUgJyArICh0eXBlb2YgdGFyZ2V0KVxuICAgIClcbiAgfVxuXG4gIGlmIChzdGFydCA9PT0gdW5kZWZpbmVkKSB7XG4gICAgc3RhcnQgPSAwXG4gIH1cbiAgaWYgKGVuZCA9PT0gdW5kZWZpbmVkKSB7XG4gICAgZW5kID0gdGFyZ2V0ID8gdGFyZ2V0Lmxlbmd0aCA6IDBcbiAgfVxuICBpZiAodGhpc1N0YXJ0ID09PSB1bmRlZmluZWQpIHtcbiAgICB0aGlzU3RhcnQgPSAwXG4gIH1cbiAgaWYgKHRoaXNFbmQgPT09IHVuZGVmaW5lZCkge1xuICAgIHRoaXNFbmQgPSB0aGlzLmxlbmd0aFxuICB9XG5cbiAgaWYgKHN0YXJ0IDwgMCB8fCBlbmQgPiB0YXJnZXQubGVuZ3RoIHx8IHRoaXNTdGFydCA8IDAgfHwgdGhpc0VuZCA+IHRoaXMubGVuZ3RoKSB7XG4gICAgdGhyb3cgbmV3IFJhbmdlRXJyb3IoJ291dCBvZiByYW5nZSBpbmRleCcpXG4gIH1cblxuICBpZiAodGhpc1N0YXJ0ID49IHRoaXNFbmQgJiYgc3RhcnQgPj0gZW5kKSB7XG4gICAgcmV0dXJuIDBcbiAgfVxuICBpZiAodGhpc1N0YXJ0ID49IHRoaXNFbmQpIHtcbiAgICByZXR1cm4gLTFcbiAgfVxuICBpZiAoc3RhcnQgPj0gZW5kKSB7XG4gICAgcmV0dXJuIDFcbiAgfVxuXG4gIHN0YXJ0ID4+Pj0gMFxuICBlbmQgPj4+PSAwXG4gIHRoaXNTdGFydCA+Pj49IDBcbiAgdGhpc0VuZCA+Pj49IDBcblxuICBpZiAodGhpcyA9PT0gdGFyZ2V0KSByZXR1cm4gMFxuXG4gIGxldCB4ID0gdGhpc0VuZCAtIHRoaXNTdGFydFxuICBsZXQgeSA9IGVuZCAtIHN0YXJ0XG4gIGNvbnN0IGxlbiA9IE1hdGgubWluKHgsIHkpXG5cbiAgY29uc3QgdGhpc0NvcHkgPSB0aGlzLnNsaWNlKHRoaXNTdGFydCwgdGhpc0VuZClcbiAgY29uc3QgdGFyZ2V0Q29weSA9IHRhcmdldC5zbGljZShzdGFydCwgZW5kKVxuXG4gIGZvciAobGV0IGkgPSAwOyBpIDwgbGVuOyArK2kpIHtcbiAgICBpZiAodGhpc0NvcHlbaV0gIT09IHRhcmdldENvcHlbaV0pIHtcbiAgICAgIHggPSB0aGlzQ29weVtpXVxuICAgICAgeSA9IHRhcmdldENvcHlbaV1cbiAgICAgIGJyZWFrXG4gICAgfVxuICB9XG5cbiAgaWYgKHggPCB5KSByZXR1cm4gLTFcbiAgaWYgKHkgPCB4KSByZXR1cm4gMVxuICByZXR1cm4gMFxufVxuXG4vLyBGaW5kcyBlaXRoZXIgdGhlIGZpcnN0IGluZGV4IG9mIGB2YWxgIGluIGBidWZmZXJgIGF0IG9mZnNldCA+PSBgYnl0ZU9mZnNldGAsXG4vLyBPUiB0aGUgbGFzdCBpbmRleCBvZiBgdmFsYCBpbiBgYnVmZmVyYCBhdCBvZmZzZXQgPD0gYGJ5dGVPZmZzZXRgLlxuLy9cbi8vIEFyZ3VtZW50czpcbi8vIC0gYnVmZmVyIC0gYSBCdWZmZXIgdG8gc2VhcmNoXG4vLyAtIHZhbCAtIGEgc3RyaW5nLCBCdWZmZXIsIG9yIG51bWJlclxuLy8gLSBieXRlT2Zmc2V0IC0gYW4gaW5kZXggaW50byBgYnVmZmVyYDsgd2lsbCBiZSBjbGFtcGVkIHRvIGFuIGludDMyXG4vLyAtIGVuY29kaW5nIC0gYW4gb3B0aW9uYWwgZW5jb2RpbmcsIHJlbGV2YW50IGlzIHZhbCBpcyBhIHN0cmluZ1xuLy8gLSBkaXIgLSB0cnVlIGZvciBpbmRleE9mLCBmYWxzZSBmb3IgbGFzdEluZGV4T2ZcbmZ1bmN0aW9uIGJpZGlyZWN0aW9uYWxJbmRleE9mIChidWZmZXIsIHZhbCwgYnl0ZU9mZnNldCwgZW5jb2RpbmcsIGRpcikge1xuICAvLyBFbXB0eSBidWZmZXIgbWVhbnMgbm8gbWF0Y2hcbiAgaWYgKGJ1ZmZlci5sZW5ndGggPT09IDApIHJldHVybiAtMVxuXG4gIC8vIE5vcm1hbGl6ZSBieXRlT2Zmc2V0XG4gIGlmICh0eXBlb2YgYnl0ZU9mZnNldCA9PT0gJ3N0cmluZycpIHtcbiAgICBlbmNvZGluZyA9IGJ5dGVPZmZzZXRcbiAgICBieXRlT2Zmc2V0ID0gMFxuICB9IGVsc2UgaWYgKGJ5dGVPZmZzZXQgPiAweDdmZmZmZmZmKSB7XG4gICAgYnl0ZU9mZnNldCA9IDB4N2ZmZmZmZmZcbiAgfSBlbHNlIGlmIChieXRlT2Zmc2V0IDwgLTB4ODAwMDAwMDApIHtcbiAgICBieXRlT2Zmc2V0ID0gLTB4ODAwMDAwMDBcbiAgfVxuICBieXRlT2Zmc2V0ID0gK2J5dGVPZmZzZXQgLy8gQ29lcmNlIHRvIE51bWJlci5cbiAgaWYgKG51bWJlcklzTmFOKGJ5dGVPZmZzZXQpKSB7XG4gICAgLy8gYnl0ZU9mZnNldDogaXQgaXQncyB1bmRlZmluZWQsIG51bGwsIE5hTiwgXCJmb29cIiwgZXRjLCBzZWFyY2ggd2hvbGUgYnVmZmVyXG4gICAgYnl0ZU9mZnNldCA9IGRpciA/IDAgOiAoYnVmZmVyLmxlbmd0aCAtIDEpXG4gIH1cblxuICAvLyBOb3JtYWxpemUgYnl0ZU9mZnNldDogbmVnYXRpdmUgb2Zmc2V0cyBzdGFydCBmcm9tIHRoZSBlbmQgb2YgdGhlIGJ1ZmZlclxuICBpZiAoYnl0ZU9mZnNldCA8IDApIGJ5dGVPZmZzZXQgPSBidWZmZXIubGVuZ3RoICsgYnl0ZU9mZnNldFxuICBpZiAoYnl0ZU9mZnNldCA+PSBidWZmZXIubGVuZ3RoKSB7XG4gICAgaWYgKGRpcikgcmV0dXJuIC0xXG4gICAgZWxzZSBieXRlT2Zmc2V0ID0gYnVmZmVyLmxlbmd0aCAtIDFcbiAgfSBlbHNlIGlmIChieXRlT2Zmc2V0IDwgMCkge1xuICAgIGlmIChkaXIpIGJ5dGVPZmZzZXQgPSAwXG4gICAgZWxzZSByZXR1cm4gLTFcbiAgfVxuXG4gIC8vIE5vcm1hbGl6ZSB2YWxcbiAgaWYgKHR5cGVvZiB2YWwgPT09ICdzdHJpbmcnKSB7XG4gICAgdmFsID0gQnVmZmVyLmZyb20odmFsLCBlbmNvZGluZylcbiAgfVxuXG4gIC8vIEZpbmFsbHksIHNlYXJjaCBlaXRoZXIgaW5kZXhPZiAoaWYgZGlyIGlzIHRydWUpIG9yIGxhc3RJbmRleE9mXG4gIGlmIChCdWZmZXIuaXNCdWZmZXIodmFsKSkge1xuICAgIC8vIFNwZWNpYWwgY2FzZTogbG9va2luZyBmb3IgZW1wdHkgc3RyaW5nL2J1ZmZlciBhbHdheXMgZmFpbHNcbiAgICBpZiAodmFsLmxlbmd0aCA9PT0gMCkge1xuICAgICAgcmV0dXJuIC0xXG4gICAgfVxuICAgIHJldHVybiBhcnJheUluZGV4T2YoYnVmZmVyLCB2YWwsIGJ5dGVPZmZzZXQsIGVuY29kaW5nLCBkaXIpXG4gIH0gZWxzZSBpZiAodHlwZW9mIHZhbCA9PT0gJ251bWJlcicpIHtcbiAgICB2YWwgPSB2YWwgJiAweEZGIC8vIFNlYXJjaCBmb3IgYSBieXRlIHZhbHVlIFswLTI1NV1cbiAgICBpZiAodHlwZW9mIFVpbnQ4QXJyYXkucHJvdG90eXBlLmluZGV4T2YgPT09ICdmdW5jdGlvbicpIHtcbiAgICAgIGlmIChkaXIpIHtcbiAgICAgICAgcmV0dXJuIFVpbnQ4QXJyYXkucHJvdG90eXBlLmluZGV4T2YuY2FsbChidWZmZXIsIHZhbCwgYnl0ZU9mZnNldClcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIHJldHVybiBVaW50OEFycmF5LnByb3RvdHlwZS5sYXN0SW5kZXhPZi5jYWxsKGJ1ZmZlciwgdmFsLCBieXRlT2Zmc2V0KVxuICAgICAgfVxuICAgIH1cbiAgICByZXR1cm4gYXJyYXlJbmRleE9mKGJ1ZmZlciwgW3ZhbF0sIGJ5dGVPZmZzZXQsIGVuY29kaW5nLCBkaXIpXG4gIH1cblxuICB0aHJvdyBuZXcgVHlwZUVycm9yKCd2YWwgbXVzdCBiZSBzdHJpbmcsIG51bWJlciBvciBCdWZmZXInKVxufVxuXG5mdW5jdGlvbiBhcnJheUluZGV4T2YgKGFyciwgdmFsLCBieXRlT2Zmc2V0LCBlbmNvZGluZywgZGlyKSB7XG4gIGxldCBpbmRleFNpemUgPSAxXG4gIGxldCBhcnJMZW5ndGggPSBhcnIubGVuZ3RoXG4gIGxldCB2YWxMZW5ndGggPSB2YWwubGVuZ3RoXG5cbiAgaWYgKGVuY29kaW5nICE9PSB1bmRlZmluZWQpIHtcbiAgICBlbmNvZGluZyA9IFN0cmluZyhlbmNvZGluZykudG9Mb3dlckNhc2UoKVxuICAgIGlmIChlbmNvZGluZyA9PT0gJ3VjczInIHx8IGVuY29kaW5nID09PSAndWNzLTInIHx8XG4gICAgICAgIGVuY29kaW5nID09PSAndXRmMTZsZScgfHwgZW5jb2RpbmcgPT09ICd1dGYtMTZsZScpIHtcbiAgICAgIGlmIChhcnIubGVuZ3RoIDwgMiB8fCB2YWwubGVuZ3RoIDwgMikge1xuICAgICAgICByZXR1cm4gLTFcbiAgICAgIH1cbiAgICAgIGluZGV4U2l6ZSA9IDJcbiAgICAgIGFyckxlbmd0aCAvPSAyXG4gICAgICB2YWxMZW5ndGggLz0gMlxuICAgICAgYnl0ZU9mZnNldCAvPSAyXG4gICAgfVxuICB9XG5cbiAgZnVuY3Rpb24gcmVhZCAoYnVmLCBpKSB7XG4gICAgaWYgKGluZGV4U2l6ZSA9PT0gMSkge1xuICAgICAgcmV0dXJuIGJ1ZltpXVxuICAgIH0gZWxzZSB7XG4gICAgICByZXR1cm4gYnVmLnJlYWRVSW50MTZCRShpICogaW5kZXhTaXplKVxuICAgIH1cbiAgfVxuXG4gIGxldCBpXG4gIGlmIChkaXIpIHtcbiAgICBsZXQgZm91bmRJbmRleCA9IC0xXG4gICAgZm9yIChpID0gYnl0ZU9mZnNldDsgaSA8IGFyckxlbmd0aDsgaSsrKSB7XG4gICAgICBpZiAocmVhZChhcnIsIGkpID09PSByZWFkKHZhbCwgZm91bmRJbmRleCA9PT0gLTEgPyAwIDogaSAtIGZvdW5kSW5kZXgpKSB7XG4gICAgICAgIGlmIChmb3VuZEluZGV4ID09PSAtMSkgZm91bmRJbmRleCA9IGlcbiAgICAgICAgaWYgKGkgLSBmb3VuZEluZGV4ICsgMSA9PT0gdmFsTGVuZ3RoKSByZXR1cm4gZm91bmRJbmRleCAqIGluZGV4U2l6ZVxuICAgICAgfSBlbHNlIHtcbiAgICAgICAgaWYgKGZvdW5kSW5kZXggIT09IC0xKSBpIC09IGkgLSBmb3VuZEluZGV4XG4gICAgICAgIGZvdW5kSW5kZXggPSAtMVxuICAgICAgfVxuICAgIH1cbiAgfSBlbHNlIHtcbiAgICBpZiAoYnl0ZU9mZnNldCArIHZhbExlbmd0aCA+IGFyckxlbmd0aCkgYnl0ZU9mZnNldCA9IGFyckxlbmd0aCAtIHZhbExlbmd0aFxuICAgIGZvciAoaSA9IGJ5dGVPZmZzZXQ7IGkgPj0gMDsgaS0tKSB7XG4gICAgICBsZXQgZm91bmQgPSB0cnVlXG4gICAgICBmb3IgKGxldCBqID0gMDsgaiA8IHZhbExlbmd0aDsgaisrKSB7XG4gICAgICAgIGlmIChyZWFkKGFyciwgaSArIGopICE9PSByZWFkKHZhbCwgaikpIHtcbiAgICAgICAgICBmb3VuZCA9IGZhbHNlXG4gICAgICAgICAgYnJlYWtcbiAgICAgICAgfVxuICAgICAgfVxuICAgICAgaWYgKGZvdW5kKSByZXR1cm4gaVxuICAgIH1cbiAgfVxuXG4gIHJldHVybiAtMVxufVxuXG5CdWZmZXIucHJvdG90eXBlLmluY2x1ZGVzID0gZnVuY3Rpb24gaW5jbHVkZXMgKHZhbCwgYnl0ZU9mZnNldCwgZW5jb2RpbmcpIHtcbiAgcmV0dXJuIHRoaXMuaW5kZXhPZih2YWwsIGJ5dGVPZmZzZXQsIGVuY29kaW5nKSAhPT0gLTFcbn1cblxuQnVmZmVyLnByb3RvdHlwZS5pbmRleE9mID0gZnVuY3Rpb24gaW5kZXhPZiAodmFsLCBieXRlT2Zmc2V0LCBlbmNvZGluZykge1xuICByZXR1cm4gYmlkaXJlY3Rpb25hbEluZGV4T2YodGhpcywgdmFsLCBieXRlT2Zmc2V0LCBlbmNvZGluZywgdHJ1ZSlcbn1cblxuQnVmZmVyLnByb3RvdHlwZS5sYXN0SW5kZXhPZiA9IGZ1bmN0aW9uIGxhc3RJbmRleE9mICh2YWwsIGJ5dGVPZmZzZXQsIGVuY29kaW5nKSB7XG4gIHJldHVybiBiaWRpcmVjdGlvbmFsSW5kZXhPZih0aGlzLCB2YWwsIGJ5dGVPZmZzZXQsIGVuY29kaW5nLCBmYWxzZSlcbn1cblxuZnVuY3Rpb24gaGV4V3JpdGUgKGJ1Ziwgc3RyaW5nLCBvZmZzZXQsIGxlbmd0aCkge1xuICBvZmZzZXQgPSBOdW1iZXIob2Zmc2V0KSB8fCAwXG4gIGNvbnN0IHJlbWFpbmluZyA9IGJ1Zi5sZW5ndGggLSBvZmZzZXRcbiAgaWYgKCFsZW5ndGgpIHtcbiAgICBsZW5ndGggPSByZW1haW5pbmdcbiAgfSBlbHNlIHtcbiAgICBsZW5ndGggPSBOdW1iZXIobGVuZ3RoKVxuICAgIGlmIChsZW5ndGggPiByZW1haW5pbmcpIHtcbiAgICAgIGxlbmd0aCA9IHJlbWFpbmluZ1xuICAgIH1cbiAgfVxuXG4gIGNvbnN0IHN0ckxlbiA9IHN0cmluZy5sZW5ndGhcblxuICBpZiAobGVuZ3RoID4gc3RyTGVuIC8gMikge1xuICAgIGxlbmd0aCA9IHN0ckxlbiAvIDJcbiAgfVxuICBsZXQgaVxuICBmb3IgKGkgPSAwOyBpIDwgbGVuZ3RoOyArK2kpIHtcbiAgICBjb25zdCBwYXJzZWQgPSBwYXJzZUludChzdHJpbmcuc3Vic3RyKGkgKiAyLCAyKSwgMTYpXG4gICAgaWYgKG51bWJlcklzTmFOKHBhcnNlZCkpIHJldHVybiBpXG4gICAgYnVmW29mZnNldCArIGldID0gcGFyc2VkXG4gIH1cbiAgcmV0dXJuIGlcbn1cblxuZnVuY3Rpb24gdXRmOFdyaXRlIChidWYsIHN0cmluZywgb2Zmc2V0LCBsZW5ndGgpIHtcbiAgcmV0dXJuIGJsaXRCdWZmZXIodXRmOFRvQnl0ZXMoc3RyaW5nLCBidWYubGVuZ3RoIC0gb2Zmc2V0KSwgYnVmLCBvZmZzZXQsIGxlbmd0aClcbn1cblxuZnVuY3Rpb24gYXNjaWlXcml0ZSAoYnVmLCBzdHJpbmcsIG9mZnNldCwgbGVuZ3RoKSB7XG4gIHJldHVybiBibGl0QnVmZmVyKGFzY2lpVG9CeXRlcyhzdHJpbmcpLCBidWYsIG9mZnNldCwgbGVuZ3RoKVxufVxuXG5mdW5jdGlvbiBiYXNlNjRXcml0ZSAoYnVmLCBzdHJpbmcsIG9mZnNldCwgbGVuZ3RoKSB7XG4gIHJldHVybiBibGl0QnVmZmVyKGJhc2U2NFRvQnl0ZXMoc3RyaW5nKSwgYnVmLCBvZmZzZXQsIGxlbmd0aClcbn1cblxuZnVuY3Rpb24gdWNzMldyaXRlIChidWYsIHN0cmluZywgb2Zmc2V0LCBsZW5ndGgpIHtcbiAgcmV0dXJuIGJsaXRCdWZmZXIodXRmMTZsZVRvQnl0ZXMoc3RyaW5nLCBidWYubGVuZ3RoIC0gb2Zmc2V0KSwgYnVmLCBvZmZzZXQsIGxlbmd0aClcbn1cblxuQnVmZmVyLnByb3RvdHlwZS53cml0ZSA9IGZ1bmN0aW9uIHdyaXRlIChzdHJpbmcsIG9mZnNldCwgbGVuZ3RoLCBlbmNvZGluZykge1xuICAvLyBCdWZmZXIjd3JpdGUoc3RyaW5nKVxuICBpZiAob2Zmc2V0ID09PSB1bmRlZmluZWQpIHtcbiAgICBlbmNvZGluZyA9ICd1dGY4J1xuICAgIGxlbmd0aCA9IHRoaXMubGVuZ3RoXG4gICAgb2Zmc2V0ID0gMFxuICAvLyBCdWZmZXIjd3JpdGUoc3RyaW5nLCBlbmNvZGluZylcbiAgfSBlbHNlIGlmIChsZW5ndGggPT09IHVuZGVmaW5lZCAmJiB0eXBlb2Ygb2Zmc2V0ID09PSAnc3RyaW5nJykge1xuICAgIGVuY29kaW5nID0gb2Zmc2V0XG4gICAgbGVuZ3RoID0gdGhpcy5sZW5ndGhcbiAgICBvZmZzZXQgPSAwXG4gIC8vIEJ1ZmZlciN3cml0ZShzdHJpbmcsIG9mZnNldFssIGxlbmd0aF1bLCBlbmNvZGluZ10pXG4gIH0gZWxzZSBpZiAoaXNGaW5pdGUob2Zmc2V0KSkge1xuICAgIG9mZnNldCA9IG9mZnNldCA+Pj4gMFxuICAgIGlmIChpc0Zpbml0ZShsZW5ndGgpKSB7XG4gICAgICBsZW5ndGggPSBsZW5ndGggPj4+IDBcbiAgICAgIGlmIChlbmNvZGluZyA9PT0gdW5kZWZpbmVkKSBlbmNvZGluZyA9ICd1dGY4J1xuICAgIH0gZWxzZSB7XG4gICAgICBlbmNvZGluZyA9IGxlbmd0aFxuICAgICAgbGVuZ3RoID0gdW5kZWZpbmVkXG4gICAgfVxuICB9IGVsc2Uge1xuICAgIHRocm93IG5ldyBFcnJvcihcbiAgICAgICdCdWZmZXIud3JpdGUoc3RyaW5nLCBlbmNvZGluZywgb2Zmc2V0WywgbGVuZ3RoXSkgaXMgbm8gbG9uZ2VyIHN1cHBvcnRlZCdcbiAgICApXG4gIH1cblxuICBjb25zdCByZW1haW5pbmcgPSB0aGlzLmxlbmd0aCAtIG9mZnNldFxuICBpZiAobGVuZ3RoID09PSB1bmRlZmluZWQgfHwgbGVuZ3RoID4gcmVtYWluaW5nKSBsZW5ndGggPSByZW1haW5pbmdcblxuICBpZiAoKHN0cmluZy5sZW5ndGggPiAwICYmIChsZW5ndGggPCAwIHx8IG9mZnNldCA8IDApKSB8fCBvZmZzZXQgPiB0aGlzLmxlbmd0aCkge1xuICAgIHRocm93IG5ldyBSYW5nZUVycm9yKCdBdHRlbXB0IHRvIHdyaXRlIG91dHNpZGUgYnVmZmVyIGJvdW5kcycpXG4gIH1cblxuICBpZiAoIWVuY29kaW5nKSBlbmNvZGluZyA9ICd1dGY4J1xuXG4gIGxldCBsb3dlcmVkQ2FzZSA9IGZhbHNlXG4gIGZvciAoOzspIHtcbiAgICBzd2l0Y2ggKGVuY29kaW5nKSB7XG4gICAgICBjYXNlICdoZXgnOlxuICAgICAgICByZXR1cm4gaGV4V3JpdGUodGhpcywgc3RyaW5nLCBvZmZzZXQsIGxlbmd0aClcblxuICAgICAgY2FzZSAndXRmOCc6XG4gICAgICBjYXNlICd1dGYtOCc6XG4gICAgICAgIHJldHVybiB1dGY4V3JpdGUodGhpcywgc3RyaW5nLCBvZmZzZXQsIGxlbmd0aClcblxuICAgICAgY2FzZSAnYXNjaWknOlxuICAgICAgY2FzZSAnbGF0aW4xJzpcbiAgICAgIGNhc2UgJ2JpbmFyeSc6XG4gICAgICAgIHJldHVybiBhc2NpaVdyaXRlKHRoaXMsIHN0cmluZywgb2Zmc2V0LCBsZW5ndGgpXG5cbiAgICAgIGNhc2UgJ2Jhc2U2NCc6XG4gICAgICAgIC8vIFdhcm5pbmc6IG1heExlbmd0aCBub3QgdGFrZW4gaW50byBhY2NvdW50IGluIGJhc2U2NFdyaXRlXG4gICAgICAgIHJldHVybiBiYXNlNjRXcml0ZSh0aGlzLCBzdHJpbmcsIG9mZnNldCwgbGVuZ3RoKVxuXG4gICAgICBjYXNlICd1Y3MyJzpcbiAgICAgIGNhc2UgJ3Vjcy0yJzpcbiAgICAgIGNhc2UgJ3V0ZjE2bGUnOlxuICAgICAgY2FzZSAndXRmLTE2bGUnOlxuICAgICAgICByZXR1cm4gdWNzMldyaXRlKHRoaXMsIHN0cmluZywgb2Zmc2V0LCBsZW5ndGgpXG5cbiAgICAgIGRlZmF1bHQ6XG4gICAgICAgIGlmIChsb3dlcmVkQ2FzZSkgdGhyb3cgbmV3IFR5cGVFcnJvcignVW5rbm93biBlbmNvZGluZzogJyArIGVuY29kaW5nKVxuICAgICAgICBlbmNvZGluZyA9ICgnJyArIGVuY29kaW5nKS50b0xvd2VyQ2FzZSgpXG4gICAgICAgIGxvd2VyZWRDYXNlID0gdHJ1ZVxuICAgIH1cbiAgfVxufVxuXG5CdWZmZXIucHJvdG90eXBlLnRvSlNPTiA9IGZ1bmN0aW9uIHRvSlNPTiAoKSB7XG4gIHJldHVybiB7XG4gICAgdHlwZTogJ0J1ZmZlcicsXG4gICAgZGF0YTogQXJyYXkucHJvdG90eXBlLnNsaWNlLmNhbGwodGhpcy5fYXJyIHx8IHRoaXMsIDApXG4gIH1cbn1cblxuZnVuY3Rpb24gYmFzZTY0U2xpY2UgKGJ1Ziwgc3RhcnQsIGVuZCkge1xuICBpZiAoc3RhcnQgPT09IDAgJiYgZW5kID09PSBidWYubGVuZ3RoKSB7XG4gICAgcmV0dXJuIGJhc2U2NC5mcm9tQnl0ZUFycmF5KGJ1ZilcbiAgfSBlbHNlIHtcbiAgICByZXR1cm4gYmFzZTY0LmZyb21CeXRlQXJyYXkoYnVmLnNsaWNlKHN0YXJ0LCBlbmQpKVxuICB9XG59XG5cbmZ1bmN0aW9uIHV0ZjhTbGljZSAoYnVmLCBzdGFydCwgZW5kKSB7XG4gIGVuZCA9IE1hdGgubWluKGJ1Zi5sZW5ndGgsIGVuZClcbiAgY29uc3QgcmVzID0gW11cblxuICBsZXQgaSA9IHN0YXJ0XG4gIHdoaWxlIChpIDwgZW5kKSB7XG4gICAgY29uc3QgZmlyc3RCeXRlID0gYnVmW2ldXG4gICAgbGV0IGNvZGVQb2ludCA9IG51bGxcbiAgICBsZXQgYnl0ZXNQZXJTZXF1ZW5jZSA9IChmaXJzdEJ5dGUgPiAweEVGKVxuICAgICAgPyA0XG4gICAgICA6IChmaXJzdEJ5dGUgPiAweERGKVxuICAgICAgICAgID8gM1xuICAgICAgICAgIDogKGZpcnN0Qnl0ZSA+IDB4QkYpXG4gICAgICAgICAgICAgID8gMlxuICAgICAgICAgICAgICA6IDFcblxuICAgIGlmIChpICsgYnl0ZXNQZXJTZXF1ZW5jZSA8PSBlbmQpIHtcbiAgICAgIGxldCBzZWNvbmRCeXRlLCB0aGlyZEJ5dGUsIGZvdXJ0aEJ5dGUsIHRlbXBDb2RlUG9pbnRcblxuICAgICAgc3dpdGNoIChieXRlc1BlclNlcXVlbmNlKSB7XG4gICAgICAgIGNhc2UgMTpcbiAgICAgICAgICBpZiAoZmlyc3RCeXRlIDwgMHg4MCkge1xuICAgICAgICAgICAgY29kZVBvaW50ID0gZmlyc3RCeXRlXG4gICAgICAgICAgfVxuICAgICAgICAgIGJyZWFrXG4gICAgICAgIGNhc2UgMjpcbiAgICAgICAgICBzZWNvbmRCeXRlID0gYnVmW2kgKyAxXVxuICAgICAgICAgIGlmICgoc2Vjb25kQnl0ZSAmIDB4QzApID09PSAweDgwKSB7XG4gICAgICAgICAgICB0ZW1wQ29kZVBvaW50ID0gKGZpcnN0Qnl0ZSAmIDB4MUYpIDw8IDB4NiB8IChzZWNvbmRCeXRlICYgMHgzRilcbiAgICAgICAgICAgIGlmICh0ZW1wQ29kZVBvaW50ID4gMHg3Rikge1xuICAgICAgICAgICAgICBjb2RlUG9pbnQgPSB0ZW1wQ29kZVBvaW50XG4gICAgICAgICAgICB9XG4gICAgICAgICAgfVxuICAgICAgICAgIGJyZWFrXG4gICAgICAgIGNhc2UgMzpcbiAgICAgICAgICBzZWNvbmRCeXRlID0gYnVmW2kgKyAxXVxuICAgICAgICAgIHRoaXJkQnl0ZSA9IGJ1ZltpICsgMl1cbiAgICAgICAgICBpZiAoKHNlY29uZEJ5dGUgJiAweEMwKSA9PT0gMHg4MCAmJiAodGhpcmRCeXRlICYgMHhDMCkgPT09IDB4ODApIHtcbiAgICAgICAgICAgIHRlbXBDb2RlUG9pbnQgPSAoZmlyc3RCeXRlICYgMHhGKSA8PCAweEMgfCAoc2Vjb25kQnl0ZSAmIDB4M0YpIDw8IDB4NiB8ICh0aGlyZEJ5dGUgJiAweDNGKVxuICAgICAgICAgICAgaWYgKHRlbXBDb2RlUG9pbnQgPiAweDdGRiAmJiAodGVtcENvZGVQb2ludCA8IDB4RDgwMCB8fCB0ZW1wQ29kZVBvaW50ID4gMHhERkZGKSkge1xuICAgICAgICAgICAgICBjb2RlUG9pbnQgPSB0ZW1wQ29kZVBvaW50XG4gICAgICAgICAgICB9XG4gICAgICAgICAgfVxuICAgICAgICAgIGJyZWFrXG4gICAgICAgIGNhc2UgNDpcbiAgICAgICAgICBzZWNvbmRCeXRlID0gYnVmW2kgKyAxXVxuICAgICAgICAgIHRoaXJkQnl0ZSA9IGJ1ZltpICsgMl1cbiAgICAgICAgICBmb3VydGhCeXRlID0gYnVmW2kgKyAzXVxuICAgICAgICAgIGlmICgoc2Vjb25kQnl0ZSAmIDB4QzApID09PSAweDgwICYmICh0aGlyZEJ5dGUgJiAweEMwKSA9PT0gMHg4MCAmJiAoZm91cnRoQnl0ZSAmIDB4QzApID09PSAweDgwKSB7XG4gICAgICAgICAgICB0ZW1wQ29kZVBvaW50ID0gKGZpcnN0Qnl0ZSAmIDB4RikgPDwgMHgxMiB8IChzZWNvbmRCeXRlICYgMHgzRikgPDwgMHhDIHwgKHRoaXJkQnl0ZSAmIDB4M0YpIDw8IDB4NiB8IChmb3VydGhCeXRlICYgMHgzRilcbiAgICAgICAgICAgIGlmICh0ZW1wQ29kZVBvaW50ID4gMHhGRkZGICYmIHRlbXBDb2RlUG9pbnQgPCAweDExMDAwMCkge1xuICAgICAgICAgICAgICBjb2RlUG9pbnQgPSB0ZW1wQ29kZVBvaW50XG4gICAgICAgICAgICB9XG4gICAgICAgICAgfVxuICAgICAgfVxuICAgIH1cblxuICAgIGlmIChjb2RlUG9pbnQgPT09IG51bGwpIHtcbiAgICAgIC8vIHdlIGRpZCBub3QgZ2VuZXJhdGUgYSB2YWxpZCBjb2RlUG9pbnQgc28gaW5zZXJ0IGFcbiAgICAgIC8vIHJlcGxhY2VtZW50IGNoYXIgKFUrRkZGRCkgYW5kIGFkdmFuY2Ugb25seSAxIGJ5dGVcbiAgICAgIGNvZGVQb2ludCA9IDB4RkZGRFxuICAgICAgYnl0ZXNQZXJTZXF1ZW5jZSA9IDFcbiAgICB9IGVsc2UgaWYgKGNvZGVQb2ludCA+IDB4RkZGRikge1xuICAgICAgLy8gZW5jb2RlIHRvIHV0ZjE2IChzdXJyb2dhdGUgcGFpciBkYW5jZSlcbiAgICAgIGNvZGVQb2ludCAtPSAweDEwMDAwXG4gICAgICByZXMucHVzaChjb2RlUG9pbnQgPj4+IDEwICYgMHgzRkYgfCAweEQ4MDApXG4gICAgICBjb2RlUG9pbnQgPSAweERDMDAgfCBjb2RlUG9pbnQgJiAweDNGRlxuICAgIH1cblxuICAgIHJlcy5wdXNoKGNvZGVQb2ludClcbiAgICBpICs9IGJ5dGVzUGVyU2VxdWVuY2VcbiAgfVxuXG4gIHJldHVybiBkZWNvZGVDb2RlUG9pbnRzQXJyYXkocmVzKVxufVxuXG4vLyBCYXNlZCBvbiBodHRwOi8vc3RhY2tvdmVyZmxvdy5jb20vYS8yMjc0NzI3Mi82ODA3NDIsIHRoZSBicm93c2VyIHdpdGhcbi8vIHRoZSBsb3dlc3QgbGltaXQgaXMgQ2hyb21lLCB3aXRoIDB4MTAwMDAgYXJncy5cbi8vIFdlIGdvIDEgbWFnbml0dWRlIGxlc3MsIGZvciBzYWZldHlcbmNvbnN0IE1BWF9BUkdVTUVOVFNfTEVOR1RIID0gMHgxMDAwXG5cbmZ1bmN0aW9uIGRlY29kZUNvZGVQb2ludHNBcnJheSAoY29kZVBvaW50cykge1xuICBjb25zdCBsZW4gPSBjb2RlUG9pbnRzLmxlbmd0aFxuICBpZiAobGVuIDw9IE1BWF9BUkdVTUVOVFNfTEVOR1RIKSB7XG4gICAgcmV0dXJuIFN0cmluZy5mcm9tQ2hhckNvZGUuYXBwbHkoU3RyaW5nLCBjb2RlUG9pbnRzKSAvLyBhdm9pZCBleHRyYSBzbGljZSgpXG4gIH1cblxuICAvLyBEZWNvZGUgaW4gY2h1bmtzIHRvIGF2b2lkIFwiY2FsbCBzdGFjayBzaXplIGV4Y2VlZGVkXCIuXG4gIGxldCByZXMgPSAnJ1xuICBsZXQgaSA9IDBcbiAgd2hpbGUgKGkgPCBsZW4pIHtcbiAgICByZXMgKz0gU3RyaW5nLmZyb21DaGFyQ29kZS5hcHBseShcbiAgICAgIFN0cmluZyxcbiAgICAgIGNvZGVQb2ludHMuc2xpY2UoaSwgaSArPSBNQVhfQVJHVU1FTlRTX0xFTkdUSClcbiAgICApXG4gIH1cbiAgcmV0dXJuIHJlc1xufVxuXG5mdW5jdGlvbiBhc2NpaVNsaWNlIChidWYsIHN0YXJ0LCBlbmQpIHtcbiAgbGV0IHJldCA9ICcnXG4gIGVuZCA9IE1hdGgubWluKGJ1Zi5sZW5ndGgsIGVuZClcblxuICBmb3IgKGxldCBpID0gc3RhcnQ7IGkgPCBlbmQ7ICsraSkge1xuICAgIHJldCArPSBTdHJpbmcuZnJvbUNoYXJDb2RlKGJ1ZltpXSAmIDB4N0YpXG4gIH1cbiAgcmV0dXJuIHJldFxufVxuXG5mdW5jdGlvbiBsYXRpbjFTbGljZSAoYnVmLCBzdGFydCwgZW5kKSB7XG4gIGxldCByZXQgPSAnJ1xuICBlbmQgPSBNYXRoLm1pbihidWYubGVuZ3RoLCBlbmQpXG5cbiAgZm9yIChsZXQgaSA9IHN0YXJ0OyBpIDwgZW5kOyArK2kpIHtcbiAgICByZXQgKz0gU3RyaW5nLmZyb21DaGFyQ29kZShidWZbaV0pXG4gIH1cbiAgcmV0dXJuIHJldFxufVxuXG5mdW5jdGlvbiBoZXhTbGljZSAoYnVmLCBzdGFydCwgZW5kKSB7XG4gIGNvbnN0IGxlbiA9IGJ1Zi5sZW5ndGhcblxuICBpZiAoIXN0YXJ0IHx8IHN0YXJ0IDwgMCkgc3RhcnQgPSAwXG4gIGlmICghZW5kIHx8IGVuZCA8IDAgfHwgZW5kID4gbGVuKSBlbmQgPSBsZW5cblxuICBsZXQgb3V0ID0gJydcbiAgZm9yIChsZXQgaSA9IHN0YXJ0OyBpIDwgZW5kOyArK2kpIHtcbiAgICBvdXQgKz0gaGV4U2xpY2VMb29rdXBUYWJsZVtidWZbaV1dXG4gIH1cbiAgcmV0dXJuIG91dFxufVxuXG5mdW5jdGlvbiB1dGYxNmxlU2xpY2UgKGJ1Ziwgc3RhcnQsIGVuZCkge1xuICBjb25zdCBieXRlcyA9IGJ1Zi5zbGljZShzdGFydCwgZW5kKVxuICBsZXQgcmVzID0gJydcbiAgLy8gSWYgYnl0ZXMubGVuZ3RoIGlzIG9kZCwgdGhlIGxhc3QgOCBiaXRzIG11c3QgYmUgaWdub3JlZCAoc2FtZSBhcyBub2RlLmpzKVxuICBmb3IgKGxldCBpID0gMDsgaSA8IGJ5dGVzLmxlbmd0aCAtIDE7IGkgKz0gMikge1xuICAgIHJlcyArPSBTdHJpbmcuZnJvbUNoYXJDb2RlKGJ5dGVzW2ldICsgKGJ5dGVzW2kgKyAxXSAqIDI1NikpXG4gIH1cbiAgcmV0dXJuIHJlc1xufVxuXG5CdWZmZXIucHJvdG90eXBlLnNsaWNlID0gZnVuY3Rpb24gc2xpY2UgKHN0YXJ0LCBlbmQpIHtcbiAgY29uc3QgbGVuID0gdGhpcy5sZW5ndGhcbiAgc3RhcnQgPSB+fnN0YXJ0XG4gIGVuZCA9IGVuZCA9PT0gdW5kZWZpbmVkID8gbGVuIDogfn5lbmRcblxuICBpZiAoc3RhcnQgPCAwKSB7XG4gICAgc3RhcnQgKz0gbGVuXG4gICAgaWYgKHN0YXJ0IDwgMCkgc3RhcnQgPSAwXG4gIH0gZWxzZSBpZiAoc3RhcnQgPiBsZW4pIHtcbiAgICBzdGFydCA9IGxlblxuICB9XG5cbiAgaWYgKGVuZCA8IDApIHtcbiAgICBlbmQgKz0gbGVuXG4gICAgaWYgKGVuZCA8IDApIGVuZCA9IDBcbiAgfSBlbHNlIGlmIChlbmQgPiBsZW4pIHtcbiAgICBlbmQgPSBsZW5cbiAgfVxuXG4gIGlmIChlbmQgPCBzdGFydCkgZW5kID0gc3RhcnRcblxuICBjb25zdCBuZXdCdWYgPSB0aGlzLnN1YmFycmF5KHN0YXJ0LCBlbmQpXG4gIC8vIFJldHVybiBhbiBhdWdtZW50ZWQgYFVpbnQ4QXJyYXlgIGluc3RhbmNlXG4gIE9iamVjdC5zZXRQcm90b3R5cGVPZihuZXdCdWYsIEJ1ZmZlci5wcm90b3R5cGUpXG5cbiAgcmV0dXJuIG5ld0J1ZlxufVxuXG4vKlxuICogTmVlZCB0byBtYWtlIHN1cmUgdGhhdCBidWZmZXIgaXNuJ3QgdHJ5aW5nIHRvIHdyaXRlIG91dCBvZiBib3VuZHMuXG4gKi9cbmZ1bmN0aW9uIGNoZWNrT2Zmc2V0IChvZmZzZXQsIGV4dCwgbGVuZ3RoKSB7XG4gIGlmICgob2Zmc2V0ICUgMSkgIT09IDAgfHwgb2Zmc2V0IDwgMCkgdGhyb3cgbmV3IFJhbmdlRXJyb3IoJ29mZnNldCBpcyBub3QgdWludCcpXG4gIGlmIChvZmZzZXQgKyBleHQgPiBsZW5ndGgpIHRocm93IG5ldyBSYW5nZUVycm9yKCdUcnlpbmcgdG8gYWNjZXNzIGJleW9uZCBidWZmZXIgbGVuZ3RoJylcbn1cblxuQnVmZmVyLnByb3RvdHlwZS5yZWFkVWludExFID1cbkJ1ZmZlci5wcm90b3R5cGUucmVhZFVJbnRMRSA9IGZ1bmN0aW9uIHJlYWRVSW50TEUgKG9mZnNldCwgYnl0ZUxlbmd0aCwgbm9Bc3NlcnQpIHtcbiAgb2Zmc2V0ID0gb2Zmc2V0ID4+PiAwXG4gIGJ5dGVMZW5ndGggPSBieXRlTGVuZ3RoID4+PiAwXG4gIGlmICghbm9Bc3NlcnQpIGNoZWNrT2Zmc2V0KG9mZnNldCwgYnl0ZUxlbmd0aCwgdGhpcy5sZW5ndGgpXG5cbiAgbGV0IHZhbCA9IHRoaXNbb2Zmc2V0XVxuICBsZXQgbXVsID0gMVxuICBsZXQgaSA9IDBcbiAgd2hpbGUgKCsraSA8IGJ5dGVMZW5ndGggJiYgKG11bCAqPSAweDEwMCkpIHtcbiAgICB2YWwgKz0gdGhpc1tvZmZzZXQgKyBpXSAqIG11bFxuICB9XG5cbiAgcmV0dXJuIHZhbFxufVxuXG5CdWZmZXIucHJvdG90eXBlLnJlYWRVaW50QkUgPVxuQnVmZmVyLnByb3RvdHlwZS5yZWFkVUludEJFID0gZnVuY3Rpb24gcmVhZFVJbnRCRSAob2Zmc2V0LCBieXRlTGVuZ3RoLCBub0Fzc2VydCkge1xuICBvZmZzZXQgPSBvZmZzZXQgPj4+IDBcbiAgYnl0ZUxlbmd0aCA9IGJ5dGVMZW5ndGggPj4+IDBcbiAgaWYgKCFub0Fzc2VydCkge1xuICAgIGNoZWNrT2Zmc2V0KG9mZnNldCwgYnl0ZUxlbmd0aCwgdGhpcy5sZW5ndGgpXG4gIH1cblxuICBsZXQgdmFsID0gdGhpc1tvZmZzZXQgKyAtLWJ5dGVMZW5ndGhdXG4gIGxldCBtdWwgPSAxXG4gIHdoaWxlIChieXRlTGVuZ3RoID4gMCAmJiAobXVsICo9IDB4MTAwKSkge1xuICAgIHZhbCArPSB0aGlzW29mZnNldCArIC0tYnl0ZUxlbmd0aF0gKiBtdWxcbiAgfVxuXG4gIHJldHVybiB2YWxcbn1cblxuQnVmZmVyLnByb3RvdHlwZS5yZWFkVWludDggPVxuQnVmZmVyLnByb3RvdHlwZS5yZWFkVUludDggPSBmdW5jdGlvbiByZWFkVUludDggKG9mZnNldCwgbm9Bc3NlcnQpIHtcbiAgb2Zmc2V0ID0gb2Zmc2V0ID4+PiAwXG4gIGlmICghbm9Bc3NlcnQpIGNoZWNrT2Zmc2V0KG9mZnNldCwgMSwgdGhpcy5sZW5ndGgpXG4gIHJldHVybiB0aGlzW29mZnNldF1cbn1cblxuQnVmZmVyLnByb3RvdHlwZS5yZWFkVWludDE2TEUgPVxuQnVmZmVyLnByb3RvdHlwZS5yZWFkVUludDE2TEUgPSBmdW5jdGlvbiByZWFkVUludDE2TEUgKG9mZnNldCwgbm9Bc3NlcnQpIHtcbiAgb2Zmc2V0ID0gb2Zmc2V0ID4+PiAwXG4gIGlmICghbm9Bc3NlcnQpIGNoZWNrT2Zmc2V0KG9mZnNldCwgMiwgdGhpcy5sZW5ndGgpXG4gIHJldHVybiB0aGlzW29mZnNldF0gfCAodGhpc1tvZmZzZXQgKyAxXSA8PCA4KVxufVxuXG5CdWZmZXIucHJvdG90eXBlLnJlYWRVaW50MTZCRSA9XG5CdWZmZXIucHJvdG90eXBlLnJlYWRVSW50MTZCRSA9IGZ1bmN0aW9uIHJlYWRVSW50MTZCRSAob2Zmc2V0LCBub0Fzc2VydCkge1xuICBvZmZzZXQgPSBvZmZzZXQgPj4+IDBcbiAgaWYgKCFub0Fzc2VydCkgY2hlY2tPZmZzZXQob2Zmc2V0LCAyLCB0aGlzLmxlbmd0aClcbiAgcmV0dXJuICh0aGlzW29mZnNldF0gPDwgOCkgfCB0aGlzW29mZnNldCArIDFdXG59XG5cbkJ1ZmZlci5wcm90b3R5cGUucmVhZFVpbnQzMkxFID1cbkJ1ZmZlci5wcm90b3R5cGUucmVhZFVJbnQzMkxFID0gZnVuY3Rpb24gcmVhZFVJbnQzMkxFIChvZmZzZXQsIG5vQXNzZXJ0KSB7XG4gIG9mZnNldCA9IG9mZnNldCA+Pj4gMFxuICBpZiAoIW5vQXNzZXJ0KSBjaGVja09mZnNldChvZmZzZXQsIDQsIHRoaXMubGVuZ3RoKVxuXG4gIHJldHVybiAoKHRoaXNbb2Zmc2V0XSkgfFxuICAgICAgKHRoaXNbb2Zmc2V0ICsgMV0gPDwgOCkgfFxuICAgICAgKHRoaXNbb2Zmc2V0ICsgMl0gPDwgMTYpKSArXG4gICAgICAodGhpc1tvZmZzZXQgKyAzXSAqIDB4MTAwMDAwMClcbn1cblxuQnVmZmVyLnByb3RvdHlwZS5yZWFkVWludDMyQkUgPVxuQnVmZmVyLnByb3RvdHlwZS5yZWFkVUludDMyQkUgPSBmdW5jdGlvbiByZWFkVUludDMyQkUgKG9mZnNldCwgbm9Bc3NlcnQpIHtcbiAgb2Zmc2V0ID0gb2Zmc2V0ID4+PiAwXG4gIGlmICghbm9Bc3NlcnQpIGNoZWNrT2Zmc2V0KG9mZnNldCwgNCwgdGhpcy5sZW5ndGgpXG5cbiAgcmV0dXJuICh0aGlzW29mZnNldF0gKiAweDEwMDAwMDApICtcbiAgICAoKHRoaXNbb2Zmc2V0ICsgMV0gPDwgMTYpIHxcbiAgICAodGhpc1tvZmZzZXQgKyAyXSA8PCA4KSB8XG4gICAgdGhpc1tvZmZzZXQgKyAzXSlcbn1cblxuQnVmZmVyLnByb3RvdHlwZS5yZWFkQmlnVUludDY0TEUgPSBkZWZpbmVCaWdJbnRNZXRob2QoZnVuY3Rpb24gcmVhZEJpZ1VJbnQ2NExFIChvZmZzZXQpIHtcbiAgb2Zmc2V0ID0gb2Zmc2V0ID4+PiAwXG4gIHZhbGlkYXRlTnVtYmVyKG9mZnNldCwgJ29mZnNldCcpXG4gIGNvbnN0IGZpcnN0ID0gdGhpc1tvZmZzZXRdXG4gIGNvbnN0IGxhc3QgPSB0aGlzW29mZnNldCArIDddXG4gIGlmIChmaXJzdCA9PT0gdW5kZWZpbmVkIHx8IGxhc3QgPT09IHVuZGVmaW5lZCkge1xuICAgIGJvdW5kc0Vycm9yKG9mZnNldCwgdGhpcy5sZW5ndGggLSA4KVxuICB9XG5cbiAgY29uc3QgbG8gPSBmaXJzdCArXG4gICAgdGhpc1srK29mZnNldF0gKiAyICoqIDggK1xuICAgIHRoaXNbKytvZmZzZXRdICogMiAqKiAxNiArXG4gICAgdGhpc1srK29mZnNldF0gKiAyICoqIDI0XG5cbiAgY29uc3QgaGkgPSB0aGlzWysrb2Zmc2V0XSArXG4gICAgdGhpc1srK29mZnNldF0gKiAyICoqIDggK1xuICAgIHRoaXNbKytvZmZzZXRdICogMiAqKiAxNiArXG4gICAgbGFzdCAqIDIgKiogMjRcblxuICByZXR1cm4gQmlnSW50KGxvKSArIChCaWdJbnQoaGkpIDw8IEJpZ0ludCgzMikpXG59KVxuXG5CdWZmZXIucHJvdG90eXBlLnJlYWRCaWdVSW50NjRCRSA9IGRlZmluZUJpZ0ludE1ldGhvZChmdW5jdGlvbiByZWFkQmlnVUludDY0QkUgKG9mZnNldCkge1xuICBvZmZzZXQgPSBvZmZzZXQgPj4+IDBcbiAgdmFsaWRhdGVOdW1iZXIob2Zmc2V0LCAnb2Zmc2V0JylcbiAgY29uc3QgZmlyc3QgPSB0aGlzW29mZnNldF1cbiAgY29uc3QgbGFzdCA9IHRoaXNbb2Zmc2V0ICsgN11cbiAgaWYgKGZpcnN0ID09PSB1bmRlZmluZWQgfHwgbGFzdCA9PT0gdW5kZWZpbmVkKSB7XG4gICAgYm91bmRzRXJyb3Iob2Zmc2V0LCB0aGlzLmxlbmd0aCAtIDgpXG4gIH1cblxuICBjb25zdCBoaSA9IGZpcnN0ICogMiAqKiAyNCArXG4gICAgdGhpc1srK29mZnNldF0gKiAyICoqIDE2ICtcbiAgICB0aGlzWysrb2Zmc2V0XSAqIDIgKiogOCArXG4gICAgdGhpc1srK29mZnNldF1cblxuICBjb25zdCBsbyA9IHRoaXNbKytvZmZzZXRdICogMiAqKiAyNCArXG4gICAgdGhpc1srK29mZnNldF0gKiAyICoqIDE2ICtcbiAgICB0aGlzWysrb2Zmc2V0XSAqIDIgKiogOCArXG4gICAgbGFzdFxuXG4gIHJldHVybiAoQmlnSW50KGhpKSA8PCBCaWdJbnQoMzIpKSArIEJpZ0ludChsbylcbn0pXG5cbkJ1ZmZlci5wcm90b3R5cGUucmVhZEludExFID0gZnVuY3Rpb24gcmVhZEludExFIChvZmZzZXQsIGJ5dGVMZW5ndGgsIG5vQXNzZXJ0KSB7XG4gIG9mZnNldCA9IG9mZnNldCA+Pj4gMFxuICBieXRlTGVuZ3RoID0gYnl0ZUxlbmd0aCA+Pj4gMFxuICBpZiAoIW5vQXNzZXJ0KSBjaGVja09mZnNldChvZmZzZXQsIGJ5dGVMZW5ndGgsIHRoaXMubGVuZ3RoKVxuXG4gIGxldCB2YWwgPSB0aGlzW29mZnNldF1cbiAgbGV0IG11bCA9IDFcbiAgbGV0IGkgPSAwXG4gIHdoaWxlICgrK2kgPCBieXRlTGVuZ3RoICYmIChtdWwgKj0gMHgxMDApKSB7XG4gICAgdmFsICs9IHRoaXNbb2Zmc2V0ICsgaV0gKiBtdWxcbiAgfVxuICBtdWwgKj0gMHg4MFxuXG4gIGlmICh2YWwgPj0gbXVsKSB2YWwgLT0gTWF0aC5wb3coMiwgOCAqIGJ5dGVMZW5ndGgpXG5cbiAgcmV0dXJuIHZhbFxufVxuXG5CdWZmZXIucHJvdG90eXBlLnJlYWRJbnRCRSA9IGZ1bmN0aW9uIHJlYWRJbnRCRSAob2Zmc2V0LCBieXRlTGVuZ3RoLCBub0Fzc2VydCkge1xuICBvZmZzZXQgPSBvZmZzZXQgPj4+IDBcbiAgYnl0ZUxlbmd0aCA9IGJ5dGVMZW5ndGggPj4+IDBcbiAgaWYgKCFub0Fzc2VydCkgY2hlY2tPZmZzZXQob2Zmc2V0LCBieXRlTGVuZ3RoLCB0aGlzLmxlbmd0aClcblxuICBsZXQgaSA9IGJ5dGVMZW5ndGhcbiAgbGV0IG11bCA9IDFcbiAgbGV0IHZhbCA9IHRoaXNbb2Zmc2V0ICsgLS1pXVxuICB3aGlsZSAoaSA+IDAgJiYgKG11bCAqPSAweDEwMCkpIHtcbiAgICB2YWwgKz0gdGhpc1tvZmZzZXQgKyAtLWldICogbXVsXG4gIH1cbiAgbXVsICo9IDB4ODBcblxuICBpZiAodmFsID49IG11bCkgdmFsIC09IE1hdGgucG93KDIsIDggKiBieXRlTGVuZ3RoKVxuXG4gIHJldHVybiB2YWxcbn1cblxuQnVmZmVyLnByb3RvdHlwZS5yZWFkSW50OCA9IGZ1bmN0aW9uIHJlYWRJbnQ4IChvZmZzZXQsIG5vQXNzZXJ0KSB7XG4gIG9mZnNldCA9IG9mZnNldCA+Pj4gMFxuICBpZiAoIW5vQXNzZXJ0KSBjaGVja09mZnNldChvZmZzZXQsIDEsIHRoaXMubGVuZ3RoKVxuICBpZiAoISh0aGlzW29mZnNldF0gJiAweDgwKSkgcmV0dXJuICh0aGlzW29mZnNldF0pXG4gIHJldHVybiAoKDB4ZmYgLSB0aGlzW29mZnNldF0gKyAxKSAqIC0xKVxufVxuXG5CdWZmZXIucHJvdG90eXBlLnJlYWRJbnQxNkxFID0gZnVuY3Rpb24gcmVhZEludDE2TEUgKG9mZnNldCwgbm9Bc3NlcnQpIHtcbiAgb2Zmc2V0ID0gb2Zmc2V0ID4+PiAwXG4gIGlmICghbm9Bc3NlcnQpIGNoZWNrT2Zmc2V0KG9mZnNldCwgMiwgdGhpcy5sZW5ndGgpXG4gIGNvbnN0IHZhbCA9IHRoaXNbb2Zmc2V0XSB8ICh0aGlzW29mZnNldCArIDFdIDw8IDgpXG4gIHJldHVybiAodmFsICYgMHg4MDAwKSA/IHZhbCB8IDB4RkZGRjAwMDAgOiB2YWxcbn1cblxuQnVmZmVyLnByb3RvdHlwZS5yZWFkSW50MTZCRSA9IGZ1bmN0aW9uIHJlYWRJbnQxNkJFIChvZmZzZXQsIG5vQXNzZXJ0KSB7XG4gIG9mZnNldCA9IG9mZnNldCA+Pj4gMFxuICBpZiAoIW5vQXNzZXJ0KSBjaGVja09mZnNldChvZmZzZXQsIDIsIHRoaXMubGVuZ3RoKVxuICBjb25zdCB2YWwgPSB0aGlzW29mZnNldCArIDFdIHwgKHRoaXNbb2Zmc2V0XSA8PCA4KVxuICByZXR1cm4gKHZhbCAmIDB4ODAwMCkgPyB2YWwgfCAweEZGRkYwMDAwIDogdmFsXG59XG5cbkJ1ZmZlci5wcm90b3R5cGUucmVhZEludDMyTEUgPSBmdW5jdGlvbiByZWFkSW50MzJMRSAob2Zmc2V0LCBub0Fzc2VydCkge1xuICBvZmZzZXQgPSBvZmZzZXQgPj4+IDBcbiAgaWYgKCFub0Fzc2VydCkgY2hlY2tPZmZzZXQob2Zmc2V0LCA0LCB0aGlzLmxlbmd0aClcblxuICByZXR1cm4gKHRoaXNbb2Zmc2V0XSkgfFxuICAgICh0aGlzW29mZnNldCArIDFdIDw8IDgpIHxcbiAgICAodGhpc1tvZmZzZXQgKyAyXSA8PCAxNikgfFxuICAgICh0aGlzW29mZnNldCArIDNdIDw8IDI0KVxufVxuXG5CdWZmZXIucHJvdG90eXBlLnJlYWRJbnQzMkJFID0gZnVuY3Rpb24gcmVhZEludDMyQkUgKG9mZnNldCwgbm9Bc3NlcnQpIHtcbiAgb2Zmc2V0ID0gb2Zmc2V0ID4+PiAwXG4gIGlmICghbm9Bc3NlcnQpIGNoZWNrT2Zmc2V0KG9mZnNldCwgNCwgdGhpcy5sZW5ndGgpXG5cbiAgcmV0dXJuICh0aGlzW29mZnNldF0gPDwgMjQpIHxcbiAgICAodGhpc1tvZmZzZXQgKyAxXSA8PCAxNikgfFxuICAgICh0aGlzW29mZnNldCArIDJdIDw8IDgpIHxcbiAgICAodGhpc1tvZmZzZXQgKyAzXSlcbn1cblxuQnVmZmVyLnByb3RvdHlwZS5yZWFkQmlnSW50NjRMRSA9IGRlZmluZUJpZ0ludE1ldGhvZChmdW5jdGlvbiByZWFkQmlnSW50NjRMRSAob2Zmc2V0KSB7XG4gIG9mZnNldCA9IG9mZnNldCA+Pj4gMFxuICB2YWxpZGF0ZU51bWJlcihvZmZzZXQsICdvZmZzZXQnKVxuICBjb25zdCBmaXJzdCA9IHRoaXNbb2Zmc2V0XVxuICBjb25zdCBsYXN0ID0gdGhpc1tvZmZzZXQgKyA3XVxuICBpZiAoZmlyc3QgPT09IHVuZGVmaW5lZCB8fCBsYXN0ID09PSB1bmRlZmluZWQpIHtcbiAgICBib3VuZHNFcnJvcihvZmZzZXQsIHRoaXMubGVuZ3RoIC0gOClcbiAgfVxuXG4gIGNvbnN0IHZhbCA9IHRoaXNbb2Zmc2V0ICsgNF0gK1xuICAgIHRoaXNbb2Zmc2V0ICsgNV0gKiAyICoqIDggK1xuICAgIHRoaXNbb2Zmc2V0ICsgNl0gKiAyICoqIDE2ICtcbiAgICAobGFzdCA8PCAyNCkgLy8gT3ZlcmZsb3dcblxuICByZXR1cm4gKEJpZ0ludCh2YWwpIDw8IEJpZ0ludCgzMikpICtcbiAgICBCaWdJbnQoZmlyc3QgK1xuICAgIHRoaXNbKytvZmZzZXRdICogMiAqKiA4ICtcbiAgICB0aGlzWysrb2Zmc2V0XSAqIDIgKiogMTYgK1xuICAgIHRoaXNbKytvZmZzZXRdICogMiAqKiAyNClcbn0pXG5cbkJ1ZmZlci5wcm90b3R5cGUucmVhZEJpZ0ludDY0QkUgPSBkZWZpbmVCaWdJbnRNZXRob2QoZnVuY3Rpb24gcmVhZEJpZ0ludDY0QkUgKG9mZnNldCkge1xuICBvZmZzZXQgPSBvZmZzZXQgPj4+IDBcbiAgdmFsaWRhdGVOdW1iZXIob2Zmc2V0LCAnb2Zmc2V0JylcbiAgY29uc3QgZmlyc3QgPSB0aGlzW29mZnNldF1cbiAgY29uc3QgbGFzdCA9IHRoaXNbb2Zmc2V0ICsgN11cbiAgaWYgKGZpcnN0ID09PSB1bmRlZmluZWQgfHwgbGFzdCA9PT0gdW5kZWZpbmVkKSB7XG4gICAgYm91bmRzRXJyb3Iob2Zmc2V0LCB0aGlzLmxlbmd0aCAtIDgpXG4gIH1cblxuICBjb25zdCB2YWwgPSAoZmlyc3QgPDwgMjQpICsgLy8gT3ZlcmZsb3dcbiAgICB0aGlzWysrb2Zmc2V0XSAqIDIgKiogMTYgK1xuICAgIHRoaXNbKytvZmZzZXRdICogMiAqKiA4ICtcbiAgICB0aGlzWysrb2Zmc2V0XVxuXG4gIHJldHVybiAoQmlnSW50KHZhbCkgPDwgQmlnSW50KDMyKSkgK1xuICAgIEJpZ0ludCh0aGlzWysrb2Zmc2V0XSAqIDIgKiogMjQgK1xuICAgIHRoaXNbKytvZmZzZXRdICogMiAqKiAxNiArXG4gICAgdGhpc1srK29mZnNldF0gKiAyICoqIDggK1xuICAgIGxhc3QpXG59KVxuXG5CdWZmZXIucHJvdG90eXBlLnJlYWRGbG9hdExFID0gZnVuY3Rpb24gcmVhZEZsb2F0TEUgKG9mZnNldCwgbm9Bc3NlcnQpIHtcbiAgb2Zmc2V0ID0gb2Zmc2V0ID4+PiAwXG4gIGlmICghbm9Bc3NlcnQpIGNoZWNrT2Zmc2V0KG9mZnNldCwgNCwgdGhpcy5sZW5ndGgpXG4gIHJldHVybiBpZWVlNzU0LnJlYWQodGhpcywgb2Zmc2V0LCB0cnVlLCAyMywgNClcbn1cblxuQnVmZmVyLnByb3RvdHlwZS5yZWFkRmxvYXRCRSA9IGZ1bmN0aW9uIHJlYWRGbG9hdEJFIChvZmZzZXQsIG5vQXNzZXJ0KSB7XG4gIG9mZnNldCA9IG9mZnNldCA+Pj4gMFxuICBpZiAoIW5vQXNzZXJ0KSBjaGVja09mZnNldChvZmZzZXQsIDQsIHRoaXMubGVuZ3RoKVxuICByZXR1cm4gaWVlZTc1NC5yZWFkKHRoaXMsIG9mZnNldCwgZmFsc2UsIDIzLCA0KVxufVxuXG5CdWZmZXIucHJvdG90eXBlLnJlYWREb3VibGVMRSA9IGZ1bmN0aW9uIHJlYWREb3VibGVMRSAob2Zmc2V0LCBub0Fzc2VydCkge1xuICBvZmZzZXQgPSBvZmZzZXQgPj4+IDBcbiAgaWYgKCFub0Fzc2VydCkgY2hlY2tPZmZzZXQob2Zmc2V0LCA4LCB0aGlzLmxlbmd0aClcbiAgcmV0dXJuIGllZWU3NTQucmVhZCh0aGlzLCBvZmZzZXQsIHRydWUsIDUyLCA4KVxufVxuXG5CdWZmZXIucHJvdG90eXBlLnJlYWREb3VibGVCRSA9IGZ1bmN0aW9uIHJlYWREb3VibGVCRSAob2Zmc2V0LCBub0Fzc2VydCkge1xuICBvZmZzZXQgPSBvZmZzZXQgPj4+IDBcbiAgaWYgKCFub0Fzc2VydCkgY2hlY2tPZmZzZXQob2Zmc2V0LCA4LCB0aGlzLmxlbmd0aClcbiAgcmV0dXJuIGllZWU3NTQucmVhZCh0aGlzLCBvZmZzZXQsIGZhbHNlLCA1MiwgOClcbn1cblxuZnVuY3Rpb24gY2hlY2tJbnQgKGJ1ZiwgdmFsdWUsIG9mZnNldCwgZXh0LCBtYXgsIG1pbikge1xuICBpZiAoIUJ1ZmZlci5pc0J1ZmZlcihidWYpKSB0aHJvdyBuZXcgVHlwZUVycm9yKCdcImJ1ZmZlclwiIGFyZ3VtZW50IG11c3QgYmUgYSBCdWZmZXIgaW5zdGFuY2UnKVxuICBpZiAodmFsdWUgPiBtYXggfHwgdmFsdWUgPCBtaW4pIHRocm93IG5ldyBSYW5nZUVycm9yKCdcInZhbHVlXCIgYXJndW1lbnQgaXMgb3V0IG9mIGJvdW5kcycpXG4gIGlmIChvZmZzZXQgKyBleHQgPiBidWYubGVuZ3RoKSB0aHJvdyBuZXcgUmFuZ2VFcnJvcignSW5kZXggb3V0IG9mIHJhbmdlJylcbn1cblxuQnVmZmVyLnByb3RvdHlwZS53cml0ZVVpbnRMRSA9XG5CdWZmZXIucHJvdG90eXBlLndyaXRlVUludExFID0gZnVuY3Rpb24gd3JpdGVVSW50TEUgKHZhbHVlLCBvZmZzZXQsIGJ5dGVMZW5ndGgsIG5vQXNzZXJ0KSB7XG4gIHZhbHVlID0gK3ZhbHVlXG4gIG9mZnNldCA9IG9mZnNldCA+Pj4gMFxuICBieXRlTGVuZ3RoID0gYnl0ZUxlbmd0aCA+Pj4gMFxuICBpZiAoIW5vQXNzZXJ0KSB7XG4gICAgY29uc3QgbWF4Qnl0ZXMgPSBNYXRoLnBvdygyLCA4ICogYnl0ZUxlbmd0aCkgLSAxXG4gICAgY2hlY2tJbnQodGhpcywgdmFsdWUsIG9mZnNldCwgYnl0ZUxlbmd0aCwgbWF4Qnl0ZXMsIDApXG4gIH1cblxuICBsZXQgbXVsID0gMVxuICBsZXQgaSA9IDBcbiAgdGhpc1tvZmZzZXRdID0gdmFsdWUgJiAweEZGXG4gIHdoaWxlICgrK2kgPCBieXRlTGVuZ3RoICYmIChtdWwgKj0gMHgxMDApKSB7XG4gICAgdGhpc1tvZmZzZXQgKyBpXSA9ICh2YWx1ZSAvIG11bCkgJiAweEZGXG4gIH1cblxuICByZXR1cm4gb2Zmc2V0ICsgYnl0ZUxlbmd0aFxufVxuXG5CdWZmZXIucHJvdG90eXBlLndyaXRlVWludEJFID1cbkJ1ZmZlci5wcm90b3R5cGUud3JpdGVVSW50QkUgPSBmdW5jdGlvbiB3cml0ZVVJbnRCRSAodmFsdWUsIG9mZnNldCwgYnl0ZUxlbmd0aCwgbm9Bc3NlcnQpIHtcbiAgdmFsdWUgPSArdmFsdWVcbiAgb2Zmc2V0ID0gb2Zmc2V0ID4+PiAwXG4gIGJ5dGVMZW5ndGggPSBieXRlTGVuZ3RoID4+PiAwXG4gIGlmICghbm9Bc3NlcnQpIHtcbiAgICBjb25zdCBtYXhCeXRlcyA9IE1hdGgucG93KDIsIDggKiBieXRlTGVuZ3RoKSAtIDFcbiAgICBjaGVja0ludCh0aGlzLCB2YWx1ZSwgb2Zmc2V0LCBieXRlTGVuZ3RoLCBtYXhCeXRlcywgMClcbiAgfVxuXG4gIGxldCBpID0gYnl0ZUxlbmd0aCAtIDFcbiAgbGV0IG11bCA9IDFcbiAgdGhpc1tvZmZzZXQgKyBpXSA9IHZhbHVlICYgMHhGRlxuICB3aGlsZSAoLS1pID49IDAgJiYgKG11bCAqPSAweDEwMCkpIHtcbiAgICB0aGlzW29mZnNldCArIGldID0gKHZhbHVlIC8gbXVsKSAmIDB4RkZcbiAgfVxuXG4gIHJldHVybiBvZmZzZXQgKyBieXRlTGVuZ3RoXG59XG5cbkJ1ZmZlci5wcm90b3R5cGUud3JpdGVVaW50OCA9XG5CdWZmZXIucHJvdG90eXBlLndyaXRlVUludDggPSBmdW5jdGlvbiB3cml0ZVVJbnQ4ICh2YWx1ZSwgb2Zmc2V0LCBub0Fzc2VydCkge1xuICB2YWx1ZSA9ICt2YWx1ZVxuICBvZmZzZXQgPSBvZmZzZXQgPj4+IDBcbiAgaWYgKCFub0Fzc2VydCkgY2hlY2tJbnQodGhpcywgdmFsdWUsIG9mZnNldCwgMSwgMHhmZiwgMClcbiAgdGhpc1tvZmZzZXRdID0gKHZhbHVlICYgMHhmZilcbiAgcmV0dXJuIG9mZnNldCArIDFcbn1cblxuQnVmZmVyLnByb3RvdHlwZS53cml0ZVVpbnQxNkxFID1cbkJ1ZmZlci5wcm90b3R5cGUud3JpdGVVSW50MTZMRSA9IGZ1bmN0aW9uIHdyaXRlVUludDE2TEUgKHZhbHVlLCBvZmZzZXQsIG5vQXNzZXJ0KSB7XG4gIHZhbHVlID0gK3ZhbHVlXG4gIG9mZnNldCA9IG9mZnNldCA+Pj4gMFxuICBpZiAoIW5vQXNzZXJ0KSBjaGVja0ludCh0aGlzLCB2YWx1ZSwgb2Zmc2V0LCAyLCAweGZmZmYsIDApXG4gIHRoaXNbb2Zmc2V0XSA9ICh2YWx1ZSAmIDB4ZmYpXG4gIHRoaXNbb2Zmc2V0ICsgMV0gPSAodmFsdWUgPj4+IDgpXG4gIHJldHVybiBvZmZzZXQgKyAyXG59XG5cbkJ1ZmZlci5wcm90b3R5cGUud3JpdGVVaW50MTZCRSA9XG5CdWZmZXIucHJvdG90eXBlLndyaXRlVUludDE2QkUgPSBmdW5jdGlvbiB3cml0ZVVJbnQxNkJFICh2YWx1ZSwgb2Zmc2V0LCBub0Fzc2VydCkge1xuICB2YWx1ZSA9ICt2YWx1ZVxuICBvZmZzZXQgPSBvZmZzZXQgPj4+IDBcbiAgaWYgKCFub0Fzc2VydCkgY2hlY2tJbnQodGhpcywgdmFsdWUsIG9mZnNldCwgMiwgMHhmZmZmLCAwKVxuICB0aGlzW29mZnNldF0gPSAodmFsdWUgPj4+IDgpXG4gIHRoaXNbb2Zmc2V0ICsgMV0gPSAodmFsdWUgJiAweGZmKVxuICByZXR1cm4gb2Zmc2V0ICsgMlxufVxuXG5CdWZmZXIucHJvdG90eXBlLndyaXRlVWludDMyTEUgPVxuQnVmZmVyLnByb3RvdHlwZS53cml0ZVVJbnQzMkxFID0gZnVuY3Rpb24gd3JpdGVVSW50MzJMRSAodmFsdWUsIG9mZnNldCwgbm9Bc3NlcnQpIHtcbiAgdmFsdWUgPSArdmFsdWVcbiAgb2Zmc2V0ID0gb2Zmc2V0ID4+PiAwXG4gIGlmICghbm9Bc3NlcnQpIGNoZWNrSW50KHRoaXMsIHZhbHVlLCBvZmZzZXQsIDQsIDB4ZmZmZmZmZmYsIDApXG4gIHRoaXNbb2Zmc2V0ICsgM10gPSAodmFsdWUgPj4+IDI0KVxuICB0aGlzW29mZnNldCArIDJdID0gKHZhbHVlID4+PiAxNilcbiAgdGhpc1tvZmZzZXQgKyAxXSA9ICh2YWx1ZSA+Pj4gOClcbiAgdGhpc1tvZmZzZXRdID0gKHZhbHVlICYgMHhmZilcbiAgcmV0dXJuIG9mZnNldCArIDRcbn1cblxuQnVmZmVyLnByb3RvdHlwZS53cml0ZVVpbnQzMkJFID1cbkJ1ZmZlci5wcm90b3R5cGUud3JpdGVVSW50MzJCRSA9IGZ1bmN0aW9uIHdyaXRlVUludDMyQkUgKHZhbHVlLCBvZmZzZXQsIG5vQXNzZXJ0KSB7XG4gIHZhbHVlID0gK3ZhbHVlXG4gIG9mZnNldCA9IG9mZnNldCA+Pj4gMFxuICBpZiAoIW5vQXNzZXJ0KSBjaGVja0ludCh0aGlzLCB2YWx1ZSwgb2Zmc2V0LCA0LCAweGZmZmZmZmZmLCAwKVxuICB0aGlzW29mZnNldF0gPSAodmFsdWUgPj4+IDI0KVxuICB0aGlzW29mZnNldCArIDFdID0gKHZhbHVlID4+PiAxNilcbiAgdGhpc1tvZmZzZXQgKyAyXSA9ICh2YWx1ZSA+Pj4gOClcbiAgdGhpc1tvZmZzZXQgKyAzXSA9ICh2YWx1ZSAmIDB4ZmYpXG4gIHJldHVybiBvZmZzZXQgKyA0XG59XG5cbmZ1bmN0aW9uIHdydEJpZ1VJbnQ2NExFIChidWYsIHZhbHVlLCBvZmZzZXQsIG1pbiwgbWF4KSB7XG4gIGNoZWNrSW50QkkodmFsdWUsIG1pbiwgbWF4LCBidWYsIG9mZnNldCwgNylcblxuICBsZXQgbG8gPSBOdW1iZXIodmFsdWUgJiBCaWdJbnQoMHhmZmZmZmZmZikpXG4gIGJ1ZltvZmZzZXQrK10gPSBsb1xuICBsbyA9IGxvID4+IDhcbiAgYnVmW29mZnNldCsrXSA9IGxvXG4gIGxvID0gbG8gPj4gOFxuICBidWZbb2Zmc2V0KytdID0gbG9cbiAgbG8gPSBsbyA+PiA4XG4gIGJ1ZltvZmZzZXQrK10gPSBsb1xuICBsZXQgaGkgPSBOdW1iZXIodmFsdWUgPj4gQmlnSW50KDMyKSAmIEJpZ0ludCgweGZmZmZmZmZmKSlcbiAgYnVmW29mZnNldCsrXSA9IGhpXG4gIGhpID0gaGkgPj4gOFxuICBidWZbb2Zmc2V0KytdID0gaGlcbiAgaGkgPSBoaSA+PiA4XG4gIGJ1ZltvZmZzZXQrK10gPSBoaVxuICBoaSA9IGhpID4+IDhcbiAgYnVmW29mZnNldCsrXSA9IGhpXG4gIHJldHVybiBvZmZzZXRcbn1cblxuZnVuY3Rpb24gd3J0QmlnVUludDY0QkUgKGJ1ZiwgdmFsdWUsIG9mZnNldCwgbWluLCBtYXgpIHtcbiAgY2hlY2tJbnRCSSh2YWx1ZSwgbWluLCBtYXgsIGJ1Ziwgb2Zmc2V0LCA3KVxuXG4gIGxldCBsbyA9IE51bWJlcih2YWx1ZSAmIEJpZ0ludCgweGZmZmZmZmZmKSlcbiAgYnVmW29mZnNldCArIDddID0gbG9cbiAgbG8gPSBsbyA+PiA4XG4gIGJ1ZltvZmZzZXQgKyA2XSA9IGxvXG4gIGxvID0gbG8gPj4gOFxuICBidWZbb2Zmc2V0ICsgNV0gPSBsb1xuICBsbyA9IGxvID4+IDhcbiAgYnVmW29mZnNldCArIDRdID0gbG9cbiAgbGV0IGhpID0gTnVtYmVyKHZhbHVlID4+IEJpZ0ludCgzMikgJiBCaWdJbnQoMHhmZmZmZmZmZikpXG4gIGJ1ZltvZmZzZXQgKyAzXSA9IGhpXG4gIGhpID0gaGkgPj4gOFxuICBidWZbb2Zmc2V0ICsgMl0gPSBoaVxuICBoaSA9IGhpID4+IDhcbiAgYnVmW29mZnNldCArIDFdID0gaGlcbiAgaGkgPSBoaSA+PiA4XG4gIGJ1ZltvZmZzZXRdID0gaGlcbiAgcmV0dXJuIG9mZnNldCArIDhcbn1cblxuQnVmZmVyLnByb3RvdHlwZS53cml0ZUJpZ1VJbnQ2NExFID0gZGVmaW5lQmlnSW50TWV0aG9kKGZ1bmN0aW9uIHdyaXRlQmlnVUludDY0TEUgKHZhbHVlLCBvZmZzZXQgPSAwKSB7XG4gIHJldHVybiB3cnRCaWdVSW50NjRMRSh0aGlzLCB2YWx1ZSwgb2Zmc2V0LCBCaWdJbnQoMCksIEJpZ0ludCgnMHhmZmZmZmZmZmZmZmZmZmZmJykpXG59KVxuXG5CdWZmZXIucHJvdG90eXBlLndyaXRlQmlnVUludDY0QkUgPSBkZWZpbmVCaWdJbnRNZXRob2QoZnVuY3Rpb24gd3JpdGVCaWdVSW50NjRCRSAodmFsdWUsIG9mZnNldCA9IDApIHtcbiAgcmV0dXJuIHdydEJpZ1VJbnQ2NEJFKHRoaXMsIHZhbHVlLCBvZmZzZXQsIEJpZ0ludCgwKSwgQmlnSW50KCcweGZmZmZmZmZmZmZmZmZmZmYnKSlcbn0pXG5cbkJ1ZmZlci5wcm90b3R5cGUud3JpdGVJbnRMRSA9IGZ1bmN0aW9uIHdyaXRlSW50TEUgKHZhbHVlLCBvZmZzZXQsIGJ5dGVMZW5ndGgsIG5vQXNzZXJ0KSB7XG4gIHZhbHVlID0gK3ZhbHVlXG4gIG9mZnNldCA9IG9mZnNldCA+Pj4gMFxuICBpZiAoIW5vQXNzZXJ0KSB7XG4gICAgY29uc3QgbGltaXQgPSBNYXRoLnBvdygyLCAoOCAqIGJ5dGVMZW5ndGgpIC0gMSlcblxuICAgIGNoZWNrSW50KHRoaXMsIHZhbHVlLCBvZmZzZXQsIGJ5dGVMZW5ndGgsIGxpbWl0IC0gMSwgLWxpbWl0KVxuICB9XG5cbiAgbGV0IGkgPSAwXG4gIGxldCBtdWwgPSAxXG4gIGxldCBzdWIgPSAwXG4gIHRoaXNbb2Zmc2V0XSA9IHZhbHVlICYgMHhGRlxuICB3aGlsZSAoKytpIDwgYnl0ZUxlbmd0aCAmJiAobXVsICo9IDB4MTAwKSkge1xuICAgIGlmICh2YWx1ZSA8IDAgJiYgc3ViID09PSAwICYmIHRoaXNbb2Zmc2V0ICsgaSAtIDFdICE9PSAwKSB7XG4gICAgICBzdWIgPSAxXG4gICAgfVxuICAgIHRoaXNbb2Zmc2V0ICsgaV0gPSAoKHZhbHVlIC8gbXVsKSA+PiAwKSAtIHN1YiAmIDB4RkZcbiAgfVxuXG4gIHJldHVybiBvZmZzZXQgKyBieXRlTGVuZ3RoXG59XG5cbkJ1ZmZlci5wcm90b3R5cGUud3JpdGVJbnRCRSA9IGZ1bmN0aW9uIHdyaXRlSW50QkUgKHZhbHVlLCBvZmZzZXQsIGJ5dGVMZW5ndGgsIG5vQXNzZXJ0KSB7XG4gIHZhbHVlID0gK3ZhbHVlXG4gIG9mZnNldCA9IG9mZnNldCA+Pj4gMFxuICBpZiAoIW5vQXNzZXJ0KSB7XG4gICAgY29uc3QgbGltaXQgPSBNYXRoLnBvdygyLCAoOCAqIGJ5dGVMZW5ndGgpIC0gMSlcblxuICAgIGNoZWNrSW50KHRoaXMsIHZhbHVlLCBvZmZzZXQsIGJ5dGVMZW5ndGgsIGxpbWl0IC0gMSwgLWxpbWl0KVxuICB9XG5cbiAgbGV0IGkgPSBieXRlTGVuZ3RoIC0gMVxuICBsZXQgbXVsID0gMVxuICBsZXQgc3ViID0gMFxuICB0aGlzW29mZnNldCArIGldID0gdmFsdWUgJiAweEZGXG4gIHdoaWxlICgtLWkgPj0gMCAmJiAobXVsICo9IDB4MTAwKSkge1xuICAgIGlmICh2YWx1ZSA8IDAgJiYgc3ViID09PSAwICYmIHRoaXNbb2Zmc2V0ICsgaSArIDFdICE9PSAwKSB7XG4gICAgICBzdWIgPSAxXG4gICAgfVxuICAgIHRoaXNbb2Zmc2V0ICsgaV0gPSAoKHZhbHVlIC8gbXVsKSA+PiAwKSAtIHN1YiAmIDB4RkZcbiAgfVxuXG4gIHJldHVybiBvZmZzZXQgKyBieXRlTGVuZ3RoXG59XG5cbkJ1ZmZlci5wcm90b3R5cGUud3JpdGVJbnQ4ID0gZnVuY3Rpb24gd3JpdGVJbnQ4ICh2YWx1ZSwgb2Zmc2V0LCBub0Fzc2VydCkge1xuICB2YWx1ZSA9ICt2YWx1ZVxuICBvZmZzZXQgPSBvZmZzZXQgPj4+IDBcbiAgaWYgKCFub0Fzc2VydCkgY2hlY2tJbnQodGhpcywgdmFsdWUsIG9mZnNldCwgMSwgMHg3ZiwgLTB4ODApXG4gIGlmICh2YWx1ZSA8IDApIHZhbHVlID0gMHhmZiArIHZhbHVlICsgMVxuICB0aGlzW29mZnNldF0gPSAodmFsdWUgJiAweGZmKVxuICByZXR1cm4gb2Zmc2V0ICsgMVxufVxuXG5CdWZmZXIucHJvdG90eXBlLndyaXRlSW50MTZMRSA9IGZ1bmN0aW9uIHdyaXRlSW50MTZMRSAodmFsdWUsIG9mZnNldCwgbm9Bc3NlcnQpIHtcbiAgdmFsdWUgPSArdmFsdWVcbiAgb2Zmc2V0ID0gb2Zmc2V0ID4+PiAwXG4gIGlmICghbm9Bc3NlcnQpIGNoZWNrSW50KHRoaXMsIHZhbHVlLCBvZmZzZXQsIDIsIDB4N2ZmZiwgLTB4ODAwMClcbiAgdGhpc1tvZmZzZXRdID0gKHZhbHVlICYgMHhmZilcbiAgdGhpc1tvZmZzZXQgKyAxXSA9ICh2YWx1ZSA+Pj4gOClcbiAgcmV0dXJuIG9mZnNldCArIDJcbn1cblxuQnVmZmVyLnByb3RvdHlwZS53cml0ZUludDE2QkUgPSBmdW5jdGlvbiB3cml0ZUludDE2QkUgKHZhbHVlLCBvZmZzZXQsIG5vQXNzZXJ0KSB7XG4gIHZhbHVlID0gK3ZhbHVlXG4gIG9mZnNldCA9IG9mZnNldCA+Pj4gMFxuICBpZiAoIW5vQXNzZXJ0KSBjaGVja0ludCh0aGlzLCB2YWx1ZSwgb2Zmc2V0LCAyLCAweDdmZmYsIC0weDgwMDApXG4gIHRoaXNbb2Zmc2V0XSA9ICh2YWx1ZSA+Pj4gOClcbiAgdGhpc1tvZmZzZXQgKyAxXSA9ICh2YWx1ZSAmIDB4ZmYpXG4gIHJldHVybiBvZmZzZXQgKyAyXG59XG5cbkJ1ZmZlci5wcm90b3R5cGUud3JpdGVJbnQzMkxFID0gZnVuY3Rpb24gd3JpdGVJbnQzMkxFICh2YWx1ZSwgb2Zmc2V0LCBub0Fzc2VydCkge1xuICB2YWx1ZSA9ICt2YWx1ZVxuICBvZmZzZXQgPSBvZmZzZXQgPj4+IDBcbiAgaWYgKCFub0Fzc2VydCkgY2hlY2tJbnQodGhpcywgdmFsdWUsIG9mZnNldCwgNCwgMHg3ZmZmZmZmZiwgLTB4ODAwMDAwMDApXG4gIHRoaXNbb2Zmc2V0XSA9ICh2YWx1ZSAmIDB4ZmYpXG4gIHRoaXNbb2Zmc2V0ICsgMV0gPSAodmFsdWUgPj4+IDgpXG4gIHRoaXNbb2Zmc2V0ICsgMl0gPSAodmFsdWUgPj4+IDE2KVxuICB0aGlzW29mZnNldCArIDNdID0gKHZhbHVlID4+PiAyNClcbiAgcmV0dXJuIG9mZnNldCArIDRcbn1cblxuQnVmZmVyLnByb3RvdHlwZS53cml0ZUludDMyQkUgPSBmdW5jdGlvbiB3cml0ZUludDMyQkUgKHZhbHVlLCBvZmZzZXQsIG5vQXNzZXJ0KSB7XG4gIHZhbHVlID0gK3ZhbHVlXG4gIG9mZnNldCA9IG9mZnNldCA+Pj4gMFxuICBpZiAoIW5vQXNzZXJ0KSBjaGVja0ludCh0aGlzLCB2YWx1ZSwgb2Zmc2V0LCA0LCAweDdmZmZmZmZmLCAtMHg4MDAwMDAwMClcbiAgaWYgKHZhbHVlIDwgMCkgdmFsdWUgPSAweGZmZmZmZmZmICsgdmFsdWUgKyAxXG4gIHRoaXNbb2Zmc2V0XSA9ICh2YWx1ZSA+Pj4gMjQpXG4gIHRoaXNbb2Zmc2V0ICsgMV0gPSAodmFsdWUgPj4+IDE2KVxuICB0aGlzW29mZnNldCArIDJdID0gKHZhbHVlID4+PiA4KVxuICB0aGlzW29mZnNldCArIDNdID0gKHZhbHVlICYgMHhmZilcbiAgcmV0dXJuIG9mZnNldCArIDRcbn1cblxuQnVmZmVyLnByb3RvdHlwZS53cml0ZUJpZ0ludDY0TEUgPSBkZWZpbmVCaWdJbnRNZXRob2QoZnVuY3Rpb24gd3JpdGVCaWdJbnQ2NExFICh2YWx1ZSwgb2Zmc2V0ID0gMCkge1xuICByZXR1cm4gd3J0QmlnVUludDY0TEUodGhpcywgdmFsdWUsIG9mZnNldCwgLUJpZ0ludCgnMHg4MDAwMDAwMDAwMDAwMDAwJyksIEJpZ0ludCgnMHg3ZmZmZmZmZmZmZmZmZmZmJykpXG59KVxuXG5CdWZmZXIucHJvdG90eXBlLndyaXRlQmlnSW50NjRCRSA9IGRlZmluZUJpZ0ludE1ldGhvZChmdW5jdGlvbiB3cml0ZUJpZ0ludDY0QkUgKHZhbHVlLCBvZmZzZXQgPSAwKSB7XG4gIHJldHVybiB3cnRCaWdVSW50NjRCRSh0aGlzLCB2YWx1ZSwgb2Zmc2V0LCAtQmlnSW50KCcweDgwMDAwMDAwMDAwMDAwMDAnKSwgQmlnSW50KCcweDdmZmZmZmZmZmZmZmZmZmYnKSlcbn0pXG5cbmZ1bmN0aW9uIGNoZWNrSUVFRTc1NCAoYnVmLCB2YWx1ZSwgb2Zmc2V0LCBleHQsIG1heCwgbWluKSB7XG4gIGlmIChvZmZzZXQgKyBleHQgPiBidWYubGVuZ3RoKSB0aHJvdyBuZXcgUmFuZ2VFcnJvcignSW5kZXggb3V0IG9mIHJhbmdlJylcbiAgaWYgKG9mZnNldCA8IDApIHRocm93IG5ldyBSYW5nZUVycm9yKCdJbmRleCBvdXQgb2YgcmFuZ2UnKVxufVxuXG5mdW5jdGlvbiB3cml0ZUZsb2F0IChidWYsIHZhbHVlLCBvZmZzZXQsIGxpdHRsZUVuZGlhbiwgbm9Bc3NlcnQpIHtcbiAgdmFsdWUgPSArdmFsdWVcbiAgb2Zmc2V0ID0gb2Zmc2V0ID4+PiAwXG4gIGlmICghbm9Bc3NlcnQpIHtcbiAgICBjaGVja0lFRUU3NTQoYnVmLCB2YWx1ZSwgb2Zmc2V0LCA0LCAzLjQwMjgyMzQ2NjM4NTI4ODZlKzM4LCAtMy40MDI4MjM0NjYzODUyODg2ZSszOClcbiAgfVxuICBpZWVlNzU0LndyaXRlKGJ1ZiwgdmFsdWUsIG9mZnNldCwgbGl0dGxlRW5kaWFuLCAyMywgNClcbiAgcmV0dXJuIG9mZnNldCArIDRcbn1cblxuQnVmZmVyLnByb3RvdHlwZS53cml0ZUZsb2F0TEUgPSBmdW5jdGlvbiB3cml0ZUZsb2F0TEUgKHZhbHVlLCBvZmZzZXQsIG5vQXNzZXJ0KSB7XG4gIHJldHVybiB3cml0ZUZsb2F0KHRoaXMsIHZhbHVlLCBvZmZzZXQsIHRydWUsIG5vQXNzZXJ0KVxufVxuXG5CdWZmZXIucHJvdG90eXBlLndyaXRlRmxvYXRCRSA9IGZ1bmN0aW9uIHdyaXRlRmxvYXRCRSAodmFsdWUsIG9mZnNldCwgbm9Bc3NlcnQpIHtcbiAgcmV0dXJuIHdyaXRlRmxvYXQodGhpcywgdmFsdWUsIG9mZnNldCwgZmFsc2UsIG5vQXNzZXJ0KVxufVxuXG5mdW5jdGlvbiB3cml0ZURvdWJsZSAoYnVmLCB2YWx1ZSwgb2Zmc2V0LCBsaXR0bGVFbmRpYW4sIG5vQXNzZXJ0KSB7XG4gIHZhbHVlID0gK3ZhbHVlXG4gIG9mZnNldCA9IG9mZnNldCA+Pj4gMFxuICBpZiAoIW5vQXNzZXJ0KSB7XG4gICAgY2hlY2tJRUVFNzU0KGJ1ZiwgdmFsdWUsIG9mZnNldCwgOCwgMS43OTc2OTMxMzQ4NjIzMTU3RSszMDgsIC0xLjc5NzY5MzEzNDg2MjMxNTdFKzMwOClcbiAgfVxuICBpZWVlNzU0LndyaXRlKGJ1ZiwgdmFsdWUsIG9mZnNldCwgbGl0dGxlRW5kaWFuLCA1MiwgOClcbiAgcmV0dXJuIG9mZnNldCArIDhcbn1cblxuQnVmZmVyLnByb3RvdHlwZS53cml0ZURvdWJsZUxFID0gZnVuY3Rpb24gd3JpdGVEb3VibGVMRSAodmFsdWUsIG9mZnNldCwgbm9Bc3NlcnQpIHtcbiAgcmV0dXJuIHdyaXRlRG91YmxlKHRoaXMsIHZhbHVlLCBvZmZzZXQsIHRydWUsIG5vQXNzZXJ0KVxufVxuXG5CdWZmZXIucHJvdG90eXBlLndyaXRlRG91YmxlQkUgPSBmdW5jdGlvbiB3cml0ZURvdWJsZUJFICh2YWx1ZSwgb2Zmc2V0LCBub0Fzc2VydCkge1xuICByZXR1cm4gd3JpdGVEb3VibGUodGhpcywgdmFsdWUsIG9mZnNldCwgZmFsc2UsIG5vQXNzZXJ0KVxufVxuXG4vLyBjb3B5KHRhcmdldEJ1ZmZlciwgdGFyZ2V0U3RhcnQ9MCwgc291cmNlU3RhcnQ9MCwgc291cmNlRW5kPWJ1ZmZlci5sZW5ndGgpXG5CdWZmZXIucHJvdG90eXBlLmNvcHkgPSBmdW5jdGlvbiBjb3B5ICh0YXJnZXQsIHRhcmdldFN0YXJ0LCBzdGFydCwgZW5kKSB7XG4gIGlmICghQnVmZmVyLmlzQnVmZmVyKHRhcmdldCkpIHRocm93IG5ldyBUeXBlRXJyb3IoJ2FyZ3VtZW50IHNob3VsZCBiZSBhIEJ1ZmZlcicpXG4gIGlmICghc3RhcnQpIHN0YXJ0ID0gMFxuICBpZiAoIWVuZCAmJiBlbmQgIT09IDApIGVuZCA9IHRoaXMubGVuZ3RoXG4gIGlmICh0YXJnZXRTdGFydCA+PSB0YXJnZXQubGVuZ3RoKSB0YXJnZXRTdGFydCA9IHRhcmdldC5sZW5ndGhcbiAgaWYgKCF0YXJnZXRTdGFydCkgdGFyZ2V0U3RhcnQgPSAwXG4gIGlmIChlbmQgPiAwICYmIGVuZCA8IHN0YXJ0KSBlbmQgPSBzdGFydFxuXG4gIC8vIENvcHkgMCBieXRlczsgd2UncmUgZG9uZVxuICBpZiAoZW5kID09PSBzdGFydCkgcmV0dXJuIDBcbiAgaWYgKHRhcmdldC5sZW5ndGggPT09IDAgfHwgdGhpcy5sZW5ndGggPT09IDApIHJldHVybiAwXG5cbiAgLy8gRmF0YWwgZXJyb3IgY29uZGl0aW9uc1xuICBpZiAodGFyZ2V0U3RhcnQgPCAwKSB7XG4gICAgdGhyb3cgbmV3IFJhbmdlRXJyb3IoJ3RhcmdldFN0YXJ0IG91dCBvZiBib3VuZHMnKVxuICB9XG4gIGlmIChzdGFydCA8IDAgfHwgc3RhcnQgPj0gdGhpcy5sZW5ndGgpIHRocm93IG5ldyBSYW5nZUVycm9yKCdJbmRleCBvdXQgb2YgcmFuZ2UnKVxuICBpZiAoZW5kIDwgMCkgdGhyb3cgbmV3IFJhbmdlRXJyb3IoJ3NvdXJjZUVuZCBvdXQgb2YgYm91bmRzJylcblxuICAvLyBBcmUgd2Ugb29iP1xuICBpZiAoZW5kID4gdGhpcy5sZW5ndGgpIGVuZCA9IHRoaXMubGVuZ3RoXG4gIGlmICh0YXJnZXQubGVuZ3RoIC0gdGFyZ2V0U3RhcnQgPCBlbmQgLSBzdGFydCkge1xuICAgIGVuZCA9IHRhcmdldC5sZW5ndGggLSB0YXJnZXRTdGFydCArIHN0YXJ0XG4gIH1cblxuICBjb25zdCBsZW4gPSBlbmQgLSBzdGFydFxuXG4gIGlmICh0aGlzID09PSB0YXJnZXQgJiYgdHlwZW9mIFVpbnQ4QXJyYXkucHJvdG90eXBlLmNvcHlXaXRoaW4gPT09ICdmdW5jdGlvbicpIHtcbiAgICAvLyBVc2UgYnVpbHQtaW4gd2hlbiBhdmFpbGFibGUsIG1pc3NpbmcgZnJvbSBJRTExXG4gICAgdGhpcy5jb3B5V2l0aGluKHRhcmdldFN0YXJ0LCBzdGFydCwgZW5kKVxuICB9IGVsc2Uge1xuICAgIFVpbnQ4QXJyYXkucHJvdG90eXBlLnNldC5jYWxsKFxuICAgICAgdGFyZ2V0LFxuICAgICAgdGhpcy5zdWJhcnJheShzdGFydCwgZW5kKSxcbiAgICAgIHRhcmdldFN0YXJ0XG4gICAgKVxuICB9XG5cbiAgcmV0dXJuIGxlblxufVxuXG4vLyBVc2FnZTpcbi8vICAgIGJ1ZmZlci5maWxsKG51bWJlclssIG9mZnNldFssIGVuZF1dKVxuLy8gICAgYnVmZmVyLmZpbGwoYnVmZmVyWywgb2Zmc2V0WywgZW5kXV0pXG4vLyAgICBidWZmZXIuZmlsbChzdHJpbmdbLCBvZmZzZXRbLCBlbmRdXVssIGVuY29kaW5nXSlcbkJ1ZmZlci5wcm90b3R5cGUuZmlsbCA9IGZ1bmN0aW9uIGZpbGwgKHZhbCwgc3RhcnQsIGVuZCwgZW5jb2RpbmcpIHtcbiAgLy8gSGFuZGxlIHN0cmluZyBjYXNlczpcbiAgaWYgKHR5cGVvZiB2YWwgPT09ICdzdHJpbmcnKSB7XG4gICAgaWYgKHR5cGVvZiBzdGFydCA9PT0gJ3N0cmluZycpIHtcbiAgICAgIGVuY29kaW5nID0gc3RhcnRcbiAgICAgIHN0YXJ0ID0gMFxuICAgICAgZW5kID0gdGhpcy5sZW5ndGhcbiAgICB9IGVsc2UgaWYgKHR5cGVvZiBlbmQgPT09ICdzdHJpbmcnKSB7XG4gICAgICBlbmNvZGluZyA9IGVuZFxuICAgICAgZW5kID0gdGhpcy5sZW5ndGhcbiAgICB9XG4gICAgaWYgKGVuY29kaW5nICE9PSB1bmRlZmluZWQgJiYgdHlwZW9mIGVuY29kaW5nICE9PSAnc3RyaW5nJykge1xuICAgICAgdGhyb3cgbmV3IFR5cGVFcnJvcignZW5jb2RpbmcgbXVzdCBiZSBhIHN0cmluZycpXG4gICAgfVxuICAgIGlmICh0eXBlb2YgZW5jb2RpbmcgPT09ICdzdHJpbmcnICYmICFCdWZmZXIuaXNFbmNvZGluZyhlbmNvZGluZykpIHtcbiAgICAgIHRocm93IG5ldyBUeXBlRXJyb3IoJ1Vua25vd24gZW5jb2Rpbmc6ICcgKyBlbmNvZGluZylcbiAgICB9XG4gICAgaWYgKHZhbC5sZW5ndGggPT09IDEpIHtcbiAgICAgIGNvbnN0IGNvZGUgPSB2YWwuY2hhckNvZGVBdCgwKVxuICAgICAgaWYgKChlbmNvZGluZyA9PT0gJ3V0ZjgnICYmIGNvZGUgPCAxMjgpIHx8XG4gICAgICAgICAgZW5jb2RpbmcgPT09ICdsYXRpbjEnKSB7XG4gICAgICAgIC8vIEZhc3QgcGF0aDogSWYgYHZhbGAgZml0cyBpbnRvIGEgc2luZ2xlIGJ5dGUsIHVzZSB0aGF0IG51bWVyaWMgdmFsdWUuXG4gICAgICAgIHZhbCA9IGNvZGVcbiAgICAgIH1cbiAgICB9XG4gIH0gZWxzZSBpZiAodHlwZW9mIHZhbCA9PT0gJ251bWJlcicpIHtcbiAgICB2YWwgPSB2YWwgJiAyNTVcbiAgfSBlbHNlIGlmICh0eXBlb2YgdmFsID09PSAnYm9vbGVhbicpIHtcbiAgICB2YWwgPSBOdW1iZXIodmFsKVxuICB9XG5cbiAgLy8gSW52YWxpZCByYW5nZXMgYXJlIG5vdCBzZXQgdG8gYSBkZWZhdWx0LCBzbyBjYW4gcmFuZ2UgY2hlY2sgZWFybHkuXG4gIGlmIChzdGFydCA8IDAgfHwgdGhpcy5sZW5ndGggPCBzdGFydCB8fCB0aGlzLmxlbmd0aCA8IGVuZCkge1xuICAgIHRocm93IG5ldyBSYW5nZUVycm9yKCdPdXQgb2YgcmFuZ2UgaW5kZXgnKVxuICB9XG5cbiAgaWYgKGVuZCA8PSBzdGFydCkge1xuICAgIHJldHVybiB0aGlzXG4gIH1cblxuICBzdGFydCA9IHN0YXJ0ID4+PiAwXG4gIGVuZCA9IGVuZCA9PT0gdW5kZWZpbmVkID8gdGhpcy5sZW5ndGggOiBlbmQgPj4+IDBcblxuICBpZiAoIXZhbCkgdmFsID0gMFxuXG4gIGxldCBpXG4gIGlmICh0eXBlb2YgdmFsID09PSAnbnVtYmVyJykge1xuICAgIGZvciAoaSA9IHN0YXJ0OyBpIDwgZW5kOyArK2kpIHtcbiAgICAgIHRoaXNbaV0gPSB2YWxcbiAgICB9XG4gIH0gZWxzZSB7XG4gICAgY29uc3QgYnl0ZXMgPSBCdWZmZXIuaXNCdWZmZXIodmFsKVxuICAgICAgPyB2YWxcbiAgICAgIDogQnVmZmVyLmZyb20odmFsLCBlbmNvZGluZylcbiAgICBjb25zdCBsZW4gPSBieXRlcy5sZW5ndGhcbiAgICBpZiAobGVuID09PSAwKSB7XG4gICAgICB0aHJvdyBuZXcgVHlwZUVycm9yKCdUaGUgdmFsdWUgXCInICsgdmFsICtcbiAgICAgICAgJ1wiIGlzIGludmFsaWQgZm9yIGFyZ3VtZW50IFwidmFsdWVcIicpXG4gICAgfVxuICAgIGZvciAoaSA9IDA7IGkgPCBlbmQgLSBzdGFydDsgKytpKSB7XG4gICAgICB0aGlzW2kgKyBzdGFydF0gPSBieXRlc1tpICUgbGVuXVxuICAgIH1cbiAgfVxuXG4gIHJldHVybiB0aGlzXG59XG5cbi8vIENVU1RPTSBFUlJPUlNcbi8vID09PT09PT09PT09PT1cblxuLy8gU2ltcGxpZmllZCB2ZXJzaW9ucyBmcm9tIE5vZGUsIGNoYW5nZWQgZm9yIEJ1ZmZlci1vbmx5IHVzYWdlXG5jb25zdCBlcnJvcnMgPSB7fVxuZnVuY3Rpb24gRSAoc3ltLCBnZXRNZXNzYWdlLCBCYXNlKSB7XG4gIGVycm9yc1tzeW1dID0gY2xhc3MgTm9kZUVycm9yIGV4dGVuZHMgQmFzZSB7XG4gICAgY29uc3RydWN0b3IgKCkge1xuICAgICAgc3VwZXIoKVxuXG4gICAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkodGhpcywgJ21lc3NhZ2UnLCB7XG4gICAgICAgIHZhbHVlOiBnZXRNZXNzYWdlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyksXG4gICAgICAgIHdyaXRhYmxlOiB0cnVlLFxuICAgICAgICBjb25maWd1cmFibGU6IHRydWVcbiAgICAgIH0pXG5cbiAgICAgIC8vIEFkZCB0aGUgZXJyb3IgY29kZSB0byB0aGUgbmFtZSB0byBpbmNsdWRlIGl0IGluIHRoZSBzdGFjayB0cmFjZS5cbiAgICAgIHRoaXMubmFtZSA9IGAke3RoaXMubmFtZX0gWyR7c3ltfV1gXG4gICAgICAvLyBBY2Nlc3MgdGhlIHN0YWNrIHRvIGdlbmVyYXRlIHRoZSBlcnJvciBtZXNzYWdlIGluY2x1ZGluZyB0aGUgZXJyb3IgY29kZVxuICAgICAgLy8gZnJvbSB0aGUgbmFtZS5cbiAgICAgIHRoaXMuc3RhY2sgLy8gZXNsaW50LWRpc2FibGUtbGluZSBuby11bnVzZWQtZXhwcmVzc2lvbnNcbiAgICAgIC8vIFJlc2V0IHRoZSBuYW1lIHRvIHRoZSBhY3R1YWwgbmFtZS5cbiAgICAgIGRlbGV0ZSB0aGlzLm5hbWVcbiAgICB9XG5cbiAgICBnZXQgY29kZSAoKSB7XG4gICAgICByZXR1cm4gc3ltXG4gICAgfVxuXG4gICAgc2V0IGNvZGUgKHZhbHVlKSB7XG4gICAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkodGhpcywgJ2NvZGUnLCB7XG4gICAgICAgIGNvbmZpZ3VyYWJsZTogdHJ1ZSxcbiAgICAgICAgZW51bWVyYWJsZTogdHJ1ZSxcbiAgICAgICAgdmFsdWUsXG4gICAgICAgIHdyaXRhYmxlOiB0cnVlXG4gICAgICB9KVxuICAgIH1cblxuICAgIHRvU3RyaW5nICgpIHtcbiAgICAgIHJldHVybiBgJHt0aGlzLm5hbWV9IFske3N5bX1dOiAke3RoaXMubWVzc2FnZX1gXG4gICAgfVxuICB9XG59XG5cbkUoJ0VSUl9CVUZGRVJfT1VUX09GX0JPVU5EUycsXG4gIGZ1bmN0aW9uIChuYW1lKSB7XG4gICAgaWYgKG5hbWUpIHtcbiAgICAgIHJldHVybiBgJHtuYW1lfSBpcyBvdXRzaWRlIG9mIGJ1ZmZlciBib3VuZHNgXG4gICAgfVxuXG4gICAgcmV0dXJuICdBdHRlbXB0IHRvIGFjY2VzcyBtZW1vcnkgb3V0c2lkZSBidWZmZXIgYm91bmRzJ1xuICB9LCBSYW5nZUVycm9yKVxuRSgnRVJSX0lOVkFMSURfQVJHX1RZUEUnLFxuICBmdW5jdGlvbiAobmFtZSwgYWN0dWFsKSB7XG4gICAgcmV0dXJuIGBUaGUgXCIke25hbWV9XCIgYXJndW1lbnQgbXVzdCBiZSBvZiB0eXBlIG51bWJlci4gUmVjZWl2ZWQgdHlwZSAke3R5cGVvZiBhY3R1YWx9YFxuICB9LCBUeXBlRXJyb3IpXG5FKCdFUlJfT1VUX09GX1JBTkdFJyxcbiAgZnVuY3Rpb24gKHN0ciwgcmFuZ2UsIGlucHV0KSB7XG4gICAgbGV0IG1zZyA9IGBUaGUgdmFsdWUgb2YgXCIke3N0cn1cIiBpcyBvdXQgb2YgcmFuZ2UuYFxuICAgIGxldCByZWNlaXZlZCA9IGlucHV0XG4gICAgaWYgKE51bWJlci5pc0ludGVnZXIoaW5wdXQpICYmIE1hdGguYWJzKGlucHV0KSA+IDIgKiogMzIpIHtcbiAgICAgIHJlY2VpdmVkID0gYWRkTnVtZXJpY2FsU2VwYXJhdG9yKFN0cmluZyhpbnB1dCkpXG4gICAgfSBlbHNlIGlmICh0eXBlb2YgaW5wdXQgPT09ICdiaWdpbnQnKSB7XG4gICAgICByZWNlaXZlZCA9IFN0cmluZyhpbnB1dClcbiAgICAgIGlmIChpbnB1dCA+IEJpZ0ludCgyKSAqKiBCaWdJbnQoMzIpIHx8IGlucHV0IDwgLShCaWdJbnQoMikgKiogQmlnSW50KDMyKSkpIHtcbiAgICAgICAgcmVjZWl2ZWQgPSBhZGROdW1lcmljYWxTZXBhcmF0b3IocmVjZWl2ZWQpXG4gICAgICB9XG4gICAgICByZWNlaXZlZCArPSAnbidcbiAgICB9XG4gICAgbXNnICs9IGAgSXQgbXVzdCBiZSAke3JhbmdlfS4gUmVjZWl2ZWQgJHtyZWNlaXZlZH1gXG4gICAgcmV0dXJuIG1zZ1xuICB9LCBSYW5nZUVycm9yKVxuXG5mdW5jdGlvbiBhZGROdW1lcmljYWxTZXBhcmF0b3IgKHZhbCkge1xuICBsZXQgcmVzID0gJydcbiAgbGV0IGkgPSB2YWwubGVuZ3RoXG4gIGNvbnN0IHN0YXJ0ID0gdmFsWzBdID09PSAnLScgPyAxIDogMFxuICBmb3IgKDsgaSA+PSBzdGFydCArIDQ7IGkgLT0gMykge1xuICAgIHJlcyA9IGBfJHt2YWwuc2xpY2UoaSAtIDMsIGkpfSR7cmVzfWBcbiAgfVxuICByZXR1cm4gYCR7dmFsLnNsaWNlKDAsIGkpfSR7cmVzfWBcbn1cblxuLy8gQ0hFQ0sgRlVOQ1RJT05TXG4vLyA9PT09PT09PT09PT09PT1cblxuZnVuY3Rpb24gY2hlY2tCb3VuZHMgKGJ1Ziwgb2Zmc2V0LCBieXRlTGVuZ3RoKSB7XG4gIHZhbGlkYXRlTnVtYmVyKG9mZnNldCwgJ29mZnNldCcpXG4gIGlmIChidWZbb2Zmc2V0XSA9PT0gdW5kZWZpbmVkIHx8IGJ1ZltvZmZzZXQgKyBieXRlTGVuZ3RoXSA9PT0gdW5kZWZpbmVkKSB7XG4gICAgYm91bmRzRXJyb3Iob2Zmc2V0LCBidWYubGVuZ3RoIC0gKGJ5dGVMZW5ndGggKyAxKSlcbiAgfVxufVxuXG5mdW5jdGlvbiBjaGVja0ludEJJICh2YWx1ZSwgbWluLCBtYXgsIGJ1Ziwgb2Zmc2V0LCBieXRlTGVuZ3RoKSB7XG4gIGlmICh2YWx1ZSA+IG1heCB8fCB2YWx1ZSA8IG1pbikge1xuICAgIGNvbnN0IG4gPSB0eXBlb2YgbWluID09PSAnYmlnaW50JyA/ICduJyA6ICcnXG4gICAgbGV0IHJhbmdlXG4gICAgaWYgKGJ5dGVMZW5ndGggPiAzKSB7XG4gICAgICBpZiAobWluID09PSAwIHx8IG1pbiA9PT0gQmlnSW50KDApKSB7XG4gICAgICAgIHJhbmdlID0gYD49IDAke259IGFuZCA8IDIke259ICoqICR7KGJ5dGVMZW5ndGggKyAxKSAqIDh9JHtufWBcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIHJhbmdlID0gYD49IC0oMiR7bn0gKiogJHsoYnl0ZUxlbmd0aCArIDEpICogOCAtIDF9JHtufSkgYW5kIDwgMiAqKiBgICtcbiAgICAgICAgICAgICAgICBgJHsoYnl0ZUxlbmd0aCArIDEpICogOCAtIDF9JHtufWBcbiAgICAgIH1cbiAgICB9IGVsc2Uge1xuICAgICAgcmFuZ2UgPSBgPj0gJHttaW59JHtufSBhbmQgPD0gJHttYXh9JHtufWBcbiAgICB9XG4gICAgdGhyb3cgbmV3IGVycm9ycy5FUlJfT1VUX09GX1JBTkdFKCd2YWx1ZScsIHJhbmdlLCB2YWx1ZSlcbiAgfVxuICBjaGVja0JvdW5kcyhidWYsIG9mZnNldCwgYnl0ZUxlbmd0aClcbn1cblxuZnVuY3Rpb24gdmFsaWRhdGVOdW1iZXIgKHZhbHVlLCBuYW1lKSB7XG4gIGlmICh0eXBlb2YgdmFsdWUgIT09ICdudW1iZXInKSB7XG4gICAgdGhyb3cgbmV3IGVycm9ycy5FUlJfSU5WQUxJRF9BUkdfVFlQRShuYW1lLCAnbnVtYmVyJywgdmFsdWUpXG4gIH1cbn1cblxuZnVuY3Rpb24gYm91bmRzRXJyb3IgKHZhbHVlLCBsZW5ndGgsIHR5cGUpIHtcbiAgaWYgKE1hdGguZmxvb3IodmFsdWUpICE9PSB2YWx1ZSkge1xuICAgIHZhbGlkYXRlTnVtYmVyKHZhbHVlLCB0eXBlKVxuICAgIHRocm93IG5ldyBlcnJvcnMuRVJSX09VVF9PRl9SQU5HRSh0eXBlIHx8ICdvZmZzZXQnLCAnYW4gaW50ZWdlcicsIHZhbHVlKVxuICB9XG5cbiAgaWYgKGxlbmd0aCA8IDApIHtcbiAgICB0aHJvdyBuZXcgZXJyb3JzLkVSUl9CVUZGRVJfT1VUX09GX0JPVU5EUygpXG4gIH1cblxuICB0aHJvdyBuZXcgZXJyb3JzLkVSUl9PVVRfT0ZfUkFOR0UodHlwZSB8fCAnb2Zmc2V0JyxcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGA+PSAke3R5cGUgPyAxIDogMH0gYW5kIDw9ICR7bGVuZ3RofWAsXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2YWx1ZSlcbn1cblxuLy8gSEVMUEVSIEZVTkNUSU9OU1xuLy8gPT09PT09PT09PT09PT09PVxuXG5jb25zdCBJTlZBTElEX0JBU0U2NF9SRSA9IC9bXisvMC05QS1aYS16LV9dL2dcblxuZnVuY3Rpb24gYmFzZTY0Y2xlYW4gKHN0cikge1xuICAvLyBOb2RlIHRha2VzIGVxdWFsIHNpZ25zIGFzIGVuZCBvZiB0aGUgQmFzZTY0IGVuY29kaW5nXG4gIHN0ciA9IHN0ci5zcGxpdCgnPScpWzBdXG4gIC8vIE5vZGUgc3RyaXBzIG91dCBpbnZhbGlkIGNoYXJhY3RlcnMgbGlrZSBcXG4gYW5kIFxcdCBmcm9tIHRoZSBzdHJpbmcsIGJhc2U2NC1qcyBkb2VzIG5vdFxuICBzdHIgPSBzdHIudHJpbSgpLnJlcGxhY2UoSU5WQUxJRF9CQVNFNjRfUkUsICcnKVxuICAvLyBOb2RlIGNvbnZlcnRzIHN0cmluZ3Mgd2l0aCBsZW5ndGggPCAyIHRvICcnXG4gIGlmIChzdHIubGVuZ3RoIDwgMikgcmV0dXJuICcnXG4gIC8vIE5vZGUgYWxsb3dzIGZvciBub24tcGFkZGVkIGJhc2U2NCBzdHJpbmdzIChtaXNzaW5nIHRyYWlsaW5nID09PSksIGJhc2U2NC1qcyBkb2VzIG5vdFxuICB3aGlsZSAoc3RyLmxlbmd0aCAlIDQgIT09IDApIHtcbiAgICBzdHIgPSBzdHIgKyAnPSdcbiAgfVxuICByZXR1cm4gc3RyXG59XG5cbmZ1bmN0aW9uIHV0ZjhUb0J5dGVzIChzdHJpbmcsIHVuaXRzKSB7XG4gIHVuaXRzID0gdW5pdHMgfHwgSW5maW5pdHlcbiAgbGV0IGNvZGVQb2ludFxuICBjb25zdCBsZW5ndGggPSBzdHJpbmcubGVuZ3RoXG4gIGxldCBsZWFkU3Vycm9nYXRlID0gbnVsbFxuICBjb25zdCBieXRlcyA9IFtdXG5cbiAgZm9yIChsZXQgaSA9IDA7IGkgPCBsZW5ndGg7ICsraSkge1xuICAgIGNvZGVQb2ludCA9IHN0cmluZy5jaGFyQ29kZUF0KGkpXG5cbiAgICAvLyBpcyBzdXJyb2dhdGUgY29tcG9uZW50XG4gICAgaWYgKGNvZGVQb2ludCA+IDB4RDdGRiAmJiBjb2RlUG9pbnQgPCAweEUwMDApIHtcbiAgICAgIC8vIGxhc3QgY2hhciB3YXMgYSBsZWFkXG4gICAgICBpZiAoIWxlYWRTdXJyb2dhdGUpIHtcbiAgICAgICAgLy8gbm8gbGVhZCB5ZXRcbiAgICAgICAgaWYgKGNvZGVQb2ludCA+IDB4REJGRikge1xuICAgICAgICAgIC8vIHVuZXhwZWN0ZWQgdHJhaWxcbiAgICAgICAgICBpZiAoKHVuaXRzIC09IDMpID4gLTEpIGJ5dGVzLnB1c2goMHhFRiwgMHhCRiwgMHhCRClcbiAgICAgICAgICBjb250aW51ZVxuICAgICAgICB9IGVsc2UgaWYgKGkgKyAxID09PSBsZW5ndGgpIHtcbiAgICAgICAgICAvLyB1bnBhaXJlZCBsZWFkXG4gICAgICAgICAgaWYgKCh1bml0cyAtPSAzKSA+IC0xKSBieXRlcy5wdXNoKDB4RUYsIDB4QkYsIDB4QkQpXG4gICAgICAgICAgY29udGludWVcbiAgICAgICAgfVxuXG4gICAgICAgIC8vIHZhbGlkIGxlYWRcbiAgICAgICAgbGVhZFN1cnJvZ2F0ZSA9IGNvZGVQb2ludFxuXG4gICAgICAgIGNvbnRpbnVlXG4gICAgICB9XG5cbiAgICAgIC8vIDIgbGVhZHMgaW4gYSByb3dcbiAgICAgIGlmIChjb2RlUG9pbnQgPCAweERDMDApIHtcbiAgICAgICAgaWYgKCh1bml0cyAtPSAzKSA+IC0xKSBieXRlcy5wdXNoKDB4RUYsIDB4QkYsIDB4QkQpXG4gICAgICAgIGxlYWRTdXJyb2dhdGUgPSBjb2RlUG9pbnRcbiAgICAgICAgY29udGludWVcbiAgICAgIH1cblxuICAgICAgLy8gdmFsaWQgc3Vycm9nYXRlIHBhaXJcbiAgICAgIGNvZGVQb2ludCA9IChsZWFkU3Vycm9nYXRlIC0gMHhEODAwIDw8IDEwIHwgY29kZVBvaW50IC0gMHhEQzAwKSArIDB4MTAwMDBcbiAgICB9IGVsc2UgaWYgKGxlYWRTdXJyb2dhdGUpIHtcbiAgICAgIC8vIHZhbGlkIGJtcCBjaGFyLCBidXQgbGFzdCBjaGFyIHdhcyBhIGxlYWRcbiAgICAgIGlmICgodW5pdHMgLT0gMykgPiAtMSkgYnl0ZXMucHVzaCgweEVGLCAweEJGLCAweEJEKVxuICAgIH1cblxuICAgIGxlYWRTdXJyb2dhdGUgPSBudWxsXG5cbiAgICAvLyBlbmNvZGUgdXRmOFxuICAgIGlmIChjb2RlUG9pbnQgPCAweDgwKSB7XG4gICAgICBpZiAoKHVuaXRzIC09IDEpIDwgMCkgYnJlYWtcbiAgICAgIGJ5dGVzLnB1c2goY29kZVBvaW50KVxuICAgIH0gZWxzZSBpZiAoY29kZVBvaW50IDwgMHg4MDApIHtcbiAgICAgIGlmICgodW5pdHMgLT0gMikgPCAwKSBicmVha1xuICAgICAgYnl0ZXMucHVzaChcbiAgICAgICAgY29kZVBvaW50ID4+IDB4NiB8IDB4QzAsXG4gICAgICAgIGNvZGVQb2ludCAmIDB4M0YgfCAweDgwXG4gICAgICApXG4gICAgfSBlbHNlIGlmIChjb2RlUG9pbnQgPCAweDEwMDAwKSB7XG4gICAgICBpZiAoKHVuaXRzIC09IDMpIDwgMCkgYnJlYWtcbiAgICAgIGJ5dGVzLnB1c2goXG4gICAgICAgIGNvZGVQb2ludCA+PiAweEMgfCAweEUwLFxuICAgICAgICBjb2RlUG9pbnQgPj4gMHg2ICYgMHgzRiB8IDB4ODAsXG4gICAgICAgIGNvZGVQb2ludCAmIDB4M0YgfCAweDgwXG4gICAgICApXG4gICAgfSBlbHNlIGlmIChjb2RlUG9pbnQgPCAweDExMDAwMCkge1xuICAgICAgaWYgKCh1bml0cyAtPSA0KSA8IDApIGJyZWFrXG4gICAgICBieXRlcy5wdXNoKFxuICAgICAgICBjb2RlUG9pbnQgPj4gMHgxMiB8IDB4RjAsXG4gICAgICAgIGNvZGVQb2ludCA+PiAweEMgJiAweDNGIHwgMHg4MCxcbiAgICAgICAgY29kZVBvaW50ID4+IDB4NiAmIDB4M0YgfCAweDgwLFxuICAgICAgICBjb2RlUG9pbnQgJiAweDNGIHwgMHg4MFxuICAgICAgKVxuICAgIH0gZWxzZSB7XG4gICAgICB0aHJvdyBuZXcgRXJyb3IoJ0ludmFsaWQgY29kZSBwb2ludCcpXG4gICAgfVxuICB9XG5cbiAgcmV0dXJuIGJ5dGVzXG59XG5cbmZ1bmN0aW9uIGFzY2lpVG9CeXRlcyAoc3RyKSB7XG4gIGNvbnN0IGJ5dGVBcnJheSA9IFtdXG4gIGZvciAobGV0IGkgPSAwOyBpIDwgc3RyLmxlbmd0aDsgKytpKSB7XG4gICAgLy8gTm9kZSdzIGNvZGUgc2VlbXMgdG8gYmUgZG9pbmcgdGhpcyBhbmQgbm90ICYgMHg3Ri4uXG4gICAgYnl0ZUFycmF5LnB1c2goc3RyLmNoYXJDb2RlQXQoaSkgJiAweEZGKVxuICB9XG4gIHJldHVybiBieXRlQXJyYXlcbn1cblxuZnVuY3Rpb24gdXRmMTZsZVRvQnl0ZXMgKHN0ciwgdW5pdHMpIHtcbiAgbGV0IGMsIGhpLCBsb1xuICBjb25zdCBieXRlQXJyYXkgPSBbXVxuICBmb3IgKGxldCBpID0gMDsgaSA8IHN0ci5sZW5ndGg7ICsraSkge1xuICAgIGlmICgodW5pdHMgLT0gMikgPCAwKSBicmVha1xuXG4gICAgYyA9IHN0ci5jaGFyQ29kZUF0KGkpXG4gICAgaGkgPSBjID4+IDhcbiAgICBsbyA9IGMgJSAyNTZcbiAgICBieXRlQXJyYXkucHVzaChsbylcbiAgICBieXRlQXJyYXkucHVzaChoaSlcbiAgfVxuXG4gIHJldHVybiBieXRlQXJyYXlcbn1cblxuZnVuY3Rpb24gYmFzZTY0VG9CeXRlcyAoc3RyKSB7XG4gIHJldHVybiBiYXNlNjQudG9CeXRlQXJyYXkoYmFzZTY0Y2xlYW4oc3RyKSlcbn1cblxuZnVuY3Rpb24gYmxpdEJ1ZmZlciAoc3JjLCBkc3QsIG9mZnNldCwgbGVuZ3RoKSB7XG4gIGxldCBpXG4gIGZvciAoaSA9IDA7IGkgPCBsZW5ndGg7ICsraSkge1xuICAgIGlmICgoaSArIG9mZnNldCA+PSBkc3QubGVuZ3RoKSB8fCAoaSA+PSBzcmMubGVuZ3RoKSkgYnJlYWtcbiAgICBkc3RbaSArIG9mZnNldF0gPSBzcmNbaV1cbiAgfVxuICByZXR1cm4gaVxufVxuXG4vLyBBcnJheUJ1ZmZlciBvciBVaW50OEFycmF5IG9iamVjdHMgZnJvbSBvdGhlciBjb250ZXh0cyAoaS5lLiBpZnJhbWVzKSBkbyBub3QgcGFzc1xuLy8gdGhlIGBpbnN0YW5jZW9mYCBjaGVjayBidXQgdGhleSBzaG91bGQgYmUgdHJlYXRlZCBhcyBvZiB0aGF0IHR5cGUuXG4vLyBTZWU6IGh0dHBzOi8vZ2l0aHViLmNvbS9mZXJvc3MvYnVmZmVyL2lzc3Vlcy8xNjZcbmZ1bmN0aW9uIGlzSW5zdGFuY2UgKG9iaiwgdHlwZSkge1xuICByZXR1cm4gb2JqIGluc3RhbmNlb2YgdHlwZSB8fFxuICAgIChvYmogIT0gbnVsbCAmJiBvYmouY29uc3RydWN0b3IgIT0gbnVsbCAmJiBvYmouY29uc3RydWN0b3IubmFtZSAhPSBudWxsICYmXG4gICAgICBvYmouY29uc3RydWN0b3IubmFtZSA9PT0gdHlwZS5uYW1lKVxufVxuZnVuY3Rpb24gbnVtYmVySXNOYU4gKG9iaikge1xuICAvLyBGb3IgSUUxMSBzdXBwb3J0XG4gIHJldHVybiBvYmogIT09IG9iaiAvLyBlc2xpbnQtZGlzYWJsZS1saW5lIG5vLXNlbGYtY29tcGFyZVxufVxuXG4vLyBDcmVhdGUgbG9va3VwIHRhYmxlIGZvciBgdG9TdHJpbmcoJ2hleCcpYFxuLy8gU2VlOiBodHRwczovL2dpdGh1Yi5jb20vZmVyb3NzL2J1ZmZlci9pc3N1ZXMvMjE5XG5jb25zdCBoZXhTbGljZUxvb2t1cFRhYmxlID0gKGZ1bmN0aW9uICgpIHtcbiAgY29uc3QgYWxwaGFiZXQgPSAnMDEyMzQ1Njc4OWFiY2RlZidcbiAgY29uc3QgdGFibGUgPSBuZXcgQXJyYXkoMjU2KVxuICBmb3IgKGxldCBpID0gMDsgaSA8IDE2OyArK2kpIHtcbiAgICBjb25zdCBpMTYgPSBpICogMTZcbiAgICBmb3IgKGxldCBqID0gMDsgaiA8IDE2OyArK2opIHtcbiAgICAgIHRhYmxlW2kxNiArIGpdID0gYWxwaGFiZXRbaV0gKyBhbHBoYWJldFtqXVxuICAgIH1cbiAgfVxuICByZXR1cm4gdGFibGVcbn0pKClcblxuLy8gUmV0dXJuIG5vdCBmdW5jdGlvbiB3aXRoIEVycm9yIGlmIEJpZ0ludCBub3Qgc3VwcG9ydGVkXG5mdW5jdGlvbiBkZWZpbmVCaWdJbnRNZXRob2QgKGZuKSB7XG4gIHJldHVybiB0eXBlb2YgQmlnSW50ID09PSAndW5kZWZpbmVkJyA/IEJ1ZmZlckJpZ0ludE5vdERlZmluZWQgOiBmblxufVxuXG5mdW5jdGlvbiBCdWZmZXJCaWdJbnROb3REZWZpbmVkICgpIHtcbiAgdGhyb3cgbmV3IEVycm9yKCdCaWdJbnQgbm90IHN1cHBvcnRlZCcpXG59XG4iLCAiaW1wb3J0IHtcbiAgICBuaXAwNCxcbiAgICBuaXA0NCxcbiAgICBuaXAxOSxcbiAgICBnZXRQdWJsaWNLZXlTeW5jLFxuICAgIGZpbmFsaXplRXZlbnQsXG4gICAgYnl0ZXNUb0hleCxcbiAgICBoZXhUb0J5dGVzLFxufSBmcm9tICdub3N0ci1jcnlwdG8tdXRpbHMnO1xuaW1wb3J0IHsgZW5jcnlwdCBhcyBuaXA0OUVuY3J5cHQsIGRlY3J5cHQgYXMgbmlwNDlEZWNyeXB0IH0gZnJvbSAnbm9zdHItY3J5cHRvLXV0aWxzL25pcDQ5JztcbmltcG9ydCB7IGtleVRvU2VlZFBocmFzZSwgc2VlZFBocmFzZVRvS2V5LCBpc1ZhbGlkU2VlZFBocmFzZSB9IGZyb20gJy4vdXRpbGl0aWVzL3NlZWRwaHJhc2UuanMnO1xuaW1wb3J0IHsgZ2VuZXJhdGVLZXlQYWlyIH0gZnJvbSAnLi91dGlsaXRpZXMva2V5cy5qcyc7XG5pbXBvcnQgeyBNdXRleCB9IGZyb20gJ2FzeW5jLW11dGV4JztcbmltcG9ydCB7XG4gICAgZ2V0UHJvZmlsZUluZGV4LFxuICAgIGdldCxcbiAgICBnZXRQcm9maWxlLFxuICAgIGdldFByb2ZpbGVzLFxuICAgIGdldFBlcm1pc3Npb24sXG4gICAgc2V0UGVybWlzc2lvbixcbiAgICBpc0VuY3J5cHRlZCxcbiAgICBjaGVja1Bhc3N3b3JkLFxuICAgIGVuY3J5cHRBbGxLZXlzLFxuICAgIGNoYW5nZVBhc3N3b3JkRm9yS2V5cyxcbiAgICByZW1vdmVQYXNzd29yZFByb3RlY3Rpb24sXG4gICAgZ2V0RGVjcnlwdGVkUHJpdktleSxcbiAgICBpc0VuY3J5cHRlZEJsb2IsXG59IGZyb20gJy4vdXRpbGl0aWVzL3V0aWxzJztcbmltcG9ydCB7IGVuY3J5cHQgYXMgZW5jcnlwdEJsb2IsIGRlY3J5cHQgYXMgZGVjcnlwdEJsb2IsIGVuY3J5cHRXaXRoS2V5LCBkZXJpdmVLZXkgfSBmcm9tICcuL3V0aWxpdGllcy9jcnlwdG8nO1xuaW1wb3J0IHsgc2F2ZUV2ZW50IH0gZnJvbSAnLi91dGlsaXRpZXMvZGInO1xuaW1wb3J0IHsgYXBpIH0gZnJvbSAnLi91dGlsaXRpZXMvYnJvd3Nlci1wb2x5ZmlsbCc7XG5pbXBvcnQgeyBpbml0U3luYywgc2NoZWR1bGVTeW5jUHVzaCB9IGZyb20gJy4vdXRpbGl0aWVzL3N5bmMtbWFuYWdlcic7XG5pbXBvcnQge1xuICAgIFJlbGF5Q29ubmVjdGlvbixcbiAgICBnZXRPckNyZWF0ZVNlc3Npb24sXG4gICAgY3JlYXRlU2Vzc2lvbixcbiAgICBkaXNjb25uZWN0U2Vzc2lvbixcbiAgICBpc1Nlc3Npb25BY3RpdmUsXG4gICAgdmFsaWRhdGVCdW5rZXJVcmwsXG59IGZyb20gJy4vdXRpbGl0aWVzL25pcDQ2JztcbmltcG9ydCB7IEJ1bmtlclNlcnZlciB9IGZyb20gJy4vdXRpbGl0aWVzL2J1bmtlci1zZXJ2ZXInO1xuaW1wb3J0IHtcbiAgICBidWlsZFZhdWx0RXZlbnQsXG4gICAgYnVpbGRWYXVsdERlbGV0aW9uLFxuICAgIGJ1aWxkVmF1bHRGaWx0ZXIsXG4gICAgcGFyc2VWYXVsdEV2ZW50LFxufSBmcm9tICcuL3V0aWxpdGllcy9uaXA3OCc7XG5cbi8vIFdyYXAgc3RvcmFnZS5sb2NhbCB3aXRoIGFuIGludGVyY2VwdG9yIHRoYXQgYXV0by10cmlnZ2VycyBzeW5jIHB1c2ggb24gd3JpdGVzXG5jb25zdCBfcmF3U3RvcmFnZSA9IGFwaS5zdG9yYWdlLmxvY2FsO1xuY29uc3Qgc3RvcmFnZSA9IHtcbiAgICBnZXQ6ICguLi5hcmdzKSA9PiBfcmF3U3RvcmFnZS5nZXQoLi4uYXJncyksXG4gICAgc2V0OiAoLi4uYXJncykgPT4ge1xuICAgICAgICBjb25zdCByZXN1bHQgPSBfcmF3U3RvcmFnZS5zZXQoLi4uYXJncyk7XG4gICAgICAgIHJlc3VsdC50aGVuKCgpID0+IHNjaGVkdWxlU3luY1B1c2goKSkuY2F0Y2goKCkgPT4ge30pO1xuICAgICAgICByZXR1cm4gcmVzdWx0O1xuICAgIH0sXG4gICAgY2xlYXI6ICguLi5hcmdzKSA9PiBfcmF3U3RvcmFnZS5jbGVhciguLi5hcmdzKSxcbiAgICByZW1vdmU6ICguLi5hcmdzKSA9PiBfcmF3U3RvcmFnZS5yZW1vdmUoLi4uYXJncyksXG59O1xuY29uc3QgbG9nID0gbXNnID0+IGNvbnNvbGUubG9nKCdCYWNrZ3JvdW5kOiAnLCBtc2cpO1xuY29uc3QgdmFsaWRhdGlvbnMgPSB7fTtcbmxldCBwcm9tcHQgPSB7IG11dGV4OiBuZXcgTXV0ZXgoKSwgcmVsZWFzZTogbnVsbCwgdGFiSWQ6IG51bGwgfTtcbmxldCBwZW5kaW5nUXVldWUgPSB7IHRvdGFsOiAwLCBwcm9jZXNzZWQ6IDAgfTtcbmxldCBhY3RpdmVCdW5rZXJTZXJ2ZXIgPSBudWxsO1xuXG4vKipcbiAqIEhlbHBlcjogcnVuIGFuIGFzeW5jIGZ1bmN0aW9uIGFuZCBkZWxpdmVyIHRoZSByZXN1bHQgdmlhIHNlbmRSZXNwb25zZS5cbiAqIENocm9tZSBNVjMgZG9lcyBub3QgcmVsaWFibHkgZGVsaXZlciBQcm9taXNlLXJldHVybiB2YWx1ZXMgZnJvbSBvbk1lc3NhZ2VcbiAqIGxpc3RlbmVycyBcdTIwMTQgb25seSB0aGUgc2VuZFJlc3BvbnNlIGNhbGxiYWNrIHBhdHRlcm4gd29ya3MuICBVc2UgdGhpcyB3aXRoXG4gKiBgcmV0dXJuIHRydWU7YCBpbiB0aGUgc3dpdGNoIGNhc2UgdG8ga2VlcCB0aGUgbWVzc2FnZSBjaGFubmVsIG9wZW4uXG4gKi9cbmZ1bmN0aW9uIHJlcGx5KHNlbmRSZXNwb25zZSwgZm4pIHtcbiAgICBmbigpLnRoZW4ociA9PiBzZW5kUmVzcG9uc2UocikpLmNhdGNoKGUgPT4ge1xuICAgICAgICBjb25zb2xlLmVycm9yKCdyZXBseSgpIGVycm9yOicsIGUpO1xuICAgICAgICBzZW5kUmVzcG9uc2UodW5kZWZpbmVkKTtcbiAgICB9KTtcbn1cblxuLy8gUmF0ZSBsaW1pdGVyOiBtYXggNSBwZXJtaXNzaW9uIHByb21wdHMgcGVyIGhvc3QgcGVyIDEwLXNlY29uZCB3aW5kb3dcbmNvbnN0IHJhdGVMaW1pdHMgPSBuZXcgTWFwKCk7XG5jb25zdCBSQVRFX0xJTUlUX01BWCA9IDU7XG5jb25zdCBSQVRFX0xJTUlUX1dJTkRPVyA9IDEwMDAwO1xuXG5mdW5jdGlvbiBpc1JhdGVMaW1pdGVkKGhvc3QpIHtcbiAgICBjb25zdCBub3cgPSBEYXRlLm5vdygpO1xuICAgIGxldCB0aW1lc3RhbXBzID0gcmF0ZUxpbWl0cy5nZXQoaG9zdCkgfHwgW107XG4gICAgdGltZXN0YW1wcyA9IHRpbWVzdGFtcHMuZmlsdGVyKHQgPT4gbm93IC0gdCA8IFJBVEVfTElNSVRfV0lORE9XKTtcbiAgICBpZiAodGltZXN0YW1wcy5sZW5ndGggPj0gUkFURV9MSU1JVF9NQVgpIHtcbiAgICAgICAgcmF0ZUxpbWl0cy5zZXQoaG9zdCwgdGltZXN0YW1wcyk7XG4gICAgICAgIHJldHVybiB0cnVlO1xuICAgIH1cbiAgICB0aW1lc3RhbXBzLnB1c2gobm93KTtcbiAgICByYXRlTGltaXRzLnNldChob3N0LCB0aW1lc3RhbXBzKTtcbiAgICByZXR1cm4gZmFsc2U7XG59XG5cbi8vIC0tLSBTZXNzaW9uIHN0YXRlIGZvciBtYXN0ZXIgcGFzc3dvcmQgZW5jcnlwdGlvbiAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cbi8vIERlY3J5cHRlZCBrZXlzIGFyZSBoZWxkIGluIG1lbW9yeSBvbmx5IHdoaWxlIHVubG9ja2VkLlxuLy8gTWFwIG9mIHByb2ZpbGVJbmRleCAtPiBoZXggcHJpdmF0ZSBrZXkgc3RyaW5nXG5jb25zdCBzZXNzaW9uS2V5cyA9IG5ldyBNYXAoKTtcbmxldCBzZXNzaW9uQ3J5cHRvS2V5ID0gbnVsbDsgLy8gZGVyaXZlZCBBRVMtMjU2LUdDTSBrZXkgKG9wYXF1ZSBDcnlwdG9LZXksIG5vdCByYXcgcGFzc3dvcmQpXG5sZXQgc2Vzc2lvbktleVNhbHQgPSBudWxsOyAgIC8vIHNhbHQgdXNlZCB0byBkZXJpdmUgc2Vzc2lvbkNyeXB0b0tleVxubGV0IGxvY2tlZCA9IHRydWU7IC8vIHN0YXJ0IGxvY2tlZDsgZGV0ZXJtaW5lZCBvbiBmaXJzdCBpc0xvY2tlZCBjaGVja1xubGV0IGVuY3J5cHRpb25FbmFibGVkID0gZmFsc2U7IC8vIGNhY2hlZCBlbmNyeXB0aW9uIHN0YXRlIGZvciBmYXN0IGxvb2t1cHNcbmxldCBhdXRvTG9ja1RpbWVvdXQgPSAxNSAqIDYwICogMTAwMDsgLy8gMTUgbWludXRlcyBkZWZhdWx0XG5sZXQgYXV0b0xvY2tUaW1lciA9IG51bGw7XG5sZXQgbm9zdHJBY2Nlc3NXaGlsZUxvY2tlZCA9IGZhbHNlO1xuXG5sZXQgYmxvY2tDcm9zc09yaWdpbkZyYW1lcyA9IHRydWU7XG5cbi8vIEJydXRlLWZvcmNlIHByb3RlY3Rpb24gZm9yIHVubG9jayBhdHRlbXB0c1xubGV0IHVubG9ja0F0dGVtcHRzID0gMDtcbmxldCB1bmxvY2tDb29sZG93blVudGlsID0gMDtcblxuLy8gUGVybWlzc2lvbiByZXF1ZXN0IHJhdGUgbGltaXRpbmcgcGVyIG9yaWdpblxuY29uc3QgcGVybWlzc2lvblJhdGVNYXAgPSBuZXcgTWFwKCk7IC8vIGhvc3QgXHUyMTkyIHsgY291bnQsIHJlc2V0QXQgfVxuXG4vLyBMb2FkIHBlcnNpc3RlZCBzdGF0ZSBvbiBzdGFydHVwXG4oYXN5bmMgKCkgPT4ge1xuICAgIGxvZygnW1NUQVJUVVBdIFJlYWRpbmcgcGVyc2lzdGVkIHN0YXRlLi4uJyk7XG4gICAgY29uc3QgZGF0YSA9IGF3YWl0IHN0b3JhZ2UuZ2V0KHsgYXV0b0xvY2tNaW51dGVzOiAxNSwgaXNFbmNyeXB0ZWQ6IGZhbHNlLCBwYXNzd29yZEhhc2g6IG51bGwsIG5vc3RyQWNjZXNzV2hpbGVMb2NrZWQ6IGZhbHNlLCBibG9ja0Nyb3NzT3JpZ2luRnJhbWVzOiB0cnVlIH0pO1xuICAgIGxvZyhgW1NUQVJUVVBdIGlzRW5jcnlwdGVkPSR7ZGF0YS5pc0VuY3J5cHRlZH0sIHBhc3N3b3JkSGFzaD0ke2RhdGEucGFzc3dvcmRIYXNoID8gJ0VYSVNUUycgOiAnbnVsbCd9LCBhdXRvTG9ja01pbnV0ZXM9JHtkYXRhLmF1dG9Mb2NrTWludXRlc31gKTtcbiAgICBhdXRvTG9ja1RpbWVvdXQgPSBkYXRhLmF1dG9Mb2NrTWludXRlcyAqIDYwICogMTAwMDtcbiAgICAvLyBEZWZlbnNpdmU6IGlmIHBhc3N3b3JkSGFzaCBleGlzdHMgYnV0IGZsYWcgaXMgc3RhbGUsIHNlbGYtaGVhbFxuICAgIGlmICghZGF0YS5pc0VuY3J5cHRlZCAmJiBkYXRhLnBhc3N3b3JkSGFzaCkge1xuICAgICAgICBsb2coJ1tTVEFSVFVQXSBTZWxmLWhlYWxpbmc6IHBhc3N3b3JkSGFzaCBleGlzdHMgYnV0IGlzRW5jcnlwdGVkPWZhbHNlIFx1MjE5MiBmaXhpbmcnKTtcbiAgICAgICAgYXdhaXQgc3RvcmFnZS5zZXQoeyBpc0VuY3J5cHRlZDogdHJ1ZSB9KTtcbiAgICAgICAgZGF0YS5pc0VuY3J5cHRlZCA9IHRydWU7XG4gICAgfVxuICAgIC8vIExvY2tvdXQgcmVjb3Zlcnk6IGlmIGlzRW5jcnlwdGVkPXRydWUgYnV0IHRoZXJlIGlzIE5PIHBhc3N3b3JkIHZlcmlmaWVyIEFORFxuICAgIC8vIG5vIGFjdHVhbGx5LWVuY3J5cHRlZCBrZXkgYmxvYnMsIGVuY3J5cHRpb24gaXMgYm9ndXMgKGUuZy4gYSBzdGFsZSBmbGFnXG4gICAgLy8gcmVjZWl2ZWQgZnJvbSBhbiBvbGRlciBidWdneSBzeW5jKS4gQ2xlYXJpbmcgaXQgcHJldmVudHMgYSBwZXJtYW5lbnQgbG9ja291dFxuICAgIC8vIHdoZXJlIHRoZSB1c2VyIGNhbiBuZXZlciB1bmxvY2sgYmVjYXVzZSBjaGVja1Bhc3N3b3JkKCkgYWx3YXlzIGZhaWxzLlxuICAgIC8vIFdlIE9OTFkgY2xlYXIgd2hlbiBubyBlbmNyeXB0ZWQgYmxvYnMgZXhpc3QgXHUyMDE0IG5ldmVyIHdoZW4gcmVhbCBjaXBoZXJ0ZXh0IGlzXG4gICAgLy8gcHJlc2VudCAodGhhdCB3b3VsZCBjb3JydXB0IGVuY3J5cHRlZCBrZXlzIGludG8gXCJwbGFpbnRleHRcIikuXG4gICAgaWYgKGRhdGEuaXNFbmNyeXB0ZWQgJiYgIWRhdGEucGFzc3dvcmRIYXNoKSB7XG4gICAgICAgIGNvbnN0IHsgcHJvZmlsZXMgPSBbXSB9ID0gYXdhaXQgc3RvcmFnZS5nZXQoeyBwcm9maWxlczogW10gfSk7XG4gICAgICAgIGNvbnN0IGhhc0VuY3J5cHRlZEJsb2IgPSBwcm9maWxlcy5zb21lKHAgPT4gaXNFbmNyeXB0ZWRCbG9iKHAucHJpdktleSkpO1xuICAgICAgICBpZiAoIWhhc0VuY3J5cHRlZEJsb2IpIHtcbiAgICAgICAgICAgIGxvZygnW1NUQVJUVVBdIExvY2tvdXQgcmVjb3Zlcnk6IGlzRW5jcnlwdGVkPXRydWUgd2l0aCBubyBwYXNzd29yZEhhc2ggYW5kIG5vIGVuY3J5cHRlZCBibG9icyBcdTIxOTIgY2xlYXJpbmcgYm9ndXMgZW5jcnlwdGlvbiBmbGFnJyk7XG4gICAgICAgICAgICBhd2FpdCBzdG9yYWdlLnNldCh7IGlzRW5jcnlwdGVkOiBmYWxzZSB9KTtcbiAgICAgICAgICAgIGRhdGEuaXNFbmNyeXB0ZWQgPSBmYWxzZTtcbiAgICAgICAgfVxuICAgIH1cbiAgICBlbmNyeXB0aW9uRW5hYmxlZCA9IGRhdGEuaXNFbmNyeXB0ZWQ7XG4gICAgbm9zdHJBY2Nlc3NXaGlsZUxvY2tlZCA9ICEhZGF0YS5ub3N0ckFjY2Vzc1doaWxlTG9ja2VkO1xuICAgIGJsb2NrQ3Jvc3NPcmlnaW5GcmFtZXMgPSBkYXRhLmJsb2NrQ3Jvc3NPcmlnaW5GcmFtZXMgIT09IGZhbHNlO1xuICAgIC8vIElmIGVuY3J5cHRpb24gaXMgZW5hYmxlZCwgd2Ugc3RhcnQgbG9ja2VkXG4gICAgbG9ja2VkID0gZW5jcnlwdGlvbkVuYWJsZWQ7XG4gICAgbG9nKGBbU1RBUlRVUF0gRmluYWwgc3RhdGU6IGVuY3J5cHRpb25FbmFibGVkPSR7ZW5jcnlwdGlvbkVuYWJsZWR9LCBsb2NrZWQ9JHtsb2NrZWR9YCk7XG5cbiAgICAvLyBJbml0aWFsaXplIHBsYXRmb3JtIHN5bmMgKHB1bGwgZnJvbSBzeW5jLCByZWdpc3RlciBsaXN0ZW5lcilcbiAgICB0cnkge1xuICAgICAgICBhd2FpdCBpbml0U3luYygpO1xuICAgICAgICBsb2coJ1tTVEFSVFVQXSBQbGF0Zm9ybSBzeW5jIGluaXRpYWxpemVkJyk7XG4gICAgfSBjYXRjaCAoZSkge1xuICAgICAgICBsb2coYFtTVEFSVFVQXSBQbGF0Zm9ybSBzeW5jIGluaXQgZXJyb3IgKG5vbi1mYXRhbCk6ICR7ZS5tZXNzYWdlfWApO1xuICAgIH1cblxuICAgIC8vIENoZWNrIGZvciBwcm9maWxlcyBzaGFyZWQgZnJvbSB0aGUgaU9TIGFwcCB2aWEgQXBwIEdyb3VwcyAoU2FmYXJpIG9ubHkpXG4gICAgdHJ5IHtcbiAgICAgICAgaWYgKHR5cGVvZiBicm93c2VyICE9PSAndW5kZWZpbmVkJyAmJiBicm93c2VyLnJ1bnRpbWUuc2VuZE5hdGl2ZU1lc3NhZ2UpIHtcbiAgICAgICAgICAgIGNvbnN0IHJlc3BvbnNlID0gYXdhaXQgYnJvd3Nlci5ydW50aW1lLnNlbmROYXRpdmVNZXNzYWdlKFxuICAgICAgICAgICAgICAgICdjb20ubm9zdHJrZXkuRXh0ZW5zaW9uJyxcbiAgICAgICAgICAgICAgICB7IGFjdGlvbjogJ2dldFNoYXJlZFByb2ZpbGVzJyB9XG4gICAgICAgICAgICApO1xuICAgICAgICAgICAgaWYgKHJlc3BvbnNlICYmIHJlc3BvbnNlLnByb2ZpbGVzICYmIHJlc3BvbnNlLnByb2ZpbGVzLmxlbmd0aCA+IDApIHtcbiAgICAgICAgICAgICAgICBjb25zdCBsb2NhbCA9IGF3YWl0IHN0b3JhZ2UuZ2V0KHsgcHJvZmlsZXM6IFtdIH0pO1xuICAgICAgICAgICAgICAgIGNvbnN0IG1lcmdlZCA9IG1lcmdlU2hhcmVkUHJvZmlsZXMobG9jYWwucHJvZmlsZXMsIHJlc3BvbnNlLnByb2ZpbGVzKTtcbiAgICAgICAgICAgICAgICBpZiAobWVyZ2VkLmNoYW5nZWQpIHtcbiAgICAgICAgICAgICAgICAgICAgYXdhaXQgc3RvcmFnZS5zZXQoeyBwcm9maWxlczogbWVyZ2VkLnByb2ZpbGVzIH0pO1xuICAgICAgICAgICAgICAgICAgICBsb2coYFtTVEFSVFVQXSBNZXJnZWQgJHtyZXNwb25zZS5wcm9maWxlcy5sZW5ndGh9IHNoYXJlZCBwcm9maWxlKHMpIGZyb20gaU9TIGFwcGApO1xuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgIH1cbiAgICAgICAgfVxuICAgIH0gY2F0Y2ggKGUpIHtcbiAgICAgICAgLy8gTm90IFNhZmFyaSwgb3Igc2hhcmVkIHN0b3JhZ2UgdW5hdmFpbGFibGUgXHUyMDE0IGlnbm9yZVxuICAgICAgICBsb2coYFtTVEFSVFVQXSBTaGFyZWQgcHJvZmlsZXMgY2hlY2sgc2tpcHBlZDogJHtlLm1lc3NhZ2V9YCk7XG4gICAgfVxufSkoKTtcblxuLyoqXG4gKiBNZXJnZSBwcm9maWxlcyBzaGFyZWQgZnJvbSB0aGUgaU9TIGFwcCBpbnRvIHRoZSBsb2NhbCBwcm9maWxlIGxpc3QuXG4gKiBGb3IgZWFjaCBzaGFyZWQgcHJvZmlsZSwgaWYgbm8gbG9jYWwgcHJvZmlsZSBoYXMgdGhlIHNhbWUgcHViS2V5LCBhZGQgaXQuXG4gKiBJZiBhIGxvY2FsIHByb2ZpbGUgaGFzIHRoZSBzYW1lIHB1YktleSwga2VlcCB0aGUgb25lIHdpdGggdGhlIG5ld2VyIHVwZGF0ZWRBdC5cbiAqIEByZXR1cm5zIHt7IHByb2ZpbGVzOiBBcnJheSwgY2hhbmdlZDogYm9vbGVhbiB9fVxuICovXG5mdW5jdGlvbiBtZXJnZVNoYXJlZFByb2ZpbGVzKGxvY2FsUHJvZmlsZXMsIHNoYXJlZFByb2ZpbGVzKSB7XG4gICAgbGV0IGNoYW5nZWQgPSBmYWxzZTtcbiAgICBjb25zdCBwcm9maWxlcyA9IFsuLi5sb2NhbFByb2ZpbGVzXTtcblxuICAgIGZvciAoY29uc3Qgc2hhcmVkIG9mIHNoYXJlZFByb2ZpbGVzKSB7XG4gICAgICAgIGlmICghc2hhcmVkLnB1YktleSkgY29udGludWU7XG5cbiAgICAgICAgY29uc3QgbG9jYWxJbmRleCA9IHByb2ZpbGVzLmZpbmRJbmRleChwID0+IHAucHViS2V5ID09PSBzaGFyZWQucHViS2V5KTtcblxuICAgICAgICBpZiAobG9jYWxJbmRleCA9PT0gLTEpIHtcbiAgICAgICAgICAgIC8vIE5ldyBwcm9maWxlIGZyb20gYXBwIFx1MjAxNCBhZGQgaXRcbiAgICAgICAgICAgIHByb2ZpbGVzLnB1c2goe1xuICAgICAgICAgICAgICAgIG5hbWU6IHNoYXJlZC5uYW1lIHx8ICdTaGFyZWQgUHJvZmlsZScsXG4gICAgICAgICAgICAgICAgcHJpdktleTogc2hhcmVkLnByaXZLZXkgfHwgJycsXG4gICAgICAgICAgICAgICAgcHViS2V5OiBzaGFyZWQucHViS2V5LFxuICAgICAgICAgICAgICAgIGhvc3RzOiB7fSxcbiAgICAgICAgICAgICAgICByZWxheXM6IHNoYXJlZC5yZWxheXMgfHwgW10sXG4gICAgICAgICAgICAgICAgdHlwZTogJ2xvY2FsJyxcbiAgICAgICAgICAgICAgICB1cGRhdGVkQXQ6IHNoYXJlZC5sYXN0U3luY2VkQXQgPyBuZXcgRGF0ZShzaGFyZWQubGFzdFN5bmNlZEF0KS5nZXRUaW1lKCkgOiBEYXRlLm5vdygpLFxuICAgICAgICAgICAgfSk7XG4gICAgICAgICAgICBjaGFuZ2VkID0gdHJ1ZTtcbiAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICAgIC8vIEV4aXN0aW5nIHByb2ZpbGUgXHUyMDE0IHVwZGF0ZSBpZiBzaGFyZWQgaXMgbmV3ZXIgYW5kIGhhcyBhIGtleSB3ZSBkb24ndFxuICAgICAgICAgICAgY29uc3QgbG9jYWwgPSBwcm9maWxlc1tsb2NhbEluZGV4XTtcbiAgICAgICAgICAgIGNvbnN0IGxvY2FsVGltZSA9IGxvY2FsLnVwZGF0ZWRBdCB8fCAwO1xuICAgICAgICAgICAgY29uc3Qgc2hhcmVkVGltZSA9IHNoYXJlZC5sYXN0U3luY2VkQXQgPyBuZXcgRGF0ZShzaGFyZWQubGFzdFN5bmNlZEF0KS5nZXRUaW1lKCkgOiAwO1xuXG4gICAgICAgICAgICBpZiAoc2hhcmVkVGltZSA+IGxvY2FsVGltZSAmJiBzaGFyZWQucHJpdktleSAmJiAhbG9jYWwucHJpdktleSkge1xuICAgICAgICAgICAgICAgIHByb2ZpbGVzW2xvY2FsSW5kZXhdID0ge1xuICAgICAgICAgICAgICAgICAgICAuLi5sb2NhbCxcbiAgICAgICAgICAgICAgICAgICAgcHJpdktleTogc2hhcmVkLnByaXZLZXksXG4gICAgICAgICAgICAgICAgICAgIG5hbWU6IHNoYXJlZC5uYW1lIHx8IGxvY2FsLm5hbWUsXG4gICAgICAgICAgICAgICAgICAgIHJlbGF5czogc2hhcmVkLnJlbGF5cyB8fCBsb2NhbC5yZWxheXMsXG4gICAgICAgICAgICAgICAgICAgIHVwZGF0ZWRBdDogc2hhcmVkVGltZSxcbiAgICAgICAgICAgICAgICB9O1xuICAgICAgICAgICAgICAgIGNoYW5nZWQgPSB0cnVlO1xuICAgICAgICAgICAgfVxuICAgICAgICB9XG4gICAgfVxuXG4gICAgcmV0dXJuIHsgcHJvZmlsZXMsIGNoYW5nZWQgfTtcbn1cblxuLyoqXG4gKiBSZXNldCB0aGUgYXV0by1sb2NrIGluYWN0aXZpdHkgdGltZXIuXG4gKi9cbmNvbnN0IEFVVE9fTE9DS19BTEFSTSA9ICdub3N0cmtleS1hdXRvLWxvY2snO1xuXG5mdW5jdGlvbiByZXNldEF1dG9Mb2NrKCkge1xuICAgIC8vIENsZWFyIGFueSBleGlzdGluZyB0aW1lciAoc2V0VGltZW91dCBmYWxsYmFjaylcbiAgICBpZiAoYXV0b0xvY2tUaW1lcikgeyBjbGVhclRpbWVvdXQoYXV0b0xvY2tUaW1lcik7IGF1dG9Mb2NrVGltZXIgPSBudWxsOyB9XG5cbiAgICBpZiAobG9ja2VkIHx8IGF1dG9Mb2NrVGltZW91dCA8PSAwKSB7XG4gICAgICAgIC8vIE5vIHRpbWVyIG5lZWRlZCBcdTIwMTQgYWxzbyBjbGVhciBhbnkgcGVuZGluZyBhbGFybVxuICAgICAgICBhcGkuYWxhcm1zPy5jbGVhcihBVVRPX0xPQ0tfQUxBUk0pLmNhdGNoKCgpID0+IHt9KTtcbiAgICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIC8vIFByZWZlciBjaHJvbWUuYWxhcm1zIChzdXJ2aXZlcyBNVjMgc2VydmljZS13b3JrZXIgZXZpY3Rpb24pXG4gICAgaWYgKGFwaS5hbGFybXMpIHtcbiAgICAgICAgYXBpLmFsYXJtcy5jcmVhdGUoQVVUT19MT0NLX0FMQVJNLCB7IGRlbGF5SW5NaW51dGVzOiBhdXRvTG9ja1RpbWVvdXQgLyA2MDAwMCB9KTtcbiAgICB9IGVsc2Uge1xuICAgICAgICAvLyBGYWxsYmFjayBmb3IgZW52aXJvbm1lbnRzIHdpdGhvdXQgYWxhcm1zIEFQSSAoU2FmYXJpIGJhY2tncm91bmQgcGFnZSlcbiAgICAgICAgYXV0b0xvY2tUaW1lciA9IHNldFRpbWVvdXQoKCkgPT4geyBsb2NrU2Vzc2lvbigpOyB9LCBhdXRvTG9ja1RpbWVvdXQpO1xuICAgIH1cbn1cblxuLy8gTGlzdGVuIGZvciB0aGUgYWxhcm0gdG8gZmlyZVxuaWYgKGFwaS5hbGFybXM/Lm9uQWxhcm0pIHtcbiAgICBhcGkuYWxhcm1zLm9uQWxhcm0uYWRkTGlzdGVuZXIoKGFsYXJtKSA9PiB7XG4gICAgICAgIGlmIChhbGFybS5uYW1lID09PSBBVVRPX0xPQ0tfQUxBUk0pIHtcbiAgICAgICAgICAgIGxvY2tTZXNzaW9uKCk7XG4gICAgICAgIH1cbiAgICB9KTtcbn1cblxuLyoqXG4gKiBNdXRleCB0aGF0IHNlcmlhbGl6ZXMgbG9ja1Nlc3Npb24gLyB1bmxvY2tTZXNzaW9uIHNvIHRoZSBhdXRvLWxvY2tcbiAqIHRpbWVyIGNhbGxiYWNrIGNhbm5vdCBpbnRlcmxlYXZlIHdpdGggYW4gaW4tcHJvZ3Jlc3MgdW5sb2NrLlxuICovXG5jb25zdCBzZXNzaW9uTXV0ZXggPSBuZXcgTXV0ZXgoKTtcblxuLyoqXG4gKiBMb2NrIHRoZSBzZXNzaW9uIFx1MjAxNCBjbGVhciBhbGwgZGVjcnlwdGVkIGtleXMgZnJvbSBtZW1vcnkuXG4gKi9cbmFzeW5jIGZ1bmN0aW9uIGxvY2tTZXNzaW9uKCkge1xuICAgIGNvbnN0IHJlbGVhc2UgPSBhd2FpdCBzZXNzaW9uTXV0ZXguYWNxdWlyZSgpO1xuICAgIHRyeSB7XG4gICAgICAgIGlmICghbm9zdHJBY2Nlc3NXaGlsZUxvY2tlZCkge1xuICAgICAgICAgICAgc2Vzc2lvbktleXMuY2xlYXIoKTtcbiAgICAgICAgfVxuICAgICAgICBzZXNzaW9uQ3J5cHRvS2V5ID0gbnVsbDtcbiAgICAgICAgc2Vzc2lvbktleVNhbHQgPSBudWxsO1xuICAgICAgICBsb2NrZWQgPSB0cnVlO1xuICAgICAgICBpZiAoYXV0b0xvY2tUaW1lcikge1xuICAgICAgICAgICAgY2xlYXJUaW1lb3V0KGF1dG9Mb2NrVGltZXIpO1xuICAgICAgICAgICAgYXV0b0xvY2tUaW1lciA9IG51bGw7XG4gICAgICAgIH1cbiAgICAgICAgbG9nKGBTZXNzaW9uIGxvY2tlZC4gS2V5cyByZXRhaW5lZDogJHtub3N0ckFjY2Vzc1doaWxlTG9ja2VkICYmIHNlc3Npb25LZXlzLnNpemUgPiAwfWApO1xuICAgIH0gZmluYWxseSB7XG4gICAgICAgIHJlbGVhc2UoKTtcbiAgICB9XG59XG5cbi8qKlxuICogVW5sb2NrIHRoZSBzZXNzaW9uIFx1MjAxNCB2ZXJpZnkgcGFzc3dvcmQgYW5kIGRlY3J5cHQgYWxsIGtleXMgaW50byBtZW1vcnkuXG4gKi9cbmFzeW5jIGZ1bmN0aW9uIHVubG9ja1Nlc3Npb24ocGFzc3dvcmQpIHtcbiAgICBjb25zdCByZWxlYXNlID0gYXdhaXQgc2Vzc2lvbk11dGV4LmFjcXVpcmUoKTtcbiAgICB0cnkge1xuICAgICAgICAvLyBCcnV0ZS1mb3JjZSBwcm90ZWN0aW9uOiBjb29sZG93biBhZnRlciAzIGZhaWxlZCBhdHRlbXB0c1xuICAgICAgICBjb25zdCBub3cgPSBEYXRlLm5vdygpO1xuICAgICAgICBpZiAobm93IDwgdW5sb2NrQ29vbGRvd25VbnRpbCkge1xuICAgICAgICAgICAgY29uc3Qgd2FpdFNlYyA9IE1hdGguY2VpbCgodW5sb2NrQ29vbGRvd25VbnRpbCAtIG5vdykgLyAxMDAwKTtcbiAgICAgICAgICAgIHJldHVybiB7IHN1Y2Nlc3M6IGZhbHNlLCBlcnJvcjogYFRvbyBtYW55IGF0dGVtcHRzLiBUcnkgYWdhaW4gaW4gJHt3YWl0U2VjfSBzZWNvbmRzLmAgfTtcbiAgICAgICAgfVxuXG4gICAgICAgIGNvbnN0IHZhbGlkID0gYXdhaXQgY2hlY2tQYXNzd29yZChwYXNzd29yZCk7XG4gICAgICAgIGlmICghdmFsaWQpIHtcbiAgICAgICAgICAgIHVubG9ja0F0dGVtcHRzKys7XG4gICAgICAgICAgICBpZiAodW5sb2NrQXR0ZW1wdHMgPj0gMykge1xuICAgICAgICAgICAgICAgIC8vIENvb2xkb3duOiAzMHMgYWZ0ZXIgMywgNjBzIGFmdGVyIDYsIDEyMHMgYWZ0ZXIgOSwgZXRjLlxuICAgICAgICAgICAgICAgIGNvbnN0IGNvb2xkb3duTXMgPSAzMDAwMCAqIE1hdGgucG93KDIsIE1hdGguZmxvb3IoKHVubG9ja0F0dGVtcHRzIC0gMykgLyAzKSk7XG4gICAgICAgICAgICAgICAgdW5sb2NrQ29vbGRvd25VbnRpbCA9IERhdGUubm93KCkgKyBjb29sZG93bk1zO1xuICAgICAgICAgICAgICAgIGxvZyhgW1NFQ1VSSVRZXSAke3VubG9ja0F0dGVtcHRzfSBmYWlsZWQgYXR0ZW1wdHMuIENvb2xkb3duOiAke2Nvb2xkb3duTXMgLyAxMDAwfXNgKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICAgIHJldHVybiB7IHN1Y2Nlc3M6IGZhbHNlLCBlcnJvcjogJ0ludmFsaWQgcGFzc3dvcmQnIH07XG4gICAgICAgIH1cblxuICAgICAgICAvLyBSZXNldCBvbiBzdWNjZXNzZnVsIHVubG9ja1xuICAgICAgICB1bmxvY2tBdHRlbXB0cyA9IDA7XG4gICAgICAgIHVubG9ja0Nvb2xkb3duVW50aWwgPSAwO1xuXG4gICAgICAgIGNvbnN0IHByb2ZpbGVzID0gYXdhaXQgZ2V0UHJvZmlsZXMoKTtcbiAgICAgICAgbGV0IG5lZWRzU2F2ZSA9IGZhbHNlO1xuICAgICAgICBmb3IgKGxldCBpID0gMDsgaSA8IHByb2ZpbGVzLmxlbmd0aDsgaSsrKSB7XG4gICAgICAgICAgICBpZiAocHJvZmlsZXNbaV0udHlwZSA9PT0gJ2J1bmtlcicpIGNvbnRpbnVlO1xuICAgICAgICAgICAgY29uc3QgaGV4ID0gYXdhaXQgZ2V0RGVjcnlwdGVkUHJpdktleShwcm9maWxlc1tpXSwgcGFzc3dvcmQpO1xuICAgICAgICAgICAgc2Vzc2lvbktleXMuc2V0KGksIGhleCk7XG4gICAgICAgICAgICAvLyBDYWNoZSBwdWJLZXkgaWYgbm90IGFscmVhZHkgY2FjaGVkIChmb3IgcHJvZmlsZXMgZW5jcnlwdGVkIGJlZm9yZSB0aGlzIGZpeClcbiAgICAgICAgICAgIGlmICghcHJvZmlsZXNbaV0ucHViS2V5ICYmIGhleCkge1xuICAgICAgICAgICAgICAgIHRyeSB7XG4gICAgICAgICAgICAgICAgICAgIHByb2ZpbGVzW2ldLnB1YktleSA9IGdldFB1YmxpY0tleVN5bmMoaGV4KTtcbiAgICAgICAgICAgICAgICAgICAgbmVlZHNTYXZlID0gdHJ1ZTtcbiAgICAgICAgICAgICAgICB9IGNhdGNoIChlKSB7XG4gICAgICAgICAgICAgICAgICAgIGNvbnNvbGUuZXJyb3IoYEZhaWxlZCB0byBjYWNoZSBwdWJLZXkgZm9yIHByb2ZpbGUgJHtpfTpgLCBlKTtcbiAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICB9XG4gICAgICAgIH1cbiAgICAgICAgaWYgKG5lZWRzU2F2ZSkge1xuICAgICAgICAgICAgYXdhaXQgc3RvcmFnZS5zZXQoeyBwcm9maWxlcyB9KTtcbiAgICAgICAgfVxuICAgICAgICAvLyBEZXJpdmUgYSBzZXNzaW9uIENyeXB0b0tleSBzbyB3ZSBuZXZlciBob2xkIHRoZSByYXcgcGFzc3dvcmQgaW4gbWVtb3J5LlxuICAgICAgICAvLyBUaGUgc2FsdCBpcyByYW5kb20gcGVyIHNlc3Npb247IGRlY3J5cHQoKSBzdGlsbCB1c2VzIHRoZSBwYXNzd29yZCBhdFxuICAgICAgICAvLyBuZXh0IHVubG9jayB0byByZS1kZXJpdmUgZnJvbSB3aGF0ZXZlciBzYWx0IHdhcyBzdG9yZWQgaW4gZWFjaCBibG9iLlxuICAgICAgICBjb25zdCBzYWx0ID0gY3J5cHRvLmdldFJhbmRvbVZhbHVlcyhuZXcgVWludDhBcnJheSgxNikpO1xuICAgICAgICBzZXNzaW9uQ3J5cHRvS2V5ID0gYXdhaXQgZGVyaXZlS2V5KHBhc3N3b3JkLCBzYWx0KTtcbiAgICAgICAgc2Vzc2lvbktleVNhbHQgPSBzYWx0O1xuICAgICAgICAvLyBwYXNzd29yZCBpcyBub3cgb25seSBvbiB0aGUgY2FsbCBzdGFjayBhbmQgd2lsbCBiZSBHQydkXG4gICAgICAgIGxvY2tlZCA9IGZhbHNlO1xuICAgICAgICByZXNldEF1dG9Mb2NrKCk7XG4gICAgICAgIGxvZygnU2Vzc2lvbiB1bmxvY2tlZC4nKTtcbiAgICAgICAgcmV0dXJuIHsgc3VjY2VzczogdHJ1ZSB9O1xuICAgIH0gZmluYWxseSB7XG4gICAgICAgIHJlbGVhc2UoKTtcbiAgICB9XG59XG5cbi8qKlxuICogQ2hlY2sgd2hldGhlciB0aGUgZXh0ZW5zaW9uIGlzIGN1cnJlbnRseSBpbiBhIGxvY2tlZCBzdGF0ZS5cbiAqIElmIG5vIHBhc3N3b3JkIGlzIHNldCwgd2UgYXJlIG5ldmVyIGxvY2tlZC5cbiAqL1xuYXN5bmMgZnVuY3Rpb24gY2hlY2tMb2NrU3RhdGUoKSB7XG4gICAgY29uc3QgZW5jcnlwdGVkID0gYXdhaXQgaXNFbmNyeXB0ZWQoKTtcbiAgICBsb2coYFtjaGVja0xvY2tTdGF0ZV0gaXNFbmNyeXB0ZWQoKT0ke2VuY3J5cHRlZH0sIGxvY2tlZD0ke2xvY2tlZH1gKTtcbiAgICBpZiAoIWVuY3J5cHRlZCkge1xuICAgICAgICBsb2NrZWQgPSBmYWxzZTtcbiAgICAgICAgcmV0dXJuIGZhbHNlO1xuICAgIH1cbiAgICByZXR1cm4gbG9ja2VkO1xufVxuXG4vLyAtLS0gU2VuZGVyIHZhbGlkYXRpb24gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLVxuXG5jb25zdCBTRU5TSVRJVkVfS0lORFMgPSBuZXcgU2V0KFtcbiAgICAnc2V0UGFzc3dvcmQnLCAnY2hhbmdlUGFzc3dvcmQnLCAncmVtb3ZlUGFzc3dvcmQnLCAncmVzZXRBbGxEYXRhJyxcbiAgICAnc2V0QXV0b0xvY2tUaW1lb3V0JywgJ3NldE5vc3RyQWNjZXNzV2hpbGVMb2NrZWQnLCAnc2V0QmxvY2tDcm9zc09yaWdpbkZyYW1lcycsXG4gICAgJ2JhY2t1cC5leHBvcnQnLCAnYmFja3VwLmltcG9ydCcsICd1bmxvY2snLFxuICAgIC8vIFN0YXJ0aW5nL3N0b3BwaW5nIHRoZSBOSVAtNDYgYnVua2VyIGV4cG9zZXMgdGhlIHVzZXIncyBrZXkgZm9yIHJlbW90ZVxuICAgIC8vIHNpZ25pbmcgYW5kIHJldHVybnMgdGhlIHNlY3JldC1iZWFyaW5nIGNvbm5lY3Rpb24gc3RyaW5nLiBJdCBtdXN0IGJlIGFcbiAgICAvLyBkZWxpYmVyYXRlIGluLWV4dGVuc2lvbiBhY3Rpb24gXHUyMDE0IG5ldmVyIHRyaWdnZXJhYmxlIGJ5IGEgd2ViIHBhZ2UgdmlhXG4gICAgLy8gd2luZG93Lm5vc3RyLm5pcDQ2LnN0YXJ0QnVua2VyKCkuXG4gICAgJ2J1bmtlclNlcnZlci5zdGFydCcsICdidW5rZXJTZXJ2ZXIuc3RvcCcsXG5dKTtcblxuZnVuY3Rpb24gaXNFeHRlbnNpb25TZW5kZXIoc2VuZGVyKSB7XG4gICAgLy8gTWVzc2FnZXMgZnJvbSBleHRlbnNpb24gcGFnZXMgKHBvcHVwLCBzaWRlcGFuZWwsIG9wdGlvbnMsIHZhdWx0KSBoYXZlIG91ciBJRC5cbiAgICAvLyBDb250ZW50IHNjcmlwdHMgaW5qZWN0IGludG8gd2ViIHBhZ2VzIFx1MjAxNCB0aGV5IGhhdmUgc2VuZGVyLnRhYiBidXQgdGhlaXIgVVJMXG4gICAgLy8gaXMgdGhlIHdlYiBwYWdlIFVSTCwgbm90IG91ciBleHRlbnNpb24gVVJMLiBFeHRlbnNpb24gcGFnZXMgb3BlbmVkIGluIHRhYnNcbiAgICAvLyAobGlrZSB2YXVsdC5odG1sKSBhbHNvIGhhdmUgc2VuZGVyLnRhYiBidXQgdGhlaXIgVVJMIHN0YXJ0cyB3aXRoIG91ciBvcmlnaW4uXG4gICAgaWYgKHNlbmRlci5pZCAhPT0gYXBpLnJ1bnRpbWUuaWQpIHJldHVybiBmYWxzZTtcbiAgICAvLyBJZiBvcGVuZWQgaW4gYSB0YWIsIGNoZWNrIHRoZSBVUkwgaXMgYWN0dWFsbHkgb3VyIGV4dGVuc2lvbiAobm90IGEgY29udGVudCBzY3JpcHQpXG4gICAgaWYgKHNlbmRlci50YWIpIHtcbiAgICAgICAgY29uc3QgZXh0T3JpZ2luID0gYGNocm9tZS1leHRlbnNpb246Ly8ke2FwaS5ydW50aW1lLmlkfWA7XG4gICAgICAgIGNvbnN0IHVybCA9IHNlbmRlci50YWIudXJsIHx8IHNlbmRlci51cmwgfHwgJyc7XG4gICAgICAgIHJldHVybiB1cmwuc3RhcnRzV2l0aChleHRPcmlnaW4pIHx8IHVybC5zdGFydHNXaXRoKCdtb3otZXh0ZW5zaW9uOi8vJyk7XG4gICAgfVxuICAgIHJldHVybiB0cnVlO1xufVxuXG4vLyAtLS0gTWVzc2FnZSBoYW5kbGVyIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG5cbmFwaS5ydW50aW1lLm9uTWVzc2FnZS5hZGRMaXN0ZW5lcigobWVzc2FnZSwgX3NlbmRlciwgc2VuZFJlc3BvbnNlKSA9PiB7XG4gICAgbG9nKG1lc3NhZ2UpO1xuXG4gICAgLy8gQmxvY2sgc2Vuc2l0aXZlIG9wZXJhdGlvbnMgZnJvbSBub24tZXh0ZW5zaW9uIGNvbnRleHRzXG4gICAgaWYgKFNFTlNJVElWRV9LSU5EUy5oYXMobWVzc2FnZS5raW5kKSAmJiAhaXNFeHRlbnNpb25TZW5kZXIoX3NlbmRlcikpIHtcbiAgICAgICAgbG9nKGBbU0VDVVJJVFldIEJsb2NrZWQgJHttZXNzYWdlLmtpbmR9IGZyb20gbm9uLWV4dGVuc2lvbiBzZW5kZXJgKTtcbiAgICAgICAgc2VuZFJlc3BvbnNlKHsgc3VjY2VzczogZmFsc2UsIGVycm9yOiAnVW5hdXRob3JpemVkIHNlbmRlcicgfSk7XG4gICAgICAgIHJldHVybiB0cnVlO1xuICAgIH1cblxuICAgIGxldCB1dWlkID0gY3J5cHRvLnJhbmRvbVVVSUQoKTtcbiAgICBsZXQgc3I7XG5cbiAgICBzd2l0Y2ggKG1lc3NhZ2Uua2luZCkge1xuICAgICAgICAvLyBHZW5lcmFsXG4gICAgICAgIGNhc2UgJ2Nsb3NlUHJvbXB0JzpcbiAgICAgICAgICAgIHByb21wdC5yZWxlYXNlPy4oKTtcbiAgICAgICAgICAgIHNlbmRSZXNwb25zZSh0cnVlKTtcbiAgICAgICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgICBjYXNlICdhbGxvd2VkJzpcbiAgICAgICAgICAgIHJlc2V0QXV0b0xvY2soKTtcbiAgICAgICAgICAgIGNvbXBsZXRlKG1lc3NhZ2UpO1xuICAgICAgICAgICAgc2VuZFJlc3BvbnNlKHRydWUpO1xuICAgICAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgICAgIGNhc2UgJ2RlbmllZCc6XG4gICAgICAgICAgICBkZW55KG1lc3NhZ2UpO1xuICAgICAgICAgICAgc2VuZFJlc3BvbnNlKHRydWUpO1xuICAgICAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgICAgIGNhc2UgJ2dlbmVyYXRlUHJpdmF0ZUtleSc6XG4gICAgICAgICAgICAoYXN5bmMgKCkgPT4ge1xuICAgICAgICAgICAgICAgIHRyeSB7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHJlc3VsdCA9IGF3YWl0IGdlbmVyYXRlUHJpdmF0ZUtleV8oKTtcbiAgICAgICAgICAgICAgICAgICAgc2VuZFJlc3BvbnNlKHJlc3VsdCk7XG4gICAgICAgICAgICAgICAgfSBjYXRjaCAoZSkge1xuICAgICAgICAgICAgICAgICAgICBjb25zb2xlLmVycm9yKCdnZW5lcmF0ZVByaXZhdGVLZXkgZXJyb3I6JywgZSk7XG4gICAgICAgICAgICAgICAgICAgIHNlbmRSZXNwb25zZShudWxsKTtcbiAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICB9KSgpO1xuICAgICAgICAgICAgcmV0dXJuIHRydWU7IC8vIEtlZXAgbWVzc2FnZSBjaGFubmVsIG9wZW4gZm9yIGFzeW5jIHNlbmRSZXNwb25zZVxuICAgICAgICBjYXNlICdzYXZlUHJpdmF0ZUtleSc6XG4gICAgICAgICAgICByZXNldEF1dG9Mb2NrKCk7XG4gICAgICAgICAgICAvLyBNdXN0IHVzZSBzZW5kUmVzcG9uc2UgKyByZXR1cm4gdHJ1ZSAobm90IGEgUHJvbWlzZSByZXR1cm4pOiBDaHJvbWUgTVYzXG4gICAgICAgICAgICAvLyBkb2VzIG5vdCBkZWxpdmVyIFByb21pc2UtcmV0dXJuIHZhbHVlcyB0byBzZW5kTWVzc2FnZSBjYWxsZXJzLCBzbyB0aGVcbiAgICAgICAgICAgIC8vIGNhbGxlciBjb3VsZCBub3QgdGVsbCB3aGV0aGVyIHRoZSBrZXkgd2FzIGFjdHVhbGx5IHNhdmVkIChvciB3aGV0aGVyIGl0XG4gICAgICAgICAgICAvLyB0aHJldykuIFRoYXQgbWFkZSBpbXBvcnRlZCBrZXlzIHNpbGVudGx5IGZhaWwgd2hpbGUgdGhlIFVJIHNob3dlZCBzdWNjZXNzLlxuICAgICAgICAgICAgKGFzeW5jICgpID0+IHtcbiAgICAgICAgICAgICAgICB0cnkge1xuICAgICAgICAgICAgICAgICAgICBhd2FpdCBzYXZlUHJpdmF0ZUtleShtZXNzYWdlLnBheWxvYWQpO1xuICAgICAgICAgICAgICAgICAgICBzZW5kUmVzcG9uc2UoeyBzdWNjZXNzOiB0cnVlIH0pO1xuICAgICAgICAgICAgICAgIH0gY2F0Y2ggKGUpIHtcbiAgICAgICAgICAgICAgICAgICAgY29uc29sZS5lcnJvcignc2F2ZVByaXZhdGVLZXkgZXJyb3I6JywgZSk7XG4gICAgICAgICAgICAgICAgICAgIHNlbmRSZXNwb25zZSh7IHN1Y2Nlc3M6IGZhbHNlLCBlcnJvcjogZS5tZXNzYWdlIHx8ICdGYWlsZWQgdG8gc2F2ZSBrZXknIH0pO1xuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgIH0pKCk7XG4gICAgICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgICAgY2FzZSAnZ2V0TnB1Yic6XG4gICAgICAgICAgICAoYXN5bmMgKCkgPT4ge1xuICAgICAgICAgICAgICAgIHRyeSB7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHJlc3VsdCA9IGF3YWl0IGdldE5wdWIobWVzc2FnZS5wYXlsb2FkKTtcbiAgICAgICAgICAgICAgICAgICAgc2VuZFJlc3BvbnNlKHJlc3VsdCk7XG4gICAgICAgICAgICAgICAgfSBjYXRjaCAoZSkge1xuICAgICAgICAgICAgICAgICAgICBjb25zb2xlLmVycm9yKCdnZXROcHViIGVycm9yOicsIGUpO1xuICAgICAgICAgICAgICAgICAgICBzZW5kUmVzcG9uc2UobnVsbCk7XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfSkoKTtcbiAgICAgICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgICBjYXNlICdnZXROc2VjJzpcbiAgICAgICAgICAgIHJlc2V0QXV0b0xvY2soKTtcbiAgICAgICAgICAgIChhc3luYyAoKSA9PiB7XG4gICAgICAgICAgICAgICAgdHJ5IHtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgcmVzdWx0ID0gYXdhaXQgZ2V0TnNlYyhtZXNzYWdlLnBheWxvYWQpO1xuICAgICAgICAgICAgICAgICAgICBzZW5kUmVzcG9uc2UocmVzdWx0KTtcbiAgICAgICAgICAgICAgICB9IGNhdGNoIChlKSB7XG4gICAgICAgICAgICAgICAgICAgIGNvbnNvbGUuZXJyb3IoJ2dldE5zZWMgZXJyb3I6JywgZSk7XG4gICAgICAgICAgICAgICAgICAgIHNlbmRSZXNwb25zZShudWxsKTtcbiAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICB9KSgpO1xuICAgICAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgICAgIGNhc2UgJ2NhbGNQdWJLZXknOlxuICAgICAgICAgICAgc2VuZFJlc3BvbnNlKGdldFB1YmxpY0tleVN5bmMobWVzc2FnZS5wYXlsb2FkKSk7XG4gICAgICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgICAgY2FzZSAnbnB1YkVuY29kZSc6XG4gICAgICAgICAgICBzZW5kUmVzcG9uc2UobmlwMTkubnB1YkVuY29kZShtZXNzYWdlLnBheWxvYWQpKTtcbiAgICAgICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgICBjYXNlICdjb3B5JzpcbiAgICAgICAgICAgIC8vIG5hdmlnYXRvci5jbGlwYm9hcmQgaXMgdW5hdmFpbGFibGUgaW4gQ2hyb21lIHNlcnZpY2Ugd29ya2Vycy5cbiAgICAgICAgICAgIC8vIFRoZSBjYWxsZXIgKHBvcHVwL29wdGlvbnMpIHNob3VsZCBoYW5kbGUgY2xpcGJvYXJkIGRpcmVjdGx5IHdoZW5cbiAgICAgICAgICAgIC8vIHBvc3NpYmxlOyB0aGlzIHBhdGggaXMga2VwdCBmb3IgU2FmYXJpIGJhY2tncm91bmQtcGFnZSBjb21wYXQuXG4gICAgICAgICAgICBpZiAodHlwZW9mIG5hdmlnYXRvciAhPT0gJ3VuZGVmaW5lZCcgJiYgbmF2aWdhdG9yLmNsaXBib2FyZD8ud3JpdGVUZXh0KSB7XG4gICAgICAgICAgICAgICAgbmF2aWdhdG9yLmNsaXBib2FyZC53cml0ZVRleHQobWVzc2FnZS5wYXlsb2FkKS50aGVuKCgpID0+IHNlbmRSZXNwb25zZSh0cnVlKSkuY2F0Y2goKCkgPT4gc2VuZFJlc3BvbnNlKGZhbHNlKSk7XG4gICAgICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgICAgIHNlbmRSZXNwb25zZShmYWxzZSk7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgICByZXR1cm4gdHJ1ZTtcblxuICAgICAgICAvLyAtLS0gTWFzdGVyIHBhc3N3b3JkIC8gbG9jayBoYW5kbGVycyAtLS1cbiAgICAgICAgLy8gTk9URTogVGhlc2UgdXNlIHNlbmRSZXNwb25zZSArIHJldHVybiB0cnVlIChjYWxsYmFjayBwYXR0ZXJuKSBiZWNhdXNlXG4gICAgICAgIC8vIENocm9tZSBNVjMgZG9lcyBub3QgcmVsaWFibHkgZGVsaXZlciBQcm9taXNlLXJldHVybiB2YWx1ZXMgZnJvbVxuICAgICAgICAvLyBvbk1lc3NhZ2UgbGlzdGVuZXJzIHRvIHNlbmRNZXNzYWdlIGNhbGxlcnMuXG4gICAgICAgIGNhc2UgJ2lzTG9ja2VkJzpcbiAgICAgICAgICAgIChhc3luYyAoKSA9PiB7XG4gICAgICAgICAgICAgICAgdHJ5IHtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgcmVzdWx0ID0gYXdhaXQgY2hlY2tMb2NrU3RhdGUoKTtcbiAgICAgICAgICAgICAgICAgICAgbG9nKGBbaXNMb2NrZWRdIFNlbmRpbmcgcmVzcG9uc2U6ICR7cmVzdWx0fWApO1xuICAgICAgICAgICAgICAgICAgICBzZW5kUmVzcG9uc2UocmVzdWx0KTtcbiAgICAgICAgICAgICAgICB9IGNhdGNoIChlKSB7XG4gICAgICAgICAgICAgICAgICAgIGxvZyhgW2lzTG9ja2VkXSBFcnJvcjogJHtlLm1lc3NhZ2V9YCk7XG4gICAgICAgICAgICAgICAgICAgIHNlbmRSZXNwb25zZShmYWxzZSk7XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfSkoKTtcbiAgICAgICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgICBjYXNlICdpc0VuY3J5cHRlZCc6XG4gICAgICAgICAgICAoYXN5bmMgKCkgPT4ge1xuICAgICAgICAgICAgICAgIHRyeSB7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IGRhdGEgPSBhd2FpdCBzdG9yYWdlLmdldCh7IGlzRW5jcnlwdGVkOiBmYWxzZSwgcGFzc3dvcmRIYXNoOiBudWxsIH0pO1xuICAgICAgICAgICAgICAgICAgICBsb2coYFtpc0VuY3J5cHRlZF0gc3RvcmFnZTogaXNFbmNyeXB0ZWQ9JHtkYXRhLmlzRW5jcnlwdGVkfSwgcGFzc3dvcmRIYXNoPSR7ZGF0YS5wYXNzd29yZEhhc2ggPyAnRVhJU1RTJyA6ICdudWxsJ31gKTtcbiAgICAgICAgICAgICAgICAgICAgaWYgKCFkYXRhLmlzRW5jcnlwdGVkICYmIGRhdGEucGFzc3dvcmRIYXNoKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICBsb2coJ1tpc0VuY3J5cHRlZF0gU2VsZi1oZWFsaW5nOiBwYXNzd29yZEhhc2ggZXhpc3RzIGJ1dCBmbGFnPWZhbHNlJyk7XG4gICAgICAgICAgICAgICAgICAgICAgICBhd2FpdCBzdG9yYWdlLnNldCh7IGlzRW5jcnlwdGVkOiB0cnVlIH0pO1xuICAgICAgICAgICAgICAgICAgICAgICAgZGF0YS5pc0VuY3J5cHRlZCA9IHRydWU7XG4gICAgICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICAgICAgZW5jcnlwdGlvbkVuYWJsZWQgPSBkYXRhLmlzRW5jcnlwdGVkO1xuICAgICAgICAgICAgICAgICAgICBsb2coYFtpc0VuY3J5cHRlZF0gU2VuZGluZyByZXNwb25zZTogJHtlbmNyeXB0aW9uRW5hYmxlZH1gKTtcbiAgICAgICAgICAgICAgICAgICAgc2VuZFJlc3BvbnNlKGVuY3J5cHRpb25FbmFibGVkKTtcbiAgICAgICAgICAgICAgICB9IGNhdGNoIChlKSB7XG4gICAgICAgICAgICAgICAgICAgIGxvZyhgW2lzRW5jcnlwdGVkXSBFcnJvcjogJHtlLm1lc3NhZ2V9YCk7XG4gICAgICAgICAgICAgICAgICAgIHNlbmRSZXNwb25zZShmYWxzZSk7XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfSkoKTtcbiAgICAgICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgICBjYXNlICdoYXNFbmNyeXB0ZWREYXRhJzpcbiAgICAgICAgICAgIChhc3luYyAoKSA9PiB7XG4gICAgICAgICAgICAgICAgdHJ5IHtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgZGF0YSA9IGF3YWl0IHN0b3JhZ2UuZ2V0KHsgcGFzc3dvcmRIYXNoOiBudWxsLCBwcm9maWxlczogW10gfSk7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IGhhc1Bhc3N3b3JkSGFzaCA9ICEhZGF0YS5wYXNzd29yZEhhc2g7XG4gICAgICAgICAgICAgICAgICAgIGxldCBlbmNyeXB0ZWRQcm9maWxlcyA9IDA7XG4gICAgICAgICAgICAgICAgICAgIGxvZyhgW2hhc0VuY3J5cHRlZERhdGFdIHBhc3N3b3JkSGFzaD0ke2hhc1Bhc3N3b3JkSGFzaH0sIHByb2ZpbGVzPSR7QXJyYXkuaXNBcnJheShkYXRhLnByb2ZpbGVzKSA/IGRhdGEucHJvZmlsZXMubGVuZ3RoIDogJ25vdC1hcnJheSd9YCk7XG4gICAgICAgICAgICAgICAgICAgIGlmIChBcnJheS5pc0FycmF5KGRhdGEucHJvZmlsZXMpKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICBmb3IgKGxldCBpID0gMDsgaSA8IGRhdGEucHJvZmlsZXMubGVuZ3RoOyBpKyspIHtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICBjb25zdCBwID0gZGF0YS5wcm9maWxlc1tpXTtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICBjb25zdCBpc0VuYyA9IHAucHJpdktleSA/IGlzRW5jcnlwdGVkQmxvYihwLnByaXZLZXkpIDogZmFsc2U7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgbG9nKGBbaGFzRW5jcnlwdGVkRGF0YV0gcHJvZmlsZVske2l9XSBuYW1lPVwiJHtwLm5hbWV9XCIgcHJpdktleT0ke3AucHJpdktleSA/IChpc0VuYyA/ICdFTkNSWVBURUQnIDogJ1BMQUlOVEVYVCcpIDogJ0VNUFRZJ31gKTtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICBpZiAoaXNFbmMpIGVuY3J5cHRlZFByb2ZpbGVzKys7XG4gICAgICAgICAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICAgICAgY29uc3QgZm91bmQgPSBoYXNQYXNzd29yZEhhc2ggfHwgZW5jcnlwdGVkUHJvZmlsZXMgPiAwO1xuICAgICAgICAgICAgICAgICAgICBsb2coYFtoYXNFbmNyeXB0ZWREYXRhXSBSZXN1bHQ6IGZvdW5kPSR7Zm91bmR9LCBoYXNQYXNzd29yZEhhc2g9JHtoYXNQYXNzd29yZEhhc2h9LCBlbmNyeXB0ZWRQcm9maWxlcz0ke2VuY3J5cHRlZFByb2ZpbGVzfWApO1xuICAgICAgICAgICAgICAgICAgICBpZiAoZm91bmQgJiYgIWVuY3J5cHRpb25FbmFibGVkKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICBsb2coJ1toYXNFbmNyeXB0ZWREYXRhXSBTZWxmLWhlYWxpbmc6IHNldHRpbmcgaXNFbmNyeXB0ZWQ9dHJ1ZSwgbG9ja2VkPXRydWUnKTtcbiAgICAgICAgICAgICAgICAgICAgICAgIGF3YWl0IHN0b3JhZ2Uuc2V0KHsgaXNFbmNyeXB0ZWQ6IHRydWUgfSk7XG4gICAgICAgICAgICAgICAgICAgICAgICBlbmNyeXB0aW9uRW5hYmxlZCA9IHRydWU7XG4gICAgICAgICAgICAgICAgICAgICAgICBsb2NrZWQgPSB0cnVlO1xuICAgICAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgICAgIHNlbmRSZXNwb25zZSh7IGZvdW5kLCBoYXNQYXNzd29yZEhhc2gsIGVuY3J5cHRlZFByb2ZpbGVzIH0pO1xuICAgICAgICAgICAgICAgIH0gY2F0Y2ggKGUpIHtcbiAgICAgICAgICAgICAgICAgICAgY29uc29sZS5lcnJvcignaGFzRW5jcnlwdGVkRGF0YSBlcnJvcjonLCBlKTtcbiAgICAgICAgICAgICAgICAgICAgc2VuZFJlc3BvbnNlKHsgZm91bmQ6IGZhbHNlLCBoYXNQYXNzd29yZEhhc2g6IGZhbHNlLCBlbmNyeXB0ZWRQcm9maWxlczogMCB9KTtcbiAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICB9KSgpO1xuICAgICAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgICAgIGNhc2UgJ3VubG9jayc6XG4gICAgICAgICAgICByZXBseShzZW5kUmVzcG9uc2UsICgpID0+IHVubG9ja1Nlc3Npb24obWVzc2FnZS5wYXlsb2FkKSk7XG4gICAgICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgICAgY2FzZSAnbG9jayc6XG4gICAgICAgICAgICBsb2NrU2Vzc2lvbigpLnRoZW4oKCkgPT4gc2VuZFJlc3BvbnNlKHRydWUpKTtcbiAgICAgICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgICBjYXNlICdzZXRQYXNzd29yZCc6XG4gICAgICAgICAgICAoYXN5bmMgKCkgPT4ge1xuICAgICAgICAgICAgICAgIHRyeSB7XG4gICAgICAgICAgICAgICAgICAgIC8vIENhY2hlIHB1YktleXMgYmVmb3JlIGVuY3J5cHRpb24gKG5lZWQgcGxhaW50ZXh0IGtleXMpXG4gICAgICAgICAgICAgICAgICAgIGF3YWl0IGNhY2hlUHViS2V5c0ZvckFsbFByb2ZpbGVzKCk7XG4gICAgICAgICAgICAgICAgICAgIGF3YWl0IGVuY3J5cHRBbGxLZXlzKG1lc3NhZ2UucGF5bG9hZCk7XG4gICAgICAgICAgICAgICAgICAgIGVuY3J5cHRpb25FbmFibGVkID0gdHJ1ZTtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgcmVzdWx0ID0gYXdhaXQgdW5sb2NrU2Vzc2lvbihtZXNzYWdlLnBheWxvYWQpO1xuICAgICAgICAgICAgICAgICAgICAvLyBCcm9hZGNhc3QgcGFzc3dvcmQgc3RhdGUgY2hhbmdlIHRvIGFsbCB2aWV3c1xuICAgICAgICAgICAgICAgICAgICBhcGkucnVudGltZS5zZW5kTWVzc2FnZSh7IGtpbmQ6ICdwYXNzd29yZFN0YXRlQ2hhbmdlZCcsIGhhc1Bhc3N3b3JkOiB0cnVlIH0pLmNhdGNoKCgpID0+IHt9KTtcbiAgICAgICAgICAgICAgICAgICAgYXBpLnJ1bnRpbWUuc2VuZE1lc3NhZ2UoeyBraW5kOiAnYmFja3VwTmVlZGVkJyB9KS5jYXRjaCgoKSA9PiB7fSk7XG4gICAgICAgICAgICAgICAgICAgIHNlbmRSZXNwb25zZShyZXN1bHQpO1xuICAgICAgICAgICAgICAgIH0gY2F0Y2ggKGUpIHtcbiAgICAgICAgICAgICAgICAgICAgc2VuZFJlc3BvbnNlKHsgc3VjY2VzczogZmFsc2UsIGVycm9yOiBlLm1lc3NhZ2UgfSk7XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfSkoKTtcbiAgICAgICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgICBjYXNlICdjaGFuZ2VQYXNzd29yZCc6XG4gICAgICAgICAgICAoYXN5bmMgKCkgPT4ge1xuICAgICAgICAgICAgICAgIHRyeSB7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHsgb2xkUGFzc3dvcmQsIG5ld1Bhc3N3b3JkIH0gPSBtZXNzYWdlLnBheWxvYWQ7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHZhbGlkID0gYXdhaXQgY2hlY2tQYXNzd29yZChvbGRQYXNzd29yZCk7XG4gICAgICAgICAgICAgICAgICAgIGlmICghdmFsaWQpIHtcbiAgICAgICAgICAgICAgICAgICAgICAgIHNlbmRSZXNwb25zZSh7IHN1Y2Nlc3M6IGZhbHNlLCBlcnJvcjogJ0ludmFsaWQgY3VycmVudCBwYXNzd29yZCcgfSk7XG4gICAgICAgICAgICAgICAgICAgICAgICByZXR1cm47XG4gICAgICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICAgICAgYXdhaXQgY2hhbmdlUGFzc3dvcmRGb3JLZXlzKG9sZFBhc3N3b3JkLCBuZXdQYXNzd29yZCk7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHJlc3VsdCA9IGF3YWl0IHVubG9ja1Nlc3Npb24obmV3UGFzc3dvcmQpO1xuICAgICAgICAgICAgICAgICAgICAvLyBCcm9hZGNhc3QgcGFzc3dvcmQgc3RhdGUgY2hhbmdlIHRvIGFsbCB2aWV3c1xuICAgICAgICAgICAgICAgICAgICBhcGkucnVudGltZS5zZW5kTWVzc2FnZSh7IGtpbmQ6ICdwYXNzd29yZFN0YXRlQ2hhbmdlZCcsIGhhc1Bhc3N3b3JkOiB0cnVlIH0pLmNhdGNoKCgpID0+IHt9KTtcbiAgICAgICAgICAgICAgICAgICAgYXBpLnJ1bnRpbWUuc2VuZE1lc3NhZ2UoeyBraW5kOiAnYmFja3VwTmVlZGVkJyB9KS5jYXRjaCgoKSA9PiB7fSk7XG4gICAgICAgICAgICAgICAgICAgIHNlbmRSZXNwb25zZShyZXN1bHQpO1xuICAgICAgICAgICAgICAgIH0gY2F0Y2ggKGUpIHtcbiAgICAgICAgICAgICAgICAgICAgc2VuZFJlc3BvbnNlKHsgc3VjY2VzczogZmFsc2UsIGVycm9yOiBlLm1lc3NhZ2UgfSk7XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfSkoKTtcbiAgICAgICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgICBjYXNlICdyZW1vdmVQYXNzd29yZCc6XG4gICAgICAgICAgICAoYXN5bmMgKCkgPT4ge1xuICAgICAgICAgICAgICAgIHRyeSB7XG4gICAgICAgICAgICAgICAgICAgIGF3YWl0IHJlbW92ZVBhc3N3b3JkUHJvdGVjdGlvbihtZXNzYWdlLnBheWxvYWQpO1xuICAgICAgICAgICAgICAgICAgICBzZXNzaW9uS2V5cy5jbGVhcigpO1xuICAgICAgICAgICAgICAgICAgICBzZXNzaW9uQ3J5cHRvS2V5ID0gbnVsbDtcbiAgICAgICAgICAgICAgICAgICAgc2Vzc2lvbktleVNhbHQgPSBudWxsO1xuICAgICAgICAgICAgICAgICAgICBsb2NrZWQgPSBmYWxzZTtcbiAgICAgICAgICAgICAgICAgICAgZW5jcnlwdGlvbkVuYWJsZWQgPSBmYWxzZTtcbiAgICAgICAgICAgICAgICAgICAgLy8gQnJvYWRjYXN0IHBhc3N3b3JkIHN0YXRlIGNoYW5nZSB0byBhbGwgdmlld3NcbiAgICAgICAgICAgICAgICAgICAgYXBpLnJ1bnRpbWUuc2VuZE1lc3NhZ2UoeyBraW5kOiAncGFzc3dvcmRTdGF0ZUNoYW5nZWQnLCBoYXNQYXNzd29yZDogZmFsc2UgfSkuY2F0Y2goKCkgPT4ge30pO1xuICAgICAgICAgICAgICAgICAgICBzZW5kUmVzcG9uc2UoeyBzdWNjZXNzOiB0cnVlIH0pO1xuICAgICAgICAgICAgICAgIH0gY2F0Y2ggKGUpIHtcbiAgICAgICAgICAgICAgICAgICAgc2VuZFJlc3BvbnNlKHsgc3VjY2VzczogZmFsc2UsIGVycm9yOiBlLm1lc3NhZ2UgfSk7XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfSkoKTtcbiAgICAgICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgICBjYXNlICdyZXNldEFsbERhdGEnOlxuICAgICAgICAgICAgKGFzeW5jICgpID0+IHtcbiAgICAgICAgICAgICAgICB0cnkge1xuICAgICAgICAgICAgICAgICAgICAvLyBDbGVhciBhbGwgZXh0ZW5zaW9uIGRhdGEgYW5kIHJlc2V0IHRvIGZyZXNoIHN0YXRlXG4gICAgICAgICAgICAgICAgICAgIGF3YWl0IHN0b3JhZ2UuY2xlYXIoKTtcbiAgICAgICAgICAgICAgICAgICAgc2Vzc2lvbktleXMuY2xlYXIoKTtcbiAgICAgICAgICAgICAgICAgICAgc2Vzc2lvbkNyeXB0b0tleSA9IG51bGw7XG4gICAgICAgICAgICAgICAgICAgIHNlc3Npb25LZXlTYWx0ID0gbnVsbDtcbiAgICAgICAgICAgICAgICAgICAgbG9ja2VkID0gZmFsc2U7XG4gICAgICAgICAgICAgICAgICAgIGVuY3J5cHRpb25FbmFibGVkID0gZmFsc2U7XG4gICAgICAgICAgICAgICAgICAgIG5vc3RyQWNjZXNzV2hpbGVMb2NrZWQgPSBmYWxzZTtcbiAgICAgICAgICAgICAgICAgICAgYmxvY2tDcm9zc09yaWdpbkZyYW1lcyA9IHRydWU7XG4gICAgICAgICAgICAgICAgICAgIC8vIFJlLWluaXRpYWxpemUgd2l0aCBkZWZhdWx0IHByb2ZpbGVcbiAgICAgICAgICAgICAgICAgICAgYXdhaXQgc3RvcmFnZS5zZXQoe1xuICAgICAgICAgICAgICAgICAgICAgICAgcHJvZmlsZXM6IFt7IG5hbWU6ICdEZWZhdWx0IE5vc3RyIFByb2ZpbGUnLCBwcml2S2V5OiAnJywgcHViS2V5OiAnJyB9XSxcbiAgICAgICAgICAgICAgICAgICAgICAgIHByb2ZpbGVJbmRleDogMCxcbiAgICAgICAgICAgICAgICAgICAgICAgIGlzRW5jcnlwdGVkOiBmYWxzZSxcbiAgICAgICAgICAgICAgICAgICAgICAgIHBhc3N3b3JkSGFzaDogbnVsbCxcbiAgICAgICAgICAgICAgICAgICAgICAgIHBhc3N3b3JkU2FsdDogbnVsbCxcbiAgICAgICAgICAgICAgICAgICAgfSk7XG4gICAgICAgICAgICAgICAgICAgIGFwaS5ydW50aW1lLnNlbmRNZXNzYWdlKHsga2luZDogJ2RhdGFSZXNldCcgfSkuY2F0Y2goKCkgPT4ge30pO1xuICAgICAgICAgICAgICAgICAgICBzZW5kUmVzcG9uc2UoeyBzdWNjZXNzOiB0cnVlIH0pO1xuICAgICAgICAgICAgICAgIH0gY2F0Y2ggKGUpIHtcbiAgICAgICAgICAgICAgICAgICAgc2VuZFJlc3BvbnNlKHsgc3VjY2VzczogZmFsc2UsIGVycm9yOiBlLm1lc3NhZ2UgfSk7XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfSkoKTtcbiAgICAgICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgICBjYXNlICdzZXRBdXRvTG9ja1RpbWVvdXQnOiB7XG4gICAgICAgICAgICBjb25zdCBBTExPV0VEX0xPQ0tfTUlOVVRFUyA9IFswLCA1LCAxNSwgMzAsIDYwLCA5MCwgMTgwXTtcbiAgICAgICAgICAgIGNvbnN0IG1pbnMgPSBOdW1iZXIobWVzc2FnZS5wYXlsb2FkKTtcbiAgICAgICAgICAgIGlmICghQUxMT1dFRF9MT0NLX01JTlVURVMuaW5jbHVkZXMobWlucykpIHtcbiAgICAgICAgICAgICAgICBzZW5kUmVzcG9uc2UoZmFsc2UpO1xuICAgICAgICAgICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgICAgICAgfVxuICAgICAgICAgICAgYXV0b0xvY2tUaW1lb3V0ID0gbWlucyAqIDYwICogMTAwMDtcbiAgICAgICAgICAgIHN0b3JhZ2Uuc2V0KHsgYXV0b0xvY2tNaW51dGVzOiBtaW5zIH0pO1xuICAgICAgICAgICAgcmVzZXRBdXRvTG9jaygpO1xuICAgICAgICAgICAgc2VuZFJlc3BvbnNlKHRydWUpO1xuICAgICAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgICAgIH1cbiAgICAgICAgY2FzZSAnZ2V0QXV0b0xvY2tUaW1lb3V0JzpcbiAgICAgICAgICAgIHJlcGx5KHNlbmRSZXNwb25zZSwgYXN5bmMgKCkgPT4ge1xuICAgICAgICAgICAgICAgIGNvbnN0IHsgYXV0b0xvY2tNaW51dGVzIH0gPSBhd2FpdCBzdG9yYWdlLmdldCh7IGF1dG9Mb2NrTWludXRlczogMTUgfSk7XG4gICAgICAgICAgICAgICAgcmV0dXJuIGF1dG9Mb2NrTWludXRlcztcbiAgICAgICAgICAgIH0pO1xuICAgICAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgICAgIGNhc2UgJ3Jlc2V0QXV0b0xvY2snOlxuICAgICAgICAgICAgcmVzZXRBdXRvTG9jaygpO1xuICAgICAgICAgICAgc2VuZFJlc3BvbnNlKHRydWUpO1xuICAgICAgICAgICAgcmV0dXJuIHRydWU7XG5cbiAgICAgICAgLy8gLS0tIE5vc3RyIGFjY2VzcyB3aGlsZSBsb2NrZWQgLS0tXG4gICAgICAgIGNhc2UgJ2dldE5vc3RyQWNjZXNzV2hpbGVMb2NrZWQnOlxuICAgICAgICAgICAgc2VuZFJlc3BvbnNlKG5vc3RyQWNjZXNzV2hpbGVMb2NrZWQpO1xuICAgICAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgICAgIGNhc2UgJ3NldE5vc3RyQWNjZXNzV2hpbGVMb2NrZWQnOlxuICAgICAgICAgICAgbm9zdHJBY2Nlc3NXaGlsZUxvY2tlZCA9ICEhbWVzc2FnZS5wYXlsb2FkO1xuICAgICAgICAgICAgc3RvcmFnZS5zZXQoeyBub3N0ckFjY2Vzc1doaWxlTG9ja2VkOiAhIW1lc3NhZ2UucGF5bG9hZCB9KTtcbiAgICAgICAgICAgIGlmICghbWVzc2FnZS5wYXlsb2FkICYmIGxvY2tlZCkge1xuICAgICAgICAgICAgICAgIHNlc3Npb25LZXlzLmNsZWFyKCk7ICAvLyBUdXJuaW5nIE9GRiB3aGlsZSBsb2NrZWQgPSBjbGVhciBrZXlzIGltbWVkaWF0ZWx5XG4gICAgICAgICAgICB9XG4gICAgICAgICAgICBzZW5kUmVzcG9uc2UodHJ1ZSk7XG4gICAgICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgICAgY2FzZSAnZ2V0QmxvY2tDcm9zc09yaWdpbkZyYW1lcyc6XG4gICAgICAgICAgICBzZW5kUmVzcG9uc2UoYmxvY2tDcm9zc09yaWdpbkZyYW1lcyk7XG4gICAgICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgICAgY2FzZSAnc2V0QmxvY2tDcm9zc09yaWdpbkZyYW1lcyc6XG4gICAgICAgICAgICBibG9ja0Nyb3NzT3JpZ2luRnJhbWVzID0gISFtZXNzYWdlLnBheWxvYWQ7XG4gICAgICAgICAgICBzdG9yYWdlLnNldCh7IGJsb2NrQ3Jvc3NPcmlnaW5GcmFtZXM6ICEhbWVzc2FnZS5wYXlsb2FkIH0pO1xuICAgICAgICAgICAgc2VuZFJlc3BvbnNlKHRydWUpO1xuICAgICAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgICAgIGNhc2UgJ2dldEFjdGl2ZVByb2ZpbGVJbmZvJzpcbiAgICAgICAgICAgIChhc3luYyAoKSA9PiB7XG4gICAgICAgICAgICAgICAgdHJ5IHtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgcGkgPSBhd2FpdCBnZXRQcm9maWxlSW5kZXgoKTtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgcHJvZmlsZXMgPSBhd2FpdCBnZXRQcm9maWxlcygpO1xuICAgICAgICAgICAgICAgICAgICBjb25zdCBwcm9maWxlID0gcHJvZmlsZXNbcGldO1xuICAgICAgICAgICAgICAgICAgICBpZiAoIXByb2ZpbGUpIHtcbiAgICAgICAgICAgICAgICAgICAgICAgIGxvZygnW2dldEFjdGl2ZVByb2ZpbGVJbmZvXSBObyBwcm9maWxlIGZvdW5kIGF0IGluZGV4ICcgKyBwaSk7XG4gICAgICAgICAgICAgICAgICAgICAgICBzZW5kUmVzcG9uc2UoeyBuYW1lOiAnVW5rbm93bicsIG5wdWI6ICcnLCBoYXNLZXlzOiBmYWxzZSB9KTtcbiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybjtcbiAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgICAgICBsZXQgbnB1YiA9ICcnO1xuICAgICAgICAgICAgICAgICAgICBpZiAocHJvZmlsZS50eXBlID09PSAnYnVua2VyJyAmJiBwcm9maWxlLnJlbW90ZVB1YmtleSkge1xuICAgICAgICAgICAgICAgICAgICAgICAgbnB1YiA9IG5pcDE5Lm5wdWJFbmNvZGUocHJvZmlsZS5yZW1vdGVQdWJrZXkpO1xuICAgICAgICAgICAgICAgICAgICB9IGVsc2UgaWYgKHByb2ZpbGUucHViS2V5KSB7XG4gICAgICAgICAgICAgICAgICAgICAgICBucHViID0gbmlwMTkubnB1YkVuY29kZShwcm9maWxlLnB1YktleSk7XG4gICAgICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICAgICAgY29uc3QgcmVzdWx0ID0ge1xuICAgICAgICAgICAgICAgICAgICAgICAgbmFtZTogcHJvZmlsZS5uYW1lIHx8ICdVbm5hbWVkIFByb2ZpbGUnLFxuICAgICAgICAgICAgICAgICAgICAgICAgbnB1YixcbiAgICAgICAgICAgICAgICAgICAgICAgIGhhc0tleXM6IHNlc3Npb25LZXlzLmhhcyhwaSksXG4gICAgICAgICAgICAgICAgICAgICAgICBpc0J1bmtlcjogcHJvZmlsZS50eXBlID09PSAnYnVua2VyJyxcbiAgICAgICAgICAgICAgICAgICAgfTtcbiAgICAgICAgICAgICAgICAgICAgbG9nKCdbZ2V0QWN0aXZlUHJvZmlsZUluZm9dIFNlbmRpbmc6ICcgKyBKU09OLnN0cmluZ2lmeShyZXN1bHQpKTtcbiAgICAgICAgICAgICAgICAgICAgc2VuZFJlc3BvbnNlKHJlc3VsdCk7XG4gICAgICAgICAgICAgICAgfSBjYXRjaCAoZSkge1xuICAgICAgICAgICAgICAgICAgICBsb2coJ1tnZXRBY3RpdmVQcm9maWxlSW5mb10gRXJyb3I6ICcgKyBlLm1lc3NhZ2UpO1xuICAgICAgICAgICAgICAgICAgICBzZW5kUmVzcG9uc2UoeyBuYW1lOiAnRXJyb3InLCBucHViOiAnJywgaGFzS2V5czogZmFsc2UgfSk7XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfSkoKTtcbiAgICAgICAgICAgIHJldHVybiB0cnVlO1xuXG4gICAgICAgIC8vIC0tLSBOSVAtNDkgbmNyeXB0c2VjIGhhbmRsZXJzIC0tLVxuICAgICAgICBjYXNlICduY3J5cHRzZWMuZGVjcnlwdCc6XG4gICAgICAgICAgICByZXBseShzZW5kUmVzcG9uc2UsIGFzeW5jICgpID0+IHtcbiAgICAgICAgICAgICAgICB0cnkge1xuICAgICAgICAgICAgICAgICAgICBjb25zdCB7IG5jcnlwdHNlYywgcGFzc3dvcmQgfSA9IG1lc3NhZ2UucGF5bG9hZDtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgaGV4S2V5ID0gYnl0ZXNUb0hleChuaXA0OURlY3J5cHQobmNyeXB0c2VjLCBwYXNzd29yZCkpO1xuICAgICAgICAgICAgICAgICAgICByZXR1cm4geyBzdWNjZXNzOiB0cnVlLCBoZXhLZXkgfTtcbiAgICAgICAgICAgICAgICB9IGNhdGNoIChlKSB7XG4gICAgICAgICAgICAgICAgICAgIHJldHVybiB7IHN1Y2Nlc3M6IGZhbHNlLCBlcnJvcjogZS5tZXNzYWdlIHx8ICdEZWNyeXB0aW9uIGZhaWxlZCcgfTtcbiAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICB9KTtcbiAgICAgICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgICBjYXNlICduY3J5cHRzZWMuZW5jcnlwdCc6XG4gICAgICAgICAgICByZXBseShzZW5kUmVzcG9uc2UsIGFzeW5jICgpID0+IHtcbiAgICAgICAgICAgICAgICB0cnkge1xuICAgICAgICAgICAgICAgICAgICBjb25zdCB7IHByb2ZpbGVJbmRleDogZWksIHBhc3N3b3JkIH0gPSBtZXNzYWdlLnBheWxvYWQ7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHByb2ZpbGUgPSBhd2FpdCBnZXRQcm9maWxlKGVpKTtcbiAgICAgICAgICAgICAgICAgICAgaWYgKHByb2ZpbGU/LnR5cGUgPT09ICdidW5rZXInKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICByZXR1cm4geyBzdWNjZXNzOiBmYWxzZSwgZXJyb3I6ICdDYW5ub3QgZXhwb3J0IGJ1bmtlciBwcm9maWxlIGFzIG5jcnlwdHNlYycgfTtcbiAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgICAgICBjb25zdCBoZXhLZXkgPSBhd2FpdCBnZXRQbGFpbnRleHRQcml2S2V5KGVpLCBwcm9maWxlKTtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgbmNyeXB0c2VjID0gbmlwNDlFbmNyeXB0KGhleFRvQnl0ZXMoaGV4S2V5KSwgcGFzc3dvcmQpO1xuICAgICAgICAgICAgICAgICAgICByZXR1cm4geyBzdWNjZXNzOiB0cnVlLCBuY3J5cHRzZWMgfTtcbiAgICAgICAgICAgICAgICB9IGNhdGNoIChlKSB7XG4gICAgICAgICAgICAgICAgICAgIHJldHVybiB7IHN1Y2Nlc3M6IGZhbHNlLCBlcnJvcjogZS5tZXNzYWdlIHx8ICdFbmNyeXB0aW9uIGZhaWxlZCcgfTtcbiAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICB9KTtcbiAgICAgICAgICAgIHJldHVybiB0cnVlO1xuXG4gICAgICAgIC8vIC0tLSBCSVAzOSBTZWVkIFBocmFzZSBoYW5kbGVycyAtLS1cbiAgICAgICAgY2FzZSAnc2VlZFBocmFzZS5mcm9tS2V5JzpcbiAgICAgICAgICAgIHJlcGx5KHNlbmRSZXNwb25zZSwgYXN5bmMgKCkgPT4ge1xuICAgICAgICAgICAgICAgIHRyeSB7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IGVpID0gbWVzc2FnZS5wYXlsb2FkO1xuICAgICAgICAgICAgICAgICAgICBjb25zdCBwcm9maWxlID0gYXdhaXQgZ2V0UHJvZmlsZShlaSk7XG4gICAgICAgICAgICAgICAgICAgIGlmIChwcm9maWxlPy50eXBlID09PSAnYnVua2VyJykge1xuICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHsgc3VjY2VzczogZmFsc2UsIGVycm9yOiAnQ2Fubm90IGV4cG9ydCBidW5rZXIgcHJvZmlsZSBhcyBzZWVkIHBocmFzZScgfTtcbiAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgICAgICBjb25zdCBoZXhLZXkgPSBhd2FpdCBnZXRQbGFpbnRleHRQcml2S2V5KGVpLCBwcm9maWxlKTtcbiAgICAgICAgICAgICAgICAgICAgY29uc3Qgc2VlZFBocmFzZSA9IGtleVRvU2VlZFBocmFzZShoZXhLZXkpO1xuICAgICAgICAgICAgICAgICAgICByZXR1cm4geyBzdWNjZXNzOiB0cnVlLCBzZWVkUGhyYXNlIH07XG4gICAgICAgICAgICAgICAgfSBjYXRjaCAoZSkge1xuICAgICAgICAgICAgICAgICAgICByZXR1cm4geyBzdWNjZXNzOiBmYWxzZSwgZXJyb3I6IGUubWVzc2FnZSB8fCAnRmFpbGVkIHRvIGdlbmVyYXRlIHNlZWQgcGhyYXNlJyB9O1xuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgIH0pO1xuICAgICAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgICAgIGNhc2UgJ3NlZWRQaHJhc2UudG9LZXknOlxuICAgICAgICAgICAgcmVwbHkoc2VuZFJlc3BvbnNlLCBhc3luYyAoKSA9PiB7XG4gICAgICAgICAgICAgICAgdHJ5IHtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgeyBoZXhLZXksIHB1YktleSB9ID0gc2VlZFBocmFzZVRvS2V5KG1lc3NhZ2UucGF5bG9hZCk7XG4gICAgICAgICAgICAgICAgICAgIHJldHVybiB7IHN1Y2Nlc3M6IHRydWUsIGhleEtleSwgcHViS2V5IH07XG4gICAgICAgICAgICAgICAgfSBjYXRjaCAoZSkge1xuICAgICAgICAgICAgICAgICAgICByZXR1cm4geyBzdWNjZXNzOiBmYWxzZSwgZXJyb3I6IGUubWVzc2FnZSB8fCAnSW52YWxpZCBzZWVkIHBocmFzZScgfTtcbiAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICB9KTtcbiAgICAgICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgICBjYXNlICdzZWVkUGhyYXNlLnZhbGlkYXRlJzpcbiAgICAgICAgICAgIHNlbmRSZXNwb25zZShpc1ZhbGlkU2VlZFBocmFzZShtZXNzYWdlLnBheWxvYWQpKTtcbiAgICAgICAgICAgIHJldHVybiB0cnVlO1xuXG4gICAgICAgIC8vIC0tLSBOSVAtNDYgQnVua2VyIGhhbmRsZXJzIC0tLVxuICAgICAgICBjYXNlICdnZXRQcm9maWxlVHlwZSc6XG4gICAgICAgICAgICByZXBseShzZW5kUmVzcG9uc2UsIGFzeW5jICgpID0+IHtcbiAgICAgICAgICAgICAgICBjb25zdCBwaSA9IG1lc3NhZ2UucGF5bG9hZCA/PyBhd2FpdCBnZXRQcm9maWxlSW5kZXgoKTtcbiAgICAgICAgICAgICAgICBjb25zdCBwcm9maWxlID0gYXdhaXQgZ2V0UHJvZmlsZShwaSk7XG4gICAgICAgICAgICAgICAgcmV0dXJuIHByb2ZpbGU/LnR5cGUgfHwgJ2xvY2FsJztcbiAgICAgICAgICAgIH0pO1xuICAgICAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgICAgIGNhc2UgJ2J1bmtlci5jb25uZWN0JzpcbiAgICAgICAgICAgIHJlcGx5KHNlbmRSZXNwb25zZSwgYXN5bmMgKCkgPT4ge1xuICAgICAgICAgICAgICAgIHRyeSB7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHsgcHJvZmlsZUluZGV4OiBiaSwgYnVua2VyVXJsIH0gPSBtZXNzYWdlLnBheWxvYWQ7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHNlc3Npb24gPSBhd2FpdCBjcmVhdGVTZXNzaW9uKGJpLCBidW5rZXJVcmwpO1xuICAgICAgICAgICAgICAgICAgICBjb25zdCByZW1vdGVQdWJrZXkgPSBhd2FpdCBzZXNzaW9uLmdldFB1YmxpY0tleSgpO1xuICAgICAgICAgICAgICAgICAgICBjb25zdCBwcm9maWxlcyA9IGF3YWl0IGdldFByb2ZpbGVzKCk7XG4gICAgICAgICAgICAgICAgICAgIHByb2ZpbGVzW2JpXS5yZW1vdGVQdWJrZXkgPSByZW1vdGVQdWJrZXk7XG4gICAgICAgICAgICAgICAgICAgIHByb2ZpbGVzW2JpXS5idW5rZXJVcmwgPSBidW5rZXJVcmw7XG4gICAgICAgICAgICAgICAgICAgIGF3YWl0IHN0b3JhZ2Uuc2V0KHsgcHJvZmlsZXMgfSk7XG4gICAgICAgICAgICAgICAgICAgIHJldHVybiB7IHN1Y2Nlc3M6IHRydWUsIHJlbW90ZVB1YmtleSB9O1xuICAgICAgICAgICAgICAgIH0gY2F0Y2ggKGUpIHtcbiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHsgc3VjY2VzczogZmFsc2UsIGVycm9yOiBlLm1lc3NhZ2UgfTtcbiAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICB9KTtcbiAgICAgICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgICBjYXNlICdidW5rZXIuZGlzY29ubmVjdCc6XG4gICAgICAgICAgICByZXBseShzZW5kUmVzcG9uc2UsIGFzeW5jICgpID0+IHtcbiAgICAgICAgICAgICAgICB0cnkge1xuICAgICAgICAgICAgICAgICAgICBjb25zdCBiaSA9IG1lc3NhZ2UucGF5bG9hZDtcbiAgICAgICAgICAgICAgICAgICAgYXdhaXQgZGlzY29ubmVjdFNlc3Npb24oYmkpO1xuICAgICAgICAgICAgICAgICAgICByZXR1cm4geyBzdWNjZXNzOiB0cnVlIH07XG4gICAgICAgICAgICAgICAgfSBjYXRjaCAoZSkge1xuICAgICAgICAgICAgICAgICAgICByZXR1cm4geyBzdWNjZXNzOiBmYWxzZSwgZXJyb3I6IGUubWVzc2FnZSB9O1xuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgIH0pO1xuICAgICAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgICAgIGNhc2UgJ2J1bmtlci5zdGF0dXMnOlxuICAgICAgICAgICAgcmVwbHkoc2VuZFJlc3BvbnNlLCBhc3luYyAoKSA9PiB7XG4gICAgICAgICAgICAgICAgY29uc3QgYmkgPSBtZXNzYWdlLnBheWxvYWQgPz8gYXdhaXQgZ2V0UHJvZmlsZUluZGV4KCk7XG4gICAgICAgICAgICAgICAgcmV0dXJuIHsgY29ubmVjdGVkOiBpc1Nlc3Npb25BY3RpdmUoYmkpIH07XG4gICAgICAgICAgICB9KTtcbiAgICAgICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgICBjYXNlICdidW5rZXIucGluZyc6XG4gICAgICAgICAgICByZXBseShzZW5kUmVzcG9uc2UsIGFzeW5jICgpID0+IHtcbiAgICAgICAgICAgICAgICB0cnkge1xuICAgICAgICAgICAgICAgICAgICBjb25zdCBiaSA9IG1lc3NhZ2UucGF5bG9hZCA/PyBhd2FpdCBnZXRQcm9maWxlSW5kZXgoKTtcbiAgICAgICAgICAgICAgICAgICAgY29uc3Qgc2Vzc2lvbiA9IGF3YWl0IGdldE9yQ3JlYXRlU2Vzc2lvbihiaSk7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHJlc3VsdCA9IGF3YWl0IHNlc3Npb24ucGluZygpO1xuICAgICAgICAgICAgICAgICAgICByZXR1cm4geyBzdWNjZXNzOiB0cnVlLCByZXN1bHQgfTtcbiAgICAgICAgICAgICAgICB9IGNhdGNoIChlKSB7XG4gICAgICAgICAgICAgICAgICAgIHJldHVybiB7IHN1Y2Nlc3M6IGZhbHNlLCBlcnJvcjogZS5tZXNzYWdlIH07XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfSk7XG4gICAgICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgICAgY2FzZSAnYnVua2VyLnZhbGlkYXRlVXJsJzpcbiAgICAgICAgICAgIHNlbmRSZXNwb25zZSh2YWxpZGF0ZUJ1bmtlclVybChtZXNzYWdlLnBheWxvYWQpKTtcbiAgICAgICAgICAgIHJldHVybiB0cnVlO1xuXG4gICAgICAgIC8vIC0tLSBCdW5rZXIgU2VydmVyIGhhbmRsZXJzIChleHRlbnNpb24gYWN0cyBhcyBOSVAtNDYgc2lnbmVyKSAtLS1cbiAgICAgICAgY2FzZSAnYnVua2VyU2VydmVyLnN0YXJ0JzpcbiAgICAgICAgICAgIHJlcGx5KHNlbmRSZXNwb25zZSwgYXN5bmMgKCkgPT4ge1xuICAgICAgICAgICAgICAgIHRyeSB7XG4gICAgICAgICAgICAgICAgICAgIGlmIChhY3RpdmVCdW5rZXJTZXJ2ZXIpIHtcbiAgICAgICAgICAgICAgICAgICAgICAgIGFjdGl2ZUJ1bmtlclNlcnZlci5zdG9wKCk7XG4gICAgICAgICAgICAgICAgICAgICAgICBhY3RpdmVCdW5rZXJTZXJ2ZXIgPSBudWxsO1xuICAgICAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHB1YmtleSA9IGF3YWl0IGdldFB1YktleSgpO1xuICAgICAgICAgICAgICAgICAgICBjb25zdCByZWxheVVybHMgPSBtZXNzYWdlLnBheWxvYWQ/LnJlbGF5VXJscyB8fCBbJ3dzczovL3JlbGF5Lm5vc3Rya2V5LmNvbSddO1xuICAgICAgICAgICAgICAgICAgICBjb25zdCBzZWNyZXQgPSBjcnlwdG8ucmFuZG9tVVVJRCgpLnJlcGxhY2UoLy0vZywgJycpLnNsaWNlKDAsIDE2KTtcbiAgICAgICAgICAgICAgICAgICAgY29uc3Qgc2VydmVyID0gbmV3IEJ1bmtlclNlcnZlcih7IHJlbGF5VXJscywgdXNlclB1YmtleTogcHVia2V5LCBzZWNyZXQgfSk7XG4gICAgICAgICAgICAgICAgICAgIGF3YWl0IHNlcnZlci5zdGFydCh7IGdldFByaXZLZXkgfSk7XG4gICAgICAgICAgICAgICAgICAgIGFjdGl2ZUJ1bmtlclNlcnZlciA9IHNlcnZlcjtcbiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHsgc3VjY2VzczogdHJ1ZSwgdXJpOiBzZXJ2ZXIuZ2V0Q29ubmVjdGlvblN0cmluZygpIH07XG4gICAgICAgICAgICAgICAgfSBjYXRjaCAoZSkge1xuICAgICAgICAgICAgICAgICAgICByZXR1cm4geyBzdWNjZXNzOiBmYWxzZSwgZXJyb3I6IGUubWVzc2FnZSB9O1xuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgIH0pO1xuICAgICAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgICAgIGNhc2UgJ2J1bmtlclNlcnZlci5zdG9wJzpcbiAgICAgICAgICAgIHJlcGx5KHNlbmRSZXNwb25zZSwgYXN5bmMgKCkgPT4ge1xuICAgICAgICAgICAgICAgIGlmIChhY3RpdmVCdW5rZXJTZXJ2ZXIpIHtcbiAgICAgICAgICAgICAgICAgICAgYWN0aXZlQnVua2VyU2VydmVyLnN0b3AoKTtcbiAgICAgICAgICAgICAgICAgICAgYWN0aXZlQnVua2VyU2VydmVyID0gbnVsbDtcbiAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgcmV0dXJuIHsgc3VjY2VzczogdHJ1ZSB9O1xuICAgICAgICAgICAgfSk7XG4gICAgICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgICAgY2FzZSAnYnVua2VyU2VydmVyLnN0YXR1cyc6XG4gICAgICAgICAgICBzZW5kUmVzcG9uc2Uoe1xuICAgICAgICAgICAgICAgIGFjdGl2ZTogISFhY3RpdmVCdW5rZXJTZXJ2ZXI/LmFjdGl2ZSxcbiAgICAgICAgICAgICAgICB1cmk6IGFjdGl2ZUJ1bmtlclNlcnZlcj8uZ2V0Q29ubmVjdGlvblN0cmluZygpIHx8IG51bGwsXG4gICAgICAgICAgICAgICAgY2xpZW50Q291bnQ6IGFjdGl2ZUJ1bmtlclNlcnZlcj8uYXV0aGVudGljYXRlZENsaWVudHMuc2l6ZSB8fCAwLFxuICAgICAgICAgICAgfSk7XG4gICAgICAgICAgICByZXR1cm4gdHJ1ZTtcblxuICAgICAgICAvLyAtLS0gVmF1bHQgaGFuZGxlcnMgLS0tXG4gICAgICAgIGNhc2UgJ3ZhdWx0LnB1Ymxpc2gnOlxuICAgICAgICAgICAgcmVwbHkoc2VuZFJlc3BvbnNlLCBhc3luYyAoKSA9PiB7XG4gICAgICAgICAgICAgICAgdHJ5IHtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgeyBwYXRoLCBjb250ZW50IH0gPSBtZXNzYWdlLnBheWxvYWQ7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHB1YmtleSA9IGF3YWl0IGdldFB1YktleSgpO1xuICAgICAgICAgICAgICAgICAgICBjb25zdCBlbmNyeXB0ZWQgPSBhd2FpdCBuaXA0NEVuY3J5cHQoeyBwdWJLZXk6IHB1YmtleSwgcGxhaW5UZXh0OiBjb250ZW50IH0pO1xuICAgICAgICAgICAgICAgICAgICBjb25zdCB1bnNpZ25lZCA9IGJ1aWxkVmF1bHRFdmVudChwYXRoLCBlbmNyeXB0ZWQpO1xuXG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHBpID0gYXdhaXQgZ2V0UHJvZmlsZUluZGV4KCk7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHByb2ZpbGUgPSBhd2FpdCBnZXRQcm9maWxlKHBpKTtcbiAgICAgICAgICAgICAgICAgICAgbGV0IHNpZ25lZDtcbiAgICAgICAgICAgICAgICAgICAgaWYgKHByb2ZpbGUudHlwZSA9PT0gJ2J1bmtlcicpIHtcbiAgICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IHNlc3Npb24gPSBhd2FpdCBnZXRPckNyZWF0ZVNlc3Npb24ocGkpO1xuICAgICAgICAgICAgICAgICAgICAgICAgc2lnbmVkID0gYXdhaXQgc2Vzc2lvbi5zaWduRXZlbnQodW5zaWduZWQpO1xuICAgICAgICAgICAgICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgICAgICAgICAgICAgY29uc3Qgc2sgPSBhd2FpdCBnZXRQcml2S2V5KCk7XG4gICAgICAgICAgICAgICAgICAgICAgICBzaWduZWQgPSBhd2FpdCBmaW5hbGl6ZUV2ZW50KHVuc2lnbmVkLCBzayk7XG4gICAgICAgICAgICAgICAgICAgIH1cblxuICAgICAgICAgICAgICAgICAgICBhd2FpdCB3aXRoUmVsYXlzKCd3cml0ZScsIGFzeW5jIChyZWxheXMpID0+IHtcbiAgICAgICAgICAgICAgICAgICAgICAgIGZvciAoY29uc3QgcmVsYXkgb2YgcmVsYXlzKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgdHJ5IHsgcmVsYXkucHVibGlzaChzaWduZWQpOyB9IGNhdGNoIChfKSB7fVxuICAgICAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgICAgICB9KTtcbiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHsgc3VjY2VzczogdHJ1ZSwgZXZlbnRJZDogc2lnbmVkLmlkLCBjcmVhdGVkQXQ6IHNpZ25lZC5jcmVhdGVkX2F0IH07XG4gICAgICAgICAgICAgICAgfSBjYXRjaCAoZSkge1xuICAgICAgICAgICAgICAgICAgICByZXR1cm4geyBzdWNjZXNzOiBmYWxzZSwgZXJyb3I6IGUubWVzc2FnZSB9O1xuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgIH0pO1xuICAgICAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgICAgIGNhc2UgJ3ZhdWx0LmZldGNoJzpcbiAgICAgICAgICAgIHJlcGx5KHNlbmRSZXNwb25zZSwgYXN5bmMgKCkgPT4ge1xuICAgICAgICAgICAgICAgIHRyeSB7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHB1YmtleSA9IGF3YWl0IGdldFB1YktleSgpO1xuICAgICAgICAgICAgICAgICAgICBjb25zdCBmaWx0ZXIgPSBidWlsZFZhdWx0RmlsdGVyKHB1YmtleSk7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IGFsbEV2ZW50cyA9IFtdO1xuXG4gICAgICAgICAgICAgICAgICAgIGF3YWl0IHdpdGhSZWxheXMoJ3JlYWQnLCBhc3luYyAocmVsYXlzKSA9PiB7XG4gICAgICAgICAgICAgICAgICAgICAgICBjb25zdCBwZXJSZWxheSA9IHJlbGF5cy5tYXAocmVsYXkgPT4gbmV3IFByb21pc2UoKHJlc29sdmUpID0+IHtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICBjb25zdCBzdWJJZCA9IGB2YXVsdC0ke2NyeXB0by5yYW5kb21VVUlEKCkuc2xpY2UoMCwgOCl9YDtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICBjb25zdCB0aW1lb3V0ID0gc2V0VGltZW91dCgoKSA9PiB7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHRyeSB7IHJlbGF5LnVuc3Vic2NyaWJlKHN1YklkKTsgfSBjYXRjaCAoXykge31cbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcmVzb2x2ZSgpO1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0sIDE1MDAwKTtcblxuICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJlbGF5LnN1YnNjcmliZShcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc3ViSWQsXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFtmaWx0ZXJdLFxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAoZXZlbnQpID0+IHsgYWxsRXZlbnRzLnB1c2goZXZlbnQpOyB9LFxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAoKSA9PiB7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBjbGVhclRpbWVvdXQodGltZW91dCk7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB0cnkgeyByZWxheS51bnN1YnNjcmliZShzdWJJZCk7IH0gY2F0Y2ggKF8pIHt9XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICByZXNvbHZlKCk7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICAgICAgICAgICAgICApO1xuICAgICAgICAgICAgICAgICAgICAgICAgfSkpO1xuICAgICAgICAgICAgICAgICAgICAgICAgYXdhaXQgUHJvbWlzZS5hbGwocGVyUmVsYXkpO1xuICAgICAgICAgICAgICAgICAgICB9KTtcblxuICAgICAgICAgICAgICAgICAgICAvLyBEZWR1cGxpY2F0ZSBieSBkLXRhZyBcdTIwMTQgbGF0ZXN0IGNyZWF0ZWRfYXQgd2lucyAoTklQLTMzKVxuICAgICAgICAgICAgICAgICAgICBjb25zdCBieUR0YWcgPSBuZXcgTWFwKCk7XG4gICAgICAgICAgICAgICAgICAgIGZvciAoY29uc3QgZXZlbnQgb2YgYWxsRXZlbnRzKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICBjb25zdCBwYXJzZWQgPSBwYXJzZVZhdWx0RXZlbnQoZXZlbnQpO1xuICAgICAgICAgICAgICAgICAgICAgICAgaWYgKCFwYXJzZWQpIGNvbnRpbnVlO1xuICAgICAgICAgICAgICAgICAgICAgICAgY29uc3QgZXhpc3RpbmcgPSBieUR0YWcuZ2V0KHBhcnNlZC5wYXRoKTtcbiAgICAgICAgICAgICAgICAgICAgICAgIGlmICghZXhpc3RpbmcgfHwgcGFyc2VkLmNyZWF0ZWRBdCA+IGV4aXN0aW5nLmNyZWF0ZWRBdCkge1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgIGJ5RHRhZy5zZXQocGFyc2VkLnBhdGgsIHsgZXZlbnQsIHBhcnNlZCB9KTtcbiAgICAgICAgICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICAgICAgfVxuXG4gICAgICAgICAgICAgICAgICAgIC8vIERlY3J5cHQgZWFjaCBkb2N1bWVudFxuICAgICAgICAgICAgICAgICAgICBjb25zdCBkb2N1bWVudHMgPSBbXTtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgcHVia2V5XyA9IGF3YWl0IGdldFB1YktleSgpO1xuICAgICAgICAgICAgICAgICAgICBmb3IgKGNvbnN0IHsgZXZlbnQsIHBhcnNlZCB9IG9mIGJ5RHRhZy52YWx1ZXMoKSkge1xuICAgICAgICAgICAgICAgICAgICAgICAgdHJ5IHtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICBjb25zdCBkZWNyeXB0ZWQgPSBhd2FpdCBuaXA0NERlY3J5cHQoeyBwdWJLZXk6IHB1YmtleV8sIGNpcGhlclRleHQ6IGV2ZW50LmNvbnRlbnQgfSk7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgZG9jdW1lbnRzLnB1c2goe1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBwYXRoOiBwYXJzZWQucGF0aCxcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY29udGVudDogZGVjcnlwdGVkLFxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBjcmVhdGVkQXQ6IHBhcnNlZC5jcmVhdGVkQXQsXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGV2ZW50SWQ6IHBhcnNlZC5ldmVudElkLFxuICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0pO1xuICAgICAgICAgICAgICAgICAgICAgICAgfSBjYXRjaCAoXykge1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8vIFNraXAgZG9jdW1lbnRzIHdlIGNhbid0IGRlY3J5cHRcbiAgICAgICAgICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgICAgICByZXR1cm4geyBzdWNjZXNzOiB0cnVlLCBkb2N1bWVudHMgfTtcbiAgICAgICAgICAgICAgICB9IGNhdGNoIChlKSB7XG4gICAgICAgICAgICAgICAgICAgIHJldHVybiB7IHN1Y2Nlc3M6IGZhbHNlLCBlcnJvcjogZS5tZXNzYWdlIH07XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfSk7XG4gICAgICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgICAgY2FzZSAndmF1bHQuZGVsZXRlJzpcbiAgICAgICAgICAgIHJlcGx5KHNlbmRSZXNwb25zZSwgYXN5bmMgKCkgPT4ge1xuICAgICAgICAgICAgICAgIHRyeSB7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHsgcGF0aCwgZXZlbnRJZCB9ID0gbWVzc2FnZS5wYXlsb2FkO1xuICAgICAgICAgICAgICAgICAgICBjb25zdCB1bnNpZ25lZCA9IGJ1aWxkVmF1bHREZWxldGlvbihldmVudElkLCBwYXRoKTtcblxuICAgICAgICAgICAgICAgICAgICBjb25zdCBwaSA9IGF3YWl0IGdldFByb2ZpbGVJbmRleCgpO1xuICAgICAgICAgICAgICAgICAgICBjb25zdCBwcm9maWxlID0gYXdhaXQgZ2V0UHJvZmlsZShwaSk7XG4gICAgICAgICAgICAgICAgICAgIGxldCBzaWduZWQ7XG4gICAgICAgICAgICAgICAgICAgIGlmIChwcm9maWxlLnR5cGUgPT09ICdidW5rZXInKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICBjb25zdCBzZXNzaW9uID0gYXdhaXQgZ2V0T3JDcmVhdGVTZXNzaW9uKHBpKTtcbiAgICAgICAgICAgICAgICAgICAgICAgIHNpZ25lZCA9IGF3YWl0IHNlc3Npb24uc2lnbkV2ZW50KHVuc2lnbmVkKTtcbiAgICAgICAgICAgICAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IHNrID0gYXdhaXQgZ2V0UHJpdktleSgpO1xuICAgICAgICAgICAgICAgICAgICAgICAgc2lnbmVkID0gYXdhaXQgZmluYWxpemVFdmVudCh1bnNpZ25lZCwgc2spO1xuICAgICAgICAgICAgICAgICAgICB9XG5cbiAgICAgICAgICAgICAgICAgICAgYXdhaXQgd2l0aFJlbGF5cygnd3JpdGUnLCBhc3luYyAocmVsYXlzKSA9PiB7XG4gICAgICAgICAgICAgICAgICAgICAgICBmb3IgKGNvbnN0IHJlbGF5IG9mIHJlbGF5cykge1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgIHRyeSB7IHJlbGF5LnB1Ymxpc2goc2lnbmVkKTsgfSBjYXRjaCAoXykge31cbiAgICAgICAgICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICAgICAgfSk7XG4gICAgICAgICAgICAgICAgICAgIHJldHVybiB7IHN1Y2Nlc3M6IHRydWUgfTtcbiAgICAgICAgICAgICAgICB9IGNhdGNoIChlKSB7XG4gICAgICAgICAgICAgICAgICAgIHJldHVybiB7IHN1Y2Nlc3M6IGZhbHNlLCBlcnJvcjogZS5tZXNzYWdlIH07XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfSk7XG4gICAgICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgICAgY2FzZSAndmF1bHQuZ2V0UmVsYXlzJzpcbiAgICAgICAgICAgIHJlcGx5KHNlbmRSZXNwb25zZSwgYXN5bmMgKCkgPT4ge1xuICAgICAgICAgICAgICAgIHRyeSB7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHByb2ZpbGUgPSBhd2FpdCBjdXJyZW50UHJvZmlsZSgpO1xuICAgICAgICAgICAgICAgICAgICBjb25zdCByZWxheXMgPSBwcm9maWxlLnJlbGF5cyB8fCBbXTtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgcmVhZCA9IHJlbGF5cy5maWx0ZXIociA9PiByLnJlYWQpLm1hcChyID0+IHIudXJsKTtcbiAgICAgICAgICAgICAgICAgICAgY29uc3Qgd3JpdGUgPSByZWxheXMuZmlsdGVyKHIgPT4gci53cml0ZSkubWFwKHIgPT4gci51cmwpO1xuICAgICAgICAgICAgICAgICAgICByZXR1cm4geyByZWFkLCB3cml0ZSB9O1xuICAgICAgICAgICAgICAgIH0gY2F0Y2ggKGUpIHtcbiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHsgcmVhZDogW10sIHdyaXRlOiBbXSB9O1xuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgIH0pO1xuICAgICAgICAgICAgcmV0dXJuIHRydWU7XG5cbiAgICAgICAgLy8gLS0tIEFQSSBLZXkgVmF1bHQgaGFuZGxlcnMgLS0tXG4gICAgICAgIGNhc2UgJ2FwaWtleXMucHVibGlzaCc6XG4gICAgICAgICAgICByZXBseShzZW5kUmVzcG9uc2UsIGFzeW5jICgpID0+IHtcbiAgICAgICAgICAgICAgICB0cnkge1xuICAgICAgICAgICAgICAgICAgICBjb25zdCB7IGtleXMgfSA9IG1lc3NhZ2UucGF5bG9hZDtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgcHVia2V5ID0gYXdhaXQgZ2V0UHViS2V5KCk7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHBsYWluVGV4dCA9IEpTT04uc3RyaW5naWZ5KGtleXMpO1xuICAgICAgICAgICAgICAgICAgICBjb25zdCBlbmNyeXB0ZWQgPSBhd2FpdCBuaXA0NEVuY3J5cHQoeyBwdWJLZXk6IHB1YmtleSwgcGxhaW5UZXh0IH0pO1xuICAgICAgICAgICAgICAgICAgICBjb25zdCB1bnNpZ25lZCA9IGJ1aWxkVmF1bHRFdmVudCgndmF1bHQvYXBpLWtleXMnLCBlbmNyeXB0ZWQpO1xuXG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHBpID0gYXdhaXQgZ2V0UHJvZmlsZUluZGV4KCk7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHByb2ZpbGUgPSBhd2FpdCBnZXRQcm9maWxlKHBpKTtcbiAgICAgICAgICAgICAgICAgICAgbGV0IHNpZ25lZDtcbiAgICAgICAgICAgICAgICAgICAgaWYgKHByb2ZpbGUudHlwZSA9PT0gJ2J1bmtlcicpIHtcbiAgICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IHNlc3Npb24gPSBhd2FpdCBnZXRPckNyZWF0ZVNlc3Npb24ocGkpO1xuICAgICAgICAgICAgICAgICAgICAgICAgc2lnbmVkID0gYXdhaXQgc2Vzc2lvbi5zaWduRXZlbnQodW5zaWduZWQpO1xuICAgICAgICAgICAgICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgICAgICAgICAgICAgY29uc3Qgc2sgPSBhd2FpdCBnZXRQcml2S2V5KCk7XG4gICAgICAgICAgICAgICAgICAgICAgICBzaWduZWQgPSBhd2FpdCBmaW5hbGl6ZUV2ZW50KHVuc2lnbmVkLCBzayk7XG4gICAgICAgICAgICAgICAgICAgIH1cblxuICAgICAgICAgICAgICAgICAgICBhd2FpdCB3aXRoUmVsYXlzKCd3cml0ZScsIGFzeW5jIChyZWxheXMpID0+IHtcbiAgICAgICAgICAgICAgICAgICAgICAgIGZvciAoY29uc3QgcmVsYXkgb2YgcmVsYXlzKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgdHJ5IHsgcmVsYXkucHVibGlzaChzaWduZWQpOyB9IGNhdGNoIChfKSB7fVxuICAgICAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgICAgICB9KTtcbiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHsgc3VjY2VzczogdHJ1ZSwgZXZlbnRJZDogc2lnbmVkLmlkLCBjcmVhdGVkQXQ6IHNpZ25lZC5jcmVhdGVkX2F0IH07XG4gICAgICAgICAgICAgICAgfSBjYXRjaCAoZSkge1xuICAgICAgICAgICAgICAgICAgICByZXR1cm4geyBzdWNjZXNzOiBmYWxzZSwgZXJyb3I6IGUubWVzc2FnZSB9O1xuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgIH0pO1xuICAgICAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgICAgIGNhc2UgJ2FwaWtleXMuZmV0Y2gnOlxuICAgICAgICAgICAgcmVwbHkoc2VuZFJlc3BvbnNlLCBhc3luYyAoKSA9PiB7XG4gICAgICAgICAgICAgICAgdHJ5IHtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgcHVia2V5ID0gYXdhaXQgZ2V0UHViS2V5KCk7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IGZpbHRlciA9IHtcbiAgICAgICAgICAgICAgICAgICAgICAgIGtpbmRzOiBbMzAwNzhdLFxuICAgICAgICAgICAgICAgICAgICAgICAgYXV0aG9yczogW3B1YmtleV0sXG4gICAgICAgICAgICAgICAgICAgICAgICAnI2QnOiBbJ25vc3Rya2V5OnZhdWx0L2FwaS1rZXlzJ10sXG4gICAgICAgICAgICAgICAgICAgIH07XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IGFsbEV2ZW50cyA9IFtdO1xuXG4gICAgICAgICAgICAgICAgICAgIGF3YWl0IHdpdGhSZWxheXMoJ3JlYWQnLCBhc3luYyAocmVsYXlzKSA9PiB7XG4gICAgICAgICAgICAgICAgICAgICAgICBjb25zdCBwZXJSZWxheSA9IHJlbGF5cy5tYXAocmVsYXkgPT4gbmV3IFByb21pc2UoKHJlc29sdmUpID0+IHtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICBjb25zdCBzdWJJZCA9IGBhcGlrZXlzLSR7Y3J5cHRvLnJhbmRvbVVVSUQoKS5zbGljZSgwLCA4KX1gO1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IHRpbWVvdXQgPSBzZXRUaW1lb3V0KCgpID0+IHtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdHJ5IHsgcmVsYXkudW5zdWJzY3JpYmUoc3ViSWQpOyB9IGNhdGNoIChfKSB7fVxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICByZXNvbHZlKCk7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgfSwgMTUwMDApO1xuXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgcmVsYXkuc3Vic2NyaWJlKFxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzdWJJZCxcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgW2ZpbHRlcl0sXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIChldmVudCkgPT4geyBhbGxFdmVudHMucHVzaChldmVudCk7IH0sXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICgpID0+IHtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNsZWFyVGltZW91dCh0aW1lb3V0KTtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHRyeSB7IHJlbGF5LnVuc3Vic2NyaWJlKHN1YklkKTsgfSBjYXRjaCAoXykge31cbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJlc29sdmUoKTtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICk7XG4gICAgICAgICAgICAgICAgICAgICAgICB9KSk7XG4gICAgICAgICAgICAgICAgICAgICAgICBhd2FpdCBQcm9taXNlLmFsbChwZXJSZWxheSk7XG4gICAgICAgICAgICAgICAgICAgIH0pO1xuXG4gICAgICAgICAgICAgICAgICAgIC8vIFRha2UgbGF0ZXN0IGJ5IGNyZWF0ZWRfYXQgKHNpbmdsZSBkLXRhZywgTklQLTMzIGRlZHVwKVxuICAgICAgICAgICAgICAgICAgICBsZXQgbGF0ZXN0ID0gbnVsbDtcbiAgICAgICAgICAgICAgICAgICAgZm9yIChjb25zdCBldmVudCBvZiBhbGxFdmVudHMpIHtcbiAgICAgICAgICAgICAgICAgICAgICAgIGlmICghbGF0ZXN0IHx8IGV2ZW50LmNyZWF0ZWRfYXQgPiBsYXRlc3QuY3JlYXRlZF9hdCkge1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgIGxhdGVzdCA9IGV2ZW50O1xuICAgICAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgICAgICB9XG5cbiAgICAgICAgICAgICAgICAgICAgaWYgKCFsYXRlc3QpIHtcbiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiB7IHN1Y2Nlc3M6IHRydWUsIGtleXM6IG51bGwsIGV2ZW50SWQ6IG51bGwsIGNyZWF0ZWRBdDogbnVsbCB9O1xuICAgICAgICAgICAgICAgICAgICB9XG5cbiAgICAgICAgICAgICAgICAgICAgY29uc3QgZGVjcnlwdGVkID0gYXdhaXQgbmlwNDREZWNyeXB0KHsgcHViS2V5OiBwdWJrZXksIGNpcGhlclRleHQ6IGxhdGVzdC5jb250ZW50IH0pO1xuICAgICAgICAgICAgICAgICAgICBjb25zdCBrZXlzID0gSlNPTi5wYXJzZShkZWNyeXB0ZWQpO1xuICAgICAgICAgICAgICAgICAgICByZXR1cm4geyBzdWNjZXNzOiB0cnVlLCBrZXlzLCBldmVudElkOiBsYXRlc3QuaWQsIGNyZWF0ZWRBdDogbGF0ZXN0LmNyZWF0ZWRfYXQgfTtcbiAgICAgICAgICAgICAgICB9IGNhdGNoIChlKSB7XG4gICAgICAgICAgICAgICAgICAgIHJldHVybiB7IHN1Y2Nlc3M6IGZhbHNlLCBlcnJvcjogZS5tZXNzYWdlIH07XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfSk7XG4gICAgICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgICAgY2FzZSAnYXBpa2V5cy5kZWxldGUnOlxuICAgICAgICAgICAgcmVwbHkoc2VuZFJlc3BvbnNlLCBhc3luYyAoKSA9PiB7XG4gICAgICAgICAgICAgICAgdHJ5IHtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgeyBldmVudElkIH0gPSBtZXNzYWdlLnBheWxvYWQ7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHVuc2lnbmVkID0gYnVpbGRWYXVsdERlbGV0aW9uKGV2ZW50SWQsICd2YXVsdC9hcGkta2V5cycpO1xuXG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHBpID0gYXdhaXQgZ2V0UHJvZmlsZUluZGV4KCk7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHByb2ZpbGUgPSBhd2FpdCBnZXRQcm9maWxlKHBpKTtcbiAgICAgICAgICAgICAgICAgICAgbGV0IHNpZ25lZDtcbiAgICAgICAgICAgICAgICAgICAgaWYgKHByb2ZpbGUudHlwZSA9PT0gJ2J1bmtlcicpIHtcbiAgICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IHNlc3Npb24gPSBhd2FpdCBnZXRPckNyZWF0ZVNlc3Npb24ocGkpO1xuICAgICAgICAgICAgICAgICAgICAgICAgc2lnbmVkID0gYXdhaXQgc2Vzc2lvbi5zaWduRXZlbnQodW5zaWduZWQpO1xuICAgICAgICAgICAgICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgICAgICAgICAgICAgY29uc3Qgc2sgPSBhd2FpdCBnZXRQcml2S2V5KCk7XG4gICAgICAgICAgICAgICAgICAgICAgICBzaWduZWQgPSBhd2FpdCBmaW5hbGl6ZUV2ZW50KHVuc2lnbmVkLCBzayk7XG4gICAgICAgICAgICAgICAgICAgIH1cblxuICAgICAgICAgICAgICAgICAgICBhd2FpdCB3aXRoUmVsYXlzKCd3cml0ZScsIGFzeW5jIChyZWxheXMpID0+IHtcbiAgICAgICAgICAgICAgICAgICAgICAgIGZvciAoY29uc3QgcmVsYXkgb2YgcmVsYXlzKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgdHJ5IHsgcmVsYXkucHVibGlzaChzaWduZWQpOyB9IGNhdGNoIChfKSB7fVxuICAgICAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgICAgICB9KTtcbiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHsgc3VjY2VzczogdHJ1ZSB9O1xuICAgICAgICAgICAgICAgIH0gY2F0Y2ggKGUpIHtcbiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHsgc3VjY2VzczogZmFsc2UsIGVycm9yOiBlLm1lc3NhZ2UgfTtcbiAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICB9KTtcbiAgICAgICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgICBjYXNlICdhcGlrZXlzLmVuY3J5cHQnOlxuICAgICAgICAgICAgcmVwbHkoc2VuZFJlc3BvbnNlLCBhc3luYyAoKSA9PiB7XG4gICAgICAgICAgICAgICAgdHJ5IHtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgeyBwbGFpblRleHQgfSA9IG1lc3NhZ2UucGF5bG9hZDtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgcHVia2V5ID0gYXdhaXQgZ2V0UHViS2V5KCk7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IGNpcGhlclRleHQgPSBhd2FpdCBuaXA0NEVuY3J5cHQoeyBwdWJLZXk6IHB1YmtleSwgcGxhaW5UZXh0IH0pO1xuICAgICAgICAgICAgICAgICAgICByZXR1cm4geyBzdWNjZXNzOiB0cnVlLCBjaXBoZXJUZXh0IH07XG4gICAgICAgICAgICAgICAgfSBjYXRjaCAoZSkge1xuICAgICAgICAgICAgICAgICAgICByZXR1cm4geyBzdWNjZXNzOiBmYWxzZSwgZXJyb3I6IGUubWVzc2FnZSB9O1xuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgIH0pO1xuICAgICAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgICAgIGNhc2UgJ2FwaWtleXMuZGVjcnlwdCc6XG4gICAgICAgICAgICByZXBseShzZW5kUmVzcG9uc2UsIGFzeW5jICgpID0+IHtcbiAgICAgICAgICAgICAgICB0cnkge1xuICAgICAgICAgICAgICAgICAgICBjb25zdCB7IGNpcGhlclRleHQgfSA9IG1lc3NhZ2UucGF5bG9hZDtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgcHVia2V5ID0gYXdhaXQgZ2V0UHViS2V5KCk7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHBsYWluVGV4dCA9IGF3YWl0IG5pcDQ0RGVjcnlwdCh7IHB1YktleTogcHVia2V5LCBjaXBoZXJUZXh0IH0pO1xuICAgICAgICAgICAgICAgICAgICByZXR1cm4geyBzdWNjZXNzOiB0cnVlLCBwbGFpblRleHQgfTtcbiAgICAgICAgICAgICAgICB9IGNhdGNoIChlKSB7XG4gICAgICAgICAgICAgICAgICAgIHJldHVybiB7IHN1Y2Nlc3M6IGZhbHNlLCBlcnJvcjogZS5tZXNzYWdlIH07XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfSk7XG4gICAgICAgICAgICByZXR1cm4gdHJ1ZTtcblxuICAgICAgICAvLyAtLS0gRW5jcnlwdGVkIHZhdWx0IGJhY2t1cCAvIHJlc3RvcmUgLS0tXG4gICAgICAgIGNhc2UgJ2JhY2t1cC5leHBvcnQnOlxuICAgICAgICAgICAgcmVwbHkoc2VuZFJlc3BvbnNlLCBhc3luYyAoKSA9PiB7XG4gICAgICAgICAgICAgICAgLy8gQmFja3VwcyBhcmUgZW5jcnlwdGVkIHdpdGggYSBkZWRpY2F0ZWQgYmFja3VwIHBhc3N3b3JkIHN1cHBsaWVkIGF0XG4gICAgICAgICAgICAgICAgLy8gZXhwb3J0IHRpbWUgXHUyMDE0IE5PVCB0aGUgaW4tbWVtb3J5IHNlc3Npb24ga2V5LiBUaGlzIGxldHMgdXNlcnMgd2l0aCBub1xuICAgICAgICAgICAgICAgIC8vIG1hc3RlciBwYXNzd29yZCBjcmVhdGUgYmFja3VwcywgYW5kIHdvcmtzIGV2ZW4gd2hpbGUgbG9ja2VkICh0aGVcbiAgICAgICAgICAgICAgICAvLyBzdG9yZWQga2V5IGJsb2JzIHN0YXkgZW5jcnlwdGVkIGFuZCBnZXQgd3JhcHBlZCBhZ2FpbiBoZXJlKS5cbiAgICAgICAgICAgICAgICBjb25zdCBwYXNzd29yZCA9IG1lc3NhZ2UucGF5bG9hZD8ucGFzc3dvcmQ7XG4gICAgICAgICAgICAgICAgaWYgKHR5cGVvZiBwYXNzd29yZCAhPT0gJ3N0cmluZycgfHwgcGFzc3dvcmQubGVuZ3RoIDwgOCkge1xuICAgICAgICAgICAgICAgICAgICByZXR1cm4geyBzdWNjZXNzOiBmYWxzZSwgZXJyb3I6ICdBIGJhY2t1cCBwYXNzd29yZCBvZiBhdCBsZWFzdCA4IGNoYXJhY3RlcnMgaXMgcmVxdWlyZWQnIH07XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgIGNvbnN0IGRhdGEgPSBhd2FpdCBzdG9yYWdlLmdldCh7XG4gICAgICAgICAgICAgICAgICAgIHByb2ZpbGVzOiBbXSxcbiAgICAgICAgICAgICAgICAgICAgcHJvZmlsZUluZGV4OiAwLFxuICAgICAgICAgICAgICAgICAgICBpc0VuY3J5cHRlZDogZmFsc2UsXG4gICAgICAgICAgICAgICAgICAgIHBhc3N3b3JkSGFzaDogbnVsbCxcbiAgICAgICAgICAgICAgICAgICAgcGFzc3dvcmRTYWx0OiBudWxsLFxuICAgICAgICAgICAgICAgICAgICBhcGlLZXlWYXVsdDogbnVsbCxcbiAgICAgICAgICAgICAgICAgICAgdmF1bHREb2NzOiBudWxsLFxuICAgICAgICAgICAgICAgICAgICBub3N0ckFjY2Vzc1doaWxlTG9ja2VkOiBmYWxzZSxcbiAgICAgICAgICAgICAgICAgICAgYmxvY2tDcm9zc09yaWdpbkZyYW1lczogdHJ1ZSxcbiAgICAgICAgICAgICAgICAgICAgYXV0b0xvY2tNaW51dGVzOiAxNSxcbiAgICAgICAgICAgICAgICAgICAgdmVyc2lvbjogbnVsbCxcbiAgICAgICAgICAgICAgICB9KTtcbiAgICAgICAgICAgICAgICBjb25zdCBwbGFpbnRleHQgPSBKU09OLnN0cmluZ2lmeShkYXRhKTtcbiAgICAgICAgICAgICAgICBjb25zdCBlbmNyeXB0ZWQgPSBhd2FpdCBlbmNyeXB0QmxvYihwbGFpbnRleHQsIHBhc3N3b3JkKTtcbiAgICAgICAgICAgICAgICBjb25zdCB2ZXJzaW9uID0gYXBpLnJ1bnRpbWUuZ2V0TWFuaWZlc3Q/LigpPy52ZXJzaW9uIHx8ICd1bmtub3duJztcbiAgICAgICAgICAgICAgICByZXR1cm4ge1xuICAgICAgICAgICAgICAgICAgICBzdWNjZXNzOiB0cnVlLFxuICAgICAgICAgICAgICAgICAgICBlbnZlbG9wZToge1xuICAgICAgICAgICAgICAgICAgICAgICAgZm9ybWF0OiAnbm9zdHJrZXktYmFja3VwJyxcbiAgICAgICAgICAgICAgICAgICAgICAgIHZlcnNpb246IDEsXG4gICAgICAgICAgICAgICAgICAgICAgICBjcmVhdGVkQXQ6IG5ldyBEYXRlKCkudG9JU09TdHJpbmcoKSxcbiAgICAgICAgICAgICAgICAgICAgICAgIGV4dGVuc2lvblZlcnNpb246IHZlcnNpb24sXG4gICAgICAgICAgICAgICAgICAgICAgICBwcm9maWxlQ291bnQ6IEFycmF5LmlzQXJyYXkoZGF0YS5wcm9maWxlcykgPyBkYXRhLnByb2ZpbGVzLmxlbmd0aCA6IDAsXG4gICAgICAgICAgICAgICAgICAgICAgICBwYXlsb2FkOiBKU09OLnBhcnNlKGVuY3J5cHRlZCksXG4gICAgICAgICAgICAgICAgICAgIH0sXG4gICAgICAgICAgICAgICAgfTtcbiAgICAgICAgICAgIH0pO1xuICAgICAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgICAgIGNhc2UgJ2JhY2t1cC5pbXBvcnQnOlxuICAgICAgICAgICAgcmVwbHkoc2VuZFJlc3BvbnNlLCBhc3luYyAoKSA9PiB7XG4gICAgICAgICAgICAgICAgdHJ5IHtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgeyBlbnZlbG9wZSwgcGFzc3dvcmQgfSA9IG1lc3NhZ2UucGF5bG9hZDtcbiAgICAgICAgICAgICAgICAgICAgaWYgKCFlbnZlbG9wZSB8fCBlbnZlbG9wZS5mb3JtYXQgIT09ICdub3N0cmtleS1iYWNrdXAnKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICByZXR1cm4geyBzdWNjZXNzOiBmYWxzZSwgZXJyb3I6ICdOb3QgYSB2YWxpZCBOb3N0cktleSBiYWNrdXAgZmlsZScgfTtcbiAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgICAgICBpZiAodHlwZW9mIGVudmVsb3BlLnZlcnNpb24gIT09ICdudW1iZXInIHx8IGVudmVsb3BlLnZlcnNpb24gPiAxKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICByZXR1cm4geyBzdWNjZXNzOiBmYWxzZSwgZXJyb3I6ICdCYWNrdXAgdmVyc2lvbiBub3Qgc3VwcG9ydGVkLiBVcGRhdGUgTm9zdHJLZXkgYW5kIHRyeSBhZ2Fpbi4nIH07XG4gICAgICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICAgICAgY29uc3QgcGF5bG9hZFN0ciA9IEpTT04uc3RyaW5naWZ5KGVudmVsb3BlLnBheWxvYWQpO1xuICAgICAgICAgICAgICAgICAgICBsZXQgcGxhaW50ZXh0O1xuICAgICAgICAgICAgICAgICAgICB0cnkge1xuICAgICAgICAgICAgICAgICAgICAgICAgcGxhaW50ZXh0ID0gYXdhaXQgZGVjcnlwdEJsb2IocGF5bG9hZFN0ciwgcGFzc3dvcmQpO1xuICAgICAgICAgICAgICAgICAgICB9IGNhdGNoIChfKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICByZXR1cm4geyBzdWNjZXNzOiBmYWxzZSwgZXJyb3I6ICdXcm9uZyBwYXNzd29yZCBcdTIwMTQgY291bGQgbm90IGRlY3J5cHQgYmFja3VwJyB9O1xuICAgICAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IGRhdGEgPSBKU09OLnBhcnNlKHBsYWludGV4dCk7XG4gICAgICAgICAgICAgICAgICAgIC8vIFdyaXRlIGFsbCBiYWNrZWQtdXAga2V5cyB0byBzdG9yYWdlXG4gICAgICAgICAgICAgICAgICAgIGF3YWl0IHN0b3JhZ2Uuc2V0KGRhdGEpO1xuICAgICAgICAgICAgICAgICAgICAvLyBVcGRhdGUgaW4tbWVtb3J5IHN0YXRlXG4gICAgICAgICAgICAgICAgICAgIGVuY3J5cHRpb25FbmFibGVkID0gISFkYXRhLmlzRW5jcnlwdGVkO1xuICAgICAgICAgICAgICAgICAgICBsb2NrZWQgPSBmYWxzZTtcbiAgICAgICAgICAgICAgICAgICAgLy8gRGVyaXZlIHNlc3Npb24ga2V5IGZyb20gcGFzc3dvcmQsIHRoZW4gbGV0IHBhc3N3b3JkIGZhbGwgb3V0IG9mIHNjb3BlXG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IGltcG9ydFNhbHQgPSBjcnlwdG8uZ2V0UmFuZG9tVmFsdWVzKG5ldyBVaW50OEFycmF5KDE2KSk7XG4gICAgICAgICAgICAgICAgICAgIHNlc3Npb25DcnlwdG9LZXkgPSBhd2FpdCBkZXJpdmVLZXkocGFzc3dvcmQsIGltcG9ydFNhbHQpO1xuICAgICAgICAgICAgICAgICAgICBzZXNzaW9uS2V5U2FsdCA9IGltcG9ydFNhbHQ7XG4gICAgICAgICAgICAgICAgICAgIG5vc3RyQWNjZXNzV2hpbGVMb2NrZWQgPSBkYXRhLm5vc3RyQWNjZXNzV2hpbGVMb2NrZWQgIT09IGZhbHNlO1xuICAgICAgICAgICAgICAgICAgICBibG9ja0Nyb3NzT3JpZ2luRnJhbWVzID0gZGF0YS5ibG9ja0Nyb3NzT3JpZ2luRnJhbWVzICE9PSBmYWxzZTtcbiAgICAgICAgICAgICAgICAgICAgaWYgKHR5cGVvZiBkYXRhLmF1dG9Mb2NrTWludXRlcyA9PT0gJ251bWJlcicpIHtcbiAgICAgICAgICAgICAgICAgICAgICAgIGF1dG9Mb2NrVGltZW91dCA9IGRhdGEuYXV0b0xvY2tNaW51dGVzICogNjAgKiAxMDAwO1xuICAgICAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgICAgIC8vIFBvcHVsYXRlIHNlc3Npb24ga2V5IGNhY2hlXG4gICAgICAgICAgICAgICAgICAgIHNlc3Npb25LZXlzLmNsZWFyKCk7XG4gICAgICAgICAgICAgICAgICAgIGlmIChBcnJheS5pc0FycmF5KGRhdGEucHJvZmlsZXMpKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICBmb3IgKGxldCBpID0gMDsgaSA8IGRhdGEucHJvZmlsZXMubGVuZ3RoOyBpKyspIHtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICBjb25zdCBwID0gZGF0YS5wcm9maWxlc1tpXTtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICBpZiAocC50eXBlID09PSAnYnVua2VyJyB8fCAhcC5wcml2S2V5KSBjb250aW51ZTtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICBpZiAoaXNFbmNyeXB0ZWRCbG9iKHAucHJpdktleSkpIHtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdHJ5IHtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IGhleCA9IGF3YWl0IGRlY3J5cHRCbG9iKHAucHJpdktleSwgcGFzc3dvcmQpO1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2Vzc2lvbktleXMuc2V0KGksIGhleCk7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0gY2F0Y2ggKF8pIHt9XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2Vzc2lvbktleXMuc2V0KGksIHAucHJpdktleSk7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgICAgIHJlc2V0QXV0b0xvY2soKTtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgcHJvZmlsZUNvdW50ID0gQXJyYXkuaXNBcnJheShkYXRhLnByb2ZpbGVzKSA/IGRhdGEucHJvZmlsZXMubGVuZ3RoIDogMDtcbiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHsgc3VjY2VzczogdHJ1ZSwgcHJvZmlsZUNvdW50IH07XG4gICAgICAgICAgICAgICAgfSBjYXRjaCAoZSkge1xuICAgICAgICAgICAgICAgICAgICByZXR1cm4geyBzdWNjZXNzOiBmYWxzZSwgZXJyb3I6IGUubWVzc2FnZSB8fCAnUmVzdG9yZSBmYWlsZWQnIH07XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfSk7XG4gICAgICAgICAgICByZXR1cm4gdHJ1ZTtcblxuICAgICAgICAvLyBub3N0cjogcHJvdG9jb2wgVVJMIGhhbmRsZXIgXHUyMDE0IG5vIGtleSBhY2Nlc3MgbmVlZGVkLCBubyBwZXJtaXNzaW9uIHByb21wdFxuICAgICAgICBjYXNlICdyZXBsYWNlVVJMJzpcbiAgICAgICAgICAgIHJlcGx5KHNlbmRSZXNwb25zZSwgYXN5bmMgKCkgPT4ge1xuICAgICAgICAgICAgICAgIGNvbnN0IHsgcHJvdG9jb2xfaGFuZGxlciB9ID0gYXdhaXQgc3RvcmFnZS5nZXQoWydwcm90b2NvbF9oYW5kbGVyJ10pO1xuICAgICAgICAgICAgICAgIGlmICghcHJvdG9jb2xfaGFuZGxlcikgcmV0dXJuIGZhbHNlO1xuICAgICAgICAgICAgICAgIGNvbnN0IHsgdXJsIH0gPSBtZXNzYWdlLnBheWxvYWQ7XG4gICAgICAgICAgICAgICAgY29uc3QgcmF3ID0gdXJsLnNwbGl0KCdub3N0cjonKVsxXTtcbiAgICAgICAgICAgICAgICBpZiAoIXJhdykgcmV0dXJuIGZhbHNlO1xuICAgICAgICAgICAgICAgIHRyeSB7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IGRlY29kZWQgPSBuaXAxOS5kZWNvZGUocmF3KTtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgeyB0eXBlLCBkYXRhIH0gPSBkZWNvZGVkO1xuICAgICAgICAgICAgICAgICAgICBjb25zdCByZXBsYWNlbWVudHMgPSB7XG4gICAgICAgICAgICAgICAgICAgICAgICByYXcsXG4gICAgICAgICAgICAgICAgICAgICAgICBocnA6IHR5cGUsXG4gICAgICAgICAgICAgICAgICAgICAgICBoZXg6XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgdHlwZSA9PT0gJ25hZGRyJ1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICA/IChkZWNvZGVkLmF1dGhvciB8fCByYXcpXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIDogKGRhdGEgfHwgcmF3KSxcbiAgICAgICAgICAgICAgICAgICAgICAgIHBfb3JfZTogeyBucHViOiAncCcsIG5vdGU6ICdlJywgbnByb2ZpbGU6ICdwJywgbmV2ZW50OiAnZScsIG5hZGRyOiAnYScgfVt0eXBlXSB8fCAnJyxcbiAgICAgICAgICAgICAgICAgICAgICAgIHVfb3JfbjogeyBucHViOiAndScsIG5vdGU6ICduJywgbnByb2ZpbGU6ICd1JywgbmV2ZW50OiAnbicsIG5hZGRyOiAnbicgfVt0eXBlXSB8fCAnJyxcbiAgICAgICAgICAgICAgICAgICAgICAgIHJlbGF5MDogZGVjb2RlZC5yZWxheXM/LlswXSB8fCAnJyxcbiAgICAgICAgICAgICAgICAgICAgICAgIHJlbGF5MTogZGVjb2RlZC5yZWxheXM/LlsxXSB8fCAnJyxcbiAgICAgICAgICAgICAgICAgICAgICAgIHJlbGF5MjogZGVjb2RlZC5yZWxheXM/LlsyXSB8fCAnJyxcbiAgICAgICAgICAgICAgICAgICAgfTtcbiAgICAgICAgICAgICAgICAgICAgbGV0IHJlc3VsdCA9IHByb3RvY29sX2hhbmRsZXI7XG4gICAgICAgICAgICAgICAgICAgIGZvciAoY29uc3QgW3BhdHRlcm4sIHZhbHVlXSBvZiBPYmplY3QuZW50cmllcyhyZXBsYWNlbWVudHMpKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICByZXN1bHQgPSByZXN1bHQucmVwbGFjZShuZXcgUmVnRXhwKGBcXFxceyAqJHtwYXR0ZXJufSAqXFxcXH1gLCAnZycpLCB2YWx1ZSk7XG4gICAgICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHJlc3VsdDtcbiAgICAgICAgICAgICAgICB9IGNhdGNoIHtcbiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGZhbHNlO1xuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgIH0pO1xuICAgICAgICAgICAgcmV0dXJuIHRydWU7XG5cbiAgICAgICAgLy8gd2luZG93Lm5vc3RyXG4gICAgICAgIGNhc2UgJ2dldFB1YktleSc6XG4gICAgICAgIGNhc2UgJ3NpZ25FdmVudCc6XG4gICAgICAgIGNhc2UgJ25pcDA0LmVuY3J5cHQnOlxuICAgICAgICBjYXNlICduaXAwNC5kZWNyeXB0JzpcbiAgICAgICAgY2FzZSAnbmlwNDQuZW5jcnlwdCc6XG4gICAgICAgIGNhc2UgJ25pcDQ0LmRlY3J5cHQnOlxuICAgICAgICBjYXNlICdnZXRSZWxheXMnOlxuICAgICAgICBjYXNlICdhZGRSZWxheSc6XG4gICAgICAgIGNhc2UgJ2V4cG9ydFByb2ZpbGUnOlxuICAgICAgICAgICAgdmFsaWRhdGlvbnNbdXVpZF0gPSBzZW5kUmVzcG9uc2U7XG4gICAgICAgICAgICBpZiAoT2JqZWN0LmtleXModmFsaWRhdGlvbnMpLmxlbmd0aCA9PT0gMSkge1xuICAgICAgICAgICAgICAgIHBlbmRpbmdRdWV1ZSA9IHsgdG90YWw6IDAsIHByb2Nlc3NlZDogMCB9O1xuICAgICAgICAgICAgfVxuICAgICAgICAgICAgcGVuZGluZ1F1ZXVlLnRvdGFsKys7XG4gICAgICAgICAgICBhc2sodXVpZCwgbWVzc2FnZSk7XG4gICAgICAgICAgICBzZXRUaW1lb3V0KCgpID0+IHtcbiAgICAgICAgICAgICAgICAvLyBINCBmaXg6IGRlbnkgcGVuZGluZyByZXF1ZXN0IG9uIHRpbWVvdXQgaW5zdGVhZCBvZiBzaWxlbnRseSByZWxlYXNpbmdcbiAgICAgICAgICAgICAgICBpZiAodmFsaWRhdGlvbnNbdXVpZF0pIHtcbiAgICAgICAgICAgICAgICAgICAgZGVueSh7IHBheWxvYWQ6IHV1aWQsIG9yaWdLaW5kOiBtZXNzYWdlLmtpbmQsIGhvc3Q6IG1lc3NhZ2UuaG9zdCB9KTtcbiAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgcHJvbXB0LnJlbGVhc2U/LigpO1xuICAgICAgICAgICAgfSwgMTBfMDAwKTtcbiAgICAgICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgICBkZWZhdWx0OlxuICAgICAgICAgICAgcmV0dXJuIGZhbHNlO1xuICAgIH1cbn0pO1xuXG5hc3luYyBmdW5jdGlvbiBmb3JjZVJlbGVhc2UoKSB7XG4gICAgaWYgKHByb21wdC50YWJJZCAhPT0gbnVsbCkge1xuICAgICAgICB0cnkge1xuICAgICAgICAgICAgLy8gSWYgdGhlIHByZXZpb3VzIHByb21wdCBpcyBzdGlsbCBvcGVuLCB0aGVuIHRoaXMgd29uJ3QgZG8gYW55dGhpbmcuXG4gICAgICAgICAgICAvLyBJZiBpdCdzIG5vdCBvcGVuLCBpdCB3aWxsIHRocm93IGFuIGVycm9yIGFuZCBnZXQgY2F1Z2h0LlxuICAgICAgICAgICAgYXdhaXQgYXBpLnRhYnMuZ2V0KHByb21wdC50YWJJZCk7XG4gICAgICAgIH0gY2F0Y2ggKGVycm9yKSB7XG4gICAgICAgICAgICAvLyBJZiB0aGUgdGFiIGlzIGNsb3NlZCwgYnV0IHNvbWVob3cgZXNjYXBlZCBvdXIgZXZlbnQgaGFuZGxpbmcsIHdlIGNhbiBjbGVhbiBpdCB1cCBoZXJlXG4gICAgICAgICAgICAvLyBiZWZvcmUgYXR0ZW1wdGluZyB0byBvcGVuIHRoZSBuZXh0IHRhYi5cbiAgICAgICAgICAgIHByb21wdC5yZWxlYXNlPy4oKTtcbiAgICAgICAgICAgIHByb21wdC50YWJJZCA9IG51bGw7XG4gICAgICAgIH1cbiAgICB9XG59XG5cbmFzeW5jIGZ1bmN0aW9uIGdlbmVyYXRlUHJpdmF0ZUtleV8oKSB7XG4gICAgY29uc3Qga2V5UGFpciA9IGF3YWl0IGdlbmVyYXRlS2V5UGFpcigpO1xuICAgIHJldHVybiBrZXlQYWlyLnByaXZhdGVLZXk7XG59XG5cbmFzeW5jIGZ1bmN0aW9uIGFzayh1dWlkLCB7IGtpbmQsIGhvc3QsIHBheWxvYWQgfSkge1xuICAgIC8vIFJhdGUgbGltaXQgcGVybWlzc2lvbiByZXF1ZXN0cyBwZXIgb3JpZ2luIFx1MjAxNCBwcmV2ZW50IHNwYW0gZnJvbSBtYWxpY2lvdXMgcGFnZXNcbiAgICBpZiAoaG9zdCkge1xuICAgICAgICBjb25zdCBub3cgPSBEYXRlLm5vdygpO1xuICAgICAgICBjb25zdCByYXRlRW50cnkgPSBwZXJtaXNzaW9uUmF0ZU1hcC5nZXQoaG9zdCkgfHwgeyBjb3VudDogMCwgcmVzZXRBdDogbm93ICsgNjAwMDAgfTtcbiAgICAgICAgaWYgKG5vdyA+IHJhdGVFbnRyeS5yZXNldEF0KSB7XG4gICAgICAgICAgICByYXRlRW50cnkuY291bnQgPSAwO1xuICAgICAgICAgICAgcmF0ZUVudHJ5LnJlc2V0QXQgPSBub3cgKyA2MDAwMDtcbiAgICAgICAgfVxuICAgICAgICByYXRlRW50cnkuY291bnQrKztcbiAgICAgICAgcGVybWlzc2lvblJhdGVNYXAuc2V0KGhvc3QsIHJhdGVFbnRyeSk7XG5cbiAgICAgICAgaWYgKHJhdGVFbnRyeS5jb3VudCA+IDUpIHtcbiAgICAgICAgICAgIGxvZyhgW1NFQ1VSSVRZXSBSYXRlIGxpbWl0ZWQgJHtob3N0fSBcdTIwMTQgJHtyYXRlRW50cnkuY291bnR9IHJlcXVlc3RzIGluIDYwc2ApO1xuICAgICAgICAgICAgY29uc3Qgc2VuZFJlc3BvbnNlID0gdmFsaWRhdGlvbnNbdXVpZF07XG4gICAgICAgICAgICBkZWxldGUgdmFsaWRhdGlvbnNbdXVpZF07XG4gICAgICAgICAgICBzZW5kUmVzcG9uc2U/Lih7IGVycm9yOiAncmF0ZV9saW1pdGVkJywgbWVzc2FnZTogJ1RvbyBtYW55IHJlcXVlc3RzLiBQbGVhc2Ugd2FpdCBhIG1vbWVudC4nIH0pO1xuICAgICAgICAgICAgcmV0dXJuO1xuICAgICAgICB9XG4gICAgfVxuXG4gICAgLy8gQnVua2VyIHByb2ZpbGVzIGRvbid0IG5lZWQgbG9jYWwga2V5IGRlY3J5cHRpb24gXHUyMDE0IHNraXAgbG9jayBjaGVja1xuICAgIGNvbnN0IHBpID0gYXdhaXQgZ2V0UHJvZmlsZUluZGV4KCk7XG4gICAgY29uc3QgcHJvZmlsZSA9IGF3YWl0IGdldFByb2ZpbGUocGkpO1xuICAgIGNvbnN0IGlzQnVua2VyID0gcHJvZmlsZT8udHlwZSA9PT0gJ2J1bmtlcic7XG5cbiAgICAvLyBSZWFkLW9ubHkgb3BlcmF0aW9ucyAoZ2V0UHViS2V5LCBnZXRSZWxheXMpIHdvcmsgZnJvbSBjYWNoZWQgZGF0YSBhbmRcbiAgICAvLyBkb24ndCBuZWVkIHRoZSBwcml2YXRlIGtleSwgc28gdGhleSBieXBhc3MgdGhlIGxvY2sgY2hlY2sgZW50aXJlbHkuXG4gICAgLy8gVGhpcyBhbHNvIGZpeGVzIFNhZmFyaSdzIG5vbi1wZXJzaXN0ZW50IGJhY2tncm91bmQgcGFnZSBsb3Npbmcgc2Vzc2lvblxuICAgIC8vIGtleXMgb24gcmVsb2FkIFx1MjAxNCB0aGVzZSBvcGVyYXRpb25zIHN0aWxsIHdvcmsgd2l0aG91dCByZS11bmxvY2tpbmcuXG4gICAgY29uc3QgbmVlZHNQcml2YXRlS2V5ID0ga2luZCAhPT0gJ2dldFB1YktleScgJiYga2luZCAhPT0gJ2dldFJlbGF5cycgJiYga2luZCAhPT0gJ2FkZFJlbGF5JyAmJiBraW5kICE9PSAnZXhwb3J0UHJvZmlsZSc7XG5cbiAgICAvLyBJZiB0aGUgZXh0ZW5zaW9uIGlzIGxvY2tlZCwgcmVqZWN0IHNpZ25pbmcvZW5jcnlwdGlvbiByZXF1ZXN0cyAobG9jYWwgcHJvZmlsZXMgb25seSlcbiAgICBpZiAoIWlzQnVua2VyICYmIG5lZWRzUHJpdmF0ZUtleSkge1xuICAgICAgICBjb25zdCBpc0xvY2tlZCA9IGF3YWl0IGNoZWNrTG9ja1N0YXRlKCk7XG4gICAgICAgIGlmIChpc0xvY2tlZCkge1xuICAgICAgICAgICAgaWYgKCEobm9zdHJBY2Nlc3NXaGlsZUxvY2tlZCAmJiBzZXNzaW9uS2V5cy5oYXMocGkpKSkge1xuICAgICAgICAgICAgICAgIC8vIE5vIGtleXMgYXZhaWxhYmxlIFx1MjAxNCBzaG93IGxvY2tlZCBub3RpZmljYXRpb24gYW5kIHJlamVjdFxuICAgICAgICAgICAgICAgIGNvbnN0IGlzRmlyc3RVbmxvY2sgPSBzZXNzaW9uS2V5cy5zaXplID09PSAwO1xuICAgICAgICAgICAgICAgIHRyeSB7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IFthY3RpdmVUYWJdID0gYXdhaXQgYXBpLnRhYnMucXVlcnkoeyBhY3RpdmU6IHRydWUsIGN1cnJlbnRXaW5kb3c6IHRydWUgfSk7XG4gICAgICAgICAgICAgICAgICAgIGlmIChhY3RpdmVUYWI/LmlkKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICBhcGkudGFicy5zZW5kTWVzc2FnZShhY3RpdmVUYWIuaWQsIHsga2luZDogJ3Nob3dMb2NrZWRTaGVldCcsIGZpcnN0VW5sb2NrOiBpc0ZpcnN0VW5sb2NrIH0pLmNhdGNoKCgpID0+IHt9KTtcbiAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgIH0gY2F0Y2ggKF8pIHt9XG4gICAgICAgICAgICAgICAgY29uc3Qgc2VuZFJlc3BvbnNlID0gdmFsaWRhdGlvbnNbdXVpZF07XG4gICAgICAgICAgICAgICAgZGVsZXRlIHZhbGlkYXRpb25zW3V1aWRdO1xuICAgICAgICAgICAgICAgIHNlbmRSZXNwb25zZT8uKHsgZXJyb3I6ICdsb2NrZWQnLCBtZXNzYWdlOiAnRXh0ZW5zaW9uIGlzIGxvY2tlZC4gUGxlYXNlIHVubG9jayB3aXRoIHlvdXIgbWFzdGVyIHBhc3N3b3JkLicgfSk7XG4gICAgICAgICAgICAgICAgcmV0dXJuO1xuICAgICAgICAgICAgfVxuICAgICAgICAgICAgLy8gS2V5cyBhdmFpbGFibGUgZGVzcGl0ZSBsb2NrIFx1MjAxNCBwcm9jZWVkIHdpdGggcGVybWlzc2lvbiBjaGVja1xuICAgICAgICB9XG4gICAgfVxuXG4gICAgLy8gUmF0ZSBsaW1pdCBwZXJtaXNzaW9uIHByb21wdHMgcGVyIGhvc3RcbiAgICBpZiAoaXNSYXRlTGltaXRlZChob3N0KSkge1xuICAgICAgICBjb25zdCBzZW5kUmVzcG9uc2UgPSB2YWxpZGF0aW9uc1t1dWlkXTtcbiAgICAgICAgZGVsZXRlIHZhbGlkYXRpb25zW3V1aWRdO1xuICAgICAgICBzZW5kUmVzcG9uc2U/Lih7IGVycm9yOiAncmF0ZV9saW1pdGVkJywgbWVzc2FnZTogJ1RvbyBtYW55IHJlcXVlc3RzLiBQbGVhc2Ugd2FpdC4nIH0pO1xuICAgICAgICBsb2coYFJhdGUgbGltaXRlZDogJHtob3N0fWApO1xuICAgICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgYXdhaXQgZm9yY2VSZWxlYXNlKCk7IC8vIENsZWFuIHVwIHByZXZpb3VzIHRhYiBpZiBpdCBjbG9zZWQgd2l0aG91dCBjbGVhbmluZyBpdHNlbGYgdXBcbiAgICBwcm9tcHQucmVsZWFzZSA9IGF3YWl0IHByb21wdC5tdXRleC5hY3F1aXJlKCk7XG5cbiAgICBwZW5kaW5nUXVldWUucHJvY2Vzc2VkKys7XG4gICAgY29uc3QgcXVldWVQb3NpdGlvbiA9IHBlbmRpbmdRdWV1ZS5wcm9jZXNzZWQ7XG4gICAgY29uc3QgcXVldWVUb3RhbCA9IHBlbmRpbmdRdWV1ZS50b3RhbDtcblxuICAgIGxldCBtS2luZCA9IGtpbmQgPT09ICdzaWduRXZlbnQnID8gYHNpZ25FdmVudDoke3BheWxvYWQua2luZH1gIDoga2luZDtcbiAgICBsZXQgcGVybWlzc2lvbiA9IGF3YWl0IGdldFBlcm1pc3Npb24oaG9zdCwgbUtpbmQpO1xuICAgIGlmIChwZXJtaXNzaW9uID09PSAnYWxsb3cnKSB7XG4gICAgICAgIGNvbXBsZXRlKHtcbiAgICAgICAgICAgIHBheWxvYWQ6IHV1aWQsXG4gICAgICAgICAgICBvcmlnS2luZDoga2luZCxcbiAgICAgICAgICAgIGV2ZW50OiBwYXlsb2FkLFxuICAgICAgICAgICAgcmVtZW1iZXI6IGZhbHNlLFxuICAgICAgICAgICAgaG9zdCxcbiAgICAgICAgfSk7XG4gICAgICAgIHByb21wdC5yZWxlYXNlKCk7XG4gICAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICBpZiAocGVybWlzc2lvbiA9PT0gJ2RlbnknKSB7XG4gICAgICAgIGRlbnkoeyBwYXlsb2FkOiB1dWlkLCBvcmlnS2luZDoga2luZCwgaG9zdCB9KTtcbiAgICAgICAgcHJvbXB0LnJlbGVhc2UoKTtcbiAgICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIC8vIFRyeSB0byBzaG93IGJvdHRvbSBzaGVldCBpbiB0aGUgYWN0aXZlIHRhYidzIGNvbnRlbnQgc2NyaXB0XG4gICAgdHJ5IHtcbiAgICAgICAgY29uc3QgW2FjdGl2ZVRhYl0gPSBhd2FpdCBhcGkudGFicy5xdWVyeSh7IGFjdGl2ZTogdHJ1ZSwgY3VycmVudFdpbmRvdzogdHJ1ZSB9KTtcbiAgICAgICAgaWYgKGFjdGl2ZVRhYj8uaWQpIHtcbiAgICAgICAgICAgIGNvbnN0IHJlc3VsdCA9IGF3YWl0IGFwaS50YWJzLnNlbmRNZXNzYWdlKGFjdGl2ZVRhYi5pZCwge1xuICAgICAgICAgICAgICAgIGtpbmQ6ICdzaG93UGVybWlzc2lvblNoZWV0JyxcbiAgICAgICAgICAgICAgICBob3N0LFxuICAgICAgICAgICAgICAgIHBlcm1pc3Npb25LaW5kOiBraW5kLFxuICAgICAgICAgICAgICAgIHF1ZXVlUG9zaXRpb24sXG4gICAgICAgICAgICAgICAgcXVldWVUb3RhbCxcbiAgICAgICAgICAgIH0pO1xuICAgICAgICAgICAgXG4gICAgICAgICAgICBpZiAocmVzdWx0KSB7XG4gICAgICAgICAgICAgICAgaWYgKHJlc3VsdC5hbGxvd2VkKSB7XG4gICAgICAgICAgICAgICAgICAgIGNvbXBsZXRlKHtcbiAgICAgICAgICAgICAgICAgICAgICAgIHBheWxvYWQ6IHV1aWQsXG4gICAgICAgICAgICAgICAgICAgICAgICBvcmlnS2luZDoga2luZCxcbiAgICAgICAgICAgICAgICAgICAgICAgIGV2ZW50OiBwYXlsb2FkLFxuICAgICAgICAgICAgICAgICAgICAgICAgcmVtZW1iZXI6IHJlc3VsdC5yZW1lbWJlcixcbiAgICAgICAgICAgICAgICAgICAgICAgIGhvc3QsXG4gICAgICAgICAgICAgICAgICAgIH0pO1xuICAgICAgICAgICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgICAgICAgICAgIGRlbnkoe1xuICAgICAgICAgICAgICAgICAgICAgICAgcGF5bG9hZDogdXVpZCxcbiAgICAgICAgICAgICAgICAgICAgICAgIG9yaWdLaW5kOiBraW5kLFxuICAgICAgICAgICAgICAgICAgICAgICAgZXZlbnQ6IHBheWxvYWQsXG4gICAgICAgICAgICAgICAgICAgICAgICByZW1lbWJlcjogcmVzdWx0LnJlbWVtYmVyLFxuICAgICAgICAgICAgICAgICAgICAgICAgaG9zdCxcbiAgICAgICAgICAgICAgICAgICAgfSk7XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgIHByb21wdC5yZWxlYXNlKCk7XG4gICAgICAgICAgICAgICAgcmV0dXJuO1xuICAgICAgICAgICAgfVxuICAgICAgICB9XG4gICAgfSBjYXRjaCAoZSkge1xuICAgICAgICAvLyBDb250ZW50IHNjcmlwdCBub3QgYXZhaWxhYmxlLCBmYWxsIGJhY2sgdG8gdGFiXG4gICAgICAgIGxvZygnQm90dG9tIHNoZWV0IHVuYXZhaWxhYmxlLCBmYWxsaW5nIGJhY2sgdG8gdGFiOicsIGUubWVzc2FnZSk7XG4gICAgfVxuXG4gICAgLy8gRmFsbGJhY2sgdG8gcGVybWlzc2lvbiB0YWJcbiAgICBsZXQgcXMgPSBuZXcgVVJMU2VhcmNoUGFyYW1zKHtcbiAgICAgICAgdXVpZCxcbiAgICAgICAga2luZCxcbiAgICAgICAgaG9zdCxcbiAgICAgICAgcGF5bG9hZDogSlNPTi5zdHJpbmdpZnkocGF5bG9hZCB8fCBmYWxzZSksXG4gICAgICAgIHF1ZXVlUG9zaXRpb24sXG4gICAgICAgIHF1ZXVlVG90YWwsXG4gICAgfSk7XG4gICAgbGV0IHRhYiA9IGF3YWl0IGFwaS50YWJzLmdldEN1cnJlbnQoKTtcbiAgICBsZXQgcCA9IGF3YWl0IGFwaS50YWJzLmNyZWF0ZSh7XG4gICAgICAgIHVybDogYXBpLnJ1bnRpbWUuZ2V0VVJMKGBwZXJtaXNzaW9uL3Blcm1pc3Npb24uaHRtbD8ke3FzLnRvU3RyaW5nKCl9YCksXG4gICAgICAgIG9wZW5lclRhYklkOiB0YWI/LmlkLFxuICAgIH0pO1xuICAgIHByb21wdC50YWJJZCA9IHAuaWQ7XG4gICAgcmV0dXJuIHRydWU7XG59XG5cbmZ1bmN0aW9uIGNvbXBsZXRlKHsgcGF5bG9hZCwgb3JpZ0tpbmQsIGV2ZW50LCByZW1lbWJlciwgaG9zdCB9KSB7XG4gICAgY29uc3Qgc2VuZFJlc3BvbnNlID0gdmFsaWRhdGlvbnNbcGF5bG9hZF07XG4gICAgZGVsZXRlIHZhbGlkYXRpb25zW3BheWxvYWRdO1xuICAgIGlmIChPYmplY3Qua2V5cyh2YWxpZGF0aW9ucykubGVuZ3RoID09PSAwKSB7XG4gICAgICAgIHBlbmRpbmdRdWV1ZSA9IHsgdG90YWw6IDAsIHByb2Nlc3NlZDogMCB9O1xuICAgIH1cblxuICAgIGlmIChyZW1lbWJlcikge1xuICAgICAgICBsZXQgbUtpbmQgPVxuICAgICAgICAgICAgb3JpZ0tpbmQgPT09ICdzaWduRXZlbnQnID8gYHNpZ25FdmVudDoke2V2ZW50LmtpbmR9YCA6IG9yaWdLaW5kO1xuICAgICAgICBzZXRQZXJtaXNzaW9uKGhvc3QsIG1LaW5kLCAnYWxsb3cnKTtcbiAgICB9XG5cbiAgICBpZiAoc2VuZFJlc3BvbnNlKSB7XG4gICAgICAgIGNvbnN0IG9uRXJyb3IgPSAoZSkgPT4ge1xuICAgICAgICAgICAgbG9nKGBFcnJvciBpbiAke29yaWdLaW5kfTogJHtlLm1lc3NhZ2V9YCk7XG4gICAgICAgICAgICBzZW5kUmVzcG9uc2UoeyBlcnJvcjogJ2J1bmtlcl9lcnJvcicsIG1lc3NhZ2U6IGUubWVzc2FnZSB9KTtcbiAgICAgICAgfTtcblxuICAgICAgICBzd2l0Y2ggKG9yaWdLaW5kKSB7XG4gICAgICAgICAgICBjYXNlICdnZXRQdWJLZXknOlxuICAgICAgICAgICAgICAgIGdldFB1YktleSgpLnRoZW4ocGsgPT4gc2VuZFJlc3BvbnNlKHBrKSkuY2F0Y2gob25FcnJvcik7XG4gICAgICAgICAgICAgICAgYnJlYWs7XG4gICAgICAgICAgICBjYXNlICdzaWduRXZlbnQnOlxuICAgICAgICAgICAgICAgIHNpZ25FdmVudF8oZXZlbnQsIGhvc3QpLnRoZW4oZSA9PiBzZW5kUmVzcG9uc2UoZSkpLmNhdGNoKG9uRXJyb3IpO1xuICAgICAgICAgICAgICAgIGJyZWFrO1xuICAgICAgICAgICAgY2FzZSAnbmlwMDQuZW5jcnlwdCc6XG4gICAgICAgICAgICAgICAgbmlwMDRFbmNyeXB0KGV2ZW50KS50aGVuKGUgPT4gc2VuZFJlc3BvbnNlKGUpKS5jYXRjaChvbkVycm9yKTtcbiAgICAgICAgICAgICAgICBicmVhaztcbiAgICAgICAgICAgIGNhc2UgJ25pcDA0LmRlY3J5cHQnOlxuICAgICAgICAgICAgICAgIG5pcDA0RGVjcnlwdChldmVudCkudGhlbihlID0+IHNlbmRSZXNwb25zZShlKSkuY2F0Y2gob25FcnJvcik7XG4gICAgICAgICAgICAgICAgYnJlYWs7XG4gICAgICAgICAgICBjYXNlICduaXA0NC5lbmNyeXB0JzpcbiAgICAgICAgICAgICAgICBuaXA0NEVuY3J5cHQoZXZlbnQpLnRoZW4oZSA9PiBzZW5kUmVzcG9uc2UoZSkpLmNhdGNoKG9uRXJyb3IpO1xuICAgICAgICAgICAgICAgIGJyZWFrO1xuICAgICAgICAgICAgY2FzZSAnbmlwNDQuZGVjcnlwdCc6XG4gICAgICAgICAgICAgICAgbmlwNDREZWNyeXB0KGV2ZW50KS50aGVuKGUgPT4gc2VuZFJlc3BvbnNlKGUpKS5jYXRjaChvbkVycm9yKTtcbiAgICAgICAgICAgICAgICBicmVhaztcbiAgICAgICAgICAgIGNhc2UgJ2dldFJlbGF5cyc6XG4gICAgICAgICAgICAgICAgZ2V0UmVsYXlzKCkudGhlbihlID0+IHNlbmRSZXNwb25zZShlKSkuY2F0Y2gob25FcnJvcik7XG4gICAgICAgICAgICAgICAgYnJlYWs7XG4gICAgICAgICAgICBjYXNlICdhZGRSZWxheSc6XG4gICAgICAgICAgICAgICAgYWRkUmVsYXkoZXZlbnQudXJsKS50aGVuKGUgPT4gc2VuZFJlc3BvbnNlKGUpKS5jYXRjaChvbkVycm9yKTtcbiAgICAgICAgICAgICAgICBicmVhaztcbiAgICAgICAgICAgIGNhc2UgJ2V4cG9ydFByb2ZpbGUnOlxuICAgICAgICAgICAgICAgIGV4cG9ydFByb2ZpbGVEYXRhKCkudGhlbihlID0+IHNlbmRSZXNwb25zZShlKSkuY2F0Y2gob25FcnJvcik7XG4gICAgICAgICAgICAgICAgYnJlYWs7XG4gICAgICAgIH1cbiAgICB9XG59XG5cbmZ1bmN0aW9uIGRlbnkoeyBvcmlnS2luZCwgaG9zdCwgcGF5bG9hZCwgcmVtZW1iZXIsIGV2ZW50IH0pIHtcbiAgICBjb25zdCBzZW5kUmVzcG9uc2UgPSB2YWxpZGF0aW9uc1twYXlsb2FkXTtcbiAgICBkZWxldGUgdmFsaWRhdGlvbnNbcGF5bG9hZF07XG4gICAgaWYgKE9iamVjdC5rZXlzKHZhbGlkYXRpb25zKS5sZW5ndGggPT09IDApIHtcbiAgICAgICAgcGVuZGluZ1F1ZXVlID0geyB0b3RhbDogMCwgcHJvY2Vzc2VkOiAwIH07XG4gICAgfVxuXG4gICAgaWYgKHJlbWVtYmVyKSB7XG4gICAgICAgIGxldCBtS2luZCA9XG4gICAgICAgICAgICBvcmlnS2luZCA9PT0gJ3NpZ25FdmVudCcgPyBgc2lnbkV2ZW50OiR7ZXZlbnQua2luZH1gIDogb3JpZ0tpbmQ7XG4gICAgICAgIHNldFBlcm1pc3Npb24oaG9zdCwgbUtpbmQsICdkZW55Jyk7XG4gICAgfVxuXG4gICAgc2VuZFJlc3BvbnNlPy4odW5kZWZpbmVkKTtcbiAgICByZXR1cm4gZmFsc2U7XG59XG5cbi8qKlxuICogQ2FjaGUgcHViS2V5cyBmb3IgYWxsIGxvY2FsIHByb2ZpbGVzIChjYWxsIGJlZm9yZSBlbmNyeXB0aW5nIGtleXMpLlxuICogVGhpcyBlbnN1cmVzIG5wdWIgaXMgYXZhaWxhYmxlIGV2ZW4gd2hlbiB0aGUgZXh0ZW5zaW9uIGlzIGxvY2tlZC5cbiAqL1xuYXN5bmMgZnVuY3Rpb24gY2FjaGVQdWJLZXlzRm9yQWxsUHJvZmlsZXMoKSB7XG4gICAgY29uc3QgcHJvZmlsZXMgPSBhd2FpdCBnZXRQcm9maWxlcygpO1xuICAgIGxldCB1cGRhdGVkID0gZmFsc2U7XG4gICAgZm9yIChsZXQgaSA9IDA7IGkgPCBwcm9maWxlcy5sZW5ndGg7IGkrKykge1xuICAgICAgICBjb25zdCBwcm9maWxlID0gcHJvZmlsZXNbaV07XG4gICAgICAgIGlmIChwcm9maWxlLnR5cGUgPT09ICdidW5rZXInKSBjb250aW51ZTtcbiAgICAgICAgaWYgKHByb2ZpbGUucHViS2V5KSBjb250aW51ZTsgLy8gQWxyZWFkeSBjYWNoZWRcbiAgICAgICAgaWYgKCFwcm9maWxlLnByaXZLZXkgfHwgaXNFbmNyeXB0ZWRCbG9iKHByb2ZpbGUucHJpdktleSkpIGNvbnRpbnVlO1xuICAgICAgICB0cnkge1xuICAgICAgICAgICAgY29uc3QgcHViS2V5ID0gZ2V0UHVibGljS2V5U3luYyhwcm9maWxlLnByaXZLZXkpO1xuICAgICAgICAgICAgcHJvZmlsZXNbaV0ucHViS2V5ID0gcHViS2V5O1xuICAgICAgICAgICAgdXBkYXRlZCA9IHRydWU7XG4gICAgICAgIH0gY2F0Y2ggKGUpIHtcbiAgICAgICAgICAgIGNvbnNvbGUuZXJyb3IoYEZhaWxlZCB0byBjYWNoZSBwdWJLZXkgZm9yIHByb2ZpbGUgJHtpfTpgLCBlKTtcbiAgICAgICAgfVxuICAgIH1cbiAgICBpZiAodXBkYXRlZCkge1xuICAgICAgICBhd2FpdCBzdG9yYWdlLnNldCh7IHByb2ZpbGVzIH0pO1xuICAgIH1cbn1cblxuLy8gT3B0aW9uc1xuYXN5bmMgZnVuY3Rpb24gc2F2ZVByaXZhdGVLZXkoW2luZGV4LCBwcml2S2V5XSkge1xuICAgIGNvbnN0IHByb2ZpbGUgPSBhd2FpdCBnZXRQcm9maWxlKGluZGV4KTtcbiAgICBpZiAocHJvZmlsZT8udHlwZSA9PT0gJ2J1bmtlcicpIHtcbiAgICAgICAgdGhyb3cgbmV3IEVycm9yKCdDYW5ub3Qgc2V0IHByaXZhdGUga2V5IG9uIGEgYnVua2VyIHByb2ZpbGUnKTtcbiAgICB9XG5cbiAgICBpZiAodHlwZW9mIHByaXZLZXkgIT09ICdzdHJpbmcnIHx8IHByaXZLZXkubGVuZ3RoID09PSAwKSB7XG4gICAgICAgIHRocm93IG5ldyBFcnJvcignSW52YWxpZCBwcml2YXRlIGtleTogbXVzdCBiZSBhIG5vbi1lbXB0eSBzdHJpbmcnKTtcbiAgICB9XG5cbiAgICBsZXQgaGV4S2V5O1xuICAgIGlmIChwcml2S2V5LnN0YXJ0c1dpdGgoJ25zZWMnKSkge1xuICAgICAgICB0cnkge1xuICAgICAgICAgICAgaGV4S2V5ID0gbmlwMTkuZGVjb2RlKHByaXZLZXkpLmRhdGE7XG4gICAgICAgIH0gY2F0Y2ggKGUpIHtcbiAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcignSW52YWxpZCBuc2VjIGtleScpO1xuICAgICAgICB9XG4gICAgfSBlbHNlIHtcbiAgICAgICAgLy8gQWxyZWFkeSBhIGhleCBzdHJpbmdcbiAgICAgICAgaGV4S2V5ID0gcHJpdktleTtcbiAgICB9XG5cbiAgICBpZiAoIS9eWzAtOWEtZl17NjR9JC9pLnRlc3QoaGV4S2V5KSkge1xuICAgICAgICB0aHJvdyBuZXcgRXJyb3IoJ0ludmFsaWQgcHJpdmF0ZSBrZXk6IG11c3QgYmUgNjQgaGV4IGNoYXJhY3RlcnMgb3IgdmFsaWQgbnNlYycpO1xuICAgIH1cblxuICAgIGxldCBwcm9maWxlcyA9IGF3YWl0IGdldCgncHJvZmlsZXMnKTtcblxuICAgIGlmICghcHJvZmlsZXMgfHwgaW5kZXggPCAwIHx8IGluZGV4ID49IHByb2ZpbGVzLmxlbmd0aCkge1xuICAgICAgICB0aHJvdyBuZXcgRXJyb3IoJ0ludmFsaWQgcHJvZmlsZSBpbmRleCcpO1xuICAgIH1cblxuICAgIC8vIENhY2hlIHRoZSBwdWJsaWMga2V5IHNvIGl0J3MgYXZhaWxhYmxlIGV2ZW4gd2hlbiBsb2NrZWRcbiAgICBjb25zdCBwdWJLZXkgPSBnZXRQdWJsaWNLZXlTeW5jKGhleEtleSk7XG4gICAgcHJvZmlsZXNbaW5kZXhdLnB1YktleSA9IHB1YktleTtcblxuICAgIC8vIElmIGVuY3J5cHRpb24gaXMgYWN0aXZlLCByZS1lbmNyeXB0IHRoZSBuZXcga2V5IHVzaW5nIHRoZSBzZXNzaW9uIGtleS5cbiAgICBjb25zdCBlbmNyeXB0ZWQgPSBhd2FpdCBpc0VuY3J5cHRlZCgpO1xuICAgIGlmIChlbmNyeXB0ZWQpIHtcbiAgICAgICAgLy8gRW5jcnlwdGlvbiBpcyBvbiBidXQgdGhlcmUncyBubyBsaXZlIHNlc3Npb24ga2V5IChsb2NrZWQsIG9yIHRoZSBNVjNcbiAgICAgICAgLy8gd29ya2VyIHdhcyBldmljdGVkIGFuZCBsb3N0IGl0KS4gUmVmdXNlIHJhdGhlciB0aGFuIGZhbGwgdGhyb3VnaCBhbmRcbiAgICAgICAgLy8gcGVyc2lzdCB0aGUga2V5IGFzIFBMQUlOVEVYVCBpbnRvIGEgdmF1bHQgdGhlIHVzZXIgYmVsaWV2ZXMgaXNcbiAgICAgICAgLy8gZW5jcnlwdGVkLiBUaGUgY2FsbGVyIHN1cmZhY2VzIHRoaXMgYXMgYSBzYXZlIGVycm9yLlxuICAgICAgICBpZiAoIXNlc3Npb25DcnlwdG9LZXkpIHtcbiAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcignRXh0ZW5zaW9uIGlzIGxvY2tlZCBcdTIwMTQgdW5sb2NrIGJlZm9yZSBzYXZpbmcgYSBrZXknKTtcbiAgICAgICAgfVxuICAgICAgICBwcm9maWxlc1tpbmRleF0ucHJpdktleSA9IGF3YWl0IGVuY3J5cHRXaXRoS2V5KGhleEtleSwgc2Vzc2lvbkNyeXB0b0tleSwgc2Vzc2lvbktleVNhbHQpO1xuICAgICAgICBzZXNzaW9uS2V5cy5zZXQoaW5kZXgsIGhleEtleSk7XG4gICAgfSBlbHNlIHtcbiAgICAgICAgcHJvZmlsZXNbaW5kZXhdLnByaXZLZXkgPSBoZXhLZXk7XG4gICAgfVxuXG4gICAgYXdhaXQgc3RvcmFnZS5zZXQoeyBwcm9maWxlcyB9KTtcbiAgICByZXR1cm4gdHJ1ZTtcbn1cblxuYXN5bmMgZnVuY3Rpb24gZ2V0TnNlYyhpbmRleCkge1xuICAgIGxldCBwcm9maWxlID0gYXdhaXQgZ2V0UHJvZmlsZShpbmRleCk7XG5cbiAgICBpZiAocHJvZmlsZS50eXBlID09PSAnYnVua2VyJykgcmV0dXJuIG51bGw7XG5cbiAgICBsZXQgaGV4S2V5ID0gYXdhaXQgZ2V0UGxhaW50ZXh0UHJpdktleShpbmRleCwgcHJvZmlsZSk7XG4gICAgbGV0IG5zZWMgPSBuaXAxOS5uc2VjRW5jb2RlKGhleEtleSk7XG4gICAgcmV0dXJuIG5zZWM7XG59XG5cbmFzeW5jIGZ1bmN0aW9uIGdldE5wdWIoaW5kZXgpIHtcbiAgICBsZXQgcHJvZmlsZSA9IGF3YWl0IGdldFByb2ZpbGUoaW5kZXgpO1xuXG4gICAgaWYgKCFwcm9maWxlKSByZXR1cm4gbnVsbDtcblxuICAgIGlmIChwcm9maWxlLnR5cGUgPT09ICdidW5rZXInKSB7XG4gICAgICAgIGlmIChwcm9maWxlLnJlbW90ZVB1YmtleSkgcmV0dXJuIG5pcDE5Lm5wdWJFbmNvZGUocHJvZmlsZS5yZW1vdGVQdWJrZXkpO1xuICAgICAgICByZXR1cm4gbnVsbDtcbiAgICB9XG5cbiAgICAvLyBVc2UgY2FjaGVkIHB1YktleSBpZiBhdmFpbGFibGUgKHdvcmtzIGV2ZW4gd2hlbiBsb2NrZWQpXG4gICAgaWYgKHByb2ZpbGUucHViS2V5KSB7XG4gICAgICAgIHJldHVybiBuaXAxOS5ucHViRW5jb2RlKHByb2ZpbGUucHViS2V5KTtcbiAgICB9XG5cbiAgICAvLyBGYWxsYmFjazogZGVyaXZlIGZyb20gcHJpdmF0ZSBrZXkgKHJlcXVpcmVzIHVubG9ja2VkIHN0YXRlKVxuICAgIHRyeSB7XG4gICAgICAgIGxldCBoZXhLZXkgPSBhd2FpdCBnZXRQbGFpbnRleHRQcml2S2V5KGluZGV4LCBwcm9maWxlKTtcbiAgICAgICAgaWYgKCFoZXhLZXkgfHwgdHlwZW9mIGhleEtleSAhPT0gJ3N0cmluZycgfHwgaGV4S2V5Lmxlbmd0aCAhPT0gNjQpIHtcbiAgICAgICAgICAgIHJldHVybiBudWxsO1xuICAgICAgICB9XG4gICAgICAgIGxldCBwdWJLZXkgPSBnZXRQdWJsaWNLZXlTeW5jKGhleEtleSk7XG4gICAgICAgIGxldCBucHViID0gbmlwMTkubnB1YkVuY29kZShwdWJLZXkpO1xuICAgICAgICByZXR1cm4gbnB1YjtcbiAgICB9IGNhdGNoIChlKSB7XG4gICAgICAgIGNvbnNvbGUuZXJyb3IoJ2dldE5wdWIgZXJyb3I6JywgZSk7XG4gICAgICAgIHJldHVybiBudWxsO1xuICAgIH1cbn1cblxuLyoqXG4gKiBHZXQgdGhlIHBsYWludGV4dCBoZXggcHJpdmF0ZSBrZXkgZm9yIGEgcHJvZmlsZS5cbiAqIFVzZXMgc2Vzc2lvbiBjYWNoZSBpZiBlbmNyeXB0aW9uIGlzIGFjdGl2ZSwgb3RoZXJ3aXNlIHJlYWRzIGZyb20gc3RvcmFnZSBkaXJlY3RseS5cbiAqL1xuYXN5bmMgZnVuY3Rpb24gZ2V0UGxhaW50ZXh0UHJpdktleShpbmRleCwgcHJvZmlsZSkge1xuICAgIGlmIChpc0VuY3J5cHRlZEJsb2IocHJvZmlsZS5wcml2S2V5KSkge1xuICAgICAgICAvLyBLZXkgaXMgZW5jcnlwdGVkIFx1MjAxNCBtdXN0IHVzZSBzZXNzaW9uIGNhY2hlXG4gICAgICAgIGlmIChzZXNzaW9uS2V5cy5oYXMoaW5kZXgpKSB7XG4gICAgICAgICAgICBjb25zdCBjYWNoZWQgPSBzZXNzaW9uS2V5cy5nZXQoaW5kZXgpO1xuICAgICAgICAgICAgLy8gR3VhcmQgYWdhaW5zdCBhIHN0YWxlIGNhY2hlIGVudHJ5LiBzZXNzaW9uS2V5cyBpcyBrZXllZCBieSBwcm9maWxlXG4gICAgICAgICAgICAvLyBpbmRleCwgYnV0IGRlbGV0aW5nIGEgcHJvZmlsZSBzaGlmdHMgZXZlcnkgbGF0ZXIgaW5kZXggZG93biBieSBvbmVcbiAgICAgICAgICAgIC8vIHdpdGhvdXQgdXBkYXRpbmcgdGhpcyBpbi1tZW1vcnkgbWFwIFx1MjAxNCBzbyBzZXNzaW9uS2V5cy5nZXQoaW5kZXgpXG4gICAgICAgICAgICAvLyBjb3VsZCBiZSBhIERJRkZFUkVOVCBpZGVudGl0eSdzIGtleS4gVmVyaWZ5IHRoZSBjYWNoZWQga2V5IGFjdHVhbGx5XG4gICAgICAgICAgICAvLyBkZXJpdmVzIHRvIHRoaXMgcHJvZmlsZSdzIHB1YmtleSBiZWZvcmUgcmV0dXJuaW5nIGl0OyBvdGhlcndpc2Ugd2VcbiAgICAgICAgICAgIC8vIHdvdWxkIHNpZ24gd2l0aCB0aGUgd3Jvbmcga2V5LiBJZiB0aGUgcHJvZmlsZSBoYXMgbm8gY2FjaGVkIHB1YmtleVxuICAgICAgICAgICAgLy8gd2UgY2FuJ3QgdmFsaWRhdGUsIHNvIGZhbGwgYmFjayB0byB0aGUgbGVnYWN5IGJlaGF2aW91ci5cbiAgICAgICAgICAgIGlmICghcHJvZmlsZS5wdWJLZXkgfHwgZ2V0UHVibGljS2V5U3luYyhjYWNoZWQpID09PSBwcm9maWxlLnB1YktleSkge1xuICAgICAgICAgICAgICAgIHJldHVybiBjYWNoZWQ7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgICAvLyBTdGFsZSBlbnRyeSBcdTIwMTQgZHJvcCBpdCBhbmQgdHJlYXQgdGhpcyBwcm9maWxlIGFzIGxvY2tlZC5cbiAgICAgICAgICAgIHNlc3Npb25LZXlzLmRlbGV0ZShpbmRleCk7XG4gICAgICAgIH1cbiAgICAgICAgdGhyb3cgbmV3IEVycm9yKCdFeHRlbnNpb24gaXMgbG9ja2VkIFx1MjAxNCBjYW5ub3QgYWNjZXNzIHByaXZhdGUga2V5Jyk7XG4gICAgfVxuICAgIHJldHVybiBwcm9maWxlLnByaXZLZXk7XG59XG5cbmFzeW5jIGZ1bmN0aW9uIGdldFByaXZLZXkoKSB7XG4gICAgbGV0IGluZGV4ID0gYXdhaXQgZ2V0UHJvZmlsZUluZGV4KCk7XG4gICAgbGV0IHByb2ZpbGUgPSBhd2FpdCBjdXJyZW50UHJvZmlsZSgpO1xuICAgIGxldCBoZXhLZXkgPSBhd2FpdCBnZXRQbGFpbnRleHRQcml2S2V5KGluZGV4LCBwcm9maWxlKTtcbiAgICByZXR1cm4gaGV4VG9CeXRlcyhoZXhLZXkpO1xufVxuXG5hc3luYyBmdW5jdGlvbiBnZXRQdWJLZXkoKSB7XG4gICAgbGV0IHBpID0gYXdhaXQgZ2V0UHJvZmlsZUluZGV4KCk7XG4gICAgbGV0IHByb2ZpbGUgPSBhd2FpdCBnZXRQcm9maWxlKHBpKTtcblxuICAgIGlmIChwcm9maWxlLnR5cGUgPT09ICdidW5rZXInKSB7XG4gICAgICAgIC8vIFJldHVybiBjYWNoZWQgcmVtb3RlUHVia2V5LCBvciBsaXZlLXF1ZXJ5IGFuZCBjYWNoZVxuICAgICAgICBpZiAocHJvZmlsZS5yZW1vdGVQdWJrZXkpIHJldHVybiBwcm9maWxlLnJlbW90ZVB1YmtleTtcbiAgICAgICAgY29uc3Qgc2Vzc2lvbiA9IGF3YWl0IGdldE9yQ3JlYXRlU2Vzc2lvbihwaSk7XG4gICAgICAgIGNvbnN0IHB1YmtleSA9IGF3YWl0IHNlc3Npb24uZ2V0UHVibGljS2V5KCk7XG4gICAgICAgIGNvbnN0IHByb2ZpbGVzID0gYXdhaXQgZ2V0KCdwcm9maWxlcycpO1xuICAgICAgICBwcm9maWxlc1twaV0ucmVtb3RlUHVia2V5ID0gcHVia2V5O1xuICAgICAgICBhd2FpdCBzdG9yYWdlLnNldCh7IHByb2ZpbGVzIH0pO1xuICAgICAgICByZXR1cm4gcHVia2V5O1xuICAgIH1cblxuICAgIC8vIFVzZSBjYWNoZWQgcHViS2V5IGlmIGF2YWlsYWJsZSAod29ya3MgZXZlbiB3aGVuIGxvY2tlZClcbiAgICBpZiAocHJvZmlsZS5wdWJLZXkpIHJldHVybiBwcm9maWxlLnB1YktleTtcblxuICAgIC8vIEZhbGxiYWNrOiBkZXJpdmUgZnJvbSBwcml2YXRlIGtleSAocmVxdWlyZXMgdW5sb2NrZWQgc3RhdGUpXG4gICAgbGV0IHByaXZLZXkgPSBhd2FpdCBnZXRQcml2S2V5KCk7XG4gICAgbGV0IHB1YktleSA9IGdldFB1YmxpY0tleVN5bmMoYnl0ZXNUb0hleChwcml2S2V5KSk7XG4gICAgcmV0dXJuIHB1YktleTtcbn1cblxuYXN5bmMgZnVuY3Rpb24gY3VycmVudFByb2ZpbGUoKSB7XG4gICAgbGV0IGluZGV4ID0gYXdhaXQgZ2V0UHJvZmlsZUluZGV4KCk7XG4gICAgbGV0IHByb2ZpbGVzID0gYXdhaXQgZ2V0KCdwcm9maWxlcycpO1xuICAgIHJldHVybiBwcm9maWxlc1tpbmRleF07XG59XG5cbmFzeW5jIGZ1bmN0aW9uIHNpZ25FdmVudF8oZXZlbnQsIGhvc3QpIHtcbiAgICBldmVudCA9IEpTT04ucGFyc2UoSlNPTi5zdHJpbmdpZnkoZXZlbnQpKTtcblxuICAgIGNvbnN0IHBpID0gYXdhaXQgZ2V0UHJvZmlsZUluZGV4KCk7XG4gICAgY29uc3QgcHJvZmlsZSA9IGF3YWl0IGdldFByb2ZpbGUocGkpO1xuXG4gICAgaWYgKHByb2ZpbGUudHlwZSA9PT0gJ2J1bmtlcicpIHtcbiAgICAgICAgY29uc3Qgc2Vzc2lvbiA9IGF3YWl0IGdldE9yQ3JlYXRlU2Vzc2lvbihwaSk7XG4gICAgICAgIGV2ZW50ID0gYXdhaXQgc2Vzc2lvbi5zaWduRXZlbnQoZXZlbnQpO1xuICAgIH0gZWxzZSB7XG4gICAgICAgIGxldCBzayA9IGF3YWl0IGdldFByaXZLZXkoKTtcbiAgICAgICAgZXZlbnQgPSBhd2FpdCBmaW5hbGl6ZUV2ZW50KGV2ZW50LCBzayk7XG4gICAgfVxuXG4gICAgc2F2ZUV2ZW50KHtcbiAgICAgICAgZXZlbnQsXG4gICAgICAgIG1ldGFkYXRhOiB7IGhvc3QsIHNpZ25lZF9hdDogTWF0aC5yb3VuZChEYXRlLm5vdygpIC8gMTAwMCkgfSxcbiAgICB9KTtcbiAgICByZXR1cm4gZXZlbnQ7XG59XG5cbmFzeW5jIGZ1bmN0aW9uIG5pcDA0RW5jcnlwdCh7IHB1YktleSwgcGxhaW5UZXh0IH0pIHtcbiAgICBjb25zdCBwaSA9IGF3YWl0IGdldFByb2ZpbGVJbmRleCgpO1xuICAgIGNvbnN0IHByb2ZpbGUgPSBhd2FpdCBnZXRQcm9maWxlKHBpKTtcblxuICAgIGlmIChwcm9maWxlLnR5cGUgPT09ICdidW5rZXInKSB7XG4gICAgICAgIGNvbnN0IHNlc3Npb24gPSBhd2FpdCBnZXRPckNyZWF0ZVNlc3Npb24ocGkpO1xuICAgICAgICByZXR1cm4gc2Vzc2lvbi5uaXAwNEVuY3J5cHQocHViS2V5LCBwbGFpblRleHQpO1xuICAgIH1cblxuICAgIGxldCBwcml2S2V5ID0gYXdhaXQgZ2V0UHJpdktleSgpO1xuICAgIHJldHVybiBuaXAwNC5lbmNyeXB0TWVzc2FnZShwbGFpblRleHQsIGJ5dGVzVG9IZXgocHJpdktleSksIHB1YktleSk7XG59XG5cbmFzeW5jIGZ1bmN0aW9uIG5pcDA0RGVjcnlwdCh7IHB1YktleSwgY2lwaGVyVGV4dCB9KSB7XG4gICAgY29uc3QgcGkgPSBhd2FpdCBnZXRQcm9maWxlSW5kZXgoKTtcbiAgICBjb25zdCBwcm9maWxlID0gYXdhaXQgZ2V0UHJvZmlsZShwaSk7XG5cbiAgICBpZiAocHJvZmlsZS50eXBlID09PSAnYnVua2VyJykge1xuICAgICAgICBjb25zdCBzZXNzaW9uID0gYXdhaXQgZ2V0T3JDcmVhdGVTZXNzaW9uKHBpKTtcbiAgICAgICAgcmV0dXJuIHNlc3Npb24ubmlwMDREZWNyeXB0KHB1YktleSwgY2lwaGVyVGV4dCk7XG4gICAgfVxuXG4gICAgbGV0IHByaXZLZXkgPSBhd2FpdCBnZXRQcml2S2V5KCk7XG4gICAgcmV0dXJuIG5pcDA0LmRlY3J5cHRNZXNzYWdlKGNpcGhlclRleHQsIGJ5dGVzVG9IZXgocHJpdktleSksIHB1YktleSk7XG59XG5cbmFzeW5jIGZ1bmN0aW9uIG5pcDQ0RW5jcnlwdCh7IHB1YktleSwgcGxhaW5UZXh0IH0pIHtcbiAgICBjb25zdCBwaSA9IGF3YWl0IGdldFByb2ZpbGVJbmRleCgpO1xuICAgIGNvbnN0IHByb2ZpbGUgPSBhd2FpdCBnZXRQcm9maWxlKHBpKTtcblxuICAgIGlmIChwcm9maWxlLnR5cGUgPT09ICdidW5rZXInKSB7XG4gICAgICAgIGNvbnN0IHNlc3Npb24gPSBhd2FpdCBnZXRPckNyZWF0ZVNlc3Npb24ocGkpO1xuICAgICAgICByZXR1cm4gc2Vzc2lvbi5uaXA0NEVuY3J5cHQocHViS2V5LCBwbGFpblRleHQpO1xuICAgIH1cblxuICAgIGxldCBwcml2S2V5ID0gYXdhaXQgZ2V0UHJpdktleSgpO1xuICAgIGxldCBjb252ZXJzYXRpb25LZXkgPSBuaXA0NC52Mi51dGlscy5nZXRDb252ZXJzYXRpb25LZXkocHJpdktleSwgcHViS2V5KTtcbiAgICByZXR1cm4gbmlwNDQudjIuZW5jcnlwdChwbGFpblRleHQsIGNvbnZlcnNhdGlvbktleSk7XG59XG5cbmFzeW5jIGZ1bmN0aW9uIG5pcDQ0RGVjcnlwdCh7IHB1YktleSwgY2lwaGVyVGV4dCB9KSB7XG4gICAgY29uc3QgcGkgPSBhd2FpdCBnZXRQcm9maWxlSW5kZXgoKTtcbiAgICBjb25zdCBwcm9maWxlID0gYXdhaXQgZ2V0UHJvZmlsZShwaSk7XG5cbiAgICBpZiAocHJvZmlsZS50eXBlID09PSAnYnVua2VyJykge1xuICAgICAgICBjb25zdCBzZXNzaW9uID0gYXdhaXQgZ2V0T3JDcmVhdGVTZXNzaW9uKHBpKTtcbiAgICAgICAgcmV0dXJuIHNlc3Npb24ubmlwNDREZWNyeXB0KHB1YktleSwgY2lwaGVyVGV4dCk7XG4gICAgfVxuXG4gICAgbGV0IHByaXZLZXkgPSBhd2FpdCBnZXRQcml2S2V5KCk7XG4gICAgbGV0IGNvbnZlcnNhdGlvbktleSA9IG5pcDQ0LnYyLnV0aWxzLmdldENvbnZlcnNhdGlvbktleShwcml2S2V5LCBwdWJLZXkpO1xuICAgIHJldHVybiBuaXA0NC52Mi5kZWNyeXB0KGNpcGhlclRleHQsIGNvbnZlcnNhdGlvbktleSk7XG59XG5cbmFzeW5jIGZ1bmN0aW9uIGdldFJlbGF5cygpIHtcbiAgICBsZXQgcHJvZmlsZSA9IGF3YWl0IGN1cnJlbnRQcm9maWxlKCk7XG4gICAgbGV0IHJlbGF5cyA9IHByb2ZpbGUucmVsYXlzO1xuICAgIGxldCByZWxheU9iaiA9IHt9O1xuICAgIC8vIFRoZSBnZXRSZWxheXMgY2FsbCBleHBlY3RzIHRoaXMgdG8gYmUgcmV0dXJuZWQgYXMgYW4gb2JqZWN0LCBub3QgYXJyYXlcbiAgICByZWxheXMuZm9yRWFjaChyZWxheSA9PiB7XG4gICAgICAgIGxldCB7IHVybCwgcmVhZCwgd3JpdGUgfSA9IHJlbGF5O1xuICAgICAgICByZWxheU9ialt1cmxdID0geyByZWFkLCB3cml0ZSB9O1xuICAgIH0pO1xuICAgIHJldHVybiByZWxheU9iajtcbn1cblxuYXN5bmMgZnVuY3Rpb24gYWRkUmVsYXkodXJsKSB7XG4gICAgLy8gVmFsaWRhdGUgVVJMXG4gICAgbGV0IHBhcnNlZDtcbiAgICB0cnkge1xuICAgICAgICBwYXJzZWQgPSBuZXcgVVJMKHVybCk7XG4gICAgfSBjYXRjaCB7XG4gICAgICAgIHRocm93IG5ldyBFcnJvcignSW52YWxpZCBVUkwnKTtcbiAgICB9XG4gICAgaWYgKHBhcnNlZC5wcm90b2NvbCAhPT0gJ3dzczonKSB7XG4gICAgICAgIHRocm93IG5ldyBFcnJvcignTXVzdCBiZSBhIHdzczovLyBVUkwnKTtcbiAgICB9XG5cbiAgICBsZXQgcHJvZmlsZXMgPSBhd2FpdCBnZXRQcm9maWxlcygpO1xuICAgIGxldCBwaSA9IGF3YWl0IGdldFByb2ZpbGVJbmRleCgpO1xuICAgIGxldCBwcm9maWxlID0gcHJvZmlsZXNbcGldO1xuICAgIGlmICghcHJvZmlsZS5yZWxheXMpIHByb2ZpbGUucmVsYXlzID0gW107XG5cbiAgICAvLyBDaGVjayBmb3IgZHVwbGljYXRlc1xuICAgIGlmIChwcm9maWxlLnJlbGF5cy5zb21lKHIgPT4gci51cmwgPT09IHBhcnNlZC5ocmVmKSkge1xuICAgICAgICByZXR1cm4geyBzdWNjZXNzOiB0cnVlLCBtZXNzYWdlOiAnUmVsYXkgYWxyZWFkeSBleGlzdHMnIH07XG4gICAgfVxuXG4gICAgcHJvZmlsZS5yZWxheXMucHVzaCh7IHVybDogcGFyc2VkLmhyZWYsIHJlYWQ6IHRydWUsIHdyaXRlOiB0cnVlIH0pO1xuICAgIHByb2ZpbGUudXBkYXRlZEF0ID0gTWF0aC5mbG9vcihEYXRlLm5vdygpIC8gMTAwMCk7XG4gICAgYXdhaXQgc3RvcmFnZS5zZXQoeyBwcm9maWxlcyB9KTtcblxuICAgIHJldHVybiB7IHN1Y2Nlc3M6IHRydWUsIG1lc3NhZ2U6ICdSZWxheSBhZGRlZCcgfTtcbn1cblxuYXN5bmMgZnVuY3Rpb24gZXhwb3J0UHJvZmlsZURhdGEoKSB7XG4gICAgbGV0IHBpID0gYXdhaXQgZ2V0UHJvZmlsZUluZGV4KCk7XG4gICAgbGV0IHByb2ZpbGUgPSBhd2FpdCBnZXRQcm9maWxlKHBpKTtcblxuICAgIGlmICghcHJvZmlsZSkgdGhyb3cgbmV3IEVycm9yKCdObyBhY3RpdmUgcHJvZmlsZScpO1xuICAgIGlmIChwcm9maWxlLnR5cGUgPT09ICdidW5rZXInKSB7XG4gICAgICAgIC8vIEJ1bmtlciBwcm9maWxlcyBkb24ndCBoYXZlIGxvY2FsIGtleXMgdG8gZXhwb3J0XG4gICAgICAgIHJldHVybiB7XG4gICAgICAgICAgICBuYW1lOiBwcm9maWxlLm5hbWUsXG4gICAgICAgICAgICB0eXBlOiAnYnVua2VyJyxcbiAgICAgICAgICAgIGJ1bmtlclVybDogcHJvZmlsZS5idW5rZXJVcmwgfHwgJycsXG4gICAgICAgICAgICBleHBvcnRlZEF0OiBuZXcgRGF0ZSgpLnRvSVNPU3RyaW5nKCksXG4gICAgICAgICAgICBzb3VyY2U6ICdOb3N0cktleScsXG4gICAgICAgIH07XG4gICAgfVxuXG4gICAgbGV0IG5wdWIgPSAnJztcbiAgICBpZiAocHJvZmlsZS5wdWJLZXkpIHtcbiAgICAgICAgbnB1YiA9IG5pcDE5Lm5wdWJFbmNvZGUocHJvZmlsZS5wdWJLZXkpO1xuICAgIH1cblxuICAgIGxldCBuc2VjID0gJyc7XG4gICAgdHJ5IHtcbiAgICAgICAgbnNlYyA9IGF3YWl0IGdldE5zZWMocGkpO1xuICAgIH0gY2F0Y2gge1xuICAgICAgICAvLyBLZXkgbWF5IGJlIGVuY3J5cHRlZCBhbmQgbG9ja2VkXG4gICAgICAgIHRocm93IG5ldyBFcnJvcignQ2Fubm90IGV4cG9ydCB3aGlsZSBsb2NrZWQuIFBsZWFzZSB1bmxvY2sgZmlyc3QuJyk7XG4gICAgfVxuXG4gICAgcmV0dXJuIHtcbiAgICAgICAgbmFtZTogcHJvZmlsZS5uYW1lLFxuICAgICAgICBucHViLFxuICAgICAgICBuc2VjLFxuICAgICAgICByZWxheXM6IChwcm9maWxlLnJlbGF5cyB8fCBbXSkubWFwKHIgPT4gci51cmwpLFxuICAgICAgICBleHBvcnRlZEF0OiBuZXcgRGF0ZSgpLnRvSVNPU3RyaW5nKCksXG4gICAgICAgIHNvdXJjZTogJ05vc3RyS2V5JyxcbiAgICB9O1xufVxuXG4vKipcbiAqIE9wZW4gZXBoZW1lcmFsIHJlbGF5IGNvbm5lY3Rpb25zLCBleGVjdXRlIGNhbGxiYWNrLCB0aGVuIGRpc2Nvbm5lY3QuXG4gKiBDb3JyZWN0IGZvciBDaHJvbWUgTVYzIHNlcnZpY2Ugd29ya2VyIGxpZmVjeWNsZSAobm8gcGVyc2lzdGVudCBwb29sKS5cbiAqXG4gKiBAcGFyYW0geydyZWFkJ3wnd3JpdGUnfSBtb2RlIC0gV2hpY2ggcmVsYXkgc3Vic2V0IHRvIGNvbm5lY3QgdG9cbiAqIEBwYXJhbSB7ZnVuY3Rpb24oUmVsYXlDb25uZWN0aW9uW10pOiBQcm9taXNlfSBjYWxsYmFja1xuICovXG5hc3luYyBmdW5jdGlvbiB3aXRoUmVsYXlzKG1vZGUsIGNhbGxiYWNrKSB7XG4gICAgY29uc3QgcHJvZmlsZSA9IGF3YWl0IGN1cnJlbnRQcm9maWxlKCk7XG4gICAgY29uc3QgcmVsYXlMaXN0ID0gcHJvZmlsZS5yZWxheXMgfHwgW107XG4gICAgY29uc3QgdXJscyA9IHJlbGF5TGlzdFxuICAgICAgICAuZmlsdGVyKHIgPT4gbW9kZSA9PT0gJ3JlYWQnID8gci5yZWFkIDogci53cml0ZSlcbiAgICAgICAgLm1hcChyID0+IHIudXJsKTtcblxuICAgIGlmICh1cmxzLmxlbmd0aCA9PT0gMCkge1xuICAgICAgICB0aHJvdyBuZXcgRXJyb3IoJ05vIHJlbGF5cyBjb25maWd1cmVkJyk7XG4gICAgfVxuXG4gICAgY29uc3QgY29ubmVjdGlvbnMgPSBbXTtcbiAgICBjb25zdCBjb25uZWN0UHJvbWlzZXMgPSB1cmxzLm1hcChhc3luYyAodXJsKSA9PiB7XG4gICAgICAgIGNvbnN0IHJlbGF5ID0gbmV3IFJlbGF5Q29ubmVjdGlvbih1cmwpO1xuICAgICAgICB0cnkge1xuICAgICAgICAgICAgYXdhaXQgcmVsYXkuY29ubmVjdCgpO1xuICAgICAgICAgICAgY29ubmVjdGlvbnMucHVzaChyZWxheSk7XG4gICAgICAgIH0gY2F0Y2ggKF8pIHtcbiAgICAgICAgICAgIC8vIFNraXAgcmVsYXlzIHRoYXQgZmFpbCB0byBjb25uZWN0XG4gICAgICAgIH1cbiAgICB9KTtcblxuICAgIGF3YWl0IFByb21pc2UuYWxsU2V0dGxlZChjb25uZWN0UHJvbWlzZXMpO1xuXG4gICAgaWYgKGNvbm5lY3Rpb25zLmxlbmd0aCA9PT0gMCkge1xuICAgICAgICB0aHJvdyBuZXcgRXJyb3IoJ0ZhaWxlZCB0byBjb25uZWN0IHRvIGFueSByZWxheScpO1xuICAgIH1cblxuICAgIHRyeSB7XG4gICAgICAgIGF3YWl0IGNhbGxiYWNrKGNvbm5lY3Rpb25zKTtcbiAgICB9IGZpbmFsbHkge1xuICAgICAgICBmb3IgKGNvbnN0IHJlbGF5IG9mIGNvbm5lY3Rpb25zKSB7XG4gICAgICAgICAgICByZWxheS5jbG9zZSgpO1xuICAgICAgICB9XG4gICAgfVxufVxuIiwgIi8qKlxuICogQG1vZHVsZSBub3N0ci1jcnlwdG8tdXRpbHNcbiAqIEBkZXNjcmlwdGlvbiBDb3JlIGNyeXB0b2dyYXBoaWMgdXRpbGl0aWVzIGZvciBOb3N0ciBwcm90b2NvbFxuICovXG5cbi8vIENvcmUgdHlwZXNcbmV4cG9ydCB0eXBlIHtcbiAgTm9zdHJFdmVudCxcbiAgVW5zaWduZWROb3N0ckV2ZW50LFxuICBTaWduZWROb3N0ckV2ZW50LFxuICBOb3N0ckZpbHRlcixcbiAgTm9zdHJTdWJzY3JpcHRpb24sXG4gIFB1YmxpY0tleSxcbiAgS2V5UGFpcixcbiAgTm9zdHJNZXNzYWdlVHVwbGUsXG59IGZyb20gJy4vdHlwZXMnO1xuXG4vLyBFdmVudCBraW5kcywgbWVzc2FnZSB0eXBlcywgYW5kIE5JUC00NiB0eXBlc1xuZXhwb3J0IHsgTm9zdHJFdmVudEtpbmQsIE5vc3RyTWVzc2FnZVR5cGUsIE5pcDQ2TWV0aG9kIH0gZnJvbSAnLi90eXBlcyc7XG5leHBvcnQgdHlwZSB7XG4gIE5pcDQ2UmVxdWVzdCxcbiAgTmlwNDZSZXNwb25zZSxcbiAgTmlwNDZTZXNzaW9uLFxuICBOaXA0NlNlc3Npb25JbmZvLFxuICBCdW5rZXJVUkksXG4gIEJ1bmtlclZhbGlkYXRpb25SZXN1bHQsXG59IGZyb20gJy4vdHlwZXMnO1xuXG4vLyBDb3JlIGNyeXB0byBmdW5jdGlvbnNcbmV4cG9ydCB7XG4gIGdlbmVyYXRlS2V5UGFpcixcbiAgZ2V0UHVibGljS2V5LFxuICBnZXRQdWJsaWNLZXlTeW5jLFxuICB2YWxpZGF0ZUtleVBhaXIsXG4gIGNyZWF0ZUV2ZW50LFxuICBzaWduRXZlbnQsXG4gIGZpbmFsaXplRXZlbnQsXG4gIHZlcmlmeVNpZ25hdHVyZSxcbiAgZW5jcnlwdCxcbiAgZGVjcnlwdCxcbn0gZnJvbSAnLi9jcnlwdG8nO1xuXG4vLyBWYWxpZGF0aW9uIGZ1bmN0aW9uc1xuZXhwb3J0IHtcbiAgdmFsaWRhdGVFdmVudCxcbiAgdmFsaWRhdGVFdmVudElkLFxuICB2YWxpZGF0ZUV2ZW50U2lnbmF0dXJlLFxuICB2YWxpZGF0ZVNpZ25lZEV2ZW50LFxuICB2YWxpZGF0ZUV2ZW50QmFzZSxcbiAgdmFsaWRhdGVGaWx0ZXIsXG4gIHZhbGlkYXRlU3Vic2NyaXB0aW9uLFxuICB2YWxpZGF0ZVJlc3BvbnNlLFxufSBmcm9tICcuL3ZhbGlkYXRpb24nO1xuXG4vLyBFdmVudCBmdW5jdGlvbnNcbmV4cG9ydCB7XG4gIGNhbGN1bGF0ZUV2ZW50SWQsXG59IGZyb20gJy4vZXZlbnQnO1xuXG4vLyBOSVAtMDQgZW5jcnlwdGlvblxuZXhwb3J0IHtcbiAgY29tcHV0ZVNoYXJlZFNlY3JldCxcbiAgZW5jcnlwdE1lc3NhZ2UsXG4gIGRlY3J5cHRNZXNzYWdlLFxufSBmcm9tICcuL25pcHMvbmlwLTA0JztcblxuLy8gUmUtZXhwb3J0IE5JUHNcbmV4cG9ydCAqIGFzIG5pcDAxIGZyb20gJy4vbmlwcy9uaXAtMDEnO1xuZXhwb3J0ICogYXMgbmlwMDQgZnJvbSAnLi9uaXBzL25pcC0wNCc7XG5leHBvcnQgKiBhcyBuaXAxOSBmcm9tICcuL25pcHMvbmlwLTE5JztcbmV4cG9ydCAqIGFzIG5pcDI2IGZyb20gJy4vbmlwcy9uaXAtMjYnO1xuZXhwb3J0ICogYXMgbmlwNDQgZnJvbSAnLi9uaXBzL25pcC00NCc7XG5leHBvcnQgKiBhcyBuaXA0NiBmcm9tICcuL25pcHMvbmlwLTQ2JztcbmV4cG9ydCAqIGFzIG5pcDQ5IGZyb20gJy4vbmlwcy9uaXAtNDknO1xuXG4vLyBVdGlsc1xuZXhwb3J0IHtcbiAgaGV4VG9CeXRlcyxcbiAgYnl0ZXNUb0hleCxcbiAgdXRmOFRvQnl0ZXMsXG4gIGJ5dGVzVG9VdGY4LFxufSBmcm9tICcuL3V0aWxzL2VuY29kaW5nJztcbiIsICIvKipcbiAqIEBtb2R1bGUgdHlwZXNcbiAqIEBkZXNjcmlwdGlvbiBUeXBlIGRlZmluaXRpb25zIGZvciBOb3N0clxuICovXG5cbmV4cG9ydCBpbnRlcmZhY2UgUHVibGljS2V5RGV0YWlscyB7XG4gIGhleDogc3RyaW5nO1xuICBieXRlczogVWludDhBcnJheTtcbn1cblxuZXhwb3J0IGludGVyZmFjZSBLZXlQYWlyIHtcbiAgcHJpdmF0ZUtleTogc3RyaW5nO1xuICBwdWJsaWNLZXk6IFB1YmxpY0tleURldGFpbHM7XG59XG5cbmV4cG9ydCBpbnRlcmZhY2UgTm9zdHJFdmVudCB7XG4gIGtpbmQ6IG51bWJlcjtcbiAgY3JlYXRlZF9hdDogbnVtYmVyO1xuICB0YWdzOiBzdHJpbmdbXVtdO1xuICBjb250ZW50OiBzdHJpbmc7XG4gIHB1YmtleTogc3RyaW5nO1xufVxuXG5leHBvcnQgaW50ZXJmYWNlIFNpZ25lZE5vc3RyRXZlbnQgZXh0ZW5kcyBOb3N0ckV2ZW50IHtcbiAgaWQ6IHN0cmluZztcbiAgc2lnOiBzdHJpbmc7XG59XG5cbmV4cG9ydCBpbnRlcmZhY2UgUHVibGljS2V5IHtcbiAgaGV4OiBzdHJpbmc7XG4gIGJ5dGVzPzogVWludDhBcnJheTtcbn1cblxuZXhwb3J0IGludGVyZmFjZSBWYWxpZGF0aW9uUmVzdWx0IHtcbiAgaXNWYWxpZDogYm9vbGVhbjtcbiAgZXJyb3I/OiBzdHJpbmc7XG59XG5cbmV4cG9ydCBlbnVtIE5vc3RyRXZlbnRLaW5kIHtcbiAgU0VUX01FVEFEQVRBID0gMCxcbiAgVEVYVF9OT1RFID0gMSxcbiAgUkVDT01NRU5EX1NFUlZFUiA9IDIsXG4gIENPTlRBQ1RfTElTVCA9IDMsXG4gIEVOQ1JZUFRFRF9ESVJFQ1RfTUVTU0FHRSA9IDQsXG4gIERFTEVURSA9IDUsXG4gIFJFUE9TVCA9IDYsXG4gIFJFQUNUSU9OID0gNyxcbiAgQkFER0VfQVdBUkQgPSA4LFxuICBDSEFOTkVMX0NSRUFURSA9IDQwLFxuICBDSEFOTkVMX01FVEFEQVRBID0gNDEsXG4gIENIQU5ORUxfTUVTU0FHRSA9IDQyLFxuICBDSEFOTkVMX0hJREVfTUVTU0FHRSA9IDQzLFxuICBDSEFOTkVMX01VVEVfVVNFUiA9IDQ0LFxuICBDSEFOTkVMX1JFU0VSVkUgPSA0NSxcbiAgUkVQT1JUSU5HID0gMTk4NCxcbiAgWkFQX1JFUVVFU1QgPSA5NzM0LFxuICBaQVAgPSA5NzM1LFxuICBNVVRFX0xJU1QgPSAxMDAwMCxcbiAgUElOX0xJU1QgPSAxMDAwMSxcbiAgUkVMQVlfTElTVF9NRVRBREFUQSA9IDEwMDAyLFxuICBDTElFTlRfQVVUSCA9IDIyMjQyLFxuICBBVVRIX1JFU1BPTlNFID0gMjIyNDMsXG4gIE5PU1RSX0NPTk5FQ1QgPSAyNDEzMyxcbiAgQ0FURUdPUklaRURfUEVPUExFID0gMzAwMDAsXG4gIENBVEVHT1JJWkVEX0JPT0tNQVJLUyA9IDMwMDAxLFxuICBQUk9GSUxFX0JBREdFUyA9IDMwMDA4LFxuICBCQURHRV9ERUZJTklUSU9OID0gMzAwMDksXG4gIExPTkdfRk9STSA9IDMwMDIzLFxuICBBUFBMSUNBVElPTl9TUEVDSUZJQyA9IDMwMDc4XG59XG5cbi8qKlxuICogUmUtZXhwb3J0IGFsbCB0eXBlcyBmcm9tIGJhc2UgbW9kdWxlXG4gKiBAcGFja2FnZURvY3VtZW50YXRpb25cbiAqL1xuZXhwb3J0ICogZnJvbSAnLi9iYXNlJztcblxuLyoqIFJlLWV4cG9ydCBwcm90b2NvbCB0eXBlcyAqL1xuZXhwb3J0ICogZnJvbSAnLi9wcm90b2NvbCc7XG5cbi8qKiBSZS1leHBvcnQgbWVzc2FnZSB0eXBlcyAqL1xuZXhwb3J0ICogZnJvbSAnLi9tZXNzYWdlcyc7XG5cbi8qKiBSZS1leHBvcnQgdHlwZSBndWFyZHMgKi9cbmV4cG9ydCAqIGZyb20gJy4vZ3VhcmRzJztcblxuLy8gUmUtZXhwb3J0IE5JUC0xOSB0eXBlc1xuZXhwb3J0IHR5cGUge1xuICBOaXAxOURhdGFUeXBlXG59IGZyb20gJy4uL25pcHMvbmlwLTE5JztcblxuLyoqIFJlLWV4cG9ydCBOSVAtNDYgdHlwZXMgKi9cbmV4cG9ydCAqIGZyb20gJy4vbmlwNDYnO1xuIiwgIi8qKlxuICogQG1vZHVsZSB0eXBlcy9iYXNlXG4gKiBAZGVzY3JpcHRpb24gQ29yZSB0eXBlIGRlZmluaXRpb25zIGZvciBOb3N0ciBwcm90b2NvbFxuICovXG5cbi8vIEtleSBUeXBlc1xuZXhwb3J0IHR5cGUgUHVibGljS2V5SGV4ID0gc3RyaW5nO1xuZXhwb3J0IHR5cGUgUHJpdmF0ZUtleUhleCA9IHN0cmluZztcblxuZXhwb3J0IGludGVyZmFjZSBQdWJsaWNLZXlEZXRhaWxzIHtcbiAgLyoqIFB1YmxpYyBrZXkgaW4gaGV4IGZvcm1hdCAqL1xuICBoZXg6IHN0cmluZztcbiAgLyoqIE5JUC0wNSBpZGVudGlmaWVyICovXG4gIG5pcDA1OiBzdHJpbmc7XG4gIC8qKiBQdWJsaWMga2V5IGluIGJ5dGVzIGZvcm1hdCAqL1xuICBieXRlczogVWludDhBcnJheTtcbn1cblxuZXhwb3J0IHR5cGUgUHVibGljS2V5ID0gUHVibGljS2V5SGV4IHwgUHVibGljS2V5RGV0YWlscztcblxuZXhwb3J0IGludGVyZmFjZSBLZXlQYWlyIHtcbiAgLyoqIFByaXZhdGUga2V5IGluIGhleCBmb3JtYXQgKi9cbiAgcHJpdmF0ZUtleTogUHJpdmF0ZUtleUhleDtcbiAgLyoqIFB1YmxpYyBrZXkgZGV0YWlscyAqL1xuICBwdWJsaWNLZXk6IFB1YmxpY0tleURldGFpbHM7XG59XG5cbi8vIEV2ZW50IFR5cGVzXG5leHBvcnQgZW51bSBOb3N0ckV2ZW50S2luZCB7XG4gIC8vIE5JUC0wMTogQ29yZSBQcm90b2NvbFxuICBTRVRfTUVUQURBVEEgPSAwLFxuICBURVhUX05PVEUgPSAxLFxuICBSRUNPTU1FTkRfU0VSVkVSID0gMixcbiAgQ09OVEFDVFMgPSAzLFxuICBFTkNSWVBURURfRElSRUNUX01FU1NBR0UgPSA0LFxuICBFVkVOVF9ERUxFVElPTiA9IDUsXG4gIFJFUE9TVCA9IDYsXG4gIFJFQUNUSU9OID0gNyxcblxuICAvLyBOSVAtMjg6IFB1YmxpYyBDaGF0XG4gIENIQU5ORUxfQ1JFQVRJT04gPSA0MCxcbiAgQ0hBTk5FTF9NRVRBREFUQSA9IDQxLFxuICBDSEFOTkVMX01FU1NBR0UgPSA0MixcbiAgQ0hBTk5FTF9ISURFX01FU1NBR0UgPSA0MyxcbiAgQ0hBTk5FTF9NVVRFX1VTRVIgPSA0NCxcblxuICAvLyBOSVAtNDI6IEF1dGhlbnRpY2F0aW9uXG4gIEFVVEggPSAyMjI0MixcbiAgQVVUSF9SRVNQT05TRSA9IDIyMjQzXG59XG5cbi8qKiBCYXNlIGludGVyZmFjZSBmb3IgYWxsIE5vc3RyIGV2ZW50cyAqL1xuZXhwb3J0IGludGVyZmFjZSBCYXNlTm9zdHJFdmVudCB7XG4gIC8qKiBFdmVudCBraW5kIGFzIGRlZmluZWQgaW4gTklQcyAqL1xuICBraW5kOiBudW1iZXI7XG4gIC8qKiBDb250ZW50IG9mIHRoZSBldmVudCAqL1xuICBjb250ZW50OiBzdHJpbmc7XG4gIC8qKiBBcnJheSBvZiB0YWdzICovXG4gIHRhZ3M6IHN0cmluZ1tdW107XG4gIC8qKiBVbml4IHRpbWVzdGFtcCBpbiBzZWNvbmRzICovXG4gIGNyZWF0ZWRfYXQ6IG51bWJlcjtcbn1cblxuLyoqIEludGVyZmFjZSBmb3IgZXZlbnRzIHRoYXQgaGF2ZW4ndCBiZWVuIHNpZ25lZCB5ZXQgKi9cbmV4cG9ydCBpbnRlcmZhY2UgVW5zaWduZWROb3N0ckV2ZW50IGV4dGVuZHMgQmFzZU5vc3RyRXZlbnQge1xuICAvKiogT3B0aW9uYWwgcHVibGljIGtleSAqL1xuICBwdWJrZXk/OiBzdHJpbmc7XG59XG5cbi8qKiBJbnRlcmZhY2UgZm9yIHNpZ25lZCBldmVudHMgKi9cbmV4cG9ydCBpbnRlcmZhY2UgU2lnbmVkTm9zdHJFdmVudCBleHRlbmRzIEJhc2VOb3N0ckV2ZW50IHtcbiAgLyoqIFB1YmxpYyBrZXkgb2YgdGhlIGV2ZW50IGNyZWF0b3IgKi9cbiAgcHVia2V5OiBzdHJpbmc7XG4gIC8qKiBFdmVudCBJRCAoc2hhMjU2IG9mIHRoZSBzZXJpYWxpemVkIGV2ZW50KSAqL1xuICBpZDogc3RyaW5nO1xuICAvKiogU2Nobm9yciBzaWduYXR1cmUgb2YgdGhlIGV2ZW50IElEICovXG4gIHNpZzogc3RyaW5nO1xufVxuXG4vKiogQWxpYXMgZm9yIGJhY2t3YXJkIGNvbXBhdGliaWxpdHkgKi9cbmV4cG9ydCB0eXBlIE5vc3RyRXZlbnQgPSBTaWduZWROb3N0ckV2ZW50O1xuXG4vKiogVHlwZSBmb3IgY3JlYXRpbmcgbmV3IGV2ZW50cyAqL1xuZXhwb3J0IHR5cGUgVW5zaWduZWRFdmVudCA9IE9taXQ8Tm9zdHJFdmVudCwgJ2lkJyB8ICdzaWcnPjtcblxuLy8gRmlsdGVyIFR5cGVzXG5leHBvcnQgaW50ZXJmYWNlIE5vc3RyRmlsdGVyIHtcbiAgaWRzPzogc3RyaW5nW107XG4gIGF1dGhvcnM/OiBzdHJpbmdbXTtcbiAga2luZHM/OiBOb3N0ckV2ZW50S2luZFtdO1xuICBzaW5jZT86IG51bWJlcjtcbiAgdW50aWw/OiBudW1iZXI7XG4gIGxpbWl0PzogbnVtYmVyO1xuICAnI2UnPzogc3RyaW5nW107XG4gICcjcCc/OiBzdHJpbmdbXTtcbiAgc2VhcmNoPzogc3RyaW5nO1xuICAvKiogU3VwcG9ydCBmb3IgYXJiaXRyYXJ5IHRhZ3MgKE5JUC0xMikgKi9cbiAgW2tleTogYCMke3N0cmluZ31gXTogc3RyaW5nW10gfCB1bmRlZmluZWQ7XG59XG5cbmV4cG9ydCBpbnRlcmZhY2UgTm9zdHJTdWJzY3JpcHRpb24ge1xuICBpZDogc3RyaW5nO1xuICBmaWx0ZXJzOiBOb3N0ckZpbHRlcltdO1xufVxuXG4vLyBNZXNzYWdlIFR5cGVzXG5leHBvcnQgZW51bSBOb3N0ck1lc3NhZ2VUeXBlIHtcbiAgRVZFTlQgPSAnRVZFTlQnLFxuICBOT1RJQ0UgPSAnTk9USUNFJyxcbiAgT0sgPSAnT0snLFxuICBFT1NFID0gJ0VPU0UnLFxuICBSRVEgPSAnUkVRJyxcbiAgQ0xPU0UgPSAnQ0xPU0UnLFxuICBBVVRIID0gJ0FVVEgnXG59XG5cbmV4cG9ydCBpbnRlcmZhY2UgTm9zdHJNZXNzYWdlIHtcbiAgdHlwZTogTm9zdHJNZXNzYWdlVHlwZTtcbiAgZXZlbnQ/OiBTaWduZWROb3N0ckV2ZW50O1xuICBzdWJzY3JpcHRpb25JZD86IHN0cmluZztcbiAgZmlsdGVycz86IE5vc3RyRmlsdGVyW107XG4gIGV2ZW50SWQ/OiBzdHJpbmc7XG4gIGFjY2VwdGVkPzogYm9vbGVhbjtcbiAgbWVzc2FnZT86IHN0cmluZztcbiAgY291bnQ/OiBudW1iZXI7XG4gIHBheWxvYWQ/OiBzdHJpbmcgfCAoc3RyaW5nIHwgYm9vbGVhbilbXTsgIFxufVxuXG5leHBvcnQgaW50ZXJmYWNlIE5vc3RyUmVzcG9uc2Uge1xuICB0eXBlOiBOb3N0ck1lc3NhZ2VUeXBlO1xuICBldmVudD86IFNpZ25lZE5vc3RyRXZlbnQ7XG4gIHN1YnNjcmlwdGlvbklkPzogc3RyaW5nO1xuICBmaWx0ZXJzPzogTm9zdHJGaWx0ZXJbXTtcbiAgZXZlbnRJZD86IHN0cmluZztcbiAgYWNjZXB0ZWQ/OiBib29sZWFuO1xuICBtZXNzYWdlPzogc3RyaW5nO1xuICBjb3VudD86IG51bWJlcjtcbn1cblxuLy8gVXRpbGl0eSBUeXBlc1xuZXhwb3J0IGludGVyZmFjZSBWYWxpZGF0aW9uUmVzdWx0IHtcbiAgaXNWYWxpZDogYm9vbGVhbjtcbiAgZXJyb3I/OiBzdHJpbmc7XG59XG5cbmV4cG9ydCBpbnRlcmZhY2UgTm9zdHJFcnJvciB7XG4gIGNvZGU6IHN0cmluZztcbiAgbWVzc2FnZTogc3RyaW5nO1xuICBkZXRhaWxzPzogUmVjb3JkPHN0cmluZywgdW5rbm93bj47XG59XG4iLCAiLyoqXG4gKiBAbW9kdWxlIHR5cGVzL3Byb3RvY29sXG4gKiBAZGVzY3JpcHRpb24gTm9zdHIgcHJvdG9jb2wgdHlwZXNcbiAqL1xuXG5pbXBvcnQgdHlwZSB7IFxuICBOb3N0ckZpbHRlciwgXG4gIFB1YmxpY0tleSxcbiAgTm9zdHJNZXNzYWdlVHlwZSxcbiAgTm9zdHJTdWJzY3JpcHRpb24sXG4gIE5vc3RyUmVzcG9uc2UsXG4gIE5vc3RyRXJyb3Jcbn0gZnJvbSAnLi9iYXNlLmpzJztcblxuLy8gUmUtZXhwb3J0IHR5cGVzIGZyb20gYmFzZSB0aGF0IGFyZSB1c2VkIGluIHRoaXMgbW9kdWxlXG5leHBvcnQgdHlwZSB7IFxuICBOb3N0ckZpbHRlciwgXG4gIFB1YmxpY0tleSxcbiAgTm9zdHJNZXNzYWdlVHlwZSxcbiAgTm9zdHJTdWJzY3JpcHRpb24sXG4gIE5vc3RyUmVzcG9uc2UsXG4gIE5vc3RyRXJyb3Jcbn07XG4iLCAiZXhwb3J0IHt9O1xuLy8jIHNvdXJjZU1hcHBpbmdVUkw9bWVzc2FnZXMuanMubWFwIiwgIi8qKlxuICogQG1vZHVsZSB0eXBlcy9ndWFyZHNcbiAqIEBkZXNjcmlwdGlvbiBUeXBlIGd1YXJkIGZ1bmN0aW9ucyBmb3IgTm9zdHIgdHlwZXNcbiAqL1xuXG5pbXBvcnQgeyBOb3N0ckV2ZW50LCBTaWduZWROb3N0ckV2ZW50LCBOb3N0ckZpbHRlciwgTm9zdHJTdWJzY3JpcHRpb24sIE5vc3RyUmVzcG9uc2UsIE5vc3RyRXJyb3IgfSBmcm9tICcuL2Jhc2UnO1xuXG4vKipcbiAqIFR5cGUgZ3VhcmQgZm9yIE5vc3RyRXZlbnRcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGlzTm9zdHJFdmVudChldmVudDogdW5rbm93bik6IGV2ZW50IGlzIE5vc3RyRXZlbnQge1xuICBpZiAodHlwZW9mIGV2ZW50ICE9PSAnb2JqZWN0JyB8fCBldmVudCA9PT0gbnVsbCkge1xuICAgIHJldHVybiBmYWxzZTtcbiAgfVxuXG4gIGNvbnN0IHZhbGlkRXZlbnQgPSBldmVudCBhcyBSZWNvcmQ8c3RyaW5nLCB1bmtub3duPjtcblxuICAvLyBSZXF1aXJlZCBmaWVsZHNcbiAgaWYgKHR5cGVvZiB2YWxpZEV2ZW50LmtpbmQgIT09ICdudW1iZXInIHx8ICFOdW1iZXIuaXNJbnRlZ2VyKHZhbGlkRXZlbnQua2luZCkgfHwgdmFsaWRFdmVudC5raW5kIDwgMCkge1xuICAgIHJldHVybiBmYWxzZTtcbiAgfVxuXG4gIGlmICh0eXBlb2YgdmFsaWRFdmVudC5jb250ZW50ICE9PSAnc3RyaW5nJykge1xuICAgIHJldHVybiBmYWxzZTtcbiAgfVxuXG4gIGlmICh0eXBlb2YgdmFsaWRFdmVudC5jcmVhdGVkX2F0ICE9PSAnbnVtYmVyJyB8fCAhTnVtYmVyLmlzSW50ZWdlcih2YWxpZEV2ZW50LmNyZWF0ZWRfYXQpKSB7XG4gICAgcmV0dXJuIGZhbHNlO1xuICB9XG5cbiAgLy8gQ2hlY2sgcHVia2V5IHN0cnVjdHVyZVxuICBpZiAodmFsaWRFdmVudC5wdWJrZXkgIT09IHVuZGVmaW5lZCkge1xuICAgIGlmICh0eXBlb2YgdmFsaWRFdmVudC5wdWJrZXkgPT09ICdzdHJpbmcnKSB7XG4gICAgICBpZiAoIXZhbGlkRXZlbnQucHVia2V5KSB7XG4gICAgICAgIHJldHVybiBmYWxzZTtcbiAgICAgIH1cbiAgICB9IGVsc2UgaWYgKHR5cGVvZiB2YWxpZEV2ZW50LnB1YmtleSA9PT0gJ29iamVjdCcgJiYgdmFsaWRFdmVudC5wdWJrZXkgIT09IG51bGwpIHtcbiAgICAgIGNvbnN0IHB1YmtleSA9IHZhbGlkRXZlbnQucHVia2V5IGFzIFJlY29yZDxzdHJpbmcsIHVua25vd24+O1xuICAgICAgaWYgKHR5cGVvZiBwdWJrZXkuaGV4ICE9PSAnc3RyaW5nJyB8fCAhcHVia2V5LmhleCkge1xuICAgICAgICByZXR1cm4gZmFsc2U7XG4gICAgICB9XG4gICAgfSBlbHNlIHtcbiAgICAgIHJldHVybiBmYWxzZTtcbiAgICB9XG4gIH1cblxuICAvLyBDaGVjayB0YWdzIGFycmF5XG4gIGlmICghQXJyYXkuaXNBcnJheSh2YWxpZEV2ZW50LnRhZ3MpKSB7XG4gICAgcmV0dXJuIGZhbHNlO1xuICB9XG5cbiAgLy8gQ2hlY2sgdGFnIGFycmF5IGVsZW1lbnRzXG4gIGlmICghdmFsaWRFdmVudC50YWdzLmV2ZXJ5KHRhZyA9PiBBcnJheS5pc0FycmF5KHRhZykgJiYgdGFnLmV2ZXJ5KGl0ZW0gPT4gdHlwZW9mIGl0ZW0gPT09ICdzdHJpbmcnKSkpIHtcbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cblxuICByZXR1cm4gdHJ1ZTtcbn1cblxuLyoqXG4gKiBUeXBlIGd1YXJkIGZvciBTaWduZWROb3N0ckV2ZW50XG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBpc1NpZ25lZE5vc3RyRXZlbnQoZXZlbnQ6IHVua25vd24pOiBldmVudCBpcyBTaWduZWROb3N0ckV2ZW50IHtcbiAgaWYgKCFldmVudCB8fCB0eXBlb2YgZXZlbnQgIT09ICdvYmplY3QnKSB7XG4gICAgcmV0dXJuIGZhbHNlO1xuICB9XG5cbiAgY29uc3Qgc2lnbmVkRXZlbnQgPSBldmVudCBhcyBSZWNvcmQ8c3RyaW5nLCB1bmtub3duPjtcblxuICAvLyBDaGVjayByZXF1aXJlZCBmaWVsZHMgZnJvbSBOb3N0ckV2ZW50XG4gIGlmICghaXNOb3N0ckV2ZW50KGV2ZW50KSkge1xuICAgIHJldHVybiBmYWxzZTtcbiAgfVxuXG4gIC8vIENoZWNrIHB1YmtleSBpcyBwcmVzZW50IGFuZCB2YWxpZFxuICBpZiAodHlwZW9mIHNpZ25lZEV2ZW50LnB1YmtleSA9PT0gJ3N0cmluZycpIHtcbiAgICBpZiAoIXNpZ25lZEV2ZW50LnB1YmtleSkge1xuICAgICAgcmV0dXJuIGZhbHNlO1xuICAgIH1cbiAgfSBlbHNlIGlmICh0eXBlb2Ygc2lnbmVkRXZlbnQucHVia2V5ID09PSAnb2JqZWN0JyAmJiBzaWduZWRFdmVudC5wdWJrZXkgIT09IG51bGwpIHtcbiAgICBjb25zdCBwdWJrZXkgPSBzaWduZWRFdmVudC5wdWJrZXkgYXMgUmVjb3JkPHN0cmluZywgdW5rbm93bj47XG4gICAgaWYgKHR5cGVvZiBwdWJrZXkuaGV4ICE9PSAnc3RyaW5nJyB8fCAhcHVia2V5LmhleCkge1xuICAgICAgcmV0dXJuIGZhbHNlO1xuICAgIH1cbiAgfSBlbHNlIHtcbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cblxuICAvLyBDaGVjayBpZCBmaWVsZFxuICBpZiAodHlwZW9mIHNpZ25lZEV2ZW50LmlkICE9PSAnc3RyaW5nJyB8fCAhc2lnbmVkRXZlbnQuaWQpIHtcbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cblxuICAvLyBDaGVjayBzaWcgZmllbGRcbiAgaWYgKHR5cGVvZiBzaWduZWRFdmVudC5zaWcgIT09ICdzdHJpbmcnIHx8ICFzaWduZWRFdmVudC5zaWcpIHtcbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cblxuICByZXR1cm4gdHJ1ZTtcbn1cblxuLyoqXG4gKiBUeXBlIGd1YXJkIGZvciBOb3N0ckZpbHRlclxuICovXG5leHBvcnQgZnVuY3Rpb24gaXNOb3N0ckZpbHRlcihmaWx0ZXI6IHVua25vd24pOiBmaWx0ZXIgaXMgTm9zdHJGaWx0ZXIge1xuICBpZiAodHlwZW9mIGZpbHRlciAhPT0gJ29iamVjdCcgfHwgZmlsdGVyID09PSBudWxsKSB7XG4gICAgcmV0dXJuIGZhbHNlO1xuICB9XG5cbiAgY29uc3QgdmFsaWRGaWx0ZXIgPSBmaWx0ZXIgYXMgUmVjb3JkPHN0cmluZywgdW5rbm93bj47XG4gIGNvbnN0IHZhbGlkS2V5cyA9IFsnaWRzJywgJ2F1dGhvcnMnLCAna2luZHMnLCAnc2luY2UnLCAndW50aWwnLCAnbGltaXQnLCAnI2UnLCAnI3AnLCAnI3QnXTtcbiAgY29uc3QgZmlsdGVyS2V5cyA9IE9iamVjdC5rZXlzKHZhbGlkRmlsdGVyKTtcblxuICAvLyBDaGVjayBpZiBhbGwga2V5cyBpbiB0aGUgZmlsdGVyIGFyZSB2YWxpZFxuICBpZiAoIWZpbHRlcktleXMuZXZlcnkoa2V5ID0+IHZhbGlkS2V5cy5pbmNsdWRlcyhrZXkpKSkge1xuICAgIHJldHVybiBmYWxzZTtcbiAgfVxuXG4gIC8vIFZhbGlkYXRlIGFycmF5IGZpZWxkc1xuICBpZiAodmFsaWRGaWx0ZXIuaWRzICE9PSB1bmRlZmluZWQgJiYgKCFBcnJheS5pc0FycmF5KHZhbGlkRmlsdGVyLmlkcykgfHwgIXZhbGlkRmlsdGVyLmlkcy5ldmVyeShpZCA9PiB0eXBlb2YgaWQgPT09ICdzdHJpbmcnKSkpIHtcbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cbiAgaWYgKHZhbGlkRmlsdGVyLmF1dGhvcnMgIT09IHVuZGVmaW5lZCAmJiAoIUFycmF5LmlzQXJyYXkodmFsaWRGaWx0ZXIuYXV0aG9ycykgfHwgIXZhbGlkRmlsdGVyLmF1dGhvcnMuZXZlcnkoYXV0aG9yID0+IHR5cGVvZiBhdXRob3IgPT09ICdzdHJpbmcnKSkpIHtcbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cbiAgaWYgKHZhbGlkRmlsdGVyLmtpbmRzICE9PSB1bmRlZmluZWQgJiYgKCFBcnJheS5pc0FycmF5KHZhbGlkRmlsdGVyLmtpbmRzKSB8fCAhdmFsaWRGaWx0ZXIua2luZHMuZXZlcnkoa2luZCA9PiB0eXBlb2Yga2luZCA9PT0gJ251bWJlcicgJiYgTnVtYmVyLmlzSW50ZWdlcihraW5kKSAmJiBraW5kID49IDApKSkge1xuICAgIHJldHVybiBmYWxzZTtcbiAgfVxuICBpZiAodmFsaWRGaWx0ZXJbJyNlJ10gIT09IHVuZGVmaW5lZCAmJiAoIUFycmF5LmlzQXJyYXkodmFsaWRGaWx0ZXJbJyNlJ10pIHx8ICF2YWxpZEZpbHRlclsnI2UnXS5ldmVyeShlID0+IHR5cGVvZiBlID09PSAnc3RyaW5nJykpKSB7XG4gICAgcmV0dXJuIGZhbHNlO1xuICB9XG4gIGlmICh2YWxpZEZpbHRlclsnI3AnXSAhPT0gdW5kZWZpbmVkICYmICghQXJyYXkuaXNBcnJheSh2YWxpZEZpbHRlclsnI3AnXSkgfHwgIXZhbGlkRmlsdGVyWycjcCddLmV2ZXJ5KHAgPT4gdHlwZW9mIHAgPT09ICdzdHJpbmcnKSkpIHtcbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cbiAgaWYgKHZhbGlkRmlsdGVyWycjdCddICE9PSB1bmRlZmluZWQgJiYgKCFBcnJheS5pc0FycmF5KHZhbGlkRmlsdGVyWycjdCddKSB8fCAhdmFsaWRGaWx0ZXJbJyN0J10uZXZlcnkodCA9PiB0eXBlb2YgdCA9PT0gJ3N0cmluZycpKSkge1xuICAgIHJldHVybiBmYWxzZTtcbiAgfVxuXG4gIC8vIFZhbGlkYXRlIG51bWJlciBmaWVsZHNcbiAgaWYgKHZhbGlkRmlsdGVyLnNpbmNlICE9PSB1bmRlZmluZWQgJiYgdHlwZW9mIHZhbGlkRmlsdGVyLnNpbmNlICE9PSAnbnVtYmVyJykgcmV0dXJuIGZhbHNlO1xuICBpZiAodmFsaWRGaWx0ZXIudW50aWwgIT09IHVuZGVmaW5lZCAmJiB0eXBlb2YgdmFsaWRGaWx0ZXIudW50aWwgIT09ICdudW1iZXInKSByZXR1cm4gZmFsc2U7XG4gIGlmICh2YWxpZEZpbHRlci5saW1pdCAhPT0gdW5kZWZpbmVkICYmIHR5cGVvZiB2YWxpZEZpbHRlci5saW1pdCAhPT0gJ251bWJlcicpIHJldHVybiBmYWxzZTtcblxuICByZXR1cm4gdHJ1ZTtcbn1cblxuLyoqXG4gKiBUeXBlIGd1YXJkIGZvciBOb3N0clN1YnNjcmlwdGlvblxuICovXG5leHBvcnQgZnVuY3Rpb24gaXNOb3N0clN1YnNjcmlwdGlvbihzdWI6IHVua25vd24pOiBzdWIgaXMgTm9zdHJTdWJzY3JpcHRpb24ge1xuICBpZiAodHlwZW9mIHN1YiAhPT0gJ29iamVjdCcgfHwgc3ViID09PSBudWxsKSB7XG4gICAgcmV0dXJuIGZhbHNlO1xuICB9XG5cbiAgY29uc3QgdmFsaWRTdWIgPSBzdWIgYXMgUmVjb3JkPHN0cmluZywgdW5rbm93bj47XG5cbiAgaWYgKHR5cGVvZiB2YWxpZFN1Yi5pZCAhPT0gJ3N0cmluZycpIHtcbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cblxuICBpZiAoIUFycmF5LmlzQXJyYXkodmFsaWRTdWIuZmlsdGVycykpIHtcbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cblxuICBpZiAoIXZhbGlkU3ViLmZpbHRlcnMuZXZlcnkoZmlsdGVyID0+IGlzTm9zdHJGaWx0ZXIoZmlsdGVyKSkpIHtcbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cblxuICByZXR1cm4gdHJ1ZTtcbn1cblxuLyoqXG4gKiBUeXBlIGd1YXJkIGZvciBOb3N0clJlc3BvbnNlXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBpc05vc3RyUmVzcG9uc2UocmVzcG9uc2U6IHVua25vd24pOiByZXNwb25zZSBpcyBOb3N0clJlc3BvbnNlIHtcbiAgaWYgKHR5cGVvZiByZXNwb25zZSAhPT0gJ29iamVjdCcgfHwgcmVzcG9uc2UgPT09IG51bGwpIHtcbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cblxuICBjb25zdCB2YWxpZFJlc3BvbnNlID0gcmVzcG9uc2UgYXMgUmVjb3JkPHN0cmluZywgdW5rbm93bj47XG5cbiAgaWYgKHR5cGVvZiB2YWxpZFJlc3BvbnNlLnR5cGUgIT09ICdzdHJpbmcnKSB7XG4gICAgcmV0dXJuIGZhbHNlO1xuICB9XG5cbiAgaWYgKHZhbGlkUmVzcG9uc2Uuc3Vic2NyaXB0aW9uSWQgIT09IHVuZGVmaW5lZCAmJiB0eXBlb2YgdmFsaWRSZXNwb25zZS5zdWJzY3JpcHRpb25JZCAhPT0gJ3N0cmluZycpIHtcbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cblxuICBpZiAodmFsaWRSZXNwb25zZS5ldmVudCAhPT0gdW5kZWZpbmVkICYmICFpc1NpZ25lZE5vc3RyRXZlbnQodmFsaWRSZXNwb25zZS5ldmVudCkpIHtcbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cblxuICBpZiAodmFsaWRSZXNwb25zZS5tZXNzYWdlICE9PSB1bmRlZmluZWQgJiYgdHlwZW9mIHZhbGlkUmVzcG9uc2UubWVzc2FnZSAhPT0gJ3N0cmluZycpIHtcbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cblxuICByZXR1cm4gdHJ1ZTtcbn1cblxuLyoqXG4gKiBUeXBlIGd1YXJkIGZvciBOb3N0ckVycm9yXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBpc05vc3RyRXJyb3IoZXJyb3I6IHVua25vd24pOiBlcnJvciBpcyBOb3N0ckVycm9yIHtcbiAgaWYgKHR5cGVvZiBlcnJvciAhPT0gJ29iamVjdCcgfHwgZXJyb3IgPT09IG51bGwpIHtcbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cblxuICBjb25zdCB2YWxpZEVycm9yID0gZXJyb3IgYXMgUmVjb3JkPHN0cmluZywgdW5rbm93bj47XG5cbiAgcmV0dXJuIChcbiAgICB0eXBlb2YgdmFsaWRFcnJvci50eXBlID09PSAnc3RyaW5nJyAmJlxuICAgIHR5cGVvZiB2YWxpZEVycm9yLm1lc3NhZ2UgPT09ICdzdHJpbmcnXG4gICk7XG59XG4iLCAiLyoqXG4gKiBAbW9kdWxlIHR5cGVzL25pcDQ2XG4gKiBAZGVzY3JpcHRpb24gVHlwZSBkZWZpbml0aW9ucyBmb3IgTklQLTQ2IChOb3N0ciBDb25uZWN0IC8gUmVtb3RlIFNpZ25pbmcpXG4gKiBAc2VlIGh0dHBzOi8vZ2l0aHViLmNvbS9ub3N0ci1wcm90b2NvbC9uaXBzL2Jsb2IvbWFzdGVyLzQ2Lm1kXG4gKi9cblxuLyoqXG4gKiBOSVAtNDYgcmVtb3RlIHNpZ25pbmcgbWV0aG9kc1xuICovXG5leHBvcnQgZW51bSBOaXA0Nk1ldGhvZCB7XG4gIENPTk5FQ1QgPSAnY29ubmVjdCcsXG4gIFBJTkcgPSAncGluZycsXG4gIEdFVF9QVUJMSUNfS0VZID0gJ2dldF9wdWJsaWNfa2V5JyxcbiAgU0lHTl9FVkVOVCA9ICdzaWduX2V2ZW50JyxcbiAgTklQMDRfRU5DUllQVCA9ICduaXAwNF9lbmNyeXB0JyxcbiAgTklQMDRfREVDUllQVCA9ICduaXAwNF9kZWNyeXB0JyxcbiAgTklQNDRfRU5DUllQVCA9ICduaXA0NF9lbmNyeXB0JyxcbiAgTklQNDRfREVDUllQVCA9ICduaXA0NF9kZWNyeXB0JyxcbiAgR0VUX1JFTEFZUyA9ICdnZXRfcmVsYXlzJyxcbn1cblxuLyoqXG4gKiBQYXJzZWQgYnVua2VyOi8vIFVSSVxuICovXG5leHBvcnQgaW50ZXJmYWNlIEJ1bmtlclVSSSB7XG4gIC8qKiBSZW1vdGUgc2lnbmVyJ3MgcHVibGljIGtleSAoaGV4KSAqL1xuICByZW1vdGVQdWJrZXk6IHN0cmluZztcbiAgLyoqIFJlbGF5IFVSTHMgZm9yIGNvbW11bmljYXRpb24gKi9cbiAgcmVsYXlzOiBzdHJpbmdbXTtcbiAgLyoqIE9wdGlvbmFsIHNlY3JldCBmb3IgaW5pdGlhbCBjb25uZWN0aW9uICovXG4gIHNlY3JldD86IHN0cmluZztcbn1cblxuLyoqXG4gKiBOSVAtNDYgSlNPTi1SUEMgcmVxdWVzdCAoY2xpZW50IC0+IHNpZ25lcilcbiAqL1xuZXhwb3J0IGludGVyZmFjZSBOaXA0NlJlcXVlc3Qge1xuICBpZDogc3RyaW5nO1xuICBtZXRob2Q6IE5pcDQ2TWV0aG9kIHwgc3RyaW5nO1xuICBwYXJhbXM6IHN0cmluZ1tdO1xufVxuXG4vKipcbiAqIE5JUC00NiBKU09OLVJQQyByZXNwb25zZSAoc2lnbmVyIC0+IGNsaWVudClcbiAqL1xuZXhwb3J0IGludGVyZmFjZSBOaXA0NlJlc3BvbnNlIHtcbiAgaWQ6IHN0cmluZztcbiAgcmVzdWx0Pzogc3RyaW5nO1xuICBlcnJvcj86IHN0cmluZztcbn1cblxuLyoqXG4gKiBBIE5JUC00NiBzZXNzaW9uIGNvbnRhaW5pbmcgdGhlIGVwaGVtZXJhbCBrZXlwYWlyIGFuZCBjb252ZXJzYXRpb24ga2V5XG4gKi9cbmV4cG9ydCBpbnRlcmZhY2UgTmlwNDZTZXNzaW9uIHtcbiAgLyoqIENsaWVudCdzIGVwaGVtZXJhbCBwcml2YXRlIGtleSAoaGV4KSAqL1xuICBjbGllbnRTZWNyZXRLZXk6IHN0cmluZztcbiAgLyoqIENsaWVudCdzIGVwaGVtZXJhbCBwdWJsaWMga2V5IChoZXgpICovXG4gIGNsaWVudFB1YmtleTogc3RyaW5nO1xuICAvKiogUmVtb3RlIHNpZ25lcidzIHB1YmxpYyBrZXkgKGhleCkgKi9cbiAgcmVtb3RlUHVia2V5OiBzdHJpbmc7XG4gIC8qKiBOSVAtNDQgY29udmVyc2F0aW9uIGtleSAoZGVyaXZlZCBmcm9tIEVDREgpICovXG4gIGNvbnZlcnNhdGlvbktleTogVWludDhBcnJheTtcbn1cblxuLyoqXG4gKiBQdWJsaWMgc2Vzc2lvbiBpbmZvIChzYWZlIHRvIGV4cG9zZTsgZXhjbHVkZXMgcHJpdmF0ZSBrZXkgYW5kIGNvbnZlcnNhdGlvbiBrZXkpXG4gKi9cbmV4cG9ydCBpbnRlcmZhY2UgTmlwNDZTZXNzaW9uSW5mbyB7XG4gIGNsaWVudFB1YmtleTogc3RyaW5nO1xuICByZW1vdGVQdWJrZXk6IHN0cmluZztcbn1cblxuLyoqXG4gKiBSZXN1bHQgb2YgdmFsaWRhdGluZyBhIGJ1bmtlcjovLyBVUklcbiAqL1xuZXhwb3J0IGludGVyZmFjZSBCdW5rZXJWYWxpZGF0aW9uUmVzdWx0IHtcbiAgaXNWYWxpZDogYm9vbGVhbjtcbiAgZXJyb3I/OiBzdHJpbmc7XG4gIHVyaT86IEJ1bmtlclVSSTtcbn1cbiIsICIvKipcbiAqIEBtb2R1bGUgY3J5cHRvXG4gKiBAZGVzY3JpcHRpb24gQ3J5cHRvZ3JhcGhpYyB1dGlsaXRpZXMgZm9yIE5vc3RyXG4gKiBcbiAqIElNUE9SVEFOVDogTm9zdHIgUHJvdG9jb2wgQ3J5cHRvZ3JhcGhpYyBSZXF1aXJlbWVudHNcbiAqIFdoaWxlIHNlY3AyNTZrMSBpcyB0aGUgdW5kZXJseWluZyBlbGxpcHRpYyBjdXJ2ZSB1c2VkIGJ5IE5vc3RyLCB0aGUgcHJvdG9jb2wgc3BlY2lmaWNhbGx5XG4gKiByZXF1aXJlcyBzY2hub3JyIHNpZ25hdHVyZXMgYXMgZGVmaW5lZCBpbiBOSVAtMDEuIFRoaXMgbWVhbnM6XG4gKiBcbiAqIDEuIEFsd2F5cyB1c2Ugc2Nobm9yci1zcGVjaWZpYyBmdW5jdGlvbnM6XG4gKiAgICAtIHNjaG5vcnIuZ2V0UHVibGljS2V5KCkgZm9yIHB1YmxpYyBrZXkgZ2VuZXJhdGlvblxuICogICAgLSBzY2hub3JyLnNpZ24oKSBmb3Igc2lnbmluZ1xuICogICAgLSBzY2hub3JyLnZlcmlmeSgpIGZvciB2ZXJpZmljYXRpb25cbiAqIFxuICogMi4gQXZvaWQgdXNpbmcgc2VjcDI1NmsxIGZ1bmN0aW9ucyBkaXJlY3RseTpcbiAqICAgIC0gRE9OJ1QgdXNlIHNlY3AyNTZrMS5nZXRQdWJsaWNLZXkoKVxuICogICAgLSBET04nVCB1c2Ugc2VjcDI1NmsxLnNpZ24oKVxuICogICAgLSBET04nVCB1c2Ugc2VjcDI1NmsxLnZlcmlmeSgpXG4gKiBcbiAqIFdoaWxlIGJvdGggbWlnaHQgd29yayBpbiBzb21lIGNhc2VzIChhcyB0aGV5IHVzZSB0aGUgc2FtZSBjdXJ2ZSksIHRoZSBzY2hub3JyIHNpZ25hdHVyZVxuICogc2NoZW1lIGhhcyBzcGVjaWZpYyByZXF1aXJlbWVudHMgZm9yIGtleSBhbmQgc2lnbmF0dXJlIGZvcm1hdHMgdGhhdCBhcmVuJ3QgZ3VhcmFudGVlZFxuICogd2hlbiB1c2luZyB0aGUgbG93ZXItbGV2ZWwgc2VjcDI1NmsxIGZ1bmN0aW9ucyBkaXJlY3RseS5cbiAqL1xuXG5pbXBvcnQgeyBzY2hub3JyLCBzZWNwMjU2azEgfSBmcm9tICdAbm9ibGUvY3VydmVzL3NlY3AyNTZrMS5qcyc7XG5pbXBvcnQgeyBieXRlc1RvSGV4LCBoZXhUb0J5dGVzLCByYW5kb21CeXRlcyB9IGZyb20gJ0Bub2JsZS9oYXNoZXMvdXRpbHMuanMnO1xuaW1wb3J0IHsgc2hhMjU2IH0gZnJvbSAnQG5vYmxlL2hhc2hlcy9zaGEyLmpzJztcbmltcG9ydCB7IEtleVBhaXIsIFB1YmxpY0tleURldGFpbHMsIE5vc3RyRXZlbnQsIFNpZ25lZE5vc3RyRXZlbnQsIFB1YmxpY0tleSB9IGZyb20gJy4vdHlwZXMvaW5kZXgnO1xuaW1wb3J0IHsgbG9nZ2VyIH0gZnJvbSAnLi91dGlscy9sb2dnZXInO1xuaW1wb3J0IHsgYnl0ZXNUb0Jhc2U2NCwgYmFzZTY0VG9CeXRlcyB9IGZyb20gJy4vZW5jb2RpbmcvYmFzZTY0JztcblxuXG4vKipcbiAqIEN1c3RvbSBjcnlwdG8gaW50ZXJmYWNlIGZvciBjcm9zcy1wbGF0Zm9ybSBjb21wYXRpYmlsaXR5XG4gKi9cbmV4cG9ydCBpbnRlcmZhY2UgQ3J5cHRvU3VidGxlIHtcbiAgc3VidGxlOiB7XG4gICAgZ2VuZXJhdGVLZXkoXG4gICAgICBhbGdvcml0aG06IFJzYUhhc2hlZEtleUdlblBhcmFtcyB8IEVjS2V5R2VuUGFyYW1zLFxuICAgICAgZXh0cmFjdGFibGU6IGJvb2xlYW4sXG4gICAgICBrZXlVc2FnZXM6IHJlYWRvbmx5IEtleVVzYWdlW11cbiAgICApOiBQcm9taXNlPENyeXB0b0tleVBhaXI+O1xuICAgIGltcG9ydEtleShcbiAgICAgIGZvcm1hdDogJ3JhdycgfCAncGtjczgnIHwgJ3Nwa2knLFxuICAgICAga2V5RGF0YTogQXJyYXlCdWZmZXIsXG4gICAgICBhbGdvcml0aG06IFJzYUhhc2hlZEltcG9ydFBhcmFtcyB8IEVjS2V5SW1wb3J0UGFyYW1zIHwgQWVzS2V5QWxnb3JpdGhtLFxuICAgICAgZXh0cmFjdGFibGU6IGJvb2xlYW4sXG4gICAgICBrZXlVc2FnZXM6IHJlYWRvbmx5IEtleVVzYWdlW11cbiAgICApOiBQcm9taXNlPENyeXB0b0tleT47XG4gICAgZW5jcnlwdChcbiAgICAgIGFsZ29yaXRobTogeyBuYW1lOiBzdHJpbmc7IGl2OiBVaW50OEFycmF5IH0sXG4gICAgICBrZXk6IENyeXB0b0tleSxcbiAgICAgIGRhdGE6IEFycmF5QnVmZmVyXG4gICAgKTogUHJvbWlzZTxBcnJheUJ1ZmZlcj47XG4gICAgZGVjcnlwdChcbiAgICAgIGFsZ29yaXRobTogeyBuYW1lOiBzdHJpbmc7IGl2OiBVaW50OEFycmF5IH0sXG4gICAgICBrZXk6IENyeXB0b0tleSxcbiAgICAgIGRhdGE6IEFycmF5QnVmZmVyXG4gICAgKTogUHJvbWlzZTxBcnJheUJ1ZmZlcj47XG4gIH07XG4gIGdldFJhbmRvbVZhbHVlczxUIGV4dGVuZHMgVWludDhBcnJheSB8IEludDhBcnJheSB8IFVpbnQxNkFycmF5IHwgSW50MTZBcnJheSB8IFVpbnQzMkFycmF5IHwgSW50MzJBcnJheT4oYXJyYXk6IFQpOiBUO1xufVxuXG5kZWNsYXJlIGdsb2JhbCB7XG4gIGludGVyZmFjZSBXaW5kb3cge1xuICAgIGNyeXB0bzogQ3J5cHRvU3VidGxlO1xuICB9XG4gIGludGVyZmFjZSBHbG9iYWwge1xuICAgIGNyeXB0bzogQ3J5cHRvU3VidGxlO1xuICB9XG59XG5cbi8vIEdldCB0aGUgYXBwcm9wcmlhdGUgY3J5cHRvIGltcGxlbWVudGF0aW9uXG5jb25zdCBnZXRDcnlwdG8gPSBhc3luYyAoKTogUHJvbWlzZTxDcnlwdG9TdWJ0bGU+ID0+IHtcbiAgaWYgKHR5cGVvZiB3aW5kb3cgIT09ICd1bmRlZmluZWQnICYmIHdpbmRvdy5jcnlwdG8pIHtcbiAgICByZXR1cm4gd2luZG93LmNyeXB0bztcbiAgfVxuICBpZiAodHlwZW9mIGdsb2JhbCAhPT0gJ3VuZGVmaW5lZCcgJiYgKGdsb2JhbCBhcyBHbG9iYWwpLmNyeXB0bykge1xuICAgIHJldHVybiAoZ2xvYmFsIGFzIEdsb2JhbCkuY3J5cHRvO1xuICB9XG4gIHRyeSB7XG4gICAgY29uc3QgY3J5cHRvTW9kdWxlID0gYXdhaXQgaW1wb3J0KCdjcnlwdG8nKTtcbiAgICBpZiAoY3J5cHRvTW9kdWxlLndlYmNyeXB0bykge1xuICAgICAgcmV0dXJuIGNyeXB0b01vZHVsZS53ZWJjcnlwdG8gYXMgQ3J5cHRvU3VidGxlO1xuICAgIH1cbiAgfSBjYXRjaCB7XG4gICAgbG9nZ2VyLmRlYnVnKCdOb2RlIGNyeXB0byBub3QgYXZhaWxhYmxlJyk7XG4gIH1cblxuICB0aHJvdyBuZXcgRXJyb3IoJ05vIFdlYkNyeXB0byBpbXBsZW1lbnRhdGlvbiBhdmFpbGFibGUnKTtcbn07XG5cbi8qKlxuICogQ3J5cHRvIGltcGxlbWVudGF0aW9uIHRoYXQgd29ya3MgaW4gYm90aCBOb2RlLmpzIGFuZCBicm93c2VyIGVudmlyb25tZW50c1xuICovXG5jbGFzcyBDdXN0b21DcnlwdG8ge1xuICBwcml2YXRlIGNyeXB0b0luc3RhbmNlOiBDcnlwdG9TdWJ0bGUgfCBudWxsID0gbnVsbDtcbiAgcHJpdmF0ZSBpbml0UHJvbWlzZTogUHJvbWlzZTx2b2lkPjtcblxuICBjb25zdHJ1Y3RvcigpIHtcbiAgICB0aGlzLmluaXRQcm9taXNlID0gdGhpcy5pbml0aWFsaXplKCk7XG4gIH1cblxuICBwcml2YXRlIGFzeW5jIGluaXRpYWxpemUoKTogUHJvbWlzZTx2b2lkPiB7XG4gICAgdGhpcy5jcnlwdG9JbnN0YW5jZSA9IGF3YWl0IGdldENyeXB0bygpO1xuICB9XG5cbiAgcHJpdmF0ZSBhc3luYyBlbnN1cmVJbml0aWFsaXplZCgpOiBQcm9taXNlPENyeXB0b1N1YnRsZT4ge1xuICAgIGF3YWl0IHRoaXMuaW5pdFByb21pc2U7XG4gICAgaWYgKCF0aGlzLmNyeXB0b0luc3RhbmNlKSB7XG4gICAgICB0aHJvdyBuZXcgRXJyb3IoJ0NyeXB0byBpbXBsZW1lbnRhdGlvbiBub3QgaW5pdGlhbGl6ZWQnKTtcbiAgICB9XG4gICAgcmV0dXJuIHRoaXMuY3J5cHRvSW5zdGFuY2U7XG4gIH1cblxuICBhc3luYyBnZXRTdWJ0bGUoKTogUHJvbWlzZTxDcnlwdG9TdWJ0bGVbJ3N1YnRsZSddPiB7XG4gICAgY29uc3QgY3J5cHRvID0gYXdhaXQgdGhpcy5lbnN1cmVJbml0aWFsaXplZCgpO1xuICAgIHJldHVybiBjcnlwdG8uc3VidGxlO1xuICB9XG5cbiAgYXN5bmMgZ2V0UmFuZG9tVmFsdWVzPFQgZXh0ZW5kcyBVaW50OEFycmF5IHwgSW50OEFycmF5IHwgVWludDE2QXJyYXkgfCBJbnQxNkFycmF5IHwgVWludDMyQXJyYXkgfCBJbnQzMkFycmF5PihhcnJheTogVCk6IFByb21pc2U8VD4ge1xuICAgIGNvbnN0IGNyeXB0byA9IGF3YWl0IHRoaXMuZW5zdXJlSW5pdGlhbGl6ZWQoKTtcbiAgICByZXR1cm4gY3J5cHRvLmdldFJhbmRvbVZhbHVlcyhhcnJheSk7XG4gIH1cbn1cblxuLy8gQ3JlYXRlIGFuZCBleHBvcnQgZGVmYXVsdCBpbnN0YW5jZVxuZXhwb3J0IGNvbnN0IGN1c3RvbUNyeXB0byA9IG5ldyBDdXN0b21DcnlwdG8oKTtcblxuLy8gRXhwb3J0IHNjaG5vcnIgZnVuY3Rpb25zXG5leHBvcnQgY29uc3Qgc2lnblNjaG5vcnIgPSBzY2hub3JyLnNpZ247XG5leHBvcnQgY29uc3QgdmVyaWZ5U2Nobm9yclNpZ25hdHVyZSA9IHNjaG5vcnIudmVyaWZ5O1xuXG4vKipcbiAqIEdldHMgdGhlIGNvbXByZXNzZWQgcHVibGljIGtleSAoMzMgYnl0ZXMgd2l0aCBwcmVmaXgpXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBnZXRDb21wcmVzc2VkUHVibGljS2V5KHByaXZhdGVLZXlCeXRlczogVWludDhBcnJheSk6IFVpbnQ4QXJyYXkge1xuICByZXR1cm4gc2VjcDI1NmsxLmdldFB1YmxpY0tleShwcml2YXRlS2V5Qnl0ZXMsIHRydWUpO1xufVxuXG4vKipcbiAqIEdldHMgdGhlIHNjaG5vcnIgcHVibGljIGtleSAoMzIgYnl0ZXMgeC1jb29yZGluYXRlKSBhcyBwZXIgQklQMzQwXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBnZXRTY2hub3JyUHVibGljS2V5KHByaXZhdGVLZXlCeXRlczogVWludDhBcnJheSk6IFVpbnQ4QXJyYXkge1xuICByZXR1cm4gc2Nobm9yci5nZXRQdWJsaWNLZXkocHJpdmF0ZUtleUJ5dGVzKTtcbn1cblxuLyoqXG4gKiBHZW5lcmF0ZXMgYSBuZXcga2V5IHBhaXJcbiAqL1xuZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIGdlbmVyYXRlS2V5UGFpcigpOiBQcm9taXNlPEtleVBhaXI+IHtcbiAgY29uc3QgcHJpdmF0ZUtleUJ5dGVzID0gcmFuZG9tQnl0ZXMoMzIpO1xuICBjb25zdCBwcml2YXRlS2V5ID0gYnl0ZXNUb0hleChwcml2YXRlS2V5Qnl0ZXMpO1xuICBwcml2YXRlS2V5Qnl0ZXMuZmlsbCgwKTsgLy8gemVybyBzb3VyY2UgbWF0ZXJpYWxcbiAgY29uc3QgcHVibGljS2V5ID0gYXdhaXQgZ2V0UHVibGljS2V5KHByaXZhdGVLZXkpO1xuXG4gIHJldHVybiB7XG4gICAgcHJpdmF0ZUtleSxcbiAgICBwdWJsaWNLZXlcbiAgfTtcbn1cblxuLyoqXG4gKiBHZXRzIGEgcHVibGljIGtleSBmcm9tIGEgcHJpdmF0ZSBrZXlcbiAqL1xuZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIGdldFB1YmxpY0tleShwcml2YXRlS2V5OiBzdHJpbmcpOiBQcm9taXNlPFB1YmxpY0tleURldGFpbHM+IHtcbiAgdHJ5IHtcbiAgICBjb25zdCBwcml2YXRlS2V5Qnl0ZXMgPSBoZXhUb0J5dGVzKHByaXZhdGVLZXkpO1xuICAgIGNvbnN0IHB1YmxpY0tleUJ5dGVzID0gc2Nobm9yci5nZXRQdWJsaWNLZXkocHJpdmF0ZUtleUJ5dGVzKTtcbiAgICByZXR1cm4ge1xuICAgICAgaGV4OiBieXRlc1RvSGV4KHB1YmxpY0tleUJ5dGVzKSxcbiAgICAgIGJ5dGVzOiBwdWJsaWNLZXlCeXRlc1xuICAgIH07XG4gIH0gY2F0Y2ggKGVycm9yKSB7XG4gICAgbG9nZ2VyLmVycm9yKHsgZXJyb3IgfSwgJ0ZhaWxlZCB0byBnZXQgcHVibGljIGtleScpO1xuICAgIHRocm93IGVycm9yO1xuICB9XG59XG5cbi8qKlxuICogVmFsaWRhdGVzIGEga2V5IHBhaXJcbiAqL1xuZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIHZhbGlkYXRlS2V5UGFpcihrZXlQYWlyOiBLZXlQYWlyKTogUHJvbWlzZTxib29sZWFuPiB7XG4gIHRyeSB7XG4gICAgY29uc3QgZGVyaXZlZFB1YktleSA9IGF3YWl0IGdldFB1YmxpY0tleShrZXlQYWlyLnByaXZhdGVLZXkpO1xuICAgIHJldHVybiBkZXJpdmVkUHViS2V5LmhleCA9PT0ga2V5UGFpci5wdWJsaWNLZXkuaGV4O1xuICB9IGNhdGNoIChlcnJvcikge1xuICAgIGxvZ2dlci5lcnJvcih7IGVycm9yIH0sICdGYWlsZWQgdG8gdmFsaWRhdGUga2V5IHBhaXInKTtcbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cbn1cblxuLyoqXG4gKiBDcmVhdGVzIGEgbmV3IGV2ZW50XG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBjcmVhdGVFdmVudChldmVudDogUGFydGlhbDxOb3N0ckV2ZW50Pik6IE5vc3RyRXZlbnQge1xuICBjb25zdCB0aW1lc3RhbXAgPSBNYXRoLmZsb29yKERhdGUubm93KCkgLyAxMDAwKTtcblxuICByZXR1cm4ge1xuICAgIC4uLmV2ZW50LFxuICAgIGNyZWF0ZWRfYXQ6IGV2ZW50LmNyZWF0ZWRfYXQgfHwgdGltZXN0YW1wLFxuICAgIHRhZ3M6IGV2ZW50LnRhZ3MgfHwgW10sXG4gICAgY29udGVudDogZXZlbnQuY29udGVudCB8fCAnJyxcbiAgICBraW5kOiBldmVudC5raW5kIHx8IDFcbiAgfSBhcyBOb3N0ckV2ZW50O1xufVxuXG4vKipcbiAqIE5vcm1hbGl6ZSBhIHByaXZhdGUga2V5IHRvIGhleCBzdHJpbmcgKGFjY2VwdHMgYm90aCBoZXggc3RyaW5nIGFuZCBVaW50OEFycmF5KVxuICovXG5mdW5jdGlvbiBub3JtYWxpemVQcml2YXRlS2V5KHByaXZhdGVLZXk6IHN0cmluZyB8IFVpbnQ4QXJyYXkpOiBzdHJpbmcge1xuICBpZiAocHJpdmF0ZUtleSBpbnN0YW5jZW9mIFVpbnQ4QXJyYXkpIHtcbiAgICByZXR1cm4gYnl0ZXNUb0hleChwcml2YXRlS2V5KTtcbiAgfVxuICByZXR1cm4gcHJpdmF0ZUtleTtcbn1cblxuLyoqXG4gKiBTaWducyBhbiBldmVudFxuICogQHBhcmFtIGV2ZW50IC0gRXZlbnQgdG8gc2lnblxuICogQHBhcmFtIHByaXZhdGVLZXkgLSBQcml2YXRlIGtleSBhcyBoZXggc3RyaW5nIG9yIFVpbnQ4QXJyYXlcbiAqL1xuZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIHNpZ25FdmVudChldmVudDogTm9zdHJFdmVudCwgcHJpdmF0ZUtleTogc3RyaW5nIHwgVWludDhBcnJheSk6IFByb21pc2U8U2lnbmVkTm9zdHJFdmVudD4ge1xuICB0cnkge1xuICAgIGNvbnN0IHByaXZhdGVLZXlIZXggPSBub3JtYWxpemVQcml2YXRlS2V5KHByaXZhdGVLZXkpO1xuXG4gICAgLy8gU2VyaWFsaXplIGV2ZW50IGZvciBzaWduaW5nIChOSVAtMDEgZm9ybWF0KVxuICAgIGNvbnN0IHNlcmlhbGl6ZWQgPSBKU09OLnN0cmluZ2lmeShbXG4gICAgICAwLFxuICAgICAgZXZlbnQucHVia2V5LFxuICAgICAgZXZlbnQuY3JlYXRlZF9hdCxcbiAgICAgIGV2ZW50LmtpbmQsXG4gICAgICBldmVudC50YWdzLFxuICAgICAgZXZlbnQuY29udGVudFxuICAgIF0pO1xuXG4gICAgLy8gQ2FsY3VsYXRlIGV2ZW50IGhhc2hcbiAgICBjb25zdCBldmVudEhhc2ggPSBzaGEyNTYobmV3IFRleHRFbmNvZGVyKCkuZW5jb2RlKHNlcmlhbGl6ZWQpKTtcblxuICAgIC8vIENvbnZlcnQgcHJpdmF0ZSBrZXkgdG8gYnl0ZXMgYW5kIHNpZ25cbiAgICBjb25zdCBwcml2YXRlS2V5Qnl0ZXMgPSBoZXhUb0J5dGVzKHByaXZhdGVLZXlIZXgpO1xuICAgIGNvbnN0IHNpZ25hdHVyZUJ5dGVzID0gc2Nobm9yci5zaWduKGV2ZW50SGFzaCwgcHJpdmF0ZUtleUJ5dGVzKTtcblxuICAgIC8vIENyZWF0ZSBzaWduZWQgZXZlbnRcbiAgICByZXR1cm4ge1xuICAgICAgLi4uZXZlbnQsXG4gICAgICBpZDogYnl0ZXNUb0hleChldmVudEhhc2gpLFxuICAgICAgc2lnOiBieXRlc1RvSGV4KHNpZ25hdHVyZUJ5dGVzKVxuICAgIH07XG4gIH0gY2F0Y2ggKGVycm9yKSB7XG4gICAgbG9nZ2VyLmVycm9yKHsgZXJyb3IgfSwgJ0ZhaWxlZCB0byBzaWduIGV2ZW50Jyk7XG4gICAgdGhyb3cgZXJyb3I7XG4gIH1cbn1cblxuLyoqXG4gKiBHZXRzIGEgcHVibGljIGtleSBoZXggc3RyaW5nIGZyb20gYSBwcml2YXRlIGtleSAoc3luY2hyb25vdXMpXG4gKiBAcGFyYW0gcHJpdmF0ZUtleSAtIFByaXZhdGUga2V5IGFzIGhleCBzdHJpbmcgb3IgVWludDhBcnJheVxuICogQHJldHVybnMgSGV4LWVuY29kZWQgcHVibGljIGtleSAoMzItYnl0ZSB4LW9ubHkgc2Nobm9yciBrZXkpXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBnZXRQdWJsaWNLZXlTeW5jKHByaXZhdGVLZXk6IHN0cmluZyB8IFVpbnQ4QXJyYXkpOiBzdHJpbmcge1xuICBjb25zdCBwcml2YXRlS2V5Qnl0ZXMgPSBwcml2YXRlS2V5IGluc3RhbmNlb2YgVWludDhBcnJheVxuICAgID8gcHJpdmF0ZUtleVxuICAgIDogaGV4VG9CeXRlcyhwcml2YXRlS2V5KTtcbiAgY29uc3QgcHVibGljS2V5Qnl0ZXMgPSBzY2hub3JyLmdldFB1YmxpY0tleShwcml2YXRlS2V5Qnl0ZXMpO1xuICByZXR1cm4gYnl0ZXNUb0hleChwdWJsaWNLZXlCeXRlcyk7XG59XG5cbi8qKlxuICogQ3JlYXRlcywgaGFzaGVzLCBhbmQgc2lnbnMgYSBOb3N0ciBldmVudCBpbiBvbmUgc3RlcFxuICogQHBhcmFtIGV2ZW50IC0gUGFydGlhbCBldmVudCAoa2luZCwgY29udGVudCwgdGFncyByZXF1aXJlZDsgcHVia2V5IGRlcml2ZWQgaWYgbWlzc2luZylcbiAqIEBwYXJhbSBwcml2YXRlS2V5IC0gUHJpdmF0ZSBrZXkgYXMgaGV4IHN0cmluZyBvciBVaW50OEFycmF5XG4gKiBAcmV0dXJucyBGdWxseSBzaWduZWQgZXZlbnQgd2l0aCBpZCwgcHVia2V5LCBhbmQgc2lnXG4gKi9cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBmaW5hbGl6ZUV2ZW50KFxuICBldmVudDogUGFydGlhbDxOb3N0ckV2ZW50PixcbiAgcHJpdmF0ZUtleTogc3RyaW5nIHwgVWludDhBcnJheVxuKTogUHJvbWlzZTxTaWduZWROb3N0ckV2ZW50PiB7XG4gIGNvbnN0IHB1YmtleSA9IGV2ZW50LnB1YmtleSB8fCBnZXRQdWJsaWNLZXlTeW5jKHByaXZhdGVLZXkpO1xuICBjb25zdCB0aW1lc3RhbXAgPSBldmVudC5jcmVhdGVkX2F0IHx8IE1hdGguZmxvb3IoRGF0ZS5ub3coKSAvIDEwMDApO1xuXG4gIGNvbnN0IGZ1bGxFdmVudDogTm9zdHJFdmVudCA9IHtcbiAgICBraW5kOiBldmVudC5raW5kIHx8IDEsXG4gICAgY3JlYXRlZF9hdDogdGltZXN0YW1wLFxuICAgIHRhZ3M6IGV2ZW50LnRhZ3MgfHwgW10sXG4gICAgY29udGVudDogZXZlbnQuY29udGVudCB8fCAnJyxcbiAgICBwdWJrZXksXG4gIH07XG5cbiAgcmV0dXJuIHNpZ25FdmVudChmdWxsRXZlbnQsIHByaXZhdGVLZXkpO1xufVxuXG4vKipcbiAqIFZlcmlmaWVzIGFuIGV2ZW50IHNpZ25hdHVyZVxuICovXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gdmVyaWZ5U2lnbmF0dXJlKGV2ZW50OiBTaWduZWROb3N0ckV2ZW50KTogUHJvbWlzZTxib29sZWFuPiB7XG4gIHRyeSB7XG4gICAgLy8gU2VyaWFsaXplIGV2ZW50IGZvciB2ZXJpZmljYXRpb24gKE5JUC0wMSBmb3JtYXQpXG4gICAgY29uc3Qgc2VyaWFsaXplZCA9IEpTT04uc3RyaW5naWZ5KFtcbiAgICAgIDAsXG4gICAgICBldmVudC5wdWJrZXksXG4gICAgICBldmVudC5jcmVhdGVkX2F0LFxuICAgICAgZXZlbnQua2luZCxcbiAgICAgIGV2ZW50LnRhZ3MsXG4gICAgICBldmVudC5jb250ZW50XG4gICAgXSk7XG5cbiAgICAvLyBDYWxjdWxhdGUgZXZlbnQgaGFzaFxuICAgIGNvbnN0IGV2ZW50SGFzaCA9IHNoYTI1NihuZXcgVGV4dEVuY29kZXIoKS5lbmNvZGUoc2VyaWFsaXplZCkpO1xuXG4gICAgLy8gVmVyaWZ5IGV2ZW50IElEXG4gICAgY29uc3QgY2FsY3VsYXRlZElkID0gYnl0ZXNUb0hleChldmVudEhhc2gpO1xuICAgIGlmIChjYWxjdWxhdGVkSWQgIT09IGV2ZW50LmlkKSB7XG4gICAgICBsb2dnZXIuZXJyb3IoJ0V2ZW50IElEIG1pc21hdGNoJyk7XG4gICAgICByZXR1cm4gZmFsc2U7XG4gICAgfVxuXG4gICAgLy8gQ29udmVydCBoZXggc3RyaW5ncyB0byBieXRlc1xuICAgIGNvbnN0IHNpZ25hdHVyZUJ5dGVzID0gaGV4VG9CeXRlcyhldmVudC5zaWcpO1xuICAgIGNvbnN0IHB1YmtleUJ5dGVzID0gaGV4VG9CeXRlcyhldmVudC5wdWJrZXkpO1xuXG4gICAgLy8gVmVyaWZ5IHNpZ25hdHVyZVxuICAgIHJldHVybiBzY2hub3JyLnZlcmlmeShzaWduYXR1cmVCeXRlcywgZXZlbnRIYXNoLCBwdWJrZXlCeXRlcyk7XG4gIH0gY2F0Y2ggKGVycm9yKSB7XG4gICAgbG9nZ2VyLmVycm9yKHsgZXJyb3IgfSwgJ0ZhaWxlZCB0byB2ZXJpZnkgc2lnbmF0dXJlJyk7XG4gICAgcmV0dXJuIGZhbHNlO1xuICB9XG59XG5cbi8qKlxuICogRW5jcnlwdHMgYSBtZXNzYWdlIHVzaW5nIE5JUC0wNFxuICovXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gZW5jcnlwdChcbiAgbWVzc2FnZTogc3RyaW5nLFxuICByZWNpcGllbnRQdWJLZXk6IFB1YmxpY0tleSB8IHN0cmluZyxcbiAgc2VuZGVyUHJpdktleTogc3RyaW5nXG4pOiBQcm9taXNlPHN0cmluZz4ge1xuICB0cnkge1xuICAgIGNvbnN0IHJlY2lwaWVudFB1YktleUhleCA9IHR5cGVvZiByZWNpcGllbnRQdWJLZXkgPT09ICdzdHJpbmcnID8gcmVjaXBpZW50UHViS2V5IDogcmVjaXBpZW50UHViS2V5LmhleDtcbiAgICBjb25zdCBzaGFyZWRQb2ludCA9IHNlY3AyNTZrMS5nZXRTaGFyZWRTZWNyZXQoaGV4VG9CeXRlcyhzZW5kZXJQcml2S2V5KSwgaGV4VG9CeXRlcyhyZWNpcGllbnRQdWJLZXlIZXgpKTtcbiAgICBjb25zdCBzaGFyZWRYID0gc2hhcmVkUG9pbnQuc2xpY2UoMSwgMzMpO1xuXG4gICAgLy8gR2VuZXJhdGUgcmFuZG9tIElWXG4gICAgY29uc3QgaXYgPSByYW5kb21CeXRlcygxNik7XG4gICAgY29uc3Qga2V5ID0gYXdhaXQgY3VzdG9tQ3J5cHRvLmdldFN1YnRsZSgpLnRoZW4oKHN1YnRsZSkgPT4gc3VidGxlLmltcG9ydEtleShcbiAgICAgICdyYXcnLFxuICAgICAgc2hhcmVkWC5idWZmZXIsXG4gICAgICB7IG5hbWU6ICdBRVMtQ0JDJywgbGVuZ3RoOiAyNTYgfSxcbiAgICAgIGZhbHNlLFxuICAgICAgWydlbmNyeXB0J11cbiAgICApKTtcblxuICAgIC8vIFplcm8gc2hhcmVkIHNlY3JldCBtYXRlcmlhbCBub3cgdGhhdCBBRVMga2V5IGlzIGltcG9ydGVkXG4gICAgc2hhcmVkWC5maWxsKDApO1xuICAgIHNoYXJlZFBvaW50LmZpbGwoMCk7XG5cbiAgICAvLyBFbmNyeXB0IHRoZSBtZXNzYWdlXG4gICAgY29uc3QgZGF0YSA9IG5ldyBUZXh0RW5jb2RlcigpLmVuY29kZShtZXNzYWdlKTtcbiAgICBjb25zdCBlbmNyeXB0ZWQgPSBhd2FpdCBjdXN0b21DcnlwdG8uZ2V0U3VidGxlKCkudGhlbigoc3VidGxlKSA9PiBzdWJ0bGUuZW5jcnlwdChcbiAgICAgIHsgbmFtZTogJ0FFUy1DQkMnLCBpdiB9LFxuICAgICAga2V5LFxuICAgICAgZGF0YS5idWZmZXJcbiAgICApKTtcblxuICAgIC8vIE5JUC0wNCBzdGFuZGFyZCBmb3JtYXQ6IGJhc2U2NChjaXBoZXJ0ZXh0KSArIFwiP2l2PVwiICsgYmFzZTY0KGl2KVxuICAgIGNvbnN0IGNpcGhlcnRleHRCYXNlNjQgPSBieXRlc1RvQmFzZTY0KG5ldyBVaW50OEFycmF5KGVuY3J5cHRlZCkpO1xuICAgIGNvbnN0IGl2QmFzZTY0ID0gYnl0ZXNUb0Jhc2U2NChpdik7XG5cbiAgICByZXR1cm4gY2lwaGVydGV4dEJhc2U2NCArICc/aXY9JyArIGl2QmFzZTY0O1xuICB9IGNhdGNoIChlcnJvcikge1xuICAgIGxvZ2dlci5lcnJvcih7IGVycm9yIH0sICdGYWlsZWQgdG8gZW5jcnlwdCBtZXNzYWdlJyk7XG4gICAgdGhyb3cgZXJyb3I7XG4gIH1cbn1cblxuLyoqXG4gKiBEZWNyeXB0cyBhIG1lc3NhZ2UgdXNpbmcgTklQLTA0XG4gKi9cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBkZWNyeXB0KFxuICBlbmNyeXB0ZWRNZXNzYWdlOiBzdHJpbmcsXG4gIHNlbmRlclB1YktleTogUHVibGljS2V5IHwgc3RyaW5nLFxuICByZWNpcGllbnRQcml2S2V5OiBzdHJpbmdcbik6IFByb21pc2U8c3RyaW5nPiB7XG4gIHRyeSB7XG4gICAgY29uc3Qgc2VuZGVyUHViS2V5SGV4ID0gdHlwZW9mIHNlbmRlclB1YktleSA9PT0gJ3N0cmluZycgPyBzZW5kZXJQdWJLZXkgOiBzZW5kZXJQdWJLZXkuaGV4O1xuICAgIGNvbnN0IHNoYXJlZFBvaW50ID0gc2VjcDI1NmsxLmdldFNoYXJlZFNlY3JldChoZXhUb0J5dGVzKHJlY2lwaWVudFByaXZLZXkpLCBoZXhUb0J5dGVzKHNlbmRlclB1YktleUhleCkpO1xuICAgIGNvbnN0IHNoYXJlZFggPSBzaGFyZWRQb2ludC5zbGljZSgxLCAzMyk7XG5cbiAgICAvLyBQYXJzZSBOSVAtMDQgc3RhbmRhcmQgZm9ybWF0OiBiYXNlNjQoY2lwaGVydGV4dCkgKyBcIj9pdj1cIiArIGJhc2U2NChpdilcbiAgICAvLyBBbHNvIHN1cHBvcnQgbGVnYWN5IGhleCBmb3JtYXQgKGl2ICsgY2lwaGVydGV4dCBjb25jYXRlbmF0ZWQpIGFzIGZhbGxiYWNrXG4gICAgbGV0IGl2OiBVaW50OEFycmF5O1xuICAgIGxldCBjaXBoZXJ0ZXh0OiBVaW50OEFycmF5O1xuXG4gICAgaWYgKGVuY3J5cHRlZE1lc3NhZ2UuaW5jbHVkZXMoJz9pdj0nKSkge1xuICAgICAgLy8gTklQLTA0IHN0YW5kYXJkIGZvcm1hdFxuICAgICAgY29uc3QgW2NpcGhlcnRleHRCYXNlNjQsIGl2QmFzZTY0XSA9IGVuY3J5cHRlZE1lc3NhZ2Uuc3BsaXQoJz9pdj0nKTtcbiAgICAgIGNpcGhlcnRleHQgPSBiYXNlNjRUb0J5dGVzKGNpcGhlcnRleHRCYXNlNjQpO1xuICAgICAgaXYgPSBiYXNlNjRUb0J5dGVzKGl2QmFzZTY0KTtcbiAgICB9IGVsc2Uge1xuICAgICAgLy8gTGVnYWN5IGhleCBmb3JtYXQgZmFsbGJhY2s6IGZpcnN0IDE2IGJ5dGVzIGFyZSBJViwgcmVzdCBpcyBjaXBoZXJ0ZXh0XG4gICAgICBjb25zdCBlbmNyeXB0ZWQgPSBoZXhUb0J5dGVzKGVuY3J5cHRlZE1lc3NhZ2UpO1xuICAgICAgaXYgPSBlbmNyeXB0ZWQuc2xpY2UoMCwgMTYpO1xuICAgICAgY2lwaGVydGV4dCA9IGVuY3J5cHRlZC5zbGljZSgxNik7XG4gICAgfVxuXG4gICAgY29uc3Qga2V5ID0gYXdhaXQgY3VzdG9tQ3J5cHRvLmdldFN1YnRsZSgpLnRoZW4oKHN1YnRsZSkgPT4gc3VidGxlLmltcG9ydEtleShcbiAgICAgICdyYXcnLFxuICAgICAgc2hhcmVkWC5idWZmZXIsXG4gICAgICB7IG5hbWU6ICdBRVMtQ0JDJywgbGVuZ3RoOiAyNTYgfSxcbiAgICAgIGZhbHNlLFxuICAgICAgWydkZWNyeXB0J11cbiAgICApKTtcblxuICAgIC8vIFplcm8gc2hhcmVkIHNlY3JldCBtYXRlcmlhbCBub3cgdGhhdCBBRVMga2V5IGlzIGltcG9ydGVkXG4gICAgc2hhcmVkWC5maWxsKDApO1xuICAgIHNoYXJlZFBvaW50LmZpbGwoMCk7XG5cbiAgICBjb25zdCBkZWNyeXB0ZWQgPSBhd2FpdCBjdXN0b21DcnlwdG8uZ2V0U3VidGxlKCkudGhlbigoc3VidGxlKSA9PiBzdWJ0bGUuZGVjcnlwdChcbiAgICAgIHsgbmFtZTogJ0FFUy1DQkMnLCBpdiB9LFxuICAgICAga2V5LFxuICAgICAgY2lwaGVydGV4dC5idWZmZXIgYXMgQXJyYXlCdWZmZXJcbiAgICApKTtcblxuICAgIHJldHVybiBuZXcgVGV4dERlY29kZXIoKS5kZWNvZGUoZGVjcnlwdGVkKTtcbiAgfSBjYXRjaCAoZXJyb3IpIHtcbiAgICBsb2dnZXIuZXJyb3IoeyBlcnJvciB9LCAnRmFpbGVkIHRvIGRlY3J5cHQgbWVzc2FnZScpO1xuICAgIHRocm93IGVycm9yO1xuICB9XG59XG4iLCAiLyoqXG4gKiBTRUNHIHNlY3AyNTZrMS4gU2VlIFtwZGZdKGh0dHBzOi8vd3d3LnNlY2cub3JnL3NlYzItdjIucGRmKS5cbiAqXG4gKiBCZWxvbmdzIHRvIEtvYmxpdHogY3VydmVzOiBpdCBoYXMgZWZmaWNpZW50bHktY29tcHV0YWJsZSBHTFYgZW5kb21vcnBoaXNtIFx1MDNDOCxcbiAqIGNoZWNrIG91dCB7QGxpbmsgRW5kb21vcnBoaXNtT3B0c30uIFNlZW1zIHRvIGJlIHJpZ2lkIChub3QgYmFja2Rvb3JlZCkuXG4gKiBAbW9kdWxlXG4gKi9cbi8qISBub2JsZS1jdXJ2ZXMgLSBNSVQgTGljZW5zZSAoYykgMjAyMiBQYXVsIE1pbGxlciAocGF1bG1pbGxyLmNvbSkgKi9cbmltcG9ydCB7IHNoYTI1NiB9IGZyb20gJ0Bub2JsZS9oYXNoZXMvc2hhMi5qcyc7XG5pbXBvcnQgeyByYW5kb21CeXRlcyB9IGZyb20gJ0Bub2JsZS9oYXNoZXMvdXRpbHMuanMnO1xuaW1wb3J0IHsgY3JlYXRlS2V5Z2VuLCB0eXBlIEN1cnZlTGVuZ3RocyB9IGZyb20gJy4vYWJzdHJhY3QvY3VydmUudHMnO1xuaW1wb3J0IHsgY3JlYXRlSGFzaGVyLCB0eXBlIEgyQ0hhc2hlciwgaXNvZ2VueU1hcCB9IGZyb20gJy4vYWJzdHJhY3QvaGFzaC10by1jdXJ2ZS50cyc7XG5pbXBvcnQgeyBGaWVsZCwgbWFwSGFzaFRvRmllbGQsIHBvdzIgfSBmcm9tICcuL2Fic3RyYWN0L21vZHVsYXIudHMnO1xuaW1wb3J0IHtcbiAgdHlwZSBFQ0RTQSxcbiAgZWNkc2EsXG4gIHR5cGUgRW5kb21vcnBoaXNtT3B0cyxcbiAgbWFwVG9DdXJ2ZVNpbXBsZVNXVSxcbiAgdHlwZSBXZWllcnN0cmFzc1BvaW50IGFzIFBvaW50VHlwZSxcbiAgd2VpZXJzdHJhc3MsXG4gIHR5cGUgV2VpZXJzdHJhc3NPcHRzLFxuICB0eXBlIFdlaWVyc3RyYXNzUG9pbnRDb25zLFxufSBmcm9tICcuL2Fic3RyYWN0L3dlaWVyc3RyYXNzLnRzJztcbmltcG9ydCB7IGFieXRlcywgYXNjaWlUb0J5dGVzLCBieXRlc1RvTnVtYmVyQkUsIGNvbmNhdEJ5dGVzIH0gZnJvbSAnLi91dGlscy50cyc7XG5cbi8vIFNlZW1zIGxpa2UgZ2VuZXJhdG9yIHdhcyBwcm9kdWNlZCBmcm9tIHNvbWUgc2VlZDpcbi8vIGBQb2ludGsxLkJBU0UubXVsdGlwbHkoUG9pbnRrMS5Gbi5pbnYoMm4sIE4pKS50b0FmZmluZSgpLnhgXG4vLyAvLyBnaXZlcyBzaG9ydCB4IDB4M2I3OGNlNTYzZjg5YTBlZDk0MTRmNWFhMjhhZDBkOTZkNjc5NWY5YzYzblxuY29uc3Qgc2VjcDI1NmsxX0NVUlZFOiBXZWllcnN0cmFzc09wdHM8YmlnaW50PiA9IHtcbiAgcDogQmlnSW50KCcweGZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZlZmZmZmZjMmYnKSxcbiAgbjogQmlnSW50KCcweGZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZlYmFhZWRjZTZhZjQ4YTAzYmJmZDI1ZThjZDAzNjQxNDEnKSxcbiAgaDogQmlnSW50KDEpLFxuICBhOiBCaWdJbnQoMCksXG4gIGI6IEJpZ0ludCg3KSxcbiAgR3g6IEJpZ0ludCgnMHg3OWJlNjY3ZWY5ZGNiYmFjNTVhMDYyOTVjZTg3MGIwNzAyOWJmY2RiMmRjZTI4ZDk1OWYyODE1YjE2ZjgxNzk4JyksXG4gIEd5OiBCaWdJbnQoJzB4NDgzYWRhNzcyNmEzYzQ2NTVkYTRmYmZjMGUxMTA4YThmZDE3YjQ0OGE2ODU1NDE5OWM0N2QwOGZmYjEwZDRiOCcpLFxufTtcblxuY29uc3Qgc2VjcDI1NmsxX0VORE86IEVuZG9tb3JwaGlzbU9wdHMgPSB7XG4gIGJldGE6IEJpZ0ludCgnMHg3YWU5NmEyYjY1N2MwNzEwNmU2NDQ3OWVhYzM0MzRlOTljZjA0OTc1MTJmNTg5OTVjMTM5NmMyODcxOTUwMWVlJyksXG4gIGJhc2lzZXM6IFtcbiAgICBbQmlnSW50KCcweDMwODZkMjIxYTdkNDZiY2RlODZjOTBlNDkyODRlYjE1JyksIC1CaWdJbnQoJzB4ZTQ0MzdlZDYwMTBlODgyODZmNTQ3ZmE5MGFiZmU0YzMnKV0sXG4gICAgW0JpZ0ludCgnMHgxMTRjYTUwZjdhOGUyZjNmNjU3YzExMDhkOWQ0NGNmZDgnKSwgQmlnSW50KCcweDMwODZkMjIxYTdkNDZiY2RlODZjOTBlNDkyODRlYjE1JyldLFxuICBdLFxufTtcblxuY29uc3QgXzBuID0gLyogQF9fUFVSRV9fICovIEJpZ0ludCgwKTtcbmNvbnN0IF8ybiA9IC8qIEBfX1BVUkVfXyAqLyBCaWdJbnQoMik7XG5cbi8qKlxuICogXHUyMjFBbiA9IG5eKChwKzEpLzQpIGZvciBmaWVsZHMgcCA9IDMgbW9kIDQuIFdlIHVud3JhcCB0aGUgbG9vcCBhbmQgbXVsdGlwbHkgYml0LWJ5LWJpdC5cbiAqIChQKzFuLzRuKS50b1N0cmluZygyKSB3b3VsZCBwcm9kdWNlIGJpdHMgWzIyM3ggMSwgMCwgMjJ4IDEsIDR4IDAsIDExLCAwMF1cbiAqL1xuZnVuY3Rpb24gc3FydE1vZCh5OiBiaWdpbnQpOiBiaWdpbnQge1xuICBjb25zdCBQID0gc2VjcDI1NmsxX0NVUlZFLnA7XG4gIC8vIHByZXR0aWVyLWlnbm9yZVxuICBjb25zdCBfM24gPSBCaWdJbnQoMyksIF82biA9IEJpZ0ludCg2KSwgXzExbiA9IEJpZ0ludCgxMSksIF8yMm4gPSBCaWdJbnQoMjIpO1xuICAvLyBwcmV0dGllci1pZ25vcmVcbiAgY29uc3QgXzIzbiA9IEJpZ0ludCgyMyksIF80NG4gPSBCaWdJbnQoNDQpLCBfODhuID0gQmlnSW50KDg4KTtcbiAgY29uc3QgYjIgPSAoeSAqIHkgKiB5KSAlIFA7IC8vIHheMywgMTFcbiAgY29uc3QgYjMgPSAoYjIgKiBiMiAqIHkpICUgUDsgLy8geF43XG4gIGNvbnN0IGI2ID0gKHBvdzIoYjMsIF8zbiwgUCkgKiBiMykgJSBQO1xuICBjb25zdCBiOSA9IChwb3cyKGI2LCBfM24sIFApICogYjMpICUgUDtcbiAgY29uc3QgYjExID0gKHBvdzIoYjksIF8ybiwgUCkgKiBiMikgJSBQO1xuICBjb25zdCBiMjIgPSAocG93MihiMTEsIF8xMW4sIFApICogYjExKSAlIFA7XG4gIGNvbnN0IGI0NCA9IChwb3cyKGIyMiwgXzIybiwgUCkgKiBiMjIpICUgUDtcbiAgY29uc3QgYjg4ID0gKHBvdzIoYjQ0LCBfNDRuLCBQKSAqIGI0NCkgJSBQO1xuICBjb25zdCBiMTc2ID0gKHBvdzIoYjg4LCBfODhuLCBQKSAqIGI4OCkgJSBQO1xuICBjb25zdCBiMjIwID0gKHBvdzIoYjE3NiwgXzQ0biwgUCkgKiBiNDQpICUgUDtcbiAgY29uc3QgYjIyMyA9IChwb3cyKGIyMjAsIF8zbiwgUCkgKiBiMykgJSBQO1xuICBjb25zdCB0MSA9IChwb3cyKGIyMjMsIF8yM24sIFApICogYjIyKSAlIFA7XG4gIGNvbnN0IHQyID0gKHBvdzIodDEsIF82biwgUCkgKiBiMikgJSBQO1xuICBjb25zdCByb290ID0gcG93Mih0MiwgXzJuLCBQKTtcbiAgaWYgKCFGcGsxLmVxbChGcGsxLnNxcihyb290KSwgeSkpIHRocm93IG5ldyBFcnJvcignQ2Fubm90IGZpbmQgc3F1YXJlIHJvb3QnKTtcbiAgcmV0dXJuIHJvb3Q7XG59XG5cbmNvbnN0IEZwazEgPSBGaWVsZChzZWNwMjU2azFfQ1VSVkUucCwgeyBzcXJ0OiBzcXJ0TW9kIH0pO1xuY29uc3QgUG9pbnRrMSA9IC8qIEBfX1BVUkVfXyAqLyB3ZWllcnN0cmFzcyhzZWNwMjU2azFfQ1VSVkUsIHtcbiAgRnA6IEZwazEsXG4gIGVuZG86IHNlY3AyNTZrMV9FTkRPLFxufSk7XG5cbi8qKlxuICogc2VjcDI1NmsxIGN1cnZlOiBFQ0RTQSBhbmQgRUNESCBtZXRob2RzLlxuICpcbiAqIFVzZXMgc2hhMjU2IHRvIGhhc2ggbWVzc2FnZXMuIFRvIHVzZSBhIGRpZmZlcmVudCBoYXNoLFxuICogcGFzcyBgeyBwcmVoYXNoOiBmYWxzZSB9YCB0byBzaWduIC8gdmVyaWZ5LlxuICpcbiAqIEBleGFtcGxlXG4gKiBgYGBqc1xuICogaW1wb3J0IHsgc2VjcDI1NmsxIH0gZnJvbSAnQG5vYmxlL2N1cnZlcy9zZWNwMjU2azEuanMnO1xuICogY29uc3QgeyBzZWNyZXRLZXksIHB1YmxpY0tleSB9ID0gc2VjcDI1NmsxLmtleWdlbigpO1xuICogLy8gY29uc3QgcHVibGljS2V5ID0gc2VjcDI1NmsxLmdldFB1YmxpY0tleShzZWNyZXRLZXkpO1xuICogY29uc3QgbXNnID0gbmV3IFRleHRFbmNvZGVyKCkuZW5jb2RlKCdoZWxsbyBub2JsZScpO1xuICogY29uc3Qgc2lnID0gc2VjcDI1NmsxLnNpZ24obXNnLCBzZWNyZXRLZXkpO1xuICogY29uc3QgaXNWYWxpZCA9IHNlY3AyNTZrMS52ZXJpZnkoc2lnLCBtc2csIHB1YmxpY0tleSk7XG4gKiAvLyBjb25zdCBzaWdLZWNjYWsgPSBzZWNwMjU2azEuc2lnbihrZWNjYWsyNTYobXNnKSwgc2VjcmV0S2V5LCB7IHByZWhhc2g6IGZhbHNlIH0pO1xuICogYGBgXG4gKi9cbmV4cG9ydCBjb25zdCBzZWNwMjU2azE6IEVDRFNBID0gLyogQF9fUFVSRV9fICovIGVjZHNhKFBvaW50azEsIHNoYTI1Nik7XG5cbi8vIFNjaG5vcnIgc2lnbmF0dXJlcyBhcmUgc3VwZXJpb3IgdG8gRUNEU0EgZnJvbSBhYm92ZS4gQmVsb3cgaXMgU2Nobm9yci1zcGVjaWZpYyBCSVAwMzQwIGNvZGUuXG4vLyBodHRwczovL2dpdGh1Yi5jb20vYml0Y29pbi9iaXBzL2Jsb2IvbWFzdGVyL2JpcC0wMzQwLm1lZGlhd2lraVxuLyoqIEFuIG9iamVjdCBtYXBwaW5nIHRhZ3MgdG8gdGhlaXIgdGFnZ2VkIGhhc2ggcHJlZml4IG9mIFtTSEEyNTYodGFnKSB8IFNIQTI1Nih0YWcpXSAqL1xuY29uc3QgVEFHR0VEX0hBU0hfUFJFRklYRVM6IHsgW3RhZzogc3RyaW5nXTogVWludDhBcnJheSB9ID0ge307XG5mdW5jdGlvbiB0YWdnZWRIYXNoKHRhZzogc3RyaW5nLCAuLi5tZXNzYWdlczogVWludDhBcnJheVtdKTogVWludDhBcnJheSB7XG4gIGxldCB0YWdQID0gVEFHR0VEX0hBU0hfUFJFRklYRVNbdGFnXTtcbiAgaWYgKHRhZ1AgPT09IHVuZGVmaW5lZCkge1xuICAgIGNvbnN0IHRhZ0ggPSBzaGEyNTYoYXNjaWlUb0J5dGVzKHRhZykpO1xuICAgIHRhZ1AgPSBjb25jYXRCeXRlcyh0YWdILCB0YWdIKTtcbiAgICBUQUdHRURfSEFTSF9QUkVGSVhFU1t0YWddID0gdGFnUDtcbiAgfVxuICByZXR1cm4gc2hhMjU2KGNvbmNhdEJ5dGVzKHRhZ1AsIC4uLm1lc3NhZ2VzKSk7XG59XG5cbi8vIEVDRFNBIGNvbXBhY3QgcG9pbnRzIGFyZSAzMy1ieXRlLiBTY2hub3JyIGlzIDMyOiB3ZSBzdHJpcCBmaXJzdCBieXRlIDB4MDIgb3IgMHgwM1xuY29uc3QgcG9pbnRUb0J5dGVzID0gKHBvaW50OiBQb2ludFR5cGU8YmlnaW50PikgPT4gcG9pbnQudG9CeXRlcyh0cnVlKS5zbGljZSgxKTtcbmNvbnN0IGhhc0V2ZW4gPSAoeTogYmlnaW50KSA9PiB5ICUgXzJuID09PSBfMG47XG5cbi8vIENhbGN1bGF0ZSBwb2ludCwgc2NhbGFyIGFuZCBieXRlc1xuZnVuY3Rpb24gc2Nobm9yckdldEV4dFB1YktleShwcml2OiBVaW50OEFycmF5KSB7XG4gIGNvbnN0IHsgRm4sIEJBU0UgfSA9IFBvaW50azE7XG4gIGNvbnN0IGRfID0gRm4uZnJvbUJ5dGVzKHByaXYpO1xuICBjb25zdCBwID0gQkFTRS5tdWx0aXBseShkXyk7IC8vIFAgPSBkJ1x1MjJDNUc7IDAgPCBkJyA8IG4gY2hlY2sgaXMgZG9uZSBpbnNpZGVcbiAgY29uc3Qgc2NhbGFyID0gaGFzRXZlbihwLnkpID8gZF8gOiBGbi5uZWcoZF8pO1xuICByZXR1cm4geyBzY2FsYXIsIGJ5dGVzOiBwb2ludFRvQnl0ZXMocCkgfTtcbn1cbi8qKlxuICogbGlmdF94IGZyb20gQklQMzQwLiBDb252ZXJ0IDMyLWJ5dGUgeCBjb29yZGluYXRlIHRvIGVsbGlwdGljIGN1cnZlIHBvaW50LlxuICogQHJldHVybnMgdmFsaWQgcG9pbnQgY2hlY2tlZCBmb3IgYmVpbmcgb24tY3VydmVcbiAqL1xuZnVuY3Rpb24gbGlmdF94KHg6IGJpZ2ludCk6IFBvaW50VHlwZTxiaWdpbnQ+IHtcbiAgY29uc3QgRnAgPSBGcGsxO1xuICBpZiAoIUZwLmlzVmFsaWROb3QwKHgpKSB0aHJvdyBuZXcgRXJyb3IoJ2ludmFsaWQgeDogRmFpbCBpZiB4IFx1MjI2NSBwJyk7XG4gIGNvbnN0IHh4ID0gRnAuY3JlYXRlKHggKiB4KTtcbiAgY29uc3QgYyA9IEZwLmNyZWF0ZSh4eCAqIHggKyBCaWdJbnQoNykpOyAvLyBMZXQgYyA9IHhcdTAwQjMgKyA3IG1vZCBwLlxuICBsZXQgeSA9IEZwLnNxcnQoYyk7IC8vIExldCB5ID0gY14ocCsxKS80IG1vZCBwLiBTYW1lIGFzIHNxcnQoKS5cbiAgLy8gUmV0dXJuIHRoZSB1bmlxdWUgcG9pbnQgUCBzdWNoIHRoYXQgeChQKSA9IHggYW5kXG4gIC8vIHkoUCkgPSB5IGlmIHkgbW9kIDIgPSAwIG9yIHkoUCkgPSBwLXkgb3RoZXJ3aXNlLlxuICBpZiAoIWhhc0V2ZW4oeSkpIHkgPSBGcC5uZWcoeSk7XG4gIGNvbnN0IHAgPSBQb2ludGsxLmZyb21BZmZpbmUoeyB4LCB5IH0pO1xuICBwLmFzc2VydFZhbGlkaXR5KCk7XG4gIHJldHVybiBwO1xufVxuY29uc3QgbnVtID0gYnl0ZXNUb051bWJlckJFO1xuLyoqXG4gKiBDcmVhdGUgdGFnZ2VkIGhhc2gsIGNvbnZlcnQgaXQgdG8gYmlnaW50LCByZWR1Y2UgbW9kdWxvLW4uXG4gKi9cbmZ1bmN0aW9uIGNoYWxsZW5nZSguLi5hcmdzOiBVaW50OEFycmF5W10pOiBiaWdpbnQge1xuICByZXR1cm4gUG9pbnRrMS5Gbi5jcmVhdGUobnVtKHRhZ2dlZEhhc2goJ0JJUDAzNDAvY2hhbGxlbmdlJywgLi4uYXJncykpKTtcbn1cblxuLyoqXG4gKiBTY2hub3JyIHB1YmxpYyBrZXkgaXMganVzdCBgeGAgY29vcmRpbmF0ZSBvZiBQb2ludCBhcyBwZXIgQklQMzQwLlxuICovXG5mdW5jdGlvbiBzY2hub3JyR2V0UHVibGljS2V5KHNlY3JldEtleTogVWludDhBcnJheSk6IFVpbnQ4QXJyYXkge1xuICByZXR1cm4gc2Nobm9yckdldEV4dFB1YktleShzZWNyZXRLZXkpLmJ5dGVzOyAvLyBkJz1pbnQoc2spLiBGYWlsIGlmIGQnPTAgb3IgZCdcdTIyNjVuLiBSZXQgYnl0ZXMoZCdcdTIyQzVHKVxufVxuXG4vKipcbiAqIENyZWF0ZXMgU2Nobm9yciBzaWduYXR1cmUgYXMgcGVyIEJJUDM0MC4gVmVyaWZpZXMgaXRzZWxmIGJlZm9yZSByZXR1cm5pbmcgYW55dGhpbmcuXG4gKiBhdXhSYW5kIGlzIG9wdGlvbmFsIGFuZCBpcyBub3QgdGhlIHNvbGUgc291cmNlIG9mIGsgZ2VuZXJhdGlvbjogYmFkIENTUFJORyB3b24ndCBiZSBkYW5nZXJvdXMuXG4gKi9cbmZ1bmN0aW9uIHNjaG5vcnJTaWduKFxuICBtZXNzYWdlOiBVaW50OEFycmF5LFxuICBzZWNyZXRLZXk6IFVpbnQ4QXJyYXksXG4gIGF1eFJhbmQ6IFVpbnQ4QXJyYXkgPSByYW5kb21CeXRlcygzMilcbik6IFVpbnQ4QXJyYXkge1xuICBjb25zdCB7IEZuIH0gPSBQb2ludGsxO1xuICBjb25zdCBtID0gYWJ5dGVzKG1lc3NhZ2UsIHVuZGVmaW5lZCwgJ21lc3NhZ2UnKTtcbiAgY29uc3QgeyBieXRlczogcHgsIHNjYWxhcjogZCB9ID0gc2Nobm9yckdldEV4dFB1YktleShzZWNyZXRLZXkpOyAvLyBjaGVja3MgZm9yIGlzV2l0aGluQ3VydmVPcmRlclxuICBjb25zdCBhID0gYWJ5dGVzKGF1eFJhbmQsIDMyLCAnYXV4UmFuZCcpOyAvLyBBdXhpbGlhcnkgcmFuZG9tIGRhdGEgYTogYSAzMi1ieXRlIGFycmF5XG4gIGNvbnN0IHQgPSBGbi50b0J5dGVzKGQgXiBudW0odGFnZ2VkSGFzaCgnQklQMDM0MC9hdXgnLCBhKSkpOyAvLyBMZXQgdCBiZSB0aGUgYnl0ZS13aXNlIHhvciBvZiBieXRlcyhkKSBhbmQgaGFzaC9hdXgoYSlcbiAgY29uc3QgcmFuZCA9IHRhZ2dlZEhhc2goJ0JJUDAzNDAvbm9uY2UnLCB0LCBweCwgbSk7IC8vIExldCByYW5kID0gaGFzaC9ub25jZSh0IHx8IGJ5dGVzKFApIHx8IG0pXG4gIC8vIExldCBrJyA9IGludChyYW5kKSBtb2Qgbi4gRmFpbCBpZiBrJyA9IDAuIExldCBSID0gaydcdTIyQzVHXG4gIGNvbnN0IHsgYnl0ZXM6IHJ4LCBzY2FsYXI6IGsgfSA9IHNjaG5vcnJHZXRFeHRQdWJLZXkocmFuZCk7XG4gIGNvbnN0IGUgPSBjaGFsbGVuZ2UocngsIHB4LCBtKTsgLy8gTGV0IGUgPSBpbnQoaGFzaC9jaGFsbGVuZ2UoYnl0ZXMoUikgfHwgYnl0ZXMoUCkgfHwgbSkpIG1vZCBuLlxuICBjb25zdCBzaWcgPSBuZXcgVWludDhBcnJheSg2NCk7IC8vIExldCBzaWcgPSBieXRlcyhSKSB8fCBieXRlcygoayArIGVkKSBtb2QgbikuXG4gIHNpZy5zZXQocngsIDApO1xuICBzaWcuc2V0KEZuLnRvQnl0ZXMoRm4uY3JlYXRlKGsgKyBlICogZCkpLCAzMik7XG4gIC8vIElmIFZlcmlmeShieXRlcyhQKSwgbSwgc2lnKSAoc2VlIGJlbG93KSByZXR1cm5zIGZhaWx1cmUsIGFib3J0XG4gIGlmICghc2Nobm9yclZlcmlmeShzaWcsIG0sIHB4KSkgdGhyb3cgbmV3IEVycm9yKCdzaWduOiBJbnZhbGlkIHNpZ25hdHVyZSBwcm9kdWNlZCcpO1xuICByZXR1cm4gc2lnO1xufVxuXG4vKipcbiAqIFZlcmlmaWVzIFNjaG5vcnIgc2lnbmF0dXJlLlxuICogV2lsbCBzd2FsbG93IGVycm9ycyAmIHJldHVybiBmYWxzZSBleGNlcHQgZm9yIGluaXRpYWwgdHlwZSB2YWxpZGF0aW9uIG9mIGFyZ3VtZW50cy5cbiAqL1xuZnVuY3Rpb24gc2Nobm9yclZlcmlmeShzaWduYXR1cmU6IFVpbnQ4QXJyYXksIG1lc3NhZ2U6IFVpbnQ4QXJyYXksIHB1YmxpY0tleTogVWludDhBcnJheSk6IGJvb2xlYW4ge1xuICBjb25zdCB7IEZwLCBGbiwgQkFTRSB9ID0gUG9pbnRrMTtcbiAgY29uc3Qgc2lnID0gYWJ5dGVzKHNpZ25hdHVyZSwgNjQsICdzaWduYXR1cmUnKTtcbiAgY29uc3QgbSA9IGFieXRlcyhtZXNzYWdlLCB1bmRlZmluZWQsICdtZXNzYWdlJyk7XG4gIGNvbnN0IHB1YiA9IGFieXRlcyhwdWJsaWNLZXksIDMyLCAncHVibGljS2V5Jyk7XG4gIHRyeSB7XG4gICAgY29uc3QgUCA9IGxpZnRfeChudW0ocHViKSk7IC8vIFAgPSBsaWZ0X3goaW50KHBrKSk7IGZhaWwgaWYgdGhhdCBmYWlsc1xuICAgIGNvbnN0IHIgPSBudW0oc2lnLnN1YmFycmF5KDAsIDMyKSk7IC8vIExldCByID0gaW50KHNpZ1swOjMyXSk7IGZhaWwgaWYgciBcdTIyNjUgcC5cbiAgICBpZiAoIUZwLmlzVmFsaWROb3QwKHIpKSByZXR1cm4gZmFsc2U7XG4gICAgY29uc3QgcyA9IG51bShzaWcuc3ViYXJyYXkoMzIsIDY0KSk7IC8vIExldCBzID0gaW50KHNpZ1szMjo2NF0pOyBmYWlsIGlmIHMgXHUyMjY1IG4uXG4gICAgaWYgKCFGbi5pc1ZhbGlkTm90MChzKSkgcmV0dXJuIGZhbHNlO1xuXG4gICAgY29uc3QgZSA9IGNoYWxsZW5nZShGbi50b0J5dGVzKHIpLCBwb2ludFRvQnl0ZXMoUCksIG0pOyAvLyBpbnQoY2hhbGxlbmdlKGJ5dGVzKHIpfHxieXRlcyhQKXx8bSkpJW5cbiAgICAvLyBSID0gc1x1MjJDNUcgLSBlXHUyMkM1UCwgd2hlcmUgLWVQID09IChuLWUpUFxuICAgIGNvbnN0IFIgPSBCQVNFLm11bHRpcGx5VW5zYWZlKHMpLmFkZChQLm11bHRpcGx5VW5zYWZlKEZuLm5lZyhlKSkpO1xuICAgIGNvbnN0IHsgeCwgeSB9ID0gUi50b0FmZmluZSgpO1xuICAgIC8vIEZhaWwgaWYgaXNfaW5maW5pdGUoUikgLyBub3QgaGFzX2V2ZW5feShSKSAvIHgoUikgXHUyMjYwIHIuXG4gICAgaWYgKFIuaXMwKCkgfHwgIWhhc0V2ZW4oeSkgfHwgeCAhPT0gcikgcmV0dXJuIGZhbHNlO1xuICAgIHJldHVybiB0cnVlO1xuICB9IGNhdGNoIChlcnJvcikge1xuICAgIHJldHVybiBmYWxzZTtcbiAgfVxufVxuXG5leHBvcnQgdHlwZSBTZWNwU2Nobm9yciA9IHtcbiAga2V5Z2VuOiAoc2VlZD86IFVpbnQ4QXJyYXkpID0+IHsgc2VjcmV0S2V5OiBVaW50OEFycmF5OyBwdWJsaWNLZXk6IFVpbnQ4QXJyYXkgfTtcbiAgZ2V0UHVibGljS2V5OiB0eXBlb2Ygc2Nobm9yckdldFB1YmxpY0tleTtcbiAgc2lnbjogdHlwZW9mIHNjaG5vcnJTaWduO1xuICB2ZXJpZnk6IHR5cGVvZiBzY2hub3JyVmVyaWZ5O1xuICBQb2ludDogV2VpZXJzdHJhc3NQb2ludENvbnM8YmlnaW50PjtcbiAgdXRpbHM6IHtcbiAgICByYW5kb21TZWNyZXRLZXk6IChzZWVkPzogVWludDhBcnJheSkgPT4gVWludDhBcnJheTtcbiAgICBwb2ludFRvQnl0ZXM6IChwb2ludDogUG9pbnRUeXBlPGJpZ2ludD4pID0+IFVpbnQ4QXJyYXk7XG4gICAgbGlmdF94OiB0eXBlb2YgbGlmdF94O1xuICAgIHRhZ2dlZEhhc2g6IHR5cGVvZiB0YWdnZWRIYXNoO1xuICB9O1xuICBsZW5ndGhzOiBDdXJ2ZUxlbmd0aHM7XG59O1xuLyoqXG4gKiBTY2hub3JyIHNpZ25hdHVyZXMgb3ZlciBzZWNwMjU2azEuXG4gKiBodHRwczovL2dpdGh1Yi5jb20vYml0Y29pbi9iaXBzL2Jsb2IvbWFzdGVyL2JpcC0wMzQwLm1lZGlhd2lraVxuICogQGV4YW1wbGVcbiAqIGBgYGpzXG4gKiBpbXBvcnQgeyBzY2hub3JyIH0gZnJvbSAnQG5vYmxlL2N1cnZlcy9zZWNwMjU2azEuanMnO1xuICogY29uc3QgeyBzZWNyZXRLZXksIHB1YmxpY0tleSB9ID0gc2Nobm9yci5rZXlnZW4oKTtcbiAqIC8vIGNvbnN0IHB1YmxpY0tleSA9IHNjaG5vcnIuZ2V0UHVibGljS2V5KHNlY3JldEtleSk7XG4gKiBjb25zdCBtc2cgPSBuZXcgVGV4dEVuY29kZXIoKS5lbmNvZGUoJ2hlbGxvJyk7XG4gKiBjb25zdCBzaWcgPSBzY2hub3JyLnNpZ24obXNnLCBzZWNyZXRLZXkpO1xuICogY29uc3QgaXNWYWxpZCA9IHNjaG5vcnIudmVyaWZ5KHNpZywgbXNnLCBwdWJsaWNLZXkpO1xuICogYGBgXG4gKi9cbmV4cG9ydCBjb25zdCBzY2hub3JyOiBTZWNwU2Nobm9yciA9IC8qIEBfX1BVUkVfXyAqLyAoKCkgPT4ge1xuICBjb25zdCBzaXplID0gMzI7XG4gIGNvbnN0IHNlZWRMZW5ndGggPSA0ODtcbiAgY29uc3QgcmFuZG9tU2VjcmV0S2V5ID0gKHNlZWQgPSByYW5kb21CeXRlcyhzZWVkTGVuZ3RoKSk6IFVpbnQ4QXJyYXkgPT4ge1xuICAgIHJldHVybiBtYXBIYXNoVG9GaWVsZChzZWVkLCBzZWNwMjU2azFfQ1VSVkUubik7XG4gIH07XG4gIHJldHVybiB7XG4gICAga2V5Z2VuOiBjcmVhdGVLZXlnZW4ocmFuZG9tU2VjcmV0S2V5LCBzY2hub3JyR2V0UHVibGljS2V5KSxcbiAgICBnZXRQdWJsaWNLZXk6IHNjaG5vcnJHZXRQdWJsaWNLZXksXG4gICAgc2lnbjogc2Nobm9yclNpZ24sXG4gICAgdmVyaWZ5OiBzY2hub3JyVmVyaWZ5LFxuICAgIFBvaW50OiBQb2ludGsxLFxuICAgIHV0aWxzOiB7XG4gICAgICByYW5kb21TZWNyZXRLZXksXG4gICAgICB0YWdnZWRIYXNoLFxuICAgICAgbGlmdF94LFxuICAgICAgcG9pbnRUb0J5dGVzLFxuICAgIH0sXG4gICAgbGVuZ3Roczoge1xuICAgICAgc2VjcmV0S2V5OiBzaXplLFxuICAgICAgcHVibGljS2V5OiBzaXplLFxuICAgICAgcHVibGljS2V5SGFzUHJlZml4OiBmYWxzZSxcbiAgICAgIHNpZ25hdHVyZTogc2l6ZSAqIDIsXG4gICAgICBzZWVkOiBzZWVkTGVuZ3RoLFxuICAgIH0sXG4gIH07XG59KSgpO1xuXG5jb25zdCBpc29NYXAgPSAvKiBAX19QVVJFX18gKi8gKCgpID0+XG4gIGlzb2dlbnlNYXAoXG4gICAgRnBrMSxcbiAgICBbXG4gICAgICAvLyB4TnVtXG4gICAgICBbXG4gICAgICAgICcweDhlMzhlMzhlMzhlMzhlMzhlMzhlMzhlMzhlMzhlMzhlMzhlMzhlMzhlMzhlMzhlMzhlMzhlMzhkYWFhYWE4YzcnLFxuICAgICAgICAnMHg3ZDNkNGM4MGJjMzIxZDViOWYzMTVjZWE3ZmQ0NGM1ZDU5NWQyZmMwYmY2M2I5MmRmZmYxMDQ0ZjE3YzY1ODEnLFxuICAgICAgICAnMHg1MzRjMzI4ZDIzZjIzNGU2ZTJhNDEzZGVjYTI1Y2FlY2U0NTA2MTQ0MDM3YzQwMzE0ZWNiZDBiNTNkOWRkMjYyJyxcbiAgICAgICAgJzB4OGUzOGUzOGUzOGUzOGUzOGUzOGUzOGUzOGUzOGUzOGUzOGUzOGUzOGUzOGUzOGUzOGUzOGUzOGRhYWFhYTg4YycsXG4gICAgICBdLFxuICAgICAgLy8geERlblxuICAgICAgW1xuICAgICAgICAnMHhkMzU3NzExOTNkOTQ5MThhOWNhMzRjY2JiN2I2NDBkZDg2Y2Q0MDk1NDJmODQ4N2Q5ZmU2Yjc0NTc4MWViNDliJyxcbiAgICAgICAgJzB4ZWRhZGM2ZjY0MzgzZGMxZGY3YzRiMmQ1MWI1NDIyNTQwNmQzNmI2NDFmNWU0MWJiYzUyYTU2NjEyYThjNmQxNCcsXG4gICAgICAgICcweDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDEnLCAvLyBMQVNUIDFcbiAgICAgIF0sXG4gICAgICAvLyB5TnVtXG4gICAgICBbXG4gICAgICAgICcweDRiZGExMmY2ODRiZGExMmY2ODRiZGExMmY2ODRiZGExMmY2ODRiZGExMmY2ODRiZGExMmY2ODRiOGUzOGUyM2MnLFxuICAgICAgICAnMHhjNzVlMGMzMmQ1Y2I3YzBmYTlkMGE1NGIxMmEwYTZkNTY0N2FiMDQ2ZDY4NmRhNmZkZmZjOTBmYzIwMWQ3MWEzJyxcbiAgICAgICAgJzB4MjlhNjE5NDY5MWY5MWE3MzcxNTIwOWVmNjUxMmU1NzY3MjI4MzBhMjAxYmUyMDE4YTc2NWU4NWE5ZWNlZTkzMScsXG4gICAgICAgICcweDJmNjg0YmRhMTJmNjg0YmRhMTJmNjg0YmRhMTJmNjg0YmRhMTJmNjg0YmRhMTJmNjg0YmRhMTJmMzhlMzhkODQnLFxuICAgICAgXSxcbiAgICAgIC8vIHlEZW5cbiAgICAgIFtcbiAgICAgICAgJzB4ZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmVmZmZmZjkzYicsXG4gICAgICAgICcweDdhMDY1MzRiYjhiZGI0OWZkNWU5ZTY2MzI3MjJjMjk4OTQ2N2MxYmZjOGU4ZDk3OGRmYjQyNWQyNjg1YzI1NzMnLFxuICAgICAgICAnMHg2NDg0YWE3MTY1NDVjYTJjZjNhNzBjM2ZhOGZlMzM3ZTBhM2QyMTE2MmYwZDYyOTlhN2JmODE5MmJmZDJhNzZmJyxcbiAgICAgICAgJzB4MDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMScsIC8vIExBU1QgMVxuICAgICAgXSxcbiAgICBdLm1hcCgoaSkgPT4gaS5tYXAoKGopID0+IEJpZ0ludChqKSkpIGFzIFtiaWdpbnRbXSwgYmlnaW50W10sIGJpZ2ludFtdLCBiaWdpbnRbXV1cbiAgKSkoKTtcbmNvbnN0IG1hcFNXVSA9IC8qIEBfX1BVUkVfXyAqLyAoKCkgPT5cbiAgbWFwVG9DdXJ2ZVNpbXBsZVNXVShGcGsxLCB7XG4gICAgQTogQmlnSW50KCcweDNmODczMWFiZGQ2NjFhZGNhMDhhNTU1OGYwZjVkMjcyZTk1M2QzNjNjYjZmMGU1ZDQwNTQ0N2MwMWE0NDQ1MzMnKSxcbiAgICBCOiBCaWdJbnQoJzE3NzEnKSxcbiAgICBaOiBGcGsxLmNyZWF0ZShCaWdJbnQoJy0xMScpKSxcbiAgfSkpKCk7XG5cbi8qKiBIYXNoaW5nIC8gZW5jb2RpbmcgdG8gc2VjcDI1NmsxIHBvaW50cyAvIGZpZWxkLiBSRkMgOTM4MCBtZXRob2RzLiAqL1xuZXhwb3J0IGNvbnN0IHNlY3AyNTZrMV9oYXNoZXI6IEgyQ0hhc2hlcjxXZWllcnN0cmFzc1BvaW50Q29uczxiaWdpbnQ+PiA9IC8qIEBfX1BVUkVfXyAqLyAoKCkgPT5cbiAgY3JlYXRlSGFzaGVyKFxuICAgIFBvaW50azEsXG4gICAgKHNjYWxhcnM6IGJpZ2ludFtdKSA9PiB7XG4gICAgICBjb25zdCB7IHgsIHkgfSA9IG1hcFNXVShGcGsxLmNyZWF0ZShzY2FsYXJzWzBdKSk7XG4gICAgICByZXR1cm4gaXNvTWFwKHgsIHkpO1xuICAgIH0sXG4gICAge1xuICAgICAgRFNUOiAnc2VjcDI1NmsxX1hNRDpTSEEtMjU2X1NTV1VfUk9fJyxcbiAgICAgIGVuY29kZURTVDogJ3NlY3AyNTZrMV9YTUQ6U0hBLTI1Nl9TU1dVX05VXycsXG4gICAgICBwOiBGcGsxLk9SREVSLFxuICAgICAgbTogMSxcbiAgICAgIGs6IDEyOCxcbiAgICAgIGV4cGFuZDogJ3htZCcsXG4gICAgICBoYXNoOiBzaGEyNTYsXG4gICAgfVxuICApKSgpO1xuIiwgIi8qKlxuICogU0hBMiBoYXNoIGZ1bmN0aW9uLiBBLmsuYS4gc2hhMjU2LCBzaGEzODQsIHNoYTUxMiwgc2hhNTEyXzIyNCwgc2hhNTEyXzI1Ni5cbiAqIFNIQTI1NiBpcyB0aGUgZmFzdGVzdCBoYXNoIGltcGxlbWVudGFibGUgaW4gSlMsIGV2ZW4gZmFzdGVyIHRoYW4gQmxha2UzLlxuICogQ2hlY2sgb3V0IFtSRkMgNDYzNF0oaHR0cHM6Ly93d3cucmZjLWVkaXRvci5vcmcvcmZjL3JmYzQ2MzQpIGFuZFxuICogW0ZJUFMgMTgwLTRdKGh0dHBzOi8vbnZscHVicy5uaXN0Lmdvdi9uaXN0cHVicy9GSVBTL05JU1QuRklQUy4xODAtNC5wZGYpLlxuICogQG1vZHVsZVxuICovXG5pbXBvcnQgeyBDaGksIEhhc2hNRCwgTWFqLCBTSEEyMjRfSVYsIFNIQTI1Nl9JViwgU0hBMzg0X0lWLCBTSEE1MTJfSVYgfSBmcm9tICcuL19tZC50cyc7XG5pbXBvcnQgKiBhcyB1NjQgZnJvbSAnLi9fdTY0LnRzJztcbmltcG9ydCB7IHR5cGUgQ0hhc2gsIGNsZWFuLCBjcmVhdGVIYXNoZXIsIG9pZE5pc3QsIHJvdHIgfSBmcm9tICcuL3V0aWxzLnRzJztcblxuLyoqXG4gKiBSb3VuZCBjb25zdGFudHM6XG4gKiBGaXJzdCAzMiBiaXRzIG9mIGZyYWN0aW9uYWwgcGFydHMgb2YgdGhlIGN1YmUgcm9vdHMgb2YgdGhlIGZpcnN0IDY0IHByaW1lcyAyLi4zMTEpXG4gKi9cbi8vIHByZXR0aWVyLWlnbm9yZVxuY29uc3QgU0hBMjU2X0sgPSAvKiBAX19QVVJFX18gKi8gVWludDMyQXJyYXkuZnJvbShbXG4gIDB4NDI4YTJmOTgsIDB4NzEzNzQ0OTEsIDB4YjVjMGZiY2YsIDB4ZTliNWRiYTUsIDB4Mzk1NmMyNWIsIDB4NTlmMTExZjEsIDB4OTIzZjgyYTQsIDB4YWIxYzVlZDUsXG4gIDB4ZDgwN2FhOTgsIDB4MTI4MzViMDEsIDB4MjQzMTg1YmUsIDB4NTUwYzdkYzMsIDB4NzJiZTVkNzQsIDB4ODBkZWIxZmUsIDB4OWJkYzA2YTcsIDB4YzE5YmYxNzQsXG4gIDB4ZTQ5YjY5YzEsIDB4ZWZiZTQ3ODYsIDB4MGZjMTlkYzYsIDB4MjQwY2ExY2MsIDB4MmRlOTJjNmYsIDB4NGE3NDg0YWEsIDB4NWNiMGE5ZGMsIDB4NzZmOTg4ZGEsXG4gIDB4OTgzZTUxNTIsIDB4YTgzMWM2NmQsIDB4YjAwMzI3YzgsIDB4YmY1OTdmYzcsIDB4YzZlMDBiZjMsIDB4ZDVhNzkxNDcsIDB4MDZjYTYzNTEsIDB4MTQyOTI5NjcsXG4gIDB4MjdiNzBhODUsIDB4MmUxYjIxMzgsIDB4NGQyYzZkZmMsIDB4NTMzODBkMTMsIDB4NjUwYTczNTQsIDB4NzY2YTBhYmIsIDB4ODFjMmM5MmUsIDB4OTI3MjJjODUsXG4gIDB4YTJiZmU4YTEsIDB4YTgxYTY2NGIsIDB4YzI0YjhiNzAsIDB4Yzc2YzUxYTMsIDB4ZDE5MmU4MTksIDB4ZDY5OTA2MjQsIDB4ZjQwZTM1ODUsIDB4MTA2YWEwNzAsXG4gIDB4MTlhNGMxMTYsIDB4MWUzNzZjMDgsIDB4Mjc0ODc3NGMsIDB4MzRiMGJjYjUsIDB4MzkxYzBjYjMsIDB4NGVkOGFhNGEsIDB4NWI5Y2NhNGYsIDB4NjgyZTZmZjMsXG4gIDB4NzQ4ZjgyZWUsIDB4NzhhNTYzNmYsIDB4ODRjODc4MTQsIDB4OGNjNzAyMDgsIDB4OTBiZWZmZmEsIDB4YTQ1MDZjZWIsIDB4YmVmOWEzZjcsIDB4YzY3MTc4ZjJcbl0pO1xuXG4vKiogUmV1c2FibGUgdGVtcG9yYXJ5IGJ1ZmZlci4gXCJXXCIgY29tZXMgc3RyYWlnaHQgZnJvbSBzcGVjLiAqL1xuY29uc3QgU0hBMjU2X1cgPSAvKiBAX19QVVJFX18gKi8gbmV3IFVpbnQzMkFycmF5KDY0KTtcblxuLyoqIEludGVybmFsIDMyLWJ5dGUgYmFzZSBTSEEyIGhhc2ggY2xhc3MuICovXG5hYnN0cmFjdCBjbGFzcyBTSEEyXzMyQjxUIGV4dGVuZHMgU0hBMl8zMkI8VD4+IGV4dGVuZHMgSGFzaE1EPFQ+IHtcbiAgLy8gV2UgY2Fubm90IHVzZSBhcnJheSBoZXJlIHNpbmNlIGFycmF5IGFsbG93cyBpbmRleGluZyBieSB2YXJpYWJsZVxuICAvLyB3aGljaCBtZWFucyBvcHRpbWl6ZXIvY29tcGlsZXIgY2Fubm90IHVzZSByZWdpc3RlcnMuXG4gIHByb3RlY3RlZCBhYnN0cmFjdCBBOiBudW1iZXI7XG4gIHByb3RlY3RlZCBhYnN0cmFjdCBCOiBudW1iZXI7XG4gIHByb3RlY3RlZCBhYnN0cmFjdCBDOiBudW1iZXI7XG4gIHByb3RlY3RlZCBhYnN0cmFjdCBEOiBudW1iZXI7XG4gIHByb3RlY3RlZCBhYnN0cmFjdCBFOiBudW1iZXI7XG4gIHByb3RlY3RlZCBhYnN0cmFjdCBGOiBudW1iZXI7XG4gIHByb3RlY3RlZCBhYnN0cmFjdCBHOiBudW1iZXI7XG4gIHByb3RlY3RlZCBhYnN0cmFjdCBIOiBudW1iZXI7XG5cbiAgY29uc3RydWN0b3Iob3V0cHV0TGVuOiBudW1iZXIpIHtcbiAgICBzdXBlcig2NCwgb3V0cHV0TGVuLCA4LCBmYWxzZSk7XG4gIH1cbiAgcHJvdGVjdGVkIGdldCgpOiBbbnVtYmVyLCBudW1iZXIsIG51bWJlciwgbnVtYmVyLCBudW1iZXIsIG51bWJlciwgbnVtYmVyLCBudW1iZXJdIHtcbiAgICBjb25zdCB7IEEsIEIsIEMsIEQsIEUsIEYsIEcsIEggfSA9IHRoaXM7XG4gICAgcmV0dXJuIFtBLCBCLCBDLCBELCBFLCBGLCBHLCBIXTtcbiAgfVxuICAvLyBwcmV0dGllci1pZ25vcmVcbiAgcHJvdGVjdGVkIHNldChcbiAgICBBOiBudW1iZXIsIEI6IG51bWJlciwgQzogbnVtYmVyLCBEOiBudW1iZXIsIEU6IG51bWJlciwgRjogbnVtYmVyLCBHOiBudW1iZXIsIEg6IG51bWJlclxuICApOiB2b2lkIHtcbiAgICB0aGlzLkEgPSBBIHwgMDtcbiAgICB0aGlzLkIgPSBCIHwgMDtcbiAgICB0aGlzLkMgPSBDIHwgMDtcbiAgICB0aGlzLkQgPSBEIHwgMDtcbiAgICB0aGlzLkUgPSBFIHwgMDtcbiAgICB0aGlzLkYgPSBGIHwgMDtcbiAgICB0aGlzLkcgPSBHIHwgMDtcbiAgICB0aGlzLkggPSBIIHwgMDtcbiAgfVxuICBwcm90ZWN0ZWQgcHJvY2Vzcyh2aWV3OiBEYXRhVmlldywgb2Zmc2V0OiBudW1iZXIpOiB2b2lkIHtcbiAgICAvLyBFeHRlbmQgdGhlIGZpcnN0IDE2IHdvcmRzIGludG8gdGhlIHJlbWFpbmluZyA0OCB3b3JkcyB3WzE2Li42M10gb2YgdGhlIG1lc3NhZ2Ugc2NoZWR1bGUgYXJyYXlcbiAgICBmb3IgKGxldCBpID0gMDsgaSA8IDE2OyBpKyssIG9mZnNldCArPSA0KSBTSEEyNTZfV1tpXSA9IHZpZXcuZ2V0VWludDMyKG9mZnNldCwgZmFsc2UpO1xuICAgIGZvciAobGV0IGkgPSAxNjsgaSA8IDY0OyBpKyspIHtcbiAgICAgIGNvbnN0IFcxNSA9IFNIQTI1Nl9XW2kgLSAxNV07XG4gICAgICBjb25zdCBXMiA9IFNIQTI1Nl9XW2kgLSAyXTtcbiAgICAgIGNvbnN0IHMwID0gcm90cihXMTUsIDcpIF4gcm90cihXMTUsIDE4KSBeIChXMTUgPj4+IDMpO1xuICAgICAgY29uc3QgczEgPSByb3RyKFcyLCAxNykgXiByb3RyKFcyLCAxOSkgXiAoVzIgPj4+IDEwKTtcbiAgICAgIFNIQTI1Nl9XW2ldID0gKHMxICsgU0hBMjU2X1dbaSAtIDddICsgczAgKyBTSEEyNTZfV1tpIC0gMTZdKSB8IDA7XG4gICAgfVxuICAgIC8vIENvbXByZXNzaW9uIGZ1bmN0aW9uIG1haW4gbG9vcCwgNjQgcm91bmRzXG4gICAgbGV0IHsgQSwgQiwgQywgRCwgRSwgRiwgRywgSCB9ID0gdGhpcztcbiAgICBmb3IgKGxldCBpID0gMDsgaSA8IDY0OyBpKyspIHtcbiAgICAgIGNvbnN0IHNpZ21hMSA9IHJvdHIoRSwgNikgXiByb3RyKEUsIDExKSBeIHJvdHIoRSwgMjUpO1xuICAgICAgY29uc3QgVDEgPSAoSCArIHNpZ21hMSArIENoaShFLCBGLCBHKSArIFNIQTI1Nl9LW2ldICsgU0hBMjU2X1dbaV0pIHwgMDtcbiAgICAgIGNvbnN0IHNpZ21hMCA9IHJvdHIoQSwgMikgXiByb3RyKEEsIDEzKSBeIHJvdHIoQSwgMjIpO1xuICAgICAgY29uc3QgVDIgPSAoc2lnbWEwICsgTWFqKEEsIEIsIEMpKSB8IDA7XG4gICAgICBIID0gRztcbiAgICAgIEcgPSBGO1xuICAgICAgRiA9IEU7XG4gICAgICBFID0gKEQgKyBUMSkgfCAwO1xuICAgICAgRCA9IEM7XG4gICAgICBDID0gQjtcbiAgICAgIEIgPSBBO1xuICAgICAgQSA9IChUMSArIFQyKSB8IDA7XG4gICAgfVxuICAgIC8vIEFkZCB0aGUgY29tcHJlc3NlZCBjaHVuayB0byB0aGUgY3VycmVudCBoYXNoIHZhbHVlXG4gICAgQSA9IChBICsgdGhpcy5BKSB8IDA7XG4gICAgQiA9IChCICsgdGhpcy5CKSB8IDA7XG4gICAgQyA9IChDICsgdGhpcy5DKSB8IDA7XG4gICAgRCA9IChEICsgdGhpcy5EKSB8IDA7XG4gICAgRSA9IChFICsgdGhpcy5FKSB8IDA7XG4gICAgRiA9IChGICsgdGhpcy5GKSB8IDA7XG4gICAgRyA9IChHICsgdGhpcy5HKSB8IDA7XG4gICAgSCA9IChIICsgdGhpcy5IKSB8IDA7XG4gICAgdGhpcy5zZXQoQSwgQiwgQywgRCwgRSwgRiwgRywgSCk7XG4gIH1cbiAgcHJvdGVjdGVkIHJvdW5kQ2xlYW4oKTogdm9pZCB7XG4gICAgY2xlYW4oU0hBMjU2X1cpO1xuICB9XG4gIGRlc3Ryb3koKTogdm9pZCB7XG4gICAgdGhpcy5zZXQoMCwgMCwgMCwgMCwgMCwgMCwgMCwgMCk7XG4gICAgY2xlYW4odGhpcy5idWZmZXIpO1xuICB9XG59XG5cbi8qKiBJbnRlcm5hbCBTSEEyLTI1NiBoYXNoIGNsYXNzLiAqL1xuZXhwb3J0IGNsYXNzIF9TSEEyNTYgZXh0ZW5kcyBTSEEyXzMyQjxfU0hBMjU2PiB7XG4gIC8vIFdlIGNhbm5vdCB1c2UgYXJyYXkgaGVyZSBzaW5jZSBhcnJheSBhbGxvd3MgaW5kZXhpbmcgYnkgdmFyaWFibGVcbiAgLy8gd2hpY2ggbWVhbnMgb3B0aW1pemVyL2NvbXBpbGVyIGNhbm5vdCB1c2UgcmVnaXN0ZXJzLlxuICBwcm90ZWN0ZWQgQTogbnVtYmVyID0gU0hBMjU2X0lWWzBdIHwgMDtcbiAgcHJvdGVjdGVkIEI6IG51bWJlciA9IFNIQTI1Nl9JVlsxXSB8IDA7XG4gIHByb3RlY3RlZCBDOiBudW1iZXIgPSBTSEEyNTZfSVZbMl0gfCAwO1xuICBwcm90ZWN0ZWQgRDogbnVtYmVyID0gU0hBMjU2X0lWWzNdIHwgMDtcbiAgcHJvdGVjdGVkIEU6IG51bWJlciA9IFNIQTI1Nl9JVls0XSB8IDA7XG4gIHByb3RlY3RlZCBGOiBudW1iZXIgPSBTSEEyNTZfSVZbNV0gfCAwO1xuICBwcm90ZWN0ZWQgRzogbnVtYmVyID0gU0hBMjU2X0lWWzZdIHwgMDtcbiAgcHJvdGVjdGVkIEg6IG51bWJlciA9IFNIQTI1Nl9JVls3XSB8IDA7XG4gIGNvbnN0cnVjdG9yKCkge1xuICAgIHN1cGVyKDMyKTtcbiAgfVxufVxuXG4vKiogSW50ZXJuYWwgU0hBMi0yMjQgaGFzaCBjbGFzcy4gKi9cbmV4cG9ydCBjbGFzcyBfU0hBMjI0IGV4dGVuZHMgU0hBMl8zMkI8X1NIQTIyND4ge1xuICBwcm90ZWN0ZWQgQTogbnVtYmVyID0gU0hBMjI0X0lWWzBdIHwgMDtcbiAgcHJvdGVjdGVkIEI6IG51bWJlciA9IFNIQTIyNF9JVlsxXSB8IDA7XG4gIHByb3RlY3RlZCBDOiBudW1iZXIgPSBTSEEyMjRfSVZbMl0gfCAwO1xuICBwcm90ZWN0ZWQgRDogbnVtYmVyID0gU0hBMjI0X0lWWzNdIHwgMDtcbiAgcHJvdGVjdGVkIEU6IG51bWJlciA9IFNIQTIyNF9JVls0XSB8IDA7XG4gIHByb3RlY3RlZCBGOiBudW1iZXIgPSBTSEEyMjRfSVZbNV0gfCAwO1xuICBwcm90ZWN0ZWQgRzogbnVtYmVyID0gU0hBMjI0X0lWWzZdIHwgMDtcbiAgcHJvdGVjdGVkIEg6IG51bWJlciA9IFNIQTIyNF9JVls3XSB8IDA7XG4gIGNvbnN0cnVjdG9yKCkge1xuICAgIHN1cGVyKDI4KTtcbiAgfVxufVxuXG4vLyBTSEEyLTUxMiBpcyBzbG93ZXIgdGhhbiBzaGEyNTYgaW4ganMgYmVjYXVzZSB1NjQgb3BlcmF0aW9ucyBhcmUgc2xvdy5cblxuLy8gUm91bmQgY29udGFudHNcbi8vIEZpcnN0IDMyIGJpdHMgb2YgdGhlIGZyYWN0aW9uYWwgcGFydHMgb2YgdGhlIGN1YmUgcm9vdHMgb2YgdGhlIGZpcnN0IDgwIHByaW1lcyAyLi40MDlcbi8vIHByZXR0aWVyLWlnbm9yZVxuY29uc3QgSzUxMiA9IC8qIEBfX1BVUkVfXyAqLyAoKCkgPT4gdTY0LnNwbGl0KFtcbiAgJzB4NDI4YTJmOThkNzI4YWUyMicsICcweDcxMzc0NDkxMjNlZjY1Y2QnLCAnMHhiNWMwZmJjZmVjNGQzYjJmJywgJzB4ZTliNWRiYTU4MTg5ZGJiYycsXG4gICcweDM5NTZjMjViZjM0OGI1MzgnLCAnMHg1OWYxMTFmMWI2MDVkMDE5JywgJzB4OTIzZjgyYTRhZjE5NGY5YicsICcweGFiMWM1ZWQ1ZGE2ZDgxMTgnLFxuICAnMHhkODA3YWE5OGEzMDMwMjQyJywgJzB4MTI4MzViMDE0NTcwNmZiZScsICcweDI0MzE4NWJlNGVlNGIyOGMnLCAnMHg1NTBjN2RjM2Q1ZmZiNGUyJyxcbiAgJzB4NzJiZTVkNzRmMjdiODk2ZicsICcweDgwZGViMWZlM2IxNjk2YjEnLCAnMHg5YmRjMDZhNzI1YzcxMjM1JywgJzB4YzE5YmYxNzRjZjY5MjY5NCcsXG4gICcweGU0OWI2OWMxOWVmMTRhZDInLCAnMHhlZmJlNDc4NjM4NGYyNWUzJywgJzB4MGZjMTlkYzY4YjhjZDViNScsICcweDI0MGNhMWNjNzdhYzljNjUnLFxuICAnMHgyZGU5MmM2ZjU5MmIwMjc1JywgJzB4NGE3NDg0YWE2ZWE2ZTQ4MycsICcweDVjYjBhOWRjYmQ0MWZiZDQnLCAnMHg3NmY5ODhkYTgzMTE1M2I1JyxcbiAgJzB4OTgzZTUxNTJlZTY2ZGZhYicsICcweGE4MzFjNjZkMmRiNDMyMTAnLCAnMHhiMDAzMjdjODk4ZmIyMTNmJywgJzB4YmY1OTdmYzdiZWVmMGVlNCcsXG4gICcweGM2ZTAwYmYzM2RhODhmYzInLCAnMHhkNWE3OTE0NzkzMGFhNzI1JywgJzB4MDZjYTYzNTFlMDAzODI2ZicsICcweDE0MjkyOTY3MGEwZTZlNzAnLFxuICAnMHgyN2I3MGE4NTQ2ZDIyZmZjJywgJzB4MmUxYjIxMzg1YzI2YzkyNicsICcweDRkMmM2ZGZjNWFjNDJhZWQnLCAnMHg1MzM4MGQxMzlkOTViM2RmJyxcbiAgJzB4NjUwYTczNTQ4YmFmNjNkZScsICcweDc2NmEwYWJiM2M3N2IyYTgnLCAnMHg4MWMyYzkyZTQ3ZWRhZWU2JywgJzB4OTI3MjJjODUxNDgyMzUzYicsXG4gICcweGEyYmZlOGExNGNmMTAzNjQnLCAnMHhhODFhNjY0YmJjNDIzMDAxJywgJzB4YzI0YjhiNzBkMGY4OTc5MScsICcweGM3NmM1MWEzMDY1NGJlMzAnLFxuICAnMHhkMTkyZTgxOWQ2ZWY1MjE4JywgJzB4ZDY5OTA2MjQ1NTY1YTkxMCcsICcweGY0MGUzNTg1NTc3MTIwMmEnLCAnMHgxMDZhYTA3MDMyYmJkMWI4JyxcbiAgJzB4MTlhNGMxMTZiOGQyZDBjOCcsICcweDFlMzc2YzA4NTE0MWFiNTMnLCAnMHgyNzQ4Nzc0Y2RmOGVlYjk5JywgJzB4MzRiMGJjYjVlMTliNDhhOCcsXG4gICcweDM5MWMwY2IzYzVjOTVhNjMnLCAnMHg0ZWQ4YWE0YWUzNDE4YWNiJywgJzB4NWI5Y2NhNGY3NzYzZTM3MycsICcweDY4MmU2ZmYzZDZiMmI4YTMnLFxuICAnMHg3NDhmODJlZTVkZWZiMmZjJywgJzB4NzhhNTYzNmY0MzE3MmY2MCcsICcweDg0Yzg3ODE0YTFmMGFiNzInLCAnMHg4Y2M3MDIwODFhNjQzOWVjJyxcbiAgJzB4OTBiZWZmZmEyMzYzMWUyOCcsICcweGE0NTA2Y2ViZGU4MmJkZTknLCAnMHhiZWY5YTNmN2IyYzY3OTE1JywgJzB4YzY3MTc4ZjJlMzcyNTMyYicsXG4gICcweGNhMjczZWNlZWEyNjYxOWMnLCAnMHhkMTg2YjhjNzIxYzBjMjA3JywgJzB4ZWFkYTdkZDZjZGUwZWIxZScsICcweGY1N2Q0ZjdmZWU2ZWQxNzgnLFxuICAnMHgwNmYwNjdhYTcyMTc2ZmJhJywgJzB4MGE2MzdkYzVhMmM4OThhNicsICcweDExM2Y5ODA0YmVmOTBkYWUnLCAnMHgxYjcxMGIzNTEzMWM0NzFiJyxcbiAgJzB4MjhkYjc3ZjUyMzA0N2Q4NCcsICcweDMyY2FhYjdiNDBjNzI0OTMnLCAnMHgzYzllYmUwYTE1YzliZWJjJywgJzB4NDMxZDY3YzQ5YzEwMGQ0YycsXG4gICcweDRjYzVkNGJlY2IzZTQyYjYnLCAnMHg1OTdmMjk5Y2ZjNjU3ZTJhJywgJzB4NWZjYjZmYWIzYWQ2ZmFlYycsICcweDZjNDQxOThjNGE0NzU4MTcnXG5dLm1hcChuID0+IEJpZ0ludChuKSkpKSgpO1xuY29uc3QgU0hBNTEyX0toID0gLyogQF9fUFVSRV9fICovICgoKSA9PiBLNTEyWzBdKSgpO1xuY29uc3QgU0hBNTEyX0tsID0gLyogQF9fUFVSRV9fICovICgoKSA9PiBLNTEyWzFdKSgpO1xuXG4vLyBSZXVzYWJsZSB0ZW1wb3JhcnkgYnVmZmVyc1xuY29uc3QgU0hBNTEyX1dfSCA9IC8qIEBfX1BVUkVfXyAqLyBuZXcgVWludDMyQXJyYXkoODApO1xuY29uc3QgU0hBNTEyX1dfTCA9IC8qIEBfX1BVUkVfXyAqLyBuZXcgVWludDMyQXJyYXkoODApO1xuXG4vKiogSW50ZXJuYWwgNjQtYnl0ZSBiYXNlIFNIQTIgaGFzaCBjbGFzcy4gKi9cbmFic3RyYWN0IGNsYXNzIFNIQTJfNjRCPFQgZXh0ZW5kcyBTSEEyXzY0QjxUPj4gZXh0ZW5kcyBIYXNoTUQ8VD4ge1xuICAvLyBXZSBjYW5ub3QgdXNlIGFycmF5IGhlcmUgc2luY2UgYXJyYXkgYWxsb3dzIGluZGV4aW5nIGJ5IHZhcmlhYmxlXG4gIC8vIHdoaWNoIG1lYW5zIG9wdGltaXplci9jb21waWxlciBjYW5ub3QgdXNlIHJlZ2lzdGVycy5cbiAgLy8gaCAtLSBoaWdoIDMyIGJpdHMsIGwgLS0gbG93IDMyIGJpdHNcbiAgcHJvdGVjdGVkIGFic3RyYWN0IEFoOiBudW1iZXI7XG4gIHByb3RlY3RlZCBhYnN0cmFjdCBBbDogbnVtYmVyO1xuICBwcm90ZWN0ZWQgYWJzdHJhY3QgQmg6IG51bWJlcjtcbiAgcHJvdGVjdGVkIGFic3RyYWN0IEJsOiBudW1iZXI7XG4gIHByb3RlY3RlZCBhYnN0cmFjdCBDaDogbnVtYmVyO1xuICBwcm90ZWN0ZWQgYWJzdHJhY3QgQ2w6IG51bWJlcjtcbiAgcHJvdGVjdGVkIGFic3RyYWN0IERoOiBudW1iZXI7XG4gIHByb3RlY3RlZCBhYnN0cmFjdCBEbDogbnVtYmVyO1xuICBwcm90ZWN0ZWQgYWJzdHJhY3QgRWg6IG51bWJlcjtcbiAgcHJvdGVjdGVkIGFic3RyYWN0IEVsOiBudW1iZXI7XG4gIHByb3RlY3RlZCBhYnN0cmFjdCBGaDogbnVtYmVyO1xuICBwcm90ZWN0ZWQgYWJzdHJhY3QgRmw6IG51bWJlcjtcbiAgcHJvdGVjdGVkIGFic3RyYWN0IEdoOiBudW1iZXI7XG4gIHByb3RlY3RlZCBhYnN0cmFjdCBHbDogbnVtYmVyO1xuICBwcm90ZWN0ZWQgYWJzdHJhY3QgSGg6IG51bWJlcjtcbiAgcHJvdGVjdGVkIGFic3RyYWN0IEhsOiBudW1iZXI7XG5cbiAgY29uc3RydWN0b3Iob3V0cHV0TGVuOiBudW1iZXIpIHtcbiAgICBzdXBlcigxMjgsIG91dHB1dExlbiwgMTYsIGZhbHNlKTtcbiAgfVxuICAvLyBwcmV0dGllci1pZ25vcmVcbiAgcHJvdGVjdGVkIGdldCgpOiBbXG4gICAgbnVtYmVyLCBudW1iZXIsIG51bWJlciwgbnVtYmVyLCBudW1iZXIsIG51bWJlciwgbnVtYmVyLCBudW1iZXIsXG4gICAgbnVtYmVyLCBudW1iZXIsIG51bWJlciwgbnVtYmVyLCBudW1iZXIsIG51bWJlciwgbnVtYmVyLCBudW1iZXJcbiAgXSB7XG4gICAgY29uc3QgeyBBaCwgQWwsIEJoLCBCbCwgQ2gsIENsLCBEaCwgRGwsIEVoLCBFbCwgRmgsIEZsLCBHaCwgR2wsIEhoLCBIbCB9ID0gdGhpcztcbiAgICByZXR1cm4gW0FoLCBBbCwgQmgsIEJsLCBDaCwgQ2wsIERoLCBEbCwgRWgsIEVsLCBGaCwgRmwsIEdoLCBHbCwgSGgsIEhsXTtcbiAgfVxuICAvLyBwcmV0dGllci1pZ25vcmVcbiAgcHJvdGVjdGVkIHNldChcbiAgICBBaDogbnVtYmVyLCBBbDogbnVtYmVyLCBCaDogbnVtYmVyLCBCbDogbnVtYmVyLCBDaDogbnVtYmVyLCBDbDogbnVtYmVyLCBEaDogbnVtYmVyLCBEbDogbnVtYmVyLFxuICAgIEVoOiBudW1iZXIsIEVsOiBudW1iZXIsIEZoOiBudW1iZXIsIEZsOiBudW1iZXIsIEdoOiBudW1iZXIsIEdsOiBudW1iZXIsIEhoOiBudW1iZXIsIEhsOiBudW1iZXJcbiAgKTogdm9pZCB7XG4gICAgdGhpcy5BaCA9IEFoIHwgMDtcbiAgICB0aGlzLkFsID0gQWwgfCAwO1xuICAgIHRoaXMuQmggPSBCaCB8IDA7XG4gICAgdGhpcy5CbCA9IEJsIHwgMDtcbiAgICB0aGlzLkNoID0gQ2ggfCAwO1xuICAgIHRoaXMuQ2wgPSBDbCB8IDA7XG4gICAgdGhpcy5EaCA9IERoIHwgMDtcbiAgICB0aGlzLkRsID0gRGwgfCAwO1xuICAgIHRoaXMuRWggPSBFaCB8IDA7XG4gICAgdGhpcy5FbCA9IEVsIHwgMDtcbiAgICB0aGlzLkZoID0gRmggfCAwO1xuICAgIHRoaXMuRmwgPSBGbCB8IDA7XG4gICAgdGhpcy5HaCA9IEdoIHwgMDtcbiAgICB0aGlzLkdsID0gR2wgfCAwO1xuICAgIHRoaXMuSGggPSBIaCB8IDA7XG4gICAgdGhpcy5IbCA9IEhsIHwgMDtcbiAgfVxuICBwcm90ZWN0ZWQgcHJvY2Vzcyh2aWV3OiBEYXRhVmlldywgb2Zmc2V0OiBudW1iZXIpOiB2b2lkIHtcbiAgICAvLyBFeHRlbmQgdGhlIGZpcnN0IDE2IHdvcmRzIGludG8gdGhlIHJlbWFpbmluZyA2NCB3b3JkcyB3WzE2Li43OV0gb2YgdGhlIG1lc3NhZ2Ugc2NoZWR1bGUgYXJyYXlcbiAgICBmb3IgKGxldCBpID0gMDsgaSA8IDE2OyBpKyssIG9mZnNldCArPSA0KSB7XG4gICAgICBTSEE1MTJfV19IW2ldID0gdmlldy5nZXRVaW50MzIob2Zmc2V0KTtcbiAgICAgIFNIQTUxMl9XX0xbaV0gPSB2aWV3LmdldFVpbnQzMigob2Zmc2V0ICs9IDQpKTtcbiAgICB9XG4gICAgZm9yIChsZXQgaSA9IDE2OyBpIDwgODA7IGkrKykge1xuICAgICAgLy8gczAgOj0gKHdbaS0xNV0gcmlnaHRyb3RhdGUgMSkgeG9yICh3W2ktMTVdIHJpZ2h0cm90YXRlIDgpIHhvciAod1tpLTE1XSByaWdodHNoaWZ0IDcpXG4gICAgICBjb25zdCBXMTVoID0gU0hBNTEyX1dfSFtpIC0gMTVdIHwgMDtcbiAgICAgIGNvbnN0IFcxNWwgPSBTSEE1MTJfV19MW2kgLSAxNV0gfCAwO1xuICAgICAgY29uc3QgczBoID0gdTY0LnJvdHJTSChXMTVoLCBXMTVsLCAxKSBeIHU2NC5yb3RyU0goVzE1aCwgVzE1bCwgOCkgXiB1NjQuc2hyU0goVzE1aCwgVzE1bCwgNyk7XG4gICAgICBjb25zdCBzMGwgPSB1NjQucm90clNMKFcxNWgsIFcxNWwsIDEpIF4gdTY0LnJvdHJTTChXMTVoLCBXMTVsLCA4KSBeIHU2NC5zaHJTTChXMTVoLCBXMTVsLCA3KTtcbiAgICAgIC8vIHMxIDo9ICh3W2ktMl0gcmlnaHRyb3RhdGUgMTkpIHhvciAod1tpLTJdIHJpZ2h0cm90YXRlIDYxKSB4b3IgKHdbaS0yXSByaWdodHNoaWZ0IDYpXG4gICAgICBjb25zdCBXMmggPSBTSEE1MTJfV19IW2kgLSAyXSB8IDA7XG4gICAgICBjb25zdCBXMmwgPSBTSEE1MTJfV19MW2kgLSAyXSB8IDA7XG4gICAgICBjb25zdCBzMWggPSB1NjQucm90clNIKFcyaCwgVzJsLCAxOSkgXiB1NjQucm90ckJIKFcyaCwgVzJsLCA2MSkgXiB1NjQuc2hyU0goVzJoLCBXMmwsIDYpO1xuICAgICAgY29uc3QgczFsID0gdTY0LnJvdHJTTChXMmgsIFcybCwgMTkpIF4gdTY0LnJvdHJCTChXMmgsIFcybCwgNjEpIF4gdTY0LnNoclNMKFcyaCwgVzJsLCA2KTtcbiAgICAgIC8vIFNIQTI1Nl9XW2ldID0gczAgKyBzMSArIFNIQTI1Nl9XW2kgLSA3XSArIFNIQTI1Nl9XW2kgLSAxNl07XG4gICAgICBjb25zdCBTVU1sID0gdTY0LmFkZDRMKHMwbCwgczFsLCBTSEE1MTJfV19MW2kgLSA3XSwgU0hBNTEyX1dfTFtpIC0gMTZdKTtcbiAgICAgIGNvbnN0IFNVTWggPSB1NjQuYWRkNEgoU1VNbCwgczBoLCBzMWgsIFNIQTUxMl9XX0hbaSAtIDddLCBTSEE1MTJfV19IW2kgLSAxNl0pO1xuICAgICAgU0hBNTEyX1dfSFtpXSA9IFNVTWggfCAwO1xuICAgICAgU0hBNTEyX1dfTFtpXSA9IFNVTWwgfCAwO1xuICAgIH1cbiAgICBsZXQgeyBBaCwgQWwsIEJoLCBCbCwgQ2gsIENsLCBEaCwgRGwsIEVoLCBFbCwgRmgsIEZsLCBHaCwgR2wsIEhoLCBIbCB9ID0gdGhpcztcbiAgICAvLyBDb21wcmVzc2lvbiBmdW5jdGlvbiBtYWluIGxvb3AsIDgwIHJvdW5kc1xuICAgIGZvciAobGV0IGkgPSAwOyBpIDwgODA7IGkrKykge1xuICAgICAgLy8gUzEgOj0gKGUgcmlnaHRyb3RhdGUgMTQpIHhvciAoZSByaWdodHJvdGF0ZSAxOCkgeG9yIChlIHJpZ2h0cm90YXRlIDQxKVxuICAgICAgY29uc3Qgc2lnbWExaCA9IHU2NC5yb3RyU0goRWgsIEVsLCAxNCkgXiB1NjQucm90clNIKEVoLCBFbCwgMTgpIF4gdTY0LnJvdHJCSChFaCwgRWwsIDQxKTtcbiAgICAgIGNvbnN0IHNpZ21hMWwgPSB1NjQucm90clNMKEVoLCBFbCwgMTQpIF4gdTY0LnJvdHJTTChFaCwgRWwsIDE4KSBeIHU2NC5yb3RyQkwoRWgsIEVsLCA0MSk7XG4gICAgICAvL2NvbnN0IFQxID0gKEggKyBzaWdtYTEgKyBDaGkoRSwgRiwgRykgKyBTSEEyNTZfS1tpXSArIFNIQTI1Nl9XW2ldKSB8IDA7XG4gICAgICBjb25zdCBDSEloID0gKEVoICYgRmgpIF4gKH5FaCAmIEdoKTtcbiAgICAgIGNvbnN0IENISWwgPSAoRWwgJiBGbCkgXiAofkVsICYgR2wpO1xuICAgICAgLy8gVDEgPSBIICsgc2lnbWExICsgQ2hpKEUsIEYsIEcpICsgU0hBNTEyX0tbaV0gKyBTSEE1MTJfV1tpXVxuICAgICAgLy8gcHJldHRpZXItaWdub3JlXG4gICAgICBjb25zdCBUMWxsID0gdTY0LmFkZDVMKEhsLCBzaWdtYTFsLCBDSElsLCBTSEE1MTJfS2xbaV0sIFNIQTUxMl9XX0xbaV0pO1xuICAgICAgY29uc3QgVDFoID0gdTY0LmFkZDVIKFQxbGwsIEhoLCBzaWdtYTFoLCBDSEloLCBTSEE1MTJfS2hbaV0sIFNIQTUxMl9XX0hbaV0pO1xuICAgICAgY29uc3QgVDFsID0gVDFsbCB8IDA7XG4gICAgICAvLyBTMCA6PSAoYSByaWdodHJvdGF0ZSAyOCkgeG9yIChhIHJpZ2h0cm90YXRlIDM0KSB4b3IgKGEgcmlnaHRyb3RhdGUgMzkpXG4gICAgICBjb25zdCBzaWdtYTBoID0gdTY0LnJvdHJTSChBaCwgQWwsIDI4KSBeIHU2NC5yb3RyQkgoQWgsIEFsLCAzNCkgXiB1NjQucm90ckJIKEFoLCBBbCwgMzkpO1xuICAgICAgY29uc3Qgc2lnbWEwbCA9IHU2NC5yb3RyU0woQWgsIEFsLCAyOCkgXiB1NjQucm90ckJMKEFoLCBBbCwgMzQpIF4gdTY0LnJvdHJCTChBaCwgQWwsIDM5KTtcbiAgICAgIGNvbnN0IE1BSmggPSAoQWggJiBCaCkgXiAoQWggJiBDaCkgXiAoQmggJiBDaCk7XG4gICAgICBjb25zdCBNQUpsID0gKEFsICYgQmwpIF4gKEFsICYgQ2wpIF4gKEJsICYgQ2wpO1xuICAgICAgSGggPSBHaCB8IDA7XG4gICAgICBIbCA9IEdsIHwgMDtcbiAgICAgIEdoID0gRmggfCAwO1xuICAgICAgR2wgPSBGbCB8IDA7XG4gICAgICBGaCA9IEVoIHwgMDtcbiAgICAgIEZsID0gRWwgfCAwO1xuICAgICAgKHsgaDogRWgsIGw6IEVsIH0gPSB1NjQuYWRkKERoIHwgMCwgRGwgfCAwLCBUMWggfCAwLCBUMWwgfCAwKSk7XG4gICAgICBEaCA9IENoIHwgMDtcbiAgICAgIERsID0gQ2wgfCAwO1xuICAgICAgQ2ggPSBCaCB8IDA7XG4gICAgICBDbCA9IEJsIHwgMDtcbiAgICAgIEJoID0gQWggfCAwO1xuICAgICAgQmwgPSBBbCB8IDA7XG4gICAgICBjb25zdCBBbGwgPSB1NjQuYWRkM0woVDFsLCBzaWdtYTBsLCBNQUpsKTtcbiAgICAgIEFoID0gdTY0LmFkZDNIKEFsbCwgVDFoLCBzaWdtYTBoLCBNQUpoKTtcbiAgICAgIEFsID0gQWxsIHwgMDtcbiAgICB9XG4gICAgLy8gQWRkIHRoZSBjb21wcmVzc2VkIGNodW5rIHRvIHRoZSBjdXJyZW50IGhhc2ggdmFsdWVcbiAgICAoeyBoOiBBaCwgbDogQWwgfSA9IHU2NC5hZGQodGhpcy5BaCB8IDAsIHRoaXMuQWwgfCAwLCBBaCB8IDAsIEFsIHwgMCkpO1xuICAgICh7IGg6IEJoLCBsOiBCbCB9ID0gdTY0LmFkZCh0aGlzLkJoIHwgMCwgdGhpcy5CbCB8IDAsIEJoIHwgMCwgQmwgfCAwKSk7XG4gICAgKHsgaDogQ2gsIGw6IENsIH0gPSB1NjQuYWRkKHRoaXMuQ2ggfCAwLCB0aGlzLkNsIHwgMCwgQ2ggfCAwLCBDbCB8IDApKTtcbiAgICAoeyBoOiBEaCwgbDogRGwgfSA9IHU2NC5hZGQodGhpcy5EaCB8IDAsIHRoaXMuRGwgfCAwLCBEaCB8IDAsIERsIHwgMCkpO1xuICAgICh7IGg6IEVoLCBsOiBFbCB9ID0gdTY0LmFkZCh0aGlzLkVoIHwgMCwgdGhpcy5FbCB8IDAsIEVoIHwgMCwgRWwgfCAwKSk7XG4gICAgKHsgaDogRmgsIGw6IEZsIH0gPSB1NjQuYWRkKHRoaXMuRmggfCAwLCB0aGlzLkZsIHwgMCwgRmggfCAwLCBGbCB8IDApKTtcbiAgICAoeyBoOiBHaCwgbDogR2wgfSA9IHU2NC5hZGQodGhpcy5HaCB8IDAsIHRoaXMuR2wgfCAwLCBHaCB8IDAsIEdsIHwgMCkpO1xuICAgICh7IGg6IEhoLCBsOiBIbCB9ID0gdTY0LmFkZCh0aGlzLkhoIHwgMCwgdGhpcy5IbCB8IDAsIEhoIHwgMCwgSGwgfCAwKSk7XG4gICAgdGhpcy5zZXQoQWgsIEFsLCBCaCwgQmwsIENoLCBDbCwgRGgsIERsLCBFaCwgRWwsIEZoLCBGbCwgR2gsIEdsLCBIaCwgSGwpO1xuICB9XG4gIHByb3RlY3RlZCByb3VuZENsZWFuKCk6IHZvaWQge1xuICAgIGNsZWFuKFNIQTUxMl9XX0gsIFNIQTUxMl9XX0wpO1xuICB9XG4gIGRlc3Ryb3koKTogdm9pZCB7XG4gICAgY2xlYW4odGhpcy5idWZmZXIpO1xuICAgIHRoaXMuc2V0KDAsIDAsIDAsIDAsIDAsIDAsIDAsIDAsIDAsIDAsIDAsIDAsIDAsIDAsIDAsIDApO1xuICB9XG59XG5cbi8qKiBJbnRlcm5hbCBTSEEyLTUxMiBoYXNoIGNsYXNzLiAqL1xuZXhwb3J0IGNsYXNzIF9TSEE1MTIgZXh0ZW5kcyBTSEEyXzY0QjxfU0hBNTEyPiB7XG4gIHByb3RlY3RlZCBBaDogbnVtYmVyID0gU0hBNTEyX0lWWzBdIHwgMDtcbiAgcHJvdGVjdGVkIEFsOiBudW1iZXIgPSBTSEE1MTJfSVZbMV0gfCAwO1xuICBwcm90ZWN0ZWQgQmg6IG51bWJlciA9IFNIQTUxMl9JVlsyXSB8IDA7XG4gIHByb3RlY3RlZCBCbDogbnVtYmVyID0gU0hBNTEyX0lWWzNdIHwgMDtcbiAgcHJvdGVjdGVkIENoOiBudW1iZXIgPSBTSEE1MTJfSVZbNF0gfCAwO1xuICBwcm90ZWN0ZWQgQ2w6IG51bWJlciA9IFNIQTUxMl9JVls1XSB8IDA7XG4gIHByb3RlY3RlZCBEaDogbnVtYmVyID0gU0hBNTEyX0lWWzZdIHwgMDtcbiAgcHJvdGVjdGVkIERsOiBudW1iZXIgPSBTSEE1MTJfSVZbN10gfCAwO1xuICBwcm90ZWN0ZWQgRWg6IG51bWJlciA9IFNIQTUxMl9JVls4XSB8IDA7XG4gIHByb3RlY3RlZCBFbDogbnVtYmVyID0gU0hBNTEyX0lWWzldIHwgMDtcbiAgcHJvdGVjdGVkIEZoOiBudW1iZXIgPSBTSEE1MTJfSVZbMTBdIHwgMDtcbiAgcHJvdGVjdGVkIEZsOiBudW1iZXIgPSBTSEE1MTJfSVZbMTFdIHwgMDtcbiAgcHJvdGVjdGVkIEdoOiBudW1iZXIgPSBTSEE1MTJfSVZbMTJdIHwgMDtcbiAgcHJvdGVjdGVkIEdsOiBudW1iZXIgPSBTSEE1MTJfSVZbMTNdIHwgMDtcbiAgcHJvdGVjdGVkIEhoOiBudW1iZXIgPSBTSEE1MTJfSVZbMTRdIHwgMDtcbiAgcHJvdGVjdGVkIEhsOiBudW1iZXIgPSBTSEE1MTJfSVZbMTVdIHwgMDtcblxuICBjb25zdHJ1Y3RvcigpIHtcbiAgICBzdXBlcig2NCk7XG4gIH1cbn1cblxuLyoqIEludGVybmFsIFNIQTItMzg0IGhhc2ggY2xhc3MuICovXG5leHBvcnQgY2xhc3MgX1NIQTM4NCBleHRlbmRzIFNIQTJfNjRCPF9TSEEzODQ+IHtcbiAgcHJvdGVjdGVkIEFoOiBudW1iZXIgPSBTSEEzODRfSVZbMF0gfCAwO1xuICBwcm90ZWN0ZWQgQWw6IG51bWJlciA9IFNIQTM4NF9JVlsxXSB8IDA7XG4gIHByb3RlY3RlZCBCaDogbnVtYmVyID0gU0hBMzg0X0lWWzJdIHwgMDtcbiAgcHJvdGVjdGVkIEJsOiBudW1iZXIgPSBTSEEzODRfSVZbM10gfCAwO1xuICBwcm90ZWN0ZWQgQ2g6IG51bWJlciA9IFNIQTM4NF9JVls0XSB8IDA7XG4gIHByb3RlY3RlZCBDbDogbnVtYmVyID0gU0hBMzg0X0lWWzVdIHwgMDtcbiAgcHJvdGVjdGVkIERoOiBudW1iZXIgPSBTSEEzODRfSVZbNl0gfCAwO1xuICBwcm90ZWN0ZWQgRGw6IG51bWJlciA9IFNIQTM4NF9JVls3XSB8IDA7XG4gIHByb3RlY3RlZCBFaDogbnVtYmVyID0gU0hBMzg0X0lWWzhdIHwgMDtcbiAgcHJvdGVjdGVkIEVsOiBudW1iZXIgPSBTSEEzODRfSVZbOV0gfCAwO1xuICBwcm90ZWN0ZWQgRmg6IG51bWJlciA9IFNIQTM4NF9JVlsxMF0gfCAwO1xuICBwcm90ZWN0ZWQgRmw6IG51bWJlciA9IFNIQTM4NF9JVlsxMV0gfCAwO1xuICBwcm90ZWN0ZWQgR2g6IG51bWJlciA9IFNIQTM4NF9JVlsxMl0gfCAwO1xuICBwcm90ZWN0ZWQgR2w6IG51bWJlciA9IFNIQTM4NF9JVlsxM10gfCAwO1xuICBwcm90ZWN0ZWQgSGg6IG51bWJlciA9IFNIQTM4NF9JVlsxNF0gfCAwO1xuICBwcm90ZWN0ZWQgSGw6IG51bWJlciA9IFNIQTM4NF9JVlsxNV0gfCAwO1xuXG4gIGNvbnN0cnVjdG9yKCkge1xuICAgIHN1cGVyKDQ4KTtcbiAgfVxufVxuXG4vKipcbiAqIFRydW5jYXRlZCBTSEE1MTIvMjU2IGFuZCBTSEE1MTIvMjI0LlxuICogU0hBNTEyX0lWIGlzIFhPUmVkIHdpdGggMHhhNWE1YTVhNWE1YTVhNWE1LCB0aGVuIHVzZWQgYXMgXCJpbnRlcm1lZGlhcnlcIiBJViBvZiBTSEE1MTIvdC5cbiAqIFRoZW4gdCBoYXNoZXMgc3RyaW5nIHRvIHByb2R1Y2UgcmVzdWx0IElWLlxuICogU2VlIGB0ZXN0L21pc2Mvc2hhMi1nZW4taXYuanNgLlxuICovXG5cbi8qKiBTSEE1MTIvMjI0IElWICovXG5jb25zdCBUMjI0X0lWID0gLyogQF9fUFVSRV9fICovIFVpbnQzMkFycmF5LmZyb20oW1xuICAweDhjM2QzN2M4LCAweDE5NTQ0ZGEyLCAweDczZTE5OTY2LCAweDg5ZGNkNGQ2LCAweDFkZmFiN2FlLCAweDMyZmY5YzgyLCAweDY3OWRkNTE0LCAweDU4MmY5ZmNmLFxuICAweDBmNmQyYjY5LCAweDdiZDQ0ZGE4LCAweDc3ZTM2ZjczLCAweDA0YzQ4OTQyLCAweDNmOWQ4NWE4LCAweDZhMWQzNmM4LCAweDExMTJlNmFkLCAweDkxZDY5MmExLFxuXSk7XG5cbi8qKiBTSEE1MTIvMjU2IElWICovXG5jb25zdCBUMjU2X0lWID0gLyogQF9fUFVSRV9fICovIFVpbnQzMkFycmF5LmZyb20oW1xuICAweDIyMzEyMTk0LCAweGZjMmJmNzJjLCAweDlmNTU1ZmEzLCAweGM4NGM2NGMyLCAweDIzOTNiODZiLCAweDZmNTNiMTUxLCAweDk2Mzg3NzE5LCAweDU5NDBlYWJkLFxuICAweDk2MjgzZWUyLCAweGE4OGVmZmUzLCAweGJlNWUxZTI1LCAweDUzODYzOTkyLCAweDJiMDE5OWZjLCAweDJjODViOGFhLCAweDBlYjcyZGRjLCAweDgxYzUyY2EyLFxuXSk7XG5cbi8qKiBJbnRlcm5hbCBTSEEyLTUxMi8yMjQgaGFzaCBjbGFzcy4gKi9cbmV4cG9ydCBjbGFzcyBfU0hBNTEyXzIyNCBleHRlbmRzIFNIQTJfNjRCPF9TSEE1MTJfMjI0PiB7XG4gIHByb3RlY3RlZCBBaDogbnVtYmVyID0gVDIyNF9JVlswXSB8IDA7XG4gIHByb3RlY3RlZCBBbDogbnVtYmVyID0gVDIyNF9JVlsxXSB8IDA7XG4gIHByb3RlY3RlZCBCaDogbnVtYmVyID0gVDIyNF9JVlsyXSB8IDA7XG4gIHByb3RlY3RlZCBCbDogbnVtYmVyID0gVDIyNF9JVlszXSB8IDA7XG4gIHByb3RlY3RlZCBDaDogbnVtYmVyID0gVDIyNF9JVls0XSB8IDA7XG4gIHByb3RlY3RlZCBDbDogbnVtYmVyID0gVDIyNF9JVls1XSB8IDA7XG4gIHByb3RlY3RlZCBEaDogbnVtYmVyID0gVDIyNF9JVls2XSB8IDA7XG4gIHByb3RlY3RlZCBEbDogbnVtYmVyID0gVDIyNF9JVls3XSB8IDA7XG4gIHByb3RlY3RlZCBFaDogbnVtYmVyID0gVDIyNF9JVls4XSB8IDA7XG4gIHByb3RlY3RlZCBFbDogbnVtYmVyID0gVDIyNF9JVls5XSB8IDA7XG4gIHByb3RlY3RlZCBGaDogbnVtYmVyID0gVDIyNF9JVlsxMF0gfCAwO1xuICBwcm90ZWN0ZWQgRmw6IG51bWJlciA9IFQyMjRfSVZbMTFdIHwgMDtcbiAgcHJvdGVjdGVkIEdoOiBudW1iZXIgPSBUMjI0X0lWWzEyXSB8IDA7XG4gIHByb3RlY3RlZCBHbDogbnVtYmVyID0gVDIyNF9JVlsxM10gfCAwO1xuICBwcm90ZWN0ZWQgSGg6IG51bWJlciA9IFQyMjRfSVZbMTRdIHwgMDtcbiAgcHJvdGVjdGVkIEhsOiBudW1iZXIgPSBUMjI0X0lWWzE1XSB8IDA7XG5cbiAgY29uc3RydWN0b3IoKSB7XG4gICAgc3VwZXIoMjgpO1xuICB9XG59XG5cbi8qKiBJbnRlcm5hbCBTSEEyLTUxMi8yNTYgaGFzaCBjbGFzcy4gKi9cbmV4cG9ydCBjbGFzcyBfU0hBNTEyXzI1NiBleHRlbmRzIFNIQTJfNjRCPF9TSEE1MTJfMjU2PiB7XG4gIHByb3RlY3RlZCBBaDogbnVtYmVyID0gVDI1Nl9JVlswXSB8IDA7XG4gIHByb3RlY3RlZCBBbDogbnVtYmVyID0gVDI1Nl9JVlsxXSB8IDA7XG4gIHByb3RlY3RlZCBCaDogbnVtYmVyID0gVDI1Nl9JVlsyXSB8IDA7XG4gIHByb3RlY3RlZCBCbDogbnVtYmVyID0gVDI1Nl9JVlszXSB8IDA7XG4gIHByb3RlY3RlZCBDaDogbnVtYmVyID0gVDI1Nl9JVls0XSB8IDA7XG4gIHByb3RlY3RlZCBDbDogbnVtYmVyID0gVDI1Nl9JVls1XSB8IDA7XG4gIHByb3RlY3RlZCBEaDogbnVtYmVyID0gVDI1Nl9JVls2XSB8IDA7XG4gIHByb3RlY3RlZCBEbDogbnVtYmVyID0gVDI1Nl9JVls3XSB8IDA7XG4gIHByb3RlY3RlZCBFaDogbnVtYmVyID0gVDI1Nl9JVls4XSB8IDA7XG4gIHByb3RlY3RlZCBFbDogbnVtYmVyID0gVDI1Nl9JVls5XSB8IDA7XG4gIHByb3RlY3RlZCBGaDogbnVtYmVyID0gVDI1Nl9JVlsxMF0gfCAwO1xuICBwcm90ZWN0ZWQgRmw6IG51bWJlciA9IFQyNTZfSVZbMTFdIHwgMDtcbiAgcHJvdGVjdGVkIEdoOiBudW1iZXIgPSBUMjU2X0lWWzEyXSB8IDA7XG4gIHByb3RlY3RlZCBHbDogbnVtYmVyID0gVDI1Nl9JVlsxM10gfCAwO1xuICBwcm90ZWN0ZWQgSGg6IG51bWJlciA9IFQyNTZfSVZbMTRdIHwgMDtcbiAgcHJvdGVjdGVkIEhsOiBudW1iZXIgPSBUMjU2X0lWWzE1XSB8IDA7XG5cbiAgY29uc3RydWN0b3IoKSB7XG4gICAgc3VwZXIoMzIpO1xuICB9XG59XG5cbi8qKlxuICogU0hBMi0yNTYgaGFzaCBmdW5jdGlvbiBmcm9tIFJGQyA0NjM0LiBJbiBKUyBpdCdzIHRoZSBmYXN0ZXN0OiBldmVuIGZhc3RlciB0aGFuIEJsYWtlMy4gU29tZSBpbmZvOlxuICpcbiAqIC0gVHJ5aW5nIDJeMTI4IGhhc2hlcyB3b3VsZCBnZXQgNTAlIGNoYW5jZSBvZiBjb2xsaXNpb24sIHVzaW5nIGJpcnRoZGF5IGF0dGFjay5cbiAqIC0gQlRDIG5ldHdvcmsgaXMgZG9pbmcgMl43MCBoYXNoZXMvc2VjICgyXjk1IGhhc2hlcy95ZWFyKSBhcyBwZXIgMjAyNS5cbiAqIC0gRWFjaCBzaGEyNTYgaGFzaCBpcyBleGVjdXRpbmcgMl4xOCBiaXQgb3BlcmF0aW9ucy5cbiAqIC0gR29vZCAyMDI0IEFTSUNzIGNhbiBkbyAyMDBUaC9zZWMgd2l0aCAzNTAwIHdhdHRzIG9mIHBvd2VyLCBjb3JyZXNwb25kaW5nIHRvIDJeMzYgaGFzaGVzL2pvdWxlLlxuICovXG5leHBvcnQgY29uc3Qgc2hhMjU2OiBDSGFzaDxfU0hBMjU2PiA9IC8qIEBfX1BVUkVfXyAqLyBjcmVhdGVIYXNoZXIoXG4gICgpID0+IG5ldyBfU0hBMjU2KCksXG4gIC8qIEBfX1BVUkVfXyAqLyBvaWROaXN0KDB4MDEpXG4pO1xuLyoqIFNIQTItMjI0IGhhc2ggZnVuY3Rpb24gZnJvbSBSRkMgNDYzNCAqL1xuZXhwb3J0IGNvbnN0IHNoYTIyNDogQ0hhc2g8X1NIQTIyND4gPSAvKiBAX19QVVJFX18gKi8gY3JlYXRlSGFzaGVyKFxuICAoKSA9PiBuZXcgX1NIQTIyNCgpLFxuICAvKiBAX19QVVJFX18gKi8gb2lkTmlzdCgweDA0KVxuKTtcblxuLyoqIFNIQTItNTEyIGhhc2ggZnVuY3Rpb24gZnJvbSBSRkMgNDYzNC4gKi9cbmV4cG9ydCBjb25zdCBzaGE1MTI6IENIYXNoPF9TSEE1MTI+ID0gLyogQF9fUFVSRV9fICovIGNyZWF0ZUhhc2hlcihcbiAgKCkgPT4gbmV3IF9TSEE1MTIoKSxcbiAgLyogQF9fUFVSRV9fICovIG9pZE5pc3QoMHgwMylcbik7XG4vKiogU0hBMi0zODQgaGFzaCBmdW5jdGlvbiBmcm9tIFJGQyA0NjM0LiAqL1xuZXhwb3J0IGNvbnN0IHNoYTM4NDogQ0hhc2g8X1NIQTM4ND4gPSAvKiBAX19QVVJFX18gKi8gY3JlYXRlSGFzaGVyKFxuICAoKSA9PiBuZXcgX1NIQTM4NCgpLFxuICAvKiBAX19QVVJFX18gKi8gb2lkTmlzdCgweDAyKVxuKTtcblxuLyoqXG4gKiBTSEEyLTUxMi8yNTYgXCJ0cnVuY2F0ZWRcIiBoYXNoIGZ1bmN0aW9uLCB3aXRoIGltcHJvdmVkIHJlc2lzdGFuY2UgdG8gbGVuZ3RoIGV4dGVuc2lvbiBhdHRhY2tzLlxuICogU2VlIHRoZSBwYXBlciBvbiBbdHJ1bmNhdGVkIFNIQTUxMl0oaHR0cHM6Ly9lcHJpbnQuaWFjci5vcmcvMjAxMC81NDgucGRmKS5cbiAqL1xuZXhwb3J0IGNvbnN0IHNoYTUxMl8yNTY6IENIYXNoPF9TSEE1MTJfMjU2PiA9IC8qIEBfX1BVUkVfXyAqLyBjcmVhdGVIYXNoZXIoXG4gICgpID0+IG5ldyBfU0hBNTEyXzI1NigpLFxuICAvKiBAX19QVVJFX18gKi8gb2lkTmlzdCgweDA2KVxuKTtcbi8qKlxuICogU0hBMi01MTIvMjI0IFwidHJ1bmNhdGVkXCIgaGFzaCBmdW5jdGlvbiwgd2l0aCBpbXByb3ZlZCByZXNpc3RhbmNlIHRvIGxlbmd0aCBleHRlbnNpb24gYXR0YWNrcy5cbiAqIFNlZSB0aGUgcGFwZXIgb24gW3RydW5jYXRlZCBTSEE1MTJdKGh0dHBzOi8vZXByaW50LmlhY3Iub3JnLzIwMTAvNTQ4LnBkZikuXG4gKi9cbmV4cG9ydCBjb25zdCBzaGE1MTJfMjI0OiBDSGFzaDxfU0hBNTEyXzIyND4gPSAvKiBAX19QVVJFX18gKi8gY3JlYXRlSGFzaGVyKFxuICAoKSA9PiBuZXcgX1NIQTUxMl8yMjQoKSxcbiAgLyogQF9fUFVSRV9fICovIG9pZE5pc3QoMHgwNSlcbik7XG4iLCAiLyoqXG4gKiBJbnRlcm5hbCBNZXJrbGUtRGFtZ2FyZCBoYXNoIHV0aWxzLlxuICogQG1vZHVsZVxuICovXG5pbXBvcnQgeyBhYnl0ZXMsIGFleGlzdHMsIGFvdXRwdXQsIGNsZWFuLCBjcmVhdGVWaWV3LCB0eXBlIEhhc2ggfSBmcm9tICcuL3V0aWxzLnRzJztcblxuLyoqIENob2ljZTogYSA/IGIgOiBjICovXG5leHBvcnQgZnVuY3Rpb24gQ2hpKGE6IG51bWJlciwgYjogbnVtYmVyLCBjOiBudW1iZXIpOiBudW1iZXIge1xuICByZXR1cm4gKGEgJiBiKSBeICh+YSAmIGMpO1xufVxuXG4vKiogTWFqb3JpdHkgZnVuY3Rpb24sIHRydWUgaWYgYW55IHR3byBpbnB1dHMgaXMgdHJ1ZS4gKi9cbmV4cG9ydCBmdW5jdGlvbiBNYWooYTogbnVtYmVyLCBiOiBudW1iZXIsIGM6IG51bWJlcik6IG51bWJlciB7XG4gIHJldHVybiAoYSAmIGIpIF4gKGEgJiBjKSBeIChiICYgYyk7XG59XG5cbi8qKlxuICogTWVya2xlLURhbWdhcmQgaGFzaCBjb25zdHJ1Y3Rpb24gYmFzZSBjbGFzcy5cbiAqIENvdWxkIGJlIHVzZWQgdG8gY3JlYXRlIE1ENSwgUklQRU1ELCBTSEExLCBTSEEyLlxuICovXG5leHBvcnQgYWJzdHJhY3QgY2xhc3MgSGFzaE1EPFQgZXh0ZW5kcyBIYXNoTUQ8VD4+IGltcGxlbWVudHMgSGFzaDxUPiB7XG4gIHByb3RlY3RlZCBhYnN0cmFjdCBwcm9jZXNzKGJ1ZjogRGF0YVZpZXcsIG9mZnNldDogbnVtYmVyKTogdm9pZDtcbiAgcHJvdGVjdGVkIGFic3RyYWN0IGdldCgpOiBudW1iZXJbXTtcbiAgcHJvdGVjdGVkIGFic3RyYWN0IHNldCguLi5hcmdzOiBudW1iZXJbXSk6IHZvaWQ7XG4gIGFic3RyYWN0IGRlc3Ryb3koKTogdm9pZDtcbiAgcHJvdGVjdGVkIGFic3RyYWN0IHJvdW5kQ2xlYW4oKTogdm9pZDtcblxuICByZWFkb25seSBibG9ja0xlbjogbnVtYmVyO1xuICByZWFkb25seSBvdXRwdXRMZW46IG51bWJlcjtcbiAgcmVhZG9ubHkgcGFkT2Zmc2V0OiBudW1iZXI7XG4gIHJlYWRvbmx5IGlzTEU6IGJvb2xlYW47XG5cbiAgLy8gRm9yIHBhcnRpYWwgdXBkYXRlcyBsZXNzIHRoYW4gYmxvY2sgc2l6ZVxuICBwcm90ZWN0ZWQgYnVmZmVyOiBVaW50OEFycmF5O1xuICBwcm90ZWN0ZWQgdmlldzogRGF0YVZpZXc7XG4gIHByb3RlY3RlZCBmaW5pc2hlZCA9IGZhbHNlO1xuICBwcm90ZWN0ZWQgbGVuZ3RoID0gMDtcbiAgcHJvdGVjdGVkIHBvcyA9IDA7XG4gIHByb3RlY3RlZCBkZXN0cm95ZWQgPSBmYWxzZTtcblxuICBjb25zdHJ1Y3RvcihibG9ja0xlbjogbnVtYmVyLCBvdXRwdXRMZW46IG51bWJlciwgcGFkT2Zmc2V0OiBudW1iZXIsIGlzTEU6IGJvb2xlYW4pIHtcbiAgICB0aGlzLmJsb2NrTGVuID0gYmxvY2tMZW47XG4gICAgdGhpcy5vdXRwdXRMZW4gPSBvdXRwdXRMZW47XG4gICAgdGhpcy5wYWRPZmZzZXQgPSBwYWRPZmZzZXQ7XG4gICAgdGhpcy5pc0xFID0gaXNMRTtcbiAgICB0aGlzLmJ1ZmZlciA9IG5ldyBVaW50OEFycmF5KGJsb2NrTGVuKTtcbiAgICB0aGlzLnZpZXcgPSBjcmVhdGVWaWV3KHRoaXMuYnVmZmVyKTtcbiAgfVxuICB1cGRhdGUoZGF0YTogVWludDhBcnJheSk6IHRoaXMge1xuICAgIGFleGlzdHModGhpcyk7XG4gICAgYWJ5dGVzKGRhdGEpO1xuICAgIGNvbnN0IHsgdmlldywgYnVmZmVyLCBibG9ja0xlbiB9ID0gdGhpcztcbiAgICBjb25zdCBsZW4gPSBkYXRhLmxlbmd0aDtcbiAgICBmb3IgKGxldCBwb3MgPSAwOyBwb3MgPCBsZW47ICkge1xuICAgICAgY29uc3QgdGFrZSA9IE1hdGgubWluKGJsb2NrTGVuIC0gdGhpcy5wb3MsIGxlbiAtIHBvcyk7XG4gICAgICAvLyBGYXN0IHBhdGg6IHdlIGhhdmUgYXQgbGVhc3Qgb25lIGJsb2NrIGluIGlucHV0LCBjYXN0IGl0IHRvIHZpZXcgYW5kIHByb2Nlc3NcbiAgICAgIGlmICh0YWtlID09PSBibG9ja0xlbikge1xuICAgICAgICBjb25zdCBkYXRhVmlldyA9IGNyZWF0ZVZpZXcoZGF0YSk7XG4gICAgICAgIGZvciAoOyBibG9ja0xlbiA8PSBsZW4gLSBwb3M7IHBvcyArPSBibG9ja0xlbikgdGhpcy5wcm9jZXNzKGRhdGFWaWV3LCBwb3MpO1xuICAgICAgICBjb250aW51ZTtcbiAgICAgIH1cbiAgICAgIGJ1ZmZlci5zZXQoZGF0YS5zdWJhcnJheShwb3MsIHBvcyArIHRha2UpLCB0aGlzLnBvcyk7XG4gICAgICB0aGlzLnBvcyArPSB0YWtlO1xuICAgICAgcG9zICs9IHRha2U7XG4gICAgICBpZiAodGhpcy5wb3MgPT09IGJsb2NrTGVuKSB7XG4gICAgICAgIHRoaXMucHJvY2Vzcyh2aWV3LCAwKTtcbiAgICAgICAgdGhpcy5wb3MgPSAwO1xuICAgICAgfVxuICAgIH1cbiAgICB0aGlzLmxlbmd0aCArPSBkYXRhLmxlbmd0aDtcbiAgICB0aGlzLnJvdW5kQ2xlYW4oKTtcbiAgICByZXR1cm4gdGhpcztcbiAgfVxuICBkaWdlc3RJbnRvKG91dDogVWludDhBcnJheSk6IHZvaWQge1xuICAgIGFleGlzdHModGhpcyk7XG4gICAgYW91dHB1dChvdXQsIHRoaXMpO1xuICAgIHRoaXMuZmluaXNoZWQgPSB0cnVlO1xuICAgIC8vIFBhZGRpbmdcbiAgICAvLyBXZSBjYW4gYXZvaWQgYWxsb2NhdGlvbiBvZiBidWZmZXIgZm9yIHBhZGRpbmcgY29tcGxldGVseSBpZiBpdFxuICAgIC8vIHdhcyBwcmV2aW91c2x5IG5vdCBhbGxvY2F0ZWQgaGVyZS4gQnV0IGl0IHdvbid0IGNoYW5nZSBwZXJmb3JtYW5jZS5cbiAgICBjb25zdCB7IGJ1ZmZlciwgdmlldywgYmxvY2tMZW4sIGlzTEUgfSA9IHRoaXM7XG4gICAgbGV0IHsgcG9zIH0gPSB0aGlzO1xuICAgIC8vIGFwcGVuZCB0aGUgYml0ICcxJyB0byB0aGUgbWVzc2FnZVxuICAgIGJ1ZmZlcltwb3MrK10gPSAwYjEwMDAwMDAwO1xuICAgIGNsZWFuKHRoaXMuYnVmZmVyLnN1YmFycmF5KHBvcykpO1xuICAgIC8vIHdlIGhhdmUgbGVzcyB0aGFuIHBhZE9mZnNldCBsZWZ0IGluIGJ1ZmZlciwgc28gd2UgY2Fubm90IHB1dCBsZW5ndGggaW5cbiAgICAvLyBjdXJyZW50IGJsb2NrLCBuZWVkIHByb2Nlc3MgaXQgYW5kIHBhZCBhZ2FpblxuICAgIGlmICh0aGlzLnBhZE9mZnNldCA+IGJsb2NrTGVuIC0gcG9zKSB7XG4gICAgICB0aGlzLnByb2Nlc3ModmlldywgMCk7XG4gICAgICBwb3MgPSAwO1xuICAgIH1cbiAgICAvLyBQYWQgdW50aWwgZnVsbCBibG9jayBieXRlIHdpdGggemVyb3NcbiAgICBmb3IgKGxldCBpID0gcG9zOyBpIDwgYmxvY2tMZW47IGkrKykgYnVmZmVyW2ldID0gMDtcbiAgICAvLyBOb3RlOiBzaGE1MTIgcmVxdWlyZXMgbGVuZ3RoIHRvIGJlIDEyOGJpdCBpbnRlZ2VyLCBidXQgbGVuZ3RoIGluIEpTIHdpbGwgb3ZlcmZsb3cgYmVmb3JlIHRoYXRcbiAgICAvLyBZb3UgbmVlZCB0byB3cml0ZSBhcm91bmQgMiBleGFieXRlcyAodTY0X21heCAvIDggLyAoMTAyNCoqNikpIGZvciB0aGlzIHRvIGhhcHBlbi5cbiAgICAvLyBTbyB3ZSBqdXN0IHdyaXRlIGxvd2VzdCA2NCBiaXRzIG9mIHRoYXQgdmFsdWUuXG4gICAgdmlldy5zZXRCaWdVaW50NjQoYmxvY2tMZW4gLSA4LCBCaWdJbnQodGhpcy5sZW5ndGggKiA4KSwgaXNMRSk7XG4gICAgdGhpcy5wcm9jZXNzKHZpZXcsIDApO1xuICAgIGNvbnN0IG92aWV3ID0gY3JlYXRlVmlldyhvdXQpO1xuICAgIGNvbnN0IGxlbiA9IHRoaXMub3V0cHV0TGVuO1xuICAgIC8vIE5PVEU6IHdlIGRvIGRpdmlzaW9uIGJ5IDQgbGF0ZXIsIHdoaWNoIG11c3QgYmUgZnVzZWQgaW4gc2luZ2xlIG9wIHdpdGggbW9kdWxvIGJ5IEpJVFxuICAgIGlmIChsZW4gJSA0KSB0aHJvdyBuZXcgRXJyb3IoJ19zaGEyOiBvdXRwdXRMZW4gbXVzdCBiZSBhbGlnbmVkIHRvIDMyYml0Jyk7XG4gICAgY29uc3Qgb3V0TGVuID0gbGVuIC8gNDtcbiAgICBjb25zdCBzdGF0ZSA9IHRoaXMuZ2V0KCk7XG4gICAgaWYgKG91dExlbiA+IHN0YXRlLmxlbmd0aCkgdGhyb3cgbmV3IEVycm9yKCdfc2hhMjogb3V0cHV0TGVuIGJpZ2dlciB0aGFuIHN0YXRlJyk7XG4gICAgZm9yIChsZXQgaSA9IDA7IGkgPCBvdXRMZW47IGkrKykgb3ZpZXcuc2V0VWludDMyKDQgKiBpLCBzdGF0ZVtpXSwgaXNMRSk7XG4gIH1cbiAgZGlnZXN0KCk6IFVpbnQ4QXJyYXkge1xuICAgIGNvbnN0IHsgYnVmZmVyLCBvdXRwdXRMZW4gfSA9IHRoaXM7XG4gICAgdGhpcy5kaWdlc3RJbnRvKGJ1ZmZlcik7XG4gICAgY29uc3QgcmVzID0gYnVmZmVyLnNsaWNlKDAsIG91dHB1dExlbik7XG4gICAgdGhpcy5kZXN0cm95KCk7XG4gICAgcmV0dXJuIHJlcztcbiAgfVxuICBfY2xvbmVJbnRvKHRvPzogVCk6IFQge1xuICAgIHRvIHx8PSBuZXcgKHRoaXMuY29uc3RydWN0b3IgYXMgYW55KSgpIGFzIFQ7XG4gICAgdG8uc2V0KC4uLnRoaXMuZ2V0KCkpO1xuICAgIGNvbnN0IHsgYmxvY2tMZW4sIGJ1ZmZlciwgbGVuZ3RoLCBmaW5pc2hlZCwgZGVzdHJveWVkLCBwb3MgfSA9IHRoaXM7XG4gICAgdG8uZGVzdHJveWVkID0gZGVzdHJveWVkO1xuICAgIHRvLmZpbmlzaGVkID0gZmluaXNoZWQ7XG4gICAgdG8ubGVuZ3RoID0gbGVuZ3RoO1xuICAgIHRvLnBvcyA9IHBvcztcbiAgICBpZiAobGVuZ3RoICUgYmxvY2tMZW4pIHRvLmJ1ZmZlci5zZXQoYnVmZmVyKTtcbiAgICByZXR1cm4gdG8gYXMgdW5rbm93biBhcyBhbnk7XG4gIH1cbiAgY2xvbmUoKTogVCB7XG4gICAgcmV0dXJuIHRoaXMuX2Nsb25lSW50bygpO1xuICB9XG59XG5cbi8qKlxuICogSW5pdGlhbCBTSEEtMiBzdGF0ZTogZnJhY3Rpb25hbCBwYXJ0cyBvZiBzcXVhcmUgcm9vdHMgb2YgZmlyc3QgMTYgcHJpbWVzIDIuLjUzLlxuICogQ2hlY2sgb3V0IGB0ZXN0L21pc2Mvc2hhMi1nZW4taXYuanNgIGZvciByZWNvbXB1dGF0aW9uIGd1aWRlLlxuICovXG5cbi8qKiBJbml0aWFsIFNIQTI1NiBzdGF0ZS4gQml0cyAwLi4zMiBvZiBmcmFjIHBhcnQgb2Ygc3FydCBvZiBwcmltZXMgMi4uMTkgKi9cbmV4cG9ydCBjb25zdCBTSEEyNTZfSVY6IFVpbnQzMkFycmF5ID0gLyogQF9fUFVSRV9fICovIFVpbnQzMkFycmF5LmZyb20oW1xuICAweDZhMDllNjY3LCAweGJiNjdhZTg1LCAweDNjNmVmMzcyLCAweGE1NGZmNTNhLCAweDUxMGU1MjdmLCAweDliMDU2ODhjLCAweDFmODNkOWFiLCAweDViZTBjZDE5LFxuXSk7XG5cbi8qKiBJbml0aWFsIFNIQTIyNCBzdGF0ZS4gQml0cyAzMi4uNjQgb2YgZnJhYyBwYXJ0IG9mIHNxcnQgb2YgcHJpbWVzIDIzLi41MyAqL1xuZXhwb3J0IGNvbnN0IFNIQTIyNF9JVjogVWludDMyQXJyYXkgPSAvKiBAX19QVVJFX18gKi8gVWludDMyQXJyYXkuZnJvbShbXG4gIDB4YzEwNTllZDgsIDB4MzY3Y2Q1MDcsIDB4MzA3MGRkMTcsIDB4ZjcwZTU5MzksIDB4ZmZjMDBiMzEsIDB4Njg1ODE1MTEsIDB4NjRmOThmYTcsIDB4YmVmYTRmYTQsXG5dKTtcblxuLyoqIEluaXRpYWwgU0hBMzg0IHN0YXRlLiBCaXRzIDAuLjY0IG9mIGZyYWMgcGFydCBvZiBzcXJ0IG9mIHByaW1lcyAyMy4uNTMgKi9cbmV4cG9ydCBjb25zdCBTSEEzODRfSVY6IFVpbnQzMkFycmF5ID0gLyogQF9fUFVSRV9fICovIFVpbnQzMkFycmF5LmZyb20oW1xuICAweGNiYmI5ZDVkLCAweGMxMDU5ZWQ4LCAweDYyOWEyOTJhLCAweDM2N2NkNTA3LCAweDkxNTkwMTVhLCAweDMwNzBkZDE3LCAweDE1MmZlY2Q4LCAweGY3MGU1OTM5LFxuICAweDY3MzMyNjY3LCAweGZmYzAwYjMxLCAweDhlYjQ0YTg3LCAweDY4NTgxNTExLCAweGRiMGMyZTBkLCAweDY0Zjk4ZmE3LCAweDQ3YjU0ODFkLCAweGJlZmE0ZmE0LFxuXSk7XG5cbi8qKiBJbml0aWFsIFNIQTUxMiBzdGF0ZS4gQml0cyAwLi42NCBvZiBmcmFjIHBhcnQgb2Ygc3FydCBvZiBwcmltZXMgMi4uMTkgKi9cbmV4cG9ydCBjb25zdCBTSEE1MTJfSVY6IFVpbnQzMkFycmF5ID0gLyogQF9fUFVSRV9fICovIFVpbnQzMkFycmF5LmZyb20oW1xuICAweDZhMDllNjY3LCAweGYzYmNjOTA4LCAweGJiNjdhZTg1LCAweDg0Y2FhNzNiLCAweDNjNmVmMzcyLCAweGZlOTRmODJiLCAweGE1NGZmNTNhLCAweDVmMWQzNmYxLFxuICAweDUxMGU1MjdmLCAweGFkZTY4MmQxLCAweDliMDU2ODhjLCAweDJiM2U2YzFmLCAweDFmODNkOWFiLCAweGZiNDFiZDZiLCAweDViZTBjZDE5LCAweDEzN2UyMTc5LFxuXSk7XG4iLCAiLyoqXG4gKiBVdGlsaXRpZXMgZm9yIGhleCwgYnl0ZXMsIENTUFJORy5cbiAqIEBtb2R1bGVcbiAqL1xuLyohIG5vYmxlLWhhc2hlcyAtIE1JVCBMaWNlbnNlIChjKSAyMDIyIFBhdWwgTWlsbGVyIChwYXVsbWlsbHIuY29tKSAqL1xuLyoqIENoZWNrcyBpZiBzb21ldGhpbmcgaXMgVWludDhBcnJheS4gQmUgY2FyZWZ1bDogbm9kZWpzIEJ1ZmZlciB3aWxsIHJldHVybiB0cnVlLiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGlzQnl0ZXMoYTogdW5rbm93bik6IGEgaXMgVWludDhBcnJheSB7XG4gIHJldHVybiBhIGluc3RhbmNlb2YgVWludDhBcnJheSB8fCAoQXJyYXlCdWZmZXIuaXNWaWV3KGEpICYmIGEuY29uc3RydWN0b3IubmFtZSA9PT0gJ1VpbnQ4QXJyYXknKTtcbn1cblxuLyoqIEFzc2VydHMgc29tZXRoaW5nIGlzIHBvc2l0aXZlIGludGVnZXIuICovXG5leHBvcnQgZnVuY3Rpb24gYW51bWJlcihuOiBudW1iZXIsIHRpdGxlOiBzdHJpbmcgPSAnJyk6IHZvaWQge1xuICBpZiAoIU51bWJlci5pc1NhZmVJbnRlZ2VyKG4pIHx8IG4gPCAwKSB7XG4gICAgY29uc3QgcHJlZml4ID0gdGl0bGUgJiYgYFwiJHt0aXRsZX1cIiBgO1xuICAgIHRocm93IG5ldyBFcnJvcihgJHtwcmVmaXh9ZXhwZWN0ZWQgaW50ZWdlciA+PSAwLCBnb3QgJHtufWApO1xuICB9XG59XG5cbi8qKiBBc3NlcnRzIHNvbWV0aGluZyBpcyBVaW50OEFycmF5LiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGFieXRlcyh2YWx1ZTogVWludDhBcnJheSwgbGVuZ3RoPzogbnVtYmVyLCB0aXRsZTogc3RyaW5nID0gJycpOiBVaW50OEFycmF5IHtcbiAgY29uc3QgYnl0ZXMgPSBpc0J5dGVzKHZhbHVlKTtcbiAgY29uc3QgbGVuID0gdmFsdWU/Lmxlbmd0aDtcbiAgY29uc3QgbmVlZHNMZW4gPSBsZW5ndGggIT09IHVuZGVmaW5lZDtcbiAgaWYgKCFieXRlcyB8fCAobmVlZHNMZW4gJiYgbGVuICE9PSBsZW5ndGgpKSB7XG4gICAgY29uc3QgcHJlZml4ID0gdGl0bGUgJiYgYFwiJHt0aXRsZX1cIiBgO1xuICAgIGNvbnN0IG9mTGVuID0gbmVlZHNMZW4gPyBgIG9mIGxlbmd0aCAke2xlbmd0aH1gIDogJyc7XG4gICAgY29uc3QgZ290ID0gYnl0ZXMgPyBgbGVuZ3RoPSR7bGVufWAgOiBgdHlwZT0ke3R5cGVvZiB2YWx1ZX1gO1xuICAgIHRocm93IG5ldyBFcnJvcihwcmVmaXggKyAnZXhwZWN0ZWQgVWludDhBcnJheScgKyBvZkxlbiArICcsIGdvdCAnICsgZ290KTtcbiAgfVxuICByZXR1cm4gdmFsdWU7XG59XG5cbi8qKiBBc3NlcnRzIHNvbWV0aGluZyBpcyBoYXNoICovXG5leHBvcnQgZnVuY3Rpb24gYWhhc2goaDogQ0hhc2gpOiB2b2lkIHtcbiAgaWYgKHR5cGVvZiBoICE9PSAnZnVuY3Rpb24nIHx8IHR5cGVvZiBoLmNyZWF0ZSAhPT0gJ2Z1bmN0aW9uJylcbiAgICB0aHJvdyBuZXcgRXJyb3IoJ0hhc2ggbXVzdCB3cmFwcGVkIGJ5IHV0aWxzLmNyZWF0ZUhhc2hlcicpO1xuICBhbnVtYmVyKGgub3V0cHV0TGVuKTtcbiAgYW51bWJlcihoLmJsb2NrTGVuKTtcbn1cblxuLyoqIEFzc2VydHMgYSBoYXNoIGluc3RhbmNlIGhhcyBub3QgYmVlbiBkZXN0cm95ZWQgLyBmaW5pc2hlZCAqL1xuZXhwb3J0IGZ1bmN0aW9uIGFleGlzdHMoaW5zdGFuY2U6IGFueSwgY2hlY2tGaW5pc2hlZCA9IHRydWUpOiB2b2lkIHtcbiAgaWYgKGluc3RhbmNlLmRlc3Ryb3llZCkgdGhyb3cgbmV3IEVycm9yKCdIYXNoIGluc3RhbmNlIGhhcyBiZWVuIGRlc3Ryb3llZCcpO1xuICBpZiAoY2hlY2tGaW5pc2hlZCAmJiBpbnN0YW5jZS5maW5pc2hlZCkgdGhyb3cgbmV3IEVycm9yKCdIYXNoI2RpZ2VzdCgpIGhhcyBhbHJlYWR5IGJlZW4gY2FsbGVkJyk7XG59XG5cbi8qKiBBc3NlcnRzIG91dHB1dCBpcyBwcm9wZXJseS1zaXplZCBieXRlIGFycmF5ICovXG5leHBvcnQgZnVuY3Rpb24gYW91dHB1dChvdXQ6IGFueSwgaW5zdGFuY2U6IGFueSk6IHZvaWQge1xuICBhYnl0ZXMob3V0LCB1bmRlZmluZWQsICdkaWdlc3RJbnRvKCkgb3V0cHV0Jyk7XG4gIGNvbnN0IG1pbiA9IGluc3RhbmNlLm91dHB1dExlbjtcbiAgaWYgKG91dC5sZW5ndGggPCBtaW4pIHtcbiAgICB0aHJvdyBuZXcgRXJyb3IoJ1wiZGlnZXN0SW50bygpIG91dHB1dFwiIGV4cGVjdGVkIHRvIGJlIG9mIGxlbmd0aCA+PScgKyBtaW4pO1xuICB9XG59XG5cbi8qKiBHZW5lcmljIHR5cGUgZW5jb21wYXNzaW5nIDgvMTYvMzItYnl0ZSBhcnJheXMgLSBidXQgbm90IDY0LWJ5dGUuICovXG4vLyBwcmV0dGllci1pZ25vcmVcbmV4cG9ydCB0eXBlIFR5cGVkQXJyYXkgPSBJbnQ4QXJyYXkgfCBVaW50OENsYW1wZWRBcnJheSB8IFVpbnQ4QXJyYXkgfFxuICBVaW50MTZBcnJheSB8IEludDE2QXJyYXkgfCBVaW50MzJBcnJheSB8IEludDMyQXJyYXk7XG5cbi8qKiBDYXN0IHU4IC8gdTE2IC8gdTMyIHRvIHU4LiAqL1xuZXhwb3J0IGZ1bmN0aW9uIHU4KGFycjogVHlwZWRBcnJheSk6IFVpbnQ4QXJyYXkge1xuICByZXR1cm4gbmV3IFVpbnQ4QXJyYXkoYXJyLmJ1ZmZlciwgYXJyLmJ5dGVPZmZzZXQsIGFyci5ieXRlTGVuZ3RoKTtcbn1cblxuLyoqIENhc3QgdTggLyB1MTYgLyB1MzIgdG8gdTMyLiAqL1xuZXhwb3J0IGZ1bmN0aW9uIHUzMihhcnI6IFR5cGVkQXJyYXkpOiBVaW50MzJBcnJheSB7XG4gIHJldHVybiBuZXcgVWludDMyQXJyYXkoYXJyLmJ1ZmZlciwgYXJyLmJ5dGVPZmZzZXQsIE1hdGguZmxvb3IoYXJyLmJ5dGVMZW5ndGggLyA0KSk7XG59XG5cbi8qKiBaZXJvaXplIGEgYnl0ZSBhcnJheS4gV2FybmluZzogSlMgcHJvdmlkZXMgbm8gZ3VhcmFudGVlcy4gKi9cbmV4cG9ydCBmdW5jdGlvbiBjbGVhbiguLi5hcnJheXM6IFR5cGVkQXJyYXlbXSk6IHZvaWQge1xuICBmb3IgKGxldCBpID0gMDsgaSA8IGFycmF5cy5sZW5ndGg7IGkrKykge1xuICAgIGFycmF5c1tpXS5maWxsKDApO1xuICB9XG59XG5cbi8qKiBDcmVhdGUgRGF0YVZpZXcgb2YgYW4gYXJyYXkgZm9yIGVhc3kgYnl0ZS1sZXZlbCBtYW5pcHVsYXRpb24uICovXG5leHBvcnQgZnVuY3Rpb24gY3JlYXRlVmlldyhhcnI6IFR5cGVkQXJyYXkpOiBEYXRhVmlldyB7XG4gIHJldHVybiBuZXcgRGF0YVZpZXcoYXJyLmJ1ZmZlciwgYXJyLmJ5dGVPZmZzZXQsIGFyci5ieXRlTGVuZ3RoKTtcbn1cblxuLyoqIFRoZSByb3RhdGUgcmlnaHQgKGNpcmN1bGFyIHJpZ2h0IHNoaWZ0KSBvcGVyYXRpb24gZm9yIHVpbnQzMiAqL1xuZXhwb3J0IGZ1bmN0aW9uIHJvdHIod29yZDogbnVtYmVyLCBzaGlmdDogbnVtYmVyKTogbnVtYmVyIHtcbiAgcmV0dXJuICh3b3JkIDw8ICgzMiAtIHNoaWZ0KSkgfCAod29yZCA+Pj4gc2hpZnQpO1xufVxuXG4vKiogVGhlIHJvdGF0ZSBsZWZ0IChjaXJjdWxhciBsZWZ0IHNoaWZ0KSBvcGVyYXRpb24gZm9yIHVpbnQzMiAqL1xuZXhwb3J0IGZ1bmN0aW9uIHJvdGwod29yZDogbnVtYmVyLCBzaGlmdDogbnVtYmVyKTogbnVtYmVyIHtcbiAgcmV0dXJuICh3b3JkIDw8IHNoaWZ0KSB8ICgod29yZCA+Pj4gKDMyIC0gc2hpZnQpKSA+Pj4gMCk7XG59XG5cbi8qKiBJcyBjdXJyZW50IHBsYXRmb3JtIGxpdHRsZS1lbmRpYW4/IE1vc3QgYXJlLiBCaWctRW5kaWFuIHBsYXRmb3JtOiBJQk0gKi9cbmV4cG9ydCBjb25zdCBpc0xFOiBib29sZWFuID0gLyogQF9fUFVSRV9fICovICgoKSA9PlxuICBuZXcgVWludDhBcnJheShuZXcgVWludDMyQXJyYXkoWzB4MTEyMjMzNDRdKS5idWZmZXIpWzBdID09PSAweDQ0KSgpO1xuXG4vKiogVGhlIGJ5dGUgc3dhcCBvcGVyYXRpb24gZm9yIHVpbnQzMiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGJ5dGVTd2FwKHdvcmQ6IG51bWJlcik6IG51bWJlciB7XG4gIHJldHVybiAoXG4gICAgKCh3b3JkIDw8IDI0KSAmIDB4ZmYwMDAwMDApIHxcbiAgICAoKHdvcmQgPDwgOCkgJiAweGZmMDAwMCkgfFxuICAgICgod29yZCA+Pj4gOCkgJiAweGZmMDApIHxcbiAgICAoKHdvcmQgPj4+IDI0KSAmIDB4ZmYpXG4gICk7XG59XG4vKiogQ29uZGl0aW9uYWxseSBieXRlIHN3YXAgaWYgb24gYSBiaWctZW5kaWFuIHBsYXRmb3JtICovXG5leHBvcnQgY29uc3Qgc3dhcDhJZkJFOiAobjogbnVtYmVyKSA9PiBudW1iZXIgPSBpc0xFXG4gID8gKG46IG51bWJlcikgPT4gblxuICA6IChuOiBudW1iZXIpID0+IGJ5dGVTd2FwKG4pO1xuXG4vKiogSW4gcGxhY2UgYnl0ZSBzd2FwIGZvciBVaW50MzJBcnJheSAqL1xuZXhwb3J0IGZ1bmN0aW9uIGJ5dGVTd2FwMzIoYXJyOiBVaW50MzJBcnJheSk6IFVpbnQzMkFycmF5IHtcbiAgZm9yIChsZXQgaSA9IDA7IGkgPCBhcnIubGVuZ3RoOyBpKyspIHtcbiAgICBhcnJbaV0gPSBieXRlU3dhcChhcnJbaV0pO1xuICB9XG4gIHJldHVybiBhcnI7XG59XG5cbmV4cG9ydCBjb25zdCBzd2FwMzJJZkJFOiAodTogVWludDMyQXJyYXkpID0+IFVpbnQzMkFycmF5ID0gaXNMRVxuICA/ICh1OiBVaW50MzJBcnJheSkgPT4gdVxuICA6IGJ5dGVTd2FwMzI7XG5cbi8vIEJ1aWx0LWluIGhleCBjb252ZXJzaW9uIGh0dHBzOi8vY2FuaXVzZS5jb20vbWRuLWphdmFzY3JpcHRfYnVpbHRpbnNfdWludDhhcnJheV9mcm9taGV4XG5jb25zdCBoYXNIZXhCdWlsdGluOiBib29sZWFuID0gLyogQF9fUFVSRV9fICovICgoKSA9PlxuICAvLyBAdHMtaWdub3JlXG4gIHR5cGVvZiBVaW50OEFycmF5LmZyb20oW10pLnRvSGV4ID09PSAnZnVuY3Rpb24nICYmIHR5cGVvZiBVaW50OEFycmF5LmZyb21IZXggPT09ICdmdW5jdGlvbicpKCk7XG5cbi8vIEFycmF5IHdoZXJlIGluZGV4IDB4ZjAgKDI0MCkgaXMgbWFwcGVkIHRvIHN0cmluZyAnZjAnXG5jb25zdCBoZXhlcyA9IC8qIEBfX1BVUkVfXyAqLyBBcnJheS5mcm9tKHsgbGVuZ3RoOiAyNTYgfSwgKF8sIGkpID0+XG4gIGkudG9TdHJpbmcoMTYpLnBhZFN0YXJ0KDIsICcwJylcbik7XG5cbi8qKlxuICogQ29udmVydCBieXRlIGFycmF5IHRvIGhleCBzdHJpbmcuIFVzZXMgYnVpbHQtaW4gZnVuY3Rpb24sIHdoZW4gYXZhaWxhYmxlLlxuICogQGV4YW1wbGUgYnl0ZXNUb0hleChVaW50OEFycmF5LmZyb20oWzB4Y2EsIDB4ZmUsIDB4MDEsIDB4MjNdKSkgLy8gJ2NhZmUwMTIzJ1xuICovXG5leHBvcnQgZnVuY3Rpb24gYnl0ZXNUb0hleChieXRlczogVWludDhBcnJheSk6IHN0cmluZyB7XG4gIGFieXRlcyhieXRlcyk7XG4gIC8vIEB0cy1pZ25vcmVcbiAgaWYgKGhhc0hleEJ1aWx0aW4pIHJldHVybiBieXRlcy50b0hleCgpO1xuICAvLyBwcmUtY2FjaGluZyBpbXByb3ZlcyB0aGUgc3BlZWQgNnhcbiAgbGV0IGhleCA9ICcnO1xuICBmb3IgKGxldCBpID0gMDsgaSA8IGJ5dGVzLmxlbmd0aDsgaSsrKSB7XG4gICAgaGV4ICs9IGhleGVzW2J5dGVzW2ldXTtcbiAgfVxuICByZXR1cm4gaGV4O1xufVxuXG4vLyBXZSB1c2Ugb3B0aW1pemVkIHRlY2huaXF1ZSB0byBjb252ZXJ0IGhleCBzdHJpbmcgdG8gYnl0ZSBhcnJheVxuY29uc3QgYXNjaWlzID0geyBfMDogNDgsIF85OiA1NywgQTogNjUsIEY6IDcwLCBhOiA5NywgZjogMTAyIH0gYXMgY29uc3Q7XG5mdW5jdGlvbiBhc2NpaVRvQmFzZTE2KGNoOiBudW1iZXIpOiBudW1iZXIgfCB1bmRlZmluZWQge1xuICBpZiAoY2ggPj0gYXNjaWlzLl8wICYmIGNoIDw9IGFzY2lpcy5fOSkgcmV0dXJuIGNoIC0gYXNjaWlzLl8wOyAvLyAnMicgPT4gNTAtNDhcbiAgaWYgKGNoID49IGFzY2lpcy5BICYmIGNoIDw9IGFzY2lpcy5GKSByZXR1cm4gY2ggLSAoYXNjaWlzLkEgLSAxMCk7IC8vICdCJyA9PiA2Ni0oNjUtMTApXG4gIGlmIChjaCA+PSBhc2NpaXMuYSAmJiBjaCA8PSBhc2NpaXMuZikgcmV0dXJuIGNoIC0gKGFzY2lpcy5hIC0gMTApOyAvLyAnYicgPT4gOTgtKDk3LTEwKVxuICByZXR1cm47XG59XG5cbi8qKlxuICogQ29udmVydCBoZXggc3RyaW5nIHRvIGJ5dGUgYXJyYXkuIFVzZXMgYnVpbHQtaW4gZnVuY3Rpb24sIHdoZW4gYXZhaWxhYmxlLlxuICogQGV4YW1wbGUgaGV4VG9CeXRlcygnY2FmZTAxMjMnKSAvLyBVaW50OEFycmF5LmZyb20oWzB4Y2EsIDB4ZmUsIDB4MDEsIDB4MjNdKVxuICovXG5leHBvcnQgZnVuY3Rpb24gaGV4VG9CeXRlcyhoZXg6IHN0cmluZyk6IFVpbnQ4QXJyYXkge1xuICBpZiAodHlwZW9mIGhleCAhPT0gJ3N0cmluZycpIHRocm93IG5ldyBFcnJvcignaGV4IHN0cmluZyBleHBlY3RlZCwgZ290ICcgKyB0eXBlb2YgaGV4KTtcbiAgLy8gQHRzLWlnbm9yZVxuICBpZiAoaGFzSGV4QnVpbHRpbikgcmV0dXJuIFVpbnQ4QXJyYXkuZnJvbUhleChoZXgpO1xuICBjb25zdCBobCA9IGhleC5sZW5ndGg7XG4gIGNvbnN0IGFsID0gaGwgLyAyO1xuICBpZiAoaGwgJSAyKSB0aHJvdyBuZXcgRXJyb3IoJ2hleCBzdHJpbmcgZXhwZWN0ZWQsIGdvdCB1bnBhZGRlZCBoZXggb2YgbGVuZ3RoICcgKyBobCk7XG4gIGNvbnN0IGFycmF5ID0gbmV3IFVpbnQ4QXJyYXkoYWwpO1xuICBmb3IgKGxldCBhaSA9IDAsIGhpID0gMDsgYWkgPCBhbDsgYWkrKywgaGkgKz0gMikge1xuICAgIGNvbnN0IG4xID0gYXNjaWlUb0Jhc2UxNihoZXguY2hhckNvZGVBdChoaSkpO1xuICAgIGNvbnN0IG4yID0gYXNjaWlUb0Jhc2UxNihoZXguY2hhckNvZGVBdChoaSArIDEpKTtcbiAgICBpZiAobjEgPT09IHVuZGVmaW5lZCB8fCBuMiA9PT0gdW5kZWZpbmVkKSB7XG4gICAgICBjb25zdCBjaGFyID0gaGV4W2hpXSArIGhleFtoaSArIDFdO1xuICAgICAgdGhyb3cgbmV3IEVycm9yKCdoZXggc3RyaW5nIGV4cGVjdGVkLCBnb3Qgbm9uLWhleCBjaGFyYWN0ZXIgXCInICsgY2hhciArICdcIiBhdCBpbmRleCAnICsgaGkpO1xuICAgIH1cbiAgICBhcnJheVthaV0gPSBuMSAqIDE2ICsgbjI7IC8vIG11bHRpcGx5IGZpcnN0IG9jdGV0LCBlLmcuICdhMycgPT4gMTAqMTYrMyA9PiAxNjAgKyAzID0+IDE2M1xuICB9XG4gIHJldHVybiBhcnJheTtcbn1cblxuLyoqXG4gKiBUaGVyZSBpcyBubyBzZXRJbW1lZGlhdGUgaW4gYnJvd3NlciBhbmQgc2V0VGltZW91dCBpcyBzbG93LlxuICogQ2FsbCBvZiBhc3luYyBmbiB3aWxsIHJldHVybiBQcm9taXNlLCB3aGljaCB3aWxsIGJlIGZ1bGxmaWxlZCBvbmx5IG9uXG4gKiBuZXh0IHNjaGVkdWxlciBxdWV1ZSBwcm9jZXNzaW5nIHN0ZXAgYW5kIHRoaXMgaXMgZXhhY3RseSB3aGF0IHdlIG5lZWQuXG4gKi9cbmV4cG9ydCBjb25zdCBuZXh0VGljayA9IGFzeW5jICgpOiBQcm9taXNlPHZvaWQ+ID0+IHt9O1xuXG4vKiogUmV0dXJucyBjb250cm9sIHRvIHRocmVhZCBlYWNoICd0aWNrJyBtcyB0byBhdm9pZCBibG9ja2luZy4gKi9cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBhc3luY0xvb3AoXG4gIGl0ZXJzOiBudW1iZXIsXG4gIHRpY2s6IG51bWJlcixcbiAgY2I6IChpOiBudW1iZXIpID0+IHZvaWRcbik6IFByb21pc2U8dm9pZD4ge1xuICBsZXQgdHMgPSBEYXRlLm5vdygpO1xuICBmb3IgKGxldCBpID0gMDsgaSA8IGl0ZXJzOyBpKyspIHtcbiAgICBjYihpKTtcbiAgICAvLyBEYXRlLm5vdygpIGlzIG5vdCBtb25vdG9uaWMsIHNvIGluIGNhc2UgaWYgY2xvY2sgZ29lcyBiYWNrd2FyZHMgd2UgcmV0dXJuIHJldHVybiBjb250cm9sIHRvb1xuICAgIGNvbnN0IGRpZmYgPSBEYXRlLm5vdygpIC0gdHM7XG4gICAgaWYgKGRpZmYgPj0gMCAmJiBkaWZmIDwgdGljaykgY29udGludWU7XG4gICAgYXdhaXQgbmV4dFRpY2soKTtcbiAgICB0cyArPSBkaWZmO1xuICB9XG59XG5cbi8vIEdsb2JhbCBzeW1ib2xzLCBidXQgdHMgZG9lc24ndCBzZWUgdGhlbTogaHR0cHM6Ly9naXRodWIuY29tL21pY3Jvc29mdC9UeXBlU2NyaXB0L2lzc3Vlcy8zMTUzNVxuZGVjbGFyZSBjb25zdCBUZXh0RW5jb2RlcjogYW55O1xuXG4vKipcbiAqIENvbnZlcnRzIHN0cmluZyB0byBieXRlcyB1c2luZyBVVEY4IGVuY29kaW5nLlxuICogQnVpbHQtaW4gZG9lc24ndCB2YWxpZGF0ZSBpbnB1dCB0byBiZSBzdHJpbmc6IHdlIGRvIHRoZSBjaGVjay5cbiAqIEBleGFtcGxlIHV0ZjhUb0J5dGVzKCdhYmMnKSAvLyBVaW50OEFycmF5LmZyb20oWzk3LCA5OCwgOTldKVxuICovXG5leHBvcnQgZnVuY3Rpb24gdXRmOFRvQnl0ZXMoc3RyOiBzdHJpbmcpOiBVaW50OEFycmF5IHtcbiAgaWYgKHR5cGVvZiBzdHIgIT09ICdzdHJpbmcnKSB0aHJvdyBuZXcgRXJyb3IoJ3N0cmluZyBleHBlY3RlZCcpO1xuICByZXR1cm4gbmV3IFVpbnQ4QXJyYXkobmV3IFRleHRFbmNvZGVyKCkuZW5jb2RlKHN0cikpOyAvLyBodHRwczovL2J1Z3ppbC5sYS8xNjgxODA5XG59XG5cbi8qKiBLREZzIGNhbiBhY2NlcHQgc3RyaW5nIG9yIFVpbnQ4QXJyYXkgZm9yIHVzZXIgY29udmVuaWVuY2UuICovXG5leHBvcnQgdHlwZSBLREZJbnB1dCA9IHN0cmluZyB8IFVpbnQ4QXJyYXk7XG5cbi8qKlxuICogSGVscGVyIGZvciBLREZzOiBjb25zdW1lcyB1aW50OGFycmF5IG9yIHN0cmluZy5cbiAqIFdoZW4gc3RyaW5nIGlzIHBhc3NlZCwgZG9lcyB1dGY4IGRlY29kaW5nLCB1c2luZyBUZXh0RGVjb2Rlci5cbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGtkZklucHV0VG9CeXRlcyhkYXRhOiBLREZJbnB1dCwgZXJyb3JUaXRsZSA9ICcnKTogVWludDhBcnJheSB7XG4gIGlmICh0eXBlb2YgZGF0YSA9PT0gJ3N0cmluZycpIHJldHVybiB1dGY4VG9CeXRlcyhkYXRhKTtcbiAgcmV0dXJuIGFieXRlcyhkYXRhLCB1bmRlZmluZWQsIGVycm9yVGl0bGUpO1xufVxuXG4vKiogQ29waWVzIHNldmVyYWwgVWludDhBcnJheXMgaW50byBvbmUuICovXG5leHBvcnQgZnVuY3Rpb24gY29uY2F0Qnl0ZXMoLi4uYXJyYXlzOiBVaW50OEFycmF5W10pOiBVaW50OEFycmF5IHtcbiAgbGV0IHN1bSA9IDA7XG4gIGZvciAobGV0IGkgPSAwOyBpIDwgYXJyYXlzLmxlbmd0aDsgaSsrKSB7XG4gICAgY29uc3QgYSA9IGFycmF5c1tpXTtcbiAgICBhYnl0ZXMoYSk7XG4gICAgc3VtICs9IGEubGVuZ3RoO1xuICB9XG4gIGNvbnN0IHJlcyA9IG5ldyBVaW50OEFycmF5KHN1bSk7XG4gIGZvciAobGV0IGkgPSAwLCBwYWQgPSAwOyBpIDwgYXJyYXlzLmxlbmd0aDsgaSsrKSB7XG4gICAgY29uc3QgYSA9IGFycmF5c1tpXTtcbiAgICByZXMuc2V0KGEsIHBhZCk7XG4gICAgcGFkICs9IGEubGVuZ3RoO1xuICB9XG4gIHJldHVybiByZXM7XG59XG5cbnR5cGUgRW1wdHlPYmogPSB7fTtcbi8qKiBNZXJnZXMgZGVmYXVsdCBvcHRpb25zIGFuZCBwYXNzZWQgb3B0aW9ucy4gKi9cbmV4cG9ydCBmdW5jdGlvbiBjaGVja09wdHM8VDEgZXh0ZW5kcyBFbXB0eU9iaiwgVDIgZXh0ZW5kcyBFbXB0eU9iaj4oXG4gIGRlZmF1bHRzOiBUMSxcbiAgb3B0cz86IFQyXG4pOiBUMSAmIFQyIHtcbiAgaWYgKG9wdHMgIT09IHVuZGVmaW5lZCAmJiB7fS50b1N0cmluZy5jYWxsKG9wdHMpICE9PSAnW29iamVjdCBPYmplY3RdJylcbiAgICB0aHJvdyBuZXcgRXJyb3IoJ29wdGlvbnMgbXVzdCBiZSBvYmplY3Qgb3IgdW5kZWZpbmVkJyk7XG4gIGNvbnN0IG1lcmdlZCA9IE9iamVjdC5hc3NpZ24oZGVmYXVsdHMsIG9wdHMpO1xuICByZXR1cm4gbWVyZ2VkIGFzIFQxICYgVDI7XG59XG5cbi8qKiBDb21tb24gaW50ZXJmYWNlIGZvciBhbGwgaGFzaGVzLiAqL1xuZXhwb3J0IGludGVyZmFjZSBIYXNoPFQ+IHtcbiAgYmxvY2tMZW46IG51bWJlcjsgLy8gQnl0ZXMgcGVyIGJsb2NrXG4gIG91dHB1dExlbjogbnVtYmVyOyAvLyBCeXRlcyBpbiBvdXRwdXRcbiAgdXBkYXRlKGJ1ZjogVWludDhBcnJheSk6IHRoaXM7XG4gIGRpZ2VzdEludG8oYnVmOiBVaW50OEFycmF5KTogdm9pZDtcbiAgZGlnZXN0KCk6IFVpbnQ4QXJyYXk7XG4gIGRlc3Ryb3koKTogdm9pZDtcbiAgX2Nsb25lSW50byh0bz86IFQpOiBUO1xuICBjbG9uZSgpOiBUO1xufVxuXG4vKiogUHNldWRvUmFuZG9tIChudW1iZXIpIEdlbmVyYXRvciAqL1xuZXhwb3J0IGludGVyZmFjZSBQUkcge1xuICBhZGRFbnRyb3B5KHNlZWQ6IFVpbnQ4QXJyYXkpOiB2b2lkO1xuICByYW5kb21CeXRlcyhsZW5ndGg6IG51bWJlcik6IFVpbnQ4QXJyYXk7XG4gIGNsZWFuKCk6IHZvaWQ7XG59XG5cbi8qKlxuICogWE9GOiBzdHJlYW1pbmcgQVBJIHRvIHJlYWQgZGlnZXN0IGluIGNodW5rcy5cbiAqIFNhbWUgYXMgJ3NxdWVlemUnIGluIGtlY2Nhay9rMTIgYW5kICdzZWVrJyBpbiBibGFrZTMsIGJ1dCBtb3JlIGdlbmVyaWMgbmFtZS5cbiAqIFdoZW4gaGFzaCB1c2VkIGluIFhPRiBtb2RlIGl0IGlzIHVwIHRvIHVzZXIgdG8gY2FsbCAnLmRlc3Ryb3knIGFmdGVyd2FyZHMsIHNpbmNlIHdlIGNhbm5vdFxuICogZGVzdHJveSBzdGF0ZSwgbmV4dCBjYWxsIGNhbiByZXF1aXJlIG1vcmUgYnl0ZXMuXG4gKi9cbmV4cG9ydCB0eXBlIEhhc2hYT0Y8VCBleHRlbmRzIEhhc2g8VD4+ID0gSGFzaDxUPiAmIHtcbiAgeG9mKGJ5dGVzOiBudW1iZXIpOiBVaW50OEFycmF5OyAvLyBSZWFkICdieXRlcycgYnl0ZXMgZnJvbSBkaWdlc3Qgc3RyZWFtXG4gIHhvZkludG8oYnVmOiBVaW50OEFycmF5KTogVWludDhBcnJheTsgLy8gcmVhZCBidWYubGVuZ3RoIGJ5dGVzIGZyb20gZGlnZXN0IHN0cmVhbSBpbnRvIGJ1ZlxufTtcblxuLyoqIEhhc2ggY29uc3RydWN0b3IgKi9cbmV4cG9ydCB0eXBlIEhhc2hlckNvbnM8VCwgT3B0cyA9IHVuZGVmaW5lZD4gPSBPcHRzIGV4dGVuZHMgdW5kZWZpbmVkID8gKCkgPT4gVCA6IChvcHRzPzogT3B0cykgPT4gVDtcbi8qKiBPcHRpb25hbCBoYXNoIHBhcmFtcy4gKi9cbmV4cG9ydCB0eXBlIEhhc2hJbmZvID0ge1xuICBvaWQ/OiBVaW50OEFycmF5OyAvLyBERVIgZW5jb2RlZCBPSUQgaW4gYnl0ZXNcbn07XG4vKiogSGFzaCBmdW5jdGlvbiAqL1xuZXhwb3J0IHR5cGUgQ0hhc2g8VCBleHRlbmRzIEhhc2g8VD4gPSBIYXNoPGFueT4sIE9wdHMgPSB1bmRlZmluZWQ+ID0ge1xuICBvdXRwdXRMZW46IG51bWJlcjtcbiAgYmxvY2tMZW46IG51bWJlcjtcbn0gJiBIYXNoSW5mbyAmXG4gIChPcHRzIGV4dGVuZHMgdW5kZWZpbmVkXG4gICAgPyB7XG4gICAgICAgIChtc2c6IFVpbnQ4QXJyYXkpOiBVaW50OEFycmF5O1xuICAgICAgICBjcmVhdGUoKTogVDtcbiAgICAgIH1cbiAgICA6IHtcbiAgICAgICAgKG1zZzogVWludDhBcnJheSwgb3B0cz86IE9wdHMpOiBVaW50OEFycmF5O1xuICAgICAgICBjcmVhdGUob3B0cz86IE9wdHMpOiBUO1xuICAgICAgfSk7XG4vKiogWE9GIHdpdGggb3V0cHV0ICovXG5leHBvcnQgdHlwZSBDSGFzaFhPRjxUIGV4dGVuZHMgSGFzaFhPRjxUPiA9IEhhc2hYT0Y8YW55PiwgT3B0cyA9IHVuZGVmaW5lZD4gPSBDSGFzaDxULCBPcHRzPjtcblxuLyoqIENyZWF0ZXMgZnVuY3Rpb24gd2l0aCBvdXRwdXRMZW4sIGJsb2NrTGVuLCBjcmVhdGUgcHJvcGVydGllcyBmcm9tIGEgY2xhc3MgY29uc3RydWN0b3IuICovXG5leHBvcnQgZnVuY3Rpb24gY3JlYXRlSGFzaGVyPFQgZXh0ZW5kcyBIYXNoPFQ+LCBPcHRzID0gdW5kZWZpbmVkPihcbiAgaGFzaENvbnM6IEhhc2hlckNvbnM8VCwgT3B0cz4sXG4gIGluZm86IEhhc2hJbmZvID0ge31cbik6IENIYXNoPFQsIE9wdHM+IHtcbiAgY29uc3QgaGFzaEM6IGFueSA9IChtc2c6IFVpbnQ4QXJyYXksIG9wdHM/OiBPcHRzKSA9PiBoYXNoQ29ucyhvcHRzKS51cGRhdGUobXNnKS5kaWdlc3QoKTtcbiAgY29uc3QgdG1wID0gaGFzaENvbnModW5kZWZpbmVkKTtcbiAgaGFzaEMub3V0cHV0TGVuID0gdG1wLm91dHB1dExlbjtcbiAgaGFzaEMuYmxvY2tMZW4gPSB0bXAuYmxvY2tMZW47XG4gIGhhc2hDLmNyZWF0ZSA9IChvcHRzPzogT3B0cykgPT4gaGFzaENvbnMob3B0cyk7XG4gIE9iamVjdC5hc3NpZ24oaGFzaEMsIGluZm8pO1xuICByZXR1cm4gT2JqZWN0LmZyZWV6ZShoYXNoQyk7XG59XG5cbi8qKiBDcnlwdG9ncmFwaGljYWxseSBzZWN1cmUgUFJORy4gVXNlcyBpbnRlcm5hbCBPUy1sZXZlbCBgY3J5cHRvLmdldFJhbmRvbVZhbHVlc2AuICovXG5leHBvcnQgZnVuY3Rpb24gcmFuZG9tQnl0ZXMoYnl0ZXNMZW5ndGggPSAzMik6IFVpbnQ4QXJyYXkge1xuICBjb25zdCBjciA9IHR5cGVvZiBnbG9iYWxUaGlzID09PSAnb2JqZWN0JyA/IChnbG9iYWxUaGlzIGFzIGFueSkuY3J5cHRvIDogbnVsbDtcbiAgaWYgKHR5cGVvZiBjcj8uZ2V0UmFuZG9tVmFsdWVzICE9PSAnZnVuY3Rpb24nKVxuICAgIHRocm93IG5ldyBFcnJvcignY3J5cHRvLmdldFJhbmRvbVZhbHVlcyBtdXN0IGJlIGRlZmluZWQnKTtcbiAgcmV0dXJuIGNyLmdldFJhbmRvbVZhbHVlcyhuZXcgVWludDhBcnJheShieXRlc0xlbmd0aCkpO1xufVxuXG4vKiogQ3JlYXRlcyBPSUQgb3B0cyBmb3IgTklTVCBoYXNoZXMsIHdpdGggcHJlZml4IDA2IDA5IDYwIDg2IDQ4IDAxIDY1IDAzIDA0IDAyLiAqL1xuZXhwb3J0IGNvbnN0IG9pZE5pc3QgPSAoc3VmZml4OiBudW1iZXIpOiBSZXF1aXJlZDxIYXNoSW5mbz4gPT4gKHtcbiAgb2lkOiBVaW50OEFycmF5LmZyb20oWzB4MDYsIDB4MDksIDB4NjAsIDB4ODYsIDB4NDgsIDB4MDEsIDB4NjUsIDB4MDMsIDB4MDQsIDB4MDIsIHN1ZmZpeF0pLFxufSk7XG4iLCAiLyoqXG4gKiBNZXRob2RzIGZvciBlbGxpcHRpYyBjdXJ2ZSBtdWx0aXBsaWNhdGlvbiBieSBzY2FsYXJzLlxuICogQ29udGFpbnMgd05BRiwgcGlwcGVuZ2VyLlxuICogQG1vZHVsZVxuICovXG4vKiEgbm9ibGUtY3VydmVzIC0gTUlUIExpY2Vuc2UgKGMpIDIwMjIgUGF1bCBNaWxsZXIgKHBhdWxtaWxsci5jb20pICovXG5pbXBvcnQgeyBiaXRMZW4sIGJpdE1hc2ssIHR5cGUgU2lnbmVyIH0gZnJvbSAnLi4vdXRpbHMudHMnO1xuaW1wb3J0IHsgRmllbGQsIEZwSW52ZXJ0QmF0Y2gsIHZhbGlkYXRlRmllbGQsIHR5cGUgSUZpZWxkIH0gZnJvbSAnLi9tb2R1bGFyLnRzJztcblxuY29uc3QgXzBuID0gLyogQF9fUFVSRV9fICovIEJpZ0ludCgwKTtcbmNvbnN0IF8xbiA9IC8qIEBfX1BVUkVfXyAqLyBCaWdJbnQoMSk7XG5cbmV4cG9ydCB0eXBlIEFmZmluZVBvaW50PFQ+ID0ge1xuICB4OiBUO1xuICB5OiBUO1xufSAmIHsgWj86IG5ldmVyIH07XG5cbi8vIFdlIGNhbid0IFwiYWJzdHJhY3Qgb3V0XCIgY29vcmRpbmF0ZXMgKFgsIFksIFo7IGFuZCBUIGluIEVkd2FyZHMpOiBhcmd1bWVudCBuYW1lcyBvZiBjb25zdHJ1Y3RvclxuLy8gYXJlIG5vdCBhY2Nlc3NpYmxlLiBTZWUgVHlwZXNjcmlwdCBnaC01NjA5MywgZ2gtNDE1OTQuXG4vL1xuLy8gV2UgaGF2ZSB0byB1c2UgcmVjdXJzaXZlIHR5cGVzLCBzbyBpdCB3aWxsIHJldHVybiBhY3R1YWwgcG9pbnQsIG5vdCBjb25zdGFpbmVkIGBDdXJ2ZVBvaW50YC5cbi8vIElmLCBhdCBhbnkgcG9pbnQsIFAgaXMgYGFueWAsIGl0IHdpbGwgZXJhc2UgYWxsIHR5cGVzIGFuZCByZXBsYWNlIGl0XG4vLyB3aXRoIGBhbnlgLCBiZWNhdXNlIG9mIHJlY3Vyc2lvbiwgYGFueSBpbXBsZW1lbnRzIEN1cnZlUG9pbnRgLFxuLy8gYnV0IHdlIGxvc2UgYWxsIGNvbnN0cmFpbnMgb24gbWV0aG9kcy5cblxuLyoqIEJhc2UgaW50ZXJmYWNlIGZvciBhbGwgZWxsaXB0aWMgY3VydmUgUG9pbnRzLiAqL1xuZXhwb3J0IGludGVyZmFjZSBDdXJ2ZVBvaW50PEYsIFAgZXh0ZW5kcyBDdXJ2ZVBvaW50PEYsIFA+PiB7XG4gIC8qKiBBZmZpbmUgeCBjb29yZGluYXRlLiBEaWZmZXJlbnQgZnJvbSBwcm9qZWN0aXZlIC8gZXh0ZW5kZWQgWCBjb29yZGluYXRlLiAqL1xuICB4OiBGO1xuICAvKiogQWZmaW5lIHkgY29vcmRpbmF0ZS4gRGlmZmVyZW50IGZyb20gcHJvamVjdGl2ZSAvIGV4dGVuZGVkIFkgY29vcmRpbmF0ZS4gKi9cbiAgeTogRjtcbiAgWj86IEY7XG4gIGRvdWJsZSgpOiBQO1xuICBuZWdhdGUoKTogUDtcbiAgYWRkKG90aGVyOiBQKTogUDtcbiAgc3VidHJhY3Qob3RoZXI6IFApOiBQO1xuICBlcXVhbHMob3RoZXI6IFApOiBib29sZWFuO1xuICBtdWx0aXBseShzY2FsYXI6IGJpZ2ludCk6IFA7XG4gIGFzc2VydFZhbGlkaXR5KCk6IHZvaWQ7XG4gIGNsZWFyQ29mYWN0b3IoKTogUDtcbiAgaXMwKCk6IGJvb2xlYW47XG4gIGlzVG9yc2lvbkZyZWUoKTogYm9vbGVhbjtcbiAgaXNTbWFsbE9yZGVyKCk6IGJvb2xlYW47XG4gIG11bHRpcGx5VW5zYWZlKHNjYWxhcjogYmlnaW50KTogUDtcbiAgLyoqXG4gICAqIE1hc3NpdmVseSBzcGVlZHMgdXAgYHAubXVsdGlwbHkobilgIGJ5IHVzaW5nIHByZWNvbXB1dGUgdGFibGVzIChjYWNoaW5nKS4gU2VlIHtAbGluayB3TkFGfS5cbiAgICogQHBhcmFtIGlzTGF6eSBjYWxjdWxhdGUgY2FjaGUgbm93LiBEZWZhdWx0ICh0cnVlKSBlbnN1cmVzIGl0J3MgZGVmZXJyZWQgdG8gZmlyc3QgYG11bHRpcGx5KClgXG4gICAqL1xuICBwcmVjb21wdXRlKHdpbmRvd1NpemU/OiBudW1iZXIsIGlzTGF6eT86IGJvb2xlYW4pOiBQO1xuICAvKiogQ29udmVydHMgcG9pbnQgdG8gMkQgeHkgYWZmaW5lIGNvb3JkaW5hdGVzICovXG4gIHRvQWZmaW5lKGludmVydGVkWj86IEYpOiBBZmZpbmVQb2ludDxGPjtcbiAgdG9CeXRlcygpOiBVaW50OEFycmF5O1xuICB0b0hleCgpOiBzdHJpbmc7XG59XG5cbi8qKiBCYXNlIGludGVyZmFjZSBmb3IgYWxsIGVsbGlwdGljIGN1cnZlIFBvaW50IGNvbnN0cnVjdG9ycy4gKi9cbmV4cG9ydCBpbnRlcmZhY2UgQ3VydmVQb2ludENvbnM8UCBleHRlbmRzIEN1cnZlUG9pbnQ8YW55LCBQPj4ge1xuICBbU3ltYm9sLmhhc0luc3RhbmNlXTogKGl0ZW06IHVua25vd24pID0+IGJvb2xlYW47XG4gIEJBU0U6IFA7XG4gIFpFUk86IFA7XG4gIC8qKiBGaWVsZCBmb3IgYmFzaWMgY3VydmUgbWF0aCAqL1xuICBGcDogSUZpZWxkPFBfRjxQPj47XG4gIC8qKiBTY2FsYXIgZmllbGQsIGZvciBzY2FsYXJzIGluIG11bHRpcGx5IGFuZCBvdGhlcnMgKi9cbiAgRm46IElGaWVsZDxiaWdpbnQ+O1xuICAvKiogQ3JlYXRlcyBwb2ludCBmcm9tIHgsIHkuIERvZXMgTk9UIHZhbGlkYXRlIGlmIHRoZSBwb2ludCBpcyB2YWxpZC4gVXNlIGAuYXNzZXJ0VmFsaWRpdHkoKWAuICovXG4gIGZyb21BZmZpbmUocDogQWZmaW5lUG9pbnQ8UF9GPFA+Pik6IFA7XG4gIGZyb21CeXRlcyhieXRlczogVWludDhBcnJheSk6IFA7XG4gIGZyb21IZXgoaGV4OiBzdHJpbmcpOiBQO1xufVxuXG4vLyBUeXBlIGluZmVyZW5jZSBoZWxwZXJzOiBQQyAtIFBvaW50Q29uc3RydWN0b3IsIFAgLSBQb2ludCwgRnAgLSBGaWVsZCBlbGVtZW50XG4vLyBTaG9ydCBuYW1lcywgYmVjYXVzZSB3ZSB1c2UgdGhlbSBhIGxvdCBpbiByZXN1bHQgdHlwZXM6XG4vLyAqIHdlIGNhbid0IGRvICdQID0gR2V0Q3VydmVQb2ludDxQQz4nOiB0aGlzIGlzIGRlZmF1bHQgdmFsdWUgYW5kIGRvZXNuJ3QgY29uc3RyYWluIGFueXRoaW5nXG4vLyAqIHdlIGNhbid0IGRvICd0eXBlIFggPSBHZXRDdXJ2ZVBvaW50PFBDPic6IGl0IHdvbid0IGJlIGFjY2VzaWJsZSBmb3IgYXJndW1lbnRzL3JldHVybiB0eXBlc1xuLy8gKiBgQ3VydmVQb2ludENvbnM8UCBleHRlbmRzIEN1cnZlUG9pbnQ8YW55LCBQPj5gIGNvbnN0cmFpbnRzIGZyb20gaW50ZXJmYWNlIGRlZmluaXRpb25cbi8vICAgd29uJ3QgcHJvcGFnYXRlLCBpZiBgUEMgZXh0ZW5kcyBDdXJ2ZVBvaW50Q29uczxhbnk+YDogdGhlIFAgd291bGQgYmUgJ2FueScsIHdoaWNoIGlzIGluY29ycmVjdFxuLy8gKiBQQyBjb3VsZCBiZSBzdXBlciBzcGVjaWZpYyB3aXRoIHN1cGVyIHNwZWNpZmljIFAsIHdoaWNoIGltcGxlbWVudHMgQ3VydmVQb2ludDxhbnksIFA+LlxuLy8gICB0aGlzIG1lYW5zIHdlIG5lZWQgdG8gZG8gc3R1ZmYgbGlrZVxuLy8gICBgZnVuY3Rpb24gdGVzdDxQIGV4dGVuZHMgQ3VydmVQb2ludDxhbnksIFA+LCBQQyBleHRlbmRzIEN1cnZlUG9pbnRDb25zPFA+PihgXG4vLyAgIGlmIHdlIHdhbnQgdHlwZSBzYWZldHkgYXJvdW5kIFAsIG90aGVyd2lzZSBQQ19QPFBDPiB3aWxsIGJlIGFueVxuXG4vKiogUmV0dXJucyBGcCB0eXBlIGZyb20gUG9pbnQgKFBfRjxQPiA9PSBQLkYpICovXG5leHBvcnQgdHlwZSBQX0Y8UCBleHRlbmRzIEN1cnZlUG9pbnQ8YW55LCBQPj4gPSBQIGV4dGVuZHMgQ3VydmVQb2ludDxpbmZlciBGLCBQPiA/IEYgOiBuZXZlcjtcbi8qKiBSZXR1cm5zIEZwIHR5cGUgZnJvbSBQb2ludENvbnMgKFBDX0Y8UEM+ID09IFBDLlAuRikgKi9cbmV4cG9ydCB0eXBlIFBDX0Y8UEMgZXh0ZW5kcyBDdXJ2ZVBvaW50Q29uczxDdXJ2ZVBvaW50PGFueSwgYW55Pj4+ID0gUENbJ0ZwJ11bJ1pFUk8nXTtcbi8qKiBSZXR1cm5zIFBvaW50IHR5cGUgZnJvbSBQb2ludENvbnMgKFBDX1A8UEM+ID09IFBDLlApICovXG5leHBvcnQgdHlwZSBQQ19QPFBDIGV4dGVuZHMgQ3VydmVQb2ludENvbnM8Q3VydmVQb2ludDxhbnksIGFueT4+PiA9IFBDWydaRVJPJ107XG5cbi8vIFVnbHkgaGFjayB0byBnZXQgcHJvcGVyIHR5cGUgaW5mZXJlbmNlLCBiZWNhdXNlIGluIHR5cGVzY3JpcHQgZmFpbHMgdG8gaW5mZXIgcmVzdXJzaXZlbHkuXG4vLyBUaGUgaGFjayBhbGxvd3MgdG8gZG8gdXAgdG8gMTAgY2hhaW5lZCBvcGVyYXRpb25zIHdpdGhvdXQgYXBwbHlpbmcgdHlwZSBlcmFzdXJlLlxuLy9cbi8vIFR5cGVzIHdoaWNoIHdvbid0IHdvcms6XG4vLyAqIGBDdXJ2ZVBvaW50Q29uczxDdXJ2ZVBvaW50PGFueSwgYW55Pj5gLCB3aWxsIHJldHVybiBgYW55YCBhZnRlciAxIG9wZXJhdGlvblxuLy8gKiBgQ3VydmVQb2ludENvbnM8YW55PjogV2VpZXJzdHJhc3NQb2ludENvbnM8YmlnaW50PiBleHRlbmRzIEN1cnZlUG9pbnRDb25zPGFueT4gPSBmYWxzZWBcbi8vICogYFAgZXh0ZW5kcyBDdXJ2ZVBvaW50LCBQQyBleHRlbmRzIEN1cnZlUG9pbnRDb25zPFA+YFxuLy8gICAgICogSXQgY2FuJ3QgaW5mZXIgUCBmcm9tIFBDIGFsb25lXG4vLyAgICAgKiBUb28gbWFueSByZWxhdGlvbnMgYmV0d2VlbiBGLCBQICYgUENcbi8vICAgICAqIEl0IHdpbGwgaW5mZXIgUC9GIGlmIGBhcmc6IEN1cnZlUG9pbnRDb25zPEYsIFA+YCwgYnV0IHdpbGwgZmFpbCBpZiBQQyBpcyBnZW5lcmljXG4vLyAgICAgKiBJdCB3aWxsIHdvcmsgY29ycmVjdGx5IGlmIHRoZXJlIGlzIGFuIGFkZGl0aW9uYWwgYXJndW1lbnQgb2YgdHlwZSBQXG4vLyAgICAgKiBCdXQgZ2VuZXJhbGx5LCB3ZSBkb24ndCB3YW50IHRvIHBhcmFtZXRyaXplIGBDdXJ2ZVBvaW50Q29uc2Agb3ZlciBgRmA6IGl0IHdpbGwgY29tcGxpY2F0ZVxuLy8gICAgICAgdHlwZXMsIG1ha2luZyB0aGVtIHVuLWluZmVyYWJsZVxuLy8gcHJldHRpZXItaWdub3JlXG5leHBvcnQgdHlwZSBQQ19BTlkgPSBDdXJ2ZVBvaW50Q29uczxcbiAgQ3VydmVQb2ludDxhbnksXG4gIEN1cnZlUG9pbnQ8YW55LFxuICBDdXJ2ZVBvaW50PGFueSxcbiAgQ3VydmVQb2ludDxhbnksXG4gIEN1cnZlUG9pbnQ8YW55LFxuICBDdXJ2ZVBvaW50PGFueSxcbiAgQ3VydmVQb2ludDxhbnksXG4gIEN1cnZlUG9pbnQ8YW55LFxuICBDdXJ2ZVBvaW50PGFueSxcbiAgQ3VydmVQb2ludDxhbnksIGFueT5cbiAgPj4+Pj4+Pj4+XG4+O1xuXG5leHBvcnQgaW50ZXJmYWNlIEN1cnZlTGVuZ3RocyB7XG4gIHNlY3JldEtleT86IG51bWJlcjtcbiAgcHVibGljS2V5PzogbnVtYmVyO1xuICBwdWJsaWNLZXlVbmNvbXByZXNzZWQ/OiBudW1iZXI7XG4gIHB1YmxpY0tleUhhc1ByZWZpeD86IGJvb2xlYW47XG4gIHNpZ25hdHVyZT86IG51bWJlcjtcbiAgc2VlZD86IG51bWJlcjtcbn1cblxuZXhwb3J0IHR5cGUgTWFwcGVyPFQ+ID0gKGk6IFRbXSkgPT4gVFtdO1xuXG5leHBvcnQgZnVuY3Rpb24gbmVnYXRlQ3Q8VCBleHRlbmRzIHsgbmVnYXRlOiAoKSA9PiBUIH0+KGNvbmRpdGlvbjogYm9vbGVhbiwgaXRlbTogVCk6IFQge1xuICBjb25zdCBuZWcgPSBpdGVtLm5lZ2F0ZSgpO1xuICByZXR1cm4gY29uZGl0aW9uID8gbmVnIDogaXRlbTtcbn1cblxuLyoqXG4gKiBUYWtlcyBhIGJ1bmNoIG9mIFByb2plY3RpdmUgUG9pbnRzIGJ1dCBleGVjdXRlcyBvbmx5IG9uZVxuICogaW52ZXJzaW9uIG9uIGFsbCBvZiB0aGVtLiBJbnZlcnNpb24gaXMgdmVyeSBzbG93IG9wZXJhdGlvbixcbiAqIHNvIHRoaXMgaW1wcm92ZXMgcGVyZm9ybWFuY2UgbWFzc2l2ZWx5LlxuICogT3B0aW1pemF0aW9uOiBjb252ZXJ0cyBhIGxpc3Qgb2YgcHJvamVjdGl2ZSBwb2ludHMgdG8gYSBsaXN0IG9mIGlkZW50aWNhbCBwb2ludHMgd2l0aCBaPTEuXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBub3JtYWxpemVaPFAgZXh0ZW5kcyBDdXJ2ZVBvaW50PGFueSwgUD4sIFBDIGV4dGVuZHMgQ3VydmVQb2ludENvbnM8UD4+KFxuICBjOiBQQyxcbiAgcG9pbnRzOiBQW11cbik6IFBbXSB7XG4gIGNvbnN0IGludmVydGVkWnMgPSBGcEludmVydEJhdGNoKFxuICAgIGMuRnAsXG4gICAgcG9pbnRzLm1hcCgocCkgPT4gcC5aISlcbiAgKTtcbiAgcmV0dXJuIHBvaW50cy5tYXAoKHAsIGkpID0+IGMuZnJvbUFmZmluZShwLnRvQWZmaW5lKGludmVydGVkWnNbaV0pKSk7XG59XG5cbmZ1bmN0aW9uIHZhbGlkYXRlVyhXOiBudW1iZXIsIGJpdHM6IG51bWJlcikge1xuICBpZiAoIU51bWJlci5pc1NhZmVJbnRlZ2VyKFcpIHx8IFcgPD0gMCB8fCBXID4gYml0cylcbiAgICB0aHJvdyBuZXcgRXJyb3IoJ2ludmFsaWQgd2luZG93IHNpemUsIGV4cGVjdGVkIFsxLi4nICsgYml0cyArICddLCBnb3QgVz0nICsgVyk7XG59XG5cbi8qKiBJbnRlcm5hbCB3TkFGIG9wdHMgZm9yIHNwZWNpZmljIFcgYW5kIHNjYWxhckJpdHMgKi9cbnR5cGUgV09wdHMgPSB7XG4gIHdpbmRvd3M6IG51bWJlcjtcbiAgd2luZG93U2l6ZTogbnVtYmVyO1xuICBtYXNrOiBiaWdpbnQ7XG4gIG1heE51bWJlcjogbnVtYmVyO1xuICBzaGlmdEJ5OiBiaWdpbnQ7XG59O1xuXG5mdW5jdGlvbiBjYWxjV09wdHMoVzogbnVtYmVyLCBzY2FsYXJCaXRzOiBudW1iZXIpOiBXT3B0cyB7XG4gIHZhbGlkYXRlVyhXLCBzY2FsYXJCaXRzKTtcbiAgY29uc3Qgd2luZG93cyA9IE1hdGguY2VpbChzY2FsYXJCaXRzIC8gVykgKyAxOyAvLyBXPTggMzMuIE5vdCAzMiwgYmVjYXVzZSB3ZSBza2lwIHplcm9cbiAgY29uc3Qgd2luZG93U2l6ZSA9IDIgKiogKFcgLSAxKTsgLy8gVz04IDEyOC4gTm90IDI1NiwgYmVjYXVzZSB3ZSBza2lwIHplcm9cbiAgY29uc3QgbWF4TnVtYmVyID0gMiAqKiBXOyAvLyBXPTggMjU2XG4gIGNvbnN0IG1hc2sgPSBiaXRNYXNrKFcpOyAvLyBXPTggMjU1ID09IG1hc2sgMGIxMTExMTExMVxuICBjb25zdCBzaGlmdEJ5ID0gQmlnSW50KFcpOyAvLyBXPTggOFxuICByZXR1cm4geyB3aW5kb3dzLCB3aW5kb3dTaXplLCBtYXNrLCBtYXhOdW1iZXIsIHNoaWZ0QnkgfTtcbn1cblxuZnVuY3Rpb24gY2FsY09mZnNldHMobjogYmlnaW50LCB3aW5kb3c6IG51bWJlciwgd09wdHM6IFdPcHRzKSB7XG4gIGNvbnN0IHsgd2luZG93U2l6ZSwgbWFzaywgbWF4TnVtYmVyLCBzaGlmdEJ5IH0gPSB3T3B0cztcbiAgbGV0IHdiaXRzID0gTnVtYmVyKG4gJiBtYXNrKTsgLy8gZXh0cmFjdCBXIGJpdHMuXG4gIGxldCBuZXh0TiA9IG4gPj4gc2hpZnRCeTsgLy8gc2hpZnQgbnVtYmVyIGJ5IFcgYml0cy5cblxuICAvLyBXaGF0IGFjdHVhbGx5IGhhcHBlbnMgaGVyZTpcbiAgLy8gY29uc3QgaGlnaGVzdEJpdCA9IE51bWJlcihtYXNrIF4gKG1hc2sgPj4gMW4pKTtcbiAgLy8gbGV0IHdiaXRzMiA9IHdiaXRzIC0gMTsgLy8gc2tpcCB6ZXJvXG4gIC8vIGlmICh3Yml0czIgJiBoaWdoZXN0Qml0KSB7IHdiaXRzMiBePSBOdW1iZXIobWFzayk7IC8vICh+KTtcblxuICAvLyBzcGxpdCBpZiBiaXRzID4gbWF4OiArMjI0ID0+IDI1Ni0zMlxuICBpZiAod2JpdHMgPiB3aW5kb3dTaXplKSB7XG4gICAgLy8gd2Ugc2tpcCB6ZXJvLCB3aGljaCBtZWFucyBpbnN0ZWFkIG9mIGA+PSBzaXplLTFgLCB3ZSBkbyBgPiBzaXplYFxuICAgIHdiaXRzIC09IG1heE51bWJlcjsgLy8gLTMyLCBjYW4gYmUgbWF4TnVtYmVyIC0gd2JpdHMsIGJ1dCB0aGVuIHdlIG5lZWQgdG8gc2V0IGlzTmVnIGhlcmUuXG4gICAgbmV4dE4gKz0gXzFuOyAvLyArMjU2IChjYXJyeSlcbiAgfVxuICBjb25zdCBvZmZzZXRTdGFydCA9IHdpbmRvdyAqIHdpbmRvd1NpemU7XG4gIGNvbnN0IG9mZnNldCA9IG9mZnNldFN0YXJ0ICsgTWF0aC5hYnMod2JpdHMpIC0gMTsgLy8gLTEgYmVjYXVzZSB3ZSBza2lwIHplcm9cbiAgY29uc3QgaXNaZXJvID0gd2JpdHMgPT09IDA7IC8vIGlzIGN1cnJlbnQgd2luZG93IHNsaWNlIGEgMD9cbiAgY29uc3QgaXNOZWcgPSB3Yml0cyA8IDA7IC8vIGlzIGN1cnJlbnQgd2luZG93IHNsaWNlIG5lZ2F0aXZlP1xuICBjb25zdCBpc05lZ0YgPSB3aW5kb3cgJSAyICE9PSAwOyAvLyBmYWtlIHJhbmRvbSBzdGF0ZW1lbnQgZm9yIG5vaXNlXG4gIGNvbnN0IG9mZnNldEYgPSBvZmZzZXRTdGFydDsgLy8gZmFrZSBvZmZzZXQgZm9yIG5vaXNlXG4gIHJldHVybiB7IG5leHROLCBvZmZzZXQsIGlzWmVybywgaXNOZWcsIGlzTmVnRiwgb2Zmc2V0RiB9O1xufVxuXG5mdW5jdGlvbiB2YWxpZGF0ZU1TTVBvaW50cyhwb2ludHM6IGFueVtdLCBjOiBhbnkpIHtcbiAgaWYgKCFBcnJheS5pc0FycmF5KHBvaW50cykpIHRocm93IG5ldyBFcnJvcignYXJyYXkgZXhwZWN0ZWQnKTtcbiAgcG9pbnRzLmZvckVhY2goKHAsIGkpID0+IHtcbiAgICBpZiAoIShwIGluc3RhbmNlb2YgYykpIHRocm93IG5ldyBFcnJvcignaW52YWxpZCBwb2ludCBhdCBpbmRleCAnICsgaSk7XG4gIH0pO1xufVxuZnVuY3Rpb24gdmFsaWRhdGVNU01TY2FsYXJzKHNjYWxhcnM6IGFueVtdLCBmaWVsZDogYW55KSB7XG4gIGlmICghQXJyYXkuaXNBcnJheShzY2FsYXJzKSkgdGhyb3cgbmV3IEVycm9yKCdhcnJheSBvZiBzY2FsYXJzIGV4cGVjdGVkJyk7XG4gIHNjYWxhcnMuZm9yRWFjaCgocywgaSkgPT4ge1xuICAgIGlmICghZmllbGQuaXNWYWxpZChzKSkgdGhyb3cgbmV3IEVycm9yKCdpbnZhbGlkIHNjYWxhciBhdCBpbmRleCAnICsgaSk7XG4gIH0pO1xufVxuXG4vLyBTaW5jZSBwb2ludHMgaW4gZGlmZmVyZW50IGdyb3VwcyBjYW5ub3QgYmUgZXF1YWwgKGRpZmZlcmVudCBvYmplY3QgY29uc3RydWN0b3IpLFxuLy8gd2UgY2FuIGhhdmUgc2luZ2xlIHBsYWNlIHRvIHN0b3JlIHByZWNvbXB1dGVzLlxuLy8gQWxsb3dzIHRvIG1ha2UgcG9pbnRzIGZyb3plbiAvIGltbXV0YWJsZS5cbmNvbnN0IHBvaW50UHJlY29tcHV0ZXMgPSBuZXcgV2Vha01hcDxhbnksIGFueVtdPigpO1xuY29uc3QgcG9pbnRXaW5kb3dTaXplcyA9IG5ldyBXZWFrTWFwPGFueSwgbnVtYmVyPigpO1xuXG5mdW5jdGlvbiBnZXRXKFA6IGFueSk6IG51bWJlciB7XG4gIC8vIFRvIGRpc2FibGUgcHJlY29tcHV0ZXM6XG4gIC8vIHJldHVybiAxO1xuICByZXR1cm4gcG9pbnRXaW5kb3dTaXplcy5nZXQoUCkgfHwgMTtcbn1cblxuZnVuY3Rpb24gYXNzZXJ0MChuOiBiaWdpbnQpOiB2b2lkIHtcbiAgaWYgKG4gIT09IF8wbikgdGhyb3cgbmV3IEVycm9yKCdpbnZhbGlkIHdOQUYnKTtcbn1cblxuLyoqXG4gKiBFbGxpcHRpYyBjdXJ2ZSBtdWx0aXBsaWNhdGlvbiBvZiBQb2ludCBieSBzY2FsYXIuIEZyYWdpbGUuXG4gKiBUYWJsZSBnZW5lcmF0aW9uIHRha2VzICoqMzBNQiBvZiByYW0gYW5kIDEwbXMgb24gaGlnaC1lbmQgQ1BVKiosXG4gKiBidXQgbWF5IHRha2UgbXVjaCBsb25nZXIgb24gc2xvdyBkZXZpY2VzLiBBY3R1YWwgZ2VuZXJhdGlvbiB3aWxsIGhhcHBlbiBvblxuICogZmlyc3QgY2FsbCBvZiBgbXVsdGlwbHkoKWAuIEJ5IGRlZmF1bHQsIGBCQVNFYCBwb2ludCBpcyBwcmVjb21wdXRlZC5cbiAqXG4gKiBTY2FsYXJzIHNob3VsZCBhbHdheXMgYmUgbGVzcyB0aGFuIGN1cnZlIG9yZGVyOiB0aGlzIHNob3VsZCBiZSBjaGVja2VkIGluc2lkZSBvZiBhIGN1cnZlIGl0c2VsZi5cbiAqIENyZWF0ZXMgcHJlY29tcHV0YXRpb24gdGFibGVzIGZvciBmYXN0IG11bHRpcGxpY2F0aW9uOlxuICogLSBwcml2YXRlIHNjYWxhciBpcyBzcGxpdCBieSBmaXhlZCBzaXplIHdpbmRvd3Mgb2YgVyBiaXRzXG4gKiAtIGV2ZXJ5IHdpbmRvdyBwb2ludCBpcyBjb2xsZWN0ZWQgZnJvbSB3aW5kb3cncyB0YWJsZSAmIGFkZGVkIHRvIGFjY3VtdWxhdG9yXG4gKiAtIHNpbmNlIHdpbmRvd3MgYXJlIGRpZmZlcmVudCwgc2FtZSBwb2ludCBpbnNpZGUgdGFibGVzIHdvbid0IGJlIGFjY2Vzc2VkIG1vcmUgdGhhbiBvbmNlIHBlciBjYWxjXG4gKiAtIGVhY2ggbXVsdGlwbGljYXRpb24gaXMgJ01hdGguY2VpbChDVVJWRV9PUkRFUiAvIFx1RDgzNVx1REM0QSkgKyAxJyBwb2ludCBhZGRpdGlvbnMgKGZpeGVkIGZvciBhbnkgc2NhbGFyKVxuICogLSArMSB3aW5kb3cgaXMgbmVjY2Vzc2FyeSBmb3Igd05BRlxuICogLSB3TkFGIHJlZHVjZXMgdGFibGUgc2l6ZTogMnggbGVzcyBtZW1vcnkgKyAyeCBmYXN0ZXIgZ2VuZXJhdGlvbiwgYnV0IDEwJSBzbG93ZXIgbXVsdGlwbGljYXRpb25cbiAqXG4gKiBAdG9kbyBSZXNlYXJjaCByZXR1cm5pbmcgMmQgSlMgYXJyYXkgb2Ygd2luZG93cywgaW5zdGVhZCBvZiBhIHNpbmdsZSB3aW5kb3cuXG4gKiBUaGlzIHdvdWxkIGFsbG93IHdpbmRvd3MgdG8gYmUgaW4gZGlmZmVyZW50IG1lbW9yeSBsb2NhdGlvbnNcbiAqL1xuZXhwb3J0IGNsYXNzIHdOQUY8UEMgZXh0ZW5kcyBQQ19BTlk+IHtcbiAgcHJpdmF0ZSByZWFkb25seSBCQVNFOiBQQ19QPFBDPjtcbiAgcHJpdmF0ZSByZWFkb25seSBaRVJPOiBQQ19QPFBDPjtcbiAgcHJpdmF0ZSByZWFkb25seSBGbjogUENbJ0ZuJ107XG4gIHJlYWRvbmx5IGJpdHM6IG51bWJlcjtcblxuICAvLyBQYXJhbWV0cml6ZWQgd2l0aCBhIGdpdmVuIFBvaW50IGNsYXNzIChub3QgaW5kaXZpZHVhbCBwb2ludClcbiAgY29uc3RydWN0b3IoUG9pbnQ6IFBDLCBiaXRzOiBudW1iZXIpIHtcbiAgICB0aGlzLkJBU0UgPSBQb2ludC5CQVNFO1xuICAgIHRoaXMuWkVSTyA9IFBvaW50LlpFUk87XG4gICAgdGhpcy5GbiA9IFBvaW50LkZuO1xuICAgIHRoaXMuYml0cyA9IGJpdHM7XG4gIH1cblxuICAvLyBub24tY29uc3QgdGltZSBtdWx0aXBsaWNhdGlvbiBsYWRkZXJcbiAgX3Vuc2FmZUxhZGRlcihlbG06IFBDX1A8UEM+LCBuOiBiaWdpbnQsIHA6IFBDX1A8UEM+ID0gdGhpcy5aRVJPKTogUENfUDxQQz4ge1xuICAgIGxldCBkOiBQQ19QPFBDPiA9IGVsbTtcbiAgICB3aGlsZSAobiA+IF8wbikge1xuICAgICAgaWYgKG4gJiBfMW4pIHAgPSBwLmFkZChkKTtcbiAgICAgIGQgPSBkLmRvdWJsZSgpO1xuICAgICAgbiA+Pj0gXzFuO1xuICAgIH1cbiAgICByZXR1cm4gcDtcbiAgfVxuXG4gIC8qKlxuICAgKiBDcmVhdGVzIGEgd05BRiBwcmVjb21wdXRhdGlvbiB3aW5kb3cuIFVzZWQgZm9yIGNhY2hpbmcuXG4gICAqIERlZmF1bHQgd2luZG93IHNpemUgaXMgc2V0IGJ5IGB1dGlscy5wcmVjb21wdXRlKClgIGFuZCBpcyBlcXVhbCB0byA4LlxuICAgKiBOdW1iZXIgb2YgcHJlY29tcHV0ZWQgcG9pbnRzIGRlcGVuZHMgb24gdGhlIGN1cnZlIHNpemU6XG4gICAqIDJeKFx1RDgzNVx1REM0QVx1MjIxMjEpICogKE1hdGguY2VpbChcdUQ4MzVcdURDNUIgLyBcdUQ4MzVcdURDNEEpICsgMSksIHdoZXJlOlxuICAgKiAtIFx1RDgzNVx1REM0QSBpcyB0aGUgd2luZG93IHNpemVcbiAgICogLSBcdUQ4MzVcdURDNUIgaXMgdGhlIGJpdGxlbmd0aCBvZiB0aGUgY3VydmUgb3JkZXIuXG4gICAqIEZvciBhIDI1Ni1iaXQgY3VydmUgYW5kIHdpbmRvdyBzaXplIDgsIHRoZSBudW1iZXIgb2YgcHJlY29tcHV0ZWQgcG9pbnRzIGlzIDEyOCAqIDMzID0gNDIyNC5cbiAgICogQHBhcmFtIHBvaW50IFBvaW50IGluc3RhbmNlXG4gICAqIEBwYXJhbSBXIHdpbmRvdyBzaXplXG4gICAqIEByZXR1cm5zIHByZWNvbXB1dGVkIHBvaW50IHRhYmxlcyBmbGF0dGVuZWQgdG8gYSBzaW5nbGUgYXJyYXlcbiAgICovXG4gIHByaXZhdGUgcHJlY29tcHV0ZVdpbmRvdyhwb2ludDogUENfUDxQQz4sIFc6IG51bWJlcik6IFBDX1A8UEM+W10ge1xuICAgIGNvbnN0IHsgd2luZG93cywgd2luZG93U2l6ZSB9ID0gY2FsY1dPcHRzKFcsIHRoaXMuYml0cyk7XG4gICAgY29uc3QgcG9pbnRzOiBQQ19QPFBDPltdID0gW107XG4gICAgbGV0IHA6IFBDX1A8UEM+ID0gcG9pbnQ7XG4gICAgbGV0IGJhc2UgPSBwO1xuICAgIGZvciAobGV0IHdpbmRvdyA9IDA7IHdpbmRvdyA8IHdpbmRvd3M7IHdpbmRvdysrKSB7XG4gICAgICBiYXNlID0gcDtcbiAgICAgIHBvaW50cy5wdXNoKGJhc2UpO1xuICAgICAgLy8gaT0xLCBiYyB3ZSBza2lwIDBcbiAgICAgIGZvciAobGV0IGkgPSAxOyBpIDwgd2luZG93U2l6ZTsgaSsrKSB7XG4gICAgICAgIGJhc2UgPSBiYXNlLmFkZChwKTtcbiAgICAgICAgcG9pbnRzLnB1c2goYmFzZSk7XG4gICAgICB9XG4gICAgICBwID0gYmFzZS5kb3VibGUoKTtcbiAgICB9XG4gICAgcmV0dXJuIHBvaW50cztcbiAgfVxuXG4gIC8qKlxuICAgKiBJbXBsZW1lbnRzIGVjIG11bHRpcGxpY2F0aW9uIHVzaW5nIHByZWNvbXB1dGVkIHRhYmxlcyBhbmQgdy1hcnkgbm9uLWFkamFjZW50IGZvcm0uXG4gICAqIE1vcmUgY29tcGFjdCBpbXBsZW1lbnRhdGlvbjpcbiAgICogaHR0cHM6Ly9naXRodWIuY29tL3BhdWxtaWxsci9ub2JsZS1zZWNwMjU2azEvYmxvYi80N2NiMTY2OWI2ZTUwNmFkNjZiMzVmZTdkNzYxMzJhZTk3NDY1ZGEyL2luZGV4LnRzI0w1MDItTDU0MVxuICAgKiBAcmV0dXJucyByZWFsIGFuZCBmYWtlIChmb3IgY29uc3QtdGltZSkgcG9pbnRzXG4gICAqL1xuICBwcml2YXRlIHdOQUYoVzogbnVtYmVyLCBwcmVjb21wdXRlczogUENfUDxQQz5bXSwgbjogYmlnaW50KTogeyBwOiBQQ19QPFBDPjsgZjogUENfUDxQQz4gfSB7XG4gICAgLy8gU2NhbGFyIHNob3VsZCBiZSBzbWFsbGVyIHRoYW4gZmllbGQgb3JkZXJcbiAgICBpZiAoIXRoaXMuRm4uaXNWYWxpZChuKSkgdGhyb3cgbmV3IEVycm9yKCdpbnZhbGlkIHNjYWxhcicpO1xuICAgIC8vIEFjY3VtdWxhdG9yc1xuICAgIGxldCBwID0gdGhpcy5aRVJPO1xuICAgIGxldCBmID0gdGhpcy5CQVNFO1xuICAgIC8vIFRoaXMgY29kZSB3YXMgZmlyc3Qgd3JpdHRlbiB3aXRoIGFzc3VtcHRpb24gdGhhdCAnZicgYW5kICdwJyB3aWxsIG5ldmVyIGJlIGluZmluaXR5IHBvaW50OlxuICAgIC8vIHNpbmNlIGVhY2ggYWRkaXRpb24gaXMgbXVsdGlwbGllZCBieSAyICoqIFcsIGl0IGNhbm5vdCBjYW5jZWwgZWFjaCBvdGhlci4gSG93ZXZlcixcbiAgICAvLyB0aGVyZSBpcyBuZWdhdGUgbm93OiBpdCBpcyBwb3NzaWJsZSB0aGF0IG5lZ2F0ZWQgZWxlbWVudCBmcm9tIGxvdyB2YWx1ZVxuICAgIC8vIHdvdWxkIGJlIHRoZSBzYW1lIGFzIGhpZ2ggZWxlbWVudCwgd2hpY2ggd2lsbCBjcmVhdGUgY2FycnkgaW50byBuZXh0IHdpbmRvdy5cbiAgICAvLyBJdCdzIG5vdCBvYnZpb3VzIGhvdyB0aGlzIGNhbiBmYWlsLCBidXQgc3RpbGwgd29ydGggaW52ZXN0aWdhdGluZyBsYXRlci5cbiAgICBjb25zdCB3byA9IGNhbGNXT3B0cyhXLCB0aGlzLmJpdHMpO1xuICAgIGZvciAobGV0IHdpbmRvdyA9IDA7IHdpbmRvdyA8IHdvLndpbmRvd3M7IHdpbmRvdysrKSB7XG4gICAgICAvLyAobiA9PT0gXzBuKSBpcyBoYW5kbGVkIGFuZCBub3QgZWFybHktZXhpdGVkLiBpc0V2ZW4gYW5kIG9mZnNldEYgYXJlIHVzZWQgZm9yIG5vaXNlXG4gICAgICBjb25zdCB7IG5leHROLCBvZmZzZXQsIGlzWmVybywgaXNOZWcsIGlzTmVnRiwgb2Zmc2V0RiB9ID0gY2FsY09mZnNldHMobiwgd2luZG93LCB3byk7XG4gICAgICBuID0gbmV4dE47XG4gICAgICBpZiAoaXNaZXJvKSB7XG4gICAgICAgIC8vIGJpdHMgYXJlIDA6IGFkZCBnYXJiYWdlIHRvIGZha2UgcG9pbnRcbiAgICAgICAgLy8gSW1wb3J0YW50IHBhcnQgZm9yIGNvbnN0LXRpbWUgZ2V0UHVibGljS2V5OiBhZGQgcmFuZG9tIFwibm9pc2VcIiBwb2ludCB0byBmLlxuICAgICAgICBmID0gZi5hZGQobmVnYXRlQ3QoaXNOZWdGLCBwcmVjb21wdXRlc1tvZmZzZXRGXSkpO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgLy8gYml0cyBhcmUgMTogYWRkIHRvIHJlc3VsdCBwb2ludFxuICAgICAgICBwID0gcC5hZGQobmVnYXRlQ3QoaXNOZWcsIHByZWNvbXB1dGVzW29mZnNldF0pKTtcbiAgICAgIH1cbiAgICB9XG4gICAgYXNzZXJ0MChuKTtcbiAgICAvLyBSZXR1cm4gYm90aCByZWFsIGFuZCBmYWtlIHBvaW50czogSklUIHdvbid0IGVsaW1pbmF0ZSBmLlxuICAgIC8vIEF0IHRoaXMgcG9pbnQgdGhlcmUgaXMgYSB3YXkgdG8gRiBiZSBpbmZpbml0eS1wb2ludCBldmVuIGlmIHAgaXMgbm90LFxuICAgIC8vIHdoaWNoIG1ha2VzIGl0IGxlc3MgY29uc3QtdGltZTogYXJvdW5kIDEgYmlnaW50IG11bHRpcGx5LlxuICAgIHJldHVybiB7IHAsIGYgfTtcbiAgfVxuXG4gIC8qKlxuICAgKiBJbXBsZW1lbnRzIGVjIHVuc2FmZSAobm9uIGNvbnN0LXRpbWUpIG11bHRpcGxpY2F0aW9uIHVzaW5nIHByZWNvbXB1dGVkIHRhYmxlcyBhbmQgdy1hcnkgbm9uLWFkamFjZW50IGZvcm0uXG4gICAqIEBwYXJhbSBhY2MgYWNjdW11bGF0b3IgcG9pbnQgdG8gYWRkIHJlc3VsdCBvZiBtdWx0aXBsaWNhdGlvblxuICAgKiBAcmV0dXJucyBwb2ludFxuICAgKi9cbiAgcHJpdmF0ZSB3TkFGVW5zYWZlKFxuICAgIFc6IG51bWJlcixcbiAgICBwcmVjb21wdXRlczogUENfUDxQQz5bXSxcbiAgICBuOiBiaWdpbnQsXG4gICAgYWNjOiBQQ19QPFBDPiA9IHRoaXMuWkVST1xuICApOiBQQ19QPFBDPiB7XG4gICAgY29uc3Qgd28gPSBjYWxjV09wdHMoVywgdGhpcy5iaXRzKTtcbiAgICBmb3IgKGxldCB3aW5kb3cgPSAwOyB3aW5kb3cgPCB3by53aW5kb3dzOyB3aW5kb3crKykge1xuICAgICAgaWYgKG4gPT09IF8wbikgYnJlYWs7IC8vIEVhcmx5LWV4aXQsIHNraXAgMCB2YWx1ZVxuICAgICAgY29uc3QgeyBuZXh0Tiwgb2Zmc2V0LCBpc1plcm8sIGlzTmVnIH0gPSBjYWxjT2Zmc2V0cyhuLCB3aW5kb3csIHdvKTtcbiAgICAgIG4gPSBuZXh0TjtcbiAgICAgIGlmIChpc1plcm8pIHtcbiAgICAgICAgLy8gV2luZG93IGJpdHMgYXJlIDA6IHNraXAgcHJvY2Vzc2luZy5cbiAgICAgICAgLy8gTW92ZSB0byBuZXh0IHdpbmRvdy5cbiAgICAgICAgY29udGludWU7XG4gICAgICB9IGVsc2Uge1xuICAgICAgICBjb25zdCBpdGVtID0gcHJlY29tcHV0ZXNbb2Zmc2V0XTtcbiAgICAgICAgYWNjID0gYWNjLmFkZChpc05lZyA/IGl0ZW0ubmVnYXRlKCkgOiBpdGVtKTsgLy8gUmUtdXNpbmcgYWNjIGFsbG93cyB0byBzYXZlIGFkZHMgaW4gTVNNXG4gICAgICB9XG4gICAgfVxuICAgIGFzc2VydDAobik7XG4gICAgcmV0dXJuIGFjYztcbiAgfVxuXG4gIHByaXZhdGUgZ2V0UHJlY29tcHV0ZXMoVzogbnVtYmVyLCBwb2ludDogUENfUDxQQz4sIHRyYW5zZm9ybT86IE1hcHBlcjxQQ19QPFBDPj4pOiBQQ19QPFBDPltdIHtcbiAgICAvLyBDYWxjdWxhdGUgcHJlY29tcHV0ZXMgb24gYSBmaXJzdCBydW4sIHJldXNlIHRoZW0gYWZ0ZXJcbiAgICBsZXQgY29tcCA9IHBvaW50UHJlY29tcHV0ZXMuZ2V0KHBvaW50KTtcbiAgICBpZiAoIWNvbXApIHtcbiAgICAgIGNvbXAgPSB0aGlzLnByZWNvbXB1dGVXaW5kb3cocG9pbnQsIFcpIGFzIFBDX1A8UEM+W107XG4gICAgICBpZiAoVyAhPT0gMSkge1xuICAgICAgICAvLyBEb2luZyB0cmFuc2Zvcm0gb3V0c2lkZSBvZiBpZiBicmluZ3MgMTUlIHBlcmYgaGl0XG4gICAgICAgIGlmICh0eXBlb2YgdHJhbnNmb3JtID09PSAnZnVuY3Rpb24nKSBjb21wID0gdHJhbnNmb3JtKGNvbXApO1xuICAgICAgICBwb2ludFByZWNvbXB1dGVzLnNldChwb2ludCwgY29tcCk7XG4gICAgICB9XG4gICAgfVxuICAgIHJldHVybiBjb21wO1xuICB9XG5cbiAgY2FjaGVkKFxuICAgIHBvaW50OiBQQ19QPFBDPixcbiAgICBzY2FsYXI6IGJpZ2ludCxcbiAgICB0cmFuc2Zvcm0/OiBNYXBwZXI8UENfUDxQQz4+XG4gICk6IHsgcDogUENfUDxQQz47IGY6IFBDX1A8UEM+IH0ge1xuICAgIGNvbnN0IFcgPSBnZXRXKHBvaW50KTtcbiAgICByZXR1cm4gdGhpcy53TkFGKFcsIHRoaXMuZ2V0UHJlY29tcHV0ZXMoVywgcG9pbnQsIHRyYW5zZm9ybSksIHNjYWxhcik7XG4gIH1cblxuICB1bnNhZmUocG9pbnQ6IFBDX1A8UEM+LCBzY2FsYXI6IGJpZ2ludCwgdHJhbnNmb3JtPzogTWFwcGVyPFBDX1A8UEM+PiwgcHJldj86IFBDX1A8UEM+KTogUENfUDxQQz4ge1xuICAgIGNvbnN0IFcgPSBnZXRXKHBvaW50KTtcbiAgICBpZiAoVyA9PT0gMSkgcmV0dXJuIHRoaXMuX3Vuc2FmZUxhZGRlcihwb2ludCwgc2NhbGFyLCBwcmV2KTsgLy8gRm9yIFc9MSBsYWRkZXIgaXMgfngyIGZhc3RlclxuICAgIHJldHVybiB0aGlzLndOQUZVbnNhZmUoVywgdGhpcy5nZXRQcmVjb21wdXRlcyhXLCBwb2ludCwgdHJhbnNmb3JtKSwgc2NhbGFyLCBwcmV2KTtcbiAgfVxuXG4gIC8vIFdlIGNhbGN1bGF0ZSBwcmVjb21wdXRlcyBmb3IgZWxsaXB0aWMgY3VydmUgcG9pbnQgbXVsdGlwbGljYXRpb25cbiAgLy8gdXNpbmcgd2luZG93ZWQgbWV0aG9kLiBUaGlzIHNwZWNpZmllcyB3aW5kb3cgc2l6ZSBhbmRcbiAgLy8gc3RvcmVzIHByZWNvbXB1dGVkIHZhbHVlcy4gVXN1YWxseSBvbmx5IGJhc2UgcG9pbnQgd291bGQgYmUgcHJlY29tcHV0ZWQuXG4gIGNyZWF0ZUNhY2hlKFA6IFBDX1A8UEM+LCBXOiBudW1iZXIpOiB2b2lkIHtcbiAgICB2YWxpZGF0ZVcoVywgdGhpcy5iaXRzKTtcbiAgICBwb2ludFdpbmRvd1NpemVzLnNldChQLCBXKTtcbiAgICBwb2ludFByZWNvbXB1dGVzLmRlbGV0ZShQKTtcbiAgfVxuXG4gIGhhc0NhY2hlKGVsbTogUENfUDxQQz4pOiBib29sZWFuIHtcbiAgICByZXR1cm4gZ2V0VyhlbG0pICE9PSAxO1xuICB9XG59XG5cbi8qKlxuICogRW5kb21vcnBoaXNtLXNwZWNpZmljIG11bHRpcGxpY2F0aW9uIGZvciBLb2JsaXR6IGN1cnZlcy5cbiAqIENvc3Q6IDEyOCBkYmwsIDAtMjU2IGFkZHMuXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBtdWxFbmRvVW5zYWZlPFAgZXh0ZW5kcyBDdXJ2ZVBvaW50PGFueSwgUD4sIFBDIGV4dGVuZHMgQ3VydmVQb2ludENvbnM8UD4+KFxuICBQb2ludDogUEMsXG4gIHBvaW50OiBQLFxuICBrMTogYmlnaW50LFxuICBrMjogYmlnaW50XG4pOiB7IHAxOiBQOyBwMjogUCB9IHtcbiAgbGV0IGFjYyA9IHBvaW50O1xuICBsZXQgcDEgPSBQb2ludC5aRVJPO1xuICBsZXQgcDIgPSBQb2ludC5aRVJPO1xuICB3aGlsZSAoazEgPiBfMG4gfHwgazIgPiBfMG4pIHtcbiAgICBpZiAoazEgJiBfMW4pIHAxID0gcDEuYWRkKGFjYyk7XG4gICAgaWYgKGsyICYgXzFuKSBwMiA9IHAyLmFkZChhY2MpO1xuICAgIGFjYyA9IGFjYy5kb3VibGUoKTtcbiAgICBrMSA+Pj0gXzFuO1xuICAgIGsyID4+PSBfMW47XG4gIH1cbiAgcmV0dXJuIHsgcDEsIHAyIH07XG59XG5cbi8qKlxuICogUGlwcGVuZ2VyIGFsZ29yaXRobSBmb3IgbXVsdGktc2NhbGFyIG11bHRpcGxpY2F0aW9uIChNU00sIFBhICsgUWIgKyBSYyArIC4uLikuXG4gKiAzMHggZmFzdGVyIHZzIG5haXZlIGFkZGl0aW9uIG9uIEw9NDA5NiwgMTB4IGZhc3RlciB0aGFuIHByZWNvbXB1dGVzLlxuICogRm9yIE49MjU0Yml0LCBMPTEsIGl0IGRvZXM6IDEwMjQgQUREICsgMjU0IERCTC4gRm9yIEw9NTogMTUzNiBBREQgKyAyNTQgREJMLlxuICogQWxnb3JpdGhtaWNhbGx5IGNvbnN0YW50LXRpbWUgKGZvciBzYW1lIEwpLCBldmVuIHdoZW4gMSBwb2ludCArIHNjYWxhciwgb3Igd2hlbiBzY2FsYXIgPSAwLlxuICogQHBhcmFtIGMgQ3VydmUgUG9pbnQgY29uc3RydWN0b3JcbiAqIEBwYXJhbSBmaWVsZE4gZmllbGQgb3ZlciBDVVJWRS5OIC0gaW1wb3J0YW50IHRoYXQgaXQncyBub3Qgb3ZlciBDVVJWRS5QXG4gKiBAcGFyYW0gcG9pbnRzIGFycmF5IG9mIEwgY3VydmUgcG9pbnRzXG4gKiBAcGFyYW0gc2NhbGFycyBhcnJheSBvZiBMIHNjYWxhcnMgKGFrYSBzZWNyZXQga2V5cyAvIGJpZ2ludHMpXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBwaXBwZW5nZXI8UCBleHRlbmRzIEN1cnZlUG9pbnQ8YW55LCBQPiwgUEMgZXh0ZW5kcyBDdXJ2ZVBvaW50Q29uczxQPj4oXG4gIGM6IFBDLFxuICBwb2ludHM6IFBbXSxcbiAgc2NhbGFyczogYmlnaW50W11cbik6IFAge1xuICAvLyBJZiB3ZSBzcGxpdCBzY2FsYXJzIGJ5IHNvbWUgd2luZG93IChsZXQncyBzYXkgOCBiaXRzKSwgZXZlcnkgY2h1bmsgd2lsbCBvbmx5XG4gIC8vIHRha2UgMjU2IGJ1Y2tldHMgZXZlbiBpZiB0aGVyZSBhcmUgNDA5NiBzY2FsYXJzLCBhbHNvIHJlLXVzZXMgZG91YmxlLlxuICAvLyBUT0RPOlxuICAvLyAtIGh0dHBzOi8vZXByaW50LmlhY3Iub3JnLzIwMjQvNzUwLnBkZlxuICAvLyAtIGh0dHBzOi8vdGNoZXMuaWFjci5vcmcvaW5kZXgucGhwL1RDSEVTL2FydGljbGUvdmlldy8xMDI4N1xuICAvLyAwIGlzIGFjY2VwdGVkIGluIHNjYWxhcnNcbiAgY29uc3QgZmllbGROID0gYy5GbjtcbiAgdmFsaWRhdGVNU01Qb2ludHMocG9pbnRzLCBjKTtcbiAgdmFsaWRhdGVNU01TY2FsYXJzKHNjYWxhcnMsIGZpZWxkTik7XG4gIGNvbnN0IHBsZW5ndGggPSBwb2ludHMubGVuZ3RoO1xuICBjb25zdCBzbGVuZ3RoID0gc2NhbGFycy5sZW5ndGg7XG4gIGlmIChwbGVuZ3RoICE9PSBzbGVuZ3RoKSB0aHJvdyBuZXcgRXJyb3IoJ2FycmF5cyBvZiBwb2ludHMgYW5kIHNjYWxhcnMgbXVzdCBoYXZlIGVxdWFsIGxlbmd0aCcpO1xuICAvLyBpZiAocGxlbmd0aCA9PT0gMCkgdGhyb3cgbmV3IEVycm9yKCdhcnJheSBtdXN0IGJlIG9mIGxlbmd0aCA+PSAyJyk7XG4gIGNvbnN0IHplcm8gPSBjLlpFUk87XG4gIGNvbnN0IHdiaXRzID0gYml0TGVuKEJpZ0ludChwbGVuZ3RoKSk7XG4gIGxldCB3aW5kb3dTaXplID0gMTsgLy8gYml0c1xuICBpZiAod2JpdHMgPiAxMikgd2luZG93U2l6ZSA9IHdiaXRzIC0gMztcbiAgZWxzZSBpZiAod2JpdHMgPiA0KSB3aW5kb3dTaXplID0gd2JpdHMgLSAyO1xuICBlbHNlIGlmICh3Yml0cyA+IDApIHdpbmRvd1NpemUgPSAyO1xuICBjb25zdCBNQVNLID0gYml0TWFzayh3aW5kb3dTaXplKTtcbiAgY29uc3QgYnVja2V0cyA9IG5ldyBBcnJheShOdW1iZXIoTUFTSykgKyAxKS5maWxsKHplcm8pOyAvLyArMSBmb3IgemVybyBhcnJheVxuICBjb25zdCBsYXN0Qml0cyA9IE1hdGguZmxvb3IoKGZpZWxkTi5CSVRTIC0gMSkgLyB3aW5kb3dTaXplKSAqIHdpbmRvd1NpemU7XG4gIGxldCBzdW0gPSB6ZXJvO1xuICBmb3IgKGxldCBpID0gbGFzdEJpdHM7IGkgPj0gMDsgaSAtPSB3aW5kb3dTaXplKSB7XG4gICAgYnVja2V0cy5maWxsKHplcm8pO1xuICAgIGZvciAobGV0IGogPSAwOyBqIDwgc2xlbmd0aDsgaisrKSB7XG4gICAgICBjb25zdCBzY2FsYXIgPSBzY2FsYXJzW2pdO1xuICAgICAgY29uc3Qgd2JpdHMgPSBOdW1iZXIoKHNjYWxhciA+PiBCaWdJbnQoaSkpICYgTUFTSyk7XG4gICAgICBidWNrZXRzW3diaXRzXSA9IGJ1Y2tldHNbd2JpdHNdLmFkZChwb2ludHNbal0pO1xuICAgIH1cbiAgICBsZXQgcmVzSSA9IHplcm87IC8vIG5vdCB1c2luZyB0aGlzIHdpbGwgZG8gc21hbGwgc3BlZWQtdXAsIGJ1dCB3aWxsIGxvc2UgY3RcbiAgICAvLyBTa2lwIGZpcnN0IGJ1Y2tldCwgYmVjYXVzZSBpdCBpcyB6ZXJvXG4gICAgZm9yIChsZXQgaiA9IGJ1Y2tldHMubGVuZ3RoIC0gMSwgc3VtSSA9IHplcm87IGogPiAwOyBqLS0pIHtcbiAgICAgIHN1bUkgPSBzdW1JLmFkZChidWNrZXRzW2pdKTtcbiAgICAgIHJlc0kgPSByZXNJLmFkZChzdW1JKTtcbiAgICB9XG4gICAgc3VtID0gc3VtLmFkZChyZXNJKTtcbiAgICBpZiAoaSAhPT0gMCkgZm9yIChsZXQgaiA9IDA7IGogPCB3aW5kb3dTaXplOyBqKyspIHN1bSA9IHN1bS5kb3VibGUoKTtcbiAgfVxuICByZXR1cm4gc3VtIGFzIFA7XG59XG4vKipcbiAqIFByZWNvbXB1dGVkIG11bHRpLXNjYWxhciBtdWx0aXBsaWNhdGlvbiAoTVNNLCBQYSArIFFiICsgUmMgKyAuLi4pLlxuICogQHBhcmFtIGMgQ3VydmUgUG9pbnQgY29uc3RydWN0b3JcbiAqIEBwYXJhbSBmaWVsZE4gZmllbGQgb3ZlciBDVVJWRS5OIC0gaW1wb3J0YW50IHRoYXQgaXQncyBub3Qgb3ZlciBDVVJWRS5QXG4gKiBAcGFyYW0gcG9pbnRzIGFycmF5IG9mIEwgY3VydmUgcG9pbnRzXG4gKiBAcmV0dXJucyBmdW5jdGlvbiB3aGljaCBtdWx0aXBsaWVzIHBvaW50cyB3aXRoIHNjYWFyc1xuICovXG5leHBvcnQgZnVuY3Rpb24gcHJlY29tcHV0ZU1TTVVuc2FmZTxQIGV4dGVuZHMgQ3VydmVQb2ludDxhbnksIFA+LCBQQyBleHRlbmRzIEN1cnZlUG9pbnRDb25zPFA+PihcbiAgYzogUEMsXG4gIHBvaW50czogUFtdLFxuICB3aW5kb3dTaXplOiBudW1iZXJcbik6IChzY2FsYXJzOiBiaWdpbnRbXSkgPT4gUCB7XG4gIC8qKlxuICAgKiBQZXJmb3JtYW5jZSBBbmFseXNpcyBvZiBXaW5kb3ctYmFzZWQgUHJlY29tcHV0YXRpb25cbiAgICpcbiAgICogQmFzZSBDYXNlICgyNTYtYml0IHNjYWxhciwgOC1iaXQgd2luZG93KTpcbiAgICogLSBTdGFuZGFyZCBwcmVjb21wdXRhdGlvbiByZXF1aXJlczpcbiAgICogICAtIDMxIGFkZGl0aW9ucyBwZXIgc2NhbGFyIFx1MDBENyAyNTYgc2NhbGFycyA9IDcsOTM2IG9wc1xuICAgKiAgIC0gUGx1cyAyNTUgc3VtbWFyeSBhZGRpdGlvbnMgPSA4LDE5MSB0b3RhbCBvcHNcbiAgICogICBOb3RlOiBTdW1tYXJ5IGFkZGl0aW9ucyBjYW4gYmUgb3B0aW1pemVkIHZpYSBhY2N1bXVsYXRvclxuICAgKlxuICAgKiBDaHVua2VkIFByZWNvbXB1dGF0aW9uIEFuYWx5c2lzOlxuICAgKiAtIFVzaW5nIDMyIGNodW5rcyByZXF1aXJlczpcbiAgICogICAtIDI1NSBhZGRpdGlvbnMgcGVyIGNodW5rXG4gICAqICAgLSAyNTYgZG91YmxpbmdzXG4gICAqICAgLSBUb3RhbDogKDI1NSBcdTAwRDcgMzIpICsgMjU2ID0gOCw0MTYgb3BzXG4gICAqXG4gICAqIE1lbW9yeSBVc2FnZSBDb21wYXJpc29uOlxuICAgKiBXaW5kb3cgU2l6ZSB8IFN0YW5kYXJkIFBvaW50cyB8IENodW5rZWQgUG9pbnRzXG4gICAqIC0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tLS0tLS1cbiAgICogICAgIDQtYml0ICAgfCAgICAgNTIwICAgICAgICAgfCAgICAgIDE1XG4gICAqICAgICA4LWJpdCAgIHwgICAgNCwyMjQgICAgICAgIHwgICAgIDI1NVxuICAgKiAgICAxMC1iaXQgICB8ICAgMTMsODI0ICAgICAgICB8ICAgMSwwMjNcbiAgICogICAgMTYtYml0ICAgfCAgNTU3LDA1NiAgICAgICAgfCAgNjUsNTM1XG4gICAqXG4gICAqIEtleSBBZHZhbnRhZ2VzOlxuICAgKiAxLiBFbmFibGVzIGxhcmdlciB3aW5kb3cgc2l6ZXMgZHVlIHRvIHJlZHVjZWQgbWVtb3J5IG92ZXJoZWFkXG4gICAqIDIuIE1vcmUgZWZmaWNpZW50IGZvciBzbWFsbGVyIHNjYWxhciBjb3VudHM6XG4gICAqICAgIC0gMTYgY2h1bmtzOiAoMTYgXHUwMEQ3IDI1NSkgKyAyNTYgPSA0LDMzNiBvcHNcbiAgICogICAgLSB+MnggZmFzdGVyIHRoYW4gc3RhbmRhcmQgOCwxOTEgb3BzXG4gICAqXG4gICAqIExpbWl0YXRpb25zOlxuICAgKiAtIE5vdCBzdWl0YWJsZSBmb3IgcGxhaW4gcHJlY29tcHV0ZXMgKHJlcXVpcmVzIDI1NiBjb25zdGFudCBkb3VibGluZ3MpXG4gICAqIC0gUGVyZm9ybWFuY2UgZGVncmFkZXMgd2l0aCBsYXJnZXIgc2NhbGFyIGNvdW50czpcbiAgICogICAtIE9wdGltYWwgZm9yIH4yNTYgc2NhbGFyc1xuICAgKiAgIC0gTGVzcyBlZmZpY2llbnQgZm9yIDQwOTYrIHNjYWxhcnMgKFBpcHBlbmdlciBwcmVmZXJyZWQpXG4gICAqL1xuICBjb25zdCBmaWVsZE4gPSBjLkZuO1xuICB2YWxpZGF0ZVcod2luZG93U2l6ZSwgZmllbGROLkJJVFMpO1xuICB2YWxpZGF0ZU1TTVBvaW50cyhwb2ludHMsIGMpO1xuICBjb25zdCB6ZXJvID0gYy5aRVJPO1xuICBjb25zdCB0YWJsZVNpemUgPSAyICoqIHdpbmRvd1NpemUgLSAxOyAvLyB0YWJsZSBzaXplICh3aXRob3V0IHplcm8pXG4gIGNvbnN0IGNodW5rcyA9IE1hdGguY2VpbChmaWVsZE4uQklUUyAvIHdpbmRvd1NpemUpOyAvLyBjaHVua3Mgb2YgaXRlbVxuICBjb25zdCBNQVNLID0gYml0TWFzayh3aW5kb3dTaXplKTtcbiAgY29uc3QgdGFibGVzID0gcG9pbnRzLm1hcCgocDogUCkgPT4ge1xuICAgIGNvbnN0IHJlcyA9IFtdO1xuICAgIGZvciAobGV0IGkgPSAwLCBhY2MgPSBwOyBpIDwgdGFibGVTaXplOyBpKyspIHtcbiAgICAgIHJlcy5wdXNoKGFjYyk7XG4gICAgICBhY2MgPSBhY2MuYWRkKHApO1xuICAgIH1cbiAgICByZXR1cm4gcmVzO1xuICB9KTtcbiAgcmV0dXJuIChzY2FsYXJzOiBiaWdpbnRbXSk6IFAgPT4ge1xuICAgIHZhbGlkYXRlTVNNU2NhbGFycyhzY2FsYXJzLCBmaWVsZE4pO1xuICAgIGlmIChzY2FsYXJzLmxlbmd0aCA+IHBvaW50cy5sZW5ndGgpXG4gICAgICB0aHJvdyBuZXcgRXJyb3IoJ2FycmF5IG9mIHNjYWxhcnMgbXVzdCBiZSBzbWFsbGVyIHRoYW4gYXJyYXkgb2YgcG9pbnRzJyk7XG4gICAgbGV0IHJlcyA9IHplcm87XG4gICAgZm9yIChsZXQgaSA9IDA7IGkgPCBjaHVua3M7IGkrKykge1xuICAgICAgLy8gTm8gbmVlZCB0byBkb3VibGUgaWYgYWNjdW11bGF0b3IgaXMgc3RpbGwgemVyby5cbiAgICAgIGlmIChyZXMgIT09IHplcm8pIGZvciAobGV0IGogPSAwOyBqIDwgd2luZG93U2l6ZTsgaisrKSByZXMgPSByZXMuZG91YmxlKCk7XG4gICAgICBjb25zdCBzaGlmdEJ5ID0gQmlnSW50KGNodW5rcyAqIHdpbmRvd1NpemUgLSAoaSArIDEpICogd2luZG93U2l6ZSk7XG4gICAgICBmb3IgKGxldCBqID0gMDsgaiA8IHNjYWxhcnMubGVuZ3RoOyBqKyspIHtcbiAgICAgICAgY29uc3QgbiA9IHNjYWxhcnNbal07XG4gICAgICAgIGNvbnN0IGN1cnIgPSBOdW1iZXIoKG4gPj4gc2hpZnRCeSkgJiBNQVNLKTtcbiAgICAgICAgaWYgKCFjdXJyKSBjb250aW51ZTsgLy8gc2tpcCB6ZXJvIHNjYWxhcnMgY2h1bmtzXG4gICAgICAgIHJlcyA9IHJlcy5hZGQodGFibGVzW2pdW2N1cnIgLSAxXSk7XG4gICAgICB9XG4gICAgfVxuICAgIHJldHVybiByZXM7XG4gIH07XG59XG5cbmV4cG9ydCB0eXBlIFZhbGlkQ3VydmVQYXJhbXM8VD4gPSB7XG4gIHA6IGJpZ2ludDtcbiAgbjogYmlnaW50O1xuICBoOiBiaWdpbnQ7XG4gIGE6IFQ7XG4gIGI/OiBUO1xuICBkPzogVDtcbiAgR3g6IFQ7XG4gIEd5OiBUO1xufTtcblxuZnVuY3Rpb24gY3JlYXRlRmllbGQ8VD4ob3JkZXI6IGJpZ2ludCwgZmllbGQ/OiBJRmllbGQ8VD4sIGlzTEU/OiBib29sZWFuKTogSUZpZWxkPFQ+IHtcbiAgaWYgKGZpZWxkKSB7XG4gICAgaWYgKGZpZWxkLk9SREVSICE9PSBvcmRlcikgdGhyb3cgbmV3IEVycm9yKCdGaWVsZC5PUkRFUiBtdXN0IG1hdGNoIG9yZGVyOiBGcCA9PSBwLCBGbiA9PSBuJyk7XG4gICAgdmFsaWRhdGVGaWVsZChmaWVsZCk7XG4gICAgcmV0dXJuIGZpZWxkO1xuICB9IGVsc2Uge1xuICAgIHJldHVybiBGaWVsZChvcmRlciwgeyBpc0xFIH0pIGFzIHVua25vd24gYXMgSUZpZWxkPFQ+O1xuICB9XG59XG5leHBvcnQgdHlwZSBGcEZuPFQ+ID0geyBGcDogSUZpZWxkPFQ+OyBGbjogSUZpZWxkPGJpZ2ludD4gfTtcblxuLyoqIFZhbGlkYXRlcyBDVVJWRSBvcHRzIGFuZCBjcmVhdGVzIGZpZWxkcyAqL1xuZXhwb3J0IGZ1bmN0aW9uIGNyZWF0ZUN1cnZlRmllbGRzPFQ+KFxuICB0eXBlOiAnd2VpZXJzdHJhc3MnIHwgJ2Vkd2FyZHMnLFxuICBDVVJWRTogVmFsaWRDdXJ2ZVBhcmFtczxUPixcbiAgY3VydmVPcHRzOiBQYXJ0aWFsPEZwRm48VD4+ID0ge30sXG4gIEZwRm5MRT86IGJvb2xlYW5cbik6IEZwRm48VD4gJiB7IENVUlZFOiBWYWxpZEN1cnZlUGFyYW1zPFQ+IH0ge1xuICBpZiAoRnBGbkxFID09PSB1bmRlZmluZWQpIEZwRm5MRSA9IHR5cGUgPT09ICdlZHdhcmRzJztcbiAgaWYgKCFDVVJWRSB8fCB0eXBlb2YgQ1VSVkUgIT09ICdvYmplY3QnKSB0aHJvdyBuZXcgRXJyb3IoYGV4cGVjdGVkIHZhbGlkICR7dHlwZX0gQ1VSVkUgb2JqZWN0YCk7XG4gIGZvciAoY29uc3QgcCBvZiBbJ3AnLCAnbicsICdoJ10gYXMgY29uc3QpIHtcbiAgICBjb25zdCB2YWwgPSBDVVJWRVtwXTtcbiAgICBpZiAoISh0eXBlb2YgdmFsID09PSAnYmlnaW50JyAmJiB2YWwgPiBfMG4pKVxuICAgICAgdGhyb3cgbmV3IEVycm9yKGBDVVJWRS4ke3B9IG11c3QgYmUgcG9zaXRpdmUgYmlnaW50YCk7XG4gIH1cbiAgY29uc3QgRnAgPSBjcmVhdGVGaWVsZChDVVJWRS5wLCBjdXJ2ZU9wdHMuRnAsIEZwRm5MRSk7XG4gIGNvbnN0IEZuID0gY3JlYXRlRmllbGQoQ1VSVkUubiwgY3VydmVPcHRzLkZuLCBGcEZuTEUpO1xuICBjb25zdCBfYjogJ2InIHwgJ2QnID0gdHlwZSA9PT0gJ3dlaWVyc3RyYXNzJyA/ICdiJyA6ICdkJztcbiAgY29uc3QgcGFyYW1zID0gWydHeCcsICdHeScsICdhJywgX2JdIGFzIGNvbnN0O1xuICBmb3IgKGNvbnN0IHAgb2YgcGFyYW1zKSB7XG4gICAgLy8gQHRzLWlnbm9yZVxuICAgIGlmICghRnAuaXNWYWxpZChDVVJWRVtwXSkpXG4gICAgICB0aHJvdyBuZXcgRXJyb3IoYENVUlZFLiR7cH0gbXVzdCBiZSB2YWxpZCBmaWVsZCBlbGVtZW50IG9mIENVUlZFLkZwYCk7XG4gIH1cbiAgQ1VSVkUgPSBPYmplY3QuZnJlZXplKE9iamVjdC5hc3NpZ24oe30sIENVUlZFKSk7XG4gIHJldHVybiB7IENVUlZFLCBGcCwgRm4gfTtcbn1cblxudHlwZSBLZXlnZW5GbiA9IChcbiAgc2VlZD86IFVpbnQ4QXJyYXksXG4gIGlzQ29tcHJlc3NlZD86IGJvb2xlYW5cbikgPT4geyBzZWNyZXRLZXk6IFVpbnQ4QXJyYXk7IHB1YmxpY0tleTogVWludDhBcnJheSB9O1xuZXhwb3J0IGZ1bmN0aW9uIGNyZWF0ZUtleWdlbihcbiAgcmFuZG9tU2VjcmV0S2V5OiBGdW5jdGlvbixcbiAgZ2V0UHVibGljS2V5OiBTaWduZXJbJ2dldFB1YmxpY0tleSddXG4pOiBLZXlnZW5GbiB7XG4gIHJldHVybiBmdW5jdGlvbiBrZXlnZW4oc2VlZD86IFVpbnQ4QXJyYXkpIHtcbiAgICBjb25zdCBzZWNyZXRLZXkgPSByYW5kb21TZWNyZXRLZXkoc2VlZCk7XG4gICAgcmV0dXJuIHsgc2VjcmV0S2V5LCBwdWJsaWNLZXk6IGdldFB1YmxpY0tleShzZWNyZXRLZXkpIH07XG4gIH07XG59XG4iLCAiLyoqXG4gKiBIZXgsIGJ5dGVzIGFuZCBudW1iZXIgdXRpbGl0aWVzLlxuICogQG1vZHVsZVxuICovXG4vKiEgbm9ibGUtY3VydmVzIC0gTUlUIExpY2Vuc2UgKGMpIDIwMjIgUGF1bCBNaWxsZXIgKHBhdWxtaWxsci5jb20pICovXG5pbXBvcnQge1xuICBhYnl0ZXMgYXMgYWJ5dGVzXyxcbiAgYW51bWJlcixcbiAgYnl0ZXNUb0hleCBhcyBieXRlc1RvSGV4XyxcbiAgY29uY2F0Qnl0ZXMgYXMgY29uY2F0Qnl0ZXNfLFxuICBoZXhUb0J5dGVzIGFzIGhleFRvQnl0ZXNfLFxufSBmcm9tICdAbm9ibGUvaGFzaGVzL3V0aWxzLmpzJztcbmV4cG9ydCB7XG4gIGFieXRlcyxcbiAgYW51bWJlcixcbiAgYnl0ZXNUb0hleCxcbiAgY29uY2F0Qnl0ZXMsXG4gIGhleFRvQnl0ZXMsXG4gIGlzQnl0ZXMsXG4gIHJhbmRvbUJ5dGVzLFxufSBmcm9tICdAbm9ibGUvaGFzaGVzL3V0aWxzLmpzJztcbmNvbnN0IF8wbiA9IC8qIEBfX1BVUkVfXyAqLyBCaWdJbnQoMCk7XG5jb25zdCBfMW4gPSAvKiBAX19QVVJFX18gKi8gQmlnSW50KDEpO1xuXG5leHBvcnQgdHlwZSBDSGFzaCA9IHtcbiAgKG1lc3NhZ2U6IFVpbnQ4QXJyYXkpOiBVaW50OEFycmF5O1xuICBibG9ja0xlbjogbnVtYmVyO1xuICBvdXRwdXRMZW46IG51bWJlcjtcbiAgY3JlYXRlKG9wdHM/OiB7IGRrTGVuPzogbnVtYmVyIH0pOiBhbnk7IC8vIEZvciBzaGFrZVxufTtcbmV4cG9ydCB0eXBlIEZIYXNoID0gKG1lc3NhZ2U6IFVpbnQ4QXJyYXkpID0+IFVpbnQ4QXJyYXk7XG5leHBvcnQgZnVuY3Rpb24gYWJvb2wodmFsdWU6IGJvb2xlYW4sIHRpdGxlOiBzdHJpbmcgPSAnJyk6IGJvb2xlYW4ge1xuICBpZiAodHlwZW9mIHZhbHVlICE9PSAnYm9vbGVhbicpIHtcbiAgICBjb25zdCBwcmVmaXggPSB0aXRsZSAmJiBgXCIke3RpdGxlfVwiIGA7XG4gICAgdGhyb3cgbmV3IEVycm9yKHByZWZpeCArICdleHBlY3RlZCBib29sZWFuLCBnb3QgdHlwZT0nICsgdHlwZW9mIHZhbHVlKTtcbiAgfVxuICByZXR1cm4gdmFsdWU7XG59XG5cbi8vIFVzZWQgaW4gd2VpZXJzdHJhc3MsIGRlclxuZnVuY3Rpb24gYWJpZ251bWJlcihuOiBudW1iZXIgfCBiaWdpbnQpIHtcbiAgaWYgKHR5cGVvZiBuID09PSAnYmlnaW50Jykge1xuICAgIGlmICghaXNQb3NCaWcobikpIHRocm93IG5ldyBFcnJvcigncG9zaXRpdmUgYmlnaW50IGV4cGVjdGVkLCBnb3QgJyArIG4pO1xuICB9IGVsc2UgYW51bWJlcihuKTtcbiAgcmV0dXJuIG47XG59XG5cbmV4cG9ydCBmdW5jdGlvbiBhc2FmZW51bWJlcih2YWx1ZTogbnVtYmVyLCB0aXRsZTogc3RyaW5nID0gJycpOiB2b2lkIHtcbiAgaWYgKCFOdW1iZXIuaXNTYWZlSW50ZWdlcih2YWx1ZSkpIHtcbiAgICBjb25zdCBwcmVmaXggPSB0aXRsZSAmJiBgXCIke3RpdGxlfVwiIGA7XG4gICAgdGhyb3cgbmV3IEVycm9yKHByZWZpeCArICdleHBlY3RlZCBzYWZlIGludGVnZXIsIGdvdCB0eXBlPScgKyB0eXBlb2YgdmFsdWUpO1xuICB9XG59XG5cbmV4cG9ydCBmdW5jdGlvbiBudW1iZXJUb0hleFVucGFkZGVkKG51bTogbnVtYmVyIHwgYmlnaW50KTogc3RyaW5nIHtcbiAgY29uc3QgaGV4ID0gYWJpZ251bWJlcihudW0pLnRvU3RyaW5nKDE2KTtcbiAgcmV0dXJuIGhleC5sZW5ndGggJiAxID8gJzAnICsgaGV4IDogaGV4O1xufVxuXG5leHBvcnQgZnVuY3Rpb24gaGV4VG9OdW1iZXIoaGV4OiBzdHJpbmcpOiBiaWdpbnQge1xuICBpZiAodHlwZW9mIGhleCAhPT0gJ3N0cmluZycpIHRocm93IG5ldyBFcnJvcignaGV4IHN0cmluZyBleHBlY3RlZCwgZ290ICcgKyB0eXBlb2YgaGV4KTtcbiAgcmV0dXJuIGhleCA9PT0gJycgPyBfMG4gOiBCaWdJbnQoJzB4JyArIGhleCk7IC8vIEJpZyBFbmRpYW5cbn1cblxuLy8gQkU6IEJpZyBFbmRpYW4sIExFOiBMaXR0bGUgRW5kaWFuXG5leHBvcnQgZnVuY3Rpb24gYnl0ZXNUb051bWJlckJFKGJ5dGVzOiBVaW50OEFycmF5KTogYmlnaW50IHtcbiAgcmV0dXJuIGhleFRvTnVtYmVyKGJ5dGVzVG9IZXhfKGJ5dGVzKSk7XG59XG5leHBvcnQgZnVuY3Rpb24gYnl0ZXNUb051bWJlckxFKGJ5dGVzOiBVaW50OEFycmF5KTogYmlnaW50IHtcbiAgcmV0dXJuIGhleFRvTnVtYmVyKGJ5dGVzVG9IZXhfKGNvcHlCeXRlcyhhYnl0ZXNfKGJ5dGVzKSkucmV2ZXJzZSgpKSk7XG59XG5cbmV4cG9ydCBmdW5jdGlvbiBudW1iZXJUb0J5dGVzQkUobjogbnVtYmVyIHwgYmlnaW50LCBsZW46IG51bWJlcik6IFVpbnQ4QXJyYXkge1xuICBhbnVtYmVyKGxlbik7XG4gIG4gPSBhYmlnbnVtYmVyKG4pO1xuICBjb25zdCByZXMgPSBoZXhUb0J5dGVzXyhuLnRvU3RyaW5nKDE2KS5wYWRTdGFydChsZW4gKiAyLCAnMCcpKTtcbiAgaWYgKHJlcy5sZW5ndGggIT09IGxlbikgdGhyb3cgbmV3IEVycm9yKCdudW1iZXIgdG9vIGxhcmdlJyk7XG4gIHJldHVybiByZXM7XG59XG5leHBvcnQgZnVuY3Rpb24gbnVtYmVyVG9CeXRlc0xFKG46IG51bWJlciB8IGJpZ2ludCwgbGVuOiBudW1iZXIpOiBVaW50OEFycmF5IHtcbiAgcmV0dXJuIG51bWJlclRvQnl0ZXNCRShuLCBsZW4pLnJldmVyc2UoKTtcbn1cbi8vIFVucGFkZGVkLCByYXJlbHkgdXNlZFxuZXhwb3J0IGZ1bmN0aW9uIG51bWJlclRvVmFyQnl0ZXNCRShuOiBudW1iZXIgfCBiaWdpbnQpOiBVaW50OEFycmF5IHtcbiAgcmV0dXJuIGhleFRvQnl0ZXNfKG51bWJlclRvSGV4VW5wYWRkZWQoYWJpZ251bWJlcihuKSkpO1xufVxuXG4vLyBDb21wYXJlcyAyIHU4YS1zIGluIGtpbmRhIGNvbnN0YW50IHRpbWVcbmV4cG9ydCBmdW5jdGlvbiBlcXVhbEJ5dGVzKGE6IFVpbnQ4QXJyYXksIGI6IFVpbnQ4QXJyYXkpOiBib29sZWFuIHtcbiAgaWYgKGEubGVuZ3RoICE9PSBiLmxlbmd0aCkgcmV0dXJuIGZhbHNlO1xuICBsZXQgZGlmZiA9IDA7XG4gIGZvciAobGV0IGkgPSAwOyBpIDwgYS5sZW5ndGg7IGkrKykgZGlmZiB8PSBhW2ldIF4gYltpXTtcbiAgcmV0dXJuIGRpZmYgPT09IDA7XG59XG5cbi8qKlxuICogQ29waWVzIFVpbnQ4QXJyYXkuIFdlIGNhbid0IHVzZSB1OGEuc2xpY2UoKSwgYmVjYXVzZSB1OGEgY2FuIGJlIEJ1ZmZlcixcbiAqIGFuZCBCdWZmZXIjc2xpY2UgY3JlYXRlcyBtdXRhYmxlIGNvcHkuIE5ldmVyIHVzZSBCdWZmZXJzIVxuICovXG5leHBvcnQgZnVuY3Rpb24gY29weUJ5dGVzKGJ5dGVzOiBVaW50OEFycmF5KTogVWludDhBcnJheSB7XG4gIHJldHVybiBVaW50OEFycmF5LmZyb20oYnl0ZXMpO1xufVxuXG4vKipcbiAqIERlY29kZXMgNy1iaXQgQVNDSUkgc3RyaW5nIHRvIFVpbnQ4QXJyYXksIHRocm93cyBvbiBub24tYXNjaWkgc3ltYm9sc1xuICogU2hvdWxkIGJlIHNhZmUgdG8gdXNlIGZvciB0aGluZ3MgZXhwZWN0ZWQgdG8gYmUgQVNDSUkuXG4gKiBSZXR1cm5zIGV4YWN0IHNhbWUgcmVzdWx0IGFzIGBUZXh0RW5jb2RlcmAgZm9yIEFTQ0lJIG9yIHRocm93cy5cbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGFzY2lpVG9CeXRlcyhhc2NpaTogc3RyaW5nKTogVWludDhBcnJheSB7XG4gIHJldHVybiBVaW50OEFycmF5LmZyb20oYXNjaWksIChjLCBpKSA9PiB7XG4gICAgY29uc3QgY2hhckNvZGUgPSBjLmNoYXJDb2RlQXQoMCk7XG4gICAgaWYgKGMubGVuZ3RoICE9PSAxIHx8IGNoYXJDb2RlID4gMTI3KSB7XG4gICAgICB0aHJvdyBuZXcgRXJyb3IoXG4gICAgICAgIGBzdHJpbmcgY29udGFpbnMgbm9uLUFTQ0lJIGNoYXJhY3RlciBcIiR7YXNjaWlbaV19XCIgd2l0aCBjb2RlICR7Y2hhckNvZGV9IGF0IHBvc2l0aW9uICR7aX1gXG4gICAgICApO1xuICAgIH1cbiAgICByZXR1cm4gY2hhckNvZGU7XG4gIH0pO1xufVxuXG4vLyBJcyBwb3NpdGl2ZSBiaWdpbnRcbmNvbnN0IGlzUG9zQmlnID0gKG46IGJpZ2ludCkgPT4gdHlwZW9mIG4gPT09ICdiaWdpbnQnICYmIF8wbiA8PSBuO1xuXG5leHBvcnQgZnVuY3Rpb24gaW5SYW5nZShuOiBiaWdpbnQsIG1pbjogYmlnaW50LCBtYXg6IGJpZ2ludCk6IGJvb2xlYW4ge1xuICByZXR1cm4gaXNQb3NCaWcobikgJiYgaXNQb3NCaWcobWluKSAmJiBpc1Bvc0JpZyhtYXgpICYmIG1pbiA8PSBuICYmIG4gPCBtYXg7XG59XG5cbi8qKlxuICogQXNzZXJ0cyBtaW4gPD0gbiA8IG1heC4gTk9URTogSXQncyA8IG1heCBhbmQgbm90IDw9IG1heC5cbiAqIEBleGFtcGxlXG4gKiBhSW5SYW5nZSgneCcsIHgsIDFuLCAyNTZuKTsgLy8gd291bGQgYXNzdW1lIHggaXMgaW4gKDFuLi4yNTVuKVxuICovXG5leHBvcnQgZnVuY3Rpb24gYUluUmFuZ2UodGl0bGU6IHN0cmluZywgbjogYmlnaW50LCBtaW46IGJpZ2ludCwgbWF4OiBiaWdpbnQpOiB2b2lkIHtcbiAgLy8gV2h5IG1pbiA8PSBuIDwgbWF4IGFuZCBub3QgYSAobWluIDwgbiA8IG1heCkgT1IgYiAobWluIDw9IG4gPD0gbWF4KT9cbiAgLy8gY29uc2lkZXIgUD0yNTZuLCBtaW49MG4sIG1heD1QXG4gIC8vIC0gYSBmb3IgbWluPTAgd291bGQgcmVxdWlyZSAtMTogICAgICAgICAgYGluUmFuZ2UoJ3gnLCB4LCAtMW4sIFApYFxuICAvLyAtIGIgd291bGQgY29tbW9ubHkgcmVxdWlyZSBzdWJ0cmFjdGlvbjogIGBpblJhbmdlKCd4JywgeCwgMG4sIFAgLSAxbilgXG4gIC8vIC0gb3VyIHdheSBpcyB0aGUgY2xlYW5lc3Q6ICAgICAgICAgICAgICAgYGluUmFuZ2UoJ3gnLCB4LCAwbiwgUClcbiAgaWYgKCFpblJhbmdlKG4sIG1pbiwgbWF4KSlcbiAgICB0aHJvdyBuZXcgRXJyb3IoJ2V4cGVjdGVkIHZhbGlkICcgKyB0aXRsZSArICc6ICcgKyBtaW4gKyAnIDw9IG4gPCAnICsgbWF4ICsgJywgZ290ICcgKyBuKTtcbn1cblxuLy8gQml0IG9wZXJhdGlvbnNcblxuLyoqXG4gKiBDYWxjdWxhdGVzIGFtb3VudCBvZiBiaXRzIGluIGEgYmlnaW50LlxuICogU2FtZSBhcyBgbi50b1N0cmluZygyKS5sZW5ndGhgXG4gKiBUT0RPOiBtZXJnZSB3aXRoIG5MZW5ndGggaW4gbW9kdWxhclxuICovXG5leHBvcnQgZnVuY3Rpb24gYml0TGVuKG46IGJpZ2ludCk6IG51bWJlciB7XG4gIGxldCBsZW47XG4gIGZvciAobGVuID0gMDsgbiA+IF8wbjsgbiA+Pj0gXzFuLCBsZW4gKz0gMSk7XG4gIHJldHVybiBsZW47XG59XG5cbi8qKlxuICogR2V0cyBzaW5nbGUgYml0IGF0IHBvc2l0aW9uLlxuICogTk9URTogZmlyc3QgYml0IHBvc2l0aW9uIGlzIDAgKHNhbWUgYXMgYXJyYXlzKVxuICogU2FtZSBhcyBgISErQXJyYXkuZnJvbShuLnRvU3RyaW5nKDIpKS5yZXZlcnNlKClbcG9zXWBcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGJpdEdldChuOiBiaWdpbnQsIHBvczogbnVtYmVyKTogYmlnaW50IHtcbiAgcmV0dXJuIChuID4+IEJpZ0ludChwb3MpKSAmIF8xbjtcbn1cblxuLyoqXG4gKiBTZXRzIHNpbmdsZSBiaXQgYXQgcG9zaXRpb24uXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBiaXRTZXQobjogYmlnaW50LCBwb3M6IG51bWJlciwgdmFsdWU6IGJvb2xlYW4pOiBiaWdpbnQge1xuICByZXR1cm4gbiB8ICgodmFsdWUgPyBfMW4gOiBfMG4pIDw8IEJpZ0ludChwb3MpKTtcbn1cblxuLyoqXG4gKiBDYWxjdWxhdGUgbWFzayBmb3IgTiBiaXRzLiBOb3QgdXNpbmcgKiogb3BlcmF0b3Igd2l0aCBiaWdpbnRzIGJlY2F1c2Ugb2Ygb2xkIGVuZ2luZXMuXG4gKiBTYW1lIGFzIEJpZ0ludChgMGIke0FycmF5KGkpLmZpbGwoJzEnKS5qb2luKCcnKX1gKVxuICovXG5leHBvcnQgY29uc3QgYml0TWFzayA9IChuOiBudW1iZXIpOiBiaWdpbnQgPT4gKF8xbiA8PCBCaWdJbnQobikpIC0gXzFuO1xuXG4vLyBEUkJHXG5cbnR5cGUgUHJlZDxUPiA9ICh2OiBVaW50OEFycmF5KSA9PiBUIHwgdW5kZWZpbmVkO1xuLyoqXG4gKiBNaW5pbWFsIEhNQUMtRFJCRyBmcm9tIE5JU1QgODAwLTkwIGZvciBSRkM2OTc5IHNpZ3MuXG4gKiBAcmV0dXJucyBmdW5jdGlvbiB0aGF0IHdpbGwgY2FsbCBEUkJHIHVudGlsIDJuZCBhcmcgcmV0dXJucyBzb21ldGhpbmcgbWVhbmluZ2Z1bFxuICogQGV4YW1wbGVcbiAqICAgY29uc3QgZHJiZyA9IGNyZWF0ZUhtYWNEUkJHPEtleT4oMzIsIDMyLCBobWFjKTtcbiAqICAgZHJiZyhzZWVkLCBieXRlc1RvS2V5KTsgLy8gYnl0ZXNUb0tleSBtdXN0IHJldHVybiBLZXkgb3IgdW5kZWZpbmVkXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBjcmVhdGVIbWFjRHJiZzxUPihcbiAgaGFzaExlbjogbnVtYmVyLFxuICBxQnl0ZUxlbjogbnVtYmVyLFxuICBobWFjRm46IChrZXk6IFVpbnQ4QXJyYXksIG1lc3NhZ2U6IFVpbnQ4QXJyYXkpID0+IFVpbnQ4QXJyYXlcbik6IChzZWVkOiBVaW50OEFycmF5LCBwcmVkaWNhdGU6IFByZWQ8VD4pID0+IFQge1xuICBhbnVtYmVyKGhhc2hMZW4sICdoYXNoTGVuJyk7XG4gIGFudW1iZXIocUJ5dGVMZW4sICdxQnl0ZUxlbicpO1xuICBpZiAodHlwZW9mIGhtYWNGbiAhPT0gJ2Z1bmN0aW9uJykgdGhyb3cgbmV3IEVycm9yKCdobWFjRm4gbXVzdCBiZSBhIGZ1bmN0aW9uJyk7XG4gIGNvbnN0IHU4biA9IChsZW46IG51bWJlcik6IFVpbnQ4QXJyYXkgPT4gbmV3IFVpbnQ4QXJyYXkobGVuKTsgLy8gY3JlYXRlcyBVaW50OEFycmF5XG4gIGNvbnN0IE5VTEwgPSBVaW50OEFycmF5Lm9mKCk7XG4gIGNvbnN0IGJ5dGUwID0gVWludDhBcnJheS5vZigweDAwKTtcbiAgY29uc3QgYnl0ZTEgPSBVaW50OEFycmF5Lm9mKDB4MDEpO1xuICBjb25zdCBfbWF4RHJiZ0l0ZXJzID0gMTAwMDtcblxuICAvLyBTdGVwIEIsIFN0ZXAgQzogc2V0IGhhc2hMZW4gdG8gOCpjZWlsKGhsZW4vOClcbiAgbGV0IHYgPSB1OG4oaGFzaExlbik7IC8vIE1pbmltYWwgbm9uLWZ1bGwtc3BlYyBITUFDLURSQkcgZnJvbSBOSVNUIDgwMC05MCBmb3IgUkZDNjk3OSBzaWdzLlxuICBsZXQgayA9IHU4bihoYXNoTGVuKTsgLy8gU3RlcHMgQiBhbmQgQyBvZiBSRkM2OTc5IDMuMjogc2V0IGhhc2hMZW4sIGluIG91ciBjYXNlIGFsd2F5cyBzYW1lXG4gIGxldCBpID0gMDsgLy8gSXRlcmF0aW9ucyBjb3VudGVyLCB3aWxsIHRocm93IHdoZW4gb3ZlciAxMDAwXG4gIGNvbnN0IHJlc2V0ID0gKCkgPT4ge1xuICAgIHYuZmlsbCgxKTtcbiAgICBrLmZpbGwoMCk7XG4gICAgaSA9IDA7XG4gIH07XG4gIGNvbnN0IGggPSAoLi4ubXNnczogVWludDhBcnJheVtdKSA9PiBobWFjRm4oaywgY29uY2F0Qnl0ZXNfKHYsIC4uLm1zZ3MpKTsgLy8gaG1hYyhrKSh2LCAuLi52YWx1ZXMpXG4gIGNvbnN0IHJlc2VlZCA9IChzZWVkOiBVaW50OEFycmF5ID0gTlVMTCkgPT4ge1xuICAgIC8vIEhNQUMtRFJCRyByZXNlZWQoKSBmdW5jdGlvbi4gU3RlcHMgRC1HXG4gICAgayA9IGgoYnl0ZTAsIHNlZWQpOyAvLyBrID0gaG1hYyhrIHx8IHYgfHwgMHgwMCB8fCBzZWVkKVxuICAgIHYgPSBoKCk7IC8vIHYgPSBobWFjKGsgfHwgdilcbiAgICBpZiAoc2VlZC5sZW5ndGggPT09IDApIHJldHVybjtcbiAgICBrID0gaChieXRlMSwgc2VlZCk7IC8vIGsgPSBobWFjKGsgfHwgdiB8fCAweDAxIHx8IHNlZWQpXG4gICAgdiA9IGgoKTsgLy8gdiA9IGhtYWMoayB8fCB2KVxuICB9O1xuICBjb25zdCBnZW4gPSAoKSA9PiB7XG4gICAgLy8gSE1BQy1EUkJHIGdlbmVyYXRlKCkgZnVuY3Rpb25cbiAgICBpZiAoaSsrID49IF9tYXhEcmJnSXRlcnMpIHRocm93IG5ldyBFcnJvcignZHJiZzogdHJpZWQgbWF4IGFtb3VudCBvZiBpdGVyYXRpb25zJyk7XG4gICAgbGV0IGxlbiA9IDA7XG4gICAgY29uc3Qgb3V0OiBVaW50OEFycmF5W10gPSBbXTtcbiAgICB3aGlsZSAobGVuIDwgcUJ5dGVMZW4pIHtcbiAgICAgIHYgPSBoKCk7XG4gICAgICBjb25zdCBzbCA9IHYuc2xpY2UoKTtcbiAgICAgIG91dC5wdXNoKHNsKTtcbiAgICAgIGxlbiArPSB2Lmxlbmd0aDtcbiAgICB9XG4gICAgcmV0dXJuIGNvbmNhdEJ5dGVzXyguLi5vdXQpO1xuICB9O1xuICBjb25zdCBnZW5VbnRpbCA9IChzZWVkOiBVaW50OEFycmF5LCBwcmVkOiBQcmVkPFQ+KTogVCA9PiB7XG4gICAgcmVzZXQoKTtcbiAgICByZXNlZWQoc2VlZCk7IC8vIFN0ZXBzIEQtR1xuICAgIGxldCByZXM6IFQgfCB1bmRlZmluZWQgPSB1bmRlZmluZWQ7IC8vIFN0ZXAgSDogZ3JpbmQgdW50aWwgayBpcyBpbiBbMS4ubi0xXVxuICAgIHdoaWxlICghKHJlcyA9IHByZWQoZ2VuKCkpKSkgcmVzZWVkKCk7XG4gICAgcmVzZXQoKTtcbiAgICByZXR1cm4gcmVzO1xuICB9O1xuICByZXR1cm4gZ2VuVW50aWw7XG59XG5cbmV4cG9ydCBmdW5jdGlvbiB2YWxpZGF0ZU9iamVjdChcbiAgb2JqZWN0OiBSZWNvcmQ8c3RyaW5nLCBhbnk+LFxuICBmaWVsZHM6IFJlY29yZDxzdHJpbmcsIHN0cmluZz4gPSB7fSxcbiAgb3B0RmllbGRzOiBSZWNvcmQ8c3RyaW5nLCBzdHJpbmc+ID0ge31cbik6IHZvaWQge1xuICBpZiAoIW9iamVjdCB8fCB0eXBlb2Ygb2JqZWN0ICE9PSAnb2JqZWN0JykgdGhyb3cgbmV3IEVycm9yKCdleHBlY3RlZCB2YWxpZCBvcHRpb25zIG9iamVjdCcpO1xuICB0eXBlIEl0ZW0gPSBrZXlvZiB0eXBlb2Ygb2JqZWN0O1xuICBmdW5jdGlvbiBjaGVja0ZpZWxkKGZpZWxkTmFtZTogSXRlbSwgZXhwZWN0ZWRUeXBlOiBzdHJpbmcsIGlzT3B0OiBib29sZWFuKSB7XG4gICAgY29uc3QgdmFsID0gb2JqZWN0W2ZpZWxkTmFtZV07XG4gICAgaWYgKGlzT3B0ICYmIHZhbCA9PT0gdW5kZWZpbmVkKSByZXR1cm47XG4gICAgY29uc3QgY3VycmVudCA9IHR5cGVvZiB2YWw7XG4gICAgaWYgKGN1cnJlbnQgIT09IGV4cGVjdGVkVHlwZSB8fCB2YWwgPT09IG51bGwpXG4gICAgICB0aHJvdyBuZXcgRXJyb3IoYHBhcmFtIFwiJHtmaWVsZE5hbWV9XCIgaXMgaW52YWxpZDogZXhwZWN0ZWQgJHtleHBlY3RlZFR5cGV9LCBnb3QgJHtjdXJyZW50fWApO1xuICB9XG4gIGNvbnN0IGl0ZXIgPSAoZjogdHlwZW9mIGZpZWxkcywgaXNPcHQ6IGJvb2xlYW4pID0+XG4gICAgT2JqZWN0LmVudHJpZXMoZikuZm9yRWFjaCgoW2ssIHZdKSA9PiBjaGVja0ZpZWxkKGssIHYsIGlzT3B0KSk7XG4gIGl0ZXIoZmllbGRzLCBmYWxzZSk7XG4gIGl0ZXIob3B0RmllbGRzLCB0cnVlKTtcbn1cblxuLyoqXG4gKiB0aHJvd3Mgbm90IGltcGxlbWVudGVkIGVycm9yXG4gKi9cbmV4cG9ydCBjb25zdCBub3RJbXBsZW1lbnRlZCA9ICgpOiBuZXZlciA9PiB7XG4gIHRocm93IG5ldyBFcnJvcignbm90IGltcGxlbWVudGVkJyk7XG59O1xuXG4vKipcbiAqIE1lbW9pemVzIChjYWNoZXMpIGNvbXB1dGF0aW9uIHJlc3VsdC5cbiAqIFVzZXMgV2Vha01hcDogdGhlIHZhbHVlIGlzIGdvaW5nIGF1dG8tY2xlYW5lZCBieSBHQyBhZnRlciBsYXN0IHJlZmVyZW5jZSBpcyByZW1vdmVkLlxuICovXG5leHBvcnQgZnVuY3Rpb24gbWVtb2l6ZWQ8VCBleHRlbmRzIG9iamVjdCwgUiwgTyBleHRlbmRzIGFueVtdPihcbiAgZm46IChhcmc6IFQsIC4uLmFyZ3M6IE8pID0+IFJcbik6IChhcmc6IFQsIC4uLmFyZ3M6IE8pID0+IFIge1xuICBjb25zdCBtYXAgPSBuZXcgV2Vha01hcDxULCBSPigpO1xuICByZXR1cm4gKGFyZzogVCwgLi4uYXJnczogTyk6IFIgPT4ge1xuICAgIGNvbnN0IHZhbCA9IG1hcC5nZXQoYXJnKTtcbiAgICBpZiAodmFsICE9PSB1bmRlZmluZWQpIHJldHVybiB2YWw7XG4gICAgY29uc3QgY29tcHV0ZWQgPSBmbihhcmcsIC4uLmFyZ3MpO1xuICAgIG1hcC5zZXQoYXJnLCBjb21wdXRlZCk7XG4gICAgcmV0dXJuIGNvbXB1dGVkO1xuICB9O1xufVxuXG5leHBvcnQgaW50ZXJmYWNlIENyeXB0b0tleXMge1xuICBsZW5ndGhzOiB7IHNlZWQ/OiBudW1iZXI7IHB1YmxpYz86IG51bWJlcjsgc2VjcmV0PzogbnVtYmVyIH07XG4gIGtleWdlbjogKHNlZWQ/OiBVaW50OEFycmF5KSA9PiB7IHNlY3JldEtleTogVWludDhBcnJheTsgcHVibGljS2V5OiBVaW50OEFycmF5IH07XG4gIGdldFB1YmxpY0tleTogKHNlY3JldEtleTogVWludDhBcnJheSkgPT4gVWludDhBcnJheTtcbn1cblxuLyoqIEdlbmVyaWMgaW50ZXJmYWNlIGZvciBzaWduYXR1cmVzLiBIYXMga2V5Z2VuLCBzaWduIGFuZCB2ZXJpZnkuICovXG5leHBvcnQgaW50ZXJmYWNlIFNpZ25lciBleHRlbmRzIENyeXB0b0tleXMge1xuICAvLyBJbnRlcmZhY2VzIGFyZSBmdW4uIFdlIGNhbm5vdCBqdXN0IGFkZCBuZXcgZmllbGRzIHdpdGhvdXQgY29weWluZyBvbGQgb25lcy5cbiAgbGVuZ3Roczoge1xuICAgIHNlZWQ/OiBudW1iZXI7XG4gICAgcHVibGljPzogbnVtYmVyO1xuICAgIHNlY3JldD86IG51bWJlcjtcbiAgICBzaWduUmFuZD86IG51bWJlcjtcbiAgICBzaWduYXR1cmU/OiBudW1iZXI7XG4gIH07XG4gIHNpZ246IChtc2c6IFVpbnQ4QXJyYXksIHNlY3JldEtleTogVWludDhBcnJheSkgPT4gVWludDhBcnJheTtcbiAgdmVyaWZ5OiAoc2lnOiBVaW50OEFycmF5LCBtc2c6IFVpbnQ4QXJyYXksIHB1YmxpY0tleTogVWludDhBcnJheSkgPT4gYm9vbGVhbjtcbn1cbiIsICIvKipcbiAqIFV0aWxzIGZvciBtb2R1bGFyIGRpdmlzaW9uIGFuZCBmaWVsZHMuXG4gKiBGaWVsZCBvdmVyIDExIGlzIGEgZmluaXRlIChHYWxvaXMpIGZpZWxkIGlzIGludGVnZXIgbnVtYmVyIG9wZXJhdGlvbnMgYG1vZCAxMWAuXG4gKiBUaGVyZSBpcyBubyBkaXZpc2lvbjogaXQgaXMgcmVwbGFjZWQgYnkgbW9kdWxhciBtdWx0aXBsaWNhdGl2ZSBpbnZlcnNlLlxuICogQG1vZHVsZVxuICovXG4vKiEgbm9ibGUtY3VydmVzIC0gTUlUIExpY2Vuc2UgKGMpIDIwMjIgUGF1bCBNaWxsZXIgKHBhdWxtaWxsci5jb20pICovXG5pbXBvcnQge1xuICBhYnl0ZXMsXG4gIGFudW1iZXIsXG4gIGJ5dGVzVG9OdW1iZXJCRSxcbiAgYnl0ZXNUb051bWJlckxFLFxuICBudW1iZXJUb0J5dGVzQkUsXG4gIG51bWJlclRvQnl0ZXNMRSxcbiAgdmFsaWRhdGVPYmplY3QsXG59IGZyb20gJy4uL3V0aWxzLnRzJztcblxuLy8gTnVtYmVycyBhcmVuJ3QgdXNlZCBpbiB4MjU1MTkgLyB4NDQ4IGJ1aWxkc1xuLy8gcHJldHRpZXItaWdub3JlXG5jb25zdCBfMG4gPSAvKiBAX19QVVJFX18gKi8gQmlnSW50KDApLCBfMW4gPSAvKiBAX19QVVJFX18gKi8gQmlnSW50KDEpLCBfMm4gPSAvKiBAX19QVVJFX18gKi8gQmlnSW50KDIpO1xuLy8gcHJldHRpZXItaWdub3JlXG5jb25zdCBfM24gPSAvKiBAX19QVVJFX18gKi8gQmlnSW50KDMpLCBfNG4gPSAvKiBAX19QVVJFX18gKi8gQmlnSW50KDQpLCBfNW4gPSAvKiBAX19QVVJFX18gKi8gQmlnSW50KDUpO1xuLy8gcHJldHRpZXItaWdub3JlXG5jb25zdCBfN24gPSAvKiBAX19QVVJFX18gKi8gQmlnSW50KDcpLCBfOG4gPSAvKiBAX19QVVJFX18gKi8gQmlnSW50KDgpLCBfOW4gPSAvKiBAX19QVVJFX18gKi8gQmlnSW50KDkpO1xuY29uc3QgXzE2biA9IC8qIEBfX1BVUkVfXyAqLyBCaWdJbnQoMTYpO1xuXG4vLyBDYWxjdWxhdGVzIGEgbW9kdWxvIGJcbmV4cG9ydCBmdW5jdGlvbiBtb2QoYTogYmlnaW50LCBiOiBiaWdpbnQpOiBiaWdpbnQge1xuICBjb25zdCByZXN1bHQgPSBhICUgYjtcbiAgcmV0dXJuIHJlc3VsdCA+PSBfMG4gPyByZXN1bHQgOiBiICsgcmVzdWx0O1xufVxuLyoqXG4gKiBFZmZpY2llbnRseSByYWlzZSBudW0gdG8gcG93ZXIgYW5kIGRvIG1vZHVsYXIgZGl2aXNpb24uXG4gKiBVbnNhZmUgaW4gc29tZSBjb250ZXh0czogdXNlcyBsYWRkZXIsIHNvIGNhbiBleHBvc2UgYmlnaW50IGJpdHMuXG4gKiBAZXhhbXBsZVxuICogcG93KDJuLCA2biwgMTFuKSAvLyA2NG4gJSAxMW4gPT0gOW5cbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIHBvdyhudW06IGJpZ2ludCwgcG93ZXI6IGJpZ2ludCwgbW9kdWxvOiBiaWdpbnQpOiBiaWdpbnQge1xuICByZXR1cm4gRnBQb3coRmllbGQobW9kdWxvKSwgbnVtLCBwb3dlcik7XG59XG5cbi8qKiBEb2VzIGB4XigyXnBvd2VyKWAgbW9kIHAuIGBwb3cyKDMwLCA0KWAgPT0gYDMwXigyXjQpYCAqL1xuZXhwb3J0IGZ1bmN0aW9uIHBvdzIoeDogYmlnaW50LCBwb3dlcjogYmlnaW50LCBtb2R1bG86IGJpZ2ludCk6IGJpZ2ludCB7XG4gIGxldCByZXMgPSB4O1xuICB3aGlsZSAocG93ZXItLSA+IF8wbikge1xuICAgIHJlcyAqPSByZXM7XG4gICAgcmVzICU9IG1vZHVsbztcbiAgfVxuICByZXR1cm4gcmVzO1xufVxuXG4vKipcbiAqIEludmVyc2VzIG51bWJlciBvdmVyIG1vZHVsby5cbiAqIEltcGxlbWVudGVkIHVzaW5nIFtFdWNsaWRlYW4gR0NEXShodHRwczovL2JyaWxsaWFudC5vcmcvd2lraS9leHRlbmRlZC1ldWNsaWRlYW4tYWxnb3JpdGhtLykuXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBpbnZlcnQobnVtYmVyOiBiaWdpbnQsIG1vZHVsbzogYmlnaW50KTogYmlnaW50IHtcbiAgaWYgKG51bWJlciA9PT0gXzBuKSB0aHJvdyBuZXcgRXJyb3IoJ2ludmVydDogZXhwZWN0ZWQgbm9uLXplcm8gbnVtYmVyJyk7XG4gIGlmIChtb2R1bG8gPD0gXzBuKSB0aHJvdyBuZXcgRXJyb3IoJ2ludmVydDogZXhwZWN0ZWQgcG9zaXRpdmUgbW9kdWx1cywgZ290ICcgKyBtb2R1bG8pO1xuICAvLyBGZXJtYXQncyBsaXR0bGUgdGhlb3JlbSBcIkNULWxpa2VcIiB2ZXJzaW9uIGludihuKSA9IG5eKG0tMikgbW9kIG0gaXMgMzB4IHNsb3dlci5cbiAgbGV0IGEgPSBtb2QobnVtYmVyLCBtb2R1bG8pO1xuICBsZXQgYiA9IG1vZHVsbztcbiAgLy8gcHJldHRpZXItaWdub3JlXG4gIGxldCB4ID0gXzBuLCB5ID0gXzFuLCB1ID0gXzFuLCB2ID0gXzBuO1xuICB3aGlsZSAoYSAhPT0gXzBuKSB7XG4gICAgLy8gSklUIGFwcGxpZXMgb3B0aW1pemF0aW9uIGlmIHRob3NlIHR3byBsaW5lcyBmb2xsb3cgZWFjaCBvdGhlclxuICAgIGNvbnN0IHEgPSBiIC8gYTtcbiAgICBjb25zdCByID0gYiAlIGE7XG4gICAgY29uc3QgbSA9IHggLSB1ICogcTtcbiAgICBjb25zdCBuID0geSAtIHYgKiBxO1xuICAgIC8vIHByZXR0aWVyLWlnbm9yZVxuICAgIGIgPSBhLCBhID0gciwgeCA9IHUsIHkgPSB2LCB1ID0gbSwgdiA9IG47XG4gIH1cbiAgY29uc3QgZ2NkID0gYjtcbiAgaWYgKGdjZCAhPT0gXzFuKSB0aHJvdyBuZXcgRXJyb3IoJ2ludmVydDogZG9lcyBub3QgZXhpc3QnKTtcbiAgcmV0dXJuIG1vZCh4LCBtb2R1bG8pO1xufVxuXG5mdW5jdGlvbiBhc3NlcnRJc1NxdWFyZTxUPihGcDogSUZpZWxkPFQ+LCByb290OiBULCBuOiBUKTogdm9pZCB7XG4gIGlmICghRnAuZXFsKEZwLnNxcihyb290KSwgbikpIHRocm93IG5ldyBFcnJvcignQ2Fubm90IGZpbmQgc3F1YXJlIHJvb3QnKTtcbn1cblxuLy8gTm90IGFsbCByb290cyBhcmUgcG9zc2libGUhIEV4YW1wbGUgd2hpY2ggd2lsbCB0aHJvdzpcbi8vIGNvbnN0IE5VTSA9XG4vLyBuID0gNzIwNTc1OTQwMzc5Mjc4MTZuO1xuLy8gRnAgPSBGaWVsZChCaWdJbnQoJzB4MWEwMTExZWEzOTdmZTY5YTRiMWJhN2I2NDM0YmFjZDc2NDc3NGI4NGYzODUxMmJmNjczMGQyYTBmNmIwZjYyNDFlYWJmZmZlYjE1M2ZmZmZiOWZlZmZmZmZmZmZhYWFiJykpO1xuZnVuY3Rpb24gc3FydDNtb2Q0PFQ+KEZwOiBJRmllbGQ8VD4sIG46IFQpIHtcbiAgY29uc3QgcDFkaXY0ID0gKEZwLk9SREVSICsgXzFuKSAvIF80bjtcbiAgY29uc3Qgcm9vdCA9IEZwLnBvdyhuLCBwMWRpdjQpO1xuICBhc3NlcnRJc1NxdWFyZShGcCwgcm9vdCwgbik7XG4gIHJldHVybiByb290O1xufVxuXG5mdW5jdGlvbiBzcXJ0NW1vZDg8VD4oRnA6IElGaWVsZDxUPiwgbjogVCkge1xuICBjb25zdCBwNWRpdjggPSAoRnAuT1JERVIgLSBfNW4pIC8gXzhuO1xuICBjb25zdCBuMiA9IEZwLm11bChuLCBfMm4pO1xuICBjb25zdCB2ID0gRnAucG93KG4yLCBwNWRpdjgpO1xuICBjb25zdCBudiA9IEZwLm11bChuLCB2KTtcbiAgY29uc3QgaSA9IEZwLm11bChGcC5tdWwobnYsIF8ybiksIHYpO1xuICBjb25zdCByb290ID0gRnAubXVsKG52LCBGcC5zdWIoaSwgRnAuT05FKSk7XG4gIGFzc2VydElzU3F1YXJlKEZwLCByb290LCBuKTtcbiAgcmV0dXJuIHJvb3Q7XG59XG5cbi8vIEJhc2VkIG9uIFJGQzkzODAsIEtvbmcgYWxnb3JpdGhtXG4vLyBwcmV0dGllci1pZ25vcmVcbmZ1bmN0aW9uIHNxcnQ5bW9kMTYoUDogYmlnaW50KTogPFQ+KEZwOiBJRmllbGQ8VD4sIG46IFQpID0+IFQge1xuICBjb25zdCBGcF8gPSBGaWVsZChQKTtcbiAgY29uc3QgdG4gPSB0b25lbGxpU2hhbmtzKFApO1xuICBjb25zdCBjMSA9IHRuKEZwXywgRnBfLm5lZyhGcF8uT05FKSk7Ly8gIDEuIGMxID0gc3FydCgtMSkgaW4gRiwgaS5lLiwgKGMxXjIpID09IC0xIGluIEZcbiAgY29uc3QgYzIgPSB0bihGcF8sIGMxKTsgICAgICAgICAgICAgIC8vICAyLiBjMiA9IHNxcnQoYzEpIGluIEYsIGkuZS4sIChjMl4yKSA9PSBjMSBpbiBGXG4gIGNvbnN0IGMzID0gdG4oRnBfLCBGcF8ubmVnKGMxKSk7ICAgICAvLyAgMy4gYzMgPSBzcXJ0KC1jMSkgaW4gRiwgaS5lLiwgKGMzXjIpID09IC1jMSBpbiBGXG4gIGNvbnN0IGM0ID0gKFAgKyBfN24pIC8gXzE2bjsgICAgICAgICAvLyAgNC4gYzQgPSAocSArIDcpIC8gMTYgICAgICAgICMgSW50ZWdlciBhcml0aG1ldGljXG4gIHJldHVybiA8VD4oRnA6IElGaWVsZDxUPiwgbjogVCkgPT4ge1xuICAgIGxldCB0djEgPSBGcC5wb3cobiwgYzQpOyAgICAgICAgICAgLy8gIDEuIHR2MSA9IHheYzRcbiAgICBsZXQgdHYyID0gRnAubXVsKHR2MSwgYzEpOyAgICAgICAgIC8vICAyLiB0djIgPSBjMSAqIHR2MVxuICAgIGNvbnN0IHR2MyA9IEZwLm11bCh0djEsIGMyKTsgICAgICAgLy8gIDMuIHR2MyA9IGMyICogdHYxXG4gICAgY29uc3QgdHY0ID0gRnAubXVsKHR2MSwgYzMpOyAgICAgICAvLyAgNC4gdHY0ID0gYzMgKiB0djFcbiAgICBjb25zdCBlMSA9IEZwLmVxbChGcC5zcXIodHYyKSwgbik7IC8vICA1LiAgZTEgPSAodHYyXjIpID09IHhcbiAgICBjb25zdCBlMiA9IEZwLmVxbChGcC5zcXIodHYzKSwgbik7IC8vICA2LiAgZTIgPSAodHYzXjIpID09IHhcbiAgICB0djEgPSBGcC5jbW92KHR2MSwgdHYyLCBlMSk7ICAgICAgIC8vICA3LiB0djEgPSBDTU9WKHR2MSwgdHYyLCBlMSkgICMgU2VsZWN0IHR2MiBpZiAodHYyXjIpID09IHhcbiAgICB0djIgPSBGcC5jbW92KHR2NCwgdHYzLCBlMik7ICAgICAgIC8vICA4LiB0djIgPSBDTU9WKHR2NCwgdHYzLCBlMikgICMgU2VsZWN0IHR2MyBpZiAodHYzXjIpID09IHhcbiAgICBjb25zdCBlMyA9IEZwLmVxbChGcC5zcXIodHYyKSwgbik7IC8vICA5LiAgZTMgPSAodHYyXjIpID09IHhcbiAgICBjb25zdCByb290ID0gRnAuY21vdih0djEsIHR2MiwgZTMpOy8vIDEwLiAgeiA9IENNT1YodHYxLCB0djIsIGUzKSAgICMgU2VsZWN0IHNxcnQgZnJvbSB0djEgJiB0djJcbiAgICBhc3NlcnRJc1NxdWFyZShGcCwgcm9vdCwgbik7XG4gICAgcmV0dXJuIHJvb3Q7XG4gIH07XG59XG5cbi8qKlxuICogVG9uZWxsaS1TaGFua3Mgc3F1YXJlIHJvb3Qgc2VhcmNoIGFsZ29yaXRobS5cbiAqIDEuIGh0dHBzOi8vZXByaW50LmlhY3Iub3JnLzIwMTIvNjg1LnBkZiAocGFnZSAxMilcbiAqIDIuIFNxdWFyZSBSb290cyBmcm9tIDE7IDI0LCA1MSwgMTAgdG8gRGFuIFNoYW5rc1xuICogQHBhcmFtIFAgZmllbGQgb3JkZXJcbiAqIEByZXR1cm5zIGZ1bmN0aW9uIHRoYXQgdGFrZXMgZmllbGQgRnAgKGNyZWF0ZWQgZnJvbSBQKSBhbmQgbnVtYmVyIG5cbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIHRvbmVsbGlTaGFua3MoUDogYmlnaW50KTogPFQ+KEZwOiBJRmllbGQ8VD4sIG46IFQpID0+IFQge1xuICAvLyBJbml0aWFsaXphdGlvbiAocHJlY29tcHV0YXRpb24pLlxuICAvLyBDYWNoaW5nIGluaXRpYWxpemF0aW9uIGNvdWxkIGJvb3N0IHBlcmYgYnkgNyUuXG4gIGlmIChQIDwgXzNuKSB0aHJvdyBuZXcgRXJyb3IoJ3NxcnQgaXMgbm90IGRlZmluZWQgZm9yIHNtYWxsIGZpZWxkJyk7XG4gIC8vIEZhY3RvciBQIC0gMSA9IFEgKiAyXlMsIHdoZXJlIFEgaXMgb2RkXG4gIGxldCBRID0gUCAtIF8xbjtcbiAgbGV0IFMgPSAwO1xuICB3aGlsZSAoUSAlIF8ybiA9PT0gXzBuKSB7XG4gICAgUSAvPSBfMm47XG4gICAgUysrO1xuICB9XG5cbiAgLy8gRmluZCB0aGUgZmlyc3QgcXVhZHJhdGljIG5vbi1yZXNpZHVlIFogPj0gMlxuICBsZXQgWiA9IF8ybjtcbiAgY29uc3QgX0ZwID0gRmllbGQoUCk7XG4gIHdoaWxlIChGcExlZ2VuZHJlKF9GcCwgWikgPT09IDEpIHtcbiAgICAvLyBCYXNpYyBwcmltYWxpdHkgdGVzdCBmb3IgUC4gQWZ0ZXIgeCBpdGVyYXRpb25zLCBjaGFuY2Ugb2ZcbiAgICAvLyBub3QgZmluZGluZyBxdWFkcmF0aWMgbm9uLXJlc2lkdWUgaXMgMl54LCBzbyAyXjEwMDAuXG4gICAgaWYgKForKyA+IDEwMDApIHRocm93IG5ldyBFcnJvcignQ2Fubm90IGZpbmQgc3F1YXJlIHJvb3Q6IHByb2JhYmx5IG5vbi1wcmltZSBQJyk7XG4gIH1cbiAgLy8gRmFzdC1wYXRoOyB1c3VhbGx5IGRvbmUgYmVmb3JlIFosIGJ1dCB3ZSBkbyBcInByaW1hbGl0eSB0ZXN0XCIuXG4gIGlmIChTID09PSAxKSByZXR1cm4gc3FydDNtb2Q0O1xuXG4gIC8vIFNsb3ctcGF0aFxuICAvLyBUT0RPOiB0ZXN0IG9uIEZwMiBhbmQgb3RoZXJzXG4gIGxldCBjYyA9IF9GcC5wb3coWiwgUSk7IC8vIGMgPSB6XlFcbiAgY29uc3QgUTFkaXYyID0gKFEgKyBfMW4pIC8gXzJuO1xuICByZXR1cm4gZnVuY3Rpb24gdG9uZWxsaVNsb3c8VD4oRnA6IElGaWVsZDxUPiwgbjogVCk6IFQge1xuICAgIGlmIChGcC5pczAobikpIHJldHVybiBuO1xuICAgIC8vIENoZWNrIGlmIG4gaXMgYSBxdWFkcmF0aWMgcmVzaWR1ZSB1c2luZyBMZWdlbmRyZSBzeW1ib2xcbiAgICBpZiAoRnBMZWdlbmRyZShGcCwgbikgIT09IDEpIHRocm93IG5ldyBFcnJvcignQ2Fubm90IGZpbmQgc3F1YXJlIHJvb3QnKTtcblxuICAgIC8vIEluaXRpYWxpemUgdmFyaWFibGVzIGZvciB0aGUgbWFpbiBsb29wXG4gICAgbGV0IE0gPSBTO1xuICAgIGxldCBjID0gRnAubXVsKEZwLk9ORSwgY2MpOyAvLyBjID0gel5RLCBtb3ZlIGNjIGZyb20gZmllbGQgX0ZwIGludG8gZmllbGQgRnBcbiAgICBsZXQgdCA9IEZwLnBvdyhuLCBRKTsgLy8gdCA9IG5eUSwgZmlyc3QgZ3Vlc3MgYXQgdGhlIGZ1ZGdlIGZhY3RvclxuICAgIGxldCBSID0gRnAucG93KG4sIFExZGl2Mik7IC8vIFIgPSBuXigoUSsxKS8yKSwgZmlyc3QgZ3Vlc3MgYXQgdGhlIHNxdWFyZSByb290XG5cbiAgICAvLyBNYWluIGxvb3BcbiAgICAvLyB3aGlsZSB0ICE9IDFcbiAgICB3aGlsZSAoIUZwLmVxbCh0LCBGcC5PTkUpKSB7XG4gICAgICBpZiAoRnAuaXMwKHQpKSByZXR1cm4gRnAuWkVSTzsgLy8gaWYgdD0wIHJldHVybiBSPTBcbiAgICAgIGxldCBpID0gMTtcblxuICAgICAgLy8gRmluZCB0aGUgc21hbGxlc3QgaSA+PSAxIHN1Y2ggdGhhdCB0XigyXmkpIFx1MjI2MSAxIChtb2QgUClcbiAgICAgIGxldCB0X3RtcCA9IEZwLnNxcih0KTsgLy8gdF4oMl4xKVxuICAgICAgd2hpbGUgKCFGcC5lcWwodF90bXAsIEZwLk9ORSkpIHtcbiAgICAgICAgaSsrO1xuICAgICAgICB0X3RtcCA9IEZwLnNxcih0X3RtcCk7IC8vIHReKDJeMikuLi5cbiAgICAgICAgaWYgKGkgPT09IE0pIHRocm93IG5ldyBFcnJvcignQ2Fubm90IGZpbmQgc3F1YXJlIHJvb3QnKTtcbiAgICAgIH1cblxuICAgICAgLy8gQ2FsY3VsYXRlIHRoZSBleHBvbmVudCBmb3IgYjogMl4oTSAtIGkgLSAxKVxuICAgICAgY29uc3QgZXhwb25lbnQgPSBfMW4gPDwgQmlnSW50KE0gLSBpIC0gMSk7IC8vIGJpZ2ludCBpcyBpbXBvcnRhbnRcbiAgICAgIGNvbnN0IGIgPSBGcC5wb3coYywgZXhwb25lbnQpOyAvLyBiID0gMl4oTSAtIGkgLSAxKVxuXG4gICAgICAvLyBVcGRhdGUgdmFyaWFibGVzXG4gICAgICBNID0gaTtcbiAgICAgIGMgPSBGcC5zcXIoYik7IC8vIGMgPSBiXjJcbiAgICAgIHQgPSBGcC5tdWwodCwgYyk7IC8vIHQgPSAodCAqIGJeMilcbiAgICAgIFIgPSBGcC5tdWwoUiwgYik7IC8vIFIgPSBSKmJcbiAgICB9XG4gICAgcmV0dXJuIFI7XG4gIH07XG59XG5cbi8qKlxuICogU3F1YXJlIHJvb3QgZm9yIGEgZmluaXRlIGZpZWxkLiBXaWxsIHRyeSBvcHRpbWl6ZWQgdmVyc2lvbnMgZmlyc3Q6XG4gKlxuICogMS4gUCBcdTIyNjEgMyAobW9kIDQpXG4gKiAyLiBQIFx1MjI2MSA1IChtb2QgOClcbiAqIDMuIFAgXHUyMjYxIDkgKG1vZCAxNilcbiAqIDQuIFRvbmVsbGktU2hhbmtzIGFsZ29yaXRobVxuICpcbiAqIERpZmZlcmVudCBhbGdvcml0aG1zIGNhbiBnaXZlIGRpZmZlcmVudCByb290cywgaXQgaXMgdXAgdG8gdXNlciB0byBkZWNpZGUgd2hpY2ggb25lIHRoZXkgd2FudC5cbiAqIEZvciBleGFtcGxlIHRoZXJlIGlzIEZwU3FydE9kZC9GcFNxcnRFdmVuIHRvIGNob2ljZSByb290IGJhc2VkIG9uIG9kZG5lc3MgKHVzZWQgZm9yIGhhc2gtdG8tY3VydmUpLlxuICovXG5leHBvcnQgZnVuY3Rpb24gRnBTcXJ0KFA6IGJpZ2ludCk6IDxUPihGcDogSUZpZWxkPFQ+LCBuOiBUKSA9PiBUIHtcbiAgLy8gUCBcdTIyNjEgMyAobW9kIDQpID0+IFx1MjIxQW4gPSBuXigoUCsxKS80KVxuICBpZiAoUCAlIF80biA9PT0gXzNuKSByZXR1cm4gc3FydDNtb2Q0O1xuICAvLyBQIFx1MjI2MSA1IChtb2QgOCkgPT4gQXRraW4gYWxnb3JpdGhtLCBwYWdlIDEwIG9mIGh0dHBzOi8vZXByaW50LmlhY3Iub3JnLzIwMTIvNjg1LnBkZlxuICBpZiAoUCAlIF84biA9PT0gXzVuKSByZXR1cm4gc3FydDVtb2Q4O1xuICAvLyBQIFx1MjI2MSA5IChtb2QgMTYpID0+IEtvbmcgYWxnb3JpdGhtLCBwYWdlIDExIG9mIGh0dHBzOi8vZXByaW50LmlhY3Iub3JnLzIwMTIvNjg1LnBkZiAoYWxnb3JpdGhtIDQpXG4gIGlmIChQICUgXzE2biA9PT0gXzluKSByZXR1cm4gc3FydDltb2QxNihQKTtcbiAgLy8gVG9uZWxsaS1TaGFua3MgYWxnb3JpdGhtXG4gIHJldHVybiB0b25lbGxpU2hhbmtzKFApO1xufVxuXG4vLyBMaXR0bGUtZW5kaWFuIGNoZWNrIGZvciBmaXJzdCBMRSBiaXQgKGxhc3QgQkUgYml0KTtcbmV4cG9ydCBjb25zdCBpc05lZ2F0aXZlTEUgPSAobnVtOiBiaWdpbnQsIG1vZHVsbzogYmlnaW50KTogYm9vbGVhbiA9PlxuICAobW9kKG51bSwgbW9kdWxvKSAmIF8xbikgPT09IF8xbjtcblxuLyoqIEZpZWxkIGlzIG5vdCBhbHdheXMgb3ZlciBwcmltZTogZm9yIGV4YW1wbGUsIEZwMiBoYXMgT1JERVIocSk9cF5tLiAqL1xuZXhwb3J0IGludGVyZmFjZSBJRmllbGQ8VD4ge1xuICBPUkRFUjogYmlnaW50O1xuICBCWVRFUzogbnVtYmVyO1xuICBCSVRTOiBudW1iZXI7XG4gIGlzTEU6IGJvb2xlYW47XG4gIFpFUk86IFQ7XG4gIE9ORTogVDtcbiAgLy8gMS1hcmdcbiAgY3JlYXRlOiAobnVtOiBUKSA9PiBUO1xuICBpc1ZhbGlkOiAobnVtOiBUKSA9PiBib29sZWFuO1xuICBpczA6IChudW06IFQpID0+IGJvb2xlYW47XG4gIGlzVmFsaWROb3QwOiAobnVtOiBUKSA9PiBib29sZWFuO1xuICBuZWcobnVtOiBUKTogVDtcbiAgaW52KG51bTogVCk6IFQ7XG4gIHNxcnQobnVtOiBUKTogVDtcbiAgc3FyKG51bTogVCk6IFQ7XG4gIC8vIDItYXJnc1xuICBlcWwobGhzOiBULCByaHM6IFQpOiBib29sZWFuO1xuICBhZGQobGhzOiBULCByaHM6IFQpOiBUO1xuICBzdWIobGhzOiBULCByaHM6IFQpOiBUO1xuICBtdWwobGhzOiBULCByaHM6IFQgfCBiaWdpbnQpOiBUO1xuICBwb3cobGhzOiBULCBwb3dlcjogYmlnaW50KTogVDtcbiAgZGl2KGxoczogVCwgcmhzOiBUIHwgYmlnaW50KTogVDtcbiAgLy8gTiBmb3IgTm9uTm9ybWFsaXplZCAoZm9yIG5vdylcbiAgYWRkTihsaHM6IFQsIHJoczogVCk6IFQ7XG4gIHN1Yk4obGhzOiBULCByaHM6IFQpOiBUO1xuICBtdWxOKGxoczogVCwgcmhzOiBUIHwgYmlnaW50KTogVDtcbiAgc3FyTihudW06IFQpOiBUO1xuXG4gIC8vIE9wdGlvbmFsXG4gIC8vIFNob3VsZCBiZSBzYW1lIGFzIHNnbjAgZnVuY3Rpb24gaW5cbiAgLy8gW1JGQzkzODBdKGh0dHBzOi8vd3d3LnJmYy1lZGl0b3Iub3JnL3JmYy9yZmM5MzgwI3NlY3Rpb24tNC4xKS5cbiAgLy8gTk9URTogc2duMCBpcyAnbmVnYXRpdmUgaW4gTEUnLCB3aGljaCBpcyBzYW1lIGFzIG9kZC4gQW5kIG5lZ2F0aXZlIGluIExFIGlzIGtpbmRhIHN0cmFuZ2UgZGVmaW5pdGlvbiBhbnl3YXkuXG4gIGlzT2RkPyhudW06IFQpOiBib29sZWFuOyAvLyBPZGQgaW5zdGVhZCBvZiBldmVuIHNpbmNlIHdlIGhhdmUgaXQgZm9yIEZwMlxuICAvLyBsZWdlbmRyZT8obnVtOiBUKTogVDtcbiAgaW52ZXJ0QmF0Y2g6IChsc3Q6IFRbXSkgPT4gVFtdO1xuICB0b0J5dGVzKG51bTogVCk6IFVpbnQ4QXJyYXk7XG4gIGZyb21CeXRlcyhieXRlczogVWludDhBcnJheSwgc2tpcFZhbGlkYXRpb24/OiBib29sZWFuKTogVDtcbiAgLy8gSWYgYyBpcyBGYWxzZSwgQ01PViByZXR1cm5zIGEsIG90aGVyd2lzZSBpdCByZXR1cm5zIGIuXG4gIGNtb3YoYTogVCwgYjogVCwgYzogYm9vbGVhbik6IFQ7XG59XG4vLyBwcmV0dGllci1pZ25vcmVcbmNvbnN0IEZJRUxEX0ZJRUxEUyA9IFtcbiAgJ2NyZWF0ZScsICdpc1ZhbGlkJywgJ2lzMCcsICduZWcnLCAnaW52JywgJ3NxcnQnLCAnc3FyJyxcbiAgJ2VxbCcsICdhZGQnLCAnc3ViJywgJ211bCcsICdwb3cnLCAnZGl2JyxcbiAgJ2FkZE4nLCAnc3ViTicsICdtdWxOJywgJ3Nxck4nXG5dIGFzIGNvbnN0O1xuZXhwb3J0IGZ1bmN0aW9uIHZhbGlkYXRlRmllbGQ8VD4oZmllbGQ6IElGaWVsZDxUPik6IElGaWVsZDxUPiB7XG4gIGNvbnN0IGluaXRpYWwgPSB7XG4gICAgT1JERVI6ICdiaWdpbnQnLFxuICAgIEJZVEVTOiAnbnVtYmVyJyxcbiAgICBCSVRTOiAnbnVtYmVyJyxcbiAgfSBhcyBSZWNvcmQ8c3RyaW5nLCBzdHJpbmc+O1xuICBjb25zdCBvcHRzID0gRklFTERfRklFTERTLnJlZHVjZSgobWFwLCB2YWw6IHN0cmluZykgPT4ge1xuICAgIG1hcFt2YWxdID0gJ2Z1bmN0aW9uJztcbiAgICByZXR1cm4gbWFwO1xuICB9LCBpbml0aWFsKTtcbiAgdmFsaWRhdGVPYmplY3QoZmllbGQsIG9wdHMpO1xuICAvLyBjb25zdCBtYXggPSAxNjM4NDtcbiAgLy8gaWYgKGZpZWxkLkJZVEVTIDwgMSB8fCBmaWVsZC5CWVRFUyA+IG1heCkgdGhyb3cgbmV3IEVycm9yKCdpbnZhbGlkIGZpZWxkJyk7XG4gIC8vIGlmIChmaWVsZC5CSVRTIDwgMSB8fCBmaWVsZC5CSVRTID4gOCAqIG1heCkgdGhyb3cgbmV3IEVycm9yKCdpbnZhbGlkIGZpZWxkJyk7XG4gIHJldHVybiBmaWVsZDtcbn1cblxuLy8gR2VuZXJpYyBmaWVsZCBmdW5jdGlvbnNcblxuLyoqXG4gKiBTYW1lIGFzIGBwb3dgIGJ1dCBmb3IgRnA6IG5vbi1jb25zdGFudC10aW1lLlxuICogVW5zYWZlIGluIHNvbWUgY29udGV4dHM6IHVzZXMgbGFkZGVyLCBzbyBjYW4gZXhwb3NlIGJpZ2ludCBiaXRzLlxuICovXG5leHBvcnQgZnVuY3Rpb24gRnBQb3c8VD4oRnA6IElGaWVsZDxUPiwgbnVtOiBULCBwb3dlcjogYmlnaW50KTogVCB7XG4gIGlmIChwb3dlciA8IF8wbikgdGhyb3cgbmV3IEVycm9yKCdpbnZhbGlkIGV4cG9uZW50LCBuZWdhdGl2ZXMgdW5zdXBwb3J0ZWQnKTtcbiAgaWYgKHBvd2VyID09PSBfMG4pIHJldHVybiBGcC5PTkU7XG4gIGlmIChwb3dlciA9PT0gXzFuKSByZXR1cm4gbnVtO1xuICBsZXQgcCA9IEZwLk9ORTtcbiAgbGV0IGQgPSBudW07XG4gIHdoaWxlIChwb3dlciA+IF8wbikge1xuICAgIGlmIChwb3dlciAmIF8xbikgcCA9IEZwLm11bChwLCBkKTtcbiAgICBkID0gRnAuc3FyKGQpO1xuICAgIHBvd2VyID4+PSBfMW47XG4gIH1cbiAgcmV0dXJuIHA7XG59XG5cbi8qKlxuICogRWZmaWNpZW50bHkgaW52ZXJ0IGFuIGFycmF5IG9mIEZpZWxkIGVsZW1lbnRzLlxuICogRXhjZXB0aW9uLWZyZWUuIFdpbGwgcmV0dXJuIGB1bmRlZmluZWRgIGZvciAwIGVsZW1lbnRzLlxuICogQHBhcmFtIHBhc3NaZXJvIG1hcCAwIHRvIDAgKGluc3RlYWQgb2YgdW5kZWZpbmVkKVxuICovXG5leHBvcnQgZnVuY3Rpb24gRnBJbnZlcnRCYXRjaDxUPihGcDogSUZpZWxkPFQ+LCBudW1zOiBUW10sIHBhc3NaZXJvID0gZmFsc2UpOiBUW10ge1xuICBjb25zdCBpbnZlcnRlZCA9IG5ldyBBcnJheShudW1zLmxlbmd0aCkuZmlsbChwYXNzWmVybyA/IEZwLlpFUk8gOiB1bmRlZmluZWQpO1xuICAvLyBXYWxrIGZyb20gZmlyc3QgdG8gbGFzdCwgbXVsdGlwbHkgdGhlbSBieSBlYWNoIG90aGVyIE1PRCBwXG4gIGNvbnN0IG11bHRpcGxpZWRBY2MgPSBudW1zLnJlZHVjZSgoYWNjLCBudW0sIGkpID0+IHtcbiAgICBpZiAoRnAuaXMwKG51bSkpIHJldHVybiBhY2M7XG4gICAgaW52ZXJ0ZWRbaV0gPSBhY2M7XG4gICAgcmV0dXJuIEZwLm11bChhY2MsIG51bSk7XG4gIH0sIEZwLk9ORSk7XG4gIC8vIEludmVydCBsYXN0IGVsZW1lbnRcbiAgY29uc3QgaW52ZXJ0ZWRBY2MgPSBGcC5pbnYobXVsdGlwbGllZEFjYyk7XG4gIC8vIFdhbGsgZnJvbSBsYXN0IHRvIGZpcnN0LCBtdWx0aXBseSB0aGVtIGJ5IGludmVydGVkIGVhY2ggb3RoZXIgTU9EIHBcbiAgbnVtcy5yZWR1Y2VSaWdodCgoYWNjLCBudW0sIGkpID0+IHtcbiAgICBpZiAoRnAuaXMwKG51bSkpIHJldHVybiBhY2M7XG4gICAgaW52ZXJ0ZWRbaV0gPSBGcC5tdWwoYWNjLCBpbnZlcnRlZFtpXSk7XG4gICAgcmV0dXJuIEZwLm11bChhY2MsIG51bSk7XG4gIH0sIGludmVydGVkQWNjKTtcbiAgcmV0dXJuIGludmVydGVkO1xufVxuXG4vLyBUT0RPOiByZW1vdmVcbmV4cG9ydCBmdW5jdGlvbiBGcERpdjxUPihGcDogSUZpZWxkPFQ+LCBsaHM6IFQsIHJoczogVCB8IGJpZ2ludCk6IFQge1xuICByZXR1cm4gRnAubXVsKGxocywgdHlwZW9mIHJocyA9PT0gJ2JpZ2ludCcgPyBpbnZlcnQocmhzLCBGcC5PUkRFUikgOiBGcC5pbnYocmhzKSk7XG59XG5cbi8qKlxuICogTGVnZW5kcmUgc3ltYm9sLlxuICogTGVnZW5kcmUgY29uc3RhbnQgaXMgdXNlZCB0byBjYWxjdWxhdGUgTGVnZW5kcmUgc3ltYm9sIChhIHwgcClcbiAqIHdoaWNoIGRlbm90ZXMgdGhlIHZhbHVlIG9mIGFeKChwLTEpLzIpIChtb2QgcCkuXG4gKlxuICogKiAoYSB8IHApIFx1MjI2MSAxICAgIGlmIGEgaXMgYSBzcXVhcmUgKG1vZCBwKSwgcXVhZHJhdGljIHJlc2lkdWVcbiAqICogKGEgfCBwKSBcdTIyNjEgLTEgICBpZiBhIGlzIG5vdCBhIHNxdWFyZSAobW9kIHApLCBxdWFkcmF0aWMgbm9uIHJlc2lkdWVcbiAqICogKGEgfCBwKSBcdTIyNjEgMCAgICBpZiBhIFx1MjI2MSAwIChtb2QgcClcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIEZwTGVnZW5kcmU8VD4oRnA6IElGaWVsZDxUPiwgbjogVCk6IC0xIHwgMCB8IDEge1xuICAvLyBXZSBjYW4gdXNlIDNyZCBhcmd1bWVudCBhcyBvcHRpb25hbCBjYWNoZSBvZiB0aGlzIHZhbHVlXG4gIC8vIGJ1dCBzZWVtcyB1bm5lZWRlZCBmb3Igbm93LiBUaGUgb3BlcmF0aW9uIGlzIHZlcnkgZmFzdC5cbiAgY29uc3QgcDFtb2QyID0gKEZwLk9SREVSIC0gXzFuKSAvIF8ybjtcbiAgY29uc3QgcG93ZXJlZCA9IEZwLnBvdyhuLCBwMW1vZDIpO1xuICBjb25zdCB5ZXMgPSBGcC5lcWwocG93ZXJlZCwgRnAuT05FKTtcbiAgY29uc3QgemVybyA9IEZwLmVxbChwb3dlcmVkLCBGcC5aRVJPKTtcbiAgY29uc3Qgbm8gPSBGcC5lcWwocG93ZXJlZCwgRnAubmVnKEZwLk9ORSkpO1xuICBpZiAoIXllcyAmJiAhemVybyAmJiAhbm8pIHRocm93IG5ldyBFcnJvcignaW52YWxpZCBMZWdlbmRyZSBzeW1ib2wgcmVzdWx0Jyk7XG4gIHJldHVybiB5ZXMgPyAxIDogemVybyA/IDAgOiAtMTtcbn1cblxuLy8gVGhpcyBmdW5jdGlvbiByZXR1cm5zIFRydWUgd2hlbmV2ZXIgdGhlIHZhbHVlIHggaXMgYSBzcXVhcmUgaW4gdGhlIGZpZWxkIEYuXG5leHBvcnQgZnVuY3Rpb24gRnBJc1NxdWFyZTxUPihGcDogSUZpZWxkPFQ+LCBuOiBUKTogYm9vbGVhbiB7XG4gIGNvbnN0IGwgPSBGcExlZ2VuZHJlKEZwLCBuKTtcbiAgcmV0dXJuIGwgPT09IDE7XG59XG5cbmV4cG9ydCB0eXBlIE5MZW5ndGggPSB7IG5CeXRlTGVuZ3RoOiBudW1iZXI7IG5CaXRMZW5ndGg6IG51bWJlciB9O1xuLy8gQ1VSVkUubiBsZW5ndGhzXG5leHBvcnQgZnVuY3Rpb24gbkxlbmd0aChuOiBiaWdpbnQsIG5CaXRMZW5ndGg/OiBudW1iZXIpOiBOTGVuZ3RoIHtcbiAgLy8gQml0IHNpemUsIGJ5dGUgc2l6ZSBvZiBDVVJWRS5uXG4gIGlmIChuQml0TGVuZ3RoICE9PSB1bmRlZmluZWQpIGFudW1iZXIobkJpdExlbmd0aCk7XG4gIGNvbnN0IF9uQml0TGVuZ3RoID0gbkJpdExlbmd0aCAhPT0gdW5kZWZpbmVkID8gbkJpdExlbmd0aCA6IG4udG9TdHJpbmcoMikubGVuZ3RoO1xuICBjb25zdCBuQnl0ZUxlbmd0aCA9IE1hdGguY2VpbChfbkJpdExlbmd0aCAvIDgpO1xuICByZXR1cm4geyBuQml0TGVuZ3RoOiBfbkJpdExlbmd0aCwgbkJ5dGVMZW5ndGggfTtcbn1cblxudHlwZSBGcEZpZWxkID0gSUZpZWxkPGJpZ2ludD4gJiBSZXF1aXJlZDxQaWNrPElGaWVsZDxiaWdpbnQ+LCAnaXNPZGQnPj47XG50eXBlIFNxcnRGbiA9IChuOiBiaWdpbnQpID0+IGJpZ2ludDtcbnR5cGUgRmllbGRPcHRzID0gUGFydGlhbDx7XG4gIGlzTEU6IGJvb2xlYW47XG4gIEJJVFM6IG51bWJlcjtcbiAgc3FydDogU3FydEZuO1xuICBhbGxvd2VkTGVuZ3Rocz86IHJlYWRvbmx5IG51bWJlcltdOyAvLyBmb3IgUDUyMSAoYWRkcyBwYWRkaW5nIGZvciBzbWFsbGVyIHNpemVzKVxuICBtb2RGcm9tQnl0ZXM6IGJvb2xlYW47IC8vIGJsczEyLTM4MSByZXF1aXJlcyBtb2QobikgaW5zdGVhZCBvZiByZWplY3Rpbmcga2V5cyA+PSBuXG59PjtcbmNsYXNzIF9GaWVsZCBpbXBsZW1lbnRzIElGaWVsZDxiaWdpbnQ+IHtcbiAgcmVhZG9ubHkgT1JERVI6IGJpZ2ludDtcbiAgcmVhZG9ubHkgQklUUzogbnVtYmVyO1xuICByZWFkb25seSBCWVRFUzogbnVtYmVyO1xuICByZWFkb25seSBpc0xFOiBib29sZWFuO1xuICByZWFkb25seSBaRVJPID0gXzBuO1xuICByZWFkb25seSBPTkUgPSBfMW47XG4gIHJlYWRvbmx5IF9sZW5ndGhzPzogbnVtYmVyW107XG4gIHByaXZhdGUgX3NxcnQ6IFJldHVyblR5cGU8dHlwZW9mIEZwU3FydD4gfCB1bmRlZmluZWQ7IC8vIGNhY2hlZCBzcXJ0XG4gIHByaXZhdGUgcmVhZG9ubHkgX21vZD86IGJvb2xlYW47XG4gIGNvbnN0cnVjdG9yKE9SREVSOiBiaWdpbnQsIG9wdHM6IEZpZWxkT3B0cyA9IHt9KSB7XG4gICAgaWYgKE9SREVSIDw9IF8wbikgdGhyb3cgbmV3IEVycm9yKCdpbnZhbGlkIGZpZWxkOiBleHBlY3RlZCBPUkRFUiA+IDAsIGdvdCAnICsgT1JERVIpO1xuICAgIGxldCBfbmJpdExlbmd0aDogbnVtYmVyIHwgdW5kZWZpbmVkID0gdW5kZWZpbmVkO1xuICAgIHRoaXMuaXNMRSA9IGZhbHNlO1xuICAgIGlmIChvcHRzICE9IG51bGwgJiYgdHlwZW9mIG9wdHMgPT09ICdvYmplY3QnKSB7XG4gICAgICBpZiAodHlwZW9mIG9wdHMuQklUUyA9PT0gJ251bWJlcicpIF9uYml0TGVuZ3RoID0gb3B0cy5CSVRTO1xuICAgICAgaWYgKHR5cGVvZiBvcHRzLnNxcnQgPT09ICdmdW5jdGlvbicpIHRoaXMuc3FydCA9IG9wdHMuc3FydDtcbiAgICAgIGlmICh0eXBlb2Ygb3B0cy5pc0xFID09PSAnYm9vbGVhbicpIHRoaXMuaXNMRSA9IG9wdHMuaXNMRTtcbiAgICAgIGlmIChvcHRzLmFsbG93ZWRMZW5ndGhzKSB0aGlzLl9sZW5ndGhzID0gb3B0cy5hbGxvd2VkTGVuZ3Rocz8uc2xpY2UoKTtcbiAgICAgIGlmICh0eXBlb2Ygb3B0cy5tb2RGcm9tQnl0ZXMgPT09ICdib29sZWFuJykgdGhpcy5fbW9kID0gb3B0cy5tb2RGcm9tQnl0ZXM7XG4gICAgfVxuICAgIGNvbnN0IHsgbkJpdExlbmd0aCwgbkJ5dGVMZW5ndGggfSA9IG5MZW5ndGgoT1JERVIsIF9uYml0TGVuZ3RoKTtcbiAgICBpZiAobkJ5dGVMZW5ndGggPiAyMDQ4KSB0aHJvdyBuZXcgRXJyb3IoJ2ludmFsaWQgZmllbGQ6IGV4cGVjdGVkIE9SREVSIG9mIDw9IDIwNDggYnl0ZXMnKTtcbiAgICB0aGlzLk9SREVSID0gT1JERVI7XG4gICAgdGhpcy5CSVRTID0gbkJpdExlbmd0aDtcbiAgICB0aGlzLkJZVEVTID0gbkJ5dGVMZW5ndGg7XG4gICAgdGhpcy5fc3FydCA9IHVuZGVmaW5lZDtcbiAgICBPYmplY3QucHJldmVudEV4dGVuc2lvbnModGhpcyk7XG4gIH1cblxuICBjcmVhdGUobnVtOiBiaWdpbnQpIHtcbiAgICByZXR1cm4gbW9kKG51bSwgdGhpcy5PUkRFUik7XG4gIH1cbiAgaXNWYWxpZChudW06IGJpZ2ludCkge1xuICAgIGlmICh0eXBlb2YgbnVtICE9PSAnYmlnaW50JylcbiAgICAgIHRocm93IG5ldyBFcnJvcignaW52YWxpZCBmaWVsZCBlbGVtZW50OiBleHBlY3RlZCBiaWdpbnQsIGdvdCAnICsgdHlwZW9mIG51bSk7XG4gICAgcmV0dXJuIF8wbiA8PSBudW0gJiYgbnVtIDwgdGhpcy5PUkRFUjsgLy8gMCBpcyB2YWxpZCBlbGVtZW50LCBidXQgaXQncyBub3QgaW52ZXJ0aWJsZVxuICB9XG4gIGlzMChudW06IGJpZ2ludCkge1xuICAgIHJldHVybiBudW0gPT09IF8wbjtcbiAgfVxuICAvLyBpcyB2YWxpZCBhbmQgaW52ZXJ0aWJsZVxuICBpc1ZhbGlkTm90MChudW06IGJpZ2ludCkge1xuICAgIHJldHVybiAhdGhpcy5pczAobnVtKSAmJiB0aGlzLmlzVmFsaWQobnVtKTtcbiAgfVxuICBpc09kZChudW06IGJpZ2ludCkge1xuICAgIHJldHVybiAobnVtICYgXzFuKSA9PT0gXzFuO1xuICB9XG4gIG5lZyhudW06IGJpZ2ludCkge1xuICAgIHJldHVybiBtb2QoLW51bSwgdGhpcy5PUkRFUik7XG4gIH1cbiAgZXFsKGxoczogYmlnaW50LCByaHM6IGJpZ2ludCkge1xuICAgIHJldHVybiBsaHMgPT09IHJocztcbiAgfVxuXG4gIHNxcihudW06IGJpZ2ludCkge1xuICAgIHJldHVybiBtb2QobnVtICogbnVtLCB0aGlzLk9SREVSKTtcbiAgfVxuICBhZGQobGhzOiBiaWdpbnQsIHJoczogYmlnaW50KSB7XG4gICAgcmV0dXJuIG1vZChsaHMgKyByaHMsIHRoaXMuT1JERVIpO1xuICB9XG4gIHN1YihsaHM6IGJpZ2ludCwgcmhzOiBiaWdpbnQpIHtcbiAgICByZXR1cm4gbW9kKGxocyAtIHJocywgdGhpcy5PUkRFUik7XG4gIH1cbiAgbXVsKGxoczogYmlnaW50LCByaHM6IGJpZ2ludCkge1xuICAgIHJldHVybiBtb2QobGhzICogcmhzLCB0aGlzLk9SREVSKTtcbiAgfVxuICBwb3cobnVtOiBiaWdpbnQsIHBvd2VyOiBiaWdpbnQpOiBiaWdpbnQge1xuICAgIHJldHVybiBGcFBvdyh0aGlzLCBudW0sIHBvd2VyKTtcbiAgfVxuICBkaXYobGhzOiBiaWdpbnQsIHJoczogYmlnaW50KSB7XG4gICAgcmV0dXJuIG1vZChsaHMgKiBpbnZlcnQocmhzLCB0aGlzLk9SREVSKSwgdGhpcy5PUkRFUik7XG4gIH1cblxuICAvLyBTYW1lIGFzIGFib3ZlLCBidXQgZG9lc24ndCBub3JtYWxpemVcbiAgc3FyTihudW06IGJpZ2ludCkge1xuICAgIHJldHVybiBudW0gKiBudW07XG4gIH1cbiAgYWRkTihsaHM6IGJpZ2ludCwgcmhzOiBiaWdpbnQpIHtcbiAgICByZXR1cm4gbGhzICsgcmhzO1xuICB9XG4gIHN1Yk4obGhzOiBiaWdpbnQsIHJoczogYmlnaW50KSB7XG4gICAgcmV0dXJuIGxocyAtIHJocztcbiAgfVxuICBtdWxOKGxoczogYmlnaW50LCByaHM6IGJpZ2ludCkge1xuICAgIHJldHVybiBsaHMgKiByaHM7XG4gIH1cblxuICBpbnYobnVtOiBiaWdpbnQpIHtcbiAgICByZXR1cm4gaW52ZXJ0KG51bSwgdGhpcy5PUkRFUik7XG4gIH1cbiAgc3FydChudW06IGJpZ2ludCk6IGJpZ2ludCB7XG4gICAgLy8gQ2FjaGluZyBfc3FydCBzcGVlZHMgdXAgc3FydDltb2QxNiBieSA1eCBhbmQgdG9ubmVsaS1zaGFua3MgYnkgMTAlXG4gICAgaWYgKCF0aGlzLl9zcXJ0KSB0aGlzLl9zcXJ0ID0gRnBTcXJ0KHRoaXMuT1JERVIpO1xuICAgIHJldHVybiB0aGlzLl9zcXJ0KHRoaXMsIG51bSk7XG4gIH1cbiAgdG9CeXRlcyhudW06IGJpZ2ludCkge1xuICAgIHJldHVybiB0aGlzLmlzTEUgPyBudW1iZXJUb0J5dGVzTEUobnVtLCB0aGlzLkJZVEVTKSA6IG51bWJlclRvQnl0ZXNCRShudW0sIHRoaXMuQllURVMpO1xuICB9XG4gIGZyb21CeXRlcyhieXRlczogVWludDhBcnJheSwgc2tpcFZhbGlkYXRpb24gPSBmYWxzZSkge1xuICAgIGFieXRlcyhieXRlcyk7XG4gICAgY29uc3QgeyBfbGVuZ3RoczogYWxsb3dlZExlbmd0aHMsIEJZVEVTLCBpc0xFLCBPUkRFUiwgX21vZDogbW9kRnJvbUJ5dGVzIH0gPSB0aGlzO1xuICAgIGlmIChhbGxvd2VkTGVuZ3Rocykge1xuICAgICAgaWYgKCFhbGxvd2VkTGVuZ3Rocy5pbmNsdWRlcyhieXRlcy5sZW5ndGgpIHx8IGJ5dGVzLmxlbmd0aCA+IEJZVEVTKSB7XG4gICAgICAgIHRocm93IG5ldyBFcnJvcihcbiAgICAgICAgICAnRmllbGQuZnJvbUJ5dGVzOiBleHBlY3RlZCAnICsgYWxsb3dlZExlbmd0aHMgKyAnIGJ5dGVzLCBnb3QgJyArIGJ5dGVzLmxlbmd0aFxuICAgICAgICApO1xuICAgICAgfVxuICAgICAgY29uc3QgcGFkZGVkID0gbmV3IFVpbnQ4QXJyYXkoQllURVMpO1xuICAgICAgLy8gaXNMRSBhZGQgMCB0byByaWdodCwgIWlzTEUgdG8gdGhlIGxlZnQuXG4gICAgICBwYWRkZWQuc2V0KGJ5dGVzLCBpc0xFID8gMCA6IHBhZGRlZC5sZW5ndGggLSBieXRlcy5sZW5ndGgpO1xuICAgICAgYnl0ZXMgPSBwYWRkZWQ7XG4gICAgfVxuICAgIGlmIChieXRlcy5sZW5ndGggIT09IEJZVEVTKVxuICAgICAgdGhyb3cgbmV3IEVycm9yKCdGaWVsZC5mcm9tQnl0ZXM6IGV4cGVjdGVkICcgKyBCWVRFUyArICcgYnl0ZXMsIGdvdCAnICsgYnl0ZXMubGVuZ3RoKTtcbiAgICBsZXQgc2NhbGFyID0gaXNMRSA/IGJ5dGVzVG9OdW1iZXJMRShieXRlcykgOiBieXRlc1RvTnVtYmVyQkUoYnl0ZXMpO1xuICAgIGlmIChtb2RGcm9tQnl0ZXMpIHNjYWxhciA9IG1vZChzY2FsYXIsIE9SREVSKTtcbiAgICBpZiAoIXNraXBWYWxpZGF0aW9uKVxuICAgICAgaWYgKCF0aGlzLmlzVmFsaWQoc2NhbGFyKSlcbiAgICAgICAgdGhyb3cgbmV3IEVycm9yKCdpbnZhbGlkIGZpZWxkIGVsZW1lbnQ6IG91dHNpZGUgb2YgcmFuZ2UgMC4uT1JERVInKTtcbiAgICAvLyBOT1RFOiB3ZSBkb24ndCB2YWxpZGF0ZSBzY2FsYXIgaGVyZSwgcGxlYXNlIHVzZSBpc1ZhbGlkLiBUaGlzIGRvbmUgc3VjaCB3YXkgYmVjYXVzZSBzb21lXG4gICAgLy8gcHJvdG9jb2wgbWF5IGFsbG93IG5vbi1yZWR1Y2VkIHNjYWxhciB0aGF0IHJlZHVjZWQgbGF0ZXIgb3IgY2hhbmdlZCBzb21lIG90aGVyIHdheS5cbiAgICByZXR1cm4gc2NhbGFyO1xuICB9XG4gIC8vIFRPRE86IHdlIGRvbid0IG5lZWQgaXQgaGVyZSwgbW92ZSBvdXQgdG8gc2VwYXJhdGUgZm5cbiAgaW52ZXJ0QmF0Y2gobHN0OiBiaWdpbnRbXSk6IGJpZ2ludFtdIHtcbiAgICByZXR1cm4gRnBJbnZlcnRCYXRjaCh0aGlzLCBsc3QpO1xuICB9XG4gIC8vIFdlIGNhbid0IG1vdmUgdGhpcyBvdXQgYmVjYXVzZSBGcDYsIEZwMTIgaW1wbGVtZW50IGl0XG4gIC8vIGFuZCBpdCdzIHVuY2xlYXIgd2hhdCB0byByZXR1cm4gaW4gdGhlcmUuXG4gIGNtb3YoYTogYmlnaW50LCBiOiBiaWdpbnQsIGNvbmRpdGlvbjogYm9vbGVhbikge1xuICAgIHJldHVybiBjb25kaXRpb24gPyBiIDogYTtcbiAgfVxufVxuXG4vKipcbiAqIENyZWF0ZXMgYSBmaW5pdGUgZmllbGQuIE1ham9yIHBlcmZvcm1hbmNlIG9wdGltaXphdGlvbnM6XG4gKiAqIDEuIERlbm9ybWFsaXplZCBvcGVyYXRpb25zIGxpa2UgbXVsTiBpbnN0ZWFkIG9mIG11bC5cbiAqICogMi4gSWRlbnRpY2FsIG9iamVjdCBzaGFwZTogbmV2ZXIgYWRkIG9yIHJlbW92ZSBrZXlzLlxuICogKiAzLiBgT2JqZWN0LmZyZWV6ZWAuXG4gKiBGcmFnaWxlOiBhbHdheXMgcnVuIGEgYmVuY2htYXJrIG9uIGEgY2hhbmdlLlxuICogU2VjdXJpdHkgbm90ZTogb3BlcmF0aW9ucyBkb24ndCBjaGVjayAnaXNWYWxpZCcgZm9yIGFsbCBlbGVtZW50cyBmb3IgcGVyZm9ybWFuY2UgcmVhc29ucyxcbiAqIGl0IGlzIGNhbGxlciByZXNwb25zaWJpbGl0eSB0byBjaGVjayB0aGlzLlxuICogVGhpcyBpcyBsb3ctbGV2ZWwgY29kZSwgcGxlYXNlIG1ha2Ugc3VyZSB5b3Uga25vdyB3aGF0IHlvdSdyZSBkb2luZy5cbiAqXG4gKiBOb3RlIGFib3V0IGZpZWxkIHByb3BlcnRpZXM6XG4gKiAqIENIQVJBQ1RFUklTVElDIHAgPSBwcmltZSBudW1iZXIsIG51bWJlciBvZiBlbGVtZW50cyBpbiBtYWluIHN1Ymdyb3VwLlxuICogKiBPUkRFUiBxID0gc2ltaWxhciB0byBjb2ZhY3RvciBpbiBjdXJ2ZXMsIG1heSBiZSBjb21wb3NpdGUgYHEgPSBwXm1gLlxuICpcbiAqIEBwYXJhbSBPUkRFUiBmaWVsZCBvcmRlciwgcHJvYmFibHkgcHJpbWUsIG9yIGNvdWxkIGJlIGNvbXBvc2l0ZVxuICogQHBhcmFtIGJpdExlbiBob3cgbWFueSBiaXRzIHRoZSBmaWVsZCBjb25zdW1lc1xuICogQHBhcmFtIGlzTEUgKGRlZmF1bHQ6IGZhbHNlKSBpZiBlbmNvZGluZyAvIGRlY29kaW5nIHNob3VsZCBiZSBpbiBsaXR0bGUtZW5kaWFuXG4gKiBAcGFyYW0gcmVkZWYgb3B0aW9uYWwgZmFzdGVyIHJlZGVmaW5pdGlvbnMgb2Ygc3FydCBhbmQgb3RoZXIgbWV0aG9kc1xuICovXG5leHBvcnQgZnVuY3Rpb24gRmllbGQoT1JERVI6IGJpZ2ludCwgb3B0czogRmllbGRPcHRzID0ge30pOiBSZWFkb25seTxGcEZpZWxkPiB7XG4gIHJldHVybiBuZXcgX0ZpZWxkKE9SREVSLCBvcHRzKTtcbn1cblxuLy8gR2VuZXJpYyByYW5kb20gc2NhbGFyLCB3ZSBjYW4gZG8gc2FtZSBmb3Igb3RoZXIgZmllbGRzIGlmIHZpYSBGcDIubXVsKEZwMi5PTkUsIEZwMi5yYW5kb20pP1xuLy8gVGhpcyBhbGxvd3MgdW5zYWZlIG1ldGhvZHMgbGlrZSBpZ25vcmUgYmlhcyBvciB6ZXJvLiBUaGVzZSB1bnNhZmUsIGJ1dCBvZnRlbiB1c2VkIGluIGRpZmZlcmVudCBwcm90b2NvbHMgKGlmIGRldGVybWluaXN0aWMgUk5HKS5cbi8vIHdoaWNoIG1lYW4gd2UgY2Fubm90IGZvcmNlIHRoaXMgdmlhIG9wdHMuXG4vLyBOb3Qgc3VyZSB3aGF0IHRvIGRvIHdpdGggcmFuZG9tQnl0ZXMsIHdlIGNhbiBhY2NlcHQgaXQgaW5zaWRlIG9wdHMgaWYgd2FudGVkLlxuLy8gUHJvYmFibHkgbmVlZCB0byBleHBvcnQgZ2V0TWluSGFzaExlbmd0aCBzb21ld2hlcmU/XG4vLyByYW5kb20oYnl0ZXM/OiBVaW50OEFycmF5LCB1bnNhZmVBbGxvd1plcm8gPSBmYWxzZSwgdW5zYWZlQWxsb3dCaWFzID0gZmFsc2UpIHtcbi8vICAgY29uc3QgTEVOID0gIXVuc2FmZUFsbG93QmlhcyA/IGdldE1pbkhhc2hMZW5ndGgoT1JERVIpIDogQllURVM7XG4vLyAgIGlmIChieXRlcyA9PT0gdW5kZWZpbmVkKSBieXRlcyA9IHJhbmRvbUJ5dGVzKExFTik7IC8vIF9vcHRzLnJhbmRvbUJ5dGVzP1xuLy8gICBjb25zdCBudW0gPSBpc0xFID8gYnl0ZXNUb051bWJlckxFKGJ5dGVzKSA6IGJ5dGVzVG9OdW1iZXJCRShieXRlcyk7XG4vLyAgIC8vIGBtb2QoeCwgMTEpYCBjYW4gc29tZXRpbWVzIHByb2R1Y2UgMC4gYG1vZCh4LCAxMCkgKyAxYCBpcyB0aGUgc2FtZSwgYnV0IG5vIDBcbi8vICAgY29uc3QgcmVkdWNlZCA9IHVuc2FmZUFsbG93WmVybyA/IG1vZChudW0sIE9SREVSKSA6IG1vZChudW0sIE9SREVSIC0gXzFuKSArIF8xbjtcbi8vICAgcmV0dXJuIHJlZHVjZWQ7XG4vLyB9LFxuXG5leHBvcnQgZnVuY3Rpb24gRnBTcXJ0T2RkPFQ+KEZwOiBJRmllbGQ8VD4sIGVsbTogVCk6IFQge1xuICBpZiAoIUZwLmlzT2RkKSB0aHJvdyBuZXcgRXJyb3IoXCJGaWVsZCBkb2Vzbid0IGhhdmUgaXNPZGRcIik7XG4gIGNvbnN0IHJvb3QgPSBGcC5zcXJ0KGVsbSk7XG4gIHJldHVybiBGcC5pc09kZChyb290KSA/IHJvb3QgOiBGcC5uZWcocm9vdCk7XG59XG5cbmV4cG9ydCBmdW5jdGlvbiBGcFNxcnRFdmVuPFQ+KEZwOiBJRmllbGQ8VD4sIGVsbTogVCk6IFQge1xuICBpZiAoIUZwLmlzT2RkKSB0aHJvdyBuZXcgRXJyb3IoXCJGaWVsZCBkb2Vzbid0IGhhdmUgaXNPZGRcIik7XG4gIGNvbnN0IHJvb3QgPSBGcC5zcXJ0KGVsbSk7XG4gIHJldHVybiBGcC5pc09kZChyb290KSA/IEZwLm5lZyhyb290KSA6IHJvb3Q7XG59XG5cbi8qKlxuICogUmV0dXJucyB0b3RhbCBudW1iZXIgb2YgYnl0ZXMgY29uc3VtZWQgYnkgdGhlIGZpZWxkIGVsZW1lbnQuXG4gKiBGb3IgZXhhbXBsZSwgMzIgYnl0ZXMgZm9yIHVzdWFsIDI1Ni1iaXQgd2VpZXJzdHJhc3MgY3VydmUuXG4gKiBAcGFyYW0gZmllbGRPcmRlciBudW1iZXIgb2YgZmllbGQgZWxlbWVudHMsIHVzdWFsbHkgQ1VSVkUublxuICogQHJldHVybnMgYnl0ZSBsZW5ndGggb2YgZmllbGRcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGdldEZpZWxkQnl0ZXNMZW5ndGgoZmllbGRPcmRlcjogYmlnaW50KTogbnVtYmVyIHtcbiAgaWYgKHR5cGVvZiBmaWVsZE9yZGVyICE9PSAnYmlnaW50JykgdGhyb3cgbmV3IEVycm9yKCdmaWVsZCBvcmRlciBtdXN0IGJlIGJpZ2ludCcpO1xuICBjb25zdCBiaXRMZW5ndGggPSBmaWVsZE9yZGVyLnRvU3RyaW5nKDIpLmxlbmd0aDtcbiAgcmV0dXJuIE1hdGguY2VpbChiaXRMZW5ndGggLyA4KTtcbn1cblxuLyoqXG4gKiBSZXR1cm5zIG1pbmltYWwgYW1vdW50IG9mIGJ5dGVzIHRoYXQgY2FuIGJlIHNhZmVseSByZWR1Y2VkXG4gKiBieSBmaWVsZCBvcmRlci5cbiAqIFNob3VsZCBiZSAyXi0xMjggZm9yIDEyOC1iaXQgY3VydmUgc3VjaCBhcyBQMjU2LlxuICogQHBhcmFtIGZpZWxkT3JkZXIgbnVtYmVyIG9mIGZpZWxkIGVsZW1lbnRzLCB1c3VhbGx5IENVUlZFLm5cbiAqIEByZXR1cm5zIGJ5dGUgbGVuZ3RoIG9mIHRhcmdldCBoYXNoXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBnZXRNaW5IYXNoTGVuZ3RoKGZpZWxkT3JkZXI6IGJpZ2ludCk6IG51bWJlciB7XG4gIGNvbnN0IGxlbmd0aCA9IGdldEZpZWxkQnl0ZXNMZW5ndGgoZmllbGRPcmRlcik7XG4gIHJldHVybiBsZW5ndGggKyBNYXRoLmNlaWwobGVuZ3RoIC8gMik7XG59XG5cbi8qKlxuICogXCJDb25zdGFudC10aW1lXCIgcHJpdmF0ZSBrZXkgZ2VuZXJhdGlvbiB1dGlsaXR5LlxuICogQ2FuIHRha2UgKG4gKyBuLzIpIG9yIG1vcmUgYnl0ZXMgb2YgdW5pZm9ybSBpbnB1dCBlLmcuIGZyb20gQ1NQUk5HIG9yIEtERlxuICogYW5kIGNvbnZlcnQgdGhlbSBpbnRvIHByaXZhdGUgc2NhbGFyLCB3aXRoIHRoZSBtb2R1bG8gYmlhcyBiZWluZyBuZWdsaWdpYmxlLlxuICogTmVlZHMgYXQgbGVhc3QgNDggYnl0ZXMgb2YgaW5wdXQgZm9yIDMyLWJ5dGUgcHJpdmF0ZSBrZXkuXG4gKiBodHRwczovL3Jlc2VhcmNoLmt1ZGVsc2tpc2VjdXJpdHkuY29tLzIwMjAvMDcvMjgvdGhlLWRlZmluaXRpdmUtZ3VpZGUtdG8tbW9kdWxvLWJpYXMtYW5kLWhvdy10by1hdm9pZC1pdC9cbiAqIEZJUFMgMTg2LTUsIEEuMiBodHRwczovL2NzcmMubmlzdC5nb3YvcHVibGljYXRpb25zL2RldGFpbC9maXBzLzE4Ni81L2ZpbmFsXG4gKiBSRkMgOTM4MCwgaHR0cHM6Ly93d3cucmZjLWVkaXRvci5vcmcvcmZjL3JmYzkzODAjc2VjdGlvbi01XG4gKiBAcGFyYW0gaGFzaCBoYXNoIG91dHB1dCBmcm9tIFNIQTMgb3IgYSBzaW1pbGFyIGZ1bmN0aW9uXG4gKiBAcGFyYW0gZ3JvdXBPcmRlciBzaXplIG9mIHN1Ymdyb3VwIC0gKGUuZy4gc2VjcDI1NmsxLlBvaW50LkZuLk9SREVSKVxuICogQHBhcmFtIGlzTEUgaW50ZXJwcmV0IGhhc2ggYnl0ZXMgYXMgTEUgbnVtXG4gKiBAcmV0dXJucyB2YWxpZCBwcml2YXRlIHNjYWxhclxuICovXG5leHBvcnQgZnVuY3Rpb24gbWFwSGFzaFRvRmllbGQoa2V5OiBVaW50OEFycmF5LCBmaWVsZE9yZGVyOiBiaWdpbnQsIGlzTEUgPSBmYWxzZSk6IFVpbnQ4QXJyYXkge1xuICBhYnl0ZXMoa2V5KTtcbiAgY29uc3QgbGVuID0ga2V5Lmxlbmd0aDtcbiAgY29uc3QgZmllbGRMZW4gPSBnZXRGaWVsZEJ5dGVzTGVuZ3RoKGZpZWxkT3JkZXIpO1xuICBjb25zdCBtaW5MZW4gPSBnZXRNaW5IYXNoTGVuZ3RoKGZpZWxkT3JkZXIpO1xuICAvLyBObyBzbWFsbCBudW1iZXJzOiBuZWVkIHRvIHVuZGVyc3RhbmQgYmlhcyBzdG9yeS4gTm8gaHVnZSBudW1iZXJzOiBlYXNpZXIgdG8gZGV0ZWN0IEpTIHRpbWluZ3MuXG4gIGlmIChsZW4gPCAxNiB8fCBsZW4gPCBtaW5MZW4gfHwgbGVuID4gMTAyNClcbiAgICB0aHJvdyBuZXcgRXJyb3IoJ2V4cGVjdGVkICcgKyBtaW5MZW4gKyAnLTEwMjQgYnl0ZXMgb2YgaW5wdXQsIGdvdCAnICsgbGVuKTtcbiAgY29uc3QgbnVtID0gaXNMRSA/IGJ5dGVzVG9OdW1iZXJMRShrZXkpIDogYnl0ZXNUb051bWJlckJFKGtleSk7XG4gIC8vIGBtb2QoeCwgMTEpYCBjYW4gc29tZXRpbWVzIHByb2R1Y2UgMC4gYG1vZCh4LCAxMCkgKyAxYCBpcyB0aGUgc2FtZSwgYnV0IG5vIDBcbiAgY29uc3QgcmVkdWNlZCA9IG1vZChudW0sIGZpZWxkT3JkZXIgLSBfMW4pICsgXzFuO1xuICByZXR1cm4gaXNMRSA/IG51bWJlclRvQnl0ZXNMRShyZWR1Y2VkLCBmaWVsZExlbikgOiBudW1iZXJUb0J5dGVzQkUocmVkdWNlZCwgZmllbGRMZW4pO1xufVxuIiwgIi8qKlxuICogU2hvcnQgV2VpZXJzdHJhc3MgY3VydmUgbWV0aG9kcy4gVGhlIGZvcm11bGEgaXM6IHlcdTAwQjIgPSB4XHUwMEIzICsgYXggKyBiLlxuICpcbiAqICMjIyBEZXNpZ24gcmF0aW9uYWxlIGZvciB0eXBlc1xuICpcbiAqICogSW50ZXJhY3Rpb24gYmV0d2VlbiBjbGFzc2VzIGZyb20gZGlmZmVyZW50IGN1cnZlcyBzaG91bGQgZmFpbDpcbiAqICAgYGsyNTYuUG9pbnQuQkFTRS5hZGQocDI1Ni5Qb2ludC5CQVNFKWBcbiAqICogRm9yIHRoaXMgcHVycG9zZSB3ZSB3YW50IHRvIHVzZSBgaW5zdGFuY2VvZmAgb3BlcmF0b3IsIHdoaWNoIGlzIGZhc3QgYW5kIHdvcmtzIGR1cmluZyBydW50aW1lXG4gKiAqIERpZmZlcmVudCBjYWxscyBvZiBgY3VydmUoKWAgd291bGQgcmV0dXJuIGRpZmZlcmVudCBjbGFzc2VzIC1cbiAqICAgYGN1cnZlKHBhcmFtcykgIT09IGN1cnZlKHBhcmFtcylgOiBpZiBzb21lYm9keSBkZWNpZGVkIHRvIG1vbmtleS1wYXRjaCB0aGVpciBjdXJ2ZSxcbiAqICAgaXQgd29uJ3QgYWZmZWN0IG90aGVyc1xuICpcbiAqIFR5cGVTY3JpcHQgY2FuJ3QgaW5mZXIgdHlwZXMgZm9yIGNsYXNzZXMgY3JlYXRlZCBpbnNpZGUgYSBmdW5jdGlvbi4gQ2xhc3NlcyBpcyBvbmUgaW5zdGFuY2VcbiAqIG9mIG5vbWluYXRpdmUgdHlwZXMgaW4gVHlwZVNjcmlwdCBhbmQgaW50ZXJmYWNlcyBvbmx5IGNoZWNrIGZvciBzaGFwZSwgc28gaXQncyBoYXJkIHRvIGNyZWF0ZVxuICogdW5pcXVlIHR5cGUgZm9yIGV2ZXJ5IGZ1bmN0aW9uIGNhbGwuXG4gKlxuICogV2UgY2FuIHVzZSBnZW5lcmljIHR5cGVzIHZpYSBzb21lIHBhcmFtLCBsaWtlIGN1cnZlIG9wdHMsIGJ1dCB0aGF0IHdvdWxkOlxuICogICAgIDEuIEVuYWJsZSBpbnRlcmFjdGlvbiBiZXR3ZWVuIGBjdXJ2ZShwYXJhbXMpYCBhbmQgYGN1cnZlKHBhcmFtcylgIChjdXJ2ZXMgb2Ygc2FtZSBwYXJhbXMpXG4gKiAgICAgd2hpY2ggaXMgaGFyZCB0byBkZWJ1Zy5cbiAqICAgICAyLiBQYXJhbXMgY2FuIGJlIGdlbmVyaWMgYW5kIHdlIGNhbid0IGVuZm9yY2UgdGhlbSB0byBiZSBjb25zdGFudCB2YWx1ZTpcbiAqICAgICBpZiBzb21lYm9keSBjcmVhdGVzIGN1cnZlIGZyb20gbm9uLWNvbnN0YW50IHBhcmFtcyxcbiAqICAgICBpdCB3b3VsZCBiZSBhbGxvd2VkIHRvIGludGVyYWN0IHdpdGggb3RoZXIgY3VydmVzIHdpdGggbm9uLWNvbnN0YW50IHBhcmFtc1xuICpcbiAqIEB0b2RvIGh0dHBzOi8vd3d3LnR5cGVzY3JpcHRsYW5nLm9yZy9kb2NzL2hhbmRib29rL3JlbGVhc2Utbm90ZXMvdHlwZXNjcmlwdC0yLTcuaHRtbCN1bmlxdWUtc3ltYm9sXG4gKiBAbW9kdWxlXG4gKi9cbi8qISBub2JsZS1jdXJ2ZXMgLSBNSVQgTGljZW5zZSAoYykgMjAyMiBQYXVsIE1pbGxlciAocGF1bG1pbGxyLmNvbSkgKi9cbmltcG9ydCB7IGhtYWMgYXMgbm9ibGVIbWFjIH0gZnJvbSAnQG5vYmxlL2hhc2hlcy9obWFjLmpzJztcbmltcG9ydCB7IGFoYXNoIH0gZnJvbSAnQG5vYmxlL2hhc2hlcy91dGlscy5qcyc7XG5pbXBvcnQge1xuICBhYm9vbCxcbiAgYWJ5dGVzLFxuICBhSW5SYW5nZSxcbiAgYml0TGVuLFxuICBiaXRNYXNrLFxuICBieXRlc1RvSGV4LFxuICBieXRlc1RvTnVtYmVyQkUsXG4gIGNvbmNhdEJ5dGVzLFxuICBjcmVhdGVIbWFjRHJiZyxcbiAgaGV4VG9CeXRlcyxcbiAgaXNCeXRlcyxcbiAgbWVtb2l6ZWQsXG4gIG51bWJlclRvSGV4VW5wYWRkZWQsXG4gIHZhbGlkYXRlT2JqZWN0LFxuICByYW5kb21CeXRlcyBhcyB3Y1JhbmRvbUJ5dGVzLFxuICB0eXBlIENIYXNoLFxuICB0eXBlIFNpZ25lcixcbn0gZnJvbSAnLi4vdXRpbHMudHMnO1xuaW1wb3J0IHtcbiAgY3JlYXRlQ3VydmVGaWVsZHMsXG4gIGNyZWF0ZUtleWdlbixcbiAgbXVsRW5kb1Vuc2FmZSxcbiAgbmVnYXRlQ3QsXG4gIG5vcm1hbGl6ZVosXG4gIHdOQUYsXG4gIHR5cGUgQWZmaW5lUG9pbnQsXG4gIHR5cGUgQ3VydmVMZW5ndGhzLFxuICB0eXBlIEN1cnZlUG9pbnQsXG4gIHR5cGUgQ3VydmVQb2ludENvbnMsXG59IGZyb20gJy4vY3VydmUudHMnO1xuaW1wb3J0IHtcbiAgRnBJbnZlcnRCYXRjaCxcbiAgZ2V0TWluSGFzaExlbmd0aCxcbiAgbWFwSGFzaFRvRmllbGQsXG4gIHZhbGlkYXRlRmllbGQsXG4gIHR5cGUgSUZpZWxkLFxufSBmcm9tICcuL21vZHVsYXIudHMnO1xuXG5leHBvcnQgdHlwZSB7IEFmZmluZVBvaW50IH07XG5cbnR5cGUgRW5kb0Jhc2lzID0gW1tiaWdpbnQsIGJpZ2ludF0sIFtiaWdpbnQsIGJpZ2ludF1dO1xuLyoqXG4gKiBXaGVuIFdlaWVyc3RyYXNzIGN1cnZlIGhhcyBgYT0wYCwgaXQgYmVjb21lcyBLb2JsaXR6IGN1cnZlLlxuICogS29ibGl0eiBjdXJ2ZXMgYWxsb3cgdXNpbmcgKiplZmZpY2llbnRseS1jb21wdXRhYmxlIEdMViBlbmRvbW9ycGhpc20gXHUwM0M4KiouXG4gKiBFbmRvbW9ycGhpc20gdXNlcyAyeCBsZXNzIFJBTSwgc3BlZWRzIHVwIHByZWNvbXB1dGF0aW9uIGJ5IDJ4IGFuZCBFQ0RIIC8ga2V5IHJlY292ZXJ5IGJ5IDIwJS5cbiAqIEZvciBwcmVjb21wdXRlZCB3TkFGIGl0IHRyYWRlcyBvZmYgMS8yIGluaXQgdGltZSAmIDEvMyByYW0gZm9yIDIwJSBwZXJmIGhpdC5cbiAqXG4gKiBFbmRvbW9ycGhpc20gY29uc2lzdHMgb2YgYmV0YSwgbGFtYmRhIGFuZCBzcGxpdFNjYWxhcjpcbiAqXG4gKiAxLiBHTFYgZW5kb21vcnBoaXNtIFx1MDNDOCB0cmFuc2Zvcm1zIGEgcG9pbnQ6IGBQID0gKHgsIHkpIFx1MjFBNiBcdTAzQzgoUCkgPSAoXHUwM0IyXHUwMEI3eCBtb2QgcCwgeSlgXG4gKiAyLiBHTFYgc2NhbGFyIGRlY29tcG9zaXRpb24gdHJhbnNmb3JtcyBhIHNjYWxhcjogYGsgXHUyMjYxIGtcdTIwODEgKyBrXHUyMDgyXHUwMEI3XHUwM0JCIChtb2QgbilgXG4gKiAzLiBUaGVuIHRoZXNlIGFyZSBjb21iaW5lZDogYGtcdTAwQjdQID0ga1x1MjA4MVx1MDBCN1AgKyBrXHUyMDgyXHUwMEI3XHUwM0M4KFApYFxuICogNC4gVHdvIDEyOC1iaXQgcG9pbnQtYnktc2NhbGFyIG11bHRpcGxpY2F0aW9ucyArIG9uZSBwb2ludCBhZGRpdGlvbiBpcyBmYXN0ZXIgdGhhblxuICogICAgb25lIDI1Ni1iaXQgbXVsdGlwbGljYXRpb24uXG4gKlxuICogd2hlcmVcbiAqICogYmV0YTogXHUwM0IyIFx1MjIwOCBGXHUyMDlBIHdpdGggXHUwM0IyXHUwMEIzID0gMSwgXHUwM0IyIFx1MjI2MCAxXG4gKiAqIGxhbWJkYTogXHUwM0JCIFx1MjIwOCBGXHUyMDk5IHdpdGggXHUwM0JCXHUwMEIzID0gMSwgXHUwM0JCIFx1MjI2MCAxXG4gKiAqIHNwbGl0U2NhbGFyIGRlY29tcG9zZXMgayBcdTIxQTYga1x1MjA4MSwga1x1MjA4MiwgYnkgdXNpbmcgcmVkdWNlZCBiYXNpcyB2ZWN0b3JzLlxuICogICBHYXVzcyBsYXR0aWNlIHJlZHVjdGlvbiBjYWxjdWxhdGVzIHRoZW0gZnJvbSBpbml0aWFsIGJhc2lzIHZlY3RvcnMgYChuLCAwKSwgKC1cdTAzQkIsIDApYFxuICpcbiAqIENoZWNrIG91dCBgdGVzdC9taXNjL2VuZG9tb3JwaGlzbS5qc2AgYW5kXG4gKiBbZ2lzdF0oaHR0cHM6Ly9naXN0LmdpdGh1Yi5jb20vcGF1bG1pbGxyL2ViNjcwODA2NzkzZTg0ZGY2MjhhN2M0MzRhODczMDY2KS5cbiAqL1xuZXhwb3J0IHR5cGUgRW5kb21vcnBoaXNtT3B0cyA9IHtcbiAgYmV0YTogYmlnaW50O1xuICBiYXNpc2VzPzogRW5kb0Jhc2lzO1xuICBzcGxpdFNjYWxhcj86IChrOiBiaWdpbnQpID0+IHsgazFuZWc6IGJvb2xlYW47IGsxOiBiaWdpbnQ7IGsybmVnOiBib29sZWFuOyBrMjogYmlnaW50IH07XG59O1xuLy8gV2UgY29uc3RydWN0IGJhc2lzIGluIHN1Y2ggd2F5IHRoYXQgZGVuIGlzIGFsd2F5cyBwb3NpdGl2ZSBhbmQgZXF1YWxzIG4sIGJ1dCBudW0gc2lnbiBkZXBlbmRzIG9uIGJhc2lzIChub3Qgb24gc2VjcmV0IHZhbHVlKVxuY29uc3QgZGl2TmVhcmVzdCA9IChudW06IGJpZ2ludCwgZGVuOiBiaWdpbnQpID0+IChudW0gKyAobnVtID49IDAgPyBkZW4gOiAtZGVuKSAvIF8ybikgLyBkZW47XG5cbmV4cG9ydCB0eXBlIFNjYWxhckVuZG9QYXJ0cyA9IHsgazFuZWc6IGJvb2xlYW47IGsxOiBiaWdpbnQ7IGsybmVnOiBib29sZWFuOyBrMjogYmlnaW50IH07XG5cbi8qKlxuICogU3BsaXRzIHNjYWxhciBmb3IgR0xWIGVuZG9tb3JwaGlzbS5cbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIF9zcGxpdEVuZG9TY2FsYXIoazogYmlnaW50LCBiYXNpczogRW5kb0Jhc2lzLCBuOiBiaWdpbnQpOiBTY2FsYXJFbmRvUGFydHMge1xuICAvLyBTcGxpdCBzY2FsYXIgaW50byB0d28gc3VjaCB0aGF0IHBhcnQgaXMgfmhhbGYgYml0czogYGFicyhwYXJ0KSA8IHNxcnQoTilgXG4gIC8vIFNpbmNlIHBhcnQgY2FuIGJlIG5lZ2F0aXZlLCB3ZSBuZWVkIHRvIGRvIHRoaXMgb24gcG9pbnQuXG4gIC8vIFRPRE86IHZlcmlmeVNjYWxhciBmdW5jdGlvbiB3aGljaCBjb25zdW1lcyBsYW1iZGFcbiAgY29uc3QgW1thMSwgYjFdLCBbYTIsIGIyXV0gPSBiYXNpcztcbiAgY29uc3QgYzEgPSBkaXZOZWFyZXN0KGIyICogaywgbik7XG4gIGNvbnN0IGMyID0gZGl2TmVhcmVzdCgtYjEgKiBrLCBuKTtcbiAgLy8gfGsxfC98azJ8IGlzIDwgc3FydChOKSwgYnV0IGNhbiBiZSBuZWdhdGl2ZS5cbiAgLy8gSWYgd2UgZG8gYGsxIG1vZCBOYCwgd2UnbGwgZ2V0IGJpZyBzY2FsYXIgKGA+IHNxcnQoTilgKTogc28sIHdlIGRvIGNoZWFwZXIgbmVnYXRpb24gaW5zdGVhZC5cbiAgbGV0IGsxID0gayAtIGMxICogYTEgLSBjMiAqIGEyO1xuICBsZXQgazIgPSAtYzEgKiBiMSAtIGMyICogYjI7XG4gIGNvbnN0IGsxbmVnID0gazEgPCBfMG47XG4gIGNvbnN0IGsybmVnID0gazIgPCBfMG47XG4gIGlmIChrMW5lZykgazEgPSAtazE7XG4gIGlmIChrMm5lZykgazIgPSAtazI7XG4gIC8vIERvdWJsZSBjaGVjayB0aGF0IHJlc3VsdGluZyBzY2FsYXIgbGVzcyB0aGFuIGhhbGYgYml0cyBvZiBOOiBvdGhlcndpc2Ugd05BRiB3aWxsIGZhaWwuXG4gIC8vIFRoaXMgc2hvdWxkIG9ubHkgaGFwcGVuIG9uIHdyb25nIGJhc2lzZXMuIEFsc28sIG1hdGggaW5zaWRlIGlzIHRvbyBjb21wbGV4IGFuZCBJIGRvbid0IHRydXN0IGl0LlxuICBjb25zdCBNQVhfTlVNID0gYml0TWFzayhNYXRoLmNlaWwoYml0TGVuKG4pIC8gMikpICsgXzFuOyAvLyBIYWxmIGJpdHMgb2YgTlxuICBpZiAoazEgPCBfMG4gfHwgazEgPj0gTUFYX05VTSB8fCBrMiA8IF8wbiB8fCBrMiA+PSBNQVhfTlVNKSB7XG4gICAgdGhyb3cgbmV3IEVycm9yKCdzcGxpdFNjYWxhciAoZW5kb21vcnBoaXNtKTogZmFpbGVkLCBrPScgKyBrKTtcbiAgfVxuICByZXR1cm4geyBrMW5lZywgazEsIGsybmVnLCBrMiB9O1xufVxuXG4vKipcbiAqIE9wdGlvbiB0byBlbmFibGUgaGVkZ2VkIHNpZ25hdHVyZXMgd2l0aCBpbXByb3ZlZCBzZWN1cml0eS5cbiAqXG4gKiAqIFJhbmRvbWx5IGdlbmVyYXRlZCBrIGlzIGJhZCwgYmVjYXVzZSBicm9rZW4gQ1NQUk5HIHdvdWxkIGxlYWsgcHJpdmF0ZSBrZXlzLlxuICogKiBEZXRlcm1pbmlzdGljIGsgKFJGQzY5NzkpIGlzIGJldHRlcjsgYnV0IGlzIHN1c3BlY3RpYmxlIHRvIGZhdWx0IGF0dGFja3MuXG4gKlxuICogV2UgYWxsb3cgdXNpbmcgdGVjaG5pcXVlIGRlc2NyaWJlZCBpbiBSRkM2OTc5IDMuNjogYWRkaXRpb25hbCBrJywgYS5rLmEuIGFkZGluZyByYW5kb21uZXNzXG4gKiB0byBkZXRlcm1pbmlzdGljIHNpZy4gSWYgQ1NQUk5HIGlzIGJyb2tlbiAmIHJhbmRvbW5lc3MgaXMgd2VhaywgaXQgd291bGQgU1RJTEwgYmUgYXMgc2VjdXJlXG4gKiBhcyBvcmRpbmFyeSBzaWcgd2l0aG91dCBFeHRyYUVudHJvcHkuXG4gKlxuICogKiBgdHJ1ZWAgbWVhbnMgXCJmZXRjaCBkYXRhLCBmcm9tIENTUFJORywgaW5jb3Jwb3JhdGUgaXQgaW50byBrIGdlbmVyYXRpb25cIlxuICogKiBgZmFsc2VgIG1lYW5zIFwiZGlzYWJsZSBleHRyYSBlbnRyb3B5LCB1c2UgcHVyZWx5IGRldGVybWluaXN0aWMga1wiXG4gKiAqIGBVaW50OEFycmF5YCBwYXNzZWQgbWVhbnMgXCJpbmNvcnBvcmF0ZSBmb2xsb3dpbmcgZGF0YSBpbnRvIGsgZ2VuZXJhdGlvblwiXG4gKlxuICogaHR0cHM6Ly9wYXVsbWlsbHIuY29tL3Bvc3RzL2RldGVybWluaXN0aWMtc2lnbmF0dXJlcy9cbiAqL1xuZXhwb3J0IHR5cGUgRUNEU0FFeHRyYUVudHJvcHkgPSBib29sZWFuIHwgVWludDhBcnJheTtcbi8qKlxuICogLSBgY29tcGFjdGAgaXMgdGhlIGRlZmF1bHQgZm9ybWF0XG4gKiAtIGByZWNvdmVyZWRgIGlzIHRoZSBzYW1lIGFzIGNvbXBhY3QsIGJ1dCB3aXRoIGFuIGV4dHJhIGJ5dGUgaW5kaWNhdGluZyByZWNvdmVyeSBieXRlXG4gKiAtIGBkZXJgIGlzIEFTTi4xIERFUiBlbmNvZGluZ1xuICovXG5leHBvcnQgdHlwZSBFQ0RTQVNpZ25hdHVyZUZvcm1hdCA9ICdjb21wYWN0JyB8ICdyZWNvdmVyZWQnIHwgJ2Rlcic7XG4vKipcbiAqIC0gYHByZWhhc2hgOiAoZGVmYXVsdDogdHJ1ZSkgaW5kaWNhdGVzIHdoZXRoZXIgdG8gZG8gc2hhMjU2KG1lc3NhZ2UpLlxuICogICBXaGVuIGEgY3VzdG9tIGhhc2ggaXMgdXNlZCwgaXQgbXVzdCBiZSBzZXQgdG8gYGZhbHNlYC5cbiAqL1xuZXhwb3J0IHR5cGUgRUNEU0FSZWNvdmVyT3B0cyA9IHtcbiAgcHJlaGFzaD86IGJvb2xlYW47XG59O1xuLyoqXG4gKiAtIGBwcmVoYXNoYDogKGRlZmF1bHQ6IHRydWUpIGluZGljYXRlcyB3aGV0aGVyIHRvIGRvIHNoYTI1NihtZXNzYWdlKS5cbiAqICAgV2hlbiBhIGN1c3RvbSBoYXNoIGlzIHVzZWQsIGl0IG11c3QgYmUgc2V0IHRvIGBmYWxzZWAuXG4gKiAtIGBsb3dTYDogKGRlZmF1bHQ6IHRydWUpIHByb2hpYml0cyBzaWduYXR1cmVzIHdoaWNoIGhhdmUgKHNpZy5zID49IENVUlZFLm4vMm4pLlxuICogICBDb21wYXRpYmxlIHdpdGggQlRDL0VUSC4gU2V0dGluZyBgbG93UzogZmFsc2VgIGFsbG93cyB0byBjcmVhdGUgbWFsbGVhYmxlIHNpZ25hdHVyZXMsXG4gKiAgIHdoaWNoIGlzIGRlZmF1bHQgb3BlbnNzbCBiZWhhdmlvci5cbiAqICAgTm9uLW1hbGxlYWJsZSBzaWduYXR1cmVzIGNhbiBzdGlsbCBiZSBzdWNjZXNzZnVsbHkgdmVyaWZpZWQgaW4gb3BlbnNzbC5cbiAqIC0gYGZvcm1hdGA6IChkZWZhdWx0OiAnY29tcGFjdCcpICdjb21wYWN0JyBvciAncmVjb3ZlcmVkJyB3aXRoIHJlY292ZXJ5IGJ5dGVcbiAqL1xuZXhwb3J0IHR5cGUgRUNEU0FWZXJpZnlPcHRzID0ge1xuICBwcmVoYXNoPzogYm9vbGVhbjtcbiAgbG93Uz86IGJvb2xlYW47XG4gIGZvcm1hdD86IEVDRFNBU2lnbmF0dXJlRm9ybWF0O1xufTtcbi8qKlxuICogLSBgcHJlaGFzaGA6IChkZWZhdWx0OiB0cnVlKSBpbmRpY2F0ZXMgd2hldGhlciB0byBkbyBzaGEyNTYobWVzc2FnZSkuXG4gKiAgIFdoZW4gYSBjdXN0b20gaGFzaCBpcyB1c2VkLCBpdCBtdXN0IGJlIHNldCB0byBgZmFsc2VgLlxuICogLSBgbG93U2A6IChkZWZhdWx0OiB0cnVlKSBwcm9oaWJpdHMgc2lnbmF0dXJlcyB3aGljaCBoYXZlIChzaWcucyA+PSBDVVJWRS5uLzJuKS5cbiAqICAgQ29tcGF0aWJsZSB3aXRoIEJUQy9FVEguIFNldHRpbmcgYGxvd1M6IGZhbHNlYCBhbGxvd3MgdG8gY3JlYXRlIG1hbGxlYWJsZSBzaWduYXR1cmVzLFxuICogICB3aGljaCBpcyBkZWZhdWx0IG9wZW5zc2wgYmVoYXZpb3IuXG4gKiAgIE5vbi1tYWxsZWFibGUgc2lnbmF0dXJlcyBjYW4gc3RpbGwgYmUgc3VjY2Vzc2Z1bGx5IHZlcmlmaWVkIGluIG9wZW5zc2wuXG4gKiAtIGBmb3JtYXRgOiAoZGVmYXVsdDogJ2NvbXBhY3QnKSAnY29tcGFjdCcgb3IgJ3JlY292ZXJlZCcgd2l0aCByZWNvdmVyeSBieXRlXG4gKiAtIGBleHRyYUVudHJvcHlgOiAoZGVmYXVsdDogZmFsc2UpIGNyZWF0ZXMgc2lncyB3aXRoIGluY3JlYXNlZCBzZWN1cml0eSwgc2VlIHtAbGluayBFQ0RTQUV4dHJhRW50cm9weX1cbiAqL1xuZXhwb3J0IHR5cGUgRUNEU0FTaWduT3B0cyA9IHtcbiAgcHJlaGFzaD86IGJvb2xlYW47XG4gIGxvd1M/OiBib29sZWFuO1xuICBmb3JtYXQ/OiBFQ0RTQVNpZ25hdHVyZUZvcm1hdDtcbiAgZXh0cmFFbnRyb3B5PzogRUNEU0FFeHRyYUVudHJvcHk7XG59O1xuXG5mdW5jdGlvbiB2YWxpZGF0ZVNpZ0Zvcm1hdChmb3JtYXQ6IHN0cmluZyk6IEVDRFNBU2lnbmF0dXJlRm9ybWF0IHtcbiAgaWYgKCFbJ2NvbXBhY3QnLCAncmVjb3ZlcmVkJywgJ2RlciddLmluY2x1ZGVzKGZvcm1hdCkpXG4gICAgdGhyb3cgbmV3IEVycm9yKCdTaWduYXR1cmUgZm9ybWF0IG11c3QgYmUgXCJjb21wYWN0XCIsIFwicmVjb3ZlcmVkXCIsIG9yIFwiZGVyXCInKTtcbiAgcmV0dXJuIGZvcm1hdCBhcyBFQ0RTQVNpZ25hdHVyZUZvcm1hdDtcbn1cblxuZnVuY3Rpb24gdmFsaWRhdGVTaWdPcHRzPFQgZXh0ZW5kcyBFQ0RTQVNpZ25PcHRzLCBEIGV4dGVuZHMgUmVxdWlyZWQ8RUNEU0FTaWduT3B0cz4+KFxuICBvcHRzOiBULFxuICBkZWY6IERcbik6IFJlcXVpcmVkPEVDRFNBU2lnbk9wdHM+IHtcbiAgY29uc3Qgb3B0c246IEVDRFNBU2lnbk9wdHMgPSB7fTtcbiAgZm9yIChsZXQgb3B0TmFtZSBvZiBPYmplY3Qua2V5cyhkZWYpKSB7XG4gICAgLy8gQHRzLWlnbm9yZVxuICAgIG9wdHNuW29wdE5hbWVdID0gb3B0c1tvcHROYW1lXSA9PT0gdW5kZWZpbmVkID8gZGVmW29wdE5hbWVdIDogb3B0c1tvcHROYW1lXTtcbiAgfVxuICBhYm9vbChvcHRzbi5sb3dTISwgJ2xvd1MnKTtcbiAgYWJvb2wob3B0c24ucHJlaGFzaCEsICdwcmVoYXNoJyk7XG4gIGlmIChvcHRzbi5mb3JtYXQgIT09IHVuZGVmaW5lZCkgdmFsaWRhdGVTaWdGb3JtYXQob3B0c24uZm9ybWF0KTtcbiAgcmV0dXJuIG9wdHNuIGFzIFJlcXVpcmVkPEVDRFNBU2lnbk9wdHM+O1xufVxuXG4vKiogSW5zdGFuY2UgbWV0aG9kcyBmb3IgM0QgWFlaIHByb2plY3RpdmUgcG9pbnRzLiAqL1xuZXhwb3J0IGludGVyZmFjZSBXZWllcnN0cmFzc1BvaW50PFQ+IGV4dGVuZHMgQ3VydmVQb2ludDxULCBXZWllcnN0cmFzc1BvaW50PFQ+PiB7XG4gIC8qKiBwcm9qZWN0aXZlIFggY29vcmRpbmF0ZS4gRGlmZmVyZW50IGZyb20gYWZmaW5lIHguICovXG4gIHJlYWRvbmx5IFg6IFQ7XG4gIC8qKiBwcm9qZWN0aXZlIFkgY29vcmRpbmF0ZS4gRGlmZmVyZW50IGZyb20gYWZmaW5lIHkuICovXG4gIHJlYWRvbmx5IFk6IFQ7XG4gIC8qKiBwcm9qZWN0aXZlIHogY29vcmRpbmF0ZSAqL1xuICByZWFkb25seSBaOiBUO1xuICAvKiogYWZmaW5lIHggY29vcmRpbmF0ZS4gRGlmZmVyZW50IGZyb20gcHJvamVjdGl2ZSBYLiAqL1xuICBnZXQgeCgpOiBUO1xuICAvKiogYWZmaW5lIHkgY29vcmRpbmF0ZS4gRGlmZmVyZW50IGZyb20gcHJvamVjdGl2ZSBZLiAqL1xuICBnZXQgeSgpOiBUO1xuICAvKiogRW5jb2RlcyBwb2ludCB1c2luZyBJRUVFIFAxMzYzIChERVIpIGVuY29kaW5nLiBGaXJzdCBieXRlIGlzIDIvMy80LiBEZWZhdWx0ID0gaXNDb21wcmVzc2VkLiAqL1xuICB0b0J5dGVzKGlzQ29tcHJlc3NlZD86IGJvb2xlYW4pOiBVaW50OEFycmF5O1xuICB0b0hleChpc0NvbXByZXNzZWQ/OiBib29sZWFuKTogc3RyaW5nO1xufVxuXG4vKiogU3RhdGljIG1ldGhvZHMgZm9yIDNEIFhZWiBwcm9qZWN0aXZlIHBvaW50cy4gKi9cbmV4cG9ydCBpbnRlcmZhY2UgV2VpZXJzdHJhc3NQb2ludENvbnM8VD4gZXh0ZW5kcyBDdXJ2ZVBvaW50Q29uczxXZWllcnN0cmFzc1BvaW50PFQ+PiB7XG4gIC8qKiBEb2VzIE5PVCB2YWxpZGF0ZSBpZiB0aGUgcG9pbnQgaXMgdmFsaWQuIFVzZSBgLmFzc2VydFZhbGlkaXR5KClgLiAqL1xuICBuZXcgKFg6IFQsIFk6IFQsIFo6IFQpOiBXZWllcnN0cmFzc1BvaW50PFQ+O1xuICBDVVJWRSgpOiBXZWllcnN0cmFzc09wdHM8VD47XG59XG5cbi8qKlxuICogV2VpZXJzdHJhc3MgY3VydmUgb3B0aW9ucy5cbiAqXG4gKiAqIHA6IHByaW1lIGNoYXJhY3RlcmlzdGljIChvcmRlcikgb2YgZmluaXRlIGZpZWxkLCBpbiB3aGljaCBhcml0aG1ldGljcyBpcyBkb25lXG4gKiAqIG46IG9yZGVyIG9mIHByaW1lIHN1Ymdyb3VwIGEuay5hIHRvdGFsIGFtb3VudCBvZiB2YWxpZCBjdXJ2ZSBwb2ludHNcbiAqICogaDogY29mYWN0b3IsIHVzdWFsbHkgMS4gaCpuIGlzIGdyb3VwIG9yZGVyOyBuIGlzIHN1Ymdyb3VwIG9yZGVyXG4gKiAqIGE6IGZvcm11bGEgcGFyYW0sIG11c3QgYmUgaW4gZmllbGQgb2YgcFxuICogKiBiOiBmb3JtdWxhIHBhcmFtLCBtdXN0IGJlIGluIGZpZWxkIG9mIHBcbiAqICogR3g6IHggY29vcmRpbmF0ZSBvZiBnZW5lcmF0b3IgcG9pbnQgYS5rLmEuIGJhc2UgcG9pbnRcbiAqICogR3k6IHkgY29vcmRpbmF0ZSBvZiBnZW5lcmF0b3IgcG9pbnRcbiAqL1xuZXhwb3J0IHR5cGUgV2VpZXJzdHJhc3NPcHRzPFQ+ID0gUmVhZG9ubHk8e1xuICBwOiBiaWdpbnQ7XG4gIG46IGJpZ2ludDtcbiAgaDogYmlnaW50O1xuICBhOiBUO1xuICBiOiBUO1xuICBHeDogVDtcbiAgR3k6IFQ7XG59PjtcblxuLy8gV2hlbiBhIGNvZmFjdG9yICE9IDEsIHRoZXJlIGNhbiBiZSBhbiBlZmZlY3RpdmUgbWV0aG9kcyB0bzpcbi8vIDEuIERldGVybWluZSB3aGV0aGVyIGEgcG9pbnQgaXMgdG9yc2lvbi1mcmVlXG4vLyAyLiBDbGVhciB0b3JzaW9uIGNvbXBvbmVudFxuZXhwb3J0IHR5cGUgV2VpZXJzdHJhc3NFeHRyYU9wdHM8VD4gPSBQYXJ0aWFsPHtcbiAgRnA6IElGaWVsZDxUPjtcbiAgRm46IElGaWVsZDxiaWdpbnQ+O1xuICBhbGxvd0luZmluaXR5UG9pbnQ6IGJvb2xlYW47XG4gIGVuZG86IEVuZG9tb3JwaGlzbU9wdHM7XG4gIGlzVG9yc2lvbkZyZWU6IChjOiBXZWllcnN0cmFzc1BvaW50Q29uczxUPiwgcG9pbnQ6IFdlaWVyc3RyYXNzUG9pbnQ8VD4pID0+IGJvb2xlYW47XG4gIGNsZWFyQ29mYWN0b3I6IChjOiBXZWllcnN0cmFzc1BvaW50Q29uczxUPiwgcG9pbnQ6IFdlaWVyc3RyYXNzUG9pbnQ8VD4pID0+IFdlaWVyc3RyYXNzUG9pbnQ8VD47XG4gIGZyb21CeXRlczogKGJ5dGVzOiBVaW50OEFycmF5KSA9PiBBZmZpbmVQb2ludDxUPjtcbiAgdG9CeXRlczogKFxuICAgIGM6IFdlaWVyc3RyYXNzUG9pbnRDb25zPFQ+LFxuICAgIHBvaW50OiBXZWllcnN0cmFzc1BvaW50PFQ+LFxuICAgIGlzQ29tcHJlc3NlZDogYm9vbGVhblxuICApID0+IFVpbnQ4QXJyYXk7XG59PjtcblxuLyoqXG4gKiBPcHRpb25zIGZvciBFQ0RTQSBzaWduYXR1cmVzIG92ZXIgYSBXZWllcnN0cmFzcyBjdXJ2ZS5cbiAqXG4gKiAqIGxvd1M6IChkZWZhdWx0OiB0cnVlKSB3aGV0aGVyIHByb2R1Y2VkIC8gdmVyaWZpZWQgc2lnbmF0dXJlcyBvY2N1cHkgbG93IGhhbGYgb2YgZWNkc2FPcHRzLnAuIFByZXZlbnRzIG1hbGxlYWJpbGl0eS5cbiAqICogaG1hYzogKGRlZmF1bHQ6IG5vYmxlLWhhc2hlcyBobWFjKSBmdW5jdGlvbiwgd291bGQgYmUgdXNlZCB0byBpbml0IGhtYWMtZHJiZyBmb3IgayBnZW5lcmF0aW9uLlxuICogKiByYW5kb21CeXRlczogKGRlZmF1bHQ6IHdlYmNyeXB0byBvcy1sZXZlbCBDU1BSTkcpIGN1c3RvbSBtZXRob2QgZm9yIGZldGNoaW5nIHNlY3VyZSByYW5kb21uZXNzLlxuICogKiBiaXRzMmludCwgYml0czJpbnRfbW9kTjogdXNlZCBpbiBzaWdzLCBzb21ldGltZXMgb3ZlcnJpZGRlbiBieSBjdXJ2ZXNcbiAqL1xuZXhwb3J0IHR5cGUgRUNEU0FPcHRzID0gUGFydGlhbDx7XG4gIGxvd1M6IGJvb2xlYW47XG4gIGhtYWM6IChrZXk6IFVpbnQ4QXJyYXksIG1lc3NhZ2U6IFVpbnQ4QXJyYXkpID0+IFVpbnQ4QXJyYXk7XG4gIHJhbmRvbUJ5dGVzOiAoYnl0ZXNMZW5ndGg/OiBudW1iZXIpID0+IFVpbnQ4QXJyYXk7XG4gIGJpdHMyaW50OiAoYnl0ZXM6IFVpbnQ4QXJyYXkpID0+IGJpZ2ludDtcbiAgYml0czJpbnRfbW9kTjogKGJ5dGVzOiBVaW50OEFycmF5KSA9PiBiaWdpbnQ7XG59PjtcblxuLyoqXG4gKiBFbGxpcHRpYyBDdXJ2ZSBEaWZmaWUtSGVsbG1hbiBpbnRlcmZhY2UuXG4gKiBQcm92aWRlcyBrZXlnZW4sIHNlY3JldC10by1wdWJsaWMgY29udmVyc2lvbiwgY2FsY3VsYXRpbmcgc2hhcmVkIHNlY3JldHMuXG4gKi9cbmV4cG9ydCBpbnRlcmZhY2UgRUNESCB7XG4gIGtleWdlbjogKHNlZWQ/OiBVaW50OEFycmF5KSA9PiB7IHNlY3JldEtleTogVWludDhBcnJheTsgcHVibGljS2V5OiBVaW50OEFycmF5IH07XG4gIGdldFB1YmxpY0tleTogKHNlY3JldEtleTogVWludDhBcnJheSwgaXNDb21wcmVzc2VkPzogYm9vbGVhbikgPT4gVWludDhBcnJheTtcbiAgZ2V0U2hhcmVkU2VjcmV0OiAoXG4gICAgc2VjcmV0S2V5QTogVWludDhBcnJheSxcbiAgICBwdWJsaWNLZXlCOiBVaW50OEFycmF5LFxuICAgIGlzQ29tcHJlc3NlZD86IGJvb2xlYW5cbiAgKSA9PiBVaW50OEFycmF5O1xuICBQb2ludDogV2VpZXJzdHJhc3NQb2ludENvbnM8YmlnaW50PjtcbiAgdXRpbHM6IHtcbiAgICBpc1ZhbGlkU2VjcmV0S2V5OiAoc2VjcmV0S2V5OiBVaW50OEFycmF5KSA9PiBib29sZWFuO1xuICAgIGlzVmFsaWRQdWJsaWNLZXk6IChwdWJsaWNLZXk6IFVpbnQ4QXJyYXksIGlzQ29tcHJlc3NlZD86IGJvb2xlYW4pID0+IGJvb2xlYW47XG4gICAgcmFuZG9tU2VjcmV0S2V5OiAoc2VlZD86IFVpbnQ4QXJyYXkpID0+IFVpbnQ4QXJyYXk7XG4gIH07XG4gIGxlbmd0aHM6IEN1cnZlTGVuZ3Rocztcbn1cblxuLyoqXG4gKiBFQ0RTQSBpbnRlcmZhY2UuXG4gKiBPbmx5IHN1cHBvcnRlZCBmb3IgcHJpbWUgZmllbGRzLCBub3QgRnAyIChleHRlbnNpb24gZmllbGRzKS5cbiAqL1xuZXhwb3J0IGludGVyZmFjZSBFQ0RTQSBleHRlbmRzIEVDREgge1xuICBzaWduOiAobWVzc2FnZTogVWludDhBcnJheSwgc2VjcmV0S2V5OiBVaW50OEFycmF5LCBvcHRzPzogRUNEU0FTaWduT3B0cykgPT4gVWludDhBcnJheTtcbiAgdmVyaWZ5OiAoXG4gICAgc2lnbmF0dXJlOiBVaW50OEFycmF5LFxuICAgIG1lc3NhZ2U6IFVpbnQ4QXJyYXksXG4gICAgcHVibGljS2V5OiBVaW50OEFycmF5LFxuICAgIG9wdHM/OiBFQ0RTQVZlcmlmeU9wdHNcbiAgKSA9PiBib29sZWFuO1xuICByZWNvdmVyUHVibGljS2V5KHNpZ25hdHVyZTogVWludDhBcnJheSwgbWVzc2FnZTogVWludDhBcnJheSwgb3B0cz86IEVDRFNBUmVjb3Zlck9wdHMpOiBVaW50OEFycmF5O1xuICBTaWduYXR1cmU6IEVDRFNBU2lnbmF0dXJlQ29ucztcbn1cbmV4cG9ydCBjbGFzcyBERVJFcnIgZXh0ZW5kcyBFcnJvciB7XG4gIGNvbnN0cnVjdG9yKG0gPSAnJykge1xuICAgIHN1cGVyKG0pO1xuICB9XG59XG5leHBvcnQgdHlwZSBJREVSID0ge1xuICAvLyBhc24uMSBERVIgZW5jb2RpbmcgdXRpbHNcbiAgRXJyOiB0eXBlb2YgREVSRXJyO1xuICAvLyBCYXNpYyBidWlsZGluZyBibG9jayBpcyBUTFYgKFRhZy1MZW5ndGgtVmFsdWUpXG4gIF90bHY6IHtcbiAgICBlbmNvZGU6ICh0YWc6IG51bWJlciwgZGF0YTogc3RyaW5nKSA9PiBzdHJpbmc7XG4gICAgLy8gdiAtIHZhbHVlLCBsIC0gbGVmdCBieXRlcyAodW5wYXJzZWQpXG4gICAgZGVjb2RlKHRhZzogbnVtYmVyLCBkYXRhOiBVaW50OEFycmF5KTogeyB2OiBVaW50OEFycmF5OyBsOiBVaW50OEFycmF5IH07XG4gIH07XG4gIC8vIGh0dHBzOi8vY3J5cHRvLnN0YWNrZXhjaGFuZ2UuY29tL2EvNTc3MzQgTGVmdG1vc3QgYml0IG9mIGZpcnN0IGJ5dGUgaXMgJ25lZ2F0aXZlJyBmbGFnLFxuICAvLyBzaW5jZSB3ZSBhbHdheXMgdXNlIHBvc2l0aXZlIGludGVnZXJzIGhlcmUuIEl0IG11c3QgYWx3YXlzIGJlIGVtcHR5OlxuICAvLyAtIGFkZCB6ZXJvIGJ5dGUgaWYgZXhpc3RzXG4gIC8vIC0gaWYgbmV4dCBieXRlIGRvZXNuJ3QgaGF2ZSBhIGZsYWcsIGxlYWRpbmcgemVybyBpcyBub3QgYWxsb3dlZCAobWluaW1hbCBlbmNvZGluZylcbiAgX2ludDoge1xuICAgIGVuY29kZShudW06IGJpZ2ludCk6IHN0cmluZztcbiAgICBkZWNvZGUoZGF0YTogVWludDhBcnJheSk6IGJpZ2ludDtcbiAgfTtcbiAgdG9TaWcoaGV4OiBzdHJpbmcgfCBVaW50OEFycmF5KTogeyByOiBiaWdpbnQ7IHM6IGJpZ2ludCB9O1xuICBoZXhGcm9tU2lnKHNpZzogeyByOiBiaWdpbnQ7IHM6IGJpZ2ludCB9KTogc3RyaW5nO1xufTtcbi8qKlxuICogQVNOLjEgREVSIGVuY29kaW5nIHV0aWxpdGllcy4gQVNOIGlzIHZlcnkgY29tcGxleCAmIGZyYWdpbGUuIEZvcm1hdDpcbiAqXG4gKiAgICAgWzB4MzAgKFNFUVVFTkNFKSwgYnl0ZWxlbmd0aCwgMHgwMiAoSU5URUdFUiksIGludExlbmd0aCwgUiwgMHgwMiAoSU5URUdFUiksIGludExlbmd0aCwgU11cbiAqXG4gKiBEb2NzOiBodHRwczovL2xldHNlbmNyeXB0Lm9yZy9kb2NzL2Etd2FybS13ZWxjb21lLXRvLWFzbjEtYW5kLWRlci8sIGh0dHBzOi8vbHVjYS5udG9wLm9yZy9UZWFjaGluZy9BcHB1bnRpL2FzbjEuaHRtbFxuICovXG5leHBvcnQgY29uc3QgREVSOiBJREVSID0ge1xuICAvLyBhc24uMSBERVIgZW5jb2RpbmcgdXRpbHNcbiAgRXJyOiBERVJFcnIsXG4gIC8vIEJhc2ljIGJ1aWxkaW5nIGJsb2NrIGlzIFRMViAoVGFnLUxlbmd0aC1WYWx1ZSlcbiAgX3Rsdjoge1xuICAgIGVuY29kZTogKHRhZzogbnVtYmVyLCBkYXRhOiBzdHJpbmcpOiBzdHJpbmcgPT4ge1xuICAgICAgY29uc3QgeyBFcnI6IEUgfSA9IERFUjtcbiAgICAgIGlmICh0YWcgPCAwIHx8IHRhZyA+IDI1NikgdGhyb3cgbmV3IEUoJ3Rsdi5lbmNvZGU6IHdyb25nIHRhZycpO1xuICAgICAgaWYgKGRhdGEubGVuZ3RoICYgMSkgdGhyb3cgbmV3IEUoJ3Rsdi5lbmNvZGU6IHVucGFkZGVkIGRhdGEnKTtcbiAgICAgIGNvbnN0IGRhdGFMZW4gPSBkYXRhLmxlbmd0aCAvIDI7XG4gICAgICBjb25zdCBsZW4gPSBudW1iZXJUb0hleFVucGFkZGVkKGRhdGFMZW4pO1xuICAgICAgaWYgKChsZW4ubGVuZ3RoIC8gMikgJiAwYjEwMDBfMDAwMCkgdGhyb3cgbmV3IEUoJ3Rsdi5lbmNvZGU6IGxvbmcgZm9ybSBsZW5ndGggdG9vIGJpZycpO1xuICAgICAgLy8gbGVuZ3RoIG9mIGxlbmd0aCB3aXRoIGxvbmcgZm9ybSBmbGFnXG4gICAgICBjb25zdCBsZW5MZW4gPSBkYXRhTGVuID4gMTI3ID8gbnVtYmVyVG9IZXhVbnBhZGRlZCgobGVuLmxlbmd0aCAvIDIpIHwgMGIxMDAwXzAwMDApIDogJyc7XG4gICAgICBjb25zdCB0ID0gbnVtYmVyVG9IZXhVbnBhZGRlZCh0YWcpO1xuICAgICAgcmV0dXJuIHQgKyBsZW5MZW4gKyBsZW4gKyBkYXRhO1xuICAgIH0sXG4gICAgLy8gdiAtIHZhbHVlLCBsIC0gbGVmdCBieXRlcyAodW5wYXJzZWQpXG4gICAgZGVjb2RlKHRhZzogbnVtYmVyLCBkYXRhOiBVaW50OEFycmF5KTogeyB2OiBVaW50OEFycmF5OyBsOiBVaW50OEFycmF5IH0ge1xuICAgICAgY29uc3QgeyBFcnI6IEUgfSA9IERFUjtcbiAgICAgIGxldCBwb3MgPSAwO1xuICAgICAgaWYgKHRhZyA8IDAgfHwgdGFnID4gMjU2KSB0aHJvdyBuZXcgRSgndGx2LmVuY29kZTogd3JvbmcgdGFnJyk7XG4gICAgICBpZiAoZGF0YS5sZW5ndGggPCAyIHx8IGRhdGFbcG9zKytdICE9PSB0YWcpIHRocm93IG5ldyBFKCd0bHYuZGVjb2RlOiB3cm9uZyB0bHYnKTtcbiAgICAgIGNvbnN0IGZpcnN0ID0gZGF0YVtwb3MrK107XG4gICAgICBjb25zdCBpc0xvbmcgPSAhIShmaXJzdCAmIDBiMTAwMF8wMDAwKTsgLy8gRmlyc3QgYml0IG9mIGZpcnN0IGxlbmd0aCBieXRlIGlzIGZsYWcgZm9yIHNob3J0L2xvbmcgZm9ybVxuICAgICAgbGV0IGxlbmd0aCA9IDA7XG4gICAgICBpZiAoIWlzTG9uZykgbGVuZ3RoID0gZmlyc3Q7XG4gICAgICBlbHNlIHtcbiAgICAgICAgLy8gTG9uZyBmb3JtOiBbbG9uZ0ZsYWcoMWJpdCksIGxlbmd0aExlbmd0aCg3Yml0KSwgbGVuZ3RoIChCRSldXG4gICAgICAgIGNvbnN0IGxlbkxlbiA9IGZpcnN0ICYgMGIwMTExXzExMTE7XG4gICAgICAgIGlmICghbGVuTGVuKSB0aHJvdyBuZXcgRSgndGx2LmRlY29kZShsb25nKTogaW5kZWZpbml0ZSBsZW5ndGggbm90IHN1cHBvcnRlZCcpO1xuICAgICAgICBpZiAobGVuTGVuID4gNCkgdGhyb3cgbmV3IEUoJ3Rsdi5kZWNvZGUobG9uZyk6IGJ5dGUgbGVuZ3RoIGlzIHRvbyBiaWcnKTsgLy8gdGhpcyB3aWxsIG92ZXJmbG93IHUzMiBpbiBqc1xuICAgICAgICBjb25zdCBsZW5ndGhCeXRlcyA9IGRhdGEuc3ViYXJyYXkocG9zLCBwb3MgKyBsZW5MZW4pO1xuICAgICAgICBpZiAobGVuZ3RoQnl0ZXMubGVuZ3RoICE9PSBsZW5MZW4pIHRocm93IG5ldyBFKCd0bHYuZGVjb2RlOiBsZW5ndGggYnl0ZXMgbm90IGNvbXBsZXRlJyk7XG4gICAgICAgIGlmIChsZW5ndGhCeXRlc1swXSA9PT0gMCkgdGhyb3cgbmV3IEUoJ3Rsdi5kZWNvZGUobG9uZyk6IHplcm8gbGVmdG1vc3QgYnl0ZScpO1xuICAgICAgICBmb3IgKGNvbnN0IGIgb2YgbGVuZ3RoQnl0ZXMpIGxlbmd0aCA9IChsZW5ndGggPDwgOCkgfCBiO1xuICAgICAgICBwb3MgKz0gbGVuTGVuO1xuICAgICAgICBpZiAobGVuZ3RoIDwgMTI4KSB0aHJvdyBuZXcgRSgndGx2LmRlY29kZShsb25nKTogbm90IG1pbmltYWwgZW5jb2RpbmcnKTtcbiAgICAgIH1cbiAgICAgIGNvbnN0IHYgPSBkYXRhLnN1YmFycmF5KHBvcywgcG9zICsgbGVuZ3RoKTtcbiAgICAgIGlmICh2Lmxlbmd0aCAhPT0gbGVuZ3RoKSB0aHJvdyBuZXcgRSgndGx2LmRlY29kZTogd3JvbmcgdmFsdWUgbGVuZ3RoJyk7XG4gICAgICByZXR1cm4geyB2LCBsOiBkYXRhLnN1YmFycmF5KHBvcyArIGxlbmd0aCkgfTtcbiAgICB9LFxuICB9LFxuICAvLyBodHRwczovL2NyeXB0by5zdGFja2V4Y2hhbmdlLmNvbS9hLzU3NzM0IExlZnRtb3N0IGJpdCBvZiBmaXJzdCBieXRlIGlzICduZWdhdGl2ZScgZmxhZyxcbiAgLy8gc2luY2Ugd2UgYWx3YXlzIHVzZSBwb3NpdGl2ZSBpbnRlZ2VycyBoZXJlLiBJdCBtdXN0IGFsd2F5cyBiZSBlbXB0eTpcbiAgLy8gLSBhZGQgemVybyBieXRlIGlmIGV4aXN0c1xuICAvLyAtIGlmIG5leHQgYnl0ZSBkb2Vzbid0IGhhdmUgYSBmbGFnLCBsZWFkaW5nIHplcm8gaXMgbm90IGFsbG93ZWQgKG1pbmltYWwgZW5jb2RpbmcpXG4gIF9pbnQ6IHtcbiAgICBlbmNvZGUobnVtOiBiaWdpbnQpOiBzdHJpbmcge1xuICAgICAgY29uc3QgeyBFcnI6IEUgfSA9IERFUjtcbiAgICAgIGlmIChudW0gPCBfMG4pIHRocm93IG5ldyBFKCdpbnRlZ2VyOiBuZWdhdGl2ZSBpbnRlZ2VycyBhcmUgbm90IGFsbG93ZWQnKTtcbiAgICAgIGxldCBoZXggPSBudW1iZXJUb0hleFVucGFkZGVkKG51bSk7XG4gICAgICAvLyBQYWQgd2l0aCB6ZXJvIGJ5dGUgaWYgbmVnYXRpdmUgZmxhZyBpcyBwcmVzZW50XG4gICAgICBpZiAoTnVtYmVyLnBhcnNlSW50KGhleFswXSwgMTYpICYgMGIxMDAwKSBoZXggPSAnMDAnICsgaGV4O1xuICAgICAgaWYgKGhleC5sZW5ndGggJiAxKSB0aHJvdyBuZXcgRSgndW5leHBlY3RlZCBERVIgcGFyc2luZyBhc3NlcnRpb246IHVucGFkZGVkIGhleCcpO1xuICAgICAgcmV0dXJuIGhleDtcbiAgICB9LFxuICAgIGRlY29kZShkYXRhOiBVaW50OEFycmF5KTogYmlnaW50IHtcbiAgICAgIGNvbnN0IHsgRXJyOiBFIH0gPSBERVI7XG4gICAgICBpZiAoZGF0YVswXSAmIDBiMTAwMF8wMDAwKSB0aHJvdyBuZXcgRSgnaW52YWxpZCBzaWduYXR1cmUgaW50ZWdlcjogbmVnYXRpdmUnKTtcbiAgICAgIGlmIChkYXRhWzBdID09PSAweDAwICYmICEoZGF0YVsxXSAmIDBiMTAwMF8wMDAwKSlcbiAgICAgICAgdGhyb3cgbmV3IEUoJ2ludmFsaWQgc2lnbmF0dXJlIGludGVnZXI6IHVubmVjZXNzYXJ5IGxlYWRpbmcgemVybycpO1xuICAgICAgcmV0dXJuIGJ5dGVzVG9OdW1iZXJCRShkYXRhKTtcbiAgICB9LFxuICB9LFxuICB0b1NpZyhieXRlczogVWludDhBcnJheSk6IHsgcjogYmlnaW50OyBzOiBiaWdpbnQgfSB7XG4gICAgLy8gcGFyc2UgREVSIHNpZ25hdHVyZVxuICAgIGNvbnN0IHsgRXJyOiBFLCBfaW50OiBpbnQsIF90bHY6IHRsdiB9ID0gREVSO1xuICAgIGNvbnN0IGRhdGEgPSBhYnl0ZXMoYnl0ZXMsIHVuZGVmaW5lZCwgJ3NpZ25hdHVyZScpO1xuICAgIGNvbnN0IHsgdjogc2VxQnl0ZXMsIGw6IHNlcUxlZnRCeXRlcyB9ID0gdGx2LmRlY29kZSgweDMwLCBkYXRhKTtcbiAgICBpZiAoc2VxTGVmdEJ5dGVzLmxlbmd0aCkgdGhyb3cgbmV3IEUoJ2ludmFsaWQgc2lnbmF0dXJlOiBsZWZ0IGJ5dGVzIGFmdGVyIHBhcnNpbmcnKTtcbiAgICBjb25zdCB7IHY6IHJCeXRlcywgbDogckxlZnRCeXRlcyB9ID0gdGx2LmRlY29kZSgweDAyLCBzZXFCeXRlcyk7XG4gICAgY29uc3QgeyB2OiBzQnl0ZXMsIGw6IHNMZWZ0Qnl0ZXMgfSA9IHRsdi5kZWNvZGUoMHgwMiwgckxlZnRCeXRlcyk7XG4gICAgaWYgKHNMZWZ0Qnl0ZXMubGVuZ3RoKSB0aHJvdyBuZXcgRSgnaW52YWxpZCBzaWduYXR1cmU6IGxlZnQgYnl0ZXMgYWZ0ZXIgcGFyc2luZycpO1xuICAgIHJldHVybiB7IHI6IGludC5kZWNvZGUockJ5dGVzKSwgczogaW50LmRlY29kZShzQnl0ZXMpIH07XG4gIH0sXG4gIGhleEZyb21TaWcoc2lnOiB7IHI6IGJpZ2ludDsgczogYmlnaW50IH0pOiBzdHJpbmcge1xuICAgIGNvbnN0IHsgX3RsdjogdGx2LCBfaW50OiBpbnQgfSA9IERFUjtcbiAgICBjb25zdCBycyA9IHRsdi5lbmNvZGUoMHgwMiwgaW50LmVuY29kZShzaWcucikpO1xuICAgIGNvbnN0IHNzID0gdGx2LmVuY29kZSgweDAyLCBpbnQuZW5jb2RlKHNpZy5zKSk7XG4gICAgY29uc3Qgc2VxID0gcnMgKyBzcztcbiAgICByZXR1cm4gdGx2LmVuY29kZSgweDMwLCBzZXEpO1xuICB9LFxufTtcblxuLy8gQmUgZnJpZW5kbHkgdG8gYmFkIEVDTUFTY3JpcHQgcGFyc2VycyBieSBub3QgdXNpbmcgYmlnaW50IGxpdGVyYWxzXG4vLyBwcmV0dGllci1pZ25vcmVcbmNvbnN0IF8wbiA9IEJpZ0ludCgwKSwgXzFuID0gQmlnSW50KDEpLCBfMm4gPSBCaWdJbnQoMiksIF8zbiA9IEJpZ0ludCgzKSwgXzRuID0gQmlnSW50KDQpO1xuXG4vKipcbiAqIENyZWF0ZXMgd2VpZXJzdHJhc3MgUG9pbnQgY29uc3RydWN0b3IsIGJhc2VkIG9uIHNwZWNpZmllZCBjdXJ2ZSBvcHRpb25zLlxuICpcbiAqIFNlZSB7QGxpbmsgV2VpZXJzdHJhc3NPcHRzfS5cbiAqXG4gKiBAZXhhbXBsZVxuYGBganNcbmNvbnN0IG9wdHMgPSB7XG4gIHA6IDB4ZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmVmZmZmYWM3M24sXG4gIG46IDB4MTAwMDAwMDAwMDAwMDAwMDAwMDAxYjhmYTE2ZGZhYjlhY2ExNmI2YjNuLFxuICBoOiAxbixcbiAgYTogMG4sXG4gIGI6IDduLFxuICBHeDogMHgzYjRjMzgyY2UzN2FhMTkyYTQwMTllNzYzMDM2ZjRmNWRkNGQ3ZWJibixcbiAgR3k6IDB4OTM4Y2Y5MzUzMThmZGNlZDZiYzI4Mjg2NTMxNzMzYzNmMDNjNGZlZW4sXG59O1xuY29uc3Qgc2VjcDE2MGsxX1BvaW50ID0gd2VpZXJzdHJhc3Mob3B0cyk7XG5gYGBcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIHdlaWVyc3RyYXNzPFQ+KFxuICBwYXJhbXM6IFdlaWVyc3RyYXNzT3B0czxUPixcbiAgZXh0cmFPcHRzOiBXZWllcnN0cmFzc0V4dHJhT3B0czxUPiA9IHt9XG4pOiBXZWllcnN0cmFzc1BvaW50Q29uczxUPiB7XG4gIGNvbnN0IHZhbGlkYXRlZCA9IGNyZWF0ZUN1cnZlRmllbGRzKCd3ZWllcnN0cmFzcycsIHBhcmFtcywgZXh0cmFPcHRzKTtcbiAgY29uc3QgeyBGcCwgRm4gfSA9IHZhbGlkYXRlZDtcbiAgbGV0IENVUlZFID0gdmFsaWRhdGVkLkNVUlZFIGFzIFdlaWVyc3RyYXNzT3B0czxUPjtcbiAgY29uc3QgeyBoOiBjb2ZhY3RvciwgbjogQ1VSVkVfT1JERVIgfSA9IENVUlZFO1xuICB2YWxpZGF0ZU9iamVjdChcbiAgICBleHRyYU9wdHMsXG4gICAge30sXG4gICAge1xuICAgICAgYWxsb3dJbmZpbml0eVBvaW50OiAnYm9vbGVhbicsXG4gICAgICBjbGVhckNvZmFjdG9yOiAnZnVuY3Rpb24nLFxuICAgICAgaXNUb3JzaW9uRnJlZTogJ2Z1bmN0aW9uJyxcbiAgICAgIGZyb21CeXRlczogJ2Z1bmN0aW9uJyxcbiAgICAgIHRvQnl0ZXM6ICdmdW5jdGlvbicsXG4gICAgICBlbmRvOiAnb2JqZWN0JyxcbiAgICB9XG4gICk7XG5cbiAgY29uc3QgeyBlbmRvIH0gPSBleHRyYU9wdHM7XG4gIGlmIChlbmRvKSB7XG4gICAgLy8gdmFsaWRhdGVPYmplY3QoZW5kbywgeyBiZXRhOiAnYmlnaW50Jywgc3BsaXRTY2FsYXI6ICdmdW5jdGlvbicgfSk7XG4gICAgaWYgKCFGcC5pczAoQ1VSVkUuYSkgfHwgdHlwZW9mIGVuZG8uYmV0YSAhPT0gJ2JpZ2ludCcgfHwgIUFycmF5LmlzQXJyYXkoZW5kby5iYXNpc2VzKSkge1xuICAgICAgdGhyb3cgbmV3IEVycm9yKCdpbnZhbGlkIGVuZG86IGV4cGVjdGVkIFwiYmV0YVwiOiBiaWdpbnQgYW5kIFwiYmFzaXNlc1wiOiBhcnJheScpO1xuICAgIH1cbiAgfVxuXG4gIGNvbnN0IGxlbmd0aHMgPSBnZXRXTGVuZ3RocyhGcCwgRm4pO1xuXG4gIGZ1bmN0aW9uIGFzc2VydENvbXByZXNzaW9uSXNTdXBwb3J0ZWQoKSB7XG4gICAgaWYgKCFGcC5pc09kZCkgdGhyb3cgbmV3IEVycm9yKCdjb21wcmVzc2lvbiBpcyBub3Qgc3VwcG9ydGVkOiBGaWVsZCBkb2VzIG5vdCBoYXZlIC5pc09kZCgpJyk7XG4gIH1cblxuICAvLyBJbXBsZW1lbnRzIElFRUUgUDEzNjMgcG9pbnQgZW5jb2RpbmdcbiAgZnVuY3Rpb24gcG9pbnRUb0J5dGVzKFxuICAgIF9jOiBXZWllcnN0cmFzc1BvaW50Q29uczxUPixcbiAgICBwb2ludDogV2VpZXJzdHJhc3NQb2ludDxUPixcbiAgICBpc0NvbXByZXNzZWQ6IGJvb2xlYW5cbiAgKTogVWludDhBcnJheSB7XG4gICAgY29uc3QgeyB4LCB5IH0gPSBwb2ludC50b0FmZmluZSgpO1xuICAgIGNvbnN0IGJ4ID0gRnAudG9CeXRlcyh4KTtcbiAgICBhYm9vbChpc0NvbXByZXNzZWQsICdpc0NvbXByZXNzZWQnKTtcbiAgICBpZiAoaXNDb21wcmVzc2VkKSB7XG4gICAgICBhc3NlcnRDb21wcmVzc2lvbklzU3VwcG9ydGVkKCk7XG4gICAgICBjb25zdCBoYXNFdmVuWSA9ICFGcC5pc09kZCEoeSk7XG4gICAgICByZXR1cm4gY29uY2F0Qnl0ZXMocHByZWZpeChoYXNFdmVuWSksIGJ4KTtcbiAgICB9IGVsc2Uge1xuICAgICAgcmV0dXJuIGNvbmNhdEJ5dGVzKFVpbnQ4QXJyYXkub2YoMHgwNCksIGJ4LCBGcC50b0J5dGVzKHkpKTtcbiAgICB9XG4gIH1cbiAgZnVuY3Rpb24gcG9pbnRGcm9tQnl0ZXMoYnl0ZXM6IFVpbnQ4QXJyYXkpIHtcbiAgICBhYnl0ZXMoYnl0ZXMsIHVuZGVmaW5lZCwgJ1BvaW50Jyk7XG4gICAgY29uc3QgeyBwdWJsaWNLZXk6IGNvbXAsIHB1YmxpY0tleVVuY29tcHJlc3NlZDogdW5jb21wIH0gPSBsZW5ndGhzOyAvLyBlLmcuIGZvciAzMi1ieXRlOiAzMywgNjVcbiAgICBjb25zdCBsZW5ndGggPSBieXRlcy5sZW5ndGg7XG4gICAgY29uc3QgaGVhZCA9IGJ5dGVzWzBdO1xuICAgIGNvbnN0IHRhaWwgPSBieXRlcy5zdWJhcnJheSgxKTtcbiAgICAvLyBObyBhY3R1YWwgdmFsaWRhdGlvbiBpcyBkb25lIGhlcmU6IHVzZSAuYXNzZXJ0VmFsaWRpdHkoKVxuICAgIGlmIChsZW5ndGggPT09IGNvbXAgJiYgKGhlYWQgPT09IDB4MDIgfHwgaGVhZCA9PT0gMHgwMykpIHtcbiAgICAgIGNvbnN0IHggPSBGcC5mcm9tQnl0ZXModGFpbCk7XG4gICAgICBpZiAoIUZwLmlzVmFsaWQoeCkpIHRocm93IG5ldyBFcnJvcignYmFkIHBvaW50OiBpcyBub3Qgb24gY3VydmUsIHdyb25nIHgnKTtcbiAgICAgIGNvbnN0IHkyID0gd2VpZXJzdHJhc3NFcXVhdGlvbih4KTsgLy8geVx1MDBCMiA9IHhcdTAwQjMgKyBheCArIGJcbiAgICAgIGxldCB5OiBUO1xuICAgICAgdHJ5IHtcbiAgICAgICAgeSA9IEZwLnNxcnQoeTIpOyAvLyB5ID0geVx1MDBCMiBeIChwKzEpLzRcbiAgICAgIH0gY2F0Y2ggKHNxcnRFcnJvcikge1xuICAgICAgICBjb25zdCBlcnIgPSBzcXJ0RXJyb3IgaW5zdGFuY2VvZiBFcnJvciA/ICc6ICcgKyBzcXJ0RXJyb3IubWVzc2FnZSA6ICcnO1xuICAgICAgICB0aHJvdyBuZXcgRXJyb3IoJ2JhZCBwb2ludDogaXMgbm90IG9uIGN1cnZlLCBzcXJ0IGVycm9yJyArIGVycik7XG4gICAgICB9XG4gICAgICBhc3NlcnRDb21wcmVzc2lvbklzU3VwcG9ydGVkKCk7XG4gICAgICBjb25zdCBldmVuWSA9IEZwLmlzT2RkISh5KTtcbiAgICAgIGNvbnN0IGV2ZW5IID0gKGhlYWQgJiAxKSA9PT0gMTsgLy8gRUNEU0Etc3BlY2lmaWNcbiAgICAgIGlmIChldmVuSCAhPT0gZXZlblkpIHkgPSBGcC5uZWcoeSk7XG4gICAgICByZXR1cm4geyB4LCB5IH07XG4gICAgfSBlbHNlIGlmIChsZW5ndGggPT09IHVuY29tcCAmJiBoZWFkID09PSAweDA0KSB7XG4gICAgICAvLyBUT0RPOiBtb3JlIGNoZWNrc1xuICAgICAgY29uc3QgTCA9IEZwLkJZVEVTO1xuICAgICAgY29uc3QgeCA9IEZwLmZyb21CeXRlcyh0YWlsLnN1YmFycmF5KDAsIEwpKTtcbiAgICAgIGNvbnN0IHkgPSBGcC5mcm9tQnl0ZXModGFpbC5zdWJhcnJheShMLCBMICogMikpO1xuICAgICAgaWYgKCFpc1ZhbGlkWFkoeCwgeSkpIHRocm93IG5ldyBFcnJvcignYmFkIHBvaW50OiBpcyBub3Qgb24gY3VydmUnKTtcbiAgICAgIHJldHVybiB7IHgsIHkgfTtcbiAgICB9IGVsc2Uge1xuICAgICAgdGhyb3cgbmV3IEVycm9yKFxuICAgICAgICBgYmFkIHBvaW50OiBnb3QgbGVuZ3RoICR7bGVuZ3RofSwgZXhwZWN0ZWQgY29tcHJlc3NlZD0ke2NvbXB9IG9yIHVuY29tcHJlc3NlZD0ke3VuY29tcH1gXG4gICAgICApO1xuICAgIH1cbiAgfVxuXG4gIGNvbnN0IGVuY29kZVBvaW50ID0gZXh0cmFPcHRzLnRvQnl0ZXMgfHwgcG9pbnRUb0J5dGVzO1xuICBjb25zdCBkZWNvZGVQb2ludCA9IGV4dHJhT3B0cy5mcm9tQnl0ZXMgfHwgcG9pbnRGcm9tQnl0ZXM7XG4gIGZ1bmN0aW9uIHdlaWVyc3RyYXNzRXF1YXRpb24oeDogVCk6IFQge1xuICAgIGNvbnN0IHgyID0gRnAuc3FyKHgpOyAvLyB4ICogeFxuICAgIGNvbnN0IHgzID0gRnAubXVsKHgyLCB4KTsgLy8geFx1MDBCMiAqIHhcbiAgICByZXR1cm4gRnAuYWRkKEZwLmFkZCh4MywgRnAubXVsKHgsIENVUlZFLmEpKSwgQ1VSVkUuYik7IC8vIHhcdTAwQjMgKyBhICogeCArIGJcbiAgfVxuXG4gIC8vIFRPRE86IG1vdmUgdG9wLWxldmVsXG4gIC8qKiBDaGVja3Mgd2hldGhlciBlcXVhdGlvbiBob2xkcyBmb3IgZ2l2ZW4geCwgeTogeVx1MDBCMiA9PSB4XHUwMEIzICsgYXggKyBiICovXG4gIGZ1bmN0aW9uIGlzVmFsaWRYWSh4OiBULCB5OiBUKTogYm9vbGVhbiB7XG4gICAgY29uc3QgbGVmdCA9IEZwLnNxcih5KTsgLy8geVx1MDBCMlxuICAgIGNvbnN0IHJpZ2h0ID0gd2VpZXJzdHJhc3NFcXVhdGlvbih4KTsgLy8geFx1MDBCMyArIGF4ICsgYlxuICAgIHJldHVybiBGcC5lcWwobGVmdCwgcmlnaHQpO1xuICB9XG5cbiAgLy8gVmFsaWRhdGUgd2hldGhlciB0aGUgcGFzc2VkIGN1cnZlIHBhcmFtcyBhcmUgdmFsaWQuXG4gIC8vIFRlc3QgMTogZXF1YXRpb24geVx1MDBCMiA9IHhcdTAwQjMgKyBheCArIGIgc2hvdWxkIHdvcmsgZm9yIGdlbmVyYXRvciBwb2ludC5cbiAgaWYgKCFpc1ZhbGlkWFkoQ1VSVkUuR3gsIENVUlZFLkd5KSkgdGhyb3cgbmV3IEVycm9yKCdiYWQgY3VydmUgcGFyYW1zOiBnZW5lcmF0b3IgcG9pbnQnKTtcblxuICAvLyBUZXN0IDI6IGRpc2NyaW1pbmFudCBcdTAzOTQgcGFydCBzaG91bGQgYmUgbm9uLXplcm86IDRhXHUwMEIzICsgMjdiXHUwMEIyICE9IDAuXG4gIC8vIEd1YXJhbnRlZXMgY3VydmUgaXMgZ2VudXMtMSwgc21vb3RoIChub24tc2luZ3VsYXIpLlxuICBjb25zdCBfNGEzID0gRnAubXVsKEZwLnBvdyhDVVJWRS5hLCBfM24pLCBfNG4pO1xuICBjb25zdCBfMjdiMiA9IEZwLm11bChGcC5zcXIoQ1VSVkUuYiksIEJpZ0ludCgyNykpO1xuICBpZiAoRnAuaXMwKEZwLmFkZChfNGEzLCBfMjdiMikpKSB0aHJvdyBuZXcgRXJyb3IoJ2JhZCBjdXJ2ZSBwYXJhbXM6IGEgb3IgYicpO1xuXG4gIC8qKiBBc3NlcnRzIGNvb3JkaW5hdGUgaXMgdmFsaWQ6IDAgPD0gbiA8IEZwLk9SREVSLiAqL1xuICBmdW5jdGlvbiBhY29vcmQodGl0bGU6IHN0cmluZywgbjogVCwgYmFuWmVybyA9IGZhbHNlKSB7XG4gICAgaWYgKCFGcC5pc1ZhbGlkKG4pIHx8IChiYW5aZXJvICYmIEZwLmlzMChuKSkpIHRocm93IG5ldyBFcnJvcihgYmFkIHBvaW50IGNvb3JkaW5hdGUgJHt0aXRsZX1gKTtcbiAgICByZXR1cm4gbjtcbiAgfVxuXG4gIGZ1bmN0aW9uIGFwcmpwb2ludChvdGhlcjogdW5rbm93bikge1xuICAgIGlmICghKG90aGVyIGluc3RhbmNlb2YgUG9pbnQpKSB0aHJvdyBuZXcgRXJyb3IoJ1dlaWVyc3RyYXNzIFBvaW50IGV4cGVjdGVkJyk7XG4gIH1cblxuICBmdW5jdGlvbiBzcGxpdEVuZG9TY2FsYXJOKGs6IGJpZ2ludCkge1xuICAgIGlmICghZW5kbyB8fCAhZW5kby5iYXNpc2VzKSB0aHJvdyBuZXcgRXJyb3IoJ25vIGVuZG8nKTtcbiAgICByZXR1cm4gX3NwbGl0RW5kb1NjYWxhcihrLCBlbmRvLmJhc2lzZXMsIEZuLk9SREVSKTtcbiAgfVxuXG4gIC8vIE1lbW9pemVkIHRvQWZmaW5lIC8gdmFsaWRpdHkgY2hlY2suIFRoZXkgYXJlIGhlYXZ5LiBQb2ludHMgYXJlIGltbXV0YWJsZS5cblxuICAvLyBDb252ZXJ0cyBQcm9qZWN0aXZlIHBvaW50IHRvIGFmZmluZSAoeCwgeSkgY29vcmRpbmF0ZXMuXG4gIC8vIENhbiBhY2NlcHQgcHJlY29tcHV0ZWQgWl4tMSAtIGZvciBleGFtcGxlLCBmcm9tIGludmVydEJhdGNoLlxuICAvLyAoWCwgWSwgWikgXHUyMjBCICh4PVgvWiwgeT1ZL1opXG4gIGNvbnN0IHRvQWZmaW5lTWVtbyA9IG1lbW9pemVkKChwOiBQb2ludCwgaXo/OiBUKTogQWZmaW5lUG9pbnQ8VD4gPT4ge1xuICAgIGNvbnN0IHsgWCwgWSwgWiB9ID0gcDtcbiAgICAvLyBGYXN0LXBhdGggZm9yIG5vcm1hbGl6ZWQgcG9pbnRzXG4gICAgaWYgKEZwLmVxbChaLCBGcC5PTkUpKSByZXR1cm4geyB4OiBYLCB5OiBZIH07XG4gICAgY29uc3QgaXMwID0gcC5pczAoKTtcbiAgICAvLyBJZiBpbnZaIHdhcyAwLCB3ZSByZXR1cm4gemVybyBwb2ludC4gSG93ZXZlciB3ZSBzdGlsbCB3YW50IHRvIGV4ZWN1dGVcbiAgICAvLyBhbGwgb3BlcmF0aW9ucywgc28gd2UgcmVwbGFjZSBpbnZaIHdpdGggYSByYW5kb20gbnVtYmVyLCAxLlxuICAgIGlmIChpeiA9PSBudWxsKSBpeiA9IGlzMCA/IEZwLk9ORSA6IEZwLmludihaKTtcbiAgICBjb25zdCB4ID0gRnAubXVsKFgsIGl6KTtcbiAgICBjb25zdCB5ID0gRnAubXVsKFksIGl6KTtcbiAgICBjb25zdCB6eiA9IEZwLm11bChaLCBpeik7XG4gICAgaWYgKGlzMCkgcmV0dXJuIHsgeDogRnAuWkVSTywgeTogRnAuWkVSTyB9O1xuICAgIGlmICghRnAuZXFsKHp6LCBGcC5PTkUpKSB0aHJvdyBuZXcgRXJyb3IoJ2ludlogd2FzIGludmFsaWQnKTtcbiAgICByZXR1cm4geyB4LCB5IH07XG4gIH0pO1xuICAvLyBOT1RFOiBvbiBleGNlcHRpb24gdGhpcyB3aWxsIGNyYXNoICdjYWNoZWQnIGFuZCBubyB2YWx1ZSB3aWxsIGJlIHNldC5cbiAgLy8gT3RoZXJ3aXNlIHRydWUgd2lsbCBiZSByZXR1cm5cbiAgY29uc3QgYXNzZXJ0VmFsaWRNZW1vID0gbWVtb2l6ZWQoKHA6IFBvaW50KSA9PiB7XG4gICAgaWYgKHAuaXMwKCkpIHtcbiAgICAgIC8vICgwLCAxLCAwKSBha2EgWkVSTyBpcyBpbnZhbGlkIGluIG1vc3QgY29udGV4dHMuXG4gICAgICAvLyBJbiBCTFMsIFpFUk8gY2FuIGJlIHNlcmlhbGl6ZWQsIHNvIHdlIGFsbG93IGl0LlxuICAgICAgLy8gKDAsIDAsIDApIGlzIGludmFsaWQgcmVwcmVzZW50YXRpb24gb2YgWkVSTy5cbiAgICAgIGlmIChleHRyYU9wdHMuYWxsb3dJbmZpbml0eVBvaW50ICYmICFGcC5pczAocC5ZKSkgcmV0dXJuO1xuICAgICAgdGhyb3cgbmV3IEVycm9yKCdiYWQgcG9pbnQ6IFpFUk8nKTtcbiAgICB9XG4gICAgLy8gU29tZSAzcmQtcGFydHkgdGVzdCB2ZWN0b3JzIHJlcXVpcmUgZGlmZmVyZW50IHdvcmRpbmcgYmV0d2VlbiBoZXJlICYgYGZyb21Db21wcmVzc2VkSGV4YFxuICAgIGNvbnN0IHsgeCwgeSB9ID0gcC50b0FmZmluZSgpO1xuICAgIGlmICghRnAuaXNWYWxpZCh4KSB8fCAhRnAuaXNWYWxpZCh5KSkgdGhyb3cgbmV3IEVycm9yKCdiYWQgcG9pbnQ6IHggb3IgeSBub3QgZmllbGQgZWxlbWVudHMnKTtcbiAgICBpZiAoIWlzVmFsaWRYWSh4LCB5KSkgdGhyb3cgbmV3IEVycm9yKCdiYWQgcG9pbnQ6IGVxdWF0aW9uIGxlZnQgIT0gcmlnaHQnKTtcbiAgICBpZiAoIXAuaXNUb3JzaW9uRnJlZSgpKSB0aHJvdyBuZXcgRXJyb3IoJ2JhZCBwb2ludDogbm90IGluIHByaW1lLW9yZGVyIHN1Ymdyb3VwJyk7XG4gICAgcmV0dXJuIHRydWU7XG4gIH0pO1xuXG4gIGZ1bmN0aW9uIGZpbmlzaEVuZG8oXG4gICAgZW5kb0JldGE6IEVuZG9tb3JwaGlzbU9wdHNbJ2JldGEnXSxcbiAgICBrMXA6IFBvaW50LFxuICAgIGsycDogUG9pbnQsXG4gICAgazFuZWc6IGJvb2xlYW4sXG4gICAgazJuZWc6IGJvb2xlYW5cbiAgKSB7XG4gICAgazJwID0gbmV3IFBvaW50KEZwLm11bChrMnAuWCwgZW5kb0JldGEpLCBrMnAuWSwgazJwLlopO1xuICAgIGsxcCA9IG5lZ2F0ZUN0KGsxbmVnLCBrMXApO1xuICAgIGsycCA9IG5lZ2F0ZUN0KGsybmVnLCBrMnApO1xuICAgIHJldHVybiBrMXAuYWRkKGsycCk7XG4gIH1cblxuICAvKipcbiAgICogUHJvamVjdGl2ZSBQb2ludCB3b3JrcyBpbiAzZCAvIHByb2plY3RpdmUgKGhvbW9nZW5lb3VzKSBjb29yZGluYXRlczooWCwgWSwgWikgXHUyMjBCICh4PVgvWiwgeT1ZL1opLlxuICAgKiBEZWZhdWx0IFBvaW50IHdvcmtzIGluIDJkIC8gYWZmaW5lIGNvb3JkaW5hdGVzOiAoeCwgeSkuXG4gICAqIFdlJ3JlIGRvaW5nIGNhbGN1bGF0aW9ucyBpbiBwcm9qZWN0aXZlLCBiZWNhdXNlIGl0cyBvcGVyYXRpb25zIGRvbid0IHJlcXVpcmUgY29zdGx5IGludmVyc2lvbi5cbiAgICovXG4gIGNsYXNzIFBvaW50IGltcGxlbWVudHMgV2VpZXJzdHJhc3NQb2ludDxUPiB7XG4gICAgLy8gYmFzZSAvIGdlbmVyYXRvciBwb2ludFxuICAgIHN0YXRpYyByZWFkb25seSBCQVNFID0gbmV3IFBvaW50KENVUlZFLkd4LCBDVVJWRS5HeSwgRnAuT05FKTtcbiAgICAvLyB6ZXJvIC8gaW5maW5pdHkgLyBpZGVudGl0eSBwb2ludFxuICAgIHN0YXRpYyByZWFkb25seSBaRVJPID0gbmV3IFBvaW50KEZwLlpFUk8sIEZwLk9ORSwgRnAuWkVSTyk7IC8vIDAsIDEsIDBcbiAgICAvLyBtYXRoIGZpZWxkXG4gICAgc3RhdGljIHJlYWRvbmx5IEZwID0gRnA7XG4gICAgLy8gc2NhbGFyIGZpZWxkXG4gICAgc3RhdGljIHJlYWRvbmx5IEZuID0gRm47XG5cbiAgICByZWFkb25seSBYOiBUO1xuICAgIHJlYWRvbmx5IFk6IFQ7XG4gICAgcmVhZG9ubHkgWjogVDtcblxuICAgIC8qKiBEb2VzIE5PVCB2YWxpZGF0ZSBpZiB0aGUgcG9pbnQgaXMgdmFsaWQuIFVzZSBgLmFzc2VydFZhbGlkaXR5KClgLiAqL1xuICAgIGNvbnN0cnVjdG9yKFg6IFQsIFk6IFQsIFo6IFQpIHtcbiAgICAgIHRoaXMuWCA9IGFjb29yZCgneCcsIFgpO1xuICAgICAgdGhpcy5ZID0gYWNvb3JkKCd5JywgWSwgdHJ1ZSk7XG4gICAgICB0aGlzLlogPSBhY29vcmQoJ3onLCBaKTtcbiAgICAgIE9iamVjdC5mcmVlemUodGhpcyk7XG4gICAgfVxuXG4gICAgc3RhdGljIENVUlZFKCk6IFdlaWVyc3RyYXNzT3B0czxUPiB7XG4gICAgICByZXR1cm4gQ1VSVkU7XG4gICAgfVxuXG4gICAgLyoqIERvZXMgTk9UIHZhbGlkYXRlIGlmIHRoZSBwb2ludCBpcyB2YWxpZC4gVXNlIGAuYXNzZXJ0VmFsaWRpdHkoKWAuICovXG4gICAgc3RhdGljIGZyb21BZmZpbmUocDogQWZmaW5lUG9pbnQ8VD4pOiBQb2ludCB7XG4gICAgICBjb25zdCB7IHgsIHkgfSA9IHAgfHwge307XG4gICAgICBpZiAoIXAgfHwgIUZwLmlzVmFsaWQoeCkgfHwgIUZwLmlzVmFsaWQoeSkpIHRocm93IG5ldyBFcnJvcignaW52YWxpZCBhZmZpbmUgcG9pbnQnKTtcbiAgICAgIGlmIChwIGluc3RhbmNlb2YgUG9pbnQpIHRocm93IG5ldyBFcnJvcigncHJvamVjdGl2ZSBwb2ludCBub3QgYWxsb3dlZCcpO1xuICAgICAgLy8gKDAsIDApIHdvdWxkJ3ZlIHByb2R1Y2VkICgwLCAwLCAxKSAtIGluc3RlYWQsIHdlIG5lZWQgKDAsIDEsIDApXG4gICAgICBpZiAoRnAuaXMwKHgpICYmIEZwLmlzMCh5KSkgcmV0dXJuIFBvaW50LlpFUk87XG4gICAgICByZXR1cm4gbmV3IFBvaW50KHgsIHksIEZwLk9ORSk7XG4gICAgfVxuXG4gICAgc3RhdGljIGZyb21CeXRlcyhieXRlczogVWludDhBcnJheSk6IFBvaW50IHtcbiAgICAgIGNvbnN0IFAgPSBQb2ludC5mcm9tQWZmaW5lKGRlY29kZVBvaW50KGFieXRlcyhieXRlcywgdW5kZWZpbmVkLCAncG9pbnQnKSkpO1xuICAgICAgUC5hc3NlcnRWYWxpZGl0eSgpO1xuICAgICAgcmV0dXJuIFA7XG4gICAgfVxuXG4gICAgc3RhdGljIGZyb21IZXgoaGV4OiBzdHJpbmcpOiBQb2ludCB7XG4gICAgICByZXR1cm4gUG9pbnQuZnJvbUJ5dGVzKGhleFRvQnl0ZXMoaGV4KSk7XG4gICAgfVxuXG4gICAgZ2V0IHgoKTogVCB7XG4gICAgICByZXR1cm4gdGhpcy50b0FmZmluZSgpLng7XG4gICAgfVxuICAgIGdldCB5KCk6IFQge1xuICAgICAgcmV0dXJuIHRoaXMudG9BZmZpbmUoKS55O1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqXG4gICAgICogQHBhcmFtIHdpbmRvd1NpemVcbiAgICAgKiBAcGFyYW0gaXNMYXp5IHRydWUgd2lsbCBkZWZlciB0YWJsZSBjb21wdXRhdGlvbiB1bnRpbCB0aGUgZmlyc3QgbXVsdGlwbGljYXRpb25cbiAgICAgKiBAcmV0dXJuc1xuICAgICAqL1xuICAgIHByZWNvbXB1dGUod2luZG93U2l6ZTogbnVtYmVyID0gOCwgaXNMYXp5ID0gdHJ1ZSk6IFBvaW50IHtcbiAgICAgIHduYWYuY3JlYXRlQ2FjaGUodGhpcywgd2luZG93U2l6ZSk7XG4gICAgICBpZiAoIWlzTGF6eSkgdGhpcy5tdWx0aXBseShfM24pOyAvLyByYW5kb20gbnVtYmVyXG4gICAgICByZXR1cm4gdGhpcztcbiAgICB9XG5cbiAgICAvLyBUT0RPOiByZXR1cm4gYHRoaXNgXG4gICAgLyoqIEEgcG9pbnQgb24gY3VydmUgaXMgdmFsaWQgaWYgaXQgY29uZm9ybXMgdG8gZXF1YXRpb24uICovXG4gICAgYXNzZXJ0VmFsaWRpdHkoKTogdm9pZCB7XG4gICAgICBhc3NlcnRWYWxpZE1lbW8odGhpcyk7XG4gICAgfVxuXG4gICAgaGFzRXZlblkoKTogYm9vbGVhbiB7XG4gICAgICBjb25zdCB7IHkgfSA9IHRoaXMudG9BZmZpbmUoKTtcbiAgICAgIGlmICghRnAuaXNPZGQpIHRocm93IG5ldyBFcnJvcihcIkZpZWxkIGRvZXNuJ3Qgc3VwcG9ydCBpc09kZFwiKTtcbiAgICAgIHJldHVybiAhRnAuaXNPZGQoeSk7XG4gICAgfVxuXG4gICAgLyoqIENvbXBhcmUgb25lIHBvaW50IHRvIGFub3RoZXIuICovXG4gICAgZXF1YWxzKG90aGVyOiBQb2ludCk6IGJvb2xlYW4ge1xuICAgICAgYXByanBvaW50KG90aGVyKTtcbiAgICAgIGNvbnN0IHsgWDogWDEsIFk6IFkxLCBaOiBaMSB9ID0gdGhpcztcbiAgICAgIGNvbnN0IHsgWDogWDIsIFk6IFkyLCBaOiBaMiB9ID0gb3RoZXI7XG4gICAgICBjb25zdCBVMSA9IEZwLmVxbChGcC5tdWwoWDEsIFoyKSwgRnAubXVsKFgyLCBaMSkpO1xuICAgICAgY29uc3QgVTIgPSBGcC5lcWwoRnAubXVsKFkxLCBaMiksIEZwLm11bChZMiwgWjEpKTtcbiAgICAgIHJldHVybiBVMSAmJiBVMjtcbiAgICB9XG5cbiAgICAvKiogRmxpcHMgcG9pbnQgdG8gb25lIGNvcnJlc3BvbmRpbmcgdG8gKHgsIC15KSBpbiBBZmZpbmUgY29vcmRpbmF0ZXMuICovXG4gICAgbmVnYXRlKCk6IFBvaW50IHtcbiAgICAgIHJldHVybiBuZXcgUG9pbnQodGhpcy5YLCBGcC5uZWcodGhpcy5ZKSwgdGhpcy5aKTtcbiAgICB9XG5cbiAgICAvLyBSZW5lcy1Db3N0ZWxsby1CYXRpbmEgZXhjZXB0aW9uLWZyZWUgZG91YmxpbmcgZm9ybXVsYS5cbiAgICAvLyBUaGVyZSBpcyAzMCUgZmFzdGVyIEphY29iaWFuIGZvcm11bGEsIGJ1dCBpdCBpcyBub3QgY29tcGxldGUuXG4gICAgLy8gaHR0cHM6Ly9lcHJpbnQuaWFjci5vcmcvMjAxNS8xMDYwLCBhbGdvcml0aG0gM1xuICAgIC8vIENvc3Q6IDhNICsgM1MgKyAzKmEgKyAyKmIzICsgMTVhZGQuXG4gICAgZG91YmxlKCkge1xuICAgICAgY29uc3QgeyBhLCBiIH0gPSBDVVJWRTtcbiAgICAgIGNvbnN0IGIzID0gRnAubXVsKGIsIF8zbik7XG4gICAgICBjb25zdCB7IFg6IFgxLCBZOiBZMSwgWjogWjEgfSA9IHRoaXM7XG4gICAgICBsZXQgWDMgPSBGcC5aRVJPLCBZMyA9IEZwLlpFUk8sIFozID0gRnAuWkVSTzsgLy8gcHJldHRpZXItaWdub3JlXG4gICAgICBsZXQgdDAgPSBGcC5tdWwoWDEsIFgxKTsgLy8gc3RlcCAxXG4gICAgICBsZXQgdDEgPSBGcC5tdWwoWTEsIFkxKTtcbiAgICAgIGxldCB0MiA9IEZwLm11bChaMSwgWjEpO1xuICAgICAgbGV0IHQzID0gRnAubXVsKFgxLCBZMSk7XG4gICAgICB0MyA9IEZwLmFkZCh0MywgdDMpOyAvLyBzdGVwIDVcbiAgICAgIFozID0gRnAubXVsKFgxLCBaMSk7XG4gICAgICBaMyA9IEZwLmFkZChaMywgWjMpO1xuICAgICAgWDMgPSBGcC5tdWwoYSwgWjMpO1xuICAgICAgWTMgPSBGcC5tdWwoYjMsIHQyKTtcbiAgICAgIFkzID0gRnAuYWRkKFgzLCBZMyk7IC8vIHN0ZXAgMTBcbiAgICAgIFgzID0gRnAuc3ViKHQxLCBZMyk7XG4gICAgICBZMyA9IEZwLmFkZCh0MSwgWTMpO1xuICAgICAgWTMgPSBGcC5tdWwoWDMsIFkzKTtcbiAgICAgIFgzID0gRnAubXVsKHQzLCBYMyk7XG4gICAgICBaMyA9IEZwLm11bChiMywgWjMpOyAvLyBzdGVwIDE1XG4gICAgICB0MiA9IEZwLm11bChhLCB0Mik7XG4gICAgICB0MyA9IEZwLnN1Yih0MCwgdDIpO1xuICAgICAgdDMgPSBGcC5tdWwoYSwgdDMpO1xuICAgICAgdDMgPSBGcC5hZGQodDMsIFozKTtcbiAgICAgIFozID0gRnAuYWRkKHQwLCB0MCk7IC8vIHN0ZXAgMjBcbiAgICAgIHQwID0gRnAuYWRkKFozLCB0MCk7XG4gICAgICB0MCA9IEZwLmFkZCh0MCwgdDIpO1xuICAgICAgdDAgPSBGcC5tdWwodDAsIHQzKTtcbiAgICAgIFkzID0gRnAuYWRkKFkzLCB0MCk7XG4gICAgICB0MiA9IEZwLm11bChZMSwgWjEpOyAvLyBzdGVwIDI1XG4gICAgICB0MiA9IEZwLmFkZCh0MiwgdDIpO1xuICAgICAgdDAgPSBGcC5tdWwodDIsIHQzKTtcbiAgICAgIFgzID0gRnAuc3ViKFgzLCB0MCk7XG4gICAgICBaMyA9IEZwLm11bCh0MiwgdDEpO1xuICAgICAgWjMgPSBGcC5hZGQoWjMsIFozKTsgLy8gc3RlcCAzMFxuICAgICAgWjMgPSBGcC5hZGQoWjMsIFozKTtcbiAgICAgIHJldHVybiBuZXcgUG9pbnQoWDMsIFkzLCBaMyk7XG4gICAgfVxuXG4gICAgLy8gUmVuZXMtQ29zdGVsbG8tQmF0aW5hIGV4Y2VwdGlvbi1mcmVlIGFkZGl0aW9uIGZvcm11bGEuXG4gICAgLy8gVGhlcmUgaXMgMzAlIGZhc3RlciBKYWNvYmlhbiBmb3JtdWxhLCBidXQgaXQgaXMgbm90IGNvbXBsZXRlLlxuICAgIC8vIGh0dHBzOi8vZXByaW50LmlhY3Iub3JnLzIwMTUvMTA2MCwgYWxnb3JpdGhtIDFcbiAgICAvLyBDb3N0OiAxMk0gKyAwUyArIDMqYSArIDMqYjMgKyAyM2FkZC5cbiAgICBhZGQob3RoZXI6IFBvaW50KTogUG9pbnQge1xuICAgICAgYXByanBvaW50KG90aGVyKTtcbiAgICAgIGNvbnN0IHsgWDogWDEsIFk6IFkxLCBaOiBaMSB9ID0gdGhpcztcbiAgICAgIGNvbnN0IHsgWDogWDIsIFk6IFkyLCBaOiBaMiB9ID0gb3RoZXI7XG4gICAgICBsZXQgWDMgPSBGcC5aRVJPLCBZMyA9IEZwLlpFUk8sIFozID0gRnAuWkVSTzsgLy8gcHJldHRpZXItaWdub3JlXG4gICAgICBjb25zdCBhID0gQ1VSVkUuYTtcbiAgICAgIGNvbnN0IGIzID0gRnAubXVsKENVUlZFLmIsIF8zbik7XG4gICAgICBsZXQgdDAgPSBGcC5tdWwoWDEsIFgyKTsgLy8gc3RlcCAxXG4gICAgICBsZXQgdDEgPSBGcC5tdWwoWTEsIFkyKTtcbiAgICAgIGxldCB0MiA9IEZwLm11bChaMSwgWjIpO1xuICAgICAgbGV0IHQzID0gRnAuYWRkKFgxLCBZMSk7XG4gICAgICBsZXQgdDQgPSBGcC5hZGQoWDIsIFkyKTsgLy8gc3RlcCA1XG4gICAgICB0MyA9IEZwLm11bCh0MywgdDQpO1xuICAgICAgdDQgPSBGcC5hZGQodDAsIHQxKTtcbiAgICAgIHQzID0gRnAuc3ViKHQzLCB0NCk7XG4gICAgICB0NCA9IEZwLmFkZChYMSwgWjEpO1xuICAgICAgbGV0IHQ1ID0gRnAuYWRkKFgyLCBaMik7IC8vIHN0ZXAgMTBcbiAgICAgIHQ0ID0gRnAubXVsKHQ0LCB0NSk7XG4gICAgICB0NSA9IEZwLmFkZCh0MCwgdDIpO1xuICAgICAgdDQgPSBGcC5zdWIodDQsIHQ1KTtcbiAgICAgIHQ1ID0gRnAuYWRkKFkxLCBaMSk7XG4gICAgICBYMyA9IEZwLmFkZChZMiwgWjIpOyAvLyBzdGVwIDE1XG4gICAgICB0NSA9IEZwLm11bCh0NSwgWDMpO1xuICAgICAgWDMgPSBGcC5hZGQodDEsIHQyKTtcbiAgICAgIHQ1ID0gRnAuc3ViKHQ1LCBYMyk7XG4gICAgICBaMyA9IEZwLm11bChhLCB0NCk7XG4gICAgICBYMyA9IEZwLm11bChiMywgdDIpOyAvLyBzdGVwIDIwXG4gICAgICBaMyA9IEZwLmFkZChYMywgWjMpO1xuICAgICAgWDMgPSBGcC5zdWIodDEsIFozKTtcbiAgICAgIFozID0gRnAuYWRkKHQxLCBaMyk7XG4gICAgICBZMyA9IEZwLm11bChYMywgWjMpO1xuICAgICAgdDEgPSBGcC5hZGQodDAsIHQwKTsgLy8gc3RlcCAyNVxuICAgICAgdDEgPSBGcC5hZGQodDEsIHQwKTtcbiAgICAgIHQyID0gRnAubXVsKGEsIHQyKTtcbiAgICAgIHQ0ID0gRnAubXVsKGIzLCB0NCk7XG4gICAgICB0MSA9IEZwLmFkZCh0MSwgdDIpO1xuICAgICAgdDIgPSBGcC5zdWIodDAsIHQyKTsgLy8gc3RlcCAzMFxuICAgICAgdDIgPSBGcC5tdWwoYSwgdDIpO1xuICAgICAgdDQgPSBGcC5hZGQodDQsIHQyKTtcbiAgICAgIHQwID0gRnAubXVsKHQxLCB0NCk7XG4gICAgICBZMyA9IEZwLmFkZChZMywgdDApO1xuICAgICAgdDAgPSBGcC5tdWwodDUsIHQ0KTsgLy8gc3RlcCAzNVxuICAgICAgWDMgPSBGcC5tdWwodDMsIFgzKTtcbiAgICAgIFgzID0gRnAuc3ViKFgzLCB0MCk7XG4gICAgICB0MCA9IEZwLm11bCh0MywgdDEpO1xuICAgICAgWjMgPSBGcC5tdWwodDUsIFozKTtcbiAgICAgIFozID0gRnAuYWRkKFozLCB0MCk7IC8vIHN0ZXAgNDBcbiAgICAgIHJldHVybiBuZXcgUG9pbnQoWDMsIFkzLCBaMyk7XG4gICAgfVxuXG4gICAgc3VidHJhY3Qob3RoZXI6IFBvaW50KSB7XG4gICAgICByZXR1cm4gdGhpcy5hZGQob3RoZXIubmVnYXRlKCkpO1xuICAgIH1cblxuICAgIGlzMCgpOiBib29sZWFuIHtcbiAgICAgIHJldHVybiB0aGlzLmVxdWFscyhQb2ludC5aRVJPKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBDb25zdGFudCB0aW1lIG11bHRpcGxpY2F0aW9uLlxuICAgICAqIFVzZXMgd05BRiBtZXRob2QuIFdpbmRvd2VkIG1ldGhvZCBtYXkgYmUgMTAlIGZhc3RlcixcbiAgICAgKiBidXQgdGFrZXMgMnggbG9uZ2VyIHRvIGdlbmVyYXRlIGFuZCBjb25zdW1lcyAyeCBtZW1vcnkuXG4gICAgICogVXNlcyBwcmVjb21wdXRlcyB3aGVuIGF2YWlsYWJsZS5cbiAgICAgKiBVc2VzIGVuZG9tb3JwaGlzbSBmb3IgS29ibGl0eiBjdXJ2ZXMuXG4gICAgICogQHBhcmFtIHNjYWxhciBieSB3aGljaCB0aGUgcG9pbnQgd291bGQgYmUgbXVsdGlwbGllZFxuICAgICAqIEByZXR1cm5zIE5ldyBwb2ludFxuICAgICAqL1xuICAgIG11bHRpcGx5KHNjYWxhcjogYmlnaW50KTogUG9pbnQge1xuICAgICAgY29uc3QgeyBlbmRvIH0gPSBleHRyYU9wdHM7XG4gICAgICBpZiAoIUZuLmlzVmFsaWROb3QwKHNjYWxhcikpIHRocm93IG5ldyBFcnJvcignaW52YWxpZCBzY2FsYXI6IG91dCBvZiByYW5nZScpOyAvLyAwIGlzIGludmFsaWRcbiAgICAgIGxldCBwb2ludDogUG9pbnQsIGZha2U6IFBvaW50OyAvLyBGYWtlIHBvaW50IGlzIHVzZWQgdG8gY29uc3QtdGltZSBtdWx0XG4gICAgICBjb25zdCBtdWwgPSAobjogYmlnaW50KSA9PiB3bmFmLmNhY2hlZCh0aGlzLCBuLCAocCkgPT4gbm9ybWFsaXplWihQb2ludCwgcCkpO1xuICAgICAgLyoqIFNlZSBkb2NzIGZvciB7QGxpbmsgRW5kb21vcnBoaXNtT3B0c30gKi9cbiAgICAgIGlmIChlbmRvKSB7XG4gICAgICAgIGNvbnN0IHsgazFuZWcsIGsxLCBrMm5lZywgazIgfSA9IHNwbGl0RW5kb1NjYWxhck4oc2NhbGFyKTtcbiAgICAgICAgY29uc3QgeyBwOiBrMXAsIGY6IGsxZiB9ID0gbXVsKGsxKTtcbiAgICAgICAgY29uc3QgeyBwOiBrMnAsIGY6IGsyZiB9ID0gbXVsKGsyKTtcbiAgICAgICAgZmFrZSA9IGsxZi5hZGQoazJmKTtcbiAgICAgICAgcG9pbnQgPSBmaW5pc2hFbmRvKGVuZG8uYmV0YSwgazFwLCBrMnAsIGsxbmVnLCBrMm5lZyk7XG4gICAgICB9IGVsc2Uge1xuICAgICAgICBjb25zdCB7IHAsIGYgfSA9IG11bChzY2FsYXIpO1xuICAgICAgICBwb2ludCA9IHA7XG4gICAgICAgIGZha2UgPSBmO1xuICAgICAgfVxuICAgICAgLy8gTm9ybWFsaXplIGB6YCBmb3IgYm90aCBwb2ludHMsIGJ1dCByZXR1cm4gb25seSByZWFsIG9uZVxuICAgICAgcmV0dXJuIG5vcm1hbGl6ZVooUG9pbnQsIFtwb2ludCwgZmFrZV0pWzBdO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIE5vbi1jb25zdGFudC10aW1lIG11bHRpcGxpY2F0aW9uLiBVc2VzIGRvdWJsZS1hbmQtYWRkIGFsZ29yaXRobS5cbiAgICAgKiBJdCdzIGZhc3RlciwgYnV0IHNob3VsZCBvbmx5IGJlIHVzZWQgd2hlbiB5b3UgZG9uJ3QgY2FyZSBhYm91dFxuICAgICAqIGFuIGV4cG9zZWQgc2VjcmV0IGtleSBlLmcuIHNpZyB2ZXJpZmljYXRpb24sIHdoaWNoIHdvcmtzIG92ZXIgKnB1YmxpYyoga2V5cy5cbiAgICAgKi9cbiAgICBtdWx0aXBseVVuc2FmZShzYzogYmlnaW50KTogUG9pbnQge1xuICAgICAgY29uc3QgeyBlbmRvIH0gPSBleHRyYU9wdHM7XG4gICAgICBjb25zdCBwID0gdGhpcyBhcyBQb2ludDtcbiAgICAgIGlmICghRm4uaXNWYWxpZChzYykpIHRocm93IG5ldyBFcnJvcignaW52YWxpZCBzY2FsYXI6IG91dCBvZiByYW5nZScpOyAvLyAwIGlzIHZhbGlkXG4gICAgICBpZiAoc2MgPT09IF8wbiB8fCBwLmlzMCgpKSByZXR1cm4gUG9pbnQuWkVSTzsgLy8gMFxuICAgICAgaWYgKHNjID09PSBfMW4pIHJldHVybiBwOyAvLyAxXG4gICAgICBpZiAod25hZi5oYXNDYWNoZSh0aGlzKSkgcmV0dXJuIHRoaXMubXVsdGlwbHkoc2MpOyAvLyBwcmVjb21wdXRlc1xuICAgICAgLy8gV2UgZG9uJ3QgaGF2ZSBtZXRob2QgZm9yIGRvdWJsZSBzY2FsYXIgbXVsdGlwbGljYXRpb24gKGFQICsgYlEpOlxuICAgICAgLy8gRXZlbiB3aXRoIHVzaW5nIFN0cmF1c3MtU2hhbWlyIHRyaWNrLCBpdCdzIDM1JSBzbG93ZXIgdGhhbiBuYVx1MDBFRnZlIG11bCthZGQuXG4gICAgICBpZiAoZW5kbykge1xuICAgICAgICBjb25zdCB7IGsxbmVnLCBrMSwgazJuZWcsIGsyIH0gPSBzcGxpdEVuZG9TY2FsYXJOKHNjKTtcbiAgICAgICAgY29uc3QgeyBwMSwgcDIgfSA9IG11bEVuZG9VbnNhZmUoUG9pbnQsIHAsIGsxLCBrMik7IC8vIDMwJSBmYXN0ZXIgdnMgd25hZi51bnNhZmVcbiAgICAgICAgcmV0dXJuIGZpbmlzaEVuZG8oZW5kby5iZXRhLCBwMSwgcDIsIGsxbmVnLCBrMm5lZyk7XG4gICAgICB9IGVsc2Uge1xuICAgICAgICByZXR1cm4gd25hZi51bnNhZmUocCwgc2MpO1xuICAgICAgfVxuICAgIH1cblxuICAgIC8qKlxuICAgICAqIENvbnZlcnRzIFByb2plY3RpdmUgcG9pbnQgdG8gYWZmaW5lICh4LCB5KSBjb29yZGluYXRlcy5cbiAgICAgKiBAcGFyYW0gaW52ZXJ0ZWRaIFpeLTEgKGludmVydGVkIHplcm8pIC0gb3B0aW9uYWwsIHByZWNvbXB1dGF0aW9uIGlzIHVzZWZ1bCBmb3IgaW52ZXJ0QmF0Y2hcbiAgICAgKi9cbiAgICB0b0FmZmluZShpbnZlcnRlZFo/OiBUKTogQWZmaW5lUG9pbnQ8VD4ge1xuICAgICAgcmV0dXJuIHRvQWZmaW5lTWVtbyh0aGlzLCBpbnZlcnRlZFopO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIENoZWNrcyB3aGV0aGVyIFBvaW50IGlzIGZyZWUgb2YgdG9yc2lvbiBlbGVtZW50cyAoaXMgaW4gcHJpbWUgc3ViZ3JvdXApLlxuICAgICAqIEFsd2F5cyB0b3JzaW9uLWZyZWUgZm9yIGNvZmFjdG9yPTEgY3VydmVzLlxuICAgICAqL1xuICAgIGlzVG9yc2lvbkZyZWUoKTogYm9vbGVhbiB7XG4gICAgICBjb25zdCB7IGlzVG9yc2lvbkZyZWUgfSA9IGV4dHJhT3B0cztcbiAgICAgIGlmIChjb2ZhY3RvciA9PT0gXzFuKSByZXR1cm4gdHJ1ZTtcbiAgICAgIGlmIChpc1RvcnNpb25GcmVlKSByZXR1cm4gaXNUb3JzaW9uRnJlZShQb2ludCwgdGhpcyk7XG4gICAgICByZXR1cm4gd25hZi51bnNhZmUodGhpcywgQ1VSVkVfT1JERVIpLmlzMCgpO1xuICAgIH1cblxuICAgIGNsZWFyQ29mYWN0b3IoKTogUG9pbnQge1xuICAgICAgY29uc3QgeyBjbGVhckNvZmFjdG9yIH0gPSBleHRyYU9wdHM7XG4gICAgICBpZiAoY29mYWN0b3IgPT09IF8xbikgcmV0dXJuIHRoaXM7IC8vIEZhc3QtcGF0aFxuICAgICAgaWYgKGNsZWFyQ29mYWN0b3IpIHJldHVybiBjbGVhckNvZmFjdG9yKFBvaW50LCB0aGlzKSBhcyBQb2ludDtcbiAgICAgIHJldHVybiB0aGlzLm11bHRpcGx5VW5zYWZlKGNvZmFjdG9yKTtcbiAgICB9XG5cbiAgICBpc1NtYWxsT3JkZXIoKTogYm9vbGVhbiB7XG4gICAgICAvLyBjYW4gd2UgdXNlIHRoaXMuY2xlYXJDb2ZhY3RvcigpP1xuICAgICAgcmV0dXJuIHRoaXMubXVsdGlwbHlVbnNhZmUoY29mYWN0b3IpLmlzMCgpO1xuICAgIH1cblxuICAgIHRvQnl0ZXMoaXNDb21wcmVzc2VkID0gdHJ1ZSk6IFVpbnQ4QXJyYXkge1xuICAgICAgYWJvb2woaXNDb21wcmVzc2VkLCAnaXNDb21wcmVzc2VkJyk7XG4gICAgICB0aGlzLmFzc2VydFZhbGlkaXR5KCk7XG4gICAgICByZXR1cm4gZW5jb2RlUG9pbnQoUG9pbnQsIHRoaXMsIGlzQ29tcHJlc3NlZCk7XG4gICAgfVxuXG4gICAgdG9IZXgoaXNDb21wcmVzc2VkID0gdHJ1ZSk6IHN0cmluZyB7XG4gICAgICByZXR1cm4gYnl0ZXNUb0hleCh0aGlzLnRvQnl0ZXMoaXNDb21wcmVzc2VkKSk7XG4gICAgfVxuXG4gICAgdG9TdHJpbmcoKSB7XG4gICAgICByZXR1cm4gYDxQb2ludCAke3RoaXMuaXMwKCkgPyAnWkVSTycgOiB0aGlzLnRvSGV4KCl9PmA7XG4gICAgfVxuICB9XG4gIGNvbnN0IGJpdHMgPSBGbi5CSVRTO1xuICBjb25zdCB3bmFmID0gbmV3IHdOQUYoUG9pbnQsIGV4dHJhT3B0cy5lbmRvID8gTWF0aC5jZWlsKGJpdHMgLyAyKSA6IGJpdHMpO1xuICBQb2ludC5CQVNFLnByZWNvbXB1dGUoOCk7IC8vIEVuYWJsZSBwcmVjb21wdXRlcy4gU2xvd3MgZG93biBmaXJzdCBwdWJsaWNLZXkgY29tcHV0YXRpb24gYnkgMjBtcy5cbiAgcmV0dXJuIFBvaW50O1xufVxuXG4vKiogTWV0aG9kcyBvZiBFQ0RTQSBzaWduYXR1cmUgaW5zdGFuY2UuICovXG5leHBvcnQgaW50ZXJmYWNlIEVDRFNBU2lnbmF0dXJlIHtcbiAgcmVhZG9ubHkgcjogYmlnaW50O1xuICByZWFkb25seSBzOiBiaWdpbnQ7XG4gIHJlYWRvbmx5IHJlY292ZXJ5PzogbnVtYmVyO1xuICBhZGRSZWNvdmVyeUJpdChyZWNvdmVyeTogbnVtYmVyKTogRUNEU0FTaWduYXR1cmUgJiB7IHJlYWRvbmx5IHJlY292ZXJ5OiBudW1iZXIgfTtcbiAgaGFzSGlnaFMoKTogYm9vbGVhbjtcbiAgcmVjb3ZlclB1YmxpY0tleShtZXNzYWdlSGFzaDogVWludDhBcnJheSk6IFdlaWVyc3RyYXNzUG9pbnQ8YmlnaW50PjtcbiAgdG9CeXRlcyhmb3JtYXQ/OiBzdHJpbmcpOiBVaW50OEFycmF5O1xuICB0b0hleChmb3JtYXQ/OiBzdHJpbmcpOiBzdHJpbmc7XG59XG4vKiogTWV0aG9kcyBvZiBFQ0RTQSBzaWduYXR1cmUgY29uc3RydWN0b3IuICovXG5leHBvcnQgdHlwZSBFQ0RTQVNpZ25hdHVyZUNvbnMgPSB7XG4gIG5ldyAocjogYmlnaW50LCBzOiBiaWdpbnQsIHJlY292ZXJ5PzogbnVtYmVyKTogRUNEU0FTaWduYXR1cmU7XG4gIGZyb21CeXRlcyhieXRlczogVWludDhBcnJheSwgZm9ybWF0PzogRUNEU0FTaWduYXR1cmVGb3JtYXQpOiBFQ0RTQVNpZ25hdHVyZTtcbiAgZnJvbUhleChoZXg6IHN0cmluZywgZm9ybWF0PzogRUNEU0FTaWduYXR1cmVGb3JtYXQpOiBFQ0RTQVNpZ25hdHVyZTtcbn07XG5cbi8vIFBvaW50cyBzdGFydCB3aXRoIGJ5dGUgMHgwMiB3aGVuIHkgaXMgZXZlbjsgb3RoZXJ3aXNlIDB4MDNcbmZ1bmN0aW9uIHBwcmVmaXgoaGFzRXZlblk6IGJvb2xlYW4pOiBVaW50OEFycmF5IHtcbiAgcmV0dXJuIFVpbnQ4QXJyYXkub2YoaGFzRXZlblkgPyAweDAyIDogMHgwMyk7XG59XG5cbi8qKlxuICogSW1wbGVtZW50YXRpb24gb2YgdGhlIFNoYWxsdWUgYW5kIHZhbiBkZSBXb2VzdGlqbmUgbWV0aG9kIGZvciBhbnkgd2VpZXJzdHJhc3MgY3VydmUuXG4gKiBUT0RPOiBjaGVjayBpZiB0aGVyZSBpcyBhIHdheSB0byBtZXJnZSB0aGlzIHdpdGggdXZSYXRpbyBpbiBFZHdhcmRzOyBtb3ZlIHRvIG1vZHVsYXIuXG4gKiBiID0gVHJ1ZSBhbmQgeSA9IHNxcnQodSAvIHYpIGlmICh1IC8gdikgaXMgc3F1YXJlIGluIEYsIGFuZFxuICogYiA9IEZhbHNlIGFuZCB5ID0gc3FydChaICogKHUgLyB2KSkgb3RoZXJ3aXNlLlxuICogQHBhcmFtIEZwXG4gKiBAcGFyYW0gWlxuICogQHJldHVybnNcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIFNXVUZwU3FydFJhdGlvPFQ+KFxuICBGcDogSUZpZWxkPFQ+LFxuICBaOiBUXG4pOiAodTogVCwgdjogVCkgPT4geyBpc1ZhbGlkOiBib29sZWFuOyB2YWx1ZTogVCB9IHtcbiAgLy8gR2VuZXJpYyBpbXBsZW1lbnRhdGlvblxuICBjb25zdCBxID0gRnAuT1JERVI7XG4gIGxldCBsID0gXzBuO1xuICBmb3IgKGxldCBvID0gcSAtIF8xbjsgbyAlIF8ybiA9PT0gXzBuOyBvIC89IF8ybikgbCArPSBfMW47XG4gIGNvbnN0IGMxID0gbDsgLy8gMS4gYzEsIHRoZSBsYXJnZXN0IGludGVnZXIgc3VjaCB0aGF0IDJeYzEgZGl2aWRlcyBxIC0gMS5cbiAgLy8gV2UgbmVlZCAybiAqKiBjMSBhbmQgMm4gKiogKGMxLTEpLiBXZSBjYW4ndCB1c2UgKio7IGJ1dCB3ZSBjYW4gdXNlIDw8LlxuICAvLyAybiAqKiBjMSA9PSAybiA8PCAoYzEtMSlcbiAgY29uc3QgXzJuX3Bvd19jMV8xID0gXzJuIDw8IChjMSAtIF8xbiAtIF8xbik7XG4gIGNvbnN0IF8ybl9wb3dfYzEgPSBfMm5fcG93X2MxXzEgKiBfMm47XG4gIGNvbnN0IGMyID0gKHEgLSBfMW4pIC8gXzJuX3Bvd19jMTsgLy8gMi4gYzIgPSAocSAtIDEpIC8gKDJeYzEpICAjIEludGVnZXIgYXJpdGhtZXRpY1xuICBjb25zdCBjMyA9IChjMiAtIF8xbikgLyBfMm47IC8vIDMuIGMzID0gKGMyIC0gMSkgLyAyICAgICAgICAgICAgIyBJbnRlZ2VyIGFyaXRobWV0aWNcbiAgY29uc3QgYzQgPSBfMm5fcG93X2MxIC0gXzFuOyAvLyA0LiBjNCA9IDJeYzEgLSAxICAgICAgICAgICAgICAgICMgSW50ZWdlciBhcml0aG1ldGljXG4gIGNvbnN0IGM1ID0gXzJuX3Bvd19jMV8xOyAvLyA1LiBjNSA9IDJeKGMxIC0gMSkgICAgICAgICAgICAgICAgICAjIEludGVnZXIgYXJpdGhtZXRpY1xuICBjb25zdCBjNiA9IEZwLnBvdyhaLCBjMik7IC8vIDYuIGM2ID0gWl5jMlxuICBjb25zdCBjNyA9IEZwLnBvdyhaLCAoYzIgKyBfMW4pIC8gXzJuKTsgLy8gNy4gYzcgPSBaXigoYzIgKyAxKSAvIDIpXG4gIGxldCBzcXJ0UmF0aW8gPSAodTogVCwgdjogVCk6IHsgaXNWYWxpZDogYm9vbGVhbjsgdmFsdWU6IFQgfSA9PiB7XG4gICAgbGV0IHR2MSA9IGM2OyAvLyAxLiB0djEgPSBjNlxuICAgIGxldCB0djIgPSBGcC5wb3codiwgYzQpOyAvLyAyLiB0djIgPSB2XmM0XG4gICAgbGV0IHR2MyA9IEZwLnNxcih0djIpOyAvLyAzLiB0djMgPSB0djJeMlxuICAgIHR2MyA9IEZwLm11bCh0djMsIHYpOyAvLyA0LiB0djMgPSB0djMgKiB2XG4gICAgbGV0IHR2NSA9IEZwLm11bCh1LCB0djMpOyAvLyA1LiB0djUgPSB1ICogdHYzXG4gICAgdHY1ID0gRnAucG93KHR2NSwgYzMpOyAvLyA2LiB0djUgPSB0djVeYzNcbiAgICB0djUgPSBGcC5tdWwodHY1LCB0djIpOyAvLyA3LiB0djUgPSB0djUgKiB0djJcbiAgICB0djIgPSBGcC5tdWwodHY1LCB2KTsgLy8gOC4gdHYyID0gdHY1ICogdlxuICAgIHR2MyA9IEZwLm11bCh0djUsIHUpOyAvLyA5LiB0djMgPSB0djUgKiB1XG4gICAgbGV0IHR2NCA9IEZwLm11bCh0djMsIHR2Mik7IC8vIDEwLiB0djQgPSB0djMgKiB0djJcbiAgICB0djUgPSBGcC5wb3codHY0LCBjNSk7IC8vIDExLiB0djUgPSB0djReYzVcbiAgICBsZXQgaXNRUiA9IEZwLmVxbCh0djUsIEZwLk9ORSk7IC8vIDEyLiBpc1FSID0gdHY1ID09IDFcbiAgICB0djIgPSBGcC5tdWwodHYzLCBjNyk7IC8vIDEzLiB0djIgPSB0djMgKiBjN1xuICAgIHR2NSA9IEZwLm11bCh0djQsIHR2MSk7IC8vIDE0LiB0djUgPSB0djQgKiB0djFcbiAgICB0djMgPSBGcC5jbW92KHR2MiwgdHYzLCBpc1FSKTsgLy8gMTUuIHR2MyA9IENNT1YodHYyLCB0djMsIGlzUVIpXG4gICAgdHY0ID0gRnAuY21vdih0djUsIHR2NCwgaXNRUik7IC8vIDE2LiB0djQgPSBDTU9WKHR2NSwgdHY0LCBpc1FSKVxuICAgIC8vIDE3LiBmb3IgaSBpbiAoYzEsIGMxIC0gMSwgLi4uLCAyKTpcbiAgICBmb3IgKGxldCBpID0gYzE7IGkgPiBfMW47IGktLSkge1xuICAgICAgbGV0IHR2NSA9IGkgLSBfMm47IC8vIDE4LiAgICB0djUgPSBpIC0gMlxuICAgICAgdHY1ID0gXzJuIDw8ICh0djUgLSBfMW4pOyAvLyAxOS4gICAgdHY1ID0gMl50djVcbiAgICAgIGxldCB0dnY1ID0gRnAucG93KHR2NCwgdHY1KTsgLy8gMjAuICAgIHR2NSA9IHR2NF50djVcbiAgICAgIGNvbnN0IGUxID0gRnAuZXFsKHR2djUsIEZwLk9ORSk7IC8vIDIxLiAgICBlMSA9IHR2NSA9PSAxXG4gICAgICB0djIgPSBGcC5tdWwodHYzLCB0djEpOyAvLyAyMi4gICAgdHYyID0gdHYzICogdHYxXG4gICAgICB0djEgPSBGcC5tdWwodHYxLCB0djEpOyAvLyAyMy4gICAgdHYxID0gdHYxICogdHYxXG4gICAgICB0dnY1ID0gRnAubXVsKHR2NCwgdHYxKTsgLy8gMjQuICAgIHR2NSA9IHR2NCAqIHR2MVxuICAgICAgdHYzID0gRnAuY21vdih0djIsIHR2MywgZTEpOyAvLyAyNS4gICAgdHYzID0gQ01PVih0djIsIHR2MywgZTEpXG4gICAgICB0djQgPSBGcC5jbW92KHR2djUsIHR2NCwgZTEpOyAvLyAyNi4gICAgdHY0ID0gQ01PVih0djUsIHR2NCwgZTEpXG4gICAgfVxuICAgIHJldHVybiB7IGlzVmFsaWQ6IGlzUVIsIHZhbHVlOiB0djMgfTtcbiAgfTtcbiAgaWYgKEZwLk9SREVSICUgXzRuID09PSBfM24pIHtcbiAgICAvLyBzcXJ0X3JhdGlvXzNtb2Q0KHUsIHYpXG4gICAgY29uc3QgYzEgPSAoRnAuT1JERVIgLSBfM24pIC8gXzRuOyAvLyAxLiBjMSA9IChxIC0gMykgLyA0ICAgICAjIEludGVnZXIgYXJpdGhtZXRpY1xuICAgIGNvbnN0IGMyID0gRnAuc3FydChGcC5uZWcoWikpOyAvLyAyLiBjMiA9IHNxcnQoLVopXG4gICAgc3FydFJhdGlvID0gKHU6IFQsIHY6IFQpID0+IHtcbiAgICAgIGxldCB0djEgPSBGcC5zcXIodik7IC8vIDEuIHR2MSA9IHZeMlxuICAgICAgY29uc3QgdHYyID0gRnAubXVsKHUsIHYpOyAvLyAyLiB0djIgPSB1ICogdlxuICAgICAgdHYxID0gRnAubXVsKHR2MSwgdHYyKTsgLy8gMy4gdHYxID0gdHYxICogdHYyXG4gICAgICBsZXQgeTEgPSBGcC5wb3codHYxLCBjMSk7IC8vIDQuIHkxID0gdHYxXmMxXG4gICAgICB5MSA9IEZwLm11bCh5MSwgdHYyKTsgLy8gNS4geTEgPSB5MSAqIHR2MlxuICAgICAgY29uc3QgeTIgPSBGcC5tdWwoeTEsIGMyKTsgLy8gNi4geTIgPSB5MSAqIGMyXG4gICAgICBjb25zdCB0djMgPSBGcC5tdWwoRnAuc3FyKHkxKSwgdik7IC8vIDcuIHR2MyA9IHkxXjI7IDguIHR2MyA9IHR2MyAqIHZcbiAgICAgIGNvbnN0IGlzUVIgPSBGcC5lcWwodHYzLCB1KTsgLy8gOS4gaXNRUiA9IHR2MyA9PSB1XG4gICAgICBsZXQgeSA9IEZwLmNtb3YoeTIsIHkxLCBpc1FSKTsgLy8gMTAuIHkgPSBDTU9WKHkyLCB5MSwgaXNRUilcbiAgICAgIHJldHVybiB7IGlzVmFsaWQ6IGlzUVIsIHZhbHVlOiB5IH07IC8vIDExLiByZXR1cm4gKGlzUVIsIHkpIGlzUVIgPyB5IDogeSpjMlxuICAgIH07XG4gIH1cbiAgLy8gTm8gY3VydmVzIHVzZXMgdGhhdFxuICAvLyBpZiAoRnAuT1JERVIgJSBfOG4gPT09IF81bikgLy8gc3FydF9yYXRpb181bW9kOFxuICByZXR1cm4gc3FydFJhdGlvO1xufVxuLyoqXG4gKiBTaW1wbGlmaWVkIFNoYWxsdWUtdmFuIGRlIFdvZXN0aWpuZS1VbGFzIE1ldGhvZFxuICogaHR0cHM6Ly93d3cucmZjLWVkaXRvci5vcmcvcmZjL3JmYzkzODAjc2VjdGlvbi02LjYuMlxuICovXG5leHBvcnQgZnVuY3Rpb24gbWFwVG9DdXJ2ZVNpbXBsZVNXVTxUPihcbiAgRnA6IElGaWVsZDxUPixcbiAgb3B0czoge1xuICAgIEE6IFQ7XG4gICAgQjogVDtcbiAgICBaOiBUO1xuICB9XG4pOiAodTogVCkgPT4geyB4OiBUOyB5OiBUIH0ge1xuICB2YWxpZGF0ZUZpZWxkKEZwKTtcbiAgY29uc3QgeyBBLCBCLCBaIH0gPSBvcHRzO1xuICBpZiAoIUZwLmlzVmFsaWQoQSkgfHwgIUZwLmlzVmFsaWQoQikgfHwgIUZwLmlzVmFsaWQoWikpXG4gICAgdGhyb3cgbmV3IEVycm9yKCdtYXBUb0N1cnZlU2ltcGxlU1dVOiBpbnZhbGlkIG9wdHMnKTtcbiAgY29uc3Qgc3FydFJhdGlvID0gU1dVRnBTcXJ0UmF0aW8oRnAsIFopO1xuICBpZiAoIUZwLmlzT2RkKSB0aHJvdyBuZXcgRXJyb3IoJ0ZpZWxkIGRvZXMgbm90IGhhdmUgLmlzT2RkKCknKTtcbiAgLy8gSW5wdXQ6IHUsIGFuIGVsZW1lbnQgb2YgRi5cbiAgLy8gT3V0cHV0OiAoeCwgeSksIGEgcG9pbnQgb24gRS5cbiAgcmV0dXJuICh1OiBUKTogeyB4OiBUOyB5OiBUIH0gPT4ge1xuICAgIC8vIHByZXR0aWVyLWlnbm9yZVxuICAgIGxldCB0djEsIHR2MiwgdHYzLCB0djQsIHR2NSwgdHY2LCB4LCB5O1xuICAgIHR2MSA9IEZwLnNxcih1KTsgLy8gMS4gIHR2MSA9IHVeMlxuICAgIHR2MSA9IEZwLm11bCh0djEsIFopOyAvLyAyLiAgdHYxID0gWiAqIHR2MVxuICAgIHR2MiA9IEZwLnNxcih0djEpOyAvLyAzLiAgdHYyID0gdHYxXjJcbiAgICB0djIgPSBGcC5hZGQodHYyLCB0djEpOyAvLyA0LiAgdHYyID0gdHYyICsgdHYxXG4gICAgdHYzID0gRnAuYWRkKHR2MiwgRnAuT05FKTsgLy8gNS4gIHR2MyA9IHR2MiArIDFcbiAgICB0djMgPSBGcC5tdWwodHYzLCBCKTsgLy8gNi4gIHR2MyA9IEIgKiB0djNcbiAgICB0djQgPSBGcC5jbW92KFosIEZwLm5lZyh0djIpLCAhRnAuZXFsKHR2MiwgRnAuWkVSTykpOyAvLyA3LiAgdHY0ID0gQ01PVihaLCAtdHYyLCB0djIgIT0gMClcbiAgICB0djQgPSBGcC5tdWwodHY0LCBBKTsgLy8gOC4gIHR2NCA9IEEgKiB0djRcbiAgICB0djIgPSBGcC5zcXIodHYzKTsgLy8gOS4gIHR2MiA9IHR2M14yXG4gICAgdHY2ID0gRnAuc3FyKHR2NCk7IC8vIDEwLiB0djYgPSB0djReMlxuICAgIHR2NSA9IEZwLm11bCh0djYsIEEpOyAvLyAxMS4gdHY1ID0gQSAqIHR2NlxuICAgIHR2MiA9IEZwLmFkZCh0djIsIHR2NSk7IC8vIDEyLiB0djIgPSB0djIgKyB0djVcbiAgICB0djIgPSBGcC5tdWwodHYyLCB0djMpOyAvLyAxMy4gdHYyID0gdHYyICogdHYzXG4gICAgdHY2ID0gRnAubXVsKHR2NiwgdHY0KTsgLy8gMTQuIHR2NiA9IHR2NiAqIHR2NFxuICAgIHR2NSA9IEZwLm11bCh0djYsIEIpOyAvLyAxNS4gdHY1ID0gQiAqIHR2NlxuICAgIHR2MiA9IEZwLmFkZCh0djIsIHR2NSk7IC8vIDE2LiB0djIgPSB0djIgKyB0djVcbiAgICB4ID0gRnAubXVsKHR2MSwgdHYzKTsgLy8gMTcuICAgeCA9IHR2MSAqIHR2M1xuICAgIGNvbnN0IHsgaXNWYWxpZCwgdmFsdWUgfSA9IHNxcnRSYXRpbyh0djIsIHR2Nik7IC8vIDE4LiAoaXNfZ3gxX3NxdWFyZSwgeTEpID0gc3FydF9yYXRpbyh0djIsIHR2NilcbiAgICB5ID0gRnAubXVsKHR2MSwgdSk7IC8vIDE5LiAgIHkgPSB0djEgKiB1ICAtPiBaICogdV4zICogeTFcbiAgICB5ID0gRnAubXVsKHksIHZhbHVlKTsgLy8gMjAuICAgeSA9IHkgKiB5MVxuICAgIHggPSBGcC5jbW92KHgsIHR2MywgaXNWYWxpZCk7IC8vIDIxLiAgIHggPSBDTU9WKHgsIHR2MywgaXNfZ3gxX3NxdWFyZSlcbiAgICB5ID0gRnAuY21vdih5LCB2YWx1ZSwgaXNWYWxpZCk7IC8vIDIyLiAgIHkgPSBDTU9WKHksIHkxLCBpc19neDFfc3F1YXJlKVxuICAgIGNvbnN0IGUxID0gRnAuaXNPZGQhKHUpID09PSBGcC5pc09kZCEoeSk7IC8vIDIzLiAgZTEgPSBzZ24wKHUpID09IHNnbjAoeSlcbiAgICB5ID0gRnAuY21vdihGcC5uZWcoeSksIHksIGUxKTsgLy8gMjQuICAgeSA9IENNT1YoLXksIHksIGUxKVxuICAgIGNvbnN0IHR2NF9pbnYgPSBGcEludmVydEJhdGNoKEZwLCBbdHY0XSwgdHJ1ZSlbMF07XG4gICAgeCA9IEZwLm11bCh4LCB0djRfaW52KTsgLy8gMjUuICAgeCA9IHggLyB0djRcbiAgICByZXR1cm4geyB4LCB5IH07XG4gIH07XG59XG5cbmZ1bmN0aW9uIGdldFdMZW5ndGhzPFQ+KEZwOiBJRmllbGQ8VD4sIEZuOiBJRmllbGQ8YmlnaW50Pikge1xuICByZXR1cm4ge1xuICAgIHNlY3JldEtleTogRm4uQllURVMsXG4gICAgcHVibGljS2V5OiAxICsgRnAuQllURVMsXG4gICAgcHVibGljS2V5VW5jb21wcmVzc2VkOiAxICsgMiAqIEZwLkJZVEVTLFxuICAgIHB1YmxpY0tleUhhc1ByZWZpeDogdHJ1ZSxcbiAgICBzaWduYXR1cmU6IDIgKiBGbi5CWVRFUyxcbiAgfTtcbn1cblxuLyoqXG4gKiBTb21ldGltZXMgdXNlcnMgb25seSBuZWVkIGdldFB1YmxpY0tleSwgZ2V0U2hhcmVkU2VjcmV0LCBhbmQgc2VjcmV0IGtleSBoYW5kbGluZy5cbiAqIFRoaXMgaGVscGVyIGVuc3VyZXMgbm8gc2lnbmF0dXJlIGZ1bmN0aW9uYWxpdHkgaXMgcHJlc2VudC4gTGVzcyBjb2RlLCBzbWFsbGVyIGJ1bmRsZSBzaXplLlxuICovXG5leHBvcnQgZnVuY3Rpb24gZWNkaChcbiAgUG9pbnQ6IFdlaWVyc3RyYXNzUG9pbnRDb25zPGJpZ2ludD4sXG4gIGVjZGhPcHRzOiB7IHJhbmRvbUJ5dGVzPzogKGJ5dGVzTGVuZ3RoPzogbnVtYmVyKSA9PiBVaW50OEFycmF5IH0gPSB7fVxuKTogRUNESCB7XG4gIGNvbnN0IHsgRm4gfSA9IFBvaW50O1xuICBjb25zdCByYW5kb21CeXRlc18gPSBlY2RoT3B0cy5yYW5kb21CeXRlcyB8fCB3Y1JhbmRvbUJ5dGVzO1xuICBjb25zdCBsZW5ndGhzID0gT2JqZWN0LmFzc2lnbihnZXRXTGVuZ3RocyhQb2ludC5GcCwgRm4pLCB7IHNlZWQ6IGdldE1pbkhhc2hMZW5ndGgoRm4uT1JERVIpIH0pO1xuXG4gIGZ1bmN0aW9uIGlzVmFsaWRTZWNyZXRLZXkoc2VjcmV0S2V5OiBVaW50OEFycmF5KSB7XG4gICAgdHJ5IHtcbiAgICAgIGNvbnN0IG51bSA9IEZuLmZyb21CeXRlcyhzZWNyZXRLZXkpO1xuICAgICAgcmV0dXJuIEZuLmlzVmFsaWROb3QwKG51bSk7XG4gICAgfSBjYXRjaCAoZXJyb3IpIHtcbiAgICAgIHJldHVybiBmYWxzZTtcbiAgICB9XG4gIH1cblxuICBmdW5jdGlvbiBpc1ZhbGlkUHVibGljS2V5KHB1YmxpY0tleTogVWludDhBcnJheSwgaXNDb21wcmVzc2VkPzogYm9vbGVhbik6IGJvb2xlYW4ge1xuICAgIGNvbnN0IHsgcHVibGljS2V5OiBjb21wLCBwdWJsaWNLZXlVbmNvbXByZXNzZWQgfSA9IGxlbmd0aHM7XG4gICAgdHJ5IHtcbiAgICAgIGNvbnN0IGwgPSBwdWJsaWNLZXkubGVuZ3RoO1xuICAgICAgaWYgKGlzQ29tcHJlc3NlZCA9PT0gdHJ1ZSAmJiBsICE9PSBjb21wKSByZXR1cm4gZmFsc2U7XG4gICAgICBpZiAoaXNDb21wcmVzc2VkID09PSBmYWxzZSAmJiBsICE9PSBwdWJsaWNLZXlVbmNvbXByZXNzZWQpIHJldHVybiBmYWxzZTtcbiAgICAgIHJldHVybiAhIVBvaW50LmZyb21CeXRlcyhwdWJsaWNLZXkpO1xuICAgIH0gY2F0Y2ggKGVycm9yKSB7XG4gICAgICByZXR1cm4gZmFsc2U7XG4gICAgfVxuICB9XG5cbiAgLyoqXG4gICAqIFByb2R1Y2VzIGNyeXB0b2dyYXBoaWNhbGx5IHNlY3VyZSBzZWNyZXQga2V5IGZyb20gcmFuZG9tIG9mIHNpemVcbiAgICogKGdyb3VwTGVuICsgY2VpbChncm91cExlbiAvIDIpKSB3aXRoIG1vZHVsbyBiaWFzIGJlaW5nIG5lZ2xpZ2libGUuXG4gICAqL1xuICBmdW5jdGlvbiByYW5kb21TZWNyZXRLZXkoc2VlZCA9IHJhbmRvbUJ5dGVzXyhsZW5ndGhzLnNlZWQpKTogVWludDhBcnJheSB7XG4gICAgcmV0dXJuIG1hcEhhc2hUb0ZpZWxkKGFieXRlcyhzZWVkLCBsZW5ndGhzLnNlZWQsICdzZWVkJyksIEZuLk9SREVSKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBDb21wdXRlcyBwdWJsaWMga2V5IGZvciBhIHNlY3JldCBrZXkuIENoZWNrcyBmb3IgdmFsaWRpdHkgb2YgdGhlIHNlY3JldCBrZXkuXG4gICAqIEBwYXJhbSBpc0NvbXByZXNzZWQgd2hldGhlciB0byByZXR1cm4gY29tcGFjdCAoZGVmYXVsdCksIG9yIGZ1bGwga2V5XG4gICAqIEByZXR1cm5zIFB1YmxpYyBrZXksIGZ1bGwgd2hlbiBpc0NvbXByZXNzZWQ9ZmFsc2U7IHNob3J0IHdoZW4gaXNDb21wcmVzc2VkPXRydWVcbiAgICovXG4gIGZ1bmN0aW9uIGdldFB1YmxpY0tleShzZWNyZXRLZXk6IFVpbnQ4QXJyYXksIGlzQ29tcHJlc3NlZCA9IHRydWUpOiBVaW50OEFycmF5IHtcbiAgICByZXR1cm4gUG9pbnQuQkFTRS5tdWx0aXBseShGbi5mcm9tQnl0ZXMoc2VjcmV0S2V5KSkudG9CeXRlcyhpc0NvbXByZXNzZWQpO1xuICB9XG5cbiAgLyoqXG4gICAqIFF1aWNrIGFuZCBkaXJ0eSBjaGVjayBmb3IgaXRlbSBiZWluZyBwdWJsaWMga2V5LiBEb2VzIG5vdCB2YWxpZGF0ZSBoZXgsIG9yIGJlaW5nIG9uLWN1cnZlLlxuICAgKi9cbiAgZnVuY3Rpb24gaXNQcm9iUHViKGl0ZW06IFVpbnQ4QXJyYXkpOiBib29sZWFuIHwgdW5kZWZpbmVkIHtcbiAgICBjb25zdCB7IHNlY3JldEtleSwgcHVibGljS2V5LCBwdWJsaWNLZXlVbmNvbXByZXNzZWQgfSA9IGxlbmd0aHM7XG4gICAgaWYgKCFpc0J5dGVzKGl0ZW0pKSByZXR1cm4gdW5kZWZpbmVkO1xuICAgIGlmICgoJ19sZW5ndGhzJyBpbiBGbiAmJiBGbi5fbGVuZ3RocykgfHwgc2VjcmV0S2V5ID09PSBwdWJsaWNLZXkpIHJldHVybiB1bmRlZmluZWQ7XG4gICAgY29uc3QgbCA9IGFieXRlcyhpdGVtLCB1bmRlZmluZWQsICdrZXknKS5sZW5ndGg7XG4gICAgcmV0dXJuIGwgPT09IHB1YmxpY0tleSB8fCBsID09PSBwdWJsaWNLZXlVbmNvbXByZXNzZWQ7XG4gIH1cblxuICAvKipcbiAgICogRUNESCAoRWxsaXB0aWMgQ3VydmUgRGlmZmllIEhlbGxtYW4pLlxuICAgKiBDb21wdXRlcyBzaGFyZWQgcHVibGljIGtleSBmcm9tIHNlY3JldCBrZXkgQSBhbmQgcHVibGljIGtleSBCLlxuICAgKiBDaGVja3M6IDEpIHNlY3JldCBrZXkgdmFsaWRpdHkgMikgc2hhcmVkIGtleSBpcyBvbi1jdXJ2ZS5cbiAgICogRG9lcyBOT1QgaGFzaCB0aGUgcmVzdWx0LlxuICAgKiBAcGFyYW0gaXNDb21wcmVzc2VkIHdoZXRoZXIgdG8gcmV0dXJuIGNvbXBhY3QgKGRlZmF1bHQpLCBvciBmdWxsIGtleVxuICAgKiBAcmV0dXJucyBzaGFyZWQgcHVibGljIGtleVxuICAgKi9cbiAgZnVuY3Rpb24gZ2V0U2hhcmVkU2VjcmV0KFxuICAgIHNlY3JldEtleUE6IFVpbnQ4QXJyYXksXG4gICAgcHVibGljS2V5QjogVWludDhBcnJheSxcbiAgICBpc0NvbXByZXNzZWQgPSB0cnVlXG4gICk6IFVpbnQ4QXJyYXkge1xuICAgIGlmIChpc1Byb2JQdWIoc2VjcmV0S2V5QSkgPT09IHRydWUpIHRocm93IG5ldyBFcnJvcignZmlyc3QgYXJnIG11c3QgYmUgcHJpdmF0ZSBrZXknKTtcbiAgICBpZiAoaXNQcm9iUHViKHB1YmxpY0tleUIpID09PSBmYWxzZSkgdGhyb3cgbmV3IEVycm9yKCdzZWNvbmQgYXJnIG11c3QgYmUgcHVibGljIGtleScpO1xuICAgIGNvbnN0IHMgPSBGbi5mcm9tQnl0ZXMoc2VjcmV0S2V5QSk7XG4gICAgY29uc3QgYiA9IFBvaW50LmZyb21CeXRlcyhwdWJsaWNLZXlCKTsgLy8gY2hlY2tzIGZvciBiZWluZyBvbi1jdXJ2ZVxuICAgIHJldHVybiBiLm11bHRpcGx5KHMpLnRvQnl0ZXMoaXNDb21wcmVzc2VkKTtcbiAgfVxuXG4gIGNvbnN0IHV0aWxzID0ge1xuICAgIGlzVmFsaWRTZWNyZXRLZXksXG4gICAgaXNWYWxpZFB1YmxpY0tleSxcbiAgICByYW5kb21TZWNyZXRLZXksXG4gIH07XG4gIGNvbnN0IGtleWdlbiA9IGNyZWF0ZUtleWdlbihyYW5kb21TZWNyZXRLZXksIGdldFB1YmxpY0tleSk7XG5cbiAgcmV0dXJuIE9iamVjdC5mcmVlemUoeyBnZXRQdWJsaWNLZXksIGdldFNoYXJlZFNlY3JldCwga2V5Z2VuLCBQb2ludCwgdXRpbHMsIGxlbmd0aHMgfSk7XG59XG5cbi8qKlxuICogQ3JlYXRlcyBFQ0RTQSBzaWduaW5nIGludGVyZmFjZSBmb3IgZ2l2ZW4gZWxsaXB0aWMgY3VydmUgYFBvaW50YCBhbmQgYGhhc2hgIGZ1bmN0aW9uLlxuICpcbiAqIEBwYXJhbSBQb2ludCBjcmVhdGVkIHVzaW5nIHtAbGluayB3ZWllcnN0cmFzc30gZnVuY3Rpb25cbiAqIEBwYXJhbSBoYXNoIHVzZWQgZm9yIDEpIG1lc3NhZ2UgcHJlaGFzaC1pbmcgMikgayBnZW5lcmF0aW9uIGluIGBzaWduYCwgdXNpbmcgaG1hY19kcmJnKGhhc2gpXG4gKiBAcGFyYW0gZWNkc2FPcHRzIHJhcmVseSBuZWVkZWQsIHNlZSB7QGxpbmsgRUNEU0FPcHRzfVxuICpcbiAqIEBleGFtcGxlXG4gKiBgYGBqc1xuICogY29uc3QgcDI1Nl9Qb2ludCA9IHdlaWVyc3RyYXNzKC4uLik7XG4gKiBjb25zdCBwMjU2X3NoYTI1NiA9IGVjZHNhKHAyNTZfUG9pbnQsIHNoYTI1Nik7XG4gKiBjb25zdCBwMjU2X3NoYTIyNCA9IGVjZHNhKHAyNTZfUG9pbnQsIHNoYTIyNCk7XG4gKiBjb25zdCBwMjU2X3NoYTIyNF9yID0gZWNkc2EocDI1Nl9Qb2ludCwgc2hhMjI0LCB7IHJhbmRvbUJ5dGVzOiAobGVuZ3RoKSA9PiB7IC4uLiB9IH0pO1xuICogYGBgXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBlY2RzYShcbiAgUG9pbnQ6IFdlaWVyc3RyYXNzUG9pbnRDb25zPGJpZ2ludD4sXG4gIGhhc2g6IENIYXNoLFxuICBlY2RzYU9wdHM6IEVDRFNBT3B0cyA9IHt9XG4pOiBFQ0RTQSB7XG4gIGFoYXNoKGhhc2gpO1xuICB2YWxpZGF0ZU9iamVjdChcbiAgICBlY2RzYU9wdHMsXG4gICAge30sXG4gICAge1xuICAgICAgaG1hYzogJ2Z1bmN0aW9uJyxcbiAgICAgIGxvd1M6ICdib29sZWFuJyxcbiAgICAgIHJhbmRvbUJ5dGVzOiAnZnVuY3Rpb24nLFxuICAgICAgYml0czJpbnQ6ICdmdW5jdGlvbicsXG4gICAgICBiaXRzMmludF9tb2ROOiAnZnVuY3Rpb24nLFxuICAgIH1cbiAgKTtcbiAgZWNkc2FPcHRzID0gT2JqZWN0LmFzc2lnbih7fSwgZWNkc2FPcHRzKTtcbiAgY29uc3QgcmFuZG9tQnl0ZXMgPSBlY2RzYU9wdHMucmFuZG9tQnl0ZXMgfHwgd2NSYW5kb21CeXRlcztcbiAgY29uc3QgaG1hYyA9IGVjZHNhT3B0cy5obWFjIHx8ICgoa2V5LCBtc2cpID0+IG5vYmxlSG1hYyhoYXNoLCBrZXksIG1zZykpO1xuXG4gIGNvbnN0IHsgRnAsIEZuIH0gPSBQb2ludDtcbiAgY29uc3QgeyBPUkRFUjogQ1VSVkVfT1JERVIsIEJJVFM6IGZuQml0cyB9ID0gRm47XG4gIGNvbnN0IHsga2V5Z2VuLCBnZXRQdWJsaWNLZXksIGdldFNoYXJlZFNlY3JldCwgdXRpbHMsIGxlbmd0aHMgfSA9IGVjZGgoUG9pbnQsIGVjZHNhT3B0cyk7XG4gIGNvbnN0IGRlZmF1bHRTaWdPcHRzOiBSZXF1aXJlZDxFQ0RTQVNpZ25PcHRzPiA9IHtcbiAgICBwcmVoYXNoOiB0cnVlLFxuICAgIGxvd1M6IHR5cGVvZiBlY2RzYU9wdHMubG93UyA9PT0gJ2Jvb2xlYW4nID8gZWNkc2FPcHRzLmxvd1MgOiB0cnVlLFxuICAgIGZvcm1hdDogJ2NvbXBhY3QnIGFzIEVDRFNBU2lnbmF0dXJlRm9ybWF0LFxuICAgIGV4dHJhRW50cm9weTogZmFsc2UsXG4gIH07XG4gIGNvbnN0IGhhc0xhcmdlQ29mYWN0b3IgPSBDVVJWRV9PUkRFUiAqIF8ybiA8IEZwLk9SREVSOyAvLyBXb24ndCBDVVJWRSgpLmggPiAybiBiZSBtb3JlIGVmZmVjdGl2ZT9cblxuICBmdW5jdGlvbiBpc0JpZ2dlclRoYW5IYWxmT3JkZXIobnVtYmVyOiBiaWdpbnQpIHtcbiAgICBjb25zdCBIQUxGID0gQ1VSVkVfT1JERVIgPj4gXzFuO1xuICAgIHJldHVybiBudW1iZXIgPiBIQUxGO1xuICB9XG4gIGZ1bmN0aW9uIHZhbGlkYXRlUlModGl0bGU6IHN0cmluZywgbnVtOiBiaWdpbnQpOiBiaWdpbnQge1xuICAgIGlmICghRm4uaXNWYWxpZE5vdDAobnVtKSlcbiAgICAgIHRocm93IG5ldyBFcnJvcihgaW52YWxpZCBzaWduYXR1cmUgJHt0aXRsZX06IG91dCBvZiByYW5nZSAxLi5Qb2ludC5Gbi5PUkRFUmApO1xuICAgIHJldHVybiBudW07XG4gIH1cbiAgZnVuY3Rpb24gYXNzZXJ0U21hbGxDb2ZhY3RvcigpOiB2b2lkIHtcbiAgICAvLyBFQ0RTQSByZWNvdmVyeSBpcyBoYXJkIGZvciBjb2ZhY3RvciA+IDEgY3VydmVzLlxuICAgIC8vIEluIHNpZ24sIGByID0gcS54IG1vZCBuYCwgYW5kIGhlcmUgd2UgcmVjb3ZlciBxLnggZnJvbSByLlxuICAgIC8vIFdoaWxlIHJlY292ZXJpbmcgcS54ID49IG4sIHdlIG5lZWQgdG8gYWRkIHIrbiBmb3IgY29mYWN0b3I9MSBjdXJ2ZXMuXG4gICAgLy8gSG93ZXZlciwgZm9yIGNvZmFjdG9yPjEsIHIrbiBtYXkgbm90IGdldCBxLng6XG4gICAgLy8gcituKmkgd291bGQgbmVlZCB0byBiZSBkb25lIGluc3RlYWQgd2hlcmUgaSBpcyB1bmtub3duLlxuICAgIC8vIFRvIGVhc2lseSBnZXQgaSwgd2UgZWl0aGVyIG5lZWQgdG86XG4gICAgLy8gYS4gaW5jcmVhc2UgYW1vdW50IG9mIHZhbGlkIHJlY2lkIHZhbHVlcyAoNCwgNS4uLik7IE9SXG4gICAgLy8gYi4gcHJvaGliaXQgbm9uLXByaW1lLW9yZGVyIHNpZ25hdHVyZXMgKHJlY2lkID4gMSkuXG4gICAgaWYgKGhhc0xhcmdlQ29mYWN0b3IpXG4gICAgICB0aHJvdyBuZXcgRXJyb3IoJ1wicmVjb3ZlcmVkXCIgc2lnIHR5cGUgaXMgbm90IHN1cHBvcnRlZCBmb3IgY29mYWN0b3IgPjIgY3VydmVzJyk7XG4gIH1cbiAgZnVuY3Rpb24gdmFsaWRhdGVTaWdMZW5ndGgoYnl0ZXM6IFVpbnQ4QXJyYXksIGZvcm1hdDogRUNEU0FTaWduYXR1cmVGb3JtYXQpIHtcbiAgICB2YWxpZGF0ZVNpZ0Zvcm1hdChmb3JtYXQpO1xuICAgIGNvbnN0IHNpemUgPSBsZW5ndGhzLnNpZ25hdHVyZSE7XG4gICAgY29uc3Qgc2l6ZXIgPSBmb3JtYXQgPT09ICdjb21wYWN0JyA/IHNpemUgOiBmb3JtYXQgPT09ICdyZWNvdmVyZWQnID8gc2l6ZSArIDEgOiB1bmRlZmluZWQ7XG4gICAgcmV0dXJuIGFieXRlcyhieXRlcywgc2l6ZXIpO1xuICB9XG5cbiAgLyoqXG4gICAqIEVDRFNBIHNpZ25hdHVyZSB3aXRoIGl0cyAociwgcykgcHJvcGVydGllcy4gU3VwcG9ydHMgY29tcGFjdCwgcmVjb3ZlcmVkICYgREVSIHJlcHJlc2VudGF0aW9ucy5cbiAgICovXG4gIGNsYXNzIFNpZ25hdHVyZSBpbXBsZW1lbnRzIEVDRFNBU2lnbmF0dXJlIHtcbiAgICByZWFkb25seSByOiBiaWdpbnQ7XG4gICAgcmVhZG9ubHkgczogYmlnaW50O1xuICAgIHJlYWRvbmx5IHJlY292ZXJ5PzogbnVtYmVyO1xuXG4gICAgY29uc3RydWN0b3IocjogYmlnaW50LCBzOiBiaWdpbnQsIHJlY292ZXJ5PzogbnVtYmVyKSB7XG4gICAgICB0aGlzLnIgPSB2YWxpZGF0ZVJTKCdyJywgcik7IC8vIHIgaW4gWzEuLk4tMV07XG4gICAgICB0aGlzLnMgPSB2YWxpZGF0ZVJTKCdzJywgcyk7IC8vIHMgaW4gWzEuLk4tMV07XG4gICAgICBpZiAocmVjb3ZlcnkgIT0gbnVsbCkge1xuICAgICAgICBhc3NlcnRTbWFsbENvZmFjdG9yKCk7XG4gICAgICAgIGlmICghWzAsIDEsIDIsIDNdLmluY2x1ZGVzKHJlY292ZXJ5KSkgdGhyb3cgbmV3IEVycm9yKCdpbnZhbGlkIHJlY292ZXJ5IGlkJyk7XG4gICAgICAgIHRoaXMucmVjb3ZlcnkgPSByZWNvdmVyeTtcbiAgICAgIH1cbiAgICAgIE9iamVjdC5mcmVlemUodGhpcyk7XG4gICAgfVxuXG4gICAgc3RhdGljIGZyb21CeXRlcyhcbiAgICAgIGJ5dGVzOiBVaW50OEFycmF5LFxuICAgICAgZm9ybWF0OiBFQ0RTQVNpZ25hdHVyZUZvcm1hdCA9IGRlZmF1bHRTaWdPcHRzLmZvcm1hdFxuICAgICk6IFNpZ25hdHVyZSB7XG4gICAgICB2YWxpZGF0ZVNpZ0xlbmd0aChieXRlcywgZm9ybWF0KTtcbiAgICAgIGxldCByZWNpZDogbnVtYmVyIHwgdW5kZWZpbmVkO1xuICAgICAgaWYgKGZvcm1hdCA9PT0gJ2RlcicpIHtcbiAgICAgICAgY29uc3QgeyByLCBzIH0gPSBERVIudG9TaWcoYWJ5dGVzKGJ5dGVzKSk7XG4gICAgICAgIHJldHVybiBuZXcgU2lnbmF0dXJlKHIsIHMpO1xuICAgICAgfVxuICAgICAgaWYgKGZvcm1hdCA9PT0gJ3JlY292ZXJlZCcpIHtcbiAgICAgICAgcmVjaWQgPSBieXRlc1swXTtcbiAgICAgICAgZm9ybWF0ID0gJ2NvbXBhY3QnO1xuICAgICAgICBieXRlcyA9IGJ5dGVzLnN1YmFycmF5KDEpO1xuICAgICAgfVxuICAgICAgY29uc3QgTCA9IGxlbmd0aHMuc2lnbmF0dXJlISAvIDI7XG4gICAgICBjb25zdCByID0gYnl0ZXMuc3ViYXJyYXkoMCwgTCk7XG4gICAgICBjb25zdCBzID0gYnl0ZXMuc3ViYXJyYXkoTCwgTCAqIDIpO1xuICAgICAgcmV0dXJuIG5ldyBTaWduYXR1cmUoRm4uZnJvbUJ5dGVzKHIpLCBGbi5mcm9tQnl0ZXMocyksIHJlY2lkKTtcbiAgICB9XG5cbiAgICBzdGF0aWMgZnJvbUhleChoZXg6IHN0cmluZywgZm9ybWF0PzogRUNEU0FTaWduYXR1cmVGb3JtYXQpIHtcbiAgICAgIHJldHVybiB0aGlzLmZyb21CeXRlcyhoZXhUb0J5dGVzKGhleCksIGZvcm1hdCk7XG4gICAgfVxuXG4gICAgcHJpdmF0ZSBhc3NlcnRSZWNvdmVyeSgpOiBudW1iZXIge1xuICAgICAgY29uc3QgeyByZWNvdmVyeSB9ID0gdGhpcztcbiAgICAgIGlmIChyZWNvdmVyeSA9PSBudWxsKSB0aHJvdyBuZXcgRXJyb3IoJ2ludmFsaWQgcmVjb3ZlcnkgaWQ6IG11c3QgYmUgcHJlc2VudCcpO1xuICAgICAgcmV0dXJuIHJlY292ZXJ5O1xuICAgIH1cblxuICAgIGFkZFJlY292ZXJ5Qml0KHJlY292ZXJ5OiBudW1iZXIpOiBSZWNvdmVyZWRTaWduYXR1cmUge1xuICAgICAgcmV0dXJuIG5ldyBTaWduYXR1cmUodGhpcy5yLCB0aGlzLnMsIHJlY292ZXJ5KSBhcyBSZWNvdmVyZWRTaWduYXR1cmU7XG4gICAgfVxuXG4gICAgcmVjb3ZlclB1YmxpY0tleShtZXNzYWdlSGFzaDogVWludDhBcnJheSk6IFdlaWVyc3RyYXNzUG9pbnQ8YmlnaW50PiB7XG4gICAgICBjb25zdCB7IHIsIHMgfSA9IHRoaXM7XG4gICAgICBjb25zdCByZWNvdmVyeSA9IHRoaXMuYXNzZXJ0UmVjb3ZlcnkoKTtcbiAgICAgIGNvbnN0IHJhZGogPSByZWNvdmVyeSA9PT0gMiB8fCByZWNvdmVyeSA9PT0gMyA/IHIgKyBDVVJWRV9PUkRFUiA6IHI7XG4gICAgICBpZiAoIUZwLmlzVmFsaWQocmFkaikpIHRocm93IG5ldyBFcnJvcignaW52YWxpZCByZWNvdmVyeSBpZDogc2lnLnIrY3VydmUubiAhPSBSLngnKTtcbiAgICAgIGNvbnN0IHggPSBGcC50b0J5dGVzKHJhZGopO1xuICAgICAgY29uc3QgUiA9IFBvaW50LmZyb21CeXRlcyhjb25jYXRCeXRlcyhwcHJlZml4KChyZWNvdmVyeSAmIDEpID09PSAwKSwgeCkpO1xuICAgICAgY29uc3QgaXIgPSBGbi5pbnYocmFkaik7IC8vIHJeLTFcbiAgICAgIGNvbnN0IGggPSBiaXRzMmludF9tb2ROKGFieXRlcyhtZXNzYWdlSGFzaCwgdW5kZWZpbmVkLCAnbXNnSGFzaCcpKTsgLy8gVHJ1bmNhdGUgaGFzaFxuICAgICAgY29uc3QgdTEgPSBGbi5jcmVhdGUoLWggKiBpcik7IC8vIC1ocl4tMVxuICAgICAgY29uc3QgdTIgPSBGbi5jcmVhdGUocyAqIGlyKTsgLy8gc3JeLTFcbiAgICAgIC8vIChzcl4tMSlSLShocl4tMSlHID0gLShocl4tMSlHICsgKHNyXi0xKS4gdW5zYWZlIGlzIGZpbmU6IHRoZXJlIGlzIG5vIHByaXZhdGUgZGF0YS5cbiAgICAgIGNvbnN0IFEgPSBQb2ludC5CQVNFLm11bHRpcGx5VW5zYWZlKHUxKS5hZGQoUi5tdWx0aXBseVVuc2FmZSh1MikpO1xuICAgICAgaWYgKFEuaXMwKCkpIHRocm93IG5ldyBFcnJvcignaW52YWxpZCByZWNvdmVyeTogcG9pbnQgYXQgaW5maW5pZnknKTtcbiAgICAgIFEuYXNzZXJ0VmFsaWRpdHkoKTtcbiAgICAgIHJldHVybiBRO1xuICAgIH1cblxuICAgIC8vIFNpZ25hdHVyZXMgc2hvdWxkIGJlIGxvdy1zLCB0byBwcmV2ZW50IG1hbGxlYWJpbGl0eS5cbiAgICBoYXNIaWdoUygpOiBib29sZWFuIHtcbiAgICAgIHJldHVybiBpc0JpZ2dlclRoYW5IYWxmT3JkZXIodGhpcy5zKTtcbiAgICB9XG5cbiAgICB0b0J5dGVzKGZvcm1hdDogRUNEU0FTaWduYXR1cmVGb3JtYXQgPSBkZWZhdWx0U2lnT3B0cy5mb3JtYXQpIHtcbiAgICAgIHZhbGlkYXRlU2lnRm9ybWF0KGZvcm1hdCk7XG4gICAgICBpZiAoZm9ybWF0ID09PSAnZGVyJykgcmV0dXJuIGhleFRvQnl0ZXMoREVSLmhleEZyb21TaWcodGhpcykpO1xuICAgICAgY29uc3QgeyByLCBzIH0gPSB0aGlzO1xuICAgICAgY29uc3QgcmIgPSBGbi50b0J5dGVzKHIpO1xuICAgICAgY29uc3Qgc2IgPSBGbi50b0J5dGVzKHMpO1xuICAgICAgaWYgKGZvcm1hdCA9PT0gJ3JlY292ZXJlZCcpIHtcbiAgICAgICAgYXNzZXJ0U21hbGxDb2ZhY3RvcigpO1xuICAgICAgICByZXR1cm4gY29uY2F0Qnl0ZXMoVWludDhBcnJheS5vZih0aGlzLmFzc2VydFJlY292ZXJ5KCkpLCByYiwgc2IpO1xuICAgICAgfVxuICAgICAgcmV0dXJuIGNvbmNhdEJ5dGVzKHJiLCBzYik7XG4gICAgfVxuXG4gICAgdG9IZXgoZm9ybWF0PzogRUNEU0FTaWduYXR1cmVGb3JtYXQpIHtcbiAgICAgIHJldHVybiBieXRlc1RvSGV4KHRoaXMudG9CeXRlcyhmb3JtYXQpKTtcbiAgICB9XG4gIH1cbiAgdHlwZSBSZWNvdmVyZWRTaWduYXR1cmUgPSBTaWduYXR1cmUgJiB7IHJlY292ZXJ5OiBudW1iZXIgfTtcblxuICAvLyBSRkM2OTc5OiBlbnN1cmUgRUNEU0EgbXNnIGlzIFggYnl0ZXMgYW5kIDwgTi4gUkZDIHN1Z2dlc3RzIG9wdGlvbmFsIHRydW5jYXRpbmcgdmlhIGJpdHMyb2N0ZXRzLlxuICAvLyBGSVBTIDE4Ni00IDQuNiBzdWdnZXN0cyB0aGUgbGVmdG1vc3QgbWluKG5CaXRMZW4sIG91dExlbikgYml0cywgd2hpY2ggbWF0Y2hlcyBiaXRzMmludC5cbiAgLy8gYml0czJpbnQgY2FuIHByb2R1Y2UgcmVzPk4sIHdlIGNhbiBkbyBtb2QocmVzLCBOKSBzaW5jZSB0aGUgYml0TGVuIGlzIHRoZSBzYW1lLlxuICAvLyBpbnQyb2N0ZXRzIGNhbid0IGJlIHVzZWQ7IHBhZHMgc21hbGwgbXNncyB3aXRoIDA6IHVuYWNjZXB0YXRibGUgZm9yIHRydW5jIGFzIHBlciBSRkMgdmVjdG9yc1xuICBjb25zdCBiaXRzMmludCA9XG4gICAgZWNkc2FPcHRzLmJpdHMyaW50IHx8XG4gICAgZnVuY3Rpb24gYml0czJpbnRfZGVmKGJ5dGVzOiBVaW50OEFycmF5KTogYmlnaW50IHtcbiAgICAgIC8vIE91ciBjdXN0b20gY2hlY2sgXCJqdXN0IGluIGNhc2VcIiwgZm9yIHByb3RlY3Rpb24gYWdhaW5zdCBEb1NcbiAgICAgIGlmIChieXRlcy5sZW5ndGggPiA4MTkyKSB0aHJvdyBuZXcgRXJyb3IoJ2lucHV0IGlzIHRvbyBsYXJnZScpO1xuICAgICAgLy8gRm9yIGN1cnZlcyB3aXRoIG5CaXRMZW5ndGggJSA4ICE9PSAwOiBiaXRzMm9jdGV0cyhiaXRzMm9jdGV0cyhtKSkgIT09IGJpdHMyb2N0ZXRzKG0pXG4gICAgICAvLyBmb3Igc29tZSBjYXNlcywgc2luY2UgYnl0ZXMubGVuZ3RoICogOCBpcyBub3QgYWN0dWFsIGJpdExlbmd0aC5cbiAgICAgIGNvbnN0IG51bSA9IGJ5dGVzVG9OdW1iZXJCRShieXRlcyk7IC8vIGNoZWNrIGZvciA9PSB1OCBkb25lIGhlcmVcbiAgICAgIGNvbnN0IGRlbHRhID0gYnl0ZXMubGVuZ3RoICogOCAtIGZuQml0czsgLy8gdHJ1bmNhdGUgdG8gbkJpdExlbmd0aCBsZWZ0bW9zdCBiaXRzXG4gICAgICByZXR1cm4gZGVsdGEgPiAwID8gbnVtID4+IEJpZ0ludChkZWx0YSkgOiBudW07XG4gICAgfTtcbiAgY29uc3QgYml0czJpbnRfbW9kTiA9XG4gICAgZWNkc2FPcHRzLmJpdHMyaW50X21vZE4gfHxcbiAgICBmdW5jdGlvbiBiaXRzMmludF9tb2ROX2RlZihieXRlczogVWludDhBcnJheSk6IGJpZ2ludCB7XG4gICAgICByZXR1cm4gRm4uY3JlYXRlKGJpdHMyaW50KGJ5dGVzKSk7IC8vIGNhbid0IHVzZSBieXRlc1RvTnVtYmVyQkUgaGVyZVxuICAgIH07XG4gIC8vIFBhZHMgb3V0cHV0IHdpdGggemVybyBhcyBwZXIgc3BlY1xuICBjb25zdCBPUkRFUl9NQVNLID0gYml0TWFzayhmbkJpdHMpO1xuICAvKiogQ29udmVydHMgdG8gYnl0ZXMuIENoZWNrcyBpZiBudW0gaW4gYFswLi5PUkRFUl9NQVNLLTFdYCBlLmcuOiBgWzAuLjJeMjU2LTFdYC4gKi9cbiAgZnVuY3Rpb24gaW50Mm9jdGV0cyhudW06IGJpZ2ludCk6IFVpbnQ4QXJyYXkge1xuICAgIC8vIElNUE9SVEFOVDogdGhlIGNoZWNrIGVuc3VyZXMgd29ya2luZyBmb3IgY2FzZSBgRm4uQllURVMgIT0gRm4uQklUUyAqIDhgXG4gICAgYUluUmFuZ2UoJ251bSA8IDJeJyArIGZuQml0cywgbnVtLCBfMG4sIE9SREVSX01BU0spO1xuICAgIHJldHVybiBGbi50b0J5dGVzKG51bSk7XG4gIH1cblxuICBmdW5jdGlvbiB2YWxpZGF0ZU1zZ0FuZEhhc2gobWVzc2FnZTogVWludDhBcnJheSwgcHJlaGFzaDogYm9vbGVhbikge1xuICAgIGFieXRlcyhtZXNzYWdlLCB1bmRlZmluZWQsICdtZXNzYWdlJyk7XG4gICAgcmV0dXJuIHByZWhhc2ggPyBhYnl0ZXMoaGFzaChtZXNzYWdlKSwgdW5kZWZpbmVkLCAncHJlaGFzaGVkIG1lc3NhZ2UnKSA6IG1lc3NhZ2U7XG4gIH1cblxuICAvKipcbiAgICogU3RlcHMgQSwgRCBvZiBSRkM2OTc5IDMuMi5cbiAgICogQ3JlYXRlcyBSRkM2OTc5IHNlZWQ7IGNvbnZlcnRzIG1zZy9wcml2S2V5IHRvIG51bWJlcnMuXG4gICAqIFVzZWQgb25seSBpbiBzaWduLCBub3QgaW4gdmVyaWZ5LlxuICAgKlxuICAgKiBXYXJuaW5nOiB3ZSBjYW5ub3QgYXNzdW1lIGhlcmUgdGhhdCBtZXNzYWdlIGhhcyBzYW1lIGFtb3VudCBvZiBieXRlcyBhcyBjdXJ2ZSBvcmRlcixcbiAgICogdGhpcyB3aWxsIGJlIGludmFsaWQgYXQgbGVhc3QgZm9yIFA1MjEuIEFsc28gaXQgY2FuIGJlIGJpZ2dlciBmb3IgUDIyNCArIFNIQTI1Ni5cbiAgICovXG4gIGZ1bmN0aW9uIHByZXBTaWcobWVzc2FnZTogVWludDhBcnJheSwgc2VjcmV0S2V5OiBVaW50OEFycmF5LCBvcHRzOiBFQ0RTQVNpZ25PcHRzKSB7XG4gICAgY29uc3QgeyBsb3dTLCBwcmVoYXNoLCBleHRyYUVudHJvcHkgfSA9IHZhbGlkYXRlU2lnT3B0cyhvcHRzLCBkZWZhdWx0U2lnT3B0cyk7XG4gICAgbWVzc2FnZSA9IHZhbGlkYXRlTXNnQW5kSGFzaChtZXNzYWdlLCBwcmVoYXNoKTsgLy8gUkZDNjk3OSAzLjIgQTogaDEgPSBIKG0pXG4gICAgLy8gV2UgY2FuJ3QgbGF0ZXIgY2FsbCBiaXRzMm9jdGV0cywgc2luY2UgbmVzdGVkIGJpdHMyaW50IGlzIGJyb2tlbiBmb3IgY3VydmVzXG4gICAgLy8gd2l0aCBmbkJpdHMgJSA4ICE9PSAwLiBCZWNhdXNlIG9mIHRoYXQsIHdlIHVud3JhcCBpdCBoZXJlIGFzIGludDJvY3RldHMgY2FsbC5cbiAgICAvLyBjb25zdCBiaXRzMm9jdGV0cyA9IChiaXRzKSA9PiBpbnQyb2N0ZXRzKGJpdHMyaW50X21vZE4oYml0cykpXG4gICAgY29uc3QgaDFpbnQgPSBiaXRzMmludF9tb2ROKG1lc3NhZ2UpO1xuICAgIGNvbnN0IGQgPSBGbi5mcm9tQnl0ZXMoc2VjcmV0S2V5KTsgLy8gdmFsaWRhdGUgc2VjcmV0IGtleSwgY29udmVydCB0byBiaWdpbnRcbiAgICBpZiAoIUZuLmlzVmFsaWROb3QwKGQpKSB0aHJvdyBuZXcgRXJyb3IoJ2ludmFsaWQgcHJpdmF0ZSBrZXknKTtcbiAgICBjb25zdCBzZWVkQXJncyA9IFtpbnQyb2N0ZXRzKGQpLCBpbnQyb2N0ZXRzKGgxaW50KV07XG4gICAgLy8gZXh0cmFFbnRyb3B5LiBSRkM2OTc5IDMuNjogYWRkaXRpb25hbCBrJyAob3B0aW9uYWwpLlxuICAgIGlmIChleHRyYUVudHJvcHkgIT0gbnVsbCAmJiBleHRyYUVudHJvcHkgIT09IGZhbHNlKSB7XG4gICAgICAvLyBLID0gSE1BQ19LKFYgfHwgMHgwMCB8fCBpbnQyb2N0ZXRzKHgpIHx8IGJpdHMyb2N0ZXRzKGgxKSB8fCBrJylcbiAgICAgIC8vIGdlbiByYW5kb20gYnl0ZXMgT1IgcGFzcyBhcy1pc1xuICAgICAgY29uc3QgZSA9IGV4dHJhRW50cm9weSA9PT0gdHJ1ZSA/IHJhbmRvbUJ5dGVzKGxlbmd0aHMuc2VjcmV0S2V5KSA6IGV4dHJhRW50cm9weTtcbiAgICAgIHNlZWRBcmdzLnB1c2goYWJ5dGVzKGUsIHVuZGVmaW5lZCwgJ2V4dHJhRW50cm9weScpKTsgLy8gY2hlY2sgZm9yIGJlaW5nIGJ5dGVzXG4gICAgfVxuICAgIGNvbnN0IHNlZWQgPSBjb25jYXRCeXRlcyguLi5zZWVkQXJncyk7IC8vIFN0ZXAgRCBvZiBSRkM2OTc5IDMuMlxuICAgIGNvbnN0IG0gPSBoMWludDsgLy8gbm8gbmVlZCB0byBjYWxsIGJpdHMyaW50IHNlY29uZCB0aW1lIGhlcmUsIGl0IGlzIGluc2lkZSB0cnVuY2F0ZUhhc2ghXG4gICAgLy8gQ29udmVydHMgc2lnbmF0dXJlIHBhcmFtcyBpbnRvIHBvaW50IHcgci9zLCBjaGVja3MgcmVzdWx0IGZvciB2YWxpZGl0eS5cbiAgICAvLyBUbyB0cmFuc2Zvcm0gayA9PiBTaWduYXR1cmU6XG4gICAgLy8gcSA9IGtcdTIyQzVHXG4gICAgLy8gciA9IHEueCBtb2QgblxuICAgIC8vIHMgPSBrXi0xKG0gKyByZCkgbW9kIG5cbiAgICAvLyBDYW4gdXNlIHNjYWxhciBibGluZGluZyBiXi0xKGJtICsgYmRyKSB3aGVyZSBiIFx1MjIwOCBbMSxxXHUyMjEyMV0gYWNjb3JkaW5nIHRvXG4gICAgLy8gaHR0cHM6Ly90Y2hlcy5pYWNyLm9yZy9pbmRleC5waHAvVENIRVMvYXJ0aWNsZS92aWV3LzczMzcvNjUwOS4gV2UndmUgZGVjaWRlZCBhZ2FpbnN0IGl0OlxuICAgIC8vIGEpIGRlcGVuZGVuY3kgb24gQ1NQUk5HIGIpIDE1JSBzbG93ZG93biBjKSBkb2Vzbid0IHJlYWxseSBoZWxwIHNpbmNlIGJpZ2ludHMgYXJlIG5vdCBDVFxuICAgIGZ1bmN0aW9uIGsyc2lnKGtCeXRlczogVWludDhBcnJheSk6IFNpZ25hdHVyZSB8IHVuZGVmaW5lZCB7XG4gICAgICAvLyBSRkMgNjk3OSBTZWN0aW9uIDMuMiwgc3RlcCAzOiBrID0gYml0czJpbnQoVClcbiAgICAgIC8vIEltcG9ydGFudDogYWxsIG1vZCgpIGNhbGxzIGhlcmUgbXVzdCBiZSBkb25lIG92ZXIgTlxuICAgICAgY29uc3QgayA9IGJpdHMyaW50KGtCeXRlcyk7IC8vIENhbm5vdCB1c2UgZmllbGRzIG1ldGhvZHMsIHNpbmNlIGl0IGlzIGdyb3VwIGVsZW1lbnRcbiAgICAgIGlmICghRm4uaXNWYWxpZE5vdDAoaykpIHJldHVybjsgLy8gVmFsaWQgc2NhbGFycyAoaW5jbHVkaW5nIGspIG11c3QgYmUgaW4gMS4uTi0xXG4gICAgICBjb25zdCBpayA9IEZuLmludihrKTsgLy8ga14tMSBtb2QgblxuICAgICAgY29uc3QgcSA9IFBvaW50LkJBU0UubXVsdGlwbHkoaykudG9BZmZpbmUoKTsgLy8gcSA9IGtcdTIyQzVHXG4gICAgICBjb25zdCByID0gRm4uY3JlYXRlKHEueCk7IC8vIHIgPSBxLnggbW9kIG5cbiAgICAgIGlmIChyID09PSBfMG4pIHJldHVybjtcbiAgICAgIGNvbnN0IHMgPSBGbi5jcmVhdGUoaWsgKiBGbi5jcmVhdGUobSArIHIgKiBkKSk7IC8vIHMgPSBrXi0xKG0gKyByZCkgbW9kIG5cbiAgICAgIGlmIChzID09PSBfMG4pIHJldHVybjtcbiAgICAgIGxldCByZWNvdmVyeSA9IChxLnggPT09IHIgPyAwIDogMikgfCBOdW1iZXIocS55ICYgXzFuKTsgLy8gcmVjb3ZlcnkgYml0ICgyIG9yIDMgd2hlbiBxLng+bilcbiAgICAgIGxldCBub3JtUyA9IHM7XG4gICAgICBpZiAobG93UyAmJiBpc0JpZ2dlclRoYW5IYWxmT3JkZXIocykpIHtcbiAgICAgICAgbm9ybVMgPSBGbi5uZWcocyk7IC8vIGlmIGxvd1Mgd2FzIHBhc3NlZCwgZW5zdXJlIHMgaXMgYWx3YXlzIGluIHRoZSBib3R0b20gaGFsZiBvZiBOXG4gICAgICAgIHJlY292ZXJ5IF49IDE7XG4gICAgICB9XG4gICAgICByZXR1cm4gbmV3IFNpZ25hdHVyZShyLCBub3JtUywgaGFzTGFyZ2VDb2ZhY3RvciA/IHVuZGVmaW5lZCA6IHJlY292ZXJ5KTtcbiAgICB9XG4gICAgcmV0dXJuIHsgc2VlZCwgazJzaWcgfTtcbiAgfVxuXG4gIC8qKlxuICAgKiBTaWducyBtZXNzYWdlIGhhc2ggd2l0aCBhIHNlY3JldCBrZXkuXG4gICAqXG4gICAqIGBgYFxuICAgKiBzaWduKG0sIGQpIHdoZXJlXG4gICAqICAgayA9IHJmYzY5NzlfaG1hY19kcmJnKG0sIGQpXG4gICAqICAgKHgsIHkpID0gRyBcdTAwRDcga1xuICAgKiAgIHIgPSB4IG1vZCBuXG4gICAqICAgcyA9IChtICsgZHIpIC8gayBtb2QgblxuICAgKiBgYGBcbiAgICovXG4gIGZ1bmN0aW9uIHNpZ24obWVzc2FnZTogVWludDhBcnJheSwgc2VjcmV0S2V5OiBVaW50OEFycmF5LCBvcHRzOiBFQ0RTQVNpZ25PcHRzID0ge30pOiBVaW50OEFycmF5IHtcbiAgICBjb25zdCB7IHNlZWQsIGsyc2lnIH0gPSBwcmVwU2lnKG1lc3NhZ2UsIHNlY3JldEtleSwgb3B0cyk7IC8vIFN0ZXBzIEEsIEQgb2YgUkZDNjk3OSAzLjIuXG4gICAgY29uc3QgZHJiZyA9IGNyZWF0ZUhtYWNEcmJnPFNpZ25hdHVyZT4oaGFzaC5vdXRwdXRMZW4sIEZuLkJZVEVTLCBobWFjKTtcbiAgICBjb25zdCBzaWcgPSBkcmJnKHNlZWQsIGsyc2lnKTsgLy8gU3RlcHMgQiwgQywgRCwgRSwgRiwgR1xuICAgIHJldHVybiBzaWcudG9CeXRlcyhvcHRzLmZvcm1hdCk7XG4gIH1cblxuICAvKipcbiAgICogVmVyaWZpZXMgYSBzaWduYXR1cmUgYWdhaW5zdCBtZXNzYWdlIGFuZCBwdWJsaWMga2V5LlxuICAgKiBSZWplY3RzIGxvd1Mgc2lnbmF0dXJlcyBieSBkZWZhdWx0OiBzZWUge0BsaW5rIEVDRFNBVmVyaWZ5T3B0c30uXG4gICAqIEltcGxlbWVudHMgc2VjdGlvbiA0LjEuNCBmcm9tIGh0dHBzOi8vd3d3LnNlY2cub3JnL3NlYzEtdjIucGRmOlxuICAgKlxuICAgKiBgYGBcbiAgICogdmVyaWZ5KHIsIHMsIGgsIFApIHdoZXJlXG4gICAqICAgdTEgPSBoc14tMSBtb2QgblxuICAgKiAgIHUyID0gcnNeLTEgbW9kIG5cbiAgICogICBSID0gdTFcdTIyQzVHICsgdTJcdTIyQzVQXG4gICAqICAgbW9kKFIueCwgbikgPT0gclxuICAgKiBgYGBcbiAgICovXG4gIGZ1bmN0aW9uIHZlcmlmeShcbiAgICBzaWduYXR1cmU6IFVpbnQ4QXJyYXksXG4gICAgbWVzc2FnZTogVWludDhBcnJheSxcbiAgICBwdWJsaWNLZXk6IFVpbnQ4QXJyYXksXG4gICAgb3B0czogRUNEU0FWZXJpZnlPcHRzID0ge31cbiAgKTogYm9vbGVhbiB7XG4gICAgY29uc3QgeyBsb3dTLCBwcmVoYXNoLCBmb3JtYXQgfSA9IHZhbGlkYXRlU2lnT3B0cyhvcHRzLCBkZWZhdWx0U2lnT3B0cyk7XG4gICAgcHVibGljS2V5ID0gYWJ5dGVzKHB1YmxpY0tleSwgdW5kZWZpbmVkLCAncHVibGljS2V5Jyk7XG4gICAgbWVzc2FnZSA9IHZhbGlkYXRlTXNnQW5kSGFzaChtZXNzYWdlLCBwcmVoYXNoKTtcbiAgICBpZiAoIWlzQnl0ZXMoc2lnbmF0dXJlIGFzIGFueSkpIHtcbiAgICAgIGNvbnN0IGVuZCA9IHNpZ25hdHVyZSBpbnN0YW5jZW9mIFNpZ25hdHVyZSA/ICcsIHVzZSBzaWcudG9CeXRlcygpJyA6ICcnO1xuICAgICAgdGhyb3cgbmV3IEVycm9yKCd2ZXJpZnkgZXhwZWN0cyBVaW50OEFycmF5IHNpZ25hdHVyZScgKyBlbmQpO1xuICAgIH1cbiAgICB2YWxpZGF0ZVNpZ0xlbmd0aChzaWduYXR1cmUsIGZvcm1hdCk7IC8vIGV4ZWN1dGUgdGhpcyB0d2ljZSBiZWNhdXNlIHdlIHdhbnQgbG91ZCBlcnJvclxuICAgIHRyeSB7XG4gICAgICBjb25zdCBzaWcgPSBTaWduYXR1cmUuZnJvbUJ5dGVzKHNpZ25hdHVyZSwgZm9ybWF0KTtcbiAgICAgIGNvbnN0IFAgPSBQb2ludC5mcm9tQnl0ZXMocHVibGljS2V5KTtcbiAgICAgIGlmIChsb3dTICYmIHNpZy5oYXNIaWdoUygpKSByZXR1cm4gZmFsc2U7XG4gICAgICBjb25zdCB7IHIsIHMgfSA9IHNpZztcbiAgICAgIGNvbnN0IGggPSBiaXRzMmludF9tb2ROKG1lc3NhZ2UpOyAvLyBtb2Qgbiwgbm90IG1vZCBwXG4gICAgICBjb25zdCBpcyA9IEZuLmludihzKTsgLy8gc14tMSBtb2QgblxuICAgICAgY29uc3QgdTEgPSBGbi5jcmVhdGUoaCAqIGlzKTsgLy8gdTEgPSBoc14tMSBtb2QgblxuICAgICAgY29uc3QgdTIgPSBGbi5jcmVhdGUociAqIGlzKTsgLy8gdTIgPSByc14tMSBtb2QgblxuICAgICAgY29uc3QgUiA9IFBvaW50LkJBU0UubXVsdGlwbHlVbnNhZmUodTEpLmFkZChQLm11bHRpcGx5VW5zYWZlKHUyKSk7IC8vIHUxXHUyMkM1RyArIHUyXHUyMkM1UFxuICAgICAgaWYgKFIuaXMwKCkpIHJldHVybiBmYWxzZTtcbiAgICAgIGNvbnN0IHYgPSBGbi5jcmVhdGUoUi54KTsgLy8gdiA9IHIueCBtb2QgblxuICAgICAgcmV0dXJuIHYgPT09IHI7XG4gICAgfSBjYXRjaCAoZSkge1xuICAgICAgcmV0dXJuIGZhbHNlO1xuICAgIH1cbiAgfVxuXG4gIGZ1bmN0aW9uIHJlY292ZXJQdWJsaWNLZXkoXG4gICAgc2lnbmF0dXJlOiBVaW50OEFycmF5LFxuICAgIG1lc3NhZ2U6IFVpbnQ4QXJyYXksXG4gICAgb3B0czogRUNEU0FSZWNvdmVyT3B0cyA9IHt9XG4gICk6IFVpbnQ4QXJyYXkge1xuICAgIGNvbnN0IHsgcHJlaGFzaCB9ID0gdmFsaWRhdGVTaWdPcHRzKG9wdHMsIGRlZmF1bHRTaWdPcHRzKTtcbiAgICBtZXNzYWdlID0gdmFsaWRhdGVNc2dBbmRIYXNoKG1lc3NhZ2UsIHByZWhhc2gpO1xuICAgIHJldHVybiBTaWduYXR1cmUuZnJvbUJ5dGVzKHNpZ25hdHVyZSwgJ3JlY292ZXJlZCcpLnJlY292ZXJQdWJsaWNLZXkobWVzc2FnZSkudG9CeXRlcygpO1xuICB9XG5cbiAgcmV0dXJuIE9iamVjdC5mcmVlemUoe1xuICAgIGtleWdlbixcbiAgICBnZXRQdWJsaWNLZXksXG4gICAgZ2V0U2hhcmVkU2VjcmV0LFxuICAgIHV0aWxzLFxuICAgIGxlbmd0aHMsXG4gICAgUG9pbnQsXG4gICAgc2lnbixcbiAgICB2ZXJpZnksXG4gICAgcmVjb3ZlclB1YmxpY0tleSxcbiAgICBTaWduYXR1cmUsXG4gICAgaGFzaCxcbiAgfSkgc2F0aXNmaWVzIFNpZ25lcjtcbn1cbiIsICIvKipcbiAqIEhNQUM6IFJGQzIxMDQgbWVzc2FnZSBhdXRoZW50aWNhdGlvbiBjb2RlLlxuICogQG1vZHVsZVxuICovXG5pbXBvcnQgeyBhYnl0ZXMsIGFleGlzdHMsIGFoYXNoLCBjbGVhbiwgdHlwZSBDSGFzaCwgdHlwZSBIYXNoIH0gZnJvbSAnLi91dGlscy50cyc7XG5cbi8qKiBJbnRlcm5hbCBjbGFzcyBmb3IgSE1BQy4gKi9cbmV4cG9ydCBjbGFzcyBfSE1BQzxUIGV4dGVuZHMgSGFzaDxUPj4gaW1wbGVtZW50cyBIYXNoPF9ITUFDPFQ+PiB7XG4gIG9IYXNoOiBUO1xuICBpSGFzaDogVDtcbiAgYmxvY2tMZW46IG51bWJlcjtcbiAgb3V0cHV0TGVuOiBudW1iZXI7XG4gIHByaXZhdGUgZmluaXNoZWQgPSBmYWxzZTtcbiAgcHJpdmF0ZSBkZXN0cm95ZWQgPSBmYWxzZTtcblxuICBjb25zdHJ1Y3RvcihoYXNoOiBDSGFzaCwga2V5OiBVaW50OEFycmF5KSB7XG4gICAgYWhhc2goaGFzaCk7XG4gICAgYWJ5dGVzKGtleSwgdW5kZWZpbmVkLCAna2V5Jyk7XG4gICAgdGhpcy5pSGFzaCA9IGhhc2guY3JlYXRlKCkgYXMgVDtcbiAgICBpZiAodHlwZW9mIHRoaXMuaUhhc2gudXBkYXRlICE9PSAnZnVuY3Rpb24nKVxuICAgICAgdGhyb3cgbmV3IEVycm9yKCdFeHBlY3RlZCBpbnN0YW5jZSBvZiBjbGFzcyB3aGljaCBleHRlbmRzIHV0aWxzLkhhc2gnKTtcbiAgICB0aGlzLmJsb2NrTGVuID0gdGhpcy5pSGFzaC5ibG9ja0xlbjtcbiAgICB0aGlzLm91dHB1dExlbiA9IHRoaXMuaUhhc2gub3V0cHV0TGVuO1xuICAgIGNvbnN0IGJsb2NrTGVuID0gdGhpcy5ibG9ja0xlbjtcbiAgICBjb25zdCBwYWQgPSBuZXcgVWludDhBcnJheShibG9ja0xlbik7XG4gICAgLy8gYmxvY2tMZW4gY2FuIGJlIGJpZ2dlciB0aGFuIG91dHB1dExlblxuICAgIHBhZC5zZXQoa2V5Lmxlbmd0aCA+IGJsb2NrTGVuID8gaGFzaC5jcmVhdGUoKS51cGRhdGUoa2V5KS5kaWdlc3QoKSA6IGtleSk7XG4gICAgZm9yIChsZXQgaSA9IDA7IGkgPCBwYWQubGVuZ3RoOyBpKyspIHBhZFtpXSBePSAweDM2O1xuICAgIHRoaXMuaUhhc2gudXBkYXRlKHBhZCk7XG4gICAgLy8gQnkgZG9pbmcgdXBkYXRlIChwcm9jZXNzaW5nIG9mIGZpcnN0IGJsb2NrKSBvZiBvdXRlciBoYXNoIGhlcmUgd2UgY2FuIHJlLXVzZSBpdCBiZXR3ZWVuIG11bHRpcGxlIGNhbGxzIHZpYSBjbG9uZVxuICAgIHRoaXMub0hhc2ggPSBoYXNoLmNyZWF0ZSgpIGFzIFQ7XG4gICAgLy8gVW5kbyBpbnRlcm5hbCBYT1IgJiYgYXBwbHkgb3V0ZXIgWE9SXG4gICAgZm9yIChsZXQgaSA9IDA7IGkgPCBwYWQubGVuZ3RoOyBpKyspIHBhZFtpXSBePSAweDM2IF4gMHg1YztcbiAgICB0aGlzLm9IYXNoLnVwZGF0ZShwYWQpO1xuICAgIGNsZWFuKHBhZCk7XG4gIH1cbiAgdXBkYXRlKGJ1ZjogVWludDhBcnJheSk6IHRoaXMge1xuICAgIGFleGlzdHModGhpcyk7XG4gICAgdGhpcy5pSGFzaC51cGRhdGUoYnVmKTtcbiAgICByZXR1cm4gdGhpcztcbiAgfVxuICBkaWdlc3RJbnRvKG91dDogVWludDhBcnJheSk6IHZvaWQge1xuICAgIGFleGlzdHModGhpcyk7XG4gICAgYWJ5dGVzKG91dCwgdGhpcy5vdXRwdXRMZW4sICdvdXRwdXQnKTtcbiAgICB0aGlzLmZpbmlzaGVkID0gdHJ1ZTtcbiAgICB0aGlzLmlIYXNoLmRpZ2VzdEludG8ob3V0KTtcbiAgICB0aGlzLm9IYXNoLnVwZGF0ZShvdXQpO1xuICAgIHRoaXMub0hhc2guZGlnZXN0SW50byhvdXQpO1xuICAgIHRoaXMuZGVzdHJveSgpO1xuICB9XG4gIGRpZ2VzdCgpOiBVaW50OEFycmF5IHtcbiAgICBjb25zdCBvdXQgPSBuZXcgVWludDhBcnJheSh0aGlzLm9IYXNoLm91dHB1dExlbik7XG4gICAgdGhpcy5kaWdlc3RJbnRvKG91dCk7XG4gICAgcmV0dXJuIG91dDtcbiAgfVxuICBfY2xvbmVJbnRvKHRvPzogX0hNQUM8VD4pOiBfSE1BQzxUPiB7XG4gICAgLy8gQ3JlYXRlIG5ldyBpbnN0YW5jZSB3aXRob3V0IGNhbGxpbmcgY29uc3RydWN0b3Igc2luY2Uga2V5IGFscmVhZHkgaW4gc3RhdGUgYW5kIHdlIGRvbid0IGtub3cgaXQuXG4gICAgdG8gfHw9IE9iamVjdC5jcmVhdGUoT2JqZWN0LmdldFByb3RvdHlwZU9mKHRoaXMpLCB7fSk7XG4gICAgY29uc3QgeyBvSGFzaCwgaUhhc2gsIGZpbmlzaGVkLCBkZXN0cm95ZWQsIGJsb2NrTGVuLCBvdXRwdXRMZW4gfSA9IHRoaXM7XG4gICAgdG8gPSB0byBhcyB0aGlzO1xuICAgIHRvLmZpbmlzaGVkID0gZmluaXNoZWQ7XG4gICAgdG8uZGVzdHJveWVkID0gZGVzdHJveWVkO1xuICAgIHRvLmJsb2NrTGVuID0gYmxvY2tMZW47XG4gICAgdG8ub3V0cHV0TGVuID0gb3V0cHV0TGVuO1xuICAgIHRvLm9IYXNoID0gb0hhc2guX2Nsb25lSW50byh0by5vSGFzaCk7XG4gICAgdG8uaUhhc2ggPSBpSGFzaC5fY2xvbmVJbnRvKHRvLmlIYXNoKTtcbiAgICByZXR1cm4gdG87XG4gIH1cbiAgY2xvbmUoKTogX0hNQUM8VD4ge1xuICAgIHJldHVybiB0aGlzLl9jbG9uZUludG8oKTtcbiAgfVxuICBkZXN0cm95KCk6IHZvaWQge1xuICAgIHRoaXMuZGVzdHJveWVkID0gdHJ1ZTtcbiAgICB0aGlzLm9IYXNoLmRlc3Ryb3koKTtcbiAgICB0aGlzLmlIYXNoLmRlc3Ryb3koKTtcbiAgfVxufVxuXG4vKipcbiAqIEhNQUM6IFJGQzIxMDQgbWVzc2FnZSBhdXRoZW50aWNhdGlvbiBjb2RlLlxuICogQHBhcmFtIGhhc2ggLSBmdW5jdGlvbiB0aGF0IHdvdWxkIGJlIHVzZWQgZS5nLiBzaGEyNTZcbiAqIEBwYXJhbSBrZXkgLSBtZXNzYWdlIGtleVxuICogQHBhcmFtIG1lc3NhZ2UgLSBtZXNzYWdlIGRhdGFcbiAqIEBleGFtcGxlXG4gKiBpbXBvcnQgeyBobWFjIH0gZnJvbSAnQG5vYmxlL2hhc2hlcy9obWFjJztcbiAqIGltcG9ydCB7IHNoYTI1NiB9IGZyb20gJ0Bub2JsZS9oYXNoZXMvc2hhMic7XG4gKiBjb25zdCBtYWMxID0gaG1hYyhzaGEyNTYsICdrZXknLCAnbWVzc2FnZScpO1xuICovXG5leHBvcnQgY29uc3QgaG1hYzoge1xuICAoaGFzaDogQ0hhc2gsIGtleTogVWludDhBcnJheSwgbWVzc2FnZTogVWludDhBcnJheSk6IFVpbnQ4QXJyYXk7XG4gIGNyZWF0ZShoYXNoOiBDSGFzaCwga2V5OiBVaW50OEFycmF5KTogX0hNQUM8YW55Pjtcbn0gPSAoaGFzaDogQ0hhc2gsIGtleTogVWludDhBcnJheSwgbWVzc2FnZTogVWludDhBcnJheSk6IFVpbnQ4QXJyYXkgPT5cbiAgbmV3IF9ITUFDPGFueT4oaGFzaCwga2V5KS51cGRhdGUobWVzc2FnZSkuZGlnZXN0KCk7XG5obWFjLmNyZWF0ZSA9IChoYXNoOiBDSGFzaCwga2V5OiBVaW50OEFycmF5KSA9PiBuZXcgX0hNQUM8YW55PihoYXNoLCBrZXkpO1xuIiwgIi8qKlxuICogQG1vZHVsZSBsb2dnZXJcbiAqIEBkZXNjcmlwdGlvbiBMb2dnZXIgdXRpbGl0eSBmb3IgdGhlIGFwcGxpY2F0aW9uXG4gKi9cblxuZW51bSBMb2dMZXZlbCB7XG4gIERFQlVHLFxuICBJTkZPLFxuICBXQVJOLFxuICBFUlJPUlxufVxuXG5pbXBvcnQgcGlubyBmcm9tICdwaW5vJztcblxuLyoqXG4gKiBDcmVhdGUgYSBsb2dnZXIgaW5zdGFuY2Ugd2l0aCBjb25zaXN0ZW50IGNvbmZpZ3VyYXRpb25cbiAqIEBwYXJhbSBuYW1lIC0gQ29tcG9uZW50IG9yIG1vZHVsZSBuYW1lIGZvciB0aGUgbG9nZ2VyXG4gKiBAcmV0dXJucyBDb25maWd1cmVkIHBpbm8gbG9nZ2VyIGluc3RhbmNlXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBjcmVhdGVMb2dnZXIobmFtZTogc3RyaW5nKTogcGluby5Mb2dnZXIge1xuICByZXR1cm4gcGlubyh7XG4gICAgbmFtZSxcbiAgICBsZXZlbDogcHJvY2Vzcy5lbnYuTE9HX0xFVkVMIHx8ICdpbmZvJyxcbiAgICB0cmFuc3BvcnQ6IHByb2Nlc3MuZW52Lk5PREVfRU5WID09PSAnZGV2ZWxvcG1lbnQnID8ge1xuICAgICAgdGFyZ2V0OiAncGluby1wcmV0dHknLFxuICAgICAgb3B0aW9uczoge1xuICAgICAgICBjb2xvcml6ZTogdHJ1ZSxcbiAgICAgICAgdHJhbnNsYXRlVGltZTogJ0hIOk1NOnNzJyxcbiAgICAgICAgaWdub3JlOiAncGlkLGhvc3RuYW1lJyxcbiAgICAgIH1cbiAgICB9IDogdW5kZWZpbmVkLFxuICAgIGZvcm1hdHRlcnM6IHtcbiAgICAgIGxldmVsOiAobGFiZWwpID0+IHtcbiAgICAgICAgcmV0dXJuIHsgbGV2ZWw6IGxhYmVsLnRvVXBwZXJDYXNlKCkgfTtcbiAgICAgIH1cbiAgICB9XG4gIH0pO1xufVxuXG4vKipcbiAqIFNpbXBsZSBsb2cgZnVuY3Rpb24gZm9yIGJhc2ljIGxvZ2dpbmcgbmVlZHNcbiAqIEBwYXJhbSBtZXNzYWdlIC0gTWVzc2FnZSB0byBsb2dcbiAqIEBwYXJhbSBkYXRhIC0gT3B0aW9uYWwgZGF0YSB0byBpbmNsdWRlXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBsb2cobWVzc2FnZTogc3RyaW5nLCBkYXRhPzogdW5rbm93bik6IHZvaWQge1xuICBjb25zb2xlLmxvZyhtZXNzYWdlLCBkYXRhKTtcbn1cblxuLyoqXG4gKiBEZWZhdWx0IGxvZ2dlciBpbnN0YW5jZSBmb3IgdGhlIGFwcGxpY2F0aW9uXG4gKiBJbmNsdWRlcyBlbmhhbmNlZCBlcnJvciBoYW5kbGluZyBhbmQgZm9ybWF0dGluZ1xuICovXG5leHBvcnQgY29uc3QgbG9nZ2VyOiBwaW5vLkxvZ2dlciA9IHBpbm8oe1xuICBuYW1lOiAnbm9zdHItY3J5cHRvLXV0aWxzJyxcbiAgbGV2ZWw6IHByb2Nlc3MuZW52LkxPR19MRVZFTCB8fCAnaW5mbycsXG4gIHRyYW5zcG9ydDogcHJvY2Vzcy5lbnYuTk9ERV9FTlYgPT09ICdkZXZlbG9wbWVudCcgPyB7XG4gICAgdGFyZ2V0OiAncGluby1wcmV0dHknLFxuICAgIG9wdGlvbnM6IHtcbiAgICAgIGNvbG9yaXplOiB0cnVlLFxuICAgICAgdHJhbnNsYXRlVGltZTogJ0hIOk1NOnNzJyxcbiAgICAgIGlnbm9yZTogJ3BpZCxob3N0bmFtZScsXG4gICAgfVxuICB9IDogdW5kZWZpbmVkLFxuICBmb3JtYXR0ZXJzOiB7XG4gICAgbGV2ZWw6IChsYWJlbCkgPT4ge1xuICAgICAgcmV0dXJuIHsgbGV2ZWw6IGxhYmVsLnRvVXBwZXJDYXNlKCkgfTtcbiAgICB9LFxuICAgIGxvZzogKG9iajogUmVjb3JkPHN0cmluZywgdW5rbm93bj4pID0+IHtcbiAgICAgIC8vIENvbnZlcnQgZXJyb3Igb2JqZWN0cyB0byBzdHJpbmdzIGZvciBiZXR0ZXIgbG9nZ2luZ1xuICAgICAgaWYgKG9iaiAmJiB0eXBlb2Ygb2JqID09PSAnb2JqZWN0JyAmJiAnZXJyJyBpbiBvYmopIHtcbiAgICAgICAgY29uc3QgbmV3T2JqID0geyAuLi5vYmogfTtcbiAgICAgICAgaWYgKG5ld09iai5lcnIgaW5zdGFuY2VvZiBFcnJvcikge1xuICAgICAgICAgIGNvbnN0IGVyciA9IG5ld09iai5lcnIgYXMgRXJyb3I7XG4gICAgICAgICAgbmV3T2JqLmVyciA9IHtcbiAgICAgICAgICAgIG1lc3NhZ2U6IGVyci5tZXNzYWdlLFxuICAgICAgICAgICAgc3RhY2s6IGVyci5zdGFjayxcbiAgICAgICAgICAgIG5hbWU6IGVyci5uYW1lLFxuICAgICAgICAgIH07XG4gICAgICAgIH1cbiAgICAgICAgcmV0dXJuIG5ld09iajtcbiAgICAgIH1cbiAgICAgIHJldHVybiBvYmo7XG4gICAgfVxuICB9XG59KTtcblxuZXhwb3J0IGNsYXNzIEN1c3RvbUxvZ2dlciB7XG4gIHByaXZhdGUgX2xldmVsOiBMb2dMZXZlbDtcblxuICBjb25zdHJ1Y3RvcihsZXZlbDogTG9nTGV2ZWwgPSBMb2dMZXZlbC5JTkZPKSB7XG4gICAgdGhpcy5fbGV2ZWwgPSBsZXZlbDtcbiAgfVxuXG4gIHNldExldmVsKGxldmVsOiBMb2dMZXZlbCk6IHZvaWQge1xuICAgIHRoaXMuX2xldmVsID0gbGV2ZWw7XG4gIH1cblxuICBwcml2YXRlIF9sb2cobGV2ZWw6IExvZ0xldmVsLCBtZXNzYWdlOiBzdHJpbmcsIGNvbnRleHQ/OiBSZWNvcmQ8c3RyaW5nLCB1bmtub3duPik6IHZvaWQge1xuICAgIGlmIChsZXZlbCA+PSB0aGlzLl9sZXZlbCkge1xuICAgICAgY29uc3QgdGltZXN0YW1wID0gbmV3IERhdGUoKS50b0lTT1N0cmluZygpO1xuICAgICAgY29uc3QgbGV2ZWxOYW1lID0gTG9nTGV2ZWxbbGV2ZWxdO1xuICAgICAgY29uc3QgY29udGV4dFN0ciA9IGNvbnRleHQgPyBgICR7SlNPTi5zdHJpbmdpZnkoY29udGV4dCl9YCA6ICcnO1xuICAgICAgY29uc29sZS5sb2coYFske3RpbWVzdGFtcH1dICR7bGV2ZWxOYW1lfTogJHttZXNzYWdlfSR7Y29udGV4dFN0cn1gKTtcbiAgICB9XG4gIH1cblxuICBkZWJ1ZyhtZXNzYWdlOiBzdHJpbmcsIGNvbnRleHQ/OiBSZWNvcmQ8c3RyaW5nLCB1bmtub3duPik6IHZvaWQge1xuICAgIHRoaXMuX2xvZyhMb2dMZXZlbC5ERUJVRywgbWVzc2FnZSwgY29udGV4dCk7XG4gIH1cblxuICBpbmZvKG1lc3NhZ2U6IHN0cmluZywgY29udGV4dD86IFJlY29yZDxzdHJpbmcsIHVua25vd24+KTogdm9pZCB7XG4gICAgdGhpcy5fbG9nKExvZ0xldmVsLklORk8sIG1lc3NhZ2UsIGNvbnRleHQpO1xuICB9XG5cbiAgd2FybihtZXNzYWdlOiBzdHJpbmcsIGNvbnRleHQ/OiBSZWNvcmQ8c3RyaW5nLCB1bmtub3duPik6IHZvaWQge1xuICAgIHRoaXMuX2xvZyhMb2dMZXZlbC5XQVJOLCBtZXNzYWdlLCBjb250ZXh0KTtcbiAgfVxuXG4gIGVycm9yKG1lc3NhZ2U6IHN0cmluZyB8IEVycm9yIHwgdW5rbm93biwgY29udGV4dD86IFJlY29yZDxzdHJpbmcsIHVua25vd24+KTogdm9pZCB7XG4gICAgY29uc3QgZXJyb3JNZXNzYWdlID0gbWVzc2FnZSBpbnN0YW5jZW9mIEVycm9yID8gbWVzc2FnZS5tZXNzYWdlIDogU3RyaW5nKG1lc3NhZ2UpO1xuICAgIHRoaXMuX2xvZyhMb2dMZXZlbC5FUlJPUiwgZXJyb3JNZXNzYWdlLCBjb250ZXh0KTtcbiAgfVxufVxuXG4vLyBSZS1leHBvcnQgdGhlIExvZ2dlciB0eXBlIGZvciB1c2UgaW4gb3RoZXIgZmlsZXNcbmV4cG9ydCB0eXBlIHsgTG9nZ2VyIH0gZnJvbSAncGlubyc7XG4iLCAiLyoqXG4gKiBCYXNlNjQgZW5jb2RpbmcgdXRpbGl0aWVzIGZvciBOb3N0clxuICogUHJvdmlkZXMgY29uc2lzdGVudCBiYXNlNjQgZW5jb2RpbmcvZGVjb2RpbmcgYWNyb3NzIGFsbCBOb3N0ci1yZWxhdGVkIHByb2plY3RzXG4gKiBVc2VzIGJyb3dzZXItY29tcGF0aWJsZSBBUElzIChubyBOb2RlLmpzIEJ1ZmZlciBkZXBlbmRlbmN5KVxuICovXG5cbi8qKlxuICogQ29udmVydCBzdHJpbmcgdG8gYmFzZTY0XG4gKiBAcGFyYW0gc3RyIFN0cmluZyB0byBjb252ZXJ0XG4gKiBAcmV0dXJucyBCYXNlNjQgc3RyaW5nXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBzdHJpbmdUb0Jhc2U2NChzdHI6IHN0cmluZyk6IHN0cmluZyB7XG4gIGNvbnN0IGJ5dGVzID0gbmV3IFRleHRFbmNvZGVyKCkuZW5jb2RlKHN0cik7XG4gIHJldHVybiBieXRlc1RvQmFzZTY0KGJ5dGVzKTtcbn1cblxuLyoqXG4gKiBDb252ZXJ0IGJhc2U2NCB0byBzdHJpbmdcbiAqIEBwYXJhbSBiYXNlNjQgQmFzZTY0IHN0cmluZyB0byBjb252ZXJ0XG4gKiBAcmV0dXJucyBVVEYtOCBzdHJpbmdcbiAqIEB0aHJvd3MgRXJyb3IgaWYgYmFzZTY0IHN0cmluZyBpcyBpbnZhbGlkXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBiYXNlNjRUb1N0cmluZyhiYXNlNjQ6IHN0cmluZyk6IHN0cmluZyB7XG4gIGlmICghaXNWYWxpZEJhc2U2NChiYXNlNjQpKSB7XG4gICAgdGhyb3cgbmV3IEVycm9yKCdJbnZhbGlkIGJhc2U2NCBzdHJpbmcnKTtcbiAgfVxuICBjb25zdCBieXRlcyA9IGJhc2U2NFRvQnl0ZXMoYmFzZTY0KTtcbiAgcmV0dXJuIG5ldyBUZXh0RGVjb2RlcigpLmRlY29kZShieXRlcyk7XG59XG5cbi8qKlxuICogQ29udmVydCBVaW50OEFycmF5IHRvIGJhc2U2NFxuICogQHBhcmFtIGJ1ZmZlciBVaW50OEFycmF5IHRvIGNvbnZlcnRcbiAqIEByZXR1cm5zIEJhc2U2NCBzdHJpbmdcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGJ1ZmZlclRvQmFzZTY0KGJ1ZmZlcjogVWludDhBcnJheSk6IHN0cmluZyB7XG4gIHJldHVybiBieXRlc1RvQmFzZTY0KGJ1ZmZlcik7XG59XG5cbi8qKlxuICogQ29udmVydCBiYXNlNjQgdG8gVWludDhBcnJheVxuICogQHBhcmFtIGJhc2U2NCBCYXNlNjQgc3RyaW5nIHRvIGNvbnZlcnRcbiAqIEByZXR1cm5zIFVpbnQ4QXJyYXlcbiAqIEB0aHJvd3MgRXJyb3IgaWYgYmFzZTY0IHN0cmluZyBpcyBpbnZhbGlkXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBiYXNlNjRUb0J1ZmZlcihiYXNlNjQ6IHN0cmluZyk6IFVpbnQ4QXJyYXkge1xuICBpZiAoIWlzVmFsaWRCYXNlNjQoYmFzZTY0KSkge1xuICAgIHRocm93IG5ldyBFcnJvcignSW52YWxpZCBiYXNlNjQgc3RyaW5nJyk7XG4gIH1cbiAgcmV0dXJuIGJhc2U2NFRvQnl0ZXMoYmFzZTY0KTtcbn1cblxuLyoqXG4gKiBDaGVjayBpZiBzdHJpbmcgaXMgdmFsaWQgYmFzZTY0XG4gKiBAcGFyYW0gYmFzZTY0IFN0cmluZyB0byBjaGVja1xuICogQHJldHVybnMgVHJ1ZSBpZiB2YWxpZCBiYXNlNjRcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGlzVmFsaWRCYXNlNjQoYmFzZTY0OiBzdHJpbmcpOiBib29sZWFuIHtcbiAgdHJ5IHtcbiAgICByZXR1cm4gQm9vbGVhbihiYXNlNjQubWF0Y2goL15bQS1aYS16MC05Ky9dKj17MCwyfSQvKSk7XG4gIH0gY2F0Y2gge1xuICAgIHJldHVybiBmYWxzZTtcbiAgfVxufVxuXG4vKipcbiAqIENvbnZlcnQgYmFzZTY0IHRvIFVSTC1zYWZlIGJhc2U2NFxuICogQHBhcmFtIGJhc2U2NCBTdGFuZGFyZCBiYXNlNjQgc3RyaW5nXG4gKiBAcmV0dXJucyBVUkwtc2FmZSBiYXNlNjQgc3RyaW5nXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiB0b0Jhc2U2NFVybChiYXNlNjQ6IHN0cmluZyk6IHN0cmluZyB7XG4gIHJldHVybiBiYXNlNjQucmVwbGFjZSgvXFwrL2csICctJykucmVwbGFjZSgvXFwvL2csICdfJykucmVwbGFjZSgvPSskLywgJycpO1xufVxuXG4vKipcbiAqIENvbnZlcnQgVVJMLXNhZmUgYmFzZTY0IHRvIHN0YW5kYXJkIGJhc2U2NFxuICogQHBhcmFtIGJhc2U2NHVybCBVUkwtc2FmZSBiYXNlNjQgc3RyaW5nXG4gKiBAcmV0dXJucyBTdGFuZGFyZCBiYXNlNjQgc3RyaW5nXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBmcm9tQmFzZTY0VXJsKGJhc2U2NHVybDogc3RyaW5nKTogc3RyaW5nIHtcbiAgY29uc3QgYmFzZTY0ID0gYmFzZTY0dXJsLnJlcGxhY2UoLy0vZywgJysnKS5yZXBsYWNlKC9fL2csICcvJyk7XG4gIGNvbnN0IHBhZGRpbmcgPSAnPScucmVwZWF0KCg0IC0gYmFzZTY0Lmxlbmd0aCAlIDQpICUgNCk7XG4gIHJldHVybiBiYXNlNjQgKyBwYWRkaW5nO1xufVxuXG4vKipcbiAqIENvbnZlcnQgaGV4IHN0cmluZyB0byBiYXNlNjRcbiAqIEBwYXJhbSBoZXggSGV4IHN0cmluZyB0byBjb252ZXJ0XG4gKiBAcmV0dXJucyBCYXNlNjQgc3RyaW5nXG4gKiBAdGhyb3dzIEVycm9yIGlmIGhleCBzdHJpbmcgaXMgaW52YWxpZFxuICovXG5leHBvcnQgZnVuY3Rpb24gaGV4VG9CYXNlNjQoaGV4OiBzdHJpbmcpOiBzdHJpbmcge1xuICBpZiAoIWhleC5tYXRjaCgvXlswLTlhLWZBLUZdKiQvKSkge1xuICAgIHRocm93IG5ldyBFcnJvcignSW52YWxpZCBoZXggc3RyaW5nJyk7XG4gIH1cbiAgY29uc3QgYnl0ZXMgPSBuZXcgVWludDhBcnJheShoZXgubGVuZ3RoIC8gMik7XG4gIGZvciAobGV0IGkgPSAwOyBpIDwgaGV4Lmxlbmd0aDsgaSArPSAyKSB7XG4gICAgYnl0ZXNbaSAvIDJdID0gcGFyc2VJbnQoaGV4LnN1YnN0cmluZyhpLCBpICsgMiksIDE2KTtcbiAgfVxuICByZXR1cm4gYnl0ZXNUb0Jhc2U2NChieXRlcyk7XG59XG5cbi8qKlxuICogQ29udmVydCBiYXNlNjQgdG8gaGV4IHN0cmluZ1xuICogQHBhcmFtIGJhc2U2NCBCYXNlNjQgc3RyaW5nIHRvIGNvbnZlcnRcbiAqIEByZXR1cm5zIEhleCBzdHJpbmdcbiAqIEB0aHJvd3MgRXJyb3IgaWYgYmFzZTY0IHN0cmluZyBpcyBpbnZhbGlkXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBiYXNlNjRUb0hleChiYXNlNjQ6IHN0cmluZyk6IHN0cmluZyB7XG4gIGlmICghaXNWYWxpZEJhc2U2NChiYXNlNjQpKSB7XG4gICAgdGhyb3cgbmV3IEVycm9yKCdJbnZhbGlkIGJhc2U2NCBzdHJpbmcnKTtcbiAgfVxuICBjb25zdCBieXRlcyA9IGJhc2U2NFRvQnl0ZXMoYmFzZTY0KTtcbiAgcmV0dXJuIEFycmF5LmZyb20oYnl0ZXMpLm1hcChiID0+IGIudG9TdHJpbmcoMTYpLnBhZFN0YXJ0KDIsICcwJykpLmpvaW4oJycpO1xufVxuXG4vKipcbiAqIENyZWF0ZSBiYXNlNjQgc3RyaW5nIGZyb20gYnl0ZSBhcnJheVxuICogQHBhcmFtIGJ5dGVzIEJ5dGUgYXJyYXlcbiAqIEByZXR1cm5zIEJhc2U2NCBzdHJpbmdcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGJ5dGVzVG9CYXNlNjQoYnl0ZXM6IFVpbnQ4QXJyYXkpOiBzdHJpbmcge1xuICBsZXQgYmluYXJ5ID0gJyc7XG4gIGZvciAobGV0IGkgPSAwOyBpIDwgYnl0ZXMubGVuZ3RoOyBpKyspIHtcbiAgICBiaW5hcnkgKz0gU3RyaW5nLmZyb21DaGFyQ29kZShieXRlc1tpXSk7XG4gIH1cbiAgcmV0dXJuIGJ0b2EoYmluYXJ5KTtcbn1cblxuLyoqXG4gKiBDb252ZXJ0IGJhc2U2NCB0byBieXRlIGFycmF5XG4gKiBAcGFyYW0gYmFzZTY0IEJhc2U2NCBzdHJpbmdcbiAqIEByZXR1cm5zIEJ5dGUgYXJyYXlcbiAqIEB0aHJvd3MgRXJyb3IgaWYgYmFzZTY0IHN0cmluZyBpcyBpbnZhbGlkXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBiYXNlNjRUb0J5dGVzKGJhc2U2NDogc3RyaW5nKTogVWludDhBcnJheSB7XG4gIGlmICghaXNWYWxpZEJhc2U2NChiYXNlNjQpKSB7XG4gICAgdGhyb3cgbmV3IEVycm9yKCdJbnZhbGlkIGJhc2U2NCBzdHJpbmcnKTtcbiAgfVxuICBjb25zdCBiaW5hcnkgPSBhdG9iKGJhc2U2NCk7XG4gIGNvbnN0IGJ5dGVzID0gbmV3IFVpbnQ4QXJyYXkoYmluYXJ5Lmxlbmd0aCk7XG4gIGZvciAobGV0IGkgPSAwOyBpIDwgYmluYXJ5Lmxlbmd0aDsgaSsrKSB7XG4gICAgYnl0ZXNbaV0gPSBiaW5hcnkuY2hhckNvZGVBdChpKTtcbiAgfVxuICByZXR1cm4gYnl0ZXM7XG59XG5cbi8qKlxuICogQ2FsY3VsYXRlIHBhZGRlZCBsZW5ndGggZm9yIGJhc2U2NCBzdHJpbmdcbiAqIEBwYXJhbSBkYXRhTGVuZ3RoIExlbmd0aCBvZiByYXcgZGF0YVxuICogQHJldHVybnMgTGVuZ3RoIG9mIHBhZGRlZCBiYXNlNjQgc3RyaW5nXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBjYWxjdWxhdGVCYXNlNjRMZW5ndGgoZGF0YUxlbmd0aDogbnVtYmVyKTogbnVtYmVyIHtcbiAgcmV0dXJuIE1hdGguY2VpbChkYXRhTGVuZ3RoIC8gMykgKiA0O1xufVxuXG4vKipcbiAqIFJlbW92ZSBiYXNlNjQgcGFkZGluZ1xuICogQHBhcmFtIGJhc2U2NCBCYXNlNjQgc3RyaW5nXG4gKiBAcmV0dXJucyBCYXNlNjQgc3RyaW5nIHdpdGhvdXQgcGFkZGluZ1xuICovXG5leHBvcnQgZnVuY3Rpb24gcmVtb3ZlQmFzZTY0UGFkZGluZyhiYXNlNjQ6IHN0cmluZyk6IHN0cmluZyB7XG4gIHJldHVybiBiYXNlNjQucmVwbGFjZSgvPSskLywgJycpO1xufVxuXG4vKipcbiAqIEFkZCBiYXNlNjQgcGFkZGluZ1xuICogQHBhcmFtIGJhc2U2NCBCYXNlNjQgc3RyaW5nIHdpdGhvdXQgcGFkZGluZ1xuICogQHJldHVybnMgUHJvcGVybHkgcGFkZGVkIGJhc2U2NCBzdHJpbmdcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGFkZEJhc2U2NFBhZGRpbmcoYmFzZTY0OiBzdHJpbmcpOiBzdHJpbmcge1xuICBjb25zdCBwYWRkaW5nID0gJz0nLnJlcGVhdCgoNCAtIGJhc2U2NC5sZW5ndGggJSA0KSAlIDQpO1xuICByZXR1cm4gYmFzZTY0ICsgcGFkZGluZztcbn1cbiIsICIvKipcbiAqIEBtb2R1bGUgdmFsaWRhdGlvblxuICogQGRlc2NyaXB0aW9uIFZhbGlkYXRpb24gdXRpbGl0aWVzIGZvciBOb3N0ciBldmVudHMsIG1lc3NhZ2VzLCBhbmQgcmVsYXRlZCBkYXRhIHN0cnVjdHVyZXMuXG4gKiBQcm92aWRlcyBmdW5jdGlvbnMgdG8gdmFsaWRhdGUgZXZlbnRzLCBzaWduYXR1cmVzLCBmaWx0ZXJzLCBhbmQgc3Vic2NyaXB0aW9ucyBhY2NvcmRpbmcgdG8gdGhlIE5vc3RyIHByb3RvY29sLlxuICovXG5cbmltcG9ydCB7IFxuICBOb3N0ckV2ZW50LCBcbiAgU2lnbmVkTm9zdHJFdmVudCwgXG4gIE5vc3RyRmlsdGVyLCBcbiAgTm9zdHJTdWJzY3JpcHRpb24sIFxuICBWYWxpZGF0aW9uUmVzdWx0LCBcbiAgUHVibGljS2V5LFxuICBOb3N0ck1lc3NhZ2VUeXBlXG59IGZyb20gJy4uL3R5cGVzL2luZGV4JztcblxuaW1wb3J0IHsgbG9nZ2VyIH0gZnJvbSAnLi4vdXRpbHMvbG9nZ2VyJztcblxuaW1wb3J0IHsgc2hhMjU2IH0gZnJvbSAnQG5vYmxlL2hhc2hlcy9zaGEyLmpzJztcbmltcG9ydCB7IGJ5dGVzVG9IZXggfSBmcm9tICdAbm9ibGUvaGFzaGVzL3V0aWxzLmpzJztcbmltcG9ydCB7IHNjaG5vcnIgfSBmcm9tICdAbm9ibGUvY3VydmVzL3NlY3AyNTZrMS5qcyc7XG5cbi8qKlxuICogR2V0cyB0aGUgaGV4IHN0cmluZyBmcm9tIGEgUHVibGljS2V5IG9yIHN0cmluZ1xuICovXG5mdW5jdGlvbiBnZXRQdWJsaWNLZXlIZXgocHVia2V5OiBQdWJsaWNLZXkgfCBzdHJpbmcpOiBzdHJpbmcge1xuICByZXR1cm4gdHlwZW9mIHB1YmtleSA9PT0gJ3N0cmluZycgPyBwdWJrZXkgOiBwdWJrZXkuaGV4O1xufVxuXG5mdW5jdGlvbiBoZXhUb0J5dGVzKGhleDogc3RyaW5nKTogVWludDhBcnJheSB7XG4gIHJldHVybiBuZXcgVWludDhBcnJheShoZXgubWF0Y2goLy57MSwyfS9nKSEubWFwKGJ5dGUgPT4gcGFyc2VJbnQoYnl0ZSwgMTYpKSk7XG59XG5cbi8qKlxuICogVmFsaWRhdGVzIGEgTm9zdHIgZXZlbnQgSUQgYnkgY2hlY2tpbmcgaWYgaXQgbWF0Y2hlcyB0aGUgU0hBLTI1NiBoYXNoIG9mIHRoZSBjYW5vbmljYWwgZXZlbnQgc2VyaWFsaXphdGlvbi5cbiAqIFxuICogQHBhcmFtIHtTaWduZWROb3N0ckV2ZW50fSBldmVudCAtIFRoZSBldmVudCB0byB2YWxpZGF0ZVxuICogQHJldHVybnMge1ZhbGlkYXRpb25SZXN1bHR9IE9iamVjdCBjb250YWluaW5nIHZhbGlkYXRpb24gcmVzdWx0IGFuZCBhbnkgZXJyb3IgbWVzc2FnZVxuICogQGV4YW1wbGVcbiAqIGBgYHR5cGVzY3JpcHRcbiAqIGNvbnN0IHJlc3VsdCA9IHZhbGlkYXRlRXZlbnRJZChldmVudCk7XG4gKiBpZiAoIXJlc3VsdC5pc1ZhbGlkKSB7XG4gKiAgIGNvbnNvbGUuZXJyb3IocmVzdWx0LmVycm9yKTtcbiAqIH1cbiAqIGBgYFxuICovXG5leHBvcnQgZnVuY3Rpb24gdmFsaWRhdGVFdmVudElkKGV2ZW50OiBTaWduZWROb3N0ckV2ZW50KTogVmFsaWRhdGlvblJlc3VsdCB7XG4gIHRyeSB7XG4gICAgY29uc3Qgc2VyaWFsaXplZCA9IEpTT04uc3RyaW5naWZ5KFtcbiAgICAgIDAsXG4gICAgICBnZXRQdWJsaWNLZXlIZXgoZXZlbnQucHVia2V5KSxcbiAgICAgIGV2ZW50LmNyZWF0ZWRfYXQsXG4gICAgICBldmVudC5raW5kLFxuICAgICAgZXZlbnQudGFncyxcbiAgICAgIGV2ZW50LmNvbnRlbnRcbiAgICBdKTtcbiAgICBjb25zdCBoYXNoID0gYnl0ZXNUb0hleChzaGEyNTYobmV3IFRleHRFbmNvZGVyKCkuZW5jb2RlKHNlcmlhbGl6ZWQpKSk7XG4gICAgcmV0dXJuIHtcbiAgICAgIGlzVmFsaWQ6IGhhc2ggPT09IGV2ZW50LmlkLFxuICAgICAgZXJyb3I6IGhhc2ggPT09IGV2ZW50LmlkID8gdW5kZWZpbmVkIDogJ0ludmFsaWQgZXZlbnQgSUQnXG4gICAgfTtcbiAgfSBjYXRjaCAoZXJyb3IpIHtcbiAgICBsb2dnZXIuZXJyb3IoeyBlcnJvciB9LCAnRmFpbGVkIHRvIHZhbGlkYXRlIGV2ZW50IElEJyk7XG4gICAgcmV0dXJuIHtcbiAgICAgIGlzVmFsaWQ6IGZhbHNlLFxuICAgICAgZXJyb3I6ICdGYWlsZWQgdG8gdmFsaWRhdGUgZXZlbnQgSUQnXG4gICAgfTtcbiAgfVxufVxuXG4vKipcbiAqIFZhbGlkYXRlcyBhIE5vc3RyIGV2ZW50IHNpZ25hdHVyZSB1c2luZyBTY2hub3JyIHNpZ25hdHVyZSB2ZXJpZmljYXRpb24uXG4gKiBcbiAqIEBwYXJhbSB7U2lnbmVkTm9zdHJFdmVudH0gZXZlbnQgLSBUaGUgZXZlbnQgdG8gdmFsaWRhdGVcbiAqIEByZXR1cm5zIHtWYWxpZGF0aW9uUmVzdWx0fSBPYmplY3QgY29udGFpbmluZyB2YWxpZGF0aW9uIHJlc3VsdCBhbmQgYW55IGVycm9yIG1lc3NhZ2VcbiAqIEBleGFtcGxlXG4gKiBgYGB0eXBlc2NyaXB0XG4gKiBjb25zdCByZXN1bHQgPSB2YWxpZGF0ZUV2ZW50U2lnbmF0dXJlKGV2ZW50KTtcbiAqIGlmICghcmVzdWx0LmlzVmFsaWQpIHtcbiAqICAgY29uc29sZS5lcnJvcihyZXN1bHQuZXJyb3IpO1xuICogfVxuICogYGBgXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiB2YWxpZGF0ZUV2ZW50U2lnbmF0dXJlKGV2ZW50OiBTaWduZWROb3N0ckV2ZW50KTogVmFsaWRhdGlvblJlc3VsdCB7XG4gIHRyeSB7XG4gICAgLy8gVmVyaWZ5IHRoZSBzaWduYXR1cmVcbiAgICBjb25zdCBzZXJpYWxpemVkID0gSlNPTi5zdHJpbmdpZnkoW1xuICAgICAgMCxcbiAgICAgIGdldFB1YmxpY0tleUhleChldmVudC5wdWJrZXkpLFxuICAgICAgZXZlbnQuY3JlYXRlZF9hdCxcbiAgICAgIGV2ZW50LmtpbmQsXG4gICAgICBldmVudC50YWdzLFxuICAgICAgZXZlbnQuY29udGVudFxuICAgIF0pO1xuICAgIGNvbnN0IGhhc2ggPSBzaGEyNTYobmV3IFRleHRFbmNvZGVyKCkuZW5jb2RlKHNlcmlhbGl6ZWQpKTtcbiAgICBjb25zdCBwdWJrZXlIZXggPSBnZXRQdWJsaWNLZXlIZXgoZXZlbnQucHVia2V5KTtcbiAgICBjb25zdCBwdWJrZXlCeXRlcyA9IGhleFRvQnl0ZXMocHVia2V5SGV4KTtcbiAgICBjb25zdCBpc1ZhbGlkID0gc2Nobm9yci52ZXJpZnkoaGV4VG9CeXRlcyhldmVudC5zaWcpLCBoYXNoLCBwdWJrZXlCeXRlcyk7XG4gICAgXG4gICAgcmV0dXJuIHtcbiAgICAgIGlzVmFsaWQsXG4gICAgICBlcnJvcjogaXNWYWxpZCA/IHVuZGVmaW5lZCA6ICdJbnZhbGlkIHNpZ25hdHVyZSdcbiAgICB9O1xuICB9IGNhdGNoIChlcnJvcikge1xuICAgIGxvZ2dlci5lcnJvcih7IGVycm9yIH0sICdGYWlsZWQgdG8gdmFsaWRhdGUgZXZlbnQgc2lnbmF0dXJlJyk7XG4gICAgcmV0dXJuIHtcbiAgICAgIGlzVmFsaWQ6IGZhbHNlLFxuICAgICAgZXJyb3I6ICdGYWlsZWQgdG8gdmFsaWRhdGUgZXZlbnQgc2lnbmF0dXJlJ1xuICAgIH07XG4gIH1cbn1cblxuLyoqXG4gKiBWYWxpZGF0ZXMgYSBjb21wbGV0ZSBOb3N0ciBldmVudCBieSBjaGVja2luZyBpdHMgc3RydWN0dXJlLCB0aW1lc3RhbXBzLCBJRCwgYW5kIHNpZ25hdHVyZS5cbiAqIFxuICogQHBhcmFtIHtTaWduZWROb3N0ckV2ZW50fSBldmVudCAtIFRoZSBldmVudCB0byB2YWxpZGF0ZVxuICogQHJldHVybnMge1ZhbGlkYXRpb25SZXN1bHR9IE9iamVjdCBjb250YWluaW5nIHZhbGlkYXRpb24gcmVzdWx0IGFuZCBhbnkgZXJyb3IgbWVzc2FnZVxuICogQGV4YW1wbGVcbiAqIGBgYHR5cGVzY3JpcHRcbiAqIGNvbnN0IHJlc3VsdCA9IHZhbGlkYXRlRXZlbnQoZXZlbnQpO1xuICogaWYgKCFyZXN1bHQuaXNWYWxpZCkge1xuICogICBjb25zb2xlLmVycm9yKHJlc3VsdC5lcnJvcik7XG4gKiB9XG4gKiBgYGBcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIHZhbGlkYXRlRXZlbnQoZXZlbnQ6IFNpZ25lZE5vc3RyRXZlbnQpOiBWYWxpZGF0aW9uUmVzdWx0IHtcbiAgLy8gRmlyc3QgdmFsaWRhdGUgdGhlIGV2ZW50IHN0cnVjdHVyZVxuICBjb25zdCBiYXNlVmFsaWRhdGlvbiA9IHZhbGlkYXRlRXZlbnRCYXNlKGV2ZW50KTtcbiAgaWYgKCFiYXNlVmFsaWRhdGlvbi5pc1ZhbGlkKSB7XG4gICAgcmV0dXJuIGJhc2VWYWxpZGF0aW9uO1xuICB9XG5cbiAgLy8gVGhlbiB2YWxpZGF0ZSB0aGUgZXZlbnQgSURcbiAgY29uc3QgaWRWYWxpZGF0aW9uID0gdmFsaWRhdGVFdmVudElkKGV2ZW50KTtcbiAgaWYgKCFpZFZhbGlkYXRpb24uaXNWYWxpZCkge1xuICAgIHJldHVybiBpZFZhbGlkYXRpb247XG4gIH1cblxuICAvLyBGaW5hbGx5IHZhbGlkYXRlIHRoZSBzaWduYXR1cmVcbiAgcmV0dXJuIHZhbGlkYXRlRXZlbnRTaWduYXR1cmUoZXZlbnQpO1xufVxuXG4vKipcbiAqIFZhbGlkYXRlcyBhIHNpZ25lZCBOb3N0ciBldmVudCBieSBjaGVja2luZyBpdHMgc3RydWN0dXJlIGFuZCBzaWduYXR1cmUgZm9ybWF0LlxuICogXG4gKiBAcGFyYW0ge1NpZ25lZE5vc3RyRXZlbnR9IGV2ZW50IC0gVGhlIGV2ZW50IHRvIHZhbGlkYXRlXG4gKiBAcmV0dXJucyB7VmFsaWRhdGlvblJlc3VsdH0gT2JqZWN0IGNvbnRhaW5pbmcgdmFsaWRhdGlvbiByZXN1bHQgYW5kIGFueSBlcnJvciBtZXNzYWdlXG4gKiBAZXhhbXBsZVxuICogYGBgdHlwZXNjcmlwdFxuICogY29uc3QgcmVzdWx0ID0gdmFsaWRhdGVTaWduZWRFdmVudChldmVudCk7XG4gKiBpZiAoIXJlc3VsdC5pc1ZhbGlkKSB7XG4gKiAgIGNvbnNvbGUuZXJyb3IocmVzdWx0LmVycm9yKTtcbiAqIH1cbiAqIGBgYFxuICovXG5leHBvcnQgZnVuY3Rpb24gdmFsaWRhdGVTaWduZWRFdmVudChldmVudDogU2lnbmVkTm9zdHJFdmVudCk6IFZhbGlkYXRpb25SZXN1bHQge1xuICB0cnkge1xuICAgIC8vIENoZWNrIGJhc2ljIGV2ZW50IHN0cnVjdHVyZVxuICAgIGNvbnN0IGJhc2VWYWxpZGF0aW9uID0gdmFsaWRhdGVFdmVudEJhc2UoZXZlbnQpO1xuICAgIGlmICghYmFzZVZhbGlkYXRpb24uaXNWYWxpZCkge1xuICAgICAgcmV0dXJuIGJhc2VWYWxpZGF0aW9uO1xuICAgIH1cblxuICAgIC8vIEdldCBwdWJrZXkgaGV4XG4gICAgY29uc3QgcHVia2V5SGV4ID0gZ2V0UHVibGljS2V5SGV4KGV2ZW50LnB1YmtleSk7XG5cbiAgICAvLyBWYWxpZGF0ZSBwdWJrZXkgZm9ybWF0XG4gICAgaWYgKCFwdWJrZXlIZXggfHwgdHlwZW9mIHB1YmtleUhleCAhPT0gJ3N0cmluZycgfHwgcHVia2V5SGV4Lmxlbmd0aCAhPT0gNjQpIHtcbiAgICAgIHJldHVybiB7XG4gICAgICAgIGlzVmFsaWQ6IGZhbHNlLFxuICAgICAgICBlcnJvcjogJ0ludmFsaWQgcHVibGljIGtleSBmb3JtYXQnXG4gICAgICB9O1xuICAgIH1cblxuICAgIC8vIFZhbGlkYXRlIHNpZ25hdHVyZSBmb3JtYXRcbiAgICBpZiAoIWV2ZW50LnNpZyB8fCB0eXBlb2YgZXZlbnQuc2lnICE9PSAnc3RyaW5nJyB8fCBldmVudC5zaWcubGVuZ3RoICE9PSAxMjgpIHtcbiAgICAgIHJldHVybiB7XG4gICAgICAgIGlzVmFsaWQ6IGZhbHNlLFxuICAgICAgICBlcnJvcjogJ0ludmFsaWQgc2lnbmF0dXJlIGZvcm1hdCdcbiAgICAgIH07XG4gICAgfVxuXG4gICAgLy8gVmFsaWRhdGUgSUQgZm9ybWF0XG4gICAgaWYgKCFldmVudC5pZCB8fCB0eXBlb2YgZXZlbnQuaWQgIT09ICdzdHJpbmcnIHx8IGV2ZW50LmlkLmxlbmd0aCAhPT0gNjQpIHtcbiAgICAgIHJldHVybiB7XG4gICAgICAgIGlzVmFsaWQ6IGZhbHNlLFxuICAgICAgICBlcnJvcjogJ0ludmFsaWQgZXZlbnQgSUQgZm9ybWF0J1xuICAgICAgfTtcbiAgICB9XG5cbiAgICByZXR1cm4geyBpc1ZhbGlkOiB0cnVlIH07XG4gIH0gY2F0Y2ggKGVycm9yKSB7XG4gICAgbG9nZ2VyLmVycm9yKHsgZXJyb3IgfSwgJ0ZhaWxlZCB0byB2YWxpZGF0ZSBzaWduZWQgZXZlbnQnKTtcbiAgICByZXR1cm4ge1xuICAgICAgaXNWYWxpZDogZmFsc2UsXG4gICAgICBlcnJvcjogJ0ZhaWxlZCB0byB2YWxpZGF0ZSBzaWduZWQgZXZlbnQnXG4gICAgfTtcbiAgfVxufVxuXG4vKipcbiAqIFZhbGlkYXRlcyBhIE5vc3RyIGV2ZW50IGJ5IGNoZWNraW5nIGl0cyBzdHJ1Y3R1cmUgYW5kIGZpZWxkcy5cbiAqIEBwYXJhbSBldmVudCAtIFRoZSBldmVudCB0byB2YWxpZGF0ZVxuICogQHJldHVybnMgVmFsaWRhdGlvbiByZXN1bHQgYW5kIGFueSBlcnJvciBtZXNzYWdlXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiB2YWxpZGF0ZUV2ZW50QmFzZShldmVudDogTm9zdHJFdmVudCB8IFNpZ25lZE5vc3RyRXZlbnQpOiBWYWxpZGF0aW9uUmVzdWx0IHtcbiAgLy8gQ2hlY2sgcmVxdWlyZWQgZmllbGRzXG4gIGlmICghZXZlbnQgfHwgdHlwZW9mIGV2ZW50ICE9PSAnb2JqZWN0Jykge1xuICAgIHJldHVybiB7IGlzVmFsaWQ6IGZhbHNlLCBlcnJvcjogJ0ludmFsaWQgZXZlbnQgc3RydWN0dXJlJyB9O1xuICB9XG5cbiAgLy8gVmFsaWRhdGUga2luZFxuICBpZiAodHlwZW9mIGV2ZW50LmtpbmQgIT09ICdudW1iZXInIHx8IGV2ZW50LmtpbmQgPCAwKSB7XG4gICAgcmV0dXJuIHsgaXNWYWxpZDogZmFsc2UsIGVycm9yOiAnRXZlbnQga2luZCBtdXN0IGJlIGEgbm9uLW5lZ2F0aXZlIGludGVnZXInIH07XG4gIH1cblxuICAvLyBWYWxpZGF0ZSB0aW1lc3RhbXBcbiAgY29uc3Qgbm93ID0gTWF0aC5mbG9vcihEYXRlLm5vdygpIC8gMTAwMCk7XG4gIGlmICh0eXBlb2YgZXZlbnQuY3JlYXRlZF9hdCAhPT0gJ251bWJlcicgfHwgZXZlbnQuY3JlYXRlZF9hdCA+IG5vdyArIDYwKSB7XG4gICAgcmV0dXJuIHsgaXNWYWxpZDogZmFsc2UsIGVycm9yOiAnRXZlbnQgdGltZXN0YW1wIGNhbm5vdCBiZSBpbiB0aGUgZnV0dXJlJyB9O1xuICB9XG5cbiAgLy8gVmFsaWRhdGUgY29udGVudFxuICBpZiAodHlwZW9mIGV2ZW50LmNvbnRlbnQgIT09ICdzdHJpbmcnKSB7XG4gICAgcmV0dXJuIHsgaXNWYWxpZDogZmFsc2UsIGVycm9yOiAnRXZlbnQgY29udGVudCBtdXN0IGJlIGEgc3RyaW5nJyB9O1xuICB9XG5cbiAgLy8gVmFsaWRhdGUgcHVia2V5IGZvcm1hdFxuICBpZiAoIWV2ZW50LnB1YmtleSkge1xuICAgIHJldHVybiB7IGlzVmFsaWQ6IGZhbHNlLCBlcnJvcjogJ01pc3NpbmcgcHVibGljIGtleScgfTtcbiAgfVxuXG4gIC8vIEdldCBwdWJrZXkgaGV4XG4gIGNvbnN0IHB1YmtleUhleCA9IGdldFB1YmxpY0tleUhleChldmVudC5wdWJrZXkpO1xuICBpZiAodHlwZW9mIHB1YmtleUhleCAhPT0gJ3N0cmluZycgfHwgIS9eWzAtOWEtZl17NjR9JC8udGVzdChwdWJrZXlIZXgpKSB7XG4gICAgcmV0dXJuIHsgaXNWYWxpZDogZmFsc2UsIGVycm9yOiAnSW52YWxpZCBwdWJsaWMga2V5IGZvcm1hdCcgfTtcbiAgfVxuXG4gIC8vIFZhbGlkYXRlIHRhZ3NcbiAgaWYgKCFBcnJheS5pc0FycmF5KGV2ZW50LnRhZ3MpKSB7XG4gICAgcmV0dXJuIHsgaXNWYWxpZDogZmFsc2UsIGVycm9yOiAnRXZlbnQgdGFncyBtdXN0IGJlIGFuIGFycmF5JyB9O1xuICB9XG5cbiAgZm9yIChjb25zdCB0YWcgb2YgZXZlbnQudGFncykge1xuICAgIGlmICghQXJyYXkuaXNBcnJheSh0YWcpKSB7XG4gICAgICByZXR1cm4geyBpc1ZhbGlkOiBmYWxzZSwgZXJyb3I6ICdFYWNoIHRhZyBtdXN0IGJlIGFuIGFycmF5JyB9O1xuICAgIH1cbiAgICBpZiAodGFnLmxlbmd0aCA9PT0gMCkge1xuICAgICAgcmV0dXJuIHsgaXNWYWxpZDogZmFsc2UsIGVycm9yOiAnRW1wdHkgdGFncyBhcmUgbm90IGFsbG93ZWQnIH07XG4gICAgfVxuICAgIGlmICh0eXBlb2YgdGFnWzBdICE9PSAnc3RyaW5nJykge1xuICAgICAgcmV0dXJuIHsgaXNWYWxpZDogZmFsc2UsIGVycm9yOiAnVGFnIGlkZW50aWZpZXIgbXVzdCBiZSBhIHN0cmluZycgfTtcbiAgICB9XG4gIH1cblxuICByZXR1cm4geyBpc1ZhbGlkOiB0cnVlIH07XG59XG5cbi8qKlxuICogVmFsaWRhdGVzIGEgTm9zdHIgZmlsdGVyIGJ5IGNoZWNraW5nIGl0cyBzdHJ1Y3R1cmUgYW5kIGZpZWxkcy5cbiAqIFxuICogQHBhcmFtIHtOb3N0ckZpbHRlcn0gZmlsdGVyIC0gVGhlIGZpbHRlciB0byB2YWxpZGF0ZVxuICogQHJldHVybnMge1ZhbGlkYXRpb25SZXN1bHR9IE9iamVjdCBjb250YWluaW5nIHZhbGlkYXRpb24gcmVzdWx0IGFuZCBhbnkgZXJyb3IgbWVzc2FnZVxuICogQGV4YW1wbGVcbiAqIGBgYHR5cGVzY3JpcHRcbiAqIGNvbnN0IHJlc3VsdCA9IHZhbGlkYXRlRmlsdGVyKGZpbHRlcik7XG4gKiBpZiAoIXJlc3VsdC5pc1ZhbGlkKSB7XG4gKiAgIGNvbnNvbGUuZXJyb3IocmVzdWx0LmVycm9yKTtcbiAqIH1cbiAqIGBgYFxuICovXG5leHBvcnQgZnVuY3Rpb24gdmFsaWRhdGVGaWx0ZXIoZmlsdGVyOiBOb3N0ckZpbHRlcik6IFZhbGlkYXRpb25SZXN1bHQge1xuICB0cnkge1xuICAgIC8vIFZhbGlkYXRlIGZpbHRlciBzdHJ1Y3R1cmVcbiAgICBpZiAoIWZpbHRlciB8fCB0eXBlb2YgZmlsdGVyICE9PSAnb2JqZWN0Jykge1xuICAgICAgcmV0dXJuIHsgaXNWYWxpZDogZmFsc2UsIGVycm9yOiAnSW52YWxpZCBmaWx0ZXIgc3RydWN0dXJlJyB9O1xuICAgIH1cblxuICAgIC8vIFZhbGlkYXRlIGlkcyBhcnJheSBpZiBwcmVzZW50XG4gICAgaWYgKGZpbHRlci5pZHMgJiYgKCFBcnJheS5pc0FycmF5KGZpbHRlci5pZHMpIHx8ICFmaWx0ZXIuaWRzLmV2ZXJ5KGlkID0+IHR5cGVvZiBpZCA9PT0gJ3N0cmluZycpKSkge1xuICAgICAgcmV0dXJuIHsgaXNWYWxpZDogZmFsc2UsIGVycm9yOiAnRmlsdGVyIGlkcyBtdXN0IGJlIGFuIGFycmF5IG9mIHN0cmluZ3MnIH07XG4gICAgfVxuXG4gICAgLy8gVmFsaWRhdGUgYXV0aG9ycyBhcnJheSBpZiBwcmVzZW50XG4gICAgaWYgKGZpbHRlci5hdXRob3JzICYmICghQXJyYXkuaXNBcnJheShmaWx0ZXIuYXV0aG9ycykgfHwgIWZpbHRlci5hdXRob3JzLmV2ZXJ5KGF1dGhvciA9PiB0eXBlb2YgYXV0aG9yID09PSAnc3RyaW5nJykpKSB7XG4gICAgICByZXR1cm4geyBpc1ZhbGlkOiBmYWxzZSwgZXJyb3I6ICdGaWx0ZXIgYXV0aG9ycyBtdXN0IGJlIGFuIGFycmF5IG9mIHN0cmluZ3MnIH07XG4gICAgfVxuXG4gICAgLy8gVmFsaWRhdGUga2luZHMgYXJyYXkgaWYgcHJlc2VudFxuICAgIGlmIChmaWx0ZXIua2luZHMpIHtcbiAgICAgIGlmICghQXJyYXkuaXNBcnJheShmaWx0ZXIua2luZHMpKSB7XG4gICAgICAgIHJldHVybiB7IGlzVmFsaWQ6IGZhbHNlLCBlcnJvcjogJ0ZpbHRlciBraW5kcyBtdXN0IGJlIGFuIGFycmF5IG9mIG51bWJlcnMnIH07XG4gICAgICB9XG4gICAgICBpZiAoIWZpbHRlci5raW5kcy5ldmVyeShraW5kID0+IHR5cGVvZiBraW5kID09PSAnbnVtYmVyJyAmJiBOdW1iZXIuaXNJbnRlZ2VyKGtpbmQpICYmIGtpbmQgPj0gMCkpIHtcbiAgICAgICAgcmV0dXJuIHsgaXNWYWxpZDogZmFsc2UsIGVycm9yOiAnRmlsdGVyIGtpbmRzIG11c3QgYmUgbm9uLW5lZ2F0aXZlIGludGVnZXJzJyB9O1xuICAgICAgfVxuICAgIH1cblxuICAgIC8vIFZhbGlkYXRlIHRpbWVzdGFtcHNcbiAgICBpZiAoZmlsdGVyLnNpbmNlICYmIHR5cGVvZiBmaWx0ZXIuc2luY2UgIT09ICdudW1iZXInKSB7XG4gICAgICByZXR1cm4geyBpc1ZhbGlkOiBmYWxzZSwgZXJyb3I6ICdGaWx0ZXIgc2luY2UgbXVzdCBiZSBhIG51bWJlcicgfTtcbiAgICB9XG4gICAgaWYgKGZpbHRlci51bnRpbCAmJiB0eXBlb2YgZmlsdGVyLnVudGlsICE9PSAnbnVtYmVyJykge1xuICAgICAgcmV0dXJuIHsgaXNWYWxpZDogZmFsc2UsIGVycm9yOiAnRmlsdGVyIHVudGlsIG11c3QgYmUgYSBudW1iZXInIH07XG4gICAgfVxuXG4gICAgLy8gVmFsaWRhdGUgbGltaXRcbiAgICBpZiAoZmlsdGVyLmxpbWl0ICYmIHR5cGVvZiBmaWx0ZXIubGltaXQgIT09ICdudW1iZXInKSB7XG4gICAgICByZXR1cm4geyBpc1ZhbGlkOiBmYWxzZSwgZXJyb3I6ICdGaWx0ZXIgbGltaXQgbXVzdCBiZSBhIG51bWJlcicgfTtcbiAgICB9XG5cbiAgICAvLyBWYWxpZGF0ZSBzZWFyY2hcbiAgICBpZiAoZmlsdGVyLnNlYXJjaCAmJiB0eXBlb2YgZmlsdGVyLnNlYXJjaCAhPT0gJ3N0cmluZycpIHtcbiAgICAgIHJldHVybiB7IGlzVmFsaWQ6IGZhbHNlLCBlcnJvcjogJ0ZpbHRlciBzZWFyY2ggbXVzdCBiZSBhIHN0cmluZycgfTtcbiAgICB9XG5cbiAgICByZXR1cm4geyBpc1ZhbGlkOiB0cnVlIH07XG4gIH0gY2F0Y2ggKGVycm9yKSB7XG4gICAgbG9nZ2VyLmVycm9yKHsgZXJyb3IgfSwgJ0ZhaWxlZCB0byB2YWxpZGF0ZSBmaWx0ZXInKTtcbiAgICByZXR1cm4geyBpc1ZhbGlkOiBmYWxzZSwgZXJyb3I6ICdGYWlsZWQgdG8gdmFsaWRhdGUgZmlsdGVyJyB9O1xuICB9XG59XG5cbi8qKlxuICogVmFsaWRhdGVzIGEgTm9zdHIgc3Vic2NyaXB0aW9uIGJ5IGNoZWNraW5nIGl0cyBzdHJ1Y3R1cmUgYW5kIGZpbHRlcnMuXG4gKiBcbiAqIEBwYXJhbSB7Tm9zdHJTdWJzY3JpcHRpb259IHN1YnNjcmlwdGlvbiAtIFRoZSBzdWJzY3JpcHRpb24gdG8gdmFsaWRhdGVcbiAqIEByZXR1cm5zIHtWYWxpZGF0aW9uUmVzdWx0fSBPYmplY3QgY29udGFpbmluZyB2YWxpZGF0aW9uIHJlc3VsdCBhbmQgYW55IGVycm9yIG1lc3NhZ2VcbiAqIEBleGFtcGxlXG4gKiBgYGB0eXBlc2NyaXB0XG4gKiBjb25zdCByZXN1bHQgPSB2YWxpZGF0ZVN1YnNjcmlwdGlvbihzdWJzY3JpcHRpb24pO1xuICogaWYgKCFyZXN1bHQuaXNWYWxpZCkge1xuICogICBjb25zb2xlLmVycm9yKHJlc3VsdC5lcnJvcik7XG4gKiB9XG4gKiBgYGBcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIHZhbGlkYXRlU3Vic2NyaXB0aW9uKHN1YnNjcmlwdGlvbjogTm9zdHJTdWJzY3JpcHRpb24pOiBWYWxpZGF0aW9uUmVzdWx0IHtcbiAgdHJ5IHtcbiAgICAvLyBWYWxpZGF0ZSBzdWJzY3JpcHRpb24gc3RydWN0dXJlXG4gICAgaWYgKCFzdWJzY3JpcHRpb24gfHwgdHlwZW9mIHN1YnNjcmlwdGlvbiAhPT0gJ29iamVjdCcpIHtcbiAgICAgIHJldHVybiB7IGlzVmFsaWQ6IGZhbHNlLCBlcnJvcjogJ0ludmFsaWQgc3Vic2NyaXB0aW9uIHN0cnVjdHVyZScgfTtcbiAgICB9XG5cbiAgICAvLyBWYWxpZGF0ZSBzdWJzY3JpcHRpb24gSURcbiAgICBpZiAoIXN1YnNjcmlwdGlvbi5pZCB8fCB0eXBlb2Ygc3Vic2NyaXB0aW9uLmlkICE9PSAnc3RyaW5nJykge1xuICAgICAgcmV0dXJuIHsgaXNWYWxpZDogZmFsc2UsIGVycm9yOiAnU3Vic2NyaXB0aW9uIG11c3QgaGF2ZSBhIHN0cmluZyBJRCcgfTtcbiAgICB9XG5cbiAgICAvLyBWYWxpZGF0ZSBmaWx0ZXJzIGFycmF5XG4gICAgaWYgKCFBcnJheS5pc0FycmF5KHN1YnNjcmlwdGlvbi5maWx0ZXJzKSkge1xuICAgICAgcmV0dXJuIHsgaXNWYWxpZDogZmFsc2UsIGVycm9yOiAnU3Vic2NyaXB0aW9uIGZpbHRlcnMgbXVzdCBiZSBhbiBhcnJheScgfTtcbiAgICB9XG5cbiAgICAvLyBWYWxpZGF0ZSBlYWNoIGZpbHRlclxuICAgIGZvciAoY29uc3QgZmlsdGVyIG9mIHN1YnNjcmlwdGlvbi5maWx0ZXJzKSB7XG4gICAgICBjb25zdCBmaWx0ZXJWYWxpZGF0aW9uID0gdmFsaWRhdGVGaWx0ZXIoZmlsdGVyKTtcbiAgICAgIGlmICghZmlsdGVyVmFsaWRhdGlvbi5pc1ZhbGlkKSB7XG4gICAgICAgIHJldHVybiBmaWx0ZXJWYWxpZGF0aW9uO1xuICAgICAgfVxuICAgIH1cblxuICAgIHJldHVybiB7IGlzVmFsaWQ6IHRydWUgfTtcbiAgfSBjYXRjaCAoZXJyb3IpIHtcbiAgICBsb2dnZXIuZXJyb3IoeyBlcnJvciB9LCAnRmFpbGVkIHRvIHZhbGlkYXRlIHN1YnNjcmlwdGlvbicpO1xuICAgIHJldHVybiB7IGlzVmFsaWQ6IGZhbHNlLCBlcnJvcjogJ0ZhaWxlZCB0byB2YWxpZGF0ZSBzdWJzY3JpcHRpb24nIH07XG4gIH1cbn1cblxuLyoqXG4gKiBWYWxpZGF0ZXMgYSBOb3N0ciByZWxheSByZXNwb25zZSBtZXNzYWdlLlxuICogXG4gKiBAcGFyYW0ge3Vua25vd259IG1lc3NhZ2UgLSBUaGUgbWVzc2FnZSB0byB2YWxpZGF0ZVxuICogQHJldHVybnMge1ZhbGlkYXRpb25SZXN1bHR9IE9iamVjdCBjb250YWluaW5nIHZhbGlkYXRpb24gcmVzdWx0IGFuZCBhbnkgZXJyb3IgbWVzc2FnZVxuICogQGV4YW1wbGVcbiAqIGBgYHR5cGVzY3JpcHRcbiAqIGNvbnN0IHJlc3VsdCA9IHZhbGlkYXRlUmVzcG9uc2UoWydFVkVOVCcsIGV2ZW50T2JqXSk7XG4gKiBpZiAoIXJlc3VsdC5pc1ZhbGlkKSB7XG4gKiAgIGNvbnNvbGUuZXJyb3IocmVzdWx0LmVycm9yKTtcbiAqIH1cbiAqIGBgYFxuICovXG5leHBvcnQgZnVuY3Rpb24gdmFsaWRhdGVSZXNwb25zZShtZXNzYWdlOiB1bmtub3duKTogVmFsaWRhdGlvblJlc3VsdCB7XG4gIC8vIENoZWNrIGlmIG1lc3NhZ2UgaXMgYW4gYXJyYXlcbiAgaWYgKCFBcnJheS5pc0FycmF5KG1lc3NhZ2UpKSB7XG4gICAgcmV0dXJuIHtcbiAgICAgIGlzVmFsaWQ6IGZhbHNlLFxuICAgICAgZXJyb3I6ICdJbnZhbGlkIG1lc3NhZ2UgZm9ybWF0OiBtdXN0IGJlIGFuIGFycmF5J1xuICAgIH07XG4gIH1cblxuICAvLyBDaGVjayBpZiBtZXNzYWdlIGhhcyBhdCBsZWFzdCBvbmUgZWxlbWVudFxuICBpZiAobWVzc2FnZS5sZW5ndGggPT09IDApIHtcbiAgICByZXR1cm4ge1xuICAgICAgaXNWYWxpZDogZmFsc2UsXG4gICAgICBlcnJvcjogJ0ludmFsaWQgbWVzc2FnZSBmb3JtYXQ6IGFycmF5IGlzIGVtcHR5J1xuICAgIH07XG4gIH1cblxuICAvLyBDaGVjayBpZiBmaXJzdCBlbGVtZW50IGlzIGEgdmFsaWQgbWVzc2FnZSB0eXBlXG4gIGNvbnN0IHR5cGUgPSBtZXNzYWdlWzBdO1xuICBpZiAoIU9iamVjdC52YWx1ZXMoTm9zdHJNZXNzYWdlVHlwZSkuaW5jbHVkZXModHlwZSBhcyBOb3N0ck1lc3NhZ2VUeXBlKSkge1xuICAgIHJldHVybiB7XG4gICAgICBpc1ZhbGlkOiBmYWxzZSxcbiAgICAgIGVycm9yOiBgSW52YWxpZCBtZXNzYWdlIHR5cGU6ICR7dHlwZX1gXG4gICAgfTtcbiAgfVxuXG4gIC8vIFR5cGUtc3BlY2lmaWMgdmFsaWRhdGlvblxuICBzd2l0Y2ggKHR5cGUpIHtcbiAgICBjYXNlIE5vc3RyTWVzc2FnZVR5cGUuRVZFTlQ6XG4gICAgICBpZiAobWVzc2FnZS5sZW5ndGggIT09IDIpIHtcbiAgICAgICAgcmV0dXJuIHtcbiAgICAgICAgICBpc1ZhbGlkOiBmYWxzZSxcbiAgICAgICAgICBlcnJvcjogJ0VWRU5UIG1lc3NhZ2UgbXVzdCBoYXZlIGV4YWN0bHkgMiBlbGVtZW50cydcbiAgICAgICAgfTtcbiAgICAgIH1cbiAgICAgIHJldHVybiB2YWxpZGF0ZVNpZ25lZEV2ZW50KG1lc3NhZ2VbMV0gYXMgU2lnbmVkTm9zdHJFdmVudCk7XG5cbiAgICBjYXNlIE5vc3RyTWVzc2FnZVR5cGUuTk9USUNFOlxuICAgICAgaWYgKG1lc3NhZ2UubGVuZ3RoICE9PSAyIHx8IHR5cGVvZiBtZXNzYWdlWzFdICE9PSAnc3RyaW5nJykge1xuICAgICAgICByZXR1cm4ge1xuICAgICAgICAgIGlzVmFsaWQ6IGZhbHNlLFxuICAgICAgICAgIGVycm9yOiAnTk9USUNFIG1lc3NhZ2UgbXVzdCBoYXZlIGV4YWN0bHkgMiBlbGVtZW50cyB3aXRoIGEgc3RyaW5nIG1lc3NhZ2UnXG4gICAgICAgIH07XG4gICAgICB9XG4gICAgICByZXR1cm4geyBpc1ZhbGlkOiB0cnVlIH07XG5cbiAgICBjYXNlIE5vc3RyTWVzc2FnZVR5cGUuT0s6XG4gICAgICBpZiAobWVzc2FnZS5sZW5ndGggIT09IDQgfHwgXG4gICAgICAgICAgdHlwZW9mIG1lc3NhZ2VbMV0gIT09ICdzdHJpbmcnIHx8IFxuICAgICAgICAgIHR5cGVvZiBtZXNzYWdlWzJdICE9PSAnYm9vbGVhbicgfHwgXG4gICAgICAgICAgdHlwZW9mIG1lc3NhZ2VbM10gIT09ICdzdHJpbmcnKSB7XG4gICAgICAgIHJldHVybiB7XG4gICAgICAgICAgaXNWYWxpZDogZmFsc2UsXG4gICAgICAgICAgZXJyb3I6ICdPSyBtZXNzYWdlIG11c3QgaGF2ZSBleGFjdGx5IDQgZWxlbWVudHM6IFt0eXBlLCBldmVudElkLCBzdWNjZXNzLCBtZXNzYWdlXSdcbiAgICAgICAgfTtcbiAgICAgIH1cbiAgICAgIHJldHVybiB7IGlzVmFsaWQ6IHRydWUgfTtcblxuICAgIGNhc2UgTm9zdHJNZXNzYWdlVHlwZS5FT1NFOlxuICAgICAgaWYgKG1lc3NhZ2UubGVuZ3RoICE9PSAyIHx8IHR5cGVvZiBtZXNzYWdlWzFdICE9PSAnc3RyaW5nJykge1xuICAgICAgICByZXR1cm4ge1xuICAgICAgICAgIGlzVmFsaWQ6IGZhbHNlLFxuICAgICAgICAgIGVycm9yOiAnRU9TRSBtZXNzYWdlIG11c3QgaGF2ZSBleGFjdGx5IDIgZWxlbWVudHMgd2l0aCBhIHN1YnNjcmlwdGlvbiBJRCdcbiAgICAgICAgfTtcbiAgICAgIH1cbiAgICAgIHJldHVybiB7IGlzVmFsaWQ6IHRydWUgfTtcblxuICAgIGNhc2UgTm9zdHJNZXNzYWdlVHlwZS5SRVE6XG4gICAgICBpZiAobWVzc2FnZS5sZW5ndGggPCAyKSB7XG4gICAgICAgIHJldHVybiB7XG4gICAgICAgICAgaXNWYWxpZDogZmFsc2UsXG4gICAgICAgICAgZXJyb3I6ICdSRVEgbWVzc2FnZSBtdXN0IGhhdmUgYXQgbGVhc3QgMiBlbGVtZW50cydcbiAgICAgICAgfTtcbiAgICAgIH1cbiAgICAgIGlmICh0eXBlb2YgbWVzc2FnZVsxXSAhPT0gJ3N0cmluZycpIHtcbiAgICAgICAgcmV0dXJuIHtcbiAgICAgICAgICBpc1ZhbGlkOiBmYWxzZSxcbiAgICAgICAgICBlcnJvcjogJ1JFUSBtZXNzYWdlIG11c3QgaGF2ZSBhIHN0cmluZyBzdWJzY3JpcHRpb24gSUQnXG4gICAgICAgIH07XG4gICAgICB9XG4gICAgICAvLyBWYWxpZGF0ZSBlYWNoIGZpbHRlciBpZiBwcmVzZW50XG4gICAgICBmb3IgKGxldCBpID0gMjsgaSA8IG1lc3NhZ2UubGVuZ3RoOyBpKyspIHtcbiAgICAgICAgY29uc3QgZmlsdGVyUmVzdWx0ID0gdmFsaWRhdGVGaWx0ZXIobWVzc2FnZVtpXSBhcyBOb3N0ckZpbHRlcik7XG4gICAgICAgIGlmICghZmlsdGVyUmVzdWx0LmlzVmFsaWQpIHtcbiAgICAgICAgICByZXR1cm4gZmlsdGVyUmVzdWx0O1xuICAgICAgICB9XG4gICAgICB9XG4gICAgICByZXR1cm4geyBpc1ZhbGlkOiB0cnVlIH07XG5cbiAgICBjYXNlIE5vc3RyTWVzc2FnZVR5cGUuQ0xPU0U6XG4gICAgICBpZiAobWVzc2FnZS5sZW5ndGggIT09IDIgfHwgdHlwZW9mIG1lc3NhZ2VbMV0gIT09ICdzdHJpbmcnKSB7XG4gICAgICAgIHJldHVybiB7XG4gICAgICAgICAgaXNWYWxpZDogZmFsc2UsXG4gICAgICAgICAgZXJyb3I6ICdDTE9TRSBtZXNzYWdlIG11c3QgaGF2ZSBleGFjdGx5IDIgZWxlbWVudHMgd2l0aCBhIHN1YnNjcmlwdGlvbiBJRCdcbiAgICAgICAgfTtcbiAgICAgIH1cbiAgICAgIHJldHVybiB7IGlzVmFsaWQ6IHRydWUgfTtcblxuICAgIGNhc2UgTm9zdHJNZXNzYWdlVHlwZS5BVVRIOlxuICAgICAgaWYgKG1lc3NhZ2UubGVuZ3RoICE9PSAyKSB7XG4gICAgICAgIHJldHVybiB7XG4gICAgICAgICAgaXNWYWxpZDogZmFsc2UsXG4gICAgICAgICAgZXJyb3I6ICdBVVRIIG1lc3NhZ2UgbXVzdCBoYXZlIGV4YWN0bHkgMiBlbGVtZW50cydcbiAgICAgICAgfTtcbiAgICAgIH1cbiAgICAgIHJldHVybiB2YWxpZGF0ZVNpZ25lZEV2ZW50KG1lc3NhZ2VbMV0gYXMgU2lnbmVkTm9zdHJFdmVudCk7XG5cbiAgICBkZWZhdWx0OlxuICAgICAgcmV0dXJuIHtcbiAgICAgICAgaXNWYWxpZDogZmFsc2UsXG4gICAgICAgIGVycm9yOiBgVW5zdXBwb3J0ZWQgbWVzc2FnZSB0eXBlOiAke3R5cGV9YFxuICAgICAgfTtcbiAgfVxufVxuIiwgIi8qKlxuICogQG1vZHVsZSBldmVudFxuICogQGRlc2NyaXB0aW9uIEV2ZW50IGhhbmRsaW5nIHV0aWxpdGllcyBmb3IgTm9zdHJcbiAqL1xuXG5leHBvcnQgeyBjcmVhdGVFdmVudCwgc2VyaWFsaXplRXZlbnQsIGdldEV2ZW50SGFzaCB9IGZyb20gJy4vY3JlYXRpb24nO1xuZXhwb3J0IHsgdmFsaWRhdGVFdmVudCwgY2FsY3VsYXRlRXZlbnRJZCB9IGZyb20gJy4vc2lnbmluZyc7XG4iLCAiLyoqXG4gKiBAbW9kdWxlIGV2ZW50L2NyZWF0aW9uXG4gKiBAZGVzY3JpcHRpb24gRXZlbnQgY3JlYXRpb24gYW5kIHNlcmlhbGl6YXRpb24gdXRpbGl0aWVzIGZvciBOb3N0clxuICovXG5cbmltcG9ydCB7IHNoYTI1NiB9IGZyb20gJ0Bub2JsZS9oYXNoZXMvc2hhMi5qcyc7XG5pbXBvcnQgeyBieXRlc1RvSGV4IH0gZnJvbSAnQG5vYmxlL2hhc2hlcy91dGlscy5qcyc7XG5pbXBvcnQgeyBsb2dnZXIgfSBmcm9tICcuLi91dGlscy9sb2dnZXInO1xuaW1wb3J0IHR5cGUgeyBOb3N0ckV2ZW50LCBOb3N0ckV2ZW50S2luZCB9IGZyb20gJy4uL3R5cGVzL2luZGV4JztcblxuLyoqXG4gKiBDcmVhdGVzIGEgbmV3IE5vc3RyIGV2ZW50IHdpdGggdGhlIHNwZWNpZmllZCBwYXJhbWV0ZXJzXG4gKiBAcGFyYW0gcGFyYW1zIC0gRXZlbnQgcGFyYW1ldGVyc1xuICogQHJldHVybnMgQ3JlYXRlZCBldmVudFxuICovXG5leHBvcnQgZnVuY3Rpb24gY3JlYXRlRXZlbnQocGFyYW1zOiB7XG4gIGtpbmQ6IE5vc3RyRXZlbnRLaW5kO1xuICBjb250ZW50OiBzdHJpbmc7XG4gIHRhZ3M/OiBzdHJpbmdbXVtdO1xuICBjcmVhdGVkX2F0PzogbnVtYmVyO1xuICBwdWJrZXk/OiBzdHJpbmc7XG59KTogTm9zdHJFdmVudCB7XG4gIGNvbnN0IHsgXG4gICAga2luZCwgXG4gICAgY29udGVudCwgXG4gICAgdGFncyA9IFtdLCBcbiAgICBjcmVhdGVkX2F0ID0gTWF0aC5mbG9vcihEYXRlLm5vdygpIC8gMTAwMCksIFxuICAgIHB1YmtleSA9ICcnIFxuICB9ID0gcGFyYW1zO1xuICBcbiAgcmV0dXJuIHtcbiAgICBraW5kLFxuICAgIGNvbnRlbnQsXG4gICAgdGFncyxcbiAgICBjcmVhdGVkX2F0LFxuICAgIHB1YmtleSxcbiAgfTtcbn1cblxuLyoqXG4gKiBTZXJpYWxpemVzIGEgTm9zdHIgZXZlbnQgZm9yIHNpZ25pbmcvaGFzaGluZyAoTklQLTAxKVxuICogQHBhcmFtIGV2ZW50IC0gRXZlbnQgdG8gc2VyaWFsaXplXG4gKiBAcmV0dXJucyBTZXJpYWxpemVkIGV2ZW50IEpTT04gc3RyaW5nXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBzZXJpYWxpemVFdmVudChldmVudDogTm9zdHJFdmVudCk6IHN0cmluZyB7XG4gIHJldHVybiBKU09OLnN0cmluZ2lmeShbXG4gICAgMCxcbiAgICBldmVudC5wdWJrZXksXG4gICAgZXZlbnQuY3JlYXRlZF9hdCxcbiAgICBldmVudC5raW5kLFxuICAgIGV2ZW50LnRhZ3MsXG4gICAgZXZlbnQuY29udGVudFxuICBdKTtcbn1cblxuLyoqXG4gKiBDYWxjdWxhdGVzIHRoZSBoYXNoIG9mIGEgTm9zdHIgZXZlbnQgKE5JUC0wMSlcbiAqIEBwYXJhbSBldmVudCAtIEV2ZW50IHRvIGhhc2hcbiAqIEByZXR1cm5zIEV2ZW50IGhhc2ggaW4gaGV4IGZvcm1hdFxuICovXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gZ2V0RXZlbnRIYXNoKGV2ZW50OiBOb3N0ckV2ZW50KTogUHJvbWlzZTxzdHJpbmc+IHtcbiAgdHJ5IHtcbiAgICBjb25zdCBzZXJpYWxpemVkID0gc2VyaWFsaXplRXZlbnQoZXZlbnQpO1xuICAgIGNvbnN0IGhhc2ggPSBhd2FpdCBzaGEyNTYobmV3IFRleHRFbmNvZGVyKCkuZW5jb2RlKHNlcmlhbGl6ZWQpKTtcbiAgICByZXR1cm4gYnl0ZXNUb0hleChoYXNoKTtcbiAgfSBjYXRjaCAoZXJyb3IpIHtcbiAgICBsb2dnZXIuZXJyb3IoeyBlcnJvciB9LCAnRmFpbGVkIHRvIGdldCBldmVudCBoYXNoJyk7XG4gICAgdGhyb3cgZXJyb3I7XG4gIH1cbn1cbiIsICIvKipcbiAqIEBtb2R1bGUgZXZlbnQvc2lnbmluZ1xuICogQGRlc2NyaXB0aW9uIEV2ZW50IHNpZ25pbmcgYW5kIHZlcmlmaWNhdGlvbiB1dGlsaXRpZXMgZm9yIE5vc3RyXG4gKi9cblxuaW1wb3J0IHsgc2Nobm9yciB9IGZyb20gJ0Bub2JsZS9jdXJ2ZXMvc2VjcDI1NmsxLmpzJztcbmltcG9ydCB7IGJ5dGVzVG9IZXgsIGhleFRvQnl0ZXMgfSBmcm9tICdAbm9ibGUvaGFzaGVzL3V0aWxzLmpzJztcbmltcG9ydCB7IGxvZ2dlciB9IGZyb20gJy4uL3V0aWxzL2xvZ2dlcic7XG5pbXBvcnQgeyBnZXRFdmVudEhhc2ggfSBmcm9tICcuL2NyZWF0aW9uJztcbmltcG9ydCB0eXBlIHsgTm9zdHJFdmVudCwgU2lnbmVkTm9zdHJFdmVudCB9IGZyb20gJy4uL3R5cGVzJztcblxuLyoqXG4gKiBTaWducyBhIE5vc3RyIGV2ZW50IHdpdGggYSBwcml2YXRlIGtleSAoTklQLTAxKVxuICogQHBhcmFtIGV2ZW50IC0gRXZlbnQgdG8gc2lnblxuICogQHBhcmFtIHByaXZhdGVLZXkgLSBQcml2YXRlIGtleSBpbiBoZXggZm9ybWF0XG4gKiBAcmV0dXJucyBTaWduZWQgZXZlbnRcbiAqL1xuZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIHNpZ25FdmVudChcbiAgZXZlbnQ6IE5vc3RyRXZlbnQsIFxuICBwcml2YXRlS2V5OiBzdHJpbmdcbik6IFByb21pc2U8U2lnbmVkTm9zdHJFdmVudD4ge1xuICB0cnkge1xuICAgIGNvbnN0IGhhc2ggPSBhd2FpdCBnZXRFdmVudEhhc2goZXZlbnQpO1xuICAgIGNvbnN0IHNpZyA9IHNjaG5vcnIuc2lnbihoZXhUb0J5dGVzKGhhc2gpLCBoZXhUb0J5dGVzKHByaXZhdGVLZXkpKTtcbiAgICBcbiAgICByZXR1cm4ge1xuICAgICAgLi4uZXZlbnQsXG4gICAgICBpZDogaGFzaCxcbiAgICAgIHNpZzogYnl0ZXNUb0hleChzaWcpLFxuICAgIH07XG4gIH0gY2F0Y2ggKGVycm9yKSB7XG4gICAgbG9nZ2VyLmVycm9yKHsgZXJyb3IgfSwgJ0ZhaWxlZCB0byBzaWduIGV2ZW50Jyk7XG4gICAgdGhyb3cgZXJyb3I7XG4gIH1cbn1cblxuLyoqXG4gKiBWZXJpZmllcyB0aGUgc2lnbmF0dXJlIG9mIGEgc2lnbmVkIE5vc3RyIGV2ZW50IChOSVAtMDEpXG4gKiBAcGFyYW0gZXZlbnQgLSBFdmVudCB0byB2ZXJpZnlcbiAqIEByZXR1cm5zIFRydWUgaWYgc2lnbmF0dXJlIGlzIHZhbGlkXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiB2ZXJpZnlTaWduYXR1cmUoZXZlbnQ6IFNpZ25lZE5vc3RyRXZlbnQpOiBib29sZWFuIHtcbiAgdHJ5IHtcbiAgICByZXR1cm4gc2Nobm9yci52ZXJpZnkoXG4gICAgICBoZXhUb0J5dGVzKGV2ZW50LnNpZyksXG4gICAgICBoZXhUb0J5dGVzKGV2ZW50LmlkKSxcbiAgICAgIGhleFRvQnl0ZXMoZXZlbnQucHVia2V5KVxuICAgICk7XG4gIH0gY2F0Y2ggKGVycm9yKSB7XG4gICAgbG9nZ2VyLmVycm9yKHsgZXJyb3IgfSwgJ0ZhaWxlZCB0byB2ZXJpZnkgc2lnbmF0dXJlJyk7XG4gICAgcmV0dXJuIGZhbHNlO1xuICB9XG59XG5cbi8qKlxuICogVmFsaWRhdGVzIGEgTm9zdHIgZXZlbnRcbiAqIEBwYXJhbSBldmVudCAtIEV2ZW50IHRvIHZhbGlkYXRlXG4gKiBAcmV0dXJucyBUcnVlIGlmIGV2ZW50IGlzIHZhbGlkXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiB2YWxpZGF0ZUV2ZW50KGV2ZW50OiBTaWduZWROb3N0ckV2ZW50KTogYm9vbGVhbiB7XG4gIHRyeSB7XG4gICAgLy8gQ2hlY2sgcmVxdWlyZWQgZmllbGRzXG4gICAgaWYgKCFldmVudC5pZCB8fCAhZXZlbnQucHVia2V5IHx8ICFldmVudC5zaWcpIHtcbiAgICAgIHJldHVybiBmYWxzZTtcbiAgICB9XG5cbiAgICAvLyBWZXJpZnkgc2lnbmF0dXJlXG4gICAgcmV0dXJuIHZlcmlmeVNpZ25hdHVyZShldmVudCk7XG4gIH0gY2F0Y2ggKGVycm9yKSB7XG4gICAgbG9nZ2VyLmVycm9yKHsgZXJyb3IgfSwgJ0Vycm9yIHZhbGlkYXRpbmcgZXZlbnQnKTtcbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cbn1cblxuLyoqXG4gKiBDYWxjdWxhdGVzIHRoZSBldmVudCBJRCBmb3IgYSBOb3N0ciBldmVudFxuICogQHBhcmFtIGV2ZW50IC0gRXZlbnQgdG8gY2FsY3VsYXRlIElEIGZvclxuICogQHJldHVybnMgRXZlbnQgSURcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGNhbGN1bGF0ZUV2ZW50SWQoZXZlbnQ6IE5vc3RyRXZlbnQpOiBQcm9taXNlPHN0cmluZz4ge1xuICByZXR1cm4gZ2V0RXZlbnRIYXNoKGV2ZW50KTtcbn1cbiIsICIvKipcbiAqIEBtb2R1bGUgbmlwcy9uaXAtMDRcbiAqIEBkZXNjcmlwdGlvbiBJbXBsZW1lbnRhdGlvbiBvZiBOSVAtMDQgKEVuY3J5cHRlZCBEaXJlY3QgTWVzc2FnZXMpXG4gKiBAc2VlIGh0dHBzOi8vZ2l0aHViLmNvbS9ub3N0ci1wcm90b2NvbC9uaXBzL2Jsb2IvbWFzdGVyLzA0Lm1kXG4gKi9cblxuaW1wb3J0IHsgc2VjcDI1NmsxIH0gZnJvbSAnQG5vYmxlL2N1cnZlcy9zZWNwMjU2azEuanMnO1xuaW1wb3J0IHsgaGV4VG9CeXRlcyB9IGZyb20gJ0Bub2JsZS9oYXNoZXMvdXRpbHMuanMnO1xuaW1wb3J0IHsgbG9nZ2VyIH0gZnJvbSAnLi4vdXRpbHMvbG9nZ2VyJztcbmltcG9ydCB7IGJ5dGVzVG9CYXNlNjQsIGJhc2U2NFRvQnl0ZXMgfSBmcm9tICcuLi9lbmNvZGluZy9iYXNlNjQnO1xuaW1wb3J0IHR5cGUgeyBDcnlwdG9TdWJ0bGUgfSBmcm9tICcuLi9jcnlwdG8nO1xuXG5cbi8vIENvbmZpZ3VyZSBjcnlwdG8gZm9yIE5vZGUuanMgYW5kIHRlc3QgZW52aXJvbm1lbnRzXG5kZWNsYXJlIGdsb2JhbCB7XG4gIGludGVyZmFjZSBXaW5kb3cge1xuICAgIGNyeXB0bzogQ3J5cHRvU3VidGxlO1xuICB9XG4gIGludGVyZmFjZSBHbG9iYWwge1xuICAgIGNyeXB0bzogQ3J5cHRvU3VidGxlO1xuICB9XG59XG5cbmNvbnN0IGdldENyeXB0byA9IGFzeW5jICgpOiBQcm9taXNlPENyeXB0b1N1YnRsZT4gPT4ge1xuICBpZiAodHlwZW9mIHdpbmRvdyAhPT0gJ3VuZGVmaW5lZCcgJiYgd2luZG93LmNyeXB0bykge1xuICAgIHJldHVybiB3aW5kb3cuY3J5cHRvO1xuICB9XG4gIGlmICh0eXBlb2YgZ2xvYmFsICE9PSAndW5kZWZpbmVkJyAmJiAoZ2xvYmFsIGFzIEdsb2JhbCkuY3J5cHRvKSB7XG4gICAgcmV0dXJuIChnbG9iYWwgYXMgR2xvYmFsKS5jcnlwdG87XG4gIH1cbiAgdHJ5IHtcbiAgICBjb25zdCBjcnlwdG9Nb2R1bGUgPSBhd2FpdCBpbXBvcnQoJ2NyeXB0bycpO1xuICAgIGlmIChjcnlwdG9Nb2R1bGUud2ViY3J5cHRvKSB7XG4gICAgICByZXR1cm4gY3J5cHRvTW9kdWxlLndlYmNyeXB0byBhcyBDcnlwdG9TdWJ0bGU7XG4gICAgfVxuICB9IGNhdGNoIHtcbiAgICBsb2dnZXIuZGVidWcoJ05vZGUgY3J5cHRvIG5vdCBhdmFpbGFibGUnKTtcbiAgfVxuXG4gIHRocm93IG5ldyBFcnJvcignTm8gV2ViQ3J5cHRvIGltcGxlbWVudGF0aW9uIGF2YWlsYWJsZScpO1xufTtcblxuY2xhc3MgQ3J5cHRvSW1wbGVtZW50YXRpb24ge1xuICBwcml2YXRlIGNyeXB0b0luc3RhbmNlOiBDcnlwdG9TdWJ0bGUgfCBudWxsID0gbnVsbDtcbiAgcHJpdmF0ZSBpbml0UHJvbWlzZTogUHJvbWlzZTx2b2lkPjtcblxuICBjb25zdHJ1Y3RvcigpIHtcbiAgICB0aGlzLmluaXRQcm9taXNlID0gdGhpcy5pbml0aWFsaXplKCk7XG4gIH1cblxuICBwcml2YXRlIGFzeW5jIGluaXRpYWxpemUoKTogUHJvbWlzZTx2b2lkPiB7XG4gICAgdGhpcy5jcnlwdG9JbnN0YW5jZSA9IGF3YWl0IGdldENyeXB0bygpO1xuICB9XG5cbiAgcHJpdmF0ZSBhc3luYyBlbnN1cmVJbml0aWFsaXplZCgpOiBQcm9taXNlPENyeXB0b1N1YnRsZT4ge1xuICAgIGF3YWl0IHRoaXMuaW5pdFByb21pc2U7XG4gICAgaWYgKCF0aGlzLmNyeXB0b0luc3RhbmNlKSB7XG4gICAgICB0aHJvdyBuZXcgRXJyb3IoJ0NyeXB0byBpbXBsZW1lbnRhdGlvbiBub3QgaW5pdGlhbGl6ZWQnKTtcbiAgICB9XG4gICAgcmV0dXJuIHRoaXMuY3J5cHRvSW5zdGFuY2U7XG4gIH1cblxuICBhc3luYyBnZXRTdWJ0bGUoKTogUHJvbWlzZTxDcnlwdG9TdWJ0bGVbJ3N1YnRsZSddPiB7XG4gICAgY29uc3QgY3J5cHRvID0gYXdhaXQgdGhpcy5lbnN1cmVJbml0aWFsaXplZCgpO1xuICAgIHJldHVybiBjcnlwdG8uc3VidGxlO1xuICB9XG5cbiAgYXN5bmMgZ2V0UmFuZG9tVmFsdWVzPFQgZXh0ZW5kcyBVaW50OEFycmF5IHwgSW50OEFycmF5IHwgVWludDE2QXJyYXkgfCBJbnQxNkFycmF5IHwgVWludDMyQXJyYXkgfCBJbnQzMkFycmF5PihhcnJheTogVCk6IFByb21pc2U8VD4ge1xuICAgIGNvbnN0IGNyeXB0byA9IGF3YWl0IHRoaXMuZW5zdXJlSW5pdGlhbGl6ZWQoKTtcbiAgICByZXR1cm4gY3J5cHRvLmdldFJhbmRvbVZhbHVlcyhhcnJheSk7XG4gIH1cbn1cblxuY29uc3QgY3J5cHRvSW1wbCA9IG5ldyBDcnlwdG9JbXBsZW1lbnRhdGlvbigpO1xuXG5pbnRlcmZhY2UgU2hhcmVkU2VjcmV0IHtcbiAgc2hhcmVkU2VjcmV0OiBVaW50OEFycmF5O1xufVxuXG4vKipcbiAqIEVuY3J5cHRzIGEgbWVzc2FnZSB1c2luZyBOSVAtMDQgZW5jcnlwdGlvblxuICogQHBhcmFtIG1lc3NhZ2UgLSBNZXNzYWdlIHRvIGVuY3J5cHRcbiAqIEBwYXJhbSBzZW5kZXJQcml2S2V5IC0gU2VuZGVyJ3MgcHJpdmF0ZSBrZXlcbiAqIEBwYXJhbSByZWNpcGllbnRQdWJLZXkgLSBSZWNpcGllbnQncyBwdWJsaWMga2V5XG4gKiBAcmV0dXJucyBFbmNyeXB0ZWQgbWVzc2FnZSBzdHJpbmdcbiAqL1xuZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIGVuY3J5cHRNZXNzYWdlKFxuICBtZXNzYWdlOiBzdHJpbmcsXG4gIHNlbmRlclByaXZLZXk6IHN0cmluZyxcbiAgcmVjaXBpZW50UHViS2V5OiBzdHJpbmdcbik6IFByb21pc2U8c3RyaW5nPiB7XG4gIHRyeSB7XG4gICAgaWYgKCFtZXNzYWdlIHx8ICFzZW5kZXJQcml2S2V5IHx8ICFyZWNpcGllbnRQdWJLZXkpIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcignSW52YWxpZCBpbnB1dCBwYXJhbWV0ZXJzJyk7XG4gICAgfVxuXG4gICAgLy8gVmFsaWRhdGUga2V5c1xuICAgIGlmICghL15bMC05YS1mXXs2NH0kL2kudGVzdChzZW5kZXJQcml2S2V5KSkge1xuICAgICAgdGhyb3cgbmV3IEVycm9yKCdJbnZhbGlkIHByaXZhdGUga2V5IGZvcm1hdCcpO1xuICAgIH1cblxuICAgIC8vIEVuc3VyZSBwdWJsaWMga2V5IGlzIGluIGNvcnJlY3QgZm9ybWF0XG4gICAgY29uc3QgcHViS2V5SGV4ID0gcmVjaXBpZW50UHViS2V5LnN0YXJ0c1dpdGgoJzAyJykgfHwgcmVjaXBpZW50UHViS2V5LnN0YXJ0c1dpdGgoJzAzJykgXG4gICAgICA/IHJlY2lwaWVudFB1YktleSBcbiAgICAgIDogJzAyJyArIHJlY2lwaWVudFB1YktleTtcblxuICAgIC8vIEdlbmVyYXRlIHNoYXJlZCBzZWNyZXRcbiAgICBjb25zdCBzaGFyZWRQb2ludCA9IHNlY3AyNTZrMS5nZXRTaGFyZWRTZWNyZXQoaGV4VG9CeXRlcyhzZW5kZXJQcml2S2V5KSwgaGV4VG9CeXRlcyhwdWJLZXlIZXgpKTtcbiAgICBjb25zdCBzaGFyZWRYID0gc2hhcmVkUG9pbnQuc2xpY2UoMSwgMzMpOyAvLyBVc2Ugb25seSB4LWNvb3JkaW5hdGVcblxuICAgIC8vIEltcG9ydCBrZXkgZm9yIEFFU1xuICAgIGNvbnN0IHNoYXJlZEtleSA9IGF3YWl0IChhd2FpdCBjcnlwdG9JbXBsLmdldFN1YnRsZSgpKS5pbXBvcnRLZXkoXG4gICAgICAncmF3JyxcbiAgICAgIHNoYXJlZFguYnVmZmVyLFxuICAgICAgeyBuYW1lOiAnQUVTLUNCQycsIGxlbmd0aDogMjU2IH0sXG4gICAgICBmYWxzZSxcbiAgICAgIFsnZW5jcnlwdCddXG4gICAgKTtcblxuICAgIC8vIFplcm8gc2hhcmVkIHNlY3JldCBtYXRlcmlhbCBub3cgdGhhdCBBRVMga2V5IGlzIGltcG9ydGVkXG4gICAgc2hhcmVkWC5maWxsKDApO1xuICAgIHNoYXJlZFBvaW50LmZpbGwoMCk7XG5cbiAgICAvLyBHZW5lcmF0ZSBJViBhbmQgZW5jcnlwdFxuICAgIGNvbnN0IGl2ID0gbmV3IFVpbnQ4QXJyYXkoMTYpO1xuICAgIGF3YWl0IGNyeXB0b0ltcGwuZ2V0UmFuZG9tVmFsdWVzKGl2KTtcblxuICAgIGNvbnN0IGVuY29kZWQgPSBuZXcgVGV4dEVuY29kZXIoKS5lbmNvZGUobWVzc2FnZSk7XG4gICAgY29uc3QgZW5jcnlwdGVkID0gYXdhaXQgKGF3YWl0IGNyeXB0b0ltcGwuZ2V0U3VidGxlKCkpLmVuY3J5cHQoXG4gICAgICB7IG5hbWU6ICdBRVMtQ0JDJywgaXYgfSxcbiAgICAgIHNoYXJlZEtleSxcbiAgICAgIGVuY29kZWQuYnVmZmVyXG4gICAgKTtcblxuICAgIC8vIE5JUC0wNCBzdGFuZGFyZCBmb3JtYXQ6IGJhc2U2NChjaXBoZXJ0ZXh0KSArIFwiP2l2PVwiICsgYmFzZTY0KGl2KVxuICAgIGNvbnN0IGNpcGhlcnRleHRCYXNlNjQgPSBieXRlc1RvQmFzZTY0KG5ldyBVaW50OEFycmF5KGVuY3J5cHRlZCkpO1xuICAgIGNvbnN0IGl2QmFzZTY0ID0gYnl0ZXNUb0Jhc2U2NChpdik7XG5cbiAgICByZXR1cm4gY2lwaGVydGV4dEJhc2U2NCArICc/aXY9JyArIGl2QmFzZTY0O1xuICB9IGNhdGNoIChlcnJvcikge1xuICAgIGxvZ2dlci5lcnJvcih7IGVycm9yIH0sICdGYWlsZWQgdG8gZW5jcnlwdCBtZXNzYWdlJyk7XG4gICAgdGhyb3cgZXJyb3I7XG4gIH1cbn1cblxuLyoqXG4gKiBEZWNyeXB0cyBhIG1lc3NhZ2UgdXNpbmcgTklQLTA0IGRlY3J5cHRpb25cbiAqIEBwYXJhbSBlbmNyeXB0ZWRNZXNzYWdlIC0gRW5jcnlwdGVkIG1lc3NhZ2Ugc3RyaW5nXG4gKiBAcGFyYW0gcmVjaXBpZW50UHJpdktleSAtIFJlY2lwaWVudCdzIHByaXZhdGUga2V5XG4gKiBAcGFyYW0gc2VuZGVyUHViS2V5IC0gU2VuZGVyJ3MgcHVibGljIGtleVxuICogQHJldHVybnMgRGVjcnlwdGVkIG1lc3NhZ2Ugc3RyaW5nXG4gKi9cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBkZWNyeXB0TWVzc2FnZShcbiAgZW5jcnlwdGVkTWVzc2FnZTogc3RyaW5nLFxuICByZWNpcGllbnRQcml2S2V5OiBzdHJpbmcsXG4gIHNlbmRlclB1YktleTogc3RyaW5nXG4pOiBQcm9taXNlPHN0cmluZz4ge1xuICB0cnkge1xuICAgIGlmICghZW5jcnlwdGVkTWVzc2FnZSB8fCAhcmVjaXBpZW50UHJpdktleSB8fCAhc2VuZGVyUHViS2V5KSB7XG4gICAgICB0aHJvdyBuZXcgRXJyb3IoJ0ludmFsaWQgaW5wdXQgcGFyYW1ldGVycycpO1xuICAgIH1cblxuICAgIC8vIFZhbGlkYXRlIGtleXNcbiAgICBpZiAoIS9eWzAtOWEtZl17NjR9JC9pLnRlc3QocmVjaXBpZW50UHJpdktleSkpIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcignSW52YWxpZCBwcml2YXRlIGtleSBmb3JtYXQnKTtcbiAgICB9XG5cbiAgICAvLyBFbnN1cmUgcHVibGljIGtleSBpcyBpbiBjb3JyZWN0IGZvcm1hdFxuICAgIGNvbnN0IHB1YktleUhleCA9IHNlbmRlclB1YktleS5zdGFydHNXaXRoKCcwMicpIHx8IHNlbmRlclB1YktleS5zdGFydHNXaXRoKCcwMycpXG4gICAgICA/IHNlbmRlclB1YktleVxuICAgICAgOiAnMDInICsgc2VuZGVyUHViS2V5O1xuXG4gICAgLy8gR2VuZXJhdGUgc2hhcmVkIHNlY3JldFxuICAgIGNvbnN0IHNoYXJlZFBvaW50ID0gc2VjcDI1NmsxLmdldFNoYXJlZFNlY3JldChoZXhUb0J5dGVzKHJlY2lwaWVudFByaXZLZXkpLCBoZXhUb0J5dGVzKHB1YktleUhleCkpO1xuICAgIGNvbnN0IHNoYXJlZFggPSBzaGFyZWRQb2ludC5zbGljZSgxLCAzMyk7IC8vIFVzZSBvbmx5IHgtY29vcmRpbmF0ZVxuXG4gICAgLy8gSW1wb3J0IGtleSBmb3IgQUVTXG4gICAgY29uc3Qgc2hhcmVkS2V5ID0gYXdhaXQgKGF3YWl0IGNyeXB0b0ltcGwuZ2V0U3VidGxlKCkpLmltcG9ydEtleShcbiAgICAgICdyYXcnLFxuICAgICAgc2hhcmVkWC5idWZmZXIsXG4gICAgICB7IG5hbWU6ICdBRVMtQ0JDJywgbGVuZ3RoOiAyNTYgfSxcbiAgICAgIGZhbHNlLFxuICAgICAgWydkZWNyeXB0J11cbiAgICApO1xuXG4gICAgLy8gWmVybyBzaGFyZWQgc2VjcmV0IG1hdGVyaWFsIG5vdyB0aGF0IEFFUyBrZXkgaXMgaW1wb3J0ZWRcbiAgICBzaGFyZWRYLmZpbGwoMCk7XG4gICAgc2hhcmVkUG9pbnQuZmlsbCgwKTtcblxuICAgIC8vIFBhcnNlIE5JUC0wNCBzdGFuZGFyZCBmb3JtYXQ6IGJhc2U2NChjaXBoZXJ0ZXh0KSArIFwiP2l2PVwiICsgYmFzZTY0KGl2KVxuICAgIC8vIEFsc28gc3VwcG9ydCBsZWdhY3kgaGV4IGZvcm1hdCAoaXYgKyBjaXBoZXJ0ZXh0IGNvbmNhdGVuYXRlZCkgYXMgZmFsbGJhY2tcbiAgICBsZXQgaXY6IFVpbnQ4QXJyYXk7XG4gICAgbGV0IGNpcGhlcnRleHQ6IFVpbnQ4QXJyYXk7XG5cbiAgICBpZiAoZW5jcnlwdGVkTWVzc2FnZS5pbmNsdWRlcygnP2l2PScpKSB7XG4gICAgICAvLyBOSVAtMDQgc3RhbmRhcmQgZm9ybWF0XG4gICAgICBjb25zdCBbY2lwaGVydGV4dEJhc2U2NCwgaXZCYXNlNjRdID0gZW5jcnlwdGVkTWVzc2FnZS5zcGxpdCgnP2l2PScpO1xuICAgICAgY2lwaGVydGV4dCA9IGJhc2U2NFRvQnl0ZXMoY2lwaGVydGV4dEJhc2U2NCk7XG4gICAgICBpdiA9IGJhc2U2NFRvQnl0ZXMoaXZCYXNlNjQpO1xuICAgIH0gZWxzZSB7XG4gICAgICAvLyBMZWdhY3kgaGV4IGZvcm1hdCBmYWxsYmFjazogZmlyc3QgMTYgYnl0ZXMgYXJlIElWLCByZXN0IGlzIGNpcGhlcnRleHRcbiAgICAgIGNvbnN0IGVuY3J5cHRlZCA9IGhleFRvQnl0ZXMoZW5jcnlwdGVkTWVzc2FnZSk7XG4gICAgICBpdiA9IGVuY3J5cHRlZC5zbGljZSgwLCAxNik7XG4gICAgICBjaXBoZXJ0ZXh0ID0gZW5jcnlwdGVkLnNsaWNlKDE2KTtcbiAgICB9XG5cbiAgICAvLyBEZWNyeXB0XG4gICAgY29uc3QgZGVjcnlwdGVkID0gYXdhaXQgKGF3YWl0IGNyeXB0b0ltcGwuZ2V0U3VidGxlKCkpLmRlY3J5cHQoXG4gICAgICB7IG5hbWU6ICdBRVMtQ0JDJywgaXYgfSxcbiAgICAgIHNoYXJlZEtleSxcbiAgICAgIGNpcGhlcnRleHQuYnVmZmVyIGFzIEFycmF5QnVmZmVyXG4gICAgKTtcblxuICAgIHJldHVybiBuZXcgVGV4dERlY29kZXIoKS5kZWNvZGUoZGVjcnlwdGVkKTtcbiAgfSBjYXRjaCAoZXJyb3IpIHtcbiAgICBsb2dnZXIuZXJyb3IoeyBlcnJvciB9LCAnRmFpbGVkIHRvIGRlY3J5cHQgbWVzc2FnZScpO1xuICAgIHRocm93IGVycm9yO1xuICB9XG59XG5cbi8qKlxuICogR2VuZXJhdGVzIGEgc2hhcmVkIHNlY3JldCBmb3IgTklQLTA0IGVuY3J5cHRpb25cbiAqIEBwYXJhbSBwcml2YXRlS2V5IC0gUHJpdmF0ZSBrZXlcbiAqIEBwYXJhbSBwdWJsaWNLZXkgLSBQdWJsaWMga2V5XG4gKiBAcmV0dXJucyBTaGFyZWQgc2VjcmV0XG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBnZW5lcmF0ZVNoYXJlZFNlY3JldChcbiAgcHJpdmF0ZUtleTogc3RyaW5nLFxuICBwdWJsaWNLZXk6IHN0cmluZ1xuKTogU2hhcmVkU2VjcmV0IHtcbiAgdHJ5IHtcbiAgICBpZiAoIXByaXZhdGVLZXkgfHwgIXB1YmxpY0tleSkge1xuICAgICAgdGhyb3cgbmV3IEVycm9yKCdJbnZhbGlkIGlucHV0IHBhcmFtZXRlcnMnKTtcbiAgICB9XG5cbiAgICAvLyBWYWxpZGF0ZSBrZXlzXG4gICAgaWYgKCEvXlswLTlhLWZdezY0fSQvaS50ZXN0KHByaXZhdGVLZXkpKSB7XG4gICAgICB0aHJvdyBuZXcgRXJyb3IoJ0ludmFsaWQgcHJpdmF0ZSBrZXkgZm9ybWF0Jyk7XG4gICAgfVxuXG4gICAgLy8gRW5zdXJlIHB1YmxpYyBrZXkgaXMgaW4gY29ycmVjdCBmb3JtYXRcbiAgICBjb25zdCBwdWJLZXlIZXggPSBwdWJsaWNLZXkuc3RhcnRzV2l0aCgnMDInKSB8fCBwdWJsaWNLZXkuc3RhcnRzV2l0aCgnMDMnKVxuICAgICAgPyBwdWJsaWNLZXlcbiAgICAgIDogJzAyJyArIHB1YmxpY0tleTtcblxuICAgIC8vIEdlbmVyYXRlIHNoYXJlZCBzZWNyZXRcbiAgICBjb25zdCBzaGFyZWRQb2ludCA9IHNlY3AyNTZrMS5nZXRTaGFyZWRTZWNyZXQoaGV4VG9CeXRlcyhwcml2YXRlS2V5KSwgaGV4VG9CeXRlcyhwdWJLZXlIZXgpKTtcbiAgICByZXR1cm4geyBzaGFyZWRTZWNyZXQ6IHNoYXJlZFBvaW50LnNsaWNlKDEsIDMzKSB9OyAvLyBSZXR1cm4gb25seSB4LWNvb3JkaW5hdGVcbiAgfSBjYXRjaCAoZXJyb3IpIHtcbiAgICBsb2dnZXIuZXJyb3IoeyBlcnJvciB9LCAnRmFpbGVkIHRvIGdlbmVyYXRlIHNoYXJlZCBzZWNyZXQnKTtcbiAgICB0aHJvdyBlcnJvcjtcbiAgfVxufVxuXG5leHBvcnQgeyBnZW5lcmF0ZVNoYXJlZFNlY3JldCBhcyBjb21wdXRlU2hhcmVkU2VjcmV0IH07XG4iLCAiLyoqXG4gKiBAbW9kdWxlIG5pcHMvbmlwLTAxXG4gKiBAZGVzY3JpcHRpb24gSW1wbGVtZW50YXRpb24gb2YgTklQLTAxOiBCYXNpYyBQcm90b2NvbCBGbG93IERlc2NyaXB0aW9uXG4gKiBAc2VlIGh0dHBzOi8vZ2l0aHViLmNvbS9ub3N0ci1wcm90b2NvbC9uaXBzL2Jsb2IvbWFzdGVyLzAxLm1kXG4gKi9cblxuaW1wb3J0IHsgc2Nobm9yciB9IGZyb20gJ0Bub2JsZS9jdXJ2ZXMvc2VjcDI1NmsxLmpzJztcbmltcG9ydCB7IHNoYTI1NiB9IGZyb20gJ0Bub2JsZS9oYXNoZXMvc2hhMi5qcyc7XG5pbXBvcnQgeyBieXRlc1RvSGV4LCBoZXhUb0J5dGVzIH0gZnJvbSAnQG5vYmxlL2hhc2hlcy91dGlscy5qcyc7XG5pbXBvcnQgeyBsb2dnZXIgfSBmcm9tICcuLi91dGlscy9sb2dnZXInO1xuaW1wb3J0IHR5cGUgeyBOb3N0ckV2ZW50LCBTaWduZWROb3N0ckV2ZW50IH0gZnJvbSAnLi4vdHlwZXMnO1xuXG4vKipcbiAqIENyZWF0ZXMgYSBuZXcgTm9zdHIgZXZlbnQgd2l0aCB0aGUgc3BlY2lmaWVkIHBhcmFtZXRlcnMgKE5JUC0wMSlcbiAqIEBwYXJhbSBwYXJhbXMgLSBFdmVudCBwYXJhbWV0ZXJzXG4gKiBAcmV0dXJucyBDcmVhdGVkIGV2ZW50XG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBjcmVhdGVFdmVudChwYXJhbXM6IHtcbiAga2luZDogbnVtYmVyO1xuICBjb250ZW50OiBzdHJpbmc7XG4gIHRhZ3M/OiBzdHJpbmdbXVtdO1xuICBjcmVhdGVkX2F0PzogbnVtYmVyO1xuICBwdWJrZXk/OiBzdHJpbmc7XG59KTogTm9zdHJFdmVudCB7XG4gIGNvbnN0IHsgXG4gICAga2luZCwgXG4gICAgY29udGVudCwgXG4gICAgdGFncyA9IFtdLCBcbiAgICBjcmVhdGVkX2F0ID0gTWF0aC5mbG9vcihEYXRlLm5vdygpIC8gMTAwMCksIFxuICAgIHB1YmtleSA9ICcnIFxuICB9ID0gcGFyYW1zO1xuICBcbiAgcmV0dXJuIHtcbiAgICBraW5kLFxuICAgIGNvbnRlbnQsXG4gICAgdGFncyxcbiAgICBjcmVhdGVkX2F0LFxuICAgIHB1YmtleSxcbiAgfTtcbn1cblxuLyoqXG4gKiBTZXJpYWxpemVzIGEgTm9zdHIgZXZlbnQgZm9yIHNpZ25pbmcvaGFzaGluZyAoTklQLTAxKVxuICogQHBhcmFtIGV2ZW50IC0gRXZlbnQgdG8gc2VyaWFsaXplXG4gKiBAcmV0dXJucyBTZXJpYWxpemVkIGV2ZW50IEpTT04gc3RyaW5nXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBzZXJpYWxpemVFdmVudChldmVudDogTm9zdHJFdmVudCk6IHN0cmluZyB7XG4gIHJldHVybiBKU09OLnN0cmluZ2lmeShbXG4gICAgMCxcbiAgICBldmVudC5wdWJrZXksXG4gICAgZXZlbnQuY3JlYXRlZF9hdCxcbiAgICBldmVudC5raW5kLFxuICAgIGV2ZW50LnRhZ3MsXG4gICAgZXZlbnQuY29udGVudFxuICBdKTtcbn1cblxuLyoqXG4gKiBDYWxjdWxhdGVzIHRoZSBoYXNoIG9mIGEgTm9zdHIgZXZlbnQgKE5JUC0wMSlcbiAqIEBwYXJhbSBldmVudCAtIEV2ZW50IHRvIGhhc2hcbiAqIEByZXR1cm5zIEV2ZW50IGhhc2ggaW4gaGV4IGZvcm1hdFxuICovXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gZ2V0RXZlbnRIYXNoKGV2ZW50OiBOb3N0ckV2ZW50KTogUHJvbWlzZTxzdHJpbmc+IHtcbiAgdHJ5IHtcbiAgICBjb25zdCBzZXJpYWxpemVkID0gc2VyaWFsaXplRXZlbnQoZXZlbnQpO1xuICAgIGNvbnN0IGhhc2ggPSBzaGEyNTYobmV3IFRleHRFbmNvZGVyKCkuZW5jb2RlKHNlcmlhbGl6ZWQpKTtcbiAgICByZXR1cm4gYnl0ZXNUb0hleChoYXNoKTtcbiAgfSBjYXRjaCAoZXJyb3IpIHtcbiAgICBsb2dnZXIuZXJyb3IoeyBlcnJvciB9LCAnRmFpbGVkIHRvIGdldCBldmVudCBoYXNoJyk7XG4gICAgdGhyb3cgZXJyb3I7XG4gIH1cbn1cblxuLyoqXG4gKiBTaWducyBhIE5vc3RyIGV2ZW50IHdpdGggYSBwcml2YXRlIGtleSAoTklQLTAxKVxuICogQHBhcmFtIGV2ZW50IC0gRXZlbnQgdG8gc2lnblxuICogQHBhcmFtIHByaXZhdGVLZXkgLSBQcml2YXRlIGtleSBpbiBoZXggZm9ybWF0XG4gKiBAcmV0dXJucyBTaWduZWQgZXZlbnRcbiAqL1xuZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIHNpZ25FdmVudChcbiAgZXZlbnQ6IE5vc3RyRXZlbnQsIFxuICBwcml2YXRlS2V5OiBzdHJpbmdcbik6IFByb21pc2U8U2lnbmVkTm9zdHJFdmVudD4ge1xuICB0cnkge1xuICAgIGNvbnN0IGhhc2ggPSBhd2FpdCBnZXRFdmVudEhhc2goZXZlbnQpO1xuICAgIGNvbnN0IHNpZyA9IHNjaG5vcnIuc2lnbihoZXhUb0J5dGVzKGhhc2gpLCBoZXhUb0J5dGVzKHByaXZhdGVLZXkpKTtcbiAgICBcbiAgICByZXR1cm4ge1xuICAgICAgLi4uZXZlbnQsXG4gICAgICBpZDogaGFzaCxcbiAgICAgIHNpZzogYnl0ZXNUb0hleChzaWcpLFxuICAgIH07XG4gIH0gY2F0Y2ggKGVycm9yKSB7XG4gICAgbG9nZ2VyLmVycm9yKHsgZXJyb3IgfSwgJ0ZhaWxlZCB0byBzaWduIGV2ZW50Jyk7XG4gICAgdGhyb3cgZXJyb3I7XG4gIH1cbn1cblxuLyoqXG4gKiBWZXJpZmllcyB0aGUgc2lnbmF0dXJlIG9mIGEgc2lnbmVkIE5vc3RyIGV2ZW50IChOSVAtMDEpXG4gKiBAcGFyYW0gZXZlbnQgLSBFdmVudCB0byB2ZXJpZnlcbiAqIEByZXR1cm5zIFRydWUgaWYgc2lnbmF0dXJlIGlzIHZhbGlkXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiB2ZXJpZnlTaWduYXR1cmUoZXZlbnQ6IFNpZ25lZE5vc3RyRXZlbnQpOiBib29sZWFuIHtcbiAgdHJ5IHtcbiAgICAvLyBWZXJpZnkgZXZlbnQgSURcbiAgICBjb25zdCBleHBlY3RlZElkID0gY2FsY3VsYXRlRXZlbnRJZChldmVudCk7XG4gICAgaWYgKGV2ZW50LmlkICE9PSBleHBlY3RlZElkKSB7XG4gICAgICByZXR1cm4gZmFsc2U7XG4gICAgfVxuXG4gICAgLy8gVmVyaWZ5IHNpZ25hdHVyZVxuICAgIHJldHVybiBzY2hub3JyLnZlcmlmeShcbiAgICAgIGhleFRvQnl0ZXMoZXZlbnQuc2lnKSxcbiAgICAgIGhleFRvQnl0ZXMoZXZlbnQuaWQpLFxuICAgICAgaGV4VG9CeXRlcyhldmVudC5wdWJrZXkpXG4gICAgKTtcbiAgfSBjYXRjaCAoZXJyb3IpIHtcbiAgICBsb2dnZXIuZXJyb3IoeyBlcnJvciB9LCAnRmFpbGVkIHRvIHZlcmlmeSBzaWduYXR1cmUnKTtcbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cbn1cblxuLyoqXG4gKiBDYWxjdWxhdGVzIHRoZSBldmVudCBJRCBhY2NvcmRpbmcgdG8gTklQLTAxXG4gKiBAcGFyYW0gZXZlbnQgLSBFdmVudCB0byBjYWxjdWxhdGUgSUQgZm9yXG4gKiBAcmV0dXJucyBFdmVudCBJRCBpbiBoZXggZm9ybWF0XG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBjYWxjdWxhdGVFdmVudElkKGV2ZW50OiBOb3N0ckV2ZW50KTogc3RyaW5nIHtcbiAgY29uc3Qgc2VyaWFsaXplZCA9IHNlcmlhbGl6ZUV2ZW50KGV2ZW50KTtcbiAgY29uc3QgaGFzaCA9IHNoYTI1NihuZXcgVGV4dEVuY29kZXIoKS5lbmNvZGUoc2VyaWFsaXplZCkpO1xuICByZXR1cm4gYnl0ZXNUb0hleChoYXNoKTtcbn1cblxuLyoqXG4gKiBWYWxpZGF0ZXMgYSBOb3N0ciBldmVudCBzdHJ1Y3R1cmUgKE5JUC0wMSlcbiAqIEBwYXJhbSBldmVudCAtIEV2ZW50IHRvIHZhbGlkYXRlXG4gKiBAcmV0dXJucyBUcnVlIGlmIGV2ZW50IHN0cnVjdHVyZSBpcyB2YWxpZFxuICovXG5leHBvcnQgZnVuY3Rpb24gdmFsaWRhdGVFdmVudChldmVudDogTm9zdHJFdmVudCk6IGJvb2xlYW4ge1xuICB0cnkge1xuICAgIGlmICh0eXBlb2YgZXZlbnQuY29udGVudCAhPT0gJ3N0cmluZycpIHJldHVybiBmYWxzZTtcbiAgICBpZiAodHlwZW9mIGV2ZW50LmNyZWF0ZWRfYXQgIT09ICdudW1iZXInKSByZXR1cm4gZmFsc2U7XG4gICAgaWYgKHR5cGVvZiBldmVudC5raW5kICE9PSAnbnVtYmVyJykgcmV0dXJuIGZhbHNlO1xuICAgIGlmICghQXJyYXkuaXNBcnJheShldmVudC50YWdzKSkgcmV0dXJuIGZhbHNlO1xuICAgIGlmICh0eXBlb2YgZXZlbnQucHVia2V5ICE9PSAnc3RyaW5nJykgcmV0dXJuIGZhbHNlO1xuICAgIFxuICAgIC8vIFZhbGlkYXRlIHRhZ3Mgc3RydWN0dXJlXG4gICAgZm9yIChjb25zdCB0YWcgb2YgZXZlbnQudGFncykge1xuICAgICAgaWYgKCFBcnJheS5pc0FycmF5KHRhZykpIHJldHVybiBmYWxzZTtcbiAgICAgIGlmICh0YWcubGVuZ3RoID09PSAwKSByZXR1cm4gZmFsc2U7XG4gICAgICBpZiAodHlwZW9mIHRhZ1swXSAhPT0gJ3N0cmluZycpIHJldHVybiBmYWxzZTtcbiAgICB9XG4gICAgXG4gICAgcmV0dXJuIHRydWU7XG4gIH0gY2F0Y2ggKGVycm9yKSB7XG4gICAgbG9nZ2VyLmVycm9yKHsgZXJyb3IgfSwgJ0ZhaWxlZCB0byB2YWxpZGF0ZSBldmVudCcpO1xuICAgIHJldHVybiBmYWxzZTtcbiAgfVxufVxuIiwgIi8qKlxuICogTklQLTE5OiBiZWNoMzItZW5jb2RlZCBlbnRpdGllc1xuICogSW1wbGVtZW50cyBlbmNvZGluZyBhbmQgZGVjb2Rpbmcgb2YgTm9zdHIgZW50aXRpZXMgdXNpbmcgYmVjaDMyIGZvcm1hdFxuICovXG5cbmltcG9ydCB7IGJlY2gzMiB9IGZyb20gJ2JlY2gzMic7XG5pbXBvcnQgeyBCdWZmZXIgfSBmcm9tICdidWZmZXInO1xuXG5leHBvcnQgdHlwZSBOaXAxOURhdGFUeXBlID0gJ25wdWInIHwgJ25zZWMnIHwgJ25vdGUnIHwgJ25wcm9maWxlJyB8ICduZXZlbnQnIHwgJ25hZGRyJyB8ICducmVsYXknO1xuXG5jb25zdCBWQUxJRF9QUkVGSVhFUzogTmlwMTlEYXRhVHlwZVtdID0gWyducHViJywgJ25zZWMnLCAnbm90ZScsICducHJvZmlsZScsICduZXZlbnQnLCAnbmFkZHInLCAnbnJlbGF5J107XG5cbmV4cG9ydCBpbnRlcmZhY2UgTmlwMTlEYXRhIHtcbiAgdHlwZTogTmlwMTlEYXRhVHlwZTtcbiAgZGF0YTogc3RyaW5nO1xuICByZWxheXM/OiBzdHJpbmdbXTtcbiAgYXV0aG9yPzogc3RyaW5nO1xuICBraW5kPzogbnVtYmVyO1xuICBpZGVudGlmaWVyPzogc3RyaW5nOyAvLyBGb3IgbmFkZHJcbn1cblxuLy8gVExWIHR5cGUgY29uc3RhbnRzXG5jb25zdCBUTFZfVFlQRVMgPSB7XG4gIFNQRUNJQUw6IDAsICAgLy8gTWFpbiBkYXRhIChoZXgpXG4gIFJFTEFZOiAxLCAgICAgLy8gUmVsYXkgVVJMICh1dGY4KVxuICBBVVRIT1I6IDIsICAgIC8vIEF1dGhvciBwdWJrZXkgKGhleClcbiAgS0lORDogMywgICAgICAvLyBFdmVudCBraW5kICh1aW50OClcbiAgSURFTlRJRklFUjogNCAvLyBJZGVudGlmaWVyICh1dGY4KVxufSBhcyBjb25zdDtcblxuLyoqXG4gKiBFbmNvZGUgYSBwdWJsaWMga2V5IGFzIGFuIG5wdWJcbiAqIEBwYXJhbSBwdWJrZXkgUHVibGljIGtleSBpbiBoZXggZm9ybWF0XG4gKiBAcmV0dXJucyBiZWNoMzItZW5jb2RlZCBucHViIHN0cmluZ1xuICogQHRocm93cyB7RXJyb3J9IElmIHB1YmtleSBpcyBpbnZhbGlkXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBucHViRW5jb2RlKHB1YmtleTogc3RyaW5nKTogc3RyaW5nIHtcbiAgdmFsaWRhdGVIZXhTdHJpbmcocHVia2V5LCA2NCk7XG4gIGNvbnN0IGRhdGEgPSBCdWZmZXIuZnJvbShwdWJrZXksICdoZXgnKTtcbiAgY29uc3Qgd29yZHMgPSBiZWNoMzIudG9Xb3JkcyhkYXRhKTtcbiAgcmV0dXJuIGJlY2gzMi5lbmNvZGUoJ25wdWInLCB3b3JkcywgMTAwMCk7XG59XG5cbi8qKlxuICogRW5jb2RlIGEgcHJpdmF0ZSBrZXkgYXMgYW4gbnNlY1xuICogQHBhcmFtIHByaXZrZXkgUHJpdmF0ZSBrZXkgaW4gaGV4IGZvcm1hdFxuICogQHJldHVybnMgYmVjaDMyLWVuY29kZWQgbnNlYyBzdHJpbmdcbiAqIEB0aHJvd3Mge0Vycm9yfSBJZiBwcml2a2V5IGlzIGludmFsaWRcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIG5zZWNFbmNvZGUocHJpdmtleTogc3RyaW5nKTogc3RyaW5nIHtcbiAgdmFsaWRhdGVIZXhTdHJpbmcocHJpdmtleSwgNjQpO1xuICBjb25zdCBkYXRhID0gQnVmZmVyLmZyb20ocHJpdmtleSwgJ2hleCcpO1xuICBjb25zdCB3b3JkcyA9IGJlY2gzMi50b1dvcmRzKGRhdGEpO1xuICByZXR1cm4gYmVjaDMyLmVuY29kZSgnbnNlYycsIHdvcmRzLCAxMDAwKTtcbn1cblxuLyoqXG4gKiBFbmNvZGUgYW4gZXZlbnQgSUQgYXMgYSBub3RlXG4gKiBAcGFyYW0gZXZlbnRJZCBFdmVudCBJRCBpbiBoZXggZm9ybWF0XG4gKiBAcmV0dXJucyBiZWNoMzItZW5jb2RlZCBub3RlIHN0cmluZ1xuICogQHRocm93cyB7RXJyb3J9IElmIGV2ZW50SWQgaXMgaW52YWxpZFxuICovXG5leHBvcnQgZnVuY3Rpb24gbm90ZUVuY29kZShldmVudElkOiBzdHJpbmcpOiBzdHJpbmcge1xuICB2YWxpZGF0ZUhleFN0cmluZyhldmVudElkLCA2NCk7XG4gIGNvbnN0IGRhdGEgPSBCdWZmZXIuZnJvbShldmVudElkLCAnaGV4Jyk7XG4gIGNvbnN0IHdvcmRzID0gYmVjaDMyLnRvV29yZHMoZGF0YSk7XG4gIHJldHVybiBiZWNoMzIuZW5jb2RlKCdub3RlJywgd29yZHMsIDEwMDApO1xufVxuXG4vKipcbiAqIEVuY29kZSBwcm9maWxlIGluZm9ybWF0aW9uXG4gKiBAcGFyYW0gcHVia2V5IFB1YmxpYyBrZXkgaW4gaGV4IGZvcm1hdFxuICogQHBhcmFtIHJlbGF5cyBPcHRpb25hbCByZWxheSBVUkxzXG4gKiBAcmV0dXJucyBiZWNoMzItZW5jb2RlZCBucHJvZmlsZSBzdHJpbmdcbiAqIEB0aHJvd3Mge0Vycm9yfSBJZiBwdWJrZXkgaXMgaW52YWxpZCBvciByZWxheXMgYXJlIG1hbGZvcm1lZFxuICovXG5leHBvcnQgZnVuY3Rpb24gbnByb2ZpbGVFbmNvZGUocHVia2V5OiBzdHJpbmcsIHJlbGF5cz86IHN0cmluZ1tdKTogc3RyaW5nIHtcbiAgdmFsaWRhdGVIZXhTdHJpbmcocHVia2V5LCA2NCk7XG4gIGlmIChyZWxheXMpIHtcbiAgICByZWxheXMuZm9yRWFjaCh2YWxpZGF0ZVJlbGF5VXJsKTtcbiAgfVxuXG4gIGNvbnN0IGRhdGEgPSBlbmNvZGVUTFYoe1xuICAgIHR5cGU6ICducHJvZmlsZScsXG4gICAgZGF0YTogcHVia2V5LFxuICAgIHJlbGF5c1xuICB9KTtcbiAgcmV0dXJuIGJlY2gzMi5lbmNvZGUoJ25wcm9maWxlJywgZGF0YSwgMTAwMCk7XG59XG5cbi8qKlxuICogRW5jb2RlIGV2ZW50IGluZm9ybWF0aW9uXG4gKiBAcGFyYW0gZXZlbnRJZCBFdmVudCBJRCBpbiBoZXggZm9ybWF0XG4gKiBAcGFyYW0gcmVsYXlzIE9wdGlvbmFsIHJlbGF5IFVSTHNcbiAqIEBwYXJhbSBhdXRob3IgT3B0aW9uYWwgYXV0aG9yIHB1YmxpYyBrZXlcbiAqIEBwYXJhbSBraW5kIE9wdGlvbmFsIGV2ZW50IGtpbmRcbiAqIEByZXR1cm5zIGJlY2gzMi1lbmNvZGVkIG5ldmVudCBzdHJpbmdcbiAqIEB0aHJvd3Mge0Vycm9yfSBJZiBwYXJhbWV0ZXJzIGFyZSBpbnZhbGlkXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBuZXZlbnRFbmNvZGUoXG4gIGV2ZW50SWQ6IHN0cmluZyxcbiAgcmVsYXlzPzogc3RyaW5nW10sXG4gIGF1dGhvcj86IHN0cmluZyxcbiAga2luZD86IG51bWJlclxuKTogc3RyaW5nIHtcbiAgdmFsaWRhdGVIZXhTdHJpbmcoZXZlbnRJZCwgNjQpO1xuICBpZiAocmVsYXlzKSB7XG4gICAgcmVsYXlzLmZvckVhY2godmFsaWRhdGVSZWxheVVybCk7XG4gIH1cbiAgaWYgKGF1dGhvcikge1xuICAgIHZhbGlkYXRlSGV4U3RyaW5nKGF1dGhvciwgNjQpO1xuICB9XG4gIGlmIChraW5kICE9PSB1bmRlZmluZWQgJiYgIU51bWJlci5pc0ludGVnZXIoa2luZCkpIHtcbiAgICB0aHJvdyBuZXcgRXJyb3IoJ0ludmFsaWQgZXZlbnQga2luZCcpO1xuICB9XG5cbiAgY29uc3QgZGF0YSA9IGVuY29kZVRMVih7XG4gICAgdHlwZTogJ25ldmVudCcsXG4gICAgZGF0YTogZXZlbnRJZCxcbiAgICByZWxheXMsXG4gICAgYXV0aG9yLFxuICAgIGtpbmRcbiAgfSk7XG4gIHJldHVybiBiZWNoMzIuZW5jb2RlKCduZXZlbnQnLCBkYXRhLCAxMDAwKTtcbn1cblxuLyoqXG4gKiBFbmNvZGUgYW4gYWRkcmVzcyAoTklQLTMzKVxuICogQHBhcmFtIHB1YmtleSBBdXRob3IncyBwdWJsaWMga2V5XG4gKiBAcGFyYW0ga2luZCBFdmVudCBraW5kXG4gKiBAcGFyYW0gaWRlbnRpZmllciBTdHJpbmcgaWRlbnRpZmllclxuICogQHBhcmFtIHJlbGF5cyBPcHRpb25hbCByZWxheSBVUkxzXG4gKiBAcmV0dXJucyBiZWNoMzItZW5jb2RlZCBuYWRkciBzdHJpbmdcbiAqIEB0aHJvd3Mge0Vycm9yfSBJZiBwYXJhbWV0ZXJzIGFyZSBpbnZhbGlkXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBuYWRkckVuY29kZShcbiAgcHVia2V5OiBzdHJpbmcsXG4gIGtpbmQ6IG51bWJlcixcbiAgaWRlbnRpZmllcjogc3RyaW5nLFxuICByZWxheXM/OiBzdHJpbmdbXVxuKTogc3RyaW5nIHtcbiAgdmFsaWRhdGVIZXhTdHJpbmcocHVia2V5LCA2NCk7XG4gIGlmICghTnVtYmVyLmlzSW50ZWdlcihraW5kKSkge1xuICAgIHRocm93IG5ldyBFcnJvcignSW52YWxpZCBldmVudCBraW5kJyk7XG4gIH1cbiAgaWYgKCFpZGVudGlmaWVyKSB7XG4gICAgdGhyb3cgbmV3IEVycm9yKCdJZGVudGlmaWVyIGlzIHJlcXVpcmVkJyk7XG4gIH1cbiAgaWYgKHJlbGF5cykge1xuICAgIHJlbGF5cy5mb3JFYWNoKHZhbGlkYXRlUmVsYXlVcmwpO1xuICB9XG5cbiAgY29uc3QgZGF0YSA9IGVuY29kZVRMVih7XG4gICAgdHlwZTogJ25hZGRyJyxcbiAgICBkYXRhOiBwdWJrZXksXG4gICAga2luZCxcbiAgICBpZGVudGlmaWVyLFxuICAgIHJlbGF5c1xuICB9KTtcbiAgcmV0dXJuIGJlY2gzMi5lbmNvZGUoJ25hZGRyJywgZGF0YSwgMTAwMCk7XG59XG5cbi8qKlxuICogRW5jb2RlIGEgcmVsYXkgVVJMXG4gKiBAcGFyYW0gdXJsIFJlbGF5IFVSTFxuICogQHJldHVybnMgYmVjaDMyLWVuY29kZWQgbnJlbGF5IHN0cmluZ1xuICogQHRocm93cyB7RXJyb3J9IElmIFVSTCBpcyBpbnZhbGlkXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBucmVsYXlFbmNvZGUodXJsOiBzdHJpbmcpOiBzdHJpbmcge1xuICB2YWxpZGF0ZVJlbGF5VXJsKHVybCk7XG4gIGNvbnN0IGRhdGEgPSBCdWZmZXIuZnJvbSh1cmwsICd1dGY4Jyk7XG4gIGNvbnN0IHdvcmRzID0gYmVjaDMyLnRvV29yZHMoZGF0YSk7XG4gIHJldHVybiBiZWNoMzIuZW5jb2RlKCducmVsYXknLCB3b3JkcywgMTAwMCk7XG59XG5cbi8qKlxuICogRGVjb2RlIGEgYmVjaDMyLWVuY29kZWQgTm9zdHIgZW50aXR5XG4gKiBAcGFyYW0gc3RyIGJlY2gzMi1lbmNvZGVkIHN0cmluZ1xuICogQHJldHVybnMgRGVjb2RlZCBkYXRhIHdpdGggdHlwZSBhbmQgbWV0YWRhdGFcbiAqIEB0aHJvd3Mge0Vycm9yfSBJZiBzdHJpbmcgaXMgaW52YWxpZCBvciBtYWxmb3JtZWRcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGRlY29kZShzdHI6IHN0cmluZyk6IE5pcDE5RGF0YSB7XG4gIGlmICghc3RyLmluY2x1ZGVzKCcxJykpIHtcbiAgICB0aHJvdyBuZXcgRXJyb3IoJ0ludmFsaWQgYmVjaDMyIHN0cmluZycpO1xuICB9XG5cbiAgY29uc3QgcHJlZml4ID0gc3RyLnNwbGl0KCcxJylbMF0udG9Mb3dlckNhc2UoKTtcbiAgaWYgKCFWQUxJRF9QUkVGSVhFUy5pbmNsdWRlcyhwcmVmaXggYXMgTmlwMTlEYXRhVHlwZSkpIHtcbiAgICB0aHJvdyBuZXcgRXJyb3IoJ1Vua25vd24gcHJlZml4Jyk7XG4gIH1cblxuICB0cnkge1xuICAgIGNvbnN0IGRlY29kZWQgPSBiZWNoMzIuZGVjb2RlKHN0ciwgMTAwMCk7XG4gICAgY29uc3QgZGF0YSA9IEJ1ZmZlci5mcm9tKGJlY2gzMi5mcm9tV29yZHMoZGVjb2RlZC53b3JkcykpO1xuXG4gICAgLy8gRm9yIG5yZWxheSB0eXBlXG4gICAgbGV0IHVybDogc3RyaW5nO1xuICAgIC8vIEZvciBUTFYgdHlwZXNcbiAgICBsZXQgZGVjb2RlZERhdGE6IE5pcDE5RGF0YTtcblxuICAgIHN3aXRjaCAoZGVjb2RlZC5wcmVmaXgpIHtcbiAgICAgIGNhc2UgJ25wdWInOlxuICAgICAgY2FzZSAnbnNlYyc6XG4gICAgICBjYXNlICdub3RlJzpcbiAgICAgICAgdmFsaWRhdGVIZXhTdHJpbmcoZGF0YS50b1N0cmluZygnaGV4JyksIDY0KTtcbiAgICAgICAgcmV0dXJuIHtcbiAgICAgICAgICB0eXBlOiBkZWNvZGVkLnByZWZpeCBhcyBOaXAxOURhdGFUeXBlLFxuICAgICAgICAgIGRhdGE6IGRhdGEudG9TdHJpbmcoJ2hleCcpXG4gICAgICAgIH07XG4gICAgICBjYXNlICducmVsYXknOlxuICAgICAgICB1cmwgPSBkYXRhLnRvU3RyaW5nKCd1dGY4Jyk7XG4gICAgICAgIHZhbGlkYXRlUmVsYXlVcmwodXJsKTtcbiAgICAgICAgcmV0dXJuIHtcbiAgICAgICAgICB0eXBlOiAnbnJlbGF5JyxcbiAgICAgICAgICBkYXRhOiB1cmxcbiAgICAgICAgfTtcbiAgICAgIGNhc2UgJ25wcm9maWxlJzpcbiAgICAgIGNhc2UgJ25ldmVudCc6XG4gICAgICBjYXNlICduYWRkcic6XG4gICAgICAgIGRlY29kZWREYXRhID0gZGVjb2RlVExWKGRlY29kZWQucHJlZml4IGFzIE5pcDE5RGF0YVR5cGUsIGRhdGEpO1xuICAgICAgICByZXR1cm4gZGVjb2RlZERhdGE7XG4gICAgICBkZWZhdWx0OlxuICAgICAgICB0aHJvdyBuZXcgRXJyb3IoJ1Vua25vd24gcHJlZml4Jyk7XG4gICAgfVxuICB9IGNhdGNoIChlcnJvcjogdW5rbm93bikge1xuICAgIGlmIChlcnJvciBpbnN0YW5jZW9mIEVycm9yKSB7XG4gICAgICB0aHJvdyBlcnJvcjtcbiAgICB9XG4gICAgdGhyb3cgbmV3IEVycm9yKCdJbnZhbGlkIGJlY2gzMiBzdHJpbmcnKTtcbiAgfVxufVxuXG4vLyBIZWxwZXIgZnVuY3Rpb25zXG5cbmZ1bmN0aW9uIHZhbGlkYXRlSGV4U3RyaW5nKHN0cjogc3RyaW5nLCBsZW5ndGg/OiBudW1iZXIpOiB2b2lkIHtcbiAgaWYgKCEvXlswLTlhLWZBLUZdKyQvLnRlc3Qoc3RyKSkge1xuICAgIHRocm93IG5ldyBFcnJvcignSW52YWxpZCBoZXggc3RyaW5nJyk7XG4gIH1cbiAgaWYgKGxlbmd0aCAmJiBzdHIubGVuZ3RoICE9PSBsZW5ndGgpIHtcbiAgICB0aHJvdyBuZXcgRXJyb3IoYEludmFsaWQgaGV4IHN0cmluZyBsZW5ndGggKGV4cGVjdGVkICR7bGVuZ3RofSlgKTtcbiAgfVxufVxuXG5mdW5jdGlvbiB2YWxpZGF0ZVJlbGF5VXJsKHVybDogc3RyaW5nKTogdm9pZCB7XG4gIHRyeSB7XG4gICAgY29uc3QgcGFyc2VkID0gbmV3IFVSTCh1cmwpO1xuICAgIGlmICghWyd3czonLCAnd3NzOiddLmluY2x1ZGVzKHBhcnNlZC5wcm90b2NvbCkpIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcignSW52YWxpZCByZWxheSBVUkwgcHJvdG9jb2wnKTtcbiAgICB9XG4gIH0gY2F0Y2gge1xuICAgIHRocm93IG5ldyBFcnJvcignSW52YWxpZCByZWxheSBVUkwnKTtcbiAgfVxufVxuXG5mdW5jdGlvbiBlbmNvZGVUTFYoZGF0YTogTmlwMTlEYXRhKTogbnVtYmVyW10ge1xuICBjb25zdCByZXN1bHQ6IG51bWJlcltdID0gW107XG4gIFxuICAvLyBTcGVjaWFsICh0eXBlIDApOiBtYWluIGRhdGFcbiAgY29uc3QgYnl0ZXMgPSBCdWZmZXIuZnJvbShkYXRhLmRhdGEsICdoZXgnKTtcbiAgcmVzdWx0LnB1c2goVExWX1RZUEVTLlNQRUNJQUwsIGJ5dGVzLmxlbmd0aCk7XG4gIHJlc3VsdC5wdXNoKC4uLmJ5dGVzKTtcblxuICAvLyBSZWxheSAodHlwZSAxKTogcmVsYXkgVVJMc1xuICBpZiAoZGF0YS5yZWxheXM/Lmxlbmd0aCkge1xuICAgIGZvciAoY29uc3QgcmVsYXkgb2YgZGF0YS5yZWxheXMpIHtcbiAgICAgIGNvbnN0IHJlbGF5Qnl0ZXMgPSBCdWZmZXIuZnJvbShyZWxheSwgJ3V0ZjgnKTtcbiAgICAgIHJlc3VsdC5wdXNoKFRMVl9UWVBFUy5SRUxBWSwgcmVsYXlCeXRlcy5sZW5ndGgpO1xuICAgICAgcmVzdWx0LnB1c2goLi4ucmVsYXlCeXRlcyk7XG4gICAgfVxuICB9XG5cbiAgLy8gQXV0aG9yICh0eXBlIDIpOiBhdXRob3IgcHVia2V5XG4gIGlmIChkYXRhLmF1dGhvcikge1xuICAgIGNvbnN0IGF1dGhvckJ5dGVzID0gQnVmZmVyLmZyb20oZGF0YS5hdXRob3IsICdoZXgnKTtcbiAgICByZXN1bHQucHVzaChUTFZfVFlQRVMuQVVUSE9SLCBhdXRob3JCeXRlcy5sZW5ndGgpO1xuICAgIHJlc3VsdC5wdXNoKC4uLmF1dGhvckJ5dGVzKTtcbiAgfVxuXG4gIC8vIEtpbmQgKHR5cGUgMyk6IGV2ZW50IGtpbmRcbiAgaWYgKGRhdGEua2luZCAhPT0gdW5kZWZpbmVkKSB7XG4gICAgY29uc3Qga2luZEJ5dGVzID0gQnVmZmVyLmFsbG9jKDQpO1xuICAgIGtpbmRCeXRlcy53cml0ZVVJbnQzMkJFKGRhdGEua2luZCk7XG4gICAgcmVzdWx0LnB1c2goVExWX1RZUEVTLktJTkQsIGtpbmRCeXRlcy5sZW5ndGgpO1xuICAgIHJlc3VsdC5wdXNoKC4uLmtpbmRCeXRlcyk7XG4gIH1cblxuICAvLyBJZGVudGlmaWVyICh0eXBlIDQpOiBmb3IgbmFkZHJcbiAgaWYgKGRhdGEuaWRlbnRpZmllcikge1xuICAgIGNvbnN0IGlkZW50aWZpZXJCeXRlcyA9IEJ1ZmZlci5mcm9tKGRhdGEuaWRlbnRpZmllciwgJ3V0ZjgnKTtcbiAgICByZXN1bHQucHVzaChUTFZfVFlQRVMuSURFTlRJRklFUiwgaWRlbnRpZmllckJ5dGVzLmxlbmd0aCk7XG4gICAgcmVzdWx0LnB1c2goLi4uaWRlbnRpZmllckJ5dGVzKTtcbiAgfVxuXG4gIHJldHVybiBiZWNoMzIudG9Xb3JkcyhCdWZmZXIuZnJvbShyZXN1bHQpKTtcbn1cblxuZnVuY3Rpb24gZGVjb2RlVExWKHByZWZpeDogTmlwMTlEYXRhVHlwZSwgZGF0YTogQnVmZmVyKTogTmlwMTlEYXRhIHtcbiAgY29uc3QgcmVzdWx0OiBOaXAxOURhdGEgPSB7XG4gICAgdHlwZTogcHJlZml4LFxuICAgIGRhdGE6ICcnLFxuICAgIHJlbGF5czogW11cbiAgfTtcblxuICBsZXQgaSA9IDA7XG4gIC8vIEZvciByZWxheSB0eXBlXG4gIGxldCByZWxheTogc3RyaW5nO1xuXG4gIHdoaWxlIChpIDwgZGF0YS5sZW5ndGgpIHtcbiAgICBjb25zdCB0eXBlID0gZGF0YVtpXTtcbiAgICBjb25zdCBsZW5ndGggPSBkYXRhW2kgKyAxXTtcbiAgICBcbiAgICBpZiAoaSArIDIgKyBsZW5ndGggPiBkYXRhLmxlbmd0aCkge1xuICAgICAgdGhyb3cgbmV3IEVycm9yKCdJbnZhbGlkIFRMViBkYXRhJyk7XG4gICAgfVxuICAgIFxuICAgIGNvbnN0IHZhbHVlID0gZGF0YS5zbGljZShpICsgMiwgaSArIDIgKyBsZW5ndGgpO1xuXG4gICAgc3dpdGNoICh0eXBlKSB7XG4gICAgICBjYXNlIFRMVl9UWVBFUy5TUEVDSUFMOlxuICAgICAgICByZXN1bHQuZGF0YSA9IHZhbHVlLnRvU3RyaW5nKCdoZXgnKTtcbiAgICAgICAgdmFsaWRhdGVIZXhTdHJpbmcocmVzdWx0LmRhdGEsIDY0KTtcbiAgICAgICAgYnJlYWs7XG4gICAgICBjYXNlIFRMVl9UWVBFUy5SRUxBWTpcbiAgICAgICAgcmVsYXkgPSB2YWx1ZS50b1N0cmluZygndXRmOCcpO1xuICAgICAgICB2YWxpZGF0ZVJlbGF5VXJsKHJlbGF5KTtcbiAgICAgICAgcmVzdWx0LnJlbGF5cyA9IHJlc3VsdC5yZWxheXMgfHwgW107XG4gICAgICAgIHJlc3VsdC5yZWxheXMucHVzaChyZWxheSk7XG4gICAgICAgIGJyZWFrO1xuICAgICAgY2FzZSBUTFZfVFlQRVMuQVVUSE9SOlxuICAgICAgICByZXN1bHQuYXV0aG9yID0gdmFsdWUudG9TdHJpbmcoJ2hleCcpO1xuICAgICAgICB2YWxpZGF0ZUhleFN0cmluZyhyZXN1bHQuYXV0aG9yLCA2NCk7XG4gICAgICAgIGJyZWFrO1xuICAgICAgY2FzZSBUTFZfVFlQRVMuS0lORDpcbiAgICAgICAgcmVzdWx0LmtpbmQgPSB2YWx1ZS5yZWFkVUludDMyQkUoKTtcbiAgICAgICAgYnJlYWs7XG4gICAgICBjYXNlIFRMVl9UWVBFUy5JREVOVElGSUVSOlxuICAgICAgICByZXN1bHQuaWRlbnRpZmllciA9IHZhbHVlLnRvU3RyaW5nKCd1dGY4Jyk7XG4gICAgICAgIGJyZWFrO1xuICAgICAgZGVmYXVsdDpcbiAgICAgICAgLy8gU2tpcCB1bmtub3duIFRMViB0eXBlc1xuICAgICAgICBicmVhaztcbiAgICB9XG5cbiAgICBpICs9IDIgKyBsZW5ndGg7XG4gIH1cblxuICByZXR1cm4gcmVzdWx0O1xufVxuIiwgIi8qKlxuICogTklQLTI2OiBEZWxlZ2F0ZWQgRXZlbnQgU2lnbmluZ1xuICogSW1wbGVtZW50cyBkZWxlZ2F0aW9uIG9mIGV2ZW50IHNpZ25pbmcgY2FwYWJpbGl0aWVzXG4gKi9cblxuaW1wb3J0IHsgc2hhMjU2IH0gZnJvbSAnQG5vYmxlL2hhc2hlcy9zaGEyLmpzJztcbmltcG9ydCB7IE5vc3RyRXZlbnQgfSBmcm9tICcuLi90eXBlcyc7XG5pbXBvcnQgeyBzaWduU2Nobm9yciwgdmVyaWZ5U2Nobm9yclNpZ25hdHVyZSB9IGZyb20gJy4uL2NyeXB0byc7XG5pbXBvcnQgeyBieXRlc1RvSGV4LCBoZXhUb0J5dGVzIH0gZnJvbSAnQG5vYmxlL2hhc2hlcy91dGlscy5qcyc7XG5pbXBvcnQgeyBzY2hub3JyIH0gZnJvbSAnQG5vYmxlL2N1cnZlcy9zZWNwMjU2azEuanMnO1xuXG5leHBvcnQgaW50ZXJmYWNlIERlbGVnYXRpb25Db25kaXRpb25zIHtcbiAga2luZD86IG51bWJlcjtcbiAgc2luY2U/OiBudW1iZXI7XG4gIHVudGlsPzogbnVtYmVyO1xufVxuXG5leHBvcnQgaW50ZXJmYWNlIERlbGVnYXRpb24ge1xuICBkZWxlZ2F0b3I6IHN0cmluZztcbiAgZGVsZWdhdGVlOiBzdHJpbmc7XG4gIGNvbmRpdGlvbnM6IERlbGVnYXRpb25Db25kaXRpb25zO1xuICB0b2tlbjogc3RyaW5nO1xufVxuXG4vKipcbiAqIENyZWF0ZSBhIGRlbGVnYXRpb24gdG9rZW5cbiAqIEBwYXJhbSBkZWxlZ2F0b3JQcml2YXRlS2V5IERlbGVnYXRvcidzIHByaXZhdGUga2V5ICh1c2VkIGZvciBzaWduaW5nIG9ubHksIG5ldmVyIHJldHVybmVkKVxuICogQHBhcmFtIGRlbGVnYXRlZSBEZWxlZ2F0ZWUncyBwdWJsaWMga2V5XG4gKiBAcGFyYW0gY29uZGl0aW9ucyBEZWxlZ2F0aW9uIGNvbmRpdGlvbnNcbiAqIEByZXR1cm5zIERlbGVnYXRpb24gdG9rZW4gKGRlbGVnYXRvciBmaWVsZCBjb250YWlucyB0aGUgUFVCTElDIGtleSwgbm90IHRoZSBwcml2YXRlIGtleSlcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGNyZWF0ZURlbGVnYXRpb24oXG4gIGRlbGVnYXRvclByaXZhdGVLZXk6IHN0cmluZyxcbiAgZGVsZWdhdGVlOiBzdHJpbmcsXG4gIGNvbmRpdGlvbnM6IERlbGVnYXRpb25Db25kaXRpb25zXG4pOiBEZWxlZ2F0aW9uIHtcbiAgY29uc3QgY29uZGl0aW9uc1N0cmluZyA9IHNlcmlhbGl6ZUNvbmRpdGlvbnMoY29uZGl0aW9ucyk7XG4gIGNvbnN0IHRva2VuID0gc2lnbkRlbGVnYXRpb24oZGVsZWdhdG9yUHJpdmF0ZUtleSwgZGVsZWdhdGVlLCBjb25kaXRpb25zU3RyaW5nKTtcblxuICAvLyBEZXJpdmUgdGhlIHB1YmxpYyBrZXkgZnJvbSB0aGUgcHJpdmF0ZSBrZXkgXHUyMDE0IE5FVkVSIHJldHVybiB0aGUgcHJpdmF0ZSBrZXlcbiAgY29uc3QgZGVsZWdhdG9yUHVibGljS2V5ID0gYnl0ZXNUb0hleChzY2hub3JyLmdldFB1YmxpY0tleShoZXhUb0J5dGVzKGRlbGVnYXRvclByaXZhdGVLZXkpKSk7XG5cbiAgcmV0dXJuIHtcbiAgICBkZWxlZ2F0b3I6IGRlbGVnYXRvclB1YmxpY0tleSxcbiAgICBkZWxlZ2F0ZWUsXG4gICAgY29uZGl0aW9ucyxcbiAgICB0b2tlblxuICB9O1xufVxuXG4vKipcbiAqIFZlcmlmeSBhIGRlbGVnYXRpb24gdG9rZW5cbiAqIEBwYXJhbSBkZWxlZ2F0aW9uIERlbGVnYXRpb24gdG8gdmVyaWZ5XG4gKiBAcmV0dXJucyBUcnVlIGlmIHZhbGlkLCBmYWxzZSBvdGhlcndpc2VcbiAqL1xuZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIHZlcmlmeURlbGVnYXRpb24oZGVsZWdhdGlvbjogRGVsZWdhdGlvbik6IFByb21pc2U8Ym9vbGVhbj4ge1xuICBjb25zdCBjb25kaXRpb25zU3RyaW5nID0gc2VyaWFsaXplQ29uZGl0aW9ucyhkZWxlZ2F0aW9uLmNvbmRpdGlvbnMpO1xuICByZXR1cm4gYXdhaXQgdmVyaWZ5RGVsZWdhdGlvblNpZ25hdHVyZShcbiAgICBkZWxlZ2F0aW9uLmRlbGVnYXRvcixcbiAgICBkZWxlZ2F0aW9uLmRlbGVnYXRlZSxcbiAgICBjb25kaXRpb25zU3RyaW5nLFxuICAgIGRlbGVnYXRpb24udG9rZW5cbiAgKTtcbn1cblxuLyoqXG4gKiBDaGVjayBpZiBhbiBldmVudCBtZWV0cyBkZWxlZ2F0aW9uIGNvbmRpdGlvbnNcbiAqIEBwYXJhbSBldmVudCBFdmVudCB0byBjaGVja1xuICogQHBhcmFtIGNvbmRpdGlvbnMgRGVsZWdhdGlvbiBjb25kaXRpb25zXG4gKiBAcmV0dXJucyBUcnVlIGlmIGNvbmRpdGlvbnMgYXJlIG1ldFxuICovXG5leHBvcnQgZnVuY3Rpb24gY2hlY2tEZWxlZ2F0aW9uQ29uZGl0aW9ucyhcbiAgZXZlbnQ6IE5vc3RyRXZlbnQsXG4gIGNvbmRpdGlvbnM6IERlbGVnYXRpb25Db25kaXRpb25zXG4pOiBib29sZWFuIHtcbiAgaWYgKGNvbmRpdGlvbnMua2luZCAhPT0gdW5kZWZpbmVkICYmIGV2ZW50LmtpbmQgIT09IGNvbmRpdGlvbnMua2luZCkge1xuICAgIHJldHVybiBmYWxzZTtcbiAgfVxuXG4gIGlmIChjb25kaXRpb25zLnNpbmNlICE9PSB1bmRlZmluZWQgJiYgZXZlbnQuY3JlYXRlZF9hdCA8IGNvbmRpdGlvbnMuc2luY2UpIHtcbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cblxuICBpZiAoY29uZGl0aW9ucy51bnRpbCAhPT0gdW5kZWZpbmVkICYmIGV2ZW50LmNyZWF0ZWRfYXQgPiBjb25kaXRpb25zLnVudGlsKSB7XG4gICAgcmV0dXJuIGZhbHNlO1xuICB9XG5cbiAgcmV0dXJuIHRydWU7XG59XG5cbi8qKlxuICogQWRkIGRlbGVnYXRpb24gdGFnIHRvIGFuIGV2ZW50XG4gKiBAcGFyYW0gZXZlbnQgRXZlbnQgdG8gYWRkIGRlbGVnYXRpb24gdG9cbiAqIEBwYXJhbSBkZWxlZ2F0aW9uIERlbGVnYXRpb24gdG8gYWRkXG4gKiBAcmV0dXJucyBVcGRhdGVkIGV2ZW50XG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBhZGREZWxlZ2F0aW9uVGFnKFxuICBldmVudDogTm9zdHJFdmVudCxcbiAgZGVsZWdhdGlvbjogRGVsZWdhdGlvblxuKTogTm9zdHJFdmVudCB7XG4gIGNvbnN0IHRhZyA9IFtcbiAgICAnZGVsZWdhdGlvbicsXG4gICAgZGVsZWdhdGlvbi5kZWxlZ2F0b3IsXG4gICAgc2VyaWFsaXplQ29uZGl0aW9ucyhkZWxlZ2F0aW9uLmNvbmRpdGlvbnMpLFxuICAgIGRlbGVnYXRpb24udG9rZW5cbiAgXTtcblxuICByZXR1cm4ge1xuICAgIC4uLmV2ZW50LFxuICAgIHRhZ3M6IFsuLi5ldmVudC50YWdzLCB0YWddXG4gIH07XG59XG5cbi8qKlxuICogRXh0cmFjdCBkZWxlZ2F0aW9uIGZyb20gYW4gZXZlbnRcbiAqIEBwYXJhbSBldmVudCBFdmVudCB0byBleHRyYWN0IGRlbGVnYXRpb24gZnJvbVxuICogQHJldHVybnMgRGVsZWdhdGlvbiBvciBudWxsIGlmIG5vdCBmb3VuZFxuICovXG5leHBvcnQgZnVuY3Rpb24gZXh0cmFjdERlbGVnYXRpb24oZXZlbnQ6IE5vc3RyRXZlbnQpOiBEZWxlZ2F0aW9uIHwgbnVsbCB7XG4gIGNvbnN0IHRhZyA9IGV2ZW50LnRhZ3MuZmluZCh0ID0+IHRbMF0gPT09ICdkZWxlZ2F0aW9uJyk7XG4gIGlmICghdGFnIHx8IHRhZy5sZW5ndGggIT09IDQpIHtcbiAgICByZXR1cm4gbnVsbDtcbiAgfVxuXG4gIHJldHVybiB7XG4gICAgZGVsZWdhdG9yOiB0YWdbMV0sXG4gICAgZGVsZWdhdGVlOiBldmVudC5wdWJrZXksXG4gICAgY29uZGl0aW9uczogcGFyc2VDb25kaXRpb25zKHRhZ1syXSksXG4gICAgdG9rZW46IHRhZ1szXVxuICB9O1xufVxuXG4vLyBIZWxwZXIgZnVuY3Rpb25zXG5mdW5jdGlvbiBzZXJpYWxpemVDb25kaXRpb25zKGNvbmRpdGlvbnM6IERlbGVnYXRpb25Db25kaXRpb25zKTogc3RyaW5nIHtcbiAgY29uc3QgcGFydHM6IHN0cmluZ1tdID0gW107XG5cbiAgaWYgKGNvbmRpdGlvbnMua2luZCAhPT0gdW5kZWZpbmVkKSB7XG4gICAgcGFydHMucHVzaChga2luZD0ke2NvbmRpdGlvbnMua2luZH1gKTtcbiAgfVxuICBpZiAoY29uZGl0aW9ucy5zaW5jZSAhPT0gdW5kZWZpbmVkKSB7XG4gICAgcGFydHMucHVzaChgY3JlYXRlZF9hdD4ke2NvbmRpdGlvbnMuc2luY2V9YCk7XG4gIH1cbiAgaWYgKGNvbmRpdGlvbnMudW50aWwgIT09IHVuZGVmaW5lZCkge1xuICAgIHBhcnRzLnB1c2goYGNyZWF0ZWRfYXQ8JHtjb25kaXRpb25zLnVudGlsfWApO1xuICB9XG5cbiAgcmV0dXJuIHBhcnRzLmpvaW4oJyYnKTtcbn1cblxuZnVuY3Rpb24gcGFyc2VDb25kaXRpb25zKGNvbmRpdGlvbnNTdHJpbmc6IHN0cmluZyk6IERlbGVnYXRpb25Db25kaXRpb25zIHtcbiAgY29uc3QgY29uZGl0aW9uczogRGVsZWdhdGlvbkNvbmRpdGlvbnMgPSB7fTtcbiAgY29uc3QgcGFydHMgPSBjb25kaXRpb25zU3RyaW5nLnNwbGl0KCcmJyk7XG5cbiAgZm9yIChjb25zdCBwYXJ0IG9mIHBhcnRzKSB7XG4gICAgaWYgKHBhcnQuc3RhcnRzV2l0aCgna2luZD0nKSkge1xuICAgICAgY29uZGl0aW9ucy5raW5kID0gcGFyc2VJbnQocGFydC5zbGljZSg1KSk7XG4gICAgfSBlbHNlIGlmIChwYXJ0LnN0YXJ0c1dpdGgoJ2NyZWF0ZWRfYXQ+JykpIHtcbiAgICAgIGNvbmRpdGlvbnMuc2luY2UgPSBwYXJzZUludChwYXJ0LnNsaWNlKDExKSk7XG4gICAgfSBlbHNlIGlmIChwYXJ0LnN0YXJ0c1dpdGgoJ2NyZWF0ZWRfYXQ8JykpIHtcbiAgICAgIGNvbmRpdGlvbnMudW50aWwgPSBwYXJzZUludChwYXJ0LnNsaWNlKDExKSk7XG4gICAgfVxuICB9XG5cbiAgcmV0dXJuIGNvbmRpdGlvbnM7XG59XG5cbmZ1bmN0aW9uIHNpZ25EZWxlZ2F0aW9uKFxuICBkZWxlZ2F0b3I6IHN0cmluZyxcbiAgZGVsZWdhdGVlOiBzdHJpbmcsXG4gIGNvbmRpdGlvbnM6IHN0cmluZ1xuKTogc3RyaW5nIHtcbiAgY29uc3QgbWVzc2FnZSA9IGBub3N0cjpkZWxlZ2F0aW9uOiR7ZGVsZWdhdGVlfToke2NvbmRpdGlvbnN9YDtcbiAgY29uc3QgaGFzaCA9IHNoYTI1NihuZXcgVGV4dEVuY29kZXIoKS5lbmNvZGUobWVzc2FnZSkpO1xuICBjb25zdCBzaWduYXR1cmUgPSBzaWduU2Nobm9ycihoYXNoLCBoZXhUb0J5dGVzKGRlbGVnYXRvcikpO1xuICByZXR1cm4gYnl0ZXNUb0hleChzaWduYXR1cmUpO1xufVxuXG5hc3luYyBmdW5jdGlvbiB2ZXJpZnlEZWxlZ2F0aW9uU2lnbmF0dXJlKFxuICBkZWxlZ2F0b3I6IHN0cmluZyxcbiAgZGVsZWdhdGVlOiBzdHJpbmcsXG4gIGNvbmRpdGlvbnM6IHN0cmluZyxcbiAgc2lnbmF0dXJlOiBzdHJpbmdcbik6IFByb21pc2U8Ym9vbGVhbj4ge1xuICBjb25zdCBtc2dIYXNoID0gc2hhMjU2KG5ldyBUZXh0RW5jb2RlcigpLmVuY29kZShgbm9zdHI6ZGVsZWdhdGlvbjoke2RlbGVnYXRlZX06JHtjb25kaXRpb25zfWApKTtcblxuICByZXR1cm4gdmVyaWZ5U2Nobm9yclNpZ25hdHVyZShoZXhUb0J5dGVzKHNpZ25hdHVyZSksIG1zZ0hhc2gsIGhleFRvQnl0ZXMoZGVsZWdhdG9yKSk7XG59XG4iLCAiLyoqXG4gKiBAbW9kdWxlIG5pcHMvbmlwLTQ0XG4gKiBAZGVzY3JpcHRpb24gSW1wbGVtZW50YXRpb24gb2YgTklQLTQ0IChWZXJzaW9uZWQgRW5jcnlwdGVkIFBheWxvYWRzKVxuICogQHNlZSBodHRwczovL2dpdGh1Yi5jb20vbm9zdHItcHJvdG9jb2wvbmlwcy9ibG9iL21hc3Rlci80NC5tZFxuICovXG5cbmltcG9ydCB7IGNoYWNoYTIwIH0gZnJvbSAnQG5vYmxlL2NpcGhlcnMvY2hhY2hhLmpzJztcbmltcG9ydCB7IGVxdWFsQnl0ZXMgfSBmcm9tICdAbm9ibGUvY2lwaGVycy91dGlscy5qcyc7XG5pbXBvcnQgeyBzZWNwMjU2azEgfSBmcm9tICdAbm9ibGUvY3VydmVzL3NlY3AyNTZrMS5qcyc7XG5pbXBvcnQgeyBleHRyYWN0IGFzIGhrZGZfZXh0cmFjdCwgZXhwYW5kIGFzIGhrZGZfZXhwYW5kIH0gZnJvbSAnQG5vYmxlL2hhc2hlcy9oa2RmLmpzJztcbmltcG9ydCB7IGhtYWMgfSBmcm9tICdAbm9ibGUvaGFzaGVzL2htYWMuanMnO1xuaW1wb3J0IHsgc2hhMjU2IH0gZnJvbSAnQG5vYmxlL2hhc2hlcy9zaGEyLmpzJztcbmltcG9ydCB7IGNvbmNhdEJ5dGVzLCBoZXhUb0J5dGVzLCByYW5kb21CeXRlcyB9IGZyb20gJ0Bub2JsZS9oYXNoZXMvdXRpbHMuanMnO1xuaW1wb3J0IHsgYmFzZTY0IH0gZnJvbSAnQHNjdXJlL2Jhc2UnO1xuXG5jb25zdCB1dGY4RW5jb2RlciA9IG5ldyBUZXh0RW5jb2RlcigpO1xuY29uc3QgdXRmOERlY29kZXIgPSBuZXcgVGV4dERlY29kZXIoKTtcblxuY29uc3QgbWluUGxhaW50ZXh0U2l6ZSA9IDE7XG5jb25zdCBtYXhQbGFpbnRleHRTaXplID0gNjU1MzU7XG5cbi8qKlxuICogQ2FsY3VsYXRlIHBhZGRlZCBsZW5ndGggZm9yIE5JUC00NCBtZXNzYWdlIHBhZGRpbmdcbiAqL1xuZnVuY3Rpb24gY2FsY1BhZGRlZExlbihsZW46IG51bWJlcik6IG51bWJlciB7XG4gIGlmICghTnVtYmVyLmlzU2FmZUludGVnZXIobGVuKSB8fCBsZW4gPCAxKSB0aHJvdyBuZXcgRXJyb3IoJ2V4cGVjdGVkIHBvc2l0aXZlIGludGVnZXInKTtcbiAgaWYgKGxlbiA8PSAzMikgcmV0dXJuIDMyO1xuICBjb25zdCBuZXh0UG93ZXIgPSAxIDw8IChNYXRoLmZsb29yKE1hdGgubG9nMihsZW4gLSAxKSkgKyAxKTtcbiAgY29uc3QgY2h1bmsgPSBuZXh0UG93ZXIgPD0gMjU2ID8gMzIgOiBuZXh0UG93ZXIgLyA4O1xuICByZXR1cm4gY2h1bmsgKiAoTWF0aC5mbG9vcigobGVuIC0gMSkgLyBjaHVuaykgKyAxKTtcbn1cblxuLyoqXG4gKiBQYWQgcGxhaW50ZXh0IHBlciBOSVAtNDQgc3BlY1xuICovXG5mdW5jdGlvbiBwYWQocGxhaW50ZXh0OiBzdHJpbmcpOiBVaW50OEFycmF5IHtcbiAgY29uc3QgdW5wYWRkZWQgPSB1dGY4RW5jb2Rlci5lbmNvZGUocGxhaW50ZXh0KTtcbiAgY29uc3QgdW5wYWRkZWRMZW4gPSB1bnBhZGRlZC5sZW5ndGg7XG4gIGlmICh1bnBhZGRlZExlbiA8IG1pblBsYWludGV4dFNpemUgfHwgdW5wYWRkZWRMZW4gPiBtYXhQbGFpbnRleHRTaXplKVxuICAgIHRocm93IG5ldyBFcnJvcignaW52YWxpZCBwbGFpbnRleHQgbGVuZ3RoOiBtdXN0IGJlIGJldHdlZW4gMSBhbmQgNjU1MzUgYnl0ZXMnKTtcbiAgY29uc3QgcHJlZml4ID0gbmV3IFVpbnQ4QXJyYXkoMik7XG4gIG5ldyBEYXRhVmlldyhwcmVmaXguYnVmZmVyKS5zZXRVaW50MTYoMCwgdW5wYWRkZWRMZW4sIGZhbHNlKTsgLy8gYmlnLWVuZGlhblxuICBjb25zdCBzdWZmaXggPSBuZXcgVWludDhBcnJheShjYWxjUGFkZGVkTGVuKHVucGFkZGVkTGVuKSAtIHVucGFkZGVkTGVuKTtcbiAgcmV0dXJuIGNvbmNhdEJ5dGVzKHByZWZpeCwgdW5wYWRkZWQsIHN1ZmZpeCk7XG59XG5cbi8qKlxuICogVW5wYWQgZGVjcnlwdGVkIG1lc3NhZ2UgcGVyIE5JUC00NCBzcGVjXG4gKi9cbmZ1bmN0aW9uIHVucGFkKHBhZGRlZDogVWludDhBcnJheSk6IHN0cmluZyB7XG4gIGNvbnN0IHVucGFkZGVkTGVuID0gbmV3IERhdGFWaWV3KHBhZGRlZC5idWZmZXIsIHBhZGRlZC5ieXRlT2Zmc2V0KS5nZXRVaW50MTYoMCwgZmFsc2UpO1xuICBjb25zdCB1bnBhZGRlZCA9IHBhZGRlZC5zdWJhcnJheSgyLCAyICsgdW5wYWRkZWRMZW4pO1xuICBpZiAoXG4gICAgdW5wYWRkZWRMZW4gPCBtaW5QbGFpbnRleHRTaXplIHx8XG4gICAgdW5wYWRkZWRMZW4gPiBtYXhQbGFpbnRleHRTaXplIHx8XG4gICAgdW5wYWRkZWQubGVuZ3RoICE9PSB1bnBhZGRlZExlbiB8fFxuICAgIHBhZGRlZC5sZW5ndGggIT09IDIgKyBjYWxjUGFkZGVkTGVuKHVucGFkZGVkTGVuKVxuICApIHtcbiAgICB0aHJvdyBuZXcgRXJyb3IoJ2ludmFsaWQgcGFkZGluZycpO1xuICB9XG4gIHJldHVybiB1dGY4RGVjb2Rlci5kZWNvZGUodW5wYWRkZWQpO1xufVxuXG4vKipcbiAqIERlcml2ZSBjb252ZXJzYXRpb24ga2V5IGZyb20gcHJpdmF0ZSBrZXkgYW5kIHB1YmxpYyBrZXkgdXNpbmcgRUNESCArIEhLREZcbiAqL1xuZnVuY3Rpb24gZ2V0Q29udmVyc2F0aW9uS2V5KHByaXZrZXlBOiBVaW50OEFycmF5LCBwdWJrZXlCOiBzdHJpbmcpOiBVaW50OEFycmF5IHtcbiAgY29uc3Qgc2hhcmVkUG9pbnQgPSBzZWNwMjU2azEuZ2V0U2hhcmVkU2VjcmV0KHByaXZrZXlBLCBoZXhUb0J5dGVzKCcwMicgKyBwdWJrZXlCKSk7XG4gIGNvbnN0IHNoYXJlZFggPSBzaGFyZWRQb2ludC5zdWJhcnJheSgxLCAzMyk7XG4gIHJldHVybiBoa2RmX2V4dHJhY3Qoc2hhMjU2LCBzaGFyZWRYLCB1dGY4RW5jb2Rlci5lbmNvZGUoJ25pcDQ0LXYyJykpO1xufVxuXG4vKipcbiAqIERlcml2ZSBtZXNzYWdlIGtleXMgKGNoYWNoYSBrZXksIGNoYWNoYSBub25jZSwgaG1hYyBrZXkpIGZyb20gY29udmVyc2F0aW9uIGtleSBhbmQgbm9uY2VcbiAqL1xuZnVuY3Rpb24gZ2V0TWVzc2FnZUtleXMoY29udmVyc2F0aW9uS2V5OiBVaW50OEFycmF5LCBub25jZTogVWludDhBcnJheSk6IHtcbiAgY2hhY2hhX2tleTogVWludDhBcnJheTtcbiAgY2hhY2hhX25vbmNlOiBVaW50OEFycmF5O1xuICBobWFjX2tleTogVWludDhBcnJheTtcbn0ge1xuICBjb25zdCBrZXlzID0gaGtkZl9leHBhbmQoc2hhMjU2LCBjb252ZXJzYXRpb25LZXksIG5vbmNlLCA3Nik7XG4gIHJldHVybiB7XG4gICAgY2hhY2hhX2tleToga2V5cy5zdWJhcnJheSgwLCAzMiksXG4gICAgY2hhY2hhX25vbmNlOiBrZXlzLnN1YmFycmF5KDMyLCA0NCksXG4gICAgaG1hY19rZXk6IGtleXMuc3ViYXJyYXkoNDQsIDc2KSxcbiAgfTtcbn1cblxuLyoqXG4gKiBFbmNyeXB0IHBsYWludGV4dCB1c2luZyBOSVAtNDQgdjJcbiAqIEBwYXJhbSBwbGFpbnRleHQgLSBUaGUgbWVzc2FnZSB0byBlbmNyeXB0XG4gKiBAcGFyYW0gY29udmVyc2F0aW9uS2V5IC0gMzItYnl0ZSBjb252ZXJzYXRpb24ga2V5IGZyb20gZ2V0Q29udmVyc2F0aW9uS2V5XG4gKiBAcGFyYW0gbm9uY2UgLSBPcHRpb25hbCAzMi1ieXRlIG5vbmNlIChyYW5kb20gaWYgbm90IHByb3ZpZGVkKVxuICogQHJldHVybnMgQmFzZTY0LWVuY29kZWQgZW5jcnlwdGVkIHBheWxvYWRcbiAqL1xuZnVuY3Rpb24gZW5jcnlwdChwbGFpbnRleHQ6IHN0cmluZywgY29udmVyc2F0aW9uS2V5OiBVaW50OEFycmF5LCBub25jZTogVWludDhBcnJheSA9IHJhbmRvbUJ5dGVzKDMyKSk6IHN0cmluZyB7XG4gIGNvbnN0IHsgY2hhY2hhX2tleSwgY2hhY2hhX25vbmNlLCBobWFjX2tleSB9ID0gZ2V0TWVzc2FnZUtleXMoY29udmVyc2F0aW9uS2V5LCBub25jZSk7XG4gIGNvbnN0IHBhZGRlZCA9IHBhZChwbGFpbnRleHQpO1xuICBjb25zdCBjaXBoZXJ0ZXh0ID0gY2hhY2hhMjAoY2hhY2hhX2tleSwgY2hhY2hhX25vbmNlLCBwYWRkZWQpO1xuICBjb25zdCBtYWMgPSBobWFjKHNoYTI1NiwgaG1hY19rZXksIGNvbmNhdEJ5dGVzKG5vbmNlLCBjaXBoZXJ0ZXh0KSk7XG4gIHJldHVybiBiYXNlNjQuZW5jb2RlKGNvbmNhdEJ5dGVzKG5ldyBVaW50OEFycmF5KFsyXSksIG5vbmNlLCBjaXBoZXJ0ZXh0LCBtYWMpKTtcbn1cblxuLyoqXG4gKiBEZWNyeXB0IGEgTklQLTQ0IHYyIHBheWxvYWRcbiAqIEBwYXJhbSBwYXlsb2FkIC0gQmFzZTY0LWVuY29kZWQgZW5jcnlwdGVkIHBheWxvYWRcbiAqIEBwYXJhbSBjb252ZXJzYXRpb25LZXkgLSAzMi1ieXRlIGNvbnZlcnNhdGlvbiBrZXkgZnJvbSBnZXRDb252ZXJzYXRpb25LZXlcbiAqIEByZXR1cm5zIERlY3J5cHRlZCBwbGFpbnRleHQgc3RyaW5nXG4gKi9cbmZ1bmN0aW9uIGRlY3J5cHQocGF5bG9hZDogc3RyaW5nLCBjb252ZXJzYXRpb25LZXk6IFVpbnQ4QXJyYXkpOiBzdHJpbmcge1xuICBjb25zdCBkYXRhID0gYmFzZTY0LmRlY29kZShwYXlsb2FkKTtcbiAgY29uc3QgdmVyc2lvbiA9IGRhdGFbMF07XG4gIGlmICh2ZXJzaW9uICE9PSAyKSB0aHJvdyBuZXcgRXJyb3IoYHVua25vd24gZW5jcnlwdGlvbiB2ZXJzaW9uOiAke3ZlcnNpb259YCk7XG4gIGlmIChkYXRhLmxlbmd0aCA8IDk5IHx8IGRhdGEubGVuZ3RoID4gNjU2MDMpIHRocm93IG5ldyBFcnJvcignaW52YWxpZCBwYXlsb2FkIHNpemUnKTtcbiAgY29uc3Qgbm9uY2UgPSBkYXRhLnN1YmFycmF5KDEsIDMzKTtcbiAgY29uc3QgY2lwaGVydGV4dCA9IGRhdGEuc3ViYXJyYXkoMzMsIGRhdGEubGVuZ3RoIC0gMzIpO1xuICBjb25zdCBtYWMgPSBkYXRhLnN1YmFycmF5KGRhdGEubGVuZ3RoIC0gMzIpO1xuICBjb25zdCB7IGNoYWNoYV9rZXksIGNoYWNoYV9ub25jZSwgaG1hY19rZXkgfSA9IGdldE1lc3NhZ2VLZXlzKGNvbnZlcnNhdGlvbktleSwgbm9uY2UpO1xuICBjb25zdCBleHBlY3RlZE1hYyA9IGhtYWMoc2hhMjU2LCBobWFjX2tleSwgY29uY2F0Qnl0ZXMobm9uY2UsIGNpcGhlcnRleHQpKTtcbiAgaWYgKCFlcXVhbEJ5dGVzKG1hYywgZXhwZWN0ZWRNYWMpKSB0aHJvdyBuZXcgRXJyb3IoJ2ludmFsaWQgTUFDJyk7XG4gIGNvbnN0IHBhZGRlZCA9IGNoYWNoYTIwKGNoYWNoYV9rZXksIGNoYWNoYV9ub25jZSwgY2lwaGVydGV4dCk7XG4gIHJldHVybiB1bnBhZChwYWRkZWQpO1xufVxuXG4vKipcbiAqIHYyIEFQSSBvYmplY3QgbWF0Y2hpbmcgbm9zdHItdG9vbHMgc2hhcGUgZm9yIGNvbXBhdGliaWxpdHlcbiAqL1xuZXhwb3J0IGNvbnN0IHYyID0ge1xuICB1dGlsczoge1xuICAgIGdldENvbnZlcnNhdGlvbktleSxcbiAgICBjYWxjUGFkZGVkTGVuLFxuICB9LFxuICBlbmNyeXB0LFxuICBkZWNyeXB0LFxufTtcblxuZXhwb3J0IHsgZ2V0Q29udmVyc2F0aW9uS2V5LCBlbmNyeXB0LCBkZWNyeXB0LCBjYWxjUGFkZGVkTGVuIH07XG4iLCAiLyoqXG4gKiBDaGFDaGEgc3RyZWFtIGNpcGhlciwgcmVsZWFzZWRcbiAqIGluIDIwMDguIERldmVsb3BlZCBhZnRlciBTYWxzYTIwLCBDaGFDaGEgYWltcyB0byBpbmNyZWFzZSBkaWZmdXNpb24gcGVyIHJvdW5kLlxuICogSXQgd2FzIHN0YW5kYXJkaXplZCBpbiBbUkZDIDg0MzldKGh0dHBzOi8vd3d3LnJmYy1lZGl0b3Iub3JnL3JmYy9yZmM4NDM5KSBhbmRcbiAqIGlzIG5vdyB1c2VkIGluIFRMUyAxLjMuXG4gKlxuICogW1hDaGFDaGEyMF0oaHR0cHM6Ly9kYXRhdHJhY2tlci5pZXRmLm9yZy9kb2MvaHRtbC9kcmFmdC1pcnRmLWNmcmcteGNoYWNoYSlcbiAqIGV4dGVuZGVkLW5vbmNlIHZhcmlhbnQgaXMgYWxzbyBwcm92aWRlZC4gU2ltaWxhciB0byBYU2Fsc2EsIGl0J3Mgc2FmZSB0byB1c2Ugd2l0aFxuICogcmFuZG9tbHktZ2VuZXJhdGVkIG5vbmNlcy5cbiAqXG4gKiBDaGVjayBvdXQgW1BERl0oaHR0cDovL2NyLnlwLnRvL2NoYWNoYS9jaGFjaGEtMjAwODAxMjgucGRmKSBhbmRcbiAqIFt3aWtpXShodHRwczovL2VuLndpa2lwZWRpYS5vcmcvd2lraS9TYWxzYTIwKSBhbmRcbiAqIFt3ZWJzaXRlXShodHRwczovL2NyLnlwLnRvL2NoYWNoYS5odG1sKS5cbiAqXG4gKiBAbW9kdWxlXG4gKi9cbmltcG9ydCB7IHR5cGUgWG9yUFJHLCBjcmVhdGVDaXBoZXIsIGNyZWF0ZVBSRywgcm90bCB9IGZyb20gJy4vX2FyeC50cyc7XG5pbXBvcnQgeyBwb2x5MTMwNSB9IGZyb20gJy4vX3BvbHkxMzA1LnRzJztcbmltcG9ydCB7XG4gIHR5cGUgQVJYQ2lwaGVyLFxuICB0eXBlIENpcGhlcldpdGhPdXRwdXQsXG4gIHR5cGUgWG9yU3RyZWFtLFxuICBhYnl0ZXMsXG4gIGNsZWFuLFxuICBlcXVhbEJ5dGVzLFxuICBnZXRPdXRwdXQsXG4gIHU2NExlbmd0aHMsXG4gIHdyYXBDaXBoZXIsXG59IGZyb20gJy4vdXRpbHMudHMnO1xuXG4vKipcbiAqIENoYUNoYSBjb3JlIGZ1bmN0aW9uLiBJdCBpcyBpbXBsZW1lbnRlZCB0d2ljZTpcbiAqIDEuIFNpbXBsZSBsb29wIChjaGFjaGFDb3JlX3NtYWxsLCBoY2hhY2hhX3NtYWxsKVxuICogMi4gVW5yb2xsZWQgbG9vcCAoY2hhY2hhQ29yZSwgaGNoYWNoYSkgLSA0eCBmYXN0ZXIsIGJ1dCBsYXJnZXIgJiBoYXJkZXIgdG8gcmVhZFxuICogVGhlIHNwZWNpZmljIGltcGxlbWVudGF0aW9uIGlzIHNlbGVjdGVkIGluIGBjcmVhdGVDaXBoZXJgIGJlbG93LlxuICovXG5cbi8qKiBxdWFydGVyLXJvdW5kICovXG4vLyBwcmV0dGllci1pZ25vcmVcbmZ1bmN0aW9uIGNoYWNoYVFSKHg6IFVpbnQzMkFycmF5LCBhOiBudW1iZXIsIGI6IG51bWJlciwgYzogbnVtYmVyLCBkOiBudW1iZXIpIHtcbiAgeFthXSA9ICh4W2FdICsgeFtiXSkgfCAwOyB4W2RdID0gcm90bCh4W2RdIF4geFthXSwgMTYpO1xuICB4W2NdID0gKHhbY10gKyB4W2RdKSB8IDA7IHhbYl0gPSByb3RsKHhbYl0gXiB4W2NdLCAxMik7XG4gIHhbYV0gPSAoeFthXSArIHhbYl0pIHwgMDsgeFtkXSA9IHJvdGwoeFtkXSBeIHhbYV0sIDgpO1xuICB4W2NdID0gKHhbY10gKyB4W2RdKSB8IDA7IHhbYl0gPSByb3RsKHhbYl0gXiB4W2NdLCA3KTtcbn1cblxuLyoqIHNpbmdsZSByb3VuZCAqL1xuZnVuY3Rpb24gY2hhY2hhUm91bmQoeDogVWludDMyQXJyYXksIHJvdW5kcyA9IDIwKSB7XG4gIGZvciAobGV0IHIgPSAwOyByIDwgcm91bmRzOyByICs9IDIpIHtcbiAgICBjaGFjaGFRUih4LCAwLCA0LCA4LCAxMik7XG4gICAgY2hhY2hhUVIoeCwgMSwgNSwgOSwgMTMpO1xuICAgIGNoYWNoYVFSKHgsIDIsIDYsIDEwLCAxNCk7XG4gICAgY2hhY2hhUVIoeCwgMywgNywgMTEsIDE1KTtcbiAgICBjaGFjaGFRUih4LCAwLCA1LCAxMCwgMTUpO1xuICAgIGNoYWNoYVFSKHgsIDEsIDYsIDExLCAxMik7XG4gICAgY2hhY2hhUVIoeCwgMiwgNywgOCwgMTMpO1xuICAgIGNoYWNoYVFSKHgsIDMsIDQsIDksIDE0KTtcbiAgfVxufVxuXG5jb25zdCBjdG1wID0gLyogQF9fUFVSRV9fICovIG5ldyBVaW50MzJBcnJheSgxNik7XG5cbi8qKiBTbWFsbCB2ZXJzaW9uIG9mIGNoYWNoYSB3aXRob3V0IGxvb3AgdW5yb2xsaW5nLiBVbnVzZWQsIHByb3ZpZGVkIGZvciBhdWRpdGFiaWxpdHkuICovXG4vLyBwcmV0dGllci1pZ25vcmVcbmZ1bmN0aW9uIGNoYWNoYShcbiAgczogVWludDMyQXJyYXksIGs6IFVpbnQzMkFycmF5LCBpOiBVaW50MzJBcnJheSwgb3V0OiBVaW50MzJBcnJheSxcbiAgaXNIQ2hhY2hhOiBib29sZWFuID0gdHJ1ZSwgcm91bmRzOiBudW1iZXIgPSAyMFxuKTogdm9pZCB7XG4gIC8vIENyZWF0ZSBpbml0aWFsIGFycmF5IHVzaW5nIGNvbW1vbiBwYXR0ZXJuXG4gIGNvbnN0IHkgPSBVaW50MzJBcnJheS5mcm9tKFtcbiAgICBzWzBdLCBzWzFdLCBzWzJdLCBzWzNdLCAvLyBcImV4cGFcIiAgIFwibmQgM1wiICBcIjItYnlcIiAgXCJ0ZSBrXCJcbiAgICBrWzBdLCBrWzFdLCBrWzJdLCBrWzNdLCAvLyBLZXkgICAgICBLZXkgICAgIEtleSAgICAgS2V5XG4gICAga1s0XSwga1s1XSwga1s2XSwga1s3XSwgLy8gS2V5ICAgICAgS2V5ICAgICBLZXkgICAgIEtleVxuICAgIGlbMF0sIGlbMV0sIGlbMl0sIGlbM10sIC8vIENvdW50ZXIgIENvdW50ZXIgTm9uY2UgICBOb25jZVxuICBdKTtcbiAgY29uc3QgeCA9IGN0bXA7XG4gIHguc2V0KHkpO1xuICBjaGFjaGFSb3VuZCh4LCByb3VuZHMpO1xuXG4gIC8vIGhjaGFjaGEgZXh0cmFjdHMgOCBzcGVjaWZpYyBieXRlcywgY2hhY2hhIGFkZHMgb3JpZyB0byByZXN1bHRcbiAgaWYgKGlzSENoYWNoYSkge1xuICAgIGNvbnN0IHhpbmRleGVzID0gWzAsIDEsIDIsIDMsIDEyLCAxMywgMTQsIDE1XTtcbiAgICBmb3IgKGxldCBpID0gMDsgaSA8IDg7IGkrKykgb3V0W2ldID0geFt4aW5kZXhlc1tpXV07XG4gIH0gZWxzZSB7XG4gICAgZm9yIChsZXQgaSA9IDA7IGkgPCAxNjsgaSsrKSBvdXRbaV0gPSAoeVtpXSArIHhbaV0pIHwgMDtcbiAgfVxufVxuXG4vKiogSWRlbnRpY2FsIHRvIGBjaGFjaGFDb3JlYC4gVW51c2VkLiAqL1xuLy8gQHRzLWlnbm9yZVxuY29uc3QgY2hhY2hhQ29yZV9zbWFsbDogdHlwZW9mIGNoYWNoYUNvcmUgPSAocywgaywgbiwgb3V0LCBjbnQsIHJvdW5kcykgPT5cbiAgY2hhY2hhKHMsIGssIFVpbnQzMkFycmF5LmZyb20oW25bMF0sIG5bMV0sIGNudCwgMF0pLCBvdXQsIGZhbHNlLCByb3VuZHMpO1xuLyoqIElkZW50aWNhbCB0byBgaGNoYWNoYWAuIFVudXNlZC4gKi9cbi8vIEB0cy1pZ25vcmVcbmNvbnN0IGhjaGFjaGFfc21hbGw6IHR5cGVvZiBoY2hhY2hhID0gY2hhY2hhO1xuXG4vKiogSWRlbnRpY2FsIHRvIGBjaGFjaGFDb3JlX3NtYWxsYC4gVW51c2VkLiAqL1xuLy8gcHJldHRpZXItaWdub3JlXG5mdW5jdGlvbiBjaGFjaGFDb3JlKFxuICBzOiBVaW50MzJBcnJheSwgazogVWludDMyQXJyYXksIG46IFVpbnQzMkFycmF5LCBvdXQ6IFVpbnQzMkFycmF5LCBjbnQ6IG51bWJlciwgcm91bmRzID0gMjBcbik6IHZvaWQge1xuICBsZXQgeTAwID0gc1swXSwgeTAxID0gc1sxXSwgeTAyID0gc1syXSwgeTAzID0gc1szXSwgLy8gXCJleHBhXCIgICBcIm5kIDNcIiAgXCIyLWJ5XCIgIFwidGUga1wiXG4gICAgICB5MDQgPSBrWzBdLCB5MDUgPSBrWzFdLCB5MDYgPSBrWzJdLCB5MDcgPSBrWzNdLCAvLyBLZXkgICAgICBLZXkgICAgIEtleSAgICAgS2V5XG4gICAgICB5MDggPSBrWzRdLCB5MDkgPSBrWzVdLCB5MTAgPSBrWzZdLCB5MTEgPSBrWzddLCAvLyBLZXkgICAgICBLZXkgICAgIEtleSAgICAgS2V5XG4gICAgICB5MTIgPSBjbnQsICB5MTMgPSBuWzBdLCB5MTQgPSBuWzFdLCB5MTUgPSBuWzJdOyAgLy8gQ291bnRlciAgQ291bnRlclx0Tm9uY2UgICBOb25jZVxuICAvLyBTYXZlIHN0YXRlIHRvIHRlbXBvcmFyeSB2YXJpYWJsZXNcbiAgbGV0IHgwMCA9IHkwMCwgeDAxID0geTAxLCB4MDIgPSB5MDIsIHgwMyA9IHkwMyxcbiAgICAgIHgwNCA9IHkwNCwgeDA1ID0geTA1LCB4MDYgPSB5MDYsIHgwNyA9IHkwNyxcbiAgICAgIHgwOCA9IHkwOCwgeDA5ID0geTA5LCB4MTAgPSB5MTAsIHgxMSA9IHkxMSxcbiAgICAgIHgxMiA9IHkxMiwgeDEzID0geTEzLCB4MTQgPSB5MTQsIHgxNSA9IHkxNTtcbiAgZm9yIChsZXQgciA9IDA7IHIgPCByb3VuZHM7IHIgKz0gMikge1xuICAgIHgwMCA9ICh4MDAgKyB4MDQpIHwgMDsgeDEyID0gcm90bCh4MTIgXiB4MDAsIDE2KTtcbiAgICB4MDggPSAoeDA4ICsgeDEyKSB8IDA7IHgwNCA9IHJvdGwoeDA0IF4geDA4LCAxMik7XG4gICAgeDAwID0gKHgwMCArIHgwNCkgfCAwOyB4MTIgPSByb3RsKHgxMiBeIHgwMCwgOCk7XG4gICAgeDA4ID0gKHgwOCArIHgxMikgfCAwOyB4MDQgPSByb3RsKHgwNCBeIHgwOCwgNyk7XG5cbiAgICB4MDEgPSAoeDAxICsgeDA1KSB8IDA7IHgxMyA9IHJvdGwoeDEzIF4geDAxLCAxNik7XG4gICAgeDA5ID0gKHgwOSArIHgxMykgfCAwOyB4MDUgPSByb3RsKHgwNSBeIHgwOSwgMTIpO1xuICAgIHgwMSA9ICh4MDEgKyB4MDUpIHwgMDsgeDEzID0gcm90bCh4MTMgXiB4MDEsIDgpO1xuICAgIHgwOSA9ICh4MDkgKyB4MTMpIHwgMDsgeDA1ID0gcm90bCh4MDUgXiB4MDksIDcpO1xuXG4gICAgeDAyID0gKHgwMiArIHgwNikgfCAwOyB4MTQgPSByb3RsKHgxNCBeIHgwMiwgMTYpO1xuICAgIHgxMCA9ICh4MTAgKyB4MTQpIHwgMDsgeDA2ID0gcm90bCh4MDYgXiB4MTAsIDEyKTtcbiAgICB4MDIgPSAoeDAyICsgeDA2KSB8IDA7IHgxNCA9IHJvdGwoeDE0IF4geDAyLCA4KTtcbiAgICB4MTAgPSAoeDEwICsgeDE0KSB8IDA7IHgwNiA9IHJvdGwoeDA2IF4geDEwLCA3KTtcblxuICAgIHgwMyA9ICh4MDMgKyB4MDcpIHwgMDsgeDE1ID0gcm90bCh4MTUgXiB4MDMsIDE2KTtcbiAgICB4MTEgPSAoeDExICsgeDE1KSB8IDA7IHgwNyA9IHJvdGwoeDA3IF4geDExLCAxMik7XG4gICAgeDAzID0gKHgwMyArIHgwNykgfCAwOyB4MTUgPSByb3RsKHgxNSBeIHgwMywgOClcbiAgICB4MTEgPSAoeDExICsgeDE1KSB8IDA7IHgwNyA9IHJvdGwoeDA3IF4geDExLCA3KTtcblxuICAgIHgwMCA9ICh4MDAgKyB4MDUpIHwgMDsgeDE1ID0gcm90bCh4MTUgXiB4MDAsIDE2KTtcbiAgICB4MTAgPSAoeDEwICsgeDE1KSB8IDA7IHgwNSA9IHJvdGwoeDA1IF4geDEwLCAxMik7XG4gICAgeDAwID0gKHgwMCArIHgwNSkgfCAwOyB4MTUgPSByb3RsKHgxNSBeIHgwMCwgOCk7XG4gICAgeDEwID0gKHgxMCArIHgxNSkgfCAwOyB4MDUgPSByb3RsKHgwNSBeIHgxMCwgNyk7XG5cbiAgICB4MDEgPSAoeDAxICsgeDA2KSB8IDA7IHgxMiA9IHJvdGwoeDEyIF4geDAxLCAxNik7XG4gICAgeDExID0gKHgxMSArIHgxMikgfCAwOyB4MDYgPSByb3RsKHgwNiBeIHgxMSwgMTIpO1xuICAgIHgwMSA9ICh4MDEgKyB4MDYpIHwgMDsgeDEyID0gcm90bCh4MTIgXiB4MDEsIDgpO1xuICAgIHgxMSA9ICh4MTEgKyB4MTIpIHwgMDsgeDA2ID0gcm90bCh4MDYgXiB4MTEsIDcpO1xuXG4gICAgeDAyID0gKHgwMiArIHgwNykgfCAwOyB4MTMgPSByb3RsKHgxMyBeIHgwMiwgMTYpO1xuICAgIHgwOCA9ICh4MDggKyB4MTMpIHwgMDsgeDA3ID0gcm90bCh4MDcgXiB4MDgsIDEyKTtcbiAgICB4MDIgPSAoeDAyICsgeDA3KSB8IDA7IHgxMyA9IHJvdGwoeDEzIF4geDAyLCA4KTtcbiAgICB4MDggPSAoeDA4ICsgeDEzKSB8IDA7IHgwNyA9IHJvdGwoeDA3IF4geDA4LCA3KTtcblxuICAgIHgwMyA9ICh4MDMgKyB4MDQpIHwgMDsgeDE0ID0gcm90bCh4MTQgXiB4MDMsIDE2KVxuICAgIHgwOSA9ICh4MDkgKyB4MTQpIHwgMDsgeDA0ID0gcm90bCh4MDQgXiB4MDksIDEyKTtcbiAgICB4MDMgPSAoeDAzICsgeDA0KSB8IDA7IHgxNCA9IHJvdGwoeDE0IF4geDAzLCA4KTtcbiAgICB4MDkgPSAoeDA5ICsgeDE0KSB8IDA7IHgwNCA9IHJvdGwoeDA0IF4geDA5LCA3KTtcbiAgfVxuICAvLyBXcml0ZSBvdXRwdXRcbiAgbGV0IG9pID0gMDtcbiAgb3V0W29pKytdID0gKHkwMCArIHgwMCkgfCAwOyBvdXRbb2krK10gPSAoeTAxICsgeDAxKSB8IDA7XG4gIG91dFtvaSsrXSA9ICh5MDIgKyB4MDIpIHwgMDsgb3V0W29pKytdID0gKHkwMyArIHgwMykgfCAwO1xuICBvdXRbb2krK10gPSAoeTA0ICsgeDA0KSB8IDA7IG91dFtvaSsrXSA9ICh5MDUgKyB4MDUpIHwgMDtcbiAgb3V0W29pKytdID0gKHkwNiArIHgwNikgfCAwOyBvdXRbb2krK10gPSAoeTA3ICsgeDA3KSB8IDA7XG4gIG91dFtvaSsrXSA9ICh5MDggKyB4MDgpIHwgMDsgb3V0W29pKytdID0gKHkwOSArIHgwOSkgfCAwO1xuICBvdXRbb2krK10gPSAoeTEwICsgeDEwKSB8IDA7IG91dFtvaSsrXSA9ICh5MTEgKyB4MTEpIHwgMDtcbiAgb3V0W29pKytdID0gKHkxMiArIHgxMikgfCAwOyBvdXRbb2krK10gPSAoeTEzICsgeDEzKSB8IDA7XG4gIG91dFtvaSsrXSA9ICh5MTQgKyB4MTQpIHwgMDsgb3V0W29pKytdID0gKHkxNSArIHgxNSkgfCAwO1xufVxuLyoqXG4gKiBoY2hhY2hhIGhhc2hlcyBrZXkgYW5kIG5vbmNlIGludG8ga2V5JyBhbmQgbm9uY2UnIGZvciB4Y2hhY2hhMjAuXG4gKiBJZGVudGljYWwgdG8gYGhjaGFjaGFfc21hbGxgLlxuICogTmVlZCB0byBmaW5kIGEgd2F5IHRvIG1lcmdlIGl0IHdpdGggYGNoYWNoYUNvcmVgIHdpdGhvdXQgMjUlIHBlcmZvcm1hbmNlIGhpdC5cbiAqL1xuLy8gcHJldHRpZXItaWdub3JlXG5leHBvcnQgZnVuY3Rpb24gaGNoYWNoYShcbiAgczogVWludDMyQXJyYXksIGs6IFVpbnQzMkFycmF5LCBpOiBVaW50MzJBcnJheSwgb3V0OiBVaW50MzJBcnJheVxuKTogdm9pZCB7XG4gIGxldCB4MDAgPSBzWzBdLCB4MDEgPSBzWzFdLCB4MDIgPSBzWzJdLCB4MDMgPSBzWzNdLFxuICAgICAgeDA0ID0ga1swXSwgeDA1ID0ga1sxXSwgeDA2ID0ga1syXSwgeDA3ID0ga1szXSxcbiAgICAgIHgwOCA9IGtbNF0sIHgwOSA9IGtbNV0sIHgxMCA9IGtbNl0sIHgxMSA9IGtbN10sXG4gICAgICB4MTIgPSBpWzBdLCB4MTMgPSBpWzFdLCB4MTQgPSBpWzJdLCB4MTUgPSBpWzNdO1xuICBmb3IgKGxldCByID0gMDsgciA8IDIwOyByICs9IDIpIHtcbiAgICB4MDAgPSAoeDAwICsgeDA0KSB8IDA7IHgxMiA9IHJvdGwoeDEyIF4geDAwLCAxNik7XG4gICAgeDA4ID0gKHgwOCArIHgxMikgfCAwOyB4MDQgPSByb3RsKHgwNCBeIHgwOCwgMTIpO1xuICAgIHgwMCA9ICh4MDAgKyB4MDQpIHwgMDsgeDEyID0gcm90bCh4MTIgXiB4MDAsIDgpO1xuICAgIHgwOCA9ICh4MDggKyB4MTIpIHwgMDsgeDA0ID0gcm90bCh4MDQgXiB4MDgsIDcpO1xuXG4gICAgeDAxID0gKHgwMSArIHgwNSkgfCAwOyB4MTMgPSByb3RsKHgxMyBeIHgwMSwgMTYpO1xuICAgIHgwOSA9ICh4MDkgKyB4MTMpIHwgMDsgeDA1ID0gcm90bCh4MDUgXiB4MDksIDEyKTtcbiAgICB4MDEgPSAoeDAxICsgeDA1KSB8IDA7IHgxMyA9IHJvdGwoeDEzIF4geDAxLCA4KTtcbiAgICB4MDkgPSAoeDA5ICsgeDEzKSB8IDA7IHgwNSA9IHJvdGwoeDA1IF4geDA5LCA3KTtcblxuICAgIHgwMiA9ICh4MDIgKyB4MDYpIHwgMDsgeDE0ID0gcm90bCh4MTQgXiB4MDIsIDE2KTtcbiAgICB4MTAgPSAoeDEwICsgeDE0KSB8IDA7IHgwNiA9IHJvdGwoeDA2IF4geDEwLCAxMik7XG4gICAgeDAyID0gKHgwMiArIHgwNikgfCAwOyB4MTQgPSByb3RsKHgxNCBeIHgwMiwgOCk7XG4gICAgeDEwID0gKHgxMCArIHgxNCkgfCAwOyB4MDYgPSByb3RsKHgwNiBeIHgxMCwgNyk7XG5cbiAgICB4MDMgPSAoeDAzICsgeDA3KSB8IDA7IHgxNSA9IHJvdGwoeDE1IF4geDAzLCAxNik7XG4gICAgeDExID0gKHgxMSArIHgxNSkgfCAwOyB4MDcgPSByb3RsKHgwNyBeIHgxMSwgMTIpO1xuICAgIHgwMyA9ICh4MDMgKyB4MDcpIHwgMDsgeDE1ID0gcm90bCh4MTUgXiB4MDMsIDgpXG4gICAgeDExID0gKHgxMSArIHgxNSkgfCAwOyB4MDcgPSByb3RsKHgwNyBeIHgxMSwgNyk7XG5cbiAgICB4MDAgPSAoeDAwICsgeDA1KSB8IDA7IHgxNSA9IHJvdGwoeDE1IF4geDAwLCAxNik7XG4gICAgeDEwID0gKHgxMCArIHgxNSkgfCAwOyB4MDUgPSByb3RsKHgwNSBeIHgxMCwgMTIpO1xuICAgIHgwMCA9ICh4MDAgKyB4MDUpIHwgMDsgeDE1ID0gcm90bCh4MTUgXiB4MDAsIDgpO1xuICAgIHgxMCA9ICh4MTAgKyB4MTUpIHwgMDsgeDA1ID0gcm90bCh4MDUgXiB4MTAsIDcpO1xuXG4gICAgeDAxID0gKHgwMSArIHgwNikgfCAwOyB4MTIgPSByb3RsKHgxMiBeIHgwMSwgMTYpO1xuICAgIHgxMSA9ICh4MTEgKyB4MTIpIHwgMDsgeDA2ID0gcm90bCh4MDYgXiB4MTEsIDEyKTtcbiAgICB4MDEgPSAoeDAxICsgeDA2KSB8IDA7IHgxMiA9IHJvdGwoeDEyIF4geDAxLCA4KTtcbiAgICB4MTEgPSAoeDExICsgeDEyKSB8IDA7IHgwNiA9IHJvdGwoeDA2IF4geDExLCA3KTtcblxuICAgIHgwMiA9ICh4MDIgKyB4MDcpIHwgMDsgeDEzID0gcm90bCh4MTMgXiB4MDIsIDE2KTtcbiAgICB4MDggPSAoeDA4ICsgeDEzKSB8IDA7IHgwNyA9IHJvdGwoeDA3IF4geDA4LCAxMik7XG4gICAgeDAyID0gKHgwMiArIHgwNykgfCAwOyB4MTMgPSByb3RsKHgxMyBeIHgwMiwgOCk7XG4gICAgeDA4ID0gKHgwOCArIHgxMykgfCAwOyB4MDcgPSByb3RsKHgwNyBeIHgwOCwgNyk7XG5cbiAgICB4MDMgPSAoeDAzICsgeDA0KSB8IDA7IHgxNCA9IHJvdGwoeDE0IF4geDAzLCAxNilcbiAgICB4MDkgPSAoeDA5ICsgeDE0KSB8IDA7IHgwNCA9IHJvdGwoeDA0IF4geDA5LCAxMik7XG4gICAgeDAzID0gKHgwMyArIHgwNCkgfCAwOyB4MTQgPSByb3RsKHgxNCBeIHgwMywgOCk7XG4gICAgeDA5ID0gKHgwOSArIHgxNCkgfCAwOyB4MDQgPSByb3RsKHgwNCBeIHgwOSwgNyk7XG4gIH1cbiAgbGV0IG9pID0gMDtcbiAgb3V0W29pKytdID0geDAwOyBvdXRbb2krK10gPSB4MDE7XG4gIG91dFtvaSsrXSA9IHgwMjsgb3V0W29pKytdID0geDAzO1xuICBvdXRbb2krK10gPSB4MTI7IG91dFtvaSsrXSA9IHgxMztcbiAgb3V0W29pKytdID0geDE0OyBvdXRbb2krK10gPSB4MTU7XG59XG5cbi8qKiBPcmlnaW5hbCwgbm9uLVJGQyBjaGFjaGEyMCBmcm9tIERKQi4gOC1ieXRlIG5vbmNlLCA4LWJ5dGUgY291bnRlci4gKi9cbmV4cG9ydCBjb25zdCBjaGFjaGEyMG9yaWc6IFhvclN0cmVhbSA9IC8qIEBfX1BVUkVfXyAqLyBjcmVhdGVDaXBoZXIoY2hhY2hhQ29yZSwge1xuICBjb3VudGVyUmlnaHQ6IGZhbHNlLFxuICBjb3VudGVyTGVuZ3RoOiA4LFxuICBhbGxvd1Nob3J0S2V5czogdHJ1ZSxcbn0pO1xuLyoqXG4gKiBDaGFDaGEgc3RyZWFtIGNpcGhlci4gQ29uZm9ybXMgdG8gUkZDIDg0MzkgKElFVEYsIFRMUykuIDEyLWJ5dGUgbm9uY2UsIDQtYnl0ZSBjb3VudGVyLlxuICogV2l0aCBzbWFsbGVyIG5vbmNlLCBpdCdzIG5vdCBzYWZlIHRvIG1ha2UgaXQgcmFuZG9tIChDU1BSTkcpLCBkdWUgdG8gY29sbGlzaW9uIGNoYW5jZS5cbiAqL1xuZXhwb3J0IGNvbnN0IGNoYWNoYTIwOiBYb3JTdHJlYW0gPSAvKiBAX19QVVJFX18gKi8gY3JlYXRlQ2lwaGVyKGNoYWNoYUNvcmUsIHtcbiAgY291bnRlclJpZ2h0OiBmYWxzZSxcbiAgY291bnRlckxlbmd0aDogNCxcbiAgYWxsb3dTaG9ydEtleXM6IGZhbHNlLFxufSk7XG5cbi8qKlxuICogWENoYUNoYSBlWHRlbmRlZC1ub25jZSBDaGFDaGEuIFdpdGggMjQtYnl0ZSBub25jZSwgaXQncyBzYWZlIHRvIG1ha2UgaXQgcmFuZG9tIChDU1BSTkcpLlxuICogU2VlIFtJUlRGIGRyYWZ0XShodHRwczovL2RhdGF0cmFja2VyLmlldGYub3JnL2RvYy9odG1sL2RyYWZ0LWlydGYtY2ZyZy14Y2hhY2hhKS5cbiAqL1xuZXhwb3J0IGNvbnN0IHhjaGFjaGEyMDogWG9yU3RyZWFtID0gLyogQF9fUFVSRV9fICovIGNyZWF0ZUNpcGhlcihjaGFjaGFDb3JlLCB7XG4gIGNvdW50ZXJSaWdodDogZmFsc2UsXG4gIGNvdW50ZXJMZW5ndGg6IDgsXG4gIGV4dGVuZE5vbmNlRm46IGhjaGFjaGEsXG4gIGFsbG93U2hvcnRLZXlzOiBmYWxzZSxcbn0pO1xuXG4vKiogUmVkdWNlZCA4LXJvdW5kIGNoYWNoYSwgZGVzY3JpYmVkIGluIG9yaWdpbmFsIHBhcGVyLiAqL1xuZXhwb3J0IGNvbnN0IGNoYWNoYTg6IFhvclN0cmVhbSA9IC8qIEBfX1BVUkVfXyAqLyBjcmVhdGVDaXBoZXIoY2hhY2hhQ29yZSwge1xuICBjb3VudGVyUmlnaHQ6IGZhbHNlLFxuICBjb3VudGVyTGVuZ3RoOiA0LFxuICByb3VuZHM6IDgsXG59KTtcblxuLyoqIFJlZHVjZWQgMTItcm91bmQgY2hhY2hhLCBkZXNjcmliZWQgaW4gb3JpZ2luYWwgcGFwZXIuICovXG5leHBvcnQgY29uc3QgY2hhY2hhMTI6IFhvclN0cmVhbSA9IC8qIEBfX1BVUkVfXyAqLyBjcmVhdGVDaXBoZXIoY2hhY2hhQ29yZSwge1xuICBjb3VudGVyUmlnaHQ6IGZhbHNlLFxuICBjb3VudGVyTGVuZ3RoOiA0LFxuICByb3VuZHM6IDEyLFxufSk7XG5cbmNvbnN0IFpFUk9TMTYgPSAvKiBAX19QVVJFX18gKi8gbmV3IFVpbnQ4QXJyYXkoMTYpO1xuLy8gUGFkIHRvIGRpZ2VzdCBzaXplIHdpdGggemVyb3NcbmNvbnN0IHVwZGF0ZVBhZGRlZCA9IChoOiBSZXR1cm5UeXBlPHR5cGVvZiBwb2x5MTMwNS5jcmVhdGU+LCBtc2c6IFVpbnQ4QXJyYXkpID0+IHtcbiAgaC51cGRhdGUobXNnKTtcbiAgY29uc3QgbGVmdG92ZXIgPSBtc2cubGVuZ3RoICUgMTY7XG4gIGlmIChsZWZ0b3ZlcikgaC51cGRhdGUoWkVST1MxNi5zdWJhcnJheShsZWZ0b3ZlcikpO1xufTtcblxuY29uc3QgWkVST1MzMiA9IC8qIEBfX1BVUkVfXyAqLyBuZXcgVWludDhBcnJheSgzMik7XG5mdW5jdGlvbiBjb21wdXRlVGFnKFxuICBmbjogWG9yU3RyZWFtLFxuICBrZXk6IFVpbnQ4QXJyYXksXG4gIG5vbmNlOiBVaW50OEFycmF5LFxuICBjaXBoZXJ0ZXh0OiBVaW50OEFycmF5LFxuICBBQUQ/OiBVaW50OEFycmF5XG4pOiBVaW50OEFycmF5IHtcbiAgaWYgKEFBRCAhPT0gdW5kZWZpbmVkKSBhYnl0ZXMoQUFELCB1bmRlZmluZWQsICdBQUQnKTtcbiAgY29uc3QgYXV0aEtleSA9IGZuKGtleSwgbm9uY2UsIFpFUk9TMzIpO1xuICBjb25zdCBsZW5ndGhzID0gdTY0TGVuZ3RocyhjaXBoZXJ0ZXh0Lmxlbmd0aCwgQUFEID8gQUFELmxlbmd0aCA6IDAsIHRydWUpO1xuXG4gIC8vIE1ldGhvZHMgYmVsb3cgY2FuIGJlIHJlcGxhY2VkIHdpdGhcbiAgLy8gcmV0dXJuIHBvbHkxMzA1X2NvbXB1dGVUYWdfc21hbGwoYXV0aEtleSwgbGVuZ3RocywgY2lwaGVydGV4dCwgQUFEKVxuICBjb25zdCBoID0gcG9seTEzMDUuY3JlYXRlKGF1dGhLZXkpO1xuICBpZiAoQUFEKSB1cGRhdGVQYWRkZWQoaCwgQUFEKTtcbiAgdXBkYXRlUGFkZGVkKGgsIGNpcGhlcnRleHQpO1xuICBoLnVwZGF0ZShsZW5ndGhzKTtcbiAgY29uc3QgcmVzID0gaC5kaWdlc3QoKTtcbiAgY2xlYW4oYXV0aEtleSwgbGVuZ3Rocyk7XG4gIHJldHVybiByZXM7XG59XG5cbi8qKlxuICogQUVBRCBhbGdvcml0aG0gZnJvbSBSRkMgODQzOS5cbiAqIFNhbHNhMjAgYW5kIGNoYWNoYSAoUkZDIDg0MzkpIHVzZSBwb2x5MTMwNSBkaWZmZXJlbnRseS5cbiAqIFdlIGNvdWxkIGhhdmUgY29tcG9zZWQgdGhlbSwgYnV0IGl0J3MgaGFyZCBiZWNhdXNlIG9mIGF1dGhLZXk6XG4gKiBJbiBzYWxzYTIwLCBhdXRoS2V5IGNoYW5nZXMgcG9zaXRpb24gaW4gc2Fsc2Egc3RyZWFtLlxuICogSW4gY2hhY2hhLCBhdXRoS2V5IGNhbid0IGJlIGNvbXB1dGVkIGluc2lkZSBjb21wdXRlVGFnLCBpdCBtb2RpZmllcyB0aGUgY291bnRlci5cbiAqL1xuZXhwb3J0IGNvbnN0IF9wb2x5MTMwNV9hZWFkID1cbiAgKHhvclN0cmVhbTogWG9yU3RyZWFtKSA9PlxuICAoa2V5OiBVaW50OEFycmF5LCBub25jZTogVWludDhBcnJheSwgQUFEPzogVWludDhBcnJheSk6IENpcGhlcldpdGhPdXRwdXQgPT4ge1xuICAgIGNvbnN0IHRhZ0xlbmd0aCA9IDE2O1xuICAgIHJldHVybiB7XG4gICAgICBlbmNyeXB0KHBsYWludGV4dDogVWludDhBcnJheSwgb3V0cHV0PzogVWludDhBcnJheSkge1xuICAgICAgICBjb25zdCBwbGVuZ3RoID0gcGxhaW50ZXh0Lmxlbmd0aDtcbiAgICAgICAgb3V0cHV0ID0gZ2V0T3V0cHV0KHBsZW5ndGggKyB0YWdMZW5ndGgsIG91dHB1dCwgZmFsc2UpO1xuICAgICAgICBvdXRwdXQuc2V0KHBsYWludGV4dCk7XG4gICAgICAgIGNvbnN0IG9QbGFpbiA9IG91dHB1dC5zdWJhcnJheSgwLCAtdGFnTGVuZ3RoKTtcbiAgICAgICAgLy8gQWN0dWFsIGVuY3J5cHRpb25cbiAgICAgICAgeG9yU3RyZWFtKGtleSwgbm9uY2UsIG9QbGFpbiwgb1BsYWluLCAxKTtcbiAgICAgICAgY29uc3QgdGFnID0gY29tcHV0ZVRhZyh4b3JTdHJlYW0sIGtleSwgbm9uY2UsIG9QbGFpbiwgQUFEKTtcbiAgICAgICAgb3V0cHV0LnNldCh0YWcsIHBsZW5ndGgpOyAvLyBhcHBlbmQgdGFnXG4gICAgICAgIGNsZWFuKHRhZyk7XG4gICAgICAgIHJldHVybiBvdXRwdXQ7XG4gICAgICB9LFxuICAgICAgZGVjcnlwdChjaXBoZXJ0ZXh0OiBVaW50OEFycmF5LCBvdXRwdXQ/OiBVaW50OEFycmF5KSB7XG4gICAgICAgIG91dHB1dCA9IGdldE91dHB1dChjaXBoZXJ0ZXh0Lmxlbmd0aCAtIHRhZ0xlbmd0aCwgb3V0cHV0LCBmYWxzZSk7XG4gICAgICAgIGNvbnN0IGRhdGEgPSBjaXBoZXJ0ZXh0LnN1YmFycmF5KDAsIC10YWdMZW5ndGgpO1xuICAgICAgICBjb25zdCBwYXNzZWRUYWcgPSBjaXBoZXJ0ZXh0LnN1YmFycmF5KC10YWdMZW5ndGgpO1xuICAgICAgICBjb25zdCB0YWcgPSBjb21wdXRlVGFnKHhvclN0cmVhbSwga2V5LCBub25jZSwgZGF0YSwgQUFEKTtcbiAgICAgICAgaWYgKCFlcXVhbEJ5dGVzKHBhc3NlZFRhZywgdGFnKSkgdGhyb3cgbmV3IEVycm9yKCdpbnZhbGlkIHRhZycpO1xuICAgICAgICBvdXRwdXQuc2V0KGNpcGhlcnRleHQuc3ViYXJyYXkoMCwgLXRhZ0xlbmd0aCkpO1xuICAgICAgICAvLyBBY3R1YWwgZGVjcnlwdGlvblxuICAgICAgICB4b3JTdHJlYW0oa2V5LCBub25jZSwgb3V0cHV0LCBvdXRwdXQsIDEpOyAvLyBzdGFydCBzdHJlYW0gd2l0aCBpPTFcbiAgICAgICAgY2xlYW4odGFnKTtcbiAgICAgICAgcmV0dXJuIG91dHB1dDtcbiAgICAgIH0sXG4gICAgfTtcbiAgfTtcblxuLyoqXG4gKiBDaGFDaGEyMC1Qb2x5MTMwNSBmcm9tIFJGQyA4NDM5LlxuICpcbiAqIFVuc2FmZSB0byB1c2UgcmFuZG9tIG5vbmNlcyB1bmRlciB0aGUgc2FtZSBrZXksIGR1ZSB0byBjb2xsaXNpb24gY2hhbmNlLlxuICogUHJlZmVyIFhDaGFDaGEgaW5zdGVhZC5cbiAqL1xuZXhwb3J0IGNvbnN0IGNoYWNoYTIwcG9seTEzMDU6IEFSWENpcGhlciA9IC8qIEBfX1BVUkVfXyAqLyB3cmFwQ2lwaGVyKFxuICB7IGJsb2NrU2l6ZTogNjQsIG5vbmNlTGVuZ3RoOiAxMiwgdGFnTGVuZ3RoOiAxNiB9LFxuICBfcG9seTEzMDVfYWVhZChjaGFjaGEyMClcbik7XG4vKipcbiAqIFhDaGFDaGEyMC1Qb2x5MTMwNSBleHRlbmRlZC1ub25jZSBjaGFjaGEuXG4gKlxuICogQ2FuIGJlIHNhZmVseSB1c2VkIHdpdGggcmFuZG9tIG5vbmNlcyAoQ1NQUk5HKS5cbiAqIFNlZSBbSVJURiBkcmFmdF0oaHR0cHM6Ly9kYXRhdHJhY2tlci5pZXRmLm9yZy9kb2MvaHRtbC9kcmFmdC1pcnRmLWNmcmcteGNoYWNoYSkuXG4gKi9cbmV4cG9ydCBjb25zdCB4Y2hhY2hhMjBwb2x5MTMwNTogQVJYQ2lwaGVyID0gLyogQF9fUFVSRV9fICovIHdyYXBDaXBoZXIoXG4gIHsgYmxvY2tTaXplOiA2NCwgbm9uY2VMZW5ndGg6IDI0LCB0YWdMZW5ndGg6IDE2IH0sXG4gIF9wb2x5MTMwNV9hZWFkKHhjaGFjaGEyMClcbik7XG5cbi8qKlxuICogQ2hhY2hhMjAgQ1NQUk5HIChjcnlwdG9ncmFwaGljYWxseSBzZWN1cmUgcHNldWRvcmFuZG9tIG51bWJlciBnZW5lcmF0b3IpLlxuICogSXQncyBiZXN0IHRvIGxpbWl0IHVzYWdlIHRvIG5vbi1wcm9kdWN0aW9uLCBub24tY3JpdGljYWwgY2FzZXM6IGZvciBleGFtcGxlLCB0ZXN0LW9ubHkuXG4gKiBDb21wYXRpYmxlIHdpdGggbGlidG9tY3J5cHQuIEl0IGRvZXMgbm90IGhhdmUgYSBzcGVjaWZpY2F0aW9uLCBzbyB1bmNsZWFyIGhvdyBzZWN1cmUgaXQgaXMuXG4gKi9cbmV4cG9ydCBjb25zdCBybmdDaGFjaGEyMDogWG9yUFJHID0gLyogQF9fUFVSRV9fICovIGNyZWF0ZVBSRyhjaGFjaGEyMG9yaWcsIDY0LCAzMiwgOCk7XG4vKipcbiAqIENoYWNoYTIwLzggQ1NQUk5HIChjcnlwdG9ncmFwaGljYWxseSBzZWN1cmUgcHNldWRvcmFuZG9tIG51bWJlciBnZW5lcmF0b3IpLlxuICogSXQncyBiZXN0IHRvIGxpbWl0IHVzYWdlIHRvIG5vbi1wcm9kdWN0aW9uLCBub24tY3JpdGljYWwgY2FzZXM6IGZvciBleGFtcGxlLCB0ZXN0LW9ubHkuXG4gKiBGYXN0ZXIgdGhhbiBgcm5nQ2hhY2hhMjBgLlxuICovXG5leHBvcnQgY29uc3Qgcm5nQ2hhY2hhODogWG9yUFJHID0gLyogQF9fUFVSRV9fICovIGNyZWF0ZVBSRyhjaGFjaGE4LCA2NCwgMzIsIDEyKTtcbiIsICIvKipcbiAqIEJhc2ljIHV0aWxzIGZvciBBUlggKGFkZC1yb3RhdGUteG9yKSBzYWxzYSBhbmQgY2hhY2hhIGNpcGhlcnMuXG5cblJGQzg0MzkgcmVxdWlyZXMgbXVsdGktc3RlcCBjaXBoZXIgc3RyZWFtLCB3aGVyZVxuYXV0aEtleSBzdGFydHMgd2l0aCBjb3VudGVyOiAwLCBhY3R1YWwgbXNnIHdpdGggY291bnRlcjogMS5cblxuRm9yIHRoaXMsIHdlIG5lZWQgYSB3YXkgdG8gcmUtdXNlIG5vbmNlIC8gY291bnRlcjpcblxuICAgIGNvbnN0IGNvdW50ZXIgPSBuZXcgVWludDhBcnJheSg0KTtcbiAgICBjaGFjaGEoLi4uLCBjb3VudGVyLCAuLi4pOyAvLyBjb3VudGVyIGlzIG5vdyAxXG4gICAgY2hhY2hhKC4uLiwgY291bnRlciwgLi4uKTsgLy8gY291bnRlciBpcyBub3cgMlxuXG5UaGlzIGlzIGNvbXBsaWNhdGVkOlxuXG4tIDMyLWJpdCBjb3VudGVycyBhcmUgZW5vdWdoLCBubyBuZWVkIGZvciA2NC1iaXQ6IG1heCBBcnJheUJ1ZmZlciBzaXplIGluIEpTIGlzIDRHQlxuLSBPcmlnaW5hbCBwYXBlcnMgZG9uJ3QgYWxsb3cgbXV0YXRpbmcgY291bnRlcnNcbi0gQ291bnRlciBvdmVyZmxvdyBpcyB1bmRlZmluZWQgW14xXVxuLSBJZGVhIEE6IGFsbG93IHByb3ZpZGluZyAobm9uY2UgfCBjb3VudGVyKSBpbnN0ZWFkIG9mIGp1c3Qgbm9uY2UsIHJlLXVzZSBpdFxuLSBDYXZlYXQ6IENhbm5vdCBiZSByZS11c2VkIHRocm91Z2ggYWxsIGNhc2VzOlxuLSAqIGNoYWNoYSBoYXMgKGNvdW50ZXIgfCBub25jZSlcbi0gKiB4Y2hhY2hhIGhhcyAobm9uY2UxNiB8IGNvdW50ZXIgfCBub25jZTE2KVxuLSBJZGVhIEI6IHNlcGFyYXRlIG5vbmNlIC8gY291bnRlciBhbmQgcHJvdmlkZSBzZXBhcmF0ZSBBUEkgZm9yIGNvdW50ZXIgcmUtdXNlXG4tIENhdmVhdDogdGhlcmUgYXJlIGRpZmZlcmVudCBjb3VudGVyIHNpemVzIGRlcGVuZGluZyBvbiBhbiBhbGdvcml0aG0uXG4tIHNhbHNhICYgY2hhY2hhIGFsc28gZGlmZmVyIGluIHN0cnVjdHVyZXMgb2Yga2V5ICYgc2lnbWE6XG4gIHNhbHNhMjA6ICAgICAgc1swXSB8IGsoNCkgfCBzWzFdIHwgbm9uY2UoMikgfCBjbnQoMikgfCBzWzJdIHwgayg0KSB8IHNbM11cbiAgY2hhY2hhOiAgICAgICBzKDQpIHwgayg4KSB8IGNudCgxKSB8IG5vbmNlKDMpXG4gIGNoYWNoYTIwb3JpZzogcyg0KSB8IGsoOCkgfCBjbnQoMikgfCBub25jZSgyKVxuLSBJZGVhIEM6IGhlbHBlciBtZXRob2Qgc3VjaCBhcyBgc2V0U2Fsc2FTdGF0ZShrZXksIG5vbmNlLCBzaWdtYSwgZGF0YSlgXG4tIENhdmVhdDogd2UgY2FuJ3QgcmUtdXNlIGNvdW50ZXIgYXJyYXlcblxueGNoYWNoYSBbXjJdIHVzZXMgdGhlIHN1YmtleSBhbmQgcmVtYWluaW5nIDggYnl0ZSBub25jZSB3aXRoIENoYUNoYTIwIGFzIG5vcm1hbFxuKHByZWZpeGVkIGJ5IDQgTlVMIGJ5dGVzLCBzaW5jZSBbUkZDODQzOV0gc3BlY2lmaWVzIGEgMTItYnl0ZSBub25jZSkuXG5cblteMV06IGh0dHBzOi8vbWFpbGFyY2hpdmUuaWV0Zi5vcmcvYXJjaC9tc2cvY2ZyZy9nc09uVEp6Y2JnRzZPcUQ4U2MwR081YVJfdFUvXG5bXjJdOiBodHRwczovL2RhdGF0cmFja2VyLmlldGYub3JnL2RvYy9odG1sL2RyYWZ0LWlydGYtY2ZyZy14Y2hhY2hhI2FwcGVuZGl4LUEuMlxuXG4gKiBAbW9kdWxlXG4gKi9cbmltcG9ydCB7XG4gIHR5cGUgUFJHLFxuICB0eXBlIFhvclN0cmVhbSxcbiAgYWJvb2wsXG4gIGFieXRlcyxcbiAgYW51bWJlcixcbiAgY2hlY2tPcHRzLFxuICBjbGVhbixcbiAgY29weUJ5dGVzLFxuICByYW5kb21CeXRlcyxcbiAgdTMyLFxufSBmcm9tICcuL3V0aWxzLnRzJztcblxuLy8gUmVwbGFjZXMgYFRleHRFbmNvZGVyYCwgd2hpY2ggaXMgbm90IGF2YWlsYWJsZSBpbiBhbGwgZW52aXJvbm1lbnRzXG5jb25zdCBlbmNvZGVTdHIgPSAoc3RyOiBzdHJpbmcpID0+IFVpbnQ4QXJyYXkuZnJvbShzdHIuc3BsaXQoJycpLCAoYykgPT4gYy5jaGFyQ29kZUF0KDApKTtcbmNvbnN0IHNpZ21hMTYgPSBlbmNvZGVTdHIoJ2V4cGFuZCAxNi1ieXRlIGsnKTtcbmNvbnN0IHNpZ21hMzIgPSBlbmNvZGVTdHIoJ2V4cGFuZCAzMi1ieXRlIGsnKTtcbmNvbnN0IHNpZ21hMTZfMzIgPSB1MzIoc2lnbWExNik7XG5jb25zdCBzaWdtYTMyXzMyID0gdTMyKHNpZ21hMzIpO1xuXG4vKiogUm90YXRlIGxlZnQuICovXG5leHBvcnQgZnVuY3Rpb24gcm90bChhOiBudW1iZXIsIGI6IG51bWJlcik6IG51bWJlciB7XG4gIHJldHVybiAoYSA8PCBiKSB8IChhID4+PiAoMzIgLSBiKSk7XG59XG5cbi8qKiBDaXBoZXJzIG11c3QgdXNlIHUzMiBmb3IgZWZmaWNpZW5jeS4gKi9cbmV4cG9ydCB0eXBlIENpcGhlckNvcmVGbiA9IChcbiAgc2lnbWE6IFVpbnQzMkFycmF5LFxuICBrZXk6IFVpbnQzMkFycmF5LFxuICBub25jZTogVWludDMyQXJyYXksXG4gIG91dHB1dDogVWludDMyQXJyYXksXG4gIGNvdW50ZXI6IG51bWJlcixcbiAgcm91bmRzPzogbnVtYmVyXG4pID0+IHZvaWQ7XG5cbi8qKiBNZXRob2Qgd2hpY2ggZXh0ZW5kcyBrZXkgKyBzaG9ydCBub25jZSBpbnRvIGxhcmdlciBub25jZSAvIGRpZmYga2V5LiAqL1xuZXhwb3J0IHR5cGUgRXh0ZW5kTm9uY2VGbiA9IChcbiAgc2lnbWE6IFVpbnQzMkFycmF5LFxuICBrZXk6IFVpbnQzMkFycmF5LFxuICBpbnB1dDogVWludDMyQXJyYXksXG4gIG91dHB1dDogVWludDMyQXJyYXlcbikgPT4gdm9pZDtcblxuLyoqIEFSWCBjaXBoZXIgb3B0aW9ucy5cbiAqICogYGFsbG93U2hvcnRLZXlzYCBmb3IgMTYtYnl0ZSBrZXlzXG4gKiAqIGBjb3VudGVyTGVuZ3RoYCBpbiBieXRlc1xuICogKiBgY291bnRlclJpZ2h0YDogcmlnaHQ6IGBub25jZXxjb3VudGVyYDsgbGVmdDogYGNvdW50ZXJ8bm9uY2VgXG4gKiAqL1xuZXhwb3J0IHR5cGUgQ2lwaGVyT3B0cyA9IHtcbiAgYWxsb3dTaG9ydEtleXM/OiBib29sZWFuOyAvLyBPcmlnaW5hbCBzYWxzYSAvIGNoYWNoYSBhbGxvdyAxNi1ieXRlIGtleXNcbiAgZXh0ZW5kTm9uY2VGbj86IEV4dGVuZE5vbmNlRm47XG4gIGNvdW50ZXJMZW5ndGg/OiBudW1iZXI7XG4gIGNvdW50ZXJSaWdodD86IGJvb2xlYW47XG4gIHJvdW5kcz86IG51bWJlcjtcbn07XG5cbi8vIElzIGJ5dGUgYXJyYXkgYWxpZ25lZCB0byA0IGJ5dGUgb2Zmc2V0ICh1MzIpP1xuZnVuY3Rpb24gaXNBbGlnbmVkMzIoYjogVWludDhBcnJheSkge1xuICByZXR1cm4gYi5ieXRlT2Zmc2V0ICUgNCA9PT0gMDtcbn1cblxuLy8gU2Fsc2EgYW5kIENoYWNoYSBibG9jayBsZW5ndGggaXMgYWx3YXlzIDUxMi1iaXRcbmNvbnN0IEJMT0NLX0xFTiA9IDY0O1xuY29uc3QgQkxPQ0tfTEVOMzIgPSAxNjtcblxuLy8gbmV3IFVpbnQzMkFycmF5KFsyKiozMl0pICAgLy8gPT4gVWludDMyQXJyYXkoMSkgWyAwIF1cbi8vIG5ldyBVaW50MzJBcnJheShbMioqMzItMV0pIC8vID0+IFVpbnQzMkFycmF5KDEpIFsgNDI5NDk2NzI5NSBdXG5jb25zdCBNQVhfQ09VTlRFUiA9IDIgKiogMzIgLSAxO1xuXG5jb25zdCBVMzJfRU1QVFkgPSBVaW50MzJBcnJheS5vZigpO1xuZnVuY3Rpb24gcnVuQ2lwaGVyKFxuICBjb3JlOiBDaXBoZXJDb3JlRm4sXG4gIHNpZ21hOiBVaW50MzJBcnJheSxcbiAga2V5OiBVaW50MzJBcnJheSxcbiAgbm9uY2U6IFVpbnQzMkFycmF5LFxuICBkYXRhOiBVaW50OEFycmF5LFxuICBvdXRwdXQ6IFVpbnQ4QXJyYXksXG4gIGNvdW50ZXI6IG51bWJlcixcbiAgcm91bmRzOiBudW1iZXJcbik6IHZvaWQge1xuICBjb25zdCBsZW4gPSBkYXRhLmxlbmd0aDtcbiAgY29uc3QgYmxvY2sgPSBuZXcgVWludDhBcnJheShCTE9DS19MRU4pO1xuICBjb25zdCBiMzIgPSB1MzIoYmxvY2spO1xuICAvLyBNYWtlIHN1cmUgdGhhdCBidWZmZXJzIGFsaWduZWQgdG8gNCBieXRlc1xuICBjb25zdCBpc0FsaWduZWQgPSBpc0FsaWduZWQzMihkYXRhKSAmJiBpc0FsaWduZWQzMihvdXRwdXQpO1xuICBjb25zdCBkMzIgPSBpc0FsaWduZWQgPyB1MzIoZGF0YSkgOiBVMzJfRU1QVFk7XG4gIGNvbnN0IG8zMiA9IGlzQWxpZ25lZCA/IHUzMihvdXRwdXQpIDogVTMyX0VNUFRZO1xuICBmb3IgKGxldCBwb3MgPSAwOyBwb3MgPCBsZW47IGNvdW50ZXIrKykge1xuICAgIGNvcmUoc2lnbWEsIGtleSwgbm9uY2UsIGIzMiwgY291bnRlciwgcm91bmRzKTtcbiAgICBpZiAoY291bnRlciA+PSBNQVhfQ09VTlRFUikgdGhyb3cgbmV3IEVycm9yKCdhcng6IGNvdW50ZXIgb3ZlcmZsb3cnKTtcbiAgICBjb25zdCB0YWtlID0gTWF0aC5taW4oQkxPQ0tfTEVOLCBsZW4gLSBwb3MpO1xuICAgIC8vIGFsaWduZWQgdG8gNCBieXRlc1xuICAgIGlmIChpc0FsaWduZWQgJiYgdGFrZSA9PT0gQkxPQ0tfTEVOKSB7XG4gICAgICBjb25zdCBwb3MzMiA9IHBvcyAvIDQ7XG4gICAgICBpZiAocG9zICUgNCAhPT0gMCkgdGhyb3cgbmV3IEVycm9yKCdhcng6IGludmFsaWQgYmxvY2sgcG9zaXRpb24nKTtcbiAgICAgIGZvciAobGV0IGogPSAwLCBwb3NqOiBudW1iZXI7IGogPCBCTE9DS19MRU4zMjsgaisrKSB7XG4gICAgICAgIHBvc2ogPSBwb3MzMiArIGo7XG4gICAgICAgIG8zMltwb3NqXSA9IGQzMltwb3NqXSBeIGIzMltqXTtcbiAgICAgIH1cbiAgICAgIHBvcyArPSBCTE9DS19MRU47XG4gICAgICBjb250aW51ZTtcbiAgICB9XG4gICAgZm9yIChsZXQgaiA9IDAsIHBvc2o7IGogPCB0YWtlOyBqKyspIHtcbiAgICAgIHBvc2ogPSBwb3MgKyBqO1xuICAgICAgb3V0cHV0W3Bvc2pdID0gZGF0YVtwb3NqXSBeIGJsb2NrW2pdO1xuICAgIH1cbiAgICBwb3MgKz0gdGFrZTtcbiAgfVxufVxuXG4vKiogQ3JlYXRlcyBBUlgtbGlrZSAoQ2hhQ2hhLCBTYWxzYSkgY2lwaGVyIHN0cmVhbSBmcm9tIGNvcmUgZnVuY3Rpb24uICovXG5leHBvcnQgZnVuY3Rpb24gY3JlYXRlQ2lwaGVyKGNvcmU6IENpcGhlckNvcmVGbiwgb3B0czogQ2lwaGVyT3B0cyk6IFhvclN0cmVhbSB7XG4gIGNvbnN0IHsgYWxsb3dTaG9ydEtleXMsIGV4dGVuZE5vbmNlRm4sIGNvdW50ZXJMZW5ndGgsIGNvdW50ZXJSaWdodCwgcm91bmRzIH0gPSBjaGVja09wdHMoXG4gICAgeyBhbGxvd1Nob3J0S2V5czogZmFsc2UsIGNvdW50ZXJMZW5ndGg6IDgsIGNvdW50ZXJSaWdodDogZmFsc2UsIHJvdW5kczogMjAgfSxcbiAgICBvcHRzXG4gICk7XG4gIGlmICh0eXBlb2YgY29yZSAhPT0gJ2Z1bmN0aW9uJykgdGhyb3cgbmV3IEVycm9yKCdjb3JlIG11c3QgYmUgYSBmdW5jdGlvbicpO1xuICBhbnVtYmVyKGNvdW50ZXJMZW5ndGgpO1xuICBhbnVtYmVyKHJvdW5kcyk7XG4gIGFib29sKGNvdW50ZXJSaWdodCk7XG4gIGFib29sKGFsbG93U2hvcnRLZXlzKTtcbiAgcmV0dXJuIChcbiAgICBrZXk6IFVpbnQ4QXJyYXksXG4gICAgbm9uY2U6IFVpbnQ4QXJyYXksXG4gICAgZGF0YTogVWludDhBcnJheSxcbiAgICBvdXRwdXQ/OiBVaW50OEFycmF5LFxuICAgIGNvdW50ZXIgPSAwXG4gICk6IFVpbnQ4QXJyYXkgPT4ge1xuICAgIGFieXRlcyhrZXksIHVuZGVmaW5lZCwgJ2tleScpO1xuICAgIGFieXRlcyhub25jZSwgdW5kZWZpbmVkLCAnbm9uY2UnKTtcbiAgICBhYnl0ZXMoZGF0YSwgdW5kZWZpbmVkLCAnZGF0YScpO1xuICAgIGNvbnN0IGxlbiA9IGRhdGEubGVuZ3RoO1xuICAgIGlmIChvdXRwdXQgPT09IHVuZGVmaW5lZCkgb3V0cHV0ID0gbmV3IFVpbnQ4QXJyYXkobGVuKTtcbiAgICBhYnl0ZXMob3V0cHV0LCB1bmRlZmluZWQsICdvdXRwdXQnKTtcbiAgICBhbnVtYmVyKGNvdW50ZXIpO1xuICAgIGlmIChjb3VudGVyIDwgMCB8fCBjb3VudGVyID49IE1BWF9DT1VOVEVSKSB0aHJvdyBuZXcgRXJyb3IoJ2FyeDogY291bnRlciBvdmVyZmxvdycpO1xuICAgIGlmIChvdXRwdXQubGVuZ3RoIDwgbGVuKVxuICAgICAgdGhyb3cgbmV3IEVycm9yKGBhcng6IG91dHB1dCAoJHtvdXRwdXQubGVuZ3RofSkgaXMgc2hvcnRlciB0aGFuIGRhdGEgKCR7bGVufSlgKTtcbiAgICBjb25zdCB0b0NsZWFuID0gW107XG5cbiAgICAvLyBLZXkgJiBzaWdtYVxuICAgIC8vIGtleT0xNiAtPiBzaWdtYTE2LCBrPWtleXxrZXlcbiAgICAvLyBrZXk9MzIgLT4gc2lnbWEzMiwgaz1rZXlcbiAgICBsZXQgbCA9IGtleS5sZW5ndGg7XG4gICAgbGV0IGs6IFVpbnQ4QXJyYXk7XG4gICAgbGV0IHNpZ21hOiBVaW50MzJBcnJheTtcbiAgICBpZiAobCA9PT0gMzIpIHtcbiAgICAgIHRvQ2xlYW4ucHVzaCgoayA9IGNvcHlCeXRlcyhrZXkpKSk7XG4gICAgICBzaWdtYSA9IHNpZ21hMzJfMzI7XG4gICAgfSBlbHNlIGlmIChsID09PSAxNiAmJiBhbGxvd1Nob3J0S2V5cykge1xuICAgICAgayA9IG5ldyBVaW50OEFycmF5KDMyKTtcbiAgICAgIGsuc2V0KGtleSk7XG4gICAgICBrLnNldChrZXksIDE2KTtcbiAgICAgIHNpZ21hID0gc2lnbWExNl8zMjtcbiAgICAgIHRvQ2xlYW4ucHVzaChrKTtcbiAgICB9IGVsc2Uge1xuICAgICAgYWJ5dGVzKGtleSwgMzIsICdhcngga2V5Jyk7XG4gICAgICB0aHJvdyBuZXcgRXJyb3IoJ2ludmFsaWQga2V5IHNpemUnKTtcbiAgICAgIC8vIHRocm93IG5ldyBFcnJvcihgXCJhcngga2V5XCIgZXhwZWN0ZWQgVWludDhBcnJheSBvZiBsZW5ndGggMzIsIGdvdCBsZW5ndGg9JHtsfWApO1xuICAgIH1cblxuICAgIC8vIE5vbmNlXG4gICAgLy8gc2Fsc2EyMDogICAgICA4ICAgKDgtYnl0ZSBjb3VudGVyKVxuICAgIC8vIGNoYWNoYTIwb3JpZzogOCAgICg4LWJ5dGUgY291bnRlcilcbiAgICAvLyBjaGFjaGEyMDogICAgIDEyICAoNC1ieXRlIGNvdW50ZXIpXG4gICAgLy8geHNhbHNhMjA6ICAgICAyNCAgKDE2IC0+IGhzYWxzYSwgIDggLT4gb2xkIG5vbmNlKVxuICAgIC8vIHhjaGFjaGEyMDogICAgMjQgICgxNiAtPiBoY2hhY2hhLCA4IC0+IG9sZCBub25jZSlcbiAgICAvLyBBbGlnbiBub25jZSB0byA0IGJ5dGVzXG4gICAgaWYgKCFpc0FsaWduZWQzMihub25jZSkpIHRvQ2xlYW4ucHVzaCgobm9uY2UgPSBjb3B5Qnl0ZXMobm9uY2UpKSk7XG5cbiAgICBjb25zdCBrMzIgPSB1MzIoayk7XG4gICAgLy8gaHNhbHNhICYgaGNoYWNoYTogaGFuZGxlIGV4dGVuZGVkIG5vbmNlXG4gICAgaWYgKGV4dGVuZE5vbmNlRm4pIHtcbiAgICAgIGlmIChub25jZS5sZW5ndGggIT09IDI0KSB0aHJvdyBuZXcgRXJyb3IoYGFyeDogZXh0ZW5kZWQgbm9uY2UgbXVzdCBiZSAyNCBieXRlc2ApO1xuICAgICAgZXh0ZW5kTm9uY2VGbihzaWdtYSwgazMyLCB1MzIobm9uY2Uuc3ViYXJyYXkoMCwgMTYpKSwgazMyKTtcbiAgICAgIG5vbmNlID0gbm9uY2Uuc3ViYXJyYXkoMTYpO1xuICAgIH1cblxuICAgIC8vIEhhbmRsZSBub25jZSBjb3VudGVyXG4gICAgY29uc3Qgbm9uY2VOY0xlbiA9IDE2IC0gY291bnRlckxlbmd0aDtcbiAgICBpZiAobm9uY2VOY0xlbiAhPT0gbm9uY2UubGVuZ3RoKVxuICAgICAgdGhyb3cgbmV3IEVycm9yKGBhcng6IG5vbmNlIG11c3QgYmUgJHtub25jZU5jTGVufSBvciAxNiBieXRlc2ApO1xuXG4gICAgLy8gUGFkIGNvdW50ZXIgd2hlbiBub25jZSBpcyA2NCBiaXRcbiAgICBpZiAobm9uY2VOY0xlbiAhPT0gMTIpIHtcbiAgICAgIGNvbnN0IG5jID0gbmV3IFVpbnQ4QXJyYXkoMTIpO1xuICAgICAgbmMuc2V0KG5vbmNlLCBjb3VudGVyUmlnaHQgPyAwIDogMTIgLSBub25jZS5sZW5ndGgpO1xuICAgICAgbm9uY2UgPSBuYztcbiAgICAgIHRvQ2xlYW4ucHVzaChub25jZSk7XG4gICAgfVxuICAgIGNvbnN0IG4zMiA9IHUzMihub25jZSk7XG4gICAgcnVuQ2lwaGVyKGNvcmUsIHNpZ21hLCBrMzIsIG4zMiwgZGF0YSwgb3V0cHV0LCBjb3VudGVyLCByb3VuZHMpO1xuICAgIGNsZWFuKC4uLnRvQ2xlYW4pO1xuICAgIHJldHVybiBvdXRwdXQ7XG4gIH07XG59XG5cbi8qKiBJbnRlcm5hbCBjbGFzcyB3aGljaCB3cmFwcyBjaGFjaGEyMCBvciBjaGFjaGE4IHRvIGNyZWF0ZSBDU1BSTkcuICovXG5leHBvcnQgY2xhc3MgX1hvclN0cmVhbVBSRyBpbXBsZW1lbnRzIFBSRyB7XG4gIHJlYWRvbmx5IGJsb2NrTGVuOiBudW1iZXI7XG4gIHJlYWRvbmx5IGtleUxlbjogbnVtYmVyO1xuICByZWFkb25seSBub25jZUxlbjogbnVtYmVyO1xuICBwcml2YXRlIHN0YXRlOiBVaW50OEFycmF5O1xuICBwcml2YXRlIGJ1ZjogVWludDhBcnJheTtcbiAgcHJpdmF0ZSBrZXk6IFVpbnQ4QXJyYXk7XG4gIHByaXZhdGUgbm9uY2U6IFVpbnQ4QXJyYXk7XG4gIHByaXZhdGUgcG9zOiBudW1iZXI7XG4gIHByaXZhdGUgY3RyOiBudW1iZXI7XG4gIHByaXZhdGUgY2lwaGVyOiBYb3JTdHJlYW07XG4gIGNvbnN0cnVjdG9yKFxuICAgIGNpcGhlcjogWG9yU3RyZWFtLFxuICAgIGJsb2NrTGVuOiBudW1iZXIsXG4gICAga2V5TGVuOiBudW1iZXIsXG4gICAgbm9uY2VMZW46IG51bWJlcixcbiAgICBzZWVkOiBVaW50OEFycmF5XG4gICkge1xuICAgIHRoaXMuY2lwaGVyID0gY2lwaGVyO1xuICAgIHRoaXMuYmxvY2tMZW4gPSBibG9ja0xlbjtcbiAgICB0aGlzLmtleUxlbiA9IGtleUxlbjtcbiAgICB0aGlzLm5vbmNlTGVuID0gbm9uY2VMZW47XG4gICAgdGhpcy5zdGF0ZSA9IG5ldyBVaW50OEFycmF5KHRoaXMua2V5TGVuICsgdGhpcy5ub25jZUxlbik7XG4gICAgdGhpcy5yZXNlZWQoc2VlZCk7XG4gICAgdGhpcy5jdHIgPSAwO1xuICAgIHRoaXMucG9zID0gdGhpcy5ibG9ja0xlbjtcbiAgICB0aGlzLmJ1ZiA9IG5ldyBVaW50OEFycmF5KHRoaXMuYmxvY2tMZW4pO1xuICAgIHRoaXMua2V5ID0gdGhpcy5zdGF0ZS5zdWJhcnJheSgwLCB0aGlzLmtleUxlbik7XG4gICAgdGhpcy5ub25jZSA9IHRoaXMuc3RhdGUuc3ViYXJyYXkodGhpcy5rZXlMZW4pO1xuICB9XG4gIHByaXZhdGUgcmVzZWVkKHNlZWQ6IFVpbnQ4QXJyYXkpIHtcbiAgICBhYnl0ZXMoc2VlZCk7XG4gICAgaWYgKCFzZWVkIHx8IHNlZWQubGVuZ3RoID09PSAwKSB0aHJvdyBuZXcgRXJyb3IoJ2VudHJvcHkgcmVxdWlyZWQnKTtcbiAgICBmb3IgKGxldCBpID0gMDsgaSA8IHNlZWQubGVuZ3RoOyBpKyspIHRoaXMuc3RhdGVbaSAlIHRoaXMuc3RhdGUubGVuZ3RoXSBePSBzZWVkW2ldO1xuICAgIHRoaXMuY3RyID0gMDtcbiAgICB0aGlzLnBvcyA9IHRoaXMuYmxvY2tMZW47XG4gIH1cbiAgYWRkRW50cm9weShzZWVkOiBVaW50OEFycmF5KTogdm9pZCB7XG4gICAgdGhpcy5zdGF0ZS5zZXQodGhpcy5yYW5kb21CeXRlcyh0aGlzLnN0YXRlLmxlbmd0aCkpO1xuICAgIHRoaXMucmVzZWVkKHNlZWQpO1xuICB9XG4gIHJhbmRvbUJ5dGVzKGxlbjogbnVtYmVyKTogVWludDhBcnJheSB7XG4gICAgYW51bWJlcihsZW4pO1xuICAgIGlmIChsZW4gPT09IDApIHJldHVybiBuZXcgVWludDhBcnJheSgwKTtcbiAgICBjb25zdCBvdXQgPSBuZXcgVWludDhBcnJheShsZW4pO1xuICAgIGxldCBvdXRQb3MgPSAwO1xuICAgIC8vIExlZnRvdmVyc1xuICAgIGlmICh0aGlzLnBvcyA8IHRoaXMuYmxvY2tMZW4pIHtcbiAgICAgIGNvbnN0IHRha2UgPSBNYXRoLm1pbihsZW4sIHRoaXMuYmxvY2tMZW4gLSB0aGlzLnBvcyk7XG4gICAgICBvdXQuc2V0KHRoaXMuYnVmLnN1YmFycmF5KHRoaXMucG9zLCB0aGlzLnBvcyArIHRha2UpLCAwKTtcbiAgICAgIHRoaXMucG9zICs9IHRha2U7XG4gICAgICBvdXRQb3MgKz0gdGFrZTtcbiAgICAgIGlmIChvdXRQb3MgPT09IGxlbikgcmV0dXJuIG91dDsgLy8gZmFzdCBwYXRoXG4gICAgfVxuICAgIC8vIEZ1bGwgYmxvY2tzIGRpcmVjdGx5IHRvIG91dFxuICAgIGNvbnN0IGJsb2NrcyA9IE1hdGguZmxvb3IoKGxlbiAtIG91dFBvcykgLyB0aGlzLmJsb2NrTGVuKTtcbiAgICBpZiAoYmxvY2tzID4gMCkge1xuICAgICAgY29uc3QgYmxvY2tCeXRlcyA9IGJsb2NrcyAqIHRoaXMuYmxvY2tMZW47XG4gICAgICBjb25zdCBiID0gb3V0LnN1YmFycmF5KG91dFBvcywgb3V0UG9zICsgYmxvY2tCeXRlcyk7XG4gICAgICB0aGlzLmNpcGhlcih0aGlzLmtleSwgdGhpcy5ub25jZSwgYiwgYiwgdGhpcy5jdHIpO1xuICAgICAgdGhpcy5jdHIgKz0gYmxvY2tzO1xuICAgICAgb3V0UG9zICs9IGJsb2NrQnl0ZXM7XG4gICAgfVxuICAgIC8vIFNhdmUgbGVmdG92ZXJzXG4gICAgY29uc3QgbGVmdCA9IGxlbiAtIG91dFBvcztcbiAgICBpZiAobGVmdCA+IDApIHtcbiAgICAgIHRoaXMuYnVmLmZpbGwoMCk7XG4gICAgICAvLyBOT1RFOiBjaXBoZXIgd2lsbCBoYW5kbGUgb3ZlcmZsb3dcbiAgICAgIHRoaXMuY2lwaGVyKHRoaXMua2V5LCB0aGlzLm5vbmNlLCB0aGlzLmJ1ZiwgdGhpcy5idWYsIHRoaXMuY3RyKyspO1xuICAgICAgb3V0LnNldCh0aGlzLmJ1Zi5zdWJhcnJheSgwLCBsZWZ0KSwgb3V0UG9zKTtcbiAgICAgIHRoaXMucG9zID0gbGVmdDtcbiAgICB9XG4gICAgcmV0dXJuIG91dDtcbiAgfVxuICBjbG9uZSgpOiBfWG9yU3RyZWFtUFJHIHtcbiAgICByZXR1cm4gbmV3IF9Yb3JTdHJlYW1QUkcoXG4gICAgICB0aGlzLmNpcGhlcixcbiAgICAgIHRoaXMuYmxvY2tMZW4sXG4gICAgICB0aGlzLmtleUxlbixcbiAgICAgIHRoaXMubm9uY2VMZW4sXG4gICAgICB0aGlzLnJhbmRvbUJ5dGVzKHRoaXMuc3RhdGUubGVuZ3RoKVxuICAgICk7XG4gIH1cbiAgY2xlYW4oKTogdm9pZCB7XG4gICAgdGhpcy5wb3MgPSAwO1xuICAgIHRoaXMuY3RyID0gMDtcbiAgICB0aGlzLmJ1Zi5maWxsKDApO1xuICAgIHRoaXMuc3RhdGUuZmlsbCgwKTtcbiAgfVxufVxuXG5leHBvcnQgdHlwZSBYb3JQUkcgPSAoc2VlZD86IFVpbnQ4QXJyYXkpID0+IF9Yb3JTdHJlYW1QUkc7XG5cbmV4cG9ydCBjb25zdCBjcmVhdGVQUkcgPSAoXG4gIGNpcGhlcjogWG9yU3RyZWFtLFxuICBibG9ja0xlbjogbnVtYmVyLFxuICBrZXlMZW46IG51bWJlcixcbiAgbm9uY2VMZW46IG51bWJlclxuKTogWG9yUFJHID0+IHtcbiAgcmV0dXJuIChzZWVkOiBVaW50OEFycmF5ID0gcmFuZG9tQnl0ZXMoMzIpKTogX1hvclN0cmVhbVBSRyA9PlxuICAgIG5ldyBfWG9yU3RyZWFtUFJHKGNpcGhlciwgYmxvY2tMZW4sIGtleUxlbiwgbm9uY2VMZW4sIHNlZWQpO1xufTtcbiIsICIvKipcbiAqIFV0aWxpdGllcyBmb3IgaGV4LCBieXRlcywgQ1NQUk5HLlxuICogQG1vZHVsZVxuICovXG4vKiEgbm9ibGUtY2lwaGVycyAtIE1JVCBMaWNlbnNlIChjKSAyMDIzIFBhdWwgTWlsbGVyIChwYXVsbWlsbHIuY29tKSAqL1xuXG4vKiogQ2hlY2tzIGlmIHNvbWV0aGluZyBpcyBVaW50OEFycmF5LiBCZSBjYXJlZnVsOiBub2RlanMgQnVmZmVyIHdpbGwgcmV0dXJuIHRydWUuICovXG5leHBvcnQgZnVuY3Rpb24gaXNCeXRlcyhhOiB1bmtub3duKTogYSBpcyBVaW50OEFycmF5IHtcbiAgcmV0dXJuIGEgaW5zdGFuY2VvZiBVaW50OEFycmF5IHx8IChBcnJheUJ1ZmZlci5pc1ZpZXcoYSkgJiYgYS5jb25zdHJ1Y3Rvci5uYW1lID09PSAnVWludDhBcnJheScpO1xufVxuXG4vKiogQXNzZXJ0cyBzb21ldGhpbmcgaXMgYm9vbGVhbi4gKi9cbmV4cG9ydCBmdW5jdGlvbiBhYm9vbChiOiBib29sZWFuKTogdm9pZCB7XG4gIGlmICh0eXBlb2YgYiAhPT0gJ2Jvb2xlYW4nKSB0aHJvdyBuZXcgRXJyb3IoYGJvb2xlYW4gZXhwZWN0ZWQsIG5vdCAke2J9YCk7XG59XG5cbi8qKiBBc3NlcnRzIHNvbWV0aGluZyBpcyBwb3NpdGl2ZSBpbnRlZ2VyLiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGFudW1iZXIobjogbnVtYmVyKTogdm9pZCB7XG4gIGlmICghTnVtYmVyLmlzU2FmZUludGVnZXIobikgfHwgbiA8IDApIHRocm93IG5ldyBFcnJvcigncG9zaXRpdmUgaW50ZWdlciBleHBlY3RlZCwgZ290ICcgKyBuKTtcbn1cblxuLyoqIEFzc2VydHMgc29tZXRoaW5nIGlzIFVpbnQ4QXJyYXkuICovXG5leHBvcnQgZnVuY3Rpb24gYWJ5dGVzKHZhbHVlOiBVaW50OEFycmF5LCBsZW5ndGg/OiBudW1iZXIsIHRpdGxlOiBzdHJpbmcgPSAnJyk6IFVpbnQ4QXJyYXkge1xuICBjb25zdCBieXRlcyA9IGlzQnl0ZXModmFsdWUpO1xuICBjb25zdCBsZW4gPSB2YWx1ZT8ubGVuZ3RoO1xuICBjb25zdCBuZWVkc0xlbiA9IGxlbmd0aCAhPT0gdW5kZWZpbmVkO1xuICBpZiAoIWJ5dGVzIHx8IChuZWVkc0xlbiAmJiBsZW4gIT09IGxlbmd0aCkpIHtcbiAgICBjb25zdCBwcmVmaXggPSB0aXRsZSAmJiBgXCIke3RpdGxlfVwiIGA7XG4gICAgY29uc3Qgb2ZMZW4gPSBuZWVkc0xlbiA/IGAgb2YgbGVuZ3RoICR7bGVuZ3RofWAgOiAnJztcbiAgICBjb25zdCBnb3QgPSBieXRlcyA/IGBsZW5ndGg9JHtsZW59YCA6IGB0eXBlPSR7dHlwZW9mIHZhbHVlfWA7XG4gICAgdGhyb3cgbmV3IEVycm9yKHByZWZpeCArICdleHBlY3RlZCBVaW50OEFycmF5JyArIG9mTGVuICsgJywgZ290ICcgKyBnb3QpO1xuICB9XG4gIHJldHVybiB2YWx1ZTtcbn1cblxuLyoqIEFzc2VydHMgYSBoYXNoIGluc3RhbmNlIGhhcyBub3QgYmVlbiBkZXN0cm95ZWQgLyBmaW5pc2hlZCAqL1xuZXhwb3J0IGZ1bmN0aW9uIGFleGlzdHMoaW5zdGFuY2U6IGFueSwgY2hlY2tGaW5pc2hlZCA9IHRydWUpOiB2b2lkIHtcbiAgaWYgKGluc3RhbmNlLmRlc3Ryb3llZCkgdGhyb3cgbmV3IEVycm9yKCdIYXNoIGluc3RhbmNlIGhhcyBiZWVuIGRlc3Ryb3llZCcpO1xuICBpZiAoY2hlY2tGaW5pc2hlZCAmJiBpbnN0YW5jZS5maW5pc2hlZCkgdGhyb3cgbmV3IEVycm9yKCdIYXNoI2RpZ2VzdCgpIGhhcyBhbHJlYWR5IGJlZW4gY2FsbGVkJyk7XG59XG5cbi8qKiBBc3NlcnRzIG91dHB1dCBpcyBwcm9wZXJseS1zaXplZCBieXRlIGFycmF5ICovXG5leHBvcnQgZnVuY3Rpb24gYW91dHB1dChvdXQ6IGFueSwgaW5zdGFuY2U6IGFueSk6IHZvaWQge1xuICBhYnl0ZXMob3V0LCB1bmRlZmluZWQsICdvdXRwdXQnKTtcbiAgY29uc3QgbWluID0gaW5zdGFuY2Uub3V0cHV0TGVuO1xuICBpZiAob3V0Lmxlbmd0aCA8IG1pbikge1xuICAgIHRocm93IG5ldyBFcnJvcignZGlnZXN0SW50bygpIGV4cGVjdHMgb3V0cHV0IGJ1ZmZlciBvZiBsZW5ndGggYXQgbGVhc3QgJyArIG1pbik7XG4gIH1cbn1cblxuZXhwb3J0IHR5cGUgSUhhc2ggPSB7XG4gIChkYXRhOiBzdHJpbmcgfCBVaW50OEFycmF5KTogVWludDhBcnJheTtcbiAgYmxvY2tMZW46IG51bWJlcjtcbiAgb3V0cHV0TGVuOiBudW1iZXI7XG4gIGNyZWF0ZTogYW55O1xufTtcblxuLyoqIEdlbmVyaWMgdHlwZSBlbmNvbXBhc3NpbmcgOC8xNi8zMi1ieXRlIGFycmF5cyAtIGJ1dCBub3QgNjQtYnl0ZS4gKi9cbi8vIHByZXR0aWVyLWlnbm9yZVxuZXhwb3J0IHR5cGUgVHlwZWRBcnJheSA9IEludDhBcnJheSB8IFVpbnQ4Q2xhbXBlZEFycmF5IHwgVWludDhBcnJheSB8XG4gIFVpbnQxNkFycmF5IHwgSW50MTZBcnJheSB8IFVpbnQzMkFycmF5IHwgSW50MzJBcnJheTtcblxuLyoqIENhc3QgdTggLyB1MTYgLyB1MzIgdG8gdTguICovXG5leHBvcnQgZnVuY3Rpb24gdTgoYXJyOiBUeXBlZEFycmF5KTogVWludDhBcnJheSB7XG4gIHJldHVybiBuZXcgVWludDhBcnJheShhcnIuYnVmZmVyLCBhcnIuYnl0ZU9mZnNldCwgYXJyLmJ5dGVMZW5ndGgpO1xufVxuXG4vKiogQ2FzdCB1OCAvIHUxNiAvIHUzMiB0byB1MzIuICovXG5leHBvcnQgZnVuY3Rpb24gdTMyKGFycjogVHlwZWRBcnJheSk6IFVpbnQzMkFycmF5IHtcbiAgcmV0dXJuIG5ldyBVaW50MzJBcnJheShhcnIuYnVmZmVyLCBhcnIuYnl0ZU9mZnNldCwgTWF0aC5mbG9vcihhcnIuYnl0ZUxlbmd0aCAvIDQpKTtcbn1cblxuLyoqIFplcm9pemUgYSBieXRlIGFycmF5LiBXYXJuaW5nOiBKUyBwcm92aWRlcyBubyBndWFyYW50ZWVzLiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGNsZWFuKC4uLmFycmF5czogVHlwZWRBcnJheVtdKTogdm9pZCB7XG4gIGZvciAobGV0IGkgPSAwOyBpIDwgYXJyYXlzLmxlbmd0aDsgaSsrKSB7XG4gICAgYXJyYXlzW2ldLmZpbGwoMCk7XG4gIH1cbn1cblxuLyoqIENyZWF0ZSBEYXRhVmlldyBvZiBhbiBhcnJheSBmb3IgZWFzeSBieXRlLWxldmVsIG1hbmlwdWxhdGlvbi4gKi9cbmV4cG9ydCBmdW5jdGlvbiBjcmVhdGVWaWV3KGFycjogVHlwZWRBcnJheSk6IERhdGFWaWV3IHtcbiAgcmV0dXJuIG5ldyBEYXRhVmlldyhhcnIuYnVmZmVyLCBhcnIuYnl0ZU9mZnNldCwgYXJyLmJ5dGVMZW5ndGgpO1xufVxuXG4vKiogSXMgY3VycmVudCBwbGF0Zm9ybSBsaXR0bGUtZW5kaWFuPyBNb3N0IGFyZS4gQmlnLUVuZGlhbiBwbGF0Zm9ybTogSUJNICovXG5leHBvcnQgY29uc3QgaXNMRTogYm9vbGVhbiA9IC8qIEBfX1BVUkVfXyAqLyAoKCkgPT5cbiAgbmV3IFVpbnQ4QXJyYXkobmV3IFVpbnQzMkFycmF5KFsweDExMjIzMzQ0XSkuYnVmZmVyKVswXSA9PT0gMHg0NCkoKTtcblxuLy8gQnVpbHQtaW4gaGV4IGNvbnZlcnNpb24gaHR0cHM6Ly9jYW5pdXNlLmNvbS9tZG4tamF2YXNjcmlwdF9idWlsdGluc191aW50OGFycmF5X2Zyb21oZXhcbmNvbnN0IGhhc0hleEJ1aWx0aW46IGJvb2xlYW4gPSAvKiBAX19QVVJFX18gKi8gKCgpID0+XG4gIC8vIEB0cy1pZ25vcmVcbiAgdHlwZW9mIFVpbnQ4QXJyYXkuZnJvbShbXSkudG9IZXggPT09ICdmdW5jdGlvbicgJiYgdHlwZW9mIFVpbnQ4QXJyYXkuZnJvbUhleCA9PT0gJ2Z1bmN0aW9uJykoKTtcblxuLy8gQXJyYXkgd2hlcmUgaW5kZXggMHhmMCAoMjQwKSBpcyBtYXBwZWQgdG8gc3RyaW5nICdmMCdcbmNvbnN0IGhleGVzID0gLyogQF9fUFVSRV9fICovIEFycmF5LmZyb20oeyBsZW5ndGg6IDI1NiB9LCAoXywgaSkgPT5cbiAgaS50b1N0cmluZygxNikucGFkU3RhcnQoMiwgJzAnKVxuKTtcblxuLyoqXG4gKiBDb252ZXJ0IGJ5dGUgYXJyYXkgdG8gaGV4IHN0cmluZy4gVXNlcyBidWlsdC1pbiBmdW5jdGlvbiwgd2hlbiBhdmFpbGFibGUuXG4gKiBAZXhhbXBsZSBieXRlc1RvSGV4KFVpbnQ4QXJyYXkuZnJvbShbMHhjYSwgMHhmZSwgMHgwMSwgMHgyM10pKSAvLyAnY2FmZTAxMjMnXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBieXRlc1RvSGV4KGJ5dGVzOiBVaW50OEFycmF5KTogc3RyaW5nIHtcbiAgYWJ5dGVzKGJ5dGVzKTtcbiAgLy8gQHRzLWlnbm9yZVxuICBpZiAoaGFzSGV4QnVpbHRpbikgcmV0dXJuIGJ5dGVzLnRvSGV4KCk7XG4gIC8vIHByZS1jYWNoaW5nIGltcHJvdmVzIHRoZSBzcGVlZCA2eFxuICBsZXQgaGV4ID0gJyc7XG4gIGZvciAobGV0IGkgPSAwOyBpIDwgYnl0ZXMubGVuZ3RoOyBpKyspIHtcbiAgICBoZXggKz0gaGV4ZXNbYnl0ZXNbaV1dO1xuICB9XG4gIHJldHVybiBoZXg7XG59XG5cbi8vIFdlIHVzZSBvcHRpbWl6ZWQgdGVjaG5pcXVlIHRvIGNvbnZlcnQgaGV4IHN0cmluZyB0byBieXRlIGFycmF5XG5jb25zdCBhc2NpaXMgPSB7IF8wOiA0OCwgXzk6IDU3LCBBOiA2NSwgRjogNzAsIGE6IDk3LCBmOiAxMDIgfSBhcyBjb25zdDtcbmZ1bmN0aW9uIGFzY2lpVG9CYXNlMTYoY2g6IG51bWJlcik6IG51bWJlciB8IHVuZGVmaW5lZCB7XG4gIGlmIChjaCA+PSBhc2NpaXMuXzAgJiYgY2ggPD0gYXNjaWlzLl85KSByZXR1cm4gY2ggLSBhc2NpaXMuXzA7IC8vICcyJyA9PiA1MC00OFxuICBpZiAoY2ggPj0gYXNjaWlzLkEgJiYgY2ggPD0gYXNjaWlzLkYpIHJldHVybiBjaCAtIChhc2NpaXMuQSAtIDEwKTsgLy8gJ0InID0+IDY2LSg2NS0xMClcbiAgaWYgKGNoID49IGFzY2lpcy5hICYmIGNoIDw9IGFzY2lpcy5mKSByZXR1cm4gY2ggLSAoYXNjaWlzLmEgLSAxMCk7IC8vICdiJyA9PiA5OC0oOTctMTApXG4gIHJldHVybjtcbn1cblxuLyoqXG4gKiBDb252ZXJ0IGhleCBzdHJpbmcgdG8gYnl0ZSBhcnJheS4gVXNlcyBidWlsdC1pbiBmdW5jdGlvbiwgd2hlbiBhdmFpbGFibGUuXG4gKiBAZXhhbXBsZSBoZXhUb0J5dGVzKCdjYWZlMDEyMycpIC8vIFVpbnQ4QXJyYXkuZnJvbShbMHhjYSwgMHhmZSwgMHgwMSwgMHgyM10pXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBoZXhUb0J5dGVzKGhleDogc3RyaW5nKTogVWludDhBcnJheSB7XG4gIGlmICh0eXBlb2YgaGV4ICE9PSAnc3RyaW5nJykgdGhyb3cgbmV3IEVycm9yKCdoZXggc3RyaW5nIGV4cGVjdGVkLCBnb3QgJyArIHR5cGVvZiBoZXgpO1xuICAvLyBAdHMtaWdub3JlXG4gIGlmIChoYXNIZXhCdWlsdGluKSByZXR1cm4gVWludDhBcnJheS5mcm9tSGV4KGhleCk7XG4gIGNvbnN0IGhsID0gaGV4Lmxlbmd0aDtcbiAgY29uc3QgYWwgPSBobCAvIDI7XG4gIGlmIChobCAlIDIpIHRocm93IG5ldyBFcnJvcignaGV4IHN0cmluZyBleHBlY3RlZCwgZ290IHVucGFkZGVkIGhleCBvZiBsZW5ndGggJyArIGhsKTtcbiAgY29uc3QgYXJyYXkgPSBuZXcgVWludDhBcnJheShhbCk7XG4gIGZvciAobGV0IGFpID0gMCwgaGkgPSAwOyBhaSA8IGFsOyBhaSsrLCBoaSArPSAyKSB7XG4gICAgY29uc3QgbjEgPSBhc2NpaVRvQmFzZTE2KGhleC5jaGFyQ29kZUF0KGhpKSk7XG4gICAgY29uc3QgbjIgPSBhc2NpaVRvQmFzZTE2KGhleC5jaGFyQ29kZUF0KGhpICsgMSkpO1xuICAgIGlmIChuMSA9PT0gdW5kZWZpbmVkIHx8IG4yID09PSB1bmRlZmluZWQpIHtcbiAgICAgIGNvbnN0IGNoYXIgPSBoZXhbaGldICsgaGV4W2hpICsgMV07XG4gICAgICB0aHJvdyBuZXcgRXJyb3IoJ2hleCBzdHJpbmcgZXhwZWN0ZWQsIGdvdCBub24taGV4IGNoYXJhY3RlciBcIicgKyBjaGFyICsgJ1wiIGF0IGluZGV4ICcgKyBoaSk7XG4gICAgfVxuICAgIGFycmF5W2FpXSA9IG4xICogMTYgKyBuMjsgLy8gbXVsdGlwbHkgZmlyc3Qgb2N0ZXQsIGUuZy4gJ2EzJyA9PiAxMCoxNiszID0+IDE2MCArIDMgPT4gMTYzXG4gIH1cbiAgcmV0dXJuIGFycmF5O1xufVxuXG4vLyBVc2VkIGluIG1pY3JvXG5leHBvcnQgZnVuY3Rpb24gaGV4VG9OdW1iZXIoaGV4OiBzdHJpbmcpOiBiaWdpbnQge1xuICBpZiAodHlwZW9mIGhleCAhPT0gJ3N0cmluZycpIHRocm93IG5ldyBFcnJvcignaGV4IHN0cmluZyBleHBlY3RlZCwgZ290ICcgKyB0eXBlb2YgaGV4KTtcbiAgcmV0dXJuIEJpZ0ludChoZXggPT09ICcnID8gJzAnIDogJzB4JyArIGhleCk7IC8vIEJpZyBFbmRpYW5cbn1cblxuLy8gVXNlZCBpbiBmZjFcbi8vIEJFOiBCaWcgRW5kaWFuLCBMRTogTGl0dGxlIEVuZGlhblxuZXhwb3J0IGZ1bmN0aW9uIGJ5dGVzVG9OdW1iZXJCRShieXRlczogVWludDhBcnJheSk6IGJpZ2ludCB7XG4gIHJldHVybiBoZXhUb051bWJlcihieXRlc1RvSGV4KGJ5dGVzKSk7XG59XG5cbi8vIFVzZWQgaW4gbWljcm8sIGZmMVxuZXhwb3J0IGZ1bmN0aW9uIG51bWJlclRvQnl0ZXNCRShuOiBudW1iZXIgfCBiaWdpbnQsIGxlbjogbnVtYmVyKTogVWludDhBcnJheSB7XG4gIHJldHVybiBoZXhUb0J5dGVzKG4udG9TdHJpbmcoMTYpLnBhZFN0YXJ0KGxlbiAqIDIsICcwJykpO1xufVxuXG4vLyBHbG9iYWwgc3ltYm9scywgYnV0IHRzIGRvZXNuJ3Qgc2VlIHRoZW06IGh0dHBzOi8vZ2l0aHViLmNvbS9taWNyb3NvZnQvVHlwZVNjcmlwdC9pc3N1ZXMvMzE1MzVcbmRlY2xhcmUgY29uc3QgVGV4dEVuY29kZXI6IGFueTtcbmRlY2xhcmUgY29uc3QgVGV4dERlY29kZXI6IGFueTtcblxuLyoqXG4gKiBDb252ZXJ0cyBzdHJpbmcgdG8gYnl0ZXMgdXNpbmcgVVRGOCBlbmNvZGluZy5cbiAqIEBleGFtcGxlIHV0ZjhUb0J5dGVzKCdhYmMnKSAvLyBuZXcgVWludDhBcnJheShbOTcsIDk4LCA5OV0pXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiB1dGY4VG9CeXRlcyhzdHI6IHN0cmluZyk6IFVpbnQ4QXJyYXkge1xuICBpZiAodHlwZW9mIHN0ciAhPT0gJ3N0cmluZycpIHRocm93IG5ldyBFcnJvcignc3RyaW5nIGV4cGVjdGVkJyk7XG4gIHJldHVybiBuZXcgVWludDhBcnJheShuZXcgVGV4dEVuY29kZXIoKS5lbmNvZGUoc3RyKSk7IC8vIGh0dHBzOi8vYnVnemlsLmxhLzE2ODE4MDlcbn1cblxuLyoqXG4gKiBDb252ZXJ0cyBieXRlcyB0byBzdHJpbmcgdXNpbmcgVVRGOCBlbmNvZGluZy5cbiAqIEBleGFtcGxlIGJ5dGVzVG9VdGY4KG5ldyBVaW50OEFycmF5KFs5NywgOTgsIDk5XSkpIC8vICdhYmMnXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBieXRlc1RvVXRmOChieXRlczogVWludDhBcnJheSk6IHN0cmluZyB7XG4gIHJldHVybiBuZXcgVGV4dERlY29kZXIoKS5kZWNvZGUoYnl0ZXMpO1xufVxuXG4vKipcbiAqIENoZWNrcyBpZiB0d28gVThBIHVzZSBzYW1lIHVuZGVybHlpbmcgYnVmZmVyIGFuZCBvdmVybGFwcy5cbiAqIFRoaXMgaXMgaW52YWxpZCBhbmQgY2FuIGNvcnJ1cHQgZGF0YS5cbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIG92ZXJsYXBCeXRlcyhhOiBVaW50OEFycmF5LCBiOiBVaW50OEFycmF5KTogYm9vbGVhbiB7XG4gIHJldHVybiAoXG4gICAgYS5idWZmZXIgPT09IGIuYnVmZmVyICYmIC8vIGJlc3Qgd2UgY2FuIGRvLCBtYXkgZmFpbCB3aXRoIGFuIG9ic2N1cmUgUHJveHlcbiAgICBhLmJ5dGVPZmZzZXQgPCBiLmJ5dGVPZmZzZXQgKyBiLmJ5dGVMZW5ndGggJiYgLy8gYSBzdGFydHMgYmVmb3JlIGIgZW5kXG4gICAgYi5ieXRlT2Zmc2V0IDwgYS5ieXRlT2Zmc2V0ICsgYS5ieXRlTGVuZ3RoIC8vIGIgc3RhcnRzIGJlZm9yZSBhIGVuZFxuICApO1xufVxuXG4vKipcbiAqIElmIGlucHV0IGFuZCBvdXRwdXQgb3ZlcmxhcCBhbmQgaW5wdXQgc3RhcnRzIGJlZm9yZSBvdXRwdXQsIHdlIHdpbGwgb3ZlcndyaXRlIGVuZCBvZiBpbnB1dCBiZWZvcmVcbiAqIHdlIHN0YXJ0IHByb2Nlc3NpbmcgaXQsIHNvIHRoaXMgaXMgbm90IHN1cHBvcnRlZCBmb3IgbW9zdCBjaXBoZXJzIChleGNlcHQgY2hhY2hhL3NhbHNlLCB3aGljaCBkZXNpZ25lZCB3aXRoIHRoaXMpXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBjb21wbGV4T3ZlcmxhcEJ5dGVzKGlucHV0OiBVaW50OEFycmF5LCBvdXRwdXQ6IFVpbnQ4QXJyYXkpOiB2b2lkIHtcbiAgLy8gVGhpcyBpcyB2ZXJ5IGN1cnNlZC4gSXQgd29ya3Mgc29tZWhvdywgYnV0IEknbSBjb21wbGV0ZWx5IHVuc3VyZSxcbiAgLy8gcmVhc29uaW5nIGFib3V0IG92ZXJsYXBwaW5nIGFsaWduZWQgd2luZG93cyBpcyB2ZXJ5IGhhcmQuXG4gIGlmIChvdmVybGFwQnl0ZXMoaW5wdXQsIG91dHB1dCkgJiYgaW5wdXQuYnl0ZU9mZnNldCA8IG91dHB1dC5ieXRlT2Zmc2V0KVxuICAgIHRocm93IG5ldyBFcnJvcignY29tcGxleCBvdmVybGFwIG9mIGlucHV0IGFuZCBvdXRwdXQgaXMgbm90IHN1cHBvcnRlZCcpO1xufVxuXG4vKipcbiAqIENvcGllcyBzZXZlcmFsIFVpbnQ4QXJyYXlzIGludG8gb25lLlxuICovXG5leHBvcnQgZnVuY3Rpb24gY29uY2F0Qnl0ZXMoLi4uYXJyYXlzOiBVaW50OEFycmF5W10pOiBVaW50OEFycmF5IHtcbiAgbGV0IHN1bSA9IDA7XG4gIGZvciAobGV0IGkgPSAwOyBpIDwgYXJyYXlzLmxlbmd0aDsgaSsrKSB7XG4gICAgY29uc3QgYSA9IGFycmF5c1tpXTtcbiAgICBhYnl0ZXMoYSk7XG4gICAgc3VtICs9IGEubGVuZ3RoO1xuICB9XG4gIGNvbnN0IHJlcyA9IG5ldyBVaW50OEFycmF5KHN1bSk7XG4gIGZvciAobGV0IGkgPSAwLCBwYWQgPSAwOyBpIDwgYXJyYXlzLmxlbmd0aDsgaSsrKSB7XG4gICAgY29uc3QgYSA9IGFycmF5c1tpXTtcbiAgICByZXMuc2V0KGEsIHBhZCk7XG4gICAgcGFkICs9IGEubGVuZ3RoO1xuICB9XG4gIHJldHVybiByZXM7XG59XG5cbi8vIFVzZWQgaW4gQVJYIG9ubHlcbnR5cGUgRW1wdHlPYmogPSB7fTtcbmV4cG9ydCBmdW5jdGlvbiBjaGVja09wdHM8VDEgZXh0ZW5kcyBFbXB0eU9iaiwgVDIgZXh0ZW5kcyBFbXB0eU9iaj4oXG4gIGRlZmF1bHRzOiBUMSxcbiAgb3B0czogVDJcbik6IFQxICYgVDIge1xuICBpZiAob3B0cyA9PSBudWxsIHx8IHR5cGVvZiBvcHRzICE9PSAnb2JqZWN0JykgdGhyb3cgbmV3IEVycm9yKCdvcHRpb25zIG11c3QgYmUgZGVmaW5lZCcpO1xuICBjb25zdCBtZXJnZWQgPSBPYmplY3QuYXNzaWduKGRlZmF1bHRzLCBvcHRzKTtcbiAgcmV0dXJuIG1lcmdlZCBhcyBUMSAmIFQyO1xufVxuXG4vKiogQ29tcGFyZXMgMiB1aW50OGFycmF5LXMgaW4ga2luZGEgY29uc3RhbnQgdGltZS4gKi9cbmV4cG9ydCBmdW5jdGlvbiBlcXVhbEJ5dGVzKGE6IFVpbnQ4QXJyYXksIGI6IFVpbnQ4QXJyYXkpOiBib29sZWFuIHtcbiAgaWYgKGEubGVuZ3RoICE9PSBiLmxlbmd0aCkgcmV0dXJuIGZhbHNlO1xuICBsZXQgZGlmZiA9IDA7XG4gIGZvciAobGV0IGkgPSAwOyBpIDwgYS5sZW5ndGg7IGkrKykgZGlmZiB8PSBhW2ldIF4gYltpXTtcbiAgcmV0dXJuIGRpZmYgPT09IDA7XG59XG5cbi8vIFRPRE86IHJlbW92ZVxuZXhwb3J0IGludGVyZmFjZSBJSGFzaDIge1xuICBibG9ja0xlbjogbnVtYmVyOyAvLyBCeXRlcyBwZXIgYmxvY2tcbiAgb3V0cHV0TGVuOiBudW1iZXI7IC8vIEJ5dGVzIGluIG91dHB1dFxuICB1cGRhdGUoYnVmOiBzdHJpbmcgfCBVaW50OEFycmF5KTogdGhpcztcbiAgLy8gV3JpdGVzIGRpZ2VzdCBpbnRvIGJ1ZlxuICBkaWdlc3RJbnRvKGJ1ZjogVWludDhBcnJheSk6IHZvaWQ7XG4gIGRpZ2VzdCgpOiBVaW50OEFycmF5O1xuICAvKipcbiAgICogUmVzZXRzIGludGVybmFsIHN0YXRlLiBNYWtlcyBIYXNoIGluc3RhbmNlIHVudXNhYmxlLlxuICAgKiBSZXNldCBpcyBpbXBvc3NpYmxlIGZvciBrZXllZCBoYXNoZXMgaWYga2V5IGlzIGNvbnN1bWVkIGludG8gc3RhdGUuIElmIGRpZ2VzdCBpcyBub3QgY29uc3VtZWRcbiAgICogYnkgdXNlciwgdGhleSB3aWxsIG5lZWQgdG8gbWFudWFsbHkgY2FsbCBgZGVzdHJveSgpYCB3aGVuIHplcm9pbmcgaXMgbmVjZXNzYXJ5LlxuICAgKi9cbiAgZGVzdHJveSgpOiB2b2lkO1xufVxuXG4vLyBUaGlzIHdpbGwgYWxsb3cgdG8gcmUtdXNlIHdpdGggY29tcG9zYWJsZSB0aGluZ3MgbGlrZSBwYWNrZWQgJiBiYXNlIGVuY29kZXJzXG4vLyBBbHNvLCB3ZSBwcm9iYWJseSBjYW4gbWFrZSB0YWdzIGNvbXBvc2FibGVcblxuLyoqIFN5bmMgY2lwaGVyOiB0YWtlcyBieXRlIGFycmF5IGFuZCByZXR1cm5zIGJ5dGUgYXJyYXkuICovXG5leHBvcnQgdHlwZSBDaXBoZXIgPSB7XG4gIGVuY3J5cHQocGxhaW50ZXh0OiBVaW50OEFycmF5KTogVWludDhBcnJheTtcbiAgZGVjcnlwdChjaXBoZXJ0ZXh0OiBVaW50OEFycmF5KTogVWludDhBcnJheTtcbn07XG5cbi8qKiBBc3luYyBjaXBoZXIgZS5nLiBmcm9tIGJ1aWx0LWluIFdlYkNyeXB0by4gKi9cbmV4cG9ydCB0eXBlIEFzeW5jQ2lwaGVyID0ge1xuICBlbmNyeXB0KHBsYWludGV4dDogVWludDhBcnJheSk6IFByb21pc2U8VWludDhBcnJheT47XG4gIGRlY3J5cHQoY2lwaGVydGV4dDogVWludDhBcnJheSk6IFByb21pc2U8VWludDhBcnJheT47XG59O1xuXG4vKiogQ2lwaGVyIHdpdGggYG91dHB1dGAgYXJndW1lbnQgd2hpY2ggY2FuIG9wdGltaXplIGJ5IGRvaW5nIDEgbGVzcyBhbGxvY2F0aW9uLiAqL1xuZXhwb3J0IHR5cGUgQ2lwaGVyV2l0aE91dHB1dCA9IENpcGhlciAmIHtcbiAgZW5jcnlwdChwbGFpbnRleHQ6IFVpbnQ4QXJyYXksIG91dHB1dD86IFVpbnQ4QXJyYXkpOiBVaW50OEFycmF5O1xuICBkZWNyeXB0KGNpcGhlcnRleHQ6IFVpbnQ4QXJyYXksIG91dHB1dD86IFVpbnQ4QXJyYXkpOiBVaW50OEFycmF5O1xufTtcblxuLyoqXG4gKiBQYXJhbXMgYXJlIG91dHNpZGUgb2YgcmV0dXJuIHR5cGUsIHNvIGl0IGlzIGFjY2Vzc2libGUgYmVmb3JlIGNhbGxpbmcgY29uc3RydWN0b3IuXG4gKiBJZiBmdW5jdGlvbiBzdXBwb3J0IG11bHRpcGxlIG5vbmNlTGVuZ3RoJ3MsIHdlIHJldHVybiB0aGUgYmVzdCBvbmUuXG4gKi9cbmV4cG9ydCB0eXBlIENpcGhlclBhcmFtcyA9IHtcbiAgYmxvY2tTaXplOiBudW1iZXI7XG4gIG5vbmNlTGVuZ3RoPzogbnVtYmVyO1xuICB0YWdMZW5ndGg/OiBudW1iZXI7XG4gIHZhclNpemVOb25jZT86IGJvb2xlYW47XG59O1xuLyoqIEFSWCBjaXBoZXIsIGxpa2Ugc2Fsc2Egb3IgY2hhY2hhLiAqL1xuZXhwb3J0IHR5cGUgQVJYQ2lwaGVyID0gKChcbiAga2V5OiBVaW50OEFycmF5LFxuICBub25jZTogVWludDhBcnJheSxcbiAgQUFEPzogVWludDhBcnJheVxuKSA9PiBDaXBoZXJXaXRoT3V0cHV0KSAmIHtcbiAgYmxvY2tTaXplOiBudW1iZXI7XG4gIG5vbmNlTGVuZ3RoOiBudW1iZXI7XG4gIHRhZ0xlbmd0aDogbnVtYmVyO1xufTtcbmV4cG9ydCB0eXBlIENpcGhlckNvbnM8VCBleHRlbmRzIGFueVtdPiA9IChrZXk6IFVpbnQ4QXJyYXksIC4uLmFyZ3M6IFQpID0+IENpcGhlcjtcbi8qKlxuICogV3JhcHMgYSBjaXBoZXI6IHZhbGlkYXRlcyBhcmdzLCBlbnN1cmVzIGVuY3J5cHQoKSBjYW4gb25seSBiZSBjYWxsZWQgb25jZS5cbiAqIEBfX05PX1NJREVfRUZGRUNUU19fXG4gKi9cbmV4cG9ydCBjb25zdCB3cmFwQ2lwaGVyID0gPEMgZXh0ZW5kcyBDaXBoZXJDb25zPGFueT4sIFAgZXh0ZW5kcyBDaXBoZXJQYXJhbXM+KFxuICBwYXJhbXM6IFAsXG4gIGNvbnN0cnVjdG9yOiBDXG4pOiBDICYgUCA9PiB7XG4gIGZ1bmN0aW9uIHdyYXBwZWRDaXBoZXIoa2V5OiBVaW50OEFycmF5LCAuLi5hcmdzOiBhbnlbXSk6IENpcGhlcldpdGhPdXRwdXQge1xuICAgIC8vIFZhbGlkYXRlIGtleVxuICAgIGFieXRlcyhrZXksIHVuZGVmaW5lZCwgJ2tleScpO1xuXG4gICAgLy8gQmlnLUVuZGlhbiBoYXJkd2FyZSBpcyByYXJlLiBKdXN0IGluIGNhc2Ugc29tZW9uZSBzdGlsbCBkZWNpZGVzIHRvIHJ1biBjaXBoZXJzOlxuICAgIGlmICghaXNMRSkgdGhyb3cgbmV3IEVycm9yKCdOb24gbGl0dGxlLWVuZGlhbiBoYXJkd2FyZSBpcyBub3QgeWV0IHN1cHBvcnRlZCcpO1xuXG4gICAgLy8gVmFsaWRhdGUgbm9uY2UgaWYgbm9uY2VMZW5ndGggaXMgcHJlc2VudFxuICAgIGlmIChwYXJhbXMubm9uY2VMZW5ndGggIT09IHVuZGVmaW5lZCkge1xuICAgICAgY29uc3Qgbm9uY2UgPSBhcmdzWzBdO1xuICAgICAgYWJ5dGVzKG5vbmNlLCBwYXJhbXMudmFyU2l6ZU5vbmNlID8gdW5kZWZpbmVkIDogcGFyYW1zLm5vbmNlTGVuZ3RoLCAnbm9uY2UnKTtcbiAgICB9XG5cbiAgICAvLyBWYWxpZGF0ZSBBQUQgaWYgdGFnTGVuZ3RoIHByZXNlbnRcbiAgICBjb25zdCB0YWdsID0gcGFyYW1zLnRhZ0xlbmd0aDtcbiAgICBpZiAodGFnbCAmJiBhcmdzWzFdICE9PSB1bmRlZmluZWQpIGFieXRlcyhhcmdzWzFdLCB1bmRlZmluZWQsICdBQUQnKTtcblxuICAgIGNvbnN0IGNpcGhlciA9IGNvbnN0cnVjdG9yKGtleSwgLi4uYXJncyk7XG4gICAgY29uc3QgY2hlY2tPdXRwdXQgPSAoZm5MZW5ndGg6IG51bWJlciwgb3V0cHV0PzogVWludDhBcnJheSkgPT4ge1xuICAgICAgaWYgKG91dHB1dCAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgIGlmIChmbkxlbmd0aCAhPT0gMikgdGhyb3cgbmV3IEVycm9yKCdjaXBoZXIgb3V0cHV0IG5vdCBzdXBwb3J0ZWQnKTtcbiAgICAgICAgYWJ5dGVzKG91dHB1dCwgdW5kZWZpbmVkLCAnb3V0cHV0Jyk7XG4gICAgICB9XG4gICAgfTtcbiAgICAvLyBDcmVhdGUgd3JhcHBlZCBjaXBoZXIgd2l0aCB2YWxpZGF0aW9uIGFuZCBzaW5nbGUtdXNlIGVuY3J5cHRpb25cbiAgICBsZXQgY2FsbGVkID0gZmFsc2U7XG4gICAgY29uc3Qgd3JDaXBoZXIgPSB7XG4gICAgICBlbmNyeXB0KGRhdGE6IFVpbnQ4QXJyYXksIG91dHB1dD86IFVpbnQ4QXJyYXkpIHtcbiAgICAgICAgaWYgKGNhbGxlZCkgdGhyb3cgbmV3IEVycm9yKCdjYW5ub3QgZW5jcnlwdCgpIHR3aWNlIHdpdGggc2FtZSBrZXkgKyBub25jZScpO1xuICAgICAgICBjYWxsZWQgPSB0cnVlO1xuICAgICAgICBhYnl0ZXMoZGF0YSk7XG4gICAgICAgIGNoZWNrT3V0cHV0KGNpcGhlci5lbmNyeXB0Lmxlbmd0aCwgb3V0cHV0KTtcbiAgICAgICAgcmV0dXJuIChjaXBoZXIgYXMgQ2lwaGVyV2l0aE91dHB1dCkuZW5jcnlwdChkYXRhLCBvdXRwdXQpO1xuICAgICAgfSxcbiAgICAgIGRlY3J5cHQoZGF0YTogVWludDhBcnJheSwgb3V0cHV0PzogVWludDhBcnJheSkge1xuICAgICAgICBhYnl0ZXMoZGF0YSk7XG4gICAgICAgIGlmICh0YWdsICYmIGRhdGEubGVuZ3RoIDwgdGFnbClcbiAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoJ1wiY2lwaGVydGV4dFwiIGV4cGVjdGVkIGxlbmd0aCBiaWdnZXIgdGhhbiB0YWdMZW5ndGg9JyArIHRhZ2wpO1xuICAgICAgICBjaGVja091dHB1dChjaXBoZXIuZGVjcnlwdC5sZW5ndGgsIG91dHB1dCk7XG4gICAgICAgIHJldHVybiAoY2lwaGVyIGFzIENpcGhlcldpdGhPdXRwdXQpLmRlY3J5cHQoZGF0YSwgb3V0cHV0KTtcbiAgICAgIH0sXG4gICAgfTtcblxuICAgIHJldHVybiB3ckNpcGhlcjtcbiAgfVxuXG4gIE9iamVjdC5hc3NpZ24od3JhcHBlZENpcGhlciwgcGFyYW1zKTtcbiAgcmV0dXJuIHdyYXBwZWRDaXBoZXIgYXMgQyAmIFA7XG59O1xuXG4vKiogUmVwcmVzZW50cyBzYWxzYSAvIGNoYWNoYSBzdHJlYW0uICovXG5leHBvcnQgdHlwZSBYb3JTdHJlYW0gPSAoXG4gIGtleTogVWludDhBcnJheSxcbiAgbm9uY2U6IFVpbnQ4QXJyYXksXG4gIGRhdGE6IFVpbnQ4QXJyYXksXG4gIG91dHB1dD86IFVpbnQ4QXJyYXksXG4gIGNvdW50ZXI/OiBudW1iZXJcbikgPT4gVWludDhBcnJheTtcblxuLyoqXG4gKiBCeSBkZWZhdWx0LCByZXR1cm5zIHU4YSBvZiBsZW5ndGguXG4gKiBXaGVuIG91dCBpcyBhdmFpbGFibGUsIGl0IGNoZWNrcyBpdCBmb3IgdmFsaWRpdHkgYW5kIHVzZXMgaXQuXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBnZXRPdXRwdXQoXG4gIGV4cGVjdGVkTGVuZ3RoOiBudW1iZXIsXG4gIG91dD86IFVpbnQ4QXJyYXksXG4gIG9ubHlBbGlnbmVkID0gdHJ1ZVxuKTogVWludDhBcnJheSB7XG4gIGlmIChvdXQgPT09IHVuZGVmaW5lZCkgcmV0dXJuIG5ldyBVaW50OEFycmF5KGV4cGVjdGVkTGVuZ3RoKTtcbiAgaWYgKG91dC5sZW5ndGggIT09IGV4cGVjdGVkTGVuZ3RoKVxuICAgIHRocm93IG5ldyBFcnJvcihcbiAgICAgICdcIm91dHB1dFwiIGV4cGVjdGVkIFVpbnQ4QXJyYXkgb2YgbGVuZ3RoICcgKyBleHBlY3RlZExlbmd0aCArICcsIGdvdDogJyArIG91dC5sZW5ndGhcbiAgICApO1xuICBpZiAob25seUFsaWduZWQgJiYgIWlzQWxpZ25lZDMyKG91dCkpIHRocm93IG5ldyBFcnJvcignaW52YWxpZCBvdXRwdXQsIG11c3QgYmUgYWxpZ25lZCcpO1xuICByZXR1cm4gb3V0O1xufVxuXG5leHBvcnQgZnVuY3Rpb24gdTY0TGVuZ3RocyhkYXRhTGVuZ3RoOiBudW1iZXIsIGFhZExlbmd0aDogbnVtYmVyLCBpc0xFOiBib29sZWFuKTogVWludDhBcnJheSB7XG4gIGFib29sKGlzTEUpO1xuICBjb25zdCBudW0gPSBuZXcgVWludDhBcnJheSgxNik7XG4gIGNvbnN0IHZpZXcgPSBjcmVhdGVWaWV3KG51bSk7XG4gIHZpZXcuc2V0QmlnVWludDY0KDAsIEJpZ0ludChhYWRMZW5ndGgpLCBpc0xFKTtcbiAgdmlldy5zZXRCaWdVaW50NjQoOCwgQmlnSW50KGRhdGFMZW5ndGgpLCBpc0xFKTtcbiAgcmV0dXJuIG51bTtcbn1cblxuLy8gSXMgYnl0ZSBhcnJheSBhbGlnbmVkIHRvIDQgYnl0ZSBvZmZzZXQgKHUzMik/XG5leHBvcnQgZnVuY3Rpb24gaXNBbGlnbmVkMzIoYnl0ZXM6IFVpbnQ4QXJyYXkpOiBib29sZWFuIHtcbiAgcmV0dXJuIGJ5dGVzLmJ5dGVPZmZzZXQgJSA0ID09PSAwO1xufVxuXG4vLyBjb3B5IGJ5dGVzIHRvIG5ldyB1OGEgKGFsaWduZWQpLiBCZWNhdXNlIEJ1ZmZlci5zbGljZSBpcyBicm9rZW4uXG5leHBvcnQgZnVuY3Rpb24gY29weUJ5dGVzKGJ5dGVzOiBVaW50OEFycmF5KTogVWludDhBcnJheSB7XG4gIHJldHVybiBVaW50OEFycmF5LmZyb20oYnl0ZXMpO1xufVxuXG4vKiogQ3J5cHRvZ3JhcGhpY2FsbHkgc2VjdXJlIFBSTkcuIFVzZXMgaW50ZXJuYWwgT1MtbGV2ZWwgYGNyeXB0by5nZXRSYW5kb21WYWx1ZXNgLiAqL1xuZXhwb3J0IGZ1bmN0aW9uIHJhbmRvbUJ5dGVzKGJ5dGVzTGVuZ3RoID0gMzIpOiBVaW50OEFycmF5IHtcbiAgY29uc3QgY3IgPSB0eXBlb2YgZ2xvYmFsVGhpcyA9PT0gJ29iamVjdCcgPyAoZ2xvYmFsVGhpcyBhcyBhbnkpLmNyeXB0byA6IG51bGw7XG4gIGlmICh0eXBlb2YgY3I/LmdldFJhbmRvbVZhbHVlcyAhPT0gJ2Z1bmN0aW9uJylcbiAgICB0aHJvdyBuZXcgRXJyb3IoJ2NyeXB0by5nZXRSYW5kb21WYWx1ZXMgbXVzdCBiZSBkZWZpbmVkJyk7XG4gIHJldHVybiBjci5nZXRSYW5kb21WYWx1ZXMobmV3IFVpbnQ4QXJyYXkoYnl0ZXNMZW5ndGgpKTtcbn1cblxuLyoqXG4gKiBUaGUgcHNldWRvcmFuZG9tIG51bWJlciBnZW5lcmF0b3IgZG9lc24ndCB3aXBlIGN1cnJlbnQgc3RhdGU6XG4gKiBpbnN0ZWFkLCBpdCBnZW5lcmF0ZXMgbmV3IG9uZSBiYXNlZCBvbiBwcmV2aW91cyBzdGF0ZSArIGVudHJvcHkuXG4gKiBOb3QgcmVzZWVkL3Jla2V5LCBzaW5jZSBBRVMgQ1RSIERSQkcgZG9lcyByZWtleSBvbiBlYWNoIHJhbmRvbUJ5dGVzLFxuICogd2hpY2ggaXMgaW4gZmFjdCBgcmVzZWVkYCwgc2luY2UgaXQgY2hhbmdlcyBjb3VudGVyIHRvby5cbiAqL1xuZXhwb3J0IGludGVyZmFjZSBQUkcge1xuICBhZGRFbnRyb3B5KHNlZWQ6IFVpbnQ4QXJyYXkpOiB2b2lkO1xuICByYW5kb21CeXRlcyhsZW5ndGg6IG51bWJlcik6IFVpbnQ4QXJyYXk7XG4gIGNsZWFuKCk6IHZvaWQ7XG59XG5cbnR5cGUgUmVtb3ZlTm9uY2VJbm5lcjxUIGV4dGVuZHMgYW55W10sIFJldD4gPSAoKC4uLmFyZ3M6IFQpID0+IFJldCkgZXh0ZW5kcyAoXG4gIGFyZzA6IGFueSxcbiAgYXJnMTogYW55LFxuICAuLi5yZXN0OiBpbmZlciBSXG4pID0+IGFueVxuICA/IChrZXk6IFVpbnQ4QXJyYXksIC4uLmFyZ3M6IFIpID0+IFJldFxuICA6IG5ldmVyO1xuXG5leHBvcnQgdHlwZSBSZW1vdmVOb25jZTxUIGV4dGVuZHMgKC4uLmFyZ3M6IGFueSkgPT4gYW55PiA9IFJlbW92ZU5vbmNlSW5uZXI8XG4gIFBhcmFtZXRlcnM8VD4sXG4gIFJldHVyblR5cGU8VD5cbj47XG5leHBvcnQgdHlwZSBDaXBoZXJXaXRoTm9uY2UgPSAoKFxuICBrZXk6IFVpbnQ4QXJyYXksXG4gIG5vbmNlOiBVaW50OEFycmF5LFxuICAuLi5hcmdzOiBhbnlbXVxuKSA9PiBDaXBoZXIgfCBBc3luY0NpcGhlcikgJiB7XG4gIG5vbmNlTGVuZ3RoOiBudW1iZXI7XG59O1xuXG4vKipcbiAqIFVzZXMgQ1NQUkcgZm9yIG5vbmNlLCBub25jZSBpbmplY3RlZCBpbiBjaXBoZXJ0ZXh0LlxuICogRm9yIGBlbmNyeXB0YCwgYSBgbm9uY2VCeXRlc2AtbGVuZ3RoIGJ1ZmZlciBpcyBmZXRjaGVkIGZyb20gQ1NQUk5HIGFuZFxuICogcHJlcGVuZGVkIHRvIGVuY3J5cHRlZCBjaXBoZXJ0ZXh0LiBGb3IgYGRlY3J5cHRgLCBmaXJzdCBgbm9uY2VCeXRlc2Agb2YgY2lwaGVydGV4dFxuICogYXJlIHRyZWF0ZWQgYXMgbm9uY2UuXG4gKlxuICogTk9URTogVW5kZXIgdGhlIHNhbWUga2V5LCB1c2luZyByYW5kb20gbm9uY2VzIChlLmcuIGBtYW5hZ2VkTm9uY2VgKSB3aXRoIEFFUy1HQ00gYW5kIENoYUNoYVxuICogc2hvdWxkIGJlIGxpbWl0ZWQgdG8gYDIqKjIzYCAoOE0pIG1lc3NhZ2VzIHRvIGdldCBhIGNvbGxpc2lvbiBjaGFuY2Ugb2YgYDIqKi01MGAuIFN0cmV0Y2hpbmcgdG8gICogYDIqKjMyYCAoNEIpIG1lc3NhZ2VzLCBjaGFuY2Ugd291bGQgYmVjb21lIGAyKiotMzNgIC0gc3RpbGwgbmVnbGlnaWJsZSwgYnV0IGNyZWVwaW5nIHVwLlxuICogQGV4YW1wbGVcbiAqIGNvbnN0IGdjbSA9IG1hbmFnZWROb25jZShhZXMuZ2NtKTtcbiAqIGNvbnN0IGNpcGhyID0gZ2NtKGtleSkuZW5jcnlwdChkYXRhKTtcbiAqIGNvbnN0IHBsYWluID0gZ2NtKGtleSkuZGVjcnlwdChjaXBoKTtcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIG1hbmFnZWROb25jZTxUIGV4dGVuZHMgQ2lwaGVyV2l0aE5vbmNlPihcbiAgZm46IFQsXG4gIHJhbmRvbUJ5dGVzXzogdHlwZW9mIHJhbmRvbUJ5dGVzID0gcmFuZG9tQnl0ZXNcbik6IFJlbW92ZU5vbmNlPFQ+IHtcbiAgY29uc3QgeyBub25jZUxlbmd0aCB9ID0gZm47XG4gIGFudW1iZXIobm9uY2VMZW5ndGgpO1xuICBjb25zdCBhZGROb25jZSA9IChub25jZTogVWludDhBcnJheSwgY2lwaGVydGV4dDogVWludDhBcnJheSkgPT4ge1xuICAgIGNvbnN0IG91dCA9IGNvbmNhdEJ5dGVzKG5vbmNlLCBjaXBoZXJ0ZXh0KTtcbiAgICBjaXBoZXJ0ZXh0LmZpbGwoMCk7XG4gICAgcmV0dXJuIG91dDtcbiAgfTtcbiAgLy8gTk9URTogd2UgY2Fubm90IHN1cHBvcnQgRFNUIGhlcmUsIGl0IHdvdWxkIGJlIG1pc3Rha2U6XG4gIC8vIC0gd2UgZG9uJ3Qga25vdyBob3cgbXVjaCBkc3QgbGVuZ3RoIGNpcGhlciByZXF1aXJlc1xuICAvLyAtIG5vbmNlIG1heSB1bmFsaWduIGRzdCBhbmQgYnJlYWsgZXZlcnl0aGluZ1xuICAvLyAtIHdlIGNyZWF0ZSBuZXcgdThhIGFueXdheSAoY29uY2F0Qnl0ZXMpXG4gIC8vIC0gcHJldmlvdXNseSB3ZSBwYXNzZWQgYWxsIGFyZ3MgdG8gY2lwaGVyLCBidXQgdGhhdCB3YXMgbWlzdGFrZSFcbiAgcmV0dXJuICgoa2V5OiBVaW50OEFycmF5LCAuLi5hcmdzOiBhbnlbXSk6IGFueSA9PiAoe1xuICAgIGVuY3J5cHQocGxhaW50ZXh0OiBVaW50OEFycmF5KSB7XG4gICAgICBhYnl0ZXMocGxhaW50ZXh0KTtcbiAgICAgIGNvbnN0IG5vbmNlID0gcmFuZG9tQnl0ZXNfKG5vbmNlTGVuZ3RoKTtcbiAgICAgIGNvbnN0IGVuY3J5cHRlZCA9IGZuKGtleSwgbm9uY2UsIC4uLmFyZ3MpLmVuY3J5cHQocGxhaW50ZXh0KTtcbiAgICAgIC8vIEB0cy1pZ25vcmVcbiAgICAgIGlmIChlbmNyeXB0ZWQgaW5zdGFuY2VvZiBQcm9taXNlKSByZXR1cm4gZW5jcnlwdGVkLnRoZW4oKGN0KSA9PiBhZGROb25jZShub25jZSwgY3QpKTtcbiAgICAgIHJldHVybiBhZGROb25jZShub25jZSwgZW5jcnlwdGVkKTtcbiAgICB9LFxuICAgIGRlY3J5cHQoY2lwaGVydGV4dDogVWludDhBcnJheSkge1xuICAgICAgYWJ5dGVzKGNpcGhlcnRleHQpO1xuICAgICAgY29uc3Qgbm9uY2UgPSBjaXBoZXJ0ZXh0LnN1YmFycmF5KDAsIG5vbmNlTGVuZ3RoKTtcbiAgICAgIGNvbnN0IGRlY3J5cHRlZCA9IGNpcGhlcnRleHQuc3ViYXJyYXkobm9uY2VMZW5ndGgpO1xuICAgICAgcmV0dXJuIGZuKGtleSwgbm9uY2UsIC4uLmFyZ3MpLmRlY3J5cHQoZGVjcnlwdGVkKTtcbiAgICB9LFxuICB9KSkgYXMgUmVtb3ZlTm9uY2U8VD47XG59XG5cbi8vIHdvcmthcm91bmQgZm9yIFRTIDUuOSBsYW5ndWFnZSBtZXNzOlxuZXhwb3J0IHR5cGUgVWludDhBcnJheUJ1ZmZlciA9IFJldHVyblR5cGU8dHlwZW9mIFVpbnQ4QXJyYXkub2Y+O1xuIiwgIi8qKlxuICogUG9seTEzMDUgKFtQREZdKGh0dHBzOi8vY3IueXAudG8vbWFjL3BvbHkxMzA1LTIwMDUwMzI5LnBkZiksXG4gKiBbd2lraV0oaHR0cHM6Ly9lbi53aWtpcGVkaWEub3JnL3dpa2kvUG9seTEzMDUpKVxuICogaXMgYSBmYXN0IGFuZCBwYXJhbGxlbCBzZWNyZXQta2V5IG1lc3NhZ2UtYXV0aGVudGljYXRpb24gY29kZSBzdWl0YWJsZSBmb3JcbiAqIGEgd2lkZSB2YXJpZXR5IG9mIGFwcGxpY2F0aW9ucy4gSXQgd2FzIHN0YW5kYXJkaXplZCBpblxuICogW1JGQyA4NDM5XShodHRwczovL3d3dy5yZmMtZWRpdG9yLm9yZy9yZmMvcmZjODQzOSkgYW5kIGlzIG5vdyB1c2VkIGluIFRMUyAxLjMuXG4gKlxuICogUG9seW5vbWlhbCBNQUNzIGFyZSBub3QgcGVyZmVjdCBmb3IgZXZlcnkgc2l0dWF0aW9uOlxuICogdGhleSBsYWNrIFJhbmRvbSBLZXkgUm9idXN0bmVzczogdGhlIE1BQyBjYW4gYmUgZm9yZ2VkLCBhbmQgY2FuJ3QgYmUgdXNlZCBpbiBQQUtFIHNjaGVtZXMuXG4gKiBTZWUgW2ludmlzaWJsZSBzYWxhbWFuZGVycyBhdHRhY2tdKGh0dHBzOi8va2V5bWF0ZXJpYWwubmV0LzIwMjAvMDkvMDcvaW52aXNpYmxlLXNhbGFtYW5kZXJzLWluLWFlcy1nY20tc2l2LykuXG4gKiBUbyBjb21iYXQgaW52aXNpYmxlIHNhbGFtYW5kZXJzLCBgaGFzaChrZXkpYCBjYW4gYmUgaW5jbHVkZWQgaW4gY2lwaGVydGV4dCxcbiAqIGhvd2V2ZXIsIHRoaXMgd291bGQgdmlvbGF0ZSBjaXBoZXJ0ZXh0IGluZGlzdGluZ3Vpc2hhYmlsaXR5OlxuICogYW4gYXR0YWNrZXIgd291bGQga25vdyB3aGljaCBrZXkgd2FzIHVzZWQgLSBzbyBgSEtERihrZXksIGkpYFxuICogY291bGQgYmUgdXNlZCBpbnN0ZWFkLlxuICpcbiAqIENoZWNrIG91dCBbb3JpZ2luYWwgd2Vic2l0ZV0oaHR0cHM6Ly9jci55cC50by9tYWMuaHRtbCkuXG4gKiBCYXNlZCBvbiBQdWJsaWMgRG9tYWluIFtwb2x5MTMwNS1kb25uYV0oaHR0cHM6Ly9naXRodWIuY29tL2Zsb29keWJlcnJ5L3BvbHkxMzA1LWRvbm5hKS5cbiAqIEBtb2R1bGVcbiAqL1xuLy8gcHJldHRpZXItaWdub3JlXG5pbXBvcnQge1xuICBhYnl0ZXMsIGFleGlzdHMsIGFvdXRwdXQsIGJ5dGVzVG9IZXgsXG4gIGNsZWFuLCBjb25jYXRCeXRlcywgY29weUJ5dGVzLCBoZXhUb051bWJlciwgbnVtYmVyVG9CeXRlc0JFLFxuICB0eXBlIElIYXNoMlxufSBmcm9tICcuL3V0aWxzLnRzJztcblxuZnVuY3Rpb24gdTh0bzE2KGE6IFVpbnQ4QXJyYXksIGk6IG51bWJlcikge1xuICByZXR1cm4gKGFbaSsrXSAmIDB4ZmYpIHwgKChhW2krK10gJiAweGZmKSA8PCA4KTtcbn1cblxuZnVuY3Rpb24gYnl0ZXNUb051bWJlckxFKGJ5dGVzOiBVaW50OEFycmF5KTogYmlnaW50IHtcbiAgcmV0dXJuIGhleFRvTnVtYmVyKGJ5dGVzVG9IZXgoVWludDhBcnJheS5mcm9tKGJ5dGVzKS5yZXZlcnNlKCkpKTtcbn1cblxuLyoqIFNtYWxsIHZlcnNpb24gb2YgYHBvbHkxMzA1YCB3aXRob3V0IGxvb3AgdW5yb2xsaW5nLiBVbnVzZWQsIHByb3ZpZGVkIGZvciBhdWRpdGFiaWxpdHkuICovXG5mdW5jdGlvbiBwb2x5MTMwNV9zbWFsbChtc2c6IFVpbnQ4QXJyYXksIGtleTogVWludDhBcnJheSk6IFVpbnQ4QXJyYXkge1xuICBhYnl0ZXMobXNnKTtcbiAgYWJ5dGVzKGtleSwgMzIsICdrZXknKTtcbiAgY29uc3QgUE9XXzJfMTMwXzUgPSBCaWdJbnQoMikgKiogQmlnSW50KDEzMCkgLSBCaWdJbnQoNSk7IC8vIDJeMTMwLTVcbiAgY29uc3QgUE9XXzJfMTI4XzEgPSBCaWdJbnQoMikgKiogQmlnSW50KDEyOCkgLSBCaWdJbnQoMSk7IC8vIDJeMTI4LTFcbiAgY29uc3QgQ0xBTVBfUiA9IEJpZ0ludCgnMHgwZmZmZmZmYzBmZmZmZmZjMGZmZmZmZmMwZmZmZmZmZicpO1xuICBjb25zdCByID0gYnl0ZXNUb051bWJlckxFKGtleS5zdWJhcnJheSgwLCAxNikpICYgQ0xBTVBfUjtcbiAgY29uc3QgcyA9IGJ5dGVzVG9OdW1iZXJMRShrZXkuc3ViYXJyYXkoMTYpKTtcbiAgLy8gUHJvY2VzcyBieSAxNiBieXRlIGNodW5rc1xuICBsZXQgYWNjID0gQmlnSW50KDApO1xuICBmb3IgKGxldCBpID0gMDsgaSA8IG1zZy5sZW5ndGg7IGkgKz0gMTYpIHtcbiAgICBjb25zdCBtID0gbXNnLnN1YmFycmF5KGksIGkgKyAxNik7XG4gICAgY29uc3QgbiA9IGJ5dGVzVG9OdW1iZXJMRShtKSB8IChCaWdJbnQoMSkgPDwgQmlnSW50KDggKiBtLmxlbmd0aCkpO1xuICAgIGFjYyA9ICgoYWNjICsgbikgKiByKSAlIFBPV18yXzEzMF81O1xuICB9XG4gIGNvbnN0IHJlcyA9IChhY2MgKyBzKSAmIFBPV18yXzEyOF8xO1xuICByZXR1cm4gbnVtYmVyVG9CeXRlc0JFKHJlcywgMTYpLnJldmVyc2UoKTsgLy8gTEVcbn1cblxuLy8gQ2FuIGJlIHVzZWQgdG8gcmVwbGFjZSBgY29tcHV0ZVRhZ2AgaW4gY2hhY2hhLnRzLiBVbnVzZWQsIHByb3ZpZGVkIGZvciBhdWRpdGFiaWxpdHkuXG4vLyBAdHMtZXhwZWN0LWVycm9yXG5mdW5jdGlvbiBwb2x5MTMwNV9jb21wdXRlVGFnX3NtYWxsKFxuICBhdXRoS2V5OiBVaW50OEFycmF5LFxuICBsZW5ndGhzOiBVaW50OEFycmF5LFxuICBjaXBoZXJ0ZXh0OiBVaW50OEFycmF5LFxuICBBQUQ/OiBVaW50OEFycmF5XG4pOiBVaW50OEFycmF5IHtcbiAgY29uc3QgcmVzID0gW107XG4gIGNvbnN0IHVwZGF0ZVBhZGRlZDIgPSAobXNnOiBVaW50OEFycmF5KSA9PiB7XG4gICAgcmVzLnB1c2gobXNnKTtcbiAgICBjb25zdCBsZWZ0b3ZlciA9IG1zZy5sZW5ndGggJSAxNjtcbiAgICBpZiAobGVmdG92ZXIpIHJlcy5wdXNoKG5ldyBVaW50OEFycmF5KDE2KS5zbGljZShsZWZ0b3ZlcikpO1xuICB9O1xuICBpZiAoQUFEKSB1cGRhdGVQYWRkZWQyKEFBRCk7XG4gIHVwZGF0ZVBhZGRlZDIoY2lwaGVydGV4dCk7XG4gIHJlcy5wdXNoKGxlbmd0aHMpO1xuICByZXR1cm4gcG9seTEzMDVfc21hbGwoY29uY2F0Qnl0ZXMoLi4ucmVzKSwgYXV0aEtleSk7XG59XG5cbi8qKiBQb2x5MTMwNSBjbGFzcy4gUHJlZmVyIHBvbHkxMzA1KCkgZnVuY3Rpb24gaW5zdGVhZC4gKi9cbmV4cG9ydCBjbGFzcyBQb2x5MTMwNSBpbXBsZW1lbnRzIElIYXNoMiB7XG4gIHJlYWRvbmx5IGJsb2NrTGVuID0gMTY7XG4gIHJlYWRvbmx5IG91dHB1dExlbiA9IDE2O1xuICBwcml2YXRlIGJ1ZmZlciA9IG5ldyBVaW50OEFycmF5KDE2KTtcbiAgcHJpdmF0ZSByID0gbmV3IFVpbnQxNkFycmF5KDEwKTsgLy8gQWxsb2NhdGluZyAxIGFycmF5IHdpdGggLnN1YmFycmF5KCkgaGVyZSBpcyBzbG93ZXIgdGhhbiAzXG4gIHByaXZhdGUgaCA9IG5ldyBVaW50MTZBcnJheSgxMCk7XG4gIHByaXZhdGUgcGFkID0gbmV3IFVpbnQxNkFycmF5KDgpO1xuICBwcml2YXRlIHBvcyA9IDA7XG4gIHByb3RlY3RlZCBmaW5pc2hlZCA9IGZhbHNlO1xuXG4gIC8vIENhbiBiZSBzcGVlZC11cCB1c2luZyBCaWdVaW50NjRBcnJheSwgYXQgdGhlIGNvc3Qgb2YgY29tcGxleGl0eVxuICBjb25zdHJ1Y3RvcihrZXk6IFVpbnQ4QXJyYXkpIHtcbiAgICBrZXkgPSBjb3B5Qnl0ZXMoYWJ5dGVzKGtleSwgMzIsICdrZXknKSk7XG4gICAgY29uc3QgdDAgPSB1OHRvMTYoa2V5LCAwKTtcbiAgICBjb25zdCB0MSA9IHU4dG8xNihrZXksIDIpO1xuICAgIGNvbnN0IHQyID0gdTh0bzE2KGtleSwgNCk7XG4gICAgY29uc3QgdDMgPSB1OHRvMTYoa2V5LCA2KTtcbiAgICBjb25zdCB0NCA9IHU4dG8xNihrZXksIDgpO1xuICAgIGNvbnN0IHQ1ID0gdTh0bzE2KGtleSwgMTApO1xuICAgIGNvbnN0IHQ2ID0gdTh0bzE2KGtleSwgMTIpO1xuICAgIGNvbnN0IHQ3ID0gdTh0bzE2KGtleSwgMTQpO1xuXG4gICAgLy8gaHR0cHM6Ly9naXRodWIuY29tL2Zsb29keWJlcnJ5L3BvbHkxMzA1LWRvbm5hL2Jsb2IvZTZhZDZlMDkxZDMwZDdmNGVjMmQ0Zjk3OGJlMWZjZmNiY2U3Mjc4MS9wb2x5MTMwNS1kb25uYS0xNi5oI0w0N1xuICAgIHRoaXMuclswXSA9IHQwICYgMHgxZmZmO1xuICAgIHRoaXMuclsxXSA9ICgodDAgPj4+IDEzKSB8ICh0MSA8PCAzKSkgJiAweDFmZmY7XG4gICAgdGhpcy5yWzJdID0gKCh0MSA+Pj4gMTApIHwgKHQyIDw8IDYpKSAmIDB4MWYwMztcbiAgICB0aGlzLnJbM10gPSAoKHQyID4+PiA3KSB8ICh0MyA8PCA5KSkgJiAweDFmZmY7XG4gICAgdGhpcy5yWzRdID0gKCh0MyA+Pj4gNCkgfCAodDQgPDwgMTIpKSAmIDB4MDBmZjtcbiAgICB0aGlzLnJbNV0gPSAodDQgPj4+IDEpICYgMHgxZmZlO1xuICAgIHRoaXMucls2XSA9ICgodDQgPj4+IDE0KSB8ICh0NSA8PCAyKSkgJiAweDFmZmY7XG4gICAgdGhpcy5yWzddID0gKCh0NSA+Pj4gMTEpIHwgKHQ2IDw8IDUpKSAmIDB4MWY4MTtcbiAgICB0aGlzLnJbOF0gPSAoKHQ2ID4+PiA4KSB8ICh0NyA8PCA4KSkgJiAweDFmZmY7XG4gICAgdGhpcy5yWzldID0gKHQ3ID4+PiA1KSAmIDB4MDA3ZjtcbiAgICBmb3IgKGxldCBpID0gMDsgaSA8IDg7IGkrKykgdGhpcy5wYWRbaV0gPSB1OHRvMTYoa2V5LCAxNiArIDIgKiBpKTtcbiAgfVxuXG4gIHByaXZhdGUgcHJvY2VzcyhkYXRhOiBVaW50OEFycmF5LCBvZmZzZXQ6IG51bWJlciwgaXNMYXN0ID0gZmFsc2UpIHtcbiAgICBjb25zdCBoaWJpdCA9IGlzTGFzdCA/IDAgOiAxIDw8IDExO1xuICAgIGNvbnN0IHsgaCwgciB9ID0gdGhpcztcbiAgICBjb25zdCByMCA9IHJbMF07XG4gICAgY29uc3QgcjEgPSByWzFdO1xuICAgIGNvbnN0IHIyID0gclsyXTtcbiAgICBjb25zdCByMyA9IHJbM107XG4gICAgY29uc3QgcjQgPSByWzRdO1xuICAgIGNvbnN0IHI1ID0gcls1XTtcbiAgICBjb25zdCByNiA9IHJbNl07XG4gICAgY29uc3QgcjcgPSByWzddO1xuICAgIGNvbnN0IHI4ID0gcls4XTtcbiAgICBjb25zdCByOSA9IHJbOV07XG5cbiAgICBjb25zdCB0MCA9IHU4dG8xNihkYXRhLCBvZmZzZXQgKyAwKTtcbiAgICBjb25zdCB0MSA9IHU4dG8xNihkYXRhLCBvZmZzZXQgKyAyKTtcbiAgICBjb25zdCB0MiA9IHU4dG8xNihkYXRhLCBvZmZzZXQgKyA0KTtcbiAgICBjb25zdCB0MyA9IHU4dG8xNihkYXRhLCBvZmZzZXQgKyA2KTtcbiAgICBjb25zdCB0NCA9IHU4dG8xNihkYXRhLCBvZmZzZXQgKyA4KTtcbiAgICBjb25zdCB0NSA9IHU4dG8xNihkYXRhLCBvZmZzZXQgKyAxMCk7XG4gICAgY29uc3QgdDYgPSB1OHRvMTYoZGF0YSwgb2Zmc2V0ICsgMTIpO1xuICAgIGNvbnN0IHQ3ID0gdTh0bzE2KGRhdGEsIG9mZnNldCArIDE0KTtcblxuICAgIGxldCBoMCA9IGhbMF0gKyAodDAgJiAweDFmZmYpO1xuICAgIGxldCBoMSA9IGhbMV0gKyAoKCh0MCA+Pj4gMTMpIHwgKHQxIDw8IDMpKSAmIDB4MWZmZik7XG4gICAgbGV0IGgyID0gaFsyXSArICgoKHQxID4+PiAxMCkgfCAodDIgPDwgNikpICYgMHgxZmZmKTtcbiAgICBsZXQgaDMgPSBoWzNdICsgKCgodDIgPj4+IDcpIHwgKHQzIDw8IDkpKSAmIDB4MWZmZik7XG4gICAgbGV0IGg0ID0gaFs0XSArICgoKHQzID4+PiA0KSB8ICh0NCA8PCAxMikpICYgMHgxZmZmKTtcbiAgICBsZXQgaDUgPSBoWzVdICsgKCh0NCA+Pj4gMSkgJiAweDFmZmYpO1xuICAgIGxldCBoNiA9IGhbNl0gKyAoKCh0NCA+Pj4gMTQpIHwgKHQ1IDw8IDIpKSAmIDB4MWZmZik7XG4gICAgbGV0IGg3ID0gaFs3XSArICgoKHQ1ID4+PiAxMSkgfCAodDYgPDwgNSkpICYgMHgxZmZmKTtcbiAgICBsZXQgaDggPSBoWzhdICsgKCgodDYgPj4+IDgpIHwgKHQ3IDw8IDgpKSAmIDB4MWZmZik7XG4gICAgbGV0IGg5ID0gaFs5XSArICgodDcgPj4+IDUpIHwgaGliaXQpO1xuXG4gICAgbGV0IGMgPSAwO1xuXG4gICAgbGV0IGQwID0gYyArIGgwICogcjAgKyBoMSAqICg1ICogcjkpICsgaDIgKiAoNSAqIHI4KSArIGgzICogKDUgKiByNykgKyBoNCAqICg1ICogcjYpO1xuICAgIGMgPSBkMCA+Pj4gMTM7XG4gICAgZDAgJj0gMHgxZmZmO1xuICAgIGQwICs9IGg1ICogKDUgKiByNSkgKyBoNiAqICg1ICogcjQpICsgaDcgKiAoNSAqIHIzKSArIGg4ICogKDUgKiByMikgKyBoOSAqICg1ICogcjEpO1xuICAgIGMgKz0gZDAgPj4+IDEzO1xuICAgIGQwICY9IDB4MWZmZjtcblxuICAgIGxldCBkMSA9IGMgKyBoMCAqIHIxICsgaDEgKiByMCArIGgyICogKDUgKiByOSkgKyBoMyAqICg1ICogcjgpICsgaDQgKiAoNSAqIHI3KTtcbiAgICBjID0gZDEgPj4+IDEzO1xuICAgIGQxICY9IDB4MWZmZjtcbiAgICBkMSArPSBoNSAqICg1ICogcjYpICsgaDYgKiAoNSAqIHI1KSArIGg3ICogKDUgKiByNCkgKyBoOCAqICg1ICogcjMpICsgaDkgKiAoNSAqIHIyKTtcbiAgICBjICs9IGQxID4+PiAxMztcbiAgICBkMSAmPSAweDFmZmY7XG5cbiAgICBsZXQgZDIgPSBjICsgaDAgKiByMiArIGgxICogcjEgKyBoMiAqIHIwICsgaDMgKiAoNSAqIHI5KSArIGg0ICogKDUgKiByOCk7XG4gICAgYyA9IGQyID4+PiAxMztcbiAgICBkMiAmPSAweDFmZmY7XG4gICAgZDIgKz0gaDUgKiAoNSAqIHI3KSArIGg2ICogKDUgKiByNikgKyBoNyAqICg1ICogcjUpICsgaDggKiAoNSAqIHI0KSArIGg5ICogKDUgKiByMyk7XG4gICAgYyArPSBkMiA+Pj4gMTM7XG4gICAgZDIgJj0gMHgxZmZmO1xuXG4gICAgbGV0IGQzID0gYyArIGgwICogcjMgKyBoMSAqIHIyICsgaDIgKiByMSArIGgzICogcjAgKyBoNCAqICg1ICogcjkpO1xuICAgIGMgPSBkMyA+Pj4gMTM7XG4gICAgZDMgJj0gMHgxZmZmO1xuICAgIGQzICs9IGg1ICogKDUgKiByOCkgKyBoNiAqICg1ICogcjcpICsgaDcgKiAoNSAqIHI2KSArIGg4ICogKDUgKiByNSkgKyBoOSAqICg1ICogcjQpO1xuICAgIGMgKz0gZDMgPj4+IDEzO1xuICAgIGQzICY9IDB4MWZmZjtcblxuICAgIGxldCBkNCA9IGMgKyBoMCAqIHI0ICsgaDEgKiByMyArIGgyICogcjIgKyBoMyAqIHIxICsgaDQgKiByMDtcbiAgICBjID0gZDQgPj4+IDEzO1xuICAgIGQ0ICY9IDB4MWZmZjtcbiAgICBkNCArPSBoNSAqICg1ICogcjkpICsgaDYgKiAoNSAqIHI4KSArIGg3ICogKDUgKiByNykgKyBoOCAqICg1ICogcjYpICsgaDkgKiAoNSAqIHI1KTtcbiAgICBjICs9IGQ0ID4+PiAxMztcbiAgICBkNCAmPSAweDFmZmY7XG5cbiAgICBsZXQgZDUgPSBjICsgaDAgKiByNSArIGgxICogcjQgKyBoMiAqIHIzICsgaDMgKiByMiArIGg0ICogcjE7XG4gICAgYyA9IGQ1ID4+PiAxMztcbiAgICBkNSAmPSAweDFmZmY7XG4gICAgZDUgKz0gaDUgKiByMCArIGg2ICogKDUgKiByOSkgKyBoNyAqICg1ICogcjgpICsgaDggKiAoNSAqIHI3KSArIGg5ICogKDUgKiByNik7XG4gICAgYyArPSBkNSA+Pj4gMTM7XG4gICAgZDUgJj0gMHgxZmZmO1xuXG4gICAgbGV0IGQ2ID0gYyArIGgwICogcjYgKyBoMSAqIHI1ICsgaDIgKiByNCArIGgzICogcjMgKyBoNCAqIHIyO1xuICAgIGMgPSBkNiA+Pj4gMTM7XG4gICAgZDYgJj0gMHgxZmZmO1xuICAgIGQ2ICs9IGg1ICogcjEgKyBoNiAqIHIwICsgaDcgKiAoNSAqIHI5KSArIGg4ICogKDUgKiByOCkgKyBoOSAqICg1ICogcjcpO1xuICAgIGMgKz0gZDYgPj4+IDEzO1xuICAgIGQ2ICY9IDB4MWZmZjtcblxuICAgIGxldCBkNyA9IGMgKyBoMCAqIHI3ICsgaDEgKiByNiArIGgyICogcjUgKyBoMyAqIHI0ICsgaDQgKiByMztcbiAgICBjID0gZDcgPj4+IDEzO1xuICAgIGQ3ICY9IDB4MWZmZjtcbiAgICBkNyArPSBoNSAqIHIyICsgaDYgKiByMSArIGg3ICogcjAgKyBoOCAqICg1ICogcjkpICsgaDkgKiAoNSAqIHI4KTtcbiAgICBjICs9IGQ3ID4+PiAxMztcbiAgICBkNyAmPSAweDFmZmY7XG5cbiAgICBsZXQgZDggPSBjICsgaDAgKiByOCArIGgxICogcjcgKyBoMiAqIHI2ICsgaDMgKiByNSArIGg0ICogcjQ7XG4gICAgYyA9IGQ4ID4+PiAxMztcbiAgICBkOCAmPSAweDFmZmY7XG4gICAgZDggKz0gaDUgKiByMyArIGg2ICogcjIgKyBoNyAqIHIxICsgaDggKiByMCArIGg5ICogKDUgKiByOSk7XG4gICAgYyArPSBkOCA+Pj4gMTM7XG4gICAgZDggJj0gMHgxZmZmO1xuXG4gICAgbGV0IGQ5ID0gYyArIGgwICogcjkgKyBoMSAqIHI4ICsgaDIgKiByNyArIGgzICogcjYgKyBoNCAqIHI1O1xuICAgIGMgPSBkOSA+Pj4gMTM7XG4gICAgZDkgJj0gMHgxZmZmO1xuICAgIGQ5ICs9IGg1ICogcjQgKyBoNiAqIHIzICsgaDcgKiByMiArIGg4ICogcjEgKyBoOSAqIHIwO1xuICAgIGMgKz0gZDkgPj4+IDEzO1xuICAgIGQ5ICY9IDB4MWZmZjtcblxuICAgIGMgPSAoKGMgPDwgMikgKyBjKSB8IDA7XG4gICAgYyA9IChjICsgZDApIHwgMDtcbiAgICBkMCA9IGMgJiAweDFmZmY7XG4gICAgYyA9IGMgPj4+IDEzO1xuICAgIGQxICs9IGM7XG5cbiAgICBoWzBdID0gZDA7XG4gICAgaFsxXSA9IGQxO1xuICAgIGhbMl0gPSBkMjtcbiAgICBoWzNdID0gZDM7XG4gICAgaFs0XSA9IGQ0O1xuICAgIGhbNV0gPSBkNTtcbiAgICBoWzZdID0gZDY7XG4gICAgaFs3XSA9IGQ3O1xuICAgIGhbOF0gPSBkODtcbiAgICBoWzldID0gZDk7XG4gIH1cblxuICBwcml2YXRlIGZpbmFsaXplKCkge1xuICAgIGNvbnN0IHsgaCwgcGFkIH0gPSB0aGlzO1xuICAgIGNvbnN0IGcgPSBuZXcgVWludDE2QXJyYXkoMTApO1xuICAgIGxldCBjID0gaFsxXSA+Pj4gMTM7XG4gICAgaFsxXSAmPSAweDFmZmY7XG4gICAgZm9yIChsZXQgaSA9IDI7IGkgPCAxMDsgaSsrKSB7XG4gICAgICBoW2ldICs9IGM7XG4gICAgICBjID0gaFtpXSA+Pj4gMTM7XG4gICAgICBoW2ldICY9IDB4MWZmZjtcbiAgICB9XG4gICAgaFswXSArPSBjICogNTtcbiAgICBjID0gaFswXSA+Pj4gMTM7XG4gICAgaFswXSAmPSAweDFmZmY7XG4gICAgaFsxXSArPSBjO1xuICAgIGMgPSBoWzFdID4+PiAxMztcbiAgICBoWzFdICY9IDB4MWZmZjtcbiAgICBoWzJdICs9IGM7XG5cbiAgICBnWzBdID0gaFswXSArIDU7XG4gICAgYyA9IGdbMF0gPj4+IDEzO1xuICAgIGdbMF0gJj0gMHgxZmZmO1xuICAgIGZvciAobGV0IGkgPSAxOyBpIDwgMTA7IGkrKykge1xuICAgICAgZ1tpXSA9IGhbaV0gKyBjO1xuICAgICAgYyA9IGdbaV0gPj4+IDEzO1xuICAgICAgZ1tpXSAmPSAweDFmZmY7XG4gICAgfVxuICAgIGdbOV0gLT0gMSA8PCAxMztcblxuICAgIGxldCBtYXNrID0gKGMgXiAxKSAtIDE7XG4gICAgZm9yIChsZXQgaSA9IDA7IGkgPCAxMDsgaSsrKSBnW2ldICY9IG1hc2s7XG4gICAgbWFzayA9IH5tYXNrO1xuICAgIGZvciAobGV0IGkgPSAwOyBpIDwgMTA7IGkrKykgaFtpXSA9IChoW2ldICYgbWFzaykgfCBnW2ldO1xuICAgIGhbMF0gPSAoaFswXSB8IChoWzFdIDw8IDEzKSkgJiAweGZmZmY7XG4gICAgaFsxXSA9ICgoaFsxXSA+Pj4gMykgfCAoaFsyXSA8PCAxMCkpICYgMHhmZmZmO1xuICAgIGhbMl0gPSAoKGhbMl0gPj4+IDYpIHwgKGhbM10gPDwgNykpICYgMHhmZmZmO1xuICAgIGhbM10gPSAoKGhbM10gPj4+IDkpIHwgKGhbNF0gPDwgNCkpICYgMHhmZmZmO1xuICAgIGhbNF0gPSAoKGhbNF0gPj4+IDEyKSB8IChoWzVdIDw8IDEpIHwgKGhbNl0gPDwgMTQpKSAmIDB4ZmZmZjtcbiAgICBoWzVdID0gKChoWzZdID4+PiAyKSB8IChoWzddIDw8IDExKSkgJiAweGZmZmY7XG4gICAgaFs2XSA9ICgoaFs3XSA+Pj4gNSkgfCAoaFs4XSA8PCA4KSkgJiAweGZmZmY7XG4gICAgaFs3XSA9ICgoaFs4XSA+Pj4gOCkgfCAoaFs5XSA8PCA1KSkgJiAweGZmZmY7XG5cbiAgICBsZXQgZiA9IGhbMF0gKyBwYWRbMF07XG4gICAgaFswXSA9IGYgJiAweGZmZmY7XG4gICAgZm9yIChsZXQgaSA9IDE7IGkgPCA4OyBpKyspIHtcbiAgICAgIGYgPSAoKChoW2ldICsgcGFkW2ldKSB8IDApICsgKGYgPj4+IDE2KSkgfCAwO1xuICAgICAgaFtpXSA9IGYgJiAweGZmZmY7XG4gICAgfVxuICAgIGNsZWFuKGcpO1xuICB9XG4gIHVwZGF0ZShkYXRhOiBVaW50OEFycmF5KTogdGhpcyB7XG4gICAgYWV4aXN0cyh0aGlzKTtcbiAgICBhYnl0ZXMoZGF0YSk7XG4gICAgZGF0YSA9IGNvcHlCeXRlcyhkYXRhKTtcbiAgICBjb25zdCB7IGJ1ZmZlciwgYmxvY2tMZW4gfSA9IHRoaXM7XG4gICAgY29uc3QgbGVuID0gZGF0YS5sZW5ndGg7XG5cbiAgICBmb3IgKGxldCBwb3MgPSAwOyBwb3MgPCBsZW47ICkge1xuICAgICAgY29uc3QgdGFrZSA9IE1hdGgubWluKGJsb2NrTGVuIC0gdGhpcy5wb3MsIGxlbiAtIHBvcyk7XG4gICAgICAvLyBGYXN0IHBhdGg6IHdlIGhhdmUgYXQgbGVhc3Qgb25lIGJsb2NrIGluIGlucHV0XG4gICAgICBpZiAodGFrZSA9PT0gYmxvY2tMZW4pIHtcbiAgICAgICAgZm9yICg7IGJsb2NrTGVuIDw9IGxlbiAtIHBvczsgcG9zICs9IGJsb2NrTGVuKSB0aGlzLnByb2Nlc3MoZGF0YSwgcG9zKTtcbiAgICAgICAgY29udGludWU7XG4gICAgICB9XG4gICAgICBidWZmZXIuc2V0KGRhdGEuc3ViYXJyYXkocG9zLCBwb3MgKyB0YWtlKSwgdGhpcy5wb3MpO1xuICAgICAgdGhpcy5wb3MgKz0gdGFrZTtcbiAgICAgIHBvcyArPSB0YWtlO1xuICAgICAgaWYgKHRoaXMucG9zID09PSBibG9ja0xlbikge1xuICAgICAgICB0aGlzLnByb2Nlc3MoYnVmZmVyLCAwLCBmYWxzZSk7XG4gICAgICAgIHRoaXMucG9zID0gMDtcbiAgICAgIH1cbiAgICB9XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cbiAgZGVzdHJveSgpOiB2b2lkIHtcbiAgICBjbGVhbih0aGlzLmgsIHRoaXMuciwgdGhpcy5idWZmZXIsIHRoaXMucGFkKTtcbiAgfVxuICBkaWdlc3RJbnRvKG91dDogVWludDhBcnJheSk6IFVpbnQ4QXJyYXkge1xuICAgIGFleGlzdHModGhpcyk7XG4gICAgYW91dHB1dChvdXQsIHRoaXMpO1xuICAgIHRoaXMuZmluaXNoZWQgPSB0cnVlO1xuICAgIGNvbnN0IHsgYnVmZmVyLCBoIH0gPSB0aGlzO1xuICAgIGxldCB7IHBvcyB9ID0gdGhpcztcbiAgICBpZiAocG9zKSB7XG4gICAgICBidWZmZXJbcG9zKytdID0gMTtcbiAgICAgIGZvciAoOyBwb3MgPCAxNjsgcG9zKyspIGJ1ZmZlcltwb3NdID0gMDtcbiAgICAgIHRoaXMucHJvY2VzcyhidWZmZXIsIDAsIHRydWUpO1xuICAgIH1cbiAgICB0aGlzLmZpbmFsaXplKCk7XG4gICAgbGV0IG9wb3MgPSAwO1xuICAgIGZvciAobGV0IGkgPSAwOyBpIDwgODsgaSsrKSB7XG4gICAgICBvdXRbb3BvcysrXSA9IGhbaV0gPj4+IDA7XG4gICAgICBvdXRbb3BvcysrXSA9IGhbaV0gPj4+IDg7XG4gICAgfVxuICAgIHJldHVybiBvdXQ7XG4gIH1cbiAgZGlnZXN0KCk6IFVpbnQ4QXJyYXkge1xuICAgIGNvbnN0IHsgYnVmZmVyLCBvdXRwdXRMZW4gfSA9IHRoaXM7XG4gICAgdGhpcy5kaWdlc3RJbnRvKGJ1ZmZlcik7XG4gICAgY29uc3QgcmVzID0gYnVmZmVyLnNsaWNlKDAsIG91dHB1dExlbik7XG4gICAgdGhpcy5kZXN0cm95KCk7XG4gICAgcmV0dXJuIHJlcztcbiAgfVxufVxuXG5leHBvcnQgdHlwZSBDSGFzaCA9IFJldHVyblR5cGU8dHlwZW9mIHdyYXBDb25zdHJ1Y3RvcldpdGhLZXk+O1xuZXhwb3J0IGZ1bmN0aW9uIHdyYXBDb25zdHJ1Y3RvcldpdGhLZXk8SCBleHRlbmRzIElIYXNoMj4oXG4gIGhhc2hDb25zOiAoa2V5OiBVaW50OEFycmF5KSA9PiBIXG4pOiB7XG4gIChtc2c6IFVpbnQ4QXJyYXksIGtleTogVWludDhBcnJheSk6IFVpbnQ4QXJyYXk7XG4gIG91dHB1dExlbjogbnVtYmVyO1xuICBibG9ja0xlbjogbnVtYmVyO1xuICBjcmVhdGUoa2V5OiBVaW50OEFycmF5KTogSDtcbn0ge1xuICBjb25zdCBoYXNoQyA9IChtc2c6IFVpbnQ4QXJyYXksIGtleTogVWludDhBcnJheSk6IFVpbnQ4QXJyYXkgPT5cbiAgICBoYXNoQ29ucyhrZXkpLnVwZGF0ZShtc2cpLmRpZ2VzdCgpO1xuICBjb25zdCB0bXAgPSBoYXNoQ29ucyhuZXcgVWludDhBcnJheSgzMikpOyAvLyB0bXAgYXJyYXksIHVzZWQganVzdCBvbmNlIGJlbG93XG4gIGhhc2hDLm91dHB1dExlbiA9IHRtcC5vdXRwdXRMZW47XG4gIGhhc2hDLmJsb2NrTGVuID0gdG1wLmJsb2NrTGVuO1xuICBoYXNoQy5jcmVhdGUgPSAoa2V5OiBVaW50OEFycmF5KSA9PiBoYXNoQ29ucyhrZXkpO1xuICByZXR1cm4gaGFzaEM7XG59XG5cbi8qKiBQb2x5MTMwNSBNQUMgZnJvbSBSRkMgODQzOS4gKi9cbmV4cG9ydCBjb25zdCBwb2x5MTMwNTogQ0hhc2ggPSAvKiogQF9fUFVSRV9fICovICgoKSA9PlxuICB3cmFwQ29uc3RydWN0b3JXaXRoS2V5KChrZXkpID0+IG5ldyBQb2x5MTMwNShrZXkpKSkoKTtcbiIsICIvKipcbiAqIEhLREYgKFJGQyA1ODY5KTogZXh0cmFjdCArIGV4cGFuZCBpbiBvbmUgc3RlcC5cbiAqIFNlZSBodHRwczovL3NvYXRvay5ibG9nLzIwMjEvMTEvMTcvdW5kZXJzdGFuZGluZy1oa2RmLy5cbiAqIEBtb2R1bGVcbiAqL1xuaW1wb3J0IHsgaG1hYyB9IGZyb20gJy4vaG1hYy50cyc7XG5pbXBvcnQgeyBhYnl0ZXMsIGFoYXNoLCBhbnVtYmVyLCB0eXBlIENIYXNoLCBjbGVhbiB9IGZyb20gJy4vdXRpbHMudHMnO1xuXG4vKipcbiAqIEhLREYtZXh0cmFjdCBmcm9tIHNwZWMuIExlc3MgaW1wb3J0YW50IHBhcnQuIGBIS0RGLUV4dHJhY3QoSUtNLCBzYWx0KSAtPiBQUktgXG4gKiBBcmd1bWVudHMgcG9zaXRpb24gZGlmZmVycyBmcm9tIHNwZWMgKElLTSBpcyBmaXJzdCBvbmUsIHNpbmNlIGl0IGlzIG5vdCBvcHRpb25hbClcbiAqIEBwYXJhbSBoYXNoIC0gaGFzaCBmdW5jdGlvbiB0aGF0IHdvdWxkIGJlIHVzZWQgKGUuZy4gc2hhMjU2KVxuICogQHBhcmFtIGlrbSAtIGlucHV0IGtleWluZyBtYXRlcmlhbCwgdGhlIGluaXRpYWwga2V5XG4gKiBAcGFyYW0gc2FsdCAtIG9wdGlvbmFsIHNhbHQgdmFsdWUgKGEgbm9uLXNlY3JldCByYW5kb20gdmFsdWUpXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBleHRyYWN0KGhhc2g6IENIYXNoLCBpa206IFVpbnQ4QXJyYXksIHNhbHQ/OiBVaW50OEFycmF5KTogVWludDhBcnJheSB7XG4gIGFoYXNoKGhhc2gpO1xuICAvLyBOT1RFOiBzb21lIGxpYnJhcmllcyB0cmVhdCB6ZXJvLWxlbmd0aCBhcnJheSBhcyAnbm90IHByb3ZpZGVkJztcbiAgLy8gd2UgZG9uJ3QsIHNpbmNlIHdlIGhhdmUgdW5kZWZpbmVkIGFzICdub3QgcHJvdmlkZWQnXG4gIC8vIGh0dHBzOi8vZ2l0aHViLmNvbS9SdXN0Q3J5cHRvL0tERnMvaXNzdWVzLzE1XG4gIGlmIChzYWx0ID09PSB1bmRlZmluZWQpIHNhbHQgPSBuZXcgVWludDhBcnJheShoYXNoLm91dHB1dExlbik7XG4gIHJldHVybiBobWFjKGhhc2gsIHNhbHQsIGlrbSk7XG59XG5cbmNvbnN0IEhLREZfQ09VTlRFUiA9IC8qIEBfX1BVUkVfXyAqLyBVaW50OEFycmF5Lm9mKDApO1xuY29uc3QgRU1QVFlfQlVGRkVSID0gLyogQF9fUFVSRV9fICovIFVpbnQ4QXJyYXkub2YoKTtcblxuLyoqXG4gKiBIS0RGLWV4cGFuZCBmcm9tIHRoZSBzcGVjLiBUaGUgbW9zdCBpbXBvcnRhbnQgcGFydC4gYEhLREYtRXhwYW5kKFBSSywgaW5mbywgTCkgLT4gT0tNYFxuICogQHBhcmFtIGhhc2ggLSBoYXNoIGZ1bmN0aW9uIHRoYXQgd291bGQgYmUgdXNlZCAoZS5nLiBzaGEyNTYpXG4gKiBAcGFyYW0gcHJrIC0gYSBwc2V1ZG9yYW5kb20ga2V5IG9mIGF0IGxlYXN0IEhhc2hMZW4gb2N0ZXRzICh1c3VhbGx5LCB0aGUgb3V0cHV0IGZyb20gdGhlIGV4dHJhY3Qgc3RlcClcbiAqIEBwYXJhbSBpbmZvIC0gb3B0aW9uYWwgY29udGV4dCBhbmQgYXBwbGljYXRpb24gc3BlY2lmaWMgaW5mb3JtYXRpb24gKGNhbiBiZSBhIHplcm8tbGVuZ3RoIHN0cmluZylcbiAqIEBwYXJhbSBsZW5ndGggLSBsZW5ndGggb2Ygb3V0cHV0IGtleWluZyBtYXRlcmlhbCBpbiBieXRlc1xuICovXG5leHBvcnQgZnVuY3Rpb24gZXhwYW5kKFxuICBoYXNoOiBDSGFzaCxcbiAgcHJrOiBVaW50OEFycmF5LFxuICBpbmZvPzogVWludDhBcnJheSxcbiAgbGVuZ3RoOiBudW1iZXIgPSAzMlxuKTogVWludDhBcnJheSB7XG4gIGFoYXNoKGhhc2gpO1xuICBhbnVtYmVyKGxlbmd0aCwgJ2xlbmd0aCcpO1xuICBjb25zdCBvbGVuID0gaGFzaC5vdXRwdXRMZW47XG4gIGlmIChsZW5ndGggPiAyNTUgKiBvbGVuKSB0aHJvdyBuZXcgRXJyb3IoJ0xlbmd0aCBtdXN0IGJlIDw9IDI1NSpIYXNoTGVuJyk7XG4gIGNvbnN0IGJsb2NrcyA9IE1hdGguY2VpbChsZW5ndGggLyBvbGVuKTtcbiAgaWYgKGluZm8gPT09IHVuZGVmaW5lZCkgaW5mbyA9IEVNUFRZX0JVRkZFUjtcbiAgZWxzZSBhYnl0ZXMoaW5mbywgdW5kZWZpbmVkLCAnaW5mbycpO1xuICAvLyBmaXJzdCBMKGVuZ3RoKSBvY3RldHMgb2YgVFxuICBjb25zdCBva20gPSBuZXcgVWludDhBcnJheShibG9ja3MgKiBvbGVuKTtcbiAgLy8gUmUtdXNlIEhNQUMgaW5zdGFuY2UgYmV0d2VlbiBibG9ja3NcbiAgY29uc3QgSE1BQyA9IGhtYWMuY3JlYXRlKGhhc2gsIHByayk7XG4gIGNvbnN0IEhNQUNUbXAgPSBITUFDLl9jbG9uZUludG8oKTtcbiAgY29uc3QgVCA9IG5ldyBVaW50OEFycmF5KEhNQUMub3V0cHV0TGVuKTtcbiAgZm9yIChsZXQgY291bnRlciA9IDA7IGNvdW50ZXIgPCBibG9ja3M7IGNvdW50ZXIrKykge1xuICAgIEhLREZfQ09VTlRFUlswXSA9IGNvdW50ZXIgKyAxO1xuICAgIC8vIFQoMCkgPSBlbXB0eSBzdHJpbmcgKHplcm8gbGVuZ3RoKVxuICAgIC8vIFQoTikgPSBITUFDLUhhc2goUFJLLCBUKE4tMSkgfCBpbmZvIHwgTilcbiAgICBITUFDVG1wLnVwZGF0ZShjb3VudGVyID09PSAwID8gRU1QVFlfQlVGRkVSIDogVClcbiAgICAgIC51cGRhdGUoaW5mbylcbiAgICAgIC51cGRhdGUoSEtERl9DT1VOVEVSKVxuICAgICAgLmRpZ2VzdEludG8oVCk7XG4gICAgb2ttLnNldChULCBvbGVuICogY291bnRlcik7XG4gICAgSE1BQy5fY2xvbmVJbnRvKEhNQUNUbXApO1xuICB9XG4gIEhNQUMuZGVzdHJveSgpO1xuICBITUFDVG1wLmRlc3Ryb3koKTtcbiAgY2xlYW4oVCwgSEtERl9DT1VOVEVSKTtcbiAgcmV0dXJuIG9rbS5zbGljZSgwLCBsZW5ndGgpO1xufVxuXG4vKipcbiAqIEhLREYgKFJGQyA1ODY5KTogZGVyaXZlIGtleXMgZnJvbSBhbiBpbml0aWFsIGlucHV0LlxuICogQ29tYmluZXMgaGtkZl9leHRyYWN0ICsgaGtkZl9leHBhbmQgaW4gb25lIHN0ZXBcbiAqIEBwYXJhbSBoYXNoIC0gaGFzaCBmdW5jdGlvbiB0aGF0IHdvdWxkIGJlIHVzZWQgKGUuZy4gc2hhMjU2KVxuICogQHBhcmFtIGlrbSAtIGlucHV0IGtleWluZyBtYXRlcmlhbCwgdGhlIGluaXRpYWwga2V5XG4gKiBAcGFyYW0gc2FsdCAtIG9wdGlvbmFsIHNhbHQgdmFsdWUgKGEgbm9uLXNlY3JldCByYW5kb20gdmFsdWUpXG4gKiBAcGFyYW0gaW5mbyAtIG9wdGlvbmFsIGNvbnRleHQgYW5kIGFwcGxpY2F0aW9uIHNwZWNpZmljIGluZm9ybWF0aW9uIChjYW4gYmUgYSB6ZXJvLWxlbmd0aCBzdHJpbmcpXG4gKiBAcGFyYW0gbGVuZ3RoIC0gbGVuZ3RoIG9mIG91dHB1dCBrZXlpbmcgbWF0ZXJpYWwgaW4gYnl0ZXNcbiAqIEBleGFtcGxlXG4gKiBpbXBvcnQgeyBoa2RmIH0gZnJvbSAnQG5vYmxlL2hhc2hlcy9oa2RmJztcbiAqIGltcG9ydCB7IHNoYTI1NiB9IGZyb20gJ0Bub2JsZS9oYXNoZXMvc2hhMic7XG4gKiBpbXBvcnQgeyByYW5kb21CeXRlcyB9IGZyb20gJ0Bub2JsZS9oYXNoZXMvdXRpbHMnO1xuICogY29uc3QgaW5wdXRLZXkgPSByYW5kb21CeXRlcygzMik7XG4gKiBjb25zdCBzYWx0ID0gcmFuZG9tQnl0ZXMoMzIpO1xuICogY29uc3QgaW5mbyA9ICdhcHBsaWNhdGlvbi1rZXknO1xuICogY29uc3QgaGsxID0gaGtkZihzaGEyNTYsIGlucHV0S2V5LCBzYWx0LCBpbmZvLCAzMik7XG4gKi9cbmV4cG9ydCBjb25zdCBoa2RmID0gKFxuICBoYXNoOiBDSGFzaCxcbiAgaWttOiBVaW50OEFycmF5LFxuICBzYWx0OiBVaW50OEFycmF5IHwgdW5kZWZpbmVkLFxuICBpbmZvOiBVaW50OEFycmF5IHwgdW5kZWZpbmVkLFxuICBsZW5ndGg6IG51bWJlclxuKTogVWludDhBcnJheSA9PiBleHBhbmQoaGFzaCwgZXh0cmFjdChoYXNoLCBpa20sIHNhbHQpLCBpbmZvLCBsZW5ndGgpO1xuIiwgIi8qISBzY3VyZS1iYXNlIC0gTUlUIExpY2Vuc2UgKGMpIDIwMjIgUGF1bCBNaWxsZXIgKHBhdWxtaWxsci5jb20pICovXG5cbmV4cG9ydCBpbnRlcmZhY2UgQ29kZXI8RiwgVD4ge1xuICBlbmNvZGUoZnJvbTogRik6IFQ7XG4gIGRlY29kZSh0bzogVCk6IEY7XG59XG5cbmV4cG9ydCBpbnRlcmZhY2UgQnl0ZXNDb2RlciBleHRlbmRzIENvZGVyPFVpbnQ4QXJyYXksIHN0cmluZz4ge1xuICBlbmNvZGU6IChkYXRhOiBVaW50OEFycmF5KSA9PiBzdHJpbmc7XG4gIGRlY29kZTogKHN0cjogc3RyaW5nKSA9PiBVaW50OEFycmF5O1xufVxuXG5mdW5jdGlvbiBpc0J5dGVzKGE6IHVua25vd24pOiBhIGlzIFVpbnQ4QXJyYXkge1xuICByZXR1cm4gYSBpbnN0YW5jZW9mIFVpbnQ4QXJyYXkgfHwgKEFycmF5QnVmZmVyLmlzVmlldyhhKSAmJiBhLmNvbnN0cnVjdG9yLm5hbWUgPT09ICdVaW50OEFycmF5Jyk7XG59XG4vKiogQXNzZXJ0cyBzb21ldGhpbmcgaXMgVWludDhBcnJheS4gKi9cbmZ1bmN0aW9uIGFieXRlcyhiOiBVaW50OEFycmF5IHwgdW5kZWZpbmVkKTogdm9pZCB7XG4gIGlmICghaXNCeXRlcyhiKSkgdGhyb3cgbmV3IEVycm9yKCdVaW50OEFycmF5IGV4cGVjdGVkJyk7XG59XG5cbmZ1bmN0aW9uIGlzQXJyYXlPZihpc1N0cmluZzogYm9vbGVhbiwgYXJyOiBhbnlbXSkge1xuICBpZiAoIUFycmF5LmlzQXJyYXkoYXJyKSkgcmV0dXJuIGZhbHNlO1xuICBpZiAoYXJyLmxlbmd0aCA9PT0gMCkgcmV0dXJuIHRydWU7XG4gIGlmIChpc1N0cmluZykge1xuICAgIHJldHVybiBhcnIuZXZlcnkoKGl0ZW0pID0+IHR5cGVvZiBpdGVtID09PSAnc3RyaW5nJyk7XG4gIH0gZWxzZSB7XG4gICAgcmV0dXJuIGFyci5ldmVyeSgoaXRlbSkgPT4gTnVtYmVyLmlzU2FmZUludGVnZXIoaXRlbSkpO1xuICB9XG59XG5cbmZ1bmN0aW9uIGFmbihpbnB1dDogRnVuY3Rpb24pOiBpbnB1dCBpcyBGdW5jdGlvbiB7XG4gIGlmICh0eXBlb2YgaW5wdXQgIT09ICdmdW5jdGlvbicpIHRocm93IG5ldyBFcnJvcignZnVuY3Rpb24gZXhwZWN0ZWQnKTtcbiAgcmV0dXJuIHRydWU7XG59XG5cbmZ1bmN0aW9uIGFzdHIobGFiZWw6IHN0cmluZywgaW5wdXQ6IHVua25vd24pOiBpbnB1dCBpcyBzdHJpbmcge1xuICBpZiAodHlwZW9mIGlucHV0ICE9PSAnc3RyaW5nJykgdGhyb3cgbmV3IEVycm9yKGAke2xhYmVsfTogc3RyaW5nIGV4cGVjdGVkYCk7XG4gIHJldHVybiB0cnVlO1xufVxuXG5mdW5jdGlvbiBhbnVtYmVyKG46IG51bWJlcik6IHZvaWQge1xuICBpZiAoIU51bWJlci5pc1NhZmVJbnRlZ2VyKG4pKSB0aHJvdyBuZXcgRXJyb3IoYGludmFsaWQgaW50ZWdlcjogJHtufWApO1xufVxuXG5mdW5jdGlvbiBhQXJyKGlucHV0OiBhbnlbXSkge1xuICBpZiAoIUFycmF5LmlzQXJyYXkoaW5wdXQpKSB0aHJvdyBuZXcgRXJyb3IoJ2FycmF5IGV4cGVjdGVkJyk7XG59XG5mdW5jdGlvbiBhc3RyQXJyKGxhYmVsOiBzdHJpbmcsIGlucHV0OiBzdHJpbmdbXSkge1xuICBpZiAoIWlzQXJyYXlPZih0cnVlLCBpbnB1dCkpIHRocm93IG5ldyBFcnJvcihgJHtsYWJlbH06IGFycmF5IG9mIHN0cmluZ3MgZXhwZWN0ZWRgKTtcbn1cbmZ1bmN0aW9uIGFudW1BcnIobGFiZWw6IHN0cmluZywgaW5wdXQ6IG51bWJlcltdKSB7XG4gIGlmICghaXNBcnJheU9mKGZhbHNlLCBpbnB1dCkpIHRocm93IG5ldyBFcnJvcihgJHtsYWJlbH06IGFycmF5IG9mIG51bWJlcnMgZXhwZWN0ZWRgKTtcbn1cblxuLy8gVE9ETzogc29tZSByZWN1c2l2ZSB0eXBlIGluZmVyZW5jZSBzbyBpdCB3b3VsZCBjaGVjayBjb3JyZWN0IG9yZGVyIG9mIGlucHV0L291dHB1dCBpbnNpZGUgcmVzdD9cbi8vIGxpa2UgPHN0cmluZywgbnVtYmVyPiwgPG51bWJlciwgYnl0ZXM+LCA8Ynl0ZXMsIGZsb2F0PlxudHlwZSBDaGFpbiA9IFtDb2RlcjxhbnksIGFueT4sIC4uLkNvZGVyPGFueSwgYW55PltdXTtcbi8vIEV4dHJhY3QgaW5mbyBmcm9tIENvZGVyIHR5cGVcbnR5cGUgSW5wdXQ8Rj4gPSBGIGV4dGVuZHMgQ29kZXI8aW5mZXIgVCwgYW55PiA/IFQgOiBuZXZlcjtcbnR5cGUgT3V0cHV0PEY+ID0gRiBleHRlbmRzIENvZGVyPGFueSwgaW5mZXIgVD4gPyBUIDogbmV2ZXI7XG4vLyBHZW5lcmljIGZ1bmN0aW9uIGZvciBhcnJheXNcbnR5cGUgRmlyc3Q8VD4gPSBUIGV4dGVuZHMgW2luZmVyIFUsIC4uLmFueVtdXSA/IFUgOiBuZXZlcjtcbnR5cGUgTGFzdDxUPiA9IFQgZXh0ZW5kcyBbLi4uYW55W10sIGluZmVyIFVdID8gVSA6IG5ldmVyO1xudHlwZSBUYWlsPFQ+ID0gVCBleHRlbmRzIFthbnksIC4uLmluZmVyIFVdID8gVSA6IG5ldmVyO1xuXG50eXBlIEFzQ2hhaW48QyBleHRlbmRzIENoYWluLCBSZXN0ID0gVGFpbDxDPj4gPSB7XG4gIC8vIENbS10gPSBDb2RlcjxJbnB1dDxDW0tdPiwgSW5wdXQ8UmVzdFtrXT4+XG4gIFtLIGluIGtleW9mIENdOiBDb2RlcjxJbnB1dDxDW0tdPiwgSW5wdXQ8SyBleHRlbmRzIGtleW9mIFJlc3QgPyBSZXN0W0tdIDogYW55Pj47XG59O1xuXG4vKipcbiAqIEBfX05PX1NJREVfRUZGRUNUU19fXG4gKi9cbmZ1bmN0aW9uIGNoYWluPFQgZXh0ZW5kcyBDaGFpbiAmIEFzQ2hhaW48VD4+KC4uLmFyZ3M6IFQpOiBDb2RlcjxJbnB1dDxGaXJzdDxUPj4sIE91dHB1dDxMYXN0PFQ+Pj4ge1xuICBjb25zdCBpZCA9IChhOiBhbnkpID0+IGE7XG4gIC8vIFdyYXAgY2FsbCBpbiBjbG9zdXJlIHNvIEpJVCBjYW4gaW5saW5lIGNhbGxzXG4gIGNvbnN0IHdyYXAgPSAoYTogYW55LCBiOiBhbnkpID0+IChjOiBhbnkpID0+IGEoYihjKSk7XG4gIC8vIENvbnN0cnVjdCBjaGFpbiBvZiBhcmdzWy0xXS5lbmNvZGUoYXJnc1stMl0uZW5jb2RlKFsuLi5dKSlcbiAgY29uc3QgZW5jb2RlID0gYXJncy5tYXAoKHgpID0+IHguZW5jb2RlKS5yZWR1Y2VSaWdodCh3cmFwLCBpZCk7XG4gIC8vIENvbnN0cnVjdCBjaGFpbiBvZiBhcmdzWzBdLmRlY29kZShhcmdzWzFdLmRlY29kZSguLi4pKVxuICBjb25zdCBkZWNvZGUgPSBhcmdzLm1hcCgoeCkgPT4geC5kZWNvZGUpLnJlZHVjZSh3cmFwLCBpZCk7XG4gIHJldHVybiB7IGVuY29kZSwgZGVjb2RlIH07XG59XG5cbi8qKlxuICogRW5jb2RlcyBpbnRlZ2VyIHJhZGl4IHJlcHJlc2VudGF0aW9uIHRvIGFycmF5IG9mIHN0cmluZ3MgdXNpbmcgYWxwaGFiZXQgYW5kIGJhY2suXG4gKiBDb3VsZCBhbHNvIGJlIGFycmF5IG9mIHN0cmluZ3MuXG4gKiBAX19OT19TSURFX0VGRkVDVFNfX1xuICovXG5mdW5jdGlvbiBhbHBoYWJldChsZXR0ZXJzOiBzdHJpbmcgfCBzdHJpbmdbXSk6IENvZGVyPG51bWJlcltdLCBzdHJpbmdbXT4ge1xuICAvLyBtYXBwaW5nIDEgdG8gXCJiXCJcbiAgY29uc3QgbGV0dGVyc0EgPSB0eXBlb2YgbGV0dGVycyA9PT0gJ3N0cmluZycgPyBsZXR0ZXJzLnNwbGl0KCcnKSA6IGxldHRlcnM7XG4gIGNvbnN0IGxlbiA9IGxldHRlcnNBLmxlbmd0aDtcbiAgYXN0ckFycignYWxwaGFiZXQnLCBsZXR0ZXJzQSk7XG5cbiAgLy8gbWFwcGluZyBcImJcIiB0byAxXG4gIGNvbnN0IGluZGV4ZXMgPSBuZXcgTWFwKGxldHRlcnNBLm1hcCgobCwgaSkgPT4gW2wsIGldKSk7XG4gIHJldHVybiB7XG4gICAgZW5jb2RlOiAoZGlnaXRzOiBudW1iZXJbXSkgPT4ge1xuICAgICAgYUFycihkaWdpdHMpO1xuICAgICAgcmV0dXJuIGRpZ2l0cy5tYXAoKGkpID0+IHtcbiAgICAgICAgaWYgKCFOdW1iZXIuaXNTYWZlSW50ZWdlcihpKSB8fCBpIDwgMCB8fCBpID49IGxlbilcbiAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoXG4gICAgICAgICAgICBgYWxwaGFiZXQuZW5jb2RlOiBkaWdpdCBpbmRleCBvdXRzaWRlIGFscGhhYmV0IFwiJHtpfVwiLiBBbGxvd2VkOiAke2xldHRlcnN9YFxuICAgICAgICAgICk7XG4gICAgICAgIHJldHVybiBsZXR0ZXJzQVtpXSE7XG4gICAgICB9KTtcbiAgICB9LFxuICAgIGRlY29kZTogKGlucHV0OiBzdHJpbmdbXSk6IG51bWJlcltdID0+IHtcbiAgICAgIGFBcnIoaW5wdXQpO1xuICAgICAgcmV0dXJuIGlucHV0Lm1hcCgobGV0dGVyKSA9PiB7XG4gICAgICAgIGFzdHIoJ2FscGhhYmV0LmRlY29kZScsIGxldHRlcik7XG4gICAgICAgIGNvbnN0IGkgPSBpbmRleGVzLmdldChsZXR0ZXIpO1xuICAgICAgICBpZiAoaSA9PT0gdW5kZWZpbmVkKSB0aHJvdyBuZXcgRXJyb3IoYFVua25vd24gbGV0dGVyOiBcIiR7bGV0dGVyfVwiLiBBbGxvd2VkOiAke2xldHRlcnN9YCk7XG4gICAgICAgIHJldHVybiBpO1xuICAgICAgfSk7XG4gICAgfSxcbiAgfTtcbn1cblxuLyoqXG4gKiBAX19OT19TSURFX0VGRkVDVFNfX1xuICovXG5mdW5jdGlvbiBqb2luKHNlcGFyYXRvciA9ICcnKTogQ29kZXI8c3RyaW5nW10sIHN0cmluZz4ge1xuICBhc3RyKCdqb2luJywgc2VwYXJhdG9yKTtcbiAgcmV0dXJuIHtcbiAgICBlbmNvZGU6IChmcm9tKSA9PiB7XG4gICAgICBhc3RyQXJyKCdqb2luLmRlY29kZScsIGZyb20pO1xuICAgICAgcmV0dXJuIGZyb20uam9pbihzZXBhcmF0b3IpO1xuICAgIH0sXG4gICAgZGVjb2RlOiAodG8pID0+IHtcbiAgICAgIGFzdHIoJ2pvaW4uZGVjb2RlJywgdG8pO1xuICAgICAgcmV0dXJuIHRvLnNwbGl0KHNlcGFyYXRvcik7XG4gICAgfSxcbiAgfTtcbn1cblxuLyoqXG4gKiBQYWQgc3RyaW5ncyBhcnJheSBzbyBpdCBoYXMgaW50ZWdlciBudW1iZXIgb2YgYml0c1xuICogQF9fTk9fU0lERV9FRkZFQ1RTX19cbiAqL1xuZnVuY3Rpb24gcGFkZGluZyhiaXRzOiBudW1iZXIsIGNociA9ICc9Jyk6IENvZGVyPHN0cmluZ1tdLCBzdHJpbmdbXT4ge1xuICBhbnVtYmVyKGJpdHMpO1xuICBhc3RyKCdwYWRkaW5nJywgY2hyKTtcbiAgcmV0dXJuIHtcbiAgICBlbmNvZGUoZGF0YTogc3RyaW5nW10pOiBzdHJpbmdbXSB7XG4gICAgICBhc3RyQXJyKCdwYWRkaW5nLmVuY29kZScsIGRhdGEpO1xuICAgICAgd2hpbGUgKChkYXRhLmxlbmd0aCAqIGJpdHMpICUgOCkgZGF0YS5wdXNoKGNocik7XG4gICAgICByZXR1cm4gZGF0YTtcbiAgICB9LFxuICAgIGRlY29kZShpbnB1dDogc3RyaW5nW10pOiBzdHJpbmdbXSB7XG4gICAgICBhc3RyQXJyKCdwYWRkaW5nLmRlY29kZScsIGlucHV0KTtcbiAgICAgIGxldCBlbmQgPSBpbnB1dC5sZW5ndGg7XG4gICAgICBpZiAoKGVuZCAqIGJpdHMpICUgOClcbiAgICAgICAgdGhyb3cgbmV3IEVycm9yKCdwYWRkaW5nOiBpbnZhbGlkLCBzdHJpbmcgc2hvdWxkIGhhdmUgd2hvbGUgbnVtYmVyIG9mIGJ5dGVzJyk7XG4gICAgICBmb3IgKDsgZW5kID4gMCAmJiBpbnB1dFtlbmQgLSAxXSA9PT0gY2hyOyBlbmQtLSkge1xuICAgICAgICBjb25zdCBsYXN0ID0gZW5kIC0gMTtcbiAgICAgICAgY29uc3QgYnl0ZSA9IGxhc3QgKiBiaXRzO1xuICAgICAgICBpZiAoYnl0ZSAlIDggPT09IDApIHRocm93IG5ldyBFcnJvcigncGFkZGluZzogaW52YWxpZCwgc3RyaW5nIGhhcyB0b28gbXVjaCBwYWRkaW5nJyk7XG4gICAgICB9XG4gICAgICByZXR1cm4gaW5wdXQuc2xpY2UoMCwgZW5kKTtcbiAgICB9LFxuICB9O1xufVxuXG4vKipcbiAqIEBfX05PX1NJREVfRUZGRUNUU19fXG4gKi9cbmZ1bmN0aW9uIG5vcm1hbGl6ZTxUPihmbjogKHZhbDogVCkgPT4gVCk6IENvZGVyPFQsIFQ+IHtcbiAgYWZuKGZuKTtcbiAgcmV0dXJuIHsgZW5jb2RlOiAoZnJvbTogVCkgPT4gZnJvbSwgZGVjb2RlOiAodG86IFQpID0+IGZuKHRvKSB9O1xufVxuXG4vKipcbiAqIFNsb3c6IE8obl4yKSB0aW1lIGNvbXBsZXhpdHlcbiAqL1xuZnVuY3Rpb24gY29udmVydFJhZGl4KGRhdGE6IG51bWJlcltdLCBmcm9tOiBudW1iZXIsIHRvOiBudW1iZXIpOiBudW1iZXJbXSB7XG4gIC8vIGJhc2UgMSBpcyBpbXBvc3NpYmxlXG4gIGlmIChmcm9tIDwgMikgdGhyb3cgbmV3IEVycm9yKGBjb252ZXJ0UmFkaXg6IGludmFsaWQgZnJvbT0ke2Zyb219LCBiYXNlIGNhbm5vdCBiZSBsZXNzIHRoYW4gMmApO1xuICBpZiAodG8gPCAyKSB0aHJvdyBuZXcgRXJyb3IoYGNvbnZlcnRSYWRpeDogaW52YWxpZCB0bz0ke3RvfSwgYmFzZSBjYW5ub3QgYmUgbGVzcyB0aGFuIDJgKTtcbiAgYUFycihkYXRhKTtcbiAgaWYgKCFkYXRhLmxlbmd0aCkgcmV0dXJuIFtdO1xuICBsZXQgcG9zID0gMDtcbiAgY29uc3QgcmVzID0gW107XG4gIGNvbnN0IGRpZ2l0cyA9IEFycmF5LmZyb20oZGF0YSwgKGQpID0+IHtcbiAgICBhbnVtYmVyKGQpO1xuICAgIGlmIChkIDwgMCB8fCBkID49IGZyb20pIHRocm93IG5ldyBFcnJvcihgaW52YWxpZCBpbnRlZ2VyOiAke2R9YCk7XG4gICAgcmV0dXJuIGQ7XG4gIH0pO1xuICBjb25zdCBkbGVuID0gZGlnaXRzLmxlbmd0aDtcbiAgd2hpbGUgKHRydWUpIHtcbiAgICBsZXQgY2FycnkgPSAwO1xuICAgIGxldCBkb25lID0gdHJ1ZTtcbiAgICBmb3IgKGxldCBpID0gcG9zOyBpIDwgZGxlbjsgaSsrKSB7XG4gICAgICBjb25zdCBkaWdpdCA9IGRpZ2l0c1tpXSE7XG4gICAgICBjb25zdCBmcm9tQ2FycnkgPSBmcm9tICogY2Fycnk7XG4gICAgICBjb25zdCBkaWdpdEJhc2UgPSBmcm9tQ2FycnkgKyBkaWdpdDtcbiAgICAgIGlmIChcbiAgICAgICAgIU51bWJlci5pc1NhZmVJbnRlZ2VyKGRpZ2l0QmFzZSkgfHxcbiAgICAgICAgZnJvbUNhcnJ5IC8gZnJvbSAhPT0gY2FycnkgfHxcbiAgICAgICAgZGlnaXRCYXNlIC0gZGlnaXQgIT09IGZyb21DYXJyeVxuICAgICAgKSB7XG4gICAgICAgIHRocm93IG5ldyBFcnJvcignY29udmVydFJhZGl4OiBjYXJyeSBvdmVyZmxvdycpO1xuICAgICAgfVxuICAgICAgY29uc3QgZGl2ID0gZGlnaXRCYXNlIC8gdG87XG4gICAgICBjYXJyeSA9IGRpZ2l0QmFzZSAlIHRvO1xuICAgICAgY29uc3Qgcm91bmRlZCA9IE1hdGguZmxvb3IoZGl2KTtcbiAgICAgIGRpZ2l0c1tpXSA9IHJvdW5kZWQ7XG4gICAgICBpZiAoIU51bWJlci5pc1NhZmVJbnRlZ2VyKHJvdW5kZWQpIHx8IHJvdW5kZWQgKiB0byArIGNhcnJ5ICE9PSBkaWdpdEJhc2UpXG4gICAgICAgIHRocm93IG5ldyBFcnJvcignY29udmVydFJhZGl4OiBjYXJyeSBvdmVyZmxvdycpO1xuICAgICAgaWYgKCFkb25lKSBjb250aW51ZTtcbiAgICAgIGVsc2UgaWYgKCFyb3VuZGVkKSBwb3MgPSBpO1xuICAgICAgZWxzZSBkb25lID0gZmFsc2U7XG4gICAgfVxuICAgIHJlcy5wdXNoKGNhcnJ5KTtcbiAgICBpZiAoZG9uZSkgYnJlYWs7XG4gIH1cbiAgZm9yIChsZXQgaSA9IDA7IGkgPCBkYXRhLmxlbmd0aCAtIDEgJiYgZGF0YVtpXSA9PT0gMDsgaSsrKSByZXMucHVzaCgwKTtcbiAgcmV0dXJuIHJlcy5yZXZlcnNlKCk7XG59XG5cbmNvbnN0IGdjZCA9IChhOiBudW1iZXIsIGI6IG51bWJlcik6IG51bWJlciA9PiAoYiA9PT0gMCA/IGEgOiBnY2QoYiwgYSAlIGIpKTtcbmNvbnN0IHJhZGl4MmNhcnJ5ID0gLyogQF9fTk9fU0lERV9FRkZFQ1RTX18gKi8gKGZyb206IG51bWJlciwgdG86IG51bWJlcikgPT5cbiAgZnJvbSArICh0byAtIGdjZChmcm9tLCB0bykpO1xuY29uc3QgcG93ZXJzOiBudW1iZXJbXSA9IC8qIEBfX1BVUkVfXyAqLyAoKCkgPT4ge1xuICBsZXQgcmVzID0gW107XG4gIGZvciAobGV0IGkgPSAwOyBpIDwgNDA7IGkrKykgcmVzLnB1c2goMiAqKiBpKTtcbiAgcmV0dXJuIHJlcztcbn0pKCk7XG4vKipcbiAqIEltcGxlbWVudGVkIHdpdGggbnVtYmVycywgYmVjYXVzZSBCaWdJbnQgaXMgNXggc2xvd2VyXG4gKi9cbmZ1bmN0aW9uIGNvbnZlcnRSYWRpeDIoZGF0YTogbnVtYmVyW10sIGZyb206IG51bWJlciwgdG86IG51bWJlciwgcGFkZGluZzogYm9vbGVhbik6IG51bWJlcltdIHtcbiAgYUFycihkYXRhKTtcbiAgaWYgKGZyb20gPD0gMCB8fCBmcm9tID4gMzIpIHRocm93IG5ldyBFcnJvcihgY29udmVydFJhZGl4Mjogd3JvbmcgZnJvbT0ke2Zyb219YCk7XG4gIGlmICh0byA8PSAwIHx8IHRvID4gMzIpIHRocm93IG5ldyBFcnJvcihgY29udmVydFJhZGl4Mjogd3JvbmcgdG89JHt0b31gKTtcbiAgaWYgKHJhZGl4MmNhcnJ5KGZyb20sIHRvKSA+IDMyKSB7XG4gICAgdGhyb3cgbmV3IEVycm9yKFxuICAgICAgYGNvbnZlcnRSYWRpeDI6IGNhcnJ5IG92ZXJmbG93IGZyb209JHtmcm9tfSB0bz0ke3RvfSBjYXJyeUJpdHM9JHtyYWRpeDJjYXJyeShmcm9tLCB0byl9YFxuICAgICk7XG4gIH1cbiAgbGV0IGNhcnJ5ID0gMDtcbiAgbGV0IHBvcyA9IDA7IC8vIGJpdHdpc2UgcG9zaXRpb24gaW4gY3VycmVudCBlbGVtZW50XG4gIGNvbnN0IG1heCA9IHBvd2Vyc1tmcm9tXSE7XG4gIGNvbnN0IG1hc2sgPSBwb3dlcnNbdG9dISAtIDE7XG4gIGNvbnN0IHJlczogbnVtYmVyW10gPSBbXTtcbiAgZm9yIChjb25zdCBuIG9mIGRhdGEpIHtcbiAgICBhbnVtYmVyKG4pO1xuICAgIGlmIChuID49IG1heCkgdGhyb3cgbmV3IEVycm9yKGBjb252ZXJ0UmFkaXgyOiBpbnZhbGlkIGRhdGEgd29yZD0ke259IGZyb209JHtmcm9tfWApO1xuICAgIGNhcnJ5ID0gKGNhcnJ5IDw8IGZyb20pIHwgbjtcbiAgICBpZiAocG9zICsgZnJvbSA+IDMyKSB0aHJvdyBuZXcgRXJyb3IoYGNvbnZlcnRSYWRpeDI6IGNhcnJ5IG92ZXJmbG93IHBvcz0ke3Bvc30gZnJvbT0ke2Zyb219YCk7XG4gICAgcG9zICs9IGZyb207XG4gICAgZm9yICg7IHBvcyA+PSB0bzsgcG9zIC09IHRvKSByZXMucHVzaCgoKGNhcnJ5ID4+IChwb3MgLSB0bykpICYgbWFzaykgPj4+IDApO1xuICAgIGNvbnN0IHBvdyA9IHBvd2Vyc1twb3NdO1xuICAgIGlmIChwb3cgPT09IHVuZGVmaW5lZCkgdGhyb3cgbmV3IEVycm9yKCdpbnZhbGlkIGNhcnJ5Jyk7XG4gICAgY2FycnkgJj0gcG93IC0gMTsgLy8gY2xlYW4gY2FycnksIG90aGVyd2lzZSBpdCB3aWxsIGNhdXNlIG92ZXJmbG93XG4gIH1cbiAgY2FycnkgPSAoY2FycnkgPDwgKHRvIC0gcG9zKSkgJiBtYXNrO1xuICBpZiAoIXBhZGRpbmcgJiYgcG9zID49IGZyb20pIHRocm93IG5ldyBFcnJvcignRXhjZXNzIHBhZGRpbmcnKTtcbiAgaWYgKCFwYWRkaW5nICYmIGNhcnJ5ID4gMCkgdGhyb3cgbmV3IEVycm9yKGBOb24temVybyBwYWRkaW5nOiAke2NhcnJ5fWApO1xuICBpZiAocGFkZGluZyAmJiBwb3MgPiAwKSByZXMucHVzaChjYXJyeSA+Pj4gMCk7XG4gIHJldHVybiByZXM7XG59XG5cbi8qKlxuICogQF9fTk9fU0lERV9FRkZFQ1RTX19cbiAqL1xuZnVuY3Rpb24gcmFkaXgobnVtOiBudW1iZXIpOiBDb2RlcjxVaW50OEFycmF5LCBudW1iZXJbXT4ge1xuICBhbnVtYmVyKG51bSk7XG4gIGNvbnN0IF8yNTYgPSAyICoqIDg7XG4gIHJldHVybiB7XG4gICAgZW5jb2RlOiAoYnl0ZXM6IFVpbnQ4QXJyYXkpID0+IHtcbiAgICAgIGlmICghaXNCeXRlcyhieXRlcykpIHRocm93IG5ldyBFcnJvcigncmFkaXguZW5jb2RlIGlucHV0IHNob3VsZCBiZSBVaW50OEFycmF5Jyk7XG4gICAgICByZXR1cm4gY29udmVydFJhZGl4KEFycmF5LmZyb20oYnl0ZXMpLCBfMjU2LCBudW0pO1xuICAgIH0sXG4gICAgZGVjb2RlOiAoZGlnaXRzOiBudW1iZXJbXSkgPT4ge1xuICAgICAgYW51bUFycigncmFkaXguZGVjb2RlJywgZGlnaXRzKTtcbiAgICAgIHJldHVybiBVaW50OEFycmF5LmZyb20oY29udmVydFJhZGl4KGRpZ2l0cywgbnVtLCBfMjU2KSk7XG4gICAgfSxcbiAgfTtcbn1cblxuLyoqXG4gKiBJZiBib3RoIGJhc2VzIGFyZSBwb3dlciBvZiBzYW1lIG51bWJlciAobGlrZSBgMioqOCA8LT4gMioqNjRgKSxcbiAqIHRoZXJlIGlzIGEgbGluZWFyIGFsZ29yaXRobS4gRm9yIG5vdyB3ZSBoYXZlIGltcGxlbWVudGF0aW9uIGZvciBwb3dlci1vZi10d28gYmFzZXMgb25seS5cbiAqIEBfX05PX1NJREVfRUZGRUNUU19fXG4gKi9cbmZ1bmN0aW9uIHJhZGl4MihiaXRzOiBudW1iZXIsIHJldlBhZGRpbmcgPSBmYWxzZSk6IENvZGVyPFVpbnQ4QXJyYXksIG51bWJlcltdPiB7XG4gIGFudW1iZXIoYml0cyk7XG4gIGlmIChiaXRzIDw9IDAgfHwgYml0cyA+IDMyKSB0aHJvdyBuZXcgRXJyb3IoJ3JhZGl4MjogYml0cyBzaG91bGQgYmUgaW4gKDAuLjMyXScpO1xuICBpZiAocmFkaXgyY2FycnkoOCwgYml0cykgPiAzMiB8fCByYWRpeDJjYXJyeShiaXRzLCA4KSA+IDMyKVxuICAgIHRocm93IG5ldyBFcnJvcigncmFkaXgyOiBjYXJyeSBvdmVyZmxvdycpO1xuICByZXR1cm4ge1xuICAgIGVuY29kZTogKGJ5dGVzOiBVaW50OEFycmF5KSA9PiB7XG4gICAgICBpZiAoIWlzQnl0ZXMoYnl0ZXMpKSB0aHJvdyBuZXcgRXJyb3IoJ3JhZGl4Mi5lbmNvZGUgaW5wdXQgc2hvdWxkIGJlIFVpbnQ4QXJyYXknKTtcbiAgICAgIHJldHVybiBjb252ZXJ0UmFkaXgyKEFycmF5LmZyb20oYnl0ZXMpLCA4LCBiaXRzLCAhcmV2UGFkZGluZyk7XG4gICAgfSxcbiAgICBkZWNvZGU6IChkaWdpdHM6IG51bWJlcltdKSA9PiB7XG4gICAgICBhbnVtQXJyKCdyYWRpeDIuZGVjb2RlJywgZGlnaXRzKTtcbiAgICAgIHJldHVybiBVaW50OEFycmF5LmZyb20oY29udmVydFJhZGl4MihkaWdpdHMsIGJpdHMsIDgsIHJldlBhZGRpbmcpKTtcbiAgICB9LFxuICB9O1xufVxuXG50eXBlIEFyZ3VtZW50VHlwZXM8RiBleHRlbmRzIEZ1bmN0aW9uPiA9IEYgZXh0ZW5kcyAoLi4uYXJnczogaW5mZXIgQSkgPT4gYW55ID8gQSA6IG5ldmVyO1xuZnVuY3Rpb24gdW5zYWZlV3JhcHBlcjxUIGV4dGVuZHMgKC4uLmFyZ3M6IGFueSkgPT4gYW55PihmbjogVCkge1xuICBhZm4oZm4pO1xuICByZXR1cm4gZnVuY3Rpb24gKC4uLmFyZ3M6IEFyZ3VtZW50VHlwZXM8VD4pOiBSZXR1cm5UeXBlPFQ+IHwgdm9pZCB7XG4gICAgdHJ5IHtcbiAgICAgIHJldHVybiBmbi5hcHBseShudWxsLCBhcmdzKTtcbiAgICB9IGNhdGNoIChlKSB7fVxuICB9O1xufVxuXG5mdW5jdGlvbiBjaGVja3N1bShcbiAgbGVuOiBudW1iZXIsXG4gIGZuOiAoZGF0YTogVWludDhBcnJheSkgPT4gVWludDhBcnJheVxuKTogQ29kZXI8VWludDhBcnJheSwgVWludDhBcnJheT4ge1xuICBhbnVtYmVyKGxlbik7XG4gIGFmbihmbik7XG4gIHJldHVybiB7XG4gICAgZW5jb2RlKGRhdGE6IFVpbnQ4QXJyYXkpIHtcbiAgICAgIGlmICghaXNCeXRlcyhkYXRhKSkgdGhyb3cgbmV3IEVycm9yKCdjaGVja3N1bS5lbmNvZGU6IGlucHV0IHNob3VsZCBiZSBVaW50OEFycmF5Jyk7XG4gICAgICBjb25zdCBzdW0gPSBmbihkYXRhKS5zbGljZSgwLCBsZW4pO1xuICAgICAgY29uc3QgcmVzID0gbmV3IFVpbnQ4QXJyYXkoZGF0YS5sZW5ndGggKyBsZW4pO1xuICAgICAgcmVzLnNldChkYXRhKTtcbiAgICAgIHJlcy5zZXQoc3VtLCBkYXRhLmxlbmd0aCk7XG4gICAgICByZXR1cm4gcmVzO1xuICAgIH0sXG4gICAgZGVjb2RlKGRhdGE6IFVpbnQ4QXJyYXkpIHtcbiAgICAgIGlmICghaXNCeXRlcyhkYXRhKSkgdGhyb3cgbmV3IEVycm9yKCdjaGVja3N1bS5kZWNvZGU6IGlucHV0IHNob3VsZCBiZSBVaW50OEFycmF5Jyk7XG4gICAgICBjb25zdCBwYXlsb2FkID0gZGF0YS5zbGljZSgwLCAtbGVuKTtcbiAgICAgIGNvbnN0IG9sZENoZWNrc3VtID0gZGF0YS5zbGljZSgtbGVuKTtcbiAgICAgIGNvbnN0IG5ld0NoZWNrc3VtID0gZm4ocGF5bG9hZCkuc2xpY2UoMCwgbGVuKTtcbiAgICAgIGZvciAobGV0IGkgPSAwOyBpIDwgbGVuOyBpKyspXG4gICAgICAgIGlmIChuZXdDaGVja3N1bVtpXSAhPT0gb2xkQ2hlY2tzdW1baV0pIHRocm93IG5ldyBFcnJvcignSW52YWxpZCBjaGVja3N1bScpO1xuICAgICAgcmV0dXJuIHBheWxvYWQ7XG4gICAgfSxcbiAgfTtcbn1cblxuLy8gcHJldHRpZXItaWdub3JlXG5leHBvcnQgY29uc3QgdXRpbHM6IHsgYWxwaGFiZXQ6IHR5cGVvZiBhbHBoYWJldDsgY2hhaW46IHR5cGVvZiBjaGFpbjsgY2hlY2tzdW06IHR5cGVvZiBjaGVja3N1bTsgY29udmVydFJhZGl4OiB0eXBlb2YgY29udmVydFJhZGl4OyBjb252ZXJ0UmFkaXgyOiB0eXBlb2YgY29udmVydFJhZGl4MjsgcmFkaXg6IHR5cGVvZiByYWRpeDsgcmFkaXgyOiB0eXBlb2YgcmFkaXgyOyBqb2luOiB0eXBlb2Ygam9pbjsgcGFkZGluZzogdHlwZW9mIHBhZGRpbmc7IH0gPSB7XG4gIGFscGhhYmV0LCBjaGFpbiwgY2hlY2tzdW0sIGNvbnZlcnRSYWRpeCwgY29udmVydFJhZGl4MiwgcmFkaXgsIHJhZGl4Miwgam9pbiwgcGFkZGluZyxcbn07XG5cbi8vIFJGQyA0NjQ4IGFrYSBSRkMgMzU0OFxuLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG5cbi8qKlxuICogYmFzZTE2IGVuY29kaW5nIGZyb20gUkZDIDQ2NDguXG4gKiBAZXhhbXBsZVxuICogYGBganNcbiAqIGJhc2UxNi5lbmNvZGUoVWludDhBcnJheS5mcm9tKFsweDEyLCAweGFiXSkpO1xuICogLy8gPT4gJzEyQUInXG4gKiBgYGBcbiAqL1xuZXhwb3J0IGNvbnN0IGJhc2UxNjogQnl0ZXNDb2RlciA9IGNoYWluKHJhZGl4Mig0KSwgYWxwaGFiZXQoJzAxMjM0NTY3ODlBQkNERUYnKSwgam9pbignJykpO1xuXG4vKipcbiAqIGJhc2UzMiBlbmNvZGluZyBmcm9tIFJGQyA0NjQ4LiBIYXMgcGFkZGluZy5cbiAqIFVzZSBgYmFzZTMybm9wYWRgIGZvciB1bnBhZGRlZCB2ZXJzaW9uLlxuICogQWxzbyBjaGVjayBvdXQgYGJhc2UzMmhleGAsIGBiYXNlMzJoZXhub3BhZGAsIGBiYXNlMzJjcm9ja2ZvcmRgLlxuICogQGV4YW1wbGVcbiAqIGBgYGpzXG4gKiBiYXNlMzIuZW5jb2RlKFVpbnQ4QXJyYXkuZnJvbShbMHgxMiwgMHhhYl0pKTtcbiAqIC8vID0+ICdDS1ZRPT09PSdcbiAqIGJhc2UzMi5kZWNvZGUoJ0NLVlE9PT09Jyk7XG4gKiAvLyA9PiBVaW50OEFycmF5LmZyb20oWzB4MTIsIDB4YWJdKVxuICogYGBgXG4gKi9cbmV4cG9ydCBjb25zdCBiYXNlMzI6IEJ5dGVzQ29kZXIgPSBjaGFpbihcbiAgcmFkaXgyKDUpLFxuICBhbHBoYWJldCgnQUJDREVGR0hJSktMTU5PUFFSU1RVVldYWVoyMzQ1NjcnKSxcbiAgcGFkZGluZyg1KSxcbiAgam9pbignJylcbik7XG5cbi8qKlxuICogYmFzZTMyIGVuY29kaW5nIGZyb20gUkZDIDQ2NDguIE5vIHBhZGRpbmcuXG4gKiBVc2UgYGJhc2UzMmAgZm9yIHBhZGRlZCB2ZXJzaW9uLlxuICogQWxzbyBjaGVjayBvdXQgYGJhc2UzMmhleGAsIGBiYXNlMzJoZXhub3BhZGAsIGBiYXNlMzJjcm9ja2ZvcmRgLlxuICogQGV4YW1wbGVcbiAqIGBgYGpzXG4gKiBiYXNlMzJub3BhZC5lbmNvZGUoVWludDhBcnJheS5mcm9tKFsweDEyLCAweGFiXSkpO1xuICogLy8gPT4gJ0NLVlEnXG4gKiBiYXNlMzJub3BhZC5kZWNvZGUoJ0NLVlEnKTtcbiAqIC8vID0+IFVpbnQ4QXJyYXkuZnJvbShbMHgxMiwgMHhhYl0pXG4gKiBgYGBcbiAqL1xuZXhwb3J0IGNvbnN0IGJhc2UzMm5vcGFkOiBCeXRlc0NvZGVyID0gY2hhaW4oXG4gIHJhZGl4Mig1KSxcbiAgYWxwaGFiZXQoJ0FCQ0RFRkdISUpLTE1OT1BRUlNUVVZXWFlaMjM0NTY3JyksXG4gIGpvaW4oJycpXG4pO1xuLyoqXG4gKiBiYXNlMzIgZW5jb2RpbmcgZnJvbSBSRkMgNDY0OC4gUGFkZGVkLiBDb21wYXJlZCB0byBvcmRpbmFyeSBgYmFzZTMyYCwgc2xpZ2h0bHkgZGlmZmVyZW50IGFscGhhYmV0LlxuICogVXNlIGBiYXNlMzJoZXhub3BhZGAgZm9yIHVucGFkZGVkIHZlcnNpb24uXG4gKiBAZXhhbXBsZVxuICogYGBganNcbiAqIGJhc2UzMmhleC5lbmNvZGUoVWludDhBcnJheS5mcm9tKFsweDEyLCAweGFiXSkpO1xuICogLy8gPT4gJzJBTEc9PT09J1xuICogYmFzZTMyaGV4LmRlY29kZSgnMkFMRz09PT0nKTtcbiAqIC8vID0+IFVpbnQ4QXJyYXkuZnJvbShbMHgxMiwgMHhhYl0pXG4gKiBgYGBcbiAqL1xuZXhwb3J0IGNvbnN0IGJhc2UzMmhleDogQnl0ZXNDb2RlciA9IGNoYWluKFxuICByYWRpeDIoNSksXG4gIGFscGhhYmV0KCcwMTIzNDU2Nzg5QUJDREVGR0hJSktMTU5PUFFSU1RVVicpLFxuICBwYWRkaW5nKDUpLFxuICBqb2luKCcnKVxuKTtcblxuLyoqXG4gKiBiYXNlMzIgZW5jb2RpbmcgZnJvbSBSRkMgNDY0OC4gTm8gcGFkZGluZy4gQ29tcGFyZWQgdG8gb3JkaW5hcnkgYGJhc2UzMmAsIHNsaWdodGx5IGRpZmZlcmVudCBhbHBoYWJldC5cbiAqIFVzZSBgYmFzZTMyaGV4YCBmb3IgcGFkZGVkIHZlcnNpb24uXG4gKiBAZXhhbXBsZVxuICogYGBganNcbiAqIGJhc2UzMmhleG5vcGFkLmVuY29kZShVaW50OEFycmF5LmZyb20oWzB4MTIsIDB4YWJdKSk7XG4gKiAvLyA9PiAnMkFMRydcbiAqIGJhc2UzMmhleG5vcGFkLmRlY29kZSgnMkFMRycpO1xuICogLy8gPT4gVWludDhBcnJheS5mcm9tKFsweDEyLCAweGFiXSlcbiAqIGBgYFxuICovXG5leHBvcnQgY29uc3QgYmFzZTMyaGV4bm9wYWQ6IEJ5dGVzQ29kZXIgPSBjaGFpbihcbiAgcmFkaXgyKDUpLFxuICBhbHBoYWJldCgnMDEyMzQ1Njc4OUFCQ0RFRkdISUpLTE1OT1BRUlNUVVYnKSxcbiAgam9pbignJylcbik7XG4vKipcbiAqIGJhc2UzMiBlbmNvZGluZyBmcm9tIFJGQyA0NjQ4LiBEb3VnIENyb2NrZm9yZCdzIHZlcnNpb24uXG4gKiBodHRwczovL3d3dy5jcm9ja2ZvcmQuY29tL2Jhc2UzMi5odG1sXG4gKiBAZXhhbXBsZVxuICogYGBganNcbiAqIGJhc2UzMmNyb2NrZm9yZC5lbmNvZGUoVWludDhBcnJheS5mcm9tKFsweDEyLCAweGFiXSkpO1xuICogLy8gPT4gJzJBTkcnXG4gKiBiYXNlMzJjcm9ja2ZvcmQuZGVjb2RlKCcyQU5HJyk7XG4gKiAvLyA9PiBVaW50OEFycmF5LmZyb20oWzB4MTIsIDB4YWJdKVxuICogYGBgXG4gKi9cbmV4cG9ydCBjb25zdCBiYXNlMzJjcm9ja2ZvcmQ6IEJ5dGVzQ29kZXIgPSBjaGFpbihcbiAgcmFkaXgyKDUpLFxuICBhbHBoYWJldCgnMDEyMzQ1Njc4OUFCQ0RFRkdISktNTlBRUlNUVldYWVonKSxcbiAgam9pbignJyksXG4gIG5vcm1hbGl6ZSgoczogc3RyaW5nKSA9PiBzLnRvVXBwZXJDYXNlKCkucmVwbGFjZSgvTy9nLCAnMCcpLnJlcGxhY2UoL1tJTF0vZywgJzEnKSlcbik7XG5cbi8vIEJ1aWx0LWluIGJhc2U2NCBjb252ZXJzaW9uIGh0dHBzOi8vY2FuaXVzZS5jb20vbWRuLWphdmFzY3JpcHRfYnVpbHRpbnNfdWludDhhcnJheV9mcm9tYmFzZTY0XG4vLyBwcmV0dGllci1pZ25vcmVcbmNvbnN0IGhhc0Jhc2U2NEJ1aWx0aW46IGJvb2xlYW4gPSAvKiBAX19QVVJFX18gKi8gKCgpID0+XG4gIHR5cGVvZiAoVWludDhBcnJheSBhcyBhbnkpLmZyb20oW10pLnRvQmFzZTY0ID09PSAnZnVuY3Rpb24nICYmXG4gIHR5cGVvZiAoVWludDhBcnJheSBhcyBhbnkpLmZyb21CYXNlNjQgPT09ICdmdW5jdGlvbicpKCk7XG5cbmNvbnN0IGRlY29kZUJhc2U2NEJ1aWx0aW4gPSAoczogc3RyaW5nLCBpc1VybDogYm9vbGVhbikgPT4ge1xuICBhc3RyKCdiYXNlNjQnLCBzKTtcbiAgY29uc3QgcmUgPSBpc1VybCA/IC9eW0EtWmEtejAtOT1fLV0rJC8gOiAvXltBLVphLXowLTk9Ky9dKyQvO1xuICBjb25zdCBhbHBoYWJldCA9IGlzVXJsID8gJ2Jhc2U2NHVybCcgOiAnYmFzZTY0JztcbiAgaWYgKHMubGVuZ3RoID4gMCAmJiAhcmUudGVzdChzKSkgdGhyb3cgbmV3IEVycm9yKCdpbnZhbGlkIGJhc2U2NCcpO1xuICByZXR1cm4gKFVpbnQ4QXJyYXkgYXMgYW55KS5mcm9tQmFzZTY0KHMsIHsgYWxwaGFiZXQsIGxhc3RDaHVua0hhbmRsaW5nOiAnc3RyaWN0JyB9KTtcbn07XG5cbi8qKlxuICogYmFzZTY0IGZyb20gUkZDIDQ2NDguIFBhZGRlZC5cbiAqIFVzZSBgYmFzZTY0bm9wYWRgIGZvciB1bnBhZGRlZCB2ZXJzaW9uLlxuICogQWxzbyBjaGVjayBvdXQgYGJhc2U2NHVybGAsIGBiYXNlNjR1cmxub3BhZGAuXG4gKiBGYWxscyBiYWNrIHRvIGJ1aWx0LWluIGZ1bmN0aW9uLCB3aGVuIGF2YWlsYWJsZS5cbiAqIEBleGFtcGxlXG4gKiBgYGBqc1xuICogYmFzZTY0LmVuY29kZShVaW50OEFycmF5LmZyb20oWzB4MTIsIDB4YWJdKSk7XG4gKiAvLyA9PiAnRXFzPSdcbiAqIGJhc2U2NC5kZWNvZGUoJ0Vxcz0nKTtcbiAqIC8vID0+IFVpbnQ4QXJyYXkuZnJvbShbMHgxMiwgMHhhYl0pXG4gKiBgYGBcbiAqL1xuLy8gcHJldHRpZXItaWdub3JlXG5leHBvcnQgY29uc3QgYmFzZTY0OiBCeXRlc0NvZGVyID0gaGFzQmFzZTY0QnVpbHRpbiA/IHtcbiAgZW5jb2RlKGIpIHsgYWJ5dGVzKGIpOyByZXR1cm4gKGIgYXMgYW55KS50b0Jhc2U2NCgpOyB9LFxuICBkZWNvZGUocykgeyByZXR1cm4gZGVjb2RlQmFzZTY0QnVpbHRpbihzLCBmYWxzZSk7IH0sXG59IDogY2hhaW4oXG4gIHJhZGl4Mig2KSxcbiAgYWxwaGFiZXQoJ0FCQ0RFRkdISUpLTE1OT1BRUlNUVVZXWFlaYWJjZGVmZ2hpamtsbW5vcHFyc3R1dnd4eXowMTIzNDU2Nzg5Ky8nKSxcbiAgcGFkZGluZyg2KSxcbiAgam9pbignJylcbik7XG4vKipcbiAqIGJhc2U2NCBmcm9tIFJGQyA0NjQ4LiBObyBwYWRkaW5nLlxuICogVXNlIGBiYXNlNjRgIGZvciBwYWRkZWQgdmVyc2lvbi5cbiAqIEBleGFtcGxlXG4gKiBgYGBqc1xuICogYmFzZTY0bm9wYWQuZW5jb2RlKFVpbnQ4QXJyYXkuZnJvbShbMHgxMiwgMHhhYl0pKTtcbiAqIC8vID0+ICdFcXMnXG4gKiBiYXNlNjRub3BhZC5kZWNvZGUoJ0VxcycpO1xuICogLy8gPT4gVWludDhBcnJheS5mcm9tKFsweDEyLCAweGFiXSlcbiAqIGBgYFxuICovXG5leHBvcnQgY29uc3QgYmFzZTY0bm9wYWQ6IEJ5dGVzQ29kZXIgPSBjaGFpbihcbiAgcmFkaXgyKDYpLFxuICBhbHBoYWJldCgnQUJDREVGR0hJSktMTU5PUFFSU1RVVldYWVphYmNkZWZnaGlqa2xtbm9wcXJzdHV2d3h5ejAxMjM0NTY3ODkrLycpLFxuICBqb2luKCcnKVxuKTtcblxuLyoqXG4gKiBiYXNlNjQgZnJvbSBSRkMgNDY0OCwgdXNpbmcgVVJMLXNhZmUgYWxwaGFiZXQuIFBhZGRlZC5cbiAqIFVzZSBgYmFzZTY0dXJsbm9wYWRgIGZvciB1bnBhZGRlZCB2ZXJzaW9uLlxuICogRmFsbHMgYmFjayB0byBidWlsdC1pbiBmdW5jdGlvbiwgd2hlbiBhdmFpbGFibGUuXG4gKiBAZXhhbXBsZVxuICogYGBganNcbiAqIGJhc2U2NHVybC5lbmNvZGUoVWludDhBcnJheS5mcm9tKFsweDEyLCAweGFiXSkpO1xuICogLy8gPT4gJ0Vxcz0nXG4gKiBiYXNlNjR1cmwuZGVjb2RlKCdFcXM9Jyk7XG4gKiAvLyA9PiBVaW50OEFycmF5LmZyb20oWzB4MTIsIDB4YWJdKVxuICogYGBgXG4gKi9cbi8vIHByZXR0aWVyLWlnbm9yZVxuZXhwb3J0IGNvbnN0IGJhc2U2NHVybDogQnl0ZXNDb2RlciA9IGhhc0Jhc2U2NEJ1aWx0aW4gPyB7XG4gIGVuY29kZShiKSB7IGFieXRlcyhiKTsgcmV0dXJuIChiIGFzIGFueSkudG9CYXNlNjQoeyBhbHBoYWJldDogJ2Jhc2U2NHVybCcgfSk7IH0sXG4gIGRlY29kZShzKSB7IHJldHVybiBkZWNvZGVCYXNlNjRCdWlsdGluKHMsIHRydWUpOyB9LFxufSA6IGNoYWluKFxuICByYWRpeDIoNiksXG4gIGFscGhhYmV0KCdBQkNERUZHSElKS0xNTk9QUVJTVFVWV1hZWmFiY2RlZmdoaWprbG1ub3BxcnN0dXZ3eHl6MDEyMzQ1Njc4OS1fJyksXG4gIHBhZGRpbmcoNiksXG4gIGpvaW4oJycpXG4pO1xuXG4vKipcbiAqIGJhc2U2NCBmcm9tIFJGQyA0NjQ4LCB1c2luZyBVUkwtc2FmZSBhbHBoYWJldC4gTm8gcGFkZGluZy5cbiAqIFVzZSBgYmFzZTY0dXJsYCBmb3IgcGFkZGVkIHZlcnNpb24uXG4gKiBAZXhhbXBsZVxuICogYGBganNcbiAqIGJhc2U2NHVybG5vcGFkLmVuY29kZShVaW50OEFycmF5LmZyb20oWzB4MTIsIDB4YWJdKSk7XG4gKiAvLyA9PiAnRXFzJ1xuICogYmFzZTY0dXJsbm9wYWQuZGVjb2RlKCdFcXMnKTtcbiAqIC8vID0+IFVpbnQ4QXJyYXkuZnJvbShbMHgxMiwgMHhhYl0pXG4gKiBgYGBcbiAqL1xuZXhwb3J0IGNvbnN0IGJhc2U2NHVybG5vcGFkOiBCeXRlc0NvZGVyID0gY2hhaW4oXG4gIHJhZGl4Mig2KSxcbiAgYWxwaGFiZXQoJ0FCQ0RFRkdISUpLTE1OT1BRUlNUVVZXWFlaYWJjZGVmZ2hpamtsbW5vcHFyc3R1dnd4eXowMTIzNDU2Nzg5LV8nKSxcbiAgam9pbignJylcbik7XG5cbi8vIGJhc2U1OCBjb2RlXG4vLyAtLS0tLS0tLS0tLVxuY29uc3QgZ2VuQmFzZTU4ID0gLyogQF9fTk9fU0lERV9FRkZFQ1RTX18gKi8gKGFiYzogc3RyaW5nKSA9PlxuICBjaGFpbihyYWRpeCg1OCksIGFscGhhYmV0KGFiYyksIGpvaW4oJycpKTtcblxuLyoqXG4gKiBiYXNlNTg6IGJhc2U2NCB3aXRob3V0IGFtYmlnb3VzIGNoYXJhY3RlcnMgKywgLywgMCwgTywgSSwgbC5cbiAqIFF1YWRyYXRpYyAoTyhuXjIpKSAtIHNvLCBjYW4ndCBiZSB1c2VkIG9uIGxhcmdlIGlucHV0cy5cbiAqIEBleGFtcGxlXG4gKiBgYGBqc1xuICogYmFzZTU4LmRlY29kZSgnMDFhYmNkZWYnKTtcbiAqIC8vID0+ICczVWhKVydcbiAqIGBgYFxuICovXG5leHBvcnQgY29uc3QgYmFzZTU4OiBCeXRlc0NvZGVyID0gZ2VuQmFzZTU4KFxuICAnMTIzNDU2Nzg5QUJDREVGR0hKS0xNTlBRUlNUVVZXWFlaYWJjZGVmZ2hpamttbm9wcXJzdHV2d3h5eidcbik7XG4vKipcbiAqIGJhc2U1ODogZmxpY2tyIHZlcnNpb24uIENoZWNrIG91dCBgYmFzZTU4YC5cbiAqL1xuZXhwb3J0IGNvbnN0IGJhc2U1OGZsaWNrcjogQnl0ZXNDb2RlciA9IGdlbkJhc2U1OChcbiAgJzEyMzQ1Njc4OWFiY2RlZmdoaWprbW5vcHFyc3R1dnd4eXpBQkNERUZHSEpLTE1OUFFSU1RVVldYWVonXG4pO1xuLyoqXG4gKiBiYXNlNTg6IFhSUCB2ZXJzaW9uLiBDaGVjayBvdXQgYGJhc2U1OGAuXG4gKi9cbmV4cG9ydCBjb25zdCBiYXNlNTh4cnA6IEJ5dGVzQ29kZXIgPSBnZW5CYXNlNTgoXG4gICdycHNobmFmMzl3QlVETkVHSEpLTE00UFFSU1Q3VldYWVoyYmNkZUNnNjVqa204b0ZxaTF0dXZBeHl6J1xuKTtcblxuLy8gRGF0YSBsZW4gKGluZGV4KSAtPiBlbmNvZGVkIGJsb2NrIGxlblxuY29uc3QgWE1SX0JMT0NLX0xFTiA9IFswLCAyLCAzLCA1LCA2LCA3LCA5LCAxMCwgMTFdO1xuXG4vKipcbiAqIGJhc2U1ODogWE1SIHZlcnNpb24uIENoZWNrIG91dCBgYmFzZTU4YC5cbiAqIERvbmUgaW4gOC1ieXRlIGJsb2NrcyAod2hpY2ggZXF1YWxzIDExIGNoYXJzIGluIGRlY29kaW5nKS4gTGFzdCAobm9uLWZ1bGwpIGJsb2NrIHBhZGRlZCB3aXRoICcxJyB0byBzaXplIGluIFhNUl9CTE9DS19MRU4uXG4gKiBCbG9jayBlbmNvZGluZyBzaWduaWZpY2FudGx5IHJlZHVjZXMgcXVhZHJhdGljIGNvbXBsZXhpdHkgb2YgYmFzZTU4LlxuICovXG5leHBvcnQgY29uc3QgYmFzZTU4eG1yOiBCeXRlc0NvZGVyID0ge1xuICBlbmNvZGUoZGF0YTogVWludDhBcnJheSkge1xuICAgIGxldCByZXMgPSAnJztcbiAgICBmb3IgKGxldCBpID0gMDsgaSA8IGRhdGEubGVuZ3RoOyBpICs9IDgpIHtcbiAgICAgIGNvbnN0IGJsb2NrID0gZGF0YS5zdWJhcnJheShpLCBpICsgOCk7XG4gICAgICByZXMgKz0gYmFzZTU4LmVuY29kZShibG9jaykucGFkU3RhcnQoWE1SX0JMT0NLX0xFTltibG9jay5sZW5ndGhdISwgJzEnKTtcbiAgICB9XG4gICAgcmV0dXJuIHJlcztcbiAgfSxcbiAgZGVjb2RlKHN0cjogc3RyaW5nKSB7XG4gICAgbGV0IHJlczogbnVtYmVyW10gPSBbXTtcbiAgICBmb3IgKGxldCBpID0gMDsgaSA8IHN0ci5sZW5ndGg7IGkgKz0gMTEpIHtcbiAgICAgIGNvbnN0IHNsaWNlID0gc3RyLnNsaWNlKGksIGkgKyAxMSk7XG4gICAgICBjb25zdCBibG9ja0xlbiA9IFhNUl9CTE9DS19MRU4uaW5kZXhPZihzbGljZS5sZW5ndGgpO1xuICAgICAgY29uc3QgYmxvY2sgPSBiYXNlNTguZGVjb2RlKHNsaWNlKTtcbiAgICAgIGZvciAobGV0IGogPSAwOyBqIDwgYmxvY2subGVuZ3RoIC0gYmxvY2tMZW47IGorKykge1xuICAgICAgICBpZiAoYmxvY2tbal0gIT09IDApIHRocm93IG5ldyBFcnJvcignYmFzZTU4eG1yOiB3cm9uZyBwYWRkaW5nJyk7XG4gICAgICB9XG4gICAgICByZXMgPSByZXMuY29uY2F0KEFycmF5LmZyb20oYmxvY2suc2xpY2UoYmxvY2subGVuZ3RoIC0gYmxvY2tMZW4pKSk7XG4gICAgfVxuICAgIHJldHVybiBVaW50OEFycmF5LmZyb20ocmVzKTtcbiAgfSxcbn07XG5cbi8qKlxuICogTWV0aG9kLCB3aGljaCBjcmVhdGVzIGJhc2U1OGNoZWNrIGVuY29kZXIuXG4gKiBSZXF1aXJlcyBmdW5jdGlvbiwgY2FsY3VsYXRpbmcgc2hhMjU2LlxuICovXG5leHBvcnQgY29uc3QgY3JlYXRlQmFzZTU4Y2hlY2sgPSAoc2hhMjU2OiAoZGF0YTogVWludDhBcnJheSkgPT4gVWludDhBcnJheSk6IEJ5dGVzQ29kZXIgPT5cbiAgY2hhaW4oXG4gICAgY2hlY2tzdW0oNCwgKGRhdGEpID0+IHNoYTI1NihzaGEyNTYoZGF0YSkpKSxcbiAgICBiYXNlNThcbiAgKTtcblxuLyoqXG4gKiBVc2UgYGNyZWF0ZUJhc2U1OGNoZWNrYCBpbnN0ZWFkLlxuICogQGRlcHJlY2F0ZWRcbiAqL1xuZXhwb3J0IGNvbnN0IGJhc2U1OGNoZWNrOiAoc2hhMjU2OiAoZGF0YTogVWludDhBcnJheSkgPT4gVWludDhBcnJheSkgPT4gQnl0ZXNDb2RlciA9XG4gIGNyZWF0ZUJhc2U1OGNoZWNrO1xuXG4vLyBCZWNoMzIgY29kZVxuLy8gLS0tLS0tLS0tLS1cbmV4cG9ydCBpbnRlcmZhY2UgQmVjaDMyRGVjb2RlZDxQcmVmaXggZXh0ZW5kcyBzdHJpbmcgPSBzdHJpbmc+IHtcbiAgcHJlZml4OiBQcmVmaXg7XG4gIHdvcmRzOiBudW1iZXJbXTtcbn1cbmV4cG9ydCBpbnRlcmZhY2UgQmVjaDMyRGVjb2RlZFdpdGhBcnJheTxQcmVmaXggZXh0ZW5kcyBzdHJpbmcgPSBzdHJpbmc+IHtcbiAgcHJlZml4OiBQcmVmaXg7XG4gIHdvcmRzOiBudW1iZXJbXTtcbiAgYnl0ZXM6IFVpbnQ4QXJyYXk7XG59XG5cbmNvbnN0IEJFQ0hfQUxQSEFCRVQ6IENvZGVyPG51bWJlcltdLCBzdHJpbmc+ID0gY2hhaW4oXG4gIGFscGhhYmV0KCdxcHpyeTl4OGdmMnR2ZHcwczNqbjU0a2hjZTZtdWE3bCcpLFxuICBqb2luKCcnKVxuKTtcblxuY29uc3QgUE9MWU1PRF9HRU5FUkFUT1JTID0gWzB4M2I2YTU3YjIsIDB4MjY1MDhlNmQsIDB4MWVhMTE5ZmEsIDB4M2Q0MjMzZGQsIDB4MmExNDYyYjNdO1xuZnVuY3Rpb24gYmVjaDMyUG9seW1vZChwcmU6IG51bWJlcik6IG51bWJlciB7XG4gIGNvbnN0IGIgPSBwcmUgPj4gMjU7XG4gIGxldCBjaGsgPSAocHJlICYgMHgxZmZmZmZmKSA8PCA1O1xuICBmb3IgKGxldCBpID0gMDsgaSA8IFBPTFlNT0RfR0VORVJBVE9SUy5sZW5ndGg7IGkrKykge1xuICAgIGlmICgoKGIgPj4gaSkgJiAxKSA9PT0gMSkgY2hrIF49IFBPTFlNT0RfR0VORVJBVE9SU1tpXSE7XG4gIH1cbiAgcmV0dXJuIGNoaztcbn1cblxuZnVuY3Rpb24gYmVjaENoZWNrc3VtKHByZWZpeDogc3RyaW5nLCB3b3JkczogbnVtYmVyW10sIGVuY29kaW5nQ29uc3QgPSAxKTogc3RyaW5nIHtcbiAgY29uc3QgbGVuID0gcHJlZml4Lmxlbmd0aDtcbiAgbGV0IGNoayA9IDE7XG4gIGZvciAobGV0IGkgPSAwOyBpIDwgbGVuOyBpKyspIHtcbiAgICBjb25zdCBjID0gcHJlZml4LmNoYXJDb2RlQXQoaSk7XG4gICAgaWYgKGMgPCAzMyB8fCBjID4gMTI2KSB0aHJvdyBuZXcgRXJyb3IoYEludmFsaWQgcHJlZml4ICgke3ByZWZpeH0pYCk7XG4gICAgY2hrID0gYmVjaDMyUG9seW1vZChjaGspIF4gKGMgPj4gNSk7XG4gIH1cbiAgY2hrID0gYmVjaDMyUG9seW1vZChjaGspO1xuICBmb3IgKGxldCBpID0gMDsgaSA8IGxlbjsgaSsrKSBjaGsgPSBiZWNoMzJQb2x5bW9kKGNoaykgXiAocHJlZml4LmNoYXJDb2RlQXQoaSkgJiAweDFmKTtcbiAgZm9yIChsZXQgdiBvZiB3b3JkcykgY2hrID0gYmVjaDMyUG9seW1vZChjaGspIF4gdjtcbiAgZm9yIChsZXQgaSA9IDA7IGkgPCA2OyBpKyspIGNoayA9IGJlY2gzMlBvbHltb2QoY2hrKTtcbiAgY2hrIF49IGVuY29kaW5nQ29uc3Q7XG4gIHJldHVybiBCRUNIX0FMUEhBQkVULmVuY29kZShjb252ZXJ0UmFkaXgyKFtjaGsgJSBwb3dlcnNbMzBdIV0sIDMwLCA1LCBmYWxzZSkpO1xufVxuXG5leHBvcnQgaW50ZXJmYWNlIEJlY2gzMiB7XG4gIGVuY29kZTxQcmVmaXggZXh0ZW5kcyBzdHJpbmc+KFxuICAgIHByZWZpeDogUHJlZml4LFxuICAgIHdvcmRzOiBudW1iZXJbXSB8IFVpbnQ4QXJyYXksXG4gICAgbGltaXQ/OiBudW1iZXIgfCBmYWxzZVxuICApOiBgJHtMb3dlcmNhc2U8UHJlZml4Pn0xJHtzdHJpbmd9YDtcbiAgZGVjb2RlPFByZWZpeCBleHRlbmRzIHN0cmluZz4oXG4gICAgc3RyOiBgJHtQcmVmaXh9MSR7c3RyaW5nfWAsXG4gICAgbGltaXQ/OiBudW1iZXIgfCBmYWxzZVxuICApOiBCZWNoMzJEZWNvZGVkPFByZWZpeD47XG4gIGVuY29kZUZyb21CeXRlcyhwcmVmaXg6IHN0cmluZywgYnl0ZXM6IFVpbnQ4QXJyYXkpOiBzdHJpbmc7XG4gIGRlY29kZVRvQnl0ZXMoc3RyOiBzdHJpbmcpOiBCZWNoMzJEZWNvZGVkV2l0aEFycmF5O1xuICBkZWNvZGVVbnNhZmUoc3RyOiBzdHJpbmcsIGxpbWl0PzogbnVtYmVyIHwgZmFsc2UpOiB2b2lkIHwgQmVjaDMyRGVjb2RlZDxzdHJpbmc+O1xuICBmcm9tV29yZHModG86IG51bWJlcltdKTogVWludDhBcnJheTtcbiAgZnJvbVdvcmRzVW5zYWZlKHRvOiBudW1iZXJbXSk6IHZvaWQgfCBVaW50OEFycmF5O1xuICB0b1dvcmRzKGZyb206IFVpbnQ4QXJyYXkpOiBudW1iZXJbXTtcbn1cbi8qKlxuICogQF9fTk9fU0lERV9FRkZFQ1RTX19cbiAqL1xuZnVuY3Rpb24gZ2VuQmVjaDMyKGVuY29kaW5nOiAnYmVjaDMyJyB8ICdiZWNoMzJtJyk6IEJlY2gzMiB7XG4gIGNvbnN0IEVOQ09ESU5HX0NPTlNUID0gZW5jb2RpbmcgPT09ICdiZWNoMzInID8gMSA6IDB4MmJjODMwYTM7XG4gIGNvbnN0IF93b3JkcyA9IHJhZGl4Mig1KTtcbiAgY29uc3QgZnJvbVdvcmRzID0gX3dvcmRzLmRlY29kZTtcbiAgY29uc3QgdG9Xb3JkcyA9IF93b3Jkcy5lbmNvZGU7XG4gIGNvbnN0IGZyb21Xb3Jkc1Vuc2FmZSA9IHVuc2FmZVdyYXBwZXIoZnJvbVdvcmRzKTtcblxuICBmdW5jdGlvbiBlbmNvZGU8UHJlZml4IGV4dGVuZHMgc3RyaW5nPihcbiAgICBwcmVmaXg6IFByZWZpeCxcbiAgICB3b3JkczogbnVtYmVyW10gfCBVaW50OEFycmF5LFxuICAgIGxpbWl0OiBudW1iZXIgfCBmYWxzZSA9IDkwXG4gICk6IGAke0xvd2VyY2FzZTxQcmVmaXg+fTEke3N0cmluZ31gIHtcbiAgICBhc3RyKCdiZWNoMzIuZW5jb2RlIHByZWZpeCcsIHByZWZpeCk7XG4gICAgaWYgKGlzQnl0ZXMod29yZHMpKSB3b3JkcyA9IEFycmF5LmZyb20od29yZHMpO1xuICAgIGFudW1BcnIoJ2JlY2gzMi5lbmNvZGUnLCB3b3Jkcyk7XG4gICAgY29uc3QgcGxlbiA9IHByZWZpeC5sZW5ndGg7XG4gICAgaWYgKHBsZW4gPT09IDApIHRocm93IG5ldyBUeXBlRXJyb3IoYEludmFsaWQgcHJlZml4IGxlbmd0aCAke3BsZW59YCk7XG4gICAgY29uc3QgYWN0dWFsTGVuZ3RoID0gcGxlbiArIDcgKyB3b3Jkcy5sZW5ndGg7XG4gICAgaWYgKGxpbWl0ICE9PSBmYWxzZSAmJiBhY3R1YWxMZW5ndGggPiBsaW1pdClcbiAgICAgIHRocm93IG5ldyBUeXBlRXJyb3IoYExlbmd0aCAke2FjdHVhbExlbmd0aH0gZXhjZWVkcyBsaW1pdCAke2xpbWl0fWApO1xuICAgIGNvbnN0IGxvd2VyZWQgPSBwcmVmaXgudG9Mb3dlckNhc2UoKTtcbiAgICBjb25zdCBzdW0gPSBiZWNoQ2hlY2tzdW0obG93ZXJlZCwgd29yZHMsIEVOQ09ESU5HX0NPTlNUKTtcbiAgICByZXR1cm4gYCR7bG93ZXJlZH0xJHtCRUNIX0FMUEhBQkVULmVuY29kZSh3b3Jkcyl9JHtzdW19YCBhcyBgJHtMb3dlcmNhc2U8UHJlZml4Pn0xJHtzdHJpbmd9YDtcbiAgfVxuXG4gIGZ1bmN0aW9uIGRlY29kZTxQcmVmaXggZXh0ZW5kcyBzdHJpbmc+KFxuICAgIHN0cjogYCR7UHJlZml4fTEke3N0cmluZ31gLFxuICAgIGxpbWl0PzogbnVtYmVyIHwgZmFsc2VcbiAgKTogQmVjaDMyRGVjb2RlZDxQcmVmaXg+O1xuICBmdW5jdGlvbiBkZWNvZGUoc3RyOiBzdHJpbmcsIGxpbWl0PzogbnVtYmVyIHwgZmFsc2UpOiBCZWNoMzJEZWNvZGVkO1xuICBmdW5jdGlvbiBkZWNvZGUoc3RyOiBzdHJpbmcsIGxpbWl0OiBudW1iZXIgfCBmYWxzZSA9IDkwKTogQmVjaDMyRGVjb2RlZCB7XG4gICAgYXN0cignYmVjaDMyLmRlY29kZSBpbnB1dCcsIHN0cik7XG4gICAgY29uc3Qgc2xlbiA9IHN0ci5sZW5ndGg7XG4gICAgaWYgKHNsZW4gPCA4IHx8IChsaW1pdCAhPT0gZmFsc2UgJiYgc2xlbiA+IGxpbWl0KSlcbiAgICAgIHRocm93IG5ldyBUeXBlRXJyb3IoYGludmFsaWQgc3RyaW5nIGxlbmd0aDogJHtzbGVufSAoJHtzdHJ9KS4gRXhwZWN0ZWQgKDguLiR7bGltaXR9KWApO1xuICAgIC8vIGRvbid0IGFsbG93IG1peGVkIGNhc2VcbiAgICBjb25zdCBsb3dlcmVkID0gc3RyLnRvTG93ZXJDYXNlKCk7XG4gICAgaWYgKHN0ciAhPT0gbG93ZXJlZCAmJiBzdHIgIT09IHN0ci50b1VwcGVyQ2FzZSgpKVxuICAgICAgdGhyb3cgbmV3IEVycm9yKGBTdHJpbmcgbXVzdCBiZSBsb3dlcmNhc2Ugb3IgdXBwZXJjYXNlYCk7XG4gICAgY29uc3Qgc2VwSW5kZXggPSBsb3dlcmVkLmxhc3RJbmRleE9mKCcxJyk7XG4gICAgaWYgKHNlcEluZGV4ID09PSAwIHx8IHNlcEluZGV4ID09PSAtMSlcbiAgICAgIHRocm93IG5ldyBFcnJvcihgTGV0dGVyIFwiMVwiIG11c3QgYmUgcHJlc2VudCBiZXR3ZWVuIHByZWZpeCBhbmQgZGF0YSBvbmx5YCk7XG4gICAgY29uc3QgcHJlZml4ID0gbG93ZXJlZC5zbGljZSgwLCBzZXBJbmRleCk7XG4gICAgY29uc3QgZGF0YSA9IGxvd2VyZWQuc2xpY2Uoc2VwSW5kZXggKyAxKTtcbiAgICBpZiAoZGF0YS5sZW5ndGggPCA2KSB0aHJvdyBuZXcgRXJyb3IoJ0RhdGEgbXVzdCBiZSBhdCBsZWFzdCA2IGNoYXJhY3RlcnMgbG9uZycpO1xuICAgIGNvbnN0IHdvcmRzID0gQkVDSF9BTFBIQUJFVC5kZWNvZGUoZGF0YSkuc2xpY2UoMCwgLTYpO1xuICAgIGNvbnN0IHN1bSA9IGJlY2hDaGVja3N1bShwcmVmaXgsIHdvcmRzLCBFTkNPRElOR19DT05TVCk7XG4gICAgaWYgKCFkYXRhLmVuZHNXaXRoKHN1bSkpIHRocm93IG5ldyBFcnJvcihgSW52YWxpZCBjaGVja3N1bSBpbiAke3N0cn06IGV4cGVjdGVkIFwiJHtzdW19XCJgKTtcbiAgICByZXR1cm4geyBwcmVmaXgsIHdvcmRzIH07XG4gIH1cblxuICBjb25zdCBkZWNvZGVVbnNhZmUgPSB1bnNhZmVXcmFwcGVyKGRlY29kZSk7XG5cbiAgZnVuY3Rpb24gZGVjb2RlVG9CeXRlcyhzdHI6IHN0cmluZyk6IEJlY2gzMkRlY29kZWRXaXRoQXJyYXkge1xuICAgIGNvbnN0IHsgcHJlZml4LCB3b3JkcyB9ID0gZGVjb2RlKHN0ciwgZmFsc2UpO1xuICAgIHJldHVybiB7IHByZWZpeCwgd29yZHMsIGJ5dGVzOiBmcm9tV29yZHMod29yZHMpIH07XG4gIH1cblxuICBmdW5jdGlvbiBlbmNvZGVGcm9tQnl0ZXMocHJlZml4OiBzdHJpbmcsIGJ5dGVzOiBVaW50OEFycmF5KSB7XG4gICAgcmV0dXJuIGVuY29kZShwcmVmaXgsIHRvV29yZHMoYnl0ZXMpKTtcbiAgfVxuXG4gIHJldHVybiB7XG4gICAgZW5jb2RlLFxuICAgIGRlY29kZSxcbiAgICBlbmNvZGVGcm9tQnl0ZXMsXG4gICAgZGVjb2RlVG9CeXRlcyxcbiAgICBkZWNvZGVVbnNhZmUsXG4gICAgZnJvbVdvcmRzLFxuICAgIGZyb21Xb3Jkc1Vuc2FmZSxcbiAgICB0b1dvcmRzLFxuICB9O1xufVxuXG4vKipcbiAqIGJlY2gzMiBmcm9tIEJJUCAxNzMuIE9wZXJhdGVzIG9uIHdvcmRzLlxuICogRm9yIGhpZ2gtbGV2ZWwsIGNoZWNrIG91dCBzY3VyZS1idGMtc2lnbmVyOlxuICogaHR0cHM6Ly9naXRodWIuY29tL3BhdWxtaWxsci9zY3VyZS1idGMtc2lnbmVyLlxuICovXG5leHBvcnQgY29uc3QgYmVjaDMyOiBCZWNoMzIgPSBnZW5CZWNoMzIoJ2JlY2gzMicpO1xuXG4vKipcbiAqIGJlY2gzMm0gZnJvbSBCSVAgMzUwLiBPcGVyYXRlcyBvbiB3b3Jkcy5cbiAqIEl0IHdhcyB0byBtaXRpZ2F0ZSBgYmVjaDMyYCB3ZWFrbmVzc2VzLlxuICogRm9yIGhpZ2gtbGV2ZWwsIGNoZWNrIG91dCBzY3VyZS1idGMtc2lnbmVyOlxuICogaHR0cHM6Ly9naXRodWIuY29tL3BhdWxtaWxsci9zY3VyZS1idGMtc2lnbmVyLlxuICovXG5leHBvcnQgY29uc3QgYmVjaDMybTogQmVjaDMyID0gZ2VuQmVjaDMyKCdiZWNoMzJtJyk7XG5cbmRlY2xhcmUgY29uc3QgVGV4dEVuY29kZXI6IGFueTtcbmRlY2xhcmUgY29uc3QgVGV4dERlY29kZXI6IGFueTtcblxuLyoqXG4gKiBVVEYtOC10by1ieXRlIGRlY29kZXIuIFVzZXMgYnVpbHQtaW4gVGV4dERlY29kZXIgLyBUZXh0RW5jb2Rlci5cbiAqIEBleGFtcGxlXG4gKiBgYGBqc1xuICogY29uc3QgYiA9IHV0ZjguZGVjb2RlKFwiaGV5XCIpOyAvLyA9PiBuZXcgVWludDhBcnJheShbIDEwNCwgMTAxLCAxMjEgXSlcbiAqIGNvbnN0IHN0ciA9IHV0ZjguZW5jb2RlKGIpOyAvLyBcImhleVwiXG4gKiBgYGBcbiAqL1xuZXhwb3J0IGNvbnN0IHV0Zjg6IEJ5dGVzQ29kZXIgPSB7XG4gIGVuY29kZTogKGRhdGEpID0+IG5ldyBUZXh0RGVjb2RlcigpLmRlY29kZShkYXRhKSxcbiAgZGVjb2RlOiAoc3RyKSA9PiBuZXcgVGV4dEVuY29kZXIoKS5lbmNvZGUoc3RyKSxcbn07XG5cbi8vIEJ1aWx0LWluIGhleCBjb252ZXJzaW9uIGh0dHBzOi8vY2FuaXVzZS5jb20vbWRuLWphdmFzY3JpcHRfYnVpbHRpbnNfdWludDhhcnJheV9mcm9taGV4XG4vLyBwcmV0dGllci1pZ25vcmVcbmNvbnN0IGhhc0hleEJ1aWx0aW46IGJvb2xlYW4gPSAvKiBAX19QVVJFX18gKi8gKCgpID0+XG4gIHR5cGVvZiAoVWludDhBcnJheSBhcyBhbnkpLmZyb20oW10pLnRvSGV4ID09PSAnZnVuY3Rpb24nICYmXG4gIHR5cGVvZiAoVWludDhBcnJheSBhcyBhbnkpLmZyb21IZXggPT09ICdmdW5jdGlvbicpKCk7XG4vLyBwcmV0dGllci1pZ25vcmVcbmNvbnN0IGhleEJ1aWx0aW46IEJ5dGVzQ29kZXIgPSB7XG4gIGVuY29kZShkYXRhKSB7IGFieXRlcyhkYXRhKTsgcmV0dXJuIChkYXRhIGFzIGFueSkudG9IZXgoKTsgfSxcbiAgZGVjb2RlKHMpIHsgYXN0cignaGV4Jywgcyk7IHJldHVybiAoVWludDhBcnJheSBhcyBhbnkpLmZyb21IZXgocyk7IH0sXG59O1xuLyoqXG4gKiBoZXggc3RyaW5nIGRlY29kZXIuIFVzZXMgYnVpbHQtaW4gZnVuY3Rpb24sIHdoZW4gYXZhaWxhYmxlLlxuICogQGV4YW1wbGVcbiAqIGBgYGpzXG4gKiBjb25zdCBiID0gaGV4LmRlY29kZShcIjAxMDJmZlwiKTsgLy8gPT4gbmV3IFVpbnQ4QXJyYXkoWyAxLCAyLCAyNTUgXSlcbiAqIGNvbnN0IHN0ciA9IGhleC5lbmNvZGUoYik7IC8vIFwiMDEwMmZmXCJcbiAqIGBgYFxuICovXG5leHBvcnQgY29uc3QgaGV4OiBCeXRlc0NvZGVyID0gaGFzSGV4QnVpbHRpblxuICA/IGhleEJ1aWx0aW5cbiAgOiBjaGFpbihcbiAgICAgIHJhZGl4Mig0KSxcbiAgICAgIGFscGhhYmV0KCcwMTIzNDU2Nzg5YWJjZGVmJyksXG4gICAgICBqb2luKCcnKSxcbiAgICAgIG5vcm1hbGl6ZSgoczogc3RyaW5nKSA9PiB7XG4gICAgICAgIGlmICh0eXBlb2YgcyAhPT0gJ3N0cmluZycgfHwgcy5sZW5ndGggJSAyICE9PSAwKVxuICAgICAgICAgIHRocm93IG5ldyBUeXBlRXJyb3IoXG4gICAgICAgICAgICBgaGV4LmRlY29kZTogZXhwZWN0ZWQgc3RyaW5nLCBnb3QgJHt0eXBlb2Ygc30gd2l0aCBsZW5ndGggJHtzLmxlbmd0aH1gXG4gICAgICAgICAgKTtcbiAgICAgICAgcmV0dXJuIHMudG9Mb3dlckNhc2UoKTtcbiAgICAgIH0pXG4gICAgKTtcblxuZXhwb3J0IHR5cGUgU29tZUNvZGVycyA9IHtcbiAgdXRmODogQnl0ZXNDb2RlcjtcbiAgaGV4OiBCeXRlc0NvZGVyO1xuICBiYXNlMTY6IEJ5dGVzQ29kZXI7XG4gIGJhc2UzMjogQnl0ZXNDb2RlcjtcbiAgYmFzZTY0OiBCeXRlc0NvZGVyO1xuICBiYXNlNjR1cmw6IEJ5dGVzQ29kZXI7XG4gIGJhc2U1ODogQnl0ZXNDb2RlcjtcbiAgYmFzZTU4eG1yOiBCeXRlc0NvZGVyO1xufTtcbi8vIHByZXR0aWVyLWlnbm9yZVxuY29uc3QgQ09ERVJTOiBTb21lQ29kZXJzID0ge1xuICB1dGY4LCBoZXgsIGJhc2UxNiwgYmFzZTMyLCBiYXNlNjQsIGJhc2U2NHVybCwgYmFzZTU4LCBiYXNlNTh4bXJcbn07XG50eXBlIENvZGVyVHlwZSA9IGtleW9mIFNvbWVDb2RlcnM7XG5jb25zdCBjb2RlclR5cGVFcnJvciA9XG4gICdJbnZhbGlkIGVuY29kaW5nIHR5cGUuIEF2YWlsYWJsZSB0eXBlczogdXRmOCwgaGV4LCBiYXNlMTYsIGJhc2UzMiwgYmFzZTY0LCBiYXNlNjR1cmwsIGJhc2U1OCwgYmFzZTU4eG1yJztcblxuLyoqIEBkZXByZWNhdGVkICovXG5leHBvcnQgY29uc3QgYnl0ZXNUb1N0cmluZyA9ICh0eXBlOiBDb2RlclR5cGUsIGJ5dGVzOiBVaW50OEFycmF5KTogc3RyaW5nID0+IHtcbiAgaWYgKHR5cGVvZiB0eXBlICE9PSAnc3RyaW5nJyB8fCAhQ09ERVJTLmhhc093blByb3BlcnR5KHR5cGUpKSB0aHJvdyBuZXcgVHlwZUVycm9yKGNvZGVyVHlwZUVycm9yKTtcbiAgaWYgKCFpc0J5dGVzKGJ5dGVzKSkgdGhyb3cgbmV3IFR5cGVFcnJvcignYnl0ZXNUb1N0cmluZygpIGV4cGVjdHMgVWludDhBcnJheScpO1xuICByZXR1cm4gQ09ERVJTW3R5cGVdLmVuY29kZShieXRlcyk7XG59O1xuXG4vKiogQGRlcHJlY2F0ZWQgKi9cbmV4cG9ydCBjb25zdCBzdHI6ICh0eXBlOiBDb2RlclR5cGUsIGJ5dGVzOiBVaW50OEFycmF5KSA9PiBzdHJpbmcgPSBieXRlc1RvU3RyaW5nOyAvLyBhcyBpbiBweXRob24sIGJ1dCBmb3IgYnl0ZXMgb25seVxuXG4vKiogQGRlcHJlY2F0ZWQgKi9cbmV4cG9ydCBjb25zdCBzdHJpbmdUb0J5dGVzID0gKHR5cGU6IENvZGVyVHlwZSwgc3RyOiBzdHJpbmcpOiBVaW50OEFycmF5ID0+IHtcbiAgaWYgKCFDT0RFUlMuaGFzT3duUHJvcGVydHkodHlwZSkpIHRocm93IG5ldyBUeXBlRXJyb3IoY29kZXJUeXBlRXJyb3IpO1xuICBpZiAodHlwZW9mIHN0ciAhPT0gJ3N0cmluZycpIHRocm93IG5ldyBUeXBlRXJyb3IoJ3N0cmluZ1RvQnl0ZXMoKSBleHBlY3RzIHN0cmluZycpO1xuICByZXR1cm4gQ09ERVJTW3R5cGVdLmRlY29kZShzdHIpO1xufTtcbi8qKiBAZGVwcmVjYXRlZCAqL1xuZXhwb3J0IGNvbnN0IGJ5dGVzOiAodHlwZTogQ29kZXJUeXBlLCBzdHI6IHN0cmluZykgPT4gVWludDhBcnJheSA9IHN0cmluZ1RvQnl0ZXM7XG4iLCAiLyoqXG4gKiBAbW9kdWxlIG5pcHMvbmlwLTQ2XG4gKiBAZGVzY3JpcHRpb24gSW1wbGVtZW50YXRpb24gb2YgTklQLTQ2IChOb3N0ciBDb25uZWN0IC8gUmVtb3RlIFNpZ25pbmcpXG4gKlxuICogUHVyZSBwcm90b2NvbCBsYXllciBcdTIwMTQgY3J5cHRvLCBlbmNvZGluZywgbWVzc2FnZSBmb3JtYXR0aW5nLlxuICogTm8gV2ViU29ja2V0LCBubyByZWxheSBjb25uZWN0aW9ucywgbm8gSS9PLlxuICogQ29uc3VtZXJzIHByb3ZpZGUgdGhlaXIgb3duIHRyYW5zcG9ydC5cbiAqXG4gKiBAc2VlIGh0dHBzOi8vZ2l0aHViLmNvbS9ub3N0ci1wcm90b2NvbC9uaXBzL2Jsb2IvbWFzdGVyLzQ2Lm1kXG4gKi9cblxuaW1wb3J0IHsgc2Nobm9yciB9IGZyb20gJ0Bub2JsZS9jdXJ2ZXMvc2VjcDI1NmsxLmpzJztcbmltcG9ydCB7IGJ5dGVzVG9IZXgsIGhleFRvQnl0ZXMsIHJhbmRvbUJ5dGVzIH0gZnJvbSAnQG5vYmxlL2hhc2hlcy91dGlscy5qcyc7XG5pbXBvcnQgeyBzaGEyNTYgfSBmcm9tICdAbm9ibGUvaGFzaGVzL3NoYTIuanMnO1xuaW1wb3J0IHtcbiAgZ2V0Q29udmVyc2F0aW9uS2V5IGFzIG5pcDQ0R2V0Q29udmVyc2F0aW9uS2V5LFxuICBlbmNyeXB0IGFzIG5pcDQ0RW5jcnlwdCxcbiAgZGVjcnlwdCBhcyBuaXA0NERlY3J5cHQsXG59IGZyb20gJy4vbmlwLTQ0JztcbmltcG9ydCB0eXBlIHtcbiAgQnVua2VyVVJJLFxuICBCdW5rZXJWYWxpZGF0aW9uUmVzdWx0LFxuICBOaXA0NlJlcXVlc3QsXG4gIE5pcDQ2UmVzcG9uc2UsXG4gIE5pcDQ2U2Vzc2lvbixcbiAgTmlwNDZTZXNzaW9uSW5mbyxcbiAgU2lnbmVkTm9zdHJFdmVudCxcbn0gZnJvbSAnLi4vdHlwZXMnO1xuaW1wb3J0IHsgTmlwNDZNZXRob2QgfSBmcm9tICcuLi90eXBlcyc7XG5cbi8vIFx1MjUwMFx1MjUwMFx1MjUwMCAxLiBCdW5rZXIgVVJJIFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFxuXG4vKipcbiAqIFBhcnNlIGEgYnVua2VyOi8vIFVSSSBpbnRvIGl0cyBjb21wb25lbnRzXG4gKiBAcGFyYW0gdXJpIC0gYnVua2VyOi8vJmx0O3JlbW90ZS1wdWJrZXkmZ3Q7P3JlbGF5PS4uLiZzZWNyZXQ9Li4uXG4gKiBAcmV0dXJucyBQYXJzZWQgQnVua2VyVVJJIG9yIHRocm93cyBvbiBpbnZhbGlkIGlucHV0XG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBwYXJzZUJ1bmtlclVSSSh1cmk6IHN0cmluZyk6IEJ1bmtlclVSSSB7XG4gIGlmICghdXJpLnN0YXJ0c1dpdGgoJ2J1bmtlcjovLycpKSB7XG4gICAgdGhyb3cgbmV3IEVycm9yKCdpbnZhbGlkIGJ1bmtlciBVUkk6IG11c3Qgc3RhcnQgd2l0aCBidW5rZXI6Ly8nKTtcbiAgfVxuXG4gIGNvbnN0IHVybCA9IG5ldyBVUkwodXJpLnJlcGxhY2UoJ2J1bmtlcjovLycsICdodHRwczovLycpKTtcbiAgY29uc3QgcmVtb3RlUHVia2V5ID0gdXJsLmhvc3RuYW1lO1xuXG4gIGlmICghL15bMC05YS1mXXs2NH0kLy50ZXN0KHJlbW90ZVB1YmtleSkpIHtcbiAgICB0aHJvdyBuZXcgRXJyb3IoJ2ludmFsaWQgYnVua2VyIFVSSTogcmVtb3RlIHB1YmtleSBtdXN0IGJlIDY0IGhleCBjaGFyYWN0ZXJzJyk7XG4gIH1cblxuICBjb25zdCByZWxheXMgPSB1cmwuc2VhcmNoUGFyYW1zLmdldEFsbCgncmVsYXknKTtcbiAgaWYgKHJlbGF5cy5sZW5ndGggPT09IDApIHtcbiAgICB0aHJvdyBuZXcgRXJyb3IoJ2ludmFsaWQgYnVua2VyIFVSSTogYXQgbGVhc3Qgb25lIHJlbGF5IGlzIHJlcXVpcmVkJyk7XG4gIH1cblxuICBjb25zdCBzZWNyZXQgPSB1cmwuc2VhcmNoUGFyYW1zLmdldCgnc2VjcmV0JykgfHwgdW5kZWZpbmVkO1xuXG4gIHJldHVybiB7IHJlbW90ZVB1YmtleSwgcmVsYXlzLCBzZWNyZXQgfTtcbn1cblxuLyoqXG4gKiBDcmVhdGUgYSBidW5rZXI6Ly8gVVJJIHN0cmluZ1xuICogQHBhcmFtIHJlbW90ZVB1YmtleSAtIFJlbW90ZSBzaWduZXIncyBwdWJsaWMga2V5IChoZXgpXG4gKiBAcGFyYW0gcmVsYXlzIC0gUmVsYXkgVVJMc1xuICogQHBhcmFtIHNlY3JldCAtIE9wdGlvbmFsIGNvbm5lY3Rpb24gc2VjcmV0XG4gKiBAcmV0dXJucyBidW5rZXI6Ly8gVVJJIHN0cmluZ1xuICovXG5leHBvcnQgZnVuY3Rpb24gY3JlYXRlQnVua2VyVVJJKHJlbW90ZVB1YmtleTogc3RyaW5nLCByZWxheXM6IHN0cmluZ1tdLCBzZWNyZXQ/OiBzdHJpbmcpOiBzdHJpbmcge1xuICBpZiAoIS9eWzAtOWEtZl17NjR9JC8udGVzdChyZW1vdGVQdWJrZXkpKSB7XG4gICAgdGhyb3cgbmV3IEVycm9yKCdyZW1vdGVQdWJrZXkgbXVzdCBiZSA2NCBoZXggY2hhcmFjdGVycycpO1xuICB9XG4gIGlmIChyZWxheXMubGVuZ3RoID09PSAwKSB7XG4gICAgdGhyb3cgbmV3IEVycm9yKCdhdCBsZWFzdCBvbmUgcmVsYXkgaXMgcmVxdWlyZWQnKTtcbiAgfVxuXG4gIGNvbnN0IHBhcmFtcyA9IHJlbGF5cy5tYXAociA9PiBgcmVsYXk9JHtlbmNvZGVVUklDb21wb25lbnQocil9YCk7XG4gIGlmIChzZWNyZXQpIHtcbiAgICBwYXJhbXMucHVzaChgc2VjcmV0PSR7ZW5jb2RlVVJJQ29tcG9uZW50KHNlY3JldCl9YCk7XG4gIH1cblxuICByZXR1cm4gYGJ1bmtlcjovLyR7cmVtb3RlUHVia2V5fT8ke3BhcmFtcy5qb2luKCcmJyl9YDtcbn1cblxuLyoqXG4gKiBWYWxpZGF0ZSBhIGJ1bmtlcjovLyBVUkkgYW5kIHJldHVybiBzdHJ1Y3R1cmVkIHJlc3VsdFxuICovXG5leHBvcnQgZnVuY3Rpb24gdmFsaWRhdGVCdW5rZXJVUkkodXJpOiBzdHJpbmcpOiBCdW5rZXJWYWxpZGF0aW9uUmVzdWx0IHtcbiAgdHJ5IHtcbiAgICBjb25zdCBwYXJzZWQgPSBwYXJzZUJ1bmtlclVSSSh1cmkpO1xuICAgIHJldHVybiB7IGlzVmFsaWQ6IHRydWUsIHVyaTogcGFyc2VkIH07XG4gIH0gY2F0Y2ggKGUpIHtcbiAgICByZXR1cm4geyBpc1ZhbGlkOiBmYWxzZSwgZXJyb3I6IChlIGFzIEVycm9yKS5tZXNzYWdlIH07XG4gIH1cbn1cblxuLy8gXHUyNTAwXHUyNTAwXHUyNTAwIDIuIFNlc3Npb24gTWFuYWdlbWVudCBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcblxuLyoqXG4gKiBDcmVhdGUgYSBuZXcgTklQLTQ2IHNlc3Npb24gd2l0aCBhbiBlcGhlbWVyYWwga2V5cGFpclxuICogQHBhcmFtIHJlbW90ZVB1YmtleSAtIFJlbW90ZSBzaWduZXIncyBwdWJsaWMga2V5IChoZXgpXG4gKiBAcmV0dXJucyBTZXNzaW9uIGNvbnRhaW5pbmcgZXBoZW1lcmFsIGtleXMgYW5kIE5JUC00NCBjb252ZXJzYXRpb24ga2V5XG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBjcmVhdGVTZXNzaW9uKHJlbW90ZVB1YmtleTogc3RyaW5nKTogTmlwNDZTZXNzaW9uIHtcbiAgaWYgKCEvXlswLTlhLWZdezY0fSQvLnRlc3QocmVtb3RlUHVia2V5KSkge1xuICAgIHRocm93IG5ldyBFcnJvcigncmVtb3RlUHVia2V5IG11c3QgYmUgNjQgaGV4IGNoYXJhY3RlcnMnKTtcbiAgfVxuXG4gIGNvbnN0IGNsaWVudFNlY3JldEtleUJ5dGVzID0gcmFuZG9tQnl0ZXMoMzIpO1xuICBjb25zdCBjbGllbnRTZWNyZXRLZXkgPSBieXRlc1RvSGV4KGNsaWVudFNlY3JldEtleUJ5dGVzKTtcbiAgY29uc3QgY2xpZW50UHVia2V5Qnl0ZXMgPSBzY2hub3JyLmdldFB1YmxpY0tleShjbGllbnRTZWNyZXRLZXlCeXRlcyk7XG4gIGNvbnN0IGNsaWVudFB1YmtleSA9IGJ5dGVzVG9IZXgoY2xpZW50UHVia2V5Qnl0ZXMpO1xuXG4gIGNvbnN0IGNvbnZlcnNhdGlvbktleSA9IG5pcDQ0R2V0Q29udmVyc2F0aW9uS2V5KGNsaWVudFNlY3JldEtleUJ5dGVzLCByZW1vdGVQdWJrZXkpO1xuXG4gIHJldHVybiB7XG4gICAgY2xpZW50U2VjcmV0S2V5LFxuICAgIGNsaWVudFB1YmtleSxcbiAgICByZW1vdGVQdWJrZXksXG4gICAgY29udmVyc2F0aW9uS2V5LFxuICB9O1xufVxuXG4vKipcbiAqIFJlc3RvcmUgYSBzZXNzaW9uIGZyb20gYSBwcmV2aW91c2x5IHNhdmVkIGVwaGVtZXJhbCBwcml2YXRlIGtleVxuICogQHBhcmFtIGNsaWVudFNlY3JldEtleSAtIEhleC1lbmNvZGVkIGVwaGVtZXJhbCBwcml2YXRlIGtleVxuICogQHBhcmFtIHJlbW90ZVB1YmtleSAtIFJlbW90ZSBzaWduZXIncyBwdWJsaWMga2V5IChoZXgpXG4gKiBAcmV0dXJucyBSZXN0b3JlZCBzZXNzaW9uXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiByZXN0b3JlU2Vzc2lvbihjbGllbnRTZWNyZXRLZXk6IHN0cmluZywgcmVtb3RlUHVia2V5OiBzdHJpbmcpOiBOaXA0NlNlc3Npb24ge1xuICBjb25zdCBjbGllbnRTZWNyZXRLZXlCeXRlcyA9IGhleFRvQnl0ZXMoY2xpZW50U2VjcmV0S2V5KTtcbiAgY29uc3QgY2xpZW50UHVia2V5Qnl0ZXMgPSBzY2hub3JyLmdldFB1YmxpY0tleShjbGllbnRTZWNyZXRLZXlCeXRlcyk7XG4gIGNvbnN0IGNsaWVudFB1YmtleSA9IGJ5dGVzVG9IZXgoY2xpZW50UHVia2V5Qnl0ZXMpO1xuXG4gIGNvbnN0IGNvbnZlcnNhdGlvbktleSA9IG5pcDQ0R2V0Q29udmVyc2F0aW9uS2V5KGNsaWVudFNlY3JldEtleUJ5dGVzLCByZW1vdGVQdWJrZXkpO1xuXG4gIHJldHVybiB7XG4gICAgY2xpZW50U2VjcmV0S2V5LFxuICAgIGNsaWVudFB1YmtleSxcbiAgICByZW1vdGVQdWJrZXksXG4gICAgY29udmVyc2F0aW9uS2V5LFxuICB9O1xufVxuXG4vKipcbiAqIEdldCBwdWJsaWMgc2Vzc2lvbiBpbmZvIChzYWZlIHRvIGV4cG9zZSlcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGdldFNlc3Npb25JbmZvKHNlc3Npb246IE5pcDQ2U2Vzc2lvbik6IE5pcDQ2U2Vzc2lvbkluZm8ge1xuICByZXR1cm4ge1xuICAgIGNsaWVudFB1YmtleTogc2Vzc2lvbi5jbGllbnRQdWJrZXksXG4gICAgcmVtb3RlUHVia2V5OiBzZXNzaW9uLnJlbW90ZVB1YmtleSxcbiAgfTtcbn1cblxuLy8gXHUyNTAwXHUyNTAwXHUyNTAwIDMuIEpTT04tUlBDIE1lc3NhZ2VzIFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFxuXG4vKipcbiAqIENyZWF0ZSBhIE5JUC00NiBKU09OLVJQQyByZXF1ZXN0XG4gKiBAcGFyYW0gbWV0aG9kIC0gUlBDIG1ldGhvZCBuYW1lXG4gKiBAcGFyYW0gcGFyYW1zIC0gQXJyYXkgb2Ygc3RyaW5nIHBhcmFtZXRlcnNcbiAqIEBwYXJhbSBpZCAtIE9wdGlvbmFsIHJlcXVlc3QgSUQgKHJhbmRvbSBpZiBub3QgcHJvdmlkZWQpXG4gKiBAcmV0dXJucyBKU09OLVJQQyByZXF1ZXN0IG9iamVjdFxuICovXG5leHBvcnQgZnVuY3Rpb24gY3JlYXRlUmVxdWVzdChtZXRob2Q6IE5pcDQ2TWV0aG9kIHwgc3RyaW5nLCBwYXJhbXM6IHN0cmluZ1tdLCBpZD86IHN0cmluZyk6IE5pcDQ2UmVxdWVzdCB7XG4gIHJldHVybiB7XG4gICAgaWQ6IGlkIHx8IGJ5dGVzVG9IZXgocmFuZG9tQnl0ZXMoMTYpKSxcbiAgICBtZXRob2QsXG4gICAgcGFyYW1zLFxuICB9O1xufVxuXG4vKipcbiAqIENyZWF0ZSBhIE5JUC00NiBKU09OLVJQQyByZXNwb25zZVxuICogQHBhcmFtIGlkIC0gUmVxdWVzdCBJRCBiZWluZyByZXNwb25kZWQgdG9cbiAqIEBwYXJhbSByZXN1bHQgLSBSZXN1bHQgc3RyaW5nIChvbiBzdWNjZXNzKVxuICogQHBhcmFtIGVycm9yIC0gRXJyb3Igc3RyaW5nIChvbiBmYWlsdXJlKVxuICogQHJldHVybnMgSlNPTi1SUEMgcmVzcG9uc2Ugb2JqZWN0XG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBjcmVhdGVSZXNwb25zZShpZDogc3RyaW5nLCByZXN1bHQ/OiBzdHJpbmcsIGVycm9yPzogc3RyaW5nKTogTmlwNDZSZXNwb25zZSB7XG4gIGNvbnN0IHJlc3BvbnNlOiBOaXA0NlJlc3BvbnNlID0geyBpZCB9O1xuICBpZiAocmVzdWx0ICE9PSB1bmRlZmluZWQpIHJlc3BvbnNlLnJlc3VsdCA9IHJlc3VsdDtcbiAgaWYgKGVycm9yICE9PSB1bmRlZmluZWQpIHJlc3BvbnNlLmVycm9yID0gZXJyb3I7XG4gIHJldHVybiByZXNwb25zZTtcbn1cblxuLyoqXG4gKiBQYXJzZSBhIEpTT04gc3RyaW5nIGludG8gYSBOSVAtNDYgcmVxdWVzdCBvciByZXNwb25zZVxuICogQHBhcmFtIGpzb24gLSBKU09OIHN0cmluZyB0byBwYXJzZVxuICogQHJldHVybnMgUGFyc2VkIHJlcXVlc3Qgb3IgcmVzcG9uc2VcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIHBhcnNlUGF5bG9hZChqc29uOiBzdHJpbmcpOiBOaXA0NlJlcXVlc3QgfCBOaXA0NlJlc3BvbnNlIHtcbiAgY29uc3Qgb2JqID0gSlNPTi5wYXJzZShqc29uKSBhcyBSZWNvcmQ8c3RyaW5nLCB1bmtub3duPjtcbiAgaWYgKHR5cGVvZiBvYmouaWQgIT09ICdzdHJpbmcnKSB7XG4gICAgdGhyb3cgbmV3IEVycm9yKCdpbnZhbGlkIE5JUC00NiBwYXlsb2FkOiBtaXNzaW5nIGlkJyk7XG4gIH1cbiAgcmV0dXJuIG9iaiBhcyB1bmtub3duIGFzIE5pcDQ2UmVxdWVzdCB8IE5pcDQ2UmVzcG9uc2U7XG59XG5cbi8qKlxuICogQ2hlY2sgaWYgYSBwYXlsb2FkIGlzIGEgTklQLTQ2IHJlcXVlc3RcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGlzUmVxdWVzdChwYXlsb2FkOiBOaXA0NlJlcXVlc3QgfCBOaXA0NlJlc3BvbnNlKTogcGF5bG9hZCBpcyBOaXA0NlJlcXVlc3Qge1xuICByZXR1cm4gJ21ldGhvZCcgaW4gcGF5bG9hZCAmJiAncGFyYW1zJyBpbiBwYXlsb2FkO1xufVxuXG4vKipcbiAqIENoZWNrIGlmIGEgcGF5bG9hZCBpcyBhIE5JUC00NiByZXNwb25zZVxuICovXG5leHBvcnQgZnVuY3Rpb24gaXNSZXNwb25zZShwYXlsb2FkOiBOaXA0NlJlcXVlc3QgfCBOaXA0NlJlc3BvbnNlKTogcGF5bG9hZCBpcyBOaXA0NlJlc3BvbnNlIHtcbiAgcmV0dXJuICdyZXN1bHQnIGluIHBheWxvYWQgfHwgJ2Vycm9yJyBpbiBwYXlsb2FkO1xufVxuXG4vLyBcdTI1MDBcdTI1MDBcdTI1MDAgNC4gRXZlbnQgV3JhcHBpbmcgKEtpbmQgMjQxMzMpIFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFxuXG4vKipcbiAqIEVuY3J5cHQgYW5kIHdyYXAgYSBOSVAtNDYgcGF5bG9hZCBpbnRvIGEga2luZCAyNDEzMyBzaWduZWQgZXZlbnRcbiAqIEBwYXJhbSBwYXlsb2FkIC0gSlNPTi1SUEMgcmVxdWVzdCBvciByZXNwb25zZSB0byBlbmNyeXB0XG4gKiBAcGFyYW0gc2Vzc2lvbiAtIE5JUC00NiBzZXNzaW9uXG4gKiBAcGFyYW0gcmVjaXBpZW50UHVia2V5IC0gVGhlIHJlY2lwaWVudCdzIHB1YmtleSAoaGV4KVxuICogQHJldHVybnMgU2lnbmVkIGtpbmQgMjQxMzMgZXZlbnRcbiAqL1xuZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIHdyYXBFdmVudChcbiAgcGF5bG9hZDogTmlwNDZSZXF1ZXN0IHwgTmlwNDZSZXNwb25zZSxcbiAgc2Vzc2lvbjogTmlwNDZTZXNzaW9uLFxuICByZWNpcGllbnRQdWJrZXk6IHN0cmluZ1xuKTogUHJvbWlzZTxTaWduZWROb3N0ckV2ZW50PiB7XG4gIGNvbnN0IGpzb24gPSBKU09OLnN0cmluZ2lmeShwYXlsb2FkKTtcbiAgY29uc3QgZW5jcnlwdGVkID0gbmlwNDRFbmNyeXB0KGpzb24sIHNlc3Npb24uY29udmVyc2F0aW9uS2V5KTtcblxuICBjb25zdCBjcmVhdGVkX2F0ID0gTWF0aC5mbG9vcihEYXRlLm5vdygpIC8gMTAwMCk7XG4gIGNvbnN0IGV2ZW50ID0ge1xuICAgIGtpbmQ6IDI0MTMzLFxuICAgIGNyZWF0ZWRfYXQsXG4gICAgdGFnczogW1sncCcsIHJlY2lwaWVudFB1YmtleV1dLFxuICAgIGNvbnRlbnQ6IGVuY3J5cHRlZCxcbiAgICBwdWJrZXk6IHNlc3Npb24uY2xpZW50UHVia2V5LFxuICB9O1xuXG4gIC8vIFNlcmlhbGl6ZSBmb3IgTklQLTAxIGV2ZW50IElEXG4gIGNvbnN0IHNlcmlhbGl6ZWQgPSBKU09OLnN0cmluZ2lmeShbXG4gICAgMCxcbiAgICBldmVudC5wdWJrZXksXG4gICAgZXZlbnQuY3JlYXRlZF9hdCxcbiAgICBldmVudC5raW5kLFxuICAgIGV2ZW50LnRhZ3MsXG4gICAgZXZlbnQuY29udGVudCxcbiAgXSk7XG5cbiAgY29uc3QgZXZlbnRIYXNoID0gc2hhMjU2KG5ldyBUZXh0RW5jb2RlcigpLmVuY29kZShzZXJpYWxpemVkKSk7XG4gIGNvbnN0IHByaXZhdGVLZXlCeXRlcyA9IGhleFRvQnl0ZXMoc2Vzc2lvbi5jbGllbnRTZWNyZXRLZXkpO1xuICBjb25zdCBzaWduYXR1cmVCeXRlcyA9IHNjaG5vcnIuc2lnbihldmVudEhhc2gsIHByaXZhdGVLZXlCeXRlcyk7XG5cbiAgcmV0dXJuIHtcbiAgICAuLi5ldmVudCxcbiAgICBpZDogYnl0ZXNUb0hleChldmVudEhhc2gpLFxuICAgIHNpZzogYnl0ZXNUb0hleChzaWduYXR1cmVCeXRlcyksXG4gIH07XG59XG5cbi8qKlxuICogRGVjcnlwdCBhbmQgcGFyc2UgYSBraW5kIDI0MTMzIGV2ZW50XG4gKiBAcGFyYW0gZXZlbnQgLSBTaWduZWQga2luZCAyNDEzMyBldmVudFxuICogQHBhcmFtIHNlc3Npb24gLSBOSVAtNDYgc2Vzc2lvblxuICogQHJldHVybnMgRGVjcnlwdGVkIEpTT04tUlBDIHJlcXVlc3Qgb3IgcmVzcG9uc2VcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIHVud3JhcEV2ZW50KFxuICBldmVudDogU2lnbmVkTm9zdHJFdmVudCxcbiAgc2Vzc2lvbjogTmlwNDZTZXNzaW9uXG4pOiBOaXA0NlJlcXVlc3QgfCBOaXA0NlJlc3BvbnNlIHtcbiAgaWYgKGV2ZW50LmtpbmQgIT09IDI0MTMzKSB7XG4gICAgdGhyb3cgbmV3IEVycm9yKGBleHBlY3RlZCBraW5kIDI0MTMzLCBnb3QgJHtldmVudC5raW5kfWApO1xuICB9XG5cbiAgY29uc3QganNvbiA9IG5pcDQ0RGVjcnlwdChldmVudC5jb250ZW50LCBzZXNzaW9uLmNvbnZlcnNhdGlvbktleSk7XG4gIHJldHVybiBwYXJzZVBheWxvYWQoanNvbik7XG59XG5cbi8vIFx1MjUwMFx1MjUwMFx1MjUwMCA1LiBDb252ZW5pZW5jZSBSZXF1ZXN0IENyZWF0b3JzIFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFx1MjUwMFxuXG4vKipcbiAqIENyZWF0ZSBhICdjb25uZWN0JyByZXF1ZXN0XG4gKiBAcGFyYW0gcmVtb3RlUHVia2V5IC0gUmVtb3RlIHNpZ25lcidzIHB1YmtleVxuICogQHBhcmFtIHNlY3JldCAtIE9wdGlvbmFsIGNvbm5lY3Rpb24gc2VjcmV0IGZyb20gYnVua2VyIFVSSVxuICogQHBhcmFtIHBlcm1pc3Npb25zIC0gT3B0aW9uYWwgY29tbWEtc2VwYXJhdGVkIHBlcm1pc3Npb24gc3RyaW5nXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBjb25uZWN0UmVxdWVzdChyZW1vdGVQdWJrZXk6IHN0cmluZywgc2VjcmV0Pzogc3RyaW5nLCBwZXJtaXNzaW9ucz86IHN0cmluZyk6IE5pcDQ2UmVxdWVzdCB7XG4gIGNvbnN0IHBhcmFtcyA9IFtyZW1vdGVQdWJrZXldO1xuICBpZiAoc2VjcmV0KSBwYXJhbXMucHVzaChzZWNyZXQpO1xuICBlbHNlIGlmIChwZXJtaXNzaW9ucykgcGFyYW1zLnB1c2goJycpO1xuICBpZiAocGVybWlzc2lvbnMpIHBhcmFtcy5wdXNoKHBlcm1pc3Npb25zKTtcbiAgcmV0dXJuIGNyZWF0ZVJlcXVlc3QoTmlwNDZNZXRob2QuQ09OTkVDVCwgcGFyYW1zKTtcbn1cblxuLyoqIENyZWF0ZSBhICdwaW5nJyByZXF1ZXN0ICovXG5leHBvcnQgZnVuY3Rpb24gcGluZ1JlcXVlc3QoKTogTmlwNDZSZXF1ZXN0IHtcbiAgcmV0dXJuIGNyZWF0ZVJlcXVlc3QoTmlwNDZNZXRob2QuUElORywgW10pO1xufVxuXG4vKiogQ3JlYXRlIGEgJ2dldF9wdWJsaWNfa2V5JyByZXF1ZXN0ICovXG5leHBvcnQgZnVuY3Rpb24gZ2V0UHVibGljS2V5UmVxdWVzdCgpOiBOaXA0NlJlcXVlc3Qge1xuICByZXR1cm4gY3JlYXRlUmVxdWVzdChOaXA0Nk1ldGhvZC5HRVRfUFVCTElDX0tFWSwgW10pO1xufVxuXG4vKipcbiAqIENyZWF0ZSBhICdzaWduX2V2ZW50JyByZXF1ZXN0XG4gKiBAcGFyYW0gZXZlbnRKc29uIC0gSlNPTi1zdHJpbmdpZmllZCB1bnNpZ25lZCBldmVudFxuICovXG5leHBvcnQgZnVuY3Rpb24gc2lnbkV2ZW50UmVxdWVzdChldmVudEpzb246IHN0cmluZyk6IE5pcDQ2UmVxdWVzdCB7XG4gIHJldHVybiBjcmVhdGVSZXF1ZXN0KE5pcDQ2TWV0aG9kLlNJR05fRVZFTlQsIFtldmVudEpzb25dKTtcbn1cblxuLyoqXG4gKiBDcmVhdGUgYSAnbmlwMDRfZW5jcnlwdCcgcmVxdWVzdFxuICogQHBhcmFtIHRoaXJkUGFydHlQdWJrZXkgLSBQdWJsaWMga2V5IG9mIHRoZSBtZXNzYWdlIHJlY2lwaWVudFxuICogQHBhcmFtIHBsYWludGV4dCAtIE1lc3NhZ2UgdG8gZW5jcnlwdFxuICovXG5leHBvcnQgZnVuY3Rpb24gbmlwMDRFbmNyeXB0UmVxdWVzdCh0aGlyZFBhcnR5UHVia2V5OiBzdHJpbmcsIHBsYWludGV4dDogc3RyaW5nKTogTmlwNDZSZXF1ZXN0IHtcbiAgcmV0dXJuIGNyZWF0ZVJlcXVlc3QoTmlwNDZNZXRob2QuTklQMDRfRU5DUllQVCwgW3RoaXJkUGFydHlQdWJrZXksIHBsYWludGV4dF0pO1xufVxuXG4vKipcbiAqIENyZWF0ZSBhICduaXAwNF9kZWNyeXB0JyByZXF1ZXN0XG4gKiBAcGFyYW0gdGhpcmRQYXJ0eVB1YmtleSAtIFB1YmxpYyBrZXkgb2YgdGhlIG1lc3NhZ2Ugc2VuZGVyXG4gKiBAcGFyYW0gY2lwaGVydGV4dCAtIEVuY3J5cHRlZCBtZXNzYWdlIHRvIGRlY3J5cHRcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIG5pcDA0RGVjcnlwdFJlcXVlc3QodGhpcmRQYXJ0eVB1YmtleTogc3RyaW5nLCBjaXBoZXJ0ZXh0OiBzdHJpbmcpOiBOaXA0NlJlcXVlc3Qge1xuICByZXR1cm4gY3JlYXRlUmVxdWVzdChOaXA0Nk1ldGhvZC5OSVAwNF9ERUNSWVBULCBbdGhpcmRQYXJ0eVB1YmtleSwgY2lwaGVydGV4dF0pO1xufVxuXG4vKipcbiAqIENyZWF0ZSBhICduaXA0NF9lbmNyeXB0JyByZXF1ZXN0XG4gKiBAcGFyYW0gdGhpcmRQYXJ0eVB1YmtleSAtIFB1YmxpYyBrZXkgb2YgdGhlIG1lc3NhZ2UgcmVjaXBpZW50XG4gKiBAcGFyYW0gcGxhaW50ZXh0IC0gTWVzc2FnZSB0byBlbmNyeXB0XG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBuaXA0NEVuY3J5cHRSZXF1ZXN0KHRoaXJkUGFydHlQdWJrZXk6IHN0cmluZywgcGxhaW50ZXh0OiBzdHJpbmcpOiBOaXA0NlJlcXVlc3Qge1xuICByZXR1cm4gY3JlYXRlUmVxdWVzdChOaXA0Nk1ldGhvZC5OSVA0NF9FTkNSWVBULCBbdGhpcmRQYXJ0eVB1YmtleSwgcGxhaW50ZXh0XSk7XG59XG5cbi8qKlxuICogQ3JlYXRlIGEgJ25pcDQ0X2RlY3J5cHQnIHJlcXVlc3RcbiAqIEBwYXJhbSB0aGlyZFBhcnR5UHVia2V5IC0gUHVibGljIGtleSBvZiB0aGUgbWVzc2FnZSBzZW5kZXJcbiAqIEBwYXJhbSBjaXBoZXJ0ZXh0IC0gRW5jcnlwdGVkIG1lc3NhZ2UgdG8gZGVjcnlwdFxuICovXG5leHBvcnQgZnVuY3Rpb24gbmlwNDREZWNyeXB0UmVxdWVzdCh0aGlyZFBhcnR5UHVia2V5OiBzdHJpbmcsIGNpcGhlcnRleHQ6IHN0cmluZyk6IE5pcDQ2UmVxdWVzdCB7XG4gIHJldHVybiBjcmVhdGVSZXF1ZXN0KE5pcDQ2TWV0aG9kLk5JUDQ0X0RFQ1JZUFQsIFt0aGlyZFBhcnR5UHVia2V5LCBjaXBoZXJ0ZXh0XSk7XG59XG5cbi8qKiBDcmVhdGUgYSAnZ2V0X3JlbGF5cycgcmVxdWVzdCAqL1xuZXhwb3J0IGZ1bmN0aW9uIGdldFJlbGF5c1JlcXVlc3QoKTogTmlwNDZSZXF1ZXN0IHtcbiAgcmV0dXJuIGNyZWF0ZVJlcXVlc3QoTmlwNDZNZXRob2QuR0VUX1JFTEFZUywgW10pO1xufVxuXG4vLyBcdTI1MDBcdTI1MDBcdTI1MDAgNi4gRmlsdGVyIEhlbHBlciBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcdTI1MDBcblxuLyoqXG4gKiBDcmVhdGUgYSBOb3N0ciBmaWx0ZXIgZm9yIHN1YnNjcmliaW5nIHRvIE5JUC00NiByZXNwb25zZSBldmVudHNcbiAqIEBwYXJhbSBjbGllbnRQdWJrZXkgLSBPdXIgZXBoZW1lcmFsIHB1YmxpYyBrZXkgKGhleClcbiAqIEBwYXJhbSBzaW5jZSAtIE9wdGlvbmFsIHNpbmNlIHRpbWVzdGFtcFxuICogQHJldHVybnMgRmlsdGVyIG9iamVjdCBmb3Iga2luZCAyNDEzMyBldmVudHMgdGFnZ2VkIHRvIHVzXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBjcmVhdGVSZXNwb25zZUZpbHRlcihcbiAgY2xpZW50UHVia2V5OiBzdHJpbmcsXG4gIHNpbmNlPzogbnVtYmVyXG4pOiB7IGtpbmRzOiBudW1iZXJbXTsgJyNwJzogc3RyaW5nW107IHNpbmNlPzogbnVtYmVyIH0ge1xuICBjb25zdCBmaWx0ZXI6IHsga2luZHM6IG51bWJlcltdOyAnI3AnOiBzdHJpbmdbXTsgc2luY2U/OiBudW1iZXIgfSA9IHtcbiAgICBraW5kczogWzI0MTMzXSxcbiAgICAnI3AnOiBbY2xpZW50UHVia2V5XSxcbiAgfTtcbiAgaWYgKHNpbmNlICE9PSB1bmRlZmluZWQpIHtcbiAgICBmaWx0ZXIuc2luY2UgPSBzaW5jZTtcbiAgfVxuICByZXR1cm4gZmlsdGVyO1xufVxuIiwgIi8qKlxuICogQG1vZHVsZSBuaXBzL25pcC00OVxuICogQGRlc2NyaXB0aW9uIEltcGxlbWVudGF0aW9uIG9mIE5JUC00OSAoUHJpdmF0ZSBLZXkgRW5jcnlwdGlvbiAvIG5jcnlwdHNlYylcbiAqIEBzZWUgaHR0cHM6Ly9naXRodWIuY29tL25vc3RyLXByb3RvY29sL25pcHMvYmxvYi9tYXN0ZXIvNDkubWRcbiAqL1xuXG5pbXBvcnQgeyB4Y2hhY2hhMjBwb2x5MTMwNSB9IGZyb20gJ0Bub2JsZS9jaXBoZXJzL2NoYWNoYS5qcyc7XG5pbXBvcnQgeyBzY3J5cHQgfSBmcm9tICdAbm9ibGUvaGFzaGVzL3NjcnlwdC5qcyc7XG5pbXBvcnQgeyBjb25jYXRCeXRlcywgcmFuZG9tQnl0ZXMgfSBmcm9tICdAbm9ibGUvaGFzaGVzL3V0aWxzLmpzJztcbmltcG9ydCB7IGJlY2gzMiBhcyBzY3VyZUJlY2gzMiB9IGZyb20gJ0BzY3VyZS9iYXNlJztcblxudHlwZSBLZXlTZWN1cml0eUJ5dGUgPSAweDAwIHwgMHgwMSB8IDB4MDI7XG5cbi8qKlxuICogRW5jcnlwdCBhIE5vc3RyIHByaXZhdGUga2V5IHdpdGggYSBwYXNzd29yZCwgcHJvZHVjaW5nIGFuIG5jcnlwdHNlYyBiZWNoMzIgc3RyaW5nXG4gKiBAcGFyYW0gc2VjIC0gMzItYnl0ZSBzZWNyZXQga2V5XG4gKiBAcGFyYW0gcGFzc3dvcmQgLSBQYXNzd29yZCBmb3IgZW5jcnlwdGlvblxuICogQHBhcmFtIGxvZ24gLSBTY3J5cHQgbG9nMihOKSBwYXJhbWV0ZXIgKGRlZmF1bHQ6IDE2LCBtZWFuaW5nIE49NjU1MzYpXG4gKiBAcGFyYW0ga3NiIC0gS2V5IHNlY3VyaXR5IGJ5dGU6IDB4MDA9dW5rbm93biwgMHgwMT11bnNhZmUsIDB4MDI9c2FmZSAoZGVmYXVsdDogMHgwMilcbiAqIEByZXR1cm5zIGJlY2gzMi1lbmNvZGVkIG5jcnlwdHNlYyBzdHJpbmdcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGVuY3J5cHQoXG4gIHNlYzogVWludDhBcnJheSxcbiAgcGFzc3dvcmQ6IHN0cmluZyxcbiAgbG9nbjogbnVtYmVyID0gMTYsXG4gIGtzYjogS2V5U2VjdXJpdHlCeXRlID0gMHgwMlxuKTogc3RyaW5nIHtcbiAgY29uc3Qgc2FsdCA9IHJhbmRvbUJ5dGVzKDE2KTtcbiAgY29uc3QgbiA9IDIgKiogbG9nbjtcbiAgY29uc3Qgbm9ybWFsaXplZFBhc3N3b3JkID0gcGFzc3dvcmQubm9ybWFsaXplKCdORktDJyk7XG4gIGNvbnN0IGtleSA9IHNjcnlwdChub3JtYWxpemVkUGFzc3dvcmQsIHNhbHQsIHsgTjogbiwgcjogOCwgcDogMSwgZGtMZW46IDMyIH0pO1xuICBjb25zdCBub25jZSA9IHJhbmRvbUJ5dGVzKDI0KTtcbiAgY29uc3QgYWFkID0gVWludDhBcnJheS5mcm9tKFtrc2JdKTtcbiAgY29uc3QgY2lwaGVyID0geGNoYWNoYTIwcG9seTEzMDUoa2V5LCBub25jZSwgYWFkKTtcbiAgY29uc3QgY2lwaGVydGV4dCA9IGNpcGhlci5lbmNyeXB0KHNlYyk7XG4gIC8vIEJpbmFyeSBmb3JtYXQ6IHZlcnNpb24oMSkgKyBsb2duKDEpICsgc2FsdCgxNikgKyBub25jZSgyNCkgKyBrc2IoMSkgKyBjaXBoZXJ0ZXh0KDQ4ID0gMzIgKyAxNiB0YWcpXG4gIGNvbnN0IHBheWxvYWQgPSBjb25jYXRCeXRlcyhcbiAgICBVaW50OEFycmF5LmZyb20oWzB4MDJdKSxcbiAgICBVaW50OEFycmF5LmZyb20oW2xvZ25dKSxcbiAgICBzYWx0LFxuICAgIG5vbmNlLFxuICAgIGFhZCxcbiAgICBjaXBoZXJ0ZXh0XG4gICk7XG4gIGNvbnN0IHdvcmRzID0gc2N1cmVCZWNoMzIudG9Xb3JkcyhwYXlsb2FkKTtcbiAgcmV0dXJuIHNjdXJlQmVjaDMyLmVuY29kZSgnbmNyeXB0c2VjJywgd29yZHMsIDIwMCk7XG59XG5cbi8qKlxuICogRGVjcnlwdCBhbiBuY3J5cHRzZWMgYmVjaDMyIHN0cmluZyBiYWNrIHRvIHRoZSAzMi1ieXRlIHNlY3JldCBrZXlcbiAqIEBwYXJhbSBuY3J5cHRzZWMgLSBiZWNoMzItZW5jb2RlZCBuY3J5cHRzZWMgc3RyaW5nXG4gKiBAcGFyYW0gcGFzc3dvcmQgLSBQYXNzd29yZCB1c2VkIGZvciBlbmNyeXB0aW9uXG4gKiBAcmV0dXJucyAzMi1ieXRlIHNlY3JldCBrZXkgYXMgVWludDhBcnJheVxuICovXG5leHBvcnQgZnVuY3Rpb24gZGVjcnlwdChuY3J5cHRzZWM6IHN0cmluZywgcGFzc3dvcmQ6IHN0cmluZyk6IFVpbnQ4QXJyYXkge1xuICBjb25zdCB7IHByZWZpeCwgd29yZHMgfSA9IHNjdXJlQmVjaDMyLmRlY29kZShuY3J5cHRzZWMgYXMgYCR7c3RyaW5nfTEke3N0cmluZ31gLCAyMDApO1xuICBpZiAocHJlZml4ICE9PSAnbmNyeXB0c2VjJykgdGhyb3cgbmV3IEVycm9yKCdpbnZhbGlkIG5jcnlwdHNlYyBwcmVmaXgnKTtcbiAgY29uc3QgZGF0YSA9IG5ldyBVaW50OEFycmF5KHNjdXJlQmVjaDMyLmZyb21Xb3Jkcyh3b3JkcykpO1xuICBjb25zdCB2ZXJzaW9uID0gZGF0YVswXTtcbiAgaWYgKHZlcnNpb24gIT09IDB4MDIpIHRocm93IG5ldyBFcnJvcihgdW5rbm93biBuY3J5cHRzZWMgdmVyc2lvbjogJHt2ZXJzaW9ufWApO1xuICBjb25zdCBsb2duID0gZGF0YVsxXTtcbiAgY29uc3Qgc2FsdCA9IGRhdGEuc3ViYXJyYXkoMiwgMTgpO1xuICBjb25zdCBub25jZSA9IGRhdGEuc3ViYXJyYXkoMTgsIDQyKTtcbiAgY29uc3Qga3NiID0gZGF0YVs0Ml07XG4gIGNvbnN0IGNpcGhlcnRleHQgPSBkYXRhLnN1YmFycmF5KDQzKTtcbiAgY29uc3QgbiA9IDIgKiogbG9nbjtcbiAgY29uc3Qgbm9ybWFsaXplZFBhc3N3b3JkID0gcGFzc3dvcmQubm9ybWFsaXplKCdORktDJyk7XG4gIGNvbnN0IGtleSA9IHNjcnlwdChub3JtYWxpemVkUGFzc3dvcmQsIHNhbHQsIHsgTjogbiwgcjogOCwgcDogMSwgZGtMZW46IDMyIH0pO1xuICBjb25zdCBhYWQgPSBVaW50OEFycmF5LmZyb20oW2tzYl0pO1xuICBjb25zdCBjaXBoZXIgPSB4Y2hhY2hhMjBwb2x5MTMwNShrZXksIG5vbmNlLCBhYWQpO1xuICByZXR1cm4gY2lwaGVyLmRlY3J5cHQoY2lwaGVydGV4dCk7XG59XG4iLCAiLyoqXG4gKiBSRkMgNzkxNCBTY3J5cHQgS0RGLiBDYW4gYmUgdXNlZCB0byBjcmVhdGUgYSBrZXkgZnJvbSBwYXNzd29yZCBhbmQgc2FsdC5cbiAqIEBtb2R1bGVcbiAqL1xuaW1wb3J0IHsgcGJrZGYyIH0gZnJvbSAnLi9wYmtkZjIudHMnO1xuaW1wb3J0IHsgc2hhMjU2IH0gZnJvbSAnLi9zaGEyLnRzJztcbi8vIHByZXR0aWVyLWlnbm9yZVxuaW1wb3J0IHtcbiAgYW51bWJlciwgYXN5bmNMb29wLFxuICBjaGVja09wdHMsIGNsZWFuLFxuICB0eXBlIEtERklucHV0LCByb3RsLFxuICBzd2FwMzJJZkJFLFxuICB1MzJcbn0gZnJvbSAnLi91dGlscy50cyc7XG5cbi8vIFRoZSBtYWluIFNjcnlwdCBsb29wOiB1c2VzIFNhbHNhIGV4dGVuc2l2ZWx5LlxuLy8gU2l4IHZlcnNpb25zIG9mIHRoZSBmdW5jdGlvbiB3ZXJlIHRyaWVkLCB0aGlzIGlzIHRoZSBmYXN0ZXN0IG9uZS5cbi8vIHByZXR0aWVyLWlnbm9yZVxuZnVuY3Rpb24gWG9yQW5kU2Fsc2EoXG4gIHByZXY6IFVpbnQzMkFycmF5LFxuICBwaTogbnVtYmVyLFxuICBpbnB1dDogVWludDMyQXJyYXksXG4gIGlpOiBudW1iZXIsXG4gIG91dDogVWludDMyQXJyYXksXG4gIG9pOiBudW1iZXJcbikge1xuICAvLyBCYXNlZCBvbiBodHRwczovL2NyLnlwLnRvL3NhbHNhMjAuaHRtbFxuICAvLyBYb3IgYmxvY2tzXG4gIGxldCB5MDAgPSBwcmV2W3BpKytdIF4gaW5wdXRbaWkrK10sIHkwMSA9IHByZXZbcGkrK10gXiBpbnB1dFtpaSsrXTtcbiAgbGV0IHkwMiA9IHByZXZbcGkrK10gXiBpbnB1dFtpaSsrXSwgeTAzID0gcHJldltwaSsrXSBeIGlucHV0W2lpKytdO1xuICBsZXQgeTA0ID0gcHJldltwaSsrXSBeIGlucHV0W2lpKytdLCB5MDUgPSBwcmV2W3BpKytdIF4gaW5wdXRbaWkrK107XG4gIGxldCB5MDYgPSBwcmV2W3BpKytdIF4gaW5wdXRbaWkrK10sIHkwNyA9IHByZXZbcGkrK10gXiBpbnB1dFtpaSsrXTtcbiAgbGV0IHkwOCA9IHByZXZbcGkrK10gXiBpbnB1dFtpaSsrXSwgeTA5ID0gcHJldltwaSsrXSBeIGlucHV0W2lpKytdO1xuICBsZXQgeTEwID0gcHJldltwaSsrXSBeIGlucHV0W2lpKytdLCB5MTEgPSBwcmV2W3BpKytdIF4gaW5wdXRbaWkrK107XG4gIGxldCB5MTIgPSBwcmV2W3BpKytdIF4gaW5wdXRbaWkrK10sIHkxMyA9IHByZXZbcGkrK10gXiBpbnB1dFtpaSsrXTtcbiAgbGV0IHkxNCA9IHByZXZbcGkrK10gXiBpbnB1dFtpaSsrXSwgeTE1ID0gcHJldltwaSsrXSBeIGlucHV0W2lpKytdO1xuICAvLyBTYXZlIHN0YXRlIHRvIHRlbXBvcmFyeSB2YXJpYWJsZXMgKHNhbHNhKVxuICBsZXQgeDAwID0geTAwLCB4MDEgPSB5MDEsIHgwMiA9IHkwMiwgeDAzID0geTAzLFxuICAgICAgeDA0ID0geTA0LCB4MDUgPSB5MDUsIHgwNiA9IHkwNiwgeDA3ID0geTA3LFxuICAgICAgeDA4ID0geTA4LCB4MDkgPSB5MDksIHgxMCA9IHkxMCwgeDExID0geTExLFxuICAgICAgeDEyID0geTEyLCB4MTMgPSB5MTMsIHgxNCA9IHkxNCwgeDE1ID0geTE1O1xuICAvLyBNYWluIGxvb3AgKHNhbHNhKVxuICBmb3IgKGxldCBpID0gMDsgaSA8IDg7IGkgKz0gMikge1xuICAgIHgwNCBePSByb3RsKHgwMCArIHgxMiB8IDAsICA3KTsgeDA4IF49IHJvdGwoeDA0ICsgeDAwIHwgMCwgIDkpO1xuICAgIHgxMiBePSByb3RsKHgwOCArIHgwNCB8IDAsIDEzKTsgeDAwIF49IHJvdGwoeDEyICsgeDA4IHwgMCwgMTgpO1xuICAgIHgwOSBePSByb3RsKHgwNSArIHgwMSB8IDAsICA3KTsgeDEzIF49IHJvdGwoeDA5ICsgeDA1IHwgMCwgIDkpO1xuICAgIHgwMSBePSByb3RsKHgxMyArIHgwOSB8IDAsIDEzKTsgeDA1IF49IHJvdGwoeDAxICsgeDEzIHwgMCwgMTgpO1xuICAgIHgxNCBePSByb3RsKHgxMCArIHgwNiB8IDAsICA3KTsgeDAyIF49IHJvdGwoeDE0ICsgeDEwIHwgMCwgIDkpO1xuICAgIHgwNiBePSByb3RsKHgwMiArIHgxNCB8IDAsIDEzKTsgeDEwIF49IHJvdGwoeDA2ICsgeDAyIHwgMCwgMTgpO1xuICAgIHgwMyBePSByb3RsKHgxNSArIHgxMSB8IDAsICA3KTsgeDA3IF49IHJvdGwoeDAzICsgeDE1IHwgMCwgIDkpO1xuICAgIHgxMSBePSByb3RsKHgwNyArIHgwMyB8IDAsIDEzKTsgeDE1IF49IHJvdGwoeDExICsgeDA3IHwgMCwgMTgpO1xuICAgIHgwMSBePSByb3RsKHgwMCArIHgwMyB8IDAsICA3KTsgeDAyIF49IHJvdGwoeDAxICsgeDAwIHwgMCwgIDkpO1xuICAgIHgwMyBePSByb3RsKHgwMiArIHgwMSB8IDAsIDEzKTsgeDAwIF49IHJvdGwoeDAzICsgeDAyIHwgMCwgMTgpO1xuICAgIHgwNiBePSByb3RsKHgwNSArIHgwNCB8IDAsICA3KTsgeDA3IF49IHJvdGwoeDA2ICsgeDA1IHwgMCwgIDkpO1xuICAgIHgwNCBePSByb3RsKHgwNyArIHgwNiB8IDAsIDEzKTsgeDA1IF49IHJvdGwoeDA0ICsgeDA3IHwgMCwgMTgpO1xuICAgIHgxMSBePSByb3RsKHgxMCArIHgwOSB8IDAsICA3KTsgeDA4IF49IHJvdGwoeDExICsgeDEwIHwgMCwgIDkpO1xuICAgIHgwOSBePSByb3RsKHgwOCArIHgxMSB8IDAsIDEzKTsgeDEwIF49IHJvdGwoeDA5ICsgeDA4IHwgMCwgMTgpO1xuICAgIHgxMiBePSByb3RsKHgxNSArIHgxNCB8IDAsICA3KTsgeDEzIF49IHJvdGwoeDEyICsgeDE1IHwgMCwgIDkpO1xuICAgIHgxNCBePSByb3RsKHgxMyArIHgxMiB8IDAsIDEzKTsgeDE1IF49IHJvdGwoeDE0ICsgeDEzIHwgMCwgMTgpO1xuICB9XG4gIC8vIFdyaXRlIG91dHB1dCAoc2Fsc2EpXG4gIG91dFtvaSsrXSA9ICh5MDAgKyB4MDApIHwgMDsgb3V0W29pKytdID0gKHkwMSArIHgwMSkgfCAwO1xuICBvdXRbb2krK10gPSAoeTAyICsgeDAyKSB8IDA7IG91dFtvaSsrXSA9ICh5MDMgKyB4MDMpIHwgMDtcbiAgb3V0W29pKytdID0gKHkwNCArIHgwNCkgfCAwOyBvdXRbb2krK10gPSAoeTA1ICsgeDA1KSB8IDA7XG4gIG91dFtvaSsrXSA9ICh5MDYgKyB4MDYpIHwgMDsgb3V0W29pKytdID0gKHkwNyArIHgwNykgfCAwO1xuICBvdXRbb2krK10gPSAoeTA4ICsgeDA4KSB8IDA7IG91dFtvaSsrXSA9ICh5MDkgKyB4MDkpIHwgMDtcbiAgb3V0W29pKytdID0gKHkxMCArIHgxMCkgfCAwOyBvdXRbb2krK10gPSAoeTExICsgeDExKSB8IDA7XG4gIG91dFtvaSsrXSA9ICh5MTIgKyB4MTIpIHwgMDsgb3V0W29pKytdID0gKHkxMyArIHgxMykgfCAwO1xuICBvdXRbb2krK10gPSAoeTE0ICsgeDE0KSB8IDA7IG91dFtvaSsrXSA9ICh5MTUgKyB4MTUpIHwgMDtcbn1cblxuZnVuY3Rpb24gQmxvY2tNaXgoaW5wdXQ6IFVpbnQzMkFycmF5LCBpaTogbnVtYmVyLCBvdXQ6IFVpbnQzMkFycmF5LCBvaTogbnVtYmVyLCByOiBudW1iZXIpIHtcbiAgLy8gVGhlIGJsb2NrIEIgaXMgciAxMjgtYnl0ZSBjaHVua3MgKHdoaWNoIGlzIGVxdWl2YWxlbnQgb2YgMnIgNjQtYnl0ZSBjaHVua3MpXG4gIGxldCBoZWFkID0gb2kgKyAwO1xuICBsZXQgdGFpbCA9IG9pICsgMTYgKiByO1xuICBmb3IgKGxldCBpID0gMDsgaSA8IDE2OyBpKyspIG91dFt0YWlsICsgaV0gPSBpbnB1dFtpaSArICgyICogciAtIDEpICogMTYgKyBpXTsgLy8gWCBcdTIxOTAgQlsyclx1MjIxMjFdXG4gIGZvciAobGV0IGkgPSAwOyBpIDwgcjsgaSsrLCBoZWFkICs9IDE2LCBpaSArPSAxNikge1xuICAgIC8vIFdlIHdyaXRlIG9kZCAmIGV2ZW4gWWkgYXQgc2FtZSB0aW1lLiBFdmVuOiAwYlhYWFhYMCBPZGQ6ICAwYlhYWFhYMVxuICAgIFhvckFuZFNhbHNhKG91dCwgdGFpbCwgaW5wdXQsIGlpLCBvdXQsIGhlYWQpOyAvLyBoZWFkW2ldID0gU2Fsc2EoYmxvY2tJblsyKmldIF4gdGFpbFtpLTFdKVxuICAgIGlmIChpID4gMCkgdGFpbCArPSAxNjsgLy8gRmlyc3QgaXRlcmF0aW9uIG92ZXJ3cml0ZXMgdG1wIHZhbHVlIGluIHRhaWxcbiAgICBYb3JBbmRTYWxzYShvdXQsIGhlYWQsIGlucHV0LCAoaWkgKz0gMTYpLCBvdXQsIHRhaWwpOyAvLyB0YWlsW2ldID0gU2Fsc2EoYmxvY2tJblsyKmkrMV0gXiBoZWFkW2ldKVxuICB9XG59XG5cbi8qKlxuICogU2NyeXB0IG9wdGlvbnM6XG4gKiAtIGBOYCBpcyBjcHUvbWVtIHdvcmsgZmFjdG9yIChwb3dlciBvZiAyIGUuZy4gYDIqKjE4YClcbiAqIC0gYHJgIGlzIGJsb2NrIHNpemUgKDggaXMgY29tbW9uKSwgZmluZS10dW5lcyBzZXF1ZW50aWFsIG1lbW9yeSByZWFkIHNpemUgYW5kIHBlcmZvcm1hbmNlXG4gKiAtIGBwYCBpcyBwYXJhbGxlbGl6YXRpb24gZmFjdG9yICgxIGlzIGNvbW1vbilcbiAqIC0gYGRrTGVuYCBpcyBvdXRwdXQga2V5IGxlbmd0aCBpbiBieXRlcyBlLmcuIDMyLlxuICogLSBgYXN5bmNUaWNrYCAtIChkZWZhdWx0OiAxMCkgbWF4IHRpbWUgaW4gbXMgZm9yIHdoaWNoIGFzeW5jIGZ1bmN0aW9uIGNhbiBibG9jayBleGVjdXRpb25cbiAqIC0gYG1heG1lbWAgLSAoZGVmYXVsdDogYDEwMjQgKiogMyArIDEwMjRgIGFrYSAxR0IrMUtCKS4gQSBsaW1pdCB0aGF0IHRoZSBhcHAgY291bGQgdXNlIGZvciBzY3J5cHRcbiAqIC0gYG9uUHJvZ3Jlc3NgIC0gY2FsbGJhY2sgZnVuY3Rpb24gdGhhdCB3b3VsZCBiZSBleGVjdXRlZCBmb3IgcHJvZ3Jlc3MgcmVwb3J0XG4gKi9cbmV4cG9ydCB0eXBlIFNjcnlwdE9wdHMgPSB7XG4gIE46IG51bWJlcjsgLy8gY29zdCBmYWN0b3JcbiAgcjogbnVtYmVyOyAvLyBibG9jayBzaXplXG4gIHA6IG51bWJlcjsgLy8gcGFyYWxsZWxpemF0aW9uXG4gIGRrTGVuPzogbnVtYmVyOyAvLyBrZXkgbGVuZ3RoXG4gIGFzeW5jVGljaz86IG51bWJlcjsgLy8gYmxvY2sgZXhlY3V0aW9uIG1heCB0aW1lXG4gIG1heG1lbT86IG51bWJlcjtcbiAgb25Qcm9ncmVzcz86IChwcm9ncmVzczogbnVtYmVyKSA9PiB2b2lkO1xufTtcblxuLy8gQ29tbW9uIHByb2xvZ3VlIGFuZCBlcGlsb2d1ZSBmb3Igc3luYy9hc3luYyBmdW5jdGlvbnNcbmZ1bmN0aW9uIHNjcnlwdEluaXQocGFzc3dvcmQ6IEtERklucHV0LCBzYWx0OiBLREZJbnB1dCwgX29wdHM/OiBTY3J5cHRPcHRzKSB7XG4gIC8vIE1heG1lbSAtIDFHQisxS0IgYnkgZGVmYXVsdFxuICBjb25zdCBvcHRzID0gY2hlY2tPcHRzKFxuICAgIHtcbiAgICAgIGRrTGVuOiAzMixcbiAgICAgIGFzeW5jVGljazogMTAsXG4gICAgICBtYXhtZW06IDEwMjQgKiogMyArIDEwMjQsXG4gICAgfSxcbiAgICBfb3B0c1xuICApO1xuICBjb25zdCB7IE4sIHIsIHAsIGRrTGVuLCBhc3luY1RpY2ssIG1heG1lbSwgb25Qcm9ncmVzcyB9ID0gb3B0cztcbiAgYW51bWJlcihOLCAnTicpO1xuICBhbnVtYmVyKHIsICdyJyk7XG4gIGFudW1iZXIocCwgJ3AnKTtcbiAgYW51bWJlcihka0xlbiwgJ2RrTGVuJyk7XG4gIGFudW1iZXIoYXN5bmNUaWNrLCAnYXN5bmNUaWNrJyk7XG4gIGFudW1iZXIobWF4bWVtLCAnbWF4bWVtJyk7XG4gIGlmIChvblByb2dyZXNzICE9PSB1bmRlZmluZWQgJiYgdHlwZW9mIG9uUHJvZ3Jlc3MgIT09ICdmdW5jdGlvbicpXG4gICAgdGhyb3cgbmV3IEVycm9yKCdwcm9ncmVzc0NiIG11c3QgYmUgYSBmdW5jdGlvbicpO1xuICBjb25zdCBibG9ja1NpemUgPSAxMjggKiByO1xuICBjb25zdCBibG9ja1NpemUzMiA9IGJsb2NrU2l6ZSAvIDQ7XG5cbiAgLy8gTWF4IE4gaXMgMl4zMiAoSW50ZWdyaWZ5IGlzIDMyLWJpdCkuXG4gIC8vIFJlYWwgbGltaXQgY2FuIGJlIDJeMjI6IHNvbWUgSlMgZW5naW5lcyBsaW1pdCBVaW50OEFycmF5IHRvIDRHQi5cbiAgLy8gU3BlYyBjaGVjayBgTiA+PSAyXihibG9ja1NpemUgLyA4KWAgaXMgbm90IGRvbmUgZm9yIGNvbXBhdCB3aXRoIHBvcHVsYXIgbGlicyxcbiAgLy8gd2hpY2ggdXNlZCBpbmNvcnJlY3QgcjogMSwgcDogOC4gQWxzbywgdGhlIGNoZWNrIHNlZW1zIHRvIGJlIGEgc3BlYyBlcnJvcjpcbiAgLy8gaHR0cHM6Ly93d3cucmZjLWVkaXRvci5vcmcvZXJyYXRhX3NlYXJjaC5waHA/cmZjPTc5MTRcbiAgY29uc3QgcG93MzIgPSBNYXRoLnBvdygyLCAzMik7XG4gIGlmIChOIDw9IDEgfHwgKE4gJiAoTiAtIDEpKSAhPT0gMCB8fCBOID4gcG93MzIpXG4gICAgdGhyb3cgbmV3IEVycm9yKCdcIk5cIiBleHBlY3RlZCBhIHBvd2VyIG9mIDIsIGFuZCAyXjEgPD0gTiA8PSAyXjMyJyk7XG4gIGlmIChwIDwgMSB8fCBwID4gKChwb3czMiAtIDEpICogMzIpIC8gYmxvY2tTaXplKVxuICAgIHRocm93IG5ldyBFcnJvcignXCJwXCIgZXhwZWN0ZWQgaW50ZWdlciAxLi4oKDJeMzIgLSAxKSAqIDMyKSAvICgxMjggKiByKScpO1xuICBpZiAoZGtMZW4gPCAxIHx8IGRrTGVuID4gKHBvdzMyIC0gMSkgKiAzMilcbiAgICB0aHJvdyBuZXcgRXJyb3IoJ1wiZGtMZW5cIiBleHBlY3RlZCBpbnRlZ2VyIDEuLigyXjMyIC0gMSkgKiAzMicpO1xuICBjb25zdCBtZW1Vc2VkID0gYmxvY2tTaXplICogKE4gKyBwKTtcbiAgaWYgKG1lbVVzZWQgPiBtYXhtZW0pXG4gICAgdGhyb3cgbmV3IEVycm9yKCdcIm1heG1lbVwiIGxpbWl0IHdhcyBoaXQsIGV4cGVjdGVkIDEyOCpyKihOK3ApIDw9IFwibWF4bWVtXCI9JyArIG1heG1lbSk7XG4gIC8vIFtCMC4uLkJwXHUyMjEyMV0gXHUyMTkwIFBCS0RGMkhNQUMtU0hBMjU2KFBhc3NwaHJhc2UsIFNhbHQsIDEsIGJsb2NrU2l6ZSpQYXJhbGxlbGl6YXRpb25GYWN0b3IpXG4gIC8vIFNpbmNlIGl0IGhhcyBvbmx5IG9uZSBpdGVyYXRpb24gdGhlcmUgaXMgbm8gcmVhc29uIHRvIHVzZSBhc3luYyB2YXJpYW50XG4gIGNvbnN0IEIgPSBwYmtkZjIoc2hhMjU2LCBwYXNzd29yZCwgc2FsdCwgeyBjOiAxLCBka0xlbjogYmxvY2tTaXplICogcCB9KTtcbiAgY29uc3QgQjMyID0gdTMyKEIpO1xuICAvLyBSZS11c2VkIGJldHdlZW4gcGFyYWxsZWwgaXRlcmF0aW9ucy4gQXJyYXkoaXRlcmF0aW9ucykgb2YgQlxuICBjb25zdCBWID0gdTMyKG5ldyBVaW50OEFycmF5KGJsb2NrU2l6ZSAqIE4pKTtcbiAgY29uc3QgdG1wID0gdTMyKG5ldyBVaW50OEFycmF5KGJsb2NrU2l6ZSkpO1xuICBsZXQgYmxvY2tNaXhDYiA9ICgpID0+IHt9O1xuICBpZiAob25Qcm9ncmVzcykge1xuICAgIGNvbnN0IHRvdGFsQmxvY2tNaXggPSAyICogTiAqIHA7XG4gICAgLy8gSW52b2tlIGNhbGxiYWNrIGlmIHByb2dyZXNzIGNoYW5nZXMgZnJvbSAxMC4wMSB0byAxMC4wMlxuICAgIC8vIEFsbG93cyB0byBkcmF3IHNtb290aCBwcm9ncmVzcyBiYXIgb24gdXAgdG8gOEsgc2NyZWVuXG4gICAgY29uc3QgY2FsbGJhY2tQZXIgPSBNYXRoLm1heChNYXRoLmZsb29yKHRvdGFsQmxvY2tNaXggLyAxMDAwMCksIDEpO1xuICAgIGxldCBibG9ja01peENudCA9IDA7XG4gICAgYmxvY2tNaXhDYiA9ICgpID0+IHtcbiAgICAgIGJsb2NrTWl4Q250Kys7XG4gICAgICBpZiAob25Qcm9ncmVzcyAmJiAoIShibG9ja01peENudCAlIGNhbGxiYWNrUGVyKSB8fCBibG9ja01peENudCA9PT0gdG90YWxCbG9ja01peCkpXG4gICAgICAgIG9uUHJvZ3Jlc3MoYmxvY2tNaXhDbnQgLyB0b3RhbEJsb2NrTWl4KTtcbiAgICB9O1xuICB9XG4gIHJldHVybiB7IE4sIHIsIHAsIGRrTGVuLCBibG9ja1NpemUzMiwgViwgQjMyLCBCLCB0bXAsIGJsb2NrTWl4Q2IsIGFzeW5jVGljayB9O1xufVxuXG5mdW5jdGlvbiBzY3J5cHRPdXRwdXQoXG4gIHBhc3N3b3JkOiBLREZJbnB1dCxcbiAgZGtMZW46IG51bWJlcixcbiAgQjogVWludDhBcnJheSxcbiAgVjogVWludDMyQXJyYXksXG4gIHRtcDogVWludDMyQXJyYXlcbikge1xuICBjb25zdCByZXMgPSBwYmtkZjIoc2hhMjU2LCBwYXNzd29yZCwgQiwgeyBjOiAxLCBka0xlbiB9KTtcbiAgY2xlYW4oQiwgViwgdG1wKTtcbiAgcmV0dXJuIHJlcztcbn1cblxuLyoqXG4gKiBTY3J5cHQgS0RGIGZyb20gUkZDIDc5MTQuIFNlZSB7QGxpbmsgU2NyeXB0T3B0c30uXG4gKiBAZXhhbXBsZVxuICogc2NyeXB0KCdwYXNzd29yZCcsICdzYWx0JywgeyBOOiAyKioxOCwgcjogOCwgcDogMSwgZGtMZW46IDMyIH0pO1xuICovXG5leHBvcnQgZnVuY3Rpb24gc2NyeXB0KHBhc3N3b3JkOiBLREZJbnB1dCwgc2FsdDogS0RGSW5wdXQsIG9wdHM6IFNjcnlwdE9wdHMpOiBVaW50OEFycmF5IHtcbiAgY29uc3QgeyBOLCByLCBwLCBka0xlbiwgYmxvY2tTaXplMzIsIFYsIEIzMiwgQiwgdG1wLCBibG9ja01peENiIH0gPSBzY3J5cHRJbml0KFxuICAgIHBhc3N3b3JkLFxuICAgIHNhbHQsXG4gICAgb3B0c1xuICApO1xuICBzd2FwMzJJZkJFKEIzMik7XG4gIGZvciAobGV0IHBpID0gMDsgcGkgPCBwOyBwaSsrKSB7XG4gICAgY29uc3QgUGkgPSBibG9ja1NpemUzMiAqIHBpO1xuICAgIGZvciAobGV0IGkgPSAwOyBpIDwgYmxvY2tTaXplMzI7IGkrKykgVltpXSA9IEIzMltQaSArIGldOyAvLyBWWzBdID0gQltpXVxuICAgIGZvciAobGV0IGkgPSAwLCBwb3MgPSAwOyBpIDwgTiAtIDE7IGkrKykge1xuICAgICAgQmxvY2tNaXgoViwgcG9zLCBWLCAocG9zICs9IGJsb2NrU2l6ZTMyKSwgcik7IC8vIFZbaV0gPSBCbG9ja01peChWW2ktMV0pO1xuICAgICAgYmxvY2tNaXhDYigpO1xuICAgIH1cbiAgICBCbG9ja01peChWLCAoTiAtIDEpICogYmxvY2tTaXplMzIsIEIzMiwgUGksIHIpOyAvLyBQcm9jZXNzIGxhc3QgZWxlbWVudFxuICAgIGJsb2NrTWl4Q2IoKTtcbiAgICBmb3IgKGxldCBpID0gMDsgaSA8IE47IGkrKykge1xuICAgICAgLy8gRmlyc3QgdTMyIG9mIHRoZSBsYXN0IDY0LWJ5dGUgYmxvY2sgKHUzMiBpcyBMRSlcbiAgICAgIC8vICYgKE4gLSAxKSBpcyAlIE4gYXMgTiBpcyBhIHBvd2VyIG9mIDIsIE4gJiAoTiAtIDEpID0gMCBpcyBjaGVja2VkIGFib3ZlOyA+Pj4gMCBmb3IgdW5zaWduZWQsIGlucHV0IGZpdHMgaW4gdTMyXG4gICAgICBjb25zdCBqID0gKEIzMltQaSArIGJsb2NrU2l6ZTMyIC0gMTZdICYgKE4gLSAxKSkgPj4+IDA7IC8vIGogPSBJbnRlZ3JpZnkoWCkgJSBpdGVyYXRpb25zXG4gICAgICBmb3IgKGxldCBrID0gMDsgayA8IGJsb2NrU2l6ZTMyOyBrKyspIHRtcFtrXSA9IEIzMltQaSArIGtdIF4gVltqICogYmxvY2tTaXplMzIgKyBrXTsgLy8gdG1wID0gQiBeIFZbal1cbiAgICAgIEJsb2NrTWl4KHRtcCwgMCwgQjMyLCBQaSwgcik7IC8vIEIgPSBCbG9ja01peChCIF4gVltqXSlcbiAgICAgIGJsb2NrTWl4Q2IoKTtcbiAgICB9XG4gIH1cbiAgc3dhcDMySWZCRShCMzIpO1xuICByZXR1cm4gc2NyeXB0T3V0cHV0KHBhc3N3b3JkLCBka0xlbiwgQiwgViwgdG1wKTtcbn1cblxuLyoqXG4gKiBTY3J5cHQgS0RGIGZyb20gUkZDIDc5MTQuIEFzeW5jIHZlcnNpb24uIFNlZSB7QGxpbmsgU2NyeXB0T3B0c30uXG4gKiBAZXhhbXBsZVxuICogYXdhaXQgc2NyeXB0QXN5bmMoJ3Bhc3N3b3JkJywgJ3NhbHQnLCB7IE46IDIqKjE4LCByOiA4LCBwOiAxLCBka0xlbjogMzIgfSk7XG4gKi9cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBzY3J5cHRBc3luYyhcbiAgcGFzc3dvcmQ6IEtERklucHV0LFxuICBzYWx0OiBLREZJbnB1dCxcbiAgb3B0czogU2NyeXB0T3B0c1xuKTogUHJvbWlzZTxVaW50OEFycmF5PiB7XG4gIGNvbnN0IHsgTiwgciwgcCwgZGtMZW4sIGJsb2NrU2l6ZTMyLCBWLCBCMzIsIEIsIHRtcCwgYmxvY2tNaXhDYiwgYXN5bmNUaWNrIH0gPSBzY3J5cHRJbml0KFxuICAgIHBhc3N3b3JkLFxuICAgIHNhbHQsXG4gICAgb3B0c1xuICApO1xuICBzd2FwMzJJZkJFKEIzMik7XG4gIGZvciAobGV0IHBpID0gMDsgcGkgPCBwOyBwaSsrKSB7XG4gICAgY29uc3QgUGkgPSBibG9ja1NpemUzMiAqIHBpO1xuICAgIGZvciAobGV0IGkgPSAwOyBpIDwgYmxvY2tTaXplMzI7IGkrKykgVltpXSA9IEIzMltQaSArIGldOyAvLyBWWzBdID0gQltpXVxuICAgIGxldCBwb3MgPSAwO1xuICAgIGF3YWl0IGFzeW5jTG9vcChOIC0gMSwgYXN5bmNUaWNrLCAoKSA9PiB7XG4gICAgICBCbG9ja01peChWLCBwb3MsIFYsIChwb3MgKz0gYmxvY2tTaXplMzIpLCByKTsgLy8gVltpXSA9IEJsb2NrTWl4KFZbaS0xXSk7XG4gICAgICBibG9ja01peENiKCk7XG4gICAgfSk7XG4gICAgQmxvY2tNaXgoViwgKE4gLSAxKSAqIGJsb2NrU2l6ZTMyLCBCMzIsIFBpLCByKTsgLy8gUHJvY2VzcyBsYXN0IGVsZW1lbnRcbiAgICBibG9ja01peENiKCk7XG4gICAgYXdhaXQgYXN5bmNMb29wKE4sIGFzeW5jVGljaywgKCkgPT4ge1xuICAgICAgLy8gRmlyc3QgdTMyIG9mIHRoZSBsYXN0IDY0LWJ5dGUgYmxvY2sgKHUzMiBpcyBMRSlcbiAgICAgIC8vICYgKE4gLSAxKSBpcyAlIE4gYXMgTiBpcyBhIHBvd2VyIG9mIDIsIE4gJiAoTiAtIDEpID0gMCBpcyBjaGVja2VkIGFib3ZlOyA+Pj4gMCBmb3IgdW5zaWduZWQsIGlucHV0IGZpdHMgaW4gdTMyXG4gICAgICBjb25zdCBqID0gKEIzMltQaSArIGJsb2NrU2l6ZTMyIC0gMTZdICYgKE4gLSAxKSkgPj4+IDA7IC8vIGogPSBJbnRlZ3JpZnkoWCkgJSBpdGVyYXRpb25zXG4gICAgICBmb3IgKGxldCBrID0gMDsgayA8IGJsb2NrU2l6ZTMyOyBrKyspIHRtcFtrXSA9IEIzMltQaSArIGtdIF4gVltqICogYmxvY2tTaXplMzIgKyBrXTsgLy8gdG1wID0gQiBeIFZbal1cbiAgICAgIEJsb2NrTWl4KHRtcCwgMCwgQjMyLCBQaSwgcik7IC8vIEIgPSBCbG9ja01peChCIF4gVltqXSlcbiAgICAgIGJsb2NrTWl4Q2IoKTtcbiAgICB9KTtcbiAgfVxuICBzd2FwMzJJZkJFKEIzMik7XG4gIHJldHVybiBzY3J5cHRPdXRwdXQocGFzc3dvcmQsIGRrTGVuLCBCLCBWLCB0bXApO1xufVxuIiwgIi8qKlxuICogUEJLREYgKFJGQyAyODk4KS4gQ2FuIGJlIHVzZWQgdG8gY3JlYXRlIGEga2V5IGZyb20gcGFzc3dvcmQgYW5kIHNhbHQuXG4gKiBAbW9kdWxlXG4gKi9cbmltcG9ydCB7IGhtYWMgfSBmcm9tICcuL2htYWMudHMnO1xuLy8gcHJldHRpZXItaWdub3JlXG5pbXBvcnQge1xuICBhaGFzaCwgYW51bWJlcixcbiAgYXN5bmNMb29wLCBjaGVja09wdHMsIGNsZWFuLCBjcmVhdGVWaWV3LCBrZGZJbnB1dFRvQnl0ZXMsXG4gIHR5cGUgQ0hhc2gsXG4gIHR5cGUgSGFzaCxcbiAgdHlwZSBLREZJbnB1dFxufSBmcm9tICcuL3V0aWxzLnRzJztcblxuLyoqXG4gKiBQQktERjIgb3B0aW9uczpcbiAqICogYzogaXRlcmF0aW9ucywgc2hvdWxkIHByb2JhYmx5IGJlIGhpZ2hlciB0aGFuIDEwMF8wMDBcbiAqICogZGtMZW46IGRlc2lyZWQgbGVuZ3RoIG9mIGRlcml2ZWQga2V5IGluIGJ5dGVzXG4gKiAqIGFzeW5jVGljazogbWF4IHRpbWUgaW4gbXMgZm9yIHdoaWNoIGFzeW5jIGZ1bmN0aW9uIGNhbiBibG9jayBleGVjdXRpb25cbiAqL1xuZXhwb3J0IHR5cGUgUGJrZGYyT3B0ID0ge1xuICBjOiBudW1iZXI7XG4gIGRrTGVuPzogbnVtYmVyO1xuICBhc3luY1RpY2s/OiBudW1iZXI7XG59O1xuLy8gQ29tbW9uIHN0YXJ0IGFuZCBlbmQgZm9yIHN5bmMvYXN5bmMgZnVuY3Rpb25zXG5mdW5jdGlvbiBwYmtkZjJJbml0KGhhc2g6IENIYXNoLCBfcGFzc3dvcmQ6IEtERklucHV0LCBfc2FsdDogS0RGSW5wdXQsIF9vcHRzOiBQYmtkZjJPcHQpIHtcbiAgYWhhc2goaGFzaCk7XG4gIGNvbnN0IG9wdHMgPSBjaGVja09wdHMoeyBka0xlbjogMzIsIGFzeW5jVGljazogMTAgfSwgX29wdHMpO1xuICBjb25zdCB7IGMsIGRrTGVuLCBhc3luY1RpY2sgfSA9IG9wdHM7XG4gIGFudW1iZXIoYywgJ2MnKTtcbiAgYW51bWJlcihka0xlbiwgJ2RrTGVuJyk7XG4gIGFudW1iZXIoYXN5bmNUaWNrLCAnYXN5bmNUaWNrJyk7XG4gIGlmIChjIDwgMSkgdGhyb3cgbmV3IEVycm9yKCdpdGVyYXRpb25zIChjKSBtdXN0IGJlID49IDEnKTtcbiAgY29uc3QgcGFzc3dvcmQgPSBrZGZJbnB1dFRvQnl0ZXMoX3Bhc3N3b3JkLCAncGFzc3dvcmQnKTtcbiAgY29uc3Qgc2FsdCA9IGtkZklucHV0VG9CeXRlcyhfc2FsdCwgJ3NhbHQnKTtcbiAgLy8gREsgPSBQQktERjIoUFJGLCBQYXNzd29yZCwgU2FsdCwgYywgZGtMZW4pO1xuICBjb25zdCBESyA9IG5ldyBVaW50OEFycmF5KGRrTGVuKTtcbiAgLy8gVTEgPSBQUkYoUGFzc3dvcmQsIFNhbHQgKyBJTlRfMzJfQkUoaSkpXG4gIGNvbnN0IFBSRiA9IGhtYWMuY3JlYXRlKGhhc2gsIHBhc3N3b3JkKTtcbiAgY29uc3QgUFJGU2FsdCA9IFBSRi5fY2xvbmVJbnRvKCkudXBkYXRlKHNhbHQpO1xuICByZXR1cm4geyBjLCBka0xlbiwgYXN5bmNUaWNrLCBESywgUFJGLCBQUkZTYWx0IH07XG59XG5cbmZ1bmN0aW9uIHBia2RmMk91dHB1dDxUIGV4dGVuZHMgSGFzaDxUPj4oXG4gIFBSRjogSGFzaDxUPixcbiAgUFJGU2FsdDogSGFzaDxUPixcbiAgREs6IFVpbnQ4QXJyYXksXG4gIHByZlc6IEhhc2g8VD4sXG4gIHU6IFVpbnQ4QXJyYXlcbikge1xuICBQUkYuZGVzdHJveSgpO1xuICBQUkZTYWx0LmRlc3Ryb3koKTtcbiAgaWYgKHByZlcpIHByZlcuZGVzdHJveSgpO1xuICBjbGVhbih1KTtcbiAgcmV0dXJuIERLO1xufVxuXG4vKipcbiAqIFBCS0RGMi1ITUFDOiBSRkMgMjg5OCBrZXkgZGVyaXZhdGlvbiBmdW5jdGlvblxuICogQHBhcmFtIGhhc2ggLSBoYXNoIGZ1bmN0aW9uIHRoYXQgd291bGQgYmUgdXNlZCBlLmcuIHNoYTI1NlxuICogQHBhcmFtIHBhc3N3b3JkIC0gcGFzc3dvcmQgZnJvbSB3aGljaCBhIGRlcml2ZWQga2V5IGlzIGdlbmVyYXRlZFxuICogQHBhcmFtIHNhbHQgLSBjcnlwdG9ncmFwaGljIHNhbHRcbiAqIEBwYXJhbSBvcHRzIC0ge2MsIGRrTGVufSB3aGVyZSBjIGlzIHdvcmsgZmFjdG9yIGFuZCBka0xlbiBpcyBvdXRwdXQgbWVzc2FnZSBzaXplXG4gKiBAZXhhbXBsZVxuICogY29uc3Qga2V5ID0gcGJrZGYyKHNoYTI1NiwgJ3Bhc3N3b3JkJywgJ3NhbHQnLCB7IGRrTGVuOiAzMiwgYzogTWF0aC5wb3coMiwgMTgpIH0pO1xuICovXG5leHBvcnQgZnVuY3Rpb24gcGJrZGYyKFxuICBoYXNoOiBDSGFzaCxcbiAgcGFzc3dvcmQ6IEtERklucHV0LFxuICBzYWx0OiBLREZJbnB1dCxcbiAgb3B0czogUGJrZGYyT3B0XG4pOiBVaW50OEFycmF5IHtcbiAgY29uc3QgeyBjLCBka0xlbiwgREssIFBSRiwgUFJGU2FsdCB9ID0gcGJrZGYySW5pdChoYXNoLCBwYXNzd29yZCwgc2FsdCwgb3B0cyk7XG4gIGxldCBwcmZXOiBhbnk7IC8vIFdvcmtpbmcgY29weVxuICBjb25zdCBhcnIgPSBuZXcgVWludDhBcnJheSg0KTtcbiAgY29uc3QgdmlldyA9IGNyZWF0ZVZpZXcoYXJyKTtcbiAgY29uc3QgdSA9IG5ldyBVaW50OEFycmF5KFBSRi5vdXRwdXRMZW4pO1xuICAvLyBESyA9IFQxICsgVDIgKyBcdTIyRUYgKyBUZGtsZW4vaGxlblxuICBmb3IgKGxldCB0aSA9IDEsIHBvcyA9IDA7IHBvcyA8IGRrTGVuOyB0aSsrLCBwb3MgKz0gUFJGLm91dHB1dExlbikge1xuICAgIC8vIFRpID0gRihQYXNzd29yZCwgU2FsdCwgYywgaSlcbiAgICBjb25zdCBUaSA9IERLLnN1YmFycmF5KHBvcywgcG9zICsgUFJGLm91dHB1dExlbik7XG4gICAgdmlldy5zZXRJbnQzMigwLCB0aSwgZmFsc2UpO1xuICAgIC8vIEYoUGFzc3dvcmQsIFNhbHQsIGMsIGkpID0gVTEgXiBVMiBeIFx1MjJFRiBeIFVjXG4gICAgLy8gVTEgPSBQUkYoUGFzc3dvcmQsIFNhbHQgKyBJTlRfMzJfQkUoaSkpXG4gICAgKHByZlcgPSBQUkZTYWx0Ll9jbG9uZUludG8ocHJmVykpLnVwZGF0ZShhcnIpLmRpZ2VzdEludG8odSk7XG4gICAgVGkuc2V0KHUuc3ViYXJyYXkoMCwgVGkubGVuZ3RoKSk7XG4gICAgZm9yIChsZXQgdWkgPSAxOyB1aSA8IGM7IHVpKyspIHtcbiAgICAgIC8vIFVjID0gUFJGKFBhc3N3b3JkLCBVY1x1MjIxMjEpXG4gICAgICBQUkYuX2Nsb25lSW50byhwcmZXKS51cGRhdGUodSkuZGlnZXN0SW50byh1KTtcbiAgICAgIGZvciAobGV0IGkgPSAwOyBpIDwgVGkubGVuZ3RoOyBpKyspIFRpW2ldIF49IHVbaV07XG4gICAgfVxuICB9XG4gIHJldHVybiBwYmtkZjJPdXRwdXQoUFJGLCBQUkZTYWx0LCBESywgcHJmVywgdSk7XG59XG5cbi8qKlxuICogUEJLREYyLUhNQUM6IFJGQyAyODk4IGtleSBkZXJpdmF0aW9uIGZ1bmN0aW9uLiBBc3luYyB2ZXJzaW9uLlxuICogQGV4YW1wbGVcbiAqIGF3YWl0IHBia2RmMkFzeW5jKHNoYTI1NiwgJ3Bhc3N3b3JkJywgJ3NhbHQnLCB7IGRrTGVuOiAzMiwgYzogNTAwXzAwMCB9KTtcbiAqL1xuZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIHBia2RmMkFzeW5jKFxuICBoYXNoOiBDSGFzaCxcbiAgcGFzc3dvcmQ6IEtERklucHV0LFxuICBzYWx0OiBLREZJbnB1dCxcbiAgb3B0czogUGJrZGYyT3B0XG4pOiBQcm9taXNlPFVpbnQ4QXJyYXk+IHtcbiAgY29uc3QgeyBjLCBka0xlbiwgYXN5bmNUaWNrLCBESywgUFJGLCBQUkZTYWx0IH0gPSBwYmtkZjJJbml0KGhhc2gsIHBhc3N3b3JkLCBzYWx0LCBvcHRzKTtcbiAgbGV0IHByZlc6IGFueTsgLy8gV29ya2luZyBjb3B5XG4gIGNvbnN0IGFyciA9IG5ldyBVaW50OEFycmF5KDQpO1xuICBjb25zdCB2aWV3ID0gY3JlYXRlVmlldyhhcnIpO1xuICBjb25zdCB1ID0gbmV3IFVpbnQ4QXJyYXkoUFJGLm91dHB1dExlbik7XG4gIC8vIERLID0gVDEgKyBUMiArIFx1MjJFRiArIFRka2xlbi9obGVuXG4gIGZvciAobGV0IHRpID0gMSwgcG9zID0gMDsgcG9zIDwgZGtMZW47IHRpKyssIHBvcyArPSBQUkYub3V0cHV0TGVuKSB7XG4gICAgLy8gVGkgPSBGKFBhc3N3b3JkLCBTYWx0LCBjLCBpKVxuICAgIGNvbnN0IFRpID0gREsuc3ViYXJyYXkocG9zLCBwb3MgKyBQUkYub3V0cHV0TGVuKTtcbiAgICB2aWV3LnNldEludDMyKDAsIHRpLCBmYWxzZSk7XG4gICAgLy8gRihQYXNzd29yZCwgU2FsdCwgYywgaSkgPSBVMSBeIFUyIF4gXHUyMkVGIF4gVWNcbiAgICAvLyBVMSA9IFBSRihQYXNzd29yZCwgU2FsdCArIElOVF8zMl9CRShpKSlcbiAgICAocHJmVyA9IFBSRlNhbHQuX2Nsb25lSW50byhwcmZXKSkudXBkYXRlKGFycikuZGlnZXN0SW50byh1KTtcbiAgICBUaS5zZXQodS5zdWJhcnJheSgwLCBUaS5sZW5ndGgpKTtcbiAgICBhd2FpdCBhc3luY0xvb3AoYyAtIDEsIGFzeW5jVGljaywgKCkgPT4ge1xuICAgICAgLy8gVWMgPSBQUkYoUGFzc3dvcmQsIFVjXHUyMjEyMSlcbiAgICAgIFBSRi5fY2xvbmVJbnRvKHByZlcpLnVwZGF0ZSh1KS5kaWdlc3RJbnRvKHUpO1xuICAgICAgZm9yIChsZXQgaSA9IDA7IGkgPCBUaS5sZW5ndGg7IGkrKykgVGlbaV0gXj0gdVtpXTtcbiAgICB9KTtcbiAgfVxuICByZXR1cm4gcGJrZGYyT3V0cHV0KFBSRiwgUFJGU2FsdCwgREssIHByZlcsIHUpO1xufVxuIiwgIi8qKlxuICogVXRpbGl0eSBmdW5jdGlvbnMgZm9yIGVuY29kaW5nIGFuZCBkZWNvZGluZyBkYXRhXG4gKi9cblxuLyoqXG4gKiBDb252ZXJ0IGEgaGV4IHN0cmluZyB0byBVaW50OEFycmF5XG4gKiBAcGFyYW0gaGV4IEhleCBzdHJpbmcgdG8gY29udmVydFxuICogQHJldHVybnMgVWludDhBcnJheSBvZiBieXRlc1xuICovXG5leHBvcnQgZnVuY3Rpb24gaGV4VG9CeXRlcyhoZXg6IHN0cmluZyk6IFVpbnQ4QXJyYXkge1xuICAgIGNvbnN0IGJ5dGVzID0gbmV3IFVpbnQ4QXJyYXkoaGV4Lmxlbmd0aCAvIDIpO1xuICAgIGZvciAobGV0IGkgPSAwOyBpIDwgaGV4Lmxlbmd0aDsgaSArPSAyKSB7XG4gICAgICAgIGJ5dGVzW2kgLyAyXSA9IHBhcnNlSW50KGhleC5zbGljZShpLCBpICsgMiksIDE2KTtcbiAgICB9XG4gICAgcmV0dXJuIGJ5dGVzO1xufVxuXG4vKipcbiAqIENvbnZlcnQgVWludDhBcnJheSB0byBoZXggc3RyaW5nXG4gKiBAcGFyYW0gYnl0ZXMgVWludDhBcnJheSB0byBjb252ZXJ0XG4gKiBAcmV0dXJucyBIZXggc3RyaW5nXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBieXRlc1RvSGV4KGJ5dGVzOiBVaW50OEFycmF5KTogc3RyaW5nIHtcbiAgICByZXR1cm4gQXJyYXkuZnJvbShieXRlcylcbiAgICAgICAgLm1hcChiID0+IGIudG9TdHJpbmcoMTYpLnBhZFN0YXJ0KDIsICcwJykpXG4gICAgICAgIC5qb2luKCcnKTtcbn1cblxuLyoqXG4gKiBDb252ZXJ0IGEgVVRGLTggc3RyaW5nIHRvIFVpbnQ4QXJyYXlcbiAqIEBwYXJhbSBzdHIgVVRGLTggc3RyaW5nIHRvIGNvbnZlcnRcbiAqIEByZXR1cm5zIFVpbnQ4QXJyYXkgb2YgYnl0ZXNcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIHV0ZjhUb0J5dGVzKHN0cjogc3RyaW5nKTogVWludDhBcnJheSB7XG4gICAgcmV0dXJuIG5ldyBUZXh0RW5jb2RlcigpLmVuY29kZShzdHIpO1xufVxuXG4vKipcbiAqIENvbnZlcnQgVWludDhBcnJheSB0byBVVEYtOCBzdHJpbmdcbiAqIEBwYXJhbSBieXRlcyBVaW50OEFycmF5IHRvIGNvbnZlcnRcbiAqIEByZXR1cm5zIFVURi04IHN0cmluZ1xuICovXG5leHBvcnQgZnVuY3Rpb24gYnl0ZXNUb1V0ZjgoYnl0ZXM6IFVpbnQ4QXJyYXkpOiBzdHJpbmcge1xuICAgIHJldHVybiBuZXcgVGV4dERlY29kZXIoKS5kZWNvZGUoYnl0ZXMpO1xufVxuIiwgIi8qKlxuICogQklQMzkgU2VlZCBQaHJhc2UgdXRpbGl0aWVzIGZvciBOb3N0cktleS5cbiAqXG4gKiBJbXBsZW1lbnRzIHRoZSBzYW1lIGFsZ29yaXRobSBhcyBgbm9zdHItbnNlYy1zZWVkcGhyYXNlYDpcbiAqIHRoZSAzMi1ieXRlIHByaXZhdGUga2V5IElTIHRoZSBCSVAzOSBlbnRyb3B5IChiaWRpcmVjdGlvbmFsIGVuY29kaW5nKS5cbiAqXG4gKiBVc2VzIEBzY3VyZS9iaXAzOSAoYWxyZWFkeSBhIHRyYW5zaXRpdmUgZGVwIG9mIG5vc3RyLXRvb2xzKS5cbiAqL1xuXG5pbXBvcnQgeyBlbnRyb3B5VG9NbmVtb25pYywgbW5lbW9uaWNUb0VudHJvcHksIHZhbGlkYXRlTW5lbW9uaWMgfSBmcm9tICdAc2N1cmUvYmlwMzknO1xuaW1wb3J0IHsgd29yZGxpc3QgfSBmcm9tICdAc2N1cmUvYmlwMzkvd29yZGxpc3RzL2VuZ2xpc2guanMnO1xuaW1wb3J0IHsgaGV4VG9CeXRlcywgYnl0ZXNUb0hleCwgZ2V0UHVibGljS2V5U3luYyB9IGZyb20gJ25vc3RyLWNyeXB0by11dGlscyc7XG5cbi8qKlxuICogQ29udmVydCBhIGhleCBwcml2YXRlIGtleSB0byBhIDI0LXdvcmQgQklQMzkgbW5lbW9uaWMuXG4gKiBAcGFyYW0ge3N0cmluZ30gaGV4S2V5IC0gNjQtY2hhciBoZXggcHJpdmF0ZSBrZXlcbiAqIEByZXR1cm5zIHtzdHJpbmd9IDI0LXdvcmQgbW5lbW9uaWNcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGtleVRvU2VlZFBocmFzZShoZXhLZXkpIHtcbiAgICBjb25zdCBieXRlcyA9IGhleFRvQnl0ZXMoaGV4S2V5KTtcbiAgICByZXR1cm4gZW50cm9weVRvTW5lbW9uaWMoYnl0ZXMsIHdvcmRsaXN0KTtcbn1cblxuLyoqXG4gKiBDb252ZXJ0IGEgQklQMzkgbW5lbW9uaWMgYmFjayB0byBhIGhleCBwcml2YXRlIGtleSArIGRlcml2ZWQgcHVia2V5LlxuICogQHBhcmFtIHtzdHJpbmd9IHBocmFzZSAtIDI0LXdvcmQgbW5lbW9uaWNcbiAqIEByZXR1cm5zIHt7IGhleEtleTogc3RyaW5nLCBwdWJLZXk6IHN0cmluZyB9fVxuICovXG5leHBvcnQgZnVuY3Rpb24gc2VlZFBocmFzZVRvS2V5KHBocmFzZSkge1xuICAgIGNvbnN0IGVudHJvcHkgPSBtbmVtb25pY1RvRW50cm9weShwaHJhc2UudHJpbSgpLnRvTG93ZXJDYXNlKCksIHdvcmRsaXN0KTtcbiAgICBjb25zdCBoZXhLZXkgPSBieXRlc1RvSGV4KGVudHJvcHkpO1xuICAgIGNvbnN0IHB1YktleSA9IGdldFB1YmxpY0tleVN5bmMoaGV4S2V5KTtcbiAgICByZXR1cm4geyBoZXhLZXksIHB1YktleSB9O1xufVxuXG4vKipcbiAqIFZhbGlkYXRlIGEgQklQMzkgbW5lbW9uaWMgKGNoZWNrc3VtICsgd29yZGxpc3QpLlxuICogQHBhcmFtIHtzdHJpbmd9IHBocmFzZVxuICogQHJldHVybnMge2Jvb2xlYW59XG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBpc1ZhbGlkU2VlZFBocmFzZShwaHJhc2UpIHtcbiAgICB0cnkge1xuICAgICAgICByZXR1cm4gdmFsaWRhdGVNbmVtb25pYyhwaHJhc2UudHJpbSgpLnRvTG93ZXJDYXNlKCksIHdvcmRsaXN0KTtcbiAgICB9IGNhdGNoIHtcbiAgICAgICAgcmV0dXJuIGZhbHNlO1xuICAgIH1cbn1cblxuLyoqXG4gKiBGYXN0IGhldXJpc3RpYzogZG9lcyB0aGUgaW5wdXQgbG9vayBsaWtlIGl0IGNvdWxkIGJlIGEgc2VlZCBwaHJhc2U/XG4gKiAoMTIrIHNwYWNlLXNlcGFyYXRlZCBhbHBoYWJldGljIHdvcmRzKVxuICogQHBhcmFtIHtzdHJpbmd9IGlucHV0XG4gKiBAcmV0dXJucyB7Ym9vbGVhbn1cbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGxvb2tzTGlrZVNlZWRQaHJhc2UoaW5wdXQpIHtcbiAgICBpZiAoIWlucHV0IHx8IHR5cGVvZiBpbnB1dCAhPT0gJ3N0cmluZycpIHJldHVybiBmYWxzZTtcbiAgICBjb25zdCB3b3JkcyA9IGlucHV0LnRyaW0oKS5zcGxpdCgvXFxzKy8pO1xuICAgIHJldHVybiB3b3Jkcy5sZW5ndGggPj0gMTIgJiYgd29yZHMuZXZlcnkodyA9PiAvXlthLXpBLVpdKyQvLnRlc3QodykpO1xufVxuIiwgIi8qISBzY3VyZS1iaXAzOSAtIE1JVCBMaWNlbnNlIChjKSAyMDIyIFBhdHJpY2lvIFBhbGxhZGlubywgUGF1bCBNaWxsZXIgKHBhdWxtaWxsci5jb20pICovXG5pbXBvcnQgeyBwYmtkZjIsIHBia2RmMkFzeW5jIH0gZnJvbSAnQG5vYmxlL2hhc2hlcy9wYmtkZjIuanMnO1xuaW1wb3J0IHsgc2hhMjU2LCBzaGE1MTIgfSBmcm9tICdAbm9ibGUvaGFzaGVzL3NoYTIuanMnO1xuaW1wb3J0IHsgYWJ5dGVzLCBhbnVtYmVyLCByYW5kb21CeXRlcyB9IGZyb20gJ0Bub2JsZS9oYXNoZXMvdXRpbHMuanMnO1xuaW1wb3J0IHsgcGJrZGYyIGFzIHBia2RmMndlYiwgc2hhNTEyIGFzIHNoYTUxMndlYiB9IGZyb20gJ0Bub2JsZS9oYXNoZXMvd2ViY3J5cHRvLmpzJztcbmltcG9ydCB7IHV0aWxzIGFzIGJhc2VVdGlscyB9IGZyb20gJ0BzY3VyZS9iYXNlJztcbi8vIEphcGFuZXNlIHdvcmRsaXN0XG5jb25zdCBpc0phcGFuZXNlID0gKHdvcmRsaXN0KSA9PiB3b3JkbGlzdFswXSA9PT0gJ1xcdTMwNDJcXHUzMDQ0XFx1MzA1M1xcdTMwNGZcXHUzMDU3XFx1MzA5Myc7XG4vLyBOb3JtYWxpemF0aW9uIHJlcGxhY2VzIGVxdWl2YWxlbnQgc2VxdWVuY2VzIG9mIGNoYXJhY3RlcnNcbi8vIHNvIHRoYXQgYW55IHR3byB0ZXh0cyB0aGF0IGFyZSBlcXVpdmFsZW50IHdpbGwgYmUgcmVkdWNlZFxuLy8gdG8gdGhlIHNhbWUgc2VxdWVuY2Ugb2YgY29kZSBwb2ludHMsIGNhbGxlZCB0aGUgbm9ybWFsIGZvcm0gb2YgdGhlIG9yaWdpbmFsIHRleHQuXG4vLyBodHRwczovL3RvbnNreS5tZS9ibG9nL3VuaWNvZGUvI3doeS1pcy1hLS0tLVxuZnVuY3Rpb24gbmZrZChzdHIpIHtcbiAgICBpZiAodHlwZW9mIHN0ciAhPT0gJ3N0cmluZycpXG4gICAgICAgIHRocm93IG5ldyBUeXBlRXJyb3IoJ2ludmFsaWQgbW5lbW9uaWMgdHlwZTogJyArIHR5cGVvZiBzdHIpO1xuICAgIHJldHVybiBzdHIubm9ybWFsaXplKCdORktEJyk7XG59XG5mdW5jdGlvbiBub3JtYWxpemUoc3RyKSB7XG4gICAgY29uc3Qgbm9ybSA9IG5ma2Qoc3RyKTtcbiAgICBjb25zdCB3b3JkcyA9IG5vcm0uc3BsaXQoJyAnKTtcbiAgICBpZiAoIVsxMiwgMTUsIDE4LCAyMSwgMjRdLmluY2x1ZGVzKHdvcmRzLmxlbmd0aCkpXG4gICAgICAgIHRocm93IG5ldyBFcnJvcignSW52YWxpZCBtbmVtb25pYycpO1xuICAgIHJldHVybiB7IG5ma2Q6IG5vcm0sIHdvcmRzIH07XG59XG5mdW5jdGlvbiBhZW50cm9weShlbnQpIHtcbiAgICBhYnl0ZXMoZW50KTtcbiAgICBpZiAoIVsxNiwgMjAsIDI0LCAyOCwgMzJdLmluY2x1ZGVzKGVudC5sZW5ndGgpKVxuICAgICAgICB0aHJvdyBuZXcgRXJyb3IoJ2ludmFsaWQgZW50cm9weSBsZW5ndGgnKTtcbn1cbi8qKlxuICogR2VuZXJhdGUgeCByYW5kb20gd29yZHMuIFVzZXMgQ3J5cHRvZ3JhcGhpY2FsbHktU2VjdXJlIFJhbmRvbSBOdW1iZXIgR2VuZXJhdG9yLlxuICogQHBhcmFtIHdvcmRsaXN0IGltcG9ydGVkIHdvcmRsaXN0IGZvciBzcGVjaWZpYyBsYW5ndWFnZVxuICogQHBhcmFtIHN0cmVuZ3RoIG1uZW1vbmljIHN0cmVuZ3RoIDEyOC0yNTYgYml0c1xuICogQGV4YW1wbGVcbiAqIGdlbmVyYXRlTW5lbW9uaWMod29yZGxpc3QsIDEyOClcbiAqIC8vICdsZWdhbCB3aW5uZXIgdGhhbmsgeWVhciB3YXZlIHNhdXNhZ2Ugd29ydGggdXNlZnVsIGxlZ2FsIHdpbm5lciB0aGFuayB5ZWxsb3cnXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBnZW5lcmF0ZU1uZW1vbmljKHdvcmRsaXN0LCBzdHJlbmd0aCA9IDEyOCkge1xuICAgIGFudW1iZXIoc3RyZW5ndGgpO1xuICAgIGlmIChzdHJlbmd0aCAlIDMyICE9PSAwIHx8IHN0cmVuZ3RoID4gMjU2KVxuICAgICAgICB0aHJvdyBuZXcgVHlwZUVycm9yKCdJbnZhbGlkIGVudHJvcHknKTtcbiAgICByZXR1cm4gZW50cm9weVRvTW5lbW9uaWMocmFuZG9tQnl0ZXMoc3RyZW5ndGggLyA4KSwgd29yZGxpc3QpO1xufVxuY29uc3QgY2FsY0NoZWNrc3VtID0gKGVudHJvcHkpID0+IHtcbiAgICAvLyBDaGVja3N1bSBpcyBlbnQubGVuZ3RoLzQgYml0cyBsb25nXG4gICAgY29uc3QgYml0c0xlZnQgPSA4IC0gZW50cm9weS5sZW5ndGggLyA0O1xuICAgIC8vIFplcm8gcmlnaHRtb3N0IFwiYml0c0xlZnRcIiBiaXRzIGluIGJ5dGVcbiAgICAvLyBGb3IgZXhhbXBsZTogYml0c0xlZnQ9NCB2YWw9MTAxMTExMDEgLT4gMTAxMTAwMDBcbiAgICByZXR1cm4gbmV3IFVpbnQ4QXJyYXkoWyhzaGEyNTYoZW50cm9weSlbMF0gPj4gYml0c0xlZnQpIDw8IGJpdHNMZWZ0XSk7XG59O1xuZnVuY3Rpb24gZ2V0Q29kZXIod29yZGxpc3QpIHtcbiAgICBpZiAoIUFycmF5LmlzQXJyYXkod29yZGxpc3QpIHx8IHdvcmRsaXN0Lmxlbmd0aCAhPT0gMjA0OCB8fCB0eXBlb2Ygd29yZGxpc3RbMF0gIT09ICdzdHJpbmcnKVxuICAgICAgICB0aHJvdyBuZXcgRXJyb3IoJ1dvcmRsaXN0OiBleHBlY3RlZCBhcnJheSBvZiAyMDQ4IHN0cmluZ3MnKTtcbiAgICB3b3JkbGlzdC5mb3JFYWNoKChpKSA9PiB7XG4gICAgICAgIGlmICh0eXBlb2YgaSAhPT0gJ3N0cmluZycpXG4gICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoJ3dvcmRsaXN0OiBub24tc3RyaW5nIGVsZW1lbnQ6ICcgKyBpKTtcbiAgICB9KTtcbiAgICByZXR1cm4gYmFzZVV0aWxzLmNoYWluKGJhc2VVdGlscy5jaGVja3N1bSgxLCBjYWxjQ2hlY2tzdW0pLCBiYXNlVXRpbHMucmFkaXgyKDExLCB0cnVlKSwgYmFzZVV0aWxzLmFscGhhYmV0KHdvcmRsaXN0KSk7XG59XG4vKipcbiAqIFJldmVyc2libGU6IENvbnZlcnRzIG1uZW1vbmljIHN0cmluZyB0byByYXcgZW50cm9weSBpbiBmb3JtIG9mIGJ5dGUgYXJyYXkuXG4gKiBAcGFyYW0gbW5lbW9uaWMgMTItMjQgd29yZHNcbiAqIEBwYXJhbSB3b3JkbGlzdCBpbXBvcnRlZCB3b3JkbGlzdCBmb3Igc3BlY2lmaWMgbGFuZ3VhZ2VcbiAqIEBleGFtcGxlXG4gKiBjb25zdCBtbmVtID0gJ2xlZ2FsIHdpbm5lciB0aGFuayB5ZWFyIHdhdmUgc2F1c2FnZSB3b3J0aCB1c2VmdWwgbGVnYWwgd2lubmVyIHRoYW5rIHllbGxvdyc7XG4gKiBtbmVtb25pY1RvRW50cm9weShtbmVtLCB3b3JkbGlzdClcbiAqIC8vIFByb2R1Y2VzXG4gKiBuZXcgVWludDhBcnJheShbXG4gKiAgIDB4N2YsIDB4N2YsIDB4N2YsIDB4N2YsIDB4N2YsIDB4N2YsIDB4N2YsIDB4N2YsXG4gKiAgIDB4N2YsIDB4N2YsIDB4N2YsIDB4N2YsIDB4N2YsIDB4N2YsIDB4N2YsIDB4N2ZcbiAqIF0pXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBtbmVtb25pY1RvRW50cm9weShtbmVtb25pYywgd29yZGxpc3QpIHtcbiAgICBjb25zdCB7IHdvcmRzIH0gPSBub3JtYWxpemUobW5lbW9uaWMpO1xuICAgIGNvbnN0IGVudHJvcHkgPSBnZXRDb2Rlcih3b3JkbGlzdCkuZGVjb2RlKHdvcmRzKTtcbiAgICBhZW50cm9weShlbnRyb3B5KTtcbiAgICByZXR1cm4gZW50cm9weTtcbn1cbi8qKlxuICogUmV2ZXJzaWJsZTogQ29udmVydHMgcmF3IGVudHJvcHkgaW4gZm9ybSBvZiBieXRlIGFycmF5IHRvIG1uZW1vbmljIHN0cmluZy5cbiAqIEBwYXJhbSBlbnRyb3B5IGJ5dGUgYXJyYXlcbiAqIEBwYXJhbSB3b3JkbGlzdCBpbXBvcnRlZCB3b3JkbGlzdCBmb3Igc3BlY2lmaWMgbGFuZ3VhZ2VcbiAqIEByZXR1cm5zIDEyLTI0IHdvcmRzXG4gKiBAZXhhbXBsZVxuICogY29uc3QgZW50ID0gbmV3IFVpbnQ4QXJyYXkoW1xuICogICAweDdmLCAweDdmLCAweDdmLCAweDdmLCAweDdmLCAweDdmLCAweDdmLCAweDdmLFxuICogICAweDdmLCAweDdmLCAweDdmLCAweDdmLCAweDdmLCAweDdmLCAweDdmLCAweDdmXG4gKiBdKTtcbiAqIGVudHJvcHlUb01uZW1vbmljKGVudCwgd29yZGxpc3QpO1xuICogLy8gJ2xlZ2FsIHdpbm5lciB0aGFuayB5ZWFyIHdhdmUgc2F1c2FnZSB3b3J0aCB1c2VmdWwgbGVnYWwgd2lubmVyIHRoYW5rIHllbGxvdydcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGVudHJvcHlUb01uZW1vbmljKGVudHJvcHksIHdvcmRsaXN0KSB7XG4gICAgYWVudHJvcHkoZW50cm9weSk7XG4gICAgY29uc3Qgd29yZHMgPSBnZXRDb2Rlcih3b3JkbGlzdCkuZW5jb2RlKGVudHJvcHkpO1xuICAgIHJldHVybiB3b3Jkcy5qb2luKGlzSmFwYW5lc2Uod29yZGxpc3QpID8gJ1xcdTMwMDAnIDogJyAnKTtcbn1cbi8qKlxuICogVmFsaWRhdGVzIG1uZW1vbmljIGZvciBiZWluZyAxMi0yNCB3b3JkcyBjb250YWluZWQgaW4gYHdvcmRsaXN0YC5cbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIHZhbGlkYXRlTW5lbW9uaWMobW5lbW9uaWMsIHdvcmRsaXN0KSB7XG4gICAgdHJ5IHtcbiAgICAgICAgbW5lbW9uaWNUb0VudHJvcHkobW5lbW9uaWMsIHdvcmRsaXN0KTtcbiAgICB9XG4gICAgY2F0Y2ggKGUpIHtcbiAgICAgICAgcmV0dXJuIGZhbHNlO1xuICAgIH1cbiAgICByZXR1cm4gdHJ1ZTtcbn1cbmNvbnN0IHBzYWx0ID0gKHBhc3NwaHJhc2UpID0+IG5ma2QoJ21uZW1vbmljJyArIHBhc3NwaHJhc2UpO1xuLyoqXG4gKiBJcnJldmVyc2libGU6IFVzZXMgS0RGIHRvIGRlcml2ZSA2NCBieXRlcyBvZiBrZXkgZGF0YSBmcm9tIG1uZW1vbmljICsgb3B0aW9uYWwgcGFzc3dvcmQuXG4gKiBAcGFyYW0gbW5lbW9uaWMgMTItMjQgd29yZHNcbiAqIEBwYXJhbSBwYXNzcGhyYXNlIHN0cmluZyB0aGF0IHdpbGwgYWRkaXRpb25hbGx5IHByb3RlY3QgdGhlIGtleVxuICogQHJldHVybnMgNjQgYnl0ZXMgb2Yga2V5IGRhdGFcbiAqIEBleGFtcGxlXG4gKiBjb25zdCBtbmVtID0gJ2xlZ2FsIHdpbm5lciB0aGFuayB5ZWFyIHdhdmUgc2F1c2FnZSB3b3J0aCB1c2VmdWwgbGVnYWwgd2lubmVyIHRoYW5rIHllbGxvdyc7XG4gKiBhd2FpdCBtbmVtb25pY1RvU2VlZChtbmVtLCAncGFzc3dvcmQnKTtcbiAqIC8vIG5ldyBVaW50OEFycmF5KFsuLi42NCBieXRlc10pXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBtbmVtb25pY1RvU2VlZChtbmVtb25pYywgcGFzc3BocmFzZSA9ICcnKSB7XG4gICAgcmV0dXJuIHBia2RmMkFzeW5jKHNoYTUxMiwgbm9ybWFsaXplKG1uZW1vbmljKS5uZmtkLCBwc2FsdChwYXNzcGhyYXNlKSwgeyBjOiAyMDQ4LCBka0xlbjogNjQgfSk7XG59XG4vKipcbiAqIElycmV2ZXJzaWJsZTogVXNlcyBLREYgdG8gZGVyaXZlIDY0IGJ5dGVzIG9mIGtleSBkYXRhIGZyb20gbW5lbW9uaWMgKyBvcHRpb25hbCBwYXNzd29yZC5cbiAqIEBwYXJhbSBtbmVtb25pYyAxMi0yNCB3b3Jkc1xuICogQHBhcmFtIHBhc3NwaHJhc2Ugc3RyaW5nIHRoYXQgd2lsbCBhZGRpdGlvbmFsbHkgcHJvdGVjdCB0aGUga2V5XG4gKiBAcmV0dXJucyA2NCBieXRlcyBvZiBrZXkgZGF0YVxuICogQGV4YW1wbGVcbiAqIGNvbnN0IG1uZW0gPSAnbGVnYWwgd2lubmVyIHRoYW5rIHllYXIgd2F2ZSBzYXVzYWdlIHdvcnRoIHVzZWZ1bCBsZWdhbCB3aW5uZXIgdGhhbmsgeWVsbG93JztcbiAqIG1uZW1vbmljVG9TZWVkU3luYyhtbmVtLCAncGFzc3dvcmQnKTtcbiAqIC8vIG5ldyBVaW50OEFycmF5KFsuLi42NCBieXRlc10pXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBtbmVtb25pY1RvU2VlZFN5bmMobW5lbW9uaWMsIHBhc3NwaHJhc2UgPSAnJykge1xuICAgIHJldHVybiBwYmtkZjIoc2hhNTEyLCBub3JtYWxpemUobW5lbW9uaWMpLm5ma2QsIHBzYWx0KHBhc3NwaHJhc2UpLCB7IGM6IDIwNDgsIGRrTGVuOiA2NCB9KTtcbn1cbi8qKlxuICogVXNlcyBuYXRpdmUsIGJ1aWx0LWluIGZ1bmN0aW9uYWxpdHksIHByb3ZpZGVkIGJ5IGdsb2JhbFRoaXMuY3J5cHRvLlxuICogSXJyZXZlcnNpYmxlOiBVc2VzIEtERiB0byBkZXJpdmUgNjQgYnl0ZXMgb2Yga2V5IGRhdGEgZnJvbSBtbmVtb25pYyArIG9wdGlvbmFsIHBhc3N3b3JkLlxuICogQHBhcmFtIG1uZW1vbmljIDEyLTI0IHdvcmRzXG4gKiBAcGFyYW0gcGFzc3BocmFzZSBzdHJpbmcgdGhhdCB3aWxsIGFkZGl0aW9uYWxseSBwcm90ZWN0IHRoZSBrZXlcbiAqIEByZXR1cm5zIDY0IGJ5dGVzIG9mIGtleSBkYXRhXG4gKiBAZXhhbXBsZVxuICogY29uc3QgbW5lbSA9ICdsZWdhbCB3aW5uZXIgdGhhbmsgeWVhciB3YXZlIHNhdXNhZ2Ugd29ydGggdXNlZnVsIGxlZ2FsIHdpbm5lciB0aGFuayB5ZWxsb3cnO1xuICogbW5lbW9uaWNUb1NlZWRXZWJjcnlwdG8obW5lbSwgJ3Bhc3N3b3JkJyk7XG4gKiAvLyBuZXcgVWludDhBcnJheShbLi4uNjQgYnl0ZXNdKVxuICovXG5leHBvcnQgZnVuY3Rpb24gbW5lbW9uaWNUb1NlZWRXZWJjcnlwdG8obW5lbW9uaWMsIHBhc3NwaHJhc2UgPSAnJykge1xuICAgIHJldHVybiBwYmtkZjJ3ZWIoc2hhNTEyd2ViLCBub3JtYWxpemUobW5lbW9uaWMpLm5ma2QsIHBzYWx0KHBhc3NwaHJhc2UpLCB7IGM6IDIwNDgsIGRrTGVuOiA2NCB9KTtcbn1cbiIsICJleHBvcnQgY29uc3Qgd29yZGxpc3QgPSBgYWJhbmRvblxuYWJpbGl0eVxuYWJsZVxuYWJvdXRcbmFib3ZlXG5hYnNlbnRcbmFic29yYlxuYWJzdHJhY3RcbmFic3VyZFxuYWJ1c2VcbmFjY2Vzc1xuYWNjaWRlbnRcbmFjY291bnRcbmFjY3VzZVxuYWNoaWV2ZVxuYWNpZFxuYWNvdXN0aWNcbmFjcXVpcmVcbmFjcm9zc1xuYWN0XG5hY3Rpb25cbmFjdG9yXG5hY3RyZXNzXG5hY3R1YWxcbmFkYXB0XG5hZGRcbmFkZGljdFxuYWRkcmVzc1xuYWRqdXN0XG5hZG1pdFxuYWR1bHRcbmFkdmFuY2VcbmFkdmljZVxuYWVyb2JpY1xuYWZmYWlyXG5hZmZvcmRcbmFmcmFpZFxuYWdhaW5cbmFnZVxuYWdlbnRcbmFncmVlXG5haGVhZFxuYWltXG5haXJcbmFpcnBvcnRcbmFpc2xlXG5hbGFybVxuYWxidW1cbmFsY29ob2xcbmFsZXJ0XG5hbGllblxuYWxsXG5hbGxleVxuYWxsb3dcbmFsbW9zdFxuYWxvbmVcbmFscGhhXG5hbHJlYWR5XG5hbHNvXG5hbHRlclxuYWx3YXlzXG5hbWF0ZXVyXG5hbWF6aW5nXG5hbW9uZ1xuYW1vdW50XG5hbXVzZWRcbmFuYWx5c3RcbmFuY2hvclxuYW5jaWVudFxuYW5nZXJcbmFuZ2xlXG5hbmdyeVxuYW5pbWFsXG5hbmtsZVxuYW5ub3VuY2VcbmFubnVhbFxuYW5vdGhlclxuYW5zd2VyXG5hbnRlbm5hXG5hbnRpcXVlXG5hbnhpZXR5XG5hbnlcbmFwYXJ0XG5hcG9sb2d5XG5hcHBlYXJcbmFwcGxlXG5hcHByb3ZlXG5hcHJpbFxuYXJjaFxuYXJjdGljXG5hcmVhXG5hcmVuYVxuYXJndWVcbmFybVxuYXJtZWRcbmFybW9yXG5hcm15XG5hcm91bmRcbmFycmFuZ2VcbmFycmVzdFxuYXJyaXZlXG5hcnJvd1xuYXJ0XG5hcnRlZmFjdFxuYXJ0aXN0XG5hcnR3b3JrXG5hc2tcbmFzcGVjdFxuYXNzYXVsdFxuYXNzZXRcbmFzc2lzdFxuYXNzdW1lXG5hc3RobWFcbmF0aGxldGVcbmF0b21cbmF0dGFja1xuYXR0ZW5kXG5hdHRpdHVkZVxuYXR0cmFjdFxuYXVjdGlvblxuYXVkaXRcbmF1Z3VzdFxuYXVudFxuYXV0aG9yXG5hdXRvXG5hdXR1bW5cbmF2ZXJhZ2VcbmF2b2NhZG9cbmF2b2lkXG5hd2FrZVxuYXdhcmVcbmF3YXlcbmF3ZXNvbWVcbmF3ZnVsXG5hd2t3YXJkXG5heGlzXG5iYWJ5XG5iYWNoZWxvclxuYmFjb25cbmJhZGdlXG5iYWdcbmJhbGFuY2VcbmJhbGNvbnlcbmJhbGxcbmJhbWJvb1xuYmFuYW5hXG5iYW5uZXJcbmJhclxuYmFyZWx5XG5iYXJnYWluXG5iYXJyZWxcbmJhc2VcbmJhc2ljXG5iYXNrZXRcbmJhdHRsZVxuYmVhY2hcbmJlYW5cbmJlYXV0eVxuYmVjYXVzZVxuYmVjb21lXG5iZWVmXG5iZWZvcmVcbmJlZ2luXG5iZWhhdmVcbmJlaGluZFxuYmVsaWV2ZVxuYmVsb3dcbmJlbHRcbmJlbmNoXG5iZW5lZml0XG5iZXN0XG5iZXRyYXlcbmJldHRlclxuYmV0d2VlblxuYmV5b25kXG5iaWN5Y2xlXG5iaWRcbmJpa2VcbmJpbmRcbmJpb2xvZ3lcbmJpcmRcbmJpcnRoXG5iaXR0ZXJcbmJsYWNrXG5ibGFkZVxuYmxhbWVcbmJsYW5rZXRcbmJsYXN0XG5ibGVha1xuYmxlc3NcbmJsaW5kXG5ibG9vZFxuYmxvc3NvbVxuYmxvdXNlXG5ibHVlXG5ibHVyXG5ibHVzaFxuYm9hcmRcbmJvYXRcbmJvZHlcbmJvaWxcbmJvbWJcbmJvbmVcbmJvbnVzXG5ib29rXG5ib29zdFxuYm9yZGVyXG5ib3JpbmdcbmJvcnJvd1xuYm9zc1xuYm90dG9tXG5ib3VuY2VcbmJveFxuYm95XG5icmFja2V0XG5icmFpblxuYnJhbmRcbmJyYXNzXG5icmF2ZVxuYnJlYWRcbmJyZWV6ZVxuYnJpY2tcbmJyaWRnZVxuYnJpZWZcbmJyaWdodFxuYnJpbmdcbmJyaXNrXG5icm9jY29saVxuYnJva2VuXG5icm9uemVcbmJyb29tXG5icm90aGVyXG5icm93blxuYnJ1c2hcbmJ1YmJsZVxuYnVkZHlcbmJ1ZGdldFxuYnVmZmFsb1xuYnVpbGRcbmJ1bGJcbmJ1bGtcbmJ1bGxldFxuYnVuZGxlXG5idW5rZXJcbmJ1cmRlblxuYnVyZ2VyXG5idXJzdFxuYnVzXG5idXNpbmVzc1xuYnVzeVxuYnV0dGVyXG5idXllclxuYnV6elxuY2FiYmFnZVxuY2FiaW5cbmNhYmxlXG5jYWN0dXNcbmNhZ2VcbmNha2VcbmNhbGxcbmNhbG1cbmNhbWVyYVxuY2FtcFxuY2FuXG5jYW5hbFxuY2FuY2VsXG5jYW5keVxuY2Fubm9uXG5jYW5vZVxuY2FudmFzXG5jYW55b25cbmNhcGFibGVcbmNhcGl0YWxcbmNhcHRhaW5cbmNhclxuY2FyYm9uXG5jYXJkXG5jYXJnb1xuY2FycGV0XG5jYXJyeVxuY2FydFxuY2FzZVxuY2FzaFxuY2FzaW5vXG5jYXN0bGVcbmNhc3VhbFxuY2F0XG5jYXRhbG9nXG5jYXRjaFxuY2F0ZWdvcnlcbmNhdHRsZVxuY2F1Z2h0XG5jYXVzZVxuY2F1dGlvblxuY2F2ZVxuY2VpbGluZ1xuY2VsZXJ5XG5jZW1lbnRcbmNlbnN1c1xuY2VudHVyeVxuY2VyZWFsXG5jZXJ0YWluXG5jaGFpclxuY2hhbGtcbmNoYW1waW9uXG5jaGFuZ2VcbmNoYW9zXG5jaGFwdGVyXG5jaGFyZ2VcbmNoYXNlXG5jaGF0XG5jaGVhcFxuY2hlY2tcbmNoZWVzZVxuY2hlZlxuY2hlcnJ5XG5jaGVzdFxuY2hpY2tlblxuY2hpZWZcbmNoaWxkXG5jaGltbmV5XG5jaG9pY2VcbmNob29zZVxuY2hyb25pY1xuY2h1Y2tsZVxuY2h1bmtcbmNodXJuXG5jaWdhclxuY2lubmFtb25cbmNpcmNsZVxuY2l0aXplblxuY2l0eVxuY2l2aWxcbmNsYWltXG5jbGFwXG5jbGFyaWZ5XG5jbGF3XG5jbGF5XG5jbGVhblxuY2xlcmtcbmNsZXZlclxuY2xpY2tcbmNsaWVudFxuY2xpZmZcbmNsaW1iXG5jbGluaWNcbmNsaXBcbmNsb2NrXG5jbG9nXG5jbG9zZVxuY2xvdGhcbmNsb3VkXG5jbG93blxuY2x1YlxuY2x1bXBcbmNsdXN0ZXJcbmNsdXRjaFxuY29hY2hcbmNvYXN0XG5jb2NvbnV0XG5jb2RlXG5jb2ZmZWVcbmNvaWxcbmNvaW5cbmNvbGxlY3RcbmNvbG9yXG5jb2x1bW5cbmNvbWJpbmVcbmNvbWVcbmNvbWZvcnRcbmNvbWljXG5jb21tb25cbmNvbXBhbnlcbmNvbmNlcnRcbmNvbmR1Y3RcbmNvbmZpcm1cbmNvbmdyZXNzXG5jb25uZWN0XG5jb25zaWRlclxuY29udHJvbFxuY29udmluY2VcbmNvb2tcbmNvb2xcbmNvcHBlclxuY29weVxuY29yYWxcbmNvcmVcbmNvcm5cbmNvcnJlY3RcbmNvc3RcbmNvdHRvblxuY291Y2hcbmNvdW50cnlcbmNvdXBsZVxuY291cnNlXG5jb3VzaW5cbmNvdmVyXG5jb3lvdGVcbmNyYWNrXG5jcmFkbGVcbmNyYWZ0XG5jcmFtXG5jcmFuZVxuY3Jhc2hcbmNyYXRlclxuY3Jhd2xcbmNyYXp5XG5jcmVhbVxuY3JlZGl0XG5jcmVla1xuY3Jld1xuY3JpY2tldFxuY3JpbWVcbmNyaXNwXG5jcml0aWNcbmNyb3BcbmNyb3NzXG5jcm91Y2hcbmNyb3dkXG5jcnVjaWFsXG5jcnVlbFxuY3J1aXNlXG5jcnVtYmxlXG5jcnVuY2hcbmNydXNoXG5jcnlcbmNyeXN0YWxcbmN1YmVcbmN1bHR1cmVcbmN1cFxuY3VwYm9hcmRcbmN1cmlvdXNcbmN1cnJlbnRcbmN1cnRhaW5cbmN1cnZlXG5jdXNoaW9uXG5jdXN0b21cbmN1dGVcbmN5Y2xlXG5kYWRcbmRhbWFnZVxuZGFtcFxuZGFuY2VcbmRhbmdlclxuZGFyaW5nXG5kYXNoXG5kYXVnaHRlclxuZGF3blxuZGF5XG5kZWFsXG5kZWJhdGVcbmRlYnJpc1xuZGVjYWRlXG5kZWNlbWJlclxuZGVjaWRlXG5kZWNsaW5lXG5kZWNvcmF0ZVxuZGVjcmVhc2VcbmRlZXJcbmRlZmVuc2VcbmRlZmluZVxuZGVmeVxuZGVncmVlXG5kZWxheVxuZGVsaXZlclxuZGVtYW5kXG5kZW1pc2VcbmRlbmlhbFxuZGVudGlzdFxuZGVueVxuZGVwYXJ0XG5kZXBlbmRcbmRlcG9zaXRcbmRlcHRoXG5kZXB1dHlcbmRlcml2ZVxuZGVzY3JpYmVcbmRlc2VydFxuZGVzaWduXG5kZXNrXG5kZXNwYWlyXG5kZXN0cm95XG5kZXRhaWxcbmRldGVjdFxuZGV2ZWxvcFxuZGV2aWNlXG5kZXZvdGVcbmRpYWdyYW1cbmRpYWxcbmRpYW1vbmRcbmRpYXJ5XG5kaWNlXG5kaWVzZWxcbmRpZXRcbmRpZmZlclxuZGlnaXRhbFxuZGlnbml0eVxuZGlsZW1tYVxuZGlubmVyXG5kaW5vc2F1clxuZGlyZWN0XG5kaXJ0XG5kaXNhZ3JlZVxuZGlzY292ZXJcbmRpc2Vhc2VcbmRpc2hcbmRpc21pc3NcbmRpc29yZGVyXG5kaXNwbGF5XG5kaXN0YW5jZVxuZGl2ZXJ0XG5kaXZpZGVcbmRpdm9yY2VcbmRpenp5XG5kb2N0b3JcbmRvY3VtZW50XG5kb2dcbmRvbGxcbmRvbHBoaW5cbmRvbWFpblxuZG9uYXRlXG5kb25rZXlcbmRvbm9yXG5kb29yXG5kb3NlXG5kb3VibGVcbmRvdmVcbmRyYWZ0XG5kcmFnb25cbmRyYW1hXG5kcmFzdGljXG5kcmF3XG5kcmVhbVxuZHJlc3NcbmRyaWZ0XG5kcmlsbFxuZHJpbmtcbmRyaXBcbmRyaXZlXG5kcm9wXG5kcnVtXG5kcnlcbmR1Y2tcbmR1bWJcbmR1bmVcbmR1cmluZ1xuZHVzdFxuZHV0Y2hcbmR1dHlcbmR3YXJmXG5keW5hbWljXG5lYWdlclxuZWFnbGVcbmVhcmx5XG5lYXJuXG5lYXJ0aFxuZWFzaWx5XG5lYXN0XG5lYXN5XG5lY2hvXG5lY29sb2d5XG5lY29ub215XG5lZGdlXG5lZGl0XG5lZHVjYXRlXG5lZmZvcnRcbmVnZ1xuZWlnaHRcbmVpdGhlclxuZWxib3dcbmVsZGVyXG5lbGVjdHJpY1xuZWxlZ2FudFxuZWxlbWVudFxuZWxlcGhhbnRcbmVsZXZhdG9yXG5lbGl0ZVxuZWxzZVxuZW1iYXJrXG5lbWJvZHlcbmVtYnJhY2VcbmVtZXJnZVxuZW1vdGlvblxuZW1wbG95XG5lbXBvd2VyXG5lbXB0eVxuZW5hYmxlXG5lbmFjdFxuZW5kXG5lbmRsZXNzXG5lbmRvcnNlXG5lbmVteVxuZW5lcmd5XG5lbmZvcmNlXG5lbmdhZ2VcbmVuZ2luZVxuZW5oYW5jZVxuZW5qb3lcbmVubGlzdFxuZW5vdWdoXG5lbnJpY2hcbmVucm9sbFxuZW5zdXJlXG5lbnRlclxuZW50aXJlXG5lbnRyeVxuZW52ZWxvcGVcbmVwaXNvZGVcbmVxdWFsXG5lcXVpcFxuZXJhXG5lcmFzZVxuZXJvZGVcbmVyb3Npb25cbmVycm9yXG5lcnVwdFxuZXNjYXBlXG5lc3NheVxuZXNzZW5jZVxuZXN0YXRlXG5ldGVybmFsXG5ldGhpY3NcbmV2aWRlbmNlXG5ldmlsXG5ldm9rZVxuZXZvbHZlXG5leGFjdFxuZXhhbXBsZVxuZXhjZXNzXG5leGNoYW5nZVxuZXhjaXRlXG5leGNsdWRlXG5leGN1c2VcbmV4ZWN1dGVcbmV4ZXJjaXNlXG5leGhhdXN0XG5leGhpYml0XG5leGlsZVxuZXhpc3RcbmV4aXRcbmV4b3RpY1xuZXhwYW5kXG5leHBlY3RcbmV4cGlyZVxuZXhwbGFpblxuZXhwb3NlXG5leHByZXNzXG5leHRlbmRcbmV4dHJhXG5leWVcbmV5ZWJyb3dcbmZhYnJpY1xuZmFjZVxuZmFjdWx0eVxuZmFkZVxuZmFpbnRcbmZhaXRoXG5mYWxsXG5mYWxzZVxuZmFtZVxuZmFtaWx5XG5mYW1vdXNcbmZhblxuZmFuY3lcbmZhbnRhc3lcbmZhcm1cbmZhc2hpb25cbmZhdFxuZmF0YWxcbmZhdGhlclxuZmF0aWd1ZVxuZmF1bHRcbmZhdm9yaXRlXG5mZWF0dXJlXG5mZWJydWFyeVxuZmVkZXJhbFxuZmVlXG5mZWVkXG5mZWVsXG5mZW1hbGVcbmZlbmNlXG5mZXN0aXZhbFxuZmV0Y2hcbmZldmVyXG5mZXdcbmZpYmVyXG5maWN0aW9uXG5maWVsZFxuZmlndXJlXG5maWxlXG5maWxtXG5maWx0ZXJcbmZpbmFsXG5maW5kXG5maW5lXG5maW5nZXJcbmZpbmlzaFxuZmlyZVxuZmlybVxuZmlyc3RcbmZpc2NhbFxuZmlzaFxuZml0XG5maXRuZXNzXG5maXhcbmZsYWdcbmZsYW1lXG5mbGFzaFxuZmxhdFxuZmxhdm9yXG5mbGVlXG5mbGlnaHRcbmZsaXBcbmZsb2F0XG5mbG9ja1xuZmxvb3JcbmZsb3dlclxuZmx1aWRcbmZsdXNoXG5mbHlcbmZvYW1cbmZvY3VzXG5mb2dcbmZvaWxcbmZvbGRcbmZvbGxvd1xuZm9vZFxuZm9vdFxuZm9yY2VcbmZvcmVzdFxuZm9yZ2V0XG5mb3JrXG5mb3J0dW5lXG5mb3J1bVxuZm9yd2FyZFxuZm9zc2lsXG5mb3N0ZXJcbmZvdW5kXG5mb3hcbmZyYWdpbGVcbmZyYW1lXG5mcmVxdWVudFxuZnJlc2hcbmZyaWVuZFxuZnJpbmdlXG5mcm9nXG5mcm9udFxuZnJvc3RcbmZyb3duXG5mcm96ZW5cbmZydWl0XG5mdWVsXG5mdW5cbmZ1bm55XG5mdXJuYWNlXG5mdXJ5XG5mdXR1cmVcbmdhZGdldFxuZ2FpblxuZ2FsYXh5XG5nYWxsZXJ5XG5nYW1lXG5nYXBcbmdhcmFnZVxuZ2FyYmFnZVxuZ2FyZGVuXG5nYXJsaWNcbmdhcm1lbnRcbmdhc1xuZ2FzcFxuZ2F0ZVxuZ2F0aGVyXG5nYXVnZVxuZ2F6ZVxuZ2VuZXJhbFxuZ2VuaXVzXG5nZW5yZVxuZ2VudGxlXG5nZW51aW5lXG5nZXN0dXJlXG5naG9zdFxuZ2lhbnRcbmdpZnRcbmdpZ2dsZVxuZ2luZ2VyXG5naXJhZmZlXG5naXJsXG5naXZlXG5nbGFkXG5nbGFuY2VcbmdsYXJlXG5nbGFzc1xuZ2xpZGVcbmdsaW1wc2Vcbmdsb2JlXG5nbG9vbVxuZ2xvcnlcbmdsb3ZlXG5nbG93XG5nbHVlXG5nb2F0XG5nb2RkZXNzXG5nb2xkXG5nb29kXG5nb29zZVxuZ29yaWxsYVxuZ29zcGVsXG5nb3NzaXBcbmdvdmVyblxuZ293blxuZ3JhYlxuZ3JhY2VcbmdyYWluXG5ncmFudFxuZ3JhcGVcbmdyYXNzXG5ncmF2aXR5XG5ncmVhdFxuZ3JlZW5cbmdyaWRcbmdyaWVmXG5ncml0XG5ncm9jZXJ5XG5ncm91cFxuZ3Jvd1xuZ3J1bnRcbmd1YXJkXG5ndWVzc1xuZ3VpZGVcbmd1aWx0XG5ndWl0YXJcbmd1blxuZ3ltXG5oYWJpdFxuaGFpclxuaGFsZlxuaGFtbWVyXG5oYW1zdGVyXG5oYW5kXG5oYXBweVxuaGFyYm9yXG5oYXJkXG5oYXJzaFxuaGFydmVzdFxuaGF0XG5oYXZlXG5oYXdrXG5oYXphcmRcbmhlYWRcbmhlYWx0aFxuaGVhcnRcbmhlYXZ5XG5oZWRnZWhvZ1xuaGVpZ2h0XG5oZWxsb1xuaGVsbWV0XG5oZWxwXG5oZW5cbmhlcm9cbmhpZGRlblxuaGlnaFxuaGlsbFxuaGludFxuaGlwXG5oaXJlXG5oaXN0b3J5XG5ob2JieVxuaG9ja2V5XG5ob2xkXG5ob2xlXG5ob2xpZGF5XG5ob2xsb3dcbmhvbWVcbmhvbmV5XG5ob29kXG5ob3BlXG5ob3JuXG5ob3Jyb3JcbmhvcnNlXG5ob3NwaXRhbFxuaG9zdFxuaG90ZWxcbmhvdXJcbmhvdmVyXG5odWJcbmh1Z2Vcbmh1bWFuXG5odW1ibGVcbmh1bW9yXG5odW5kcmVkXG5odW5ncnlcbmh1bnRcbmh1cmRsZVxuaHVycnlcbmh1cnRcbmh1c2JhbmRcbmh5YnJpZFxuaWNlXG5pY29uXG5pZGVhXG5pZGVudGlmeVxuaWRsZVxuaWdub3JlXG5pbGxcbmlsbGVnYWxcbmlsbG5lc3NcbmltYWdlXG5pbWl0YXRlXG5pbW1lbnNlXG5pbW11bmVcbmltcGFjdFxuaW1wb3NlXG5pbXByb3ZlXG5pbXB1bHNlXG5pbmNoXG5pbmNsdWRlXG5pbmNvbWVcbmluY3JlYXNlXG5pbmRleFxuaW5kaWNhdGVcbmluZG9vclxuaW5kdXN0cnlcbmluZmFudFxuaW5mbGljdFxuaW5mb3JtXG5pbmhhbGVcbmluaGVyaXRcbmluaXRpYWxcbmluamVjdFxuaW5qdXJ5XG5pbm1hdGVcbmlubmVyXG5pbm5vY2VudFxuaW5wdXRcbmlucXVpcnlcbmluc2FuZVxuaW5zZWN0XG5pbnNpZGVcbmluc3BpcmVcbmluc3RhbGxcbmludGFjdFxuaW50ZXJlc3RcbmludG9cbmludmVzdFxuaW52aXRlXG5pbnZvbHZlXG5pcm9uXG5pc2xhbmRcbmlzb2xhdGVcbmlzc3VlXG5pdGVtXG5pdm9yeVxuamFja2V0XG5qYWd1YXJcbmphclxuamF6elxuamVhbG91c1xuamVhbnNcbmplbGx5XG5qZXdlbFxuam9iXG5qb2luXG5qb2tlXG5qb3VybmV5XG5qb3lcbmp1ZGdlXG5qdWljZVxuanVtcFxuanVuZ2xlXG5qdW5pb3Jcbmp1bmtcbmp1c3Rcbmthbmdhcm9vXG5rZWVuXG5rZWVwXG5rZXRjaHVwXG5rZXlcbmtpY2tcbmtpZFxua2lkbmV5XG5raW5kXG5raW5nZG9tXG5raXNzXG5raXRcbmtpdGNoZW5cbmtpdGVcbmtpdHRlblxua2l3aVxua25lZVxua25pZmVcbmtub2NrXG5rbm93XG5sYWJcbmxhYmVsXG5sYWJvclxubGFkZGVyXG5sYWR5XG5sYWtlXG5sYW1wXG5sYW5ndWFnZVxubGFwdG9wXG5sYXJnZVxubGF0ZXJcbmxhdGluXG5sYXVnaFxubGF1bmRyeVxubGF2YVxubGF3XG5sYXduXG5sYXdzdWl0XG5sYXllclxubGF6eVxubGVhZGVyXG5sZWFmXG5sZWFyblxubGVhdmVcbmxlY3R1cmVcbmxlZnRcbmxlZ1xubGVnYWxcbmxlZ2VuZFxubGVpc3VyZVxubGVtb25cbmxlbmRcbmxlbmd0aFxubGVuc1xubGVvcGFyZFxubGVzc29uXG5sZXR0ZXJcbmxldmVsXG5saWFyXG5saWJlcnR5XG5saWJyYXJ5XG5saWNlbnNlXG5saWZlXG5saWZ0XG5saWdodFxubGlrZVxubGltYlxubGltaXRcbmxpbmtcbmxpb25cbmxpcXVpZFxubGlzdFxubGl0dGxlXG5saXZlXG5saXphcmRcbmxvYWRcbmxvYW5cbmxvYnN0ZXJcbmxvY2FsXG5sb2NrXG5sb2dpY1xubG9uZWx5XG5sb25nXG5sb29wXG5sb3R0ZXJ5XG5sb3VkXG5sb3VuZ2VcbmxvdmVcbmxveWFsXG5sdWNreVxubHVnZ2FnZVxubHVtYmVyXG5sdW5hclxubHVuY2hcbmx1eHVyeVxubHlyaWNzXG5tYWNoaW5lXG5tYWRcbm1hZ2ljXG5tYWduZXRcbm1haWRcbm1haWxcbm1haW5cbm1ham9yXG5tYWtlXG5tYW1tYWxcbm1hblxubWFuYWdlXG5tYW5kYXRlXG5tYW5nb1xubWFuc2lvblxubWFudWFsXG5tYXBsZVxubWFyYmxlXG5tYXJjaFxubWFyZ2luXG5tYXJpbmVcbm1hcmtldFxubWFycmlhZ2Vcbm1hc2tcbm1hc3Ncbm1hc3RlclxubWF0Y2hcbm1hdGVyaWFsXG5tYXRoXG5tYXRyaXhcbm1hdHRlclxubWF4aW11bVxubWF6ZVxubWVhZG93XG5tZWFuXG5tZWFzdXJlXG5tZWF0XG5tZWNoYW5pY1xubWVkYWxcbm1lZGlhXG5tZWxvZHlcbm1lbHRcbm1lbWJlclxubWVtb3J5XG5tZW50aW9uXG5tZW51XG5tZXJjeVxubWVyZ2Vcbm1lcml0XG5tZXJyeVxubWVzaFxubWVzc2FnZVxubWV0YWxcbm1ldGhvZFxubWlkZGxlXG5taWRuaWdodFxubWlsa1xubWlsbGlvblxubWltaWNcbm1pbmRcbm1pbmltdW1cbm1pbm9yXG5taW51dGVcbm1pcmFjbGVcbm1pcnJvclxubWlzZXJ5XG5taXNzXG5taXN0YWtlXG5taXhcbm1peGVkXG5taXh0dXJlXG5tb2JpbGVcbm1vZGVsXG5tb2RpZnlcbm1vbVxubW9tZW50XG5tb25pdG9yXG5tb25rZXlcbm1vbnN0ZXJcbm1vbnRoXG5tb29uXG5tb3JhbFxubW9yZVxubW9ybmluZ1xubW9zcXVpdG9cbm1vdGhlclxubW90aW9uXG5tb3RvclxubW91bnRhaW5cbm1vdXNlXG5tb3ZlXG5tb3ZpZVxubXVjaFxubXVmZmluXG5tdWxlXG5tdWx0aXBseVxubXVzY2xlXG5tdXNldW1cbm11c2hyb29tXG5tdXNpY1xubXVzdFxubXV0dWFsXG5teXNlbGZcbm15c3Rlcnlcbm15dGhcbm5haXZlXG5uYW1lXG5uYXBraW5cbm5hcnJvd1xubmFzdHlcbm5hdGlvblxubmF0dXJlXG5uZWFyXG5uZWNrXG5uZWVkXG5uZWdhdGl2ZVxubmVnbGVjdFxubmVpdGhlclxubmVwaGV3XG5uZXJ2ZVxubmVzdFxubmV0XG5uZXR3b3JrXG5uZXV0cmFsXG5uZXZlclxubmV3c1xubmV4dFxubmljZVxubmlnaHRcbm5vYmxlXG5ub2lzZVxubm9taW5lZVxubm9vZGxlXG5ub3JtYWxcbm5vcnRoXG5ub3NlXG5ub3RhYmxlXG5ub3RlXG5ub3RoaW5nXG5ub3RpY2Vcbm5vdmVsXG5ub3dcbm51Y2xlYXJcbm51bWJlclxubnVyc2Vcbm51dFxub2FrXG5vYmV5XG5vYmplY3Rcbm9ibGlnZVxub2JzY3VyZVxub2JzZXJ2ZVxub2J0YWluXG5vYnZpb3VzXG5vY2N1clxub2NlYW5cbm9jdG9iZXJcbm9kb3Jcbm9mZlxub2ZmZXJcbm9mZmljZVxub2Z0ZW5cbm9pbFxub2theVxub2xkXG5vbGl2ZVxub2x5bXBpY1xub21pdFxub25jZVxub25lXG5vbmlvblxub25saW5lXG5vbmx5XG5vcGVuXG5vcGVyYVxub3Bpbmlvblxub3Bwb3NlXG5vcHRpb25cbm9yYW5nZVxub3JiaXRcbm9yY2hhcmRcbm9yZGVyXG5vcmRpbmFyeVxub3JnYW5cbm9yaWVudFxub3JpZ2luYWxcbm9ycGhhblxub3N0cmljaFxub3RoZXJcbm91dGRvb3Jcbm91dGVyXG5vdXRwdXRcbm91dHNpZGVcbm92YWxcbm92ZW5cbm92ZXJcbm93blxub3duZXJcbm94eWdlblxub3lzdGVyXG5vem9uZVxucGFjdFxucGFkZGxlXG5wYWdlXG5wYWlyXG5wYWxhY2VcbnBhbG1cbnBhbmRhXG5wYW5lbFxucGFuaWNcbnBhbnRoZXJcbnBhcGVyXG5wYXJhZGVcbnBhcmVudFxucGFya1xucGFycm90XG5wYXJ0eVxucGFzc1xucGF0Y2hcbnBhdGhcbnBhdGllbnRcbnBhdHJvbFxucGF0dGVyblxucGF1c2VcbnBhdmVcbnBheW1lbnRcbnBlYWNlXG5wZWFudXRcbnBlYXJcbnBlYXNhbnRcbnBlbGljYW5cbnBlblxucGVuYWx0eVxucGVuY2lsXG5wZW9wbGVcbnBlcHBlclxucGVyZmVjdFxucGVybWl0XG5wZXJzb25cbnBldFxucGhvbmVcbnBob3RvXG5waHJhc2VcbnBoeXNpY2FsXG5waWFub1xucGljbmljXG5waWN0dXJlXG5waWVjZVxucGlnXG5waWdlb25cbnBpbGxcbnBpbG90XG5waW5rXG5waW9uZWVyXG5waXBlXG5waXN0b2xcbnBpdGNoXG5waXp6YVxucGxhY2VcbnBsYW5ldFxucGxhc3RpY1xucGxhdGVcbnBsYXlcbnBsZWFzZVxucGxlZGdlXG5wbHVja1xucGx1Z1xucGx1bmdlXG5wb2VtXG5wb2V0XG5wb2ludFxucG9sYXJcbnBvbGVcbnBvbGljZVxucG9uZFxucG9ueVxucG9vbFxucG9wdWxhclxucG9ydGlvblxucG9zaXRpb25cbnBvc3NpYmxlXG5wb3N0XG5wb3RhdG9cbnBvdHRlcnlcbnBvdmVydHlcbnBvd2RlclxucG93ZXJcbnByYWN0aWNlXG5wcmFpc2VcbnByZWRpY3RcbnByZWZlclxucHJlcGFyZVxucHJlc2VudFxucHJldHR5XG5wcmV2ZW50XG5wcmljZVxucHJpZGVcbnByaW1hcnlcbnByaW50XG5wcmlvcml0eVxucHJpc29uXG5wcml2YXRlXG5wcml6ZVxucHJvYmxlbVxucHJvY2Vzc1xucHJvZHVjZVxucHJvZml0XG5wcm9ncmFtXG5wcm9qZWN0XG5wcm9tb3RlXG5wcm9vZlxucHJvcGVydHlcbnByb3NwZXJcbnByb3RlY3RcbnByb3VkXG5wcm92aWRlXG5wdWJsaWNcbnB1ZGRpbmdcbnB1bGxcbnB1bHBcbnB1bHNlXG5wdW1wa2luXG5wdW5jaFxucHVwaWxcbnB1cHB5XG5wdXJjaGFzZVxucHVyaXR5XG5wdXJwb3NlXG5wdXJzZVxucHVzaFxucHV0XG5wdXp6bGVcbnB5cmFtaWRcbnF1YWxpdHlcbnF1YW50dW1cbnF1YXJ0ZXJcbnF1ZXN0aW9uXG5xdWlja1xucXVpdFxucXVpelxucXVvdGVcbnJhYmJpdFxucmFjY29vblxucmFjZVxucmFja1xucmFkYXJcbnJhZGlvXG5yYWlsXG5yYWluXG5yYWlzZVxucmFsbHlcbnJhbXBcbnJhbmNoXG5yYW5kb21cbnJhbmdlXG5yYXBpZFxucmFyZVxucmF0ZVxucmF0aGVyXG5yYXZlblxucmF3XG5yYXpvclxucmVhZHlcbnJlYWxcbnJlYXNvblxucmViZWxcbnJlYnVpbGRcbnJlY2FsbFxucmVjZWl2ZVxucmVjaXBlXG5yZWNvcmRcbnJlY3ljbGVcbnJlZHVjZVxucmVmbGVjdFxucmVmb3JtXG5yZWZ1c2VcbnJlZ2lvblxucmVncmV0XG5yZWd1bGFyXG5yZWplY3RcbnJlbGF4XG5yZWxlYXNlXG5yZWxpZWZcbnJlbHlcbnJlbWFpblxucmVtZW1iZXJcbnJlbWluZFxucmVtb3ZlXG5yZW5kZXJcbnJlbmV3XG5yZW50XG5yZW9wZW5cbnJlcGFpclxucmVwZWF0XG5yZXBsYWNlXG5yZXBvcnRcbnJlcXVpcmVcbnJlc2N1ZVxucmVzZW1ibGVcbnJlc2lzdFxucmVzb3VyY2VcbnJlc3BvbnNlXG5yZXN1bHRcbnJldGlyZVxucmV0cmVhdFxucmV0dXJuXG5yZXVuaW9uXG5yZXZlYWxcbnJldmlld1xucmV3YXJkXG5yaHl0aG1cbnJpYlxucmliYm9uXG5yaWNlXG5yaWNoXG5yaWRlXG5yaWRnZVxucmlmbGVcbnJpZ2h0XG5yaWdpZFxucmluZ1xucmlvdFxucmlwcGxlXG5yaXNrXG5yaXR1YWxcbnJpdmFsXG5yaXZlclxucm9hZFxucm9hc3RcbnJvYm90XG5yb2J1c3RcbnJvY2tldFxucm9tYW5jZVxucm9vZlxucm9va2llXG5yb29tXG5yb3NlXG5yb3RhdGVcbnJvdWdoXG5yb3VuZFxucm91dGVcbnJveWFsXG5ydWJiZXJcbnJ1ZGVcbnJ1Z1xucnVsZVxucnVuXG5ydW53YXlcbnJ1cmFsXG5zYWRcbnNhZGRsZVxuc2FkbmVzc1xuc2FmZVxuc2FpbFxuc2FsYWRcbnNhbG1vblxuc2Fsb25cbnNhbHRcbnNhbHV0ZVxuc2FtZVxuc2FtcGxlXG5zYW5kXG5zYXRpc2Z5XG5zYXRvc2hpXG5zYXVjZVxuc2F1c2FnZVxuc2F2ZVxuc2F5XG5zY2FsZVxuc2Nhblxuc2NhcmVcbnNjYXR0ZXJcbnNjZW5lXG5zY2hlbWVcbnNjaG9vbFxuc2NpZW5jZVxuc2Npc3NvcnNcbnNjb3JwaW9uXG5zY291dFxuc2NyYXBcbnNjcmVlblxuc2NyaXB0XG5zY3J1Ylxuc2VhXG5zZWFyY2hcbnNlYXNvblxuc2VhdFxuc2Vjb25kXG5zZWNyZXRcbnNlY3Rpb25cbnNlY3VyaXR5XG5zZWVkXG5zZWVrXG5zZWdtZW50XG5zZWxlY3RcbnNlbGxcbnNlbWluYXJcbnNlbmlvclxuc2Vuc2VcbnNlbnRlbmNlXG5zZXJpZXNcbnNlcnZpY2VcbnNlc3Npb25cbnNldHRsZVxuc2V0dXBcbnNldmVuXG5zaGFkb3dcbnNoYWZ0XG5zaGFsbG93XG5zaGFyZVxuc2hlZFxuc2hlbGxcbnNoZXJpZmZcbnNoaWVsZFxuc2hpZnRcbnNoaW5lXG5zaGlwXG5zaGl2ZXJcbnNob2NrXG5zaG9lXG5zaG9vdFxuc2hvcFxuc2hvcnRcbnNob3VsZGVyXG5zaG92ZVxuc2hyaW1wXG5zaHJ1Z1xuc2h1ZmZsZVxuc2h5XG5zaWJsaW5nXG5zaWNrXG5zaWRlXG5zaWVnZVxuc2lnaHRcbnNpZ25cbnNpbGVudFxuc2lsa1xuc2lsbHlcbnNpbHZlclxuc2ltaWxhclxuc2ltcGxlXG5zaW5jZVxuc2luZ1xuc2lyZW5cbnNpc3Rlclxuc2l0dWF0ZVxuc2l4XG5zaXplXG5za2F0ZVxuc2tldGNoXG5za2lcbnNraWxsXG5za2luXG5za2lydFxuc2t1bGxcbnNsYWJcbnNsYW1cbnNsZWVwXG5zbGVuZGVyXG5zbGljZVxuc2xpZGVcbnNsaWdodFxuc2xpbVxuc2xvZ2FuXG5zbG90XG5zbG93XG5zbHVzaFxuc21hbGxcbnNtYXJ0XG5zbWlsZVxuc21va2VcbnNtb290aFxuc25hY2tcbnNuYWtlXG5zbmFwXG5zbmlmZlxuc25vd1xuc29hcFxuc29jY2VyXG5zb2NpYWxcbnNvY2tcbnNvZGFcbnNvZnRcbnNvbGFyXG5zb2xkaWVyXG5zb2xpZFxuc29sdXRpb25cbnNvbHZlXG5zb21lb25lXG5zb25nXG5zb29uXG5zb3JyeVxuc29ydFxuc291bFxuc291bmRcbnNvdXBcbnNvdXJjZVxuc291dGhcbnNwYWNlXG5zcGFyZVxuc3BhdGlhbFxuc3Bhd25cbnNwZWFrXG5zcGVjaWFsXG5zcGVlZFxuc3BlbGxcbnNwZW5kXG5zcGhlcmVcbnNwaWNlXG5zcGlkZXJcbnNwaWtlXG5zcGluXG5zcGlyaXRcbnNwbGl0XG5zcG9pbFxuc3BvbnNvclxuc3Bvb25cbnNwb3J0XG5zcG90XG5zcHJheVxuc3ByZWFkXG5zcHJpbmdcbnNweVxuc3F1YXJlXG5zcXVlZXplXG5zcXVpcnJlbFxuc3RhYmxlXG5zdGFkaXVtXG5zdGFmZlxuc3RhZ2VcbnN0YWlyc1xuc3RhbXBcbnN0YW5kXG5zdGFydFxuc3RhdGVcbnN0YXlcbnN0ZWFrXG5zdGVlbFxuc3RlbVxuc3RlcFxuc3RlcmVvXG5zdGlja1xuc3RpbGxcbnN0aW5nXG5zdG9ja1xuc3RvbWFjaFxuc3RvbmVcbnN0b29sXG5zdG9yeVxuc3RvdmVcbnN0cmF0ZWd5XG5zdHJlZXRcbnN0cmlrZVxuc3Ryb25nXG5zdHJ1Z2dsZVxuc3R1ZGVudFxuc3R1ZmZcbnN0dW1ibGVcbnN0eWxlXG5zdWJqZWN0XG5zdWJtaXRcbnN1YndheVxuc3VjY2Vzc1xuc3VjaFxuc3VkZGVuXG5zdWZmZXJcbnN1Z2FyXG5zdWdnZXN0XG5zdWl0XG5zdW1tZXJcbnN1blxuc3VubnlcbnN1bnNldFxuc3VwZXJcbnN1cHBseVxuc3VwcmVtZVxuc3VyZVxuc3VyZmFjZVxuc3VyZ2VcbnN1cnByaXNlXG5zdXJyb3VuZFxuc3VydmV5XG5zdXNwZWN0XG5zdXN0YWluXG5zd2FsbG93XG5zd2FtcFxuc3dhcFxuc3dhcm1cbnN3ZWFyXG5zd2VldFxuc3dpZnRcbnN3aW1cbnN3aW5nXG5zd2l0Y2hcbnN3b3JkXG5zeW1ib2xcbnN5bXB0b21cbnN5cnVwXG5zeXN0ZW1cbnRhYmxlXG50YWNrbGVcbnRhZ1xudGFpbFxudGFsZW50XG50YWxrXG50YW5rXG50YXBlXG50YXJnZXRcbnRhc2tcbnRhc3RlXG50YXR0b29cbnRheGlcbnRlYWNoXG50ZWFtXG50ZWxsXG50ZW5cbnRlbmFudFxudGVubmlzXG50ZW50XG50ZXJtXG50ZXN0XG50ZXh0XG50aGFua1xudGhhdFxudGhlbWVcbnRoZW5cbnRoZW9yeVxudGhlcmVcbnRoZXlcbnRoaW5nXG50aGlzXG50aG91Z2h0XG50aHJlZVxudGhyaXZlXG50aHJvd1xudGh1bWJcbnRodW5kZXJcbnRpY2tldFxudGlkZVxudGlnZXJcbnRpbHRcbnRpbWJlclxudGltZVxudGlueVxudGlwXG50aXJlZFxudGlzc3VlXG50aXRsZVxudG9hc3RcbnRvYmFjY29cbnRvZGF5XG50b2RkbGVyXG50b2VcbnRvZ2V0aGVyXG50b2lsZXRcbnRva2VuXG50b21hdG9cbnRvbW9ycm93XG50b25lXG50b25ndWVcbnRvbmlnaHRcbnRvb2xcbnRvb3RoXG50b3BcbnRvcGljXG50b3BwbGVcbnRvcmNoXG50b3JuYWRvXG50b3J0b2lzZVxudG9zc1xudG90YWxcbnRvdXJpc3RcbnRvd2FyZFxudG93ZXJcbnRvd25cbnRveVxudHJhY2tcbnRyYWRlXG50cmFmZmljXG50cmFnaWNcbnRyYWluXG50cmFuc2ZlclxudHJhcFxudHJhc2hcbnRyYXZlbFxudHJheVxudHJlYXRcbnRyZWVcbnRyZW5kXG50cmlhbFxudHJpYmVcbnRyaWNrXG50cmlnZ2VyXG50cmltXG50cmlwXG50cm9waHlcbnRyb3VibGVcbnRydWNrXG50cnVlXG50cnVseVxudHJ1bXBldFxudHJ1c3RcbnRydXRoXG50cnlcbnR1YmVcbnR1aXRpb25cbnR1bWJsZVxudHVuYVxudHVubmVsXG50dXJrZXlcbnR1cm5cbnR1cnRsZVxudHdlbHZlXG50d2VudHlcbnR3aWNlXG50d2luXG50d2lzdFxudHdvXG50eXBlXG50eXBpY2FsXG51Z2x5XG51bWJyZWxsYVxudW5hYmxlXG51bmF3YXJlXG51bmNsZVxudW5jb3ZlclxudW5kZXJcbnVuZG9cbnVuZmFpclxudW5mb2xkXG51bmhhcHB5XG51bmlmb3JtXG51bmlxdWVcbnVuaXRcbnVuaXZlcnNlXG51bmtub3duXG51bmxvY2tcbnVudGlsXG51bnVzdWFsXG51bnZlaWxcbnVwZGF0ZVxudXBncmFkZVxudXBob2xkXG51cG9uXG51cHBlclxudXBzZXRcbnVyYmFuXG51cmdlXG51c2FnZVxudXNlXG51c2VkXG51c2VmdWxcbnVzZWxlc3NcbnVzdWFsXG51dGlsaXR5XG52YWNhbnRcbnZhY3V1bVxudmFndWVcbnZhbGlkXG52YWxsZXlcbnZhbHZlXG52YW5cbnZhbmlzaFxudmFwb3JcbnZhcmlvdXNcbnZhc3RcbnZhdWx0XG52ZWhpY2xlXG52ZWx2ZXRcbnZlbmRvclxudmVudHVyZVxudmVudWVcbnZlcmJcbnZlcmlmeVxudmVyc2lvblxudmVyeVxudmVzc2VsXG52ZXRlcmFuXG52aWFibGVcbnZpYnJhbnRcbnZpY2lvdXNcbnZpY3RvcnlcbnZpZGVvXG52aWV3XG52aWxsYWdlXG52aW50YWdlXG52aW9saW5cbnZpcnR1YWxcbnZpcnVzXG52aXNhXG52aXNpdFxudmlzdWFsXG52aXRhbFxudml2aWRcbnZvY2FsXG52b2ljZVxudm9pZFxudm9sY2Fub1xudm9sdW1lXG52b3RlXG52b3lhZ2VcbndhZ2VcbndhZ29uXG53YWl0XG53YWxrXG53YWxsXG53YWxudXRcbndhbnRcbndhcmZhcmVcbndhcm1cbndhcnJpb3Jcbndhc2hcbndhc3Bcbndhc3RlXG53YXRlclxud2F2ZVxud2F5XG53ZWFsdGhcbndlYXBvblxud2Vhclxud2Vhc2VsXG53ZWF0aGVyXG53ZWJcbndlZGRpbmdcbndlZWtlbmRcbndlaXJkXG53ZWxjb21lXG53ZXN0XG53ZXRcbndoYWxlXG53aGF0XG53aGVhdFxud2hlZWxcbndoZW5cbndoZXJlXG53aGlwXG53aGlzcGVyXG53aWRlXG53aWR0aFxud2lmZVxud2lsZFxud2lsbFxud2luXG53aW5kb3dcbndpbmVcbndpbmdcbndpbmtcbndpbm5lclxud2ludGVyXG53aXJlXG53aXNkb21cbndpc2Vcbndpc2hcbndpdG5lc3NcbndvbGZcbndvbWFuXG53b25kZXJcbndvb2Rcbndvb2xcbndvcmRcbndvcmtcbndvcmxkXG53b3JyeVxud29ydGhcbndyYXBcbndyZWNrXG53cmVzdGxlXG53cmlzdFxud3JpdGVcbndyb25nXG55YXJkXG55ZWFyXG55ZWxsb3dcbnlvdVxueW91bmdcbnlvdXRoXG56ZWJyYVxuemVyb1xuem9uZVxuem9vYC5zcGxpdCgnXFxuJyk7XG4iLCAiLyoqXG4gKiBLZXkgZ2VuZXJhdGlvbiB1dGlsaXRpZXMgZm9yIE5vc3RyXG4gKlxuICogVXNlcyBub3N0ci1jcnlwdG8tdXRpbHMgZm9yIGFsbCBjcnlwdG9ncmFwaGljIG9wZXJhdGlvbnMuXG4gKiBSZXR1cm5zIHBsYWluIGhleCBzdHJpbmdzIGZvciBib3RoIHByaXZhdGUgYW5kIHB1YmxpYyBrZXlzLlxuICovXG5cbmltcG9ydCB7IGdlbmVyYXRlS2V5UGFpciBhcyBnZW5lcmF0ZUtleVBhaXJDcnlwdG8sIGdldFB1YmxpY0tleVN5bmMsIGJ5dGVzVG9IZXggfSBmcm9tICdub3N0ci1jcnlwdG8tdXRpbHMnO1xuXG4vKipcbiAqIEdlbmVyYXRlcyBhIG5ldyBOb3N0ciBrZXlwYWlyLlxuICogUmV0dXJucyB0aGUgcHJpdmF0ZSBrZXkgYW5kIHB1YmxpYyBrZXkgYXMgaGV4IHN0cmluZ3MuXG4gKi9cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBnZW5lcmF0ZUtleVBhaXIoKSB7XG4gICAgY29uc3Qga2V5UGFpciA9IGF3YWl0IGdlbmVyYXRlS2V5UGFpckNyeXB0bygpO1xuICAgIHJldHVybiB7XG4gICAgICAgIHByaXZhdGVLZXk6IGtleVBhaXIucHJpdmF0ZUtleSxcbiAgICAgICAgcHVibGljS2V5OiBrZXlQYWlyLnB1YmxpY0tleS5oZXgsXG4gICAgfTtcbn1cblxuLyoqXG4gKiBHZXRzIHRoZSBwdWJsaWMga2V5IGZyb20gYSBwcml2YXRlIGtleSAoaGV4IHN0cmluZykuXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBnZXRQdWJsaWNLZXlGcm9tUHJpdmF0ZShwcml2YXRlS2V5SGV4KSB7XG4gICAgcmV0dXJuIGdldFB1YmxpY0tleVN5bmMocHJpdmF0ZUtleUhleCk7XG59XG5cbmV4cG9ydCB7IGJ5dGVzVG9IZXggfTtcbiIsICJjb25zdCBFX1RJTUVPVVQgPSBuZXcgRXJyb3IoJ3RpbWVvdXQgd2hpbGUgd2FpdGluZyBmb3IgbXV0ZXggdG8gYmVjb21lIGF2YWlsYWJsZScpO1xuY29uc3QgRV9BTFJFQURZX0xPQ0tFRCA9IG5ldyBFcnJvcignbXV0ZXggYWxyZWFkeSBsb2NrZWQnKTtcbmNvbnN0IEVfQ0FOQ0VMRUQgPSBuZXcgRXJyb3IoJ3JlcXVlc3QgZm9yIGxvY2sgY2FuY2VsZWQnKTtcblxudmFyIF9fYXdhaXRlciQyID0gKHVuZGVmaW5lZCAmJiB1bmRlZmluZWQuX19hd2FpdGVyKSB8fCBmdW5jdGlvbiAodGhpc0FyZywgX2FyZ3VtZW50cywgUCwgZ2VuZXJhdG9yKSB7XG4gICAgZnVuY3Rpb24gYWRvcHQodmFsdWUpIHsgcmV0dXJuIHZhbHVlIGluc3RhbmNlb2YgUCA/IHZhbHVlIDogbmV3IFAoZnVuY3Rpb24gKHJlc29sdmUpIHsgcmVzb2x2ZSh2YWx1ZSk7IH0pOyB9XG4gICAgcmV0dXJuIG5ldyAoUCB8fCAoUCA9IFByb21pc2UpKShmdW5jdGlvbiAocmVzb2x2ZSwgcmVqZWN0KSB7XG4gICAgICAgIGZ1bmN0aW9uIGZ1bGZpbGxlZCh2YWx1ZSkgeyB0cnkgeyBzdGVwKGdlbmVyYXRvci5uZXh0KHZhbHVlKSk7IH0gY2F0Y2ggKGUpIHsgcmVqZWN0KGUpOyB9IH1cbiAgICAgICAgZnVuY3Rpb24gcmVqZWN0ZWQodmFsdWUpIHsgdHJ5IHsgc3RlcChnZW5lcmF0b3JbXCJ0aHJvd1wiXSh2YWx1ZSkpOyB9IGNhdGNoIChlKSB7IHJlamVjdChlKTsgfSB9XG4gICAgICAgIGZ1bmN0aW9uIHN0ZXAocmVzdWx0KSB7IHJlc3VsdC5kb25lID8gcmVzb2x2ZShyZXN1bHQudmFsdWUpIDogYWRvcHQocmVzdWx0LnZhbHVlKS50aGVuKGZ1bGZpbGxlZCwgcmVqZWN0ZWQpOyB9XG4gICAgICAgIHN0ZXAoKGdlbmVyYXRvciA9IGdlbmVyYXRvci5hcHBseSh0aGlzQXJnLCBfYXJndW1lbnRzIHx8IFtdKSkubmV4dCgpKTtcbiAgICB9KTtcbn07XG5jbGFzcyBTZW1hcGhvcmUge1xuICAgIGNvbnN0cnVjdG9yKF92YWx1ZSwgX2NhbmNlbEVycm9yID0gRV9DQU5DRUxFRCkge1xuICAgICAgICB0aGlzLl92YWx1ZSA9IF92YWx1ZTtcbiAgICAgICAgdGhpcy5fY2FuY2VsRXJyb3IgPSBfY2FuY2VsRXJyb3I7XG4gICAgICAgIHRoaXMuX3F1ZXVlID0gW107XG4gICAgICAgIHRoaXMuX3dlaWdodGVkV2FpdGVycyA9IFtdO1xuICAgIH1cbiAgICBhY3F1aXJlKHdlaWdodCA9IDEsIHByaW9yaXR5ID0gMCkge1xuICAgICAgICBpZiAod2VpZ2h0IDw9IDApXG4gICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoYGludmFsaWQgd2VpZ2h0ICR7d2VpZ2h0fTogbXVzdCBiZSBwb3NpdGl2ZWApO1xuICAgICAgICByZXR1cm4gbmV3IFByb21pc2UoKHJlc29sdmUsIHJlamVjdCkgPT4ge1xuICAgICAgICAgICAgY29uc3QgdGFzayA9IHsgcmVzb2x2ZSwgcmVqZWN0LCB3ZWlnaHQsIHByaW9yaXR5IH07XG4gICAgICAgICAgICBjb25zdCBpID0gZmluZEluZGV4RnJvbUVuZCh0aGlzLl9xdWV1ZSwgKG90aGVyKSA9PiBwcmlvcml0eSA8PSBvdGhlci5wcmlvcml0eSk7XG4gICAgICAgICAgICBpZiAoaSA9PT0gLTEgJiYgd2VpZ2h0IDw9IHRoaXMuX3ZhbHVlKSB7XG4gICAgICAgICAgICAgICAgLy8gTmVlZHMgaW1tZWRpYXRlIGRpc3BhdGNoLCBza2lwIHRoZSBxdWV1ZVxuICAgICAgICAgICAgICAgIHRoaXMuX2Rpc3BhdGNoSXRlbSh0YXNrKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICAgIGVsc2Uge1xuICAgICAgICAgICAgICAgIHRoaXMuX3F1ZXVlLnNwbGljZShpICsgMSwgMCwgdGFzayk7XG4gICAgICAgICAgICB9XG4gICAgICAgIH0pO1xuICAgIH1cbiAgICBydW5FeGNsdXNpdmUoY2FsbGJhY2tfMSkge1xuICAgICAgICByZXR1cm4gX19hd2FpdGVyJDIodGhpcywgYXJndW1lbnRzLCB2b2lkIDAsIGZ1bmN0aW9uKiAoY2FsbGJhY2ssIHdlaWdodCA9IDEsIHByaW9yaXR5ID0gMCkge1xuICAgICAgICAgICAgY29uc3QgW3ZhbHVlLCByZWxlYXNlXSA9IHlpZWxkIHRoaXMuYWNxdWlyZSh3ZWlnaHQsIHByaW9yaXR5KTtcbiAgICAgICAgICAgIHRyeSB7XG4gICAgICAgICAgICAgICAgcmV0dXJuIHlpZWxkIGNhbGxiYWNrKHZhbHVlKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICAgIGZpbmFsbHkge1xuICAgICAgICAgICAgICAgIHJlbGVhc2UoKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgfSk7XG4gICAgfVxuICAgIHdhaXRGb3JVbmxvY2sod2VpZ2h0ID0gMSwgcHJpb3JpdHkgPSAwKSB7XG4gICAgICAgIGlmICh3ZWlnaHQgPD0gMClcbiAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcihgaW52YWxpZCB3ZWlnaHQgJHt3ZWlnaHR9OiBtdXN0IGJlIHBvc2l0aXZlYCk7XG4gICAgICAgIGlmICh0aGlzLl9jb3VsZExvY2tJbW1lZGlhdGVseSh3ZWlnaHQsIHByaW9yaXR5KSkge1xuICAgICAgICAgICAgcmV0dXJuIFByb21pc2UucmVzb2x2ZSgpO1xuICAgICAgICB9XG4gICAgICAgIGVsc2Uge1xuICAgICAgICAgICAgcmV0dXJuIG5ldyBQcm9taXNlKChyZXNvbHZlKSA9PiB7XG4gICAgICAgICAgICAgICAgaWYgKCF0aGlzLl93ZWlnaHRlZFdhaXRlcnNbd2VpZ2h0IC0gMV0pXG4gICAgICAgICAgICAgICAgICAgIHRoaXMuX3dlaWdodGVkV2FpdGVyc1t3ZWlnaHQgLSAxXSA9IFtdO1xuICAgICAgICAgICAgICAgIGluc2VydFNvcnRlZCh0aGlzLl93ZWlnaHRlZFdhaXRlcnNbd2VpZ2h0IC0gMV0sIHsgcmVzb2x2ZSwgcHJpb3JpdHkgfSk7XG4gICAgICAgICAgICB9KTtcbiAgICAgICAgfVxuICAgIH1cbiAgICBpc0xvY2tlZCgpIHtcbiAgICAgICAgcmV0dXJuIHRoaXMuX3ZhbHVlIDw9IDA7XG4gICAgfVxuICAgIGdldFZhbHVlKCkge1xuICAgICAgICByZXR1cm4gdGhpcy5fdmFsdWU7XG4gICAgfVxuICAgIHNldFZhbHVlKHZhbHVlKSB7XG4gICAgICAgIHRoaXMuX3ZhbHVlID0gdmFsdWU7XG4gICAgICAgIHRoaXMuX2Rpc3BhdGNoUXVldWUoKTtcbiAgICB9XG4gICAgcmVsZWFzZSh3ZWlnaHQgPSAxKSB7XG4gICAgICAgIGlmICh3ZWlnaHQgPD0gMClcbiAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcihgaW52YWxpZCB3ZWlnaHQgJHt3ZWlnaHR9OiBtdXN0IGJlIHBvc2l0aXZlYCk7XG4gICAgICAgIHRoaXMuX3ZhbHVlICs9IHdlaWdodDtcbiAgICAgICAgdGhpcy5fZGlzcGF0Y2hRdWV1ZSgpO1xuICAgIH1cbiAgICBjYW5jZWwoKSB7XG4gICAgICAgIHRoaXMuX3F1ZXVlLmZvckVhY2goKGVudHJ5KSA9PiBlbnRyeS5yZWplY3QodGhpcy5fY2FuY2VsRXJyb3IpKTtcbiAgICAgICAgdGhpcy5fcXVldWUgPSBbXTtcbiAgICB9XG4gICAgX2Rpc3BhdGNoUXVldWUoKSB7XG4gICAgICAgIHRoaXMuX2RyYWluVW5sb2NrV2FpdGVycygpO1xuICAgICAgICB3aGlsZSAodGhpcy5fcXVldWUubGVuZ3RoID4gMCAmJiB0aGlzLl9xdWV1ZVswXS53ZWlnaHQgPD0gdGhpcy5fdmFsdWUpIHtcbiAgICAgICAgICAgIHRoaXMuX2Rpc3BhdGNoSXRlbSh0aGlzLl9xdWV1ZS5zaGlmdCgpKTtcbiAgICAgICAgICAgIHRoaXMuX2RyYWluVW5sb2NrV2FpdGVycygpO1xuICAgICAgICB9XG4gICAgfVxuICAgIF9kaXNwYXRjaEl0ZW0oaXRlbSkge1xuICAgICAgICBjb25zdCBwcmV2aW91c1ZhbHVlID0gdGhpcy5fdmFsdWU7XG4gICAgICAgIHRoaXMuX3ZhbHVlIC09IGl0ZW0ud2VpZ2h0O1xuICAgICAgICBpdGVtLnJlc29sdmUoW3ByZXZpb3VzVmFsdWUsIHRoaXMuX25ld1JlbGVhc2VyKGl0ZW0ud2VpZ2h0KV0pO1xuICAgIH1cbiAgICBfbmV3UmVsZWFzZXIod2VpZ2h0KSB7XG4gICAgICAgIGxldCBjYWxsZWQgPSBmYWxzZTtcbiAgICAgICAgcmV0dXJuICgpID0+IHtcbiAgICAgICAgICAgIGlmIChjYWxsZWQpXG4gICAgICAgICAgICAgICAgcmV0dXJuO1xuICAgICAgICAgICAgY2FsbGVkID0gdHJ1ZTtcbiAgICAgICAgICAgIHRoaXMucmVsZWFzZSh3ZWlnaHQpO1xuICAgICAgICB9O1xuICAgIH1cbiAgICBfZHJhaW5VbmxvY2tXYWl0ZXJzKCkge1xuICAgICAgICBpZiAodGhpcy5fcXVldWUubGVuZ3RoID09PSAwKSB7XG4gICAgICAgICAgICBmb3IgKGxldCB3ZWlnaHQgPSB0aGlzLl92YWx1ZTsgd2VpZ2h0ID4gMDsgd2VpZ2h0LS0pIHtcbiAgICAgICAgICAgICAgICBjb25zdCB3YWl0ZXJzID0gdGhpcy5fd2VpZ2h0ZWRXYWl0ZXJzW3dlaWdodCAtIDFdO1xuICAgICAgICAgICAgICAgIGlmICghd2FpdGVycylcbiAgICAgICAgICAgICAgICAgICAgY29udGludWU7XG4gICAgICAgICAgICAgICAgd2FpdGVycy5mb3JFYWNoKCh3YWl0ZXIpID0+IHdhaXRlci5yZXNvbHZlKCkpO1xuICAgICAgICAgICAgICAgIHRoaXMuX3dlaWdodGVkV2FpdGVyc1t3ZWlnaHQgLSAxXSA9IFtdO1xuICAgICAgICAgICAgfVxuICAgICAgICB9XG4gICAgICAgIGVsc2Uge1xuICAgICAgICAgICAgY29uc3QgcXVldWVkUHJpb3JpdHkgPSB0aGlzLl9xdWV1ZVswXS5wcmlvcml0eTtcbiAgICAgICAgICAgIGZvciAobGV0IHdlaWdodCA9IHRoaXMuX3ZhbHVlOyB3ZWlnaHQgPiAwOyB3ZWlnaHQtLSkge1xuICAgICAgICAgICAgICAgIGNvbnN0IHdhaXRlcnMgPSB0aGlzLl93ZWlnaHRlZFdhaXRlcnNbd2VpZ2h0IC0gMV07XG4gICAgICAgICAgICAgICAgaWYgKCF3YWl0ZXJzKVxuICAgICAgICAgICAgICAgICAgICBjb250aW51ZTtcbiAgICAgICAgICAgICAgICBjb25zdCBpID0gd2FpdGVycy5maW5kSW5kZXgoKHdhaXRlcikgPT4gd2FpdGVyLnByaW9yaXR5IDw9IHF1ZXVlZFByaW9yaXR5KTtcbiAgICAgICAgICAgICAgICAoaSA9PT0gLTEgPyB3YWl0ZXJzIDogd2FpdGVycy5zcGxpY2UoMCwgaSkpXG4gICAgICAgICAgICAgICAgICAgIC5mb3JFYWNoKCh3YWl0ZXIgPT4gd2FpdGVyLnJlc29sdmUoKSkpO1xuICAgICAgICAgICAgfVxuICAgICAgICB9XG4gICAgfVxuICAgIF9jb3VsZExvY2tJbW1lZGlhdGVseSh3ZWlnaHQsIHByaW9yaXR5KSB7XG4gICAgICAgIHJldHVybiAodGhpcy5fcXVldWUubGVuZ3RoID09PSAwIHx8IHRoaXMuX3F1ZXVlWzBdLnByaW9yaXR5IDwgcHJpb3JpdHkpICYmXG4gICAgICAgICAgICB3ZWlnaHQgPD0gdGhpcy5fdmFsdWU7XG4gICAgfVxufVxuZnVuY3Rpb24gaW5zZXJ0U29ydGVkKGEsIHYpIHtcbiAgICBjb25zdCBpID0gZmluZEluZGV4RnJvbUVuZChhLCAob3RoZXIpID0+IHYucHJpb3JpdHkgPD0gb3RoZXIucHJpb3JpdHkpO1xuICAgIGEuc3BsaWNlKGkgKyAxLCAwLCB2KTtcbn1cbmZ1bmN0aW9uIGZpbmRJbmRleEZyb21FbmQoYSwgcHJlZGljYXRlKSB7XG4gICAgZm9yIChsZXQgaSA9IGEubGVuZ3RoIC0gMTsgaSA+PSAwOyBpLS0pIHtcbiAgICAgICAgaWYgKHByZWRpY2F0ZShhW2ldKSkge1xuICAgICAgICAgICAgcmV0dXJuIGk7XG4gICAgICAgIH1cbiAgICB9XG4gICAgcmV0dXJuIC0xO1xufVxuXG52YXIgX19hd2FpdGVyJDEgPSAodW5kZWZpbmVkICYmIHVuZGVmaW5lZC5fX2F3YWl0ZXIpIHx8IGZ1bmN0aW9uICh0aGlzQXJnLCBfYXJndW1lbnRzLCBQLCBnZW5lcmF0b3IpIHtcbiAgICBmdW5jdGlvbiBhZG9wdCh2YWx1ZSkgeyByZXR1cm4gdmFsdWUgaW5zdGFuY2VvZiBQID8gdmFsdWUgOiBuZXcgUChmdW5jdGlvbiAocmVzb2x2ZSkgeyByZXNvbHZlKHZhbHVlKTsgfSk7IH1cbiAgICByZXR1cm4gbmV3IChQIHx8IChQID0gUHJvbWlzZSkpKGZ1bmN0aW9uIChyZXNvbHZlLCByZWplY3QpIHtcbiAgICAgICAgZnVuY3Rpb24gZnVsZmlsbGVkKHZhbHVlKSB7IHRyeSB7IHN0ZXAoZ2VuZXJhdG9yLm5leHQodmFsdWUpKTsgfSBjYXRjaCAoZSkgeyByZWplY3QoZSk7IH0gfVxuICAgICAgICBmdW5jdGlvbiByZWplY3RlZCh2YWx1ZSkgeyB0cnkgeyBzdGVwKGdlbmVyYXRvcltcInRocm93XCJdKHZhbHVlKSk7IH0gY2F0Y2ggKGUpIHsgcmVqZWN0KGUpOyB9IH1cbiAgICAgICAgZnVuY3Rpb24gc3RlcChyZXN1bHQpIHsgcmVzdWx0LmRvbmUgPyByZXNvbHZlKHJlc3VsdC52YWx1ZSkgOiBhZG9wdChyZXN1bHQudmFsdWUpLnRoZW4oZnVsZmlsbGVkLCByZWplY3RlZCk7IH1cbiAgICAgICAgc3RlcCgoZ2VuZXJhdG9yID0gZ2VuZXJhdG9yLmFwcGx5KHRoaXNBcmcsIF9hcmd1bWVudHMgfHwgW10pKS5uZXh0KCkpO1xuICAgIH0pO1xufTtcbmNsYXNzIE11dGV4IHtcbiAgICBjb25zdHJ1Y3RvcihjYW5jZWxFcnJvcikge1xuICAgICAgICB0aGlzLl9zZW1hcGhvcmUgPSBuZXcgU2VtYXBob3JlKDEsIGNhbmNlbEVycm9yKTtcbiAgICB9XG4gICAgYWNxdWlyZSgpIHtcbiAgICAgICAgcmV0dXJuIF9fYXdhaXRlciQxKHRoaXMsIGFyZ3VtZW50cywgdm9pZCAwLCBmdW5jdGlvbiogKHByaW9yaXR5ID0gMCkge1xuICAgICAgICAgICAgY29uc3QgWywgcmVsZWFzZXJdID0geWllbGQgdGhpcy5fc2VtYXBob3JlLmFjcXVpcmUoMSwgcHJpb3JpdHkpO1xuICAgICAgICAgICAgcmV0dXJuIHJlbGVhc2VyO1xuICAgICAgICB9KTtcbiAgICB9XG4gICAgcnVuRXhjbHVzaXZlKGNhbGxiYWNrLCBwcmlvcml0eSA9IDApIHtcbiAgICAgICAgcmV0dXJuIHRoaXMuX3NlbWFwaG9yZS5ydW5FeGNsdXNpdmUoKCkgPT4gY2FsbGJhY2soKSwgMSwgcHJpb3JpdHkpO1xuICAgIH1cbiAgICBpc0xvY2tlZCgpIHtcbiAgICAgICAgcmV0dXJuIHRoaXMuX3NlbWFwaG9yZS5pc0xvY2tlZCgpO1xuICAgIH1cbiAgICB3YWl0Rm9yVW5sb2NrKHByaW9yaXR5ID0gMCkge1xuICAgICAgICByZXR1cm4gdGhpcy5fc2VtYXBob3JlLndhaXRGb3JVbmxvY2soMSwgcHJpb3JpdHkpO1xuICAgIH1cbiAgICByZWxlYXNlKCkge1xuICAgICAgICBpZiAodGhpcy5fc2VtYXBob3JlLmlzTG9ja2VkKCkpXG4gICAgICAgICAgICB0aGlzLl9zZW1hcGhvcmUucmVsZWFzZSgpO1xuICAgIH1cbiAgICBjYW5jZWwoKSB7XG4gICAgICAgIHJldHVybiB0aGlzLl9zZW1hcGhvcmUuY2FuY2VsKCk7XG4gICAgfVxufVxuXG52YXIgX19hd2FpdGVyID0gKHVuZGVmaW5lZCAmJiB1bmRlZmluZWQuX19hd2FpdGVyKSB8fCBmdW5jdGlvbiAodGhpc0FyZywgX2FyZ3VtZW50cywgUCwgZ2VuZXJhdG9yKSB7XG4gICAgZnVuY3Rpb24gYWRvcHQodmFsdWUpIHsgcmV0dXJuIHZhbHVlIGluc3RhbmNlb2YgUCA/IHZhbHVlIDogbmV3IFAoZnVuY3Rpb24gKHJlc29sdmUpIHsgcmVzb2x2ZSh2YWx1ZSk7IH0pOyB9XG4gICAgcmV0dXJuIG5ldyAoUCB8fCAoUCA9IFByb21pc2UpKShmdW5jdGlvbiAocmVzb2x2ZSwgcmVqZWN0KSB7XG4gICAgICAgIGZ1bmN0aW9uIGZ1bGZpbGxlZCh2YWx1ZSkgeyB0cnkgeyBzdGVwKGdlbmVyYXRvci5uZXh0KHZhbHVlKSk7IH0gY2F0Y2ggKGUpIHsgcmVqZWN0KGUpOyB9IH1cbiAgICAgICAgZnVuY3Rpb24gcmVqZWN0ZWQodmFsdWUpIHsgdHJ5IHsgc3RlcChnZW5lcmF0b3JbXCJ0aHJvd1wiXSh2YWx1ZSkpOyB9IGNhdGNoIChlKSB7IHJlamVjdChlKTsgfSB9XG4gICAgICAgIGZ1bmN0aW9uIHN0ZXAocmVzdWx0KSB7IHJlc3VsdC5kb25lID8gcmVzb2x2ZShyZXN1bHQudmFsdWUpIDogYWRvcHQocmVzdWx0LnZhbHVlKS50aGVuKGZ1bGZpbGxlZCwgcmVqZWN0ZWQpOyB9XG4gICAgICAgIHN0ZXAoKGdlbmVyYXRvciA9IGdlbmVyYXRvci5hcHBseSh0aGlzQXJnLCBfYXJndW1lbnRzIHx8IFtdKSkubmV4dCgpKTtcbiAgICB9KTtcbn07XG5mdW5jdGlvbiB3aXRoVGltZW91dChzeW5jLCB0aW1lb3V0LCB0aW1lb3V0RXJyb3IgPSBFX1RJTUVPVVQpIHtcbiAgICByZXR1cm4ge1xuICAgICAgICBhY3F1aXJlOiAod2VpZ2h0T3JQcmlvcml0eSwgcHJpb3JpdHkpID0+IHtcbiAgICAgICAgICAgIGxldCB3ZWlnaHQ7XG4gICAgICAgICAgICBpZiAoaXNTZW1hcGhvcmUoc3luYykpIHtcbiAgICAgICAgICAgICAgICB3ZWlnaHQgPSB3ZWlnaHRPclByaW9yaXR5O1xuICAgICAgICAgICAgfVxuICAgICAgICAgICAgZWxzZSB7XG4gICAgICAgICAgICAgICAgd2VpZ2h0ID0gdW5kZWZpbmVkO1xuICAgICAgICAgICAgICAgIHByaW9yaXR5ID0gd2VpZ2h0T3JQcmlvcml0eTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICAgIGlmICh3ZWlnaHQgIT09IHVuZGVmaW5lZCAmJiB3ZWlnaHQgPD0gMCkge1xuICAgICAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcihgaW52YWxpZCB3ZWlnaHQgJHt3ZWlnaHR9OiBtdXN0IGJlIHBvc2l0aXZlYCk7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgICByZXR1cm4gbmV3IFByb21pc2UoKHJlc29sdmUsIHJlamVjdCkgPT4gX19hd2FpdGVyKHRoaXMsIHZvaWQgMCwgdm9pZCAwLCBmdW5jdGlvbiogKCkge1xuICAgICAgICAgICAgICAgIGxldCBpc1RpbWVvdXQgPSBmYWxzZTtcbiAgICAgICAgICAgICAgICBjb25zdCBoYW5kbGUgPSBzZXRUaW1lb3V0KCgpID0+IHtcbiAgICAgICAgICAgICAgICAgICAgaXNUaW1lb3V0ID0gdHJ1ZTtcbiAgICAgICAgICAgICAgICAgICAgcmVqZWN0KHRpbWVvdXRFcnJvcik7XG4gICAgICAgICAgICAgICAgfSwgdGltZW91dCk7XG4gICAgICAgICAgICAgICAgdHJ5IHtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgdGlja2V0ID0geWllbGQgKGlzU2VtYXBob3JlKHN5bmMpXG4gICAgICAgICAgICAgICAgICAgICAgICA/IHN5bmMuYWNxdWlyZSh3ZWlnaHQsIHByaW9yaXR5KVxuICAgICAgICAgICAgICAgICAgICAgICAgOiBzeW5jLmFjcXVpcmUocHJpb3JpdHkpKTtcbiAgICAgICAgICAgICAgICAgICAgaWYgKGlzVGltZW91dCkge1xuICAgICAgICAgICAgICAgICAgICAgICAgY29uc3QgcmVsZWFzZSA9IEFycmF5LmlzQXJyYXkodGlja2V0KSA/IHRpY2tldFsxXSA6IHRpY2tldDtcbiAgICAgICAgICAgICAgICAgICAgICAgIHJlbGVhc2UoKTtcbiAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgICAgICBlbHNlIHtcbiAgICAgICAgICAgICAgICAgICAgICAgIGNsZWFyVGltZW91dChoYW5kbGUpO1xuICAgICAgICAgICAgICAgICAgICAgICAgcmVzb2x2ZSh0aWNrZXQpO1xuICAgICAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgIGNhdGNoIChlKSB7XG4gICAgICAgICAgICAgICAgICAgIGlmICghaXNUaW1lb3V0KSB7XG4gICAgICAgICAgICAgICAgICAgICAgICBjbGVhclRpbWVvdXQoaGFuZGxlKTtcbiAgICAgICAgICAgICAgICAgICAgICAgIHJlamVjdChlKTtcbiAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgIH0pKTtcbiAgICAgICAgfSxcbiAgICAgICAgcnVuRXhjbHVzaXZlKGNhbGxiYWNrLCB3ZWlnaHQsIHByaW9yaXR5KSB7XG4gICAgICAgICAgICByZXR1cm4gX19hd2FpdGVyKHRoaXMsIHZvaWQgMCwgdm9pZCAwLCBmdW5jdGlvbiogKCkge1xuICAgICAgICAgICAgICAgIGxldCByZWxlYXNlID0gKCkgPT4gdW5kZWZpbmVkO1xuICAgICAgICAgICAgICAgIHRyeSB7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHRpY2tldCA9IHlpZWxkIHRoaXMuYWNxdWlyZSh3ZWlnaHQsIHByaW9yaXR5KTtcbiAgICAgICAgICAgICAgICAgICAgaWYgKEFycmF5LmlzQXJyYXkodGlja2V0KSkge1xuICAgICAgICAgICAgICAgICAgICAgICAgcmVsZWFzZSA9IHRpY2tldFsxXTtcbiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiB5aWVsZCBjYWxsYmFjayh0aWNrZXRbMF0pO1xuICAgICAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgICAgIGVsc2Uge1xuICAgICAgICAgICAgICAgICAgICAgICAgcmVsZWFzZSA9IHRpY2tldDtcbiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiB5aWVsZCBjYWxsYmFjaygpO1xuICAgICAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgIGZpbmFsbHkge1xuICAgICAgICAgICAgICAgICAgICByZWxlYXNlKCk7XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfSk7XG4gICAgICAgIH0sXG4gICAgICAgIHJlbGVhc2Uod2VpZ2h0KSB7XG4gICAgICAgICAgICBzeW5jLnJlbGVhc2Uod2VpZ2h0KTtcbiAgICAgICAgfSxcbiAgICAgICAgY2FuY2VsKCkge1xuICAgICAgICAgICAgcmV0dXJuIHN5bmMuY2FuY2VsKCk7XG4gICAgICAgIH0sXG4gICAgICAgIHdhaXRGb3JVbmxvY2s6ICh3ZWlnaHRPclByaW9yaXR5LCBwcmlvcml0eSkgPT4ge1xuICAgICAgICAgICAgbGV0IHdlaWdodDtcbiAgICAgICAgICAgIGlmIChpc1NlbWFwaG9yZShzeW5jKSkge1xuICAgICAgICAgICAgICAgIHdlaWdodCA9IHdlaWdodE9yUHJpb3JpdHk7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgICBlbHNlIHtcbiAgICAgICAgICAgICAgICB3ZWlnaHQgPSB1bmRlZmluZWQ7XG4gICAgICAgICAgICAgICAgcHJpb3JpdHkgPSB3ZWlnaHRPclByaW9yaXR5O1xuICAgICAgICAgICAgfVxuICAgICAgICAgICAgaWYgKHdlaWdodCAhPT0gdW5kZWZpbmVkICYmIHdlaWdodCA8PSAwKSB7XG4gICAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKGBpbnZhbGlkIHdlaWdodCAke3dlaWdodH06IG11c3QgYmUgcG9zaXRpdmVgKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICAgIHJldHVybiBuZXcgUHJvbWlzZSgocmVzb2x2ZSwgcmVqZWN0KSA9PiB7XG4gICAgICAgICAgICAgICAgY29uc3QgaGFuZGxlID0gc2V0VGltZW91dCgoKSA9PiByZWplY3QodGltZW91dEVycm9yKSwgdGltZW91dCk7XG4gICAgICAgICAgICAgICAgKGlzU2VtYXBob3JlKHN5bmMpXG4gICAgICAgICAgICAgICAgICAgID8gc3luYy53YWl0Rm9yVW5sb2NrKHdlaWdodCwgcHJpb3JpdHkpXG4gICAgICAgICAgICAgICAgICAgIDogc3luYy53YWl0Rm9yVW5sb2NrKHByaW9yaXR5KSkudGhlbigoKSA9PiB7XG4gICAgICAgICAgICAgICAgICAgIGNsZWFyVGltZW91dChoYW5kbGUpO1xuICAgICAgICAgICAgICAgICAgICByZXNvbHZlKCk7XG4gICAgICAgICAgICAgICAgfSk7XG4gICAgICAgICAgICB9KTtcbiAgICAgICAgfSxcbiAgICAgICAgaXNMb2NrZWQ6ICgpID0+IHN5bmMuaXNMb2NrZWQoKSxcbiAgICAgICAgZ2V0VmFsdWU6ICgpID0+IHN5bmMuZ2V0VmFsdWUoKSxcbiAgICAgICAgc2V0VmFsdWU6ICh2YWx1ZSkgPT4gc3luYy5zZXRWYWx1ZSh2YWx1ZSksXG4gICAgfTtcbn1cbmZ1bmN0aW9uIGlzU2VtYXBob3JlKHN5bmMpIHtcbiAgICByZXR1cm4gc3luYy5nZXRWYWx1ZSAhPT0gdW5kZWZpbmVkO1xufVxuXG4vLyBlc2xpbnQtZGlzYWJsZS1uZXh0LWxpc25lIEB0eXBlc2NyaXB0LWVzbGludC9leHBsaWNpdC1tb2R1bGUtYm91bmRhcnktdHlwZXNcbmZ1bmN0aW9uIHRyeUFjcXVpcmUoc3luYywgYWxyZWFkeUFjcXVpcmVkRXJyb3IgPSBFX0FMUkVBRFlfTE9DS0VEKSB7XG4gICAgLy8gZXNsaW50LWRpc2FibGUtbmV4dC1saW5lIEB0eXBlc2NyaXB0LWVzbGludC9uby1leHBsaWNpdC1hbnlcbiAgICByZXR1cm4gd2l0aFRpbWVvdXQoc3luYywgMCwgYWxyZWFkeUFjcXVpcmVkRXJyb3IpO1xufVxuXG5leHBvcnQgeyBFX0FMUkVBRFlfTE9DS0VELCBFX0NBTkNFTEVELCBFX1RJTUVPVVQsIE11dGV4LCBTZW1hcGhvcmUsIHRyeUFjcXVpcmUsIHdpdGhUaW1lb3V0IH07XG4iLCAiaW1wb3J0IHsgYXBpIH0gZnJvbSAnLi9icm93c2VyLXBvbHlmaWxsJztcbmltcG9ydCB7IGVuY3J5cHQsIGRlY3J5cHQsIGhhc2hQYXNzd29yZCwgdmVyaWZ5UGFzc3dvcmQgfSBmcm9tICcuL2NyeXB0byc7XG5pbXBvcnQgeyBsb29rc0xpa2VTZWVkUGhyYXNlLCBpc1ZhbGlkU2VlZFBocmFzZSB9IGZyb20gJy4vc2VlZHBocmFzZSc7XG5cbmNvbnN0IERCX1ZFUlNJT04gPSA2O1xuY29uc3Qgc3RvcmFnZSA9IGFwaS5zdG9yYWdlLmxvY2FsO1xuZXhwb3J0IGNvbnN0IFJFQ09NTUVOREVEX1JFTEFZUyA9IFtcbiAgICBuZXcgVVJMKCd3c3M6Ly9yZWxheS5kYW11cy5pbycpLFxuICAgIG5ldyBVUkwoJ3dzczovL3JlbGF5LnByaW1hbC5uZXQnKSxcbiAgICBuZXcgVVJMKCd3c3M6Ly9yZWxheS5zbm9ydC5zb2NpYWwnKSxcbiAgICBuZXcgVVJMKCd3c3M6Ly9yZWxheS5nZXRhbGJ5LmNvbS92MScpLFxuICAgIG5ldyBVUkwoJ3dzczovL25vcy5sb2wnKSxcbl07XG4vLyBwcmV0dGllci1pZ25vcmVcbmV4cG9ydCBjb25zdCBLSU5EUyA9IFtcbiAgICBbMCwgJ01ldGFkYXRhJywgJ2h0dHBzOi8vZ2l0aHViLmNvbS9ub3N0ci1wcm90b2NvbC9uaXBzL2Jsb2IvbWFzdGVyLzAxLm1kJ10sXG4gICAgWzEsICdUZXh0JywgJ2h0dHBzOi8vZ2l0aHViLmNvbS9ub3N0ci1wcm90b2NvbC9uaXBzL2Jsb2IvbWFzdGVyLzAxLm1kJ10sXG4gICAgWzIsICdSZWNvbW1lbmQgUmVsYXknLCAnaHR0cHM6Ly9naXRodWIuY29tL25vc3RyLXByb3RvY29sL25pcHMvYmxvYi9tYXN0ZXIvMDEubWQnXSxcbiAgICBbMywgJ0NvbnRhY3RzJywgJ2h0dHBzOi8vZ2l0aHViLmNvbS9ub3N0ci1wcm90b2NvbC9uaXBzL2Jsb2IvbWFzdGVyLzAyLm1kJ10sXG4gICAgWzQsICdFbmNyeXB0ZWQgRGlyZWN0IE1lc3NhZ2VzJywgJ2h0dHBzOi8vZ2l0aHViLmNvbS9ub3N0ci1wcm90b2NvbC9uaXBzL2Jsb2IvbWFzdGVyLzA0Lm1kJ10sXG4gICAgWzUsICdFdmVudCBEZWxldGlvbicsICdodHRwczovL2dpdGh1Yi5jb20vbm9zdHItcHJvdG9jb2wvbmlwcy9ibG9iL21hc3Rlci8wOS5tZCddLFxuICAgIFs2LCAnUmVwb3N0JywgJ2h0dHBzOi8vZ2l0aHViLmNvbS9ub3N0ci1wcm90b2NvbC9uaXBzL2Jsb2IvbWFzdGVyLzE4Lm1kJ10sXG4gICAgWzcsICdSZWFjdGlvbicsICdodHRwczovL2dpdGh1Yi5jb20vbm9zdHItcHJvdG9jb2wvbmlwcy9ibG9iL21hc3Rlci8yNS5tZCddLFxuICAgIFs4LCAnQmFkZ2UgQXdhcmQnLCAnaHR0cHM6Ly9naXRodWIuY29tL25vc3RyLXByb3RvY29sL25pcHMvYmxvYi9tYXN0ZXIvNTgubWQnXSxcbiAgICBbMTYsICdHZW5lcmljIFJlcG9zdCcsICdodHRwczovL2dpdGh1Yi5jb20vbm9zdHItcHJvdG9jb2wvbmlwcy9ibG9iL21hc3Rlci8xOC5tZCddLFxuICAgIFs0MCwgJ0NoYW5uZWwgQ3JlYXRpb24nLCAnaHR0cHM6Ly9naXRodWIuY29tL25vc3RyLXByb3RvY29sL25pcHMvYmxvYi9tYXN0ZXIvMjgubWQnXSxcbiAgICBbNDEsICdDaGFubmVsIE1ldGFkYXRhJywgJ2h0dHBzOi8vZ2l0aHViLmNvbS9ub3N0ci1wcm90b2NvbC9uaXBzL2Jsb2IvbWFzdGVyLzI4Lm1kJ10sXG4gICAgWzQyLCAnQ2hhbm5lbCBNZXNzYWdlJywgJ2h0dHBzOi8vZ2l0aHViLmNvbS9ub3N0ci1wcm90b2NvbC9uaXBzL2Jsb2IvbWFzdGVyLzI4Lm1kJ10sXG4gICAgWzQzLCAnQ2hhbm5lbCBIaWRlIE1lc3NhZ2UnLCAnaHR0cHM6Ly9naXRodWIuY29tL25vc3RyLXByb3RvY29sL25pcHMvYmxvYi9tYXN0ZXIvMjgubWQnXSxcbiAgICBbNDQsICdDaGFubmVsIE11dGUgVXNlcicsICdodHRwczovL2dpdGh1Yi5jb20vbm9zdHItcHJvdG9jb2wvbmlwcy9ibG9iL21hc3Rlci8yOC5tZCddLFxuICAgIFsxMDYzLCAnRmlsZSBNZXRhZGF0YScsICdodHRwczovL2dpdGh1Yi5jb20vbm9zdHItcHJvdG9jb2wvbmlwcy9ibG9iL21hc3Rlci85NC5tZCddLFxuICAgIFsxMzExLCAnTGl2ZSBDaGF0IE1lc3NhZ2UnLCAnaHR0cHM6Ly9naXRodWIuY29tL25vc3RyLXByb3RvY29sL25pcHMvYmxvYi9tYXN0ZXIvNTMubWQnXSxcbiAgICBbMTk4NCwgJ1JlcG9ydGluZycsICdodHRwczovL2dpdGh1Yi5jb20vbm9zdHItcHJvdG9jb2wvbmlwcy9ibG9iL21hc3Rlci81Ni5tZCddLFxuICAgIFsxOTg1LCAnTGFiZWwnLCAnaHR0cHM6Ly9naXRodWIuY29tL25vc3RyLXByb3RvY29sL25pcHMvYmxvYi9tYXN0ZXIvMzIubWQnXSxcbiAgICBbNDU1MCwgJ0NvbW11bml0eSBQb3N0IEFwcHJvdmFsJywgJ2h0dHBzOi8vZ2l0aHViLmNvbS9ub3N0ci1wcm90b2NvbC9uaXBzL2Jsb2IvbWFzdGVyLzcyLm1kJ10sXG4gICAgWzcwMDAsICdKb2IgRmVlZGJhY2snLCAnaHR0cHM6Ly9naXRodWIuY29tL25vc3RyLXByb3RvY29sL25pcHMvYmxvYi9tYXN0ZXIvOTAubWQnXSxcbiAgICBbOTA0MSwgJ1phcCBHb2FsJywgJ2h0dHBzOi8vZ2l0aHViLmNvbS9ub3N0ci1wcm90b2NvbC9uaXBzL2Jsb2IvbWFzdGVyLzc1Lm1kJ10sXG4gICAgWzk3MzQsICdaYXAgUmVxdWVzdCcsICdodHRwczovL2dpdGh1Yi5jb20vbm9zdHItcHJvdG9jb2wvbmlwcy9ibG9iL21hc3Rlci81Ny5tZCddLFxuICAgIFs5NzM1LCAnWmFwJywgJ2h0dHBzOi8vZ2l0aHViLmNvbS9ub3N0ci1wcm90b2NvbC9uaXBzL2Jsb2IvbWFzdGVyLzU3Lm1kJ10sXG4gICAgWzEwMDAwLCAnTXV0ZSBMaXN0JywgJ2h0dHBzOi8vZ2l0aHViLmNvbS9ub3N0ci1wcm90b2NvbC9uaXBzL2Jsb2IvbWFzdGVyLzUxLm1kJ10sXG4gICAgWzEwMDAxLCAnUGluIExpc3QnLCAnaHR0cHM6Ly9naXRodWIuY29tL25vc3RyLXByb3RvY29sL25pcHMvYmxvYi9tYXN0ZXIvNTEubWQnXSxcbiAgICBbMTAwMDIsICdSZWxheSBMaXN0IE1ldGFkYXRhJywgJ2h0dHBzOi8vZ2l0aHViLmNvbS9ub3N0ci1wcm90b2NvbC9uaXBzL2Jsb2IvbWFzdGVyLzY1Lm1kJ10sXG4gICAgWzEzMTk0LCAnV2FsbGV0IEluZm8nLCAnaHR0cHM6Ly9naXRodWIuY29tL25vc3RyLXByb3RvY29sL25pcHMvYmxvYi9tYXN0ZXIvNDcubWQnXSxcbiAgICBbMjIyNDIsICdDbGllbnQgQXV0aGVudGljYXRpb24nLCAnaHR0cHM6Ly9naXRodWIuY29tL25vc3RyLXByb3RvY29sL25pcHMvYmxvYi9tYXN0ZXIvNDIubWQnXSxcbiAgICBbMjMxOTQsICdXYWxsZXQgUmVxdWVzdCcsICdodHRwczovL2dpdGh1Yi5jb20vbm9zdHItcHJvdG9jb2wvbmlwcy9ibG9iL21hc3Rlci80Ny5tZCddLFxuICAgIFsyMzE5NSwgJ1dhbGxldCBSZXNwb25zZScsICdodHRwczovL2dpdGh1Yi5jb20vbm9zdHItcHJvdG9jb2wvbmlwcy9ibG9iL21hc3Rlci80Ny5tZCddLFxuICAgIFsyNDEzMywgJ05vc3RyIENvbm5lY3QnLCAnaHR0cHM6Ly9naXRodWIuY29tL25vc3RyLXByb3RvY29sL25pcHMvYmxvYi9tYXN0ZXIvNDYubWQnXSxcbiAgICBbMjcyMzUsICdIVFRQIEF1dGgnLCAnaHR0cHM6Ly9naXRodWIuY29tL25vc3RyLXByb3RvY29sL25pcHMvYmxvYi9tYXN0ZXIvOTgubWQnXSxcbiAgICBbMzAwMDAsICdDYXRlZ29yaXplZCBQZW9wbGUgTGlzdCcsICdodHRwczovL2dpdGh1Yi5jb20vbm9zdHItcHJvdG9jb2wvbmlwcy9ibG9iL21hc3Rlci81MS5tZCddLFxuICAgIFszMDAwMSwgJ0NhdGVnb3JpemVkIEJvb2ttYXJrIExpc3QnLCAnaHR0cHM6Ly9naXRodWIuY29tL25vc3RyLXByb3RvY29sL25pcHMvYmxvYi9tYXN0ZXIvNTEubWQnXSxcbiAgICBbMzAwMDgsICdQcm9maWxlIEJhZGdlcycsICdodHRwczovL2dpdGh1Yi5jb20vbm9zdHItcHJvdG9jb2wvbmlwcy9ibG9iL21hc3Rlci81OC5tZCddLFxuICAgIFszMDAwOSwgJ0JhZGdlIERlZmluaXRpb24nLCAnaHR0cHM6Ly9naXRodWIuY29tL25vc3RyLXByb3RvY29sL25pcHMvYmxvYi9tYXN0ZXIvNTgubWQnXSxcbiAgICBbMzAwMTcsICdDcmVhdGUgb3IgdXBkYXRlIGEgc3RhbGwnLCAnaHR0cHM6Ly9naXRodWIuY29tL25vc3RyLXByb3RvY29sL25pcHMvYmxvYi9tYXN0ZXIvMTUubWQnXSxcbiAgICBbMzAwMTgsICdDcmVhdGUgb3IgdXBkYXRlIGEgcHJvZHVjdCcsICdodHRwczovL2dpdGh1Yi5jb20vbm9zdHItcHJvdG9jb2wvbmlwcy9ibG9iL21hc3Rlci8xNS5tZCddLFxuICAgIFszMDAyMywgJ0xvbmctRm9ybSBDb250ZW50JywgJ2h0dHBzOi8vZ2l0aHViLmNvbS9ub3N0ci1wcm90b2NvbC9uaXBzL2Jsb2IvbWFzdGVyLzIzLm1kJ10sXG4gICAgWzMwMDI0LCAnRHJhZnQgTG9uZy1mb3JtIENvbnRlbnQnLCAnaHR0cHM6Ly9naXRodWIuY29tL25vc3RyLXByb3RvY29sL25pcHMvYmxvYi9tYXN0ZXIvMjMubWQnXSxcbiAgICBbMzAwNzgsICdBcHBsaWNhdGlvbi1zcGVjaWZpYyBEYXRhJywgJ2h0dHBzOi8vZ2l0aHViLmNvbS9ub3N0ci1wcm90b2NvbC9uaXBzL2Jsb2IvbWFzdGVyLzc4Lm1kJ10sXG4gICAgWzMwMzExLCAnTGl2ZSBFdmVudCcsICdodHRwczovL2dpdGh1Yi5jb20vbm9zdHItcHJvdG9jb2wvbmlwcy9ibG9iL21hc3Rlci81My5tZCddLFxuICAgIFszMDMxNSwgJ1VzZXIgU3RhdHVzZXMnLCAnaHR0cHM6Ly9naXRodWIuY29tL25vc3RyLXByb3RvY29sL25pcHMvYmxvYi9tYXN0ZXIvMzgubWQnXSxcbiAgICBbMzA0MDIsICdDbGFzc2lmaWVkIExpc3RpbmcnLCAnaHR0cHM6Ly9naXRodWIuY29tL25vc3RyLXByb3RvY29sL25pcHMvYmxvYi9tYXN0ZXIvOTkubWQnXSxcbiAgICBbMzA0MDMsICdEcmFmdCBDbGFzc2lmaWVkIExpc3RpbmcnLCAnaHR0cHM6Ly9naXRodWIuY29tL25vc3RyLXByb3RvY29sL25pcHMvYmxvYi9tYXN0ZXIvOTkubWQnXSxcbiAgICBbMzE5MjIsICdEYXRlLUJhc2VkIENhbGVuZGFyIEV2ZW50JywgJ2h0dHBzOi8vZ2l0aHViLmNvbS9ub3N0ci1wcm90b2NvbC9uaXBzL2Jsb2IvbWFzdGVyLzUyLm1kJ10sXG4gICAgWzMxOTIzLCAnVGltZS1CYXNlZCBDYWxlbmRhciBFdmVudCcsICdodHRwczovL2dpdGh1Yi5jb20vbm9zdHItcHJvdG9jb2wvbmlwcy9ibG9iL21hc3Rlci81Mi5tZCddLFxuICAgIFszMTkyNCwgJ0NhbGVuZGFyJywgJ2h0dHBzOi8vZ2l0aHViLmNvbS9ub3N0ci1wcm90b2NvbC9uaXBzL2Jsb2IvbWFzdGVyLzUyLm1kJ10sXG4gICAgWzMxOTI1LCAnQ2FsZW5kYXIgRXZlbnQgUlNWUCcsICdodHRwczovL2dpdGh1Yi5jb20vbm9zdHItcHJvdG9jb2wvbmlwcy9ibG9iL21hc3Rlci81Mi5tZCddLFxuICAgIFszMTk4OSwgJ0hhbmRsZXIgcmVjb21tZW5kYXRpb24nLCAnaHR0cHM6Ly9naXRodWIuY29tL25vc3RyLXByb3RvY29sL25pcHMvYmxvYi9tYXN0ZXIvODkubWQnXSxcbiAgICBbMzE5OTAsICdIYW5kbGVyIGluZm9ybWF0aW9uJywgJ2h0dHBzOi8vZ2l0aHViLmNvbS9ub3N0ci1wcm90b2NvbC9uaXBzL2Jsb2IvbWFzdGVyLzg5Lm1kJ10sXG4gICAgWzM0NTUwLCAnQ29tbXVuaXR5IERlZmluaXRpb24nLCAnaHR0cHM6Ly9naXRodWIuY29tL25vc3RyLXByb3RvY29sL25pcHMvYmxvYi9tYXN0ZXIvNzIubWQnXSxcbl07XG5cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBpbml0aWFsaXplKCkge1xuICAgIGF3YWl0IGdldE9yU2V0RGVmYXVsdCgncHJvZmlsZUluZGV4JywgMCk7XG4gICAgYXdhaXQgZ2V0T3JTZXREZWZhdWx0KCdwcm9maWxlcycsIFthd2FpdCBnZW5lcmF0ZVByb2ZpbGUoKV0pO1xuICAgIGxldCB2ZXJzaW9uID0gKGF3YWl0IHN0b3JhZ2UuZ2V0KHsgdmVyc2lvbjogMCB9KSkudmVyc2lvbjtcbiAgICBjb25zb2xlLmxvZygnREIgdmVyc2lvbjogJywgdmVyc2lvbik7XG4gICAgd2hpbGUgKHZlcnNpb24gPCBEQl9WRVJTSU9OKSB7XG4gICAgICAgIHZlcnNpb24gPSBhd2FpdCBtaWdyYXRlKHZlcnNpb24sIERCX1ZFUlNJT04pO1xuICAgICAgICBhd2FpdCBzdG9yYWdlLnNldCh7IHZlcnNpb24gfSk7XG4gICAgfVxufVxuXG5hc3luYyBmdW5jdGlvbiBtaWdyYXRlKHZlcnNpb24sIGdvYWwpIHtcbiAgICBpZiAodmVyc2lvbiA9PT0gMCkge1xuICAgICAgICBjb25zb2xlLmxvZygnTWlncmF0aW5nIHRvIHZlcnNpb24gMS4nKTtcbiAgICAgICAgbGV0IHByb2ZpbGVzID0gYXdhaXQgZ2V0UHJvZmlsZXMoKTtcbiAgICAgICAgcHJvZmlsZXMuZm9yRWFjaChwcm9maWxlID0+IChwcm9maWxlLmhvc3RzID0ge30pKTtcbiAgICAgICAgYXdhaXQgc3RvcmFnZS5zZXQoeyBwcm9maWxlcyB9KTtcbiAgICAgICAgcmV0dXJuIHZlcnNpb24gKyAxO1xuICAgIH1cblxuICAgIGlmICh2ZXJzaW9uID09PSAxKSB7XG4gICAgICAgIGNvbnNvbGUubG9nKCdtaWdyYXRpbmcgdG8gdmVyc2lvbiAyLicpO1xuICAgICAgICBsZXQgcHJvZmlsZXMgPSBhd2FpdCBnZXRQcm9maWxlcygpO1xuICAgICAgICBhd2FpdCBzdG9yYWdlLnNldCh7IHByb2ZpbGVzIH0pO1xuICAgICAgICByZXR1cm4gdmVyc2lvbiArIDE7XG4gICAgfVxuXG4gICAgaWYgKHZlcnNpb24gPT09IDIpIHtcbiAgICAgICAgY29uc29sZS5sb2coJ01pZ3JhdGluZyB0byB2ZXJzaW9uIDMuJyk7XG4gICAgICAgIGxldCBwcm9maWxlcyA9IGF3YWl0IGdldFByb2ZpbGVzKCk7XG4gICAgICAgIHByb2ZpbGVzLmZvckVhY2gocHJvZmlsZSA9PiAocHJvZmlsZS5yZWxheVJlbWluZGVyID0gdHJ1ZSkpO1xuICAgICAgICBhd2FpdCBzdG9yYWdlLnNldCh7IHByb2ZpbGVzIH0pO1xuICAgICAgICByZXR1cm4gdmVyc2lvbiArIDE7XG4gICAgfVxuXG4gICAgaWYgKHZlcnNpb24gPT09IDMpIHtcbiAgICAgICAgY29uc29sZS5sb2coJ01pZ3JhdGluZyB0byB2ZXJzaW9uIDQgKGVuY3J5cHRpb24gc3VwcG9ydCkuJyk7XG4gICAgICAgIC8vIE5vIGRhdGEgdHJhbnNmb3JtYXRpb24gbmVlZGVkIFx1MjAxNCBleGlzdGluZyBwbGFpbnRleHQga2V5cyBzdGF5IGFzLWlzLlxuICAgICAgICAvLyBFbmNyeXB0aW9uIG9ubHkgYWN0aXZhdGVzIHdoZW4gdGhlIHVzZXIgc2V0cyBhIG1hc3RlciBwYXNzd29yZC5cbiAgICAgICAgLy8gV2UganVzdCBlbnN1cmUgdGhlIGlzRW5jcnlwdGVkIGZsYWcgZXhpc3RzIGFuZCBkZWZhdWx0cyB0byBmYWxzZS5cbiAgICAgICAgbGV0IGRhdGEgPSBhd2FpdCBzdG9yYWdlLmdldCh7IGlzRW5jcnlwdGVkOiBmYWxzZSB9KTtcbiAgICAgICAgaWYgKCFkYXRhLmlzRW5jcnlwdGVkKSB7XG4gICAgICAgICAgICBhd2FpdCBzdG9yYWdlLnNldCh7IGlzRW5jcnlwdGVkOiBmYWxzZSB9KTtcbiAgICAgICAgfVxuICAgICAgICByZXR1cm4gdmVyc2lvbiArIDE7XG4gICAgfVxuXG4gICAgaWYgKHZlcnNpb24gPT09IDQpIHtcbiAgICAgICAgY29uc29sZS5sb2coJ01pZ3JhdGluZyB0byB2ZXJzaW9uIDUgKE5JUC00NiBidW5rZXIgc3VwcG9ydCkuJyk7XG4gICAgICAgIGxldCBwcm9maWxlcyA9IGF3YWl0IGdldFByb2ZpbGVzKCk7XG4gICAgICAgIHByb2ZpbGVzLmZvckVhY2gocHJvZmlsZSA9PiB7XG4gICAgICAgICAgICBpZiAoIXByb2ZpbGUudHlwZSkgcHJvZmlsZS50eXBlID0gJ2xvY2FsJztcbiAgICAgICAgICAgIGlmIChwcm9maWxlLmJ1bmtlclVybCA9PT0gdW5kZWZpbmVkKSBwcm9maWxlLmJ1bmtlclVybCA9IG51bGw7XG4gICAgICAgICAgICBpZiAocHJvZmlsZS5yZW1vdGVQdWJrZXkgPT09IHVuZGVmaW5lZCkgcHJvZmlsZS5yZW1vdGVQdWJrZXkgPSBudWxsO1xuICAgICAgICB9KTtcbiAgICAgICAgYXdhaXQgc3RvcmFnZS5zZXQoeyBwcm9maWxlcyB9KTtcbiAgICAgICAgcmV0dXJuIHZlcnNpb24gKyAxO1xuICAgIH1cblxuICAgIGlmICh2ZXJzaW9uID09PSA1KSB7XG4gICAgICAgIGNvbnNvbGUubG9nKCdNaWdyYXRpbmcgdG8gdmVyc2lvbiA2IChwbGF0Zm9ybSBzeW5jIHN1cHBvcnQpLicpO1xuICAgICAgICBjb25zdCBub3cgPSBNYXRoLmZsb29yKERhdGUubm93KCkgLyAxMDAwKTtcbiAgICAgICAgbGV0IHByb2ZpbGVzID0gYXdhaXQgZ2V0UHJvZmlsZXMoKTtcbiAgICAgICAgcHJvZmlsZXMuZm9yRWFjaChwcm9maWxlID0+IHtcbiAgICAgICAgICAgIGlmIChwcm9maWxlLnVwZGF0ZWRBdCA9PT0gdW5kZWZpbmVkKSBwcm9maWxlLnVwZGF0ZWRBdCA9IG5vdztcbiAgICAgICAgfSk7XG4gICAgICAgIGF3YWl0IHN0b3JhZ2Uuc2V0KHsgcHJvZmlsZXMsIHBsYXRmb3JtU3luY0VuYWJsZWQ6IHRydWUgfSk7XG4gICAgICAgIHJldHVybiB2ZXJzaW9uICsgMTtcbiAgICB9XG59XG5cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBnZXRQcm9maWxlcygpIHtcbiAgICBsZXQgcHJvZmlsZXMgPSBhd2FpdCBzdG9yYWdlLmdldCh7IHByb2ZpbGVzOiBbXSB9KTtcbiAgICByZXR1cm4gcHJvZmlsZXMucHJvZmlsZXM7XG59XG5cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBnZXRQcm9maWxlKGluZGV4KSB7XG4gICAgbGV0IHByb2ZpbGVzID0gYXdhaXQgZ2V0UHJvZmlsZXMoKTtcbiAgICByZXR1cm4gcHJvZmlsZXNbaW5kZXhdO1xufVxuXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gZ2V0UHJvZmlsZU5hbWVzKCkge1xuICAgIGxldCBwcm9maWxlcyA9IGF3YWl0IGdldFByb2ZpbGVzKCk7XG4gICAgcmV0dXJuIHByb2ZpbGVzLm1hcChwID0+IHAubmFtZSk7XG59XG5cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBnZXRQcm9maWxlSW5kZXgoKSB7XG4gICAgY29uc3QgaW5kZXggPSBhd2FpdCBzdG9yYWdlLmdldCh7IHByb2ZpbGVJbmRleDogMCB9KTtcbiAgICByZXR1cm4gaW5kZXgucHJvZmlsZUluZGV4O1xufVxuXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gc2V0UHJvZmlsZUluZGV4KHByb2ZpbGVJbmRleCkge1xuICAgIGF3YWl0IHN0b3JhZ2Uuc2V0KHsgcHJvZmlsZUluZGV4IH0pO1xufVxuXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gZGVsZXRlUHJvZmlsZShpbmRleCkge1xuICAgIGxldCBwcm9maWxlcyA9IGF3YWl0IGdldFByb2ZpbGVzKCk7XG4gICAgbGV0IHByb2ZpbGVJbmRleCA9IGF3YWl0IGdldFByb2ZpbGVJbmRleCgpO1xuICAgIHByb2ZpbGVzLnNwbGljZShpbmRleCwgMSk7XG4gICAgaWYgKHByb2ZpbGVzLmxlbmd0aCA9PSAwKSB7XG4gICAgICAgIGF3YWl0IGNsZWFyRGF0YSgpOyAvLyBJZiB3ZSBoYXZlIGRlbGV0ZWQgYWxsIG9mIHRoZSBwcm9maWxlcywgbGV0J3MganVzdCBzdGFydCBmcmVzaCB3aXRoIGFsbCBuZXcgZGF0YVxuICAgICAgICBhd2FpdCBpbml0aWFsaXplKCk7XG4gICAgfSBlbHNlIHtcbiAgICAgICAgLy8gSWYgdGhlIGluZGV4IGRlbGV0ZWQgd2FzIHRoZSBhY3RpdmUgcHJvZmlsZSwgY2hhbmdlIHRoZSBhY3RpdmUgcHJvZmlsZSB0byB0aGUgbmV4dCBvbmVcbiAgICAgICAgbGV0IG5ld0luZGV4ID1cbiAgICAgICAgICAgIHByb2ZpbGVJbmRleCA9PT0gaW5kZXggPyBNYXRoLm1heChpbmRleCAtIDEsIDApIDogcHJvZmlsZUluZGV4O1xuICAgICAgICBhd2FpdCBzdG9yYWdlLnNldCh7IHByb2ZpbGVzLCBwcm9maWxlSW5kZXg6IG5ld0luZGV4IH0pO1xuICAgIH1cbn1cblxuZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIGNsZWFyRGF0YSgpIHtcbiAgICBsZXQgaWdub3JlSW5zdGFsbEhvb2sgPSBhd2FpdCBzdG9yYWdlLmdldCh7IGlnbm9yZUluc3RhbGxIb29rOiBmYWxzZSB9KTtcbiAgICBhd2FpdCBzdG9yYWdlLmNsZWFyKCk7XG4gICAgYXdhaXQgc3RvcmFnZS5zZXQoaWdub3JlSW5zdGFsbEhvb2spO1xufVxuXG5hc3luYyBmdW5jdGlvbiBnZW5lcmF0ZVByaXZhdGVLZXkoKSB7XG4gICAgcmV0dXJuIGF3YWl0IGFwaS5ydW50aW1lLnNlbmRNZXNzYWdlKHsga2luZDogJ2dlbmVyYXRlUHJpdmF0ZUtleScgfSk7XG59XG5cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBnZW5lcmF0ZVByb2ZpbGUobmFtZSA9ICdEZWZhdWx0IE5vc3RyIFByb2ZpbGUnLCB0eXBlID0gJ2xvY2FsJykge1xuICAgIHJldHVybiB7XG4gICAgICAgIG5hbWUsXG4gICAgICAgIHByaXZLZXk6IHR5cGUgPT09ICdsb2NhbCcgPyBhd2FpdCBnZW5lcmF0ZVByaXZhdGVLZXkoKSA6ICcnLFxuICAgICAgICBob3N0czoge30sXG4gICAgICAgIHJlbGF5czogUkVDT01NRU5ERURfUkVMQVlTLm1hcChyID0+ICh7IHVybDogci5ocmVmLCByZWFkOiB0cnVlLCB3cml0ZTogdHJ1ZSB9KSksXG4gICAgICAgIHJlbGF5UmVtaW5kZXI6IGZhbHNlLFxuICAgICAgICB0eXBlLFxuICAgICAgICBidW5rZXJVcmw6IG51bGwsXG4gICAgICAgIHJlbW90ZVB1YmtleTogbnVsbCxcbiAgICAgICAgdXBkYXRlZEF0OiBNYXRoLmZsb29yKERhdGUubm93KCkgLyAxMDAwKSxcbiAgICB9O1xufVxuXG5hc3luYyBmdW5jdGlvbiBnZXRPclNldERlZmF1bHQoa2V5LCBkZWYpIHtcbiAgICBsZXQgdmFsID0gKGF3YWl0IHN0b3JhZ2UuZ2V0KGtleSkpW2tleV07XG4gICAgaWYgKHZhbCA9PSBudWxsIHx8IHZhbCA9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgYXdhaXQgc3RvcmFnZS5zZXQoeyBba2V5XTogZGVmIH0pO1xuICAgICAgICByZXR1cm4gZGVmO1xuICAgIH1cblxuICAgIHJldHVybiB2YWw7XG59XG5cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBzYXZlUHJvZmlsZU5hbWUoaW5kZXgsIHByb2ZpbGVOYW1lKSB7XG4gICAgbGV0IHByb2ZpbGVzID0gYXdhaXQgZ2V0UHJvZmlsZXMoKTtcbiAgICBwcm9maWxlc1tpbmRleF0ubmFtZSA9IHByb2ZpbGVOYW1lO1xuICAgIHByb2ZpbGVzW2luZGV4XS51cGRhdGVkQXQgPSBNYXRoLmZsb29yKERhdGUubm93KCkgLyAxMDAwKTtcbiAgICBhd2FpdCBzdG9yYWdlLnNldCh7IHByb2ZpbGVzIH0pO1xufVxuXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gc2F2ZVByaXZhdGVLZXkoaW5kZXgsIHByaXZhdGVLZXkpIHtcbiAgICBjb25zdCByZXMgPSBhd2FpdCBhcGkucnVudGltZS5zZW5kTWVzc2FnZSh7XG4gICAgICAgIGtpbmQ6ICdzYXZlUHJpdmF0ZUtleScsXG4gICAgICAgIHBheWxvYWQ6IFtpbmRleCwgcHJpdmF0ZUtleV0sXG4gICAgfSk7XG4gICAgaWYgKCFyZXMgfHwgIXJlcy5zdWNjZXNzKSB7XG4gICAgICAgIHRocm93IG5ldyBFcnJvcihyZXM/LmVycm9yIHx8ICdGYWlsZWQgdG8gc2F2ZSBwcml2YXRlIGtleScpO1xuICAgIH1cbiAgICByZXR1cm4gcmVzO1xufVxuXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gbmV3UHJvZmlsZSgpIHtcbiAgICBsZXQgcHJvZmlsZXMgPSBhd2FpdCBnZXRQcm9maWxlcygpO1xuICAgIGNvbnN0IG5ld1Byb2ZpbGUgPSBhd2FpdCBnZW5lcmF0ZVByb2ZpbGUoJ05ldyBQcm9maWxlJyk7XG4gICAgcHJvZmlsZXMucHVzaChuZXdQcm9maWxlKTtcbiAgICBhd2FpdCBzdG9yYWdlLnNldCh7IHByb2ZpbGVzIH0pO1xuICAgIHJldHVybiBwcm9maWxlcy5sZW5ndGggLSAxO1xufVxuXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gbmV3QnVua2VyUHJvZmlsZShuYW1lID0gJ05ldyBCdW5rZXInLCBidW5rZXJVcmwgPSBudWxsKSB7XG4gICAgbGV0IHByb2ZpbGVzID0gYXdhaXQgZ2V0UHJvZmlsZXMoKTtcbiAgICBjb25zdCBwcm9maWxlID0gYXdhaXQgZ2VuZXJhdGVQcm9maWxlKG5hbWUsICdidW5rZXInKTtcbiAgICBwcm9maWxlLmJ1bmtlclVybCA9IGJ1bmtlclVybDtcbiAgICBwcm9maWxlcy5wdXNoKHByb2ZpbGUpO1xuICAgIGF3YWl0IHN0b3JhZ2Uuc2V0KHsgcHJvZmlsZXMgfSk7XG4gICAgcmV0dXJuIHByb2ZpbGVzLmxlbmd0aCAtIDE7XG59XG5cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBnZXRSZWxheXMocHJvZmlsZUluZGV4KSB7XG4gICAgbGV0IHByb2ZpbGUgPSBhd2FpdCBnZXRQcm9maWxlKHByb2ZpbGVJbmRleCk7XG4gICAgcmV0dXJuIHByb2ZpbGUucmVsYXlzIHx8IFtdO1xufVxuXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gc2F2ZVJlbGF5cyhwcm9maWxlSW5kZXgsIHJlbGF5cykge1xuICAgIC8vIEhhdmluZyBhbiBBbHBpbmUgcHJveHkgb2JqZWN0IGFzIGEgc3ViLW9iamVjdCBkb2VzIG5vdCBzZXJpYWxpemUgY29ycmVjdGx5IGluIHN0b3JhZ2UsXG4gICAgLy8gc28gd2UgYXJlIHByZS1zZXJpYWxpemluZyBoZXJlIGJlZm9yZSBhc3NpZ25pbmcgaXQgdG8gdGhlIHByb2ZpbGUsIHNvIHRoZSBwcm94eVxuICAgIC8vIG9iaiBkb2Vzbid0IGJ1ZyBvdXQuXG4gICAgbGV0IGZpeGVkUmVsYXlzID0gSlNPTi5wYXJzZShKU09OLnN0cmluZ2lmeShyZWxheXMpKTtcbiAgICBsZXQgcHJvZmlsZXMgPSBhd2FpdCBnZXRQcm9maWxlcygpO1xuICAgIGxldCBwcm9maWxlID0gcHJvZmlsZXNbcHJvZmlsZUluZGV4XTtcbiAgICBwcm9maWxlLnJlbGF5cyA9IGZpeGVkUmVsYXlzO1xuICAgIHByb2ZpbGUudXBkYXRlZEF0ID0gTWF0aC5mbG9vcihEYXRlLm5vdygpIC8gMTAwMCk7XG4gICAgYXdhaXQgc3RvcmFnZS5zZXQoeyBwcm9maWxlcyB9KTtcbn1cblxuZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIGdldChpdGVtKSB7XG4gICAgcmV0dXJuIChhd2FpdCBzdG9yYWdlLmdldChpdGVtKSlbaXRlbV07XG59XG5cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBnZXRQZXJtaXNzaW9ucyhpbmRleCA9IG51bGwpIHtcbiAgICBpZiAoaW5kZXggPT0gbnVsbCkge1xuICAgICAgICBpbmRleCA9IGF3YWl0IGdldFByb2ZpbGVJbmRleCgpO1xuICAgIH1cbiAgICBsZXQgcHJvZmlsZSA9IGF3YWl0IGdldFByb2ZpbGUoaW5kZXgpO1xuICAgIGxldCBob3N0cyA9IGF3YWl0IHByb2ZpbGUuaG9zdHM7XG4gICAgcmV0dXJuIGhvc3RzO1xufVxuXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gZ2V0UGVybWlzc2lvbihob3N0LCBhY3Rpb24pIHtcbiAgICBsZXQgaW5kZXggPSBhd2FpdCBnZXRQcm9maWxlSW5kZXgoKTtcbiAgICBsZXQgcHJvZmlsZSA9IGF3YWl0IGdldFByb2ZpbGUoaW5kZXgpO1xuICAgIHJldHVybiBwcm9maWxlPy5ob3N0cz8uW2hvc3RdPy5bYWN0aW9uXSB8fCAnYXNrJztcbn1cblxuZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIHNldFBlcm1pc3Npb24oaG9zdCwgYWN0aW9uLCBwZXJtLCBpbmRleCA9IG51bGwpIHtcbiAgICBsZXQgcHJvZmlsZXMgPSBhd2FpdCBnZXRQcm9maWxlcygpO1xuICAgIC8vIFVzZSBgPT0gbnVsbGAgKG5vdCBgIWluZGV4YCk6IHByb2ZpbGUgaW5kZXggMCBpcyBhIHZhbGlkIGV4cGxpY2l0IHRhcmdldC5cbiAgICAvLyBgIWluZGV4YCB0cmVhdGVkIGluZGV4IDAgYXMgXCJ1bnNldFwiIGFuZCB3cm90ZSB0aGUgZ3JhbnQgdG8gd2hhdGV2ZXJcbiAgICAvLyBwcm9maWxlIGhhcHBlbmVkIHRvIGJlIGFjdGl2ZSBcdTIwMTQgbGVha2luZyBwZXJtaXNzaW9ucyBhY3Jvc3MgaWRlbnRpdGllcy5cbiAgICBpZiAoaW5kZXggPT0gbnVsbCkge1xuICAgICAgICBpbmRleCA9IGF3YWl0IGdldFByb2ZpbGVJbmRleCgpO1xuICAgIH1cbiAgICBsZXQgcHJvZmlsZSA9IHByb2ZpbGVzW2luZGV4XTtcbiAgICBsZXQgbmV3UGVybXMgPSBwcm9maWxlLmhvc3RzW2hvc3RdIHx8IHt9O1xuICAgIG5ld1Blcm1zID0geyAuLi5uZXdQZXJtcywgW2FjdGlvbl06IHBlcm0gfTtcbiAgICBwcm9maWxlLmhvc3RzW2hvc3RdID0gbmV3UGVybXM7XG4gICAgcHJvZmlsZS51cGRhdGVkQXQgPSBNYXRoLmZsb29yKERhdGUubm93KCkgLyAxMDAwKTtcbiAgICBwcm9maWxlc1tpbmRleF0gPSBwcm9maWxlO1xuICAgIGF3YWl0IHN0b3JhZ2Uuc2V0KHsgcHJvZmlsZXMgfSk7XG59XG5cbmV4cG9ydCBmdW5jdGlvbiBodW1hblBlcm1pc3Npb24ocCkge1xuICAgIC8vIEhhbmRsZSBzcGVjaWFsIGNhc2Ugd2hlcmUgZXZlbnQgc2lnbmluZyBpbmNsdWRlcyBhIGtpbmQgbnVtYmVyXG4gICAgaWYgKHAuc3RhcnRzV2l0aCgnc2lnbkV2ZW50OicpKSB7XG4gICAgICAgIGxldCBbZSwgbl0gPSBwLnNwbGl0KCc6Jyk7XG4gICAgICAgIG4gPSBwYXJzZUludChuKTtcbiAgICAgICAgbGV0IG5uYW1lID0gS0lORFMuZmluZChrID0+IGtbMF0gPT09IG4pPy5bMV0gfHwgYFVua25vd24gKEtpbmQgJHtufSlgO1xuICAgICAgICByZXR1cm4gYFNpZ24gZXZlbnQ6ICR7bm5hbWV9YDtcbiAgICB9XG5cbiAgICBzd2l0Y2ggKHApIHtcbiAgICAgICAgY2FzZSAnZ2V0UHViS2V5JzpcbiAgICAgICAgICAgIHJldHVybiAnUmVhZCBwdWJsaWMga2V5JztcbiAgICAgICAgY2FzZSAnc2lnbkV2ZW50JzpcbiAgICAgICAgICAgIHJldHVybiAnU2lnbiBldmVudCc7XG4gICAgICAgIGNhc2UgJ2dldFJlbGF5cyc6XG4gICAgICAgICAgICByZXR1cm4gJ1JlYWQgcmVsYXkgbGlzdCc7XG4gICAgICAgIGNhc2UgJ25pcDA0LmVuY3J5cHQnOlxuICAgICAgICAgICAgcmV0dXJuICdFbmNyeXB0IHByaXZhdGUgbWVzc2FnZSAoTklQLTA0KSc7XG4gICAgICAgIGNhc2UgJ25pcDA0LmRlY3J5cHQnOlxuICAgICAgICAgICAgcmV0dXJuICdEZWNyeXB0IHByaXZhdGUgbWVzc2FnZSAoTklQLTA0KSc7XG4gICAgICAgIGNhc2UgJ25pcDQ0LmVuY3J5cHQnOlxuICAgICAgICAgICAgcmV0dXJuICdFbmNyeXB0IHByaXZhdGUgbWVzc2FnZSAoTklQLTQ0KSc7XG4gICAgICAgIGNhc2UgJ25pcDQ0LmRlY3J5cHQnOlxuICAgICAgICAgICAgcmV0dXJuICdEZWNyeXB0IHByaXZhdGUgbWVzc2FnZSAoTklQLTQ0KSc7XG4gICAgICAgIGRlZmF1bHQ6XG4gICAgICAgICAgICByZXR1cm4gJ1Vua25vd24nO1xuICAgIH1cbn1cblxuZXhwb3J0IGZ1bmN0aW9uIHZhbGlkYXRlS2V5KGtleSkge1xuICAgIGNvbnN0IGhleE1hdGNoID0gL15bXFxkYS1mXXs2NH0kL2kudGVzdChrZXkpO1xuICAgIGNvbnN0IGIzMk1hdGNoID0gL15uc2VjMVtxcHpyeTl4OGdmMnR2ZHcwczNqbjU0a2hjZTZtdWE3bF17NTh9JC8udGVzdChrZXkpO1xuXG4gICAgcmV0dXJuIGhleE1hdGNoIHx8IGIzMk1hdGNoIHx8IGlzTmNyeXB0c2VjKGtleSkgfHwgaXNWYWxpZFNlZWRQaHJhc2Uoa2V5KTtcbn1cblxuZXhwb3J0IHsgbG9va3NMaWtlU2VlZFBocmFzZSB9O1xuZXhwb3J0IGNvbnN0IGlzU2VlZFBocmFzZSA9IGlzVmFsaWRTZWVkUGhyYXNlO1xuXG5leHBvcnQgZnVuY3Rpb24gaXNOY3J5cHRzZWMoa2V5KSB7XG4gICAgcmV0dXJuIC9ebmNyeXB0c2VjMVtxcHpyeTl4OGdmMnR2ZHcwczNqbjU0a2hjZTZtdWE3bF0rJC8udGVzdChrZXkpO1xufVxuXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gZmVhdHVyZShuYW1lKSB7XG4gICAgbGV0IGZuYW1lID0gYGZlYXR1cmU6JHtuYW1lfWA7XG4gICAgbGV0IGYgPSBhd2FpdCBhcGkuc3RvcmFnZS5sb2NhbC5nZXQoeyBbZm5hbWVdOiBmYWxzZSB9KTtcbiAgICByZXR1cm4gZltmbmFtZV07XG59XG5cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiByZWxheVJlbWluZGVyKCkge1xuICAgIGxldCBpbmRleCA9IGF3YWl0IGdldFByb2ZpbGVJbmRleCgpO1xuICAgIGxldCBwcm9maWxlID0gYXdhaXQgZ2V0UHJvZmlsZShpbmRleCk7XG4gICAgcmV0dXJuIHByb2ZpbGUucmVsYXlSZW1pbmRlcjtcbn1cblxuZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIHRvZ2dsZVJlbGF5UmVtaW5kZXIoKSB7XG4gICAgbGV0IGluZGV4ID0gYXdhaXQgZ2V0UHJvZmlsZUluZGV4KCk7XG4gICAgbGV0IHByb2ZpbGVzID0gYXdhaXQgZ2V0UHJvZmlsZXMoKTtcbiAgICBwcm9maWxlc1tpbmRleF0ucmVsYXlSZW1pbmRlciA9IGZhbHNlO1xuICAgIGF3YWl0IHN0b3JhZ2Uuc2V0KHsgcHJvZmlsZXMgfSk7XG59XG5cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBnZXROcHViKCkge1xuICAgIGxldCBpbmRleCA9IGF3YWl0IGdldFByb2ZpbGVJbmRleCgpO1xuICAgIHJldHVybiBhd2FpdCBhcGkucnVudGltZS5zZW5kTWVzc2FnZSh7XG4gICAgICAgIGtpbmQ6ICdnZXROcHViJyxcbiAgICAgICAgcGF5bG9hZDogaW5kZXgsXG4gICAgfSk7XG59XG5cbi8vIC0tLSBNYXN0ZXIgcGFzc3dvcmQgZW5jcnlwdGlvbiBoZWxwZXJzIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cblxuLyoqXG4gKiBDaGVjayB3aGV0aGVyIG1hc3RlciBwYXNzd29yZCBlbmNyeXB0aW9uIGlzIGFjdGl2ZS5cbiAqXG4gKiBEZWZlbnNpdmU6IGNoZWNrcyBtdWx0aXBsZSBpbmRpY2F0b3JzLCBub3QganVzdCB0aGUgYm9vbGVhbiBmbGFnLlxuICogSWYgcGFzc3dvcmRIYXNoIG9yIGVuY3J5cHRlZCBrZXkgYmxvYnMgZXhpc3QgYnV0IHRoZSBpc0VuY3J5cHRlZCBmbGFnXG4gKiBpcyBmYWxzZSAoaW5jb25zaXN0ZW50IHN0YXRlIGZyb20gc2VydmljZSB3b3JrZXIgY3Jhc2gsIHJhY2UgY29uZGl0aW9uLFxuICogZXRjLiksIHNlbGYtaGVhbHMgYnkgc2V0dGluZyB0aGUgZmxhZyBiYWNrIHRvIHRydWUuXG4gKi9cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBpc0VuY3J5cHRlZCgpIHtcbiAgICBjb25zdCBkYXRhID0gYXdhaXQgc3RvcmFnZS5nZXQoeyBpc0VuY3J5cHRlZDogZmFsc2UsIHBhc3N3b3JkSGFzaDogbnVsbCwgcHJvZmlsZXM6IFtdIH0pO1xuICAgIGlmIChkYXRhLmlzRW5jcnlwdGVkKSByZXR1cm4gdHJ1ZTtcblxuICAgIC8vIEZhbGxiYWNrIDE6IHBhc3N3b3JkSGFzaCBleGlzdHMgYnV0IGZsYWcgaXMgc3RhbGVcbiAgICBpZiAoZGF0YS5wYXNzd29yZEhhc2gpIHtcbiAgICAgICAgYXdhaXQgc3RvcmFnZS5zZXQoeyBpc0VuY3J5cHRlZDogdHJ1ZSB9KTtcbiAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgfVxuXG4gICAgLy8gRmFsbGJhY2sgMjogZW5jcnlwdGVkIGJsb2JzIGV4aXN0IGluIHByb2ZpbGVzIGJ1dCBmbGFnICsgaGFzaCBhcmUgbWlzc2luZ1xuICAgIGZvciAoY29uc3QgcHJvZmlsZSBvZiBkYXRhLnByb2ZpbGVzKSB7XG4gICAgICAgIGlmIChpc0VuY3J5cHRlZEJsb2IocHJvZmlsZS5wcml2S2V5KSkge1xuICAgICAgICAgICAgYXdhaXQgc3RvcmFnZS5zZXQoeyBpc0VuY3J5cHRlZDogdHJ1ZSB9KTtcbiAgICAgICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgICB9XG4gICAgfVxuXG4gICAgcmV0dXJuIGZhbHNlO1xufVxuXG4vKipcbiAqIFN0b3JlIHRoZSBwYXNzd29yZCB2ZXJpZmljYXRpb24gaGFzaCAobmV2ZXIgdGhlIHBhc3N3b3JkIGl0c2VsZikuXG4gKi9cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBzZXRQYXNzd29yZEhhc2gocGFzc3dvcmQpIHtcbiAgICBjb25zdCB7IGhhc2gsIHNhbHQgfSA9IGF3YWl0IGhhc2hQYXNzd29yZChwYXNzd29yZCk7XG4gICAgYXdhaXQgc3RvcmFnZS5zZXQoe1xuICAgICAgICBwYXNzd29yZEhhc2g6IGhhc2gsXG4gICAgICAgIHBhc3N3b3JkU2FsdDogc2FsdCxcbiAgICAgICAgaXNFbmNyeXB0ZWQ6IHRydWUsXG4gICAgfSk7XG59XG5cbi8qKlxuICogVmVyaWZ5IGEgcGFzc3dvcmQgYWdhaW5zdCB0aGUgc3RvcmVkIGhhc2guXG4gKi9cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBjaGVja1Bhc3N3b3JkKHBhc3N3b3JkKSB7XG4gICAgY29uc3QgZGF0YSA9IGF3YWl0IHN0b3JhZ2UuZ2V0KHtcbiAgICAgICAgcGFzc3dvcmRIYXNoOiBudWxsLFxuICAgICAgICBwYXNzd29yZFNhbHQ6IG51bGwsXG4gICAgfSk7XG4gICAgaWYgKCFkYXRhLnBhc3N3b3JkSGFzaCB8fCAhZGF0YS5wYXNzd29yZFNhbHQpIHJldHVybiBmYWxzZTtcbiAgICByZXR1cm4gdmVyaWZ5UGFzc3dvcmQocGFzc3dvcmQsIGRhdGEucGFzc3dvcmRIYXNoLCBkYXRhLnBhc3N3b3JkU2FsdCk7XG59XG5cbi8qKlxuICogUmVtb3ZlIG1hc3RlciBwYXNzd29yZCBwcm90ZWN0aW9uIFx1MjAxNCBjbGVhcnMgaGFzaCBhbmQgZGVjcnlwdHMgYWxsIGtleXMuXG4gKi9cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiByZW1vdmVQYXNzd29yZFByb3RlY3Rpb24ocGFzc3dvcmQpIHtcbiAgICBjb25zdCB2YWxpZCA9IGF3YWl0IGNoZWNrUGFzc3dvcmQocGFzc3dvcmQpO1xuICAgIGlmICghdmFsaWQpIHRocm93IG5ldyBFcnJvcignSW52YWxpZCBwYXNzd29yZCcpO1xuXG4gICAgbGV0IHByb2ZpbGVzID0gYXdhaXQgZ2V0UHJvZmlsZXMoKTtcbiAgICBmb3IgKGxldCBpID0gMDsgaSA8IHByb2ZpbGVzLmxlbmd0aDsgaSsrKSB7XG4gICAgICAgIGlmIChwcm9maWxlc1tpXS50eXBlID09PSAnYnVua2VyJykgY29udGludWU7XG4gICAgICAgIGlmIChpc0VuY3J5cHRlZEJsb2IocHJvZmlsZXNbaV0ucHJpdktleSkpIHtcbiAgICAgICAgICAgIHByb2ZpbGVzW2ldLnByaXZLZXkgPSBhd2FpdCBkZWNyeXB0KHByb2ZpbGVzW2ldLnByaXZLZXksIHBhc3N3b3JkKTtcbiAgICAgICAgfVxuICAgIH1cbiAgICBhd2FpdCBzdG9yYWdlLnNldCh7XG4gICAgICAgIHByb2ZpbGVzLFxuICAgICAgICBpc0VuY3J5cHRlZDogZmFsc2UsXG4gICAgICAgIHBhc3N3b3JkSGFzaDogbnVsbCxcbiAgICAgICAgcGFzc3dvcmRTYWx0OiBudWxsLFxuICAgIH0pO1xufVxuXG4vKipcbiAqIEVuY3J5cHQgYWxsIHByb2ZpbGUgcHJpdmF0ZSBrZXlzIHdpdGggYSBtYXN0ZXIgcGFzc3dvcmQuXG4gKi9cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBlbmNyeXB0QWxsS2V5cyhwYXNzd29yZCkge1xuICAgIGxldCBwcm9maWxlcyA9IGF3YWl0IGdldFByb2ZpbGVzKCk7XG4gICAgZm9yIChsZXQgaSA9IDA7IGkgPCBwcm9maWxlcy5sZW5ndGg7IGkrKykge1xuICAgICAgICBpZiAocHJvZmlsZXNbaV0udHlwZSA9PT0gJ2J1bmtlcicpIGNvbnRpbnVlO1xuICAgICAgICBpZiAoIWlzRW5jcnlwdGVkQmxvYihwcm9maWxlc1tpXS5wcml2S2V5KSkge1xuICAgICAgICAgICAgcHJvZmlsZXNbaV0ucHJpdktleSA9IGF3YWl0IGVuY3J5cHQocHJvZmlsZXNbaV0ucHJpdktleSwgcGFzc3dvcmQpO1xuICAgICAgICB9XG4gICAgfVxuICAgIGF3YWl0IHNldFBhc3N3b3JkSGFzaChwYXNzd29yZCk7XG4gICAgYXdhaXQgc3RvcmFnZS5zZXQoeyBwcm9maWxlcyB9KTtcbn1cblxuLyoqXG4gKiBSZS1lbmNyeXB0IGFsbCBrZXlzIHdpdGggYSBuZXcgcGFzc3dvcmQgKHJlcXVpcmVzIHRoZSBvbGQgcGFzc3dvcmQpLlxuICovXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gY2hhbmdlUGFzc3dvcmRGb3JLZXlzKG9sZFBhc3N3b3JkLCBuZXdQYXNzd29yZCkge1xuICAgIGxldCBwcm9maWxlcyA9IGF3YWl0IGdldFByb2ZpbGVzKCk7XG4gICAgZm9yIChsZXQgaSA9IDA7IGkgPCBwcm9maWxlcy5sZW5ndGg7IGkrKykge1xuICAgICAgICBpZiAocHJvZmlsZXNbaV0udHlwZSA9PT0gJ2J1bmtlcicpIGNvbnRpbnVlO1xuICAgICAgICBsZXQgaGV4ID0gcHJvZmlsZXNbaV0ucHJpdktleTtcbiAgICAgICAgaWYgKGlzRW5jcnlwdGVkQmxvYihoZXgpKSB7XG4gICAgICAgICAgICBoZXggPSBhd2FpdCBkZWNyeXB0KGhleCwgb2xkUGFzc3dvcmQpO1xuICAgICAgICB9XG4gICAgICAgIHByb2ZpbGVzW2ldLnByaXZLZXkgPSBhd2FpdCBlbmNyeXB0KGhleCwgbmV3UGFzc3dvcmQpO1xuICAgIH1cbiAgICBjb25zdCB7IGhhc2gsIHNhbHQgfSA9IGF3YWl0IGhhc2hQYXNzd29yZChuZXdQYXNzd29yZCk7XG4gICAgYXdhaXQgc3RvcmFnZS5zZXQoe1xuICAgICAgICBwcm9maWxlcyxcbiAgICAgICAgcGFzc3dvcmRIYXNoOiBoYXNoLFxuICAgICAgICBwYXNzd29yZFNhbHQ6IHNhbHQsXG4gICAgICAgIGlzRW5jcnlwdGVkOiB0cnVlLFxuICAgIH0pO1xufVxuXG4vKipcbiAqIERlY3J5cHQgYSBzaW5nbGUgcHJvZmlsZSdzIHByaXZhdGUga2V5LCByZXR1cm5pbmcgdGhlIGhleCBzdHJpbmcuXG4gKi9cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBnZXREZWNyeXB0ZWRQcml2S2V5KHByb2ZpbGUsIHBhc3N3b3JkKSB7XG4gICAgaWYgKHByb2ZpbGUudHlwZSA9PT0gJ2J1bmtlcicpIHJldHVybiAnJztcbiAgICBpZiAoaXNFbmNyeXB0ZWRCbG9iKHByb2ZpbGUucHJpdktleSkpIHtcbiAgICAgICAgcmV0dXJuIGRlY3J5cHQocHJvZmlsZS5wcml2S2V5LCBwYXNzd29yZCk7XG4gICAgfVxuICAgIHJldHVybiBwcm9maWxlLnByaXZLZXk7XG59XG5cbi8qKlxuICogQ2hlY2sgd2hldGhlciBhIHN0b3JlZCB2YWx1ZSBsb29rcyBsaWtlIGFuIGVuY3J5cHRlZCBibG9iLlxuICogRW5jcnlwdGVkIGJsb2JzIGFyZSBKU09OIHN0cmluZ3MgY29udGFpbmluZyB7c2FsdCwgaXYsIGNpcGhlcnRleHR9LlxuICovXG5leHBvcnQgZnVuY3Rpb24gaXNFbmNyeXB0ZWRCbG9iKHZhbHVlKSB7XG4gICAgaWYgKHR5cGVvZiB2YWx1ZSAhPT0gJ3N0cmluZycpIHJldHVybiBmYWxzZTtcbiAgICB0cnkge1xuICAgICAgICBjb25zdCBwYXJzZWQgPSBKU09OLnBhcnNlKHZhbHVlKTtcbiAgICAgICAgcmV0dXJuICEhKHBhcnNlZC5zYWx0ICYmIHBhcnNlZC5pdiAmJiBwYXJzZWQuY2lwaGVydGV4dCk7XG4gICAgfSBjYXRjaCB7XG4gICAgICAgIHJldHVybiBmYWxzZTtcbiAgICB9XG59XG4iLCAiLyoqXG4gKiBCcm93c2VyIEFQSSBjb21wYXRpYmlsaXR5IGxheWVyIGZvciBDaHJvbWUgLyBTYWZhcmkgLyBGaXJlZm94LlxuICpcbiAqIFNhZmFyaSBhbmQgRmlyZWZveCBleHBvc2UgYGJyb3dzZXIuKmAgKFByb21pc2UtYmFzZWQsIFdlYkV4dGVuc2lvbiBzdGFuZGFyZCkuXG4gKiBDaHJvbWUgZXhwb3NlcyBgY2hyb21lLipgIChjYWxsYmFjay1iYXNlZCBoaXN0b3JpY2FsbHksIGJ1dCBNVjMgc3VwcG9ydHNcbiAqIHByb21pc2VzIG9uIG1vc3QgQVBJcykuIEluIGEgc2VydmljZS13b3JrZXIgY29udGV4dCBgYnJvd3NlcmAgaXMgdW5kZWZpbmVkXG4gKiBvbiBDaHJvbWUsIHNvIHdlIG5vcm1hbGlzZSBldmVyeXRoaW5nIGhlcmUuXG4gKlxuICogVXNhZ2U6ICBpbXBvcnQgeyBhcGkgfSBmcm9tICcuL3V0aWxpdGllcy9icm93c2VyLXBvbHlmaWxsJztcbiAqICAgICAgICAgYXBpLnJ1bnRpbWUuc2VuZE1lc3NhZ2UoLi4uKVxuICpcbiAqIFRoZSBleHBvcnRlZCBgYXBpYCBvYmplY3QgbWlycm9ycyB0aGUgc3Vic2V0IG9mIHRoZSBXZWJFeHRlbnNpb24gQVBJIHRoYXRcbiAqIE5vc3RyS2V5IGFjdHVhbGx5IHVzZXMsIHdpdGggZXZlcnkgbWV0aG9kIHJldHVybmluZyBhIFByb21pc2UuXG4gKi9cblxuLy8gRGV0ZWN0IHdoaWNoIGdsb2JhbCBuYW1lc3BhY2UgaXMgYXZhaWxhYmxlLlxuY29uc3QgX2Jyb3dzZXIgPVxuICAgIHR5cGVvZiBicm93c2VyICE9PSAndW5kZWZpbmVkJyA/IGJyb3dzZXIgOlxuICAgIHR5cGVvZiBjaHJvbWUgICE9PSAndW5kZWZpbmVkJyA/IGNocm9tZSAgOlxuICAgIG51bGw7XG5cbmlmICghX2Jyb3dzZXIpIHtcbiAgICB0aHJvdyBuZXcgRXJyb3IoJ2Jyb3dzZXItcG9seWZpbGw6IE5vIGV4dGVuc2lvbiBBUEkgbmFtZXNwYWNlIGZvdW5kIChuZWl0aGVyIGJyb3dzZXIgbm9yIGNocm9tZSkuJyk7XG59XG5cbi8qKlxuICogVHJ1ZSB3aGVuIHJ1bm5pbmcgb24gQ2hyb21lIChvciBhbnkgQ2hyb21pdW0tYmFzZWQgYnJvd3NlciB0aGF0IG9ubHlcbiAqIGV4cG9zZXMgdGhlIGBjaHJvbWVgIG5hbWVzcGFjZSkuXG4gKi9cbmNvbnN0IGlzQ2hyb21lID0gdHlwZW9mIGJyb3dzZXIgPT09ICd1bmRlZmluZWQnICYmIHR5cGVvZiBjaHJvbWUgIT09ICd1bmRlZmluZWQnO1xuXG4vKipcbiAqIFdyYXAgYSBDaHJvbWUgY2FsbGJhY2stc3R5bGUgbWV0aG9kIHNvIGl0IHJldHVybnMgYSBQcm9taXNlLlxuICogSWYgdGhlIG1ldGhvZCBhbHJlYWR5IHJldHVybnMgYSBwcm9taXNlIChNVjMpIHdlIGp1c3QgcGFzcyB0aHJvdWdoLlxuICovXG5mdW5jdGlvbiBwcm9taXNpZnkoY29udGV4dCwgbWV0aG9kKSB7XG4gICAgcmV0dXJuICguLi5hcmdzKSA9PiB7XG4gICAgICAgIC8vIE1WMyBDaHJvbWUgQVBJcyByZXR1cm4gcHJvbWlzZXMgd2hlbiBubyBjYWxsYmFjayBpcyBzdXBwbGllZC5cbiAgICAgICAgLy8gV2UgdHJ5IHRoZSBwcm9taXNlIHBhdGggZmlyc3Q7IGlmIHRoZSBydW50aW1lIHNpZ25hbHMgYW4gZXJyb3JcbiAgICAgICAgLy8gdmlhIGNocm9tZS5ydW50aW1lLmxhc3RFcnJvciBpbnNpZGUgYSBjYWxsYmFjayB3ZSBjYXRjaCB0aGF0IHRvby5cbiAgICAgICAgdHJ5IHtcbiAgICAgICAgICAgIGNvbnN0IHJlc3VsdCA9IG1ldGhvZC5hcHBseShjb250ZXh0LCBhcmdzKTtcbiAgICAgICAgICAgIGlmIChyZXN1bHQgJiYgdHlwZW9mIHJlc3VsdC50aGVuID09PSAnZnVuY3Rpb24nKSB7XG4gICAgICAgICAgICAgICAgcmV0dXJuIHJlc3VsdDtcbiAgICAgICAgICAgIH1cbiAgICAgICAgfSBjYXRjaCAoXykge1xuICAgICAgICAgICAgLy8gZmFsbCB0aHJvdWdoIHRvIGNhbGxiYWNrIHdyYXBwaW5nXG4gICAgICAgIH1cblxuICAgICAgICByZXR1cm4gbmV3IFByb21pc2UoKHJlc29sdmUsIHJlamVjdCkgPT4ge1xuICAgICAgICAgICAgbWV0aG9kLmFwcGx5KGNvbnRleHQsIFtcbiAgICAgICAgICAgICAgICAuLi5hcmdzLFxuICAgICAgICAgICAgICAgICguLi5jYkFyZ3MpID0+IHtcbiAgICAgICAgICAgICAgICAgICAgaWYgKF9icm93c2VyLnJ1bnRpbWUgJiYgX2Jyb3dzZXIucnVudGltZS5sYXN0RXJyb3IpIHtcbiAgICAgICAgICAgICAgICAgICAgICAgIHJlamVjdChuZXcgRXJyb3IoX2Jyb3dzZXIucnVudGltZS5sYXN0RXJyb3IubWVzc2FnZSkpO1xuICAgICAgICAgICAgICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgICAgICAgICAgICAgcmVzb2x2ZShjYkFyZ3MubGVuZ3RoIDw9IDEgPyBjYkFyZ3NbMF0gOiBjYkFyZ3MpO1xuICAgICAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgfSxcbiAgICAgICAgICAgIF0pO1xuICAgICAgICB9KTtcbiAgICB9O1xufVxuXG4vLyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cbi8vIEJ1aWxkIHRoZSB1bmlmaWVkIGBhcGlgIG9iamVjdFxuLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG5cbmNvbnN0IGFwaSA9IHt9O1xuXG4vLyAtLS0gcnVudGltZSAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cbmFwaS5ydW50aW1lID0ge1xuICAgIC8qKlxuICAgICAqIHNlbmRNZXNzYWdlIFx1MjAxMyBhbHdheXMgcmV0dXJucyBhIFByb21pc2UuXG4gICAgICovXG4gICAgc2VuZE1lc3NhZ2UoLi4uYXJncykge1xuICAgICAgICBpZiAoIWlzQ2hyb21lKSB7XG4gICAgICAgICAgICByZXR1cm4gX2Jyb3dzZXIucnVudGltZS5zZW5kTWVzc2FnZSguLi5hcmdzKTtcbiAgICAgICAgfVxuICAgICAgICByZXR1cm4gcHJvbWlzaWZ5KF9icm93c2VyLnJ1bnRpbWUsIF9icm93c2VyLnJ1bnRpbWUuc2VuZE1lc3NhZ2UpKC4uLmFyZ3MpO1xuICAgIH0sXG5cbiAgICAvKipcbiAgICAgKiBvbk1lc3NhZ2UgXHUyMDEzIHRoaW4gd3JhcHBlciBzbyBjYWxsZXJzIHVzZSBhIGNvbnNpc3RlbnQgcmVmZXJlbmNlLlxuICAgICAqIFRoZSBsaXN0ZW5lciBzaWduYXR1cmUgaXMgKG1lc3NhZ2UsIHNlbmRlciwgc2VuZFJlc3BvbnNlKS5cbiAgICAgKiBPbiBDaHJvbWUgdGhlIGxpc3RlbmVyIGNhbiByZXR1cm4gYHRydWVgIHRvIGtlZXAgdGhlIGNoYW5uZWwgb3BlbixcbiAgICAgKiBvciByZXR1cm4gYSBQcm9taXNlIChNVjMpLiAgU2FmYXJpIC8gRmlyZWZveCBleHBlY3QgYSBQcm9taXNlIHJldHVybi5cbiAgICAgKi9cbiAgICBvbk1lc3NhZ2U6IF9icm93c2VyLnJ1bnRpbWUub25NZXNzYWdlLFxuXG4gICAgLyoqXG4gICAgICogZ2V0VVJMIFx1MjAxMyBzeW5jaHJvbm91cyBvbiBhbGwgYnJvd3NlcnMuXG4gICAgICovXG4gICAgZ2V0VVJMKHBhdGgpIHtcbiAgICAgICAgcmV0dXJuIF9icm93c2VyLnJ1bnRpbWUuZ2V0VVJMKHBhdGgpO1xuICAgIH0sXG5cbiAgICAvKipcbiAgICAgKiBvcGVuT3B0aW9uc1BhZ2VcbiAgICAgKi9cbiAgICBvcGVuT3B0aW9uc1BhZ2UoKSB7XG4gICAgICAgIGlmICghaXNDaHJvbWUpIHtcbiAgICAgICAgICAgIHJldHVybiBfYnJvd3Nlci5ydW50aW1lLm9wZW5PcHRpb25zUGFnZSgpO1xuICAgICAgICB9XG4gICAgICAgIHJldHVybiBwcm9taXNpZnkoX2Jyb3dzZXIucnVudGltZSwgX2Jyb3dzZXIucnVudGltZS5vcGVuT3B0aW9uc1BhZ2UpKCk7XG4gICAgfSxcblxuICAgIC8qKlxuICAgICAqIEV4cG9zZSB0aGUgaWQgZm9yIGNvbnZlbmllbmNlLlxuICAgICAqL1xuICAgIGdldCBpZCgpIHtcbiAgICAgICAgcmV0dXJuIF9icm93c2VyLnJ1bnRpbWUuaWQ7XG4gICAgfSxcbn07XG5cbi8vIC0tLSBzdG9yYWdlLmxvY2FsIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLVxuYXBpLnN0b3JhZ2UgPSB7XG4gICAgbG9jYWw6IHtcbiAgICAgICAgZ2V0KC4uLmFyZ3MpIHtcbiAgICAgICAgICAgIGlmICghaXNDaHJvbWUpIHtcbiAgICAgICAgICAgICAgICByZXR1cm4gX2Jyb3dzZXIuc3RvcmFnZS5sb2NhbC5nZXQoLi4uYXJncyk7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgICByZXR1cm4gcHJvbWlzaWZ5KF9icm93c2VyLnN0b3JhZ2UubG9jYWwsIF9icm93c2VyLnN0b3JhZ2UubG9jYWwuZ2V0KSguLi5hcmdzKTtcbiAgICAgICAgfSxcbiAgICAgICAgc2V0KC4uLmFyZ3MpIHtcbiAgICAgICAgICAgIGlmICghaXNDaHJvbWUpIHtcbiAgICAgICAgICAgICAgICByZXR1cm4gX2Jyb3dzZXIuc3RvcmFnZS5sb2NhbC5zZXQoLi4uYXJncyk7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgICByZXR1cm4gcHJvbWlzaWZ5KF9icm93c2VyLnN0b3JhZ2UubG9jYWwsIF9icm93c2VyLnN0b3JhZ2UubG9jYWwuc2V0KSguLi5hcmdzKTtcbiAgICAgICAgfSxcbiAgICAgICAgY2xlYXIoLi4uYXJncykge1xuICAgICAgICAgICAgaWYgKCFpc0Nocm9tZSkge1xuICAgICAgICAgICAgICAgIHJldHVybiBfYnJvd3Nlci5zdG9yYWdlLmxvY2FsLmNsZWFyKC4uLmFyZ3MpO1xuICAgICAgICAgICAgfVxuICAgICAgICAgICAgcmV0dXJuIHByb21pc2lmeShfYnJvd3Nlci5zdG9yYWdlLmxvY2FsLCBfYnJvd3Nlci5zdG9yYWdlLmxvY2FsLmNsZWFyKSguLi5hcmdzKTtcbiAgICAgICAgfSxcbiAgICAgICAgcmVtb3ZlKC4uLmFyZ3MpIHtcbiAgICAgICAgICAgIGlmICghaXNDaHJvbWUpIHtcbiAgICAgICAgICAgICAgICByZXR1cm4gX2Jyb3dzZXIuc3RvcmFnZS5sb2NhbC5yZW1vdmUoLi4uYXJncyk7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgICByZXR1cm4gcHJvbWlzaWZ5KF9icm93c2VyLnN0b3JhZ2UubG9jYWwsIF9icm93c2VyLnN0b3JhZ2UubG9jYWwucmVtb3ZlKSguLi5hcmdzKTtcbiAgICAgICAgfSxcbiAgICB9LFxuXG4gICAgLy8gLS0tIHN0b3JhZ2Uuc3luYyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG4gICAgLy8gTnVsbCB3aGVuIHRoZSBicm93c2VyIGRvZXNuJ3Qgc3VwcG9ydCBzeW5jIChvbGRlciBTYWZhcmksIGV0Yy4pXG4gICAgc3luYzogX2Jyb3dzZXIuc3RvcmFnZT8uc3luYyA/IHtcbiAgICAgICAgZ2V0KC4uLmFyZ3MpIHtcbiAgICAgICAgICAgIGlmICghaXNDaHJvbWUpIHtcbiAgICAgICAgICAgICAgICByZXR1cm4gX2Jyb3dzZXIuc3RvcmFnZS5zeW5jLmdldCguLi5hcmdzKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICAgIHJldHVybiBwcm9taXNpZnkoX2Jyb3dzZXIuc3RvcmFnZS5zeW5jLCBfYnJvd3Nlci5zdG9yYWdlLnN5bmMuZ2V0KSguLi5hcmdzKTtcbiAgICAgICAgfSxcbiAgICAgICAgc2V0KC4uLmFyZ3MpIHtcbiAgICAgICAgICAgIGlmICghaXNDaHJvbWUpIHtcbiAgICAgICAgICAgICAgICByZXR1cm4gX2Jyb3dzZXIuc3RvcmFnZS5zeW5jLnNldCguLi5hcmdzKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICAgIHJldHVybiBwcm9taXNpZnkoX2Jyb3dzZXIuc3RvcmFnZS5zeW5jLCBfYnJvd3Nlci5zdG9yYWdlLnN5bmMuc2V0KSguLi5hcmdzKTtcbiAgICAgICAgfSxcbiAgICAgICAgcmVtb3ZlKC4uLmFyZ3MpIHtcbiAgICAgICAgICAgIGlmICghaXNDaHJvbWUpIHtcbiAgICAgICAgICAgICAgICByZXR1cm4gX2Jyb3dzZXIuc3RvcmFnZS5zeW5jLnJlbW92ZSguLi5hcmdzKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICAgIHJldHVybiBwcm9taXNpZnkoX2Jyb3dzZXIuc3RvcmFnZS5zeW5jLCBfYnJvd3Nlci5zdG9yYWdlLnN5bmMucmVtb3ZlKSguLi5hcmdzKTtcbiAgICAgICAgfSxcbiAgICAgICAgY2xlYXIoLi4uYXJncykge1xuICAgICAgICAgICAgaWYgKCFpc0Nocm9tZSkge1xuICAgICAgICAgICAgICAgIHJldHVybiBfYnJvd3Nlci5zdG9yYWdlLnN5bmMuY2xlYXIoLi4uYXJncyk7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgICByZXR1cm4gcHJvbWlzaWZ5KF9icm93c2VyLnN0b3JhZ2Uuc3luYywgX2Jyb3dzZXIuc3RvcmFnZS5zeW5jLmNsZWFyKSguLi5hcmdzKTtcbiAgICAgICAgfSxcbiAgICAgICAgZ2V0Qnl0ZXNJblVzZSguLi5hcmdzKSB7XG4gICAgICAgICAgICBpZiAoIV9icm93c2VyLnN0b3JhZ2Uuc3luYy5nZXRCeXRlc0luVXNlKSB7XG4gICAgICAgICAgICAgICAgLy8gU2FmYXJpIGRvZXNuJ3Qgc3VwcG9ydCBnZXRCeXRlc0luVXNlIFx1MjAxNCByZXR1cm4gMFxuICAgICAgICAgICAgICAgIHJldHVybiBQcm9taXNlLnJlc29sdmUoMCk7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgICBpZiAoIWlzQ2hyb21lKSB7XG4gICAgICAgICAgICAgICAgcmV0dXJuIF9icm93c2VyLnN0b3JhZ2Uuc3luYy5nZXRCeXRlc0luVXNlKC4uLmFyZ3MpO1xuICAgICAgICAgICAgfVxuICAgICAgICAgICAgcmV0dXJuIHByb21pc2lmeShfYnJvd3Nlci5zdG9yYWdlLnN5bmMsIF9icm93c2VyLnN0b3JhZ2Uuc3luYy5nZXRCeXRlc0luVXNlKSguLi5hcmdzKTtcbiAgICAgICAgfSxcbiAgICB9IDogbnVsbCxcblxuICAgIC8vIC0tLSBzdG9yYWdlLm9uQ2hhbmdlZCAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLVxuICAgIG9uQ2hhbmdlZDogX2Jyb3dzZXIuc3RvcmFnZT8ub25DaGFuZ2VkIHx8IG51bGwsXG59O1xuXG4vLyAtLS0gdGFicyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cbmFwaS50YWJzID0ge1xuICAgIGNyZWF0ZSguLi5hcmdzKSB7XG4gICAgICAgIGlmICghaXNDaHJvbWUpIHtcbiAgICAgICAgICAgIHJldHVybiBfYnJvd3Nlci50YWJzLmNyZWF0ZSguLi5hcmdzKTtcbiAgICAgICAgfVxuICAgICAgICByZXR1cm4gcHJvbWlzaWZ5KF9icm93c2VyLnRhYnMsIF9icm93c2VyLnRhYnMuY3JlYXRlKSguLi5hcmdzKTtcbiAgICB9LFxuICAgIHF1ZXJ5KC4uLmFyZ3MpIHtcbiAgICAgICAgaWYgKCFpc0Nocm9tZSkge1xuICAgICAgICAgICAgcmV0dXJuIF9icm93c2VyLnRhYnMucXVlcnkoLi4uYXJncyk7XG4gICAgICAgIH1cbiAgICAgICAgcmV0dXJuIHByb21pc2lmeShfYnJvd3Nlci50YWJzLCBfYnJvd3Nlci50YWJzLnF1ZXJ5KSguLi5hcmdzKTtcbiAgICB9LFxuICAgIHJlbW92ZSguLi5hcmdzKSB7XG4gICAgICAgIGlmICghaXNDaHJvbWUpIHtcbiAgICAgICAgICAgIHJldHVybiBfYnJvd3Nlci50YWJzLnJlbW92ZSguLi5hcmdzKTtcbiAgICAgICAgfVxuICAgICAgICByZXR1cm4gcHJvbWlzaWZ5KF9icm93c2VyLnRhYnMsIF9icm93c2VyLnRhYnMucmVtb3ZlKSguLi5hcmdzKTtcbiAgICB9LFxuICAgIHVwZGF0ZSguLi5hcmdzKSB7XG4gICAgICAgIGlmICghaXNDaHJvbWUpIHtcbiAgICAgICAgICAgIHJldHVybiBfYnJvd3Nlci50YWJzLnVwZGF0ZSguLi5hcmdzKTtcbiAgICAgICAgfVxuICAgICAgICByZXR1cm4gcHJvbWlzaWZ5KF9icm93c2VyLnRhYnMsIF9icm93c2VyLnRhYnMudXBkYXRlKSguLi5hcmdzKTtcbiAgICB9LFxuICAgIGdldCguLi5hcmdzKSB7XG4gICAgICAgIGlmICghaXNDaHJvbWUpIHtcbiAgICAgICAgICAgIHJldHVybiBfYnJvd3Nlci50YWJzLmdldCguLi5hcmdzKTtcbiAgICAgICAgfVxuICAgICAgICByZXR1cm4gcHJvbWlzaWZ5KF9icm93c2VyLnRhYnMsIF9icm93c2VyLnRhYnMuZ2V0KSguLi5hcmdzKTtcbiAgICB9LFxuICAgIGdldEN1cnJlbnQoLi4uYXJncykge1xuICAgICAgICBpZiAoIWlzQ2hyb21lKSB7XG4gICAgICAgICAgICByZXR1cm4gX2Jyb3dzZXIudGFicy5nZXRDdXJyZW50KC4uLmFyZ3MpO1xuICAgICAgICB9XG4gICAgICAgIHJldHVybiBwcm9taXNpZnkoX2Jyb3dzZXIudGFicywgX2Jyb3dzZXIudGFicy5nZXRDdXJyZW50KSguLi5hcmdzKTtcbiAgICB9LFxuICAgIHNlbmRNZXNzYWdlKC4uLmFyZ3MpIHtcbiAgICAgICAgaWYgKCFpc0Nocm9tZSkge1xuICAgICAgICAgICAgcmV0dXJuIF9icm93c2VyLnRhYnMuc2VuZE1lc3NhZ2UoLi4uYXJncyk7XG4gICAgICAgIH1cbiAgICAgICAgcmV0dXJuIHByb21pc2lmeShfYnJvd3Nlci50YWJzLCBfYnJvd3Nlci50YWJzLnNlbmRNZXNzYWdlKSguLi5hcmdzKTtcbiAgICB9LFxufTtcblxuLy8gLS0tIGFsYXJtcyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG4vLyBjaHJvbWUuYWxhcm1zIHN1cnZpdmVzIE1WMyBzZXJ2aWNlLXdvcmtlciBldmljdGlvbjsgc2V0VGltZW91dCBkb2VzIG5vdC5cbmFwaS5hbGFybXMgPSBfYnJvd3Nlci5hbGFybXMgPyB7XG4gICAgY3JlYXRlKC4uLmFyZ3MpIHtcbiAgICAgICAgLy8gYWxhcm1zLmNyZWF0ZSBpcyBzeW5jaHJvbm91cyBvbiBDaHJvbWUsIHJldHVybnMgUHJvbWlzZSBvbiBGaXJlZm94L1NhZmFyaVxuICAgICAgICBjb25zdCByZXN1bHQgPSBfYnJvd3Nlci5hbGFybXMuY3JlYXRlKC4uLmFyZ3MpO1xuICAgICAgICByZXR1cm4gcmVzdWx0ICYmIHR5cGVvZiByZXN1bHQudGhlbiA9PT0gJ2Z1bmN0aW9uJyA/IHJlc3VsdCA6IFByb21pc2UucmVzb2x2ZSgpO1xuICAgIH0sXG4gICAgY2xlYXIoLi4uYXJncykge1xuICAgICAgICBpZiAoIWlzQ2hyb21lKSB7XG4gICAgICAgICAgICByZXR1cm4gX2Jyb3dzZXIuYWxhcm1zLmNsZWFyKC4uLmFyZ3MpO1xuICAgICAgICB9XG4gICAgICAgIHJldHVybiBwcm9taXNpZnkoX2Jyb3dzZXIuYWxhcm1zLCBfYnJvd3Nlci5hbGFybXMuY2xlYXIpKC4uLmFyZ3MpO1xuICAgIH0sXG4gICAgb25BbGFybTogX2Jyb3dzZXIuYWxhcm1zLm9uQWxhcm0sXG59IDogbnVsbDtcblxuZXhwb3J0IHsgYXBpLCBpc0Nocm9tZSB9O1xuIiwgIi8qKlxuICogRW5jcnlwdGlvbiB1dGlsaXRpZXMgZm9yIE5vc3RyS2V5IG1hc3RlciBwYXNzd29yZCBmZWF0dXJlLlxuICpcbiAqIFVzZXMgV2ViIENyeXB0byBBUEkgKGNyeXB0by5zdWJ0bGUpIGV4Y2x1c2l2ZWx5IFx1MjAxNCBubyBleHRlcm5hbCBsaWJyYXJpZXMuXG4gKiAtIFBCS0RGMiB3aXRoIDYwMCwwMDAgaXRlcmF0aW9ucyAoT1dBU1AgMjAyMyByZWNvbW1lbmRhdGlvbilcbiAqIC0gQUVTLTI1Ni1HQ00gZm9yIGF1dGhlbnRpY2F0ZWQgZW5jcnlwdGlvblxuICogLSBSYW5kb20gc2FsdCAoMTYgYnl0ZXMpIGFuZCBJViAoMTIgYnl0ZXMpIHBlciBvcGVyYXRpb25cbiAqIC0gQWxsIGJpbmFyeSBkYXRhIGVuY29kZWQgYXMgYmFzZTY0IGZvciBKU09OIHN0b3JhZ2UgY29tcGF0aWJpbGl0eVxuICovXG5cbmNvbnN0IFBCS0RGMl9JVEVSQVRJT05TID0gNjAwXzAwMDtcbmNvbnN0IFNBTFRfQllURVMgPSAxNjtcbmNvbnN0IElWX0JZVEVTID0gMTI7XG5cbi8vIC0tLSBCYXNlNjQgaGVscGVycyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cblxuZnVuY3Rpb24gYXJyYXlCdWZmZXJUb0Jhc2U2NChidWZmZXIpIHtcbiAgICBjb25zdCBieXRlcyA9IG5ldyBVaW50OEFycmF5KGJ1ZmZlcik7XG4gICAgbGV0IGJpbmFyeSA9ICcnO1xuICAgIGZvciAobGV0IGkgPSAwOyBpIDwgYnl0ZXMubGVuZ3RoOyBpKyspIHtcbiAgICAgICAgYmluYXJ5ICs9IFN0cmluZy5mcm9tQ2hhckNvZGUoYnl0ZXNbaV0pO1xuICAgIH1cbiAgICByZXR1cm4gYnRvYShiaW5hcnkpO1xufVxuXG5mdW5jdGlvbiBiYXNlNjRUb0FycmF5QnVmZmVyKGJhc2U2NCkge1xuICAgIGNvbnN0IGJpbmFyeSA9IGF0b2IoYmFzZTY0KTtcbiAgICBjb25zdCBieXRlcyA9IG5ldyBVaW50OEFycmF5KGJpbmFyeS5sZW5ndGgpO1xuICAgIGZvciAobGV0IGkgPSAwOyBpIDwgYmluYXJ5Lmxlbmd0aDsgaSsrKSB7XG4gICAgICAgIGJ5dGVzW2ldID0gYmluYXJ5LmNoYXJDb2RlQXQoaSk7XG4gICAgfVxuICAgIHJldHVybiBieXRlcy5idWZmZXI7XG59XG5cbi8vIC0tLSBLZXkgZGVyaXZhdGlvbiAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cblxuLyoqXG4gKiBEZXJpdmUgYW4gQUVTLTI1Ni1HQ00gQ3J5cHRvS2V5IGZyb20gYSBwYXNzd29yZCBhbmQgc2FsdCB1c2luZyBQQktERjIuXG4gKlxuICogQHBhcmFtIHtzdHJpbmd9IHBhc3N3b3JkIC0gVGhlIG1hc3RlciBwYXNzd29yZFxuICogQHBhcmFtIHtBcnJheUJ1ZmZlcnxVaW50OEFycmF5fSBzYWx0IC0gMTYtYnl0ZSBzYWx0XG4gKiBAcmV0dXJucyB7UHJvbWlzZTxDcnlwdG9LZXk+fSBBRVMtMjU2LUdDTSBrZXlcbiAqL1xuZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIGRlcml2ZUtleShwYXNzd29yZCwgc2FsdCkge1xuICAgIGNvbnN0IGVuYyA9IG5ldyBUZXh0RW5jb2RlcigpO1xuICAgIGNvbnN0IGtleU1hdGVyaWFsID0gYXdhaXQgY3J5cHRvLnN1YnRsZS5pbXBvcnRLZXkoXG4gICAgICAgICdyYXcnLFxuICAgICAgICBlbmMuZW5jb2RlKHBhc3N3b3JkKSxcbiAgICAgICAgJ1BCS0RGMicsXG4gICAgICAgIGZhbHNlLFxuICAgICAgICBbJ2Rlcml2ZUtleSddXG4gICAgKTtcblxuICAgIHJldHVybiBjcnlwdG8uc3VidGxlLmRlcml2ZUtleShcbiAgICAgICAge1xuICAgICAgICAgICAgbmFtZTogJ1BCS0RGMicsXG4gICAgICAgICAgICBzYWx0OiBzYWx0IGluc3RhbmNlb2YgVWludDhBcnJheSA/IHNhbHQgOiBuZXcgVWludDhBcnJheShzYWx0KSxcbiAgICAgICAgICAgIGl0ZXJhdGlvbnM6IFBCS0RGMl9JVEVSQVRJT05TLFxuICAgICAgICAgICAgaGFzaDogJ1NIQS0yNTYnLFxuICAgICAgICB9LFxuICAgICAgICBrZXlNYXRlcmlhbCxcbiAgICAgICAgeyBuYW1lOiAnQUVTLUdDTScsIGxlbmd0aDogMjU2IH0sXG4gICAgICAgIGZhbHNlLFxuICAgICAgICBbJ2VuY3J5cHQnLCAnZGVjcnlwdCddXG4gICAgKTtcbn1cblxuLy8gLS0tIEVuY3J5cHQgd2l0aCBwcmUtZGVyaXZlZCBrZXkgLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLVxuXG4vKipcbiAqIEVuY3J5cHQgYSBwbGFpbnRleHQgc3RyaW5nIHVzaW5nIGEgcHJlLWRlcml2ZWQgQ3J5cHRvS2V5IGFuZCBpdHMgc2FsdC5cbiAqXG4gKiBUaGlzIGF2b2lkcyBob2xkaW5nIHRoZSByYXcgcGFzc3dvcmQgaW4gbWVtb3J5IFx1MjAxNCB0aGUgY2FsbGVyIGRlcml2ZXMgdGhlXG4gKiBrZXkgb25jZSAodmlhIGRlcml2ZUtleSkgYW5kIHJldXNlcyBpdCBmb3IgdGhlIHNlc3Npb24uICBUaGUgb3V0cHV0XG4gKiBmb3JtYXQgaXMgaWRlbnRpY2FsIHRvIGVuY3J5cHQoKSwgc28gZGVjcnlwdCgpIGNhbiBzdGlsbCBiZSB1c2VkIHdpdGhcbiAqIHRoZSBvcmlnaW5hbCBwYXNzd29yZC5cbiAqXG4gKiBAcGFyYW0ge3N0cmluZ30gcGxhaW50ZXh0ICAgICAgICAgIC0gVGhlIGRhdGEgdG8gZW5jcnlwdFxuICogQHBhcmFtIHtDcnlwdG9LZXl9IGtleSAgICAgICAgICAgICAtIEFFUy0yNTYtR0NNIGtleSBmcm9tIGRlcml2ZUtleSgpXG4gKiBAcGFyYW0ge1VpbnQ4QXJyYXl9IHNhbHQgICAgICAgICAgIC0gVGhlIHNhbHQgdGhhdCB3YXMgdXNlZCB0byBkZXJpdmUgYGtleWBcbiAqIEByZXR1cm5zIHtQcm9taXNlPHN0cmluZz59IEpTT04gc3RyaW5nOiB7IHNhbHQsIGl2LCBjaXBoZXJ0ZXh0IH0gKGFsbCBiYXNlNjQpXG4gKi9cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBlbmNyeXB0V2l0aEtleShwbGFpbnRleHQsIGtleSwgc2FsdCkge1xuICAgIGNvbnN0IGl2ID0gY3J5cHRvLmdldFJhbmRvbVZhbHVlcyhuZXcgVWludDhBcnJheShJVl9CWVRFUykpO1xuICAgIGNvbnN0IGVuYyA9IG5ldyBUZXh0RW5jb2RlcigpO1xuICAgIGNvbnN0IGNpcGhlcnRleHQgPSBhd2FpdCBjcnlwdG8uc3VidGxlLmVuY3J5cHQoXG4gICAgICAgIHsgbmFtZTogJ0FFUy1HQ00nLCBpdiB9LFxuICAgICAgICBrZXksXG4gICAgICAgIGVuYy5lbmNvZGUocGxhaW50ZXh0KVxuICAgICk7XG5cbiAgICByZXR1cm4gSlNPTi5zdHJpbmdpZnkoe1xuICAgICAgICBzYWx0OiBhcnJheUJ1ZmZlclRvQmFzZTY0KHNhbHQpLFxuICAgICAgICBpdjogYXJyYXlCdWZmZXJUb0Jhc2U2NChpdiksXG4gICAgICAgIGNpcGhlcnRleHQ6IGFycmF5QnVmZmVyVG9CYXNlNjQoY2lwaGVydGV4dCksXG4gICAgfSk7XG59XG5cbi8vIC0tLSBFbmNyeXB0IC8gRGVjcnlwdCAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cblxuLyoqXG4gKiBFbmNyeXB0IGEgcGxhaW50ZXh0IHN0cmluZyB3aXRoIGEgcGFzc3dvcmQuXG4gKlxuICogR2VuZXJhdGVzIGEgcmFuZG9tIHNhbHQgKDE2IGJ5dGVzKSBhbmQgSVYgKDEyIGJ5dGVzKSwgZGVyaXZlcyBhblxuICogQUVTLTI1Ni1HQ00ga2V5IHZpYSBQQktERjIsIGFuZCByZXR1cm5zIGEgSlNPTiBzdHJpbmcgY29udGFpbmluZ1xuICogYmFzZTY0LWVuY29kZWQgc2FsdCwgaXYsIGFuZCBjaXBoZXJ0ZXh0LlxuICpcbiAqIEBwYXJhbSB7c3RyaW5nfSBwbGFpbnRleHQgLSBUaGUgZGF0YSB0byBlbmNyeXB0IChlLmcuIGhleCBwcml2YXRlIGtleSlcbiAqIEBwYXJhbSB7c3RyaW5nfSBwYXNzd29yZCAgLSBUaGUgbWFzdGVyIHBhc3N3b3JkXG4gKiBAcmV0dXJucyB7UHJvbWlzZTxzdHJpbmc+fSBKU09OIHN0cmluZzogeyBzYWx0LCBpdiwgY2lwaGVydGV4dCB9IChhbGwgYmFzZTY0KVxuICovXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gZW5jcnlwdChwbGFpbnRleHQsIHBhc3N3b3JkKSB7XG4gICAgY29uc3Qgc2FsdCA9IGNyeXB0by5nZXRSYW5kb21WYWx1ZXMobmV3IFVpbnQ4QXJyYXkoU0FMVF9CWVRFUykpO1xuICAgIGNvbnN0IGl2ID0gY3J5cHRvLmdldFJhbmRvbVZhbHVlcyhuZXcgVWludDhBcnJheShJVl9CWVRFUykpO1xuICAgIGNvbnN0IGtleSA9IGF3YWl0IGRlcml2ZUtleShwYXNzd29yZCwgc2FsdCk7XG5cbiAgICBjb25zdCBlbmMgPSBuZXcgVGV4dEVuY29kZXIoKTtcbiAgICBjb25zdCBjaXBoZXJ0ZXh0ID0gYXdhaXQgY3J5cHRvLnN1YnRsZS5lbmNyeXB0KFxuICAgICAgICB7IG5hbWU6ICdBRVMtR0NNJywgaXYgfSxcbiAgICAgICAga2V5LFxuICAgICAgICBlbmMuZW5jb2RlKHBsYWludGV4dClcbiAgICApO1xuXG4gICAgcmV0dXJuIEpTT04uc3RyaW5naWZ5KHtcbiAgICAgICAgc2FsdDogYXJyYXlCdWZmZXJUb0Jhc2U2NChzYWx0KSxcbiAgICAgICAgaXY6IGFycmF5QnVmZmVyVG9CYXNlNjQoaXYpLFxuICAgICAgICBjaXBoZXJ0ZXh0OiBhcnJheUJ1ZmZlclRvQmFzZTY0KGNpcGhlcnRleHQpLFxuICAgIH0pO1xufVxuXG4vKipcbiAqIERlY3J5cHQgZGF0YSB0aGF0IHdhcyBlbmNyeXB0ZWQgd2l0aCBgZW5jcnlwdCgpYC5cbiAqXG4gKiBAcGFyYW0ge3N0cmluZ30gZW5jcnlwdGVkRGF0YSAtIEpTT04gc3RyaW5nIGZyb20gZW5jcnlwdCgpXG4gKiBAcGFyYW0ge3N0cmluZ30gcGFzc3dvcmQgICAgICAtIFRoZSBtYXN0ZXIgcGFzc3dvcmRcbiAqIEByZXR1cm5zIHtQcm9taXNlPHN0cmluZz59IFRoZSBvcmlnaW5hbCBwbGFpbnRleHRcbiAqIEB0aHJvd3Mge0Vycm9yfSBJZiB0aGUgcGFzc3dvcmQgaXMgd3Jvbmcgb3IgZGF0YSBpcyB0YW1wZXJlZCB3aXRoXG4gKi9cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBkZWNyeXB0KGVuY3J5cHRlZERhdGEsIHBhc3N3b3JkKSB7XG4gICAgY29uc3QgeyBzYWx0LCBpdiwgY2lwaGVydGV4dCB9ID0gSlNPTi5wYXJzZShlbmNyeXB0ZWREYXRhKTtcblxuICAgIGNvbnN0IHNhbHRCdWYgPSBuZXcgVWludDhBcnJheShiYXNlNjRUb0FycmF5QnVmZmVyKHNhbHQpKTtcbiAgICBjb25zdCBpdkJ1ZiA9IG5ldyBVaW50OEFycmF5KGJhc2U2NFRvQXJyYXlCdWZmZXIoaXYpKTtcbiAgICBjb25zdCBjdEJ1ZiA9IGJhc2U2NFRvQXJyYXlCdWZmZXIoY2lwaGVydGV4dCk7XG5cbiAgICBjb25zdCBrZXkgPSBhd2FpdCBkZXJpdmVLZXkocGFzc3dvcmQsIHNhbHRCdWYpO1xuXG4gICAgY29uc3QgcGxhaW5CdWYgPSBhd2FpdCBjcnlwdG8uc3VidGxlLmRlY3J5cHQoXG4gICAgICAgIHsgbmFtZTogJ0FFUy1HQ00nLCBpdjogaXZCdWYgfSxcbiAgICAgICAga2V5LFxuICAgICAgICBjdEJ1ZlxuICAgICk7XG5cbiAgICBjb25zdCBkZWMgPSBuZXcgVGV4dERlY29kZXIoKTtcbiAgICByZXR1cm4gZGVjLmRlY29kZShwbGFpbkJ1Zik7XG59XG5cbi8vIC0tLSBQYXNzd29yZCBoYXNoaW5nIChmb3IgdmVyaWZpY2F0aW9uKSAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cblxuLyoqXG4gKiBIYXNoIGEgcGFzc3dvcmQgd2l0aCBQQktERjIgZm9yIHZlcmlmaWNhdGlvbiBwdXJwb3Nlcy5cbiAqXG4gKiBUaGlzIHByb2R1Y2VzIGEgc2VwYXJhdGUgaGFzaCAobm90IHRoZSBlbmNyeXB0aW9uIGtleSkgdGhhdCBjYW4gYmUgc3RvcmVkXG4gKiB0byB2ZXJpZnkgdGhlIHBhc3N3b3JkIHdpdGhvdXQgbmVlZGluZyB0byBhdHRlbXB0IGRlY3J5cHRpb24uXG4gKlxuICogQHBhcmFtIHtzdHJpbmd9IHBhc3N3b3JkIC0gVGhlIG1hc3RlciBwYXNzd29yZFxuICogQHBhcmFtIHtVaW50OEFycmF5fSBbc2FsdF0gLSBPcHRpb25hbCBzYWx0OyBnZW5lcmF0ZWQgaWYgb21pdHRlZFxuICogQHJldHVybnMge1Byb21pc2U8eyBoYXNoOiBzdHJpbmcsIHNhbHQ6IHN0cmluZyB9Pn0gYmFzZTY0LWVuY29kZWQgaGFzaCBhbmQgc2FsdFxuICovXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gaGFzaFBhc3N3b3JkKHBhc3N3b3JkLCBzYWx0KSB7XG4gICAgaWYgKCFzYWx0KSB7XG4gICAgICAgIHNhbHQgPSBjcnlwdG8uZ2V0UmFuZG9tVmFsdWVzKG5ldyBVaW50OEFycmF5KFNBTFRfQllURVMpKTtcbiAgICB9IGVsc2UgaWYgKHR5cGVvZiBzYWx0ID09PSAnc3RyaW5nJykge1xuICAgICAgICBzYWx0ID0gbmV3IFVpbnQ4QXJyYXkoYmFzZTY0VG9BcnJheUJ1ZmZlcihzYWx0KSk7XG4gICAgfVxuXG4gICAgY29uc3QgZW5jID0gbmV3IFRleHRFbmNvZGVyKCk7XG4gICAgY29uc3Qga2V5TWF0ZXJpYWwgPSBhd2FpdCBjcnlwdG8uc3VidGxlLmltcG9ydEtleShcbiAgICAgICAgJ3JhdycsXG4gICAgICAgIGVuYy5lbmNvZGUocGFzc3dvcmQpLFxuICAgICAgICAnUEJLREYyJyxcbiAgICAgICAgZmFsc2UsXG4gICAgICAgIFsnZGVyaXZlQml0cyddXG4gICAgKTtcblxuICAgIGNvbnN0IGhhc2hCaXRzID0gYXdhaXQgY3J5cHRvLnN1YnRsZS5kZXJpdmVCaXRzKFxuICAgICAgICB7XG4gICAgICAgICAgICBuYW1lOiAnUEJLREYyJyxcbiAgICAgICAgICAgIHNhbHQsXG4gICAgICAgICAgICBpdGVyYXRpb25zOiBQQktERjJfSVRFUkFUSU9OUyxcbiAgICAgICAgICAgIGhhc2g6ICdTSEEtMjU2JyxcbiAgICAgICAgfSxcbiAgICAgICAga2V5TWF0ZXJpYWwsXG4gICAgICAgIDI1NlxuICAgICk7XG5cbiAgICByZXR1cm4ge1xuICAgICAgICBoYXNoOiBhcnJheUJ1ZmZlclRvQmFzZTY0KGhhc2hCaXRzKSxcbiAgICAgICAgc2FsdDogYXJyYXlCdWZmZXJUb0Jhc2U2NChzYWx0KSxcbiAgICB9O1xufVxuXG4vKipcbiAqIFZlcmlmeSBhIHBhc3N3b3JkIGFnYWluc3QgYSBzdG9yZWQgaGFzaC5cbiAqXG4gKiBAcGFyYW0ge3N0cmluZ30gcGFzc3dvcmQgICAtIFRoZSBwYXNzd29yZCB0byB2ZXJpZnlcbiAqIEBwYXJhbSB7c3RyaW5nfSBzdG9yZWRIYXNoIC0gYmFzZTY0LWVuY29kZWQgaGFzaCBmcm9tIGhhc2hQYXNzd29yZCgpXG4gKiBAcGFyYW0ge3N0cmluZ30gc3RvcmVkU2FsdCAtIGJhc2U2NC1lbmNvZGVkIHNhbHQgZnJvbSBoYXNoUGFzc3dvcmQoKVxuICogQHJldHVybnMge1Byb21pc2U8Ym9vbGVhbj59IFRydWUgaWYgdGhlIHBhc3N3b3JkIG1hdGNoZXNcbiAqL1xuZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIHZlcmlmeVBhc3N3b3JkKHBhc3N3b3JkLCBzdG9yZWRIYXNoLCBzdG9yZWRTYWx0KSB7XG4gICAgY29uc3QgeyBoYXNoIH0gPSBhd2FpdCBoYXNoUGFzc3dvcmQocGFzc3dvcmQsIHN0b3JlZFNhbHQpO1xuICAgIHJldHVybiBoYXNoID09PSBzdG9yZWRIYXNoO1xufVxuIiwgImltcG9ydCB7IG9wZW5EQiB9IGZyb20gJ2lkYic7XG5cbmFzeW5jIGZ1bmN0aW9uIG9wZW5FdmVudHNEYigpIHtcbiAgICByZXR1cm4gYXdhaXQgb3BlbkRCKCdldmVudHMnLCAxLCB7XG4gICAgICAgIHVwZ3JhZGUoZGIpIHtcbiAgICAgICAgICAgIGNvbnN0IGV2ZW50cyA9IGRiLmNyZWF0ZU9iamVjdFN0b3JlKCdldmVudHMnLCB7XG4gICAgICAgICAgICAgICAga2V5UGF0aDogJ2V2ZW50LmlkJyxcbiAgICAgICAgICAgIH0pO1xuICAgICAgICAgICAgZXZlbnRzLmNyZWF0ZUluZGV4KCdwdWJrZXknLCAnZXZlbnQucHVia2V5Jyk7XG4gICAgICAgICAgICBldmVudHMuY3JlYXRlSW5kZXgoJ2NyZWF0ZWRfYXQnLCAnZXZlbnQuY3JlYXRlZF9hdCcpO1xuICAgICAgICAgICAgZXZlbnRzLmNyZWF0ZUluZGV4KCdraW5kJywgJ2V2ZW50LmtpbmQnKTtcbiAgICAgICAgICAgIGV2ZW50cy5jcmVhdGVJbmRleCgnaG9zdCcsICdtZXRhZGF0YS5ob3N0Jyk7XG4gICAgICAgIH0sXG4gICAgfSk7XG59XG5cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBzYXZlRXZlbnQoZXZlbnQpIHtcbiAgICBsZXQgZGIgPSBhd2FpdCBvcGVuRXZlbnRzRGIoKTtcbiAgICByZXR1cm4gZGIucHV0KCdldmVudHMnLCBldmVudCk7XG59XG5cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBzb3J0QnlJbmRleChpbmRleCwgcXVlcnksIGFzYywgbWF4KSB7XG4gICAgbGV0IGRiID0gYXdhaXQgb3BlbkV2ZW50c0RiKCk7XG4gICAgbGV0IGV2ZW50cyA9IFtdO1xuICAgIGxldCBjdXJzb3IgPSBhd2FpdCBkYlxuICAgICAgICAudHJhbnNhY3Rpb24oJ2V2ZW50cycpXG4gICAgICAgIC5zdG9yZS5pbmRleChpbmRleClcbiAgICAgICAgLm9wZW5DdXJzb3IocXVlcnksIGFzYyA/ICduZXh0JyA6ICdwcmV2Jyk7XG4gICAgd2hpbGUgKGN1cnNvcikge1xuICAgICAgICBldmVudHMucHVzaChjdXJzb3IudmFsdWUpO1xuICAgICAgICBpZiAoZXZlbnRzLmxlbmd0aCA+PSBtYXgpIHtcbiAgICAgICAgICAgIGJyZWFrO1xuICAgICAgICB9XG4gICAgICAgIGN1cnNvciA9IGF3YWl0IGN1cnNvci5jb250aW51ZSgpO1xuICAgIH1cbiAgICByZXR1cm4gZXZlbnRzO1xufVxuXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gZ2V0SG9zdHMoKSB7XG4gICAgbGV0IGRiID0gYXdhaXQgb3BlbkV2ZW50c0RiKCk7XG4gICAgbGV0IGhvc3RzID0gbmV3IFNldCgpO1xuICAgIGxldCBjdXJzb3IgPSBhd2FpdCBkYi50cmFuc2FjdGlvbignZXZlbnRzJykuc3RvcmUub3BlbkN1cnNvcigpO1xuICAgIHdoaWxlIChjdXJzb3IpIHtcbiAgICAgICAgaG9zdHMuYWRkKGN1cnNvci52YWx1ZS5tZXRhZGF0YS5ob3N0KTtcbiAgICAgICAgY3Vyc29yID0gYXdhaXQgY3Vyc29yLmNvbnRpbnVlKCk7XG4gICAgfVxuICAgIHJldHVybiBbLi4uaG9zdHNdO1xufVxuXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gZG93bmxvYWRBbGxDb250ZW50cygpIHtcbiAgICBsZXQgZGIgPSBhd2FpdCBvcGVuRXZlbnRzRGIoKTtcbiAgICBsZXQgZXZlbnRzID0gW107XG4gICAgbGV0IGN1cnNvciA9IGF3YWl0IGRiLnRyYW5zYWN0aW9uKCdldmVudHMnKS5zdG9yZS5vcGVuQ3Vyc29yKCk7XG4gICAgd2hpbGUgKGN1cnNvcikge1xuICAgICAgICBldmVudHMucHVzaChjdXJzb3IudmFsdWUuZXZlbnQpO1xuICAgICAgICBjdXJzb3IgPSBhd2FpdCBjdXJzb3IuY29udGludWUoKTtcbiAgICB9XG4gICAgZXZlbnRzID0gZXZlbnRzLm1hcChlID0+IEpTT04uc3RyaW5naWZ5KGUpKTtcbiAgICBldmVudHMgPSBldmVudHMuam9pbignXFxuJyk7XG4gICAgY29uc29sZS5sb2coZXZlbnRzKTtcblxuICAgIGNvbnN0IGZpbGUgPSBuZXcgRmlsZShbZXZlbnRzXSwgJ2V2ZW50cy5qc29ubCcsIHtcbiAgICAgICAgdHlwZTogJ2FwcGxpY2F0aW9uL29jdGV0LXN0cmVhbScsXG4gICAgfSk7XG5cbiAgICBjb25zdCBibG9iID0gbmV3IEJsb2IoW2V2ZW50c10sIHsgdHlwZTogJ3BsYWluL3RleHQnIH0pO1xuXG4gICAgcmV0dXJuIGJsb2I7XG59XG4iLCAiY29uc3QgaW5zdGFuY2VPZkFueSA9IChvYmplY3QsIGNvbnN0cnVjdG9ycykgPT4gY29uc3RydWN0b3JzLnNvbWUoKGMpID0+IG9iamVjdCBpbnN0YW5jZW9mIGMpO1xuXG5sZXQgaWRiUHJveHlhYmxlVHlwZXM7XG5sZXQgY3Vyc29yQWR2YW5jZU1ldGhvZHM7XG4vLyBUaGlzIGlzIGEgZnVuY3Rpb24gdG8gcHJldmVudCBpdCB0aHJvd2luZyB1cCBpbiBub2RlIGVudmlyb25tZW50cy5cbmZ1bmN0aW9uIGdldElkYlByb3h5YWJsZVR5cGVzKCkge1xuICAgIHJldHVybiAoaWRiUHJveHlhYmxlVHlwZXMgfHxcbiAgICAgICAgKGlkYlByb3h5YWJsZVR5cGVzID0gW1xuICAgICAgICAgICAgSURCRGF0YWJhc2UsXG4gICAgICAgICAgICBJREJPYmplY3RTdG9yZSxcbiAgICAgICAgICAgIElEQkluZGV4LFxuICAgICAgICAgICAgSURCQ3Vyc29yLFxuICAgICAgICAgICAgSURCVHJhbnNhY3Rpb24sXG4gICAgICAgIF0pKTtcbn1cbi8vIFRoaXMgaXMgYSBmdW5jdGlvbiB0byBwcmV2ZW50IGl0IHRocm93aW5nIHVwIGluIG5vZGUgZW52aXJvbm1lbnRzLlxuZnVuY3Rpb24gZ2V0Q3Vyc29yQWR2YW5jZU1ldGhvZHMoKSB7XG4gICAgcmV0dXJuIChjdXJzb3JBZHZhbmNlTWV0aG9kcyB8fFxuICAgICAgICAoY3Vyc29yQWR2YW5jZU1ldGhvZHMgPSBbXG4gICAgICAgICAgICBJREJDdXJzb3IucHJvdG90eXBlLmFkdmFuY2UsXG4gICAgICAgICAgICBJREJDdXJzb3IucHJvdG90eXBlLmNvbnRpbnVlLFxuICAgICAgICAgICAgSURCQ3Vyc29yLnByb3RvdHlwZS5jb250aW51ZVByaW1hcnlLZXksXG4gICAgICAgIF0pKTtcbn1cbmNvbnN0IHRyYW5zYWN0aW9uRG9uZU1hcCA9IG5ldyBXZWFrTWFwKCk7XG5jb25zdCB0cmFuc2Zvcm1DYWNoZSA9IG5ldyBXZWFrTWFwKCk7XG5jb25zdCByZXZlcnNlVHJhbnNmb3JtQ2FjaGUgPSBuZXcgV2Vha01hcCgpO1xuZnVuY3Rpb24gcHJvbWlzaWZ5UmVxdWVzdChyZXF1ZXN0KSB7XG4gICAgY29uc3QgcHJvbWlzZSA9IG5ldyBQcm9taXNlKChyZXNvbHZlLCByZWplY3QpID0+IHtcbiAgICAgICAgY29uc3QgdW5saXN0ZW4gPSAoKSA9PiB7XG4gICAgICAgICAgICByZXF1ZXN0LnJlbW92ZUV2ZW50TGlzdGVuZXIoJ3N1Y2Nlc3MnLCBzdWNjZXNzKTtcbiAgICAgICAgICAgIHJlcXVlc3QucmVtb3ZlRXZlbnRMaXN0ZW5lcignZXJyb3InLCBlcnJvcik7XG4gICAgICAgIH07XG4gICAgICAgIGNvbnN0IHN1Y2Nlc3MgPSAoKSA9PiB7XG4gICAgICAgICAgICByZXNvbHZlKHdyYXAocmVxdWVzdC5yZXN1bHQpKTtcbiAgICAgICAgICAgIHVubGlzdGVuKCk7XG4gICAgICAgIH07XG4gICAgICAgIGNvbnN0IGVycm9yID0gKCkgPT4ge1xuICAgICAgICAgICAgcmVqZWN0KHJlcXVlc3QuZXJyb3IpO1xuICAgICAgICAgICAgdW5saXN0ZW4oKTtcbiAgICAgICAgfTtcbiAgICAgICAgcmVxdWVzdC5hZGRFdmVudExpc3RlbmVyKCdzdWNjZXNzJywgc3VjY2Vzcyk7XG4gICAgICAgIHJlcXVlc3QuYWRkRXZlbnRMaXN0ZW5lcignZXJyb3InLCBlcnJvcik7XG4gICAgfSk7XG4gICAgLy8gVGhpcyBtYXBwaW5nIGV4aXN0cyBpbiByZXZlcnNlVHJhbnNmb3JtQ2FjaGUgYnV0IGRvZXNuJ3QgZXhpc3QgaW4gdHJhbnNmb3JtQ2FjaGUuIFRoaXNcbiAgICAvLyBpcyBiZWNhdXNlIHdlIGNyZWF0ZSBtYW55IHByb21pc2VzIGZyb20gYSBzaW5nbGUgSURCUmVxdWVzdC5cbiAgICByZXZlcnNlVHJhbnNmb3JtQ2FjaGUuc2V0KHByb21pc2UsIHJlcXVlc3QpO1xuICAgIHJldHVybiBwcm9taXNlO1xufVxuZnVuY3Rpb24gY2FjaGVEb25lUHJvbWlzZUZvclRyYW5zYWN0aW9uKHR4KSB7XG4gICAgLy8gRWFybHkgYmFpbCBpZiB3ZSd2ZSBhbHJlYWR5IGNyZWF0ZWQgYSBkb25lIHByb21pc2UgZm9yIHRoaXMgdHJhbnNhY3Rpb24uXG4gICAgaWYgKHRyYW5zYWN0aW9uRG9uZU1hcC5oYXModHgpKVxuICAgICAgICByZXR1cm47XG4gICAgY29uc3QgZG9uZSA9IG5ldyBQcm9taXNlKChyZXNvbHZlLCByZWplY3QpID0+IHtcbiAgICAgICAgY29uc3QgdW5saXN0ZW4gPSAoKSA9PiB7XG4gICAgICAgICAgICB0eC5yZW1vdmVFdmVudExpc3RlbmVyKCdjb21wbGV0ZScsIGNvbXBsZXRlKTtcbiAgICAgICAgICAgIHR4LnJlbW92ZUV2ZW50TGlzdGVuZXIoJ2Vycm9yJywgZXJyb3IpO1xuICAgICAgICAgICAgdHgucmVtb3ZlRXZlbnRMaXN0ZW5lcignYWJvcnQnLCBlcnJvcik7XG4gICAgICAgIH07XG4gICAgICAgIGNvbnN0IGNvbXBsZXRlID0gKCkgPT4ge1xuICAgICAgICAgICAgcmVzb2x2ZSgpO1xuICAgICAgICAgICAgdW5saXN0ZW4oKTtcbiAgICAgICAgfTtcbiAgICAgICAgY29uc3QgZXJyb3IgPSAoKSA9PiB7XG4gICAgICAgICAgICByZWplY3QodHguZXJyb3IgfHwgbmV3IERPTUV4Y2VwdGlvbignQWJvcnRFcnJvcicsICdBYm9ydEVycm9yJykpO1xuICAgICAgICAgICAgdW5saXN0ZW4oKTtcbiAgICAgICAgfTtcbiAgICAgICAgdHguYWRkRXZlbnRMaXN0ZW5lcignY29tcGxldGUnLCBjb21wbGV0ZSk7XG4gICAgICAgIHR4LmFkZEV2ZW50TGlzdGVuZXIoJ2Vycm9yJywgZXJyb3IpO1xuICAgICAgICB0eC5hZGRFdmVudExpc3RlbmVyKCdhYm9ydCcsIGVycm9yKTtcbiAgICB9KTtcbiAgICAvLyBDYWNoZSBpdCBmb3IgbGF0ZXIgcmV0cmlldmFsLlxuICAgIHRyYW5zYWN0aW9uRG9uZU1hcC5zZXQodHgsIGRvbmUpO1xufVxubGV0IGlkYlByb3h5VHJhcHMgPSB7XG4gICAgZ2V0KHRhcmdldCwgcHJvcCwgcmVjZWl2ZXIpIHtcbiAgICAgICAgaWYgKHRhcmdldCBpbnN0YW5jZW9mIElEQlRyYW5zYWN0aW9uKSB7XG4gICAgICAgICAgICAvLyBTcGVjaWFsIGhhbmRsaW5nIGZvciB0cmFuc2FjdGlvbi5kb25lLlxuICAgICAgICAgICAgaWYgKHByb3AgPT09ICdkb25lJylcbiAgICAgICAgICAgICAgICByZXR1cm4gdHJhbnNhY3Rpb25Eb25lTWFwLmdldCh0YXJnZXQpO1xuICAgICAgICAgICAgLy8gTWFrZSB0eC5zdG9yZSByZXR1cm4gdGhlIG9ubHkgc3RvcmUgaW4gdGhlIHRyYW5zYWN0aW9uLCBvciB1bmRlZmluZWQgaWYgdGhlcmUgYXJlIG1hbnkuXG4gICAgICAgICAgICBpZiAocHJvcCA9PT0gJ3N0b3JlJykge1xuICAgICAgICAgICAgICAgIHJldHVybiByZWNlaXZlci5vYmplY3RTdG9yZU5hbWVzWzFdXG4gICAgICAgICAgICAgICAgICAgID8gdW5kZWZpbmVkXG4gICAgICAgICAgICAgICAgICAgIDogcmVjZWl2ZXIub2JqZWN0U3RvcmUocmVjZWl2ZXIub2JqZWN0U3RvcmVOYW1lc1swXSk7XG4gICAgICAgICAgICB9XG4gICAgICAgIH1cbiAgICAgICAgLy8gRWxzZSB0cmFuc2Zvcm0gd2hhdGV2ZXIgd2UgZ2V0IGJhY2suXG4gICAgICAgIHJldHVybiB3cmFwKHRhcmdldFtwcm9wXSk7XG4gICAgfSxcbiAgICBzZXQodGFyZ2V0LCBwcm9wLCB2YWx1ZSkge1xuICAgICAgICB0YXJnZXRbcHJvcF0gPSB2YWx1ZTtcbiAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgfSxcbiAgICBoYXModGFyZ2V0LCBwcm9wKSB7XG4gICAgICAgIGlmICh0YXJnZXQgaW5zdGFuY2VvZiBJREJUcmFuc2FjdGlvbiAmJlxuICAgICAgICAgICAgKHByb3AgPT09ICdkb25lJyB8fCBwcm9wID09PSAnc3RvcmUnKSkge1xuICAgICAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgICAgIH1cbiAgICAgICAgcmV0dXJuIHByb3AgaW4gdGFyZ2V0O1xuICAgIH0sXG59O1xuZnVuY3Rpb24gcmVwbGFjZVRyYXBzKGNhbGxiYWNrKSB7XG4gICAgaWRiUHJveHlUcmFwcyA9IGNhbGxiYWNrKGlkYlByb3h5VHJhcHMpO1xufVxuZnVuY3Rpb24gd3JhcEZ1bmN0aW9uKGZ1bmMpIHtcbiAgICAvLyBEdWUgdG8gZXhwZWN0ZWQgb2JqZWN0IGVxdWFsaXR5ICh3aGljaCBpcyBlbmZvcmNlZCBieSB0aGUgY2FjaGluZyBpbiBgd3JhcGApLCB3ZVxuICAgIC8vIG9ubHkgY3JlYXRlIG9uZSBuZXcgZnVuYyBwZXIgZnVuYy5cbiAgICAvLyBDdXJzb3IgbWV0aG9kcyBhcmUgc3BlY2lhbCwgYXMgdGhlIGJlaGF2aW91ciBpcyBhIGxpdHRsZSBtb3JlIGRpZmZlcmVudCB0byBzdGFuZGFyZCBJREIuIEluXG4gICAgLy8gSURCLCB5b3UgYWR2YW5jZSB0aGUgY3Vyc29yIGFuZCB3YWl0IGZvciBhIG5ldyAnc3VjY2Vzcycgb24gdGhlIElEQlJlcXVlc3QgdGhhdCBnYXZlIHlvdSB0aGVcbiAgICAvLyBjdXJzb3IuIEl0J3Mga2luZGEgbGlrZSBhIHByb21pc2UgdGhhdCBjYW4gcmVzb2x2ZSB3aXRoIG1hbnkgdmFsdWVzLiBUaGF0IGRvZXNuJ3QgbWFrZSBzZW5zZVxuICAgIC8vIHdpdGggcmVhbCBwcm9taXNlcywgc28gZWFjaCBhZHZhbmNlIG1ldGhvZHMgcmV0dXJucyBhIG5ldyBwcm9taXNlIGZvciB0aGUgY3Vyc29yIG9iamVjdCwgb3JcbiAgICAvLyB1bmRlZmluZWQgaWYgdGhlIGVuZCBvZiB0aGUgY3Vyc29yIGhhcyBiZWVuIHJlYWNoZWQuXG4gICAgaWYgKGdldEN1cnNvckFkdmFuY2VNZXRob2RzKCkuaW5jbHVkZXMoZnVuYykpIHtcbiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uICguLi5hcmdzKSB7XG4gICAgICAgICAgICAvLyBDYWxsaW5nIHRoZSBvcmlnaW5hbCBmdW5jdGlvbiB3aXRoIHRoZSBwcm94eSBhcyAndGhpcycgY2F1c2VzIElMTEVHQUwgSU5WT0NBVElPTiwgc28gd2UgdXNlXG4gICAgICAgICAgICAvLyB0aGUgb3JpZ2luYWwgb2JqZWN0LlxuICAgICAgICAgICAgZnVuYy5hcHBseSh1bndyYXAodGhpcyksIGFyZ3MpO1xuICAgICAgICAgICAgcmV0dXJuIHdyYXAodGhpcy5yZXF1ZXN0KTtcbiAgICAgICAgfTtcbiAgICB9XG4gICAgcmV0dXJuIGZ1bmN0aW9uICguLi5hcmdzKSB7XG4gICAgICAgIC8vIENhbGxpbmcgdGhlIG9yaWdpbmFsIGZ1bmN0aW9uIHdpdGggdGhlIHByb3h5IGFzICd0aGlzJyBjYXVzZXMgSUxMRUdBTCBJTlZPQ0FUSU9OLCBzbyB3ZSB1c2VcbiAgICAgICAgLy8gdGhlIG9yaWdpbmFsIG9iamVjdC5cbiAgICAgICAgcmV0dXJuIHdyYXAoZnVuYy5hcHBseSh1bndyYXAodGhpcyksIGFyZ3MpKTtcbiAgICB9O1xufVxuZnVuY3Rpb24gdHJhbnNmb3JtQ2FjaGFibGVWYWx1ZSh2YWx1ZSkge1xuICAgIGlmICh0eXBlb2YgdmFsdWUgPT09ICdmdW5jdGlvbicpXG4gICAgICAgIHJldHVybiB3cmFwRnVuY3Rpb24odmFsdWUpO1xuICAgIC8vIFRoaXMgZG9lc24ndCByZXR1cm4sIGl0IGp1c3QgY3JlYXRlcyBhICdkb25lJyBwcm9taXNlIGZvciB0aGUgdHJhbnNhY3Rpb24sXG4gICAgLy8gd2hpY2ggaXMgbGF0ZXIgcmV0dXJuZWQgZm9yIHRyYW5zYWN0aW9uLmRvbmUgKHNlZSBpZGJPYmplY3RIYW5kbGVyKS5cbiAgICBpZiAodmFsdWUgaW5zdGFuY2VvZiBJREJUcmFuc2FjdGlvbilcbiAgICAgICAgY2FjaGVEb25lUHJvbWlzZUZvclRyYW5zYWN0aW9uKHZhbHVlKTtcbiAgICBpZiAoaW5zdGFuY2VPZkFueSh2YWx1ZSwgZ2V0SWRiUHJveHlhYmxlVHlwZXMoKSkpXG4gICAgICAgIHJldHVybiBuZXcgUHJveHkodmFsdWUsIGlkYlByb3h5VHJhcHMpO1xuICAgIC8vIFJldHVybiB0aGUgc2FtZSB2YWx1ZSBiYWNrIGlmIHdlJ3JlIG5vdCBnb2luZyB0byB0cmFuc2Zvcm0gaXQuXG4gICAgcmV0dXJuIHZhbHVlO1xufVxuZnVuY3Rpb24gd3JhcCh2YWx1ZSkge1xuICAgIC8vIFdlIHNvbWV0aW1lcyBnZW5lcmF0ZSBtdWx0aXBsZSBwcm9taXNlcyBmcm9tIGEgc2luZ2xlIElEQlJlcXVlc3QgKGVnIHdoZW4gY3Vyc29yaW5nKSwgYmVjYXVzZVxuICAgIC8vIElEQiBpcyB3ZWlyZCBhbmQgYSBzaW5nbGUgSURCUmVxdWVzdCBjYW4geWllbGQgbWFueSByZXNwb25zZXMsIHNvIHRoZXNlIGNhbid0IGJlIGNhY2hlZC5cbiAgICBpZiAodmFsdWUgaW5zdGFuY2VvZiBJREJSZXF1ZXN0KVxuICAgICAgICByZXR1cm4gcHJvbWlzaWZ5UmVxdWVzdCh2YWx1ZSk7XG4gICAgLy8gSWYgd2UndmUgYWxyZWFkeSB0cmFuc2Zvcm1lZCB0aGlzIHZhbHVlIGJlZm9yZSwgcmV1c2UgdGhlIHRyYW5zZm9ybWVkIHZhbHVlLlxuICAgIC8vIFRoaXMgaXMgZmFzdGVyLCBidXQgaXQgYWxzbyBwcm92aWRlcyBvYmplY3QgZXF1YWxpdHkuXG4gICAgaWYgKHRyYW5zZm9ybUNhY2hlLmhhcyh2YWx1ZSkpXG4gICAgICAgIHJldHVybiB0cmFuc2Zvcm1DYWNoZS5nZXQodmFsdWUpO1xuICAgIGNvbnN0IG5ld1ZhbHVlID0gdHJhbnNmb3JtQ2FjaGFibGVWYWx1ZSh2YWx1ZSk7XG4gICAgLy8gTm90IGFsbCB0eXBlcyBhcmUgdHJhbnNmb3JtZWQuXG4gICAgLy8gVGhlc2UgbWF5IGJlIHByaW1pdGl2ZSB0eXBlcywgc28gdGhleSBjYW4ndCBiZSBXZWFrTWFwIGtleXMuXG4gICAgaWYgKG5ld1ZhbHVlICE9PSB2YWx1ZSkge1xuICAgICAgICB0cmFuc2Zvcm1DYWNoZS5zZXQodmFsdWUsIG5ld1ZhbHVlKTtcbiAgICAgICAgcmV2ZXJzZVRyYW5zZm9ybUNhY2hlLnNldChuZXdWYWx1ZSwgdmFsdWUpO1xuICAgIH1cbiAgICByZXR1cm4gbmV3VmFsdWU7XG59XG5jb25zdCB1bndyYXAgPSAodmFsdWUpID0+IHJldmVyc2VUcmFuc2Zvcm1DYWNoZS5nZXQodmFsdWUpO1xuXG4vKipcbiAqIE9wZW4gYSBkYXRhYmFzZS5cbiAqXG4gKiBAcGFyYW0gbmFtZSBOYW1lIG9mIHRoZSBkYXRhYmFzZS5cbiAqIEBwYXJhbSB2ZXJzaW9uIFNjaGVtYSB2ZXJzaW9uLlxuICogQHBhcmFtIGNhbGxiYWNrcyBBZGRpdGlvbmFsIGNhbGxiYWNrcy5cbiAqL1xuZnVuY3Rpb24gb3BlbkRCKG5hbWUsIHZlcnNpb24sIHsgYmxvY2tlZCwgdXBncmFkZSwgYmxvY2tpbmcsIHRlcm1pbmF0ZWQgfSA9IHt9KSB7XG4gICAgY29uc3QgcmVxdWVzdCA9IGluZGV4ZWREQi5vcGVuKG5hbWUsIHZlcnNpb24pO1xuICAgIGNvbnN0IG9wZW5Qcm9taXNlID0gd3JhcChyZXF1ZXN0KTtcbiAgICBpZiAodXBncmFkZSkge1xuICAgICAgICByZXF1ZXN0LmFkZEV2ZW50TGlzdGVuZXIoJ3VwZ3JhZGVuZWVkZWQnLCAoZXZlbnQpID0+IHtcbiAgICAgICAgICAgIHVwZ3JhZGUod3JhcChyZXF1ZXN0LnJlc3VsdCksIGV2ZW50Lm9sZFZlcnNpb24sIGV2ZW50Lm5ld1ZlcnNpb24sIHdyYXAocmVxdWVzdC50cmFuc2FjdGlvbiksIGV2ZW50KTtcbiAgICAgICAgfSk7XG4gICAgfVxuICAgIGlmIChibG9ja2VkKSB7XG4gICAgICAgIHJlcXVlc3QuYWRkRXZlbnRMaXN0ZW5lcignYmxvY2tlZCcsIChldmVudCkgPT4gYmxvY2tlZChcbiAgICAgICAgLy8gQ2FzdGluZyBkdWUgdG8gaHR0cHM6Ly9naXRodWIuY29tL21pY3Jvc29mdC9UeXBlU2NyaXB0LURPTS1saWItZ2VuZXJhdG9yL3B1bGwvMTQwNVxuICAgICAgICBldmVudC5vbGRWZXJzaW9uLCBldmVudC5uZXdWZXJzaW9uLCBldmVudCkpO1xuICAgIH1cbiAgICBvcGVuUHJvbWlzZVxuICAgICAgICAudGhlbigoZGIpID0+IHtcbiAgICAgICAgaWYgKHRlcm1pbmF0ZWQpXG4gICAgICAgICAgICBkYi5hZGRFdmVudExpc3RlbmVyKCdjbG9zZScsICgpID0+IHRlcm1pbmF0ZWQoKSk7XG4gICAgICAgIGlmIChibG9ja2luZykge1xuICAgICAgICAgICAgZGIuYWRkRXZlbnRMaXN0ZW5lcigndmVyc2lvbmNoYW5nZScsIChldmVudCkgPT4gYmxvY2tpbmcoZXZlbnQub2xkVmVyc2lvbiwgZXZlbnQubmV3VmVyc2lvbiwgZXZlbnQpKTtcbiAgICAgICAgfVxuICAgIH0pXG4gICAgICAgIC5jYXRjaCgoKSA9PiB7IH0pO1xuICAgIHJldHVybiBvcGVuUHJvbWlzZTtcbn1cbi8qKlxuICogRGVsZXRlIGEgZGF0YWJhc2UuXG4gKlxuICogQHBhcmFtIG5hbWUgTmFtZSBvZiB0aGUgZGF0YWJhc2UuXG4gKi9cbmZ1bmN0aW9uIGRlbGV0ZURCKG5hbWUsIHsgYmxvY2tlZCB9ID0ge30pIHtcbiAgICBjb25zdCByZXF1ZXN0ID0gaW5kZXhlZERCLmRlbGV0ZURhdGFiYXNlKG5hbWUpO1xuICAgIGlmIChibG9ja2VkKSB7XG4gICAgICAgIHJlcXVlc3QuYWRkRXZlbnRMaXN0ZW5lcignYmxvY2tlZCcsIChldmVudCkgPT4gYmxvY2tlZChcbiAgICAgICAgLy8gQ2FzdGluZyBkdWUgdG8gaHR0cHM6Ly9naXRodWIuY29tL21pY3Jvc29mdC9UeXBlU2NyaXB0LURPTS1saWItZ2VuZXJhdG9yL3B1bGwvMTQwNVxuICAgICAgICBldmVudC5vbGRWZXJzaW9uLCBldmVudCkpO1xuICAgIH1cbiAgICByZXR1cm4gd3JhcChyZXF1ZXN0KS50aGVuKCgpID0+IHVuZGVmaW5lZCk7XG59XG5cbmNvbnN0IHJlYWRNZXRob2RzID0gWydnZXQnLCAnZ2V0S2V5JywgJ2dldEFsbCcsICdnZXRBbGxLZXlzJywgJ2NvdW50J107XG5jb25zdCB3cml0ZU1ldGhvZHMgPSBbJ3B1dCcsICdhZGQnLCAnZGVsZXRlJywgJ2NsZWFyJ107XG5jb25zdCBjYWNoZWRNZXRob2RzID0gbmV3IE1hcCgpO1xuZnVuY3Rpb24gZ2V0TWV0aG9kKHRhcmdldCwgcHJvcCkge1xuICAgIGlmICghKHRhcmdldCBpbnN0YW5jZW9mIElEQkRhdGFiYXNlICYmXG4gICAgICAgICEocHJvcCBpbiB0YXJnZXQpICYmXG4gICAgICAgIHR5cGVvZiBwcm9wID09PSAnc3RyaW5nJykpIHtcbiAgICAgICAgcmV0dXJuO1xuICAgIH1cbiAgICBpZiAoY2FjaGVkTWV0aG9kcy5nZXQocHJvcCkpXG4gICAgICAgIHJldHVybiBjYWNoZWRNZXRob2RzLmdldChwcm9wKTtcbiAgICBjb25zdCB0YXJnZXRGdW5jTmFtZSA9IHByb3AucmVwbGFjZSgvRnJvbUluZGV4JC8sICcnKTtcbiAgICBjb25zdCB1c2VJbmRleCA9IHByb3AgIT09IHRhcmdldEZ1bmNOYW1lO1xuICAgIGNvbnN0IGlzV3JpdGUgPSB3cml0ZU1ldGhvZHMuaW5jbHVkZXModGFyZ2V0RnVuY05hbWUpO1xuICAgIGlmIChcbiAgICAvLyBCYWlsIGlmIHRoZSB0YXJnZXQgZG9lc24ndCBleGlzdCBvbiB0aGUgdGFyZ2V0LiBFZywgZ2V0QWxsIGlzbid0IGluIEVkZ2UuXG4gICAgISh0YXJnZXRGdW5jTmFtZSBpbiAodXNlSW5kZXggPyBJREJJbmRleCA6IElEQk9iamVjdFN0b3JlKS5wcm90b3R5cGUpIHx8XG4gICAgICAgICEoaXNXcml0ZSB8fCByZWFkTWV0aG9kcy5pbmNsdWRlcyh0YXJnZXRGdW5jTmFtZSkpKSB7XG4gICAgICAgIHJldHVybjtcbiAgICB9XG4gICAgY29uc3QgbWV0aG9kID0gYXN5bmMgZnVuY3Rpb24gKHN0b3JlTmFtZSwgLi4uYXJncykge1xuICAgICAgICAvLyBpc1dyaXRlID8gJ3JlYWR3cml0ZScgOiB1bmRlZmluZWQgZ3ppcHBzIGJldHRlciwgYnV0IGZhaWxzIGluIEVkZ2UgOihcbiAgICAgICAgY29uc3QgdHggPSB0aGlzLnRyYW5zYWN0aW9uKHN0b3JlTmFtZSwgaXNXcml0ZSA/ICdyZWFkd3JpdGUnIDogJ3JlYWRvbmx5Jyk7XG4gICAgICAgIGxldCB0YXJnZXQgPSB0eC5zdG9yZTtcbiAgICAgICAgaWYgKHVzZUluZGV4KVxuICAgICAgICAgICAgdGFyZ2V0ID0gdGFyZ2V0LmluZGV4KGFyZ3Muc2hpZnQoKSk7XG4gICAgICAgIC8vIE11c3QgcmVqZWN0IGlmIG9wIHJlamVjdHMuXG4gICAgICAgIC8vIElmIGl0J3MgYSB3cml0ZSBvcGVyYXRpb24sIG11c3QgcmVqZWN0IGlmIHR4LmRvbmUgcmVqZWN0cy5cbiAgICAgICAgLy8gTXVzdCByZWplY3Qgd2l0aCBvcCByZWplY3Rpb24gZmlyc3QuXG4gICAgICAgIC8vIE11c3QgcmVzb2x2ZSB3aXRoIG9wIHZhbHVlLlxuICAgICAgICAvLyBNdXN0IGhhbmRsZSBib3RoIHByb21pc2VzIChubyB1bmhhbmRsZWQgcmVqZWN0aW9ucylcbiAgICAgICAgcmV0dXJuIChhd2FpdCBQcm9taXNlLmFsbChbXG4gICAgICAgICAgICB0YXJnZXRbdGFyZ2V0RnVuY05hbWVdKC4uLmFyZ3MpLFxuICAgICAgICAgICAgaXNXcml0ZSAmJiB0eC5kb25lLFxuICAgICAgICBdKSlbMF07XG4gICAgfTtcbiAgICBjYWNoZWRNZXRob2RzLnNldChwcm9wLCBtZXRob2QpO1xuICAgIHJldHVybiBtZXRob2Q7XG59XG5yZXBsYWNlVHJhcHMoKG9sZFRyYXBzKSA9PiAoe1xuICAgIC4uLm9sZFRyYXBzLFxuICAgIGdldDogKHRhcmdldCwgcHJvcCwgcmVjZWl2ZXIpID0+IGdldE1ldGhvZCh0YXJnZXQsIHByb3ApIHx8IG9sZFRyYXBzLmdldCh0YXJnZXQsIHByb3AsIHJlY2VpdmVyKSxcbiAgICBoYXM6ICh0YXJnZXQsIHByb3ApID0+ICEhZ2V0TWV0aG9kKHRhcmdldCwgcHJvcCkgfHwgb2xkVHJhcHMuaGFzKHRhcmdldCwgcHJvcCksXG59KSk7XG5cbmNvbnN0IGFkdmFuY2VNZXRob2RQcm9wcyA9IFsnY29udGludWUnLCAnY29udGludWVQcmltYXJ5S2V5JywgJ2FkdmFuY2UnXTtcbmNvbnN0IG1ldGhvZE1hcCA9IHt9O1xuY29uc3QgYWR2YW5jZVJlc3VsdHMgPSBuZXcgV2Vha01hcCgpO1xuY29uc3QgaXR0clByb3hpZWRDdXJzb3JUb09yaWdpbmFsUHJveHkgPSBuZXcgV2Vha01hcCgpO1xuY29uc3QgY3Vyc29ySXRlcmF0b3JUcmFwcyA9IHtcbiAgICBnZXQodGFyZ2V0LCBwcm9wKSB7XG4gICAgICAgIGlmICghYWR2YW5jZU1ldGhvZFByb3BzLmluY2x1ZGVzKHByb3ApKVxuICAgICAgICAgICAgcmV0dXJuIHRhcmdldFtwcm9wXTtcbiAgICAgICAgbGV0IGNhY2hlZEZ1bmMgPSBtZXRob2RNYXBbcHJvcF07XG4gICAgICAgIGlmICghY2FjaGVkRnVuYykge1xuICAgICAgICAgICAgY2FjaGVkRnVuYyA9IG1ldGhvZE1hcFtwcm9wXSA9IGZ1bmN0aW9uICguLi5hcmdzKSB7XG4gICAgICAgICAgICAgICAgYWR2YW5jZVJlc3VsdHMuc2V0KHRoaXMsIGl0dHJQcm94aWVkQ3Vyc29yVG9PcmlnaW5hbFByb3h5LmdldCh0aGlzKVtwcm9wXSguLi5hcmdzKSk7XG4gICAgICAgICAgICB9O1xuICAgICAgICB9XG4gICAgICAgIHJldHVybiBjYWNoZWRGdW5jO1xuICAgIH0sXG59O1xuYXN5bmMgZnVuY3Rpb24qIGl0ZXJhdGUoLi4uYXJncykge1xuICAgIC8vIHRzbGludDpkaXNhYmxlLW5leHQtbGluZTpuby10aGlzLWFzc2lnbm1lbnRcbiAgICBsZXQgY3Vyc29yID0gdGhpcztcbiAgICBpZiAoIShjdXJzb3IgaW5zdGFuY2VvZiBJREJDdXJzb3IpKSB7XG4gICAgICAgIGN1cnNvciA9IGF3YWl0IGN1cnNvci5vcGVuQ3Vyc29yKC4uLmFyZ3MpO1xuICAgIH1cbiAgICBpZiAoIWN1cnNvcilcbiAgICAgICAgcmV0dXJuO1xuICAgIGN1cnNvciA9IGN1cnNvcjtcbiAgICBjb25zdCBwcm94aWVkQ3Vyc29yID0gbmV3IFByb3h5KGN1cnNvciwgY3Vyc29ySXRlcmF0b3JUcmFwcyk7XG4gICAgaXR0clByb3hpZWRDdXJzb3JUb09yaWdpbmFsUHJveHkuc2V0KHByb3hpZWRDdXJzb3IsIGN1cnNvcik7XG4gICAgLy8gTWFwIHRoaXMgZG91YmxlLXByb3h5IGJhY2sgdG8gdGhlIG9yaWdpbmFsLCBzbyBvdGhlciBjdXJzb3IgbWV0aG9kcyB3b3JrLlxuICAgIHJldmVyc2VUcmFuc2Zvcm1DYWNoZS5zZXQocHJveGllZEN1cnNvciwgdW53cmFwKGN1cnNvcikpO1xuICAgIHdoaWxlIChjdXJzb3IpIHtcbiAgICAgICAgeWllbGQgcHJveGllZEN1cnNvcjtcbiAgICAgICAgLy8gSWYgb25lIG9mIHRoZSBhZHZhbmNpbmcgbWV0aG9kcyB3YXMgbm90IGNhbGxlZCwgY2FsbCBjb250aW51ZSgpLlxuICAgICAgICBjdXJzb3IgPSBhd2FpdCAoYWR2YW5jZVJlc3VsdHMuZ2V0KHByb3hpZWRDdXJzb3IpIHx8IGN1cnNvci5jb250aW51ZSgpKTtcbiAgICAgICAgYWR2YW5jZVJlc3VsdHMuZGVsZXRlKHByb3hpZWRDdXJzb3IpO1xuICAgIH1cbn1cbmZ1bmN0aW9uIGlzSXRlcmF0b3JQcm9wKHRhcmdldCwgcHJvcCkge1xuICAgIHJldHVybiAoKHByb3AgPT09IFN5bWJvbC5hc3luY0l0ZXJhdG9yICYmXG4gICAgICAgIGluc3RhbmNlT2ZBbnkodGFyZ2V0LCBbSURCSW5kZXgsIElEQk9iamVjdFN0b3JlLCBJREJDdXJzb3JdKSkgfHxcbiAgICAgICAgKHByb3AgPT09ICdpdGVyYXRlJyAmJiBpbnN0YW5jZU9mQW55KHRhcmdldCwgW0lEQkluZGV4LCBJREJPYmplY3RTdG9yZV0pKSk7XG59XG5yZXBsYWNlVHJhcHMoKG9sZFRyYXBzKSA9PiAoe1xuICAgIC4uLm9sZFRyYXBzLFxuICAgIGdldCh0YXJnZXQsIHByb3AsIHJlY2VpdmVyKSB7XG4gICAgICAgIGlmIChpc0l0ZXJhdG9yUHJvcCh0YXJnZXQsIHByb3ApKVxuICAgICAgICAgICAgcmV0dXJuIGl0ZXJhdGU7XG4gICAgICAgIHJldHVybiBvbGRUcmFwcy5nZXQodGFyZ2V0LCBwcm9wLCByZWNlaXZlcik7XG4gICAgfSxcbiAgICBoYXModGFyZ2V0LCBwcm9wKSB7XG4gICAgICAgIHJldHVybiBpc0l0ZXJhdG9yUHJvcCh0YXJnZXQsIHByb3ApIHx8IG9sZFRyYXBzLmhhcyh0YXJnZXQsIHByb3ApO1xuICAgIH0sXG59KSk7XG5cbmV4cG9ydCB7IGRlbGV0ZURCLCBvcGVuREIsIHVud3JhcCwgd3JhcCB9O1xuIiwgIi8qKlxuICogU3luYyBNYW5hZ2VyIFx1MjAxNCBQbGF0Zm9ybSBzeW5jIHZpYSBzdG9yYWdlLnN5bmMgKENocm9tZSBcdTIxOTIgR29vZ2xlLCBTYWZhcmkgXHUyMTkyIGlDbG91ZClcbiAqXG4gKiBBcmNoaXRlY3R1cmU6XG4gKiAgIFdyaXRlOiBhcHAgXHUyMTkyIHN0b3JhZ2UubG9jYWwgXHUyMTkyIHNjaGVkdWxlU3luY1B1c2goKSBcdTIxOTIgc3RvcmFnZS5zeW5jXG4gKiAgIFJlYWQ6ICBwdWxsRnJvbVN5bmMoKSBvbiBzdGFydHVwIFx1MjE5MiBtZXJnZSBpbnRvIHN0b3JhZ2UubG9jYWxcbiAqICAgTGlzdGVuOiBzdG9yYWdlLm9uQ2hhbmdlZChcInN5bmNcIikgXHUyMTkyIG1lcmdlIHJlbW90ZSBjaGFuZ2VzIGludG8gbG9jYWxcbiAqXG4gKiBzdG9yYWdlLmxvY2FsIHJlbWFpbnMgdGhlIHNvdXJjZSBvZiB0cnV0aC4gc3RvcmFnZS5zeW5jIGlzIGEgYmVzdC1lZmZvcnQgbWlycm9yLlxuICovXG5cbmltcG9ydCB7IGFwaSB9IGZyb20gJy4vYnJvd3Nlci1wb2x5ZmlsbCc7XG5cbi8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLVxuLy8gQ29uc3RhbnRzXG4vLyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cbmNvbnN0IFNZTkNfUVVPVEEgPSAxMDJfNDAwOyAgICAgICAvLyAxMDAgS0IgdG90YWxcbmNvbnN0IE1BWF9JVEVNID0gOF8xOTI7ICAgICAgICAgICAvLyA4IEtCIHBlciBpdGVtXG5jb25zdCBNQVhfSVRFTVMgPSA1MTI7XG5jb25zdCBDSFVOS19QUkVGSVggPSAnX2NodW5rOic7XG5jb25zdCBTWU5DX01FVEFfS0VZID0gJ19zeW5jX21ldGEnO1xuY29uc3QgTE9DQUxfRU5BQkxFRF9LRVkgPSAncGxhdGZvcm1TeW5jRW5hYmxlZCc7XG5cbi8vIEtleXMgdGhhdCBzaG91bGQgbmV2ZXIgYmUgc3luY2VkXG5jb25zdCBFWENMVURFRF9LRVlTID0gW1xuICAgICdidW5rZXJTZXNzaW9ucycsXG4gICAgJ2lnbm9yZUluc3RhbGxIb29rJyxcbiAgICAncGFzc3dvcmRIYXNoJyxcbiAgICAncGFzc3dvcmRTYWx0Jyxcbl07XG5cbi8vIFByaW9yaXR5IHRpZXJzIGZvciBidWRnZXQgYWxsb2NhdGlvblxuY29uc3QgUFJJT1JJVFkgPSB7XG4gICAgUDFfUFJPRklMRVM6IDEsXG4gICAgUDJfU0VUVElOR1M6IDIsXG4gICAgUDNfQVBJS0VZUzogMyxcbiAgICBQNF9WQVVMVDogNCxcbn07XG5cbmNvbnN0IHN0b3JhZ2UgPSBhcGkuc3RvcmFnZS5sb2NhbDtcbmxldCBwdXNoVGltZXIgPSBudWxsO1xuXG4vLyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cbi8vIENodW5raW5nIGhlbHBlcnNcbi8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLVxuXG4vKipcbiAqIFNwbGl0IGEgSlNPTi1zZXJpYWxpc2VkIHZhbHVlIGludG8gPD04S0IgY2h1bmtzLlxuICogUmV0dXJucyBhbiBhcnJheSBvZiB7IGtleSwgdmFsdWUgfSBwYWlycyByZWFkeSBmb3Igc3RvcmFnZS5zeW5jLnNldCgpLlxuICovXG5mdW5jdGlvbiBjaHVua1ZhbHVlKGtleSwganNvblN0cmluZykge1xuICAgIGNvbnN0IGNodW5rcyA9IFtdO1xuICAgIGZvciAobGV0IGkgPSAwOyBpIDwganNvblN0cmluZy5sZW5ndGg7IGkgKz0gTUFYX0lURU0gLSAxMDApIHtcbiAgICAgICAgLy8gUmVzZXJ2ZSB+MTAwIGJ5dGVzIGZvciB0aGUga2V5IG92ZXJoZWFkIGluIHRoZSBzdG9yZWQgaXRlbVxuICAgICAgICBjaHVua3MucHVzaChqc29uU3RyaW5nLnNsaWNlKGksIGkgKyBNQVhfSVRFTSAtIDEwMCkpO1xuICAgIH1cbiAgICBpZiAoY2h1bmtzLmxlbmd0aCA9PT0gMSkge1xuICAgICAgICAvLyBGaXRzIGluIGEgc2luZ2xlIGl0ZW0gXHUyMDE0IHN0b3JlIGRpcmVjdGx5XG4gICAgICAgIHJldHVybiBbeyBrZXksIHZhbHVlOiBqc29uU3RyaW5nIH1dO1xuICAgIH1cbiAgICAvLyBNdWx0aXBsZSBjaHVua3NcbiAgICBjb25zdCBlbnRyaWVzID0gW107XG4gICAgZm9yIChsZXQgaSA9IDA7IGkgPCBjaHVua3MubGVuZ3RoOyBpKyspIHtcbiAgICAgICAgZW50cmllcy5wdXNoKHsga2V5OiBgJHtDSFVOS19QUkVGSVh9JHtrZXl9OiR7aX1gLCB2YWx1ZTogY2h1bmtzW2ldIH0pO1xuICAgIH1cbiAgICAvLyBTdG9yZSBhIG1ldGFkYXRhIGVudHJ5IHNvIHdlIGtub3cgaG93IG1hbnkgY2h1bmtzIHRoZXJlIGFyZVxuICAgIGVudHJpZXMucHVzaCh7IGtleSwgdmFsdWU6IEpTT04uc3RyaW5naWZ5KHsgX19jaHVua2VkOiB0cnVlLCBjb3VudDogY2h1bmtzLmxlbmd0aCB9KSB9KTtcbiAgICByZXR1cm4gZW50cmllcztcbn1cblxuLyoqXG4gKiBSZWFzc2VtYmxlIGNodW5rZWQgZGF0YSBmcm9tIGEgc3luYyBkYXRhIG9iamVjdC5cbiAqIFJldHVybnMgdGhlIHBhcnNlZCBKU09OIHZhbHVlLCBvciBudWxsIG9uIGVycm9yLlxuICovXG5mdW5jdGlvbiByZWFzc2VtYmxlRnJvbVN5bmNEYXRhKGtleSwgc3luY0RhdGEpIHtcbiAgICB0cnkge1xuICAgICAgICBjb25zdCBtZXRhID0gdHlwZW9mIHN5bmNEYXRhW2tleV0gPT09ICdzdHJpbmcnID8gSlNPTi5wYXJzZShzeW5jRGF0YVtrZXldKSA6IHN5bmNEYXRhW2tleV07XG4gICAgICAgIGlmICghbWV0YSB8fCAhbWV0YS5fX2NodW5rZWQpIHtcbiAgICAgICAgICAgIC8vIE5vdCBjaHVua2VkIFx1MjAxNCBwYXJzZSBkaXJlY3RseVxuICAgICAgICAgICAgcmV0dXJuIHR5cGVvZiBzeW5jRGF0YVtrZXldID09PSAnc3RyaW5nJyA/IEpTT04ucGFyc2Uoc3luY0RhdGFba2V5XSkgOiBzeW5jRGF0YVtrZXldO1xuICAgICAgICB9XG4gICAgICAgIGxldCBjb21iaW5lZCA9ICcnO1xuICAgICAgICBmb3IgKGxldCBpID0gMDsgaSA8IG1ldGEuY291bnQ7IGkrKykge1xuICAgICAgICAgICAgY29uc3QgY2h1bmtLZXkgPSBgJHtDSFVOS19QUkVGSVh9JHtrZXl9OiR7aX1gO1xuICAgICAgICAgICAgaWYgKHN5bmNEYXRhW2NodW5rS2V5XSA9PSBudWxsKSByZXR1cm4gbnVsbDtcbiAgICAgICAgICAgIGNvbWJpbmVkICs9IHN5bmNEYXRhW2NodW5rS2V5XTtcbiAgICAgICAgfVxuICAgICAgICByZXR1cm4gSlNPTi5wYXJzZShjb21iaW5lZCk7XG4gICAgfSBjYXRjaCB7XG4gICAgICAgIHJldHVybiBudWxsO1xuICAgIH1cbn1cblxuLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG4vLyBCdWlsZCBzeW5jIHBheWxvYWRcbi8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLVxuXG4vKipcbiAqIFJlYWQgYWxsIGxvY2FsIGRhdGEgYW5kIGJ1aWxkIGEgcHJpb3JpdGlzZWQgbGlzdCBvZiBlbnRyaWVzIHRvIHN5bmMuXG4gKiBSZXR1cm5zIHsgZW50cmllczogW3sga2V5LCBqc29uU3RyaW5nLCBwcmlvcml0eSwgc2l6ZSB9XSwgdG90YWxTaXplIH1cbiAqL1xuYXN5bmMgZnVuY3Rpb24gYnVpbGRTeW5jUGF5bG9hZCgpIHtcbiAgICBjb25zdCBhbGwgPSBhd2FpdCBzdG9yYWdlLmdldChudWxsKTtcbiAgICBjb25zdCBlbnRyaWVzID0gW107XG5cbiAgICAvLyBQMTogUHJvZmlsZXMgKHN0cmlwIGBob3N0c2AgdG8gc2F2ZSBzcGFjZSkgKyBwcm9maWxlSW5kZXhcbiAgICBpZiAoYWxsLnByb2ZpbGVzKSB7XG4gICAgICAgIGNvbnN0IGNsZWFuUHJvZmlsZXMgPSBhbGwucHJvZmlsZXMubWFwKHAgPT4ge1xuICAgICAgICAgICAgY29uc3QgeyBob3N0cywgLi4ucmVzdCB9ID0gcDtcbiAgICAgICAgICAgIHJldHVybiByZXN0O1xuICAgICAgICB9KTtcbiAgICAgICAgY29uc3QganNvbiA9IEpTT04uc3RyaW5naWZ5KGNsZWFuUHJvZmlsZXMpO1xuICAgICAgICBlbnRyaWVzLnB1c2goeyBrZXk6ICdwcm9maWxlcycsIGpzb25TdHJpbmc6IGpzb24sIHByaW9yaXR5OiBQUklPUklUWS5QMV9QUk9GSUxFUywgc2l6ZToganNvbi5sZW5ndGggfSk7XG4gICAgfVxuICAgIGlmIChhbGwucHJvZmlsZUluZGV4ICE9IG51bGwpIHtcbiAgICAgICAgY29uc3QganNvbiA9IEpTT04uc3RyaW5naWZ5KGFsbC5wcm9maWxlSW5kZXgpO1xuICAgICAgICBlbnRyaWVzLnB1c2goeyBrZXk6ICdwcm9maWxlSW5kZXgnLCBqc29uU3RyaW5nOiBqc29uLCBwcmlvcml0eTogUFJJT1JJVFkuUDFfUFJPRklMRVMsIHNpemU6IGpzb24ubGVuZ3RoIH0pO1xuICAgIH1cbiAgICAvLyBOT1RFOiBgaXNFbmNyeXB0ZWRgIGlzIGludGVudGlvbmFsbHkgTk9UIHN5bmNlZC4gVGhlIHBhc3N3b3JkIHZlcmlmaWVyXG4gICAgLy8gKHBhc3N3b3JkSGFzaC9wYXNzd29yZFNhbHQpIGlzIGV4Y2x1ZGVkIGZyb20gc3luYyBmb3Igc2VjdXJpdHksIHNvIGEgZGV2aWNlXG4gICAgLy8gdGhhdCByZWNlaXZlZCBpc0VuY3J5cHRlZD10cnVlIHdpdGggbm8gaGFzaCB3b3VsZCBiZSBwZXJtYW5lbnRseSBsb2NrZWQgb3V0XG4gICAgLy8gKGNoZWNrUGFzc3dvcmQgYWx3YXlzIGZhaWxzKS4gRW5jcnlwdGlvbiBzdGF0ZSBpcyBzdHJpY3RseSBkZXZpY2UtbG9jYWwuXG5cbiAgICAvLyBQMjogU2V0dGluZ3NcbiAgICBjb25zdCBzZXR0aW5nc0tleXMgPSBbJ2F1dG9Mb2NrTWludXRlcycsICd2ZXJzaW9uJywgJ3Byb3RvY29sX2hhbmRsZXInLCBMT0NBTF9FTkFCTEVEX0tFWV07XG4gICAgZm9yIChjb25zdCBrIG9mIHNldHRpbmdzS2V5cykge1xuICAgICAgICBpZiAoYWxsW2tdICE9IG51bGwpIHtcbiAgICAgICAgICAgIGNvbnN0IGpzb24gPSBKU09OLnN0cmluZ2lmeShhbGxba10pO1xuICAgICAgICAgICAgZW50cmllcy5wdXNoKHsga2V5OiBrLCBqc29uU3RyaW5nOiBqc29uLCBwcmlvcml0eTogUFJJT1JJVFkuUDJfU0VUVElOR1MsIHNpemU6IGpzb24ubGVuZ3RoIH0pO1xuICAgICAgICB9XG4gICAgfVxuICAgIC8vIEZlYXR1cmUgZmxhZ3NcbiAgICBmb3IgKGNvbnN0IGsgb2YgT2JqZWN0LmtleXMoYWxsKSkge1xuICAgICAgICBpZiAoay5zdGFydHNXaXRoKCdmZWF0dXJlOicpKSB7XG4gICAgICAgICAgICBjb25zdCBqc29uID0gSlNPTi5zdHJpbmdpZnkoYWxsW2tdKTtcbiAgICAgICAgICAgIGVudHJpZXMucHVzaCh7IGtleTogaywganNvblN0cmluZzoganNvbiwgcHJpb3JpdHk6IFBSSU9SSVRZLlAyX1NFVFRJTkdTLCBzaXplOiBqc29uLmxlbmd0aCB9KTtcbiAgICAgICAgfVxuICAgIH1cblxuICAgIC8vIFAzOiBBUEkga2V5IHZhdWx0XG4gICAgaWYgKGFsbC5hcGlLZXlWYXVsdCkge1xuICAgICAgICBjb25zdCBqc29uID0gSlNPTi5zdHJpbmdpZnkoYWxsLmFwaUtleVZhdWx0KTtcbiAgICAgICAgZW50cmllcy5wdXNoKHsga2V5OiAnYXBpS2V5VmF1bHQnLCBqc29uU3RyaW5nOiBqc29uLCBwcmlvcml0eTogUFJJT1JJVFkuUDNfQVBJS0VZUywgc2l6ZToganNvbi5sZW5ndGggfSk7XG4gICAgfVxuXG4gICAgLy8gUDQ6IFZhdWx0IGRvY3MgKGluZGl2aWR1YWxseSwgbmV3ZXN0IGZpcnN0KVxuICAgIGlmIChhbGwudmF1bHREb2NzICYmIHR5cGVvZiBhbGwudmF1bHREb2NzID09PSAnb2JqZWN0Jykge1xuICAgICAgICBjb25zdCBkb2NzID0gT2JqZWN0LnZhbHVlcyhhbGwudmF1bHREb2NzKS5zb3J0KChhLCBiKSA9PiAoYi51cGRhdGVkQXQgfHwgMCkgLSAoYS51cGRhdGVkQXQgfHwgMCkpO1xuICAgICAgICBmb3IgKGNvbnN0IGRvYyBvZiBkb2NzKSB7XG4gICAgICAgICAgICBjb25zdCBkb2NLZXkgPSBgdmF1bHREb2M6JHtkb2MucGF0aH1gO1xuICAgICAgICAgICAgY29uc3QganNvbiA9IEpTT04uc3RyaW5naWZ5KGRvYyk7XG4gICAgICAgICAgICBlbnRyaWVzLnB1c2goeyBrZXk6IGRvY0tleSwganNvblN0cmluZzoganNvbiwgcHJpb3JpdHk6IFBSSU9SSVRZLlA0X1ZBVUxULCBzaXplOiBqc29uLmxlbmd0aCB9KTtcbiAgICAgICAgfVxuICAgIH1cblxuICAgIHJldHVybiBlbnRyaWVzO1xufVxuXG4vLyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cbi8vIFB1c2ggdG8gc3luY1xuLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG5cbmFzeW5jIGZ1bmN0aW9uIHB1c2hUb1N5bmMoKSB7XG4gICAgaWYgKCFhcGkuc3RvcmFnZS5zeW5jKSByZXR1cm47XG5cbiAgICBjb25zdCBlbmFibGVkID0gYXdhaXQgaXNTeW5jRW5hYmxlZCgpO1xuICAgIGlmICghZW5hYmxlZCkgcmV0dXJuO1xuXG4gICAgdHJ5IHtcbiAgICAgICAgY29uc3QgZW50cmllcyA9IGF3YWl0IGJ1aWxkU3luY1BheWxvYWQoKTtcblxuICAgICAgICAvLyBTb3J0IGJ5IHByaW9yaXR5IChhc2NlbmRpbmcgPSBtb3N0IGltcG9ydGFudCBmaXJzdClcbiAgICAgICAgZW50cmllcy5zb3J0KChhLCBiKSA9PiBhLnByaW9yaXR5IC0gYi5wcmlvcml0eSk7XG5cbiAgICAgICAgLy8gQnVpbGQgdGhlIHN5bmMgcGF5bG9hZCByZXNwZWN0aW5nIGJ1ZGdldFxuICAgICAgICBsZXQgdXNlZEJ5dGVzID0gMDtcbiAgICAgICAgbGV0IHVzZWRJdGVtcyA9IDA7XG4gICAgICAgIGNvbnN0IHN5bmNQYXlsb2FkID0ge307XG4gICAgICAgIGNvbnN0IGFsbFN5bmNLZXlzID0gW107XG4gICAgICAgIGxldCBidWRnZXRFeGhhdXN0ZWQgPSBmYWxzZTtcblxuICAgICAgICBmb3IgKGNvbnN0IGVudHJ5IG9mIGVudHJpZXMpIHtcbiAgICAgICAgICAgIGlmIChidWRnZXRFeGhhdXN0ZWQpIGJyZWFrO1xuXG4gICAgICAgICAgICBjb25zdCBjaHVua3MgPSBjaHVua1ZhbHVlKGVudHJ5LmtleSwgZW50cnkuanNvblN0cmluZyk7XG4gICAgICAgICAgICBsZXQgZW50cnlTaXplID0gMDtcbiAgICAgICAgICAgIGZvciAoY29uc3QgYyBvZiBjaHVua3MpIHtcbiAgICAgICAgICAgICAgICBlbnRyeVNpemUgKz0gYy5rZXkubGVuZ3RoICsgKHR5cGVvZiBjLnZhbHVlID09PSAnc3RyaW5nJyA/IGMudmFsdWUubGVuZ3RoIDogSlNPTi5zdHJpbmdpZnkoYy52YWx1ZSkubGVuZ3RoKTtcbiAgICAgICAgICAgIH1cblxuICAgICAgICAgICAgaWYgKHVzZWRCeXRlcyArIGVudHJ5U2l6ZSA+IFNZTkNfUVVPVEEgLSA1MDAgfHwgdXNlZEl0ZW1zICsgY2h1bmtzLmxlbmd0aCA+IE1BWF9JVEVNUyAtIDUpIHtcbiAgICAgICAgICAgICAgICBpZiAoZW50cnkucHJpb3JpdHkgPD0gUFJJT1JJVFkuUDNfQVBJS0VZUykge1xuICAgICAgICAgICAgICAgICAgICAvLyBDcml0aWNhbCBkYXRhIFx1MjAxNCB0cnkgYW55d2F5LCBsZXQgdGhlIEFQSSB0aHJvdyBpZiB0cnVseSBvdmVyXG4gICAgICAgICAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICAgICAgICAgICAgY29uc29sZS53YXJuKGBbU3luY01hbmFnZXJdIEJ1ZGdldCBleGhhdXN0ZWQgYXQgcHJpb3JpdHkgJHtlbnRyeS5wcmlvcml0eX0sIHNraXBwaW5nIHJlbWFpbmluZyBlbnRyaWVzYCk7XG4gICAgICAgICAgICAgICAgICAgIGJ1ZGdldEV4aGF1c3RlZCA9IHRydWU7XG4gICAgICAgICAgICAgICAgICAgIGJyZWFrO1xuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgIH1cblxuICAgICAgICAgICAgZm9yIChjb25zdCBjIG9mIGNodW5rcykge1xuICAgICAgICAgICAgICAgIHN5bmNQYXlsb2FkW2Mua2V5XSA9IGMudmFsdWU7XG4gICAgICAgICAgICAgICAgYWxsU3luY0tleXMucHVzaChjLmtleSk7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgICB1c2VkQnl0ZXMgKz0gZW50cnlTaXplO1xuICAgICAgICAgICAgdXNlZEl0ZW1zICs9IGNodW5rcy5sZW5ndGg7XG4gICAgICAgIH1cblxuICAgICAgICAvLyBBZGQgc3luYyBtZXRhZGF0YVxuICAgICAgICBjb25zdCBtZXRhID0ge1xuICAgICAgICAgICAgbGFzdFdyaXR0ZW5BdDogRGF0ZS5ub3coKSxcbiAgICAgICAgICAgIGtleXM6IGFsbFN5bmNLZXlzLFxuICAgICAgICB9O1xuICAgICAgICBzeW5jUGF5bG9hZFtTWU5DX01FVEFfS0VZXSA9IEpTT04uc3RyaW5naWZ5KG1ldGEpO1xuXG4gICAgICAgIC8vIFdyaXRlIHRvIHN5bmMgc3RvcmFnZVxuICAgICAgICBhd2FpdCBhcGkuc3RvcmFnZS5zeW5jLnNldChzeW5jUGF5bG9hZCk7XG5cbiAgICAgICAgLy8gQ2xlYW4gb3JwaGFuZWQgY2h1bmtzOiByZWFkIGV4aXN0aW5nIHN5bmMga2V5cyBhbmQgcmVtb3ZlIGFueSBub3QgaW4gb3VyIHBheWxvYWRcbiAgICAgICAgdHJ5IHtcbiAgICAgICAgICAgIGNvbnN0IGV4aXN0aW5nID0gYXdhaXQgYXBpLnN0b3JhZ2Uuc3luYy5nZXQobnVsbCk7XG4gICAgICAgICAgICBjb25zdCBvcnBoYW5LZXlzID0gT2JqZWN0LmtleXMoZXhpc3RpbmcpLmZpbHRlcihrID0+XG4gICAgICAgICAgICAgICAgayAhPT0gU1lOQ19NRVRBX0tFWSAmJiAhYWxsU3luY0tleXMuaW5jbHVkZXMoaylcbiAgICAgICAgICAgICk7XG4gICAgICAgICAgICBpZiAob3JwaGFuS2V5cy5sZW5ndGggPiAwKSB7XG4gICAgICAgICAgICAgICAgYXdhaXQgYXBpLnN0b3JhZ2Uuc3luYy5yZW1vdmUob3JwaGFuS2V5cyk7XG4gICAgICAgICAgICB9XG4gICAgICAgIH0gY2F0Y2gge1xuICAgICAgICAgICAgLy8gTm9uLWNyaXRpY2FsIGNsZWFudXBcbiAgICAgICAgfVxuXG4gICAgICAgIGNvbnNvbGUubG9nKGBbU3luY01hbmFnZXJdIFB1c2hlZCAke2FsbFN5bmNLZXlzLmxlbmd0aH0gZW50cmllcyAoJHt1c2VkQnl0ZXN9IGJ5dGVzKSB0byBzeW5jIHN0b3JhZ2VgKTtcbiAgICB9IGNhdGNoIChlKSB7XG4gICAgICAgIGNvbnNvbGUuZXJyb3IoJ1tTeW5jTWFuYWdlcl0gcHVzaFRvU3luYyBlcnJvcjonLCBlKTtcbiAgICAgICAgLy8gTG9jYWwgc3RvcmFnZSBpcyB1bmFmZmVjdGVkIFx1MjAxNCBncmFjZWZ1bCBkZWdyYWRhdGlvblxuICAgIH1cbn1cblxuLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG4vLyBQdWxsIGZyb20gc3luY1xuLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG5cbi8qKlxuICogUmVhZCBhbGwgZGF0YSBmcm9tIHN5bmMgc3RvcmFnZSBhbmQgcmV0dXJuIGFzIGEgcGxhaW4gb2JqZWN0IHdpdGhcbiAqIHJlYXNzZW1ibGVkIGNodW5rZWQgdmFsdWVzLlxuICovXG5hc3luYyBmdW5jdGlvbiBwdWxsRnJvbVN5bmMoKSB7XG4gICAgaWYgKCFhcGkuc3RvcmFnZS5zeW5jKSByZXR1cm4gbnVsbDtcblxuICAgIHRyeSB7XG4gICAgICAgIGNvbnN0IHJhdyA9IGF3YWl0IGFwaS5zdG9yYWdlLnN5bmMuZ2V0KG51bGwpO1xuICAgICAgICBpZiAoIXJhdyB8fCBPYmplY3Qua2V5cyhyYXcpLmxlbmd0aCA9PT0gMCkgcmV0dXJuIG51bGw7XG5cbiAgICAgICAgY29uc3QgbWV0YVN0ciA9IHJhd1tTWU5DX01FVEFfS0VZXTtcbiAgICAgICAgaWYgKCFtZXRhU3RyKSByZXR1cm4gbnVsbDtcblxuICAgICAgICBsZXQgbWV0YTtcbiAgICAgICAgdHJ5IHsgbWV0YSA9IEpTT04ucGFyc2UobWV0YVN0cik7IH0gY2F0Y2ggeyByZXR1cm4gbnVsbDsgfVxuXG4gICAgICAgIGNvbnN0IHJlc3VsdCA9IHt9O1xuICAgICAgICAvLyBDb2xsZWN0IHRoZSBub24tY2h1bmssIG5vbi1tZXRhIGtleXNcbiAgICAgICAgY29uc3QgZGF0YUtleXMgPSBtZXRhLmtleXMuZmlsdGVyKGsgPT4gIWsuc3RhcnRzV2l0aChDSFVOS19QUkVGSVgpICYmIGsgIT09IFNZTkNfTUVUQV9LRVkpO1xuXG4gICAgICAgIGZvciAoY29uc3Qga2V5IG9mIGRhdGFLZXlzKSB7XG4gICAgICAgICAgICBjb25zdCB2YWx1ZSA9IHJlYXNzZW1ibGVGcm9tU3luY0RhdGEoa2V5LCByYXcpO1xuICAgICAgICAgICAgaWYgKHZhbHVlICE9IG51bGwpIHtcbiAgICAgICAgICAgICAgICByZXN1bHRba2V5XSA9IHZhbHVlO1xuICAgICAgICAgICAgfVxuICAgICAgICB9XG5cbiAgICAgICAgcmVzdWx0Ll9zeW5jTWV0YSA9IG1ldGE7XG4gICAgICAgIHJldHVybiByZXN1bHQ7XG4gICAgfSBjYXRjaCAoZSkge1xuICAgICAgICBjb25zb2xlLmVycm9yKCdbU3luY01hbmFnZXJdIHB1bGxGcm9tU3luYyBlcnJvcjonLCBlKTtcbiAgICAgICAgcmV0dXJuIG51bGw7XG4gICAgfVxufVxuXG4vLyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cbi8vIE1lcmdlIGxvZ2ljXG4vLyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cblxuLyoqXG4gKiBNZXJnZSBzeW5jIGRhdGEgaW50byBsb2NhbCBzdG9yYWdlIHdpdGggY29uZmxpY3QgcmVzb2x1dGlvbi5cbiAqL1xuLyoqXG4gKiBDb21wYXJlIHR3byBkb3R0ZWQgdmVyc2lvbiBzdHJpbmdzIG51bWVyaWNhbGx5LCBjb21wb25lbnQgYnkgY29tcG9uZW50LlxuICogUmV0dXJucyAtMSBpZiBhIDwgYiwgMCBpZiBlcXVhbCwgMSBpZiBhID4gYi4gTm9uLW51bWVyaWMgLyBtaXNzaW5nXG4gKiBjb21wb25lbnRzIGFyZSB0cmVhdGVkIGFzIDAgKGUuZy4gJzEuNicgPT09ICcxLjYuMCcpLlxuICovXG5leHBvcnQgZnVuY3Rpb24gY29tcGFyZVNlbXZlcihhLCBiKSB7XG4gICAgY29uc3QgcGEgPSBTdHJpbmcoYSkuc3BsaXQoJy4nKTtcbiAgICBjb25zdCBwYiA9IFN0cmluZyhiKS5zcGxpdCgnLicpO1xuICAgIGNvbnN0IGxlbiA9IE1hdGgubWF4KHBhLmxlbmd0aCwgcGIubGVuZ3RoKTtcbiAgICBmb3IgKGxldCBpID0gMDsgaSA8IGxlbjsgaSsrKSB7XG4gICAgICAgIGNvbnN0IG5hID0gcGFyc2VJbnQocGFbaV0sIDEwKSB8fCAwO1xuICAgICAgICBjb25zdCBuYiA9IHBhcnNlSW50KHBiW2ldLCAxMCkgfHwgMDtcbiAgICAgICAgaWYgKG5hID4gbmIpIHJldHVybiAxO1xuICAgICAgICBpZiAobmEgPCBuYikgcmV0dXJuIC0xO1xuICAgIH1cbiAgICByZXR1cm4gMDtcbn1cblxuYXN5bmMgZnVuY3Rpb24gbWVyZ2VJbnRvTG9jYWwoc3luY0RhdGEpIHtcbiAgICBpZiAoIXN5bmNEYXRhKSByZXR1cm47XG5cbiAgICBjb25zdCBsb2NhbCA9IGF3YWl0IHN0b3JhZ2UuZ2V0KG51bGwpO1xuICAgIGNvbnN0IHsgdXBkYXRlcywgY2hhbmdlZCB9ID0gY29tcHV0ZU1lcmdlVXBkYXRlcyhsb2NhbCwgc3luY0RhdGEpO1xuXG4gICAgaWYgKGNoYW5nZWQpIHtcbiAgICAgICAgYXdhaXQgc3RvcmFnZS5zZXQodXBkYXRlcyk7XG4gICAgICAgIGNvbnNvbGUubG9nKCdbU3luY01hbmFnZXJdIE1lcmdlZCBzeW5jIGRhdGEgaW50byBsb2NhbDonLCBPYmplY3Qua2V5cyh1cGRhdGVzKSk7XG4gICAgfVxufVxuXG4vKipcbiAqIFB1cmUgbWVyZ2U6IGdpdmVuIHRoZSBjdXJyZW50IGxvY2FsIHN0YXRlIGFuZCBhbiBpbmNvbWluZyBzeW5jIHBheWxvYWQsXG4gKiBjb21wdXRlIHRoZSBzdG9yYWdlIHVwZGF0ZXMgdG8gYXBwbHkuIE5vIEkvTyBcdTIwMTQgZXhwb3J0ZWQgc28gdGhlIG1lcmdlIHJ1bGVzXG4gKiAoZnJlc2gtaW5zdGFsbCBkZXRlY3Rpb24sIHB1YmtleS1rZXllZCBwcm9maWxlIG1hdGNoaW5nLCBlbmNyeXB0aW9uLXN0YXRlXG4gKiBleGNsdXNpb24pIGNhbiBiZSByZWdyZXNzaW9uLXRlc3RlZCBkaXJlY3RseS5cbiAqXG4gKiBAcmV0dXJucyB7eyB1cGRhdGVzOiBPYmplY3QsIGNoYW5nZWQ6IGJvb2xlYW4gfX1cbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGNvbXB1dGVNZXJnZVVwZGF0ZXMobG9jYWwsIHN5bmNEYXRhKSB7XG4gICAgY29uc3QgdXBkYXRlcyA9IHt9O1xuICAgIGxldCBjaGFuZ2VkID0gZmFsc2U7XG4gICAgaWYgKCFzeW5jRGF0YSkgcmV0dXJuIHsgdXBkYXRlcywgY2hhbmdlZCB9O1xuXG4gICAgLy8gRGV0ZWN0IGZyZXNoIGluc3RhbGw6IG5vIHByb2ZpbGVzLCBvciBvbmx5IHByb2ZpbGUocykgdGhhdCBjYXJyeSBub1xuICAgIC8vIGlkZW50aXR5IGF0IGFsbCAobm8gcHJpdmF0ZSBrZXksIG5vIGNhY2hlZCBwdWJrZXksIG5vdCBhIGJ1bmtlci9yZW1vdGVcbiAgICAvLyBzaWduZXIpLiBBIGJ1bmtlciBwcm9maWxlIGxlZ2l0aW1hdGVseSBoYXMgcHJpdktleTonJyBidXQgSVMgYSByZWFsXG4gICAgLy8gaWRlbnRpdHkgXHUyMDE0IGl0IG11c3Qgbm90IGJlIHRyZWF0ZWQgYXMgYSBibGFuayBpbnN0YWxsIGFuZCB3aXBlZC5cbiAgICBjb25zdCBoYXNJZGVudGl0eSA9IChwKSA9PlxuICAgICAgICAhIShwLnByaXZLZXkgfHwgcC5wdWJLZXkgfHwgcC50eXBlID09PSAnYnVua2VyJyB8fCBwLmJ1bmtlclVybCB8fCBwLnJlbW90ZVB1YmtleSk7XG4gICAgY29uc3QgaXNGcmVzaCA9ICFsb2NhbC5wcm9maWxlcyB8fFxuICAgICAgICBsb2NhbC5wcm9maWxlcy5sZW5ndGggPT09IDAgfHxcbiAgICAgICAgIWxvY2FsLnByb2ZpbGVzLnNvbWUoaGFzSWRlbnRpdHkpO1xuXG4gICAgLy8gLS0tIFByb2ZpbGVzIChQMSkgLS0tXG4gICAgaWYgKHN5bmNEYXRhLnByb2ZpbGVzKSB7XG4gICAgICAgIGlmIChpc0ZyZXNoKSB7XG4gICAgICAgICAgICAvLyBGcmVzaCBpbnN0YWxsIFx1MjAxNCBhZG9wdCBzeW5jIHByb2ZpbGVzIGVudGlyZWx5XG4gICAgICAgICAgICB1cGRhdGVzLnByb2ZpbGVzID0gc3luY0RhdGEucHJvZmlsZXM7XG4gICAgICAgICAgICBjaGFuZ2VkID0gdHJ1ZTtcbiAgICAgICAgfSBlbHNlIGlmIChsb2NhbC5wcm9maWxlcykge1xuICAgICAgICAgICAgLy8gTWF0Y2ggcHJvZmlsZXMgYnkgcHVia2V5IChzdGFibGUgaWRlbnRpdHkpLCBOT1QgYXJyYXkgaW5kZXggXHUyMDE0XG4gICAgICAgICAgICAvLyByZW9yZGVyaW5nIG9yIGluc2VydGluZyBhIHByb2ZpbGUgb24gb25lIGRldmljZSBtdXN0IG5ldmVyIGNhdXNlXG4gICAgICAgICAgICAvLyBvbmUgaWRlbnRpdHkncyBrZXkgbWF0ZXJpYWwgdG8gb3ZlcndyaXRlIGFuIHVucmVsYXRlZCBwcm9maWxlLlxuICAgICAgICAgICAgY29uc3QgbWVyZ2VkID0gWy4uLmxvY2FsLnByb2ZpbGVzXTtcbiAgICAgICAgICAgIGNvbnN0IGluZGV4QnlQdWJrZXkgPSBuZXcgTWFwKCk7XG4gICAgICAgICAgICBtZXJnZWQuZm9yRWFjaCgocCwgaSkgPT4geyBpZiAocC5wdWJLZXkpIGluZGV4QnlQdWJrZXkuc2V0KHAucHViS2V5LCBpKTsgfSk7XG5cbiAgICAgICAgICAgIGZvciAoY29uc3Qgc3luY1Byb2ZpbGUgb2Ygc3luY0RhdGEucHJvZmlsZXMpIHtcbiAgICAgICAgICAgICAgICBjb25zdCBsb2NhbElkeCA9IHN5bmNQcm9maWxlLnB1YktleSAhPSBudWxsXG4gICAgICAgICAgICAgICAgICAgID8gaW5kZXhCeVB1YmtleS5nZXQoc3luY1Byb2ZpbGUucHViS2V5KVxuICAgICAgICAgICAgICAgICAgICA6IHVuZGVmaW5lZDtcblxuICAgICAgICAgICAgICAgIGlmIChsb2NhbElkeCA9PT0gdW5kZWZpbmVkKSB7XG4gICAgICAgICAgICAgICAgICAgIC8vIE5vIGxvY2FsIHByb2ZpbGUgd2l0aCB0aGlzIHB1YmtleSBcdTIwMTQgaXQncyBhIG5ldyBvbmUgZnJvbSBzeW5jLlxuICAgICAgICAgICAgICAgICAgICAvLyAoUHJvZmlsZXMgd2l0aG91dCBhIHB1YmtleSBjYW4ndCBiZSBzYWZlbHkgbWF0Y2hlZCwgc28gd2UgYWRkXG4gICAgICAgICAgICAgICAgICAgIC8vIHJhdGhlciB0aGFuIHJpc2sgY2xvYmJlcmluZyBhbiB1bnJlbGF0ZWQgbG9jYWwgcHJvZmlsZS4pXG4gICAgICAgICAgICAgICAgICAgIG1lcmdlZC5wdXNoKHN5bmNQcm9maWxlKTtcbiAgICAgICAgICAgICAgICAgICAgaWYgKHN5bmNQcm9maWxlLnB1YktleSkgaW5kZXhCeVB1YmtleS5zZXQoc3luY1Byb2ZpbGUucHViS2V5LCBtZXJnZWQubGVuZ3RoIC0gMSk7XG4gICAgICAgICAgICAgICAgICAgIGNoYW5nZWQgPSB0cnVlO1xuICAgICAgICAgICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IGxvY2FsUHJvZmlsZSA9IG1lcmdlZFtsb2NhbElkeF07XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHN5bmNUaW1lID0gc3luY1Byb2ZpbGUudXBkYXRlZEF0IHx8IDA7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IGxvY2FsVGltZSA9IGxvY2FsUHJvZmlsZS51cGRhdGVkQXQgfHwgMDtcbiAgICAgICAgICAgICAgICAgICAgaWYgKHN5bmNUaW1lID4gbG9jYWxUaW1lKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICAvLyBTeW5jIGlzIG5ld2VyIFx1MjAxNCBtZXJnZSBidXQgcHJlc2VydmUgbG9jYWwgaG9zdHNcbiAgICAgICAgICAgICAgICAgICAgICAgIG1lcmdlZFtsb2NhbElkeF0gPSB7IC4uLnN5bmNQcm9maWxlLCBob3N0czogbG9jYWxQcm9maWxlLmhvc3RzIHx8IHt9IH07XG4gICAgICAgICAgICAgICAgICAgICAgICBjaGFuZ2VkID0gdHJ1ZTtcbiAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgIH1cbiAgICAgICAgICAgIGlmIChjaGFuZ2VkKSB1cGRhdGVzLnByb2ZpbGVzID0gbWVyZ2VkO1xuICAgICAgICB9XG4gICAgfVxuXG4gICAgLy8gLS0tIFByb2ZpbGUgaW5kZXggKFAxKSAtLS1cbiAgICBpZiAoc3luY0RhdGEucHJvZmlsZUluZGV4ICE9IG51bGwgJiYgaXNGcmVzaCkge1xuICAgICAgICB1cGRhdGVzLnByb2ZpbGVJbmRleCA9IHN5bmNEYXRhLnByb2ZpbGVJbmRleDtcbiAgICAgICAgY2hhbmdlZCA9IHRydWU7XG4gICAgfVxuXG4gICAgLy8gLS0tIEVuY3J5cHRpb24gc3RhdGUgKFAxKSAtLS1cbiAgICAvLyBJbnRlbnRpb25hbGx5IE5PVCBtZXJnZWQgZnJvbSBzeW5jLiBTZWUgYnVpbGRTeW5jUGF5bG9hZCgpOiB0aGUgcGFzc3dvcmRcbiAgICAvLyB2ZXJpZmllciBpcyBuZXZlciBzeW5jZWQsIHNvIHRydXN0aW5nIGEgc3luY2VkIGlzRW5jcnlwdGVkPXRydWUgd291bGQgbG9ja1xuICAgIC8vIHRoZSB1c2VyIG91dCBwZXJtYW5lbnRseS4gRW5jcnlwdGlvbiBzdGF0ZSBzdGF5cyBkZXZpY2UtbG9jYWwuXG5cbiAgICAvLyAtLS0gU2V0dGluZ3MgKFAyKSBcdTIwMTQgbGFzdC13cml0ZS13aW5zIC0tLVxuICAgIGNvbnN0IHN5bmNNZXRhID0gc3luY0RhdGEuX3N5bmNNZXRhIHx8IHt9O1xuICAgIGNvbnN0IHNldHRpbmdzS2V5cyA9IFsnYXV0b0xvY2tNaW51dGVzJywgJ3ZlcnNpb24nLCAncHJvdG9jb2xfaGFuZGxlcicsIExPQ0FMX0VOQUJMRURfS0VZXTtcbiAgICBmb3IgKGNvbnN0IGtleSBvZiBzZXR0aW5nc0tleXMpIHtcbiAgICAgICAgaWYgKHN5bmNEYXRhW2tleV0gIT0gbnVsbCAmJiBzeW5jRGF0YVtrZXldICE9PSBsb2NhbFtrZXldKSB7XG4gICAgICAgICAgICAvLyBGb3IgdmVyc2lvbiwgb25seSBhY2NlcHQgaGlnaGVyLiBDb21wYXJlIG51bWVyaWNhbGx5IHBlciBzZW12ZXJcbiAgICAgICAgICAgIC8vIGNvbXBvbmVudCBcdTIwMTQgYSBzdHJpbmcgYDw9YCBtYWtlcyAnMS4xMC4wJyA8PSAnMS45LjAnIChzbyBhIGdlbnVpbmVseVxuICAgICAgICAgICAgLy8gbmV3ZXIgYnVpbGQgZnJvbSBzeW5jIHdvdWxkIGJlIHdyb25nbHkgcmVqZWN0ZWQpLlxuICAgICAgICAgICAgaWYgKGtleSA9PT0gJ3ZlcnNpb24nICYmIGxvY2FsLnZlcnNpb24gJiYgY29tcGFyZVNlbXZlcihzeW5jRGF0YS52ZXJzaW9uLCBsb2NhbC52ZXJzaW9uKSA8PSAwKSBjb250aW51ZTtcbiAgICAgICAgICAgIHVwZGF0ZXNba2V5XSA9IHN5bmNEYXRhW2tleV07XG4gICAgICAgICAgICBjaGFuZ2VkID0gdHJ1ZTtcbiAgICAgICAgfVxuICAgIH1cbiAgICAvLyBGZWF0dXJlIGZsYWdzXG4gICAgZm9yIChjb25zdCBrZXkgb2YgT2JqZWN0LmtleXMoc3luY0RhdGEpKSB7XG4gICAgICAgIGlmIChrZXkuc3RhcnRzV2l0aCgnZmVhdHVyZTonKSAmJiBzeW5jRGF0YVtrZXldICE9PSBsb2NhbFtrZXldKSB7XG4gICAgICAgICAgICB1cGRhdGVzW2tleV0gPSBzeW5jRGF0YVtrZXldO1xuICAgICAgICAgICAgY2hhbmdlZCA9IHRydWU7XG4gICAgICAgIH1cbiAgICB9XG5cbiAgICAvLyAtLS0gQVBJIEtleSBWYXVsdCAoUDMpIC0tLVxuICAgIGlmIChzeW5jRGF0YS5hcGlLZXlWYXVsdCkge1xuICAgICAgICBpZiAoIWxvY2FsLmFwaUtleVZhdWx0IHx8IGlzRnJlc2gpIHtcbiAgICAgICAgICAgIHVwZGF0ZXMuYXBpS2V5VmF1bHQgPSBzeW5jRGF0YS5hcGlLZXlWYXVsdDtcbiAgICAgICAgICAgIGNoYW5nZWQgPSB0cnVlO1xuICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgLy8gTWVyZ2UgaW5kaXZpZHVhbCBrZXlzIGJ5IHVwZGF0ZWRBdFxuICAgICAgICAgICAgY29uc3QgbG9jYWxLZXlzID0gbG9jYWwuYXBpS2V5VmF1bHQua2V5cyB8fCB7fTtcbiAgICAgICAgICAgIGNvbnN0IHN5bmNLZXlzID0gc3luY0RhdGEuYXBpS2V5VmF1bHQua2V5cyB8fCB7fTtcbiAgICAgICAgICAgIGNvbnN0IG1lcmdlZCA9IHsgLi4ubG9jYWxLZXlzIH07XG4gICAgICAgICAgICBmb3IgKGNvbnN0IFtpZCwgc3luY0tleV0gb2YgT2JqZWN0LmVudHJpZXMoc3luY0tleXMpKSB7XG4gICAgICAgICAgICAgICAgY29uc3QgbG9jYWxLZXkgPSBtZXJnZWRbaWRdO1xuICAgICAgICAgICAgICAgIGlmICghbG9jYWxLZXkgfHwgKHN5bmNLZXkudXBkYXRlZEF0IHx8IDApID4gKGxvY2FsS2V5LnVwZGF0ZWRBdCB8fCAwKSkge1xuICAgICAgICAgICAgICAgICAgICBtZXJnZWRbaWRdID0gc3luY0tleTtcbiAgICAgICAgICAgICAgICAgICAgY2hhbmdlZCA9IHRydWU7XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfVxuICAgICAgICAgICAgaWYgKGNoYW5nZWQpIHtcbiAgICAgICAgICAgICAgICB1cGRhdGVzLmFwaUtleVZhdWx0ID0geyAuLi5sb2NhbC5hcGlLZXlWYXVsdCwga2V5czogbWVyZ2VkIH07XG4gICAgICAgICAgICB9XG4gICAgICAgIH1cbiAgICB9XG5cbiAgICAvLyAtLS0gVmF1bHQgZG9jcyAoUDQpIC0tLVxuICAgIGNvbnN0IGxvY2FsRG9jcyA9IGxvY2FsLnZhdWx0RG9jcyB8fCB7fTtcbiAgICBsZXQgZG9jc0NoYW5nZWQgPSBmYWxzZTtcbiAgICBjb25zdCBtZXJnZWREb2NzID0geyAuLi5sb2NhbERvY3MgfTtcbiAgICBmb3IgKGNvbnN0IGtleSBvZiBPYmplY3Qua2V5cyhzeW5jRGF0YSkpIHtcbiAgICAgICAgaWYgKCFrZXkuc3RhcnRzV2l0aCgndmF1bHREb2M6JykpIGNvbnRpbnVlO1xuICAgICAgICBjb25zdCBkb2MgPSBzeW5jRGF0YVtrZXldO1xuICAgICAgICBpZiAoIWRvYyB8fCAhZG9jLnBhdGgpIGNvbnRpbnVlO1xuICAgICAgICBjb25zdCBsb2NhbERvYyA9IG1lcmdlZERvY3NbZG9jLnBhdGhdO1xuICAgICAgICBpZiAoIWxvY2FsRG9jIHx8IChkb2MudXBkYXRlZEF0IHx8IDApID4gKGxvY2FsRG9jLnVwZGF0ZWRBdCB8fCAwKSkge1xuICAgICAgICAgICAgbWVyZ2VkRG9jc1tkb2MucGF0aF0gPSBkb2M7XG4gICAgICAgICAgICBkb2NzQ2hhbmdlZCA9IHRydWU7XG4gICAgICAgIH1cbiAgICB9XG4gICAgaWYgKGRvY3NDaGFuZ2VkKSB7XG4gICAgICAgIHVwZGF0ZXMudmF1bHREb2NzID0gbWVyZ2VkRG9jcztcbiAgICAgICAgY2hhbmdlZCA9IHRydWU7XG4gICAgfVxuXG4gICAgcmV0dXJuIHsgdXBkYXRlcywgY2hhbmdlZCB9O1xufVxuXG4vLyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cbi8vIERlYm91bmNlZCBwdXNoXG4vLyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cblxuLyoqXG4gKiBTY2hlZHVsZSBhIHN5bmMgcHVzaCB3aXRoIGEgMi1zZWNvbmQgZGVib3VuY2UuXG4gKiBFeHBvcnRlZCBmb3IgdXNlIGJ5IHN0b3JlcyBhbmQgdGhlIHN0b3JhZ2UgaW50ZXJjZXB0b3IuXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBzY2hlZHVsZVN5bmNQdXNoKCkge1xuICAgIGlmICghYXBpLnN0b3JhZ2Uuc3luYykgcmV0dXJuO1xuICAgIGlmIChwdXNoVGltZXIpIGNsZWFyVGltZW91dChwdXNoVGltZXIpO1xuICAgIHB1c2hUaW1lciA9IHNldFRpbWVvdXQoKCkgPT4ge1xuICAgICAgICBwdXNoVGltZXIgPSBudWxsO1xuICAgICAgICBwdXNoVG9TeW5jKCk7XG4gICAgfSwgMjAwMCk7XG59XG5cbi8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLVxuLy8gRW5hYmxlIC8gZGlzYWJsZVxuLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG5cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBpc1N5bmNFbmFibGVkKCkge1xuICAgIGNvbnN0IGRhdGEgPSBhd2FpdCBzdG9yYWdlLmdldCh7IFtMT0NBTF9FTkFCTEVEX0tFWV06IHRydWUgfSk7XG4gICAgcmV0dXJuIGRhdGFbTE9DQUxfRU5BQkxFRF9LRVldO1xufVxuXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gc2V0U3luY0VuYWJsZWQoZW5hYmxlZCkge1xuICAgIGF3YWl0IHN0b3JhZ2Uuc2V0KHsgW0xPQ0FMX0VOQUJMRURfS0VZXTogZW5hYmxlZCB9KTtcbiAgICBpZiAoZW5hYmxlZCkge1xuICAgICAgICBzY2hlZHVsZVN5bmNQdXNoKCk7XG4gICAgfVxufVxuXG4vLyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cbi8vIEluaXRpYWxpc2F0aW9uXG4vLyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cblxuLyoqXG4gKiBDYWxsZWQgb25jZSBvbiBzdGFydHVwIChmcm9tIGJhY2tncm91bmQuanMpLlxuICogUHVsbHMgZnJvbSBzeW5jLCBtZXJnZXMsIHRoZW4gbGlzdGVucyBmb3IgcmVtb3RlIGNoYW5nZXMuXG4gKi9cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBpbml0U3luYygpIHtcbiAgICBpZiAoIWFwaS5zdG9yYWdlLnN5bmMpIHtcbiAgICAgICAgY29uc29sZS5sb2coJ1tTeW5jTWFuYWdlcl0gc3RvcmFnZS5zeW5jIG5vdCBhdmFpbGFibGUgXHUyMDE0IHNraXBwaW5nJyk7XG4gICAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICBjb25zdCBlbmFibGVkID0gYXdhaXQgaXNTeW5jRW5hYmxlZCgpO1xuICAgIGlmICghZW5hYmxlZCkge1xuICAgICAgICBjb25zb2xlLmxvZygnW1N5bmNNYW5hZ2VyXSBQbGF0Zm9ybSBzeW5jIGRpc2FibGVkJyk7XG4gICAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICAvLyBQdWxsICsgbWVyZ2VcbiAgICB0cnkge1xuICAgICAgICBjb25zdCBzeW5jRGF0YSA9IGF3YWl0IHB1bGxGcm9tU3luYygpO1xuICAgICAgICBpZiAoc3luY0RhdGEpIHtcbiAgICAgICAgICAgIGF3YWl0IG1lcmdlSW50b0xvY2FsKHN5bmNEYXRhKTtcbiAgICAgICAgICAgIGNvbnNvbGUubG9nKCdbU3luY01hbmFnZXJdIEluaXRpYWwgcHVsbCttZXJnZSBjb21wbGV0ZScpO1xuICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgY29uc29sZS5sb2coJ1tTeW5jTWFuYWdlcl0gTm8gc3luYyBkYXRhIGZvdW5kIFx1MjAxNCBmcmVzaCBzeW5jJyk7XG4gICAgICAgIH1cbiAgICB9IGNhdGNoIChlKSB7XG4gICAgICAgIGNvbnNvbGUuZXJyb3IoJ1tTeW5jTWFuYWdlcl0gSW5pdGlhbCBwdWxsIGZhaWxlZDonLCBlKTtcbiAgICB9XG5cbiAgICAvLyBMaXN0ZW4gZm9yIHJlbW90ZSBjaGFuZ2VzXG4gICAgaWYgKGFwaS5zdG9yYWdlLm9uQ2hhbmdlZCkge1xuICAgICAgICBhcGkuc3RvcmFnZS5vbkNoYW5nZWQuYWRkTGlzdGVuZXIoKGNoYW5nZXMsIGFyZWFOYW1lKSA9PiB7XG4gICAgICAgICAgICBpZiAoYXJlYU5hbWUgIT09ICdzeW5jJykgcmV0dXJuO1xuICAgICAgICAgICAgY29uc29sZS5sb2coJ1tTeW5jTWFuYWdlcl0gUmVtb3RlIHN5bmMgY2hhbmdlIGRldGVjdGVkJyk7XG4gICAgICAgICAgICAvLyBSZS1wdWxsIGFuZCBtZXJnZSB0aGUgZnVsbCBzeW5jIGRhdGEgdG8gaGFuZGxlIGNodW5rZWQgdmFsdWVzIGNvcnJlY3RseVxuICAgICAgICAgICAgcHVsbEZyb21TeW5jKCkudGhlbihzeW5jRGF0YSA9PiB7XG4gICAgICAgICAgICAgICAgaWYgKHN5bmNEYXRhKSBtZXJnZUludG9Mb2NhbChzeW5jRGF0YSk7XG4gICAgICAgICAgICB9KS5jYXRjaChlID0+IHtcbiAgICAgICAgICAgICAgICBjb25zb2xlLmVycm9yKCdbU3luY01hbmFnZXJdIFJlbW90ZSBtZXJnZSBlcnJvcjonLCBlKTtcbiAgICAgICAgICAgIH0pO1xuICAgICAgICB9KTtcbiAgICB9XG5cbiAgICAvLyBEbyBhbiBpbml0aWFsIHB1c2ggc28gbG9jYWwgZGF0YSBpcyBtaXJyb3JlZFxuICAgIHNjaGVkdWxlU3luY1B1c2goKTtcbn1cbiIsICIvKipcbiAqIE5JUC00NiBOb3N0ciBDb25uZWN0IChuc2VjQnVua2VyKSBDbGllbnRcbiAqXG4gKiBJbXBsZW1lbnRzIHRoZSBjbGllbnQgc2lkZSBvZiBOSVAtNDYgZm9yIHJlbW90ZSBzaWduaW5nLlxuICogVGhlIGV4dGVuc2lvbiBjb25uZWN0cyB0byBhIGJ1bmtlciB2aWEgTm9zdHIgcmVsYXlzLlxuICogVGhlIGJ1bmtlciBob2xkcyB0aGUgbnNlYyBhbmQgcGVyZm9ybXMgc2lnbmluZyBvcGVyYXRpb25zLlxuICpcbiAqIEZsb3c6XG4gKiAgIDEuIFVzZXIgcHJvdmlkZXMgYSBidW5rZXI6Ly8gY29ubmVjdGlvbiBzdHJpbmdcbiAqICAgMi4gQ2xpZW50IGdlbmVyYXRlcyBhbiBlcGhlbWVyYWwga2V5cGFpciBmb3IgdGhlIHNlc3Npb25cbiAqICAgMy4gQ2xpZW50IGNvbm5lY3RzIHRvIHRoZSByZWxheSBzcGVjaWZpZWQgaW4gdGhlIGNvbm5lY3Rpb24gc3RyaW5nXG4gKiAgIDQuIENsaWVudCBzZW5kcyBOSVAtNDQgZW5jcnlwdGVkIHJlcXVlc3RzIHRvIHRoZSBidW5rZXIgcHVia2V5XG4gKiAgIDUuIEJ1bmtlciByZXNwb25kcyB3aXRoIE5JUC00NCBlbmNyeXB0ZWQgcmVzdWx0c1xuICogICA2LiBDbGllbnQgZGVjcnlwdHMgYW5kIHJldHVybnMgdGhlIHJlc3VsdFxuICpcbiAqIENvbm5lY3Rpb24gc3RyaW5nIGZvcm1hdDpcbiAqICAgYnVua2VyOi8vPHJlbW90ZS1zaWduZXItcHVia2V5Pj9yZWxheT13c3M6Ly8uLi4mcmVsYXk9d3NzOi8vLi4uJnNlY3JldD08b3B0aW9uYWw+XG4gKi9cblxuaW1wb3J0IHtcbiAgICBmaW5hbGl6ZUV2ZW50LFxuICAgIGJ5dGVzVG9IZXgsXG4gICAgaGV4VG9CeXRlcyxcbn0gZnJvbSAnbm9zdHItY3J5cHRvLXV0aWxzJztcbmltcG9ydCB7IGdlbmVyYXRlS2V5UGFpciB9IGZyb20gJy4va2V5cy5qcyc7XG5pbXBvcnQgKiBhcyBuaXA0NCBmcm9tICdub3N0ci1jcnlwdG8tdXRpbHMvbmlwNDQnO1xuaW1wb3J0IHsgYXBpIH0gZnJvbSAnLi9icm93c2VyLXBvbHlmaWxsJztcblxuY29uc3Qgc3RvcmFnZSA9IGFwaS5zdG9yYWdlLmxvY2FsO1xuY29uc3QgbG9nID0gbXNnID0+IGNvbnNvbGUubG9nKCdOSVAtNDY6ICcsIG1zZyk7XG5cbi8vIEFjdGl2ZSBidW5rZXIgc2Vzc2lvbnMga2V5ZWQgYnkgcHJvZmlsZSBpbmRleFxuY29uc3Qgc2Vzc2lvbnMgPSBuZXcgTWFwKCk7XG5cbi8qKlxuICogUGFyc2UgYSBidW5rZXI6Ly8gY29ubmVjdGlvbiBzdHJpbmdcbiAqIEZvcm1hdDogYnVua2VyOi8vPHB1YmtleT4/cmVsYXk9d3NzOi8vLi4uJnJlbGF5PXdzczovLy4uLiZzZWNyZXQ9PG9wdGlvbmFsPlxuICovXG5leHBvcnQgZnVuY3Rpb24gcGFyc2VCdW5rZXJVcmwodXJsKSB7XG4gICAgaWYgKCF1cmwuc3RhcnRzV2l0aCgnYnVua2VyOi8vJykpIHtcbiAgICAgICAgdGhyb3cgbmV3IEVycm9yKCdJbnZhbGlkIGJ1bmtlciBVUkw6IG11c3Qgc3RhcnQgd2l0aCBidW5rZXI6Ly8nKTtcbiAgICB9XG5cbiAgICBjb25zdCBwYXJzZWQgPSBuZXcgVVJMKHVybCk7XG4gICAgY29uc3QgcmVtb3RlUHVia2V5ID0gcGFyc2VkLmhvc3RuYW1lIHx8IHBhcnNlZC5wYXRobmFtZS5yZXBsYWNlKCcvLycsICcnKTtcblxuICAgIGlmICghL15bMC05YS1mXXs2NH0kL2kudGVzdChyZW1vdGVQdWJrZXkpKSB7XG4gICAgICAgIHRocm93IG5ldyBFcnJvcignSW52YWxpZCBidW5rZXIgVVJMOiBwdWJrZXkgbXVzdCBiZSA2NCBoZXggY2hhcmFjdGVycycpO1xuICAgIH1cblxuICAgIGNvbnN0IHJlbGF5cyA9IHBhcnNlZC5zZWFyY2hQYXJhbXMuZ2V0QWxsKCdyZWxheScpO1xuICAgIGlmIChyZWxheXMubGVuZ3RoID09PSAwKSB7XG4gICAgICAgIHRocm93IG5ldyBFcnJvcignSW52YWxpZCBidW5rZXIgVVJMOiBhdCBsZWFzdCBvbmUgcmVsYXkgaXMgcmVxdWlyZWQnKTtcbiAgICB9XG5cbiAgICAvLyBWYWxpZGF0ZSByZWxheSBVUkxzXG4gICAgZm9yIChjb25zdCByZWxheSBvZiByZWxheXMpIHtcbiAgICAgICAgdHJ5IHtcbiAgICAgICAgICAgIGNvbnN0IHIgPSBuZXcgVVJMKHJlbGF5KTtcbiAgICAgICAgICAgIGlmIChyLnByb3RvY29sICE9PSAnd3NzOicgJiYgci5wcm90b2NvbCAhPT0gJ3dzOicpIHtcbiAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoYEludmFsaWQgcmVsYXkgcHJvdG9jb2w6ICR7ci5wcm90b2NvbH1gKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgfSBjYXRjaCAoZSkge1xuICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKGBJbnZhbGlkIHJlbGF5IFVSTDogJHtyZWxheX1gKTtcbiAgICAgICAgfVxuICAgIH1cblxuICAgIGNvbnN0IHNlY3JldCA9IHBhcnNlZC5zZWFyY2hQYXJhbXMuZ2V0KCdzZWNyZXQnKSB8fCBudWxsO1xuXG4gICAgcmV0dXJuIHsgcmVtb3RlUHVia2V5LCByZWxheXMsIHNlY3JldCB9O1xufVxuXG4vKipcbiAqIEEgc2luZ2xlIFdlYlNvY2tldCBjb25uZWN0aW9uIHRvIGEgTm9zdHIgcmVsYXlcbiAqL1xuZXhwb3J0IGNsYXNzIFJlbGF5Q29ubmVjdGlvbiB7XG4gICAgY29uc3RydWN0b3IodXJsKSB7XG4gICAgICAgIHRoaXMudXJsID0gdXJsO1xuICAgICAgICB0aGlzLndzID0gbnVsbDtcbiAgICAgICAgdGhpcy5zdWJzY3JpcHRpb25zID0gbmV3IE1hcCgpO1xuICAgICAgICB0aGlzLmVvc2VDYWxsYmFja3MgPSBuZXcgTWFwKCk7XG4gICAgICAgIHRoaXMuY29ubmVjdGVkID0gZmFsc2U7XG4gICAgICAgIHRoaXMucmVjb25uZWN0VGltZXIgPSBudWxsO1xuICAgICAgICB0aGlzLnJlY29ubmVjdEF0dGVtcHRzID0gMDtcbiAgICAgICAgdGhpcy5tYXhSZWNvbm5lY3RBdHRlbXB0cyA9IDU7XG4gICAgfVxuXG4gICAgY29ubmVjdCgpIHtcbiAgICAgICAgcmV0dXJuIG5ldyBQcm9taXNlKChyZXNvbHZlLCByZWplY3QpID0+IHtcbiAgICAgICAgICAgIHRyeSB7XG4gICAgICAgICAgICAgICAgdGhpcy53cyA9IG5ldyBXZWJTb2NrZXQodGhpcy51cmwpO1xuICAgICAgICAgICAgfSBjYXRjaCAoZSkge1xuICAgICAgICAgICAgICAgIHJlamVjdChuZXcgRXJyb3IoYEZhaWxlZCB0byBjcmVhdGUgV2ViU29ja2V0OiAke2UubWVzc2FnZX1gKSk7XG4gICAgICAgICAgICAgICAgcmV0dXJuO1xuICAgICAgICAgICAgfVxuXG4gICAgICAgICAgICBjb25zdCB0aW1lb3V0ID0gc2V0VGltZW91dCgoKSA9PiB7XG4gICAgICAgICAgICAgICAgdGhpcy53cz8uY2xvc2UoKTtcbiAgICAgICAgICAgICAgICByZWplY3QobmV3IEVycm9yKGBDb25uZWN0aW9uIHRpbWVvdXQ6ICR7dGhpcy51cmx9YCkpO1xuICAgICAgICAgICAgfSwgMTAwMDApO1xuXG4gICAgICAgICAgICB0aGlzLndzLm9ub3BlbiA9ICgpID0+IHtcbiAgICAgICAgICAgICAgICBjbGVhclRpbWVvdXQodGltZW91dCk7XG4gICAgICAgICAgICAgICAgdGhpcy5jb25uZWN0ZWQgPSB0cnVlO1xuICAgICAgICAgICAgICAgIHRoaXMucmVjb25uZWN0QXR0ZW1wdHMgPSAwO1xuICAgICAgICAgICAgICAgIGxvZyhgQ29ubmVjdGVkIHRvICR7dGhpcy51cmx9YCk7XG4gICAgICAgICAgICAgICAgcmVzb2x2ZSgpO1xuICAgICAgICAgICAgfTtcblxuICAgICAgICAgICAgdGhpcy53cy5vbmVycm9yID0gKGVycikgPT4ge1xuICAgICAgICAgICAgICAgIGNsZWFyVGltZW91dCh0aW1lb3V0KTtcbiAgICAgICAgICAgICAgICBsb2coYFdlYlNvY2tldCBlcnJvcjogJHt0aGlzLnVybH1gKTtcbiAgICAgICAgICAgICAgICByZWplY3QobmV3IEVycm9yKGBXZWJTb2NrZXQgZXJyb3I6ICR7dGhpcy51cmx9YCkpO1xuICAgICAgICAgICAgfTtcblxuICAgICAgICAgICAgdGhpcy53cy5vbmNsb3NlID0gKCkgPT4ge1xuICAgICAgICAgICAgICAgIHRoaXMuY29ubmVjdGVkID0gZmFsc2U7XG4gICAgICAgICAgICAgICAgbG9nKGBEaXNjb25uZWN0ZWQgZnJvbSAke3RoaXMudXJsfWApO1xuICAgICAgICAgICAgICAgIHRoaXMuc2NoZWR1bGVSZWNvbm5lY3QoKTtcbiAgICAgICAgICAgIH07XG5cbiAgICAgICAgICAgIHRoaXMud3Mub25tZXNzYWdlID0gKG1zZykgPT4ge1xuICAgICAgICAgICAgICAgIHRyeSB7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IGRhdGEgPSBKU09OLnBhcnNlKG1zZy5kYXRhKTtcbiAgICAgICAgICAgICAgICAgICAgdGhpcy5oYW5kbGVNZXNzYWdlKGRhdGEpO1xuICAgICAgICAgICAgICAgIH0gY2F0Y2ggKGUpIHtcbiAgICAgICAgICAgICAgICAgICAgbG9nKGBGYWlsZWQgdG8gcGFyc2UgbWVzc2FnZTogJHtlLm1lc3NhZ2V9YCk7XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfTtcbiAgICAgICAgfSk7XG4gICAgfVxuXG4gICAgaGFuZGxlTWVzc2FnZShkYXRhKSB7XG4gICAgICAgIGNvbnN0IFt0eXBlLCBzdWJJZCwgLi4ucmVzdF0gPSBkYXRhO1xuXG4gICAgICAgIGlmICh0eXBlID09PSAnRVZFTlQnICYmIHN1YklkICYmIHJlc3RbMF0pIHtcbiAgICAgICAgICAgIGNvbnN0IGV2ZW50ID0gcmVzdFswXTtcbiAgICAgICAgICAgIGNvbnN0IGhhbmRsZXIgPSB0aGlzLnN1YnNjcmlwdGlvbnMuZ2V0KHN1YklkKTtcbiAgICAgICAgICAgIGlmIChoYW5kbGVyKSB7XG4gICAgICAgICAgICAgICAgaGFuZGxlcihldmVudCk7XG4gICAgICAgICAgICB9XG4gICAgICAgIH0gZWxzZSBpZiAodHlwZSA9PT0gJ0VPU0UnICYmIHN1YklkKSB7XG4gICAgICAgICAgICBjb25zdCBlb3NlSGFuZGxlciA9IHRoaXMuZW9zZUNhbGxiYWNrcy5nZXQoc3ViSWQpO1xuICAgICAgICAgICAgaWYgKGVvc2VIYW5kbGVyKSB7XG4gICAgICAgICAgICAgICAgdGhpcy5lb3NlQ2FsbGJhY2tzLmRlbGV0ZShzdWJJZCk7XG4gICAgICAgICAgICAgICAgZW9zZUhhbmRsZXIoKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgfSBlbHNlIGlmICh0eXBlID09PSAnT0snKSB7XG4gICAgICAgICAgICAvLyBFdmVudCBhY2NlcHRlZFxuICAgICAgICB9IGVsc2UgaWYgKHR5cGUgPT09ICdOT1RJQ0UnKSB7XG4gICAgICAgICAgICBsb2coYFJlbGF5IG5vdGljZTogJHtyZXN0WzBdfWApO1xuICAgICAgICB9XG4gICAgfVxuXG4gICAgc3Vic2NyaWJlKHN1YklkLCBmaWx0ZXJzLCBvbkV2ZW50LCBvbkVvc2UgPSBudWxsKSB7XG4gICAgICAgIGlmICghdGhpcy5jb25uZWN0ZWQgfHwgIXRoaXMud3MpIHtcbiAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcignTm90IGNvbm5lY3RlZCcpO1xuICAgICAgICB9XG4gICAgICAgIHRoaXMuc3Vic2NyaXB0aW9ucy5zZXQoc3ViSWQsIG9uRXZlbnQpO1xuICAgICAgICBpZiAob25Fb3NlKSB7XG4gICAgICAgICAgICB0aGlzLmVvc2VDYWxsYmFja3Muc2V0KHN1YklkLCBvbkVvc2UpO1xuICAgICAgICB9XG4gICAgICAgIHRoaXMud3Muc2VuZChKU09OLnN0cmluZ2lmeShbJ1JFUScsIHN1YklkLCAuLi5maWx0ZXJzXSkpO1xuICAgIH1cblxuICAgIHVuc3Vic2NyaWJlKHN1YklkKSB7XG4gICAgICAgIGlmICh0aGlzLndzICYmIHRoaXMuY29ubmVjdGVkKSB7XG4gICAgICAgICAgICB0aGlzLndzLnNlbmQoSlNPTi5zdHJpbmdpZnkoWydDTE9TRScsIHN1YklkXSkpO1xuICAgICAgICB9XG4gICAgICAgIHRoaXMuc3Vic2NyaXB0aW9ucy5kZWxldGUoc3ViSWQpO1xuICAgICAgICB0aGlzLmVvc2VDYWxsYmFja3MuZGVsZXRlKHN1YklkKTtcbiAgICB9XG5cbiAgICBwdWJsaXNoKGV2ZW50KSB7XG4gICAgICAgIGlmICghdGhpcy5jb25uZWN0ZWQgfHwgIXRoaXMud3MpIHtcbiAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcignTm90IGNvbm5lY3RlZCcpO1xuICAgICAgICB9XG4gICAgICAgIHRoaXMud3Muc2VuZChKU09OLnN0cmluZ2lmeShbJ0VWRU5UJywgZXZlbnRdKSk7XG4gICAgfVxuXG4gICAgc2NoZWR1bGVSZWNvbm5lY3QoKSB7XG4gICAgICAgIGlmICh0aGlzLnJlY29ubmVjdEF0dGVtcHRzID49IHRoaXMubWF4UmVjb25uZWN0QXR0ZW1wdHMpIHtcbiAgICAgICAgICAgIGxvZyhgTWF4IHJlY29ubmVjdCBhdHRlbXB0cyByZWFjaGVkIGZvciAke3RoaXMudXJsfWApO1xuICAgICAgICAgICAgcmV0dXJuO1xuICAgICAgICB9XG5cbiAgICAgICAgY29uc3QgZGVsYXkgPSBNYXRoLm1pbigxMDAwICogTWF0aC5wb3coMiwgdGhpcy5yZWNvbm5lY3RBdHRlbXB0cyksIDMwMDAwKTtcbiAgICAgICAgdGhpcy5yZWNvbm5lY3RBdHRlbXB0cysrO1xuXG4gICAgICAgIHRoaXMucmVjb25uZWN0VGltZXIgPSBzZXRUaW1lb3V0KCgpID0+IHtcbiAgICAgICAgICAgIGxvZyhgUmVjb25uZWN0aW5nIHRvICR7dGhpcy51cmx9IChhdHRlbXB0ICR7dGhpcy5yZWNvbm5lY3RBdHRlbXB0c30pYCk7XG4gICAgICAgICAgICB0aGlzLmNvbm5lY3QoKS5jYXRjaCgoKSA9PiB7fSk7XG4gICAgICAgIH0sIGRlbGF5KTtcbiAgICB9XG5cbiAgICBjbG9zZSgpIHtcbiAgICAgICAgY2xlYXJUaW1lb3V0KHRoaXMucmVjb25uZWN0VGltZXIpO1xuICAgICAgICB0aGlzLm1heFJlY29ubmVjdEF0dGVtcHRzID0gMDsgLy8gUHJldmVudCBmdXJ0aGVyIHJlY29ubmVjdHNcbiAgICAgICAgdGhpcy5zdWJzY3JpcHRpb25zLmNsZWFyKCk7XG4gICAgICAgIHRoaXMuZW9zZUNhbGxiYWNrcy5jbGVhcigpO1xuICAgICAgICBpZiAodGhpcy53cykge1xuICAgICAgICAgICAgdGhpcy53cy5jbG9zZSgpO1xuICAgICAgICAgICAgdGhpcy53cyA9IG51bGw7XG4gICAgICAgIH1cbiAgICAgICAgdGhpcy5jb25uZWN0ZWQgPSBmYWxzZTtcbiAgICB9XG59XG5cbi8qKlxuICogTklQLTQ2IEJ1bmtlciBTZXNzaW9uXG4gKlxuICogTWFuYWdlcyBhIHNlc3Npb24gd2l0aCBhIHJlbW90ZSBzaWduZXIgKG5zZWNCdW5rZXIpLlxuICogVXNlcyBhbiBlcGhlbWVyYWwga2V5cGFpciBmb3IgZW5jcnlwdGVkIGNvbW11bmljYXRpb24uXG4gKi9cbmV4cG9ydCBjbGFzcyBCdW5rZXJTZXNzaW9uIHtcbiAgICBjb25zdHJ1Y3Rvcih7IHJlbW90ZVB1YmtleSwgcmVsYXlzLCBzZWNyZXQgfSkge1xuICAgICAgICB0aGlzLnJlbW90ZVB1YmtleSA9IHJlbW90ZVB1YmtleTtcbiAgICAgICAgdGhpcy5yZWxheVVybHMgPSByZWxheXM7XG4gICAgICAgIHRoaXMuc2VjcmV0ID0gc2VjcmV0O1xuXG4gICAgICAgIC8vIEtleXBhaXIgd2lsbCBiZSBpbml0aWFsaXplZCBpbiBpbml0KClcbiAgICAgICAgdGhpcy5zZXNzaW9uUHJpdmtleSA9IG51bGw7XG4gICAgICAgIHRoaXMuc2Vzc2lvblB1YmtleSA9IG51bGw7XG4gICAgICAgIHRoaXMuY29udmVyc2F0aW9uS2V5ID0gbnVsbDtcblxuICAgICAgICB0aGlzLnJlbGF5cyA9IFtdO1xuICAgICAgICB0aGlzLnBlbmRpbmdSZXF1ZXN0cyA9IG5ldyBNYXAoKTtcbiAgICAgICAgdGhpcy5jb25uZWN0ZWQgPSBmYWxzZTtcbiAgICAgICAgdGhpcy5zdWJJZCA9IGBub3N0cmtleS0ke2NyeXB0by5yYW5kb21VVUlEKCkuc2xpY2UoMCwgOCl9YDtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBJbml0aWFsaXplIHRoZSBlcGhlbWVyYWwgc2Vzc2lvbiBrZXlwYWlyIChhc3luYylcbiAgICAgKi9cbiAgICBhc3luYyBpbml0KCkge1xuICAgICAgICBpZiAodGhpcy5zZXNzaW9uUHJpdmtleSkgcmV0dXJuOyAvLyBBbHJlYWR5IGluaXRpYWxpemVkXG5cbiAgICAgICAgLy8gR2VuZXJhdGUgZXBoZW1lcmFsIHNlc3Npb24ga2V5cGFpclxuICAgICAgICBjb25zdCBrZXlQYWlyID0gYXdhaXQgZ2VuZXJhdGVLZXlQYWlyKCk7XG4gICAgICAgIHRoaXMuc2Vzc2lvblByaXZrZXkgPSBoZXhUb0J5dGVzKGtleVBhaXIucHJpdmF0ZUtleSk7XG4gICAgICAgIHRoaXMuc2Vzc2lvblB1YmtleSA9IGtleVBhaXIucHVibGljS2V5O1xuXG4gICAgICAgIC8vIERlcml2ZSBOSVAtNDQgY29udmVyc2F0aW9uIGtleVxuICAgICAgICB0aGlzLmNvbnZlcnNhdGlvbktleSA9IG5pcDQ0LnYyLnV0aWxzLmdldENvbnZlcnNhdGlvbktleShcbiAgICAgICAgICAgIHRoaXMuc2Vzc2lvblByaXZrZXksXG4gICAgICAgICAgICB0aGlzLnJlbW90ZVB1YmtleVxuICAgICAgICApO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIENvbm5lY3QgdG8gYWxsIHJlbGF5cyBhbmQgc3Vic2NyaWJlIGZvciByZXNwb25zZXNcbiAgICAgKi9cbiAgICBhc3luYyBjb25uZWN0KCkge1xuICAgICAgICAvLyBFbnN1cmUga2V5cGFpciBpcyBpbml0aWFsaXplZFxuICAgICAgICBhd2FpdCB0aGlzLmluaXQoKTtcblxuICAgICAgICAvLyBDb25uZWN0IHRvIHJlbGF5c1xuICAgICAgICBjb25zdCBjb25uZWN0aW9ucyA9IHRoaXMucmVsYXlVcmxzLm1hcCh1cmwgPT4ge1xuICAgICAgICAgICAgY29uc3QgcmVsYXkgPSBuZXcgUmVsYXlDb25uZWN0aW9uKHVybCk7XG4gICAgICAgICAgICByZXR1cm4gcmVsYXkuY29ubmVjdCgpLnRoZW4oKCkgPT4ge1xuICAgICAgICAgICAgICAgIHRoaXMucmVsYXlzLnB1c2gocmVsYXkpO1xuICAgICAgICAgICAgICAgIHJldHVybiByZWxheTtcbiAgICAgICAgICAgIH0pO1xuICAgICAgICB9KTtcblxuICAgICAgICAvLyBXYWl0IGZvciBhdCBsZWFzdCBvbmUgY29ubmVjdGlvblxuICAgICAgICBjb25zdCByZXN1bHRzID0gYXdhaXQgUHJvbWlzZS5hbGxTZXR0bGVkKGNvbm5lY3Rpb25zKTtcbiAgICAgICAgY29uc3QgY29ubmVjdGVkID0gcmVzdWx0cy5maWx0ZXIociA9PiByLnN0YXR1cyA9PT0gJ2Z1bGZpbGxlZCcpO1xuXG4gICAgICAgIGlmIChjb25uZWN0ZWQubGVuZ3RoID09PSAwKSB7XG4gICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoJ0ZhaWxlZCB0byBjb25uZWN0IHRvIGFueSByZWxheScpO1xuICAgICAgICB9XG5cbiAgICAgICAgbG9nKGBDb25uZWN0ZWQgdG8gJHtjb25uZWN0ZWQubGVuZ3RofS8ke3RoaXMucmVsYXlVcmxzLmxlbmd0aH0gcmVsYXlzYCk7XG5cbiAgICAgICAgLy8gU3Vic2NyaWJlIGZvciBOSVAtNDYgcmVzcG9uc2VzIChraW5kIDI0MTMzIGFkZHJlc3NlZCB0byBvdXIgc2Vzc2lvbiBwdWJrZXkpXG4gICAgICAgIGZvciAoY29uc3QgcmVsYXkgb2YgdGhpcy5yZWxheXMpIHtcbiAgICAgICAgICAgIHJlbGF5LnN1YnNjcmliZShcbiAgICAgICAgICAgICAgICB0aGlzLnN1YklkLFxuICAgICAgICAgICAgICAgIFt7IGtpbmRzOiBbMjQxMzNdLCAnI3AnOiBbdGhpcy5zZXNzaW9uUHVia2V5XSB9XSxcbiAgICAgICAgICAgICAgICAoZXZlbnQpID0+IHRoaXMuaGFuZGxlUmVzcG9uc2UoZXZlbnQpXG4gICAgICAgICAgICApO1xuICAgICAgICB9XG5cbiAgICAgICAgdGhpcy5jb25uZWN0ZWQgPSB0cnVlO1xuXG4gICAgICAgIC8vIFNlbmQgY29ubmVjdCByZXF1ZXN0IGlmIHNlY3JldCBpcyBwcm92aWRlZFxuICAgICAgICBpZiAodGhpcy5zZWNyZXQpIHtcbiAgICAgICAgICAgIGF3YWl0IHRoaXMuc2VuZFJlcXVlc3QoJ2Nvbm5lY3QnLCBbdGhpcy5yZW1vdGVQdWJrZXksIHRoaXMuc2VjcmV0XSk7XG4gICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgICBhd2FpdCB0aGlzLnNlbmRSZXF1ZXN0KCdjb25uZWN0JywgW3RoaXMucmVtb3RlUHVia2V5XSk7XG4gICAgICAgIH1cbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBIYW5kbGUgYW4gaW5jb21pbmcgTklQLTQ2IHJlc3BvbnNlIGV2ZW50XG4gICAgICovXG4gICAgaGFuZGxlUmVzcG9uc2UoZXZlbnQpIHtcbiAgICAgICAgLy8gTXVzdCBiZSBmcm9tIHRoZSByZW1vdGUgc2lnbmVyXG4gICAgICAgIGlmIChldmVudC5wdWJrZXkgIT09IHRoaXMucmVtb3RlUHVia2V5KSB7XG4gICAgICAgICAgICBsb2coYElnbm9yaW5nIGV2ZW50IGZyb20gdW5rbm93biBwdWJrZXk6ICR7ZXZlbnQucHVia2V5fWApO1xuICAgICAgICAgICAgcmV0dXJuO1xuICAgICAgICB9XG5cbiAgICAgICAgdHJ5IHtcbiAgICAgICAgICAgIC8vIERlY3J5cHQgdGhlIHJlc3BvbnNlXG4gICAgICAgICAgICBjb25zdCBwbGFpbnRleHQgPSBuaXA0NC52Mi5kZWNyeXB0KGV2ZW50LmNvbnRlbnQsIHRoaXMuY29udmVyc2F0aW9uS2V5KTtcbiAgICAgICAgICAgIGNvbnN0IHJlc3BvbnNlID0gSlNPTi5wYXJzZShwbGFpbnRleHQpO1xuXG4gICAgICAgICAgICBsb2coYFJlc3BvbnNlOiAke3Jlc3BvbnNlLmlkfSAtPiAke3Jlc3BvbnNlLnJlc3VsdCA/ICdvaycgOiByZXNwb25zZS5lcnJvcn1gKTtcblxuICAgICAgICAgICAgY29uc3QgcGVuZGluZyA9IHRoaXMucGVuZGluZ1JlcXVlc3RzLmdldChyZXNwb25zZS5pZCk7XG4gICAgICAgICAgICBpZiAocGVuZGluZykge1xuICAgICAgICAgICAgICAgIHRoaXMucGVuZGluZ1JlcXVlc3RzLmRlbGV0ZShyZXNwb25zZS5pZCk7XG5cbiAgICAgICAgICAgICAgICBpZiAocmVzcG9uc2UuZXJyb3IpIHtcbiAgICAgICAgICAgICAgICAgICAgcGVuZGluZy5yZWplY3QobmV3IEVycm9yKHJlc3BvbnNlLmVycm9yKSk7XG4gICAgICAgICAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICAgICAgICAgICAgcGVuZGluZy5yZXNvbHZlKHJlc3BvbnNlLnJlc3VsdCk7XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfVxuICAgICAgICB9IGNhdGNoIChlKSB7XG4gICAgICAgICAgICBsb2coYEZhaWxlZCB0byBoYW5kbGUgcmVzcG9uc2U6ICR7ZS5tZXNzYWdlfWApO1xuICAgICAgICB9XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogU2VuZCBhbiBlbmNyeXB0ZWQgTklQLTQ2IHJlcXVlc3QgdG8gdGhlIGJ1bmtlclxuICAgICAqL1xuICAgIGFzeW5jIHNlbmRSZXF1ZXN0KG1ldGhvZCwgcGFyYW1zID0gW10pIHtcbiAgICAgICAgaWYgKCF0aGlzLmNvbm5lY3RlZCAmJiBtZXRob2QgIT09ICdjb25uZWN0Jykge1xuICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCdOb3QgY29ubmVjdGVkIHRvIGJ1bmtlcicpO1xuICAgICAgICB9XG5cbiAgICAgICAgY29uc3QgaWQgPSBjcnlwdG8ucmFuZG9tVVVJRCgpO1xuXG4gICAgICAgIGNvbnN0IHJlcXVlc3QgPSBKU09OLnN0cmluZ2lmeSh7IGlkLCBtZXRob2QsIHBhcmFtcyB9KTtcbiAgICAgICAgY29uc3QgZW5jcnlwdGVkID0gbmlwNDQudjIuZW5jcnlwdChyZXF1ZXN0LCB0aGlzLmNvbnZlcnNhdGlvbktleSk7XG5cbiAgICAgICAgLy8gQ3JlYXRlIGFuZCBzaWduIHRoZSBldmVudFxuICAgICAgICBjb25zdCBldmVudCA9IGF3YWl0IGZpbmFsaXplRXZlbnQoe1xuICAgICAgICAgICAga2luZDogMjQxMzMsXG4gICAgICAgICAgICBjb250ZW50OiBlbmNyeXB0ZWQsXG4gICAgICAgICAgICB0YWdzOiBbWydwJywgdGhpcy5yZW1vdGVQdWJrZXldXSxcbiAgICAgICAgICAgIGNyZWF0ZWRfYXQ6IE1hdGguZmxvb3IoRGF0ZS5ub3coKSAvIDEwMDApLFxuICAgICAgICB9LCB0aGlzLnNlc3Npb25Qcml2a2V5KTtcblxuICAgICAgICAvLyBQdWJsaXNoIHRvIGFsbCBjb25uZWN0ZWQgcmVsYXlzXG4gICAgICAgIGZvciAoY29uc3QgcmVsYXkgb2YgdGhpcy5yZWxheXMpIHtcbiAgICAgICAgICAgIHRyeSB7XG4gICAgICAgICAgICAgICAgcmVsYXkucHVibGlzaChldmVudCk7XG4gICAgICAgICAgICB9IGNhdGNoIChlKSB7XG4gICAgICAgICAgICAgICAgbG9nKGBGYWlsZWQgdG8gcHVibGlzaCB0byAke3JlbGF5LnVybH06ICR7ZS5tZXNzYWdlfWApO1xuICAgICAgICAgICAgfVxuICAgICAgICB9XG5cbiAgICAgICAgLy8gV2FpdCBmb3IgcmVzcG9uc2Ugd2l0aCB0aW1lb3V0XG4gICAgICAgIHJldHVybiBuZXcgUHJvbWlzZSgocmVzb2x2ZSwgcmVqZWN0KSA9PiB7XG4gICAgICAgICAgICBjb25zdCB0aW1lb3V0ID0gc2V0VGltZW91dCgoKSA9PiB7XG4gICAgICAgICAgICAgICAgdGhpcy5wZW5kaW5nUmVxdWVzdHMuZGVsZXRlKGlkKTtcbiAgICAgICAgICAgICAgICByZWplY3QobmV3IEVycm9yKGBSZXF1ZXN0IHRpbWVvdXQ6ICR7bWV0aG9kfWApKTtcbiAgICAgICAgICAgIH0sIDMwMDAwKTtcblxuICAgICAgICAgICAgdGhpcy5wZW5kaW5nUmVxdWVzdHMuc2V0KGlkLCB7XG4gICAgICAgICAgICAgICAgcmVzb2x2ZTogKHJlc3VsdCkgPT4ge1xuICAgICAgICAgICAgICAgICAgICBjbGVhclRpbWVvdXQodGltZW91dCk7XG4gICAgICAgICAgICAgICAgICAgIHJlc29sdmUocmVzdWx0KTtcbiAgICAgICAgICAgICAgICB9LFxuICAgICAgICAgICAgICAgIHJlamVjdDogKGVycm9yKSA9PiB7XG4gICAgICAgICAgICAgICAgICAgIGNsZWFyVGltZW91dCh0aW1lb3V0KTtcbiAgICAgICAgICAgICAgICAgICAgcmVqZWN0KGVycm9yKTtcbiAgICAgICAgICAgICAgICB9LFxuICAgICAgICAgICAgfSk7XG4gICAgICAgIH0pO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIE5JUC00NiBNZXRob2RzXG4gICAgICovXG5cbiAgICBhc3luYyBnZXRQdWJsaWNLZXkoKSB7XG4gICAgICAgIHJldHVybiBhd2FpdCB0aGlzLnNlbmRSZXF1ZXN0KCdnZXRfcHVibGljX2tleScpO1xuICAgIH1cblxuICAgIGFzeW5jIHNpZ25FdmVudChldmVudCkge1xuICAgICAgICBjb25zdCByZXN1bHQgPSBhd2FpdCB0aGlzLnNlbmRSZXF1ZXN0KCdzaWduX2V2ZW50JywgW0pTT04uc3RyaW5naWZ5KGV2ZW50KV0pO1xuICAgICAgICByZXR1cm4gSlNPTi5wYXJzZShyZXN1bHQpO1xuICAgIH1cblxuICAgIGFzeW5jIG5pcDA0RW5jcnlwdCh0aGlyZFBhcnR5UHVia2V5LCBwbGFpbnRleHQpIHtcbiAgICAgICAgcmV0dXJuIGF3YWl0IHRoaXMuc2VuZFJlcXVlc3QoJ25pcDA0X2VuY3J5cHQnLCBbdGhpcmRQYXJ0eVB1YmtleSwgcGxhaW50ZXh0XSk7XG4gICAgfVxuXG4gICAgYXN5bmMgbmlwMDREZWNyeXB0KHRoaXJkUGFydHlQdWJrZXksIGNpcGhlcnRleHQpIHtcbiAgICAgICAgcmV0dXJuIGF3YWl0IHRoaXMuc2VuZFJlcXVlc3QoJ25pcDA0X2RlY3J5cHQnLCBbdGhpcmRQYXJ0eVB1YmtleSwgY2lwaGVydGV4dF0pO1xuICAgIH1cblxuICAgIGFzeW5jIG5pcDQ0RW5jcnlwdCh0aGlyZFBhcnR5UHVia2V5LCBwbGFpbnRleHQpIHtcbiAgICAgICAgcmV0dXJuIGF3YWl0IHRoaXMuc2VuZFJlcXVlc3QoJ25pcDQ0X2VuY3J5cHQnLCBbdGhpcmRQYXJ0eVB1YmtleSwgcGxhaW50ZXh0XSk7XG4gICAgfVxuXG4gICAgYXN5bmMgbmlwNDREZWNyeXB0KHRoaXJkUGFydHlQdWJrZXksIGNpcGhlcnRleHQpIHtcbiAgICAgICAgcmV0dXJuIGF3YWl0IHRoaXMuc2VuZFJlcXVlc3QoJ25pcDQ0X2RlY3J5cHQnLCBbdGhpcmRQYXJ0eVB1YmtleSwgY2lwaGVydGV4dF0pO1xuICAgIH1cblxuICAgIGFzeW5jIHBpbmcoKSB7XG4gICAgICAgIHJldHVybiBhd2FpdCB0aGlzLnNlbmRSZXF1ZXN0KCdwaW5nJyk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogR2V0IHNlc3Npb24gaW5mbyBmb3IgcGVyc2lzdGVuY2VcbiAgICAgKi9cbiAgICBnZXRTZXNzaW9uSW5mbygpIHtcbiAgICAgICAgcmV0dXJuIHtcbiAgICAgICAgICAgIHJlbW90ZVB1YmtleTogdGhpcy5yZW1vdGVQdWJrZXksXG4gICAgICAgICAgICByZWxheVVybHM6IHRoaXMucmVsYXlVcmxzLFxuICAgICAgICAgICAgc2VjcmV0OiB0aGlzLnNlY3JldCxcbiAgICAgICAgICAgIHNlc3Npb25Qcml2a2V5OiBieXRlc1RvSGV4KHRoaXMuc2Vzc2lvblByaXZrZXkpLFxuICAgICAgICAgICAgc2Vzc2lvblB1YmtleTogdGhpcy5zZXNzaW9uUHVia2V5LFxuICAgICAgICB9O1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIERpc2Nvbm5lY3QgZnJvbSBhbGwgcmVsYXlzXG4gICAgICovXG4gICAgZGlzY29ubmVjdCgpIHtcbiAgICAgICAgZm9yIChjb25zdCByZWxheSBvZiB0aGlzLnJlbGF5cykge1xuICAgICAgICAgICAgcmVsYXkudW5zdWJzY3JpYmUodGhpcy5zdWJJZCk7XG4gICAgICAgICAgICByZWxheS5jbG9zZSgpO1xuICAgICAgICB9XG4gICAgICAgIHRoaXMucmVsYXlzID0gW107XG4gICAgICAgIHRoaXMucGVuZGluZ1JlcXVlc3RzLmNsZWFyKCk7XG4gICAgICAgIHRoaXMuY29ubmVjdGVkID0gZmFsc2U7XG4gICAgICAgIGxvZygnRGlzY29ubmVjdGVkIGZyb20gYnVua2VyJyk7XG4gICAgfVxufVxuXG4vKipcbiAqIFJlc3RvcmUgYSBzZXNzaW9uIGZyb20gcGVyc2lzdGVkIHNlc3Npb24gaW5mb1xuICovXG5leHBvcnQgZnVuY3Rpb24gcmVzdG9yZVNlc3Npb24oc2Vzc2lvbkluZm8pIHtcbiAgICBjb25zdCBzZXNzaW9uID0gbmV3IEJ1bmtlclNlc3Npb24oe1xuICAgICAgICByZW1vdGVQdWJrZXk6IHNlc3Npb25JbmZvLnJlbW90ZVB1YmtleSxcbiAgICAgICAgcmVsYXlzOiBzZXNzaW9uSW5mby5yZWxheVVybHMsXG4gICAgICAgIHNlY3JldDogc2Vzc2lvbkluZm8uc2VjcmV0LFxuICAgIH0pO1xuXG4gICAgLy8gUmVzdG9yZSB0aGUgb3JpZ2luYWwgc2Vzc2lvbiBrZXlwYWlyIGluc3RlYWQgb2YgZ2VuZXJhdGluZyBuZXcgb25lXG4gICAgc2Vzc2lvbi5zZXNzaW9uUHJpdmtleSA9IGhleFRvQnl0ZXMoc2Vzc2lvbkluZm8uc2Vzc2lvblByaXZrZXkpO1xuICAgIHNlc3Npb24uc2Vzc2lvblB1YmtleSA9IHNlc3Npb25JbmZvLnNlc3Npb25QdWJrZXk7XG4gICAgc2Vzc2lvbi5jb252ZXJzYXRpb25LZXkgPSBuaXA0NC52Mi51dGlscy5nZXRDb252ZXJzYXRpb25LZXkoXG4gICAgICAgIHNlc3Npb24uc2Vzc2lvblByaXZrZXksXG4gICAgICAgIHNlc3Npb24ucmVtb3RlUHVia2V5XG4gICAgKTtcblxuICAgIHJldHVybiBzZXNzaW9uO1xufVxuXG4vKipcbiAqIFNlc3Npb24gTWFuYWdlciBcdTIwMTQgbWFuYWdlcyBhY3RpdmUgYnVua2VyIHNlc3Npb25zIHBlciBwcm9maWxlXG4gKi9cblxuZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIGdldE9yQ3JlYXRlU2Vzc2lvbihwcm9maWxlSW5kZXgpIHtcbiAgICAvLyBDaGVjayBpZiB3ZSBoYXZlIGFuIGFjdGl2ZSBzZXNzaW9uXG4gICAgaWYgKHNlc3Npb25zLmhhcyhwcm9maWxlSW5kZXgpKSB7XG4gICAgICAgIGNvbnN0IHNlc3Npb24gPSBzZXNzaW9ucy5nZXQocHJvZmlsZUluZGV4KTtcbiAgICAgICAgaWYgKHNlc3Npb24uY29ubmVjdGVkKSB7XG4gICAgICAgICAgICByZXR1cm4gc2Vzc2lvbjtcbiAgICAgICAgfVxuICAgICAgICAvLyBTZXNzaW9uIGRpc2Nvbm5lY3RlZCwgY2xlYW4gdXBcbiAgICAgICAgc2Vzc2lvbi5kaXNjb25uZWN0KCk7XG4gICAgICAgIHNlc3Npb25zLmRlbGV0ZShwcm9maWxlSW5kZXgpO1xuICAgIH1cblxuICAgIC8vIFRyeSB0byByZXN0b3JlIGZyb20gcGVyc2lzdGVkIHNlc3Npb24gaW5mb1xuICAgIGNvbnN0IGRhdGEgPSBhd2FpdCBzdG9yYWdlLmdldCh7IGJ1bmtlclNlc3Npb25zOiB7fSB9KTtcbiAgICBjb25zdCBzZXNzaW9uSW5mbyA9IGRhdGEuYnVua2VyU2Vzc2lvbnM/Lltwcm9maWxlSW5kZXhdO1xuXG4gICAgaWYgKCFzZXNzaW9uSW5mbykge1xuICAgICAgICB0aHJvdyBuZXcgRXJyb3IoJ05vIGJ1bmtlciBzZXNzaW9uIGNvbmZpZ3VyZWQgZm9yIHRoaXMgcHJvZmlsZScpO1xuICAgIH1cblxuICAgIGNvbnN0IHNlc3Npb24gPSByZXN0b3JlU2Vzc2lvbihzZXNzaW9uSW5mbyk7XG4gICAgYXdhaXQgc2Vzc2lvbi5jb25uZWN0KCk7XG4gICAgc2Vzc2lvbnMuc2V0KHByb2ZpbGVJbmRleCwgc2Vzc2lvbik7XG4gICAgcmV0dXJuIHNlc3Npb247XG59XG5cbmV4cG9ydCBhc3luYyBmdW5jdGlvbiBjcmVhdGVTZXNzaW9uKHByb2ZpbGVJbmRleCwgYnVua2VyVXJsKSB7XG4gICAgLy8gRGlzY29ubmVjdCBleGlzdGluZyBzZXNzaW9uXG4gICAgaWYgKHNlc3Npb25zLmhhcyhwcm9maWxlSW5kZXgpKSB7XG4gICAgICAgIHNlc3Npb25zLmdldChwcm9maWxlSW5kZXgpLmRpc2Nvbm5lY3QoKTtcbiAgICAgICAgc2Vzc2lvbnMuZGVsZXRlKHByb2ZpbGVJbmRleCk7XG4gICAgfVxuXG4gICAgY29uc3QgY29uZmlnID0gcGFyc2VCdW5rZXJVcmwoYnVua2VyVXJsKTtcbiAgICBjb25zdCBzZXNzaW9uID0gbmV3IEJ1bmtlclNlc3Npb24oY29uZmlnKTtcbiAgICBhd2FpdCBzZXNzaW9uLmNvbm5lY3QoKTtcblxuICAgIC8vIFBlcnNpc3Qgc2Vzc2lvbiBpbmZvXG4gICAgY29uc3QgZGF0YSA9IGF3YWl0IHN0b3JhZ2UuZ2V0KHsgYnVua2VyU2Vzc2lvbnM6IHt9IH0pO1xuICAgIGNvbnN0IGJ1bmtlclNlc3Npb25zID0gZGF0YS5idW5rZXJTZXNzaW9ucyB8fCB7fTtcbiAgICBidW5rZXJTZXNzaW9uc1twcm9maWxlSW5kZXhdID0gc2Vzc2lvbi5nZXRTZXNzaW9uSW5mbygpO1xuICAgIGF3YWl0IHN0b3JhZ2Uuc2V0KHsgYnVua2VyU2Vzc2lvbnMgfSk7XG5cbiAgICBzZXNzaW9ucy5zZXQocHJvZmlsZUluZGV4LCBzZXNzaW9uKTtcbiAgICByZXR1cm4gc2Vzc2lvbjtcbn1cblxuZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIGRpc2Nvbm5lY3RTZXNzaW9uKHByb2ZpbGVJbmRleCkge1xuICAgIGlmIChzZXNzaW9ucy5oYXMocHJvZmlsZUluZGV4KSkge1xuICAgICAgICBzZXNzaW9ucy5nZXQocHJvZmlsZUluZGV4KS5kaXNjb25uZWN0KCk7XG4gICAgICAgIHNlc3Npb25zLmRlbGV0ZShwcm9maWxlSW5kZXgpO1xuICAgIH1cblxuICAgIC8vIFJlbW92ZSBwZXJzaXN0ZWQgc2Vzc2lvblxuICAgIGNvbnN0IGRhdGEgPSBhd2FpdCBzdG9yYWdlLmdldCh7IGJ1bmtlclNlc3Npb25zOiB7fSB9KTtcbiAgICBjb25zdCBidW5rZXJTZXNzaW9ucyA9IGRhdGEuYnVua2VyU2Vzc2lvbnMgfHwge307XG4gICAgZGVsZXRlIGJ1bmtlclNlc3Npb25zW3Byb2ZpbGVJbmRleF07XG4gICAgYXdhaXQgc3RvcmFnZS5zZXQoeyBidW5rZXJTZXNzaW9ucyB9KTtcbn1cblxuZXhwb3J0IGZ1bmN0aW9uIGlzU2Vzc2lvbkFjdGl2ZShwcm9maWxlSW5kZXgpIHtcbiAgICByZXR1cm4gc2Vzc2lvbnMuaGFzKHByb2ZpbGVJbmRleCkgJiYgc2Vzc2lvbnMuZ2V0KHByb2ZpbGVJbmRleCkuY29ubmVjdGVkO1xufVxuXG4vKipcbiAqIFZhbGlkYXRlIGEgYnVua2VyIFVSTCB3aXRob3V0IGNvbm5lY3RpbmdcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIHZhbGlkYXRlQnVua2VyVXJsKHVybCkge1xuICAgIHRyeSB7XG4gICAgICAgIHBhcnNlQnVua2VyVXJsKHVybCk7XG4gICAgICAgIHJldHVybiB7IHZhbGlkOiB0cnVlLCBlcnJvcjogbnVsbCB9O1xuICAgIH0gY2F0Y2ggKGUpIHtcbiAgICAgICAgcmV0dXJuIHsgdmFsaWQ6IGZhbHNlLCBlcnJvcjogZS5tZXNzYWdlIH07XG4gICAgfVxufVxuIiwgIi8qKlxuICogTklQLTQ2IEJ1bmtlciBTZXJ2ZXJcbiAqXG4gKiBUaGUgaW52ZXJzZSBvZiBCdW5rZXJTZXNzaW9uIGluIG5pcDQ2LmpzIFx1MjAxNCB0aGlzIG1ha2VzIHRoZSBOb3N0cktleVxuICogZXh0ZW5zaW9uIGFjdCBhcyBhIE5JUC00NiByZW1vdGUgc2lnbmVyIChidW5rZXIpLlxuICpcbiAqIEZsb3c6XG4gKiAgIDEuIEV4dGVuc2lvbiBnZW5lcmF0ZXMgYSBjb25uZWN0aW9uIHNlY3JldCBhbmQgb3BlbnMgYSBXZWJTb2NrZXQgdG8gdGhlIHJlbGF5XG4gKiAgIDIuIEV4dGVuc2lvbiBzdWJzY3JpYmVzIGZvciBraW5kIDI0MTMzIGV2ZW50cyB0YWdnZWQgd2l0aCB0aGUgdXNlcidzIHB1YmtleVxuICogICAzLiBBIHJlbW90ZSBjbGllbnQgc2VuZHMgYW4gZW5jcnlwdGVkIHJlcXVlc3QgKGNvbm5lY3QsIHNpZ25fZXZlbnQsIGV0Yy4pXG4gKiAgIDQuIEV4dGVuc2lvbiBkZWNyeXB0cywgZXhlY3V0ZXMsIGVuY3J5cHRzIHRoZSByZXNwb25zZSwgcHVibGlzaGVzIGJhY2tcbiAqXG4gKiBDb25uZWN0aW9uIHN0cmluZyBmb3JtYXQ6XG4gKiAgIGJ1bmtlcjovLzx1c2VyLXB1YmtleT4/cmVsYXk9d3NzOi8vLi4uJnNlY3JldD08cmFuZG9tPlxuICovXG5cbmltcG9ydCB7XG4gICAgZmluYWxpemVFdmVudCxcbiAgICBieXRlc1RvSGV4LFxuICAgIG5pcDA0LFxufSBmcm9tICdub3N0ci1jcnlwdG8tdXRpbHMnO1xuaW1wb3J0ICogYXMgbmlwNDQgZnJvbSAnbm9zdHItY3J5cHRvLXV0aWxzL25pcDQ0JztcbmltcG9ydCB7IFJlbGF5Q29ubmVjdGlvbiB9IGZyb20gJy4vbmlwNDYuanMnO1xuXG5jb25zdCBsb2cgPSBtc2cgPT4gY29uc29sZS5sb2coJ0J1bmtlclNlcnZlcjogJywgbXNnKTtcblxuZXhwb3J0IGNsYXNzIEJ1bmtlclNlcnZlciB7XG4gICAgLyoqXG4gICAgICogQHBhcmFtIHtPYmplY3R9IG9wdHNcbiAgICAgKiBAcGFyYW0ge3N0cmluZ1tdfSBvcHRzLnJlbGF5VXJscyAgLSByZWxheSBVUkxzIHRvIGNvbm5lY3QgdG9cbiAgICAgKiBAcGFyYW0ge3N0cmluZ30gICBvcHRzLnVzZXJQdWJrZXkgLSBoZXggcHVia2V5IG9mIHRoZSBsb2NhbCB1c2VyXG4gICAgICogQHBhcmFtIHtzdHJpbmd9ICAgb3B0cy5zZWNyZXQgICAgIC0gc2hhcmVkIHNlY3JldCBmb3IgY29ubmVjdCBoYW5kc2hha2VcbiAgICAgKi9cbiAgICBjb25zdHJ1Y3Rvcih7IHJlbGF5VXJscywgdXNlclB1YmtleSwgc2VjcmV0IH0pIHtcbiAgICAgICAgdGhpcy5yZWxheVVybHMgPSByZWxheVVybHM7XG4gICAgICAgIHRoaXMudXNlclB1YmtleSA9IHVzZXJQdWJrZXk7XG4gICAgICAgIHRoaXMuc2VjcmV0ID0gc2VjcmV0O1xuXG4gICAgICAgIHRoaXMucmVsYXlzID0gW107XG4gICAgICAgIHRoaXMuYXV0aGVudGljYXRlZENsaWVudHMgPSBuZXcgU2V0KCk7XG4gICAgICAgIHRoaXMuc3ViSWQgPSBgYnVua2VyLXNydi0ke2NyeXB0by5yYW5kb21VVUlEKCkuc2xpY2UoMCwgOCl9YDtcbiAgICAgICAgdGhpcy5hY3RpdmUgPSBmYWxzZTtcblxuICAgICAgICAvLyBXaWxsIGJlIHNldCBieSBzdGFydCgpXG4gICAgICAgIHRoaXMuX2dldFByaXZLZXkgPSBudWxsO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFN0YXJ0IHRoZSBidW5rZXIgc2VydmVyLlxuICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvcHRzXG4gICAgICogQHBhcmFtIHtGdW5jdGlvbn0gb3B0cy5nZXRQcml2S2V5IC0gYXN5bmMgKCkgPT4gVWludDhBcnJheSAodXNlcidzIHByaXZhdGUga2V5KVxuICAgICAqL1xuICAgIGFzeW5jIHN0YXJ0KHsgZ2V0UHJpdktleSB9KSB7XG4gICAgICAgIHRoaXMuX2dldFByaXZLZXkgPSBnZXRQcml2S2V5O1xuXG4gICAgICAgIC8vIENvbm5lY3QgdG8gcmVsYXlzXG4gICAgICAgIGNvbnN0IGNvbm5lY3Rpb25zID0gdGhpcy5yZWxheVVybHMubWFwKHVybCA9PiB7XG4gICAgICAgICAgICBjb25zdCByZWxheSA9IG5ldyBSZWxheUNvbm5lY3Rpb24odXJsKTtcbiAgICAgICAgICAgIHJldHVybiByZWxheS5jb25uZWN0KCkudGhlbigoKSA9PiB7XG4gICAgICAgICAgICAgICAgdGhpcy5yZWxheXMucHVzaChyZWxheSk7XG4gICAgICAgICAgICAgICAgcmV0dXJuIHJlbGF5O1xuICAgICAgICAgICAgfSk7XG4gICAgICAgIH0pO1xuXG4gICAgICAgIGNvbnN0IHJlc3VsdHMgPSBhd2FpdCBQcm9taXNlLmFsbFNldHRsZWQoY29ubmVjdGlvbnMpO1xuICAgICAgICBjb25zdCBjb25uZWN0ZWQgPSByZXN1bHRzLmZpbHRlcihyID0+IHIuc3RhdHVzID09PSAnZnVsZmlsbGVkJyk7XG5cbiAgICAgICAgaWYgKGNvbm5lY3RlZC5sZW5ndGggPT09IDApIHtcbiAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcignRmFpbGVkIHRvIGNvbm5lY3QgdG8gYW55IHJlbGF5Jyk7XG4gICAgICAgIH1cblxuICAgICAgICBsb2coYENvbm5lY3RlZCB0byAke2Nvbm5lY3RlZC5sZW5ndGh9LyR7dGhpcy5yZWxheVVybHMubGVuZ3RofSByZWxheXNgKTtcblxuICAgICAgICAvLyBTdWJzY3JpYmUgZm9yIGluY29taW5nIE5JUC00NiByZXF1ZXN0cyAoa2luZCAyNDEzMyB0YWdnZWQgd2l0aCBvdXIgcHVia2V5KVxuICAgICAgICBmb3IgKGNvbnN0IHJlbGF5IG9mIHRoaXMucmVsYXlzKSB7XG4gICAgICAgICAgICByZWxheS5zdWJzY3JpYmUoXG4gICAgICAgICAgICAgICAgdGhpcy5zdWJJZCxcbiAgICAgICAgICAgICAgICBbeyBraW5kczogWzI0MTMzXSwgJyNwJzogW3RoaXMudXNlclB1YmtleV0sIHNpbmNlOiBNYXRoLmZsb29yKERhdGUubm93KCkgLyAxMDAwKSAtIDUgfV0sXG4gICAgICAgICAgICAgICAgKGV2ZW50KSA9PiB0aGlzLl9oYW5kbGVSZXF1ZXN0KGV2ZW50KVxuICAgICAgICAgICAgKTtcbiAgICAgICAgfVxuXG4gICAgICAgIHRoaXMuYWN0aXZlID0gdHJ1ZTtcbiAgICAgICAgbG9nKCdCdW5rZXIgc2VydmVyIHN0YXJ0ZWQnKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBTdG9wIHRoZSBidW5rZXIgc2VydmVyLlxuICAgICAqL1xuICAgIHN0b3AoKSB7XG4gICAgICAgIGZvciAoY29uc3QgcmVsYXkgb2YgdGhpcy5yZWxheXMpIHtcbiAgICAgICAgICAgIHJlbGF5LnVuc3Vic2NyaWJlKHRoaXMuc3ViSWQpO1xuICAgICAgICAgICAgcmVsYXkuY2xvc2UoKTtcbiAgICAgICAgfVxuICAgICAgICB0aGlzLnJlbGF5cyA9IFtdO1xuICAgICAgICB0aGlzLmF1dGhlbnRpY2F0ZWRDbGllbnRzLmNsZWFyKCk7XG4gICAgICAgIHRoaXMuYWN0aXZlID0gZmFsc2U7XG4gICAgICAgIHRoaXMuX2dldFByaXZLZXkgPSBudWxsO1xuICAgICAgICBsb2coJ0J1bmtlciBzZXJ2ZXIgc3RvcHBlZCcpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIEdlbmVyYXRlIHRoZSBidW5rZXI6Ly8gY29ubmVjdGlvbiBzdHJpbmcuXG4gICAgICovXG4gICAgZ2V0Q29ubmVjdGlvblN0cmluZygpIHtcbiAgICAgICAgY29uc3QgcmVsYXlQYXJhbXMgPSB0aGlzLnJlbGF5VXJscy5tYXAodSA9PiBgcmVsYXk9JHtlbmNvZGVVUklDb21wb25lbnQodSl9YCkuam9pbignJicpO1xuICAgICAgICByZXR1cm4gYGJ1bmtlcjovLyR7dGhpcy51c2VyUHVia2V5fT8ke3JlbGF5UGFyYW1zfSZzZWNyZXQ9JHt0aGlzLnNlY3JldH1gO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIEhhbmRsZSBhbiBpbmNvbWluZyBOSVAtNDYgcmVxdWVzdCBldmVudC5cbiAgICAgKi9cbiAgICBhc3luYyBfaGFuZGxlUmVxdWVzdChldmVudCkge1xuICAgICAgICBjb25zdCBjbGllbnRQdWJrZXkgPSBldmVudC5wdWJrZXk7XG5cbiAgICAgICAgbGV0IHByaXZLZXk7XG4gICAgICAgIHRyeSB7XG4gICAgICAgICAgICBwcml2S2V5ID0gYXdhaXQgdGhpcy5fZ2V0UHJpdktleSgpO1xuICAgICAgICB9IGNhdGNoIChlKSB7XG4gICAgICAgICAgICBsb2coYENhbm5vdCBnZXQgcHJpdmF0ZSBrZXkgKGxvY2tlZD8pOiAke2UubWVzc2FnZX1gKTtcbiAgICAgICAgICAgIHJldHVybjtcbiAgICAgICAgfVxuXG4gICAgICAgIC8vIERlcml2ZSBjb252ZXJzYXRpb24ga2V5IHdpdGggdGhlIHJlcXVlc3RpbmcgY2xpZW50XG4gICAgICAgIGxldCBjb252ZXJzYXRpb25LZXk7XG4gICAgICAgIHRyeSB7XG4gICAgICAgICAgICBjb252ZXJzYXRpb25LZXkgPSBuaXA0NC52Mi51dGlscy5nZXRDb252ZXJzYXRpb25LZXkocHJpdktleSwgY2xpZW50UHVia2V5KTtcbiAgICAgICAgfSBjYXRjaCAoZSkge1xuICAgICAgICAgICAgbG9nKGBGYWlsZWQgdG8gZGVyaXZlIGNvbnZlcnNhdGlvbiBrZXk6ICR7ZS5tZXNzYWdlfWApO1xuICAgICAgICAgICAgcmV0dXJuO1xuICAgICAgICB9XG5cbiAgICAgICAgLy8gRGVjcnlwdCB0aGUgcmVxdWVzdFxuICAgICAgICBsZXQgcmVxdWVzdDtcbiAgICAgICAgdHJ5IHtcbiAgICAgICAgICAgIGNvbnN0IHBsYWludGV4dCA9IG5pcDQ0LnYyLmRlY3J5cHQoZXZlbnQuY29udGVudCwgY29udmVyc2F0aW9uS2V5KTtcbiAgICAgICAgICAgIHJlcXVlc3QgPSBKU09OLnBhcnNlKHBsYWludGV4dCk7XG4gICAgICAgIH0gY2F0Y2ggKGUpIHtcbiAgICAgICAgICAgIGxvZyhgRmFpbGVkIHRvIGRlY3J5cHQgcmVxdWVzdDogJHtlLm1lc3NhZ2V9YCk7XG4gICAgICAgICAgICByZXR1cm47XG4gICAgICAgIH1cblxuICAgICAgICBjb25zdCB7IGlkLCBtZXRob2QsIHBhcmFtcyB9ID0gcmVxdWVzdDtcbiAgICAgICAgbG9nKGBSZXF1ZXN0OiAke21ldGhvZH0gKGlkPSR7aWR9KSBmcm9tICR7Y2xpZW50UHVia2V5LnNsaWNlKDAsIDgpfS4uLmApO1xuXG4gICAgICAgIC8vIFNlY3VyaXR5OiByZWplY3QgdW5hdXRoZW50aWNhdGVkIGNsaWVudHMgZm9yIGV2ZXJ5dGhpbmcgZXhjZXB0IGNvbm5lY3RcbiAgICAgICAgaWYgKG1ldGhvZCAhPT0gJ2Nvbm5lY3QnICYmICF0aGlzLmF1dGhlbnRpY2F0ZWRDbGllbnRzLmhhcyhjbGllbnRQdWJrZXkpKSB7XG4gICAgICAgICAgICBhd2FpdCB0aGlzLl9zZW5kUmVzcG9uc2UocHJpdktleSwgY2xpZW50UHVia2V5LCBjb252ZXJzYXRpb25LZXksIHtcbiAgICAgICAgICAgICAgICBpZCxcbiAgICAgICAgICAgICAgICByZXN1bHQ6IG51bGwsXG4gICAgICAgICAgICAgICAgZXJyb3I6ICdVbmF1dGhvcml6ZWQ6IHNlbmQgY29ubmVjdCBmaXJzdCcsXG4gICAgICAgICAgICB9KTtcbiAgICAgICAgICAgIHJldHVybjtcbiAgICAgICAgfVxuXG4gICAgICAgIC8vIERpc3BhdGNoXG4gICAgICAgIGxldCByZXN1bHQgPSBudWxsO1xuICAgICAgICBsZXQgZXJyb3IgPSBudWxsO1xuXG4gICAgICAgIHRyeSB7XG4gICAgICAgICAgICBzd2l0Y2ggKG1ldGhvZCkge1xuICAgICAgICAgICAgICAgIGNhc2UgJ2Nvbm5lY3QnOiB7XG4gICAgICAgICAgICAgICAgICAgIC8vIHBhcmFtc1swXSA9IHJlbW90ZSBwdWJrZXkgKHNob3VsZCBtYXRjaCBvdXJzKSwgcGFyYW1zWzFdID0gc2VjcmV0XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IGNsaWVudFNlY3JldCA9IHBhcmFtc1sxXTtcbiAgICAgICAgICAgICAgICAgICAgLy8gRmFpbCBjbG9zZWQ6IGEgc2VydmVyIHdpdGggbm8gc2VjcmV0IG11c3QgTk9UIGF1dGhlbnRpY2F0ZVxuICAgICAgICAgICAgICAgICAgICAvLyBhbnlvbmUuIE90aGVyd2lzZSBhbnkgcmVsYXkgb2JzZXJ2ZXIgY291bGQgYGNvbm5lY3RgIGFuZCB0aGVuXG4gICAgICAgICAgICAgICAgICAgIC8vIHJlcXVlc3Qgc2lnbmluZy4gQSBzZWNyZXQgaXMgYWx3YXlzIHNldCB3aGVuIHN0YXJ0ZWQgdmlhIHRoZVxuICAgICAgICAgICAgICAgICAgICAvLyBleHRlbnNpb247IHRoaXMgZ3VhcmRzIGFnYWluc3QgYSBtaXMtY29uc3RydWN0ZWQgc2VydmVyLlxuICAgICAgICAgICAgICAgICAgICBpZiAoIXRoaXMuc2VjcmV0IHx8IGNsaWVudFNlY3JldCAhPT0gdGhpcy5zZWNyZXQpIHtcbiAgICAgICAgICAgICAgICAgICAgICAgIGVycm9yID0gJ0ludmFsaWQgc2VjcmV0JztcbiAgICAgICAgICAgICAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICAgICAgICAgICAgICAgIHRoaXMuYXV0aGVudGljYXRlZENsaWVudHMuYWRkKGNsaWVudFB1YmtleSk7XG4gICAgICAgICAgICAgICAgICAgICAgICByZXN1bHQgPSAnYWNrJztcbiAgICAgICAgICAgICAgICAgICAgICAgIGxvZyhgQ2xpZW50IGF1dGhlbnRpY2F0ZWQ6ICR7Y2xpZW50UHVia2V5LnNsaWNlKDAsIDgpfS4uLmApO1xuICAgICAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgICAgIGJyZWFrO1xuICAgICAgICAgICAgICAgIH1cblxuICAgICAgICAgICAgICAgIGNhc2UgJ2dldF9wdWJsaWNfa2V5JzpcbiAgICAgICAgICAgICAgICAgICAgcmVzdWx0ID0gdGhpcy51c2VyUHVia2V5O1xuICAgICAgICAgICAgICAgICAgICBicmVhaztcblxuICAgICAgICAgICAgICAgIGNhc2UgJ3NpZ25fZXZlbnQnOiB7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHVuc2lnbmVkID0gSlNPTi5wYXJzZShwYXJhbXNbMF0pO1xuICAgICAgICAgICAgICAgICAgICBjb25zdCBzaWduZWQgPSBhd2FpdCBmaW5hbGl6ZUV2ZW50KHVuc2lnbmVkLCBwcml2S2V5KTtcbiAgICAgICAgICAgICAgICAgICAgcmVzdWx0ID0gSlNPTi5zdHJpbmdpZnkoc2lnbmVkKTtcbiAgICAgICAgICAgICAgICAgICAgYnJlYWs7XG4gICAgICAgICAgICAgICAgfVxuXG4gICAgICAgICAgICAgICAgY2FzZSAnbmlwNDRfZW5jcnlwdCc6IHtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgdGhpcmRQYXJ0eVB1YmtleSA9IHBhcmFtc1swXTtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgcGxhaW50ZXh0ID0gcGFyYW1zWzFdO1xuICAgICAgICAgICAgICAgICAgICBjb25zdCBjayA9IG5pcDQ0LnYyLnV0aWxzLmdldENvbnZlcnNhdGlvbktleShwcml2S2V5LCB0aGlyZFBhcnR5UHVia2V5KTtcbiAgICAgICAgICAgICAgICAgICAgcmVzdWx0ID0gbmlwNDQudjIuZW5jcnlwdChwbGFpbnRleHQsIGNrKTtcbiAgICAgICAgICAgICAgICAgICAgYnJlYWs7XG4gICAgICAgICAgICAgICAgfVxuXG4gICAgICAgICAgICAgICAgY2FzZSAnbmlwNDRfZGVjcnlwdCc6IHtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgdGhpcmRQYXJ0eVB1YmtleSA9IHBhcmFtc1swXTtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgY2lwaGVydGV4dCA9IHBhcmFtc1sxXTtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgY2sgPSBuaXA0NC52Mi51dGlscy5nZXRDb252ZXJzYXRpb25LZXkocHJpdktleSwgdGhpcmRQYXJ0eVB1YmtleSk7XG4gICAgICAgICAgICAgICAgICAgIHJlc3VsdCA9IG5pcDQ0LnYyLmRlY3J5cHQoY2lwaGVydGV4dCwgY2spO1xuICAgICAgICAgICAgICAgICAgICBicmVhaztcbiAgICAgICAgICAgICAgICB9XG5cbiAgICAgICAgICAgICAgICBjYXNlICduaXAwNF9lbmNyeXB0Jzoge1xuICAgICAgICAgICAgICAgICAgICBjb25zdCB0aGlyZFBhcnR5UHVia2V5ID0gcGFyYW1zWzBdO1xuICAgICAgICAgICAgICAgICAgICBjb25zdCBwbGFpbnRleHQgPSBwYXJhbXNbMV07XG4gICAgICAgICAgICAgICAgICAgIHJlc3VsdCA9IGF3YWl0IG5pcDA0LmVuY3J5cHRNZXNzYWdlKHBsYWludGV4dCwgYnl0ZXNUb0hleChwcml2S2V5KSwgdGhpcmRQYXJ0eVB1YmtleSk7XG4gICAgICAgICAgICAgICAgICAgIGJyZWFrO1xuICAgICAgICAgICAgICAgIH1cblxuICAgICAgICAgICAgICAgIGNhc2UgJ25pcDA0X2RlY3J5cHQnOiB7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHRoaXJkUGFydHlQdWJrZXkgPSBwYXJhbXNbMF07XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IGNpcGhlcnRleHQgPSBwYXJhbXNbMV07XG4gICAgICAgICAgICAgICAgICAgIHJlc3VsdCA9IGF3YWl0IG5pcDA0LmRlY3J5cHRNZXNzYWdlKGNpcGhlcnRleHQsIGJ5dGVzVG9IZXgocHJpdktleSksIHRoaXJkUGFydHlQdWJrZXkpO1xuICAgICAgICAgICAgICAgICAgICBicmVhaztcbiAgICAgICAgICAgICAgICB9XG5cbiAgICAgICAgICAgICAgICBjYXNlICdwaW5nJzpcbiAgICAgICAgICAgICAgICAgICAgcmVzdWx0ID0gJ3BvbmcnO1xuICAgICAgICAgICAgICAgICAgICBicmVhaztcblxuICAgICAgICAgICAgICAgIGRlZmF1bHQ6XG4gICAgICAgICAgICAgICAgICAgIGVycm9yID0gYFVuc3VwcG9ydGVkIG1ldGhvZDogJHttZXRob2R9YDtcbiAgICAgICAgICAgIH1cbiAgICAgICAgfSBjYXRjaCAoZSkge1xuICAgICAgICAgICAgZXJyb3IgPSBlLm1lc3NhZ2U7XG4gICAgICAgICAgICBsb2coYEVycm9yIGhhbmRsaW5nICR7bWV0aG9kfTogJHtlLm1lc3NhZ2V9YCk7XG4gICAgICAgIH1cblxuICAgICAgICBhd2FpdCB0aGlzLl9zZW5kUmVzcG9uc2UocHJpdktleSwgY2xpZW50UHVia2V5LCBjb252ZXJzYXRpb25LZXksIHsgaWQsIHJlc3VsdCwgZXJyb3IgfSk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogRW5jcnlwdCBhbmQgcHVibGlzaCBhIE5JUC00NiByZXNwb25zZS5cbiAgICAgKi9cbiAgICBhc3luYyBfc2VuZFJlc3BvbnNlKHByaXZLZXksIGNsaWVudFB1YmtleSwgY29udmVyc2F0aW9uS2V5LCByZXNwb25zZSkge1xuICAgICAgICBjb25zdCBlbmNyeXB0ZWQgPSBuaXA0NC52Mi5lbmNyeXB0KEpTT04uc3RyaW5naWZ5KHJlc3BvbnNlKSwgY29udmVyc2F0aW9uS2V5KTtcblxuICAgICAgICBjb25zdCBldmVudCA9IGF3YWl0IGZpbmFsaXplRXZlbnQoe1xuICAgICAgICAgICAga2luZDogMjQxMzMsXG4gICAgICAgICAgICBjb250ZW50OiBlbmNyeXB0ZWQsXG4gICAgICAgICAgICB0YWdzOiBbWydwJywgY2xpZW50UHVia2V5XV0sXG4gICAgICAgICAgICBjcmVhdGVkX2F0OiBNYXRoLmZsb29yKERhdGUubm93KCkgLyAxMDAwKSxcbiAgICAgICAgfSwgcHJpdktleSk7XG5cbiAgICAgICAgZm9yIChjb25zdCByZWxheSBvZiB0aGlzLnJlbGF5cykge1xuICAgICAgICAgICAgdHJ5IHtcbiAgICAgICAgICAgICAgICByZWxheS5wdWJsaXNoKGV2ZW50KTtcbiAgICAgICAgICAgIH0gY2F0Y2ggKGUpIHtcbiAgICAgICAgICAgICAgICBsb2coYEZhaWxlZCB0byBwdWJsaXNoIHJlc3BvbnNlIHRvICR7cmVsYXkudXJsfTogJHtlLm1lc3NhZ2V9YCk7XG4gICAgICAgICAgICB9XG4gICAgICAgIH1cblxuICAgICAgICBsb2coYFJlc3BvbnNlIHNlbnQ6ICR7cmVzcG9uc2UuaWR9ICR7cmVzcG9uc2UuZXJyb3IgPyAnRVJST1InIDogJ09LJ31gKTtcbiAgICB9XG59XG4iLCAiLyoqXG4gKiBOSVAtNzggRW5jcnlwdGVkIFZhdWx0IFByb3RvY29sXG4gKlxuICogUHVyZSBmdW5jdGlvbnMgZm9yIGJ1aWxkaW5nL3BhcnNpbmcga2luZCAzMDA3OCAocGFyYW1ldGVyaXplZCByZXBsYWNlYWJsZSlcbiAqIGV2ZW50cyB1c2VkIGFzIGFuIGVuY3J5cHRlZCBtYXJrZG93biBkb2N1bWVudCB2YXVsdC5cbiAqXG4gKiBkLXRhZyBwcmVmaXggXCJub3N0cmtleTpcIiBuYW1lc3BhY2VzIG91ciB2YXVsdCBpdGVtcyBmcm9tIG90aGVyIE5JUC03OCBhcHBzLlxuICogUmVsYXlzIHNlZSBmaWxlIHBhdGhzIGJ1dCBub3QgY29udGVudCAoTklQLTQ0IGVuY3J5cHRlZCB0byBzZWxmKS5cbiAqL1xuXG5jb25zdCBLSU5EX0FQUF9EQVRBID0gMzAwNzg7XG5jb25zdCBLSU5EX0RFTEVUSU9OID0gNTtcbmNvbnN0IERUQUdfUFJFRklYID0gJ25vc3Rya2V5Oic7XG5jb25zdCBDTElFTlRfVEFHID0gJ25vc3Rya2V5JztcblxuLyoqXG4gKiBCdWlsZCBhbiB1bnNpZ25lZCBraW5kIDMwMDc4IHZhdWx0IGV2ZW50LlxuICogQ2FsbGVyIG11c3Qgc2lnbiAoZmluYWxpemVFdmVudCBvciBidW5rZXIgc2Vzc2lvbi5zaWduRXZlbnQpLlxuICpcbiAqIEBwYXJhbSB7c3RyaW5nfSBwYXRoIC0gRG9jdW1lbnQgcGF0aCAoZS5nLiBcIm5vdGVzL3RvZG8ubWRcIilcbiAqIEBwYXJhbSB7c3RyaW5nfSBlbmNyeXB0ZWRDb250ZW50IC0gTklQLTQ0IGVuY3J5cHRlZCBjb250ZW50IHN0cmluZ1xuICogQHJldHVybnMge29iamVjdH0gVW5zaWduZWQgZXZlbnQgdGVtcGxhdGVcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGJ1aWxkVmF1bHRFdmVudChwYXRoLCBlbmNyeXB0ZWRDb250ZW50KSB7XG4gICAgcmV0dXJuIHtcbiAgICAgICAga2luZDogS0lORF9BUFBfREFUQSxcbiAgICAgICAgY29udGVudDogZW5jcnlwdGVkQ29udGVudCxcbiAgICAgICAgdGFnczogW1xuICAgICAgICAgICAgWydkJywgYCR7RFRBR19QUkVGSVh9JHtwYXRofWBdLFxuICAgICAgICAgICAgWydjbGllbnQnLCBDTElFTlRfVEFHXSxcbiAgICAgICAgXSxcbiAgICAgICAgY3JlYXRlZF9hdDogTWF0aC5mbG9vcihEYXRlLm5vdygpIC8gMTAwMCksXG4gICAgfTtcbn1cblxuLyoqXG4gKiBCdWlsZCBhbiB1bnNpZ25lZCBraW5kIDUgZGVsZXRpb24gZXZlbnQgKE5JUC0wOSkgZm9yIGEgdmF1bHQgZG9jdW1lbnQuXG4gKlxuICogQHBhcmFtIHtzdHJpbmd9IGV2ZW50SWQgLSBUaGUgZXZlbnQgaWQgdG8gZGVsZXRlXG4gKiBAcGFyYW0ge3N0cmluZ30gcGF0aCAtIERvY3VtZW50IHBhdGggKGZvciB0aGUgYS10YWcgcmVmZXJlbmNlKVxuICogQHJldHVybnMge29iamVjdH0gVW5zaWduZWQgZGVsZXRpb24gZXZlbnQgdGVtcGxhdGVcbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGJ1aWxkVmF1bHREZWxldGlvbihldmVudElkLCBwYXRoKSB7XG4gICAgcmV0dXJuIHtcbiAgICAgICAga2luZDogS0lORF9ERUxFVElPTixcbiAgICAgICAgY29udGVudDogJ3ZhdWx0IGRvY3VtZW50IGRlbGV0ZWQnLFxuICAgICAgICB0YWdzOiBbXG4gICAgICAgICAgICBbJ2UnLCBldmVudElkXSxcbiAgICAgICAgICAgIFsnYScsIGAke0tJTkRfQVBQX0RBVEF9Ojoke0RUQUdfUFJFRklYfSR7cGF0aH1gXSxcbiAgICAgICAgXSxcbiAgICAgICAgY3JlYXRlZF9hdDogTWF0aC5mbG9vcihEYXRlLm5vdygpIC8gMTAwMCksXG4gICAgfTtcbn1cblxuLyoqXG4gKiBCdWlsZCBhIFJFUSBmaWx0ZXIgZm9yIGZldGNoaW5nIGFsbCB2YXVsdCBkb2N1bWVudHMgZm9yIGEgcHVia2V5LlxuICpcbiAqIEBwYXJhbSB7c3RyaW5nfSBwdWJrZXkgLSBIZXggcHVibGljIGtleVxuICogQHJldHVybnMge29iamVjdH0gTm9zdHIgUkVRIGZpbHRlclxuICovXG5leHBvcnQgZnVuY3Rpb24gYnVpbGRWYXVsdEZpbHRlcihwdWJrZXkpIHtcbiAgICByZXR1cm4ge1xuICAgICAgICBraW5kczogW0tJTkRfQVBQX0RBVEFdLFxuICAgICAgICBhdXRob3JzOiBbcHVia2V5XSxcbiAgICB9O1xufVxuXG4vKipcbiAqIFBhcnNlIGEga2luZCAzMDA3OCBldmVudCBpbnRvIGEgdmF1bHQgZG9jdW1lbnQgZGVzY3JpcHRvci5cbiAqIFJldHVybnMgbnVsbCBpZiB0aGUgZXZlbnQgaXMgbm90IGEgbm9zdHJrZXkgdmF1bHQgZXZlbnQuXG4gKlxuICogQHBhcmFtIHtvYmplY3R9IGV2ZW50IC0gTm9zdHIgZXZlbnRcbiAqIEByZXR1cm5zIHt7IHBhdGg6IHN0cmluZywgY29udGVudDogc3RyaW5nLCBjcmVhdGVkQXQ6IG51bWJlciwgZXZlbnRJZDogc3RyaW5nIH0gfCBudWxsfVxuICovXG5leHBvcnQgZnVuY3Rpb24gcGFyc2VWYXVsdEV2ZW50KGV2ZW50KSB7XG4gICAgaWYgKGV2ZW50LmtpbmQgIT09IEtJTkRfQVBQX0RBVEEpIHJldHVybiBudWxsO1xuXG4gICAgY29uc3QgZFRhZyA9IGV2ZW50LnRhZ3M/LmZpbmQodCA9PiB0WzBdID09PSAnZCcpO1xuICAgIGlmICghZFRhZyB8fCAhZFRhZ1sxXT8uc3RhcnRzV2l0aChEVEFHX1BSRUZJWCkpIHJldHVybiBudWxsO1xuXG4gICAgY29uc3QgcGF0aCA9IGRUYWdbMV0uc2xpY2UoRFRBR19QUkVGSVgubGVuZ3RoKTtcbiAgICBpZiAoIXBhdGgpIHJldHVybiBudWxsO1xuXG4gICAgcmV0dXJuIHtcbiAgICAgICAgcGF0aCxcbiAgICAgICAgY29udGVudDogZXZlbnQuY29udGVudCxcbiAgICAgICAgY3JlYXRlZEF0OiBldmVudC5jcmVhdGVkX2F0LFxuICAgICAgICBldmVudElkOiBldmVudC5pZCxcbiAgICB9O1xufVxuIl0sCiAgIm1hcHBpbmdzIjogIjs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7QUFBQSxNQU1XO0FBTlg7QUFBQTtBQU1PLE1BQUksVUFBVTtBQUFBLFFBQ2pCLEtBQUssRUFBRSxVQUFVLGNBQWMsV0FBVyxPQUFPO0FBQUEsUUFDakQsU0FBUztBQUFBLFFBQ1QsU0FBUztBQUFBLFFBQ1QsUUFBUTtBQUFBLFFBQ1IsUUFBUTtBQUFBLFFBQ1IsVUFBVSxTQUFVLElBQUk7QUFDcEIsY0FBSSxPQUFPLE1BQU0sVUFBVSxNQUFNLEtBQUssV0FBVyxDQUFDO0FBQ2xELGtCQUFRLFFBQVEsRUFBRSxLQUFLLFdBQVk7QUFBRSxlQUFHLE1BQU0sTUFBTSxJQUFJO0FBQUEsVUFBRyxDQUFDO0FBQUEsUUFDaEU7QUFBQSxNQUNKO0FBQUE7QUFBQTs7O0FDaEJBO0FBQUE7QUFBQTtBQUFBO0FBQ0EsZUFBUyxhQUFjLEdBQUc7QUFDeEIsWUFBSTtBQUFFLGlCQUFPLEtBQUssVUFBVSxDQUFDO0FBQUEsUUFBRSxTQUFRLEdBQUc7QUFBRSxpQkFBTztBQUFBLFFBQWU7QUFBQSxNQUNwRTtBQUVBLGFBQU8sVUFBVTtBQUVqQixlQUFTLE9BQU8sR0FBRyxNQUFNLE1BQU07QUFDN0IsWUFBSSxLQUFNLFFBQVEsS0FBSyxhQUFjO0FBQ3JDLFlBQUksU0FBUztBQUNiLFlBQUksT0FBTyxNQUFNLFlBQVksTUFBTSxNQUFNO0FBQ3ZDLGNBQUksTUFBTSxLQUFLLFNBQVM7QUFDeEIsY0FBSSxRQUFRLEVBQUcsUUFBTztBQUN0QixjQUFJLFVBQVUsSUFBSSxNQUFNLEdBQUc7QUFDM0Isa0JBQVEsQ0FBQyxJQUFJLEdBQUcsQ0FBQztBQUNqQixtQkFBUyxRQUFRLEdBQUcsUUFBUSxLQUFLLFNBQVM7QUFDeEMsb0JBQVEsS0FBSyxJQUFJLEdBQUcsS0FBSyxLQUFLLENBQUM7QUFBQSxVQUNqQztBQUNBLGlCQUFPLFFBQVEsS0FBSyxHQUFHO0FBQUEsUUFDekI7QUFDQSxZQUFJLE9BQU8sTUFBTSxVQUFVO0FBQ3pCLGlCQUFPO0FBQUEsUUFDVDtBQUNBLFlBQUksU0FBUyxLQUFLO0FBQ2xCLFlBQUksV0FBVyxFQUFHLFFBQU87QUFDekIsWUFBSSxNQUFNO0FBQ1YsWUFBSSxJQUFJLElBQUk7QUFDWixZQUFJLFVBQVU7QUFDZCxZQUFJLE9BQVEsS0FBSyxFQUFFLFVBQVc7QUFDOUIsaUJBQVMsSUFBSSxHQUFHLElBQUksUUFBTztBQUN6QixjQUFJLEVBQUUsV0FBVyxDQUFDLE1BQU0sTUFBTSxJQUFJLElBQUksTUFBTTtBQUMxQyxzQkFBVSxVQUFVLEtBQUssVUFBVTtBQUNuQyxvQkFBUSxFQUFFLFdBQVcsSUFBSSxDQUFDLEdBQUc7QUFBQSxjQUMzQixLQUFLO0FBQUE7QUFBQSxjQUNMLEtBQUs7QUFDSCxvQkFBSSxLQUFLO0FBQ1A7QUFDRixvQkFBSSxLQUFLLENBQUMsS0FBSyxLQUFPO0FBQ3RCLG9CQUFJLFVBQVU7QUFDWix5QkFBTyxFQUFFLE1BQU0sU0FBUyxDQUFDO0FBQzNCLHVCQUFPLE9BQU8sS0FBSyxDQUFDLENBQUM7QUFDckIsMEJBQVUsSUFBSTtBQUNkO0FBQ0E7QUFBQSxjQUNGLEtBQUs7QUFDSCxvQkFBSSxLQUFLO0FBQ1A7QUFDRixvQkFBSSxLQUFLLENBQUMsS0FBSyxLQUFPO0FBQ3RCLG9CQUFJLFVBQVU7QUFDWix5QkFBTyxFQUFFLE1BQU0sU0FBUyxDQUFDO0FBQzNCLHVCQUFPLEtBQUssTUFBTSxPQUFPLEtBQUssQ0FBQyxDQUFDLENBQUM7QUFDakMsMEJBQVUsSUFBSTtBQUNkO0FBQ0E7QUFBQSxjQUNGLEtBQUs7QUFBQTtBQUFBLGNBQ0wsS0FBSztBQUFBO0FBQUEsY0FDTCxLQUFLO0FBQ0gsb0JBQUksS0FBSztBQUNQO0FBQ0Ysb0JBQUksS0FBSyxDQUFDLE1BQU0sT0FBVztBQUMzQixvQkFBSSxVQUFVO0FBQ1oseUJBQU8sRUFBRSxNQUFNLFNBQVMsQ0FBQztBQUMzQixvQkFBSSxPQUFPLE9BQU8sS0FBSyxDQUFDO0FBQ3hCLG9CQUFJLFNBQVMsVUFBVTtBQUNyQix5QkFBTyxNQUFPLEtBQUssQ0FBQyxJQUFJO0FBQ3hCLDRCQUFVLElBQUk7QUFDZDtBQUNBO0FBQUEsZ0JBQ0Y7QUFDQSxvQkFBSSxTQUFTLFlBQVk7QUFDdkIseUJBQU8sS0FBSyxDQUFDLEVBQUUsUUFBUTtBQUN2Qiw0QkFBVSxJQUFJO0FBQ2Q7QUFDQTtBQUFBLGdCQUNGO0FBQ0EsdUJBQU8sR0FBRyxLQUFLLENBQUMsQ0FBQztBQUNqQiwwQkFBVSxJQUFJO0FBQ2Q7QUFDQTtBQUFBLGNBQ0YsS0FBSztBQUNILG9CQUFJLEtBQUs7QUFDUDtBQUNGLG9CQUFJLFVBQVU7QUFDWix5QkFBTyxFQUFFLE1BQU0sU0FBUyxDQUFDO0FBQzNCLHVCQUFPLE9BQU8sS0FBSyxDQUFDLENBQUM7QUFDckIsMEJBQVUsSUFBSTtBQUNkO0FBQ0E7QUFBQSxjQUNGLEtBQUs7QUFDSCxvQkFBSSxVQUFVO0FBQ1oseUJBQU8sRUFBRSxNQUFNLFNBQVMsQ0FBQztBQUMzQix1QkFBTztBQUNQLDBCQUFVLElBQUk7QUFDZDtBQUNBO0FBQ0E7QUFBQSxZQUNKO0FBQ0EsY0FBRTtBQUFBLFVBQ0o7QUFDQSxZQUFFO0FBQUEsUUFDSjtBQUNBLFlBQUksWUFBWTtBQUNkLGlCQUFPO0FBQUEsaUJBQ0EsVUFBVSxNQUFNO0FBQ3ZCLGlCQUFPLEVBQUUsTUFBTSxPQUFPO0FBQUEsUUFDeEI7QUFFQSxlQUFPO0FBQUEsTUFDVDtBQUFBO0FBQUE7OztBQzVHQTtBQUFBO0FBQUE7QUFBQTtBQUVBLFVBQU0sU0FBUztBQUVmLGFBQU8sVUFBVUE7QUFFakIsVUFBTSxXQUFXLHVCQUF1QixFQUFFLFdBQVcsQ0FBQztBQUN0RCxVQUFNLGlCQUFpQjtBQUFBLFFBQ3JCLGdCQUFnQjtBQUFBLFFBQ2hCLGlCQUFpQjtBQUFBLFFBQ2pCLHVCQUF1QjtBQUFBLFFBQ3ZCLHdCQUF3QjtBQUFBLFFBQ3hCLHFCQUFxQjtBQUFBLFFBQ3JCLEtBQUs7QUFBQSxRQUNMLEtBQUs7QUFBQSxRQUNMLEtBQUs7QUFBQSxRQUNMLGNBQWM7QUFBQSxNQUNoQjtBQUNBLGVBQVMsYUFBYyxPQUFPQyxTQUFRO0FBQ3BDLGVBQU8sVUFBVSxXQUNiLFdBQ0FBLFFBQU8sT0FBTyxPQUFPLEtBQUs7QUFBQSxNQUNoQztBQUNBLFVBQU0sd0JBQXdCLHVCQUFPLGVBQWU7QUFDcEQsVUFBTSxrQkFBa0IsdUJBQU8sZ0JBQWdCO0FBRS9DLFVBQU0saUJBQWlCO0FBQUEsUUFDckIsT0FBTztBQUFBLFFBQ1AsT0FBTztBQUFBLFFBQ1AsTUFBTTtBQUFBLFFBQ04sTUFBTTtBQUFBLFFBQ04sT0FBTztBQUFBLFFBQ1AsT0FBTztBQUFBLE1BQ1Q7QUFFQSxlQUFTLGtCQUFtQixjQUFjLGFBQWE7QUFDckQsY0FBTSxXQUFXO0FBQUEsVUFDZixRQUFRO0FBQUEsVUFDUixRQUFRLGFBQWEsZUFBZTtBQUFBLFFBQ3RDO0FBQ0Esb0JBQVksZUFBZSxJQUFJO0FBQUEsTUFDakM7QUFFQSxlQUFTLHNCQUF1QkEsU0FBUSxRQUFRLE9BQU87QUFDckQsY0FBTSxlQUFlLENBQUM7QUFDdEIsZUFBTyxRQUFRLFdBQVM7QUFDdEIsdUJBQWEsS0FBSyxJQUFJLE1BQU0sS0FBSyxJQUFJLE1BQU0sS0FBSyxJQUFLLFNBQVMsS0FBSyxLQUFLLFNBQVMsZUFBZSxLQUFLLEtBQUssS0FBSyxLQUFLO0FBQUEsUUFDdEgsQ0FBQztBQUNELFFBQUFBLFFBQU8scUJBQXFCLElBQUk7QUFBQSxNQUNsQztBQUVBLGVBQVMsZ0JBQWlCLFdBQVcsYUFBYTtBQUNoRCxZQUFJLE1BQU0sUUFBUSxTQUFTLEdBQUc7QUFDNUIsZ0JBQU0sY0FBYyxVQUFVLE9BQU8sU0FBVSxHQUFHO0FBQ2hELG1CQUFPLE1BQU07QUFBQSxVQUNmLENBQUM7QUFDRCxpQkFBTztBQUFBLFFBQ1QsV0FBVyxjQUFjLE1BQU07QUFDN0IsaUJBQU8sT0FBTyxLQUFLLFdBQVc7QUFBQSxRQUNoQztBQUVBLGVBQU87QUFBQSxNQUNUO0FBRUEsZUFBU0QsTUFBTSxNQUFNO0FBQ25CLGVBQU8sUUFBUSxDQUFDO0FBQ2hCLGFBQUssVUFBVSxLQUFLLFdBQVcsQ0FBQztBQUVoQyxjQUFNRSxZQUFXLEtBQUssUUFBUTtBQUM5QixZQUFJQSxhQUFZLE9BQU9BLFVBQVMsU0FBUyxZQUFZO0FBQUUsZ0JBQU0sTUFBTSxpREFBaUQ7QUFBQSxRQUFFO0FBRXRILGNBQU0sUUFBUSxLQUFLLFFBQVEsU0FBUztBQUNwQyxZQUFJLEtBQUssUUFBUSxNQUFPLE1BQUssUUFBUSxXQUFXO0FBQ2hELGNBQU0sY0FBYyxLQUFLLGVBQWUsQ0FBQztBQUN6QyxjQUFNLFlBQVksZ0JBQWdCLEtBQUssUUFBUSxXQUFXLFdBQVc7QUFDckUsWUFBSSxrQkFBa0IsS0FBSyxRQUFRO0FBRW5DLFlBQ0UsTUFBTSxRQUFRLEtBQUssUUFBUSxTQUFTLEtBQ3BDLEtBQUssUUFBUSxVQUFVLFFBQVEscUJBQXFCLElBQUksR0FDeEQsbUJBQWtCO0FBRXBCLGNBQU0sZUFBZSxPQUFPLEtBQUssS0FBSyxnQkFBZ0IsQ0FBQyxDQUFDO0FBQ3hELGNBQU0sU0FBUyxDQUFDLFNBQVMsU0FBUyxRQUFRLFFBQVEsU0FBUyxPQUFPLEVBQUUsT0FBTyxZQUFZO0FBRXZGLFlBQUksT0FBTyxVQUFVLFlBQVk7QUFDL0IsaUJBQU8sUUFBUSxTQUFVQyxRQUFPO0FBQzlCLGtCQUFNQSxNQUFLLElBQUk7QUFBQSxVQUNqQixDQUFDO0FBQUEsUUFDSDtBQUNBLFlBQUksS0FBSyxZQUFZLFNBQVMsS0FBSyxRQUFRLFNBQVUsTUFBSyxRQUFRO0FBQ2xFLGNBQU0sUUFBUSxLQUFLLFNBQVM7QUFDNUIsY0FBTUYsVUFBUyxPQUFPLE9BQU8sS0FBSztBQUNsQyxZQUFJLENBQUNBLFFBQU8sSUFBSyxDQUFBQSxRQUFPLE1BQU07QUFFOUIsOEJBQXNCQSxTQUFRLFFBQVEsS0FBSztBQUUzQywwQkFBa0IsQ0FBQyxHQUFHQSxPQUFNO0FBRTVCLGVBQU8sZUFBZUEsU0FBUSxZQUFZO0FBQUEsVUFDeEMsS0FBSztBQUFBLFFBQ1AsQ0FBQztBQUNELGVBQU8sZUFBZUEsU0FBUSxTQUFTO0FBQUEsVUFDckMsS0FBSztBQUFBLFVBQ0wsS0FBSztBQUFBLFFBQ1AsQ0FBQztBQUVELGNBQU0sVUFBVTtBQUFBLFVBQ2QsVUFBQUM7QUFBQSxVQUNBO0FBQUEsVUFDQSxVQUFVLEtBQUssUUFBUTtBQUFBLFVBQ3ZCLHNCQUFzQixLQUFLLFFBQVE7QUFBQSxVQUNuQyxZQUFZLEtBQUssUUFBUTtBQUFBLFVBQ3pCLGNBQWMsS0FBSyxRQUFRO0FBQUEsVUFDM0I7QUFBQSxVQUNBLFdBQVcsZ0JBQWdCLElBQUk7QUFBQSxVQUMvQixZQUFZLEtBQUssY0FBYztBQUFBLFVBQy9CLFNBQVMsS0FBSyxXQUFXO0FBQUEsUUFDM0I7QUFDQSxRQUFBRCxRQUFPLFNBQVMsVUFBVSxJQUFJO0FBQzlCLFFBQUFBLFFBQU8sUUFBUTtBQUVmLFFBQUFBLFFBQU8saUJBQWlCLFNBQVVFLFFBQU87QUFDdkMsY0FBSSxDQUFDLEtBQUssT0FBTyxPQUFPQSxNQUFLLEdBQUc7QUFDOUIsbUJBQU87QUFBQSxVQUNUO0FBRUEsaUJBQU8sS0FBSyxPQUFPLE9BQU9BLE1BQUssS0FBSyxLQUFLLE9BQU8sT0FBTyxLQUFLLEtBQUs7QUFBQSxRQUNuRTtBQUNBLFFBQUFGLFFBQU8sa0JBQWtCQSxRQUFPLGtCQUNoQ0EsUUFBTyxPQUFPQSxRQUFPLGNBQWNBLFFBQU8sS0FDMUNBLFFBQU8sa0JBQWtCQSxRQUFPLE9BQ2hDQSxRQUFPLHNCQUFzQkEsUUFBTyxpQkFDcENBLFFBQU8scUJBQXFCQSxRQUFPLFlBQ25DQSxRQUFPLGdCQUFnQkEsUUFBTyxhQUM5QkEsUUFBTyxRQUFRQSxRQUFPLFFBQVE7QUFDOUIsUUFBQUEsUUFBTyxjQUFjO0FBQ3JCLFFBQUFBLFFBQU8sYUFBYTtBQUNwQixRQUFBQSxRQUFPLG1CQUFtQjtBQUMxQixRQUFBQSxRQUFPLFFBQVEsWUFBYSxNQUFNO0FBQUUsaUJBQU8sTUFBTSxLQUFLLE1BQU0sU0FBUyxHQUFHLElBQUk7QUFBQSxRQUFFO0FBRTlFLFlBQUlDLFVBQVUsQ0FBQUQsUUFBTyxZQUFZLG9CQUFvQjtBQUVyRCxpQkFBUyxjQUFlO0FBQ3RCLGlCQUFPLGFBQWEsS0FBSyxPQUFPLElBQUk7QUFBQSxRQUN0QztBQUVBLGlCQUFTLFdBQVk7QUFDbkIsaUJBQU8sS0FBSztBQUFBLFFBQ2Q7QUFDQSxpQkFBUyxTQUFVRSxRQUFPO0FBQ3hCLGNBQUlBLFdBQVUsWUFBWSxDQUFDLEtBQUssT0FBTyxPQUFPQSxNQUFLLEdBQUc7QUFDcEQsa0JBQU0sTUFBTSxtQkFBbUJBLE1BQUs7QUFBQSxVQUN0QztBQUNBLGVBQUssU0FBU0E7QUFFZCxjQUFJLE1BQU0sU0FBU0YsU0FBUSxPQUFPO0FBQ2xDLGNBQUksTUFBTSxTQUFTQSxTQUFRLE9BQU87QUFDbEMsY0FBSSxNQUFNLFNBQVNBLFNBQVEsTUFBTTtBQUNqQyxjQUFJLE1BQU0sU0FBU0EsU0FBUSxNQUFNO0FBQ2pDLGNBQUksTUFBTSxTQUFTQSxTQUFRLE9BQU87QUFDbEMsY0FBSSxNQUFNLFNBQVNBLFNBQVEsT0FBTztBQUVsQyx1QkFBYSxRQUFRLENBQUNFLFdBQVU7QUFDOUIsZ0JBQUksTUFBTSxTQUFTRixTQUFRRSxNQUFLO0FBQUEsVUFDbEMsQ0FBQztBQUFBLFFBQ0g7QUFFQSxpQkFBUyxNQUFPQyxVQUFTLFVBQVUsY0FBYztBQUMvQyxjQUFJLENBQUMsVUFBVTtBQUNiLGtCQUFNLElBQUksTUFBTSxpQ0FBaUM7QUFBQSxVQUNuRDtBQUNBLHlCQUFlLGdCQUFnQixDQUFDO0FBQ2hDLGNBQUksYUFBYSxTQUFTLGFBQWE7QUFDckMseUJBQWEsY0FBYyxTQUFTO0FBQUEsVUFDdEM7QUFDQSxnQkFBTSwwQkFBMEIsYUFBYTtBQUM3QyxjQUFJLGFBQWEseUJBQXlCO0FBQ3hDLGdCQUFJLG1CQUFtQixPQUFPLE9BQU8sQ0FBQyxHQUFHLGFBQWEsdUJBQXVCO0FBQzdFLGdCQUFJLGlCQUFpQixLQUFLLFFBQVEsY0FBYyxPQUM1QyxPQUFPLEtBQUssZ0JBQWdCLElBQzVCO0FBQ0osbUJBQU8sU0FBUztBQUNoQiw2QkFBaUIsQ0FBQyxRQUFRLEdBQUcsZ0JBQWdCLGtCQUFrQixLQUFLLGdCQUFnQjtBQUFBLFVBQ3RGO0FBQ0EsbUJBQVMsTUFBTyxRQUFRO0FBQ3RCLGlCQUFLLGVBQWUsT0FBTyxjQUFjLEtBQUs7QUFHOUMsaUJBQUssV0FBVztBQUVoQixnQkFBSSxrQkFBa0I7QUFDcEIsbUJBQUssY0FBYztBQUNuQixtQkFBSyxhQUFhO0FBQUEsWUFDcEI7QUFDQSxnQkFBSUYsV0FBVTtBQUNaLG1CQUFLLFlBQVk7QUFBQSxnQkFDZixDQUFDLEVBQUUsT0FBTyxPQUFPLFVBQVUsVUFBVSxRQUFRO0FBQUEsY0FDL0M7QUFBQSxZQUNGO0FBQUEsVUFDRjtBQUNBLGdCQUFNLFlBQVk7QUFDbEIsZ0JBQU0sWUFBWSxJQUFJLE1BQU0sSUFBSTtBQUdoQyw0QkFBa0IsTUFBTSxTQUFTO0FBQ2pDLG9CQUFVLFFBQVEsWUFBYSxNQUFNO0FBQUUsbUJBQU8sTUFBTSxLQUFLLE1BQU1FLFVBQVMsR0FBRyxJQUFJO0FBQUEsVUFBRTtBQUVqRixvQkFBVSxRQUFRLGFBQWEsU0FBUyxLQUFLO0FBQzdDLFVBQUFBLFNBQVEsUUFBUSxTQUFTO0FBRXpCLGlCQUFPO0FBQUEsUUFDVDtBQUNBLGVBQU9IO0FBQUEsTUFDVDtBQUVBLGVBQVMsVUFBVyxNQUFNO0FBQ3hCLGNBQU0sZUFBZSxLQUFLLGdCQUFnQixDQUFDO0FBRTNDLGNBQU0sU0FBUyxPQUFPLE9BQU8sQ0FBQyxHQUFHRCxNQUFLLE9BQU8sUUFBUSxZQUFZO0FBQ2pFLGNBQU0sU0FBUyxPQUFPLE9BQU8sQ0FBQyxHQUFHQSxNQUFLLE9BQU8sUUFBUSxhQUFhLFlBQVksQ0FBQztBQUUvRSxlQUFPO0FBQUEsVUFDTDtBQUFBLFVBQ0E7QUFBQSxRQUNGO0FBQUEsTUFDRjtBQUVBLGVBQVMsYUFBYyxLQUFLO0FBQzFCLGNBQU0sV0FBVyxDQUFDO0FBQ2xCLGVBQU8sS0FBSyxHQUFHLEVBQUUsUUFBUSxTQUFVLEtBQUs7QUFDdEMsbUJBQVMsSUFBSSxHQUFHLENBQUMsSUFBSTtBQUFBLFFBQ3ZCLENBQUM7QUFDRCxlQUFPO0FBQUEsTUFDVDtBQUVBLE1BQUFBLE1BQUssU0FBUztBQUFBLFFBQ1osUUFBUTtBQUFBLFVBQ04sT0FBTztBQUFBLFVBQ1AsT0FBTztBQUFBLFVBQ1AsTUFBTTtBQUFBLFVBQ04sTUFBTTtBQUFBLFVBQ04sT0FBTztBQUFBLFVBQ1AsT0FBTztBQUFBLFFBQ1Q7QUFBQSxRQUNBLFFBQVE7QUFBQSxVQUNOLElBQUk7QUFBQSxVQUNKLElBQUk7QUFBQSxVQUNKLElBQUk7QUFBQSxVQUNKLElBQUk7QUFBQSxVQUNKLElBQUk7QUFBQSxVQUNKLElBQUk7QUFBQSxRQUNOO0FBQUEsTUFDRjtBQUVBLE1BQUFBLE1BQUssaUJBQWlCO0FBQ3RCLE1BQUFBLE1BQUssbUJBQW1CLE9BQU8sT0FBTyxDQUFDLEdBQUcsRUFBRSxVQUFVLFdBQVcsVUFBVSxRQUFRLENBQUM7QUFFcEYsZUFBUyxnQkFBaUJDLFNBQVE7QUFDaEMsY0FBTSxXQUFXLENBQUM7QUFDbEIsWUFBSUEsUUFBTyxVQUFVO0FBQ25CLG1CQUFTLEtBQUtBLFFBQU8sUUFBUTtBQUFBLFFBQy9CO0FBR0EsWUFBSSxZQUFZQSxRQUFPLGVBQWU7QUFDdEMsZUFBTyxVQUFVLFFBQVE7QUFDdkIsc0JBQVksVUFBVTtBQUN0QixjQUFJLFVBQVUsT0FBTyxVQUFVO0FBQzdCLHFCQUFTLEtBQUssVUFBVSxPQUFPLFFBQVE7QUFBQSxVQUN6QztBQUFBLFFBQ0Y7QUFFQSxlQUFPLFNBQVMsUUFBUTtBQUFBLE1BQzFCO0FBRUEsZUFBUyxJQUFLSSxPQUFNLE1BQU0sWUFBWSxPQUFPO0FBRTNDLGVBQU8sZUFBZUEsT0FBTSxPQUFPO0FBQUEsVUFDakMsT0FBUSxhQUFhQSxNQUFLLE9BQU8sVUFBVSxJQUFJLGFBQWEsT0FBTyxVQUFVLElBQ3pFLE9BQ0EsV0FBVyxxQkFBcUIsRUFBRSxLQUFLO0FBQUEsVUFDM0MsVUFBVTtBQUFBLFVBQ1YsWUFBWTtBQUFBLFVBQ1osY0FBYztBQUFBLFFBQ2hCLENBQUM7QUFFRCxZQUFJQSxNQUFLLEtBQUssTUFBTSxNQUFNO0FBQ3hCLGNBQUksQ0FBQyxLQUFLLFNBQVU7QUFFcEIsZ0JBQU0sZ0JBQWdCLEtBQUssU0FBUyxTQUFTQSxNQUFLO0FBQ2xELGdCQUFNLGdCQUFnQixhQUFhLGVBQWUsVUFBVTtBQUM1RCxnQkFBTSxjQUFjLGFBQWEsT0FBTyxVQUFVO0FBQ2xELGNBQUksY0FBYyxjQUFlO0FBQUEsUUFDbkM7QUFHQSxRQUFBQSxNQUFLLEtBQUssSUFBSSxXQUFXQSxPQUFNLE1BQU0sWUFBWSxLQUFLO0FBR3RELGNBQU0sV0FBVyxnQkFBZ0JBLEtBQUk7QUFDckMsWUFBSSxTQUFTLFdBQVcsR0FBRztBQUV6QjtBQUFBLFFBQ0Y7QUFDQSxRQUFBQSxNQUFLLEtBQUssSUFBSSwyQkFBMkIsVUFBVUEsTUFBSyxLQUFLLENBQUM7QUFBQSxNQUNoRTtBQUVBLGVBQVMsMkJBQTRCLFVBQVUsU0FBUztBQUN0RCxlQUFPLFdBQVk7QUFDakIsaUJBQU8sUUFBUSxNQUFNLE1BQU0sQ0FBQyxHQUFHLFVBQVUsR0FBRyxTQUFTLENBQUM7QUFBQSxRQUN4RDtBQUFBLE1BQ0Y7QUFFQSxlQUFTLFdBQVlBLE9BQU0sTUFBTSxZQUFZLE9BQU87QUFDbEQsZUFBUSwwQkFBVSxPQUFPO0FBQ3ZCLGlCQUFPLFNBQVMsTUFBTztBQUNyQixrQkFBTSxLQUFLLEtBQUssVUFBVTtBQUMxQixrQkFBTSxPQUFPLElBQUksTUFBTSxVQUFVLE1BQU07QUFDdkMsa0JBQU0sUUFBUyxPQUFPLGtCQUFrQixPQUFPLGVBQWUsSUFBSSxNQUFNLFdBQVksV0FBVztBQUMvRixxQkFBUyxJQUFJLEdBQUcsSUFBSSxLQUFLLFFBQVEsSUFBSyxNQUFLLENBQUMsSUFBSSxVQUFVLENBQUM7QUFFM0QsZ0JBQUksbUJBQW1CO0FBQ3ZCLGdCQUFJLEtBQUssV0FBVztBQUNsQiwrQkFBaUIsTUFBTSxLQUFLLFlBQVksS0FBSyxhQUFhLEtBQUssZ0JBQWdCO0FBQy9FLGlDQUFtQjtBQUFBLFlBQ3JCO0FBQ0EsZ0JBQUksS0FBSyxZQUFZLEtBQUssWUFBWTtBQUNwQyxvQkFBTSxNQUFNLFNBQVMsTUFBTSxPQUFPLE1BQU0sSUFBSSxJQUFJO0FBQ2hELGtCQUFJLEtBQUssZ0JBQWdCLE9BQU8sSUFBSSxTQUFTLEtBQUssSUFBSSxDQUFDLEtBQUssT0FBTyxJQUFJLENBQUMsTUFBTSxVQUFVO0FBQ3RGLG9CQUFJO0FBQ0Ysd0JBQU0sU0FBUyxrQkFBa0I7QUFDakMsc0JBQUksT0FBUSxLQUFJLENBQUMsRUFBRSxTQUFTO0FBQUEsZ0JBQzlCLFNBQVMsR0FBRztBQUFBLGdCQUFDO0FBQUEsY0FDZjtBQUNBLG9CQUFNLEtBQUssT0FBTyxHQUFHLEdBQUc7QUFBQSxZQUMxQixPQUFPO0FBQ0wsa0JBQUksS0FBSyxjQUFjO0FBQ3JCLG9CQUFJO0FBQ0Ysd0JBQU0sU0FBUyxrQkFBa0I7QUFDakMsc0JBQUksT0FBUSxNQUFLLEtBQUssTUFBTTtBQUFBLGdCQUM5QixTQUFTLEdBQUc7QUFBQSxnQkFBQztBQUFBLGNBQ2Y7QUFDQSxvQkFBTSxNQUFNLE9BQU8sSUFBSTtBQUFBLFlBQ3pCO0FBRUEsZ0JBQUksS0FBSyxVQUFVO0FBQ2pCLG9CQUFNLGdCQUFnQixLQUFLLFNBQVMsU0FBU0EsTUFBSztBQUNsRCxvQkFBTSxnQkFBZ0IsYUFBYSxlQUFlLFVBQVU7QUFDNUQsb0JBQU0sY0FBYyxhQUFhLE9BQU8sVUFBVTtBQUNsRCxrQkFBSSxjQUFjLGNBQWU7QUFDakMsdUJBQVMsTUFBTTtBQUFBLGdCQUNiO0FBQUEsZ0JBQ0EsYUFBYTtBQUFBLGdCQUNiO0FBQUEsZ0JBQ0E7QUFBQSxnQkFDQSxlQUFlLFdBQVcsT0FBTyxPQUFPLEtBQUssU0FBUyxTQUFTQSxNQUFLLE1BQU07QUFBQSxnQkFDMUUsTUFBTSxLQUFLLFNBQVM7QUFBQSxnQkFDcEIsS0FBSyxhQUFhQSxNQUFLLFFBQVEsVUFBVTtBQUFBLGNBQzNDLEdBQUcsTUFBTSxnQkFBZ0I7QUFBQSxZQUMzQjtBQUFBLFVBQ0Y7QUFBQSxRQUNGLEdBQUdBLE1BQUsscUJBQXFCLEVBQUUsS0FBSyxDQUFDO0FBQUEsTUFDdkM7QUFFQSxlQUFTLFNBQVVKLFNBQVEsT0FBTyxNQUFNLElBQUksTUFBTTtBQUNoRCxjQUFNO0FBQUEsVUFDSixPQUFPO0FBQUEsVUFDUCxLQUFLLHFCQUFxQixDQUFDLFFBQVE7QUFBQSxRQUNyQyxJQUFJLEtBQUssY0FBYyxDQUFDO0FBQ3hCLGNBQU0sYUFBYSxLQUFLLE1BQU07QUFDOUIsWUFBSSxNQUFNLFdBQVcsQ0FBQztBQUN0QixjQUFNLFlBQVksQ0FBQztBQUVuQixZQUFJLE9BQU9BLFFBQU8sY0FBYyxLQUFLO0FBQ3JDLFlBQUksTUFBTSxFQUFHLE9BQU07QUFFbkIsWUFBSSxJQUFJO0FBQ04sb0JBQVUsT0FBTztBQUFBLFFBQ25CO0FBRUEsWUFBSSxnQkFBZ0I7QUFDbEIsZ0JBQU0saUJBQWlCLGVBQWUsT0FBT0EsUUFBTyxPQUFPLE9BQU8sS0FBSyxDQUFDO0FBQ3hFLGlCQUFPLE9BQU8sV0FBVyxjQUFjO0FBQUEsUUFDekMsT0FBTztBQUNMLG9CQUFVLFFBQVFBLFFBQU8sT0FBTyxPQUFPLEtBQUs7QUFBQSxRQUM5QztBQUVBLFlBQUksS0FBSyxzQkFBc0I7QUFDN0IsY0FBSSxRQUFRLFFBQVEsT0FBTyxRQUFRLFVBQVU7QUFDM0MsbUJBQU8sU0FBUyxPQUFPLFdBQVcsQ0FBQyxNQUFNLFVBQVU7QUFDakQscUJBQU8sT0FBTyxXQUFXLFdBQVcsTUFBTSxDQUFDO0FBQUEsWUFDN0M7QUFBQSxVQUNGO0FBRUEsZ0JBQU0scUJBQXFCLG1CQUFtQixTQUFTO0FBQ3ZELGlCQUFPLENBQUMsb0JBQW9CLEdBQUcsVUFBVTtBQUFBLFFBQzNDLE9BQU87QUFFTCxjQUFJLFFBQVEsUUFBUSxPQUFPLFFBQVEsVUFBVTtBQUMzQyxtQkFBTyxTQUFTLE9BQU8sV0FBVyxDQUFDLE1BQU0sVUFBVTtBQUNqRCxxQkFBTyxPQUFPLFdBQVcsV0FBVyxNQUFNLENBQUM7QUFBQSxZQUM3QztBQUNBLGtCQUFNLFdBQVcsU0FBUyxPQUFPLFdBQVcsTUFBTSxHQUFHLFVBQVUsSUFBSTtBQUFBLFVBQ3JFLFdBQVcsT0FBTyxRQUFRLFNBQVUsT0FBTSxPQUFPLFdBQVcsTUFBTSxHQUFHLFVBQVU7QUFDL0UsY0FBSSxRQUFRLE9BQVcsV0FBVSxLQUFLLFVBQVUsSUFBSTtBQUVwRCxnQkFBTSxxQkFBcUIsbUJBQW1CLFNBQVM7QUFDdkQsaUJBQU8sQ0FBQyxrQkFBa0I7QUFBQSxRQUM1QjtBQUFBLE1BQ0Y7QUFFQSxlQUFTLGlCQUFrQixNQUFNLFdBQVcsYUFBYSxpQkFBaUI7QUFDeEUsbUJBQVcsS0FBSyxNQUFNO0FBQ3BCLGNBQUksbUJBQW1CLEtBQUssQ0FBQyxhQUFhLE9BQU87QUFDL0MsaUJBQUssQ0FBQyxJQUFJRCxNQUFLLGVBQWUsSUFBSSxLQUFLLENBQUMsQ0FBQztBQUFBLFVBQzNDLFdBQVcsT0FBTyxLQUFLLENBQUMsTUFBTSxZQUFZLENBQUMsTUFBTSxRQUFRLEtBQUssQ0FBQyxDQUFDLEtBQUssV0FBVztBQUM5RSx1QkFBVyxLQUFLLEtBQUssQ0FBQyxHQUFHO0FBQ3ZCLGtCQUFJLFVBQVUsUUFBUSxDQUFDLElBQUksTUFBTSxLQUFLLGFBQWE7QUFDakQscUJBQUssQ0FBQyxFQUFFLENBQUMsSUFBSSxZQUFZLENBQUMsRUFBRSxLQUFLLENBQUMsRUFBRSxDQUFDLENBQUM7QUFBQSxjQUN4QztBQUFBLFlBQ0Y7QUFBQSxVQUNGO0FBQUEsUUFDRjtBQUFBLE1BQ0Y7QUFFQSxlQUFTLFNBQVVDLFNBQVEsTUFBTSxNQUFNLG1CQUFtQixPQUFPO0FBQy9ELGNBQU0sT0FBTyxLQUFLO0FBQ2xCLGNBQU0sS0FBSyxLQUFLO0FBQ2hCLGNBQU0sY0FBYyxLQUFLO0FBQ3pCLGNBQU0sY0FBYyxLQUFLO0FBQ3pCLGNBQU0sTUFBTSxLQUFLO0FBQ2pCLGNBQU0sV0FBV0EsUUFBTyxVQUFVO0FBRWxDLFlBQUksQ0FBQyxrQkFBa0I7QUFDckI7QUFBQSxZQUNFO0FBQUEsWUFDQUEsUUFBTyxjQUFjLE9BQU8sS0FBS0EsUUFBTyxXQUFXO0FBQUEsWUFDbkRBLFFBQU87QUFBQSxZQUNQQSxRQUFPLHFCQUFxQixTQUFZLE9BQU9BLFFBQU87QUFBQSxVQUN4RDtBQUFBLFFBQ0Y7QUFFQSxRQUFBQSxRQUFPLFVBQVUsS0FBSztBQUN0QixRQUFBQSxRQUFPLFVBQVUsV0FBVyxLQUFLLE9BQU8sU0FBVSxLQUFLO0FBRXJELGlCQUFPLFNBQVMsUUFBUSxHQUFHLE1BQU07QUFBQSxRQUNuQyxDQUFDO0FBRUQsUUFBQUEsUUFBTyxVQUFVLE1BQU0sUUFBUTtBQUMvQixRQUFBQSxRQUFPLFVBQVUsTUFBTSxRQUFRO0FBRS9CLGFBQUssYUFBYUEsUUFBTyxXQUFXLEdBQUc7QUFFdkMsUUFBQUEsUUFBTyxZQUFZLG9CQUFvQixRQUFRO0FBQUEsTUFDakQ7QUFFQSxlQUFTLG9CQUFxQixVQUFVO0FBQ3RDLGVBQU87QUFBQSxVQUNMLElBQUk7QUFBQSxVQUNKLFVBQVUsQ0FBQztBQUFBLFVBQ1gsVUFBVSxZQUFZLENBQUM7QUFBQSxVQUN2QixPQUFPLEVBQUUsT0FBTyxJQUFJLE9BQU8sRUFBRTtBQUFBLFFBQy9CO0FBQUEsTUFDRjtBQUVBLGVBQVMsV0FBWSxLQUFLO0FBQ3hCLGNBQU0sTUFBTTtBQUFBLFVBQ1YsTUFBTSxJQUFJLFlBQVk7QUFBQSxVQUN0QixLQUFLLElBQUk7QUFBQSxVQUNULE9BQU8sSUFBSTtBQUFBLFFBQ2I7QUFDQSxtQkFBVyxPQUFPLEtBQUs7QUFDckIsY0FBSSxJQUFJLEdBQUcsTUFBTSxRQUFXO0FBQzFCLGdCQUFJLEdBQUcsSUFBSSxJQUFJLEdBQUc7QUFBQSxVQUNwQjtBQUFBLFFBQ0Y7QUFDQSxlQUFPO0FBQUEsTUFDVDtBQUVBLGVBQVMsZ0JBQWlCLE1BQU07QUFDOUIsWUFBSSxPQUFPLEtBQUssY0FBYyxZQUFZO0FBQ3hDLGlCQUFPLEtBQUs7QUFBQSxRQUNkO0FBQ0EsWUFBSSxLQUFLLGNBQWMsT0FBTztBQUM1QixpQkFBTztBQUFBLFFBQ1Q7QUFDQSxlQUFPO0FBQUEsTUFDVDtBQUVBLGVBQVMsT0FBUTtBQUFFLGVBQU8sQ0FBQztBQUFBLE1BQUU7QUFDN0IsZUFBUyxZQUFhLEdBQUc7QUFBRSxlQUFPO0FBQUEsTUFBRTtBQUNwQyxlQUFTLE9BQVE7QUFBQSxNQUFDO0FBRWxCLGVBQVMsV0FBWTtBQUFFLGVBQU87QUFBQSxNQUFNO0FBQ3BDLGVBQVMsWUFBYTtBQUFFLGVBQU8sS0FBSyxJQUFJO0FBQUEsTUFBRTtBQUMxQyxlQUFTLFdBQVk7QUFBRSxlQUFPLEtBQUssTUFBTSxLQUFLLElBQUksSUFBSSxHQUFNO0FBQUEsTUFBRTtBQUM5RCxlQUFTLFVBQVc7QUFBRSxlQUFPLElBQUksS0FBSyxLQUFLLElBQUksQ0FBQyxFQUFFLFlBQVk7QUFBQSxNQUFFO0FBSWhFLGVBQVMseUJBQTBCO0FBQ2pDLGlCQUFTLEtBQU0sR0FBRztBQUFFLGlCQUFPLE9BQU8sTUFBTSxlQUFlO0FBQUEsUUFBRTtBQUN6RCxZQUFJO0FBQ0YsY0FBSSxPQUFPLGVBQWUsWUFBYSxRQUFPO0FBQzlDLGlCQUFPLGVBQWUsT0FBTyxXQUFXLGNBQWM7QUFBQSxZQUNwRCxLQUFLLFdBQVk7QUFDZixxQkFBTyxPQUFPLFVBQVU7QUFDeEIscUJBQVEsS0FBSyxhQUFhO0FBQUEsWUFDNUI7QUFBQSxZQUNBLGNBQWM7QUFBQSxVQUNoQixDQUFDO0FBQ0QsaUJBQU87QUFBQSxRQUNULFNBQVMsR0FBRztBQUNWLGlCQUFPLEtBQUssSUFBSSxLQUFLLEtBQUssTUFBTSxLQUFLLEtBQUssSUFBSSxLQUFLLENBQUM7QUFBQSxRQUN0RDtBQUFBLE1BQ0Y7QUFHQSxhQUFPLFFBQVEsVUFBVUQ7QUFDekIsYUFBTyxRQUFRLE9BQU9BO0FBSXRCLGVBQVMsb0JBQXFCO0FBQzVCLGNBQU0sUUFBUyxJQUFJLE1BQU0sRUFBRztBQUM1QixZQUFJLENBQUMsTUFBTyxRQUFPO0FBQ25CLGNBQU0sUUFBUSxNQUFNLE1BQU0sSUFBSTtBQUM5QixpQkFBUyxJQUFJLEdBQUcsSUFBSSxNQUFNLFFBQVEsS0FBSztBQUNyQyxnQkFBTSxJQUFJLE1BQU0sQ0FBQyxFQUFFLEtBQUs7QUFFeEIsY0FBSSw0RUFBNEUsS0FBSyxDQUFDLEVBQUc7QUFDekYsY0FBSSxFQUFFLFFBQVEsWUFBWSxNQUFNLEdBQUk7QUFDcEMsY0FBSSxFQUFFLFFBQVEsZUFBZSxNQUFNLEdBQUk7QUFDdkMsY0FBSSxFQUFFLFFBQVEsY0FBYyxNQUFNLEdBQUk7QUFFdEMsY0FBSSxJQUFJLEVBQUUsTUFBTSx1QkFBdUI7QUFDdkMsY0FBSSxDQUFDLEVBQUcsS0FBSSxFQUFFLE1BQU0sd0JBQXdCO0FBQzVDLGNBQUksR0FBRztBQUNMLGtCQUFNLE9BQU8sRUFBRSxDQUFDO0FBQ2hCLGtCQUFNLE9BQU8sRUFBRSxDQUFDO0FBQ2hCLGtCQUFNLE1BQU0sRUFBRSxDQUFDO0FBQ2YsbUJBQU8sT0FBTyxNQUFNLE9BQU8sTUFBTTtBQUFBLFVBQ25DO0FBQUEsUUFDRjtBQUNBLGVBQU87QUFBQSxNQUNUO0FBQUE7QUFBQTs7O0FDbGlCQTtBQUFBO0FBQUE7QUFBQSxhQUFPLFVBQVUsQ0FBQztBQUFBO0FBQUE7OztBQ0FsQjtBQUFBO0FBQUE7QUFBQTtBQUNBLGFBQU8sZUFBZSxTQUFTLGNBQWMsRUFBRSxPQUFPLEtBQUssQ0FBQztBQUM1RCxjQUFRLFVBQVUsUUFBUSxTQUFTO0FBQ25DLFVBQU0sV0FBVztBQUNqQixVQUFNLGVBQWUsQ0FBQztBQUN0QixlQUFTLElBQUksR0FBRyxJQUFJLFNBQVMsUUFBUSxLQUFLO0FBQ3RDLGNBQU0sSUFBSSxTQUFTLE9BQU8sQ0FBQztBQUMzQixxQkFBYSxDQUFDLElBQUk7QUFBQSxNQUN0QjtBQUNBLGVBQVMsWUFBWSxLQUFLO0FBQ3RCLGNBQU0sSUFBSSxPQUFPO0FBQ2pCLGdCQUFVLE1BQU0sYUFBYyxJQUN6QixFQUFHLEtBQUssSUFBSyxLQUFLLFlBQ2xCLEVBQUcsS0FBSyxJQUFLLEtBQUssWUFDbEIsRUFBRyxLQUFLLElBQUssS0FBSyxZQUNsQixFQUFHLEtBQUssSUFBSyxLQUFLLGFBQ2xCLEVBQUcsS0FBSyxJQUFLLEtBQUs7QUFBQSxNQUMzQjtBQUNBLGVBQVMsVUFBVSxRQUFRO0FBQ3ZCLFlBQUksTUFBTTtBQUNWLGlCQUFTLElBQUksR0FBRyxJQUFJLE9BQU8sUUFBUSxFQUFFLEdBQUc7QUFDcEMsZ0JBQU0sSUFBSSxPQUFPLFdBQVcsQ0FBQztBQUM3QixjQUFJLElBQUksTUFBTSxJQUFJO0FBQ2QsbUJBQU8scUJBQXFCLFNBQVM7QUFDekMsZ0JBQU0sWUFBWSxHQUFHLElBQUssS0FBSztBQUFBLFFBQ25DO0FBQ0EsY0FBTSxZQUFZLEdBQUc7QUFDckIsaUJBQVMsSUFBSSxHQUFHLElBQUksT0FBTyxRQUFRLEVBQUUsR0FBRztBQUNwQyxnQkFBTSxJQUFJLE9BQU8sV0FBVyxDQUFDO0FBQzdCLGdCQUFNLFlBQVksR0FBRyxJQUFLLElBQUk7QUFBQSxRQUNsQztBQUNBLGVBQU87QUFBQSxNQUNYO0FBQ0EsZUFBUyxRQUFRLE1BQU0sUUFBUSxTQUFTTSxNQUFLO0FBQ3pDLFlBQUksUUFBUTtBQUNaLFlBQUksT0FBTztBQUNYLGNBQU0sUUFBUSxLQUFLLFdBQVc7QUFDOUIsY0FBTSxTQUFTLENBQUM7QUFDaEIsaUJBQVMsSUFBSSxHQUFHLElBQUksS0FBSyxRQUFRLEVBQUUsR0FBRztBQUNsQyxrQkFBUyxTQUFTLFNBQVUsS0FBSyxDQUFDO0FBQ2xDLGtCQUFRO0FBQ1IsaUJBQU8sUUFBUSxTQUFTO0FBQ3BCLG9CQUFRO0FBQ1IsbUJBQU8sS0FBTSxTQUFTLE9BQVEsSUFBSTtBQUFBLFVBQ3RDO0FBQUEsUUFDSjtBQUNBLFlBQUlBLE1BQUs7QUFDTCxjQUFJLE9BQU8sR0FBRztBQUNWLG1CQUFPLEtBQU0sU0FBVSxVQUFVLE9BQVMsSUFBSTtBQUFBLFVBQ2xEO0FBQUEsUUFDSixPQUNLO0FBQ0QsY0FBSSxRQUFRO0FBQ1IsbUJBQU87QUFDWCxjQUFLLFNBQVUsVUFBVSxPQUFTO0FBQzlCLG1CQUFPO0FBQUEsUUFDZjtBQUNBLGVBQU87QUFBQSxNQUNYO0FBQ0EsZUFBUyxRQUFRLE9BQU87QUFDcEIsZUFBTyxRQUFRLE9BQU8sR0FBRyxHQUFHLElBQUk7QUFBQSxNQUNwQztBQUNBLGVBQVMsZ0JBQWdCLE9BQU87QUFDNUIsY0FBTSxNQUFNLFFBQVEsT0FBTyxHQUFHLEdBQUcsS0FBSztBQUN0QyxZQUFJLE1BQU0sUUFBUSxHQUFHO0FBQ2pCLGlCQUFPO0FBQUEsTUFDZjtBQUNBLGVBQVMsVUFBVSxPQUFPO0FBQ3RCLGNBQU0sTUFBTSxRQUFRLE9BQU8sR0FBRyxHQUFHLEtBQUs7QUFDdEMsWUFBSSxNQUFNLFFBQVEsR0FBRztBQUNqQixpQkFBTztBQUNYLGNBQU0sSUFBSSxNQUFNLEdBQUc7QUFBQSxNQUN2QjtBQUNBLGVBQVMsdUJBQXVCLFVBQVU7QUFDdEMsWUFBSTtBQUNKLFlBQUksYUFBYSxVQUFVO0FBQ3ZCLDJCQUFpQjtBQUFBLFFBQ3JCLE9BQ0s7QUFDRCwyQkFBaUI7QUFBQSxRQUNyQjtBQUNBLGlCQUFTLE9BQU8sUUFBUSxPQUFPLE9BQU87QUFDbEMsa0JBQVEsU0FBUztBQUNqQixjQUFJLE9BQU8sU0FBUyxJQUFJLE1BQU0sU0FBUztBQUNuQyxrQkFBTSxJQUFJLFVBQVUsc0JBQXNCO0FBQzlDLG1CQUFTLE9BQU8sWUFBWTtBQUU1QixjQUFJLE1BQU0sVUFBVSxNQUFNO0FBQzFCLGNBQUksT0FBTyxRQUFRO0FBQ2Ysa0JBQU0sSUFBSSxNQUFNLEdBQUc7QUFDdkIsY0FBSSxTQUFTLFNBQVM7QUFDdEIsbUJBQVMsSUFBSSxHQUFHLElBQUksTUFBTSxRQUFRLEVBQUUsR0FBRztBQUNuQyxrQkFBTSxJQUFJLE1BQU0sQ0FBQztBQUNqQixnQkFBSSxLQUFLLE1BQU07QUFDWCxvQkFBTSxJQUFJLE1BQU0sZ0JBQWdCO0FBQ3BDLGtCQUFNLFlBQVksR0FBRyxJQUFJO0FBQ3pCLHNCQUFVLFNBQVMsT0FBTyxDQUFDO0FBQUEsVUFDL0I7QUFDQSxtQkFBUyxJQUFJLEdBQUcsSUFBSSxHQUFHLEVBQUUsR0FBRztBQUN4QixrQkFBTSxZQUFZLEdBQUc7QUFBQSxVQUN6QjtBQUNBLGlCQUFPO0FBQ1AsbUJBQVMsSUFBSSxHQUFHLElBQUksR0FBRyxFQUFFLEdBQUc7QUFDeEIsa0JBQU0sSUFBSyxRQUFTLElBQUksS0FBSyxJQUFNO0FBQ25DLHNCQUFVLFNBQVMsT0FBTyxDQUFDO0FBQUEsVUFDL0I7QUFDQSxpQkFBTztBQUFBLFFBQ1g7QUFDQSxpQkFBUyxTQUFTLEtBQUssT0FBTztBQUMxQixrQkFBUSxTQUFTO0FBQ2pCLGNBQUksSUFBSSxTQUFTO0FBQ2IsbUJBQU8sTUFBTTtBQUNqQixjQUFJLElBQUksU0FBUztBQUNiLG1CQUFPO0FBRVgsZ0JBQU0sVUFBVSxJQUFJLFlBQVk7QUFDaEMsZ0JBQU0sVUFBVSxJQUFJLFlBQVk7QUFDaEMsY0FBSSxRQUFRLFdBQVcsUUFBUTtBQUMzQixtQkFBTyx1QkFBdUI7QUFDbEMsZ0JBQU07QUFDTixnQkFBTSxRQUFRLElBQUksWUFBWSxHQUFHO0FBQ2pDLGNBQUksVUFBVTtBQUNWLG1CQUFPLGdDQUFnQztBQUMzQyxjQUFJLFVBQVU7QUFDVixtQkFBTyx3QkFBd0I7QUFDbkMsZ0JBQU0sU0FBUyxJQUFJLE1BQU0sR0FBRyxLQUFLO0FBQ2pDLGdCQUFNLFlBQVksSUFBSSxNQUFNLFFBQVEsQ0FBQztBQUNyQyxjQUFJLFVBQVUsU0FBUztBQUNuQixtQkFBTztBQUNYLGNBQUksTUFBTSxVQUFVLE1BQU07QUFDMUIsY0FBSSxPQUFPLFFBQVE7QUFDZixtQkFBTztBQUNYLGdCQUFNLFFBQVEsQ0FBQztBQUNmLG1CQUFTLElBQUksR0FBRyxJQUFJLFVBQVUsUUFBUSxFQUFFLEdBQUc7QUFDdkMsa0JBQU0sSUFBSSxVQUFVLE9BQU8sQ0FBQztBQUM1QixrQkFBTSxJQUFJLGFBQWEsQ0FBQztBQUN4QixnQkFBSSxNQUFNO0FBQ04scUJBQU8sdUJBQXVCO0FBQ2xDLGtCQUFNLFlBQVksR0FBRyxJQUFJO0FBRXpCLGdCQUFJLElBQUksS0FBSyxVQUFVO0FBQ25CO0FBQ0osa0JBQU0sS0FBSyxDQUFDO0FBQUEsVUFDaEI7QUFDQSxjQUFJLFFBQVE7QUFDUixtQkFBTywwQkFBMEI7QUFDckMsaUJBQU8sRUFBRSxRQUFRLE1BQU07QUFBQSxRQUMzQjtBQUNBLGlCQUFTLGFBQWEsS0FBSyxPQUFPO0FBQzlCLGdCQUFNLE1BQU0sU0FBUyxLQUFLLEtBQUs7QUFDL0IsY0FBSSxPQUFPLFFBQVE7QUFDZixtQkFBTztBQUFBLFFBQ2Y7QUFDQSxpQkFBU0MsUUFBTyxLQUFLLE9BQU87QUFDeEIsZ0JBQU0sTUFBTSxTQUFTLEtBQUssS0FBSztBQUMvQixjQUFJLE9BQU8sUUFBUTtBQUNmLG1CQUFPO0FBQ1gsZ0JBQU0sSUFBSSxNQUFNLEdBQUc7QUFBQSxRQUN2QjtBQUNBLGVBQU87QUFBQSxVQUNIO0FBQUEsVUFDQSxRQUFBQTtBQUFBLFVBQ0E7QUFBQSxVQUNBO0FBQUEsVUFDQTtBQUFBLFVBQ0E7QUFBQSxRQUNKO0FBQUEsTUFDSjtBQUNBLGNBQVEsU0FBUyx1QkFBdUIsUUFBUTtBQUNoRCxjQUFRLFVBQVUsdUJBQXVCLFNBQVM7QUFBQTtBQUFBOzs7QUN6S2xEO0FBQUE7QUFBQTtBQUFBO0FBRUEsY0FBUSxhQUFhO0FBQ3JCLGNBQVEsY0FBYztBQUN0QixjQUFRLGdCQUFnQjtBQUV4QixVQUFJLFNBQVMsQ0FBQztBQUNkLFVBQUksWUFBWSxDQUFDO0FBQ2pCLFVBQUksTUFBTSxPQUFPLGVBQWUsY0FBYyxhQUFhO0FBRTNELFVBQUksT0FBTztBQUNYLFdBQVMsSUFBSSxHQUFHLE1BQU0sS0FBSyxRQUFRLElBQUksS0FBSyxFQUFFLEdBQUc7QUFDL0MsZUFBTyxDQUFDLElBQUksS0FBSyxDQUFDO0FBQ2xCLGtCQUFVLEtBQUssV0FBVyxDQUFDLENBQUMsSUFBSTtBQUFBLE1BQ2xDO0FBSFM7QUFBTztBQU9oQixnQkFBVSxJQUFJLFdBQVcsQ0FBQyxDQUFDLElBQUk7QUFDL0IsZ0JBQVUsSUFBSSxXQUFXLENBQUMsQ0FBQyxJQUFJO0FBRS9CLGVBQVMsUUFBUyxLQUFLO0FBQ3JCLFlBQUlDLE9BQU0sSUFBSTtBQUVkLFlBQUlBLE9BQU0sSUFBSSxHQUFHO0FBQ2YsZ0JBQU0sSUFBSSxNQUFNLGdEQUFnRDtBQUFBLFFBQ2xFO0FBSUEsWUFBSSxXQUFXLElBQUksUUFBUSxHQUFHO0FBQzlCLFlBQUksYUFBYSxHQUFJLFlBQVdBO0FBRWhDLFlBQUksa0JBQWtCLGFBQWFBLE9BQy9CLElBQ0EsSUFBSyxXQUFXO0FBRXBCLGVBQU8sQ0FBQyxVQUFVLGVBQWU7QUFBQSxNQUNuQztBQUdBLGVBQVMsV0FBWSxLQUFLO0FBQ3hCLFlBQUksT0FBTyxRQUFRLEdBQUc7QUFDdEIsWUFBSSxXQUFXLEtBQUssQ0FBQztBQUNyQixZQUFJLGtCQUFrQixLQUFLLENBQUM7QUFDNUIsZ0JBQVMsV0FBVyxtQkFBbUIsSUFBSSxJQUFLO0FBQUEsTUFDbEQ7QUFFQSxlQUFTLFlBQWEsS0FBSyxVQUFVLGlCQUFpQjtBQUNwRCxnQkFBUyxXQUFXLG1CQUFtQixJQUFJLElBQUs7QUFBQSxNQUNsRDtBQUVBLGVBQVMsWUFBYSxLQUFLO0FBQ3pCLFlBQUk7QUFDSixZQUFJLE9BQU8sUUFBUSxHQUFHO0FBQ3RCLFlBQUksV0FBVyxLQUFLLENBQUM7QUFDckIsWUFBSSxrQkFBa0IsS0FBSyxDQUFDO0FBRTVCLFlBQUksTUFBTSxJQUFJLElBQUksWUFBWSxLQUFLLFVBQVUsZUFBZSxDQUFDO0FBRTdELFlBQUksVUFBVTtBQUdkLFlBQUlBLE9BQU0sa0JBQWtCLElBQ3hCLFdBQVcsSUFDWDtBQUVKLFlBQUlDO0FBQ0osYUFBS0EsS0FBSSxHQUFHQSxLQUFJRCxNQUFLQyxNQUFLLEdBQUc7QUFDM0IsZ0JBQ0csVUFBVSxJQUFJLFdBQVdBLEVBQUMsQ0FBQyxLQUFLLEtBQ2hDLFVBQVUsSUFBSSxXQUFXQSxLQUFJLENBQUMsQ0FBQyxLQUFLLEtBQ3BDLFVBQVUsSUFBSSxXQUFXQSxLQUFJLENBQUMsQ0FBQyxLQUFLLElBQ3JDLFVBQVUsSUFBSSxXQUFXQSxLQUFJLENBQUMsQ0FBQztBQUNqQyxjQUFJLFNBQVMsSUFBSyxPQUFPLEtBQU07QUFDL0IsY0FBSSxTQUFTLElBQUssT0FBTyxJQUFLO0FBQzlCLGNBQUksU0FBUyxJQUFJLE1BQU07QUFBQSxRQUN6QjtBQUVBLFlBQUksb0JBQW9CLEdBQUc7QUFDekIsZ0JBQ0csVUFBVSxJQUFJLFdBQVdBLEVBQUMsQ0FBQyxLQUFLLElBQ2hDLFVBQVUsSUFBSSxXQUFXQSxLQUFJLENBQUMsQ0FBQyxLQUFLO0FBQ3ZDLGNBQUksU0FBUyxJQUFJLE1BQU07QUFBQSxRQUN6QjtBQUVBLFlBQUksb0JBQW9CLEdBQUc7QUFDekIsZ0JBQ0csVUFBVSxJQUFJLFdBQVdBLEVBQUMsQ0FBQyxLQUFLLEtBQ2hDLFVBQVUsSUFBSSxXQUFXQSxLQUFJLENBQUMsQ0FBQyxLQUFLLElBQ3BDLFVBQVUsSUFBSSxXQUFXQSxLQUFJLENBQUMsQ0FBQyxLQUFLO0FBQ3ZDLGNBQUksU0FBUyxJQUFLLE9BQU8sSUFBSztBQUM5QixjQUFJLFNBQVMsSUFBSSxNQUFNO0FBQUEsUUFDekI7QUFFQSxlQUFPO0FBQUEsTUFDVDtBQUVBLGVBQVMsZ0JBQWlCQyxNQUFLO0FBQzdCLGVBQU8sT0FBT0EsUUFBTyxLQUFLLEVBQUksSUFDNUIsT0FBT0EsUUFBTyxLQUFLLEVBQUksSUFDdkIsT0FBT0EsUUFBTyxJQUFJLEVBQUksSUFDdEIsT0FBT0EsT0FBTSxFQUFJO0FBQUEsTUFDckI7QUFFQSxlQUFTLFlBQWEsT0FBTyxPQUFPLEtBQUs7QUFDdkMsWUFBSTtBQUNKLFlBQUksU0FBUyxDQUFDO0FBQ2QsaUJBQVNELEtBQUksT0FBT0EsS0FBSSxLQUFLQSxNQUFLLEdBQUc7QUFDbkMsaUJBQ0ksTUFBTUEsRUFBQyxLQUFLLEtBQU0sYUFDbEIsTUFBTUEsS0FBSSxDQUFDLEtBQUssSUFBSyxVQUN0QixNQUFNQSxLQUFJLENBQUMsSUFBSTtBQUNsQixpQkFBTyxLQUFLLGdCQUFnQixHQUFHLENBQUM7QUFBQSxRQUNsQztBQUNBLGVBQU8sT0FBTyxLQUFLLEVBQUU7QUFBQSxNQUN2QjtBQUVBLGVBQVMsY0FBZSxPQUFPO0FBQzdCLFlBQUk7QUFDSixZQUFJRCxPQUFNLE1BQU07QUFDaEIsWUFBSSxhQUFhQSxPQUFNO0FBQ3ZCLFlBQUksUUFBUSxDQUFDO0FBQ2IsWUFBSSxpQkFBaUI7QUFHckIsaUJBQVNDLEtBQUksR0FBR0UsUUFBT0gsT0FBTSxZQUFZQyxLQUFJRSxPQUFNRixNQUFLLGdCQUFnQjtBQUN0RSxnQkFBTSxLQUFLLFlBQVksT0FBT0EsSUFBSUEsS0FBSSxpQkFBa0JFLFFBQU9BLFFBQVFGLEtBQUksY0FBZSxDQUFDO0FBQUEsUUFDN0Y7QUFHQSxZQUFJLGVBQWUsR0FBRztBQUNwQixnQkFBTSxNQUFNRCxPQUFNLENBQUM7QUFDbkIsZ0JBQU07QUFBQSxZQUNKLE9BQU8sT0FBTyxDQUFDLElBQ2YsT0FBUSxPQUFPLElBQUssRUFBSSxJQUN4QjtBQUFBLFVBQ0Y7QUFBQSxRQUNGLFdBQVcsZUFBZSxHQUFHO0FBQzNCLGlCQUFPLE1BQU1BLE9BQU0sQ0FBQyxLQUFLLEtBQUssTUFBTUEsT0FBTSxDQUFDO0FBQzNDLGdCQUFNO0FBQUEsWUFDSixPQUFPLE9BQU8sRUFBRSxJQUNoQixPQUFRLE9BQU8sSUFBSyxFQUFJLElBQ3hCLE9BQVEsT0FBTyxJQUFLLEVBQUksSUFDeEI7QUFBQSxVQUNGO0FBQUEsUUFDRjtBQUVBLGVBQU8sTUFBTSxLQUFLLEVBQUU7QUFBQSxNQUN0QjtBQUFBO0FBQUE7OztBQ3JKQTtBQUFBO0FBQUE7QUFDQSxjQUFRLE9BQU8sU0FBVSxRQUFRLFFBQVFJLE9BQU0sTUFBTSxRQUFRO0FBQzNELFlBQUksR0FBRztBQUNQLFlBQUksT0FBUSxTQUFTLElBQUssT0FBTztBQUNqQyxZQUFJLFFBQVEsS0FBSyxRQUFRO0FBQ3pCLFlBQUksUUFBUSxRQUFRO0FBQ3BCLFlBQUksUUFBUTtBQUNaLFlBQUksSUFBSUEsUUFBUSxTQUFTLElBQUs7QUFDOUIsWUFBSSxJQUFJQSxRQUFPLEtBQUs7QUFDcEIsWUFBSSxJQUFJLE9BQU8sU0FBUyxDQUFDO0FBRXpCLGFBQUs7QUFFTCxZQUFJLEtBQU0sS0FBTSxDQUFDLFNBQVU7QUFDM0IsY0FBTyxDQUFDO0FBQ1IsaUJBQVM7QUFDVCxlQUFPLFFBQVEsR0FBRyxJQUFLLElBQUksTUFBTyxPQUFPLFNBQVMsQ0FBQyxHQUFHLEtBQUssR0FBRyxTQUFTLEdBQUc7QUFBQSxRQUFDO0FBRTNFLFlBQUksS0FBTSxLQUFNLENBQUMsU0FBVTtBQUMzQixjQUFPLENBQUM7QUFDUixpQkFBUztBQUNULGVBQU8sUUFBUSxHQUFHLElBQUssSUFBSSxNQUFPLE9BQU8sU0FBUyxDQUFDLEdBQUcsS0FBSyxHQUFHLFNBQVMsR0FBRztBQUFBLFFBQUM7QUFFM0UsWUFBSSxNQUFNLEdBQUc7QUFDWCxjQUFJLElBQUk7QUFBQSxRQUNWLFdBQVcsTUFBTSxNQUFNO0FBQ3JCLGlCQUFPLElBQUksT0FBUSxJQUFJLEtBQUssS0FBSztBQUFBLFFBQ25DLE9BQU87QUFDTCxjQUFJLElBQUksS0FBSyxJQUFJLEdBQUcsSUFBSTtBQUN4QixjQUFJLElBQUk7QUFBQSxRQUNWO0FBQ0EsZ0JBQVEsSUFBSSxLQUFLLEtBQUssSUFBSSxLQUFLLElBQUksR0FBRyxJQUFJLElBQUk7QUFBQSxNQUNoRDtBQUVBLGNBQVEsUUFBUSxTQUFVLFFBQVEsT0FBTyxRQUFRQSxPQUFNLE1BQU0sUUFBUTtBQUNuRSxZQUFJLEdBQUcsR0FBRztBQUNWLFlBQUksT0FBUSxTQUFTLElBQUssT0FBTztBQUNqQyxZQUFJLFFBQVEsS0FBSyxRQUFRO0FBQ3pCLFlBQUksUUFBUSxRQUFRO0FBQ3BCLFlBQUksS0FBTSxTQUFTLEtBQUssS0FBSyxJQUFJLEdBQUcsR0FBRyxJQUFJLEtBQUssSUFBSSxHQUFHLEdBQUcsSUFBSTtBQUM5RCxZQUFJLElBQUlBLFFBQU8sSUFBSyxTQUFTO0FBQzdCLFlBQUksSUFBSUEsUUFBTyxJQUFJO0FBQ25CLFlBQUksSUFBSSxRQUFRLEtBQU0sVUFBVSxLQUFLLElBQUksUUFBUSxJQUFLLElBQUk7QUFFMUQsZ0JBQVEsS0FBSyxJQUFJLEtBQUs7QUFFdEIsWUFBSSxNQUFNLEtBQUssS0FBSyxVQUFVLFVBQVU7QUFDdEMsY0FBSSxNQUFNLEtBQUssSUFBSSxJQUFJO0FBQ3ZCLGNBQUk7QUFBQSxRQUNOLE9BQU87QUFDTCxjQUFJLEtBQUssTUFBTSxLQUFLLElBQUksS0FBSyxJQUFJLEtBQUssR0FBRztBQUN6QyxjQUFJLFNBQVMsSUFBSSxLQUFLLElBQUksR0FBRyxDQUFDLENBQUMsS0FBSyxHQUFHO0FBQ3JDO0FBQ0EsaUJBQUs7QUFBQSxVQUNQO0FBQ0EsY0FBSSxJQUFJLFNBQVMsR0FBRztBQUNsQixxQkFBUyxLQUFLO0FBQUEsVUFDaEIsT0FBTztBQUNMLHFCQUFTLEtBQUssS0FBSyxJQUFJLEdBQUcsSUFBSSxLQUFLO0FBQUEsVUFDckM7QUFDQSxjQUFJLFFBQVEsS0FBSyxHQUFHO0FBQ2xCO0FBQ0EsaUJBQUs7QUFBQSxVQUNQO0FBRUEsY0FBSSxJQUFJLFNBQVMsTUFBTTtBQUNyQixnQkFBSTtBQUNKLGdCQUFJO0FBQUEsVUFDTixXQUFXLElBQUksU0FBUyxHQUFHO0FBQ3pCLGlCQUFNLFFBQVEsSUFBSyxLQUFLLEtBQUssSUFBSSxHQUFHLElBQUk7QUFDeEMsZ0JBQUksSUFBSTtBQUFBLFVBQ1YsT0FBTztBQUNMLGdCQUFJLFFBQVEsS0FBSyxJQUFJLEdBQUcsUUFBUSxDQUFDLElBQUksS0FBSyxJQUFJLEdBQUcsSUFBSTtBQUNyRCxnQkFBSTtBQUFBLFVBQ047QUFBQSxRQUNGO0FBRUEsZUFBTyxRQUFRLEdBQUcsT0FBTyxTQUFTLENBQUMsSUFBSSxJQUFJLEtBQU0sS0FBSyxHQUFHLEtBQUssS0FBSyxRQUFRLEdBQUc7QUFBQSxRQUFDO0FBRS9FLFlBQUssS0FBSyxPQUFRO0FBQ2xCLGdCQUFRO0FBQ1IsZUFBTyxPQUFPLEdBQUcsT0FBTyxTQUFTLENBQUMsSUFBSSxJQUFJLEtBQU0sS0FBSyxHQUFHLEtBQUssS0FBSyxRQUFRLEdBQUc7QUFBQSxRQUFDO0FBRTlFLGVBQU8sU0FBUyxJQUFJLENBQUMsS0FBSyxJQUFJO0FBQUEsTUFDaEM7QUFBQTtBQUFBOzs7QUNwRkE7QUFBQTtBQUFBO0FBQUE7QUFVQSxVQUFNQyxVQUFTO0FBQ2YsVUFBTSxVQUFVO0FBQ2hCLFVBQU0sc0JBQ0gsT0FBTyxXQUFXLGNBQWMsT0FBTyxPQUFPLEtBQUssTUFBTSxhQUN0RCxPQUFPLEtBQUssRUFBRSw0QkFBNEIsSUFDMUM7QUFFTixjQUFRLFNBQVNDO0FBQ2pCLGNBQVEsYUFBYTtBQUNyQixjQUFRLG9CQUFvQjtBQUU1QixVQUFNLGVBQWU7QUFDckIsY0FBUSxhQUFhO0FBZ0JyQixNQUFBQSxRQUFPLHNCQUFzQixrQkFBa0I7QUFFL0MsVUFBSSxDQUFDQSxRQUFPLHVCQUF1QixPQUFPLFlBQVksZUFDbEQsT0FBTyxRQUFRLFVBQVUsWUFBWTtBQUN2QyxnQkFBUTtBQUFBLFVBQ047QUFBQSxRQUVGO0FBQUEsTUFDRjtBQUVBLGVBQVMsb0JBQXFCO0FBRTVCLFlBQUk7QUFDRixnQkFBTSxNQUFNLElBQUksV0FBVyxDQUFDO0FBQzVCLGdCQUFNLFFBQVEsRUFBRSxLQUFLLFdBQVk7QUFBRSxtQkFBTztBQUFBLFVBQUcsRUFBRTtBQUMvQyxpQkFBTyxlQUFlLE9BQU8sV0FBVyxTQUFTO0FBQ2pELGlCQUFPLGVBQWUsS0FBSyxLQUFLO0FBQ2hDLGlCQUFPLElBQUksSUFBSSxNQUFNO0FBQUEsUUFDdkIsU0FBUyxHQUFHO0FBQ1YsaUJBQU87QUFBQSxRQUNUO0FBQUEsTUFDRjtBQUVBLGFBQU8sZUFBZUEsUUFBTyxXQUFXLFVBQVU7QUFBQSxRQUNoRCxZQUFZO0FBQUEsUUFDWixLQUFLLFdBQVk7QUFDZixjQUFJLENBQUNBLFFBQU8sU0FBUyxJQUFJLEVBQUcsUUFBTztBQUNuQyxpQkFBTyxLQUFLO0FBQUEsUUFDZDtBQUFBLE1BQ0YsQ0FBQztBQUVELGFBQU8sZUFBZUEsUUFBTyxXQUFXLFVBQVU7QUFBQSxRQUNoRCxZQUFZO0FBQUEsUUFDWixLQUFLLFdBQVk7QUFDZixjQUFJLENBQUNBLFFBQU8sU0FBUyxJQUFJLEVBQUcsUUFBTztBQUNuQyxpQkFBTyxLQUFLO0FBQUEsUUFDZDtBQUFBLE1BQ0YsQ0FBQztBQUVELGVBQVMsYUFBYyxRQUFRO0FBQzdCLFlBQUksU0FBUyxjQUFjO0FBQ3pCLGdCQUFNLElBQUksV0FBVyxnQkFBZ0IsU0FBUyxnQ0FBZ0M7QUFBQSxRQUNoRjtBQUVBLGNBQU0sTUFBTSxJQUFJLFdBQVcsTUFBTTtBQUNqQyxlQUFPLGVBQWUsS0FBS0EsUUFBTyxTQUFTO0FBQzNDLGVBQU87QUFBQSxNQUNUO0FBWUEsZUFBU0EsUUFBUSxLQUFLLGtCQUFrQixRQUFRO0FBRTlDLFlBQUksT0FBTyxRQUFRLFVBQVU7QUFDM0IsY0FBSSxPQUFPLHFCQUFxQixVQUFVO0FBQ3hDLGtCQUFNLElBQUk7QUFBQSxjQUNSO0FBQUEsWUFDRjtBQUFBLFVBQ0Y7QUFDQSxpQkFBTyxZQUFZLEdBQUc7QUFBQSxRQUN4QjtBQUNBLGVBQU8sS0FBSyxLQUFLLGtCQUFrQixNQUFNO0FBQUEsTUFDM0M7QUFFQSxNQUFBQSxRQUFPLFdBQVc7QUFFbEIsZUFBUyxLQUFNLE9BQU8sa0JBQWtCLFFBQVE7QUFDOUMsWUFBSSxPQUFPLFVBQVUsVUFBVTtBQUM3QixpQkFBTyxXQUFXLE9BQU8sZ0JBQWdCO0FBQUEsUUFDM0M7QUFFQSxZQUFJLFlBQVksT0FBTyxLQUFLLEdBQUc7QUFDN0IsaUJBQU8sY0FBYyxLQUFLO0FBQUEsUUFDNUI7QUFFQSxZQUFJLFNBQVMsTUFBTTtBQUNqQixnQkFBTSxJQUFJO0FBQUEsWUFDUixvSEFDMEMsT0FBTztBQUFBLFVBQ25EO0FBQUEsUUFDRjtBQUVBLFlBQUksV0FBVyxPQUFPLFdBQVcsS0FDNUIsU0FBUyxXQUFXLE1BQU0sUUFBUSxXQUFXLEdBQUk7QUFDcEQsaUJBQU8sZ0JBQWdCLE9BQU8sa0JBQWtCLE1BQU07QUFBQSxRQUN4RDtBQUVBLFlBQUksT0FBTyxzQkFBc0IsZ0JBQzVCLFdBQVcsT0FBTyxpQkFBaUIsS0FDbkMsU0FBUyxXQUFXLE1BQU0sUUFBUSxpQkFBaUIsSUFBSztBQUMzRCxpQkFBTyxnQkFBZ0IsT0FBTyxrQkFBa0IsTUFBTTtBQUFBLFFBQ3hEO0FBRUEsWUFBSSxPQUFPLFVBQVUsVUFBVTtBQUM3QixnQkFBTSxJQUFJO0FBQUEsWUFDUjtBQUFBLFVBQ0Y7QUFBQSxRQUNGO0FBRUEsY0FBTSxVQUFVLE1BQU0sV0FBVyxNQUFNLFFBQVE7QUFDL0MsWUFBSSxXQUFXLFFBQVEsWUFBWSxPQUFPO0FBQ3hDLGlCQUFPQSxRQUFPLEtBQUssU0FBUyxrQkFBa0IsTUFBTTtBQUFBLFFBQ3REO0FBRUEsY0FBTSxJQUFJLFdBQVcsS0FBSztBQUMxQixZQUFJLEVBQUcsUUFBTztBQUVkLFlBQUksT0FBTyxXQUFXLGVBQWUsT0FBTyxlQUFlLFFBQ3ZELE9BQU8sTUFBTSxPQUFPLFdBQVcsTUFBTSxZQUFZO0FBQ25ELGlCQUFPQSxRQUFPLEtBQUssTUFBTSxPQUFPLFdBQVcsRUFBRSxRQUFRLEdBQUcsa0JBQWtCLE1BQU07QUFBQSxRQUNsRjtBQUVBLGNBQU0sSUFBSTtBQUFBLFVBQ1Isb0hBQzBDLE9BQU87QUFBQSxRQUNuRDtBQUFBLE1BQ0Y7QUFVQSxNQUFBQSxRQUFPLE9BQU8sU0FBVSxPQUFPLGtCQUFrQixRQUFRO0FBQ3ZELGVBQU8sS0FBSyxPQUFPLGtCQUFrQixNQUFNO0FBQUEsTUFDN0M7QUFJQSxhQUFPLGVBQWVBLFFBQU8sV0FBVyxXQUFXLFNBQVM7QUFDNUQsYUFBTyxlQUFlQSxTQUFRLFVBQVU7QUFFeEMsZUFBUyxXQUFZLE1BQU07QUFDekIsWUFBSSxPQUFPLFNBQVMsVUFBVTtBQUM1QixnQkFBTSxJQUFJLFVBQVUsd0NBQXdDO0FBQUEsUUFDOUQsV0FBVyxPQUFPLEdBQUc7QUFDbkIsZ0JBQU0sSUFBSSxXQUFXLGdCQUFnQixPQUFPLGdDQUFnQztBQUFBLFFBQzlFO0FBQUEsTUFDRjtBQUVBLGVBQVMsTUFBTyxNQUFNLE1BQU0sVUFBVTtBQUNwQyxtQkFBVyxJQUFJO0FBQ2YsWUFBSSxRQUFRLEdBQUc7QUFDYixpQkFBTyxhQUFhLElBQUk7QUFBQSxRQUMxQjtBQUNBLFlBQUksU0FBUyxRQUFXO0FBSXRCLGlCQUFPLE9BQU8sYUFBYSxXQUN2QixhQUFhLElBQUksRUFBRSxLQUFLLE1BQU0sUUFBUSxJQUN0QyxhQUFhLElBQUksRUFBRSxLQUFLLElBQUk7QUFBQSxRQUNsQztBQUNBLGVBQU8sYUFBYSxJQUFJO0FBQUEsTUFDMUI7QUFNQSxNQUFBQSxRQUFPLFFBQVEsU0FBVSxNQUFNLE1BQU0sVUFBVTtBQUM3QyxlQUFPLE1BQU0sTUFBTSxNQUFNLFFBQVE7QUFBQSxNQUNuQztBQUVBLGVBQVMsWUFBYSxNQUFNO0FBQzFCLG1CQUFXLElBQUk7QUFDZixlQUFPLGFBQWEsT0FBTyxJQUFJLElBQUksUUFBUSxJQUFJLElBQUksQ0FBQztBQUFBLE1BQ3REO0FBS0EsTUFBQUEsUUFBTyxjQUFjLFNBQVUsTUFBTTtBQUNuQyxlQUFPLFlBQVksSUFBSTtBQUFBLE1BQ3pCO0FBSUEsTUFBQUEsUUFBTyxrQkFBa0IsU0FBVSxNQUFNO0FBQ3ZDLGVBQU8sWUFBWSxJQUFJO0FBQUEsTUFDekI7QUFFQSxlQUFTLFdBQVksUUFBUSxVQUFVO0FBQ3JDLFlBQUksT0FBTyxhQUFhLFlBQVksYUFBYSxJQUFJO0FBQ25ELHFCQUFXO0FBQUEsUUFDYjtBQUVBLFlBQUksQ0FBQ0EsUUFBTyxXQUFXLFFBQVEsR0FBRztBQUNoQyxnQkFBTSxJQUFJLFVBQVUsdUJBQXVCLFFBQVE7QUFBQSxRQUNyRDtBQUVBLGNBQU0sU0FBUyxXQUFXLFFBQVEsUUFBUSxJQUFJO0FBQzlDLFlBQUksTUFBTSxhQUFhLE1BQU07QUFFN0IsY0FBTSxTQUFTLElBQUksTUFBTSxRQUFRLFFBQVE7QUFFekMsWUFBSSxXQUFXLFFBQVE7QUFJckIsZ0JBQU0sSUFBSSxNQUFNLEdBQUcsTUFBTTtBQUFBLFFBQzNCO0FBRUEsZUFBTztBQUFBLE1BQ1Q7QUFFQSxlQUFTLGNBQWUsT0FBTztBQUM3QixjQUFNLFNBQVMsTUFBTSxTQUFTLElBQUksSUFBSSxRQUFRLE1BQU0sTUFBTSxJQUFJO0FBQzlELGNBQU0sTUFBTSxhQUFhLE1BQU07QUFDL0IsaUJBQVMsSUFBSSxHQUFHLElBQUksUUFBUSxLQUFLLEdBQUc7QUFDbEMsY0FBSSxDQUFDLElBQUksTUFBTSxDQUFDLElBQUk7QUFBQSxRQUN0QjtBQUNBLGVBQU87QUFBQSxNQUNUO0FBRUEsZUFBUyxjQUFlLFdBQVc7QUFDakMsWUFBSSxXQUFXLFdBQVcsVUFBVSxHQUFHO0FBQ3JDLGdCQUFNLE9BQU8sSUFBSSxXQUFXLFNBQVM7QUFDckMsaUJBQU8sZ0JBQWdCLEtBQUssUUFBUSxLQUFLLFlBQVksS0FBSyxVQUFVO0FBQUEsUUFDdEU7QUFDQSxlQUFPLGNBQWMsU0FBUztBQUFBLE1BQ2hDO0FBRUEsZUFBUyxnQkFBaUIsT0FBTyxZQUFZLFFBQVE7QUFDbkQsWUFBSSxhQUFhLEtBQUssTUFBTSxhQUFhLFlBQVk7QUFDbkQsZ0JBQU0sSUFBSSxXQUFXLHNDQUFzQztBQUFBLFFBQzdEO0FBRUEsWUFBSSxNQUFNLGFBQWEsY0FBYyxVQUFVLElBQUk7QUFDakQsZ0JBQU0sSUFBSSxXQUFXLHNDQUFzQztBQUFBLFFBQzdEO0FBRUEsWUFBSTtBQUNKLFlBQUksZUFBZSxVQUFhLFdBQVcsUUFBVztBQUNwRCxnQkFBTSxJQUFJLFdBQVcsS0FBSztBQUFBLFFBQzVCLFdBQVcsV0FBVyxRQUFXO0FBQy9CLGdCQUFNLElBQUksV0FBVyxPQUFPLFVBQVU7QUFBQSxRQUN4QyxPQUFPO0FBQ0wsZ0JBQU0sSUFBSSxXQUFXLE9BQU8sWUFBWSxNQUFNO0FBQUEsUUFDaEQ7QUFHQSxlQUFPLGVBQWUsS0FBS0EsUUFBTyxTQUFTO0FBRTNDLGVBQU87QUFBQSxNQUNUO0FBRUEsZUFBUyxXQUFZLEtBQUs7QUFDeEIsWUFBSUEsUUFBTyxTQUFTLEdBQUcsR0FBRztBQUN4QixnQkFBTSxNQUFNLFFBQVEsSUFBSSxNQUFNLElBQUk7QUFDbEMsZ0JBQU0sTUFBTSxhQUFhLEdBQUc7QUFFNUIsY0FBSSxJQUFJLFdBQVcsR0FBRztBQUNwQixtQkFBTztBQUFBLFVBQ1Q7QUFFQSxjQUFJLEtBQUssS0FBSyxHQUFHLEdBQUcsR0FBRztBQUN2QixpQkFBTztBQUFBLFFBQ1Q7QUFFQSxZQUFJLElBQUksV0FBVyxRQUFXO0FBQzVCLGNBQUksT0FBTyxJQUFJLFdBQVcsWUFBWSxZQUFZLElBQUksTUFBTSxHQUFHO0FBQzdELG1CQUFPLGFBQWEsQ0FBQztBQUFBLFVBQ3ZCO0FBQ0EsaUJBQU8sY0FBYyxHQUFHO0FBQUEsUUFDMUI7QUFFQSxZQUFJLElBQUksU0FBUyxZQUFZLE1BQU0sUUFBUSxJQUFJLElBQUksR0FBRztBQUNwRCxpQkFBTyxjQUFjLElBQUksSUFBSTtBQUFBLFFBQy9CO0FBQUEsTUFDRjtBQUVBLGVBQVMsUUFBUyxRQUFRO0FBR3hCLFlBQUksVUFBVSxjQUFjO0FBQzFCLGdCQUFNLElBQUksV0FBVyw0REFDYSxhQUFhLFNBQVMsRUFBRSxJQUFJLFFBQVE7QUFBQSxRQUN4RTtBQUNBLGVBQU8sU0FBUztBQUFBLE1BQ2xCO0FBRUEsZUFBUyxXQUFZLFFBQVE7QUFDM0IsWUFBSSxDQUFDLFVBQVUsUUFBUTtBQUNyQixtQkFBUztBQUFBLFFBQ1g7QUFDQSxlQUFPQSxRQUFPLE1BQU0sQ0FBQyxNQUFNO0FBQUEsTUFDN0I7QUFFQSxNQUFBQSxRQUFPLFdBQVcsU0FBUyxTQUFVLEdBQUc7QUFDdEMsZUFBTyxLQUFLLFFBQVEsRUFBRSxjQUFjLFFBQ2xDLE1BQU1BLFFBQU87QUFBQSxNQUNqQjtBQUVBLE1BQUFBLFFBQU8sVUFBVSxTQUFTLFFBQVMsR0FBRyxHQUFHO0FBQ3ZDLFlBQUksV0FBVyxHQUFHLFVBQVUsRUFBRyxLQUFJQSxRQUFPLEtBQUssR0FBRyxFQUFFLFFBQVEsRUFBRSxVQUFVO0FBQ3hFLFlBQUksV0FBVyxHQUFHLFVBQVUsRUFBRyxLQUFJQSxRQUFPLEtBQUssR0FBRyxFQUFFLFFBQVEsRUFBRSxVQUFVO0FBQ3hFLFlBQUksQ0FBQ0EsUUFBTyxTQUFTLENBQUMsS0FBSyxDQUFDQSxRQUFPLFNBQVMsQ0FBQyxHQUFHO0FBQzlDLGdCQUFNLElBQUk7QUFBQSxZQUNSO0FBQUEsVUFDRjtBQUFBLFFBQ0Y7QUFFQSxZQUFJLE1BQU0sRUFBRyxRQUFPO0FBRXBCLFlBQUksSUFBSSxFQUFFO0FBQ1YsWUFBSSxJQUFJLEVBQUU7QUFFVixpQkFBUyxJQUFJLEdBQUcsTUFBTSxLQUFLLElBQUksR0FBRyxDQUFDLEdBQUcsSUFBSSxLQUFLLEVBQUUsR0FBRztBQUNsRCxjQUFJLEVBQUUsQ0FBQyxNQUFNLEVBQUUsQ0FBQyxHQUFHO0FBQ2pCLGdCQUFJLEVBQUUsQ0FBQztBQUNQLGdCQUFJLEVBQUUsQ0FBQztBQUNQO0FBQUEsVUFDRjtBQUFBLFFBQ0Y7QUFFQSxZQUFJLElBQUksRUFBRyxRQUFPO0FBQ2xCLFlBQUksSUFBSSxFQUFHLFFBQU87QUFDbEIsZUFBTztBQUFBLE1BQ1Q7QUFFQSxNQUFBQSxRQUFPLGFBQWEsU0FBUyxXQUFZLFVBQVU7QUFDakQsZ0JBQVEsT0FBTyxRQUFRLEVBQUUsWUFBWSxHQUFHO0FBQUEsVUFDdEMsS0FBSztBQUFBLFVBQ0wsS0FBSztBQUFBLFVBQ0wsS0FBSztBQUFBLFVBQ0wsS0FBSztBQUFBLFVBQ0wsS0FBSztBQUFBLFVBQ0wsS0FBSztBQUFBLFVBQ0wsS0FBSztBQUFBLFVBQ0wsS0FBSztBQUFBLFVBQ0wsS0FBSztBQUFBLFVBQ0wsS0FBSztBQUFBLFVBQ0wsS0FBSztBQUNILG1CQUFPO0FBQUEsVUFDVDtBQUNFLG1CQUFPO0FBQUEsUUFDWDtBQUFBLE1BQ0Y7QUFFQSxNQUFBQSxRQUFPLFNBQVMsU0FBUyxPQUFRLE1BQU0sUUFBUTtBQUM3QyxZQUFJLENBQUMsTUFBTSxRQUFRLElBQUksR0FBRztBQUN4QixnQkFBTSxJQUFJLFVBQVUsNkNBQTZDO0FBQUEsUUFDbkU7QUFFQSxZQUFJLEtBQUssV0FBVyxHQUFHO0FBQ3JCLGlCQUFPQSxRQUFPLE1BQU0sQ0FBQztBQUFBLFFBQ3ZCO0FBRUEsWUFBSTtBQUNKLFlBQUksV0FBVyxRQUFXO0FBQ3hCLG1CQUFTO0FBQ1QsZUFBSyxJQUFJLEdBQUcsSUFBSSxLQUFLLFFBQVEsRUFBRSxHQUFHO0FBQ2hDLHNCQUFVLEtBQUssQ0FBQyxFQUFFO0FBQUEsVUFDcEI7QUFBQSxRQUNGO0FBRUEsY0FBTSxTQUFTQSxRQUFPLFlBQVksTUFBTTtBQUN4QyxZQUFJLE1BQU07QUFDVixhQUFLLElBQUksR0FBRyxJQUFJLEtBQUssUUFBUSxFQUFFLEdBQUc7QUFDaEMsY0FBSSxNQUFNLEtBQUssQ0FBQztBQUNoQixjQUFJLFdBQVcsS0FBSyxVQUFVLEdBQUc7QUFDL0IsZ0JBQUksTUFBTSxJQUFJLFNBQVMsT0FBTyxRQUFRO0FBQ3BDLGtCQUFJLENBQUNBLFFBQU8sU0FBUyxHQUFHLEVBQUcsT0FBTUEsUUFBTyxLQUFLLEdBQUc7QUFDaEQsa0JBQUksS0FBSyxRQUFRLEdBQUc7QUFBQSxZQUN0QixPQUFPO0FBQ0wseUJBQVcsVUFBVSxJQUFJO0FBQUEsZ0JBQ3ZCO0FBQUEsZ0JBQ0E7QUFBQSxnQkFDQTtBQUFBLGNBQ0Y7QUFBQSxZQUNGO0FBQUEsVUFDRixXQUFXLENBQUNBLFFBQU8sU0FBUyxHQUFHLEdBQUc7QUFDaEMsa0JBQU0sSUFBSSxVQUFVLDZDQUE2QztBQUFBLFVBQ25FLE9BQU87QUFDTCxnQkFBSSxLQUFLLFFBQVEsR0FBRztBQUFBLFVBQ3RCO0FBQ0EsaUJBQU8sSUFBSTtBQUFBLFFBQ2I7QUFDQSxlQUFPO0FBQUEsTUFDVDtBQUVBLGVBQVMsV0FBWSxRQUFRLFVBQVU7QUFDckMsWUFBSUEsUUFBTyxTQUFTLE1BQU0sR0FBRztBQUMzQixpQkFBTyxPQUFPO0FBQUEsUUFDaEI7QUFDQSxZQUFJLFlBQVksT0FBTyxNQUFNLEtBQUssV0FBVyxRQUFRLFdBQVcsR0FBRztBQUNqRSxpQkFBTyxPQUFPO0FBQUEsUUFDaEI7QUFDQSxZQUFJLE9BQU8sV0FBVyxVQUFVO0FBQzlCLGdCQUFNLElBQUk7QUFBQSxZQUNSLDZGQUNtQixPQUFPO0FBQUEsVUFDNUI7QUFBQSxRQUNGO0FBRUEsY0FBTSxNQUFNLE9BQU87QUFDbkIsY0FBTSxZQUFhLFVBQVUsU0FBUyxLQUFLLFVBQVUsQ0FBQyxNQUFNO0FBQzVELFlBQUksQ0FBQyxhQUFhLFFBQVEsRUFBRyxRQUFPO0FBR3BDLFlBQUksY0FBYztBQUNsQixtQkFBUztBQUNQLGtCQUFRLFVBQVU7QUFBQSxZQUNoQixLQUFLO0FBQUEsWUFDTCxLQUFLO0FBQUEsWUFDTCxLQUFLO0FBQ0gscUJBQU87QUFBQSxZQUNULEtBQUs7QUFBQSxZQUNMLEtBQUs7QUFDSCxxQkFBT0MsYUFBWSxNQUFNLEVBQUU7QUFBQSxZQUM3QixLQUFLO0FBQUEsWUFDTCxLQUFLO0FBQUEsWUFDTCxLQUFLO0FBQUEsWUFDTCxLQUFLO0FBQ0gscUJBQU8sTUFBTTtBQUFBLFlBQ2YsS0FBSztBQUNILHFCQUFPLFFBQVE7QUFBQSxZQUNqQixLQUFLO0FBQ0gscUJBQU9DLGVBQWMsTUFBTSxFQUFFO0FBQUEsWUFDL0I7QUFDRSxrQkFBSSxhQUFhO0FBQ2YsdUJBQU8sWUFBWSxLQUFLRCxhQUFZLE1BQU0sRUFBRTtBQUFBLGNBQzlDO0FBQ0EsMEJBQVksS0FBSyxVQUFVLFlBQVk7QUFDdkMsNEJBQWM7QUFBQSxVQUNsQjtBQUFBLFFBQ0Y7QUFBQSxNQUNGO0FBQ0EsTUFBQUQsUUFBTyxhQUFhO0FBRXBCLGVBQVMsYUFBYyxVQUFVLE9BQU8sS0FBSztBQUMzQyxZQUFJLGNBQWM7QUFTbEIsWUFBSSxVQUFVLFVBQWEsUUFBUSxHQUFHO0FBQ3BDLGtCQUFRO0FBQUEsUUFDVjtBQUdBLFlBQUksUUFBUSxLQUFLLFFBQVE7QUFDdkIsaUJBQU87QUFBQSxRQUNUO0FBRUEsWUFBSSxRQUFRLFVBQWEsTUFBTSxLQUFLLFFBQVE7QUFDMUMsZ0JBQU0sS0FBSztBQUFBLFFBQ2I7QUFFQSxZQUFJLE9BQU8sR0FBRztBQUNaLGlCQUFPO0FBQUEsUUFDVDtBQUdBLGlCQUFTO0FBQ1QsbUJBQVc7QUFFWCxZQUFJLE9BQU8sT0FBTztBQUNoQixpQkFBTztBQUFBLFFBQ1Q7QUFFQSxZQUFJLENBQUMsU0FBVSxZQUFXO0FBRTFCLGVBQU8sTUFBTTtBQUNYLGtCQUFRLFVBQVU7QUFBQSxZQUNoQixLQUFLO0FBQ0gscUJBQU8sU0FBUyxNQUFNLE9BQU8sR0FBRztBQUFBLFlBRWxDLEtBQUs7QUFBQSxZQUNMLEtBQUs7QUFDSCxxQkFBTyxVQUFVLE1BQU0sT0FBTyxHQUFHO0FBQUEsWUFFbkMsS0FBSztBQUNILHFCQUFPLFdBQVcsTUFBTSxPQUFPLEdBQUc7QUFBQSxZQUVwQyxLQUFLO0FBQUEsWUFDTCxLQUFLO0FBQ0gscUJBQU8sWUFBWSxNQUFNLE9BQU8sR0FBRztBQUFBLFlBRXJDLEtBQUs7QUFDSCxxQkFBTyxZQUFZLE1BQU0sT0FBTyxHQUFHO0FBQUEsWUFFckMsS0FBSztBQUFBLFlBQ0wsS0FBSztBQUFBLFlBQ0wsS0FBSztBQUFBLFlBQ0wsS0FBSztBQUNILHFCQUFPLGFBQWEsTUFBTSxPQUFPLEdBQUc7QUFBQSxZQUV0QztBQUNFLGtCQUFJLFlBQWEsT0FBTSxJQUFJLFVBQVUsdUJBQXVCLFFBQVE7QUFDcEUsMEJBQVksV0FBVyxJQUFJLFlBQVk7QUFDdkMsNEJBQWM7QUFBQSxVQUNsQjtBQUFBLFFBQ0Y7QUFBQSxNQUNGO0FBUUEsTUFBQUEsUUFBTyxVQUFVLFlBQVk7QUFFN0IsZUFBUyxLQUFNLEdBQUcsR0FBRyxHQUFHO0FBQ3RCLGNBQU0sSUFBSSxFQUFFLENBQUM7QUFDYixVQUFFLENBQUMsSUFBSSxFQUFFLENBQUM7QUFDVixVQUFFLENBQUMsSUFBSTtBQUFBLE1BQ1Q7QUFFQSxNQUFBQSxRQUFPLFVBQVUsU0FBUyxTQUFTLFNBQVU7QUFDM0MsY0FBTSxNQUFNLEtBQUs7QUFDakIsWUFBSSxNQUFNLE1BQU0sR0FBRztBQUNqQixnQkFBTSxJQUFJLFdBQVcsMkNBQTJDO0FBQUEsUUFDbEU7QUFDQSxpQkFBUyxJQUFJLEdBQUcsSUFBSSxLQUFLLEtBQUssR0FBRztBQUMvQixlQUFLLE1BQU0sR0FBRyxJQUFJLENBQUM7QUFBQSxRQUNyQjtBQUNBLGVBQU87QUFBQSxNQUNUO0FBRUEsTUFBQUEsUUFBTyxVQUFVLFNBQVMsU0FBUyxTQUFVO0FBQzNDLGNBQU0sTUFBTSxLQUFLO0FBQ2pCLFlBQUksTUFBTSxNQUFNLEdBQUc7QUFDakIsZ0JBQU0sSUFBSSxXQUFXLDJDQUEyQztBQUFBLFFBQ2xFO0FBQ0EsaUJBQVMsSUFBSSxHQUFHLElBQUksS0FBSyxLQUFLLEdBQUc7QUFDL0IsZUFBSyxNQUFNLEdBQUcsSUFBSSxDQUFDO0FBQ25CLGVBQUssTUFBTSxJQUFJLEdBQUcsSUFBSSxDQUFDO0FBQUEsUUFDekI7QUFDQSxlQUFPO0FBQUEsTUFDVDtBQUVBLE1BQUFBLFFBQU8sVUFBVSxTQUFTLFNBQVMsU0FBVTtBQUMzQyxjQUFNLE1BQU0sS0FBSztBQUNqQixZQUFJLE1BQU0sTUFBTSxHQUFHO0FBQ2pCLGdCQUFNLElBQUksV0FBVywyQ0FBMkM7QUFBQSxRQUNsRTtBQUNBLGlCQUFTLElBQUksR0FBRyxJQUFJLEtBQUssS0FBSyxHQUFHO0FBQy9CLGVBQUssTUFBTSxHQUFHLElBQUksQ0FBQztBQUNuQixlQUFLLE1BQU0sSUFBSSxHQUFHLElBQUksQ0FBQztBQUN2QixlQUFLLE1BQU0sSUFBSSxHQUFHLElBQUksQ0FBQztBQUN2QixlQUFLLE1BQU0sSUFBSSxHQUFHLElBQUksQ0FBQztBQUFBLFFBQ3pCO0FBQ0EsZUFBTztBQUFBLE1BQ1Q7QUFFQSxNQUFBQSxRQUFPLFVBQVUsV0FBVyxTQUFTLFdBQVk7QUFDL0MsY0FBTSxTQUFTLEtBQUs7QUFDcEIsWUFBSSxXQUFXLEVBQUcsUUFBTztBQUN6QixZQUFJLFVBQVUsV0FBVyxFQUFHLFFBQU8sVUFBVSxNQUFNLEdBQUcsTUFBTTtBQUM1RCxlQUFPLGFBQWEsTUFBTSxNQUFNLFNBQVM7QUFBQSxNQUMzQztBQUVBLE1BQUFBLFFBQU8sVUFBVSxpQkFBaUJBLFFBQU8sVUFBVTtBQUVuRCxNQUFBQSxRQUFPLFVBQVUsU0FBUyxTQUFTLE9BQVEsR0FBRztBQUM1QyxZQUFJLENBQUNBLFFBQU8sU0FBUyxDQUFDLEVBQUcsT0FBTSxJQUFJLFVBQVUsMkJBQTJCO0FBQ3hFLFlBQUksU0FBUyxFQUFHLFFBQU87QUFDdkIsZUFBT0EsUUFBTyxRQUFRLE1BQU0sQ0FBQyxNQUFNO0FBQUEsTUFDckM7QUFFQSxNQUFBQSxRQUFPLFVBQVUsVUFBVSxTQUFTLFVBQVc7QUFDN0MsWUFBSSxNQUFNO0FBQ1YsY0FBTSxNQUFNLFFBQVE7QUFDcEIsY0FBTSxLQUFLLFNBQVMsT0FBTyxHQUFHLEdBQUcsRUFBRSxRQUFRLFdBQVcsS0FBSyxFQUFFLEtBQUs7QUFDbEUsWUFBSSxLQUFLLFNBQVMsSUFBSyxRQUFPO0FBQzlCLGVBQU8sYUFBYSxNQUFNO0FBQUEsTUFDNUI7QUFDQSxVQUFJLHFCQUFxQjtBQUN2QixRQUFBQSxRQUFPLFVBQVUsbUJBQW1CLElBQUlBLFFBQU8sVUFBVTtBQUFBLE1BQzNEO0FBRUEsTUFBQUEsUUFBTyxVQUFVLFVBQVUsU0FBUyxRQUFTLFFBQVEsT0FBTyxLQUFLLFdBQVcsU0FBUztBQUNuRixZQUFJLFdBQVcsUUFBUSxVQUFVLEdBQUc7QUFDbEMsbUJBQVNBLFFBQU8sS0FBSyxRQUFRLE9BQU8sUUFBUSxPQUFPLFVBQVU7QUFBQSxRQUMvRDtBQUNBLFlBQUksQ0FBQ0EsUUFBTyxTQUFTLE1BQU0sR0FBRztBQUM1QixnQkFBTSxJQUFJO0FBQUEsWUFDUixtRkFDb0IsT0FBTztBQUFBLFVBQzdCO0FBQUEsUUFDRjtBQUVBLFlBQUksVUFBVSxRQUFXO0FBQ3ZCLGtCQUFRO0FBQUEsUUFDVjtBQUNBLFlBQUksUUFBUSxRQUFXO0FBQ3JCLGdCQUFNLFNBQVMsT0FBTyxTQUFTO0FBQUEsUUFDakM7QUFDQSxZQUFJLGNBQWMsUUFBVztBQUMzQixzQkFBWTtBQUFBLFFBQ2Q7QUFDQSxZQUFJLFlBQVksUUFBVztBQUN6QixvQkFBVSxLQUFLO0FBQUEsUUFDakI7QUFFQSxZQUFJLFFBQVEsS0FBSyxNQUFNLE9BQU8sVUFBVSxZQUFZLEtBQUssVUFBVSxLQUFLLFFBQVE7QUFDOUUsZ0JBQU0sSUFBSSxXQUFXLG9CQUFvQjtBQUFBLFFBQzNDO0FBRUEsWUFBSSxhQUFhLFdBQVcsU0FBUyxLQUFLO0FBQ3hDLGlCQUFPO0FBQUEsUUFDVDtBQUNBLFlBQUksYUFBYSxTQUFTO0FBQ3hCLGlCQUFPO0FBQUEsUUFDVDtBQUNBLFlBQUksU0FBUyxLQUFLO0FBQ2hCLGlCQUFPO0FBQUEsUUFDVDtBQUVBLG1CQUFXO0FBQ1gsaUJBQVM7QUFDVCx1QkFBZTtBQUNmLHFCQUFhO0FBRWIsWUFBSSxTQUFTLE9BQVEsUUFBTztBQUU1QixZQUFJLElBQUksVUFBVTtBQUNsQixZQUFJLElBQUksTUFBTTtBQUNkLGNBQU0sTUFBTSxLQUFLLElBQUksR0FBRyxDQUFDO0FBRXpCLGNBQU0sV0FBVyxLQUFLLE1BQU0sV0FBVyxPQUFPO0FBQzlDLGNBQU0sYUFBYSxPQUFPLE1BQU0sT0FBTyxHQUFHO0FBRTFDLGlCQUFTLElBQUksR0FBRyxJQUFJLEtBQUssRUFBRSxHQUFHO0FBQzVCLGNBQUksU0FBUyxDQUFDLE1BQU0sV0FBVyxDQUFDLEdBQUc7QUFDakMsZ0JBQUksU0FBUyxDQUFDO0FBQ2QsZ0JBQUksV0FBVyxDQUFDO0FBQ2hCO0FBQUEsVUFDRjtBQUFBLFFBQ0Y7QUFFQSxZQUFJLElBQUksRUFBRyxRQUFPO0FBQ2xCLFlBQUksSUFBSSxFQUFHLFFBQU87QUFDbEIsZUFBTztBQUFBLE1BQ1Q7QUFXQSxlQUFTLHFCQUFzQixRQUFRLEtBQUssWUFBWSxVQUFVLEtBQUs7QUFFckUsWUFBSSxPQUFPLFdBQVcsRUFBRyxRQUFPO0FBR2hDLFlBQUksT0FBTyxlQUFlLFVBQVU7QUFDbEMscUJBQVc7QUFDWCx1QkFBYTtBQUFBLFFBQ2YsV0FBVyxhQUFhLFlBQVk7QUFDbEMsdUJBQWE7QUFBQSxRQUNmLFdBQVcsYUFBYSxhQUFhO0FBQ25DLHVCQUFhO0FBQUEsUUFDZjtBQUNBLHFCQUFhLENBQUM7QUFDZCxZQUFJLFlBQVksVUFBVSxHQUFHO0FBRTNCLHVCQUFhLE1BQU0sSUFBSyxPQUFPLFNBQVM7QUFBQSxRQUMxQztBQUdBLFlBQUksYUFBYSxFQUFHLGNBQWEsT0FBTyxTQUFTO0FBQ2pELFlBQUksY0FBYyxPQUFPLFFBQVE7QUFDL0IsY0FBSSxJQUFLLFFBQU87QUFBQSxjQUNYLGNBQWEsT0FBTyxTQUFTO0FBQUEsUUFDcEMsV0FBVyxhQUFhLEdBQUc7QUFDekIsY0FBSSxJQUFLLGNBQWE7QUFBQSxjQUNqQixRQUFPO0FBQUEsUUFDZDtBQUdBLFlBQUksT0FBTyxRQUFRLFVBQVU7QUFDM0IsZ0JBQU1BLFFBQU8sS0FBSyxLQUFLLFFBQVE7QUFBQSxRQUNqQztBQUdBLFlBQUlBLFFBQU8sU0FBUyxHQUFHLEdBQUc7QUFFeEIsY0FBSSxJQUFJLFdBQVcsR0FBRztBQUNwQixtQkFBTztBQUFBLFVBQ1Q7QUFDQSxpQkFBTyxhQUFhLFFBQVEsS0FBSyxZQUFZLFVBQVUsR0FBRztBQUFBLFFBQzVELFdBQVcsT0FBTyxRQUFRLFVBQVU7QUFDbEMsZ0JBQU0sTUFBTTtBQUNaLGNBQUksT0FBTyxXQUFXLFVBQVUsWUFBWSxZQUFZO0FBQ3RELGdCQUFJLEtBQUs7QUFDUCxxQkFBTyxXQUFXLFVBQVUsUUFBUSxLQUFLLFFBQVEsS0FBSyxVQUFVO0FBQUEsWUFDbEUsT0FBTztBQUNMLHFCQUFPLFdBQVcsVUFBVSxZQUFZLEtBQUssUUFBUSxLQUFLLFVBQVU7QUFBQSxZQUN0RTtBQUFBLFVBQ0Y7QUFDQSxpQkFBTyxhQUFhLFFBQVEsQ0FBQyxHQUFHLEdBQUcsWUFBWSxVQUFVLEdBQUc7QUFBQSxRQUM5RDtBQUVBLGNBQU0sSUFBSSxVQUFVLHNDQUFzQztBQUFBLE1BQzVEO0FBRUEsZUFBUyxhQUFjLEtBQUssS0FBSyxZQUFZLFVBQVUsS0FBSztBQUMxRCxZQUFJLFlBQVk7QUFDaEIsWUFBSSxZQUFZLElBQUk7QUFDcEIsWUFBSSxZQUFZLElBQUk7QUFFcEIsWUFBSSxhQUFhLFFBQVc7QUFDMUIscUJBQVcsT0FBTyxRQUFRLEVBQUUsWUFBWTtBQUN4QyxjQUFJLGFBQWEsVUFBVSxhQUFhLFdBQ3BDLGFBQWEsYUFBYSxhQUFhLFlBQVk7QUFDckQsZ0JBQUksSUFBSSxTQUFTLEtBQUssSUFBSSxTQUFTLEdBQUc7QUFDcEMscUJBQU87QUFBQSxZQUNUO0FBQ0Esd0JBQVk7QUFDWix5QkFBYTtBQUNiLHlCQUFhO0FBQ2IsMEJBQWM7QUFBQSxVQUNoQjtBQUFBLFFBQ0Y7QUFFQSxpQkFBUyxLQUFNLEtBQUtHLElBQUc7QUFDckIsY0FBSSxjQUFjLEdBQUc7QUFDbkIsbUJBQU8sSUFBSUEsRUFBQztBQUFBLFVBQ2QsT0FBTztBQUNMLG1CQUFPLElBQUksYUFBYUEsS0FBSSxTQUFTO0FBQUEsVUFDdkM7QUFBQSxRQUNGO0FBRUEsWUFBSTtBQUNKLFlBQUksS0FBSztBQUNQLGNBQUksYUFBYTtBQUNqQixlQUFLLElBQUksWUFBWSxJQUFJLFdBQVcsS0FBSztBQUN2QyxnQkFBSSxLQUFLLEtBQUssQ0FBQyxNQUFNLEtBQUssS0FBSyxlQUFlLEtBQUssSUFBSSxJQUFJLFVBQVUsR0FBRztBQUN0RSxrQkFBSSxlQUFlLEdBQUksY0FBYTtBQUNwQyxrQkFBSSxJQUFJLGFBQWEsTUFBTSxVQUFXLFFBQU8sYUFBYTtBQUFBLFlBQzVELE9BQU87QUFDTCxrQkFBSSxlQUFlLEdBQUksTUFBSyxJQUFJO0FBQ2hDLDJCQUFhO0FBQUEsWUFDZjtBQUFBLFVBQ0Y7QUFBQSxRQUNGLE9BQU87QUFDTCxjQUFJLGFBQWEsWUFBWSxVQUFXLGNBQWEsWUFBWTtBQUNqRSxlQUFLLElBQUksWUFBWSxLQUFLLEdBQUcsS0FBSztBQUNoQyxnQkFBSSxRQUFRO0FBQ1oscUJBQVMsSUFBSSxHQUFHLElBQUksV0FBVyxLQUFLO0FBQ2xDLGtCQUFJLEtBQUssS0FBSyxJQUFJLENBQUMsTUFBTSxLQUFLLEtBQUssQ0FBQyxHQUFHO0FBQ3JDLHdCQUFRO0FBQ1I7QUFBQSxjQUNGO0FBQUEsWUFDRjtBQUNBLGdCQUFJLE1BQU8sUUFBTztBQUFBLFVBQ3BCO0FBQUEsUUFDRjtBQUVBLGVBQU87QUFBQSxNQUNUO0FBRUEsTUFBQUgsUUFBTyxVQUFVLFdBQVcsU0FBUyxTQUFVLEtBQUssWUFBWSxVQUFVO0FBQ3hFLGVBQU8sS0FBSyxRQUFRLEtBQUssWUFBWSxRQUFRLE1BQU07QUFBQSxNQUNyRDtBQUVBLE1BQUFBLFFBQU8sVUFBVSxVQUFVLFNBQVMsUUFBUyxLQUFLLFlBQVksVUFBVTtBQUN0RSxlQUFPLHFCQUFxQixNQUFNLEtBQUssWUFBWSxVQUFVLElBQUk7QUFBQSxNQUNuRTtBQUVBLE1BQUFBLFFBQU8sVUFBVSxjQUFjLFNBQVMsWUFBYSxLQUFLLFlBQVksVUFBVTtBQUM5RSxlQUFPLHFCQUFxQixNQUFNLEtBQUssWUFBWSxVQUFVLEtBQUs7QUFBQSxNQUNwRTtBQUVBLGVBQVMsU0FBVSxLQUFLLFFBQVEsUUFBUSxRQUFRO0FBQzlDLGlCQUFTLE9BQU8sTUFBTSxLQUFLO0FBQzNCLGNBQU0sWUFBWSxJQUFJLFNBQVM7QUFDL0IsWUFBSSxDQUFDLFFBQVE7QUFDWCxtQkFBUztBQUFBLFFBQ1gsT0FBTztBQUNMLG1CQUFTLE9BQU8sTUFBTTtBQUN0QixjQUFJLFNBQVMsV0FBVztBQUN0QixxQkFBUztBQUFBLFVBQ1g7QUFBQSxRQUNGO0FBRUEsY0FBTSxTQUFTLE9BQU87QUFFdEIsWUFBSSxTQUFTLFNBQVMsR0FBRztBQUN2QixtQkFBUyxTQUFTO0FBQUEsUUFDcEI7QUFDQSxZQUFJO0FBQ0osYUFBSyxJQUFJLEdBQUcsSUFBSSxRQUFRLEVBQUUsR0FBRztBQUMzQixnQkFBTSxTQUFTLFNBQVMsT0FBTyxPQUFPLElBQUksR0FBRyxDQUFDLEdBQUcsRUFBRTtBQUNuRCxjQUFJLFlBQVksTUFBTSxFQUFHLFFBQU87QUFDaEMsY0FBSSxTQUFTLENBQUMsSUFBSTtBQUFBLFFBQ3BCO0FBQ0EsZUFBTztBQUFBLE1BQ1Q7QUFFQSxlQUFTLFVBQVcsS0FBSyxRQUFRLFFBQVEsUUFBUTtBQUMvQyxlQUFPLFdBQVdDLGFBQVksUUFBUSxJQUFJLFNBQVMsTUFBTSxHQUFHLEtBQUssUUFBUSxNQUFNO0FBQUEsTUFDakY7QUFFQSxlQUFTLFdBQVksS0FBSyxRQUFRLFFBQVEsUUFBUTtBQUNoRCxlQUFPLFdBQVdHLGNBQWEsTUFBTSxHQUFHLEtBQUssUUFBUSxNQUFNO0FBQUEsTUFDN0Q7QUFFQSxlQUFTLFlBQWEsS0FBSyxRQUFRLFFBQVEsUUFBUTtBQUNqRCxlQUFPLFdBQVdGLGVBQWMsTUFBTSxHQUFHLEtBQUssUUFBUSxNQUFNO0FBQUEsTUFDOUQ7QUFFQSxlQUFTLFVBQVcsS0FBSyxRQUFRLFFBQVEsUUFBUTtBQUMvQyxlQUFPLFdBQVcsZUFBZSxRQUFRLElBQUksU0FBUyxNQUFNLEdBQUcsS0FBSyxRQUFRLE1BQU07QUFBQSxNQUNwRjtBQUVBLE1BQUFGLFFBQU8sVUFBVSxRQUFRLFNBQVMsTUFBTyxRQUFRLFFBQVEsUUFBUSxVQUFVO0FBRXpFLFlBQUksV0FBVyxRQUFXO0FBQ3hCLHFCQUFXO0FBQ1gsbUJBQVMsS0FBSztBQUNkLG1CQUFTO0FBQUEsUUFFWCxXQUFXLFdBQVcsVUFBYSxPQUFPLFdBQVcsVUFBVTtBQUM3RCxxQkFBVztBQUNYLG1CQUFTLEtBQUs7QUFDZCxtQkFBUztBQUFBLFFBRVgsV0FBVyxTQUFTLE1BQU0sR0FBRztBQUMzQixtQkFBUyxXQUFXO0FBQ3BCLGNBQUksU0FBUyxNQUFNLEdBQUc7QUFDcEIscUJBQVMsV0FBVztBQUNwQixnQkFBSSxhQUFhLE9BQVcsWUFBVztBQUFBLFVBQ3pDLE9BQU87QUFDTCx1QkFBVztBQUNYLHFCQUFTO0FBQUEsVUFDWDtBQUFBLFFBQ0YsT0FBTztBQUNMLGdCQUFNLElBQUk7QUFBQSxZQUNSO0FBQUEsVUFDRjtBQUFBLFFBQ0Y7QUFFQSxjQUFNLFlBQVksS0FBSyxTQUFTO0FBQ2hDLFlBQUksV0FBVyxVQUFhLFNBQVMsVUFBVyxVQUFTO0FBRXpELFlBQUssT0FBTyxTQUFTLE1BQU0sU0FBUyxLQUFLLFNBQVMsTUFBTyxTQUFTLEtBQUssUUFBUTtBQUM3RSxnQkFBTSxJQUFJLFdBQVcsd0NBQXdDO0FBQUEsUUFDL0Q7QUFFQSxZQUFJLENBQUMsU0FBVSxZQUFXO0FBRTFCLFlBQUksY0FBYztBQUNsQixtQkFBUztBQUNQLGtCQUFRLFVBQVU7QUFBQSxZQUNoQixLQUFLO0FBQ0gscUJBQU8sU0FBUyxNQUFNLFFBQVEsUUFBUSxNQUFNO0FBQUEsWUFFOUMsS0FBSztBQUFBLFlBQ0wsS0FBSztBQUNILHFCQUFPLFVBQVUsTUFBTSxRQUFRLFFBQVEsTUFBTTtBQUFBLFlBRS9DLEtBQUs7QUFBQSxZQUNMLEtBQUs7QUFBQSxZQUNMLEtBQUs7QUFDSCxxQkFBTyxXQUFXLE1BQU0sUUFBUSxRQUFRLE1BQU07QUFBQSxZQUVoRCxLQUFLO0FBRUgscUJBQU8sWUFBWSxNQUFNLFFBQVEsUUFBUSxNQUFNO0FBQUEsWUFFakQsS0FBSztBQUFBLFlBQ0wsS0FBSztBQUFBLFlBQ0wsS0FBSztBQUFBLFlBQ0wsS0FBSztBQUNILHFCQUFPLFVBQVUsTUFBTSxRQUFRLFFBQVEsTUFBTTtBQUFBLFlBRS9DO0FBQ0Usa0JBQUksWUFBYSxPQUFNLElBQUksVUFBVSx1QkFBdUIsUUFBUTtBQUNwRSwwQkFBWSxLQUFLLFVBQVUsWUFBWTtBQUN2Qyw0QkFBYztBQUFBLFVBQ2xCO0FBQUEsUUFDRjtBQUFBLE1BQ0Y7QUFFQSxNQUFBQSxRQUFPLFVBQVUsU0FBUyxTQUFTLFNBQVU7QUFDM0MsZUFBTztBQUFBLFVBQ0wsTUFBTTtBQUFBLFVBQ04sTUFBTSxNQUFNLFVBQVUsTUFBTSxLQUFLLEtBQUssUUFBUSxNQUFNLENBQUM7QUFBQSxRQUN2RDtBQUFBLE1BQ0Y7QUFFQSxlQUFTLFlBQWEsS0FBSyxPQUFPLEtBQUs7QUFDckMsWUFBSSxVQUFVLEtBQUssUUFBUSxJQUFJLFFBQVE7QUFDckMsaUJBQU9ELFFBQU8sY0FBYyxHQUFHO0FBQUEsUUFDakMsT0FBTztBQUNMLGlCQUFPQSxRQUFPLGNBQWMsSUFBSSxNQUFNLE9BQU8sR0FBRyxDQUFDO0FBQUEsUUFDbkQ7QUFBQSxNQUNGO0FBRUEsZUFBUyxVQUFXLEtBQUssT0FBTyxLQUFLO0FBQ25DLGNBQU0sS0FBSyxJQUFJLElBQUksUUFBUSxHQUFHO0FBQzlCLGNBQU0sTUFBTSxDQUFDO0FBRWIsWUFBSSxJQUFJO0FBQ1IsZUFBTyxJQUFJLEtBQUs7QUFDZCxnQkFBTSxZQUFZLElBQUksQ0FBQztBQUN2QixjQUFJLFlBQVk7QUFDaEIsY0FBSSxtQkFBb0IsWUFBWSxNQUNoQyxJQUNDLFlBQVksTUFDVCxJQUNDLFlBQVksTUFDVCxJQUNBO0FBRVosY0FBSSxJQUFJLG9CQUFvQixLQUFLO0FBQy9CLGdCQUFJLFlBQVksV0FBVyxZQUFZO0FBRXZDLG9CQUFRLGtCQUFrQjtBQUFBLGNBQ3hCLEtBQUs7QUFDSCxvQkFBSSxZQUFZLEtBQU07QUFDcEIsOEJBQVk7QUFBQSxnQkFDZDtBQUNBO0FBQUEsY0FDRixLQUFLO0FBQ0gsNkJBQWEsSUFBSSxJQUFJLENBQUM7QUFDdEIscUJBQUssYUFBYSxTQUFVLEtBQU07QUFDaEMsbUNBQWlCLFlBQVksT0FBUyxJQUFPLGFBQWE7QUFDMUQsc0JBQUksZ0JBQWdCLEtBQU07QUFDeEIsZ0NBQVk7QUFBQSxrQkFDZDtBQUFBLGdCQUNGO0FBQ0E7QUFBQSxjQUNGLEtBQUs7QUFDSCw2QkFBYSxJQUFJLElBQUksQ0FBQztBQUN0Qiw0QkFBWSxJQUFJLElBQUksQ0FBQztBQUNyQixxQkFBSyxhQUFhLFNBQVUsUUFBUyxZQUFZLFNBQVUsS0FBTTtBQUMvRCxtQ0FBaUIsWUFBWSxPQUFRLE1BQU8sYUFBYSxPQUFTLElBQU8sWUFBWTtBQUNyRixzQkFBSSxnQkFBZ0IsU0FBVSxnQkFBZ0IsU0FBVSxnQkFBZ0IsUUFBUztBQUMvRSxnQ0FBWTtBQUFBLGtCQUNkO0FBQUEsZ0JBQ0Y7QUFDQTtBQUFBLGNBQ0YsS0FBSztBQUNILDZCQUFhLElBQUksSUFBSSxDQUFDO0FBQ3RCLDRCQUFZLElBQUksSUFBSSxDQUFDO0FBQ3JCLDZCQUFhLElBQUksSUFBSSxDQUFDO0FBQ3RCLHFCQUFLLGFBQWEsU0FBVSxRQUFTLFlBQVksU0FBVSxRQUFTLGFBQWEsU0FBVSxLQUFNO0FBQy9GLG1DQUFpQixZQUFZLE9BQVEsTUFBUSxhQUFhLE9BQVMsTUFBTyxZQUFZLE9BQVMsSUFBTyxhQUFhO0FBQ25ILHNCQUFJLGdCQUFnQixTQUFVLGdCQUFnQixTQUFVO0FBQ3RELGdDQUFZO0FBQUEsa0JBQ2Q7QUFBQSxnQkFDRjtBQUFBLFlBQ0o7QUFBQSxVQUNGO0FBRUEsY0FBSSxjQUFjLE1BQU07QUFHdEIsd0JBQVk7QUFDWiwrQkFBbUI7QUFBQSxVQUNyQixXQUFXLFlBQVksT0FBUTtBQUU3Qix5QkFBYTtBQUNiLGdCQUFJLEtBQUssY0FBYyxLQUFLLE9BQVEsS0FBTTtBQUMxQyx3QkFBWSxRQUFTLFlBQVk7QUFBQSxVQUNuQztBQUVBLGNBQUksS0FBSyxTQUFTO0FBQ2xCLGVBQUs7QUFBQSxRQUNQO0FBRUEsZUFBTyxzQkFBc0IsR0FBRztBQUFBLE1BQ2xDO0FBS0EsVUFBTSx1QkFBdUI7QUFFN0IsZUFBUyxzQkFBdUIsWUFBWTtBQUMxQyxjQUFNLE1BQU0sV0FBVztBQUN2QixZQUFJLE9BQU8sc0JBQXNCO0FBQy9CLGlCQUFPLE9BQU8sYUFBYSxNQUFNLFFBQVEsVUFBVTtBQUFBLFFBQ3JEO0FBR0EsWUFBSSxNQUFNO0FBQ1YsWUFBSSxJQUFJO0FBQ1IsZUFBTyxJQUFJLEtBQUs7QUFDZCxpQkFBTyxPQUFPLGFBQWE7QUFBQSxZQUN6QjtBQUFBLFlBQ0EsV0FBVyxNQUFNLEdBQUcsS0FBSyxvQkFBb0I7QUFBQSxVQUMvQztBQUFBLFFBQ0Y7QUFDQSxlQUFPO0FBQUEsTUFDVDtBQUVBLGVBQVMsV0FBWSxLQUFLLE9BQU8sS0FBSztBQUNwQyxZQUFJLE1BQU07QUFDVixjQUFNLEtBQUssSUFBSSxJQUFJLFFBQVEsR0FBRztBQUU5QixpQkFBUyxJQUFJLE9BQU8sSUFBSSxLQUFLLEVBQUUsR0FBRztBQUNoQyxpQkFBTyxPQUFPLGFBQWEsSUFBSSxDQUFDLElBQUksR0FBSTtBQUFBLFFBQzFDO0FBQ0EsZUFBTztBQUFBLE1BQ1Q7QUFFQSxlQUFTLFlBQWEsS0FBSyxPQUFPLEtBQUs7QUFDckMsWUFBSSxNQUFNO0FBQ1YsY0FBTSxLQUFLLElBQUksSUFBSSxRQUFRLEdBQUc7QUFFOUIsaUJBQVMsSUFBSSxPQUFPLElBQUksS0FBSyxFQUFFLEdBQUc7QUFDaEMsaUJBQU8sT0FBTyxhQUFhLElBQUksQ0FBQyxDQUFDO0FBQUEsUUFDbkM7QUFDQSxlQUFPO0FBQUEsTUFDVDtBQUVBLGVBQVMsU0FBVSxLQUFLLE9BQU8sS0FBSztBQUNsQyxjQUFNLE1BQU0sSUFBSTtBQUVoQixZQUFJLENBQUMsU0FBUyxRQUFRLEVBQUcsU0FBUTtBQUNqQyxZQUFJLENBQUMsT0FBTyxNQUFNLEtBQUssTUFBTSxJQUFLLE9BQU07QUFFeEMsWUFBSSxNQUFNO0FBQ1YsaUJBQVMsSUFBSSxPQUFPLElBQUksS0FBSyxFQUFFLEdBQUc7QUFDaEMsaUJBQU8sb0JBQW9CLElBQUksQ0FBQyxDQUFDO0FBQUEsUUFDbkM7QUFDQSxlQUFPO0FBQUEsTUFDVDtBQUVBLGVBQVMsYUFBYyxLQUFLLE9BQU8sS0FBSztBQUN0QyxjQUFNLFFBQVEsSUFBSSxNQUFNLE9BQU8sR0FBRztBQUNsQyxZQUFJLE1BQU07QUFFVixpQkFBUyxJQUFJLEdBQUcsSUFBSSxNQUFNLFNBQVMsR0FBRyxLQUFLLEdBQUc7QUFDNUMsaUJBQU8sT0FBTyxhQUFhLE1BQU0sQ0FBQyxJQUFLLE1BQU0sSUFBSSxDQUFDLElBQUksR0FBSTtBQUFBLFFBQzVEO0FBQ0EsZUFBTztBQUFBLE1BQ1Q7QUFFQSxNQUFBQyxRQUFPLFVBQVUsUUFBUSxTQUFTLE1BQU8sT0FBTyxLQUFLO0FBQ25ELGNBQU0sTUFBTSxLQUFLO0FBQ2pCLGdCQUFRLENBQUMsQ0FBQztBQUNWLGNBQU0sUUFBUSxTQUFZLE1BQU0sQ0FBQyxDQUFDO0FBRWxDLFlBQUksUUFBUSxHQUFHO0FBQ2IsbUJBQVM7QUFDVCxjQUFJLFFBQVEsRUFBRyxTQUFRO0FBQUEsUUFDekIsV0FBVyxRQUFRLEtBQUs7QUFDdEIsa0JBQVE7QUFBQSxRQUNWO0FBRUEsWUFBSSxNQUFNLEdBQUc7QUFDWCxpQkFBTztBQUNQLGNBQUksTUFBTSxFQUFHLE9BQU07QUFBQSxRQUNyQixXQUFXLE1BQU0sS0FBSztBQUNwQixnQkFBTTtBQUFBLFFBQ1I7QUFFQSxZQUFJLE1BQU0sTUFBTyxPQUFNO0FBRXZCLGNBQU0sU0FBUyxLQUFLLFNBQVMsT0FBTyxHQUFHO0FBRXZDLGVBQU8sZUFBZSxRQUFRQSxRQUFPLFNBQVM7QUFFOUMsZUFBTztBQUFBLE1BQ1Q7QUFLQSxlQUFTLFlBQWEsUUFBUSxLQUFLLFFBQVE7QUFDekMsWUFBSyxTQUFTLE1BQU8sS0FBSyxTQUFTLEVBQUcsT0FBTSxJQUFJLFdBQVcsb0JBQW9CO0FBQy9FLFlBQUksU0FBUyxNQUFNLE9BQVEsT0FBTSxJQUFJLFdBQVcsdUNBQXVDO0FBQUEsTUFDekY7QUFFQSxNQUFBQSxRQUFPLFVBQVUsYUFDakJBLFFBQU8sVUFBVSxhQUFhLFNBQVMsV0FBWSxRQUFRSyxhQUFZLFVBQVU7QUFDL0UsaUJBQVMsV0FBVztBQUNwQixRQUFBQSxjQUFhQSxnQkFBZTtBQUM1QixZQUFJLENBQUMsU0FBVSxhQUFZLFFBQVFBLGFBQVksS0FBSyxNQUFNO0FBRTFELFlBQUksTUFBTSxLQUFLLE1BQU07QUFDckIsWUFBSSxNQUFNO0FBQ1YsWUFBSSxJQUFJO0FBQ1IsZUFBTyxFQUFFLElBQUlBLGdCQUFlLE9BQU8sTUFBUTtBQUN6QyxpQkFBTyxLQUFLLFNBQVMsQ0FBQyxJQUFJO0FBQUEsUUFDNUI7QUFFQSxlQUFPO0FBQUEsTUFDVDtBQUVBLE1BQUFMLFFBQU8sVUFBVSxhQUNqQkEsUUFBTyxVQUFVLGFBQWEsU0FBUyxXQUFZLFFBQVFLLGFBQVksVUFBVTtBQUMvRSxpQkFBUyxXQUFXO0FBQ3BCLFFBQUFBLGNBQWFBLGdCQUFlO0FBQzVCLFlBQUksQ0FBQyxVQUFVO0FBQ2Isc0JBQVksUUFBUUEsYUFBWSxLQUFLLE1BQU07QUFBQSxRQUM3QztBQUVBLFlBQUksTUFBTSxLQUFLLFNBQVMsRUFBRUEsV0FBVTtBQUNwQyxZQUFJLE1BQU07QUFDVixlQUFPQSxjQUFhLE1BQU0sT0FBTyxNQUFRO0FBQ3ZDLGlCQUFPLEtBQUssU0FBUyxFQUFFQSxXQUFVLElBQUk7QUFBQSxRQUN2QztBQUVBLGVBQU87QUFBQSxNQUNUO0FBRUEsTUFBQUwsUUFBTyxVQUFVLFlBQ2pCQSxRQUFPLFVBQVUsWUFBWSxTQUFTLFVBQVcsUUFBUSxVQUFVO0FBQ2pFLGlCQUFTLFdBQVc7QUFDcEIsWUFBSSxDQUFDLFNBQVUsYUFBWSxRQUFRLEdBQUcsS0FBSyxNQUFNO0FBQ2pELGVBQU8sS0FBSyxNQUFNO0FBQUEsTUFDcEI7QUFFQSxNQUFBQSxRQUFPLFVBQVUsZUFDakJBLFFBQU8sVUFBVSxlQUFlLFNBQVMsYUFBYyxRQUFRLFVBQVU7QUFDdkUsaUJBQVMsV0FBVztBQUNwQixZQUFJLENBQUMsU0FBVSxhQUFZLFFBQVEsR0FBRyxLQUFLLE1BQU07QUFDakQsZUFBTyxLQUFLLE1BQU0sSUFBSyxLQUFLLFNBQVMsQ0FBQyxLQUFLO0FBQUEsTUFDN0M7QUFFQSxNQUFBQSxRQUFPLFVBQVUsZUFDakJBLFFBQU8sVUFBVSxlQUFlLFNBQVMsYUFBYyxRQUFRLFVBQVU7QUFDdkUsaUJBQVMsV0FBVztBQUNwQixZQUFJLENBQUMsU0FBVSxhQUFZLFFBQVEsR0FBRyxLQUFLLE1BQU07QUFDakQsZUFBUSxLQUFLLE1BQU0sS0FBSyxJQUFLLEtBQUssU0FBUyxDQUFDO0FBQUEsTUFDOUM7QUFFQSxNQUFBQSxRQUFPLFVBQVUsZUFDakJBLFFBQU8sVUFBVSxlQUFlLFNBQVMsYUFBYyxRQUFRLFVBQVU7QUFDdkUsaUJBQVMsV0FBVztBQUNwQixZQUFJLENBQUMsU0FBVSxhQUFZLFFBQVEsR0FBRyxLQUFLLE1BQU07QUFFakQsZ0JBQVMsS0FBSyxNQUFNLElBQ2YsS0FBSyxTQUFTLENBQUMsS0FBSyxJQUNwQixLQUFLLFNBQVMsQ0FBQyxLQUFLLE1BQ3BCLEtBQUssU0FBUyxDQUFDLElBQUk7QUFBQSxNQUMxQjtBQUVBLE1BQUFBLFFBQU8sVUFBVSxlQUNqQkEsUUFBTyxVQUFVLGVBQWUsU0FBUyxhQUFjLFFBQVEsVUFBVTtBQUN2RSxpQkFBUyxXQUFXO0FBQ3BCLFlBQUksQ0FBQyxTQUFVLGFBQVksUUFBUSxHQUFHLEtBQUssTUFBTTtBQUVqRCxlQUFRLEtBQUssTUFBTSxJQUFJLFlBQ25CLEtBQUssU0FBUyxDQUFDLEtBQUssS0FDckIsS0FBSyxTQUFTLENBQUMsS0FBSyxJQUNyQixLQUFLLFNBQVMsQ0FBQztBQUFBLE1BQ25CO0FBRUEsTUFBQUEsUUFBTyxVQUFVLGtCQUFrQixtQkFBbUIsU0FBUyxnQkFBaUIsUUFBUTtBQUN0RixpQkFBUyxXQUFXO0FBQ3BCLHVCQUFlLFFBQVEsUUFBUTtBQUMvQixjQUFNLFFBQVEsS0FBSyxNQUFNO0FBQ3pCLGNBQU0sT0FBTyxLQUFLLFNBQVMsQ0FBQztBQUM1QixZQUFJLFVBQVUsVUFBYSxTQUFTLFFBQVc7QUFDN0Msc0JBQVksUUFBUSxLQUFLLFNBQVMsQ0FBQztBQUFBLFFBQ3JDO0FBRUEsY0FBTSxLQUFLLFFBQ1QsS0FBSyxFQUFFLE1BQU0sSUFBSSxLQUFLLElBQ3RCLEtBQUssRUFBRSxNQUFNLElBQUksS0FBSyxLQUN0QixLQUFLLEVBQUUsTUFBTSxJQUFJLEtBQUs7QUFFeEIsY0FBTSxLQUFLLEtBQUssRUFBRSxNQUFNLElBQ3RCLEtBQUssRUFBRSxNQUFNLElBQUksS0FBSyxJQUN0QixLQUFLLEVBQUUsTUFBTSxJQUFJLEtBQUssS0FDdEIsT0FBTyxLQUFLO0FBRWQsZUFBTyxPQUFPLEVBQUUsS0FBSyxPQUFPLEVBQUUsS0FBSyxPQUFPLEVBQUU7QUFBQSxNQUM5QyxDQUFDO0FBRUQsTUFBQUEsUUFBTyxVQUFVLGtCQUFrQixtQkFBbUIsU0FBUyxnQkFBaUIsUUFBUTtBQUN0RixpQkFBUyxXQUFXO0FBQ3BCLHVCQUFlLFFBQVEsUUFBUTtBQUMvQixjQUFNLFFBQVEsS0FBSyxNQUFNO0FBQ3pCLGNBQU0sT0FBTyxLQUFLLFNBQVMsQ0FBQztBQUM1QixZQUFJLFVBQVUsVUFBYSxTQUFTLFFBQVc7QUFDN0Msc0JBQVksUUFBUSxLQUFLLFNBQVMsQ0FBQztBQUFBLFFBQ3JDO0FBRUEsY0FBTSxLQUFLLFFBQVEsS0FBSyxLQUN0QixLQUFLLEVBQUUsTUFBTSxJQUFJLEtBQUssS0FDdEIsS0FBSyxFQUFFLE1BQU0sSUFBSSxLQUFLLElBQ3RCLEtBQUssRUFBRSxNQUFNO0FBRWYsY0FBTSxLQUFLLEtBQUssRUFBRSxNQUFNLElBQUksS0FBSyxLQUMvQixLQUFLLEVBQUUsTUFBTSxJQUFJLEtBQUssS0FDdEIsS0FBSyxFQUFFLE1BQU0sSUFBSSxLQUFLLElBQ3RCO0FBRUYsZ0JBQVEsT0FBTyxFQUFFLEtBQUssT0FBTyxFQUFFLEtBQUssT0FBTyxFQUFFO0FBQUEsTUFDL0MsQ0FBQztBQUVELE1BQUFBLFFBQU8sVUFBVSxZQUFZLFNBQVMsVUFBVyxRQUFRSyxhQUFZLFVBQVU7QUFDN0UsaUJBQVMsV0FBVztBQUNwQixRQUFBQSxjQUFhQSxnQkFBZTtBQUM1QixZQUFJLENBQUMsU0FBVSxhQUFZLFFBQVFBLGFBQVksS0FBSyxNQUFNO0FBRTFELFlBQUksTUFBTSxLQUFLLE1BQU07QUFDckIsWUFBSSxNQUFNO0FBQ1YsWUFBSSxJQUFJO0FBQ1IsZUFBTyxFQUFFLElBQUlBLGdCQUFlLE9BQU8sTUFBUTtBQUN6QyxpQkFBTyxLQUFLLFNBQVMsQ0FBQyxJQUFJO0FBQUEsUUFDNUI7QUFDQSxlQUFPO0FBRVAsWUFBSSxPQUFPLElBQUssUUFBTyxLQUFLLElBQUksR0FBRyxJQUFJQSxXQUFVO0FBRWpELGVBQU87QUFBQSxNQUNUO0FBRUEsTUFBQUwsUUFBTyxVQUFVLFlBQVksU0FBUyxVQUFXLFFBQVFLLGFBQVksVUFBVTtBQUM3RSxpQkFBUyxXQUFXO0FBQ3BCLFFBQUFBLGNBQWFBLGdCQUFlO0FBQzVCLFlBQUksQ0FBQyxTQUFVLGFBQVksUUFBUUEsYUFBWSxLQUFLLE1BQU07QUFFMUQsWUFBSSxJQUFJQTtBQUNSLFlBQUksTUFBTTtBQUNWLFlBQUksTUFBTSxLQUFLLFNBQVMsRUFBRSxDQUFDO0FBQzNCLGVBQU8sSUFBSSxNQUFNLE9BQU8sTUFBUTtBQUM5QixpQkFBTyxLQUFLLFNBQVMsRUFBRSxDQUFDLElBQUk7QUFBQSxRQUM5QjtBQUNBLGVBQU87QUFFUCxZQUFJLE9BQU8sSUFBSyxRQUFPLEtBQUssSUFBSSxHQUFHLElBQUlBLFdBQVU7QUFFakQsZUFBTztBQUFBLE1BQ1Q7QUFFQSxNQUFBTCxRQUFPLFVBQVUsV0FBVyxTQUFTLFNBQVUsUUFBUSxVQUFVO0FBQy9ELGlCQUFTLFdBQVc7QUFDcEIsWUFBSSxDQUFDLFNBQVUsYUFBWSxRQUFRLEdBQUcsS0FBSyxNQUFNO0FBQ2pELFlBQUksRUFBRSxLQUFLLE1BQU0sSUFBSSxLQUFPLFFBQVEsS0FBSyxNQUFNO0FBQy9DLGdCQUFTLE1BQU8sS0FBSyxNQUFNLElBQUksS0FBSztBQUFBLE1BQ3RDO0FBRUEsTUFBQUEsUUFBTyxVQUFVLGNBQWMsU0FBUyxZQUFhLFFBQVEsVUFBVTtBQUNyRSxpQkFBUyxXQUFXO0FBQ3BCLFlBQUksQ0FBQyxTQUFVLGFBQVksUUFBUSxHQUFHLEtBQUssTUFBTTtBQUNqRCxjQUFNLE1BQU0sS0FBSyxNQUFNLElBQUssS0FBSyxTQUFTLENBQUMsS0FBSztBQUNoRCxlQUFRLE1BQU0sUUFBVSxNQUFNLGFBQWE7QUFBQSxNQUM3QztBQUVBLE1BQUFBLFFBQU8sVUFBVSxjQUFjLFNBQVMsWUFBYSxRQUFRLFVBQVU7QUFDckUsaUJBQVMsV0FBVztBQUNwQixZQUFJLENBQUMsU0FBVSxhQUFZLFFBQVEsR0FBRyxLQUFLLE1BQU07QUFDakQsY0FBTSxNQUFNLEtBQUssU0FBUyxDQUFDLElBQUssS0FBSyxNQUFNLEtBQUs7QUFDaEQsZUFBUSxNQUFNLFFBQVUsTUFBTSxhQUFhO0FBQUEsTUFDN0M7QUFFQSxNQUFBQSxRQUFPLFVBQVUsY0FBYyxTQUFTLFlBQWEsUUFBUSxVQUFVO0FBQ3JFLGlCQUFTLFdBQVc7QUFDcEIsWUFBSSxDQUFDLFNBQVUsYUFBWSxRQUFRLEdBQUcsS0FBSyxNQUFNO0FBRWpELGVBQVEsS0FBSyxNQUFNLElBQ2hCLEtBQUssU0FBUyxDQUFDLEtBQUssSUFDcEIsS0FBSyxTQUFTLENBQUMsS0FBSyxLQUNwQixLQUFLLFNBQVMsQ0FBQyxLQUFLO0FBQUEsTUFDekI7QUFFQSxNQUFBQSxRQUFPLFVBQVUsY0FBYyxTQUFTLFlBQWEsUUFBUSxVQUFVO0FBQ3JFLGlCQUFTLFdBQVc7QUFDcEIsWUFBSSxDQUFDLFNBQVUsYUFBWSxRQUFRLEdBQUcsS0FBSyxNQUFNO0FBRWpELGVBQVEsS0FBSyxNQUFNLEtBQUssS0FDckIsS0FBSyxTQUFTLENBQUMsS0FBSyxLQUNwQixLQUFLLFNBQVMsQ0FBQyxLQUFLLElBQ3BCLEtBQUssU0FBUyxDQUFDO0FBQUEsTUFDcEI7QUFFQSxNQUFBQSxRQUFPLFVBQVUsaUJBQWlCLG1CQUFtQixTQUFTLGVBQWdCLFFBQVE7QUFDcEYsaUJBQVMsV0FBVztBQUNwQix1QkFBZSxRQUFRLFFBQVE7QUFDL0IsY0FBTSxRQUFRLEtBQUssTUFBTTtBQUN6QixjQUFNLE9BQU8sS0FBSyxTQUFTLENBQUM7QUFDNUIsWUFBSSxVQUFVLFVBQWEsU0FBUyxRQUFXO0FBQzdDLHNCQUFZLFFBQVEsS0FBSyxTQUFTLENBQUM7QUFBQSxRQUNyQztBQUVBLGNBQU0sTUFBTSxLQUFLLFNBQVMsQ0FBQyxJQUN6QixLQUFLLFNBQVMsQ0FBQyxJQUFJLEtBQUssSUFDeEIsS0FBSyxTQUFTLENBQUMsSUFBSSxLQUFLLE1BQ3ZCLFFBQVE7QUFFWCxnQkFBUSxPQUFPLEdBQUcsS0FBSyxPQUFPLEVBQUUsS0FDOUIsT0FBTyxRQUNQLEtBQUssRUFBRSxNQUFNLElBQUksS0FBSyxJQUN0QixLQUFLLEVBQUUsTUFBTSxJQUFJLEtBQUssS0FDdEIsS0FBSyxFQUFFLE1BQU0sSUFBSSxLQUFLLEVBQUU7QUFBQSxNQUM1QixDQUFDO0FBRUQsTUFBQUEsUUFBTyxVQUFVLGlCQUFpQixtQkFBbUIsU0FBUyxlQUFnQixRQUFRO0FBQ3BGLGlCQUFTLFdBQVc7QUFDcEIsdUJBQWUsUUFBUSxRQUFRO0FBQy9CLGNBQU0sUUFBUSxLQUFLLE1BQU07QUFDekIsY0FBTSxPQUFPLEtBQUssU0FBUyxDQUFDO0FBQzVCLFlBQUksVUFBVSxVQUFhLFNBQVMsUUFBVztBQUM3QyxzQkFBWSxRQUFRLEtBQUssU0FBUyxDQUFDO0FBQUEsUUFDckM7QUFFQSxjQUFNLE9BQU8sU0FBUztBQUFBLFFBQ3BCLEtBQUssRUFBRSxNQUFNLElBQUksS0FBSyxLQUN0QixLQUFLLEVBQUUsTUFBTSxJQUFJLEtBQUssSUFDdEIsS0FBSyxFQUFFLE1BQU07QUFFZixnQkFBUSxPQUFPLEdBQUcsS0FBSyxPQUFPLEVBQUUsS0FDOUIsT0FBTyxLQUFLLEVBQUUsTUFBTSxJQUFJLEtBQUssS0FDN0IsS0FBSyxFQUFFLE1BQU0sSUFBSSxLQUFLLEtBQ3RCLEtBQUssRUFBRSxNQUFNLElBQUksS0FBSyxJQUN0QixJQUFJO0FBQUEsTUFDUixDQUFDO0FBRUQsTUFBQUEsUUFBTyxVQUFVLGNBQWMsU0FBUyxZQUFhLFFBQVEsVUFBVTtBQUNyRSxpQkFBUyxXQUFXO0FBQ3BCLFlBQUksQ0FBQyxTQUFVLGFBQVksUUFBUSxHQUFHLEtBQUssTUFBTTtBQUNqRCxlQUFPLFFBQVEsS0FBSyxNQUFNLFFBQVEsTUFBTSxJQUFJLENBQUM7QUFBQSxNQUMvQztBQUVBLE1BQUFBLFFBQU8sVUFBVSxjQUFjLFNBQVMsWUFBYSxRQUFRLFVBQVU7QUFDckUsaUJBQVMsV0FBVztBQUNwQixZQUFJLENBQUMsU0FBVSxhQUFZLFFBQVEsR0FBRyxLQUFLLE1BQU07QUFDakQsZUFBTyxRQUFRLEtBQUssTUFBTSxRQUFRLE9BQU8sSUFBSSxDQUFDO0FBQUEsTUFDaEQ7QUFFQSxNQUFBQSxRQUFPLFVBQVUsZUFBZSxTQUFTLGFBQWMsUUFBUSxVQUFVO0FBQ3ZFLGlCQUFTLFdBQVc7QUFDcEIsWUFBSSxDQUFDLFNBQVUsYUFBWSxRQUFRLEdBQUcsS0FBSyxNQUFNO0FBQ2pELGVBQU8sUUFBUSxLQUFLLE1BQU0sUUFBUSxNQUFNLElBQUksQ0FBQztBQUFBLE1BQy9DO0FBRUEsTUFBQUEsUUFBTyxVQUFVLGVBQWUsU0FBUyxhQUFjLFFBQVEsVUFBVTtBQUN2RSxpQkFBUyxXQUFXO0FBQ3BCLFlBQUksQ0FBQyxTQUFVLGFBQVksUUFBUSxHQUFHLEtBQUssTUFBTTtBQUNqRCxlQUFPLFFBQVEsS0FBSyxNQUFNLFFBQVEsT0FBTyxJQUFJLENBQUM7QUFBQSxNQUNoRDtBQUVBLGVBQVMsU0FBVSxLQUFLLE9BQU8sUUFBUSxLQUFLLEtBQUssS0FBSztBQUNwRCxZQUFJLENBQUNBLFFBQU8sU0FBUyxHQUFHLEVBQUcsT0FBTSxJQUFJLFVBQVUsNkNBQTZDO0FBQzVGLFlBQUksUUFBUSxPQUFPLFFBQVEsSUFBSyxPQUFNLElBQUksV0FBVyxtQ0FBbUM7QUFDeEYsWUFBSSxTQUFTLE1BQU0sSUFBSSxPQUFRLE9BQU0sSUFBSSxXQUFXLG9CQUFvQjtBQUFBLE1BQzFFO0FBRUEsTUFBQUEsUUFBTyxVQUFVLGNBQ2pCQSxRQUFPLFVBQVUsY0FBYyxTQUFTLFlBQWEsT0FBTyxRQUFRSyxhQUFZLFVBQVU7QUFDeEYsZ0JBQVEsQ0FBQztBQUNULGlCQUFTLFdBQVc7QUFDcEIsUUFBQUEsY0FBYUEsZ0JBQWU7QUFDNUIsWUFBSSxDQUFDLFVBQVU7QUFDYixnQkFBTSxXQUFXLEtBQUssSUFBSSxHQUFHLElBQUlBLFdBQVUsSUFBSTtBQUMvQyxtQkFBUyxNQUFNLE9BQU8sUUFBUUEsYUFBWSxVQUFVLENBQUM7QUFBQSxRQUN2RDtBQUVBLFlBQUksTUFBTTtBQUNWLFlBQUksSUFBSTtBQUNSLGFBQUssTUFBTSxJQUFJLFFBQVE7QUFDdkIsZUFBTyxFQUFFLElBQUlBLGdCQUFlLE9BQU8sTUFBUTtBQUN6QyxlQUFLLFNBQVMsQ0FBQyxJQUFLLFFBQVEsTUFBTztBQUFBLFFBQ3JDO0FBRUEsZUFBTyxTQUFTQTtBQUFBLE1BQ2xCO0FBRUEsTUFBQUwsUUFBTyxVQUFVLGNBQ2pCQSxRQUFPLFVBQVUsY0FBYyxTQUFTLFlBQWEsT0FBTyxRQUFRSyxhQUFZLFVBQVU7QUFDeEYsZ0JBQVEsQ0FBQztBQUNULGlCQUFTLFdBQVc7QUFDcEIsUUFBQUEsY0FBYUEsZ0JBQWU7QUFDNUIsWUFBSSxDQUFDLFVBQVU7QUFDYixnQkFBTSxXQUFXLEtBQUssSUFBSSxHQUFHLElBQUlBLFdBQVUsSUFBSTtBQUMvQyxtQkFBUyxNQUFNLE9BQU8sUUFBUUEsYUFBWSxVQUFVLENBQUM7QUFBQSxRQUN2RDtBQUVBLFlBQUksSUFBSUEsY0FBYTtBQUNyQixZQUFJLE1BQU07QUFDVixhQUFLLFNBQVMsQ0FBQyxJQUFJLFFBQVE7QUFDM0IsZUFBTyxFQUFFLEtBQUssTUFBTSxPQUFPLE1BQVE7QUFDakMsZUFBSyxTQUFTLENBQUMsSUFBSyxRQUFRLE1BQU87QUFBQSxRQUNyQztBQUVBLGVBQU8sU0FBU0E7QUFBQSxNQUNsQjtBQUVBLE1BQUFMLFFBQU8sVUFBVSxhQUNqQkEsUUFBTyxVQUFVLGFBQWEsU0FBUyxXQUFZLE9BQU8sUUFBUSxVQUFVO0FBQzFFLGdCQUFRLENBQUM7QUFDVCxpQkFBUyxXQUFXO0FBQ3BCLFlBQUksQ0FBQyxTQUFVLFVBQVMsTUFBTSxPQUFPLFFBQVEsR0FBRyxLQUFNLENBQUM7QUFDdkQsYUFBSyxNQUFNLElBQUssUUFBUTtBQUN4QixlQUFPLFNBQVM7QUFBQSxNQUNsQjtBQUVBLE1BQUFBLFFBQU8sVUFBVSxnQkFDakJBLFFBQU8sVUFBVSxnQkFBZ0IsU0FBUyxjQUFlLE9BQU8sUUFBUSxVQUFVO0FBQ2hGLGdCQUFRLENBQUM7QUFDVCxpQkFBUyxXQUFXO0FBQ3BCLFlBQUksQ0FBQyxTQUFVLFVBQVMsTUFBTSxPQUFPLFFBQVEsR0FBRyxPQUFRLENBQUM7QUFDekQsYUFBSyxNQUFNLElBQUssUUFBUTtBQUN4QixhQUFLLFNBQVMsQ0FBQyxJQUFLLFVBQVU7QUFDOUIsZUFBTyxTQUFTO0FBQUEsTUFDbEI7QUFFQSxNQUFBQSxRQUFPLFVBQVUsZ0JBQ2pCQSxRQUFPLFVBQVUsZ0JBQWdCLFNBQVMsY0FBZSxPQUFPLFFBQVEsVUFBVTtBQUNoRixnQkFBUSxDQUFDO0FBQ1QsaUJBQVMsV0FBVztBQUNwQixZQUFJLENBQUMsU0FBVSxVQUFTLE1BQU0sT0FBTyxRQUFRLEdBQUcsT0FBUSxDQUFDO0FBQ3pELGFBQUssTUFBTSxJQUFLLFVBQVU7QUFDMUIsYUFBSyxTQUFTLENBQUMsSUFBSyxRQUFRO0FBQzVCLGVBQU8sU0FBUztBQUFBLE1BQ2xCO0FBRUEsTUFBQUEsUUFBTyxVQUFVLGdCQUNqQkEsUUFBTyxVQUFVLGdCQUFnQixTQUFTLGNBQWUsT0FBTyxRQUFRLFVBQVU7QUFDaEYsZ0JBQVEsQ0FBQztBQUNULGlCQUFTLFdBQVc7QUFDcEIsWUFBSSxDQUFDLFNBQVUsVUFBUyxNQUFNLE9BQU8sUUFBUSxHQUFHLFlBQVksQ0FBQztBQUM3RCxhQUFLLFNBQVMsQ0FBQyxJQUFLLFVBQVU7QUFDOUIsYUFBSyxTQUFTLENBQUMsSUFBSyxVQUFVO0FBQzlCLGFBQUssU0FBUyxDQUFDLElBQUssVUFBVTtBQUM5QixhQUFLLE1BQU0sSUFBSyxRQUFRO0FBQ3hCLGVBQU8sU0FBUztBQUFBLE1BQ2xCO0FBRUEsTUFBQUEsUUFBTyxVQUFVLGdCQUNqQkEsUUFBTyxVQUFVLGdCQUFnQixTQUFTLGNBQWUsT0FBTyxRQUFRLFVBQVU7QUFDaEYsZ0JBQVEsQ0FBQztBQUNULGlCQUFTLFdBQVc7QUFDcEIsWUFBSSxDQUFDLFNBQVUsVUFBUyxNQUFNLE9BQU8sUUFBUSxHQUFHLFlBQVksQ0FBQztBQUM3RCxhQUFLLE1BQU0sSUFBSyxVQUFVO0FBQzFCLGFBQUssU0FBUyxDQUFDLElBQUssVUFBVTtBQUM5QixhQUFLLFNBQVMsQ0FBQyxJQUFLLFVBQVU7QUFDOUIsYUFBSyxTQUFTLENBQUMsSUFBSyxRQUFRO0FBQzVCLGVBQU8sU0FBUztBQUFBLE1BQ2xCO0FBRUEsZUFBUyxlQUFnQixLQUFLLE9BQU8sUUFBUSxLQUFLLEtBQUs7QUFDckQsbUJBQVcsT0FBTyxLQUFLLEtBQUssS0FBSyxRQUFRLENBQUM7QUFFMUMsWUFBSSxLQUFLLE9BQU8sUUFBUSxPQUFPLFVBQVUsQ0FBQztBQUMxQyxZQUFJLFFBQVEsSUFBSTtBQUNoQixhQUFLLE1BQU07QUFDWCxZQUFJLFFBQVEsSUFBSTtBQUNoQixhQUFLLE1BQU07QUFDWCxZQUFJLFFBQVEsSUFBSTtBQUNoQixhQUFLLE1BQU07QUFDWCxZQUFJLFFBQVEsSUFBSTtBQUNoQixZQUFJLEtBQUssT0FBTyxTQUFTLE9BQU8sRUFBRSxJQUFJLE9BQU8sVUFBVSxDQUFDO0FBQ3hELFlBQUksUUFBUSxJQUFJO0FBQ2hCLGFBQUssTUFBTTtBQUNYLFlBQUksUUFBUSxJQUFJO0FBQ2hCLGFBQUssTUFBTTtBQUNYLFlBQUksUUFBUSxJQUFJO0FBQ2hCLGFBQUssTUFBTTtBQUNYLFlBQUksUUFBUSxJQUFJO0FBQ2hCLGVBQU87QUFBQSxNQUNUO0FBRUEsZUFBUyxlQUFnQixLQUFLLE9BQU8sUUFBUSxLQUFLLEtBQUs7QUFDckQsbUJBQVcsT0FBTyxLQUFLLEtBQUssS0FBSyxRQUFRLENBQUM7QUFFMUMsWUFBSSxLQUFLLE9BQU8sUUFBUSxPQUFPLFVBQVUsQ0FBQztBQUMxQyxZQUFJLFNBQVMsQ0FBQyxJQUFJO0FBQ2xCLGFBQUssTUFBTTtBQUNYLFlBQUksU0FBUyxDQUFDLElBQUk7QUFDbEIsYUFBSyxNQUFNO0FBQ1gsWUFBSSxTQUFTLENBQUMsSUFBSTtBQUNsQixhQUFLLE1BQU07QUFDWCxZQUFJLFNBQVMsQ0FBQyxJQUFJO0FBQ2xCLFlBQUksS0FBSyxPQUFPLFNBQVMsT0FBTyxFQUFFLElBQUksT0FBTyxVQUFVLENBQUM7QUFDeEQsWUFBSSxTQUFTLENBQUMsSUFBSTtBQUNsQixhQUFLLE1BQU07QUFDWCxZQUFJLFNBQVMsQ0FBQyxJQUFJO0FBQ2xCLGFBQUssTUFBTTtBQUNYLFlBQUksU0FBUyxDQUFDLElBQUk7QUFDbEIsYUFBSyxNQUFNO0FBQ1gsWUFBSSxNQUFNLElBQUk7QUFDZCxlQUFPLFNBQVM7QUFBQSxNQUNsQjtBQUVBLE1BQUFBLFFBQU8sVUFBVSxtQkFBbUIsbUJBQW1CLFNBQVMsaUJBQWtCLE9BQU8sU0FBUyxHQUFHO0FBQ25HLGVBQU8sZUFBZSxNQUFNLE9BQU8sUUFBUSxPQUFPLENBQUMsR0FBRyxPQUFPLG9CQUFvQixDQUFDO0FBQUEsTUFDcEYsQ0FBQztBQUVELE1BQUFBLFFBQU8sVUFBVSxtQkFBbUIsbUJBQW1CLFNBQVMsaUJBQWtCLE9BQU8sU0FBUyxHQUFHO0FBQ25HLGVBQU8sZUFBZSxNQUFNLE9BQU8sUUFBUSxPQUFPLENBQUMsR0FBRyxPQUFPLG9CQUFvQixDQUFDO0FBQUEsTUFDcEYsQ0FBQztBQUVELE1BQUFBLFFBQU8sVUFBVSxhQUFhLFNBQVMsV0FBWSxPQUFPLFFBQVFLLGFBQVksVUFBVTtBQUN0RixnQkFBUSxDQUFDO0FBQ1QsaUJBQVMsV0FBVztBQUNwQixZQUFJLENBQUMsVUFBVTtBQUNiLGdCQUFNLFFBQVEsS0FBSyxJQUFJLEdBQUksSUFBSUEsY0FBYyxDQUFDO0FBRTlDLG1CQUFTLE1BQU0sT0FBTyxRQUFRQSxhQUFZLFFBQVEsR0FBRyxDQUFDLEtBQUs7QUFBQSxRQUM3RDtBQUVBLFlBQUksSUFBSTtBQUNSLFlBQUksTUFBTTtBQUNWLFlBQUksTUFBTTtBQUNWLGFBQUssTUFBTSxJQUFJLFFBQVE7QUFDdkIsZUFBTyxFQUFFLElBQUlBLGdCQUFlLE9BQU8sTUFBUTtBQUN6QyxjQUFJLFFBQVEsS0FBSyxRQUFRLEtBQUssS0FBSyxTQUFTLElBQUksQ0FBQyxNQUFNLEdBQUc7QUFDeEQsa0JBQU07QUFBQSxVQUNSO0FBQ0EsZUFBSyxTQUFTLENBQUMsS0FBTSxRQUFRLE9BQVEsS0FBSyxNQUFNO0FBQUEsUUFDbEQ7QUFFQSxlQUFPLFNBQVNBO0FBQUEsTUFDbEI7QUFFQSxNQUFBTCxRQUFPLFVBQVUsYUFBYSxTQUFTLFdBQVksT0FBTyxRQUFRSyxhQUFZLFVBQVU7QUFDdEYsZ0JBQVEsQ0FBQztBQUNULGlCQUFTLFdBQVc7QUFDcEIsWUFBSSxDQUFDLFVBQVU7QUFDYixnQkFBTSxRQUFRLEtBQUssSUFBSSxHQUFJLElBQUlBLGNBQWMsQ0FBQztBQUU5QyxtQkFBUyxNQUFNLE9BQU8sUUFBUUEsYUFBWSxRQUFRLEdBQUcsQ0FBQyxLQUFLO0FBQUEsUUFDN0Q7QUFFQSxZQUFJLElBQUlBLGNBQWE7QUFDckIsWUFBSSxNQUFNO0FBQ1YsWUFBSSxNQUFNO0FBQ1YsYUFBSyxTQUFTLENBQUMsSUFBSSxRQUFRO0FBQzNCLGVBQU8sRUFBRSxLQUFLLE1BQU0sT0FBTyxNQUFRO0FBQ2pDLGNBQUksUUFBUSxLQUFLLFFBQVEsS0FBSyxLQUFLLFNBQVMsSUFBSSxDQUFDLE1BQU0sR0FBRztBQUN4RCxrQkFBTTtBQUFBLFVBQ1I7QUFDQSxlQUFLLFNBQVMsQ0FBQyxLQUFNLFFBQVEsT0FBUSxLQUFLLE1BQU07QUFBQSxRQUNsRDtBQUVBLGVBQU8sU0FBU0E7QUFBQSxNQUNsQjtBQUVBLE1BQUFMLFFBQU8sVUFBVSxZQUFZLFNBQVMsVUFBVyxPQUFPLFFBQVEsVUFBVTtBQUN4RSxnQkFBUSxDQUFDO0FBQ1QsaUJBQVMsV0FBVztBQUNwQixZQUFJLENBQUMsU0FBVSxVQUFTLE1BQU0sT0FBTyxRQUFRLEdBQUcsS0FBTSxJQUFLO0FBQzNELFlBQUksUUFBUSxFQUFHLFNBQVEsTUFBTyxRQUFRO0FBQ3RDLGFBQUssTUFBTSxJQUFLLFFBQVE7QUFDeEIsZUFBTyxTQUFTO0FBQUEsTUFDbEI7QUFFQSxNQUFBQSxRQUFPLFVBQVUsZUFBZSxTQUFTLGFBQWMsT0FBTyxRQUFRLFVBQVU7QUFDOUUsZ0JBQVEsQ0FBQztBQUNULGlCQUFTLFdBQVc7QUFDcEIsWUFBSSxDQUFDLFNBQVUsVUFBUyxNQUFNLE9BQU8sUUFBUSxHQUFHLE9BQVEsTUFBTztBQUMvRCxhQUFLLE1BQU0sSUFBSyxRQUFRO0FBQ3hCLGFBQUssU0FBUyxDQUFDLElBQUssVUFBVTtBQUM5QixlQUFPLFNBQVM7QUFBQSxNQUNsQjtBQUVBLE1BQUFBLFFBQU8sVUFBVSxlQUFlLFNBQVMsYUFBYyxPQUFPLFFBQVEsVUFBVTtBQUM5RSxnQkFBUSxDQUFDO0FBQ1QsaUJBQVMsV0FBVztBQUNwQixZQUFJLENBQUMsU0FBVSxVQUFTLE1BQU0sT0FBTyxRQUFRLEdBQUcsT0FBUSxNQUFPO0FBQy9ELGFBQUssTUFBTSxJQUFLLFVBQVU7QUFDMUIsYUFBSyxTQUFTLENBQUMsSUFBSyxRQUFRO0FBQzVCLGVBQU8sU0FBUztBQUFBLE1BQ2xCO0FBRUEsTUFBQUEsUUFBTyxVQUFVLGVBQWUsU0FBUyxhQUFjLE9BQU8sUUFBUSxVQUFVO0FBQzlFLGdCQUFRLENBQUM7QUFDVCxpQkFBUyxXQUFXO0FBQ3BCLFlBQUksQ0FBQyxTQUFVLFVBQVMsTUFBTSxPQUFPLFFBQVEsR0FBRyxZQUFZLFdBQVc7QUFDdkUsYUFBSyxNQUFNLElBQUssUUFBUTtBQUN4QixhQUFLLFNBQVMsQ0FBQyxJQUFLLFVBQVU7QUFDOUIsYUFBSyxTQUFTLENBQUMsSUFBSyxVQUFVO0FBQzlCLGFBQUssU0FBUyxDQUFDLElBQUssVUFBVTtBQUM5QixlQUFPLFNBQVM7QUFBQSxNQUNsQjtBQUVBLE1BQUFBLFFBQU8sVUFBVSxlQUFlLFNBQVMsYUFBYyxPQUFPLFFBQVEsVUFBVTtBQUM5RSxnQkFBUSxDQUFDO0FBQ1QsaUJBQVMsV0FBVztBQUNwQixZQUFJLENBQUMsU0FBVSxVQUFTLE1BQU0sT0FBTyxRQUFRLEdBQUcsWUFBWSxXQUFXO0FBQ3ZFLFlBQUksUUFBUSxFQUFHLFNBQVEsYUFBYSxRQUFRO0FBQzVDLGFBQUssTUFBTSxJQUFLLFVBQVU7QUFDMUIsYUFBSyxTQUFTLENBQUMsSUFBSyxVQUFVO0FBQzlCLGFBQUssU0FBUyxDQUFDLElBQUssVUFBVTtBQUM5QixhQUFLLFNBQVMsQ0FBQyxJQUFLLFFBQVE7QUFDNUIsZUFBTyxTQUFTO0FBQUEsTUFDbEI7QUFFQSxNQUFBQSxRQUFPLFVBQVUsa0JBQWtCLG1CQUFtQixTQUFTLGdCQUFpQixPQUFPLFNBQVMsR0FBRztBQUNqRyxlQUFPLGVBQWUsTUFBTSxPQUFPLFFBQVEsQ0FBQyxPQUFPLG9CQUFvQixHQUFHLE9BQU8sb0JBQW9CLENBQUM7QUFBQSxNQUN4RyxDQUFDO0FBRUQsTUFBQUEsUUFBTyxVQUFVLGtCQUFrQixtQkFBbUIsU0FBUyxnQkFBaUIsT0FBTyxTQUFTLEdBQUc7QUFDakcsZUFBTyxlQUFlLE1BQU0sT0FBTyxRQUFRLENBQUMsT0FBTyxvQkFBb0IsR0FBRyxPQUFPLG9CQUFvQixDQUFDO0FBQUEsTUFDeEcsQ0FBQztBQUVELGVBQVMsYUFBYyxLQUFLLE9BQU8sUUFBUSxLQUFLLEtBQUssS0FBSztBQUN4RCxZQUFJLFNBQVMsTUFBTSxJQUFJLE9BQVEsT0FBTSxJQUFJLFdBQVcsb0JBQW9CO0FBQ3hFLFlBQUksU0FBUyxFQUFHLE9BQU0sSUFBSSxXQUFXLG9CQUFvQjtBQUFBLE1BQzNEO0FBRUEsZUFBUyxXQUFZLEtBQUssT0FBTyxRQUFRLGNBQWMsVUFBVTtBQUMvRCxnQkFBUSxDQUFDO0FBQ1QsaUJBQVMsV0FBVztBQUNwQixZQUFJLENBQUMsVUFBVTtBQUNiLHVCQUFhLEtBQUssT0FBTyxRQUFRLEdBQUcsc0JBQXdCLHFCQUF1QjtBQUFBLFFBQ3JGO0FBQ0EsZ0JBQVEsTUFBTSxLQUFLLE9BQU8sUUFBUSxjQUFjLElBQUksQ0FBQztBQUNyRCxlQUFPLFNBQVM7QUFBQSxNQUNsQjtBQUVBLE1BQUFBLFFBQU8sVUFBVSxlQUFlLFNBQVMsYUFBYyxPQUFPLFFBQVEsVUFBVTtBQUM5RSxlQUFPLFdBQVcsTUFBTSxPQUFPLFFBQVEsTUFBTSxRQUFRO0FBQUEsTUFDdkQ7QUFFQSxNQUFBQSxRQUFPLFVBQVUsZUFBZSxTQUFTLGFBQWMsT0FBTyxRQUFRLFVBQVU7QUFDOUUsZUFBTyxXQUFXLE1BQU0sT0FBTyxRQUFRLE9BQU8sUUFBUTtBQUFBLE1BQ3hEO0FBRUEsZUFBUyxZQUFhLEtBQUssT0FBTyxRQUFRLGNBQWMsVUFBVTtBQUNoRSxnQkFBUSxDQUFDO0FBQ1QsaUJBQVMsV0FBVztBQUNwQixZQUFJLENBQUMsVUFBVTtBQUNiLHVCQUFhLEtBQUssT0FBTyxRQUFRLEdBQUcsdUJBQXlCLHNCQUF3QjtBQUFBLFFBQ3ZGO0FBQ0EsZ0JBQVEsTUFBTSxLQUFLLE9BQU8sUUFBUSxjQUFjLElBQUksQ0FBQztBQUNyRCxlQUFPLFNBQVM7QUFBQSxNQUNsQjtBQUVBLE1BQUFBLFFBQU8sVUFBVSxnQkFBZ0IsU0FBUyxjQUFlLE9BQU8sUUFBUSxVQUFVO0FBQ2hGLGVBQU8sWUFBWSxNQUFNLE9BQU8sUUFBUSxNQUFNLFFBQVE7QUFBQSxNQUN4RDtBQUVBLE1BQUFBLFFBQU8sVUFBVSxnQkFBZ0IsU0FBUyxjQUFlLE9BQU8sUUFBUSxVQUFVO0FBQ2hGLGVBQU8sWUFBWSxNQUFNLE9BQU8sUUFBUSxPQUFPLFFBQVE7QUFBQSxNQUN6RDtBQUdBLE1BQUFBLFFBQU8sVUFBVSxPQUFPLFNBQVMsS0FBTSxRQUFRLGFBQWEsT0FBTyxLQUFLO0FBQ3RFLFlBQUksQ0FBQ0EsUUFBTyxTQUFTLE1BQU0sRUFBRyxPQUFNLElBQUksVUFBVSw2QkFBNkI7QUFDL0UsWUFBSSxDQUFDLE1BQU8sU0FBUTtBQUNwQixZQUFJLENBQUMsT0FBTyxRQUFRLEVBQUcsT0FBTSxLQUFLO0FBQ2xDLFlBQUksZUFBZSxPQUFPLE9BQVEsZUFBYyxPQUFPO0FBQ3ZELFlBQUksQ0FBQyxZQUFhLGVBQWM7QUFDaEMsWUFBSSxNQUFNLEtBQUssTUFBTSxNQUFPLE9BQU07QUFHbEMsWUFBSSxRQUFRLE1BQU8sUUFBTztBQUMxQixZQUFJLE9BQU8sV0FBVyxLQUFLLEtBQUssV0FBVyxFQUFHLFFBQU87QUFHckQsWUFBSSxjQUFjLEdBQUc7QUFDbkIsZ0JBQU0sSUFBSSxXQUFXLDJCQUEyQjtBQUFBLFFBQ2xEO0FBQ0EsWUFBSSxRQUFRLEtBQUssU0FBUyxLQUFLLE9BQVEsT0FBTSxJQUFJLFdBQVcsb0JBQW9CO0FBQ2hGLFlBQUksTUFBTSxFQUFHLE9BQU0sSUFBSSxXQUFXLHlCQUF5QjtBQUczRCxZQUFJLE1BQU0sS0FBSyxPQUFRLE9BQU0sS0FBSztBQUNsQyxZQUFJLE9BQU8sU0FBUyxjQUFjLE1BQU0sT0FBTztBQUM3QyxnQkFBTSxPQUFPLFNBQVMsY0FBYztBQUFBLFFBQ3RDO0FBRUEsY0FBTSxNQUFNLE1BQU07QUFFbEIsWUFBSSxTQUFTLFVBQVUsT0FBTyxXQUFXLFVBQVUsZUFBZSxZQUFZO0FBRTVFLGVBQUssV0FBVyxhQUFhLE9BQU8sR0FBRztBQUFBLFFBQ3pDLE9BQU87QUFDTCxxQkFBVyxVQUFVLElBQUk7QUFBQSxZQUN2QjtBQUFBLFlBQ0EsS0FBSyxTQUFTLE9BQU8sR0FBRztBQUFBLFlBQ3hCO0FBQUEsVUFDRjtBQUFBLFFBQ0Y7QUFFQSxlQUFPO0FBQUEsTUFDVDtBQU1BLE1BQUFBLFFBQU8sVUFBVSxPQUFPLFNBQVMsS0FBTSxLQUFLLE9BQU8sS0FBSyxVQUFVO0FBRWhFLFlBQUksT0FBTyxRQUFRLFVBQVU7QUFDM0IsY0FBSSxPQUFPLFVBQVUsVUFBVTtBQUM3Qix1QkFBVztBQUNYLG9CQUFRO0FBQ1Isa0JBQU0sS0FBSztBQUFBLFVBQ2IsV0FBVyxPQUFPLFFBQVEsVUFBVTtBQUNsQyx1QkFBVztBQUNYLGtCQUFNLEtBQUs7QUFBQSxVQUNiO0FBQ0EsY0FBSSxhQUFhLFVBQWEsT0FBTyxhQUFhLFVBQVU7QUFDMUQsa0JBQU0sSUFBSSxVQUFVLDJCQUEyQjtBQUFBLFVBQ2pEO0FBQ0EsY0FBSSxPQUFPLGFBQWEsWUFBWSxDQUFDQSxRQUFPLFdBQVcsUUFBUSxHQUFHO0FBQ2hFLGtCQUFNLElBQUksVUFBVSx1QkFBdUIsUUFBUTtBQUFBLFVBQ3JEO0FBQ0EsY0FBSSxJQUFJLFdBQVcsR0FBRztBQUNwQixrQkFBTSxPQUFPLElBQUksV0FBVyxDQUFDO0FBQzdCLGdCQUFLLGFBQWEsVUFBVSxPQUFPLE9BQy9CLGFBQWEsVUFBVTtBQUV6QixvQkFBTTtBQUFBLFlBQ1I7QUFBQSxVQUNGO0FBQUEsUUFDRixXQUFXLE9BQU8sUUFBUSxVQUFVO0FBQ2xDLGdCQUFNLE1BQU07QUFBQSxRQUNkLFdBQVcsT0FBTyxRQUFRLFdBQVc7QUFDbkMsZ0JBQU0sT0FBTyxHQUFHO0FBQUEsUUFDbEI7QUFHQSxZQUFJLFFBQVEsS0FBSyxLQUFLLFNBQVMsU0FBUyxLQUFLLFNBQVMsS0FBSztBQUN6RCxnQkFBTSxJQUFJLFdBQVcsb0JBQW9CO0FBQUEsUUFDM0M7QUFFQSxZQUFJLE9BQU8sT0FBTztBQUNoQixpQkFBTztBQUFBLFFBQ1Q7QUFFQSxnQkFBUSxVQUFVO0FBQ2xCLGNBQU0sUUFBUSxTQUFZLEtBQUssU0FBUyxRQUFRO0FBRWhELFlBQUksQ0FBQyxJQUFLLE9BQU07QUFFaEIsWUFBSTtBQUNKLFlBQUksT0FBTyxRQUFRLFVBQVU7QUFDM0IsZUFBSyxJQUFJLE9BQU8sSUFBSSxLQUFLLEVBQUUsR0FBRztBQUM1QixpQkFBSyxDQUFDLElBQUk7QUFBQSxVQUNaO0FBQUEsUUFDRixPQUFPO0FBQ0wsZ0JBQU0sUUFBUUEsUUFBTyxTQUFTLEdBQUcsSUFDN0IsTUFDQUEsUUFBTyxLQUFLLEtBQUssUUFBUTtBQUM3QixnQkFBTSxNQUFNLE1BQU07QUFDbEIsY0FBSSxRQUFRLEdBQUc7QUFDYixrQkFBTSxJQUFJLFVBQVUsZ0JBQWdCLE1BQ2xDLG1DQUFtQztBQUFBLFVBQ3ZDO0FBQ0EsZUFBSyxJQUFJLEdBQUcsSUFBSSxNQUFNLE9BQU8sRUFBRSxHQUFHO0FBQ2hDLGlCQUFLLElBQUksS0FBSyxJQUFJLE1BQU0sSUFBSSxHQUFHO0FBQUEsVUFDakM7QUFBQSxRQUNGO0FBRUEsZUFBTztBQUFBLE1BQ1Q7QUFNQSxVQUFNLFNBQVMsQ0FBQztBQUNoQixlQUFTLEVBQUcsS0FBSyxZQUFZLE1BQU07QUFDakMsZUFBTyxHQUFHLElBQUksTUFBTSxrQkFBa0IsS0FBSztBQUFBLFVBQ3pDLGNBQWU7QUFDYixrQkFBTTtBQUVOLG1CQUFPLGVBQWUsTUFBTSxXQUFXO0FBQUEsY0FDckMsT0FBTyxXQUFXLE1BQU0sTUFBTSxTQUFTO0FBQUEsY0FDdkMsVUFBVTtBQUFBLGNBQ1YsY0FBYztBQUFBLFlBQ2hCLENBQUM7QUFHRCxpQkFBSyxPQUFPLEdBQUcsS0FBSyxJQUFJLEtBQUssR0FBRztBQUdoQyxpQkFBSztBQUVMLG1CQUFPLEtBQUs7QUFBQSxVQUNkO0FBQUEsVUFFQSxJQUFJLE9BQVE7QUFDVixtQkFBTztBQUFBLFVBQ1Q7QUFBQSxVQUVBLElBQUksS0FBTSxPQUFPO0FBQ2YsbUJBQU8sZUFBZSxNQUFNLFFBQVE7QUFBQSxjQUNsQyxjQUFjO0FBQUEsY0FDZCxZQUFZO0FBQUEsY0FDWjtBQUFBLGNBQ0EsVUFBVTtBQUFBLFlBQ1osQ0FBQztBQUFBLFVBQ0g7QUFBQSxVQUVBLFdBQVk7QUFDVixtQkFBTyxHQUFHLEtBQUssSUFBSSxLQUFLLEdBQUcsTUFBTSxLQUFLLE9BQU87QUFBQSxVQUMvQztBQUFBLFFBQ0Y7QUFBQSxNQUNGO0FBRUE7QUFBQSxRQUFFO0FBQUEsUUFDQSxTQUFVLE1BQU07QUFDZCxjQUFJLE1BQU07QUFDUixtQkFBTyxHQUFHLElBQUk7QUFBQSxVQUNoQjtBQUVBLGlCQUFPO0FBQUEsUUFDVDtBQUFBLFFBQUc7QUFBQSxNQUFVO0FBQ2Y7QUFBQSxRQUFFO0FBQUEsUUFDQSxTQUFVLE1BQU0sUUFBUTtBQUN0QixpQkFBTyxRQUFRLElBQUksb0RBQW9ELE9BQU8sTUFBTTtBQUFBLFFBQ3RGO0FBQUEsUUFBRztBQUFBLE1BQVM7QUFDZDtBQUFBLFFBQUU7QUFBQSxRQUNBLFNBQVUsS0FBSyxPQUFPLE9BQU87QUFDM0IsY0FBSSxNQUFNLGlCQUFpQixHQUFHO0FBQzlCLGNBQUksV0FBVztBQUNmLGNBQUksT0FBTyxVQUFVLEtBQUssS0FBSyxLQUFLLElBQUksS0FBSyxJQUFJLEtBQUssSUFBSTtBQUN4RCx1QkFBVyxzQkFBc0IsT0FBTyxLQUFLLENBQUM7QUFBQSxVQUNoRCxXQUFXLE9BQU8sVUFBVSxVQUFVO0FBQ3BDLHVCQUFXLE9BQU8sS0FBSztBQUN2QixnQkFBSSxRQUFRLE9BQU8sQ0FBQyxLQUFLLE9BQU8sRUFBRSxLQUFLLFFBQVEsRUFBRSxPQUFPLENBQUMsS0FBSyxPQUFPLEVBQUUsSUFBSTtBQUN6RSx5QkFBVyxzQkFBc0IsUUFBUTtBQUFBLFlBQzNDO0FBQ0Esd0JBQVk7QUFBQSxVQUNkO0FBQ0EsaUJBQU8sZUFBZSxLQUFLLGNBQWMsUUFBUTtBQUNqRCxpQkFBTztBQUFBLFFBQ1Q7QUFBQSxRQUFHO0FBQUEsTUFBVTtBQUVmLGVBQVMsc0JBQXVCLEtBQUs7QUFDbkMsWUFBSSxNQUFNO0FBQ1YsWUFBSSxJQUFJLElBQUk7QUFDWixjQUFNLFFBQVEsSUFBSSxDQUFDLE1BQU0sTUFBTSxJQUFJO0FBQ25DLGVBQU8sS0FBSyxRQUFRLEdBQUcsS0FBSyxHQUFHO0FBQzdCLGdCQUFNLElBQUksSUFBSSxNQUFNLElBQUksR0FBRyxDQUFDLENBQUMsR0FBRyxHQUFHO0FBQUEsUUFDckM7QUFDQSxlQUFPLEdBQUcsSUFBSSxNQUFNLEdBQUcsQ0FBQyxDQUFDLEdBQUcsR0FBRztBQUFBLE1BQ2pDO0FBS0EsZUFBUyxZQUFhLEtBQUssUUFBUUssYUFBWTtBQUM3Qyx1QkFBZSxRQUFRLFFBQVE7QUFDL0IsWUFBSSxJQUFJLE1BQU0sTUFBTSxVQUFhLElBQUksU0FBU0EsV0FBVSxNQUFNLFFBQVc7QUFDdkUsc0JBQVksUUFBUSxJQUFJLFVBQVVBLGNBQWEsRUFBRTtBQUFBLFFBQ25EO0FBQUEsTUFDRjtBQUVBLGVBQVMsV0FBWSxPQUFPLEtBQUssS0FBSyxLQUFLLFFBQVFBLGFBQVk7QUFDN0QsWUFBSSxRQUFRLE9BQU8sUUFBUSxLQUFLO0FBQzlCLGdCQUFNLElBQUksT0FBTyxRQUFRLFdBQVcsTUFBTTtBQUMxQyxjQUFJO0FBQ0osY0FBSUEsY0FBYSxHQUFHO0FBQ2xCLGdCQUFJLFFBQVEsS0FBSyxRQUFRLE9BQU8sQ0FBQyxHQUFHO0FBQ2xDLHNCQUFRLE9BQU8sQ0FBQyxXQUFXLENBQUMsUUFBUUEsY0FBYSxLQUFLLENBQUMsR0FBRyxDQUFDO0FBQUEsWUFDN0QsT0FBTztBQUNMLHNCQUFRLFNBQVMsQ0FBQyxRQUFRQSxjQUFhLEtBQUssSUFBSSxDQUFDLEdBQUcsQ0FBQyxpQkFDekNBLGNBQWEsS0FBSyxJQUFJLENBQUMsR0FBRyxDQUFDO0FBQUEsWUFDekM7QUFBQSxVQUNGLE9BQU87QUFDTCxvQkFBUSxNQUFNLEdBQUcsR0FBRyxDQUFDLFdBQVcsR0FBRyxHQUFHLENBQUM7QUFBQSxVQUN6QztBQUNBLGdCQUFNLElBQUksT0FBTyxpQkFBaUIsU0FBUyxPQUFPLEtBQUs7QUFBQSxRQUN6RDtBQUNBLG9CQUFZLEtBQUssUUFBUUEsV0FBVTtBQUFBLE1BQ3JDO0FBRUEsZUFBUyxlQUFnQixPQUFPLE1BQU07QUFDcEMsWUFBSSxPQUFPLFVBQVUsVUFBVTtBQUM3QixnQkFBTSxJQUFJLE9BQU8scUJBQXFCLE1BQU0sVUFBVSxLQUFLO0FBQUEsUUFDN0Q7QUFBQSxNQUNGO0FBRUEsZUFBUyxZQUFhLE9BQU8sUUFBUSxNQUFNO0FBQ3pDLFlBQUksS0FBSyxNQUFNLEtBQUssTUFBTSxPQUFPO0FBQy9CLHlCQUFlLE9BQU8sSUFBSTtBQUMxQixnQkFBTSxJQUFJLE9BQU8saUJBQWlCLFFBQVEsVUFBVSxjQUFjLEtBQUs7QUFBQSxRQUN6RTtBQUVBLFlBQUksU0FBUyxHQUFHO0FBQ2QsZ0JBQU0sSUFBSSxPQUFPLHlCQUF5QjtBQUFBLFFBQzVDO0FBRUEsY0FBTSxJQUFJLE9BQU87QUFBQSxVQUFpQixRQUFRO0FBQUEsVUFDUixNQUFNLE9BQU8sSUFBSSxDQUFDLFdBQVcsTUFBTTtBQUFBLFVBQ25DO0FBQUEsUUFBSztBQUFBLE1BQ3pDO0FBS0EsVUFBTSxvQkFBb0I7QUFFMUIsZUFBUyxZQUFhLEtBQUs7QUFFekIsY0FBTSxJQUFJLE1BQU0sR0FBRyxFQUFFLENBQUM7QUFFdEIsY0FBTSxJQUFJLEtBQUssRUFBRSxRQUFRLG1CQUFtQixFQUFFO0FBRTlDLFlBQUksSUFBSSxTQUFTLEVBQUcsUUFBTztBQUUzQixlQUFPLElBQUksU0FBUyxNQUFNLEdBQUc7QUFDM0IsZ0JBQU0sTUFBTTtBQUFBLFFBQ2Q7QUFDQSxlQUFPO0FBQUEsTUFDVDtBQUVBLGVBQVNKLGFBQWEsUUFBUSxPQUFPO0FBQ25DLGdCQUFRLFNBQVM7QUFDakIsWUFBSTtBQUNKLGNBQU0sU0FBUyxPQUFPO0FBQ3RCLFlBQUksZ0JBQWdCO0FBQ3BCLGNBQU0sUUFBUSxDQUFDO0FBRWYsaUJBQVMsSUFBSSxHQUFHLElBQUksUUFBUSxFQUFFLEdBQUc7QUFDL0Isc0JBQVksT0FBTyxXQUFXLENBQUM7QUFHL0IsY0FBSSxZQUFZLFNBQVUsWUFBWSxPQUFRO0FBRTVDLGdCQUFJLENBQUMsZUFBZTtBQUVsQixrQkFBSSxZQUFZLE9BQVE7QUFFdEIscUJBQUssU0FBUyxLQUFLLEdBQUksT0FBTSxLQUFLLEtBQU0sS0FBTSxHQUFJO0FBQ2xEO0FBQUEsY0FDRixXQUFXLElBQUksTUFBTSxRQUFRO0FBRTNCLHFCQUFLLFNBQVMsS0FBSyxHQUFJLE9BQU0sS0FBSyxLQUFNLEtBQU0sR0FBSTtBQUNsRDtBQUFBLGNBQ0Y7QUFHQSw4QkFBZ0I7QUFFaEI7QUFBQSxZQUNGO0FBR0EsZ0JBQUksWUFBWSxPQUFRO0FBQ3RCLG1CQUFLLFNBQVMsS0FBSyxHQUFJLE9BQU0sS0FBSyxLQUFNLEtBQU0sR0FBSTtBQUNsRCw4QkFBZ0I7QUFDaEI7QUFBQSxZQUNGO0FBR0EseUJBQWEsZ0JBQWdCLFNBQVUsS0FBSyxZQUFZLFNBQVU7QUFBQSxVQUNwRSxXQUFXLGVBQWU7QUFFeEIsaUJBQUssU0FBUyxLQUFLLEdBQUksT0FBTSxLQUFLLEtBQU0sS0FBTSxHQUFJO0FBQUEsVUFDcEQ7QUFFQSwwQkFBZ0I7QUFHaEIsY0FBSSxZQUFZLEtBQU07QUFDcEIsaUJBQUssU0FBUyxLQUFLLEVBQUc7QUFDdEIsa0JBQU0sS0FBSyxTQUFTO0FBQUEsVUFDdEIsV0FBVyxZQUFZLE1BQU87QUFDNUIsaUJBQUssU0FBUyxLQUFLLEVBQUc7QUFDdEIsa0JBQU07QUFBQSxjQUNKLGFBQWEsSUFBTTtBQUFBLGNBQ25CLFlBQVksS0FBTztBQUFBLFlBQ3JCO0FBQUEsVUFDRixXQUFXLFlBQVksT0FBUztBQUM5QixpQkFBSyxTQUFTLEtBQUssRUFBRztBQUN0QixrQkFBTTtBQUFBLGNBQ0osYUFBYSxLQUFNO0FBQUEsY0FDbkIsYUFBYSxJQUFNLEtBQU87QUFBQSxjQUMxQixZQUFZLEtBQU87QUFBQSxZQUNyQjtBQUFBLFVBQ0YsV0FBVyxZQUFZLFNBQVU7QUFDL0IsaUJBQUssU0FBUyxLQUFLLEVBQUc7QUFDdEIsa0JBQU07QUFBQSxjQUNKLGFBQWEsS0FBTztBQUFBLGNBQ3BCLGFBQWEsS0FBTSxLQUFPO0FBQUEsY0FDMUIsYUFBYSxJQUFNLEtBQU87QUFBQSxjQUMxQixZQUFZLEtBQU87QUFBQSxZQUNyQjtBQUFBLFVBQ0YsT0FBTztBQUNMLGtCQUFNLElBQUksTUFBTSxvQkFBb0I7QUFBQSxVQUN0QztBQUFBLFFBQ0Y7QUFFQSxlQUFPO0FBQUEsTUFDVDtBQUVBLGVBQVNHLGNBQWMsS0FBSztBQUMxQixjQUFNLFlBQVksQ0FBQztBQUNuQixpQkFBUyxJQUFJLEdBQUcsSUFBSSxJQUFJLFFBQVEsRUFBRSxHQUFHO0FBRW5DLG9CQUFVLEtBQUssSUFBSSxXQUFXLENBQUMsSUFBSSxHQUFJO0FBQUEsUUFDekM7QUFDQSxlQUFPO0FBQUEsTUFDVDtBQUVBLGVBQVMsZUFBZ0IsS0FBSyxPQUFPO0FBQ25DLFlBQUksR0FBRyxJQUFJO0FBQ1gsY0FBTSxZQUFZLENBQUM7QUFDbkIsaUJBQVMsSUFBSSxHQUFHLElBQUksSUFBSSxRQUFRLEVBQUUsR0FBRztBQUNuQyxlQUFLLFNBQVMsS0FBSyxFQUFHO0FBRXRCLGNBQUksSUFBSSxXQUFXLENBQUM7QUFDcEIsZUFBSyxLQUFLO0FBQ1YsZUFBSyxJQUFJO0FBQ1Qsb0JBQVUsS0FBSyxFQUFFO0FBQ2pCLG9CQUFVLEtBQUssRUFBRTtBQUFBLFFBQ25CO0FBRUEsZUFBTztBQUFBLE1BQ1Q7QUFFQSxlQUFTRixlQUFlLEtBQUs7QUFDM0IsZUFBT0gsUUFBTyxZQUFZLFlBQVksR0FBRyxDQUFDO0FBQUEsTUFDNUM7QUFFQSxlQUFTLFdBQVksS0FBSyxLQUFLLFFBQVEsUUFBUTtBQUM3QyxZQUFJO0FBQ0osYUFBSyxJQUFJLEdBQUcsSUFBSSxRQUFRLEVBQUUsR0FBRztBQUMzQixjQUFLLElBQUksVUFBVSxJQUFJLFVBQVksS0FBSyxJQUFJLE9BQVM7QUFDckQsY0FBSSxJQUFJLE1BQU0sSUFBSSxJQUFJLENBQUM7QUFBQSxRQUN6QjtBQUNBLGVBQU87QUFBQSxNQUNUO0FBS0EsZUFBUyxXQUFZLEtBQUssTUFBTTtBQUM5QixlQUFPLGVBQWUsUUFDbkIsT0FBTyxRQUFRLElBQUksZUFBZSxRQUFRLElBQUksWUFBWSxRQUFRLFFBQ2pFLElBQUksWUFBWSxTQUFTLEtBQUs7QUFBQSxNQUNwQztBQUNBLGVBQVMsWUFBYSxLQUFLO0FBRXpCLGVBQU8sUUFBUTtBQUFBLE1BQ2pCO0FBSUEsVUFBTSx1QkFBdUIsV0FBWTtBQUN2QyxjQUFNTyxZQUFXO0FBQ2pCLGNBQU0sUUFBUSxJQUFJLE1BQU0sR0FBRztBQUMzQixpQkFBUyxJQUFJLEdBQUcsSUFBSSxJQUFJLEVBQUUsR0FBRztBQUMzQixnQkFBTSxNQUFNLElBQUk7QUFDaEIsbUJBQVMsSUFBSSxHQUFHLElBQUksSUFBSSxFQUFFLEdBQUc7QUFDM0Isa0JBQU0sTUFBTSxDQUFDLElBQUlBLFVBQVMsQ0FBQyxJQUFJQSxVQUFTLENBQUM7QUFBQSxVQUMzQztBQUFBLFFBQ0Y7QUFDQSxlQUFPO0FBQUEsTUFDVCxHQUFHO0FBR0gsZUFBUyxtQkFBb0IsSUFBSTtBQUMvQixlQUFPLE9BQU8sV0FBVyxjQUFjLHlCQUF5QjtBQUFBLE1BQ2xFO0FBRUEsZUFBUyx5QkFBMEI7QUFDakMsY0FBTSxJQUFJLE1BQU0sc0JBQXNCO0FBQUEsTUFDeEM7QUFBQTtBQUFBOzs7QUN6akVBOzs7QUNBQTs7O0FDQUE7OztBQ0FBO0FBNEJBLE1BQVk7QUFBWixHQUFBLFNBQVlDLGlCQUFjO0FBRXhCLElBQUFBLGdCQUFBQSxnQkFBQSxjQUFBLElBQUEsQ0FBQSxJQUFBO0FBQ0EsSUFBQUEsZ0JBQUFBLGdCQUFBLFdBQUEsSUFBQSxDQUFBLElBQUE7QUFDQSxJQUFBQSxnQkFBQUEsZ0JBQUEsa0JBQUEsSUFBQSxDQUFBLElBQUE7QUFDQSxJQUFBQSxnQkFBQUEsZ0JBQUEsVUFBQSxJQUFBLENBQUEsSUFBQTtBQUNBLElBQUFBLGdCQUFBQSxnQkFBQSwwQkFBQSxJQUFBLENBQUEsSUFBQTtBQUNBLElBQUFBLGdCQUFBQSxnQkFBQSxnQkFBQSxJQUFBLENBQUEsSUFBQTtBQUNBLElBQUFBLGdCQUFBQSxnQkFBQSxRQUFBLElBQUEsQ0FBQSxJQUFBO0FBQ0EsSUFBQUEsZ0JBQUFBLGdCQUFBLFVBQUEsSUFBQSxDQUFBLElBQUE7QUFHQSxJQUFBQSxnQkFBQUEsZ0JBQUEsa0JBQUEsSUFBQSxFQUFBLElBQUE7QUFDQSxJQUFBQSxnQkFBQUEsZ0JBQUEsa0JBQUEsSUFBQSxFQUFBLElBQUE7QUFDQSxJQUFBQSxnQkFBQUEsZ0JBQUEsaUJBQUEsSUFBQSxFQUFBLElBQUE7QUFDQSxJQUFBQSxnQkFBQUEsZ0JBQUEsc0JBQUEsSUFBQSxFQUFBLElBQUE7QUFDQSxJQUFBQSxnQkFBQUEsZ0JBQUEsbUJBQUEsSUFBQSxFQUFBLElBQUE7QUFHQSxJQUFBQSxnQkFBQUEsZ0JBQUEsTUFBQSxJQUFBLEtBQUEsSUFBQTtBQUNBLElBQUFBLGdCQUFBQSxnQkFBQSxlQUFBLElBQUEsS0FBQSxJQUFBO0VBQ0YsR0FyQlksbUJBQUEsaUJBQWMsQ0FBQSxFQUFBO0FBOEUxQixNQUFZO0FBQVosR0FBQSxTQUFZQyxtQkFBZ0I7QUFDMUIsSUFBQUEsa0JBQUEsT0FBQSxJQUFBO0FBQ0EsSUFBQUEsa0JBQUEsUUFBQSxJQUFBO0FBQ0EsSUFBQUEsa0JBQUEsSUFBQSxJQUFBO0FBQ0EsSUFBQUEsa0JBQUEsTUFBQSxJQUFBO0FBQ0EsSUFBQUEsa0JBQUEsS0FBQSxJQUFBO0FBQ0EsSUFBQUEsa0JBQUEsT0FBQSxJQUFBO0FBQ0EsSUFBQUEsa0JBQUEsTUFBQSxJQUFBO0VBQ0YsR0FSWSxxQkFBQSxtQkFBZ0IsQ0FBQSxFQUFBOzs7QUMxRzVCOzs7QUNBQTs7O0FDQUE7OztBQ0FBO0FBU0EsTUFBWTtBQUFaLEdBQUEsU0FBWUMsY0FBVztBQUNyQixJQUFBQSxhQUFBLFNBQUEsSUFBQTtBQUNBLElBQUFBLGFBQUEsTUFBQSxJQUFBO0FBQ0EsSUFBQUEsYUFBQSxnQkFBQSxJQUFBO0FBQ0EsSUFBQUEsYUFBQSxZQUFBLElBQUE7QUFDQSxJQUFBQSxhQUFBLGVBQUEsSUFBQTtBQUNBLElBQUFBLGFBQUEsZUFBQSxJQUFBO0FBQ0EsSUFBQUEsYUFBQSxlQUFBLElBQUE7QUFDQSxJQUFBQSxhQUFBLGVBQUEsSUFBQTtBQUNBLElBQUFBLGFBQUEsWUFBQSxJQUFBO0VBQ0YsR0FWWSxnQkFBQSxjQUFXLENBQUEsRUFBQTs7O0FMNkJ2QixNQUFZQztBQUFaLEdBQUEsU0FBWUEsaUJBQWM7QUFDeEIsSUFBQUEsZ0JBQUFBLGdCQUFBLGNBQUEsSUFBQSxDQUFBLElBQUE7QUFDQSxJQUFBQSxnQkFBQUEsZ0JBQUEsV0FBQSxJQUFBLENBQUEsSUFBQTtBQUNBLElBQUFBLGdCQUFBQSxnQkFBQSxrQkFBQSxJQUFBLENBQUEsSUFBQTtBQUNBLElBQUFBLGdCQUFBQSxnQkFBQSxjQUFBLElBQUEsQ0FBQSxJQUFBO0FBQ0EsSUFBQUEsZ0JBQUFBLGdCQUFBLDBCQUFBLElBQUEsQ0FBQSxJQUFBO0FBQ0EsSUFBQUEsZ0JBQUFBLGdCQUFBLFFBQUEsSUFBQSxDQUFBLElBQUE7QUFDQSxJQUFBQSxnQkFBQUEsZ0JBQUEsUUFBQSxJQUFBLENBQUEsSUFBQTtBQUNBLElBQUFBLGdCQUFBQSxnQkFBQSxVQUFBLElBQUEsQ0FBQSxJQUFBO0FBQ0EsSUFBQUEsZ0JBQUFBLGdCQUFBLGFBQUEsSUFBQSxDQUFBLElBQUE7QUFDQSxJQUFBQSxnQkFBQUEsZ0JBQUEsZ0JBQUEsSUFBQSxFQUFBLElBQUE7QUFDQSxJQUFBQSxnQkFBQUEsZ0JBQUEsa0JBQUEsSUFBQSxFQUFBLElBQUE7QUFDQSxJQUFBQSxnQkFBQUEsZ0JBQUEsaUJBQUEsSUFBQSxFQUFBLElBQUE7QUFDQSxJQUFBQSxnQkFBQUEsZ0JBQUEsc0JBQUEsSUFBQSxFQUFBLElBQUE7QUFDQSxJQUFBQSxnQkFBQUEsZ0JBQUEsbUJBQUEsSUFBQSxFQUFBLElBQUE7QUFDQSxJQUFBQSxnQkFBQUEsZ0JBQUEsaUJBQUEsSUFBQSxFQUFBLElBQUE7QUFDQSxJQUFBQSxnQkFBQUEsZ0JBQUEsV0FBQSxJQUFBLElBQUEsSUFBQTtBQUNBLElBQUFBLGdCQUFBQSxnQkFBQSxhQUFBLElBQUEsSUFBQSxJQUFBO0FBQ0EsSUFBQUEsZ0JBQUFBLGdCQUFBLEtBQUEsSUFBQSxJQUFBLElBQUE7QUFDQSxJQUFBQSxnQkFBQUEsZ0JBQUEsV0FBQSxJQUFBLEdBQUEsSUFBQTtBQUNBLElBQUFBLGdCQUFBQSxnQkFBQSxVQUFBLElBQUEsS0FBQSxJQUFBO0FBQ0EsSUFBQUEsZ0JBQUFBLGdCQUFBLHFCQUFBLElBQUEsS0FBQSxJQUFBO0FBQ0EsSUFBQUEsZ0JBQUFBLGdCQUFBLGFBQUEsSUFBQSxLQUFBLElBQUE7QUFDQSxJQUFBQSxnQkFBQUEsZ0JBQUEsZUFBQSxJQUFBLEtBQUEsSUFBQTtBQUNBLElBQUFBLGdCQUFBQSxnQkFBQSxlQUFBLElBQUEsS0FBQSxJQUFBO0FBQ0EsSUFBQUEsZ0JBQUFBLGdCQUFBLG9CQUFBLElBQUEsR0FBQSxJQUFBO0FBQ0EsSUFBQUEsZ0JBQUFBLGdCQUFBLHVCQUFBLElBQUEsS0FBQSxJQUFBO0FBQ0EsSUFBQUEsZ0JBQUFBLGdCQUFBLGdCQUFBLElBQUEsS0FBQSxJQUFBO0FBQ0EsSUFBQUEsZ0JBQUFBLGdCQUFBLGtCQUFBLElBQUEsS0FBQSxJQUFBO0FBQ0EsSUFBQUEsZ0JBQUFBLGdCQUFBLFdBQUEsSUFBQSxLQUFBLElBQUE7QUFDQSxJQUFBQSxnQkFBQUEsZ0JBQUEsc0JBQUEsSUFBQSxLQUFBLElBQUE7RUFDRixHQS9CWUEsb0JBQUFBLGtCQUFjLENBQUEsRUFBQTs7O0FNdEMxQjs7O0FDQUE7OztBQ0FBOzs7QUNBQTs7O0FDQUE7QUFNTSxXQUFVLFFBQVEsR0FBVTtBQUNoQyxXQUFPLGFBQWEsY0FBZSxZQUFZLE9BQU8sQ0FBQyxLQUFLLEVBQUUsWUFBWSxTQUFTO0VBQ3JGO0FBR00sV0FBVSxRQUFRLEdBQVcsUUFBZ0IsSUFBRTtBQUNuRCxRQUFJLENBQUMsT0FBTyxjQUFjLENBQUMsS0FBSyxJQUFJLEdBQUc7QUFDckMsWUFBTSxTQUFTLFNBQVMsSUFBSSxLQUFLO0FBQ2pDLFlBQU0sSUFBSSxNQUFNLEdBQUcsTUFBTSw4QkFBOEIsQ0FBQyxFQUFFO0lBQzVEO0VBQ0Y7QUFHTSxXQUFVLE9BQU8sT0FBbUIsUUFBaUIsUUFBZ0IsSUFBRTtBQUMzRSxVQUFNLFFBQVEsUUFBUSxLQUFLO0FBQzNCLFVBQU0sTUFBTSxPQUFPO0FBQ25CLFVBQU0sV0FBVyxXQUFXO0FBQzVCLFFBQUksQ0FBQyxTQUFVLFlBQVksUUFBUSxRQUFTO0FBQzFDLFlBQU0sU0FBUyxTQUFTLElBQUksS0FBSztBQUNqQyxZQUFNLFFBQVEsV0FBVyxjQUFjLE1BQU0sS0FBSztBQUNsRCxZQUFNLE1BQU0sUUFBUSxVQUFVLEdBQUcsS0FBSyxRQUFRLE9BQU8sS0FBSztBQUMxRCxZQUFNLElBQUksTUFBTSxTQUFTLHdCQUF3QixRQUFRLFdBQVcsR0FBRztJQUN6RTtBQUNBLFdBQU87RUFDVDtBQUdNLFdBQVUsTUFBTSxHQUFRO0FBQzVCLFFBQUksT0FBTyxNQUFNLGNBQWMsT0FBTyxFQUFFLFdBQVc7QUFDakQsWUFBTSxJQUFJLE1BQU0seUNBQXlDO0FBQzNELFlBQVEsRUFBRSxTQUFTO0FBQ25CLFlBQVEsRUFBRSxRQUFRO0VBQ3BCO0FBR00sV0FBVSxRQUFRLFVBQWUsZ0JBQWdCLE1BQUk7QUFDekQsUUFBSSxTQUFTO0FBQVcsWUFBTSxJQUFJLE1BQU0sa0NBQWtDO0FBQzFFLFFBQUksaUJBQWlCLFNBQVM7QUFBVSxZQUFNLElBQUksTUFBTSx1Q0FBdUM7RUFDakc7QUFHTSxXQUFVLFFBQVEsS0FBVSxVQUFhO0FBQzdDLFdBQU8sS0FBSyxRQUFXLHFCQUFxQjtBQUM1QyxVQUFNLE1BQU0sU0FBUztBQUNyQixRQUFJLElBQUksU0FBUyxLQUFLO0FBQ3BCLFlBQU0sSUFBSSxNQUFNLHNEQUFzRCxHQUFHO0lBQzNFO0VBQ0Y7QUFhTSxXQUFVLElBQUksS0FBZTtBQUNqQyxXQUFPLElBQUksWUFBWSxJQUFJLFFBQVEsSUFBSSxZQUFZLEtBQUssTUFBTSxJQUFJLGFBQWEsQ0FBQyxDQUFDO0VBQ25GO0FBR00sV0FBVSxTQUFTLFFBQW9CO0FBQzNDLGFBQVMsSUFBSSxHQUFHLElBQUksT0FBTyxRQUFRLEtBQUs7QUFDdEMsYUFBTyxDQUFDLEVBQUUsS0FBSyxDQUFDO0lBQ2xCO0VBQ0Y7QUFHTSxXQUFVLFdBQVcsS0FBZTtBQUN4QyxXQUFPLElBQUksU0FBUyxJQUFJLFFBQVEsSUFBSSxZQUFZLElBQUksVUFBVTtFQUNoRTtBQUdNLFdBQVUsS0FBSyxNQUFjLE9BQWE7QUFDOUMsV0FBUSxRQUFTLEtBQUssUUFBVyxTQUFTO0VBQzVDO0FBR00sV0FBVSxLQUFLLE1BQWMsT0FBYTtBQUM5QyxXQUFRLFFBQVEsUUFBVyxTQUFVLEtBQUssVUFBWTtFQUN4RDtBQUdPLE1BQU0sT0FBaUMsdUJBQzVDLElBQUksV0FBVyxJQUFJLFlBQVksQ0FBQyxTQUFVLENBQUMsRUFBRSxNQUFNLEVBQUUsQ0FBQyxNQUFNLElBQUs7QUFHN0QsV0FBVSxTQUFTLE1BQVk7QUFDbkMsV0FDSSxRQUFRLEtBQU0sYUFDZCxRQUFRLElBQUssV0FDYixTQUFTLElBQUssUUFDZCxTQUFTLEtBQU07RUFFckI7QUFPTSxXQUFVLFdBQVcsS0FBZ0I7QUFDekMsYUFBUyxJQUFJLEdBQUcsSUFBSSxJQUFJLFFBQVEsS0FBSztBQUNuQyxVQUFJLENBQUMsSUFBSSxTQUFTLElBQUksQ0FBQyxDQUFDO0lBQzFCO0FBQ0EsV0FBTztFQUNUO0FBRU8sTUFBTSxhQUE4QyxPQUN2RCxDQUFDLE1BQW1CLElBQ3BCO0FBR0osTUFBTSxnQkFBMEM7O0lBRTlDLE9BQU8sV0FBVyxLQUFLLENBQUEsQ0FBRSxFQUFFLFVBQVUsY0FBYyxPQUFPLFdBQVcsWUFBWTtLQUFXO0FBRzlGLE1BQU0sUUFBd0Isc0JBQU0sS0FBSyxFQUFFLFFBQVEsSUFBRyxHQUFJLENBQUMsR0FBRyxNQUM1RCxFQUFFLFNBQVMsRUFBRSxFQUFFLFNBQVMsR0FBRyxHQUFHLENBQUM7QUFPM0IsV0FBVSxXQUFXLE9BQWlCO0FBQzFDLFdBQU8sS0FBSztBQUVaLFFBQUk7QUFBZSxhQUFPLE1BQU0sTUFBSztBQUVyQyxRQUFJLE1BQU07QUFDVixhQUFTLElBQUksR0FBRyxJQUFJLE1BQU0sUUFBUSxLQUFLO0FBQ3JDLGFBQU8sTUFBTSxNQUFNLENBQUMsQ0FBQztJQUN2QjtBQUNBLFdBQU87RUFDVDtBQUdBLE1BQU0sU0FBUyxFQUFFLElBQUksSUFBSSxJQUFJLElBQUksR0FBRyxJQUFJLEdBQUcsSUFBSSxHQUFHLElBQUksR0FBRyxJQUFHO0FBQzVELFdBQVMsY0FBYyxJQUFVO0FBQy9CLFFBQUksTUFBTSxPQUFPLE1BQU0sTUFBTSxPQUFPO0FBQUksYUFBTyxLQUFLLE9BQU87QUFDM0QsUUFBSSxNQUFNLE9BQU8sS0FBSyxNQUFNLE9BQU87QUFBRyxhQUFPLE1BQU0sT0FBTyxJQUFJO0FBQzlELFFBQUksTUFBTSxPQUFPLEtBQUssTUFBTSxPQUFPO0FBQUcsYUFBTyxNQUFNLE9BQU8sSUFBSTtBQUM5RDtFQUNGO0FBTU0sV0FBVSxXQUFXLEtBQVc7QUFDcEMsUUFBSSxPQUFPLFFBQVE7QUFBVSxZQUFNLElBQUksTUFBTSw4QkFBOEIsT0FBTyxHQUFHO0FBRXJGLFFBQUk7QUFBZSxhQUFPLFdBQVcsUUFBUSxHQUFHO0FBQ2hELFVBQU0sS0FBSyxJQUFJO0FBQ2YsVUFBTSxLQUFLLEtBQUs7QUFDaEIsUUFBSSxLQUFLO0FBQUcsWUFBTSxJQUFJLE1BQU0scURBQXFELEVBQUU7QUFDbkYsVUFBTSxRQUFRLElBQUksV0FBVyxFQUFFO0FBQy9CLGFBQVMsS0FBSyxHQUFHLEtBQUssR0FBRyxLQUFLLElBQUksTUFBTSxNQUFNLEdBQUc7QUFDL0MsWUFBTSxLQUFLLGNBQWMsSUFBSSxXQUFXLEVBQUUsQ0FBQztBQUMzQyxZQUFNLEtBQUssY0FBYyxJQUFJLFdBQVcsS0FBSyxDQUFDLENBQUM7QUFDL0MsVUFBSSxPQUFPLFVBQWEsT0FBTyxRQUFXO0FBQ3hDLGNBQU0sT0FBTyxJQUFJLEVBQUUsSUFBSSxJQUFJLEtBQUssQ0FBQztBQUNqQyxjQUFNLElBQUksTUFBTSxpREFBaUQsT0FBTyxnQkFBZ0IsRUFBRTtNQUM1RjtBQUNBLFlBQU0sRUFBRSxJQUFJLEtBQUssS0FBSztJQUN4QjtBQUNBLFdBQU87RUFDVDtBQWtDTSxXQUFVLFlBQVksS0FBVztBQUNyQyxRQUFJLE9BQU8sUUFBUTtBQUFVLFlBQU0sSUFBSSxNQUFNLGlCQUFpQjtBQUM5RCxXQUFPLElBQUksV0FBVyxJQUFJLFlBQVcsRUFBRyxPQUFPLEdBQUcsQ0FBQztFQUNyRDtBQVNNLFdBQVUsZ0JBQWdCLE1BQWdCLGFBQWEsSUFBRTtBQUM3RCxRQUFJLE9BQU8sU0FBUztBQUFVLGFBQU8sWUFBWSxJQUFJO0FBQ3JELFdBQU8sT0FBTyxNQUFNLFFBQVcsVUFBVTtFQUMzQztBQUdNLFdBQVUsZUFBZSxRQUFvQjtBQUNqRCxRQUFJLE1BQU07QUFDVixhQUFTLElBQUksR0FBRyxJQUFJLE9BQU8sUUFBUSxLQUFLO0FBQ3RDLFlBQU0sSUFBSSxPQUFPLENBQUM7QUFDbEIsYUFBTyxDQUFDO0FBQ1IsYUFBTyxFQUFFO0lBQ1g7QUFDQSxVQUFNLE1BQU0sSUFBSSxXQUFXLEdBQUc7QUFDOUIsYUFBUyxJQUFJLEdBQUdDLE9BQU0sR0FBRyxJQUFJLE9BQU8sUUFBUSxLQUFLO0FBQy9DLFlBQU0sSUFBSSxPQUFPLENBQUM7QUFDbEIsVUFBSSxJQUFJLEdBQUdBLElBQUc7QUFDZCxNQUFBQSxRQUFPLEVBQUU7SUFDWDtBQUNBLFdBQU87RUFDVDtBQUlNLFdBQVUsVUFDZCxVQUNBLE1BQVM7QUFFVCxRQUFJLFNBQVMsVUFBYSxDQUFBLEVBQUcsU0FBUyxLQUFLLElBQUksTUFBTTtBQUNuRCxZQUFNLElBQUksTUFBTSxxQ0FBcUM7QUFDdkQsVUFBTSxTQUFTLE9BQU8sT0FBTyxVQUFVLElBQUk7QUFDM0MsV0FBTztFQUNUO0FBd0RNLFdBQVUsYUFDZCxVQUNBLE9BQWlCLENBQUEsR0FBRTtBQUVuQixVQUFNLFFBQWEsQ0FBQyxLQUFpQixTQUFnQixTQUFTLElBQUksRUFBRSxPQUFPLEdBQUcsRUFBRSxPQUFNO0FBQ3RGLFVBQU0sTUFBTSxTQUFTLE1BQVM7QUFDOUIsVUFBTSxZQUFZLElBQUk7QUFDdEIsVUFBTSxXQUFXLElBQUk7QUFDckIsVUFBTSxTQUFTLENBQUMsU0FBZ0IsU0FBUyxJQUFJO0FBQzdDLFdBQU8sT0FBTyxPQUFPLElBQUk7QUFDekIsV0FBTyxPQUFPLE9BQU8sS0FBSztFQUM1QjtBQUdNLFdBQVUsWUFBWSxjQUFjLElBQUU7QUFDMUMsVUFBTSxLQUFLLE9BQU8sZUFBZSxXQUFZLFdBQW1CLFNBQVM7QUFDekUsUUFBSSxPQUFPLElBQUksb0JBQW9CO0FBQ2pDLFlBQU0sSUFBSSxNQUFNLHdDQUF3QztBQUMxRCxXQUFPLEdBQUcsZ0JBQWdCLElBQUksV0FBVyxXQUFXLENBQUM7RUFDdkQ7QUFHTyxNQUFNLFVBQVUsQ0FBQyxZQUF3QztJQUM5RCxLQUFLLFdBQVcsS0FBSyxDQUFDLEdBQU0sR0FBTSxJQUFNLEtBQU0sSUFBTSxHQUFNLEtBQU0sR0FBTSxHQUFNLEdBQU0sTUFBTSxDQUFDOzs7O0FEelVyRixXQUFVLElBQUksR0FBVyxHQUFXLEdBQVM7QUFDakQsV0FBUSxJQUFJLElBQU0sQ0FBQyxJQUFJO0VBQ3pCO0FBR00sV0FBVSxJQUFJLEdBQVcsR0FBVyxHQUFTO0FBQ2pELFdBQVEsSUFBSSxJQUFNLElBQUksSUFBTSxJQUFJO0VBQ2xDO0FBTU0sTUFBZ0IsU0FBaEIsTUFBc0I7SUFPakI7SUFDQTtJQUNBO0lBQ0E7O0lBR0M7SUFDQTtJQUNBLFdBQVc7SUFDWCxTQUFTO0lBQ1QsTUFBTTtJQUNOLFlBQVk7SUFFdEIsWUFBWSxVQUFrQixXQUFtQixXQUFtQkMsT0FBYTtBQUMvRSxXQUFLLFdBQVc7QUFDaEIsV0FBSyxZQUFZO0FBQ2pCLFdBQUssWUFBWTtBQUNqQixXQUFLLE9BQU9BO0FBQ1osV0FBSyxTQUFTLElBQUksV0FBVyxRQUFRO0FBQ3JDLFdBQUssT0FBTyxXQUFXLEtBQUssTUFBTTtJQUNwQztJQUNBLE9BQU8sTUFBZ0I7QUFDckIsY0FBUSxJQUFJO0FBQ1osYUFBTyxJQUFJO0FBQ1gsWUFBTSxFQUFFLE1BQU0sUUFBUSxTQUFRLElBQUs7QUFDbkMsWUFBTSxNQUFNLEtBQUs7QUFDakIsZUFBUyxNQUFNLEdBQUcsTUFBTSxPQUFPO0FBQzdCLGNBQU0sT0FBTyxLQUFLLElBQUksV0FBVyxLQUFLLEtBQUssTUFBTSxHQUFHO0FBRXBELFlBQUksU0FBUyxVQUFVO0FBQ3JCLGdCQUFNLFdBQVcsV0FBVyxJQUFJO0FBQ2hDLGlCQUFPLFlBQVksTUFBTSxLQUFLLE9BQU87QUFBVSxpQkFBSyxRQUFRLFVBQVUsR0FBRztBQUN6RTtRQUNGO0FBQ0EsZUFBTyxJQUFJLEtBQUssU0FBUyxLQUFLLE1BQU0sSUFBSSxHQUFHLEtBQUssR0FBRztBQUNuRCxhQUFLLE9BQU87QUFDWixlQUFPO0FBQ1AsWUFBSSxLQUFLLFFBQVEsVUFBVTtBQUN6QixlQUFLLFFBQVEsTUFBTSxDQUFDO0FBQ3BCLGVBQUssTUFBTTtRQUNiO01BQ0Y7QUFDQSxXQUFLLFVBQVUsS0FBSztBQUNwQixXQUFLLFdBQVU7QUFDZixhQUFPO0lBQ1Q7SUFDQSxXQUFXLEtBQWU7QUFDeEIsY0FBUSxJQUFJO0FBQ1osY0FBUSxLQUFLLElBQUk7QUFDakIsV0FBSyxXQUFXO0FBSWhCLFlBQU0sRUFBRSxRQUFRLE1BQU0sVUFBVSxNQUFBQSxNQUFJLElBQUs7QUFDekMsVUFBSSxFQUFFLElBQUcsSUFBSztBQUVkLGFBQU8sS0FBSyxJQUFJO0FBQ2hCLFlBQU0sS0FBSyxPQUFPLFNBQVMsR0FBRyxDQUFDO0FBRy9CLFVBQUksS0FBSyxZQUFZLFdBQVcsS0FBSztBQUNuQyxhQUFLLFFBQVEsTUFBTSxDQUFDO0FBQ3BCLGNBQU07TUFDUjtBQUVBLGVBQVMsSUFBSSxLQUFLLElBQUksVUFBVTtBQUFLLGVBQU8sQ0FBQyxJQUFJO0FBSWpELFdBQUssYUFBYSxXQUFXLEdBQUcsT0FBTyxLQUFLLFNBQVMsQ0FBQyxHQUFHQSxLQUFJO0FBQzdELFdBQUssUUFBUSxNQUFNLENBQUM7QUFDcEIsWUFBTSxRQUFRLFdBQVcsR0FBRztBQUM1QixZQUFNLE1BQU0sS0FBSztBQUVqQixVQUFJLE1BQU07QUFBRyxjQUFNLElBQUksTUFBTSwyQ0FBMkM7QUFDeEUsWUFBTSxTQUFTLE1BQU07QUFDckIsWUFBTSxRQUFRLEtBQUssSUFBRztBQUN0QixVQUFJLFNBQVMsTUFBTTtBQUFRLGNBQU0sSUFBSSxNQUFNLG9DQUFvQztBQUMvRSxlQUFTLElBQUksR0FBRyxJQUFJLFFBQVE7QUFBSyxjQUFNLFVBQVUsSUFBSSxHQUFHLE1BQU0sQ0FBQyxHQUFHQSxLQUFJO0lBQ3hFO0lBQ0EsU0FBTTtBQUNKLFlBQU0sRUFBRSxRQUFRLFVBQVMsSUFBSztBQUM5QixXQUFLLFdBQVcsTUFBTTtBQUN0QixZQUFNLE1BQU0sT0FBTyxNQUFNLEdBQUcsU0FBUztBQUNyQyxXQUFLLFFBQU87QUFDWixhQUFPO0lBQ1Q7SUFDQSxXQUFXLElBQU07QUFDZixhQUFPLElBQUssS0FBSyxZQUFtQjtBQUNwQyxTQUFHLElBQUksR0FBRyxLQUFLLElBQUcsQ0FBRTtBQUNwQixZQUFNLEVBQUUsVUFBVSxRQUFRLFFBQVEsVUFBVSxXQUFXLElBQUcsSUFBSztBQUMvRCxTQUFHLFlBQVk7QUFDZixTQUFHLFdBQVc7QUFDZCxTQUFHLFNBQVM7QUFDWixTQUFHLE1BQU07QUFDVCxVQUFJLFNBQVM7QUFBVSxXQUFHLE9BQU8sSUFBSSxNQUFNO0FBQzNDLGFBQU87SUFDVDtJQUNBLFFBQUs7QUFDSCxhQUFPLEtBQUssV0FBVTtJQUN4Qjs7QUFTSyxNQUFNLFlBQXlDLDRCQUFZLEtBQUs7SUFDckU7SUFBWTtJQUFZO0lBQVk7SUFBWTtJQUFZO0lBQVk7SUFBWTtHQUNyRjs7O0FEMUhELE1BQU0sV0FBMkIsNEJBQVksS0FBSztJQUNoRDtJQUFZO0lBQVk7SUFBWTtJQUFZO0lBQVk7SUFBWTtJQUFZO0lBQ3BGO0lBQVk7SUFBWTtJQUFZO0lBQVk7SUFBWTtJQUFZO0lBQVk7SUFDcEY7SUFBWTtJQUFZO0lBQVk7SUFBWTtJQUFZO0lBQVk7SUFBWTtJQUNwRjtJQUFZO0lBQVk7SUFBWTtJQUFZO0lBQVk7SUFBWTtJQUFZO0lBQ3BGO0lBQVk7SUFBWTtJQUFZO0lBQVk7SUFBWTtJQUFZO0lBQVk7SUFDcEY7SUFBWTtJQUFZO0lBQVk7SUFBWTtJQUFZO0lBQVk7SUFBWTtJQUNwRjtJQUFZO0lBQVk7SUFBWTtJQUFZO0lBQVk7SUFBWTtJQUFZO0lBQ3BGO0lBQVk7SUFBWTtJQUFZO0lBQVk7SUFBWTtJQUFZO0lBQVk7R0FDckY7QUFHRCxNQUFNLFdBQTJCLG9CQUFJLFlBQVksRUFBRTtBQUduRCxNQUFlLFdBQWYsY0FBdUQsT0FBUztJQVk5RCxZQUFZLFdBQWlCO0FBQzNCLFlBQU0sSUFBSSxXQUFXLEdBQUcsS0FBSztJQUMvQjtJQUNVLE1BQUc7QUFDWCxZQUFNLEVBQUUsR0FBRyxHQUFHLEdBQUcsR0FBRyxHQUFHLEdBQUcsR0FBRyxFQUFDLElBQUs7QUFDbkMsYUFBTyxDQUFDLEdBQUcsR0FBRyxHQUFHLEdBQUcsR0FBRyxHQUFHLEdBQUcsQ0FBQztJQUNoQzs7SUFFVSxJQUNSLEdBQVcsR0FBVyxHQUFXLEdBQVcsR0FBVyxHQUFXLEdBQVcsR0FBUztBQUV0RixXQUFLLElBQUksSUFBSTtBQUNiLFdBQUssSUFBSSxJQUFJO0FBQ2IsV0FBSyxJQUFJLElBQUk7QUFDYixXQUFLLElBQUksSUFBSTtBQUNiLFdBQUssSUFBSSxJQUFJO0FBQ2IsV0FBSyxJQUFJLElBQUk7QUFDYixXQUFLLElBQUksSUFBSTtBQUNiLFdBQUssSUFBSSxJQUFJO0lBQ2Y7SUFDVSxRQUFRLE1BQWdCLFFBQWM7QUFFOUMsZUFBUyxJQUFJLEdBQUcsSUFBSSxJQUFJLEtBQUssVUFBVTtBQUFHLGlCQUFTLENBQUMsSUFBSSxLQUFLLFVBQVUsUUFBUSxLQUFLO0FBQ3BGLGVBQVMsSUFBSSxJQUFJLElBQUksSUFBSSxLQUFLO0FBQzVCLGNBQU0sTUFBTSxTQUFTLElBQUksRUFBRTtBQUMzQixjQUFNLEtBQUssU0FBUyxJQUFJLENBQUM7QUFDekIsY0FBTSxLQUFLLEtBQUssS0FBSyxDQUFDLElBQUksS0FBSyxLQUFLLEVBQUUsSUFBSyxRQUFRO0FBQ25ELGNBQU0sS0FBSyxLQUFLLElBQUksRUFBRSxJQUFJLEtBQUssSUFBSSxFQUFFLElBQUssT0FBTztBQUNqRCxpQkFBUyxDQUFDLElBQUssS0FBSyxTQUFTLElBQUksQ0FBQyxJQUFJLEtBQUssU0FBUyxJQUFJLEVBQUUsSUFBSztNQUNqRTtBQUVBLFVBQUksRUFBRSxHQUFHLEdBQUcsR0FBRyxHQUFHLEdBQUcsR0FBRyxHQUFHLEVBQUMsSUFBSztBQUNqQyxlQUFTLElBQUksR0FBRyxJQUFJLElBQUksS0FBSztBQUMzQixjQUFNLFNBQVMsS0FBSyxHQUFHLENBQUMsSUFBSSxLQUFLLEdBQUcsRUFBRSxJQUFJLEtBQUssR0FBRyxFQUFFO0FBQ3BELGNBQU0sS0FBTSxJQUFJLFNBQVMsSUFBSSxHQUFHLEdBQUcsQ0FBQyxJQUFJLFNBQVMsQ0FBQyxJQUFJLFNBQVMsQ0FBQyxJQUFLO0FBQ3JFLGNBQU0sU0FBUyxLQUFLLEdBQUcsQ0FBQyxJQUFJLEtBQUssR0FBRyxFQUFFLElBQUksS0FBSyxHQUFHLEVBQUU7QUFDcEQsY0FBTSxLQUFNLFNBQVMsSUFBSSxHQUFHLEdBQUcsQ0FBQyxJQUFLO0FBQ3JDLFlBQUk7QUFDSixZQUFJO0FBQ0osWUFBSTtBQUNKLFlBQUssSUFBSSxLQUFNO0FBQ2YsWUFBSTtBQUNKLFlBQUk7QUFDSixZQUFJO0FBQ0osWUFBSyxLQUFLLEtBQU07TUFDbEI7QUFFQSxVQUFLLElBQUksS0FBSyxJQUFLO0FBQ25CLFVBQUssSUFBSSxLQUFLLElBQUs7QUFDbkIsVUFBSyxJQUFJLEtBQUssSUFBSztBQUNuQixVQUFLLElBQUksS0FBSyxJQUFLO0FBQ25CLFVBQUssSUFBSSxLQUFLLElBQUs7QUFDbkIsVUFBSyxJQUFJLEtBQUssSUFBSztBQUNuQixVQUFLLElBQUksS0FBSyxJQUFLO0FBQ25CLFVBQUssSUFBSSxLQUFLLElBQUs7QUFDbkIsV0FBSyxJQUFJLEdBQUcsR0FBRyxHQUFHLEdBQUcsR0FBRyxHQUFHLEdBQUcsQ0FBQztJQUNqQztJQUNVLGFBQVU7QUFDbEIsWUFBTSxRQUFRO0lBQ2hCO0lBQ0EsVUFBTztBQUNMLFdBQUssSUFBSSxHQUFHLEdBQUcsR0FBRyxHQUFHLEdBQUcsR0FBRyxHQUFHLENBQUM7QUFDL0IsWUFBTSxLQUFLLE1BQU07SUFDbkI7O0FBSUksTUFBTyxVQUFQLGNBQXVCLFNBQWlCOzs7SUFHbEMsSUFBWSxVQUFVLENBQUMsSUFBSTtJQUMzQixJQUFZLFVBQVUsQ0FBQyxJQUFJO0lBQzNCLElBQVksVUFBVSxDQUFDLElBQUk7SUFDM0IsSUFBWSxVQUFVLENBQUMsSUFBSTtJQUMzQixJQUFZLFVBQVUsQ0FBQyxJQUFJO0lBQzNCLElBQVksVUFBVSxDQUFDLElBQUk7SUFDM0IsSUFBWSxVQUFVLENBQUMsSUFBSTtJQUMzQixJQUFZLFVBQVUsQ0FBQyxJQUFJO0lBQ3JDLGNBQUE7QUFDRSxZQUFNLEVBQUU7SUFDVjs7QUFxVEssTUFBTSxTQUF5QztJQUNwRCxNQUFNLElBQUksUUFBTztJQUNELHdCQUFRLENBQUk7RUFBQzs7O0FHbGIvQjs7O0FDQUE7QUFxQkEsTUFBTSxNQUFzQix1QkFBTyxDQUFDO0FBQ3BDLE1BQU0sTUFBc0IsdUJBQU8sQ0FBQztBQVM5QixXQUFVLE1BQU0sT0FBZ0IsUUFBZ0IsSUFBRTtBQUN0RCxRQUFJLE9BQU8sVUFBVSxXQUFXO0FBQzlCLFlBQU0sU0FBUyxTQUFTLElBQUksS0FBSztBQUNqQyxZQUFNLElBQUksTUFBTSxTQUFTLGdDQUFnQyxPQUFPLEtBQUs7SUFDdkU7QUFDQSxXQUFPO0VBQ1Q7QUFHQSxXQUFTLFdBQVcsR0FBa0I7QUFDcEMsUUFBSSxPQUFPLE1BQU0sVUFBVTtBQUN6QixVQUFJLENBQUMsU0FBUyxDQUFDO0FBQUcsY0FBTSxJQUFJLE1BQU0sbUNBQW1DLENBQUM7SUFDeEU7QUFBTyxjQUFRLENBQUM7QUFDaEIsV0FBTztFQUNUO0FBU00sV0FBVSxvQkFBb0JDLE1BQW9CO0FBQ3RELFVBQU0sTUFBTSxXQUFXQSxJQUFHLEVBQUUsU0FBUyxFQUFFO0FBQ3ZDLFdBQU8sSUFBSSxTQUFTLElBQUksTUFBTSxNQUFNO0VBQ3RDO0FBRU0sV0FBVSxZQUFZLEtBQVc7QUFDckMsUUFBSSxPQUFPLFFBQVE7QUFBVSxZQUFNLElBQUksTUFBTSw4QkFBOEIsT0FBTyxHQUFHO0FBQ3JGLFdBQU8sUUFBUSxLQUFLLE1BQU0sT0FBTyxPQUFPLEdBQUc7RUFDN0M7QUFHTSxXQUFVLGdCQUFnQixPQUFpQjtBQUMvQyxXQUFPLFlBQVksV0FBWSxLQUFLLENBQUM7RUFDdkM7QUFDTSxXQUFVLGdCQUFnQixPQUFpQjtBQUMvQyxXQUFPLFlBQVksV0FBWSxVQUFVLE9BQVEsS0FBSyxDQUFDLEVBQUUsUUFBTyxDQUFFLENBQUM7RUFDckU7QUFFTSxXQUFVLGdCQUFnQixHQUFvQixLQUFXO0FBQzdELFlBQVEsR0FBRztBQUNYLFFBQUksV0FBVyxDQUFDO0FBQ2hCLFVBQU0sTUFBTSxXQUFZLEVBQUUsU0FBUyxFQUFFLEVBQUUsU0FBUyxNQUFNLEdBQUcsR0FBRyxDQUFDO0FBQzdELFFBQUksSUFBSSxXQUFXO0FBQUssWUFBTSxJQUFJLE1BQU0sa0JBQWtCO0FBQzFELFdBQU87RUFDVDtBQUNNLFdBQVUsZ0JBQWdCLEdBQW9CLEtBQVc7QUFDN0QsV0FBTyxnQkFBZ0IsR0FBRyxHQUFHLEVBQUUsUUFBTztFQUN4QztBQWtCTSxXQUFVLFVBQVUsT0FBaUI7QUFDekMsV0FBTyxXQUFXLEtBQUssS0FBSztFQUM5QjtBQU9NLFdBQVUsYUFBYSxPQUFhO0FBQ3hDLFdBQU8sV0FBVyxLQUFLLE9BQU8sQ0FBQyxHQUFHLE1BQUs7QUFDckMsWUFBTSxXQUFXLEVBQUUsV0FBVyxDQUFDO0FBQy9CLFVBQUksRUFBRSxXQUFXLEtBQUssV0FBVyxLQUFLO0FBQ3BDLGNBQU0sSUFBSSxNQUNSLHdDQUF3QyxNQUFNLENBQUMsQ0FBQyxlQUFlLFFBQVEsZ0JBQWdCLENBQUMsRUFBRTtNQUU5RjtBQUNBLGFBQU87SUFDVCxDQUFDO0VBQ0g7QUFHQSxNQUFNLFdBQVcsQ0FBQyxNQUFjLE9BQU8sTUFBTSxZQUFZLE9BQU87QUFFMUQsV0FBVSxRQUFRLEdBQVcsS0FBYSxLQUFXO0FBQ3pELFdBQU8sU0FBUyxDQUFDLEtBQUssU0FBUyxHQUFHLEtBQUssU0FBUyxHQUFHLEtBQUssT0FBTyxLQUFLLElBQUk7RUFDMUU7QUFPTSxXQUFVLFNBQVMsT0FBZSxHQUFXLEtBQWEsS0FBVztBQU16RSxRQUFJLENBQUMsUUFBUSxHQUFHLEtBQUssR0FBRztBQUN0QixZQUFNLElBQUksTUFBTSxvQkFBb0IsUUFBUSxPQUFPLE1BQU0sYUFBYSxNQUFNLFdBQVcsQ0FBQztFQUM1RjtBQVNNLFdBQVUsT0FBTyxHQUFTO0FBQzlCLFFBQUk7QUFDSixTQUFLLE1BQU0sR0FBRyxJQUFJLEtBQUssTUFBTSxLQUFLLE9BQU87QUFBRTtBQUMzQyxXQUFPO0VBQ1Q7QUFzQk8sTUFBTSxVQUFVLENBQUMsT0FBdUIsT0FBTyxPQUFPLENBQUMsS0FBSztBQVk3RCxXQUFVLGVBQ2QsU0FDQSxVQUNBLFFBQTREO0FBRTVELFlBQVEsU0FBUyxTQUFTO0FBQzFCLFlBQVEsVUFBVSxVQUFVO0FBQzVCLFFBQUksT0FBTyxXQUFXO0FBQVksWUFBTSxJQUFJLE1BQU0sMkJBQTJCO0FBQzdFLFVBQU0sTUFBTSxDQUFDLFFBQTRCLElBQUksV0FBVyxHQUFHO0FBQzNELFVBQU0sT0FBTyxXQUFXLEdBQUU7QUFDMUIsVUFBTSxRQUFRLFdBQVcsR0FBRyxDQUFJO0FBQ2hDLFVBQU0sUUFBUSxXQUFXLEdBQUcsQ0FBSTtBQUNoQyxVQUFNLGdCQUFnQjtBQUd0QixRQUFJLElBQUksSUFBSSxPQUFPO0FBQ25CLFFBQUksSUFBSSxJQUFJLE9BQU87QUFDbkIsUUFBSSxJQUFJO0FBQ1IsVUFBTSxRQUFRLE1BQUs7QUFDakIsUUFBRSxLQUFLLENBQUM7QUFDUixRQUFFLEtBQUssQ0FBQztBQUNSLFVBQUk7SUFDTjtBQUNBLFVBQU0sSUFBSSxJQUFJLFNBQXVCLE9BQU8sR0FBRyxZQUFhLEdBQUcsR0FBRyxJQUFJLENBQUM7QUFDdkUsVUFBTSxTQUFTLENBQUMsT0FBbUIsU0FBUTtBQUV6QyxVQUFJLEVBQUUsT0FBTyxJQUFJO0FBQ2pCLFVBQUksRUFBQztBQUNMLFVBQUksS0FBSyxXQUFXO0FBQUc7QUFDdkIsVUFBSSxFQUFFLE9BQU8sSUFBSTtBQUNqQixVQUFJLEVBQUM7SUFDUDtBQUNBLFVBQU0sTUFBTSxNQUFLO0FBRWYsVUFBSSxPQUFPO0FBQWUsY0FBTSxJQUFJLE1BQU0sc0NBQXNDO0FBQ2hGLFVBQUksTUFBTTtBQUNWLFlBQU0sTUFBb0IsQ0FBQTtBQUMxQixhQUFPLE1BQU0sVUFBVTtBQUNyQixZQUFJLEVBQUM7QUFDTCxjQUFNLEtBQUssRUFBRSxNQUFLO0FBQ2xCLFlBQUksS0FBSyxFQUFFO0FBQ1gsZUFBTyxFQUFFO01BQ1g7QUFDQSxhQUFPLFlBQWEsR0FBRyxHQUFHO0lBQzVCO0FBQ0EsVUFBTSxXQUFXLENBQUMsTUFBa0IsU0FBb0I7QUFDdEQsWUFBSztBQUNMLGFBQU8sSUFBSTtBQUNYLFVBQUksTUFBcUI7QUFDekIsYUFBTyxFQUFFLE1BQU0sS0FBSyxJQUFHLENBQUU7QUFBSSxlQUFNO0FBQ25DLFlBQUs7QUFDTCxhQUFPO0lBQ1Q7QUFDQSxXQUFPO0VBQ1Q7QUFFTSxXQUFVLGVBQ2QsUUFDQSxTQUFpQyxDQUFBLEdBQ2pDLFlBQW9DLENBQUEsR0FBRTtBQUV0QyxRQUFJLENBQUMsVUFBVSxPQUFPLFdBQVc7QUFBVSxZQUFNLElBQUksTUFBTSwrQkFBK0I7QUFFMUYsYUFBUyxXQUFXLFdBQWlCLGNBQXNCLE9BQWM7QUFDdkUsWUFBTSxNQUFNLE9BQU8sU0FBUztBQUM1QixVQUFJLFNBQVMsUUFBUTtBQUFXO0FBQ2hDLFlBQU0sVUFBVSxPQUFPO0FBQ3ZCLFVBQUksWUFBWSxnQkFBZ0IsUUFBUTtBQUN0QyxjQUFNLElBQUksTUFBTSxVQUFVLFNBQVMsMEJBQTBCLFlBQVksU0FBUyxPQUFPLEVBQUU7SUFDL0Y7QUFDQSxVQUFNLE9BQU8sQ0FBQyxHQUFrQixVQUM5QixPQUFPLFFBQVEsQ0FBQyxFQUFFLFFBQVEsQ0FBQyxDQUFDLEdBQUcsQ0FBQyxNQUFNLFdBQVcsR0FBRyxHQUFHLEtBQUssQ0FBQztBQUMvRCxTQUFLLFFBQVEsS0FBSztBQUNsQixTQUFLLFdBQVcsSUFBSTtFQUN0QjtBQWFNLFdBQVUsU0FDZCxJQUE2QjtBQUU3QixVQUFNLE1BQU0sb0JBQUksUUFBTztBQUN2QixXQUFPLENBQUMsUUFBVyxTQUFjO0FBQy9CLFlBQU0sTUFBTSxJQUFJLElBQUksR0FBRztBQUN2QixVQUFJLFFBQVE7QUFBVyxlQUFPO0FBQzlCLFlBQU0sV0FBVyxHQUFHLEtBQUssR0FBRyxJQUFJO0FBQ2hDLFVBQUksSUFBSSxLQUFLLFFBQVE7QUFDckIsYUFBTztJQUNUO0VBQ0Y7OztBQzdSQTtBQW1CQSxNQUFNQyxPQUFzQix1QkFBTyxDQUFDO0FBQXBDLE1BQXVDQyxPQUFzQix1QkFBTyxDQUFDO0FBQXJFLE1BQXdFLE1BQXNCLHVCQUFPLENBQUM7QUFFdEcsTUFBTSxNQUFzQix1QkFBTyxDQUFDO0FBQXBDLE1BQXVDLE1BQXNCLHVCQUFPLENBQUM7QUFBckUsTUFBd0UsTUFBc0IsdUJBQU8sQ0FBQztBQUV0RyxNQUFNLE1BQXNCLHVCQUFPLENBQUM7QUFBcEMsTUFBdUMsTUFBc0IsdUJBQU8sQ0FBQztBQUFyRSxNQUF3RSxNQUFzQix1QkFBTyxDQUFDO0FBQ3RHLE1BQU0sT0FBdUIsdUJBQU8sRUFBRTtBQUdoQyxXQUFVLElBQUksR0FBVyxHQUFTO0FBQ3RDLFVBQU0sU0FBUyxJQUFJO0FBQ25CLFdBQU8sVUFBVUQsT0FBTSxTQUFTLElBQUk7RUFDdEM7QUFZTSxXQUFVLEtBQUssR0FBVyxPQUFlLFFBQWM7QUFDM0QsUUFBSSxNQUFNO0FBQ1YsV0FBTyxVQUFVRSxNQUFLO0FBQ3BCLGFBQU87QUFDUCxhQUFPO0lBQ1Q7QUFDQSxXQUFPO0VBQ1Q7QUFNTSxXQUFVLE9BQU8sUUFBZ0IsUUFBYztBQUNuRCxRQUFJLFdBQVdBO0FBQUssWUFBTSxJQUFJLE1BQU0sa0NBQWtDO0FBQ3RFLFFBQUksVUFBVUE7QUFBSyxZQUFNLElBQUksTUFBTSw0Q0FBNEMsTUFBTTtBQUVyRixRQUFJLElBQUksSUFBSSxRQUFRLE1BQU07QUFDMUIsUUFBSSxJQUFJO0FBRVIsUUFBSSxJQUFJQSxNQUFLLElBQUlDLE1BQUssSUFBSUEsTUFBSyxJQUFJRDtBQUNuQyxXQUFPLE1BQU1BLE1BQUs7QUFFaEIsWUFBTSxJQUFJLElBQUk7QUFDZCxZQUFNLElBQUksSUFBSTtBQUNkLFlBQU0sSUFBSSxJQUFJLElBQUk7QUFDbEIsWUFBTSxJQUFJLElBQUksSUFBSTtBQUVsQixVQUFJLEdBQUcsSUFBSSxHQUFHLElBQUksR0FBRyxJQUFJLEdBQUcsSUFBSSxHQUFHLElBQUk7SUFDekM7QUFDQSxVQUFNRSxPQUFNO0FBQ1osUUFBSUEsU0FBUUQ7QUFBSyxZQUFNLElBQUksTUFBTSx3QkFBd0I7QUFDekQsV0FBTyxJQUFJLEdBQUcsTUFBTTtFQUN0QjtBQUVBLFdBQVMsZUFBa0IsSUFBZSxNQUFTLEdBQUk7QUFDckQsUUFBSSxDQUFDLEdBQUcsSUFBSSxHQUFHLElBQUksSUFBSSxHQUFHLENBQUM7QUFBRyxZQUFNLElBQUksTUFBTSx5QkFBeUI7RUFDekU7QUFNQSxXQUFTLFVBQWEsSUFBZSxHQUFJO0FBQ3ZDLFVBQU0sVUFBVSxHQUFHLFFBQVFBLFFBQU87QUFDbEMsVUFBTSxPQUFPLEdBQUcsSUFBSSxHQUFHLE1BQU07QUFDN0IsbUJBQWUsSUFBSSxNQUFNLENBQUM7QUFDMUIsV0FBTztFQUNUO0FBRUEsV0FBUyxVQUFhLElBQWUsR0FBSTtBQUN2QyxVQUFNLFVBQVUsR0FBRyxRQUFRLE9BQU87QUFDbEMsVUFBTSxLQUFLLEdBQUcsSUFBSSxHQUFHLEdBQUc7QUFDeEIsVUFBTSxJQUFJLEdBQUcsSUFBSSxJQUFJLE1BQU07QUFDM0IsVUFBTSxLQUFLLEdBQUcsSUFBSSxHQUFHLENBQUM7QUFDdEIsVUFBTSxJQUFJLEdBQUcsSUFBSSxHQUFHLElBQUksSUFBSSxHQUFHLEdBQUcsQ0FBQztBQUNuQyxVQUFNLE9BQU8sR0FBRyxJQUFJLElBQUksR0FBRyxJQUFJLEdBQUcsR0FBRyxHQUFHLENBQUM7QUFDekMsbUJBQWUsSUFBSSxNQUFNLENBQUM7QUFDMUIsV0FBTztFQUNUO0FBSUEsV0FBUyxXQUFXLEdBQVM7QUFDM0IsVUFBTSxNQUFNLE1BQU0sQ0FBQztBQUNuQixVQUFNLEtBQUssY0FBYyxDQUFDO0FBQzFCLFVBQU0sS0FBSyxHQUFHLEtBQUssSUFBSSxJQUFJLElBQUksR0FBRyxDQUFDO0FBQ25DLFVBQU0sS0FBSyxHQUFHLEtBQUssRUFBRTtBQUNyQixVQUFNLEtBQUssR0FBRyxLQUFLLElBQUksSUFBSSxFQUFFLENBQUM7QUFDOUIsVUFBTSxNQUFNLElBQUksT0FBTztBQUN2QixXQUFPLENBQUksSUFBZSxNQUFRO0FBQ2hDLFVBQUksTUFBTSxHQUFHLElBQUksR0FBRyxFQUFFO0FBQ3RCLFVBQUksTUFBTSxHQUFHLElBQUksS0FBSyxFQUFFO0FBQ3hCLFlBQU0sTUFBTSxHQUFHLElBQUksS0FBSyxFQUFFO0FBQzFCLFlBQU0sTUFBTSxHQUFHLElBQUksS0FBSyxFQUFFO0FBQzFCLFlBQU0sS0FBSyxHQUFHLElBQUksR0FBRyxJQUFJLEdBQUcsR0FBRyxDQUFDO0FBQ2hDLFlBQU0sS0FBSyxHQUFHLElBQUksR0FBRyxJQUFJLEdBQUcsR0FBRyxDQUFDO0FBQ2hDLFlBQU0sR0FBRyxLQUFLLEtBQUssS0FBSyxFQUFFO0FBQzFCLFlBQU0sR0FBRyxLQUFLLEtBQUssS0FBSyxFQUFFO0FBQzFCLFlBQU0sS0FBSyxHQUFHLElBQUksR0FBRyxJQUFJLEdBQUcsR0FBRyxDQUFDO0FBQ2hDLFlBQU0sT0FBTyxHQUFHLEtBQUssS0FBSyxLQUFLLEVBQUU7QUFDakMscUJBQWUsSUFBSSxNQUFNLENBQUM7QUFDMUIsYUFBTztJQUNUO0VBQ0Y7QUFTTSxXQUFVLGNBQWMsR0FBUztBQUdyQyxRQUFJLElBQUk7QUFBSyxZQUFNLElBQUksTUFBTSxxQ0FBcUM7QUFFbEUsUUFBSSxJQUFJLElBQUlBO0FBQ1osUUFBSSxJQUFJO0FBQ1IsV0FBTyxJQUFJLFFBQVFELE1BQUs7QUFDdEIsV0FBSztBQUNMO0lBQ0Y7QUFHQSxRQUFJLElBQUk7QUFDUixVQUFNLE1BQU0sTUFBTSxDQUFDO0FBQ25CLFdBQU8sV0FBVyxLQUFLLENBQUMsTUFBTSxHQUFHO0FBRy9CLFVBQUksTUFBTTtBQUFNLGNBQU0sSUFBSSxNQUFNLCtDQUErQztJQUNqRjtBQUVBLFFBQUksTUFBTTtBQUFHLGFBQU87QUFJcEIsUUFBSSxLQUFLLElBQUksSUFBSSxHQUFHLENBQUM7QUFDckIsVUFBTSxVQUFVLElBQUlDLFFBQU87QUFDM0IsV0FBTyxTQUFTLFlBQWUsSUFBZSxHQUFJO0FBQ2hELFVBQUksR0FBRyxJQUFJLENBQUM7QUFBRyxlQUFPO0FBRXRCLFVBQUksV0FBVyxJQUFJLENBQUMsTUFBTTtBQUFHLGNBQU0sSUFBSSxNQUFNLHlCQUF5QjtBQUd0RSxVQUFJLElBQUk7QUFDUixVQUFJLElBQUksR0FBRyxJQUFJLEdBQUcsS0FBSyxFQUFFO0FBQ3pCLFVBQUksSUFBSSxHQUFHLElBQUksR0FBRyxDQUFDO0FBQ25CLFVBQUksSUFBSSxHQUFHLElBQUksR0FBRyxNQUFNO0FBSXhCLGFBQU8sQ0FBQyxHQUFHLElBQUksR0FBRyxHQUFHLEdBQUcsR0FBRztBQUN6QixZQUFJLEdBQUcsSUFBSSxDQUFDO0FBQUcsaUJBQU8sR0FBRztBQUN6QixZQUFJLElBQUk7QUFHUixZQUFJLFFBQVEsR0FBRyxJQUFJLENBQUM7QUFDcEIsZUFBTyxDQUFDLEdBQUcsSUFBSSxPQUFPLEdBQUcsR0FBRyxHQUFHO0FBQzdCO0FBQ0Esa0JBQVEsR0FBRyxJQUFJLEtBQUs7QUFDcEIsY0FBSSxNQUFNO0FBQUcsa0JBQU0sSUFBSSxNQUFNLHlCQUF5QjtRQUN4RDtBQUdBLGNBQU0sV0FBV0EsUUFBTyxPQUFPLElBQUksSUFBSSxDQUFDO0FBQ3hDLGNBQU0sSUFBSSxHQUFHLElBQUksR0FBRyxRQUFRO0FBRzVCLFlBQUk7QUFDSixZQUFJLEdBQUcsSUFBSSxDQUFDO0FBQ1osWUFBSSxHQUFHLElBQUksR0FBRyxDQUFDO0FBQ2YsWUFBSSxHQUFHLElBQUksR0FBRyxDQUFDO01BQ2pCO0FBQ0EsYUFBTztJQUNUO0VBQ0Y7QUFhTSxXQUFVLE9BQU8sR0FBUztBQUU5QixRQUFJLElBQUksUUFBUTtBQUFLLGFBQU87QUFFNUIsUUFBSSxJQUFJLFFBQVE7QUFBSyxhQUFPO0FBRTVCLFFBQUksSUFBSSxTQUFTO0FBQUssYUFBTyxXQUFXLENBQUM7QUFFekMsV0FBTyxjQUFjLENBQUM7RUFDeEI7QUFpREEsTUFBTSxlQUFlO0lBQ25CO0lBQVU7SUFBVztJQUFPO0lBQU87SUFBTztJQUFRO0lBQ2xEO0lBQU87SUFBTztJQUFPO0lBQU87SUFBTztJQUNuQztJQUFRO0lBQVE7SUFBUTs7QUFFcEIsV0FBVSxjQUFpQixPQUFnQjtBQUMvQyxVQUFNLFVBQVU7TUFDZCxPQUFPO01BQ1AsT0FBTztNQUNQLE1BQU07O0FBRVIsVUFBTSxPQUFPLGFBQWEsT0FBTyxDQUFDLEtBQUssUUFBZTtBQUNwRCxVQUFJLEdBQUcsSUFBSTtBQUNYLGFBQU87SUFDVCxHQUFHLE9BQU87QUFDVixtQkFBZSxPQUFPLElBQUk7QUFJMUIsV0FBTztFQUNUO0FBUU0sV0FBVSxNQUFTLElBQWVFLE1BQVEsT0FBYTtBQUMzRCxRQUFJLFFBQVFDO0FBQUssWUFBTSxJQUFJLE1BQU0seUNBQXlDO0FBQzFFLFFBQUksVUFBVUE7QUFBSyxhQUFPLEdBQUc7QUFDN0IsUUFBSSxVQUFVQztBQUFLLGFBQU9GO0FBQzFCLFFBQUksSUFBSSxHQUFHO0FBQ1gsUUFBSSxJQUFJQTtBQUNSLFdBQU8sUUFBUUMsTUFBSztBQUNsQixVQUFJLFFBQVFDO0FBQUssWUFBSSxHQUFHLElBQUksR0FBRyxDQUFDO0FBQ2hDLFVBQUksR0FBRyxJQUFJLENBQUM7QUFDWixnQkFBVUE7SUFDWjtBQUNBLFdBQU87RUFDVDtBQU9NLFdBQVUsY0FBaUIsSUFBZSxNQUFXLFdBQVcsT0FBSztBQUN6RSxVQUFNLFdBQVcsSUFBSSxNQUFNLEtBQUssTUFBTSxFQUFFLEtBQUssV0FBVyxHQUFHLE9BQU8sTUFBUztBQUUzRSxVQUFNLGdCQUFnQixLQUFLLE9BQU8sQ0FBQyxLQUFLRixNQUFLLE1BQUs7QUFDaEQsVUFBSSxHQUFHLElBQUlBLElBQUc7QUFBRyxlQUFPO0FBQ3hCLGVBQVMsQ0FBQyxJQUFJO0FBQ2QsYUFBTyxHQUFHLElBQUksS0FBS0EsSUFBRztJQUN4QixHQUFHLEdBQUcsR0FBRztBQUVULFVBQU0sY0FBYyxHQUFHLElBQUksYUFBYTtBQUV4QyxTQUFLLFlBQVksQ0FBQyxLQUFLQSxNQUFLLE1BQUs7QUFDL0IsVUFBSSxHQUFHLElBQUlBLElBQUc7QUFBRyxlQUFPO0FBQ3hCLGVBQVMsQ0FBQyxJQUFJLEdBQUcsSUFBSSxLQUFLLFNBQVMsQ0FBQyxDQUFDO0FBQ3JDLGFBQU8sR0FBRyxJQUFJLEtBQUtBLElBQUc7SUFDeEIsR0FBRyxXQUFXO0FBQ2QsV0FBTztFQUNUO0FBZ0JNLFdBQVUsV0FBYyxJQUFlLEdBQUk7QUFHL0MsVUFBTSxVQUFVLEdBQUcsUUFBUUcsUUFBTztBQUNsQyxVQUFNLFVBQVUsR0FBRyxJQUFJLEdBQUcsTUFBTTtBQUNoQyxVQUFNLE1BQU0sR0FBRyxJQUFJLFNBQVMsR0FBRyxHQUFHO0FBQ2xDLFVBQU0sT0FBTyxHQUFHLElBQUksU0FBUyxHQUFHLElBQUk7QUFDcEMsVUFBTSxLQUFLLEdBQUcsSUFBSSxTQUFTLEdBQUcsSUFBSSxHQUFHLEdBQUcsQ0FBQztBQUN6QyxRQUFJLENBQUMsT0FBTyxDQUFDLFFBQVEsQ0FBQztBQUFJLFlBQU0sSUFBSSxNQUFNLGdDQUFnQztBQUMxRSxXQUFPLE1BQU0sSUFBSSxPQUFPLElBQUk7RUFDOUI7QUFVTSxXQUFVLFFBQVEsR0FBVyxZQUFtQjtBQUVwRCxRQUFJLGVBQWU7QUFBVyxjQUFRLFVBQVU7QUFDaEQsVUFBTSxjQUFjLGVBQWUsU0FBWSxhQUFhLEVBQUUsU0FBUyxDQUFDLEVBQUU7QUFDMUUsVUFBTSxjQUFjLEtBQUssS0FBSyxjQUFjLENBQUM7QUFDN0MsV0FBTyxFQUFFLFlBQVksYUFBYSxZQUFXO0VBQy9DO0FBV0EsTUFBTSxTQUFOLE1BQVk7SUFDRDtJQUNBO0lBQ0E7SUFDQTtJQUNBLE9BQU9DO0lBQ1AsTUFBTUM7SUFDTjtJQUNEOztJQUNTO0lBQ2pCLFlBQVksT0FBZSxPQUFrQixDQUFBLEdBQUU7QUFDN0MsVUFBSSxTQUFTRDtBQUFLLGNBQU0sSUFBSSxNQUFNLDRDQUE0QyxLQUFLO0FBQ25GLFVBQUksY0FBa0M7QUFDdEMsV0FBSyxPQUFPO0FBQ1osVUFBSSxRQUFRLFFBQVEsT0FBTyxTQUFTLFVBQVU7QUFDNUMsWUFBSSxPQUFPLEtBQUssU0FBUztBQUFVLHdCQUFjLEtBQUs7QUFDdEQsWUFBSSxPQUFPLEtBQUssU0FBUztBQUFZLGVBQUssT0FBTyxLQUFLO0FBQ3RELFlBQUksT0FBTyxLQUFLLFNBQVM7QUFBVyxlQUFLLE9BQU8sS0FBSztBQUNyRCxZQUFJLEtBQUs7QUFBZ0IsZUFBSyxXQUFXLEtBQUssZ0JBQWdCLE1BQUs7QUFDbkUsWUFBSSxPQUFPLEtBQUssaUJBQWlCO0FBQVcsZUFBSyxPQUFPLEtBQUs7TUFDL0Q7QUFDQSxZQUFNLEVBQUUsWUFBWSxZQUFXLElBQUssUUFBUSxPQUFPLFdBQVc7QUFDOUQsVUFBSSxjQUFjO0FBQU0sY0FBTSxJQUFJLE1BQU0sZ0RBQWdEO0FBQ3hGLFdBQUssUUFBUTtBQUNiLFdBQUssT0FBTztBQUNaLFdBQUssUUFBUTtBQUNiLFdBQUssUUFBUTtBQUNiLGFBQU8sa0JBQWtCLElBQUk7SUFDL0I7SUFFQSxPQUFPRSxNQUFXO0FBQ2hCLGFBQU8sSUFBSUEsTUFBSyxLQUFLLEtBQUs7SUFDNUI7SUFDQSxRQUFRQSxNQUFXO0FBQ2pCLFVBQUksT0FBT0EsU0FBUTtBQUNqQixjQUFNLElBQUksTUFBTSxpREFBaUQsT0FBT0EsSUFBRztBQUM3RSxhQUFPRixRQUFPRSxRQUFPQSxPQUFNLEtBQUs7SUFDbEM7SUFDQSxJQUFJQSxNQUFXO0FBQ2IsYUFBT0EsU0FBUUY7SUFDakI7O0lBRUEsWUFBWUUsTUFBVztBQUNyQixhQUFPLENBQUMsS0FBSyxJQUFJQSxJQUFHLEtBQUssS0FBSyxRQUFRQSxJQUFHO0lBQzNDO0lBQ0EsTUFBTUEsTUFBVztBQUNmLGNBQVFBLE9BQU1ELFVBQVNBO0lBQ3pCO0lBQ0EsSUFBSUMsTUFBVztBQUNiLGFBQU8sSUFBSSxDQUFDQSxNQUFLLEtBQUssS0FBSztJQUM3QjtJQUNBLElBQUksS0FBYSxLQUFXO0FBQzFCLGFBQU8sUUFBUTtJQUNqQjtJQUVBLElBQUlBLE1BQVc7QUFDYixhQUFPLElBQUlBLE9BQU1BLE1BQUssS0FBSyxLQUFLO0lBQ2xDO0lBQ0EsSUFBSSxLQUFhLEtBQVc7QUFDMUIsYUFBTyxJQUFJLE1BQU0sS0FBSyxLQUFLLEtBQUs7SUFDbEM7SUFDQSxJQUFJLEtBQWEsS0FBVztBQUMxQixhQUFPLElBQUksTUFBTSxLQUFLLEtBQUssS0FBSztJQUNsQztJQUNBLElBQUksS0FBYSxLQUFXO0FBQzFCLGFBQU8sSUFBSSxNQUFNLEtBQUssS0FBSyxLQUFLO0lBQ2xDO0lBQ0EsSUFBSUEsTUFBYSxPQUFhO0FBQzVCLGFBQU8sTUFBTSxNQUFNQSxNQUFLLEtBQUs7SUFDL0I7SUFDQSxJQUFJLEtBQWEsS0FBVztBQUMxQixhQUFPLElBQUksTUFBTSxPQUFPLEtBQUssS0FBSyxLQUFLLEdBQUcsS0FBSyxLQUFLO0lBQ3REOztJQUdBLEtBQUtBLE1BQVc7QUFDZCxhQUFPQSxPQUFNQTtJQUNmO0lBQ0EsS0FBSyxLQUFhLEtBQVc7QUFDM0IsYUFBTyxNQUFNO0lBQ2Y7SUFDQSxLQUFLLEtBQWEsS0FBVztBQUMzQixhQUFPLE1BQU07SUFDZjtJQUNBLEtBQUssS0FBYSxLQUFXO0FBQzNCLGFBQU8sTUFBTTtJQUNmO0lBRUEsSUFBSUEsTUFBVztBQUNiLGFBQU8sT0FBT0EsTUFBSyxLQUFLLEtBQUs7SUFDL0I7SUFDQSxLQUFLQSxNQUFXO0FBRWQsVUFBSSxDQUFDLEtBQUs7QUFBTyxhQUFLLFFBQVEsT0FBTyxLQUFLLEtBQUs7QUFDL0MsYUFBTyxLQUFLLE1BQU0sTUFBTUEsSUFBRztJQUM3QjtJQUNBLFFBQVFBLE1BQVc7QUFDakIsYUFBTyxLQUFLLE9BQU8sZ0JBQWdCQSxNQUFLLEtBQUssS0FBSyxJQUFJLGdCQUFnQkEsTUFBSyxLQUFLLEtBQUs7SUFDdkY7SUFDQSxVQUFVLE9BQW1CLGlCQUFpQixPQUFLO0FBQ2pELGFBQU8sS0FBSztBQUNaLFlBQU0sRUFBRSxVQUFVLGdCQUFnQixPQUFPLE1BQUFDLE9BQU0sT0FBTyxNQUFNLGFBQVksSUFBSztBQUM3RSxVQUFJLGdCQUFnQjtBQUNsQixZQUFJLENBQUMsZUFBZSxTQUFTLE1BQU0sTUFBTSxLQUFLLE1BQU0sU0FBUyxPQUFPO0FBQ2xFLGdCQUFNLElBQUksTUFDUiwrQkFBK0IsaUJBQWlCLGlCQUFpQixNQUFNLE1BQU07UUFFakY7QUFDQSxjQUFNLFNBQVMsSUFBSSxXQUFXLEtBQUs7QUFFbkMsZUFBTyxJQUFJLE9BQU9BLFFBQU8sSUFBSSxPQUFPLFNBQVMsTUFBTSxNQUFNO0FBQ3pELGdCQUFRO01BQ1Y7QUFDQSxVQUFJLE1BQU0sV0FBVztBQUNuQixjQUFNLElBQUksTUFBTSwrQkFBK0IsUUFBUSxpQkFBaUIsTUFBTSxNQUFNO0FBQ3RGLFVBQUksU0FBU0EsUUFBTyxnQkFBZ0IsS0FBSyxJQUFJLGdCQUFnQixLQUFLO0FBQ2xFLFVBQUk7QUFBYyxpQkFBUyxJQUFJLFFBQVEsS0FBSztBQUM1QyxVQUFJLENBQUM7QUFDSCxZQUFJLENBQUMsS0FBSyxRQUFRLE1BQU07QUFDdEIsZ0JBQU0sSUFBSSxNQUFNLGtEQUFrRDs7QUFHdEUsYUFBTztJQUNUOztJQUVBLFlBQVksS0FBYTtBQUN2QixhQUFPLGNBQWMsTUFBTSxHQUFHO0lBQ2hDOzs7SUFHQSxLQUFLLEdBQVcsR0FBVyxXQUFrQjtBQUMzQyxhQUFPLFlBQVksSUFBSTtJQUN6Qjs7QUFzQkksV0FBVSxNQUFNLE9BQWUsT0FBa0IsQ0FBQSxHQUFFO0FBQ3ZELFdBQU8sSUFBSSxPQUFPLE9BQU8sSUFBSTtFQUMvQjtBQWtDTSxXQUFVLG9CQUFvQixZQUFrQjtBQUNwRCxRQUFJLE9BQU8sZUFBZTtBQUFVLFlBQU0sSUFBSSxNQUFNLDRCQUE0QjtBQUNoRixVQUFNLFlBQVksV0FBVyxTQUFTLENBQUMsRUFBRTtBQUN6QyxXQUFPLEtBQUssS0FBSyxZQUFZLENBQUM7RUFDaEM7QUFTTSxXQUFVLGlCQUFpQixZQUFrQjtBQUNqRCxVQUFNLFNBQVMsb0JBQW9CLFVBQVU7QUFDN0MsV0FBTyxTQUFTLEtBQUssS0FBSyxTQUFTLENBQUM7RUFDdEM7QUFlTSxXQUFVLGVBQWUsS0FBaUIsWUFBb0JDLFFBQU8sT0FBSztBQUM5RSxXQUFPLEdBQUc7QUFDVixVQUFNLE1BQU0sSUFBSTtBQUNoQixVQUFNLFdBQVcsb0JBQW9CLFVBQVU7QUFDL0MsVUFBTSxTQUFTLGlCQUFpQixVQUFVO0FBRTFDLFFBQUksTUFBTSxNQUFNLE1BQU0sVUFBVSxNQUFNO0FBQ3BDLFlBQU0sSUFBSSxNQUFNLGNBQWMsU0FBUywrQkFBK0IsR0FBRztBQUMzRSxVQUFNQyxPQUFNRCxRQUFPLGdCQUFnQixHQUFHLElBQUksZ0JBQWdCLEdBQUc7QUFFN0QsVUFBTSxVQUFVLElBQUlDLE1BQUssYUFBYUMsSUFBRyxJQUFJQTtBQUM3QyxXQUFPRixRQUFPLGdCQUFnQixTQUFTLFFBQVEsSUFBSSxnQkFBZ0IsU0FBUyxRQUFRO0VBQ3RGOzs7QUZubUJBLE1BQU1HLE9BQXNCLHVCQUFPLENBQUM7QUFDcEMsTUFBTUMsT0FBc0IsdUJBQU8sQ0FBQztBQXFIOUIsV0FBVSxTQUF3QyxXQUFvQixNQUFPO0FBQ2pGLFVBQU0sTUFBTSxLQUFLLE9BQU07QUFDdkIsV0FBTyxZQUFZLE1BQU07RUFDM0I7QUFRTSxXQUFVLFdBQ2QsR0FDQSxRQUFXO0FBRVgsVUFBTSxhQUFhLGNBQ2pCLEVBQUUsSUFDRixPQUFPLElBQUksQ0FBQyxNQUFNLEVBQUUsQ0FBRSxDQUFDO0FBRXpCLFdBQU8sT0FBTyxJQUFJLENBQUMsR0FBRyxNQUFNLEVBQUUsV0FBVyxFQUFFLFNBQVMsV0FBVyxDQUFDLENBQUMsQ0FBQyxDQUFDO0VBQ3JFO0FBRUEsV0FBUyxVQUFVLEdBQVcsTUFBWTtBQUN4QyxRQUFJLENBQUMsT0FBTyxjQUFjLENBQUMsS0FBSyxLQUFLLEtBQUssSUFBSTtBQUM1QyxZQUFNLElBQUksTUFBTSx1Q0FBdUMsT0FBTyxjQUFjLENBQUM7RUFDakY7QUFXQSxXQUFTLFVBQVUsR0FBVyxZQUFrQjtBQUM5QyxjQUFVLEdBQUcsVUFBVTtBQUN2QixVQUFNLFVBQVUsS0FBSyxLQUFLLGFBQWEsQ0FBQyxJQUFJO0FBQzVDLFVBQU0sYUFBYSxNQUFNLElBQUk7QUFDN0IsVUFBTSxZQUFZLEtBQUs7QUFDdkIsVUFBTSxPQUFPLFFBQVEsQ0FBQztBQUN0QixVQUFNLFVBQVUsT0FBTyxDQUFDO0FBQ3hCLFdBQU8sRUFBRSxTQUFTLFlBQVksTUFBTSxXQUFXLFFBQU87RUFDeEQ7QUFFQSxXQUFTLFlBQVksR0FBV0MsU0FBZ0IsT0FBWTtBQUMxRCxVQUFNLEVBQUUsWUFBWSxNQUFNLFdBQVcsUUFBTyxJQUFLO0FBQ2pELFFBQUksUUFBUSxPQUFPLElBQUksSUFBSTtBQUMzQixRQUFJLFFBQVEsS0FBSztBQVFqQixRQUFJLFFBQVEsWUFBWTtBQUV0QixlQUFTO0FBQ1QsZUFBU0Q7SUFDWDtBQUNBLFVBQU0sY0FBY0MsVUFBUztBQUM3QixVQUFNLFNBQVMsY0FBYyxLQUFLLElBQUksS0FBSyxJQUFJO0FBQy9DLFVBQU0sU0FBUyxVQUFVO0FBQ3pCLFVBQU0sUUFBUSxRQUFRO0FBQ3RCLFVBQU0sU0FBU0EsVUFBUyxNQUFNO0FBQzlCLFVBQU0sVUFBVTtBQUNoQixXQUFPLEVBQUUsT0FBTyxRQUFRLFFBQVEsT0FBTyxRQUFRLFFBQU87RUFDeEQ7QUFrQkEsTUFBTSxtQkFBbUIsb0JBQUksUUFBTztBQUNwQyxNQUFNLG1CQUFtQixvQkFBSSxRQUFPO0FBRXBDLFdBQVMsS0FBSyxHQUFNO0FBR2xCLFdBQU8saUJBQWlCLElBQUksQ0FBQyxLQUFLO0VBQ3BDO0FBRUEsV0FBUyxRQUFRLEdBQVM7QUFDeEIsUUFBSSxNQUFNQztBQUFLLFlBQU0sSUFBSSxNQUFNLGNBQWM7RUFDL0M7QUFvQk0sTUFBTyxPQUFQLE1BQVc7SUFDRTtJQUNBO0lBQ0E7SUFDUjs7SUFHVCxZQUFZLE9BQVcsTUFBWTtBQUNqQyxXQUFLLE9BQU8sTUFBTTtBQUNsQixXQUFLLE9BQU8sTUFBTTtBQUNsQixXQUFLLEtBQUssTUFBTTtBQUNoQixXQUFLLE9BQU87SUFDZDs7SUFHQSxjQUFjLEtBQWUsR0FBVyxJQUFjLEtBQUssTUFBSTtBQUM3RCxVQUFJLElBQWM7QUFDbEIsYUFBTyxJQUFJQSxNQUFLO0FBQ2QsWUFBSSxJQUFJQztBQUFLLGNBQUksRUFBRSxJQUFJLENBQUM7QUFDeEIsWUFBSSxFQUFFLE9BQU07QUFDWixjQUFNQTtNQUNSO0FBQ0EsYUFBTztJQUNUOzs7Ozs7Ozs7Ozs7O0lBY1EsaUJBQWlCLE9BQWlCLEdBQVM7QUFDakQsWUFBTSxFQUFFLFNBQVMsV0FBVSxJQUFLLFVBQVUsR0FBRyxLQUFLLElBQUk7QUFDdEQsWUFBTSxTQUFxQixDQUFBO0FBQzNCLFVBQUksSUFBYztBQUNsQixVQUFJLE9BQU87QUFDWCxlQUFTQyxVQUFTLEdBQUdBLFVBQVMsU0FBU0EsV0FBVTtBQUMvQyxlQUFPO0FBQ1AsZUFBTyxLQUFLLElBQUk7QUFFaEIsaUJBQVMsSUFBSSxHQUFHLElBQUksWUFBWSxLQUFLO0FBQ25DLGlCQUFPLEtBQUssSUFBSSxDQUFDO0FBQ2pCLGlCQUFPLEtBQUssSUFBSTtRQUNsQjtBQUNBLFlBQUksS0FBSyxPQUFNO01BQ2pCO0FBQ0EsYUFBTztJQUNUOzs7Ozs7O0lBUVEsS0FBSyxHQUFXLGFBQXlCLEdBQVM7QUFFeEQsVUFBSSxDQUFDLEtBQUssR0FBRyxRQUFRLENBQUM7QUFBRyxjQUFNLElBQUksTUFBTSxnQkFBZ0I7QUFFekQsVUFBSSxJQUFJLEtBQUs7QUFDYixVQUFJLElBQUksS0FBSztBQU1iLFlBQU0sS0FBSyxVQUFVLEdBQUcsS0FBSyxJQUFJO0FBQ2pDLGVBQVNBLFVBQVMsR0FBR0EsVUFBUyxHQUFHLFNBQVNBLFdBQVU7QUFFbEQsY0FBTSxFQUFFLE9BQU8sUUFBUSxRQUFRLE9BQU8sUUFBUSxRQUFPLElBQUssWUFBWSxHQUFHQSxTQUFRLEVBQUU7QUFDbkYsWUFBSTtBQUNKLFlBQUksUUFBUTtBQUdWLGNBQUksRUFBRSxJQUFJLFNBQVMsUUFBUSxZQUFZLE9BQU8sQ0FBQyxDQUFDO1FBQ2xELE9BQU87QUFFTCxjQUFJLEVBQUUsSUFBSSxTQUFTLE9BQU8sWUFBWSxNQUFNLENBQUMsQ0FBQztRQUNoRDtNQUNGO0FBQ0EsY0FBUSxDQUFDO0FBSVQsYUFBTyxFQUFFLEdBQUcsRUFBQztJQUNmOzs7Ozs7SUFPUSxXQUNOLEdBQ0EsYUFDQSxHQUNBLE1BQWdCLEtBQUssTUFBSTtBQUV6QixZQUFNLEtBQUssVUFBVSxHQUFHLEtBQUssSUFBSTtBQUNqQyxlQUFTQSxVQUFTLEdBQUdBLFVBQVMsR0FBRyxTQUFTQSxXQUFVO0FBQ2xELFlBQUksTUFBTUY7QUFBSztBQUNmLGNBQU0sRUFBRSxPQUFPLFFBQVEsUUFBUSxNQUFLLElBQUssWUFBWSxHQUFHRSxTQUFRLEVBQUU7QUFDbEUsWUFBSTtBQUNKLFlBQUksUUFBUTtBQUdWO1FBQ0YsT0FBTztBQUNMLGdCQUFNLE9BQU8sWUFBWSxNQUFNO0FBQy9CLGdCQUFNLElBQUksSUFBSSxRQUFRLEtBQUssT0FBTSxJQUFLLElBQUk7UUFDNUM7TUFDRjtBQUNBLGNBQVEsQ0FBQztBQUNULGFBQU87SUFDVDtJQUVRLGVBQWUsR0FBVyxPQUFpQixXQUE0QjtBQUU3RSxVQUFJLE9BQU8saUJBQWlCLElBQUksS0FBSztBQUNyQyxVQUFJLENBQUMsTUFBTTtBQUNULGVBQU8sS0FBSyxpQkFBaUIsT0FBTyxDQUFDO0FBQ3JDLFlBQUksTUFBTSxHQUFHO0FBRVgsY0FBSSxPQUFPLGNBQWM7QUFBWSxtQkFBTyxVQUFVLElBQUk7QUFDMUQsMkJBQWlCLElBQUksT0FBTyxJQUFJO1FBQ2xDO01BQ0Y7QUFDQSxhQUFPO0lBQ1Q7SUFFQSxPQUNFLE9BQ0EsUUFDQSxXQUE0QjtBQUU1QixZQUFNLElBQUksS0FBSyxLQUFLO0FBQ3BCLGFBQU8sS0FBSyxLQUFLLEdBQUcsS0FBSyxlQUFlLEdBQUcsT0FBTyxTQUFTLEdBQUcsTUFBTTtJQUN0RTtJQUVBLE9BQU8sT0FBaUIsUUFBZ0IsV0FBOEIsTUFBZTtBQUNuRixZQUFNLElBQUksS0FBSyxLQUFLO0FBQ3BCLFVBQUksTUFBTTtBQUFHLGVBQU8sS0FBSyxjQUFjLE9BQU8sUUFBUSxJQUFJO0FBQzFELGFBQU8sS0FBSyxXQUFXLEdBQUcsS0FBSyxlQUFlLEdBQUcsT0FBTyxTQUFTLEdBQUcsUUFBUSxJQUFJO0lBQ2xGOzs7O0lBS0EsWUFBWSxHQUFhLEdBQVM7QUFDaEMsZ0JBQVUsR0FBRyxLQUFLLElBQUk7QUFDdEIsdUJBQWlCLElBQUksR0FBRyxDQUFDO0FBQ3pCLHVCQUFpQixPQUFPLENBQUM7SUFDM0I7SUFFQSxTQUFTLEtBQWE7QUFDcEIsYUFBTyxLQUFLLEdBQUcsTUFBTTtJQUN2Qjs7QUFPSSxXQUFVLGNBQ2QsT0FDQSxPQUNBLElBQ0EsSUFBVTtBQUVWLFFBQUksTUFBTTtBQUNWLFFBQUksS0FBSyxNQUFNO0FBQ2YsUUFBSSxLQUFLLE1BQU07QUFDZixXQUFPLEtBQUtGLFFBQU8sS0FBS0EsTUFBSztBQUMzQixVQUFJLEtBQUtDO0FBQUssYUFBSyxHQUFHLElBQUksR0FBRztBQUM3QixVQUFJLEtBQUtBO0FBQUssYUFBSyxHQUFHLElBQUksR0FBRztBQUM3QixZQUFNLElBQUksT0FBTTtBQUNoQixhQUFPQTtBQUNQLGFBQU9BO0lBQ1Q7QUFDQSxXQUFPLEVBQUUsSUFBSSxHQUFFO0VBQ2pCO0FBdUpBLFdBQVMsWUFBZSxPQUFlLE9BQW1CRSxPQUFjO0FBQ3RFLFFBQUksT0FBTztBQUNULFVBQUksTUFBTSxVQUFVO0FBQU8sY0FBTSxJQUFJLE1BQU0sZ0RBQWdEO0FBQzNGLG9CQUFjLEtBQUs7QUFDbkIsYUFBTztJQUNULE9BQU87QUFDTCxhQUFPLE1BQU0sT0FBTyxFQUFFLE1BQUFBLE1BQUksQ0FBRTtJQUM5QjtFQUNGO0FBSU0sV0FBVSxrQkFDZCxNQUNBLE9BQ0EsWUFBOEIsQ0FBQSxHQUM5QixRQUFnQjtBQUVoQixRQUFJLFdBQVc7QUFBVyxlQUFTLFNBQVM7QUFDNUMsUUFBSSxDQUFDLFNBQVMsT0FBTyxVQUFVO0FBQVUsWUFBTSxJQUFJLE1BQU0sa0JBQWtCLElBQUksZUFBZTtBQUM5RixlQUFXLEtBQUssQ0FBQyxLQUFLLEtBQUssR0FBRyxHQUFZO0FBQ3hDLFlBQU0sTUFBTSxNQUFNLENBQUM7QUFDbkIsVUFBSSxFQUFFLE9BQU8sUUFBUSxZQUFZLE1BQU1DO0FBQ3JDLGNBQU0sSUFBSSxNQUFNLFNBQVMsQ0FBQywwQkFBMEI7SUFDeEQ7QUFDQSxVQUFNLEtBQUssWUFBWSxNQUFNLEdBQUcsVUFBVSxJQUFJLE1BQU07QUFDcEQsVUFBTSxLQUFLLFlBQVksTUFBTSxHQUFHLFVBQVUsSUFBSSxNQUFNO0FBQ3BELFVBQU0sS0FBZ0IsU0FBUyxnQkFBZ0IsTUFBTTtBQUNyRCxVQUFNLFNBQVMsQ0FBQyxNQUFNLE1BQU0sS0FBSyxFQUFFO0FBQ25DLGVBQVcsS0FBSyxRQUFRO0FBRXRCLFVBQUksQ0FBQyxHQUFHLFFBQVEsTUFBTSxDQUFDLENBQUM7QUFDdEIsY0FBTSxJQUFJLE1BQU0sU0FBUyxDQUFDLDBDQUEwQztJQUN4RTtBQUNBLFlBQVEsT0FBTyxPQUFPLE9BQU8sT0FBTyxDQUFBLEdBQUksS0FBSyxDQUFDO0FBQzlDLFdBQU8sRUFBRSxPQUFPLElBQUksR0FBRTtFQUN4QjtBQU1NLFdBQVUsYUFDZCxpQkFDQUMsZUFBb0M7QUFFcEMsV0FBTyxTQUFTLE9BQU8sTUFBaUI7QUFDdEMsWUFBTSxZQUFZLGdCQUFnQixJQUFJO0FBQ3RDLGFBQU8sRUFBRSxXQUFXLFdBQVdBLGNBQWEsU0FBUyxFQUFDO0lBQ3hEO0VBQ0Y7OztBR3huQkE7OztBQ0FBO0FBT00sTUFBTyxRQUFQLE1BQVk7SUFDaEI7SUFDQTtJQUNBO0lBQ0E7SUFDUSxXQUFXO0lBQ1gsWUFBWTtJQUVwQixZQUFZLE1BQWEsS0FBZTtBQUN0QyxZQUFNLElBQUk7QUFDVixhQUFPLEtBQUssUUFBVyxLQUFLO0FBQzVCLFdBQUssUUFBUSxLQUFLLE9BQU07QUFDeEIsVUFBSSxPQUFPLEtBQUssTUFBTSxXQUFXO0FBQy9CLGNBQU0sSUFBSSxNQUFNLHFEQUFxRDtBQUN2RSxXQUFLLFdBQVcsS0FBSyxNQUFNO0FBQzNCLFdBQUssWUFBWSxLQUFLLE1BQU07QUFDNUIsWUFBTSxXQUFXLEtBQUs7QUFDdEIsWUFBTUMsT0FBTSxJQUFJLFdBQVcsUUFBUTtBQUVuQyxNQUFBQSxLQUFJLElBQUksSUFBSSxTQUFTLFdBQVcsS0FBSyxPQUFNLEVBQUcsT0FBTyxHQUFHLEVBQUUsT0FBTSxJQUFLLEdBQUc7QUFDeEUsZUFBUyxJQUFJLEdBQUcsSUFBSUEsS0FBSSxRQUFRO0FBQUssUUFBQUEsS0FBSSxDQUFDLEtBQUs7QUFDL0MsV0FBSyxNQUFNLE9BQU9BLElBQUc7QUFFckIsV0FBSyxRQUFRLEtBQUssT0FBTTtBQUV4QixlQUFTLElBQUksR0FBRyxJQUFJQSxLQUFJLFFBQVE7QUFBSyxRQUFBQSxLQUFJLENBQUMsS0FBSyxLQUFPO0FBQ3RELFdBQUssTUFBTSxPQUFPQSxJQUFHO0FBQ3JCLFlBQU1BLElBQUc7SUFDWDtJQUNBLE9BQU8sS0FBZTtBQUNwQixjQUFRLElBQUk7QUFDWixXQUFLLE1BQU0sT0FBTyxHQUFHO0FBQ3JCLGFBQU87SUFDVDtJQUNBLFdBQVcsS0FBZTtBQUN4QixjQUFRLElBQUk7QUFDWixhQUFPLEtBQUssS0FBSyxXQUFXLFFBQVE7QUFDcEMsV0FBSyxXQUFXO0FBQ2hCLFdBQUssTUFBTSxXQUFXLEdBQUc7QUFDekIsV0FBSyxNQUFNLE9BQU8sR0FBRztBQUNyQixXQUFLLE1BQU0sV0FBVyxHQUFHO0FBQ3pCLFdBQUssUUFBTztJQUNkO0lBQ0EsU0FBTTtBQUNKLFlBQU0sTUFBTSxJQUFJLFdBQVcsS0FBSyxNQUFNLFNBQVM7QUFDL0MsV0FBSyxXQUFXLEdBQUc7QUFDbkIsYUFBTztJQUNUO0lBQ0EsV0FBVyxJQUFhO0FBRXRCLGFBQU8sT0FBTyxPQUFPLE9BQU8sZUFBZSxJQUFJLEdBQUcsQ0FBQSxDQUFFO0FBQ3BELFlBQU0sRUFBRSxPQUFPLE9BQU8sVUFBVSxXQUFXLFVBQVUsVUFBUyxJQUFLO0FBQ25FLFdBQUs7QUFDTCxTQUFHLFdBQVc7QUFDZCxTQUFHLFlBQVk7QUFDZixTQUFHLFdBQVc7QUFDZCxTQUFHLFlBQVk7QUFDZixTQUFHLFFBQVEsTUFBTSxXQUFXLEdBQUcsS0FBSztBQUNwQyxTQUFHLFFBQVEsTUFBTSxXQUFXLEdBQUcsS0FBSztBQUNwQyxhQUFPO0lBQ1Q7SUFDQSxRQUFLO0FBQ0gsYUFBTyxLQUFLLFdBQVU7SUFDeEI7SUFDQSxVQUFPO0FBQ0wsV0FBSyxZQUFZO0FBQ2pCLFdBQUssTUFBTSxRQUFPO0FBQ2xCLFdBQUssTUFBTSxRQUFPO0lBQ3BCOztBQWFLLE1BQU0sT0FHVCxDQUFDLE1BQWEsS0FBaUIsWUFDakMsSUFBSSxNQUFXLE1BQU0sR0FBRyxFQUFFLE9BQU8sT0FBTyxFQUFFLE9BQU07QUFDbEQsT0FBSyxTQUFTLENBQUMsTUFBYSxRQUFvQixJQUFJLE1BQVcsTUFBTSxHQUFHOzs7QURPeEUsTUFBTSxhQUFhLENBQUNDLE1BQWEsU0FBaUJBLFFBQU9BLFFBQU8sSUFBSSxNQUFNLENBQUMsT0FBT0MsUUFBTztBQU9uRixXQUFVLGlCQUFpQixHQUFXLE9BQWtCLEdBQVM7QUFJckUsVUFBTSxDQUFDLENBQUMsSUFBSSxFQUFFLEdBQUcsQ0FBQyxJQUFJLEVBQUUsQ0FBQyxJQUFJO0FBQzdCLFVBQU0sS0FBSyxXQUFXLEtBQUssR0FBRyxDQUFDO0FBQy9CLFVBQU0sS0FBSyxXQUFXLENBQUMsS0FBSyxHQUFHLENBQUM7QUFHaEMsUUFBSSxLQUFLLElBQUksS0FBSyxLQUFLLEtBQUs7QUFDNUIsUUFBSSxLQUFLLENBQUMsS0FBSyxLQUFLLEtBQUs7QUFDekIsVUFBTSxRQUFRLEtBQUtDO0FBQ25CLFVBQU0sUUFBUSxLQUFLQTtBQUNuQixRQUFJO0FBQU8sV0FBSyxDQUFDO0FBQ2pCLFFBQUk7QUFBTyxXQUFLLENBQUM7QUFHakIsVUFBTSxVQUFVLFFBQVEsS0FBSyxLQUFLLE9BQU8sQ0FBQyxJQUFJLENBQUMsQ0FBQyxJQUFJQztBQUNwRCxRQUFJLEtBQUtELFFBQU8sTUFBTSxXQUFXLEtBQUtBLFFBQU8sTUFBTSxTQUFTO0FBQzFELFlBQU0sSUFBSSxNQUFNLDJDQUEyQyxDQUFDO0lBQzlEO0FBQ0EsV0FBTyxFQUFFLE9BQU8sSUFBSSxPQUFPLEdBQUU7RUFDL0I7QUErREEsV0FBUyxrQkFBa0IsUUFBYztBQUN2QyxRQUFJLENBQUMsQ0FBQyxXQUFXLGFBQWEsS0FBSyxFQUFFLFNBQVMsTUFBTTtBQUNsRCxZQUFNLElBQUksTUFBTSwyREFBMkQ7QUFDN0UsV0FBTztFQUNUO0FBRUEsV0FBUyxnQkFDUCxNQUNBLEtBQU07QUFFTixVQUFNLFFBQXVCLENBQUE7QUFDN0IsYUFBUyxXQUFXLE9BQU8sS0FBSyxHQUFHLEdBQUc7QUFFcEMsWUFBTSxPQUFPLElBQUksS0FBSyxPQUFPLE1BQU0sU0FBWSxJQUFJLE9BQU8sSUFBSSxLQUFLLE9BQU87SUFDNUU7QUFDQSxVQUFNLE1BQU0sTUFBTyxNQUFNO0FBQ3pCLFVBQU0sTUFBTSxTQUFVLFNBQVM7QUFDL0IsUUFBSSxNQUFNLFdBQVc7QUFBVyx3QkFBa0IsTUFBTSxNQUFNO0FBQzlELFdBQU87RUFDVDtBQXFITSxNQUFPLFNBQVAsY0FBc0IsTUFBSztJQUMvQixZQUFZLElBQUksSUFBRTtBQUNoQixZQUFNLENBQUM7SUFDVDs7QUE2QkssTUFBTSxNQUFZOztJQUV2QixLQUFLOztJQUVMLE1BQU07TUFDSixRQUFRLENBQUMsS0FBYSxTQUF3QjtBQUM1QyxjQUFNLEVBQUUsS0FBSyxFQUFDLElBQUs7QUFDbkIsWUFBSSxNQUFNLEtBQUssTUFBTTtBQUFLLGdCQUFNLElBQUksRUFBRSx1QkFBdUI7QUFDN0QsWUFBSSxLQUFLLFNBQVM7QUFBRyxnQkFBTSxJQUFJLEVBQUUsMkJBQTJCO0FBQzVELGNBQU0sVUFBVSxLQUFLLFNBQVM7QUFDOUIsY0FBTSxNQUFNLG9CQUFvQixPQUFPO0FBQ3ZDLFlBQUssSUFBSSxTQUFTLElBQUs7QUFBYSxnQkFBTSxJQUFJLEVBQUUsc0NBQXNDO0FBRXRGLGNBQU0sU0FBUyxVQUFVLE1BQU0sb0JBQXFCLElBQUksU0FBUyxJQUFLLEdBQVcsSUFBSTtBQUNyRixjQUFNLElBQUksb0JBQW9CLEdBQUc7QUFDakMsZUFBTyxJQUFJLFNBQVMsTUFBTTtNQUM1Qjs7TUFFQSxPQUFPLEtBQWEsTUFBZ0I7QUFDbEMsY0FBTSxFQUFFLEtBQUssRUFBQyxJQUFLO0FBQ25CLFlBQUksTUFBTTtBQUNWLFlBQUksTUFBTSxLQUFLLE1BQU07QUFBSyxnQkFBTSxJQUFJLEVBQUUsdUJBQXVCO0FBQzdELFlBQUksS0FBSyxTQUFTLEtBQUssS0FBSyxLQUFLLE1BQU07QUFBSyxnQkFBTSxJQUFJLEVBQUUsdUJBQXVCO0FBQy9FLGNBQU0sUUFBUSxLQUFLLEtBQUs7QUFDeEIsY0FBTSxTQUFTLENBQUMsRUFBRSxRQUFRO0FBQzFCLFlBQUksU0FBUztBQUNiLFlBQUksQ0FBQztBQUFRLG1CQUFTO2FBQ2pCO0FBRUgsZ0JBQU0sU0FBUyxRQUFRO0FBQ3ZCLGNBQUksQ0FBQztBQUFRLGtCQUFNLElBQUksRUFBRSxtREFBbUQ7QUFDNUUsY0FBSSxTQUFTO0FBQUcsa0JBQU0sSUFBSSxFQUFFLDBDQUEwQztBQUN0RSxnQkFBTSxjQUFjLEtBQUssU0FBUyxLQUFLLE1BQU0sTUFBTTtBQUNuRCxjQUFJLFlBQVksV0FBVztBQUFRLGtCQUFNLElBQUksRUFBRSx1Q0FBdUM7QUFDdEYsY0FBSSxZQUFZLENBQUMsTUFBTTtBQUFHLGtCQUFNLElBQUksRUFBRSxzQ0FBc0M7QUFDNUUscUJBQVcsS0FBSztBQUFhLHFCQUFVLFVBQVUsSUFBSztBQUN0RCxpQkFBTztBQUNQLGNBQUksU0FBUztBQUFLLGtCQUFNLElBQUksRUFBRSx3Q0FBd0M7UUFDeEU7QUFDQSxjQUFNLElBQUksS0FBSyxTQUFTLEtBQUssTUFBTSxNQUFNO0FBQ3pDLFlBQUksRUFBRSxXQUFXO0FBQVEsZ0JBQU0sSUFBSSxFQUFFLGdDQUFnQztBQUNyRSxlQUFPLEVBQUUsR0FBRyxHQUFHLEtBQUssU0FBUyxNQUFNLE1BQU0sRUFBQztNQUM1Qzs7Ozs7O0lBTUYsTUFBTTtNQUNKLE9BQU9GLE1BQVc7QUFDaEIsY0FBTSxFQUFFLEtBQUssRUFBQyxJQUFLO0FBQ25CLFlBQUlBLE9BQU1FO0FBQUssZ0JBQU0sSUFBSSxFQUFFLDRDQUE0QztBQUN2RSxZQUFJLE1BQU0sb0JBQW9CRixJQUFHO0FBRWpDLFlBQUksT0FBTyxTQUFTLElBQUksQ0FBQyxHQUFHLEVBQUUsSUFBSTtBQUFRLGdCQUFNLE9BQU87QUFDdkQsWUFBSSxJQUFJLFNBQVM7QUFBRyxnQkFBTSxJQUFJLEVBQUUsZ0RBQWdEO0FBQ2hGLGVBQU87TUFDVDtNQUNBLE9BQU8sTUFBZ0I7QUFDckIsY0FBTSxFQUFFLEtBQUssRUFBQyxJQUFLO0FBQ25CLFlBQUksS0FBSyxDQUFDLElBQUk7QUFBYSxnQkFBTSxJQUFJLEVBQUUscUNBQXFDO0FBQzVFLFlBQUksS0FBSyxDQUFDLE1BQU0sS0FBUSxFQUFFLEtBQUssQ0FBQyxJQUFJO0FBQ2xDLGdCQUFNLElBQUksRUFBRSxxREFBcUQ7QUFDbkUsZUFBTyxnQkFBZ0IsSUFBSTtNQUM3Qjs7SUFFRixNQUFNLE9BQWlCO0FBRXJCLFlBQU0sRUFBRSxLQUFLLEdBQUcsTUFBTSxLQUFLLE1BQU0sSUFBRyxJQUFLO0FBQ3pDLFlBQU0sT0FBTyxPQUFPLE9BQU8sUUFBVyxXQUFXO0FBQ2pELFlBQU0sRUFBRSxHQUFHLFVBQVUsR0FBRyxhQUFZLElBQUssSUFBSSxPQUFPLElBQU0sSUFBSTtBQUM5RCxVQUFJLGFBQWE7QUFBUSxjQUFNLElBQUksRUFBRSw2Q0FBNkM7QUFDbEYsWUFBTSxFQUFFLEdBQUcsUUFBUSxHQUFHLFdBQVUsSUFBSyxJQUFJLE9BQU8sR0FBTSxRQUFRO0FBQzlELFlBQU0sRUFBRSxHQUFHLFFBQVEsR0FBRyxXQUFVLElBQUssSUFBSSxPQUFPLEdBQU0sVUFBVTtBQUNoRSxVQUFJLFdBQVc7QUFBUSxjQUFNLElBQUksRUFBRSw2Q0FBNkM7QUFDaEYsYUFBTyxFQUFFLEdBQUcsSUFBSSxPQUFPLE1BQU0sR0FBRyxHQUFHLElBQUksT0FBTyxNQUFNLEVBQUM7SUFDdkQ7SUFDQSxXQUFXLEtBQTZCO0FBQ3RDLFlBQU0sRUFBRSxNQUFNLEtBQUssTUFBTSxJQUFHLElBQUs7QUFDakMsWUFBTSxLQUFLLElBQUksT0FBTyxHQUFNLElBQUksT0FBTyxJQUFJLENBQUMsQ0FBQztBQUM3QyxZQUFNLEtBQUssSUFBSSxPQUFPLEdBQU0sSUFBSSxPQUFPLElBQUksQ0FBQyxDQUFDO0FBQzdDLFlBQU0sTUFBTSxLQUFLO0FBQ2pCLGFBQU8sSUFBSSxPQUFPLElBQU0sR0FBRztJQUM3Qjs7QUFLRixNQUFNRSxPQUFNLE9BQU8sQ0FBQztBQUFwQixNQUF1QkMsT0FBTSxPQUFPLENBQUM7QUFBckMsTUFBd0NGLE9BQU0sT0FBTyxDQUFDO0FBQXRELE1BQXlERyxPQUFNLE9BQU8sQ0FBQztBQUF2RSxNQUEwRUMsT0FBTSxPQUFPLENBQUM7QUFxQmxGLFdBQVUsWUFDZCxRQUNBLFlBQXFDLENBQUEsR0FBRTtBQUV2QyxVQUFNLFlBQVksa0JBQWtCLGVBQWUsUUFBUSxTQUFTO0FBQ3BFLFVBQU0sRUFBRSxJQUFJLEdBQUUsSUFBSztBQUNuQixRQUFJLFFBQVEsVUFBVTtBQUN0QixVQUFNLEVBQUUsR0FBRyxVQUFVLEdBQUcsWUFBVyxJQUFLO0FBQ3hDLG1CQUNFLFdBQ0EsQ0FBQSxHQUNBO01BQ0Usb0JBQW9CO01BQ3BCLGVBQWU7TUFDZixlQUFlO01BQ2YsV0FBVztNQUNYLFNBQVM7TUFDVCxNQUFNO0tBQ1A7QUFHSCxVQUFNLEVBQUUsS0FBSSxJQUFLO0FBQ2pCLFFBQUksTUFBTTtBQUVSLFVBQUksQ0FBQyxHQUFHLElBQUksTUFBTSxDQUFDLEtBQUssT0FBTyxLQUFLLFNBQVMsWUFBWSxDQUFDLE1BQU0sUUFBUSxLQUFLLE9BQU8sR0FBRztBQUNyRixjQUFNLElBQUksTUFBTSw0REFBNEQ7TUFDOUU7SUFDRjtBQUVBLFVBQU0sVUFBVSxZQUFZLElBQUksRUFBRTtBQUVsQyxhQUFTLCtCQUE0QjtBQUNuQyxVQUFJLENBQUMsR0FBRztBQUFPLGNBQU0sSUFBSSxNQUFNLDREQUE0RDtJQUM3RjtBQUdBLGFBQVNDLGNBQ1AsSUFDQSxPQUNBLGNBQXFCO0FBRXJCLFlBQU0sRUFBRSxHQUFHLEVBQUMsSUFBSyxNQUFNLFNBQVE7QUFDL0IsWUFBTSxLQUFLLEdBQUcsUUFBUSxDQUFDO0FBQ3ZCLFlBQU0sY0FBYyxjQUFjO0FBQ2xDLFVBQUksY0FBYztBQUNoQixxQ0FBNEI7QUFDNUIsY0FBTSxXQUFXLENBQUMsR0FBRyxNQUFPLENBQUM7QUFDN0IsZUFBTyxZQUFZLFFBQVEsUUFBUSxHQUFHLEVBQUU7TUFDMUMsT0FBTztBQUNMLGVBQU8sWUFBWSxXQUFXLEdBQUcsQ0FBSSxHQUFHLElBQUksR0FBRyxRQUFRLENBQUMsQ0FBQztNQUMzRDtJQUNGO0FBQ0EsYUFBUyxlQUFlLE9BQWlCO0FBQ3ZDLGFBQU8sT0FBTyxRQUFXLE9BQU87QUFDaEMsWUFBTSxFQUFFLFdBQVcsTUFBTSx1QkFBdUIsT0FBTSxJQUFLO0FBQzNELFlBQU0sU0FBUyxNQUFNO0FBQ3JCLFlBQU0sT0FBTyxNQUFNLENBQUM7QUFDcEIsWUFBTSxPQUFPLE1BQU0sU0FBUyxDQUFDO0FBRTdCLFVBQUksV0FBVyxTQUFTLFNBQVMsS0FBUSxTQUFTLElBQU87QUFDdkQsY0FBTSxJQUFJLEdBQUcsVUFBVSxJQUFJO0FBQzNCLFlBQUksQ0FBQyxHQUFHLFFBQVEsQ0FBQztBQUFHLGdCQUFNLElBQUksTUFBTSxxQ0FBcUM7QUFDekUsY0FBTSxLQUFLLG9CQUFvQixDQUFDO0FBQ2hDLFlBQUk7QUFDSixZQUFJO0FBQ0YsY0FBSSxHQUFHLEtBQUssRUFBRTtRQUNoQixTQUFTLFdBQVc7QUFDbEIsZ0JBQU0sTUFBTSxxQkFBcUIsUUFBUSxPQUFPLFVBQVUsVUFBVTtBQUNwRSxnQkFBTSxJQUFJLE1BQU0sMkNBQTJDLEdBQUc7UUFDaEU7QUFDQSxxQ0FBNEI7QUFDNUIsY0FBTSxRQUFRLEdBQUcsTUFBTyxDQUFDO0FBQ3pCLGNBQU0sU0FBUyxPQUFPLE9BQU87QUFDN0IsWUFBSSxVQUFVO0FBQU8sY0FBSSxHQUFHLElBQUksQ0FBQztBQUNqQyxlQUFPLEVBQUUsR0FBRyxFQUFDO01BQ2YsV0FBVyxXQUFXLFVBQVUsU0FBUyxHQUFNO0FBRTdDLGNBQU0sSUFBSSxHQUFHO0FBQ2IsY0FBTSxJQUFJLEdBQUcsVUFBVSxLQUFLLFNBQVMsR0FBRyxDQUFDLENBQUM7QUFDMUMsY0FBTSxJQUFJLEdBQUcsVUFBVSxLQUFLLFNBQVMsR0FBRyxJQUFJLENBQUMsQ0FBQztBQUM5QyxZQUFJLENBQUMsVUFBVSxHQUFHLENBQUM7QUFBRyxnQkFBTSxJQUFJLE1BQU0sNEJBQTRCO0FBQ2xFLGVBQU8sRUFBRSxHQUFHLEVBQUM7TUFDZixPQUFPO0FBQ0wsY0FBTSxJQUFJLE1BQ1IseUJBQXlCLE1BQU0seUJBQXlCLElBQUksb0JBQW9CLE1BQU0sRUFBRTtNQUU1RjtJQUNGO0FBRUEsVUFBTSxjQUFjLFVBQVUsV0FBV0E7QUFDekMsVUFBTSxjQUFjLFVBQVUsYUFBYTtBQUMzQyxhQUFTLG9CQUFvQixHQUFJO0FBQy9CLFlBQU0sS0FBSyxHQUFHLElBQUksQ0FBQztBQUNuQixZQUFNLEtBQUssR0FBRyxJQUFJLElBQUksQ0FBQztBQUN2QixhQUFPLEdBQUcsSUFBSSxHQUFHLElBQUksSUFBSSxHQUFHLElBQUksR0FBRyxNQUFNLENBQUMsQ0FBQyxHQUFHLE1BQU0sQ0FBQztJQUN2RDtBQUlBLGFBQVMsVUFBVSxHQUFNLEdBQUk7QUFDM0IsWUFBTSxPQUFPLEdBQUcsSUFBSSxDQUFDO0FBQ3JCLFlBQU0sUUFBUSxvQkFBb0IsQ0FBQztBQUNuQyxhQUFPLEdBQUcsSUFBSSxNQUFNLEtBQUs7SUFDM0I7QUFJQSxRQUFJLENBQUMsVUFBVSxNQUFNLElBQUksTUFBTSxFQUFFO0FBQUcsWUFBTSxJQUFJLE1BQU0sbUNBQW1DO0FBSXZGLFVBQU0sT0FBTyxHQUFHLElBQUksR0FBRyxJQUFJLE1BQU0sR0FBR0YsSUFBRyxHQUFHQyxJQUFHO0FBQzdDLFVBQU0sUUFBUSxHQUFHLElBQUksR0FBRyxJQUFJLE1BQU0sQ0FBQyxHQUFHLE9BQU8sRUFBRSxDQUFDO0FBQ2hELFFBQUksR0FBRyxJQUFJLEdBQUcsSUFBSSxNQUFNLEtBQUssQ0FBQztBQUFHLFlBQU0sSUFBSSxNQUFNLDBCQUEwQjtBQUczRSxhQUFTLE9BQU8sT0FBZSxHQUFNLFVBQVUsT0FBSztBQUNsRCxVQUFJLENBQUMsR0FBRyxRQUFRLENBQUMsS0FBTSxXQUFXLEdBQUcsSUFBSSxDQUFDO0FBQUksY0FBTSxJQUFJLE1BQU0sd0JBQXdCLEtBQUssRUFBRTtBQUM3RixhQUFPO0lBQ1Q7QUFFQSxhQUFTLFVBQVUsT0FBYztBQUMvQixVQUFJLEVBQUUsaUJBQWlCO0FBQVEsY0FBTSxJQUFJLE1BQU0sNEJBQTRCO0lBQzdFO0FBRUEsYUFBUyxpQkFBaUIsR0FBUztBQUNqQyxVQUFJLENBQUMsUUFBUSxDQUFDLEtBQUs7QUFBUyxjQUFNLElBQUksTUFBTSxTQUFTO0FBQ3JELGFBQU8saUJBQWlCLEdBQUcsS0FBSyxTQUFTLEdBQUcsS0FBSztJQUNuRDtBQU9BLFVBQU0sZUFBZSxTQUFTLENBQUMsR0FBVSxPQUEwQjtBQUNqRSxZQUFNLEVBQUUsR0FBRyxHQUFHLEVBQUMsSUFBSztBQUVwQixVQUFJLEdBQUcsSUFBSSxHQUFHLEdBQUcsR0FBRztBQUFHLGVBQU8sRUFBRSxHQUFHLEdBQUcsR0FBRyxFQUFDO0FBQzFDLFlBQU0sTUFBTSxFQUFFLElBQUc7QUFHakIsVUFBSSxNQUFNO0FBQU0sYUFBSyxNQUFNLEdBQUcsTUFBTSxHQUFHLElBQUksQ0FBQztBQUM1QyxZQUFNLElBQUksR0FBRyxJQUFJLEdBQUcsRUFBRTtBQUN0QixZQUFNLElBQUksR0FBRyxJQUFJLEdBQUcsRUFBRTtBQUN0QixZQUFNLEtBQUssR0FBRyxJQUFJLEdBQUcsRUFBRTtBQUN2QixVQUFJO0FBQUssZUFBTyxFQUFFLEdBQUcsR0FBRyxNQUFNLEdBQUcsR0FBRyxLQUFJO0FBQ3hDLFVBQUksQ0FBQyxHQUFHLElBQUksSUFBSSxHQUFHLEdBQUc7QUFBRyxjQUFNLElBQUksTUFBTSxrQkFBa0I7QUFDM0QsYUFBTyxFQUFFLEdBQUcsRUFBQztJQUNmLENBQUM7QUFHRCxVQUFNLGtCQUFrQixTQUFTLENBQUMsTUFBWTtBQUM1QyxVQUFJLEVBQUUsSUFBRyxHQUFJO0FBSVgsWUFBSSxVQUFVLHNCQUFzQixDQUFDLEdBQUcsSUFBSSxFQUFFLENBQUM7QUFBRztBQUNsRCxjQUFNLElBQUksTUFBTSxpQkFBaUI7TUFDbkM7QUFFQSxZQUFNLEVBQUUsR0FBRyxFQUFDLElBQUssRUFBRSxTQUFRO0FBQzNCLFVBQUksQ0FBQyxHQUFHLFFBQVEsQ0FBQyxLQUFLLENBQUMsR0FBRyxRQUFRLENBQUM7QUFBRyxjQUFNLElBQUksTUFBTSxzQ0FBc0M7QUFDNUYsVUFBSSxDQUFDLFVBQVUsR0FBRyxDQUFDO0FBQUcsY0FBTSxJQUFJLE1BQU0sbUNBQW1DO0FBQ3pFLFVBQUksQ0FBQyxFQUFFLGNBQWE7QUFBSSxjQUFNLElBQUksTUFBTSx3Q0FBd0M7QUFDaEYsYUFBTztJQUNULENBQUM7QUFFRCxhQUFTLFdBQ1AsVUFDQSxLQUNBLEtBQ0EsT0FDQSxPQUFjO0FBRWQsWUFBTSxJQUFJLE1BQU0sR0FBRyxJQUFJLElBQUksR0FBRyxRQUFRLEdBQUcsSUFBSSxHQUFHLElBQUksQ0FBQztBQUNyRCxZQUFNLFNBQVMsT0FBTyxHQUFHO0FBQ3pCLFlBQU0sU0FBUyxPQUFPLEdBQUc7QUFDekIsYUFBTyxJQUFJLElBQUksR0FBRztJQUNwQjtJQU9BLE1BQU0sTUFBSzs7TUFFVCxPQUFnQixPQUFPLElBQUksTUFBTSxNQUFNLElBQUksTUFBTSxJQUFJLEdBQUcsR0FBRzs7TUFFM0QsT0FBZ0IsT0FBTyxJQUFJLE1BQU0sR0FBRyxNQUFNLEdBQUcsS0FBSyxHQUFHLElBQUk7OztNQUV6RCxPQUFnQixLQUFLOztNQUVyQixPQUFnQixLQUFLO01BRVo7TUFDQTtNQUNBOztNQUdULFlBQVksR0FBTSxHQUFNLEdBQUk7QUFDMUIsYUFBSyxJQUFJLE9BQU8sS0FBSyxDQUFDO0FBQ3RCLGFBQUssSUFBSSxPQUFPLEtBQUssR0FBRyxJQUFJO0FBQzVCLGFBQUssSUFBSSxPQUFPLEtBQUssQ0FBQztBQUN0QixlQUFPLE9BQU8sSUFBSTtNQUNwQjtNQUVBLE9BQU8sUUFBSztBQUNWLGVBQU87TUFDVDs7TUFHQSxPQUFPLFdBQVcsR0FBaUI7QUFDakMsY0FBTSxFQUFFLEdBQUcsRUFBQyxJQUFLLEtBQUssQ0FBQTtBQUN0QixZQUFJLENBQUMsS0FBSyxDQUFDLEdBQUcsUUFBUSxDQUFDLEtBQUssQ0FBQyxHQUFHLFFBQVEsQ0FBQztBQUFHLGdCQUFNLElBQUksTUFBTSxzQkFBc0I7QUFDbEYsWUFBSSxhQUFhO0FBQU8sZ0JBQU0sSUFBSSxNQUFNLDhCQUE4QjtBQUV0RSxZQUFJLEdBQUcsSUFBSSxDQUFDLEtBQUssR0FBRyxJQUFJLENBQUM7QUFBRyxpQkFBTyxNQUFNO0FBQ3pDLGVBQU8sSUFBSSxNQUFNLEdBQUcsR0FBRyxHQUFHLEdBQUc7TUFDL0I7TUFFQSxPQUFPLFVBQVUsT0FBaUI7QUFDaEMsY0FBTSxJQUFJLE1BQU0sV0FBVyxZQUFZLE9BQU8sT0FBTyxRQUFXLE9BQU8sQ0FBQyxDQUFDO0FBQ3pFLFVBQUUsZUFBYztBQUNoQixlQUFPO01BQ1Q7TUFFQSxPQUFPLFFBQVEsS0FBVztBQUN4QixlQUFPLE1BQU0sVUFBVSxXQUFXLEdBQUcsQ0FBQztNQUN4QztNQUVBLElBQUksSUFBQztBQUNILGVBQU8sS0FBSyxTQUFRLEVBQUc7TUFDekI7TUFDQSxJQUFJLElBQUM7QUFDSCxlQUFPLEtBQUssU0FBUSxFQUFHO01BQ3pCOzs7Ozs7O01BUUEsV0FBVyxhQUFxQixHQUFHLFNBQVMsTUFBSTtBQUM5QyxhQUFLLFlBQVksTUFBTSxVQUFVO0FBQ2pDLFlBQUksQ0FBQztBQUFRLGVBQUssU0FBU0QsSUFBRztBQUM5QixlQUFPO01BQ1Q7OztNQUlBLGlCQUFjO0FBQ1osd0JBQWdCLElBQUk7TUFDdEI7TUFFQSxXQUFRO0FBQ04sY0FBTSxFQUFFLEVBQUMsSUFBSyxLQUFLLFNBQVE7QUFDM0IsWUFBSSxDQUFDLEdBQUc7QUFBTyxnQkFBTSxJQUFJLE1BQU0sNkJBQTZCO0FBQzVELGVBQU8sQ0FBQyxHQUFHLE1BQU0sQ0FBQztNQUNwQjs7TUFHQSxPQUFPLE9BQVk7QUFDakIsa0JBQVUsS0FBSztBQUNmLGNBQU0sRUFBRSxHQUFHLElBQUksR0FBRyxJQUFJLEdBQUcsR0FBRSxJQUFLO0FBQ2hDLGNBQU0sRUFBRSxHQUFHLElBQUksR0FBRyxJQUFJLEdBQUcsR0FBRSxJQUFLO0FBQ2hDLGNBQU0sS0FBSyxHQUFHLElBQUksR0FBRyxJQUFJLElBQUksRUFBRSxHQUFHLEdBQUcsSUFBSSxJQUFJLEVBQUUsQ0FBQztBQUNoRCxjQUFNLEtBQUssR0FBRyxJQUFJLEdBQUcsSUFBSSxJQUFJLEVBQUUsR0FBRyxHQUFHLElBQUksSUFBSSxFQUFFLENBQUM7QUFDaEQsZUFBTyxNQUFNO01BQ2Y7O01BR0EsU0FBTTtBQUNKLGVBQU8sSUFBSSxNQUFNLEtBQUssR0FBRyxHQUFHLElBQUksS0FBSyxDQUFDLEdBQUcsS0FBSyxDQUFDO01BQ2pEOzs7OztNQU1BLFNBQU07QUFDSixjQUFNLEVBQUUsR0FBRyxFQUFDLElBQUs7QUFDakIsY0FBTSxLQUFLLEdBQUcsSUFBSSxHQUFHQSxJQUFHO0FBQ3hCLGNBQU0sRUFBRSxHQUFHLElBQUksR0FBRyxJQUFJLEdBQUcsR0FBRSxJQUFLO0FBQ2hDLFlBQUksS0FBSyxHQUFHLE1BQU0sS0FBSyxHQUFHLE1BQU0sS0FBSyxHQUFHO0FBQ3hDLFlBQUksS0FBSyxHQUFHLElBQUksSUFBSSxFQUFFO0FBQ3RCLFlBQUksS0FBSyxHQUFHLElBQUksSUFBSSxFQUFFO0FBQ3RCLFlBQUksS0FBSyxHQUFHLElBQUksSUFBSSxFQUFFO0FBQ3RCLFlBQUksS0FBSyxHQUFHLElBQUksSUFBSSxFQUFFO0FBQ3RCLGFBQUssR0FBRyxJQUFJLElBQUksRUFBRTtBQUNsQixhQUFLLEdBQUcsSUFBSSxJQUFJLEVBQUU7QUFDbEIsYUFBSyxHQUFHLElBQUksSUFBSSxFQUFFO0FBQ2xCLGFBQUssR0FBRyxJQUFJLEdBQUcsRUFBRTtBQUNqQixhQUFLLEdBQUcsSUFBSSxJQUFJLEVBQUU7QUFDbEIsYUFBSyxHQUFHLElBQUksSUFBSSxFQUFFO0FBQ2xCLGFBQUssR0FBRyxJQUFJLElBQUksRUFBRTtBQUNsQixhQUFLLEdBQUcsSUFBSSxJQUFJLEVBQUU7QUFDbEIsYUFBSyxHQUFHLElBQUksSUFBSSxFQUFFO0FBQ2xCLGFBQUssR0FBRyxJQUFJLElBQUksRUFBRTtBQUNsQixhQUFLLEdBQUcsSUFBSSxJQUFJLEVBQUU7QUFDbEIsYUFBSyxHQUFHLElBQUksR0FBRyxFQUFFO0FBQ2pCLGFBQUssR0FBRyxJQUFJLElBQUksRUFBRTtBQUNsQixhQUFLLEdBQUcsSUFBSSxHQUFHLEVBQUU7QUFDakIsYUFBSyxHQUFHLElBQUksSUFBSSxFQUFFO0FBQ2xCLGFBQUssR0FBRyxJQUFJLElBQUksRUFBRTtBQUNsQixhQUFLLEdBQUcsSUFBSSxJQUFJLEVBQUU7QUFDbEIsYUFBSyxHQUFHLElBQUksSUFBSSxFQUFFO0FBQ2xCLGFBQUssR0FBRyxJQUFJLElBQUksRUFBRTtBQUNsQixhQUFLLEdBQUcsSUFBSSxJQUFJLEVBQUU7QUFDbEIsYUFBSyxHQUFHLElBQUksSUFBSSxFQUFFO0FBQ2xCLGFBQUssR0FBRyxJQUFJLElBQUksRUFBRTtBQUNsQixhQUFLLEdBQUcsSUFBSSxJQUFJLEVBQUU7QUFDbEIsYUFBSyxHQUFHLElBQUksSUFBSSxFQUFFO0FBQ2xCLGFBQUssR0FBRyxJQUFJLElBQUksRUFBRTtBQUNsQixhQUFLLEdBQUcsSUFBSSxJQUFJLEVBQUU7QUFDbEIsYUFBSyxHQUFHLElBQUksSUFBSSxFQUFFO0FBQ2xCLGVBQU8sSUFBSSxNQUFNLElBQUksSUFBSSxFQUFFO01BQzdCOzs7OztNQU1BLElBQUksT0FBWTtBQUNkLGtCQUFVLEtBQUs7QUFDZixjQUFNLEVBQUUsR0FBRyxJQUFJLEdBQUcsSUFBSSxHQUFHLEdBQUUsSUFBSztBQUNoQyxjQUFNLEVBQUUsR0FBRyxJQUFJLEdBQUcsSUFBSSxHQUFHLEdBQUUsSUFBSztBQUNoQyxZQUFJLEtBQUssR0FBRyxNQUFNLEtBQUssR0FBRyxNQUFNLEtBQUssR0FBRztBQUN4QyxjQUFNLElBQUksTUFBTTtBQUNoQixjQUFNLEtBQUssR0FBRyxJQUFJLE1BQU0sR0FBR0EsSUFBRztBQUM5QixZQUFJLEtBQUssR0FBRyxJQUFJLElBQUksRUFBRTtBQUN0QixZQUFJLEtBQUssR0FBRyxJQUFJLElBQUksRUFBRTtBQUN0QixZQUFJLEtBQUssR0FBRyxJQUFJLElBQUksRUFBRTtBQUN0QixZQUFJLEtBQUssR0FBRyxJQUFJLElBQUksRUFBRTtBQUN0QixZQUFJLEtBQUssR0FBRyxJQUFJLElBQUksRUFBRTtBQUN0QixhQUFLLEdBQUcsSUFBSSxJQUFJLEVBQUU7QUFDbEIsYUFBSyxHQUFHLElBQUksSUFBSSxFQUFFO0FBQ2xCLGFBQUssR0FBRyxJQUFJLElBQUksRUFBRTtBQUNsQixhQUFLLEdBQUcsSUFBSSxJQUFJLEVBQUU7QUFDbEIsWUFBSSxLQUFLLEdBQUcsSUFBSSxJQUFJLEVBQUU7QUFDdEIsYUFBSyxHQUFHLElBQUksSUFBSSxFQUFFO0FBQ2xCLGFBQUssR0FBRyxJQUFJLElBQUksRUFBRTtBQUNsQixhQUFLLEdBQUcsSUFBSSxJQUFJLEVBQUU7QUFDbEIsYUFBSyxHQUFHLElBQUksSUFBSSxFQUFFO0FBQ2xCLGFBQUssR0FBRyxJQUFJLElBQUksRUFBRTtBQUNsQixhQUFLLEdBQUcsSUFBSSxJQUFJLEVBQUU7QUFDbEIsYUFBSyxHQUFHLElBQUksSUFBSSxFQUFFO0FBQ2xCLGFBQUssR0FBRyxJQUFJLElBQUksRUFBRTtBQUNsQixhQUFLLEdBQUcsSUFBSSxHQUFHLEVBQUU7QUFDakIsYUFBSyxHQUFHLElBQUksSUFBSSxFQUFFO0FBQ2xCLGFBQUssR0FBRyxJQUFJLElBQUksRUFBRTtBQUNsQixhQUFLLEdBQUcsSUFBSSxJQUFJLEVBQUU7QUFDbEIsYUFBSyxHQUFHLElBQUksSUFBSSxFQUFFO0FBQ2xCLGFBQUssR0FBRyxJQUFJLElBQUksRUFBRTtBQUNsQixhQUFLLEdBQUcsSUFBSSxJQUFJLEVBQUU7QUFDbEIsYUFBSyxHQUFHLElBQUksSUFBSSxFQUFFO0FBQ2xCLGFBQUssR0FBRyxJQUFJLEdBQUcsRUFBRTtBQUNqQixhQUFLLEdBQUcsSUFBSSxJQUFJLEVBQUU7QUFDbEIsYUFBSyxHQUFHLElBQUksSUFBSSxFQUFFO0FBQ2xCLGFBQUssR0FBRyxJQUFJLElBQUksRUFBRTtBQUNsQixhQUFLLEdBQUcsSUFBSSxHQUFHLEVBQUU7QUFDakIsYUFBSyxHQUFHLElBQUksSUFBSSxFQUFFO0FBQ2xCLGFBQUssR0FBRyxJQUFJLElBQUksRUFB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Q1AsUUFBRSxDQUFDLElBQUk7QUFDUCxRQUFFLENBQUMsSUFBSTtBQUNQLFFBQUUsQ0FBQyxJQUFJO0FBQ1AsUUFBRSxDQUFDLElBQUk7QUFDUCxRQUFFLENBQUMsSUFBSTtJQUNUO0lBRVEsV0FBUTtBQUNkLFlBQU0sRUFBRSxHQUFHLEtBQUFDLEtBQUcsSUFBSztBQUNuQixZQUFNLElBQUksSUFBSSxZQUFZLEVBQUU7QUFDNUIsVUFBSSxJQUFJLEVBQUUsQ0FBQyxNQUFNO0FBQ2pCLFFBQUUsQ0FBQyxLQUFLO0FBQ1IsZUFBUyxJQUFJLEdBQUcsSUFBSSxJQUFJLEtBQUs7QUFDM0IsVUFBRSxDQUFDLEtBQUs7QUFDUixZQUFJLEVBQUUsQ0FBQyxNQUFNO0FBQ2IsVUFBRSxDQUFDLEtBQUs7TUFDVjtBQUNBLFFBQUUsQ0FBQyxLQUFLLElBQUk7QUFDWixVQUFJLEVBQUUsQ0FBQyxNQUFNO0FBQ2IsUUFBRSxDQUFDLEtBQUs7QUFDUixRQUFFLENBQUMsS0FBSztBQUNSLFVBQUksRUFBRSxDQUFDLE1BQU07QUFDYixRQUFFLENBQUMsS0FBSztBQUNSLFFBQUUsQ0FBQyxLQUFLO0FBRVIsUUFBRSxDQUFDLElBQUksRUFBRSxDQUFDLElBQUk7QUFDZCxVQUFJLEVBQUUsQ0FBQyxNQUFNO0FBQ2IsUUFBRSxDQUFDLEtBQUs7QUFDUixlQUFTLElBQUksR0FBRyxJQUFJLElBQUksS0FBSztBQUMzQixVQUFFLENBQUMsSUFBSSxFQUFFLENBQUMsSUFBSTtBQUNkLFlBQUksRUFBRSxDQUFDLE1BQU07QUFDYixVQUFFLENBQUMsS0FBSztNQUNWO0FBQ0EsUUFBRSxDQUFDLEtBQUssS0FBSztBQUViLFVBQUksUUFBUSxJQUFJLEtBQUs7QUFDckIsZUFBUyxJQUFJLEdBQUcsSUFBSSxJQUFJO0FBQUssVUFBRSxDQUFDLEtBQUs7QUFDckMsYUFBTyxDQUFDO0FBQ1IsZUFBUyxJQUFJLEdBQUcsSUFBSSxJQUFJO0FBQUssVUFBRSxDQUFDLElBQUssRUFBRSxDQUFDLElBQUksT0FBUSxFQUFFLENBQUM7QUFDdkQsUUFB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O0FBQUcsWUFBTUMsTUFBSyxNQUFNLEtBQUssRUFBRTtBQUMvQyxZQUFPLE1BQU0sTUFBTztBQUFHLFlBQU1BLE1BQUssTUFBTSxLQUFLLEVBQUU7QUFDL0MsWUFBTyxNQUFNLE1BQU87QUFBRyxZQUFNQSxNQUFLLE1BQU0sS0FBSyxDQUFDO0FBQzlDLFlBQU8sTUFBTSxNQUFPO0FBQUcsWUFBTUEsTUFBSyxNQUFNLEtBQUssQ0FBQztBQUU5QyxZQUFPLE1BQU0sTUFBTztBQUFHLFlBQU1BLE1BQUssTUFBTSxLQUFLLEVBQUU7QUFDL0MsWUFBTyxNQUFNLE1BQU87QUFBRyxZQUFNQSxNQUFLLE1BQU0sS0FBSyxFQUFFO0FBQy9DLFlBQU8sTUFBTSxNQUFPO0FBQUcsWUFBTUEsTUFBSyxNQUFNLEtBQUssQ0FBQztBQUM5QyxZQUFPLE1BQU0sTUFBTztBQUFHLFlBQU1BLE1BQUssTUFBTSxLQUFLLENBQUM7QUFFOUMsWUFBTyxNQUFNLE1BQU87QUFBRyxZQUFNQSxNQUFLLE1BQU0sS0FBSyxFQUFFO0FBQy9DLFlBQU8sTUFBTSxNQUFPO0FBQUcsWUFBTUEsTUFBSyxNQUFNLEtBQUssRUFBRTtBQUMvQyxZQUFPLE1BQU0sTUFBTztBQUFHLFlBQU1BLE1BQUssTUFBTSxLQUFLLENBQUM7QUFDOUMsWUFBTyxNQUFNLE1BQU87QUFBRyxZQUFNQSxNQUFLLE1BQU0sS0FBSyxDQUFDO0FBRTlDLFlBQU8sTUFBTSxNQUFPO0FBQUcsWUFBTUEsTUFBSyxNQUFNLEtBQUssRUFBRTtBQUMvQyxZQUFPLE1BQU0sTUFBTztBQUFHLFlBQU1BLE1BQUssTUFBTSxLQUFLLEVBQUU7QUFDL0MsWUFBTyxNQUFNLE1BQU87QUFBRyxZQUFNQSxNQUFLLE1BQU0sS0FBSyxDQUFDO0FBQzlDLFlBQU8sTUFBTSxNQUFPO0FBQUcsWUFBTUEsTUFBSyxNQUFNLEtBQUssQ0FBQztBQUU5QyxZQUFPLE1BQU0sTUFBTztBQUFHLFlBQU1BLE1BQUssTUFBTSxLQUFLLEVBQUU7QUFDL0MsWUFBTyxNQUFNLE1BQU87QUFBRyxZQUFNQSxNQUFLLE1BQU0sS0FBSyxFQUFFO0FBQy9DLFlBQU8sTUFBTSxNQUFPO0FBQUcsWUFBTUEsTUFBSyxNQUFNLEtBQUssQ0FBQztBQUM5QyxZQUFPLE1BQU0sTUFBTztBQUFHLFlBQU1BLE1BQUssTUFBTSxLQUFLLENBQUM7QUFFOUMsWUFBTyxNQUFNLE1BQU87QUFBRyxZQUFNQSxNQUFLLE1BQU0sS0FBSyxFQUFFO0FBQy9DLFlBQU8sTUFBTSxNQUFPO0FBQUcsWUFBTUEsTUFBSyxNQUFNLEtBQUssRUFBRTtBQUMvQyxZQUFPLE1BQU0sTUFBTztBQUFHLFlBQU1BLE1BQUssTUFBTSxLQUFLLENBQUM7QUFDOUMsWUFBTyxNQUFNLE1BQU87QUFBRyxZQUFNQSxNQUFLLE1BQU0sS0FBSyxDQUFDO0FBRTlDLFlBQU8sTUFBTSxNQUFPO0FBQUcsWUFBTUEsTUFBSyxNQUFNLEtBQUssRUFBRTtBQUMvQyxZQUFPLE1BQU0sTUFBTztBQUFHLFlBQU1BLE1BQUssTUFBTSxLQUFLLEVBQUU7QUFDL0MsWUFBTyxNQUFNLE1BQU87QUFBRyxZQUFNQSxNQUFLLE1BQU0sS0FBSyxDQUFDO0FBQzlDLFlBQU8sTUFBTSxNQUFPO0FBQUcsWUFBTUEsTUFBSyxNQUFNLEtBQUssQ0FBQztBQUU5QyxZQUFPLE1BQU0sTUFBTztBQUFHLFlBQU1BLE1BQUssTUFBTSxLQUFLLEVBQUU7QUFDL0MsWUFBTyxNQUFNLE1BQU87QUFBRyxZQUFNQSxNQUFLLE1BQU0sS0FBSyxFQUFFO0FBQy9DLFlBQU8sTUFBTSxNQUFPO0FBQUcsWUFBTUEsTUFBSyxNQUFNLEtBQUssQ0FBQztBQUM5QyxZQUFPLE1BQU0sTUFBTztBQUFHLFlBQU1BLE1BQUssTUFBTSxLQUFLLENBQUM7SUFDaEQ7QUFFQSxRQUFJLEtBQUs7QUFDVCxRQUFJLElBQUksSUFBSyxNQUFNLE1BQU87QUFBRyxRQUFJLElBQUksSUFBSyxNQUFNLE1BQU87QUFDdkQsUUFBSSxJQUFJLElBQUssTUFBTSxNQUFPO0FBQUcsUUFBSSxJQUFJLElBQUssTUFBTSxNQUFPO0FBQ3ZELFFBQUksSUFBSSxJQUFLLE1BQU0sTUFBTztBQUFHLFFBQUksSUFBSSxJQUFLLE1BQU0sTUFBTztBQUN2RCxRQUFJLElBQUksSUFBSyxNQUFNLE1BQU87QUFBRyxRQUFJLElBQUksSUFBSyxNQUFNLE1BQU87QUFDdkQsUUFBSSxJQUFJLElBQUssTUFBTSxNQUFPO0FBQUcsUUFBSSxJQUFJLElBQUssTUFBTSxNQUFPO0FBQ3ZELFFBQUksSUFBSSxJQUFLLE1BQU0sTUFBTztBQUFHLFFBQUksSUFBSSxJQUFLLE1BQU0sTUFBTztBQUN2RCxRQUFJLElBQUksSUFBSyxNQUFNLE1BQU87QUFBRyxRQUFJLElBQUksSUFBSyxNQUFNLE1BQU87QUFDdkQsUUFBSSxJQUFJLElBQUssTUFBTSxNQUFPO0FBQUcsUUFBSSxJQUFJLElBQUssTUFBTSxNQUFPO0VBQ3pEO0FBT00sV0FBVSxRQUNkLEdBQWdCLEdBQWdCLEdBQWdCLEtBQWdCO0FBRWhFLFFBQUksTUFBTSxFQUFFLENBQUMsR0FBRyxNQUFNLEVBQUUsQ0FBQyxHQUFHLE1BQU0sRUFBRSxDQUFDLEdBQUcsTUFBTSxFQUFFLENBQUMsR0FDN0MsTUFBTSxFQUFFLENBQUMsR0FBRyxNQUFNLEVBQUUsQ0FBQyxHQUFHLE1BQU0sRUFBRSxDQUFDLEdBQUcsTUFBTSxFQUFFLENBQUMsR0FDN0MsTUFBTSxFQUFFLENBQUMsR0FBRyxNQUFNLEVBQUUsQ0FBQyxHQUFHLE1BQU0sRUFBRSxDQUFDLEdBQUcsTUFBTSxFQUFFLENBQUMsR0FDN0MsTUFBTSxFQUFFLENBQUMsR0FBRyxNQUFNLEVBQUUsQ0FBQyxHQUFHLE1BQU0sRUFBRSxDQUFDLEdBQUcsTUFBTSxFQUFFLENBQUM7QUFDakQsYUFBUyxJQUFJLEdBQUcsSUFBSSxJQUFJLEtBQUssR0FBRztBQUM5QixZQUFPLE1BQU0sTUFBTztBQUFHLFlBQU1BLE1BQUssTUFBTSxLQUFLLEVBQUU7QUFDL0MsWUFBTyxNQUFNLE1BQU87QUFBRyxZQUFNQSxNQUFLLE1BQU0sS0FBSyxFQUFFO0FBQy9DLFlBQU8sTUFBTSxNQUFPO0FBQUcsWUFBTUEsTUFBSyxNQUFNLEtBQUssQ0FBQztBQUM5QyxZQUFPLE1BQU0sTUFBTztBQUFHLFlBQU1BLE1BQUssTUFBTSxLQUFLLENBQUM7QUFFOUMsWUFBTyxNQUFNLE1BQU87QUFBRyxZQUFNQSxNQUFLLE1BQU0sS0FBSyxFQUFFO0FBQy9DLFlBQU8sTUFBTSxNQUFPO0FBQUcsWUFBTUEsTUFBSyxNQUFNLEtBQUssRUFBRTtBQUMvQyxZQUFPLE1BQU0sTUFBTztBQUFHLFlBQU1BLE1BQUssTUFBTSxLQUFLLENBQUM7QUFDOUMsWUFBTyxNQUFNLE1BQU87QUFBRyxZQUFNQSxNQUFLLE1BQU0sS0FBSyxDQUFDO0FBRTlDLFlBQU8sTUFBTSxNQUFPO0FBQUcsWUFBTUEsTUFBSyxNQUFNLEtBQUssRUFBRTtBQUMvQyxZQUFPLE1BQU0sTUFBTztBQUFHLFlBQU1BLE1BQUssTUFBTSxLQUFLLEVBQUU7QUFDL0MsWUFBTyxNQUFNLE1BQU87QUFBRyxZQUFNQSxNQUFLLE1BQU0sS0FBSyxDQUFDO0FBQzlDLFlBQU8sTUFBTSxNQUFPO0FBQUcsWUFBTUEsTUFBSyxNQUFNLEtBQUssQ0FBQztBQUU5QyxZQUFPLE1BQU0sTUFBTztBQUFHLFlBQU1BLE1BQUssTUFBTSxLQUFLLEVBQUU7QUFDL0MsWUFBTyxNQUFNLE1BQU87QUFBRyxZQUFNQSxNQUFLLE1BQU0sS0FBSyxFQUFFO0FBQy9DLFlBQU8sTUFBTSxNQUFPO0FBQUcsWUFBTUEsTUFBSyxNQUFNLEtBQUssQ0FBQztBQUM5QyxZQUFPLE1BQU0sTUFBTztBQUFHLFlBQU1BLE1BQUssTUFBTSxLQUFLLENBQUM7QUFFOUMsWUFBTyxNQUFNLE1BQU87QUFBRyxZQUFNQSxNQUFLLE1BQU0sS0FBSyxFQUFFO0FBQy9DLFlBQU8sTUFBTSxNQUFPO0FBQUcsWUFBTUEsTUFBSyxNQUFNLEtBQUssRUFBRTtBQUMvQyxZQUFPLE1BQU0sTUFBTztBQUFHLFlBQU1BLE1BQUssTUFBTSxLQUFLLENBQUM7QUFDOUMsWUFBTyxNQUFNLE1BQU87QUFBRyxZQUFNQSxNQUFLLE1BQU0sS0FB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LEtBQUssTUFBTSxNQUFNLEdBQUcsRUFBRTtBQUFHLGFBQU8sS0FBSyxNQUFNLE1BQU0sR0FBRyxFQUFFO0FBQzdELGFBQU8sS0FBSyxNQUFNLE1BQU0sR0FBSSxDQUFDO0FBQUcsYUFBTyxLQUFLLE1BQU0sTUFBTSxHQUFJLENBQUM7QUFDN0QsYUFBTyxLQUFLLE1BQU0sTUFBTSxHQUFHLEVBQUU7QUFBRyxhQUFPLEtBQUssTUFBTSxNQUFNLEdBQUcsRUFBRTtBQUM3RCxhQUFPLEtBQUssTUFBTSxNQUFNLEdBQUksQ0FBQztBQUFHLGFBQU8sS0FBSyxNQUFNLE1BQU0sR0FBSSxDQUFDO0FBQzdELGFBQU8sS0FBSyxNQUFNLE1BQU0sR0FBRyxFQUFFO0FBQUcsYUFBTyxLQUFLLE1BQU0sTUFBTSxHQUFHLEVBQUU7QUFDN0QsYUFBTyxLQUFLLE1BQU0sTUFBTSxHQUFJLENBQUM7QUFBRyxhQUFPLEtBQUssTUFBTSxNQUFNLEdBQUksQ0FBQztBQUM3RCxhQUFPLEtBQUssTUFBTSxNQUFNLEdBQUcsRUFBRTtBQUFHLGFBQU8sS0FBSyxNQUFNLE1BQU0sR0FBRyxFQUFFO0FBQzdELGFBQU8sS0FBSyxNQUFNLE1BQU0sR0FBSSxDQUFDO0FBQUcsYUFBTyxLQUFLLE1BQU0sTUFBTSxHQUFJLENBQUM7QUFDN0QsYUFBTyxLQUFLLE1BQU0sTUFBTSxHQUFHLEVBQUU7QUFBRyxhQUFPLEtBQUssTUFBTSxNQUFNLEdBQUcsRUFBRTtBQUM3RCxhQUFPLEtBQUssTUFBTSxNQUFNLEdBQUksQ0FBQztBQUFHLGFBQU8sS0FBSyxNQUFNLE1BQU0sR0FBSSxDQUFDO0FBQzdELGFBQU8sS0FBSyxNQUFNLE1BQU0sR0FBRyxFQUFFO0FBQUcsYUFBTyxLQUFLLE1BQU0sTUFBTSxHQUFHLEVBQUU7QUFDN0QsYUFBTyxLQUFLLE1BQU0sTUFBTSxHQUFJLENBQUM7QUFBRyxhQUFPLEtBQUssTUFBTSxNQUFNLEdBQUksQ0FBQztBQUM3RCxhQUFPLEtBQUssTUFBTSxNQUFNLEdBQUcsRUFBRTtBQUFHLGFBQU8sS0FBSyxNQUFNLE1BQU0sR0FBRyxFQUFFO0lBQy9EO0FBRUEsUUFBSSxJQUFJLElBQUssTUFBTSxNQUFPO0FBQUcsUUFBSSxJQUFJLElBQUssTUFBTSxNQUFPO0FBQ3ZELFFBQUksSUFBSSxJQUFLLE1BQU0sTUFBTztBQUFHLFFBQUksSUFBSSxJQUFLLE1BQU0sTUFBTztBQUN2RCxRQUFJLElBQUksSUFBSyxNQUFNLE1BQU87QUFBRyxRQUFJLElBQUksSUFBSyxNQUFNLE1BQU87QUFDdkQsUUFBSSxJQUFJLElBQUssTUFBTSxNQUFPO0FBQUcsUUFBSSxJQUFJLElBQUssTUFBTSxNQUFPO0FBQ3ZELFFBQUksSUFBSSxJQUFLLE1BQU0sTUFBTztBQUFHLFFBQUksSUFBSSxJQUFLLE1BQU0sTUFBTztBQUN2RCxRQUFJLElBQUksSUFBSyxNQUFNLE1BQU87QUFBRyxRQUFJLElBQUksSUFBSyxNQUFNLE1BQU87QUFDdkQsUUFBSSxJQUFJLElBQUssTUFBTSxNQUFPO0FBQUcsUUFBSSxJQUFJLElBQUssTUFBTSxNQUFPO0FBQ3ZELFFBQUksSUFBSSxJQUFLLE1BQU0sTUFBTztBQUFHLFFBQUksSUFBSSxJQUFLLE1BQU0sTUFBTztFQUN6RDtBQUVBLFdBQVMsU0FBUyxPQUFvQixJQUFZLEtBQWtCLElBQVksR0FBUztBQUV2RixRQUFJLE9BQU8sS0FBSztBQUNoQixRQUFJLE9BQU8sS0FBSyxLQUFLO0FBQ3JCLGFBQVMsSUFBSSxHQUFHLElBQUksSUFBSTtBQUFLLFVBQUksT0FBTyxDQUFDLElBQUksTUFBTSxNQUFNLElBQUksSUFBSSxLQUFLLEtBQUssQ0FBQztBQUM1RSxhQUFTLElBQUksR0FBRyxJQUFJLEdBQUcsS0FBSyxRQUFRLElBQUksTUFBTSxJQUFJO0FBRWhELGtCQUFZLEtBQUssTUFBTSxPQUFPLElBQUksS0FBSyxJQUFJO0FBQzNDLFVBQUksSUFBSTtBQUFHLGdCQUFRO0FBQ25CLGtCQUFZLEtBQUssTUFBTSxPQUFRLE1BQU0sSUFBSyxLQUFLLElBQUk7SUFDckQ7RUFDRjtBQXVCQSxXQUFTLFdBQVcsVUFBb0IsTUFBZ0IsT0FBa0I7QUFFeEUsVUFBTSxPQUFPLFVBQ1g7TUFDRSxPQUFPO01BQ1AsV0FBVztNQUNYLFFBQVEsUUFBUSxJQUFJO09BRXRCLEtBQUs7QUFFUCxVQUFNLEVBQUUsR0FBRyxHQUFHLEdBQUcsT0FBTyxXQUFXLFFBQVEsV0FBVSxJQUFLO0FBQzFELFlBQVEsR0FBRyxHQUFHO0FBQ2QsWUFBUSxHQUFHLEdBQUc7QUFDZCxZQUFRLEdBQUcsR0FBRztBQUNkLFlBQVEsT0FBTyxPQUFPO0FBQ3RCLFlBQVEsV0FBVyxXQUFXO0FBQzlCLFlBQVEsUUFBUSxRQUFRO0FBQ3hCLFFBQUksZUFBZSxVQUFhLE9BQU8sZUFBZTtBQUNwRCxZQUFNLElBQUksTUFBTSwrQkFBK0I7QUFDakQsVUFBTSxZQUFZLE1BQU07QUFDeEIsVUFBTSxjQUFjLFlBQVk7QUFPaEMsVUFBTSxRQUFRLEtBQUssSUFBSSxHQUFHLEVBQUU7QUFDNUIsUUFBSSxLQUFLLE1BQU0sSUFBSyxJQUFJLE9BQVEsS0FBSyxJQUFJO0FBQ3ZDLFlBQU0sSUFBSSxNQUFNLGlEQUFpRDtBQUNuRSxRQUFJLElBQUksS0FBSyxLQUFNLFFBQVEsS0FBSyxLQUFNO0FBQ3BDLFlBQU0sSUFBSSxNQUFNLHVEQUF1RDtBQUN6RSxRQUFJLFFBQVEsS0FBSyxTQUFTLFFBQVEsS0FBSztBQUNyQyxZQUFNLElBQUksTUFBTSw2Q0FBNkM7QUFDL0QsVUFBTSxVQUFVLGFBQWEsSUFBSTtBQUNqQyxRQUFJLFVBQVU7QUFDWixZQUFNLElBQUksTUFBTSw4REFBOEQsTUFBTTtBQUd0RixVQUFNLElBQUksT0FBTyxRQUFRLFVBQVUsTUFBTSxFQUFFLEdBQUcsR0FBRyxPQUFPLFlBQVksRUFBQyxDQUFFO0FBQ3ZFLFVBQU0sTUFBTSxJQUFJLENBQUM7QUFFakIsVUFBTSxJQUFJLElBQUksSUFBSSxXQUFXLFlBQVksQ0FBQyxDQUFDO0FBQzNDLFVBQU0sTUFBTSxJQUFJLElBQUksV0FBVyxTQUFTLENBQUM7QUFDekMsUUFBSSxhQUFhLE1BQUs7SUFBRTtBQUN4QixRQUFJLFlBQVk7QUFDZCxZQUFNLGdCQUFnQixJQUFJLElBQUk7QUFHOUIsWUFBTSxjQUFjLEtBQUssSUFBSSxLQUFLLE1BQU0sZ0JBQWdCLEdBQUssR0FBRyxDQUFDO0FBQ2pFLFVBQUksY0FBYztBQUNsQixtQkFBYSxNQUFLO0FBQ2hCO0FBQ0EsWUFBSSxlQUFlLEVBQUUsY0FBYyxnQkFBZ0IsZ0JBQWdCO0FBQ2pFLHFCQUFXLGNBQWMsYUFBYTtNQUMxQztJQUNGO0FBQ0EsV0FBTyxFQUFFLEdBQUcsR0FBRyxHQUFHLE9BQU8sYUFBYSxHQUFHLEtBQUssR0FBRyxLQUFLLFlBQVksVUFBUztFQUM3RTtBQUVBLFdBQVMsYUFDUCxVQUNBLE9BQ0EsR0FDQSxHQUNBLEtBQWdCO0FBRWhCLFVBQU0sTUFBTSxPQUFPLFFBQVEsVUFBVSxHQUFHLEVBQUUsR0FBRyxHQUFHLE1BQUssQ0FBRTtBQUN2RCxVQUFNLEdBQUcsR0FBRyxHQUFHO0FBQ2YsV0FBTztFQUNUO0FBT00sV0FBVSxPQUFPLFVBQW9CLE1BQWdCLE1BQWdCO0FBQ3pFLFVBQU0sRUFBRSxHQUFHLEdBQUcsR0FBRyxPQUFPLGFBQWEsR0FBRyxLQUFLLEdBQUcsS0FBSyxXQUFVLElBQUssV0FDbEUsVUFDQSxNQUNBLElBQUk7QUFFTixlQUFXLEdBQUc7QUFDZCxhQUFTLEtBQUssR0FBRyxLQUFLLEdBQUcsTUFBTTtBQUM3QixZQUFNLEtBQUssY0FBYztBQUN6QixlQUFTLElBQUksR0FBRyxJQUFJLGFBQWE7QUFBSyxVQUFFLENBQUMsSUFBSSxJQUFJLEtBQUssQ0FBQztBQUN2RCxlQUFTLElBQUksR0FBRyxNQUFNLEdBQUcsSUFBSSxJQUFJLEdBQUcsS0FBSztBQUN2QyxpQkFBUyxHQUFHLEtBQUssR0FBSSxPQUFPLGFBQWMsQ0FBQztBQUMzQyxtQkFBVTtNQUNaO0FBQ0EsZUFBUyxJQUFJLElBQUksS0FBSyxhQUFhLEtBQUssSUFBSSxDQUFDO0FBQzdDLGlCQUFVO0FBQ1YsZUFBUyxJQUFJLEdBQUcsSUFBSSxHQUFHLEtBQUs7QUFHMUIsY0FBTSxLQUFLLElBQUksS0FBSyxjQUFjLEVBQUUsSUFBSyxJQUFJLE9BQVE7QUFDckQsaUJBQVMsSUFBSSxHQUFHLElBQUksYUFBYTtBQUFLLGNBQUksQ0FBQyxJQUFJLElBQUksS0FBSyxDQUFDLElBQUksRUFBRSxJQUFJLGNBQWMsQ0FBQztBQUNsRixpQkFBUyxLQUFLLEdBQUcsS0FBSyxJQUFJLENBQUM7QUFDM0IsbUJBQVU7TUFDWjtJQUNGO0FBQ0EsZUFBVyxHQUFHO0FBQ2QsV0FBTyxhQUFhLFVBQVUsT0FBTyxHQUFHLEdBQUcsR0FBRztFQUNoRDs7O0FENUxNLFdBQVVDLFNBQ2QsS0FDQSxVQUNBLE9BQWUsSUFDZixNQUF1QixHQUFJO0FBRTNCLFVBQU0sT0FBTyxZQUFZLEVBQUU7QUFDM0IsVUFBTSxJQUFJLEtBQUs7QUFDZixVQUFNLHFCQUFxQixTQUFTLFVBQVUsTUFBTTtBQUNwRCxVQUFNLE1BQU0sT0FBTyxvQkFBb0IsTUFBTSxFQUFFLEdBQUcsR0FBRyxHQUFHLEdBQUcsR0FBRyxHQUFHLE9BQU8sR0FBRSxDQUFFO0FBQzVFLFVBQU0sUUFBUSxZQUFZLEVBQUU7QUFDNUIsVUFBTSxNQUFNLFdBQVcsS0FBSyxDQUFDLEdBQUcsQ0FBQztBQUNqQyxVQUFNLFNBQVMsa0JBQWtCLEtBQUssT0FBTyxHQUFHO0FBQ2hELFVBQU0sYUFBYSxPQUFPLFFBQVEsR0FBRztBQUVyQyxVQUFNLFVBQVUsWUFDZCxXQUFXLEtBQUssQ0FBQyxDQUFJLENBQUMsR0FDdEIsV0FBVyxLQUFLLENBQUMsSUFBSSxDQUFDLEdBQ3RCLE1BQ0EsT0FDQSxLQUNBLFVBQVU7QUFFWixVQUFNLFFBQVFDLFFBQVksUUFBUSxPQUFPO0FBQ3pDLFdBQU9BLFFBQVksT0FBTyxhQUFhLE9BQU8sR0FBRztFQUNuRDtBQVFNLFdBQVVDLFNBQVEsV0FBbUIsVUFBZ0I7QUFDekQsVUFBTSxFQUFFLFFBQVEsTUFBSyxJQUFLRCxRQUFZLE9BQU8sV0FBb0MsR0FBRztBQUNwRixRQUFJLFdBQVc7QUFBYSxZQUFNLElBQUksTUFBTSwwQkFBMEI7QUFDdEUsVUFBTSxPQUFPLElBQUksV0FBV0EsUUFBWSxVQUFVLEtBQUssQ0FBQztBQUN4RCxVQUFNLFVBQVUsS0FBSyxDQUFDO0FBQ3RCLFFBQUksWUFBWTtBQUFNLFlBQU0sSUFBSSxNQUFNLDhCQUE4QixPQUFPLEVBQUU7QUFDN0UsVUFBTSxPQUFPLEtBQUssQ0FBQztBQUNuQixVQUFNLE9BQU8sS0FBSyxTQUFTLEdBQUcsRUFBRTtBQUNoQyxVQUFNLFFBQVEsS0FBSyxTQUFTLElBQUksRUFBRTtBQUNsQyxVQUFNLE1BQU0sS0FBSyxFQUFFO0FBQ25CLFVBQU0sYUFBYSxLQUFLLFNBQVMsRUFBRTtBQUNuQyxVQUFNLElBQUksS0FBSztBQUNmLFVBQU0scUJBQXFCLFNBQVMsVUFBVSxNQUFNO0FBQ3BELFVBQU0sTUFBTSxPQUFPLG9CQUFvQixNQUFNLEVBQUUsR0FBRyxHQUFHLEdBQUcsR0FBRyxHQUFHLEdBQUcsT0FBTyxHQUFFLENBQUU7QUFDNUUsVUFBTSxNQUFNLFdBQVcsS0FBSyxDQUFDLEdBQUcsQ0FBQztBQUNqQyxVQUFNLFNBQVMsa0JBQWtCLEtBQUssT0FBTyxHQUFHO0FBQ2hELFdBQU8sT0FBTyxRQUFRLFVBQVU7RUFDbEM7OztBR3ZFQTtBQVNNLFdBQVVFLFlBQVcsS0FBVztBQUNsQyxVQUFNLFFBQVEsSUFBSSxXQUFXLElBQUksU0FBUyxDQUFDO0FBQzNDLGFBQVMsSUFBSSxHQUFHLElBQUksSUFBSSxRQUFRLEtBQUssR0FBRztBQUNwQyxZQUFNLElBQUksQ0FBQyxJQUFJLFNBQVMsSUFBSSxNQUFNLEdBQUcsSUFBSSxDQUFDLEdBQUcsRUFBRTtJQUNuRDtBQUNBLFdBQU87RUFDWDtBQU9NLFdBQVVDLFlBQVcsT0FBaUI7QUFDeEMsV0FBTyxNQUFNLEtBQUssS0FBSyxFQUNsQixJQUFJLE9BQUssRUFBRSxTQUFTLEVBQUUsRUFBRSxTQUFTLEdBQUcsR0FBRyxDQUFDLEVBQ3hDLEtBQUssRUFBRTtFQUNoQjs7O0FDMUJBOzs7QUNBQTtBQU9BLE1BQU0sYUFBYSxDQUFDQyxjQUFhQSxVQUFTLENBQUMsTUFBTTtBQUtqRCxXQUFTLEtBQUssS0FBSztBQUNmLFFBQUksT0FBTyxRQUFRO0FBQ2YsWUFBTSxJQUFJLFVBQVUsNEJBQTRCLE9BQU8sR0FBRztBQUM5RCxXQUFPLElBQUksVUFBVSxNQUFNO0FBQUEsRUFDL0I7QUFDQSxXQUFTLFVBQVUsS0FBSztBQUNwQixVQUFNLE9BQU8sS0FBSyxHQUFHO0FBQ3JCLFVBQU0sUUFBUSxLQUFLLE1BQU0sR0FBRztBQUM1QixRQUFJLENBQUMsQ0FBQyxJQUFJLElBQUksSUFBSSxJQUFJLEVBQUUsRUFBRSxTQUFTLE1BQU0sTUFBTTtBQUMzQyxZQUFNLElBQUksTUFBTSxrQkFBa0I7QUFDdEMsV0FBTyxFQUFFLE1BQU0sTUFBTSxNQUFNO0FBQUEsRUFDL0I7QUFDQSxXQUFTLFNBQVMsS0FBSztBQUNuQixXQUFPLEdBQUc7QUFDVixRQUFJLENBQUMsQ0FBQyxJQUFJLElBQUksSUFBSSxJQUFJLEVBQUUsRUFBRSxTQUFTLElBQUksTUFBTTtBQUN6QyxZQUFNLElBQUksTUFBTSx3QkFBd0I7QUFBQSxFQUNoRDtBQWVBLE1BQU0sZUFBZSxDQUFDLFlBQVk7QUFFOUIsVUFBTSxXQUFXLElBQUksUUFBUSxTQUFTO0FBR3RDLFdBQU8sSUFBSSxXQUFXLENBQUUsT0FBTyxPQUFPLEVBQUUsQ0FBQyxLQUFLLFlBQWEsUUFBUSxDQUFDO0FBQUEsRUFDeEU7QUFDQSxXQUFTLFNBQVNDLFdBQVU7QUFDeEIsUUFBSSxDQUFDLE1BQU0sUUFBUUEsU0FBUSxLQUFLQSxVQUFTLFdBQVcsUUFBUSxPQUFPQSxVQUFTLENBQUMsTUFBTTtBQUMvRSxZQUFNLElBQUksTUFBTSwwQ0FBMEM7QUFDOUQsSUFBQUEsVUFBUyxRQUFRLENBQUMsTUFBTTtBQUNwQixVQUFJLE9BQU8sTUFBTTtBQUNiLGNBQU0sSUFBSSxNQUFNLG1DQUFtQyxDQUFDO0FBQUEsSUFDNUQsQ0FBQztBQUNELFdBQU8sTUFBVSxNQUFNLE1BQVUsU0FBUyxHQUFHLFlBQVksR0FBRyxNQUFVLE9BQU8sSUFBSSxJQUFJLEdBQUcsTUFBVSxTQUFTQSxTQUFRLENBQUM7QUFBQSxFQUN4SDtBQWNPLFdBQVMsa0JBQWtCLFVBQVVBLFdBQVU7QUFDbEQsVUFBTSxFQUFFLE1BQU0sSUFBSSxVQUFVLFFBQVE7QUFDcEMsVUFBTSxVQUFVLFNBQVNBLFNBQVEsRUFBRSxPQUFPLEtBQUs7QUFDL0MsYUFBUyxPQUFPO0FBQ2hCLFdBQU87QUFBQSxFQUNYO0FBY08sV0FBUyxrQkFBa0IsU0FBU0EsV0FBVTtBQUNqRCxhQUFTLE9BQU87QUFDaEIsVUFBTSxRQUFRLFNBQVNBLFNBQVEsRUFBRSxPQUFPLE9BQU87QUFDL0MsV0FBTyxNQUFNLEtBQUssV0FBV0EsU0FBUSxJQUFJLFdBQVcsR0FBRztBQUFBLEVBQzNEO0FBSU8sV0FBUyxpQkFBaUIsVUFBVUEsV0FBVTtBQUNqRCxRQUFJO0FBQ0Esd0JBQWtCLFVBQVVBLFNBQVE7QUFBQSxJQUN4QyxTQUNPLEdBQUc7QUFDTixhQUFPO0FBQUEsSUFDWDtBQUNBLFdBQU87QUFBQSxFQUNYOzs7QUMzR0E7QUFBTyxNQUFNLFdBQVc7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUE7QUFBQSxLQSsvRG5CLE1BQU0sSUFBSTs7O0FGNytEUixXQUFTLGdCQUFnQixRQUFRO0FBQ3BDLFVBQU0sUUFBUUMsWUFBVyxNQUFNO0FBQy9CLFdBQU8sa0JBQWtCLE9BQU8sUUFB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QVEsV0FBVyxlQUFlO0FBRXhDLFFBQUksWUFBWSxXQUFXLEdBQUc7QUFDMUIsWUFBTSxJQUFJLE1BQU0sZ0NBQWdDO0FBQUEsSUFDcEQ7QUFFQSxRQUFJO0FBQ0EsWUFBTSxTQUFTLFdBQVc7QUFBQSxJQUM5QixVQUFFO0FBQ0UsaUJBQVcsU0FBUyxhQUFhO0FBQzdCLGNBQU0sTUFBTTtBQUFBLE1BQ2hCO0FBQUEsSUFDSjtBQUFBLEVBQ0o7IiwKICAibmFtZXMiOiBbInBpbm8iLCAibG9nZ2VyIiwgInRyYW5zbWl0IiwgImxldmVsIiwgInNldE9wdHMiLCAic2VsZiIsICJwYWQiLCAiZGVjb2RlIiwgImxlbiIsICJpIiwgIm51bSIsICJsZW4yIiwgImlzTEUiLCAiYmFzZTY0IiwgIkJ1ZmZlciIsICJ1dGY4VG9CeXRlcyIsICJiYXNlNjRUb0J5dGVzIiwgImkiLCAiYXNjaWlUb0J5dGVzIiwgImJ5dGVMZW5ndGgiLCAiYWxwaGFiZXQiLCAiTm9zdHJFdmVudEtpbmQiLCAiTm9zdHJNZXNzYWdlVHlwZSIsICJOaXA0Nk1ldGhvZCIsICJOb3N0ckV2ZW50S2luZCIsICJwYWQiLCAiaXNMRSIsICJudW0iLCAiXzBuIiwgIl8xbiIsICJfMG4iLCAiXzFuIiwgImdjZCIsICJudW0iLCAiXzBuIiwgIl8xbiIsICJfMW4iLCAiXzBuIiwgIl8xbiIsICJudW0iLCAiaXNMRSIsICJpc0xFIiwgIm51bSIsICJfMW4iLCAiXzBuIiwgIl8xbiIsICJ3aW5kb3ciLCAiXzBuIiwgIl8xbiIsICJ3aW5kb3ciLCAiaXNMRSIsICJfMG4iLCAiZ2V0UHVibGljS2V5IiwgInBhZCIsICJudW0iLCAiXzJuIiwgIl8wbiIsICJfMW4iLCAiXzNuIiwgIl80biIsICJwb2ludFRvQnl0ZXMiLCAiZW5kbyIsICJudW0iLCAiZ2V0UHVibGljS2V5IiwgInV0aWxzIiwgInJhbmRvbUJ5dGVzIiwgImhtYWMiLCAiXzJuIiwgIl8xbiIsICJyIiwgInMiLCAiXzBuIiwgIl8wbiIsICJfMm4iLCAiXzNuIiwgIkxvZ0xldmVsIiwgInBpbm8iLCAiYmFzZTY0IiwgImJhc2U2NCIsICJjcnlwdG8iLCAiZ2V0Q3J5cHRvIiwgImNyeXB0byIsICJpc0J5dGVzIiwgImFib29sIiwgImFudW1iZXIiLCAiYWJ5dGVzIiwgImFleGlzdHMiLCAiYW91dHB1dCIsICJ1MzIiLCAiY2xlYW4iLCAiY3JlYXRlVmlldyIsICJpc0xFIiwgImNoZWNrT3B0cyIsICJhYnl0ZXMiLCAiaXNMRSIsICJhYm9vbCIsICJudW0iLCAiY3JlYXRlVmlldyIsICJjb3B5Qnl0ZXMiLCAidTMyIiwgInJvdGwiLCAiaXNBbGlnbmVkMzIiLCAiY2hlY2tPcHRzIiwgImFudW1iZXIiLCAiYWJvb2wiLCAiYWJ5dGVzIiwgImNvcHlCeXRlcyIsICJjbGVhbiIsICJjb3B5Qnl0ZXMiLCAiYWJ5dGVzIiwgInBhZCIsICJjbGVhbiIsICJhZXhpc3RzIiwgImFvdXRwdXQiLCAicm90bCIsICJhYnl0ZXMiLCAiY2xlYW4iLCAiaXNCeXRlcyIsICJhYnl0ZXMiLCAiYW51bWJlciIsICJ3cmFwIiwgImRlY29kZSIsICJhbnVtYmVyIiwgInBhZGRpbmciLCAibnVtIiwgImlzQnl0ZXMiLCAiYWxwaGFiZXQiLCAiYWJ5dGVzIiwgImlzQnl0ZXMiLCAiZGVjb2RlIiwgImJlY2gzMiIsICJlbmNyeXB0IiwgImJlY2gzMiIsICJkZWNyeXB0IiwgImhleFRvQnl0ZXMiLCAiYnl0ZXNUb0hleCIsICJ3b3JkbGlzdCIsICJ3b3JkbGlzdCIsICJoZXhUb0J5dGVzIiwgImJ5dGVzVG9IZXgiLCAiZ2VuZXJhdGVLZXlQYWlyIiwgImJhc2U2NCIsICJlbmNyeXB0IiwgImRlY3J5cHQiLCAiZGVjcnlwdCIsICJlbmNyeXB0IiwgImNvbXBsZXRlIiwgInRhcmdldCIsICJzdG9yYWdlIiwgInN0b3JhZ2UiLCAiZ2VuZXJhdGVLZXlQYWlyIiwgImhleFRvQnl0ZXMiLCAiYnl0ZXNUb0hleCIsICJzZXNzaW9uIiwgImxvZyIsICJnZXRQcml2S2V5IiwgImJ5dGVzVG9IZXgiLCAic3RvcmFnZSIsICJsb2ciLCAiYnl0ZXNUb0hleCIsICJkZWNyeXB0IiwgImVuY3J5cHQiLCAiaGV4VG9CeXRlcyIsICJnZW5lcmF0ZUtleVBhaXIiXQp9Cg== diff --git a/distros/safari/background.js b/distros/safari/background.js index f62e006..f8aa568 100644 --- a/distros/safari/background.js +++ b/distros/safari/background.js @@ -128,6 +128,21 @@ const permissionRateMap = new Map(); // host → { count, resetAt } await storage.set({ isEncrypted: true }); data.isEncrypted = true; } + // Lockout recovery: if isEncrypted=true but there is NO password verifier AND + // no actually-encrypted key blobs, encryption is bogus (e.g. a stale flag + // received from an older buggy sync). Clearing it prevents a permanent lockout + // where the user can never unlock because checkPassword() always fails. + // We ONLY clear when no encrypted blobs exist — never when real ciphertext is + // present (that would corrupt encrypted keys into "plaintext"). + if (data.isEncrypted && !data.passwordHash) { + const { profiles = [] } = await storage.get({ profiles: [] }); + const hasEncryptedBlob = profiles.some(p => isEncryptedBlob(p.privKey)); + if (!hasEncryptedBlob) { + log('[STARTUP] Lockout recovery: isEncrypted=true with no passwordHash and no encrypted blobs → clearing bogus encryption flag'); + await storage.set({ isEncrypted: false }); + data.isEncrypted = false; + } + } encryptionEnabled = data.isEncrypted; nostrAccessWhileLocked = !!data.nostrAccessWhileLocked; blockCrossOriginFrames = data.blockCrossOriginFrames !== false; @@ -359,6 +374,11 @@ const SENSITIVE_KINDS = new Set([ 'setPassword', 'changePassword', 'removePassword', 'resetAllData', 'setAutoLockTimeout', 'setNostrAccessWhileLocked', 'setBlockCrossOriginFrames', 'backup.export', 'backup.import', 'unlock', + // Starting/stopping the NIP-46 bunker exposes the user's key for remote + // signing and returns the secret-bearing connection string. It must be a + // deliberate in-extension action — never triggerable by a web page via + // window.nostr.nip46.startBunker(). + 'bunkerServer.start', 'bunkerServer.stop', ]); function isExtensionSender(sender) { @@ -419,7 +439,20 @@ api.runtime.onMessage.addListener((message, _sender, sendResponse) => { return true; // Keep message channel open for async sendResponse case 'savePrivateKey': resetAutoLock(); - return savePrivateKey(message.payload); + // Must use sendResponse + return true (not a Promise return): Chrome MV3 + // does not deliver Promise-return values to sendMessage callers, so the + // caller could not tell whether the key was actually saved (or whether it + // threw). That made imported keys silently fail while the UI showed success. + (async () => { + try { + await savePrivateKey(message.payload); + sendResponse({ success: true }); + } catch (e) { + console.error('savePrivateKey error:', e); + sendResponse({ success: false, error: e.message || 'Failed to save key' }); + } + })(); + return true; case 'getNpub': (async () => { try { @@ -1118,8 +1151,13 @@ api.runtime.onMessage.addListener((message, _sender, sendResponse) => { // --- Encrypted vault backup / restore --- case 'backup.export': reply(sendResponse, async () => { - if (!sessionCryptoKey) { - return { success: false, error: 'Extension must be unlocked to create a backup' }; + // Backups are encrypted with a dedicated backup password supplied at + // export time — NOT the in-memory session key. This lets users with no + // master password create backups, and works even while locked (the + // stored key blobs stay encrypted and get wrapped again here). + const password = message.payload?.password; + if (typeof password !== 'string' || password.length < 8) { + return { success: false, error: 'A backup password of at least 8 characters is required' }; } const data = await storage.get({ profiles: [], @@ -1135,7 +1173,7 @@ api.runtime.onMessage.addListener((message, _sender, sendResponse) => { version: null, }); const plaintext = JSON.stringify(data); - const encrypted = await encryptWithKey(plaintext, sessionCryptoKey, sessionKeySalt); + const encrypted = await encryptBlob(plaintext, password); const version = api.runtime.getManifest?.()?.version || 'unknown'; return { success: true, @@ -1568,9 +1606,16 @@ async function savePrivateKey([index, privKey]) { const pubKey = getPublicKeySync(hexKey); profiles[index].pubKey = pubKey; - // If encryption is active, re-encrypt the new key using the session key + // If encryption is active, re-encrypt the new key using the session key. const encrypted = await isEncrypted(); - if (encrypted && sessionCryptoKey) { + if (encrypted) { + // Encryption is on but there's no live session key (locked, or the MV3 + // worker was evicted and lost it). Refuse rather than fall through and + // persist the key as PLAINTEXT into a vault the user believes is + // encrypted. The caller surfaces this as a save error. + if (!sessionCryptoKey) { + throw new Error('Extension is locked — unlock before saving a key'); + } profiles[index].privKey = await encryptWithKey(hexKey, sessionCryptoKey, sessionKeySalt); sessionKeys.set(index, hexKey); } else { @@ -1629,7 +1674,19 @@ async function getPlaintextPrivKey(index, profile) { if (isEncryptedBlob(profile.privKey)) { // Key is encrypted — must use session cache if (sessionKeys.has(index)) { - return sessionKeys.get(index); + const cached = sessionKeys.get(index); + // Guard against a stale cache entry. sessionKeys is keyed by profile + // index, but deleting a profile shifts every later index down by one + // without updating this in-memory map — so sessionKeys.get(index) + // could be a DIFFERENT identity's key. Verify the cached key actually + // derives to this profile's pubkey before returning it; otherwise we + // would sign with the wrong key. If the profile has no cached pubkey + // we can't validate, so fall back to the legacy behaviour. + if (!profile.pubKey || getPublicKeySync(cached) === profile.pubKey) { + return cached; + } + // Stale entry — drop it and treat this profile as locked. + sessionKeys.delete(index); } throw new Error('Extension is locked — cannot access private key'); } diff --git a/distros/safari/content.build.js b/distros/safari/content.build.js index 1a2824e..c4672f6 100644 --- a/distros/safari/content.build.js +++ b/distros/safari/content.build.js @@ -1,4 +1,233 @@ -(()=>{var t=typeof browser<"u"?browser:typeof chrome<"u"?chrome:null;if(!t)throw new Error("browser-polyfill: No extension API namespace found (neither browser nor chrome).");var r=typeof browser>"u"&&typeof chrome<"u";function s(e,n){return(...o)=>{try{let i=n.apply(e,o);if(i&&typeof i.then=="function")return i}catch{}return new Promise((i,c)=>{n.apply(e,[...o,(...u)=>{t.runtime&&t.runtime.lastError?c(new Error(t.runtime.lastError.message)):i(u.length<=1?u[0]:u)}])})}}var a={};a.runtime={sendMessage(...e){return r?s(t.runtime,t.runtime.sendMessage)(...e):t.runtime.sendMessage(...e)},onMessage:t.runtime.onMessage,getURL(e){return t.runtime.getURL(e)},openOptionsPage(){return r?s(t.runtime,t.runtime.openOptionsPage)():t.runtime.openOptionsPage()},get id(){return t.runtime.id}};a.storage={local:{get(...e){return r?s(t.storage.local,t.storage.local.get)(...e):t.storage.local.get(...e)},set(...e){return r?s(t.storage.local,t.storage.local.set)(...e):t.storage.local.set(...e)},clear(...e){return r?s(t.storage.local,t.storage.local.clear)(...e):t.storage.local.clear(...e)},remove(...e){return r?s(t.storage.local,t.storage.local.remove)(...e):t.storage.local.remove(...e)}},sync:t.storage?.sync?{get(...e){return r?s(t.storage.sync,t.storage.sync.get)(...e):t.storage.sync.get(...e)},set(...e){return r?s(t.storage.sync,t.storage.sync.set)(...e):t.storage.sync.set(...e)},remove(...e){return r?s(t.storage.sync,t.storage.sync.remove)(...e):t.storage.sync.remove(...e)},clear(...e){return r?s(t.storage.sync,t.storage.sync.clear)(...e):t.storage.sync.clear(...e)},getBytesInUse(...e){return t.storage.sync.getBytesInUse?r?s(t.storage.sync,t.storage.sync.getBytesInUse)(...e):t.storage.sync.getBytesInUse(...e):Promise.resolve(0)}}:null,onChanged:t.storage?.onChanged||null};a.tabs={create(...e){return r?s(t.tabs,t.tabs.create)(...e):t.tabs.create(...e)},query(...e){return r?s(t.tabs,t.tabs.query)(...e):t.tabs.query(...e)},remove(...e){return r?s(t.tabs,t.tabs.remove)(...e):t.tabs.remove(...e)},update(...e){return r?s(t.tabs,t.tabs.update)(...e):t.tabs.update(...e)},get(...e){return r?s(t.tabs,t.tabs.get)(...e):t.tabs.get(...e)},getCurrent(...e){return r?s(t.tabs,t.tabs.getCurrent)(...e):t.tabs.getCurrent(...e)},sendMessage(...e){return r?s(t.tabs,t.tabs.sendMessage)(...e):t.tabs.sendMessage(...e)}};a.alarms=t.alarms?{create(...e){let n=t.alarms.create(...e);return n&&typeof n.then=="function"?n:Promise.resolve()},clear(...e){return r?s(t.alarms,t.alarms.clear)(...e):t.alarms.clear(...e)},onAlarm:t.alarms.onAlarm}:null;async function b(){if(window===window.top)return!0;try{if(!(await a.storage.local.get({blockCrossOriginFrames:!0})).blockCrossOriginFrames)return!0}catch{return!1}try{return window.top.location.href,!0}catch{return!1}}b().then(e=>{if(!e)return;let n=document.createElement("script");n.setAttribute("src",a.runtime.getURL("nostr.build.js")),document.body.appendChild(n),document.addEventListener("visibilitychange",()=>{document.visibilityState==="visible"&&a.runtime.sendMessage({kind:"resetAutoLock"}).catch(()=>{})})});var d=null,m=null;function g(){if(d)return;let e=document.createElement("div");e.id="nostrkey-permission-sheet",e.innerHTML=` +(() => { + // src/utilities/browser-polyfill.js + var _browser = typeof browser !== "undefined" ? browser : typeof chrome !== "undefined" ? chrome : null; + if (!_browser) { + throw new Error("browser-polyfill: No extension API namespace found (neither browser nor chrome)."); + } + var isChrome = typeof browser === "undefined" && typeof chrome !== "undefined"; + function promisify(context, method) { + return (...args) => { + try { + const result = method.apply(context, args); + if (result && typeof result.then === "function") { + return result; + } + } catch (_) { + } + return new Promise((resolve, reject) => { + method.apply(context, [ + ...args, + (...cbArgs) => { + if (_browser.runtime && _browser.runtime.lastError) { + reject(new Error(_browser.runtime.lastError.message)); + } else { + resolve(cbArgs.length <= 1 ? cbArgs[0] : cbArgs); + } + } + ]); + }); + }; + } + var api = {}; + api.runtime = { + /** + * sendMessage – always returns a Promise. + */ + sendMessage(...args) { + if (!isChrome) { + return _browser.runtime.sendMessage(...args); + } + return promisify(_browser.runtime, _browser.runtime.sendMessage)(...args); + }, + /** + * onMessage – thin wrapper so callers use a consistent reference. + * The listener signature is (message, sender, sendResponse). + * On Chrome the listener can return `true` to keep the channel open, + * or return a Promise (MV3). Safari / Firefox expect a Promise return. + */ + onMessage: _browser.runtime.onMessage, + /** + * getURL – synchronous on all browsers. + */ + getURL(path) { + return _browser.runtime.getURL(path); + }, + /** + * openOptionsPage + */ + openOptionsPage() { + if (!isChrome) { + return _browser.runtime.openOptionsPage(); + } + return promisify(_browser.runtime, _browser.runtime.openOptionsPage)(); + }, + /** + * Expose the id for convenience. + */ + get id() { + return _browser.runtime.id; + } + }; + api.storage = { + local: { + get(...args) { + if (!isChrome) { + return _browser.storage.local.get(...args); + } + return promisify(_browser.storage.local, _browser.storage.local.get)(...args); + }, + set(...args) { + if (!isChrome) { + return _browser.storage.local.set(...args); + } + return promisify(_browser.storage.local, _browser.storage.local.set)(...args); + }, + clear(...args) { + if (!isChrome) { + return _browser.storage.local.clear(...args); + } + return promisify(_browser.storage.local, _browser.storage.local.clear)(...args); + }, + remove(...args) { + if (!isChrome) { + return _browser.storage.local.remove(...args); + } + return promisify(_browser.storage.local, _browser.storage.local.remove)(...args); + } + }, + // --- storage.sync ---------------------------------------------------------- + // Null when the browser doesn't support sync (older Safari, etc.) + sync: _browser.storage?.sync ? { + get(...args) { + if (!isChrome) { + return _browser.storage.sync.get(...args); + } + return promisify(_browser.storage.sync, _browser.storage.sync.get)(...args); + }, + set(...args) { + if (!isChrome) { + return _browser.storage.sync.set(...args); + } + return promisify(_browser.storage.sync, _browser.storage.sync.set)(...args); + }, + remove(...args) { + if (!isChrome) { + return _browser.storage.sync.remove(...args); + } + return promisify(_browser.storage.sync, _browser.storage.sync.remove)(...args); + }, + clear(...args) { + if (!isChrome) { + return _browser.storage.sync.clear(...args); + } + return promisify(_browser.storage.sync, _browser.storage.sync.clear)(...args); + }, + getBytesInUse(...args) { + if (!_browser.storage.sync.getBytesInUse) { + return Promise.resolve(0); + } + if (!isChrome) { + return _browser.storage.sync.getBytesInUse(...args); + } + return promisify(_browser.storage.sync, _browser.storage.sync.getBytesInUse)(...args); + } + } : null, + // --- storage.onChanged ----------------------------------------------------- + onChanged: _browser.storage?.onChanged || null + }; + api.tabs = { + create(...args) { + if (!isChrome) { + return _browser.tabs.create(...args); + } + return promisify(_browser.tabs, _browser.tabs.create)(...args); + }, + query(...args) { + if (!isChrome) { + return _browser.tabs.query(...args); + } + return promisify(_browser.tabs, _browser.tabs.query)(...args); + }, + remove(...args) { + if (!isChrome) { + return _browser.tabs.remove(...args); + } + return promisify(_browser.tabs, _browser.tabs.remove)(...args); + }, + update(...args) { + if (!isChrome) { + return _browser.tabs.update(...args); + } + return promisify(_browser.tabs, _browser.tabs.update)(...args); + }, + get(...args) { + if (!isChrome) { + return _browser.tabs.get(...args); + } + return promisify(_browser.tabs, _browser.tabs.get)(...args); + }, + getCurrent(...args) { + if (!isChrome) { + return _browser.tabs.getCurrent(...args); + } + return promisify(_browser.tabs, _browser.tabs.getCurrent)(...args); + }, + sendMessage(...args) { + if (!isChrome) { + return _browser.tabs.sendMessage(...args); + } + return promisify(_browser.tabs, _browser.tabs.sendMessage)(...args); + } + }; + api.alarms = _browser.alarms ? { + create(...args) { + const result = _browser.alarms.create(...args); + return result && typeof result.then === "function" ? result : Promise.resolve(); + }, + clear(...args) { + if (!isChrome) { + return _browser.alarms.clear(...args); + } + return promisify(_browser.alarms, _browser.alarms.clear)(...args); + }, + onAlarm: _browser.alarms.onAlarm + } : null; + + // src/content.js + async function shouldInject() { + if (window === window.top) return true; + try { + const data = await api.storage.local.get({ blockCrossOriginFrames: true }); + if (!data.blockCrossOriginFrames) return true; + } catch { + return false; + } + try { + void window.top.location.href; + return true; + } catch { + return false; + } + } + shouldInject().then((inject) => { + if (!inject) return; + let script = document.createElement("script"); + script.setAttribute("src", api.runtime.getURL("nostr.build.js")); + document.body.appendChild(script); + document.addEventListener("visibilitychange", () => { + if (document.visibilityState === "visible") { + api.runtime.sendMessage({ kind: "resetAutoLock" }).catch(() => { + }); + } + }); + }); + var permissionSheet = null; + var permissionResolve = null; + function createPermissionSheet() { + if (permissionSheet) return; + const sheet = document.createElement("div"); + sheet.id = "nostrkey-permission-sheet"; + sheet.innerHTML = `